Commit 22406f07 authored by 罗超's avatar 罗超

新增模板上传自动生成缩略图

parent 8b14a5fc
...@@ -6,15 +6,20 @@ page { ...@@ -6,15 +6,20 @@ page {
Segoe UI, Arial, Roboto, 'PingFang SC', 'miui', 'Hiragino Sans GB', 'Microsoft Yahei', Segoe UI, Arial, Roboto, 'PingFang SC', 'miui', 'Hiragino Sans GB', 'Microsoft Yahei',
sans-serif; sans-serif;
} }
/* .0123456789+-ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz导入设计文件基础数据绑定 */
/* .0123456789+-ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz导入设计文件基础数据绑定模板预览选择、上传图片 */
@font-face { @font-face {
font-family: "alifont";src: url("//at.alicdn.com/wf/webfont/MQHUV6e56ce5/WSdQY8NXp7aI.woff2") format("woff2"), font-family: "alifont";
url("//at.alicdn.com/wf/webfont/MQHUV6e56ce5/cW4aPGiVFgIJ.woff") format("woff"); src: url("//at.alicdn.com/wf/webfont/MQHUV6e56ce5/hnLMgZN9aCoO.woff2") format("woff2"),
url("//at.alicdn.com/wf/webfont/MQHUV6e56ce5/KFZWXS7eHHXx.woff") format("woff");
font-display: swap; font-display: swap;
} }
.alifont{ .alifont{
font-family: alifont,chineseAlifont; font-family: alifont,chineseAlifont;
} }
.small-padding .el-dialog__body{
padding:10px !important;
}
.adobeFont{ .adobeFont{
font-family: adobeFont; font-family: adobeFont;
} }
......
...@@ -80,7 +80,7 @@ import {getFonts, toSlider, toThumbnails} from '@/utils/psdParser/index' ...@@ -80,7 +80,7 @@ import {getFonts, toSlider, toThumbnails} from '@/utils/psdParser/index'
import { useSlidesStore } from '@/store' import { useSlidesStore } from '@/store'
import { ElMessage, ElMessageBox } from 'element-plus' import { ElMessage, ElMessageBox } from 'element-plus'
import AliyunUpload from '@/utils/upload/aliyun' import AliyunUpload from '@/utils/upload/aliyun'
import { useFontStore } from '@/store' import { useFontStore,useScreenStore } from '@/store'
import { CustomerFonts } from '@/store/font' import { CustomerFonts } from '@/store/font'
const props = defineProps({ const props = defineProps({
...@@ -181,9 +181,14 @@ const resolveToSliderHandler = async()=>{ ...@@ -181,9 +181,14 @@ const resolveToSliderHandler = async()=>{
}) })
}else{ }else{
await useFontStore().loadAllFonts() await useFontStore().loadAllFonts()
useSlidesStore().setSlides(sliders.value) const slidesStore = useSlidesStore()
useSlidesStore().setLayouts(sliders.value) const screenSotre = useScreenStore()
useSlidesStore().updateSlideIndex(0) slidesStore.setSlides(sliders.value)
slidesStore.setLayouts(sliders.value)
slidesStore.setThumbnails(thumbnails.value)
slidesStore.updateSlideIndex(0)
screenSotre.isCoverImg = false
screenSotre.CoverImg = thumbnails.value[0]
close() close()
} }
} }
......
...@@ -29,7 +29,8 @@ export interface SlidesState { ...@@ -29,7 +29,8 @@ export interface SlidesState {
slides: Slide[] slides: Slide[]
slideIndex: number slideIndex: number
viewportRatio: number viewportRatio: number
layoutSlides: Slide[] layoutSlides: Slide[],
thumbnails:string[]
} }
export const useSlidesStore = defineStore('slides', { export const useSlidesStore = defineStore('slides', {
...@@ -48,13 +49,16 @@ export const useSlidesStore = defineStore('slides', { ...@@ -48,13 +49,16 @@ export const useSlidesStore = defineStore('slides', {
slideIndex: 0, // 当前页面索引 slideIndex: 0, // 当前页面索引
viewportRatio: 0.7069, // 可视区域比例,默认16:9 0.5625 viewportRatio: 0.7069, // 可视区域比例,默认16:9 0.5625
layoutSlides: [], // 所有模版数据 layoutSlides: [], // 所有模版数据
thumbnails:[]
}), }),
getters: { getters: {
currentSlide(state) { currentSlide(state) {
return state.slides[state.slideIndex] return state.slides[state.slideIndex]
}, },
getThumbnails(state){
return state.thumbnails
},
currentSlideAnimations(state) { currentSlideAnimations(state) {
const currentSlide = state.slides[state.slideIndex] const currentSlide = state.slides[state.slideIndex]
if (!currentSlide?.animations) return [] if (!currentSlide?.animations) return []
...@@ -135,9 +139,12 @@ export const useSlidesStore = defineStore('slides', { ...@@ -135,9 +139,12 @@ export const useSlidesStore = defineStore('slides', {
setSlides(slides: Slide[]) { setSlides(slides: Slide[]) {
this.slides = slides this.slides = slides
this.thumbnails = []
this.setFonts(slides) this.setFonts(slides)
}, },
setThumbnails(thumbs:string[]){
this.thumbnails = thumbs
},
setFonts(slides: Slide[]){ setFonts(slides: Slide[]){
let iFonts:string[] = [] let iFonts:string[] = []
var regex = /(?<=font-family:\s*).*?(?=;)/g var regex = /(?<=font-family:\s*).*?(?=;)/g
......
...@@ -18,7 +18,7 @@ export const ResolveThumbHandler = async (psd:any)=>{ ...@@ -18,7 +18,7 @@ export const ResolveThumbHandler = async (psd:any)=>{
const item = _children[i]; const item = _children[i];
if(item.layer.artboard) { if(item.layer.artboard) {
let cropImagePath = await cropImage(imgBase64String,"image/jpeg",item.layer.artboard().export().coords) let cropImagePath = await cropImage(imgBase64String,"image/jpeg",item.layer.artboard().export().coords)
let imagePath = await compressionThumbnail(cropImagePath,"image/jpeg",300) let imagePath = await compressionThumbnail(cropImagePath,"image/jpeg",600)
imgs.push(imagePath) imgs.push(imagePath)
} }
} }
......
...@@ -196,6 +196,8 @@ const FeatureImgStore = useScreenStore() ...@@ -196,6 +196,8 @@ const FeatureImgStore = useScreenStore()
const ConfigIdStore = useScreenStore() const ConfigIdStore = useScreenStore()
const FeatureImgRef = ref(null) const FeatureImgRef = ref(null)
const FeatureImgList = ref(null) const FeatureImgList = ref(null)
const loadingInstance = ref<any>(null)
const thumbnails = ref<string[]>()
const { exportFeatureImg } = useExport() const { exportFeatureImg } = useExport()
...@@ -235,6 +237,7 @@ const goBack = () =>{ ...@@ -235,6 +237,7 @@ const goBack = () =>{
searchData.value.TempId = 0 searchData.value.TempId = 0
marketStore.setMarket(true) marketStore.setMarket(true)
slidesStore.setSlides(list) slidesStore.setSlides(list)
slidesStore.setThumbnails([])
layoutsStore.setLayouts([]) layoutsStore.setLayouts([])
CoverImgStore.setCoverImg(null) CoverImgStore.setCoverImg(null)
}).catch(() => {}) }).catch(() => {})
...@@ -275,7 +278,7 @@ const SetTripTemplateSlide = async () => { ...@@ -275,7 +278,7 @@ const SetTripTemplateSlide = async () => {
const uploadImageHandler = async ()=>{ const uploadImageHandler = async ()=>{
let count = 0 let count = 0
let index = 0 let index = 0
const instance = ElLoading.service({ loadingInstance.value = ElLoading.service({
text:'收集需要处理的图片' text:'收集需要处理的图片'
}) })
for (let i = 0; i < slides.value.length; i++) { for (let i = 0; i < slides.value.length; i++) {
...@@ -292,7 +295,7 @@ const uploadImageHandler = async ()=>{ ...@@ -292,7 +295,7 @@ const uploadImageHandler = async ()=>{
let temp = slide.elements.filter(x => "src" in x && x.src.startsWith("data:image")) ?? [] let temp = slide.elements.filter(x => "src" in x && x.src.startsWith("data:image")) ?? []
for(let j = 0; j < temp.length; j++){ for(let j = 0; j < temp.length; j++){
index++ index++
instance.text.value = `当前图片处理进度:${index} / ${count}` loadingInstance.value.text = `当前图片处理进度:${index} / ${count}`
const item = temp[j] as PPTImageElement const item = temp[j] as PPTImageElement
let name = new Date().getTime()+".png" let name = new Date().getTime()+".png"
...@@ -307,8 +310,26 @@ const uploadImageHandler = async ()=>{ ...@@ -307,8 +310,26 @@ const uploadImageHandler = async ()=>{
} }
} }
} }
instance.close() const thumbnails = useSlidesStore().getThumbnails
if(thumbnails && thumbnails.length>0){
loadingInstance.value.text='正在上传模板缩略图'
queryObj.value.PageImage=[]
for (let i = 0; i < thumbnails.length; i++) {
loadingInstance.value.text = `缩略图处理进度:${i+1} / ${thumbnails.length}`
let name = new Date().getTime()+".png"
const file = dataURLtoFile(thumbnails[i], name)
let url = await AliyunUpload.UploadAsync(file,`pptist/desgin/${name}`)
if(url!=''){
queryObj.value.PageImage.push(url)
}
}
useSlidesStore().setThumbnails([])
}
loadingInstance.value.close()
loadingInstance.value = null
//instance.close()
} }
const dataURLtoFile = (dataurl:string, filename:string) => { const dataURLtoFile = (dataurl:string, filename:string) => {
...@@ -332,25 +353,25 @@ const SetTripTemplateConfig = async () => { ...@@ -332,25 +353,25 @@ const SetTripTemplateConfig = async () => {
TempData: queryObj.value.TempData, TempData: queryObj.value.TempData,
// FeatureImg: datas.FeatureImgList // FeatureImg: datas.FeatureImgList
} }
let TemplateRes = await ConfigService.SetSetTripConfig(queryMsg); let TemplateRes = await ConfigService.SetSetTripConfig(queryMsg);
if (TemplateRes.data.resultCode == 1) { if (TemplateRes.data.resultCode == 1) {
if(!ConfigId.value){ if(!ConfigId.value){
ConfigIdStore.value = TemplateRes.data.data.ConfigId ConfigIdStore.value = TemplateRes.data.data.ConfigId
}
ElMessage({
showClose: true,
message: '操作成功',
type: 'success',
})
window.parent.postMessage('行程数据保存成功', `${domainManager().notificationUrl}`);
dataLoadingStore.setDataLoading(2)
}else{
ElMessage({
showClose: true,
message: '操作失败',
type: 'warning',
})
} }
ElMessage({
showClose: true,
message: '操作成功',
type: 'success',
})
window.parent.postMessage('行程数据保存成功', `${domainManager().notificationUrl}`);
dataLoadingStore.setDataLoading(2)
}else{
ElMessage({
showClose: true,
message: '操作失败',
type: 'warning',
})
}
} catch (error) {} } catch (error) {}
FeatureImgStore.setFeatureImg([]) FeatureImgStore.setFeatureImg([])
datas.loading = false datas.loading = false
...@@ -362,11 +383,11 @@ const setTemplate = async () =>{ ...@@ -362,11 +383,11 @@ const setTemplate = async () =>{
if(SourceLoading.value) setNewDatasList(datas.DataSource) if(SourceLoading.value) setNewDatasList(datas.DataSource)
await uploadImageHandler() await uploadImageHandler()
let arr = JSON.parse(JSON.stringify(slides.value)) let arr = JSON.parse(JSON.stringify(slides.value))
if(dataLoading.value){ if(dataLoading.value){
dataLoadingStore.setDataLoading(0) dataLoadingStore.setDataLoading(0)
} }
// console.log(JSON.stringify(slides.value),'----保存接口',queryObj.value)
if(model.value&&userInfo.value.IsEditTripTemplate==1){ if(model.value&&userInfo.value.IsEditTripTemplate==1){
arr.forEach(x=>{ arr.forEach(x=>{
x.elements.forEach(y=>{ x.elements.forEach(y=>{
...@@ -374,7 +395,7 @@ const setTemplate = async () =>{ ...@@ -374,7 +395,7 @@ const setTemplate = async () =>{
delete y.TemplateList delete y.TemplateList
}) })
}) })
if(queryObj.value.CoverImg=='') { if(queryObj.value.CoverImg=='' && CoverImg.value=='') {
datas.loading = false datas.loading = false
mainStore.setToolbarState(ToolbarStates.EL_TEMPLATEDATA) mainStore.setToolbarState(ToolbarStates.EL_TEMPLATEDATA)
return ElMessage({ return ElMessage({
...@@ -382,6 +403,11 @@ const setTemplate = async () =>{ ...@@ -382,6 +403,11 @@ const setTemplate = async () =>{
message: '请生成封面图', message: '请生成封面图',
type: 'warning', type: 'warning',
}) })
}else if(queryObj.value.CoverImg=='' && CoverImg.value.startsWith("data:image")){
let name = new Date().getTime()+".jpg"
const file = dataURLtoFile(CoverImg.value, name)
let url = await AliyunUpload.UploadAsync(file,`Feature/CoverImg_${name}`)
queryObj.value.CoverImg = url
} }
if(queryObj.value.Title==''||!queryObj.value.LineId||queryObj.value.LineName=='' if(queryObj.value.Title==''||!queryObj.value.LineId||queryObj.value.LineName==''
||queryObj.value.CountryName==''||queryObj.value.SeasonName=='' ||queryObj.value.CountryName==''||queryObj.value.SeasonName==''
...@@ -417,30 +443,13 @@ const setTemplate = async () =>{ ...@@ -417,30 +443,13 @@ const setTemplate = async () =>{
// console.log(arr,'-------tttt') // console.log(arr,'-------tttt')
queryObj.value.TempData = JSON.stringify(arr) queryObj.value.TempData = JSON.stringify(arr)
if(model.value&&userInfo.value.IsEditTripTemplate==1){ if(model.value&&userInfo.value.IsEditTripTemplate==1){
await SetTripTemplateSlide() await SetTripTemplateSlide()
} }else if(ConfigId.value){
if(ConfigId.value){
await SetTripTemplateConfig() await SetTripTemplateConfig()
} }
} }
// 行程图生成bes64图
const testHandler = async ()=>{
FeatureImgStore.setFeatureImg([])
if(FeatureImgRef.value&&FeatureImgRef.value.length>0){
for (let i = 0; i < FeatureImgRef.value.length; i++) {
let result = await exportFeatureImg(FeatureImgRef.value[i], 'jpeg', 1, false, i)
if(!result){
console.log('异常')
datas.loading = false
break
}
}
setFeatureImgList()
}
}
// 行程图上传 // 行程图上传
const setFeatureImgList = async () => { const setFeatureImgList = async () => {
......
...@@ -100,25 +100,13 @@ ...@@ -100,25 +100,13 @@
</div> </div>
</div> </div>
</div> </div>
<el-dialog v-model="datas.DetailsVisible" :show-close="true" :close-on-press-escape="false" <el-dialog v-model="datas.DetailsVisible" :align-center="true" :show-close="true" :close-on-press-escape="false"
:close-on-click-modal="true" style="width: 650px;"> :close-on-click-modal="true" style="width: 600px;" class="small-padding ">
<template #header> <template #header>
<div class="text-title">{{datas.TemplateRow.Title}} 模版详情</div> <div class="text-title">模板预览</div>
</template> </template>
<div class="MarketDetails-LayoutPool" v-loading="datas.loading"> <div v-if="showCurrentTemplate && showCurrentTemplate.PageImageList" style="max-height: 80vh; overflow-y: auto;">
<LayoutPool style="width: 100%;"/> <img v-for="(x,i) in showCurrentTemplate.PageImageList" :src="x" :key="i" style="width:100%;height:auto;margin-bottom: 10px;">
</div>
<div class="q-mt-lg row items-center">
<div class="col">
</div>
<div>
<el-button v-if="ConfigId||model" class="q-ml-lg"
@click="datas.DetailsVisible=false,datas.TemplateRow={}">关闭</el-button>
<el-button v-if="ConfigId||model" type="primary" class="q-ml-lg"
@click="goToTemplate(datas.TemplateRow)">选择该模版</el-button>
</div>
</div> </div>
</el-dialog> </el-dialog>
</template> </template>
...@@ -134,6 +122,7 @@ ...@@ -134,6 +122,7 @@
import { injectKeyTemplate } from '@/types/injectKey' import { injectKeyTemplate } from '@/types/injectKey'
import LayoutPool from './LayoutPool.vue' import LayoutPool from './LayoutPool.vue'
import { ElMessage } from "element-plus";
const { const {
userInfo userInfo
...@@ -146,6 +135,7 @@ ...@@ -146,6 +135,7 @@
const marketRef = ref<any>() const marketRef = ref<any>()
const currentPage = ref(1 as Number); const currentPage = ref(1 as Number);
const showCurrentTemplate = ref<any>()
const datas = reactive({ const datas = reactive({
TemplateRow: {}, TemplateRow: {},
DetailsVisible: false, DetailsVisible: false,
...@@ -177,34 +167,16 @@ ...@@ -177,34 +167,16 @@
} }
// 查看所有子模版 // 查看所有子模版
const getTemplate = async (item) => { const getTemplate = async (item:any) => {
datas.DetailsVisible = true
datas.TemplateRow = JSON.parse(JSON.stringify(item)) if(item.PageImageList && item.PageImageList.length>0){
datas.loading = true datas.DetailsVisible = true
layoutsStore.setLayouts([]) showCurrentTemplate.value = item
try { }else{
let queryMsg = { ElMessage.warning({
TempId: item.TempId showClose: true,
} message: '当前模板没有预览信息,请选择其他操作',
let dataRes = await ConfigService.GetTripTemplateSlide(queryMsg); })
if (dataRes.data.resultCode == 1) {
let SlidesData = JSON.parse(dataRes.data.data.TempData)
let newSlides = []
if(typeof SlidesData=='object'&&!SlidesData.length){
let obj = {
pageType: 1,
...SlidesData
}
newSlides.push(obj)
}else if(SlidesData.length>0){
newSlides = SlidesData
}
layoutsStore.setLayouts(JSON.parse(JSON.stringify(newSlides)))
}
datas.loading = false
} catch (error) {
console.log("GetTripTemplateSlide", error);
datas.loading = false
} }
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment