布局修改 部分bug修复
@@ -9,6 +9,7 @@
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.ipad{
|
||||
*{
|
||||
-webkit-touch-callout:none;
|
||||
|
||||
BIN
src/assets/images/homePage/aidaIcon.png
Normal file
|
After Width: | Height: | Size: 1.8 KiB |
|
After Width: | Height: | Size: 14 KiB |
|
After Width: | Height: | Size: 8.8 KiB |
BIN
src/assets/images/homePage/learnMore.png
Normal file
|
After Width: | Height: | Size: 22 KiB |
|
Before Width: | Height: | Size: 760 KiB |
BIN
src/assets/images/homePage/login_banner.mp4
Normal file
BIN
src/assets/images/homePage/maskIcon.png
Normal file
|
After Width: | Height: | Size: 1.8 KiB |
BIN
src/assets/images/homePage/squareBg.png
Normal file
|
After Width: | Height: | Size: 2.9 MiB |
|
Before Width: | Height: | Size: 1.0 MiB |
|
Before Width: | Height: | Size: 32 KiB |
@@ -4,7 +4,7 @@ body,
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
height: 100%;
|
||||
font-family: 'Roboto', sans-serif;
|
||||
font-family: pingfang_medium, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
|
||||
overflow: hidden;
|
||||
--aida-fsize2: calc(2.6rem);
|
||||
--aida-fsize1-8: calc(1.8rem);
|
||||
@@ -219,6 +219,14 @@ li {
|
||||
box-sizing: border-box;
|
||||
white-space: nowrap;
|
||||
}
|
||||
@media (max-width: 768px) {
|
||||
.gallery_btn {
|
||||
line-height: 2.4rem;
|
||||
font-size: 0.72rem;
|
||||
border-radius: 1.6rem;
|
||||
padding: 0 1.7rem;
|
||||
}
|
||||
}
|
||||
.gallery_btn.btnSamil {
|
||||
padding: 0rem 2rem;
|
||||
line-height: 4rem;
|
||||
@@ -930,6 +938,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
font-size: 1.4rem;
|
||||
padding: 6rem 7rem;
|
||||
position: relative;
|
||||
|
||||
}
|
||||
.generalModel .fi-rr-down-to-line,
|
||||
.generalModel .fi-rr-arrow-small-right,
|
||||
@@ -1072,7 +1081,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
}
|
||||
.generalModel_table_content .operate_list .operate_item {
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
@@ -1504,7 +1513,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
}
|
||||
.admin_table_content .operate_list .operate_item {
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
@@ -1524,7 +1533,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
}
|
||||
.admin_table_content .operate_list .operate_item {
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
|
||||
@@ -3,7 +3,8 @@ html,body,#app{
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
height: 100%;
|
||||
font-family: 'Roboto', sans-serif;
|
||||
font-weight: 500;
|
||||
font-family: pingfang_medium, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
|
||||
overflow: hidden;
|
||||
// --antd-wave-shadow-color: #341e57;
|
||||
--aida-fsize2: calc(2.6rem);
|
||||
@@ -20,6 +21,18 @@ input{
|
||||
outline: none;
|
||||
border: .1rem solid #dcdfe6;
|
||||
}
|
||||
input[type="radio"] {
|
||||
accent-color: #000; /* 统一修改选中颜色 */
|
||||
}
|
||||
input[type="number"] {
|
||||
-moz-appearance: textfield; /* Firefox */
|
||||
}
|
||||
|
||||
/* Chrome/Safari等Webkit浏览器 */
|
||||
input[type="number"]::-webkit-outer-spin-button,
|
||||
input[type="number"]::-webkit-inner-spin-button {
|
||||
-webkit-appearance: none;
|
||||
}
|
||||
@media (max-width: 768px) {
|
||||
.mdhidden{
|
||||
display: none !important;
|
||||
@@ -66,19 +79,25 @@ input:focus{
|
||||
width: calc(100% - 2rem);
|
||||
|
||||
.ant-slider-rail{
|
||||
height: 0.6rem;
|
||||
border-radius: 0.3rem;
|
||||
height: 1rem;
|
||||
border-radius: 4rem;
|
||||
background: #F2F0FD;
|
||||
}
|
||||
.ant-slider-track{
|
||||
height: 0.6rem;
|
||||
border-radius: 0.3rem;
|
||||
height: 1rem;
|
||||
border-radius: 3rem;
|
||||
background: #000;
|
||||
}
|
||||
.ant-slider-handle{
|
||||
margin-top: -0.4rem;
|
||||
margin-top: 0.1rem;
|
||||
top: 0;
|
||||
height: 1.7rem;
|
||||
width: 1.7rem;
|
||||
border: solid 0.2rem #000;
|
||||
}
|
||||
.ant-slider-step{
|
||||
height: 1rem;
|
||||
}
|
||||
}
|
||||
.ant-slider:hover{
|
||||
.ant-slider-handle{
|
||||
@@ -95,7 +114,6 @@ input:focus{
|
||||
.ant-slider-handle {
|
||||
background-color: #000000 !important;
|
||||
border: none !important;
|
||||
margin-top: -4px;
|
||||
}
|
||||
.ant-slider-handle:hover {
|
||||
box-shadow: 0 0 0 5px rgba(0, 0, 0, 0.2);
|
||||
@@ -223,13 +241,19 @@ input:focus{
|
||||
cursor: pointer;
|
||||
box-sizing: border-box;
|
||||
white-space: nowrap;
|
||||
@media (max-width: 768px) {
|
||||
line-height: 2.4rem;
|
||||
font-size: .72rem;
|
||||
border-radius: 1.6rem;
|
||||
padding: 0 1.7rem;
|
||||
}
|
||||
&.btnSamil{
|
||||
padding: 0rem 2rem;
|
||||
line-height: 4rem;
|
||||
font-size: 1.6rem;
|
||||
}
|
||||
&.gallery_btn_radius{
|
||||
border-radius: 1.4rem;
|
||||
border-radius: 1.3rem;
|
||||
}
|
||||
&.gallery_btn:hover{
|
||||
background-color: #fff;
|
||||
@@ -993,6 +1017,9 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
position: relative;
|
||||
box-shadow: none;
|
||||
height: calc(65rem*1.2);
|
||||
@media (max-width: 768px) {
|
||||
height: calc(48rem*1.2);
|
||||
}
|
||||
&.fullScreen{
|
||||
max-width: 100%;
|
||||
> .ant-modal-content{
|
||||
@@ -1022,7 +1049,6 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
font-size: 1.4rem;
|
||||
padding: 6rem 7rem;
|
||||
position: relative;
|
||||
|
||||
}
|
||||
.fi-rr-down-to-line,.fi-rr-arrow-small-right,.fi-rr-arrow-small-left{
|
||||
font-size: 2rem;
|
||||
@@ -1071,6 +1097,10 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
z-index: 2;
|
||||
@media (max-width: 768px) {
|
||||
width: 2.5rem;
|
||||
height: 2.5rem;
|
||||
}
|
||||
> svg{
|
||||
flex-shrink: 0;
|
||||
border-radius: 50%;
|
||||
@@ -1169,7 +1199,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
justify-content: center;
|
||||
.operate_item {
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
@@ -1653,7 +1683,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
|
||||
.operate_item{
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
@@ -1675,7 +1705,7 @@ tr > .ant-picker-cell-in-view.ant-picker-cell-range-hover-start:last-child::afte
|
||||
justify-content: center;
|
||||
.operate_item {
|
||||
font-size: 1.4rem;
|
||||
font-family: Roboto;
|
||||
font-family: pingfang_medium;
|
||||
font-weight: 400;
|
||||
color: #000;
|
||||
cursor: pointer;
|
||||
@@ -1932,6 +1962,7 @@ textarea:focus{
|
||||
align-items: center;
|
||||
flex-wrap: wrap;
|
||||
justify-content: space-between;
|
||||
width: 100%;
|
||||
.inputShowText{
|
||||
width: 100%;
|
||||
display: none;
|
||||
|
||||
@@ -325,6 +325,7 @@ export default defineComponent({
|
||||
> .label{
|
||||
display: flex;
|
||||
margin: 0;
|
||||
align-items: center;
|
||||
> .content{
|
||||
> input{
|
||||
min-width: 20rem;
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<div class="account_generalMessage_title modal_title_text">
|
||||
<span class="account_generalMessage_title_seach">
|
||||
<input class="gallery_input" type="text" :placeholder="$t('LibraryPage.jsContent7')" @keydown.enter="searchFollowFansList" v-model="getListData.seachContent">
|
||||
<div class="gallery_btn" style="margin-left: 2rem;line-height: 4rem;" @click="searchFollowFansList">Search</div>
|
||||
<div class="gallery_btn" style="margin-left: 2rem;line-height: 4rem;" @click="searchFollowFansList">{{ $t('account.search') }}</div>
|
||||
</span>
|
||||
</div>
|
||||
<div class="account_generalMessage_center modal_title_text">
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
</span> -->
|
||||
<span class="account_generalMessage_title_seach">
|
||||
<input class="gallery_input" type="text" :placeholder="$t('LibraryPage.jsContent7')" @keydown.enter="searchFollowFansList" v-model="getListData.seachContent">
|
||||
<div class="gallery_btn" style="margin-left: 2rem;line-height: 4rem;" @click="searchFollowFansList">Search</div>
|
||||
<div class="gallery_btn" style="margin-left: 2rem;line-height: 4rem;" @click="searchFollowFansList">{{ $t('account.search') }}</div>
|
||||
</span>
|
||||
</div>
|
||||
<div class="account_generalMessage_center modal_title_text">
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
style="width: 100%;"
|
||||
optionFilterProp="label"
|
||||
:options="countryList"
|
||||
:field-names="{ label: locale == 'CHINESE_SIMPLIFIED'?'labelCn':'label' }"
|
||||
placeholder="Please select"
|
||||
allowClear
|
||||
show-search
|
||||
@@ -62,7 +63,7 @@ export default defineComponent({
|
||||
},
|
||||
setup() {
|
||||
const store = useStore();
|
||||
const {t} = useI18n();
|
||||
const {t,locale} = useI18n();
|
||||
let userDetail:any= computed(()=>{
|
||||
return store.state.UserHabit.userDetail
|
||||
})
|
||||
@@ -143,6 +144,7 @@ export default defineComponent({
|
||||
...toRefs(accountHomeData),
|
||||
userDetail,
|
||||
setSubmit,
|
||||
locale,
|
||||
}
|
||||
},
|
||||
data(){
|
||||
|
||||
@@ -17,13 +17,12 @@
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg
|
||||
width="46"
|
||||
height="46"
|
||||
width="100%" height="100%"
|
||||
viewBox="0 0 46 46"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3" />
|
||||
<circle cx="23" cy="23" r="23" fill="black" fill-opacity="0.3" />
|
||||
<rect
|
||||
x="32.5063"
|
||||
y="12"
|
||||
@@ -157,7 +156,7 @@ export default defineComponent({
|
||||
operationsData.accountId = data.id;
|
||||
operationsData.userName = data.userName;
|
||||
operationsData.userEmail = data.userEmail;
|
||||
operationsData.password = data.userPassword;
|
||||
operationsData.password = data.userPassword?data.userPassword:null;
|
||||
operationsData.oldPassword = data.userPassword;
|
||||
// operationsData.validStartTime='2024-08-05T00:00:06'
|
||||
// operationsData.validEndTime='2024-08-05T00:00:06'
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
:options="allCountry"
|
||||
></a-select>
|
||||
</div> -->
|
||||
<div class="admin_state_item">
|
||||
<!-- <div class="admin_state_item">
|
||||
<span>Email:</span>
|
||||
<input
|
||||
v-model="email"
|
||||
@@ -43,13 +43,14 @@
|
||||
type="text"
|
||||
style="width: 230px"
|
||||
/>
|
||||
</div>
|
||||
</div> -->
|
||||
<div class="admin_state_item">
|
||||
<span>User Name:</span>
|
||||
<a-select
|
||||
v-model:value="ids"
|
||||
mode="multiple"
|
||||
style="width: 230px"
|
||||
:field-names="{ label: 'label', value: 'label' }"
|
||||
:filter-option="filterOption"
|
||||
placeholder="Select Item..."
|
||||
max-tag-count="responsive"
|
||||
@@ -165,6 +166,8 @@ import {
|
||||
import { formatTime } from "@/tool/util";
|
||||
import { useStore } from "vuex";
|
||||
import { Https } from "@/tool/https";
|
||||
import { Modal,message } from 'ant-design-vue';
|
||||
import { ExclamationCircleOutlined } from '@ant-design/icons-vue';
|
||||
import allUserPoerationsVue from "./addAllUser.vue";
|
||||
export default defineComponent({
|
||||
components: {allUserPoerationsVue,},
|
||||
@@ -281,6 +284,22 @@ export default defineComponent({
|
||||
key: "credits",
|
||||
width:100,
|
||||
sorter: true,
|
||||
},
|
||||
{
|
||||
title: "Credits Usage",
|
||||
align: "center",
|
||||
dataIndex: "creditsUsage",
|
||||
key: "creditsUsage",
|
||||
width:150,
|
||||
sorter: true,
|
||||
},
|
||||
{
|
||||
title: "Credits Usage Limit",
|
||||
align: "center",
|
||||
dataIndex: "creditsUsageLimit",
|
||||
key: "creditsUsageLimit",
|
||||
width:200,
|
||||
sorter: true,
|
||||
},
|
||||
{
|
||||
title: "Operations",
|
||||
@@ -345,13 +364,15 @@ export default defineComponent({
|
||||
page: filterData.currentPage,
|
||||
systemUser: filterData.systemUser,
|
||||
country: filterData.country,
|
||||
email: filterData.email.trim(),
|
||||
// email: filterData.email.trim(),
|
||||
userType: filterData.userType,
|
||||
ids: filterData.ids,
|
||||
ids: [],
|
||||
occupation: filterData.occupation,
|
||||
order: filterData.order,
|
||||
orderBy: filterData.orderBy,
|
||||
userName: filterData.userName,
|
||||
// userName: filterData.userName,
|
||||
userName: filterData.ids,
|
||||
|
||||
};
|
||||
return data;
|
||||
};
|
||||
@@ -435,7 +456,28 @@ export default defineComponent({
|
||||
fileInput.click();
|
||||
|
||||
}
|
||||
const deleteAagree = (event:any)=>{
|
||||
const confirmDelete = ()=>{
|
||||
return new Promise<void>((resolve, reject) => {
|
||||
Modal.confirm({
|
||||
title: 'Are you sure you want to delete this item?',
|
||||
icon: createVNode(ExclamationCircleOutlined),
|
||||
okText: 'Yes',
|
||||
cancelText: 'No',
|
||||
centered:true,
|
||||
onOk() {
|
||||
resolve(true)
|
||||
},
|
||||
onCancel(){
|
||||
resolve(false)
|
||||
}
|
||||
});
|
||||
})
|
||||
}
|
||||
const deleteAagree = async (event:any)=>{
|
||||
let boolean:any = await confirmDelete()
|
||||
if(!boolean){
|
||||
return
|
||||
}
|
||||
const value = {
|
||||
deleteIdList:[event.id]
|
||||
}
|
||||
|
||||
@@ -95,6 +95,7 @@ export default defineComponent({
|
||||
width: 50,
|
||||
dataIndex: "id",
|
||||
key: "id",
|
||||
sorter: true,
|
||||
fixed: "left",
|
||||
},
|
||||
{
|
||||
@@ -127,6 +128,7 @@ export default defineComponent({
|
||||
dataIndex: "totalEarnings",
|
||||
key: "totalEarnings",
|
||||
openType:'month',
|
||||
sorter: true,
|
||||
},{
|
||||
title: 'Monthly income',
|
||||
align: "center",
|
||||
@@ -200,7 +202,6 @@ export default defineComponent({
|
||||
let collectionList: any = ref([]);
|
||||
let status: any = ref(0);
|
||||
const openDetail = (value:any,openType:string)=>{
|
||||
console.log(value,openType);
|
||||
let data = {
|
||||
id:value.id,
|
||||
type:openType
|
||||
@@ -225,6 +226,7 @@ export default defineComponent({
|
||||
pageSize: 10,
|
||||
total: 0,
|
||||
order:'',
|
||||
orderBy:'',
|
||||
affiliateId:'',
|
||||
historyTableHeight: 0,
|
||||
newCollectionName: "",
|
||||
@@ -244,6 +246,16 @@ export default defineComponent({
|
||||
this.currentPage = e.current;
|
||||
this.pageSize = e.pageSize;
|
||||
this.order = sorter.order == "descend" ? "DESC" : "ASC";
|
||||
console.log(sorter.columnKey)
|
||||
if(sorter.order){
|
||||
if(sorter.columnKey == 'id'){
|
||||
this.orderBy = 'id'
|
||||
}else if(sorter.columnKey == "createTime"){
|
||||
this.orderBy = 'createTime'
|
||||
}else if(sorter.columnKey == "totalEarnings"){
|
||||
this.orderBy = 'totalIncome'
|
||||
}
|
||||
}
|
||||
this.gettrialList();
|
||||
},
|
||||
//查询列表
|
||||
@@ -263,6 +275,7 @@ export default defineComponent({
|
||||
page: this.currentPage,
|
||||
size: this.pageSize,
|
||||
order: this.order,
|
||||
orderBy: this.orderBy,
|
||||
status: this.currentState.value,
|
||||
startTime:startDate,
|
||||
endTime:endDate,
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -70,6 +70,7 @@
|
||||
import { defineComponent, ref, createVNode, computed, reactive, toRefs, nextTick } from "vue";
|
||||
import { Https } from "@/tool/https";
|
||||
import { Modal, message } from "ant-design-vue";
|
||||
import { orderBy } from "element-plus/es/components/table/src/util.mjs";
|
||||
export default defineComponent({
|
||||
components: {
|
||||
},
|
||||
@@ -87,6 +88,7 @@ export default defineComponent({
|
||||
currentPage: 1,
|
||||
pageSize: 10,
|
||||
order:'',
|
||||
orderBy:'',
|
||||
total: 0,
|
||||
historyTableHeight:0,
|
||||
columns:computed(() => {
|
||||
@@ -98,6 +100,7 @@ export default defineComponent({
|
||||
dataIndex: "accountId",
|
||||
key: "accountId",
|
||||
fixed: "left",
|
||||
sorter: true,
|
||||
},{
|
||||
title: 'User Name',
|
||||
key: "username",
|
||||
@@ -118,6 +121,7 @@ export default defineComponent({
|
||||
width: 200,
|
||||
dataIndex: "firstSubscriptionPaymentAmount",
|
||||
key: "firstSubscriptionPaymentAmount",
|
||||
sorter: true,
|
||||
},{
|
||||
title: 'Commission',
|
||||
align: "center",
|
||||
@@ -177,6 +181,15 @@ export default defineComponent({
|
||||
const changePage = (e: any, filters:any, sorter:any)=>{
|
||||
itemAffiliateDetail.currentPage = e.current;
|
||||
itemAffiliateDetail.pageSize = e.pageSize;
|
||||
if(sorter.order){
|
||||
if(sorter.columnKey == 'accountId'){
|
||||
itemAffiliateDetail.orderBy = 'id'
|
||||
}else if(sorter.columnKey == "time"){
|
||||
itemAffiliateDetail.orderBy = 'createTime'
|
||||
}else if(sorter.columnKey == "firstSubscriptionPaymentAmount"){
|
||||
itemAffiliateDetail.orderBy = 'totalIncome'
|
||||
}
|
||||
}
|
||||
itemAffiliateDetail.order = sorter.order == "descend" ? "DESC" : "ASC";
|
||||
getDetailList();
|
||||
}
|
||||
@@ -193,6 +206,7 @@ export default defineComponent({
|
||||
endTime:endDate,
|
||||
startTime:startDate,
|
||||
order:itemAffiliateDetail.order,
|
||||
orderBy:itemAffiliateDetail.orderBy,
|
||||
page: itemAffiliateDetail.currentPage,
|
||||
size: itemAffiliateDetail.pageSize,
|
||||
}
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -17,13 +17,12 @@
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg
|
||||
width="46"
|
||||
height="46"
|
||||
width="100%" height="100%"
|
||||
viewBox="0 0 46 46"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3" />
|
||||
<circle cx="23" cy="23" r="23" fill="black" fill-opacity="0.3" />
|
||||
<rect
|
||||
x="32.5063"
|
||||
y="12"
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -47,7 +47,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="closeModal()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
<!-- 笔刷类型选择 -->
|
||||
<div class="brush-section">
|
||||
<div class="section-header">
|
||||
<span>笔刷类型</span>
|
||||
<span>{{ $t('Canvas.BrushType') }}</span>
|
||||
</div>
|
||||
<div class="brush-type-grid">
|
||||
<div
|
||||
@@ -314,14 +314,14 @@
|
||||
<!-- 阴影设置 -->
|
||||
<div class="brush-section">
|
||||
<div class="section-header">
|
||||
<span>{{ $t("阴影设置") }}</span>
|
||||
<span>{{ $t("Canvas.ShadowSettings") }}</span>
|
||||
</div>
|
||||
|
||||
<div class="property-list">
|
||||
<!-- 阴影开关 -->
|
||||
<div class="property-item">
|
||||
<div class="checkbox-property">
|
||||
<span>{{ $t("启用阴影") }}</span>
|
||||
<span>{{ $t("Canvas.EnableShadows") }}</span>
|
||||
<div class="toggle-switch">
|
||||
<input
|
||||
type="checkbox"
|
||||
@@ -340,7 +340,7 @@
|
||||
<div class="property-item">
|
||||
<div class="color-property">
|
||||
<div class="color-header">
|
||||
<span>{{ $t("阴影颜色") }}</span>
|
||||
<span>{{ $t("Canvas.ShadowColor") }}</span>
|
||||
<div
|
||||
class="color-preview"
|
||||
:style="{ backgroundColor: brushStore.state.shadowColor }"
|
||||
@@ -361,7 +361,7 @@
|
||||
<div class="property-item">
|
||||
<div class="slider-property">
|
||||
<div class="slider-header">
|
||||
<span>{{ $t("阴影宽度") }}</span>
|
||||
<span>{{ $t("Canvas.ShadowWidth") }}</span>
|
||||
<span class="slider-value">{{ brushStore.state.shadowWidth }}px</span>
|
||||
</div>
|
||||
<div class="slider-container">
|
||||
@@ -396,7 +396,7 @@
|
||||
<div class="property-item">
|
||||
<div class="slider-property">
|
||||
<div class="slider-header">
|
||||
<span>{{ $t("阴影X偏移") }}</span>
|
||||
<span>{{ $t("Canvas.ShadowOffsetX") }}</span>
|
||||
<span class="slider-value">{{ brushStore.state.shadowOffsetX }}px</span>
|
||||
</div>
|
||||
<div class="slider-container">
|
||||
@@ -432,7 +432,7 @@
|
||||
<div class="property-item">
|
||||
<div class="slider-property">
|
||||
<div class="slider-header">
|
||||
<span>{{ $t("阴影Y偏移") }}</span>
|
||||
<span>{{ $t("Canvas.ShadowOffsetY") }}</span>
|
||||
<span class="slider-value">{{ brushStore.state.shadowOffsetY }}px</span>
|
||||
</div>
|
||||
<div class="slider-container">
|
||||
@@ -467,7 +467,7 @@
|
||||
<!-- 阴影预览 -->
|
||||
<div class="property-item">
|
||||
<div class="shadow-preview-container">
|
||||
<div class="shadow-preview-title">{{ $t("阴影预览") }}</div>
|
||||
<div class="shadow-preview-title">{{ $t("Canvas.ShadowPreview") }}</div>
|
||||
<div class="shadow-preview-box">
|
||||
<div
|
||||
class="shadow-preview-element"
|
||||
@@ -489,7 +489,7 @@
|
||||
<!-- 笔刷预设 -->
|
||||
<div class="brush-section">
|
||||
<div class="section-header">
|
||||
<span>笔刷预设</span>
|
||||
<span>{{ $t('Canvas.BrushPreset') }}</span>
|
||||
<button class="save-preset-btn" @click="saveCurrentAsPreset" title="保存当前设置为预设">
|
||||
<i class="save-icon">+</i>
|
||||
</button>
|
||||
@@ -904,7 +904,7 @@ const brushStore = BrushStore;
|
||||
/* overflow-y: auto; */
|
||||
min-width: 280px;
|
||||
border-left: 1px solid rgba(0, 0, 0, 0.05); /* 更柔和的边框 */
|
||||
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
|
||||
font-family: pingfang_medium, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
|
||||
animation: panelFadeIn 0.3s ease;
|
||||
box-shadow: 0 4px 20px rgba(0, 0, 0, 0.1); /* 添加阴影效果 */
|
||||
backdrop-filter: blur(2px); /* 添加模糊效果 */
|
||||
@@ -1066,7 +1066,7 @@ const brushStore = BrushStore;
|
||||
background-color: rgba(0, 0, 0, 0.05);
|
||||
padding: 3px 7px;
|
||||
border-radius: 4px;
|
||||
font-family: "Consolas", monospace;
|
||||
font-family: pingfang_medium, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
|
||||
}
|
||||
|
||||
.slider-container {
|
||||
|
||||
@@ -272,7 +272,7 @@ onMounted(() => {
|
||||
<template>
|
||||
<div class="canvas-header">
|
||||
<div class="canvas-header-wrapper">
|
||||
<span class="canvas-title">Canvas</span>
|
||||
<span class="canvas-title">{{ $t('Canvas.Canvas') }}</span>
|
||||
<!-- 默认设置 -->
|
||||
<!-- v-if="
|
||||
!activeTool ||
|
||||
@@ -283,7 +283,7 @@ onMounted(() => {
|
||||
<div class="setting-group">
|
||||
<span class="setting-label">{{ $t("Canvas.width") }}</span>
|
||||
<a-input-number
|
||||
:value="canvasWidth"
|
||||
:value="canvasWidth?.toFixed(2)"
|
||||
class="setting-input"
|
||||
:min="1"
|
||||
:max="9999"
|
||||
@@ -299,7 +299,7 @@ onMounted(() => {
|
||||
<div class="setting-group">
|
||||
<span class="setting-label">{{ $t("Canvas.height") }}</span>
|
||||
<a-input-number
|
||||
:value="canvasHeight"
|
||||
:value="canvasHeight?.toFixed(2)"
|
||||
class="setting-input"
|
||||
:min="1"
|
||||
:max="9999"
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
<!-- 参数调整区域 -->
|
||||
<div class="liquify-params">
|
||||
<div class="param-item">
|
||||
<div class="param-label">尺寸</div>
|
||||
<div class="param-label">{{ $t('liquifyPanel.size') }}</div>
|
||||
<div class="param-control">
|
||||
<input
|
||||
type="range"
|
||||
@@ -48,7 +48,7 @@
|
||||
</div>
|
||||
|
||||
<div class="param-item">
|
||||
<div class="param-label">压力</div>
|
||||
<div class="param-label">{{ $t('liquifyPanel.pressure') }}</div>
|
||||
<div class="param-control">
|
||||
<input
|
||||
type="range"
|
||||
@@ -63,7 +63,7 @@
|
||||
</div>
|
||||
|
||||
<div class="param-item" v-if="showDistortion">
|
||||
<div class="param-label">失真</div>
|
||||
<div class="param-label">{{ $t('liquifyPanel.distortion') }}</div>
|
||||
<div class="param-control">
|
||||
<input
|
||||
type="range"
|
||||
@@ -78,7 +78,7 @@
|
||||
</div>
|
||||
|
||||
<div class="param-item">
|
||||
<div class="param-label">动力</div>
|
||||
<div class="param-label">{{ $t('liquifyPanel.power') }}</div>
|
||||
<div class="param-control">
|
||||
<input
|
||||
type="range"
|
||||
@@ -139,6 +139,9 @@ import { OperationType } from "../utils/layerHelper";
|
||||
import { LiquifyRealTimeUpdater } from "../managers/liquify/LiquifyRealTimeUpdater";
|
||||
import { LiquifyStateManager } from "../managers/liquify/LiquifyStateManager";
|
||||
import { Modal } from "ant-design-vue";
|
||||
import { useI18n } from "vue-i18n";
|
||||
const {t} = useI18n()
|
||||
|
||||
|
||||
// Props定义
|
||||
const props = defineProps({
|
||||
@@ -227,9 +230,9 @@ const stateManager = ref(null);
|
||||
|
||||
// 可用液化模式
|
||||
const availableModes = ref([
|
||||
{ id: "push", name: "推", iconText: "↔" },
|
||||
{ id: "clockwise", name: "顺时针转动", iconText: "↻" },
|
||||
{ id: "counterclockwise", name: "逆时针转动", iconText: "↺" },
|
||||
{ id: "push", name: t('liquifyPanel.push'), iconText: "↔" },
|
||||
{ id: "clockwise", name: t('liquifyPanel.clockwise'), iconText: "↻" },
|
||||
{ id: "counterclockwise", name: t('liquifyPanel.counterclockwise'), iconText: "↺" },
|
||||
// { id: "pinch", name: "捏合", iconText: "⤢" },
|
||||
// { id: "expand", name: "展开", iconText: "⤡" },
|
||||
// { id: "crystal", name: "水晶", iconText: "✧" },
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
import { ref, inject, computed, onMounted, onUnmounted } from "vue";
|
||||
import { findLayerRecursively, OperationType } from "../utils/layerHelper";
|
||||
import ToolButton from "../../ExistsImageList/ToolButton.vue";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
|
||||
|
||||
const emit = defineEmits([
|
||||
"tool-selected",
|
||||
@@ -15,7 +17,7 @@ const emit = defineEmits([
|
||||
"toggle-red-green-mode",
|
||||
"undo-redo-status-changed",
|
||||
]);
|
||||
|
||||
const {t} = useI18n()
|
||||
const props = defineProps({
|
||||
activeTool: String,
|
||||
minimapEnabled: {
|
||||
@@ -62,63 +64,63 @@ const redoFun = () => commandManager.redo();
|
||||
const normalToolsList = ref([
|
||||
{
|
||||
id: "undo",
|
||||
title: "Undo",
|
||||
title: t("Canvas.undo"),
|
||||
action: undo,
|
||||
icon: { name: "CUndo", size: "20" },
|
||||
class: "undo-btn",
|
||||
},
|
||||
{
|
||||
id: "redo",
|
||||
title: "Redo",
|
||||
title: t("Canvas.Redo"),
|
||||
action: redo,
|
||||
icon: { name: "CRedo", size: "20" },
|
||||
class: "redo-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.DRAW,
|
||||
title: "Drawing",
|
||||
title: t("Canvas.Drawing"),
|
||||
action: () => selectTool(OperationType.DRAW),
|
||||
icon: { name: "CBrush", size: "24" },
|
||||
class: "draw-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.ERASER,
|
||||
title: "Eraser",
|
||||
title: t("Canvas.Eraser"),
|
||||
action: () => selectTool(OperationType.ERASER),
|
||||
icon: { name: "CEraser", size: "22" },
|
||||
class: "eraser-btn",
|
||||
},
|
||||
{
|
||||
id: "fillColor",
|
||||
title: "Fill Color",
|
||||
title: t("Canvas.FillColor"),
|
||||
action: () => fillColorRef.value.click(),
|
||||
icon: { name: "CThemeColor", size: "22" },
|
||||
class: "fill-color-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.PAN,
|
||||
title: "Pan",
|
||||
title: t("Canvas.Pan"),
|
||||
action: () => selectTool(OperationType.PAN),
|
||||
icon: { name: "CHand", size: "28" },
|
||||
class: "hand-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.SELECT,
|
||||
title: "Select",
|
||||
title: t("Canvas.Select"),
|
||||
action: () => selectTool(OperationType.SELECT),
|
||||
icon: { name: "CSelect", size: "28" },
|
||||
class: "select-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.LIQUIFY,
|
||||
title: "Liquefying",
|
||||
title: t("Canvas.Liquefying"),
|
||||
action: () => selectTool(OperationType.LIQUIFY),
|
||||
icon: { name: "CLiquefying", size: "32" },
|
||||
class: "liquify-btn",
|
||||
},
|
||||
{
|
||||
id: OperationType.LASSO,
|
||||
title: "Lasso",
|
||||
title: t("Canvas.Lasso"),
|
||||
action: () => selectTool(OperationType.LASSO),
|
||||
icon: { name: "CLasso", size: "28" },
|
||||
class: "lasso-btn",
|
||||
@@ -131,28 +133,28 @@ const normalToolsList = ref([
|
||||
},
|
||||
{
|
||||
id: "zoomIn",
|
||||
title: "Zoom In",
|
||||
title: t("Canvas.ZoomIn"),
|
||||
action: zoomIn,
|
||||
icon: { name: "CZoomIn", size: "30" },
|
||||
class: "zoom-in-btn",
|
||||
},
|
||||
{
|
||||
id: "zoomOut",
|
||||
title: "Zoom Out",
|
||||
title: t("Canvas.ZoomOut"),
|
||||
action: zoomOut,
|
||||
icon: { name: "CZoomOut", size: "26" },
|
||||
class: "zoom-out-btn",
|
||||
},
|
||||
{
|
||||
id: "upload",
|
||||
title: "Upload Image",
|
||||
title: t("Canvas.Upload"),
|
||||
action: triggerImageUpload,
|
||||
icon: { name: "CUpload", size: "26" },
|
||||
class: "upload-btn",
|
||||
},
|
||||
{
|
||||
id: "addText",
|
||||
title: "Add Text",
|
||||
title: t("Canvas.AddText"),
|
||||
action: () => addText(),
|
||||
icon: { name: "CFont", size: "20" },
|
||||
class: "text-btn",
|
||||
@@ -163,14 +165,14 @@ const normalToolsList = ref([
|
||||
const redGreenToolsList = ref([
|
||||
{
|
||||
id: "undo",
|
||||
title: "Undo",
|
||||
title: t("Canvas.undo"),
|
||||
action: undo,
|
||||
icon: { name: "CUndo", size: "20" },
|
||||
class: "undo-btn",
|
||||
},
|
||||
{
|
||||
id: "redo",
|
||||
title: "Redo",
|
||||
title: t("Canvas.Redo"),
|
||||
action: redo,
|
||||
icon: { name: "CRedo", size: "20" },
|
||||
class: "redo-btn",
|
||||
@@ -193,21 +195,21 @@ const redGreenToolsList = ref([
|
||||
},
|
||||
{
|
||||
id: OperationType.ERASER,
|
||||
title: "Eraser (E)",
|
||||
title: t("Canvas.Eraser"),
|
||||
action: () => selectTool(OperationType.ERASER, true),
|
||||
icon: { name: "CEraser", size: "22" },
|
||||
class: "eraser-btn",
|
||||
},
|
||||
{
|
||||
id: "zoomIn",
|
||||
title: "Zoom In",
|
||||
title: t("Canvas.ZoomIn"),
|
||||
action: zoomIn,
|
||||
icon: { name: "CZoomIn", size: "30" },
|
||||
class: "zoom-in-btn",
|
||||
},
|
||||
{
|
||||
id: "zoomOut",
|
||||
title: "Zoom Out",
|
||||
title: t("Canvas.ZoomOut"),
|
||||
action: zoomOut,
|
||||
icon: { name: "CZoomOut", size: "26" },
|
||||
class: "zoom-out-btn",
|
||||
|
||||
@@ -118,7 +118,7 @@ const canvasManagerLoaded = ref(false); // 画布是否加载完成
|
||||
// 红绿图模式状态
|
||||
const isRedGreenMode = ref(false);
|
||||
|
||||
const isShowLayerPanel = ref(true); // 是否显示图层面板
|
||||
const isShowLayerPanel = ref(false); // 是否显示图层面板
|
||||
|
||||
provide("isShowLayerPanel", isShowLayerPanel); // 提供红绿图模式状态给子组件
|
||||
|
||||
@@ -255,6 +255,7 @@ onMounted(async () => {
|
||||
layerManager,
|
||||
activeTool, // 响应式引用,存储当前选中的工具
|
||||
brushSize: brushSize.value, // 可选,初始画笔大小
|
||||
t, // 国际化函数
|
||||
});
|
||||
|
||||
// 初始化文本编辑功能
|
||||
@@ -1127,7 +1128,7 @@ defineExpose({
|
||||
flex-direction: column;
|
||||
/* height: 100vh; */
|
||||
background-color: #ffffff;
|
||||
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
|
||||
font-family: pingfang_medium, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
right: 0;
|
||||
|
||||
@@ -26,12 +26,14 @@ export class ToolManager {
|
||||
* @param {Object} options.layerManager 图层管理实例
|
||||
* @param {Object} options.brushManager 画笔管理器实例(可选,如果不提供会创建一个)
|
||||
* @param {Object} options.activeTool 当前活动工具的响应式引用
|
||||
* @param {Function} options.t 国际化函数
|
||||
*/
|
||||
constructor(options = {}) {
|
||||
this.canvas = options.canvas;
|
||||
this.commandManager = options.commandManager;
|
||||
this.canvasManager = options.canvasManager;
|
||||
this.layerManager = options.layerManager;
|
||||
this.t = options.t
|
||||
this.activeTool = options.activeTool || {
|
||||
value: OperationType.SELECT,
|
||||
};
|
||||
@@ -47,6 +49,7 @@ export class ToolManager {
|
||||
canvas: this.canvas,
|
||||
brushSize: options.brushSize,
|
||||
layerManager: this.layerManager, // 传入图层管理器引用
|
||||
t:this.t
|
||||
});
|
||||
|
||||
// 初始化笔刷指示器
|
||||
|
||||
@@ -7,11 +7,12 @@ export class BaseBrush {
|
||||
* 构造函数
|
||||
* @param {Object} canvas fabric画布实例
|
||||
* @param {Object} options 笔刷配置选项
|
||||
* @param {Object} t 翻译函数
|
||||
*/
|
||||
constructor(canvas, options = {}) {
|
||||
this.canvas = canvas;
|
||||
this.options = options;
|
||||
|
||||
this.t = options.t;
|
||||
// 基本属性
|
||||
this.id = options.id || this.constructor.name;
|
||||
this.name = options.name || "未命名笔刷";
|
||||
@@ -211,35 +212,35 @@ export class BaseBrush {
|
||||
return [
|
||||
{
|
||||
id: "size",
|
||||
name: "笔刷大小",
|
||||
name: this.t('Canvas.BrushSize'),
|
||||
type: "slider",
|
||||
defaultValue: 5,
|
||||
min: 0.5,
|
||||
max: 100,
|
||||
step: 0.5,
|
||||
description: "笔刷的大小(像素)",
|
||||
category: "基本",
|
||||
description: this.t('Canvas.BrushDeSize'),
|
||||
category: this.t('Canvas.basic'),
|
||||
order: 10,
|
||||
},
|
||||
{
|
||||
id: "color",
|
||||
name: "笔刷颜色",
|
||||
name: this.t('Canvas.BrushColor'),
|
||||
type: "color",
|
||||
defaultValue: "#000000",
|
||||
description: "笔刷的颜色",
|
||||
category: "基本",
|
||||
description: this.t('Canvas.BrushDeColor'),
|
||||
category: this.t('Canvas.basic'),
|
||||
order: 20,
|
||||
},
|
||||
{
|
||||
id: "opacity",
|
||||
name: "不透明度",
|
||||
name: this.t('Canvas.BrushOpacity'),
|
||||
type: "slider",
|
||||
defaultValue: 1,
|
||||
min: 0.05,
|
||||
max: 1,
|
||||
step: 0.01,
|
||||
description: "笔刷的不透明度",
|
||||
category: "基本",
|
||||
description: this.t('Canvas.BrushdeOpacity'),
|
||||
category: this.t('Canvas.basic'),
|
||||
order: 30,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -33,11 +33,13 @@ export class BrushManager {
|
||||
* @param {Object} options.canvas fabric.js画布实例
|
||||
* @param {Object} options.brushStore 笔刷数据存储(可选)
|
||||
* @param {Object} options.layerManager 图层管理器实例(可选)
|
||||
* @param {Function} options.t 国际化函数
|
||||
*/
|
||||
constructor(options = {}) {
|
||||
this.canvas = options.canvas;
|
||||
this.brushStore = options.brushStore || BrushStore;
|
||||
this.layerManager = options.layerManager; // 添加图层管理器引用
|
||||
this.t = options.t
|
||||
|
||||
// 当前活动笔刷
|
||||
this.activeBrush = null;
|
||||
@@ -59,76 +61,89 @@ export class BrushManager {
|
||||
_registerDefaultBrushes() {
|
||||
// 注册铅笔笔刷
|
||||
brushRegistry.register("pencil", PencilBrush, {
|
||||
name: "Pencil",
|
||||
name: this.t("Canvas.Pencil"),
|
||||
description: "基础铅笔工具,适合精细线条绘制",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
|
||||
// 注册材质笔刷
|
||||
brushRegistry.register("texture", TextureBrush, {
|
||||
name: "Texture",
|
||||
name: this.t("Canvas.Texture"),
|
||||
description: "使用纹理图片作为笔刷,支持缩放和透明度",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
|
||||
// 注册集成的笔刷类型
|
||||
brushRegistry.register("crayon", CrayonBrush, {
|
||||
name: "Crayon",
|
||||
name: this.t("Canvas.Crayon"),
|
||||
description: "使用纹理图片作为笔刷,支持缩放和透明度",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("fur", FurBrush, {
|
||||
name: "Fur",
|
||||
name: this.t("Canvas.Fur"),
|
||||
description: "使用纹理图片作为笔刷,支持缩放和透明度",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("ink", InkBrush, {
|
||||
name: "Ink",
|
||||
name: this.t("Canvas.Ink"),
|
||||
description: "墨水笔刷,适合书写和绘图",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("", LongfurBrush, {
|
||||
name: "Longfur",
|
||||
name: this.t("Canvas.Longfur"),
|
||||
description: "长毛发笔刷,适合绘制动物毛皮、草或头发",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("writing", WritingBrush, {
|
||||
name: "Writing",
|
||||
name: this.t("Canvas.Writing"),
|
||||
description: "书法笔刷,模拟中国传统书法毛笔效果,具有笔锋和墨色变化",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("marker", MarkerBrush, {
|
||||
name: "Marker",
|
||||
name: this.t("Canvas.Marker"),
|
||||
description: "马克笔笔刷,适合粗线条和填充",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("pen", CustomPenBrush, {
|
||||
name: "Pen",
|
||||
name: this.t("Canvas.Pen"),
|
||||
description: "自定义钢笔笔刷,适合书写和绘图",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("ribbon", RibbonBrush, {
|
||||
name: "Ribbon",
|
||||
name: this.t("Canvas.Ribbon"),
|
||||
description: "丝带笔刷,适合创建流动的丝带效果",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
brushRegistry.register("shaded", ShadedBrush, {
|
||||
name: "Shaded",
|
||||
name: this.t("Canvas.Shaded"),
|
||||
description: "阴影笔刷,适合创建渐变和阴影效果",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
|
||||
brushRegistry.register("spray", SprayBrush, {
|
||||
name: "spray",
|
||||
name: this.t("Canvas.Spray"),
|
||||
description: "模拟喷枪效果,创建散点效果",
|
||||
category: "基础笔刷",
|
||||
t:this.t,
|
||||
category: this.t('Canvas.BasicBrushes'),
|
||||
});
|
||||
|
||||
// brushRegistry.register("sketchy", SketchyBrush);
|
||||
// brushRegistry.register("spraypaint", SpraypaintBrush, {
|
||||
// name: "Spraypaint",
|
||||
// description: "喷漆笔刷,模拟喷漆效果",
|
||||
// category: "基础笔刷",
|
||||
// t:this.t,
|
||||
// category: this.t('Canvas.BasicBrushes'),
|
||||
// });
|
||||
|
||||
// // // 注册喷枪笔刷
|
||||
@@ -140,7 +155,7 @@ export class BrushManager {
|
||||
// id: "spray",
|
||||
// name: "Spray",
|
||||
// description: "模拟喷枪效果,创建散点效果",
|
||||
// category: "基础笔刷",
|
||||
// category: this.t('Canvas.BasicBrushes'),
|
||||
// ...options,
|
||||
// });
|
||||
// }
|
||||
|
||||
@@ -13,9 +13,9 @@ export class CrayonBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "crayon",
|
||||
name: "蜡笔",
|
||||
name: options.t("Canvas.Crayon"),
|
||||
description: "模拟蜡笔效果,具有颗粒感和纹理",
|
||||
category: "特效笔刷",
|
||||
category: options.t("Canvas.SpecialEffectsBrush"),
|
||||
icon: "crayon",
|
||||
...options,
|
||||
});
|
||||
@@ -27,6 +27,7 @@ export class CrayonBrush extends BaseBrush {
|
||||
this._inkAmount = options._inkAmount || 10;
|
||||
this.randomness = options.randomness || 0.5; // 随机性
|
||||
this.texture = options.texture || "default"; // 纹理类型
|
||||
this.t = options.t
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -149,52 +150,52 @@ export class CrayonBrush extends BaseBrush {
|
||||
const crayonProperties = [
|
||||
{
|
||||
id: "separation",
|
||||
name: "颗粒分离度",
|
||||
name: this.t('Canvas.ParticleSeparationDegree'),
|
||||
type: "slider",
|
||||
defaultValue: this._sep,
|
||||
min: 0.5,
|
||||
max: 10,
|
||||
step: 0.5,
|
||||
description: "控制蜡笔颗粒的分离程度",
|
||||
category: "蜡笔设置",
|
||||
description: this.t('Canvas.ParticleSeparationDegreeDescription'),
|
||||
category: this.t('Canvas.PencilSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "inkAmount",
|
||||
name: "墨量",
|
||||
name: this.t('Canvas.TheAmountOfInk'),
|
||||
type: "slider",
|
||||
defaultValue: this._inkAmount,
|
||||
min: 1,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制蜡笔的颜料量",
|
||||
category: "蜡笔设置",
|
||||
description: this.t('Canvas.TheAmountOfInkDescription'),
|
||||
category: this.t('Canvas.PencilSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "randomness",
|
||||
name: "随机性",
|
||||
name: this.t('Canvas.randomness'),
|
||||
type: "slider",
|
||||
defaultValue: this.randomness,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制蜡笔纹理的随机程度",
|
||||
category: "蜡笔设置",
|
||||
description: this.t('Canvas.randomnessDescription'),
|
||||
category: this.t('Canvas.PencilSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "texture",
|
||||
name: "纹理类型",
|
||||
name: this.t('Canvas.TextureType'),
|
||||
type: "select",
|
||||
defaultValue: this.texture,
|
||||
options: [
|
||||
{ value: "default", label: "默认" },
|
||||
{ value: "rough", label: "粗糙" },
|
||||
{ value: "smooth", label: "平滑" },
|
||||
{ value: "default", label: this.t('Canvas.Default') },
|
||||
{ value: "rough", label: this.t('Canvas.Rough') },
|
||||
{ value: "smooth", label: this.t('Canvas.Smooth') },
|
||||
],
|
||||
description: "设置蜡笔的纹理类型",
|
||||
category: "蜡笔设置",
|
||||
description: this.t('Canvas.TextureTypeDescription'),
|
||||
category: this.t('Canvas.PencilSettings'),
|
||||
order: 130,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class CustomPenBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "pen",
|
||||
name: "钢笔",
|
||||
name: options.t('Canvas.Pen'),
|
||||
description: "模拟钢笔效果,具有变化的透明度",
|
||||
category: "基础笔刷",
|
||||
category: options.t('Canvas.BasicBrushes'),
|
||||
icon: "pen",
|
||||
...options,
|
||||
});
|
||||
@@ -115,38 +115,38 @@ export class CustomPenBrush extends BaseBrush {
|
||||
const penProperties = [
|
||||
{
|
||||
id: "lineWidth",
|
||||
name: "线条宽度",
|
||||
name: this.t('Canvas.PenWidth'),
|
||||
type: "slider",
|
||||
defaultValue: this._lineWidth,
|
||||
min: 1,
|
||||
max: 10,
|
||||
step: 0.5,
|
||||
description: "控制钢笔线条的宽度",
|
||||
category: "钢笔设置",
|
||||
description: this.t('Canvas.PenWidthDescription'),
|
||||
category: this.t('Canvas.PenSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "inkOpacityMin",
|
||||
name: "最小墨水透明度",
|
||||
name: this.t('Canvas.PenMinimumInkTransparency'),
|
||||
type: "slider",
|
||||
defaultValue: this.inkOpacityMin,
|
||||
min: 0.1,
|
||||
max: 0.5,
|
||||
step: 0.05,
|
||||
description: "控制钢笔墨水最小透明度",
|
||||
category: "钢笔设置",
|
||||
description: this.t('Canvas.PenMinimumInkTransparencyDescription'),
|
||||
category: this.t('Canvas.PenSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "inkOpacityMax",
|
||||
name: "最大墨水透明度",
|
||||
name: this.t('Canvas.PenMaximumInkTransparency'),
|
||||
type: "slider",
|
||||
defaultValue: this.inkOpacityMax,
|
||||
min: 0.3,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制钢笔墨水最大透明度",
|
||||
category: "钢笔设置",
|
||||
description: this.t('Canvas.PenMaximumInkTransparencyDescription'),
|
||||
category: this.t('Canvas.PenSettings'),
|
||||
order: 120,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class FurBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "fur",
|
||||
name: "毛发笔刷",
|
||||
name: options.t('Canvas.Longfur'),
|
||||
description: "创建类似于毛发或草的纹理效果",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "fur",
|
||||
...options,
|
||||
});
|
||||
@@ -123,38 +123,38 @@ export class FurBrush extends BaseBrush {
|
||||
const furProperties = [
|
||||
{
|
||||
id: "furLength",
|
||||
name: "毛发长度",
|
||||
name: this.t('Canvas.FurLength'),
|
||||
type: "slider",
|
||||
defaultValue: this.furLength,
|
||||
min: 1,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制毛发的长度",
|
||||
category: "毛发设置",
|
||||
description: this.t('Canvas.FurLengthDescription'),
|
||||
category: this.t('Canvas.FurSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "furDensity",
|
||||
name: "毛发密度",
|
||||
name: this.t('Canvas.FurDensity'),
|
||||
type: "slider",
|
||||
defaultValue: this.furDensity,
|
||||
min: 0.1,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制毛发的密度",
|
||||
category: "毛发设置",
|
||||
description: this.t('Canvas.FurDensityDescription'),
|
||||
category: this.t('Canvas.FurSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "furRandomness",
|
||||
name: "随机性",
|
||||
name: this.t('Canvas.FurRandomness'),
|
||||
type: "slider",
|
||||
defaultValue: this.furRandomness,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制毛发的随机分布程度",
|
||||
category: "毛发设置",
|
||||
description: this.t('Canvas.FurRandomnessDescription'),
|
||||
category: this.t('Canvas.FurSettings'),
|
||||
order: 120,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class InkBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "ink",
|
||||
name: "水墨笔刷",
|
||||
name: options.t('Canvas.Ink'),
|
||||
description: "模拟中国传统水墨画效果,墨色深浅不一",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "ink",
|
||||
...options,
|
||||
});
|
||||
@@ -27,6 +27,7 @@ export class InkBrush extends BaseBrush {
|
||||
this.splashEnabled = options.splashEnabled !== undefined ? options.splashEnabled : true;
|
||||
this.splashSize = options.splashSize || 5;
|
||||
this.splashDistance = options.splashDistance || 30;
|
||||
this.t = options.t
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -159,60 +160,60 @@ export class InkBrush extends BaseBrush {
|
||||
const inkProperties = [
|
||||
{
|
||||
id: "inkAmount",
|
||||
name: "墨量",
|
||||
name: this.t('Canvas.InkAmount'),
|
||||
type: "slider",
|
||||
defaultValue: this._inkAmount,
|
||||
min: 1,
|
||||
max: 20,
|
||||
step: 1,
|
||||
description: "控制水墨的浓度",
|
||||
category: "水墨设置",
|
||||
description: this.t('Canvas.InkAmountDescription'),
|
||||
category: this.t('Canvas.InkSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "range",
|
||||
name: "笔触范围",
|
||||
name: this.t('Canvas.InkRange'),
|
||||
type: "slider",
|
||||
defaultValue: this._range,
|
||||
min: 5,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制水墨扩散的范围",
|
||||
category: "水墨设置",
|
||||
description: this.t('Canvas.InkRangeDescription'),
|
||||
category: this.t('Canvas.InkSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "splashEnabled",
|
||||
name: "溅墨效果",
|
||||
name: this.t('Canvas.InkSplashEnabled'),
|
||||
type: "checkbox",
|
||||
defaultValue: this.splashEnabled,
|
||||
description: "是否启用溅墨效果",
|
||||
category: "水墨设置",
|
||||
description: this.t('Canvas.InkSplashEnabledDescription'),
|
||||
category: this.t('Canvas.InkSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "splashSize",
|
||||
name: "溅墨大小",
|
||||
name: this.t('Canvas.InkSize'),
|
||||
type: "slider",
|
||||
defaultValue: this.splashSize,
|
||||
min: 1,
|
||||
max: 20,
|
||||
step: 1,
|
||||
description: "溅墨点的大小",
|
||||
category: "水墨设置",
|
||||
description: this.t('Canvas.InkSizeDescription'),
|
||||
category: this.t('Canvas.InkSettings'),
|
||||
order: 130,
|
||||
visibleWhen: { splashEnabled: true },
|
||||
},
|
||||
{
|
||||
id: "splashDistance",
|
||||
name: "溅墨距离",
|
||||
name: this.t('Canvas.InkRandomness'),
|
||||
type: "slider",
|
||||
defaultValue: this.splashDistance,
|
||||
min: 10,
|
||||
max: 100,
|
||||
step: 5,
|
||||
description: "溅墨可扩散的最大距离",
|
||||
category: "水墨设置",
|
||||
description: this.t('Canvas.InkRandomnessDescription'),
|
||||
category: this.t('Canvas.InkSettings'),
|
||||
order: 140,
|
||||
visibleWhen: { splashEnabled: true },
|
||||
},
|
||||
|
||||
@@ -13,9 +13,9 @@ export class LongfurBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "longfur",
|
||||
name: "长毛发",
|
||||
name: options.t('Canvas.Longfur'),
|
||||
description: "创建流动的长毛发效果,适合绘制动物毛皮、草或头发",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "longfur",
|
||||
...options,
|
||||
});
|
||||
@@ -198,59 +198,59 @@ export class LongfurBrush extends BaseBrush {
|
||||
const longfurProperties = [
|
||||
{
|
||||
id: "furLength",
|
||||
name: "毛发长度",
|
||||
name: this.t('Canvas.FurLength'),
|
||||
type: "slider",
|
||||
defaultValue: this.furLength,
|
||||
min: 5,
|
||||
max: 100,
|
||||
step: 1,
|
||||
description: "控制毛发的长度",
|
||||
category: "长毛发设置",
|
||||
description: this.t('Canvas.FurLengthDescription'),
|
||||
category: this.t('Canvas.LongfurSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "furDensity",
|
||||
name: "毛发密度",
|
||||
name: this.t('Canvas.FurDensity'),
|
||||
type: "slider",
|
||||
defaultValue: this.furDensity,
|
||||
min: 0.1,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制毛发的密度",
|
||||
category: "长毛发设置",
|
||||
description: this.t('Canvas.FurDensityDescription'),
|
||||
category: this.t('Canvas.LongfurSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "furFlowFactor",
|
||||
name: "流动系数",
|
||||
name: this.t('Canvas.FlowCoefficient'),
|
||||
type: "slider",
|
||||
defaultValue: this.furFlowFactor,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制毛发的流动感",
|
||||
category: "长毛发设置",
|
||||
description: this.t('Canvas.FlowCoefficientDescription'),
|
||||
category: this.t('Canvas.LongfurSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "furCurvature",
|
||||
name: "弯曲度",
|
||||
name: this.t('Canvas.furCurvature'),
|
||||
type: "slider",
|
||||
defaultValue: this.furCurvature,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制毛发的弯曲程度",
|
||||
category: "长毛发设置",
|
||||
description: this.t('Canvas.furCurvatureDescription'),
|
||||
category: this.t('Canvas.LongfurSettings'),
|
||||
order: 130,
|
||||
},
|
||||
{
|
||||
id: "randomizeDirection",
|
||||
name: "随机方向",
|
||||
name: this.t('Canvas.randomizeDirection'),
|
||||
type: "checkbox",
|
||||
defaultValue: this.randomizeDirection,
|
||||
description: "是否随机化毛发方向",
|
||||
category: "长毛发设置",
|
||||
description: this.t('Canvas.randomizeDirectionDescription'),
|
||||
category: this.t('Canvas.LongfurSettings'),
|
||||
order: 140,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class MarkerBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "marker",
|
||||
name: "马克笔",
|
||||
name: options.t("Canva.Marker"),
|
||||
description: "模拟马克笔效果,具有半透明平头笔触",
|
||||
category: "基础笔刷",
|
||||
category: options.t("Canvas.BasicBrushes"),
|
||||
icon: "marker",
|
||||
...options,
|
||||
});
|
||||
@@ -150,40 +150,40 @@ export class MarkerBrush extends BaseBrush {
|
||||
const markerProperties = [
|
||||
{
|
||||
id: "lineWidth",
|
||||
name: "笔触宽度",
|
||||
name: this.t('Canvas.MarkerWidth'),
|
||||
type: "slider",
|
||||
defaultValue: this._lineWidth,
|
||||
min: 1,
|
||||
max: 10,
|
||||
step: 0.5,
|
||||
description: "控制马克笔笔触的宽度",
|
||||
category: "马克笔设置",
|
||||
description: this.t('Canvas.MarkerWidthDescription'),
|
||||
category: this.t('Canvas.MarkerSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "capStyle",
|
||||
name: "笔头样式",
|
||||
name: this.t('Canvas.MarkerCapStyle'),
|
||||
type: "select",
|
||||
defaultValue: this.capStyle,
|
||||
options: [
|
||||
{ value: "round", label: "圆形" },
|
||||
{ value: "square", label: "方形" },
|
||||
{ value: "round", label: this.t('Canvas.MarkerCapStyleRound') },
|
||||
{ value: "square", label: this.t('Canvas.MarkerCapStyleSquare') },
|
||||
],
|
||||
description: "设置马克笔笔头的形状",
|
||||
category: "马克笔设置",
|
||||
description: this.t('Canvas.MarkerCapStyleDescription'),
|
||||
category: this.t('Canvas.MarkerSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "blendMode",
|
||||
name: "混合模式",
|
||||
name: this.t('Canvas.MarkerMixedModel'),
|
||||
type: "select",
|
||||
defaultValue: this.blendMode,
|
||||
options: [
|
||||
{ value: "multiply", label: "正片叠底" },
|
||||
{ value: "normal", label: "正常" },
|
||||
{ value: "multiply", label: this.t('Canvas.MarkerMixedModelMultiply') },
|
||||
{ value: "normal", label: this.t('Canvas.MarkerMixedModelNormal') },
|
||||
],
|
||||
description: "设置马克笔的颜色混合方式",
|
||||
category: "马克笔设置",
|
||||
description: this.t('Canvas.MarkerMixedModelDescription'),
|
||||
category: this.t('Canvas.MarkerSettings'),
|
||||
order: 120,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class RibbonBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "ribbon",
|
||||
name: "飘带",
|
||||
name: options.t('Canvas.Ribbon'),
|
||||
description: "创建流畅的飘带状线条,具有动态宽度变化和曲线美感",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "ribbon",
|
||||
...options,
|
||||
});
|
||||
@@ -237,66 +237,66 @@ export class RibbonBrush extends BaseBrush {
|
||||
const ribbonProperties = [
|
||||
{
|
||||
id: "ribbonWidth",
|
||||
name: "飘带宽度",
|
||||
name: this.t('Canvas.RibbonWidth'),
|
||||
type: "slider",
|
||||
defaultValue: this.ribbonWidth,
|
||||
min: 5,
|
||||
max: 100,
|
||||
step: 5,
|
||||
description: "控制飘带的最大宽度",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonWidthDescription'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "widthVariation",
|
||||
name: "宽度变化",
|
||||
name: this.t('Canvas.RibbonVariation'),
|
||||
type: "slider",
|
||||
defaultValue: this.widthVariation,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制飘带宽度的变化程度",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonVariationDescription'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "ribbonSmoothness",
|
||||
name: "平滑度",
|
||||
name: this.t('Canvas.RibbonSmoothness'),
|
||||
type: "slider",
|
||||
defaultValue: this.ribbonSmoothness,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制飘带曲线的平滑程度",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonSmoothnessDescription'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "gradient",
|
||||
name: "启用渐变",
|
||||
name: this.t('Canvas.RibbonGradient'),
|
||||
type: "checkbox",
|
||||
defaultValue: this.gradient,
|
||||
description: "是否启用渐变效果",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonGradientDescription'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 130,
|
||||
},
|
||||
{
|
||||
id: "gradientColor1",
|
||||
name: "渐变起始颜色",
|
||||
name: this.t('Canvas.RibbonGradientColor1'),
|
||||
type: "color",
|
||||
defaultValue: this.gradientColors[0] || "#000000",
|
||||
description: "设置渐变的起始颜色",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonGradientColor1Description'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 140,
|
||||
visibleWhen: { gradient: true },
|
||||
},
|
||||
{
|
||||
id: "gradientColor2",
|
||||
name: "渐变结束颜色",
|
||||
name: this.t('Canvas.RibbonGradientColor2'),
|
||||
type: "color",
|
||||
defaultValue: this.gradientColors[1] || "#555555",
|
||||
description: "设置渐变的结束颜色",
|
||||
category: "飘带设置",
|
||||
description: this.t('Canvas.RibbonGradientColor2Description'),
|
||||
category: this.t('Canvas.RibbonSettings'),
|
||||
order: 150,
|
||||
visibleWhen: { gradient: true },
|
||||
},
|
||||
|
||||
@@ -13,9 +13,9 @@ export class ShadedBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "shaded",
|
||||
name: "阴影笔",
|
||||
name: options.t('Canvas.Shaded'),
|
||||
description: "创建带有阴影效果的绘制,适合素描和明暗表现",
|
||||
category: "绘画笔刷",
|
||||
category: options.t('Canvas.PaintingBrush'),
|
||||
icon: "shaded",
|
||||
...options,
|
||||
});
|
||||
@@ -246,70 +246,70 @@ export class ShadedBrush extends BaseBrush {
|
||||
const shadedProperties = [
|
||||
{
|
||||
id: "shadowColor",
|
||||
name: "阴影颜色",
|
||||
name: this.t('Canvas.ShadedColor'),
|
||||
type: "color",
|
||||
defaultValue: this.shadowColor,
|
||||
description: "设置阴影的颜色",
|
||||
category: "阴影设置",
|
||||
description: this.t('Canvas.ShadedColorDescription'),
|
||||
category: this.t('Canvas.ShadedSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "shadowBlur",
|
||||
name: "阴影模糊",
|
||||
name: this.t('Canvas.ShadedBlur'),
|
||||
type: "slider",
|
||||
defaultValue: this.shadowBlur,
|
||||
min: 0,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制阴影的模糊程度",
|
||||
category: "阴影设置",
|
||||
description: this.t('Canvas.ShadedBlurDescription'),
|
||||
category: this.t('Canvas.ShadedSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "shadowOffsetX",
|
||||
name: "阴影X偏移",
|
||||
name: this.t('Canvas.ShadedOffsetX'),
|
||||
type: "slider",
|
||||
defaultValue: this.shadowOffsetX,
|
||||
min: -20,
|
||||
max: 20,
|
||||
step: 1,
|
||||
description: "控制阴影的水平偏移",
|
||||
category: "阴影设置",
|
||||
description: this.t('Canvas.ShadedOffsetXDescription'),
|
||||
category: this.t('Canvas.ShadedSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "shadowOffsetY",
|
||||
name: "阴影Y偏移",
|
||||
name: this.t('Canvas.ShadedOffsetY'),
|
||||
type: "slider",
|
||||
defaultValue: this.shadowOffsetY,
|
||||
min: -20,
|
||||
max: 20,
|
||||
step: 1,
|
||||
description: "控制阴影的垂直偏移",
|
||||
category: "阴影设置",
|
||||
description: this.t('Canvas.ShadedOffsetYDescription'),
|
||||
category: this.t('Canvas.ShadedSettings'),
|
||||
order: 130,
|
||||
},
|
||||
{
|
||||
id: "blendMode",
|
||||
name: "混合模式",
|
||||
name: this.t('Canvas.ShadedBlendMode'),
|
||||
type: "select",
|
||||
defaultValue: this.blendMode,
|
||||
options: [
|
||||
{ value: "normal", label: "正常" },
|
||||
{ value: "multiply", label: "正片叠底" },
|
||||
{ value: "screen", label: "滤色" },
|
||||
{ value: "overlay", label: "叠加" },
|
||||
{ value: "darken", label: "变暗" },
|
||||
{ value: "lighten", label: "变亮" },
|
||||
{ value: "color-dodge", label: "颜色减淡" },
|
||||
{ value: "color-burn", label: "颜色加深" },
|
||||
{ value: "hard-light", label: "强光" },
|
||||
{ value: "soft-light", label: "柔光" },
|
||||
{ value: "difference", label: "差值" },
|
||||
{ value: "exclusion", label: "排除" },
|
||||
{ value: "normal", label: this.t('Canvas.ShadedMixedModelNormal') },
|
||||
{ value: "multiply", label: this.t('Canvas.ShadedMixedModelMultiply') },
|
||||
{ value: "screen", label: this.t('Canvas.ShadedMixedModelScreen') },
|
||||
{ value: "overlay", label: this.t('Canvas.ShadedMixedModelOverlay') },
|
||||
{ value: "darken", label: this.t('Canvas.ShadedMixedModelDarken') },
|
||||
{ value: "lighten", label: this.t('Canvas.ShadedMixedModelLighten') },
|
||||
{ value: "color-dodge", label: this.t('Canvas.ShadedMixedModelColorDodge') },
|
||||
{ value: "color-burn", label: this.t('Canvas.ShadedMixedModelColorBurn') },
|
||||
{ value: "hard-light", label: this.t('Canvas.ShadedMixedModelHardLight') },
|
||||
{ value: "soft-light", label: this.t('Canvas.ShadedMixedModelSoftLight') },
|
||||
{ value: "difference", label: this.t('Canvas.ShadedMixedModelDifference') },
|
||||
{ value: "exclusion", label: this.t('Canvas.ShadedMixedModelExclusion') },
|
||||
],
|
||||
description: "设置阴影的混合模式",
|
||||
category: "阴影设置",
|
||||
description: this.t('Canvas.ShadedBlendModeDescription'),
|
||||
category: this.t('Canvas.ShadedSettings'),
|
||||
order: 140,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class SprayBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "crayon",
|
||||
name: "喷枪",
|
||||
name: options.t('Canvas.Spray'),
|
||||
description: "模拟喷枪效果,具有颗粒感和纹理",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "crayon",
|
||||
...options,
|
||||
});
|
||||
@@ -151,52 +151,52 @@ export class SprayBrush extends BaseBrush {
|
||||
const crayonProperties = [
|
||||
{
|
||||
id: "separation",
|
||||
name: "颗粒分离度",
|
||||
name: this.t('Canvas.ParticleSeparationDegree'),
|
||||
type: "slider",
|
||||
defaultValue: this._sep,
|
||||
min: 0.5,
|
||||
max: 10,
|
||||
step: 0.5,
|
||||
description: "控制喷枪颗粒的分离程度",
|
||||
category: "喷枪设置",
|
||||
description: this.t('Canvas.ParticleSeparationDegree'),
|
||||
category: this.t('Canvas.SpraySettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "inkAmount",
|
||||
name: "墨量",
|
||||
name: this.t('Canvas.TheAmountOfInk'),
|
||||
type: "slider",
|
||||
defaultValue: this._inkAmount,
|
||||
min: 1,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制喷枪的颜料量",
|
||||
category: "喷枪设置",
|
||||
description: this.t('Canvas.TheAmountOfInkDescription'),
|
||||
category: this.t('Canvas.SpraySettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "randomness",
|
||||
name: "随机性",
|
||||
name: this.t('Canvas.randomness'),
|
||||
type: "slider",
|
||||
defaultValue: this.randomness,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制喷枪纹理的随机程度",
|
||||
category: "喷枪设置",
|
||||
description: this.t('Canvas.randomnessDescription'),
|
||||
category: this.t('Canvas.SpraySettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "texture",
|
||||
name: "纹理类型",
|
||||
name: this.t('Canvas.TextureType'),
|
||||
type: "select",
|
||||
defaultValue: this.texture,
|
||||
options: [
|
||||
{ value: "default", label: "默认" },
|
||||
{ value: "rough", label: "粗糙" },
|
||||
{ value: "smooth", label: "平滑" },
|
||||
{ value: "default", label: this.t('Canvas.Default') },
|
||||
{ value: "rough", label: this.t('Canvas.Rough') },
|
||||
{ value: "smooth", label: this.t('Canvas.Smooth') },
|
||||
],
|
||||
description: "设置喷枪的纹理类型",
|
||||
category: "喷枪设置",
|
||||
description: this.t('Canvas.TextureTypeDescription'),
|
||||
category: this.t('Canvas.SpraySettings'),
|
||||
order: 130,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -13,9 +13,9 @@ export class WritingBrush extends BaseBrush {
|
||||
constructor(canvas, options = {}) {
|
||||
super(canvas, {
|
||||
id: "writing",
|
||||
name: "书法笔",
|
||||
name: options.t('Canvas.Writing'),
|
||||
description: "模拟中国传统书法毛笔效果,具有笔锋和墨色变化",
|
||||
category: "特效笔刷",
|
||||
category: options.t('Canvas.SpecialEffectsBrush'),
|
||||
icon: "writing",
|
||||
...options,
|
||||
});
|
||||
@@ -174,47 +174,47 @@ export class WritingBrush extends BaseBrush {
|
||||
const writingProperties = [
|
||||
{
|
||||
id: "brushPressure",
|
||||
name: "笔压感应",
|
||||
name: this.t('Canvas.WritingBrushPressure'),
|
||||
type: "slider",
|
||||
defaultValue: this.brushPressure,
|
||||
min: 0.1,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制笔触的力度感应",
|
||||
category: "书法设置",
|
||||
description: this.t('Canvas.WritingBrushPressureDescription'),
|
||||
category: this.t('Canvas.WritingSettings'),
|
||||
order: 100,
|
||||
},
|
||||
{
|
||||
id: "inkAmount",
|
||||
name: "墨量",
|
||||
name: this.t('Canvas.WritingAmount'),
|
||||
type: "slider",
|
||||
defaultValue: this.inkAmount,
|
||||
min: 1,
|
||||
max: 50,
|
||||
step: 1,
|
||||
description: "控制笔触中的墨水量",
|
||||
category: "书法设置",
|
||||
description: this.t('Canvas.WritingAmountDescription'),
|
||||
category: this.t('Canvas.WritingSettings'),
|
||||
order: 110,
|
||||
},
|
||||
{
|
||||
id: "brushTaperFactor",
|
||||
name: "笔锋系数",
|
||||
name: this.t('Canvas.WritingPenTipCoefficient'),
|
||||
type: "slider",
|
||||
defaultValue: this.brushTaperFactor,
|
||||
min: 0,
|
||||
max: 1,
|
||||
step: 0.05,
|
||||
description: "控制笔锋的尖锐程度",
|
||||
category: "书法设置",
|
||||
description: this.t('Canvas.WritingPenTipCoefficientDescription'),
|
||||
category: this.t('Canvas.WritingSettings'),
|
||||
order: 120,
|
||||
},
|
||||
{
|
||||
id: "enableInkDripping",
|
||||
name: "墨滴效果",
|
||||
name: this.t('Canvas.WritingDropEffect'),
|
||||
type: "checkbox",
|
||||
defaultValue: this.enableInkDripping,
|
||||
description: "是否启用墨滴效果",
|
||||
category: "书法设置",
|
||||
description: this.t('Canvas.WritingDropEffectDescription'),
|
||||
category: this.t('Canvas.WritingSettings'),
|
||||
order: 130,
|
||||
},
|
||||
];
|
||||
|
||||
@@ -36,11 +36,11 @@ const state = reactive({
|
||||
|
||||
// 笔刷预设
|
||||
presets: [
|
||||
{ name: "细线", size: 2, opacity: 1, color: "#000000", type: "pencil" },
|
||||
{ name: "中粗", size: 5, opacity: 1, color: "#000000", type: "pencil" },
|
||||
{ name: "粗线", size: 10, opacity: 1, color: "#000000", type: "pencil" },
|
||||
{ name: "水彩", size: 15, opacity: 0.7, color: "#3366ff", type: "marker" },
|
||||
{ name: "喷枪", size: 20, opacity: 0.5, color: "#ff6633", type: "spray" },
|
||||
// { name: "细线", size: 2, opacity: 1, color: "#000000", type: "pencil" },
|
||||
// { name: "中粗", size: 5, opacity: 1, color: "#000000", type: "pencil" },
|
||||
// { name: "粗线", size: 10, opacity: 1, color: "#000000", type: "pencil" },
|
||||
// { name: "水彩", size: 15, opacity: 0.7, color: "#3366ff", type: "marker" },
|
||||
// { name: "喷枪", size: 20, opacity: 0.5, color: "#ff6633", type: "spray" },
|
||||
],
|
||||
|
||||
// 材质预设
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
>
|
||||
<div class="image-list-modal">
|
||||
<div class="modal-header">
|
||||
<h3>{{ $t("图片库") }}</h3>
|
||||
<h3>{{ $t("Canvas.photoGallery") }}</h3>
|
||||
<button class="close-btn" @click="showPanel = false">×</button>
|
||||
</div>
|
||||
|
||||
@@ -62,13 +62,13 @@
|
||||
<!-- 空状态 -->
|
||||
<div v-if="filteredImages.length === 0" class="empty-state">
|
||||
<div class="empty-icon">📷</div>
|
||||
<p>{{ $t("暂无图片") }}</p>
|
||||
<p>{{ $t("Canvas.NoPicture") }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="modal-footer">
|
||||
<div class="image-count">
|
||||
{{ $t("共") }} {{ filteredImages.length }} {{ $t("张图片") }}
|
||||
{{ $t("Canvas.general") }} {{ filteredImages.length }} {{ $t("Canvas.PicturesInTotal") }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -78,6 +78,7 @@
|
||||
|
||||
<script setup>
|
||||
import { ref, computed, defineProps, defineEmits } from "vue";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
|
||||
// Props
|
||||
const props = defineProps({
|
||||
@@ -94,17 +95,18 @@ const props = defineProps({
|
||||
},
|
||||
},
|
||||
});
|
||||
const {t} = useI18n();
|
||||
|
||||
// Emits
|
||||
const emits = defineEmits(["select"]);
|
||||
|
||||
// 响应式数据
|
||||
const showPanel = ref(false);
|
||||
const selectedCategory = ref("全部");
|
||||
const selectedCategory = ref(t("Canvas.all"));
|
||||
|
||||
// 计算属性:获取所有分类
|
||||
const categories = computed(() => {
|
||||
const allCategories = ["全部"];
|
||||
const allCategories = [t("Canvas.all")];
|
||||
const typeSet = new Set();
|
||||
|
||||
props.list.forEach((item) => {
|
||||
@@ -207,7 +209,7 @@ const handleImageError = (event) => {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
z-index: 1000;
|
||||
z-index: 1001;
|
||||
animation: fadeIn 0.3s ease;
|
||||
}
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -1,720 +0,0 @@
|
||||
<template>
|
||||
<div class="detail_modal_body_result">
|
||||
<div v-show="type_ == 1" class="result_apparel_print">
|
||||
<div class="upload_title result_apparel" v-show="type_ == 1">
|
||||
<i class="color_edit fi fi-bs-comments"></i>
|
||||
<span>{{ $t('DesignDetailEnd.NewApparel') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="result_apparel_print_img">
|
||||
<img v-show="type_==1" class="result_appare_img" :src="sketchImg?.path?sketchImg?.path:current?.path" :title="current?.type">
|
||||
<!-- <div v-show="type_==2" class="result_print_img" @click="setPrint" :title="current?.type">
|
||||
<img v-for="item in current?.layersObject" :src="item.imageUrl" alt="">
|
||||
</div> -->
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="type_ == 2" class="result_apparel_elements">
|
||||
<div class="upload_title result_apparel">
|
||||
<i class="color_edit fi fi-bs-comments"></i>
|
||||
<span>{{ $t('DesignDetailEnd.NewPrint') }}</span>
|
||||
</div>
|
||||
<div class="modal_img">
|
||||
<div class="modal_img_item" v-for="item,index in exhibitionList.print" :key="item" >
|
||||
<!-- <div class="modal_img_item" v-for="item,index in current.printObject.prints" :key="item" > -->
|
||||
<img v-lazy="item.path" alt="">
|
||||
<sketchCategory :disignTypeList="designTypeList" :generateList="exhibitionList.print" :item="item" :isSpread="true" :isSetSketchCategory="true"></sketchCategory>
|
||||
<!-- <div
|
||||
class="delete_file_block"
|
||||
@click="deleteSelectptints(item,index)"
|
||||
>
|
||||
<span class="icon iconfont icon-shanchu"></span>
|
||||
</div> -->
|
||||
</div>
|
||||
<div class="modal_img_item" v-for="item,index in printsList" :key="item" >
|
||||
<img v-lazy="item.path" alt="">
|
||||
<sketchCategory :disignTypeList="designTypeList" :generateList="printsList" :item="item" :isSpread="true" :isSetSketchCategory="true"></sketchCategory>
|
||||
<div
|
||||
class="delete_file_block"
|
||||
@click="deleteptints(item,index)"
|
||||
>
|
||||
<span class="icon iconfont icon-shanchu"></span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="type_ == 3">
|
||||
<div class="result_color upload_title">
|
||||
<i class="color_edit fi fi-bs-comments"></i>
|
||||
<span>{{ $t('DesignDetailEnd.NewColor') }}</span>
|
||||
</div>
|
||||
<div class="modal_img">
|
||||
<div class="modal_img_item" v-for="color,index in colorList" :key="color" >
|
||||
<div :title="color?.name?color?.name:''" @click="selectColorItem(index,color)" @dblclick="setSelectColorItem(color)" :class="['upload_color',selectIndex === index ? 'select_upload_color' : '',]" :style="{background:`rgba(${color?.r},${color?.g},${color?.b},${color?.a})`}">
|
||||
<div v-if="!color?.gradient" class="color_content" :style="{'background-color':`rgba(${color.rgba?.r},${color.rgba?.g},${color.rgba?.b},${color.rgba?.a})`}">
|
||||
</div>
|
||||
<div class="color_content" v-else :style="{height:'100%','background-image':color?.gradient?`linear-gradient(${color?.gradient.angle}deg,${setGradient(color?.gradient)}`:'none'}"></div>
|
||||
<div v-if="!color?.gradient" class="color_content_body" :style="{'text-align':color?.name?'left':'center'}">
|
||||
<div class="color_des">{{color.tcx}}</div>
|
||||
<div class="color_des">{{ color.name }}</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="type_ == 4" class="result_apparel_elements">
|
||||
<div class="upload_title result_apparel">
|
||||
<i class="color_edit fi fi-bs-comments"></i>
|
||||
<span>New Elements</span>
|
||||
</div>
|
||||
<div class="modal_img">
|
||||
|
||||
<!-- <div class="modal_img_item" v-for="item,index in current.trims.prints" :key="item" > -->
|
||||
<div class="modal_img_item" v-for="item,index in exhibitionList.elements" :key="item" >
|
||||
<img v-lazy="item.path" alt="">
|
||||
<div
|
||||
class="delete_file_block"
|
||||
@click="deleteSelectElements(item,index)"
|
||||
>
|
||||
<span class="icon iconfont icon-shanchu"></span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal_img_item" v-for="item,index in elementsList" :key="item" >
|
||||
<img v-lazy="item.url" alt="">
|
||||
<div
|
||||
class="delete_file_block"
|
||||
@click="deleteElements(item,index)"
|
||||
>
|
||||
<span class="icon iconfont icon-shanchu"></span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="type_ == 1 || type_ == 3" @click.stop="setPreview" class="subitOkPreviewBtn" :class="[ !sketchImg?.id?!current?.id?'active':'':'' ]">{{ $t('DesignDetailEnd.preview') }}</div>
|
||||
|
||||
<div v-if="type_ == 2 && (current?.printObject?.prints?.length != 0 || exhibitionList.print.length != 0)" @click.stop="setPreview('clearPrint')" class="subitOkPreviewBtn clear">{{ $t('Habit.Clear') }}</div>
|
||||
<div v-if="type_ == 2 && (current?.printObject?.prints?.length != 0 || printsList.length != 0 || exhibitionList.print.length != 0)" @click.stop="setPrint" class="subitOkPreviewBtn Guide_1_23">{{ $t('DesignDetailEnd.Layout') }}</div>
|
||||
<!-- <div v-else-if="type_ == 2 && designItemDetail?.clothes?.[currentIndex]?.printObject?.prints?.[0]?.path != null && current?.printObject?.prints?.[0]?.path == null" @click.stop="setPreview" class="subitOkPreviewBtn">{{ $t('DesignDetailEnd.preview') }}</div> -->
|
||||
<div v-if="type_ == 4 && (elementsList.length != 0 || exhibitionList.elements.length != 0)" @click.stop="setElemets" class="subitOkPreviewBtn">{{ $t('DesignDetailEnd.Layout') }}</div>
|
||||
<DesignPrintOperation ref="DesignPrintOperation"></DesignPrintOperation>
|
||||
<DesignElementsOperation ref="DesignElementsOperation"></DesignElementsOperation>
|
||||
</div>
|
||||
<div class="mark_loading" v-show="loadingShow">
|
||||
<a-spin size="large" />
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import { defineComponent,computed,ref, nextTick,h ,inject} from 'vue'
|
||||
import Draggable from 'vuedraggable'
|
||||
import { Https } from "@/tool/https";
|
||||
import { useStore } from "vuex";
|
||||
import { Sketch} from '@ans1998/vue3-color'
|
||||
import DesignPrintOperation from './DesignPrintOperation.vue';
|
||||
import DesignElementsOperation from './DesignElements.vue';
|
||||
import { message,Upload} from 'ant-design-vue';
|
||||
import { openGuide,driverObj__ } from "@/tool/guide";
|
||||
import {isMoible,setGradual} from '@/tool/util'
|
||||
import { useI18n } from 'vue-i18n';
|
||||
import sketchCategory from "@/component/HomePage/sketchCategory.vue";
|
||||
|
||||
export default defineComponent({
|
||||
props: ["msg"],
|
||||
components:{
|
||||
Draggable,Sketch,DesignPrintOperation,
|
||||
DesignElementsOperation,sketchCategory
|
||||
},
|
||||
setup(prop) {
|
||||
const store = useStore();
|
||||
let type_ = ref(0);
|
||||
let current = inject('current')//父组件传过来的数据
|
||||
let setRevocation = inject('setRevocation')//父组件传过来的数据
|
||||
let sketchImg = ref({})
|
||||
let driver__ = inject('driver__')//父组件传过来的数据
|
||||
let moible = inject('moible')//父组件传过来的数据
|
||||
let designItemDetail = inject('designItemDetail')//父组件传过来的数据
|
||||
let currentIndex = inject('currentIndex')//父组件传过来的数据
|
||||
let designTypeList = inject('designTypeList')//父组件传过来的数据
|
||||
let previewShow = ref(false)
|
||||
//印花
|
||||
|
||||
//颜色
|
||||
// let colorList = ref([{}])
|
||||
// let colorList = ref([{},{},{},{},{},{},{},{},{}])
|
||||
let colorList = inject('colorList')//父组件传过来的数据
|
||||
let selectIndex = inject('selectIndex')//父组件传过来的数据
|
||||
//加载中
|
||||
let loadingShow = ref(false)
|
||||
|
||||
let exhibitionList = inject('exhibitionList')
|
||||
let {t} = useI18n()
|
||||
let printsList = ref([])
|
||||
let elementsList = ref([
|
||||
|
||||
])
|
||||
return{
|
||||
store,
|
||||
current,
|
||||
setRevocation,
|
||||
sketchImg,
|
||||
driver__,
|
||||
moible,
|
||||
designItemDetail,
|
||||
currentIndex,
|
||||
designTypeList,
|
||||
previewShow,
|
||||
type_,
|
||||
colorList,
|
||||
selectIndex,
|
||||
loadingShow,
|
||||
exhibitionList,
|
||||
t,
|
||||
printsList,
|
||||
elementsList,
|
||||
}
|
||||
},
|
||||
data(){
|
||||
return{
|
||||
|
||||
//颜色
|
||||
getRGBA:{},
|
||||
selectColor:{},
|
||||
}
|
||||
},
|
||||
computed:{
|
||||
setGradient(){
|
||||
return (gradient)=>{
|
||||
let gradientStr = ''
|
||||
gradient.gradientList.sort((a, b) => {
|
||||
let aArr = a.left.split('%')[0]
|
||||
let bArr = b.left.split('%')[0]
|
||||
return aArr - bArr;
|
||||
});
|
||||
gradient.gradientList.forEach((item,index)=>{
|
||||
let str = ','
|
||||
if(gradient.gradientList.length == index+1)str = ''
|
||||
gradientStr += `rgba(${item.rgba.r},${item.rgba.g},${item.rgba.b},${item.rgba.a}) ${item.left}${str}`
|
||||
|
||||
})
|
||||
return `${gradientStr}`
|
||||
}
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
'exhibitionList.print':{
|
||||
handler(newVal,oldVal){
|
||||
this.printsList = this.printsList.filter(objA => {
|
||||
return !newVal.some(objB => objB.minIOPath === objA.minIOPath);
|
||||
});
|
||||
this.setExhibitionType('print')
|
||||
}
|
||||
},
|
||||
'exhibitionList.elements':{
|
||||
handler(newVal,oldVal){
|
||||
this.elementsList = this.elementsList.filter(objA => {
|
||||
return !newVal.some(objB => objB.minIOPath === objA.minIOPath);
|
||||
});
|
||||
this.setExhibitionType('elements')
|
||||
}
|
||||
}
|
||||
},
|
||||
methods:{
|
||||
|
||||
//点击判断
|
||||
init(num){
|
||||
// this.current = JSON.parse(JSON.stringify(this.currentItem))
|
||||
this.type_ = num
|
||||
this.colorList[this.selectIndex] = this.$parent.selectColor
|
||||
if(num == 2){
|
||||
this.setExhibitionType('print')
|
||||
}else if(num == 4){
|
||||
this.setExhibitionType('elements')
|
||||
}
|
||||
},
|
||||
clearModal(){
|
||||
this.elementsList = []
|
||||
this.printsList = []
|
||||
},
|
||||
//模型
|
||||
setSketchImg(v){
|
||||
this.sketchImg.id_ = v.id
|
||||
this.sketchImg.id = v.id
|
||||
this.sketchImg.path = v.url
|
||||
this.sketchImg.minIOPath = v.minIOPath
|
||||
this.sketchImg.type = v.level2Type
|
||||
this.sketchImg.designType = v.designType
|
||||
},
|
||||
//印花
|
||||
setExhibitionType(str){
|
||||
this.exhibitionList[str].forEach((item,index)=>{
|
||||
if(!item.categoryValue){
|
||||
this.designTypeList.forEach((typeItem)=>{
|
||||
if(item.level2Type == typeItem.value){
|
||||
item.categoryValue = typeItem.value
|
||||
item.category = typeItem.name
|
||||
}
|
||||
|
||||
})
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
setPrint(){
|
||||
// if(this.current?.printObject?.prints?.[0]?.path){
|
||||
let DesignPrintOperation = this.$refs.DesignPrintOperation
|
||||
DesignPrintOperation.init()
|
||||
if(this.driver__.driver){
|
||||
nextTick().then(()=>{
|
||||
driverObj__.moveNext();
|
||||
})
|
||||
}
|
||||
// }else{
|
||||
// message.info(this.t('DesignDetailEnd.jsContent1'));
|
||||
// }
|
||||
|
||||
},
|
||||
deleteFile(){
|
||||
this.current.printObject = {}
|
||||
},
|
||||
|
||||
|
||||
//颜色
|
||||
selectColorItem(index,color){
|
||||
this.selectIndex = index
|
||||
// if(this.$parent.selectColor?.rgba?.r == color?.rgba?.r && this.$parent.selectColor.rgba.g == color?.rgba?.g && this.$parent.selectColor.rgba.b == color?.rgba?.b){
|
||||
// return
|
||||
// }
|
||||
if(color.rgba?.r){
|
||||
this.$parent.selectColor = color
|
||||
}else{
|
||||
this.$parent.selectColor.isClick = {}
|
||||
}
|
||||
//判断是否对一个颜色重复点击
|
||||
|
||||
// this.$parent.selectColor.tcxColor = ''
|
||||
// this.$parent.selectColor.pantongName = ''
|
||||
},
|
||||
setSelectColorItem(color){
|
||||
let designItemDetail = this.store.state.DesignDetailModule.designItemDetail
|
||||
let string = `${color.rgba.r},${color.rgba.g},${color.rgba.b}`
|
||||
this.current.color = string
|
||||
designItemDetail.clothes.forEach((element,index) => {
|
||||
if(element.id == this.current.id){
|
||||
designItemDetail.clothes[index] = this.current
|
||||
}
|
||||
});
|
||||
},
|
||||
hasDuplicateId(arr) {
|
||||
const set = new Set();
|
||||
for (let i = 0; i < arr.length; i++) {
|
||||
const id = arr[i].id;
|
||||
if (set.has(id)) {
|
||||
return true;
|
||||
}
|
||||
set.add(id);
|
||||
}
|
||||
return false;
|
||||
},
|
||||
soleId(arr,index){
|
||||
let randomNum = Math.floor(100 + Math.random() * 900);
|
||||
// if(this.sketchImg.id_){
|
||||
if(this.sketchImg.id){
|
||||
if(this.sketchImg.id == this.sketchImg.id_){
|
||||
arr[index].id = Number(this.sketchImg.id_+(randomNum+""))
|
||||
arr[index].changed = true
|
||||
if(this.hasDuplicateId(arr)){
|
||||
this.sketchImg.id_ = this.sketchImg.id
|
||||
this.soleId(arr,index)
|
||||
}
|
||||
}else{
|
||||
arr[index].id = this.sketchImg.id_
|
||||
}
|
||||
}else{
|
||||
arr[index].id = this.current.id
|
||||
}
|
||||
// arr[index].id = this.sketchImg.id_? this.sketchImg.id_:this.current.id
|
||||
return arr
|
||||
},
|
||||
deleteptints(item,index){
|
||||
this.printsList.splice(index,1)
|
||||
},
|
||||
deleteSelectptints(item,index){
|
||||
this.exhibitionList.print.splice(index,1)
|
||||
},
|
||||
deleteElements(item,index){
|
||||
this.elementsList.splice(index,1)
|
||||
},
|
||||
deleteSelectElements(item,index){
|
||||
this.exhibitionList.elements.splice(index,1)
|
||||
},
|
||||
setElemets(){
|
||||
if(this.current.trims.prints && this.current.trims.prints.length == 0 && this.elementsList.length == 0)return message.info('请选择至少一张element')
|
||||
let DesignElementsOperation = this.$refs.DesignElementsOperation
|
||||
DesignElementsOperation.init()
|
||||
},
|
||||
//提交
|
||||
async setPreview(str){
|
||||
let designItemDetail = JSON.parse(JSON.stringify(this.store.state.DesignDetailModule.designItemDetail))
|
||||
let index
|
||||
let data = JSON.parse(JSON.stringify(this.store.state.DesignDetailModule.designPreviewData))
|
||||
// let bor = false
|
||||
let zIndex = 10
|
||||
designItemDetail.clothes.forEach((v,ind)=>{
|
||||
if(v.id == this.current.id){
|
||||
index = ind
|
||||
// bor = true
|
||||
}
|
||||
if(v.priority){
|
||||
if(zIndex < v.priority){
|
||||
zIndex = v.priority
|
||||
}
|
||||
}
|
||||
})
|
||||
index = index? index:0
|
||||
if(!this.current.id){
|
||||
if(index && data?.designSingleItemDTOList){
|
||||
data.designSingleItemDTOList[index].priority = zIndex+=1
|
||||
}
|
||||
}
|
||||
if(this.type_ == 1){
|
||||
if(data.designSingleItemDTOList[index].path != this.sketchImg.minIOPath && this.sketchImg.id_){
|
||||
data.designSingleItemDTOList[index].offset = [0,0]
|
||||
data.designSingleItemDTOList[index].scale = [1,1]
|
||||
}
|
||||
data.designSingleItemDTOList = this.soleId(data.designSingleItemDTOList,index)
|
||||
this.sketchImg.id_ = data.designSingleItemDTOList[index].id
|
||||
data.designSingleItemDTOList[index].path =this.sketchImg.minIOPath? this.sketchImg.minIOPath: this.current.minIOPath
|
||||
data.designSingleItemDTOList[index].type =this.sketchImg.type? this.sketchImg.type: this.current.type
|
||||
}else if(this.type_ == 2){
|
||||
if(str == 'clearPrint'){
|
||||
data.designSingleItemDTOList[index].printObject.prints = []
|
||||
}
|
||||
}else if(this.type_ == 3){
|
||||
if(this.colorList[this.selectIndex]?.rgba?.r == undefined){
|
||||
message.info(this.t('DesignDetailEnd.jsContent2'))
|
||||
return
|
||||
}
|
||||
let color = `${this.colorList[this.selectIndex].rgba.r} ${this.colorList[this.selectIndex].rgba.g} ${this.colorList[this.selectIndex].rgba.b}`
|
||||
data.designSingleItemDTOList[index].color = color
|
||||
}else if(this.type_ == 4){
|
||||
data.designSingleItemDTOList[index].trims = this.current.trims
|
||||
}
|
||||
if(this.colorList[this.selectIndex].gradient){
|
||||
let gradient = this.colorList[this.selectIndex].gradient
|
||||
gradient.colorImg = await setGradual(gradient,320,700)
|
||||
data.designSingleItemDTOList[index].gradient = gradient
|
||||
}else{
|
||||
delete data.designSingleItemDTOList[index].gradient
|
||||
}
|
||||
data.designSingleItemDTOList[index].designType = this.sketchImg.designType?this.sketchImg.designType:this.current.designType
|
||||
data.timeZone = Intl.DateTimeFormat().resolvedOptions().timeZone
|
||||
this.loadingShow = true
|
||||
Https.axiosPost(Https.httpUrls.designSingle, data).then(
|
||||
(rv) => {
|
||||
let bor = false
|
||||
rv.clothes.forEach((item)=>{
|
||||
if(item.type != 'body'){
|
||||
if(item.id == designItemDetail.clothes[index].id || item.id == this.sketchImg.id_){
|
||||
designItemDetail.clothes[index].color = item.color
|
||||
if(item.gradient){
|
||||
designItemDetail.clothes[index].gradient = item.gradient
|
||||
}else{
|
||||
delete designItemDetail.clothes[index].gradient
|
||||
}
|
||||
designItemDetail.clothes[index].designType = item.designType
|
||||
designItemDetail.clothes[index].trims = item.trims
|
||||
designItemDetail.clothes[index].layersObject = item.layersObject
|
||||
designItemDetail.clothes[index].minIOPath = item.minIOPath
|
||||
designItemDetail.clothes[index].path = item.path
|
||||
designItemDetail.clothes[index].id = item.id
|
||||
designItemDetail.clothes[index].changed = item.changed?item.changed:false
|
||||
designItemDetail.clothes[index].type = item.type
|
||||
designItemDetail.clothes[index].printObject = item.printObject
|
||||
designItemDetail.clothes[index].undividedLayer = item?.undividedLayer
|
||||
bor = true
|
||||
}else{
|
||||
|
||||
}
|
||||
if(!this.current.id ){
|
||||
designItemDetail.clothes[index].priority = zIndex
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
designItemDetail.currentFullBodyView = rv.currentFullBodyView
|
||||
designItemDetail.ifSubmit = true
|
||||
designItemDetail.clothes.forEach((item,index)=>{
|
||||
let a
|
||||
if(item.layersObject[0].imageCategory.indexOf("back") == -1){
|
||||
a = item.layersObject[0]
|
||||
item.layersObject[0] = item.layersObject[1]
|
||||
item.layersObject[1] = a
|
||||
}
|
||||
item.layersObject[0].id = designItemDetail.clothes[index].layersObject[0].id
|
||||
item.layersObject[1].id = designItemDetail.clothes[index].layersObject[1].id
|
||||
})
|
||||
this.loadingShow = false
|
||||
this.store.commit("setDesignItemDetail", designItemDetail);
|
||||
this.store.commit("setDesignPreviewData", data);
|
||||
this.setRevocation(designItemDetail,data)
|
||||
}
|
||||
).catch(res=>{
|
||||
this.loadingShow = false
|
||||
});
|
||||
}
|
||||
}
|
||||
})
|
||||
</script>
|
||||
<style lang="less" scoped>
|
||||
.detail_modal_body_result{
|
||||
width: 26%;
|
||||
position: relative;
|
||||
i{
|
||||
font-size: var(--aida-fsize1-8);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.upload_title{
|
||||
display: flex;
|
||||
margin-bottom: calc(1rem*1.2);
|
||||
margin-top: calc(1rem*1.2);
|
||||
&.upload_title:nth-child(1){
|
||||
margin-top: 0;
|
||||
}
|
||||
span{
|
||||
margin-left: calc(1rem*1.2);
|
||||
font-size: var(--aida-fsize1-8);
|
||||
color: #000000;
|
||||
}
|
||||
}
|
||||
//模型和印花
|
||||
.result_apparel_print{
|
||||
height: 100%;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
.result_apparel_print_img{
|
||||
position: relative;
|
||||
flex: 1;
|
||||
text-align: center;
|
||||
img{
|
||||
max-width: 100%;
|
||||
max-height: 100%;
|
||||
width: auto;
|
||||
height: auto;
|
||||
max-height: calc(35rem*1.2);
|
||||
margin-top: calc(2rem*1.2);
|
||||
width: 100%;
|
||||
object-fit: contain;
|
||||
}
|
||||
.result_print_img{
|
||||
transform: scale(.85);
|
||||
transform-origin: center top;
|
||||
cursor: pointer;
|
||||
img:nth-child(1){
|
||||
position: absolute;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
//印花
|
||||
.result_print{
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
height: calc(14rem*1.2);
|
||||
>div{
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
.print_left,.print_right{
|
||||
display: flex;
|
||||
flex: 1;
|
||||
align-items: center;
|
||||
align-items: flex-start;
|
||||
}
|
||||
}
|
||||
.print_left{
|
||||
position: relative;
|
||||
img{
|
||||
width: auto;
|
||||
height: calc(8rem*1.2);
|
||||
margin: auto;
|
||||
display: block;
|
||||
}
|
||||
.delete_file_block{
|
||||
display: none;
|
||||
width: calc(3.2rem*1.2);
|
||||
height: calc(3.2rem*1.2);
|
||||
background: rgba(0,0,0,0.6);
|
||||
border-radius: calc(0.4rem*1.2);
|
||||
position: absolute;
|
||||
top: calc(0.9rem*1.2);
|
||||
right: calc(0.9rem*1.2);
|
||||
text-align: center;
|
||||
line-height: calc(3.2rem*1.2);
|
||||
left: auto;
|
||||
.icon-shanchu{
|
||||
font-size: calc(1.6rem*1.2);
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
&:hover .delete_file_block{
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.print_right{
|
||||
|
||||
.habit_Overal_Single {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
// margin: 2rem*1.2) 0;
|
||||
transform: scale(.8);
|
||||
// margin: 3rem*1.2) 0;
|
||||
.habit_Overal_Single_text {
|
||||
font-weight: 600;
|
||||
color: rgba(0, 0, 0, 0.5);
|
||||
&.active {
|
||||
color: rgba(0, 0, 0, 0.7);
|
||||
// font-weight: 900;
|
||||
transform: scale(1.2);
|
||||
}
|
||||
}
|
||||
:deep(.ant-switch) {
|
||||
margin: 0 calc(1rem*1.2);
|
||||
background-color: #efefef;
|
||||
}
|
||||
:deep(.ant-switch-checked) {
|
||||
background-color: #000;
|
||||
}
|
||||
}
|
||||
.habit_System_Designer {
|
||||
margin-top: calc(4rem*1.2);
|
||||
transform: scale(.8);
|
||||
|
||||
:deep(.ant-slider-track),
|
||||
:deep(.ant-slider-rail) {
|
||||
height: calc(.6rem*1.2);
|
||||
background-color: #e1e1e1;
|
||||
border-radius: calc(0.5rem*1.2);
|
||||
}
|
||||
:deep(.ant-slider .ant-slider-handle:not(.ant-tooltip-open)),
|
||||
:deep(.ant-slider-handle) {
|
||||
background-color: #2d2e76 !important;
|
||||
border: none !important;
|
||||
}
|
||||
:deep(.ant-slider-handle:hover) {
|
||||
box-shadow: 0 0 0 5px rgba(45, 46, 118, 0.2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
//颜色
|
||||
.modal_img{
|
||||
width: 100%;
|
||||
overflow-x: hidden;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
padding-left: calc(2rem*1.2);
|
||||
align-content: flex-start;
|
||||
&.modal_img::-webkit-scrollbar {
|
||||
display: none;
|
||||
}
|
||||
.modal_img_item{
|
||||
margin: 0 calc(1rem*1.2) calc(1rem*1.2) 0;
|
||||
position: relative;
|
||||
// cursor: pointer;
|
||||
border: calc(0.1rem*1.2) solid #DCDCEC;
|
||||
//放8个
|
||||
height: calc(8.5rem*1.2);
|
||||
width: calc(7rem*1.2);
|
||||
// height: 32rem*1.2);
|
||||
// width: 25rem*1.2);
|
||||
overflow: hidden;
|
||||
@media screen and (max-width: 1440px) {
|
||||
&.modal_img_item {
|
||||
line-height: 1.2;
|
||||
}
|
||||
}
|
||||
box-sizing: border-box;
|
||||
.color_content{
|
||||
width: 100%;
|
||||
//放8个
|
||||
height: calc(4rem*1.2);
|
||||
// height: 25rem*1.2);
|
||||
}
|
||||
.color_content_body{
|
||||
.color_des{
|
||||
// font-size: 1.8rem*1.2);
|
||||
font-weight: 600;
|
||||
white-space: nowrap;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
text-overflow:ellipsis;
|
||||
}
|
||||
}
|
||||
.select_upload_color{
|
||||
border: calc(0.1rem*1.2) solid #000;
|
||||
}
|
||||
.upload_color{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
//elements
|
||||
.result_apparel_elements{
|
||||
height: 85%;
|
||||
// height: 100%;
|
||||
.modal_img{
|
||||
height: calc(100%);
|
||||
overflow-y: auto;
|
||||
}
|
||||
.modal_img_item{
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
position: relative;
|
||||
// height: auto;
|
||||
border: none;
|
||||
img{
|
||||
width: 100%;
|
||||
object-fit: contain;
|
||||
}
|
||||
.delete_file_block{
|
||||
display: none;
|
||||
width: calc(3.2rem*1.2);
|
||||
height: calc(3.2rem*1.2);
|
||||
background: rgba(0,0,0,0.6);
|
||||
border-radius: calc(0.4rem*1.2);
|
||||
position: absolute;
|
||||
top: calc(0.9rem*1.2);
|
||||
right: calc(0.9rem*1.2);
|
||||
text-align: center;
|
||||
line-height: calc(3.2rem*1.2);
|
||||
left: auto;
|
||||
cursor: pointer;
|
||||
.icon-shanchu{
|
||||
font-size: calc(1.6rem*1.2);
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
&:hover .delete_file_block{
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
}
|
||||
.subitOkPreviewBtn{
|
||||
bottom: calc(3rem*1.2);
|
||||
position: absolute;
|
||||
&.clear{
|
||||
bottom: calc(7rem);
|
||||
}
|
||||
&.active{
|
||||
opacity: .5;
|
||||
pointer-events:none;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
</style>
|
||||
@@ -1,117 +0,0 @@
|
||||
<template>
|
||||
<a-modal class="hsitory_detail_modal_component"
|
||||
v-model:visible="hsitoryDetailShow"
|
||||
:footer="null"
|
||||
:title="collectionName"
|
||||
width="80%"
|
||||
:maskClosable="false"
|
||||
:keyboard="false"
|
||||
:centered="true"
|
||||
>
|
||||
<template #closeIcon>
|
||||
<div class="close_icon" @click.stop="changeDetailShow()"><span class="icon iconfont icon-guanbi"></span></div>
|
||||
</template>
|
||||
<div class="history_detail_content scroll_style">
|
||||
<div class="history_img_block" v-for="img in groupDetails" :key="img">
|
||||
<div class="history_img_item" >
|
||||
<img class="element_img" :src="img.url">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</a-modal>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import { defineComponent } from 'vue'
|
||||
|
||||
export default defineComponent({
|
||||
props:{
|
||||
groupDetails:{
|
||||
default:{},
|
||||
},
|
||||
collectionName:{
|
||||
default:''
|
||||
}
|
||||
},
|
||||
setup() {
|
||||
|
||||
},
|
||||
data(){
|
||||
return{
|
||||
hsitoryDetailShow:false,
|
||||
}
|
||||
},
|
||||
methods:{
|
||||
changeDetailShow(){
|
||||
this.hsitoryDetailShow = !this.hsitoryDetailShow
|
||||
}
|
||||
}
|
||||
})
|
||||
</script>
|
||||
<style lang="less">
|
||||
.hsitory_detail_modal_component{
|
||||
|
||||
.ant-modal-close{
|
||||
width: 3.6rem;
|
||||
height: 3.6rem;
|
||||
position: absolute;
|
||||
top: -1.8rem;
|
||||
right: -1.8rem;
|
||||
}
|
||||
|
||||
.ant-modal-header{
|
||||
background: #F7F7F7;
|
||||
}
|
||||
|
||||
.ant-modal-body{
|
||||
background: #F2F3FB;
|
||||
height: 80vh;
|
||||
min-height: 72rem;
|
||||
overflow-y: hidden;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.close_icon{
|
||||
width: 3.6rem;
|
||||
height: 3.6rem;
|
||||
background: #000000;
|
||||
border-radius: 50%;
|
||||
line-height: 3.6rem;
|
||||
text-align: center;
|
||||
|
||||
.icon-guanbi{
|
||||
font-size: 2rem;
|
||||
color: #ffffff;
|
||||
}
|
||||
}
|
||||
|
||||
.history_detail_content{
|
||||
padding: 2.6rem 2.0rem 2.6rem 3.7rem;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
overflow-y:auto;
|
||||
background: #FFFFFF;
|
||||
|
||||
.history_img_block{
|
||||
width: 16.5rem;
|
||||
height: 16.5rem;
|
||||
border: 0.1rem solid #000;
|
||||
margin: 0 1.7rem 1.7rem 0;
|
||||
display: inline-block;
|
||||
|
||||
.history_img_item{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.element_img{
|
||||
max-width: 100%;
|
||||
max-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -17,7 +17,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="#000"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="#000"/>
|
||||
|
||||
@@ -3,27 +3,16 @@
|
||||
<!-- designDetailShow -->
|
||||
<!-- :class="[driver__.driver?'hideEvents':'']" -->
|
||||
<div class="canvasContent" ref="canvasContent">
|
||||
<!-- <div class="argument-box">
|
||||
<argument
|
||||
ref="argument"
|
||||
class="argument"
|
||||
v-if="canvasObj.id || frontBackCanvasObj.id"
|
||||
@toolLiquefaction="toolLiquefaction"
|
||||
@setFrontBackColor="setFrontBackColor"
|
||||
:isEditFrontBack="isEditFrontBack">
|
||||
</argument>
|
||||
</div> -->
|
||||
<div class="content-bottom" ref="canvasContent">
|
||||
<!-- <div class="tool-box">
|
||||
<tool ref="tool" class="tool" v-if="canvasObj.id || frontBackCanvasObj.id" @toolLiquefaction="toolLiquefaction" @editFront="editFront" :isEditFrontBack="isEditFrontBack"></tool>
|
||||
</div> -->
|
||||
|
||||
<div class="contet">
|
||||
<div class="canvas" v-if="currentView === 'canvasEditor'" @click.stop>
|
||||
<editCanvas v-if="canvasLoad" :config="canvasConfig"
|
||||
@canvasInit="canvasInit"
|
||||
@changeCanvas="changeCanvas"
|
||||
:clothingImageUrl="selectDetail.undividedLayer"
|
||||
isFixedErasable
|
||||
showFixedLayer
|
||||
:canvasJSON="canvasJSON"
|
||||
:clothing-image-opts="{
|
||||
imageMode:'contains',
|
||||
}"
|
||||
@@ -70,9 +59,9 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- <div class="mark_loading" v-show="isShowMark">
|
||||
<div class="mark_loading" v-show="isShowMark">
|
||||
<a-spin size="large" />
|
||||
</div> -->
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</template>
|
||||
@@ -83,20 +72,15 @@ import { Modal,message } from 'ant-design-vue';
|
||||
import {getUploadUrl,isMoible,setGradual} from '@/tool/util'
|
||||
import { useStore } from "vuex";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import editFrontBack from '@/component/Detail/editFrontBack.vue'
|
||||
import editCanvas from "@/component/Canvas/CanvasEditor/index.vue";
|
||||
import { formatTime,segmentImage } from "@/tool/util";
|
||||
|
||||
|
||||
import canvasGeneral from "@/tool/canvasGeneralCopy";
|
||||
import argument from './argument.vue'
|
||||
import canvasContent from './canvasContent.vue'
|
||||
import tool from "./tool.vue"
|
||||
import { formatTime,segmentImage,getMinioUrl } from "@/tool/util";
|
||||
|
||||
export default defineComponent({
|
||||
components:{
|
||||
tool,argument,editFrontBack,editCanvas
|
||||
editCanvas
|
||||
},
|
||||
props:{
|
||||
},
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
const {t} = useI18n();
|
||||
@@ -112,45 +96,28 @@ export default defineComponent({
|
||||
return store.state.UserHabit.userDetail
|
||||
})
|
||||
const detailData = reactive({
|
||||
canvasObj:new canvasGeneral('aa'),
|
||||
frontBackCanvasObj:new canvasGeneral('vv'),
|
||||
isShowMark:false,
|
||||
liquefactionData:null as any,
|
||||
liquefaction:null as any,
|
||||
canvasType:'export',
|
||||
imgDomIndex:-1,
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
frontBack:computed(()=>store.state.DesignDetailCopy.frontBack),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
frontBack:computed(()=>store.state.DesignDetail.frontBack),
|
||||
canvasLoad:false,
|
||||
canvasConfig:{
|
||||
} as any,
|
||||
currentView:'canvasEditor',
|
||||
getCanvasIfEdit:inject('getCanvasIfEdit')as any,
|
||||
canvasInstance:null as any,
|
||||
canvasJSON:'',
|
||||
})
|
||||
watch(()=>detailData.selectDetail,(newValue,oldValue)=>{
|
||||
detailData.imgDomIndex = detailData.frontBack.front.findIndex((item:any)=>item.id == newValue.id)
|
||||
// privewDetail(oldValue)
|
||||
},{immediate: true})
|
||||
provide('frontBackCanvasObj',detailData.frontBackCanvasObj)
|
||||
provide('canvasObj',detailData.canvasObj)
|
||||
provide('isShowMark',detailData.isShowMark)
|
||||
provide('canvasType',detailData.canvasType)
|
||||
|
||||
const setLiquefaction = async ()=>{//进入液化页面
|
||||
detailData.canvasObj.getLiquefactionImgObj().then((data)=>{
|
||||
if(data?.img){
|
||||
detailData.liquefactionData = data
|
||||
detailData.liquefaction.init(data.img)
|
||||
}else {
|
||||
message.info(t('exportModel.jsContent6'))
|
||||
return null;
|
||||
}
|
||||
})
|
||||
}
|
||||
const toolLiquefaction = ()=>{//工具点击按钮
|
||||
setLiquefaction()
|
||||
}
|
||||
const editFront = (str:any)=>{//编辑前后片
|
||||
|
||||
let canvasJSON = '' as any
|
||||
@@ -192,8 +159,7 @@ export default defineComponent({
|
||||
if(!detailDom.editCanvas)return
|
||||
return new Promise((res,reject)=>{
|
||||
detailDom.editCanvas.exportImage({isContainBg:false,isContainFixed:true}).then((rv)=>{
|
||||
// let data = await detailData.canvasObj.detailSubmit()
|
||||
if(oldSelectDetail.partialDesign)oldSelectDetail.partialDesign.partialDesignBase64 = rv
|
||||
if(oldSelectDetail?.partialDesign)oldSelectDetail.partialDesign.partialDesignBase64 = rv
|
||||
res('')
|
||||
})
|
||||
})
|
||||
@@ -230,12 +196,12 @@ export default defineComponent({
|
||||
if(!front?.oldImageUrl)front.oldImageUrl = front.imageUrl
|
||||
if(!front?.oldMaskUrl)front.oldMaskUrl = front.imageUrl
|
||||
if(!back?.oldImageUrl)back.oldImageUrl = back.imageUrl
|
||||
if(!front?.oldMaskUrl)store.commit('DesignDetailCopy/updataDetailItem',{maskUrl:front.oldMaskUrl})
|
||||
if(!front?.oldMaskUrl)store.commit('DesignDetail/updataDetailItem',{maskUrl:front.oldMaskUrl})
|
||||
|
||||
front.imageUrl = rv.targetFrontUrl
|
||||
front.maskUrl = value
|
||||
back.imageUrl = rv.targetBackUrl
|
||||
store.commit('DesignDetailCopy/updataDetailItem',{maskUrl:value})
|
||||
store.commit('DesignDetail/updataDetailItem',{maskUrl:value})
|
||||
})
|
||||
|
||||
}
|
||||
@@ -243,17 +209,59 @@ export default defineComponent({
|
||||
// detailDom.editCanvas.addImageToLayer(detailData.selectDetail.undividedLayer,{layerId:value.layers.value[0].id,imageMode:'contains',undoable:false})
|
||||
detailData.canvasInstance = value
|
||||
detailData.getCanvasIfEdit.fun = getCanvasLength
|
||||
detailData.isShowMark = false
|
||||
}
|
||||
const getCanvasLength = ()=>{
|
||||
return detailData.canvasInstance?.commandManager?.undoStack?.length
|
||||
}
|
||||
const saveCanvas = async (type:string = '')=>{
|
||||
if(type !== 'auto'){
|
||||
detailData.isShowMark = true
|
||||
}
|
||||
const index = detailData.designDetail.clothes.findIndex(item => item.id === detailData.selectDetail.id);
|
||||
console.log(index,detailData.selectDetail.id)
|
||||
await new Promise<void>((resolve, reject) => {
|
||||
let canvasJSON = detailDom.editCanvas.getJSON()
|
||||
let canvasData = JSON.parse(canvasJSON)
|
||||
if(!canvasData)return
|
||||
canvasData.canvas.objects.forEach((objectsItem:any) => {
|
||||
if(objectsItem.type == 'image')objectsItem.minioUrl = getMinioUrl(objectsItem.src)
|
||||
});
|
||||
let blob = new Blob([JSON.stringify(canvasData)], { type: "application/json" });
|
||||
let formData = new FormData();
|
||||
formData.append("file", blob, "data.json");
|
||||
formData.append("designItemDetailId", detailData.selectDetail.id);
|
||||
formData.append("module", "designItemDetail");
|
||||
let config = {
|
||||
headers: { "Content-Type": "multipart/form-data", Accept: "*/*" },
|
||||
};
|
||||
Https.axiosPost(Https.httpUrls.exportSave, formData, config).then(
|
||||
(rv) => {
|
||||
if(index>-1)detailData.designDetail.clothes[index].canvasId = rv
|
||||
// detailData.selectDetail.canvasId = rv
|
||||
detailData.isShowMark = false
|
||||
resolve()
|
||||
}
|
||||
).catch(()=>{
|
||||
detailData.isShowMark = false
|
||||
resolve()
|
||||
});
|
||||
})
|
||||
}
|
||||
let time = null as any
|
||||
const changeCanvas = ()=>{
|
||||
clearTimeout(time)
|
||||
time = setTimeout(()=>{
|
||||
saveCanvas('auto')
|
||||
},3000)
|
||||
}
|
||||
onBeforeUnmount(()=>{
|
||||
let front = detailData.frontBack.front[detailData.imgDomIndex]
|
||||
let back = detailData.frontBack.back[detailData.imgDomIndex]
|
||||
if(front?.oldImageUrl)front.imageUrl = front.oldImageUrl
|
||||
if(front?.oldMaskUrl)front.maskUrl = front.oldMaskUrl
|
||||
if(back?.oldImageUrl)back.imageUrl = back.oldImageUrl
|
||||
if(front?.oldMaskUrl)store.commit('DesignDetailCopy/updataDetailItem',{maskUrl:front.oldMaskUrl})
|
||||
if(front?.oldMaskUrl)store.commit('DesignDetail/updataDetailItem',{maskUrl:front.oldMaskUrl})
|
||||
|
||||
sessionStorage.removeItem('frontBackEdit');
|
||||
sessionStorage.removeItem('sketchEdit');
|
||||
@@ -261,7 +269,26 @@ export default defineComponent({
|
||||
privewDetail()
|
||||
})
|
||||
onMounted(()=>{
|
||||
nextTick(()=>{
|
||||
nextTick(async ()=>{
|
||||
console.log(JSON.parse(JSON.stringify(detailData.selectDetail)))
|
||||
detailData.isShowMark = true
|
||||
if(detailData.selectDetail.canvasId){
|
||||
await new Promise((resolve, reject) => {
|
||||
let value = {
|
||||
module:'designItemDetail',
|
||||
id:detailData.selectDetail.canvasId,
|
||||
}
|
||||
Https.axiosPost(Https.httpUrls.exportSearch, value)
|
||||
.then((rv) => {
|
||||
detailData.canvasJSON = rv
|
||||
resolve('')
|
||||
})
|
||||
.catch((rv) => {
|
||||
resolve(null)
|
||||
});
|
||||
})
|
||||
}
|
||||
|
||||
setCanvas(detailData.selectDetail.undividedLayer).then(()=>{
|
||||
detailData.canvasLoad = true
|
||||
})
|
||||
@@ -270,12 +297,13 @@ export default defineComponent({
|
||||
return{
|
||||
...toRefs(detailDom),
|
||||
...toRefs(detailData),
|
||||
toolLiquefaction,
|
||||
editFront,
|
||||
privewDetail,
|
||||
setFrontBackColor,
|
||||
frontBackChange,
|
||||
canvasInit,
|
||||
saveCanvas,
|
||||
changeCanvas,
|
||||
}
|
||||
},
|
||||
provide() {
|
||||
@@ -53,9 +53,9 @@ export default defineComponent({
|
||||
const {t} = useI18n();
|
||||
const colorData = reactive({
|
||||
selectTitle:'current',
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
allBoardData:computed(()=>store.state.UploadFilesModule.allBoardData),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
colorList:{
|
||||
list:{},
|
||||
index:-1,
|
||||
@@ -91,13 +91,13 @@ export default defineComponent({
|
||||
data:newVal,
|
||||
str:'color'
|
||||
}
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}else{
|
||||
let value = {
|
||||
data:{},
|
||||
str:'color'
|
||||
}
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}
|
||||
})
|
||||
watch(()=>colorData.selectDetail.id,(newVal,oldVal)=>{
|
||||
@@ -49,7 +49,7 @@ export default defineComponent({
|
||||
const {t} = useI18n();
|
||||
const store = useStore();
|
||||
const colorUpload = reactive({
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
|
||||
uploadList:{} as any,
|
||||
indicator: h(LoadingOutlined, {
|
||||
@@ -30,12 +30,12 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectTitle:'current',
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
printCatecoryList:computed(()=>{
|
||||
return store.state.UserHabit.designElementsType
|
||||
}),
|
||||
elementList:[],
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType)
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType)
|
||||
})
|
||||
watch(()=>detailData?.selectDetail?.trims?.prints,(newVal,oldVal)=>{
|
||||
if(!newVal)return
|
||||
@@ -72,17 +72,17 @@ export default defineComponent({
|
||||
minIOPath:data.minIOPath,
|
||||
url:data.path,
|
||||
}
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',value)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',value)
|
||||
}
|
||||
const selectImgItem = (data:any)=>{
|
||||
let value = {
|
||||
data,
|
||||
}
|
||||
if(detailData.currentDetailType != 'print' && detailData.currentDetailType != 'element'){
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}else{
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',null)
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',data)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',null)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',data)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -30,8 +30,8 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectTitle:'upload',
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
total:0,
|
||||
@@ -27,13 +27,13 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectTitle:'current',
|
||||
frontBack:computed(()=>store.state.DesignDetailCopy.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
frontBack:computed(()=>store.state.DesignDetail.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
sketchCatecoryList:computed(()=>{
|
||||
return store.state.UserHabit.sex.value
|
||||
}),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType)
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType)
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
total:0,
|
||||
@@ -58,7 +58,7 @@ export default defineComponent({
|
||||
let value = {
|
||||
data,
|
||||
}
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}
|
||||
const openAddDetail = ()=>{
|
||||
emit('addDetail')
|
||||
@@ -48,7 +48,7 @@ export default defineComponent({
|
||||
color:computed(()=>store.state.UploadFilesModule.allBoardData.colorBoards),
|
||||
models:computed(()=>store.state.Workspace.probjects.model),
|
||||
},
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
@@ -63,7 +63,7 @@ export default defineComponent({
|
||||
file.designType = file.resData.designType
|
||||
}
|
||||
}
|
||||
// store.commit('DesignDetailCopy/setNewDetail',file.resData)
|
||||
// store.commit('DesignDetail/setNewDetail',file.resData)
|
||||
emit('selectImgItem',file)
|
||||
}
|
||||
|
||||
@@ -154,7 +154,7 @@ export default defineComponent({
|
||||
designTypeList:computed(()=>props.catecoryList) as any,
|
||||
designType:'',
|
||||
searchPictureName:'',
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
mannequinData:{
|
||||
sex:'Female',
|
||||
style:'',
|
||||
@@ -200,7 +200,7 @@ export default defineComponent({
|
||||
const selectImgItem = (file:any)=>{
|
||||
let randomNum = Math.floor(100 + Math.random() * 900);
|
||||
let type = props.type
|
||||
// let type = store.state.DesignDetailCopy.currentDetailType
|
||||
// let type = store.state.DesignDetail.currentDetailType
|
||||
let id = file.id
|
||||
if(type == 'sketch'){
|
||||
id = Number(file.id + (randomNum + ''))
|
||||
@@ -217,7 +217,7 @@ export default defineComponent({
|
||||
data.id = id
|
||||
}
|
||||
emit('selectImgItem',data)
|
||||
// store.commit('DesignDetailCopy/setNewDetail',data)
|
||||
// store.commit('DesignDetail/setNewDetail',data)
|
||||
}
|
||||
const getLibraryList = ()=>{
|
||||
if(props.type == 'models'){
|
||||
@@ -260,7 +260,7 @@ export default defineComponent({
|
||||
detailData.isShowLoading = true
|
||||
let level2Type = ''
|
||||
let workspace = store.state.Workspace.probjects
|
||||
// let type = store.state.DesignDetailCopy.currentDetailType
|
||||
// let type = store.state.DesignDetail.currentDetailType
|
||||
let data = {
|
||||
level1Type:props.level1Type,
|
||||
// level2Type:'Pattern',
|
||||
@@ -89,7 +89,7 @@ export default defineComponent({
|
||||
},
|
||||
token:getCookie("token"),
|
||||
uploadUrl:getUploadUrl(),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType)
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType)
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
total:0,
|
||||
@@ -98,7 +98,7 @@ export default defineComponent({
|
||||
})
|
||||
const selectImgItem = (file:any)=>{
|
||||
// let data = JSON.parse(JSON.stringify(file))
|
||||
// store.commit('DesignDetailCopy/setNewDetail',file)
|
||||
// store.commit('DesignDetail/setNewDetail',file)
|
||||
emit('selectImgItem',file)
|
||||
}
|
||||
const upFileUploadChange = (data:any)=>{
|
||||
@@ -76,7 +76,7 @@ export default defineComponent({
|
||||
},
|
||||
token:getCookie("token"),
|
||||
uploadUrl:getUploadUrl(),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
})
|
||||
const dataDom = reactive({
|
||||
uploadModel:null as any
|
||||
@@ -88,7 +88,7 @@ export default defineComponent({
|
||||
})
|
||||
const selectImgItem = (file:any)=>{
|
||||
// let data = JSON.parse(JSON.stringify(file))
|
||||
// store.commit('DesignDetailCopy/setNewDetail',file)
|
||||
// store.commit('DesignDetail/setNewDetail',file)
|
||||
emit('selectImgItem',file)
|
||||
}
|
||||
const setUploadImgList = (list:any)=>{
|
||||
@@ -30,12 +30,12 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectTitle:'current',
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
printCatecoryList:computed(()=>{
|
||||
return store.state.UserHabit.printType
|
||||
}),
|
||||
printList:[],
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType)
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType)
|
||||
})
|
||||
watch(()=>detailData?.selectDetail?.printObject?.prints,(newVal,oldVal)=>{
|
||||
if(!newVal)return
|
||||
@@ -71,17 +71,17 @@ export default defineComponent({
|
||||
minIOPath:data.minIOPath,
|
||||
url:data.path,
|
||||
}
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',value)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',value)
|
||||
}
|
||||
const selectImgItem = (data:any)=>{
|
||||
let value = {
|
||||
data,
|
||||
}
|
||||
if(detailData.currentDetailType != 'print' && detailData.currentDetailType != 'element'){
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}else{
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',null)
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',data)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',null)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',data)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,11 +34,11 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectTitle:'current',
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
sketchCatecoryList:computed(()=>{
|
||||
return store.state.Workspace.probjects.positionList
|
||||
}),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType)
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType)
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
total:0,
|
||||
@@ -67,7 +67,7 @@ export default defineComponent({
|
||||
if(detailData.currentDetailType == 'sketch'){
|
||||
detailData.selectDetail.sketchString = ''
|
||||
}
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}
|
||||
const openAddDetail = ()=>{
|
||||
emit('addDetail')
|
||||
@@ -121,9 +121,9 @@ export default defineComponent({
|
||||
sketchImg:null as any,
|
||||
})
|
||||
const editPrintElementData = reactive({
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
currentPrintElement:computed(()=>store.state.DesignDetailCopy.currentPrintElement),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
currentPrintElement:computed(()=>store.state.DesignDetail.currentPrintElement),
|
||||
overallSingle:true,
|
||||
systemDesignerPercentage:0,
|
||||
printStyleList:{
|
||||
@@ -221,7 +221,7 @@ export default defineComponent({
|
||||
}
|
||||
getItemPosition(item)
|
||||
setItemPosition()
|
||||
store.commit('DesignDetailCopy/setCurrentPrintElement',null)
|
||||
store.commit('DesignDetail/setCurrentPrintElement',null)
|
||||
}
|
||||
const previewDetailPrintData = ()=>{
|
||||
let data:any = []
|
||||
@@ -270,7 +270,7 @@ export default defineComponent({
|
||||
data,
|
||||
str:props.type
|
||||
}
|
||||
store.commit('DesignDetailCopy/setNewDetail',value)
|
||||
store.commit('DesignDetail/setNewDetail',value)
|
||||
}
|
||||
const sort = (list:any)=>{
|
||||
list.sort((a:any,b:any)=>{
|
||||
@@ -27,10 +27,10 @@ export default defineComponent({
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
editPrintElement:null as any,
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
})
|
||||
const privewDetail = ()=>{
|
||||
if(detailData.editPrintElement?.previewDetailPrintData)detailData.editPrintElement.previewDetailPrintData()
|
||||
@@ -19,8 +19,8 @@ export default defineComponent({
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
|
||||
@@ -39,8 +39,8 @@ export default defineComponent({
|
||||
sketchCatecoryList:computed(()=>{
|
||||
return store.state.UserHabit.printType
|
||||
}),
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
selectList:[],
|
||||
})
|
||||
watch(()=>detailData.selectDetail?.printObject?.prints,(newVal,oldVal)=>{
|
||||
@@ -19,8 +19,8 @@ export default defineComponent({
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
})
|
||||
const getDetailListData = reactive({
|
||||
|
||||
@@ -1,447 +0,0 @@
|
||||
<template>
|
||||
<div class="editFrontBack_center">
|
||||
<!-- <div class="editFrontBack_center_btn editFrontBack_center_item" :class="{spread:spreadState}">
|
||||
<i class="icon iconfont icon-chehui" @click="historyState('')"></i>
|
||||
<i class="icon iconfont icon-fanchehui" @click="historyState('reverse')"></i>
|
||||
<i class="icon iconfont icon-bianji" @click="setOperation('pencil')" :class="{active:canvasState == 'pencil'}"></i>
|
||||
<div class="editFrontBack_center_btn_colorRed" @click="setOperationColor('rgb(255,0,0)')" :class="{active:(canvasState != 'eraser' && rgba == 'rgb(255,0,0)')}" title="front">front</div>
|
||||
<div class="editFrontBack_center_btn_colorGreen" @click="setOperationColor('rgb(0,255,0)')" :class="{active:(canvasState != 'eraser' && rgba == 'rgb(0,255,0)')}" title="back">back</div>
|
||||
<div class="editFrontBack_center_btn_colorWhite" @click="setOperation('eraser')" :class="{active:canvasState == 'eraser'}" title="background">background</div>
|
||||
<input type="range" v-show="canvasState != 'move'" @input="setPencilWidth" min="1" max="50" v-model="canvasPencilWidth[canvasState]">
|
||||
</div> -->
|
||||
<div class="exportCanvasBox_center_box">
|
||||
<div class="exportCanvasBox_center">
|
||||
<div class="editFrontBack_bgImg" v-show="loadingShow">
|
||||
<img :src="imgData?.undividedLayer" alt="">
|
||||
</div>
|
||||
<div class="editFrontBack_pencilbtn" v-show="loadingShow" :style="frontBackCanvasObj.pencilbtnStyle" style="display: block;"></div>
|
||||
|
||||
</div>
|
||||
<!-- <div class="editFrontBack_pencilbtn" v-show="loadingShow" :style="pencilbtnStyle"></div> -->
|
||||
<!--
|
||||
<div class="editFrontBack_pencilbtn" v-show="loadingShow" :style="frontBackCanvasObj.pencilbtnStyle" style="display: block;"></div>
|
||||
{{frontBackCanvasObj.pencilbtnStyle}} -->
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import { defineComponent, ref, reactive, inject, onMounted, nextTick, toRefs, onBeforeUnmount, watch, computed } from "vue";
|
||||
import { formatTime,segmentImage } from "@/tool/util";
|
||||
import { exportSele,JSRectUpdata,JSchangeType,JScanvasMouseDown,JSSetRemoveImage,JScreateCheck,JSSetTexture } from "@/tool/canvasDrawing";
|
||||
import { getMousePosition } from "@/tool/mdEvent";
|
||||
import { useStore } from "vuex";
|
||||
import { useI18n } from "vue-i18n";
|
||||
export default defineComponent({
|
||||
components: {
|
||||
},
|
||||
// emits: ['setSloganData'],
|
||||
props:['patchData','imgDomIndex'],
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
let presentState = ref('paypal');
|
||||
let loadingShow = ref(false);
|
||||
let { t } = useI18n();
|
||||
// let canvas = new frontBackCanvasObjCopy();
|
||||
let canvas = null;
|
||||
let frontBackCanvasObj = inject('frontBackCanvasObj')
|
||||
let ratio = [1,1]
|
||||
let exportWH = 0
|
||||
let imgData = ref()
|
||||
let pencilbtnStyle = ref({
|
||||
background:'',
|
||||
width:0+'px',
|
||||
height:0+'px',
|
||||
display:'none',
|
||||
left:0+'px',
|
||||
top:0+'px',
|
||||
})
|
||||
let selectDetail = computed(()=>store.state.DesignDetailCopy.selectDetail)
|
||||
|
||||
// let a = computed(()=>{
|
||||
// console.log(123);
|
||||
// return props.patchData
|
||||
// })
|
||||
watch(()=>pencilbtnStyle.value.background,(newVal)=>{
|
||||
frontBackCanvasObj.brushwork.color = newVal
|
||||
frontBackCanvasObj.setPencilColor()
|
||||
})
|
||||
onMounted(()=>{
|
||||
props.patchData.front.imageUrl= ''
|
||||
clearTimeout(setTimeSubmit)
|
||||
// init(props.patchData.front[props.imgDomIndex],'')
|
||||
})
|
||||
let canvasBtn = reactive({
|
||||
canvasState:'move',
|
||||
canvasPencilWidth:{
|
||||
pencil:20,
|
||||
eraser:20,
|
||||
},
|
||||
spreadState:false,
|
||||
})
|
||||
let canvasWH = ref(0);
|
||||
|
||||
let reverseCanvasState = ref([])//存放canvas操作
|
||||
let normalCanvasState = ref([])//存放canvas操作
|
||||
|
||||
let down = false
|
||||
let init = (data,index)=>{
|
||||
normalCanvasState.value = []
|
||||
reverseCanvasState.value = []
|
||||
ratio = [1,1]
|
||||
imgData.value = data
|
||||
nextTick(()=>{
|
||||
let contentBox = document.querySelector(".editFrontBack_center");
|
||||
let canvasBox = document.querySelector(".editFrontBack_center .exportCanvasBox_center");
|
||||
let editFrontBack_bgImg = document.querySelector(".editFrontBack_center .editFrontBack_bgImg");
|
||||
document.removeEventListener('mousemove', mouseMove);
|
||||
document.removeEventListener('touchmove', touchmove);
|
||||
let img = new Image();
|
||||
img.onload = async function(){
|
||||
loadingShow.value = true
|
||||
let scale
|
||||
|
||||
|
||||
let wScale = 1
|
||||
let hScale = 1
|
||||
let styleWidth = Number(data.style.width.split('px')[0])
|
||||
let styleHeight = Number(data.style.height.split('px')[0])
|
||||
let width = contentBox.offsetWidth;
|
||||
let height = contentBox.offsetHeight;
|
||||
if(styleWidth>styleHeight){
|
||||
hScale = styleHeight/styleWidth
|
||||
exportWH = img.width
|
||||
canvasWH.value = width
|
||||
scale = img.height/img.width
|
||||
console.log(width,scale)
|
||||
canvasBox.style.height = width * scale+'px'
|
||||
}else{
|
||||
wScale = styleWidth/styleHeight
|
||||
exportWH = img.height
|
||||
canvasWH.value = height
|
||||
scale = img.width/img.height
|
||||
canvasBox.style.width = height * scale+'px'
|
||||
}
|
||||
editFrontBack_bgImg.style.width = canvasWH.value * wScale+'px'
|
||||
editFrontBack_bgImg.style.height = canvasWH.value * hScale+'px'
|
||||
ratio = [wScale,hScale]
|
||||
await frontBackCanvasObj.canvasInit(canvasBox,{
|
||||
width:canvasWH.value * wScale,
|
||||
height:canvasWH.value * hScale,
|
||||
},data.maskUrl,'',{noWheel:true})
|
||||
// undividedLayer
|
||||
canvas = frontBackCanvasObj.canvas
|
||||
|
||||
frontBackCanvasObj.setOperation('pencil')
|
||||
pencilbtnStyle.value.background = rgba.value
|
||||
// console.log(frontBackCanvasObj,frontBackCanvasObj.setPencilWidth);
|
||||
frontBackCanvasObj.setPencilWidth()
|
||||
fabric.Object.prototype.cornerSize = 10
|
||||
fabric.Object.prototype.transparentCorners = false
|
||||
// await frontBackCanvasObj.addPartImg({minioUrl:data.maskUrl},'',{opacity: 0.5})
|
||||
|
||||
// await new Promise((resolve, reject) => {
|
||||
// fabric.Image.fromURL(data.maskUrl, function(img) {
|
||||
// // 设置背景图对象的宽度和高度与 canvas 相同
|
||||
// canvas.add(img)
|
||||
// resolve('')
|
||||
// },{ crossOrigin: "Anonymous" });
|
||||
// })
|
||||
|
||||
|
||||
//画布上移动
|
||||
// canvas.on("mouse:move", event =>setCanvasMove(event));
|
||||
canvas.on('mouse:up', (event)=> {
|
||||
updateCanvasState('mouseUp')
|
||||
});
|
||||
document.addEventListener('mousemove', mouseMove);
|
||||
document.addEventListener('touchmove', touchmove);
|
||||
createSetTimeSubmit()
|
||||
img.remove()
|
||||
}
|
||||
img.src = data.maskUrl
|
||||
|
||||
})
|
||||
}
|
||||
const setBackground = (value)=>{
|
||||
if(value == 'background'){
|
||||
frontBackCanvasObj.setOperation('eraser')
|
||||
}else{
|
||||
frontBackCanvasObj.setOperation('pencil')
|
||||
frontBackCanvasObj.brushwork.color = value
|
||||
frontBackCanvasObj.pencilColor()
|
||||
}
|
||||
}
|
||||
let updateCanvasState = (str) =>{
|
||||
if(str != 'mouseUp'){
|
||||
// editFrontBackPencilbtn.value.style.display = 'none'
|
||||
}else{
|
||||
clearTimeout(setTimeSubmit)
|
||||
setTimeSubmit = setTimeout(()=>{
|
||||
createSetTimeSubmit()
|
||||
},1000)
|
||||
}
|
||||
}
|
||||
let setClone = ()=>{
|
||||
let canvasBox = document.querySelector(".editFrontBack_center .exportCanvasBox_center");
|
||||
let oldCanvasDom = canvasBox.querySelector('.canvas-container')
|
||||
let oldCanvasDom1 = canvasBox.querySelector('canvas')
|
||||
if(oldCanvasDom)oldCanvasDom.remove()
|
||||
if(oldCanvasDom1)oldCanvasDom1.remove()
|
||||
loadingShow.value = false
|
||||
}
|
||||
let rgba = ref('#ff0000')
|
||||
let mouseMove = (event)=>{
|
||||
let e = getMousePosition(event,false)
|
||||
setCanvasMove(e)
|
||||
}
|
||||
let touchmove = (event)=>{
|
||||
let e = getMousePosition(event,true)
|
||||
setCanvasMove(e)
|
||||
}
|
||||
let setCanvasMove = (event)=>{
|
||||
if(canvas.isDrawingMode && canvas){
|
||||
canvas.setCursor('none');
|
||||
}
|
||||
let canvasCenterBox = document.querySelector(".editFrontBack_center .exportCanvasBox_center_box");
|
||||
if(!canvasCenterBox)return
|
||||
let parentX = event.clientX - canvasCenterBox.getBoundingClientRect().left
|
||||
let parentY = event.clientY - canvasCenterBox.getBoundingClientRect().top
|
||||
pencilbtnStyle.value.left = parentX + "px"
|
||||
pencilbtnStyle.value.top = parentY+'px'
|
||||
}
|
||||
let mousedown = (e)=>{
|
||||
if(e.target instanceof HTMLCanvasElement){
|
||||
down = true
|
||||
}
|
||||
}
|
||||
let mouseup = (e)=>{
|
||||
if(down){
|
||||
nextTick(()=>{
|
||||
createSetTimeSubmit()
|
||||
})
|
||||
}
|
||||
down = false
|
||||
}
|
||||
let setTimeSubmit = null
|
||||
let createSetTimeSubmit = ()=>{
|
||||
setSubmit()
|
||||
}
|
||||
//撤回
|
||||
|
||||
let setSubmit = async ()=>{
|
||||
// let data = await frontBackCanvasObj.allExport()
|
||||
let data = await frontBackCanvasObj.detailSubmit()
|
||||
// props.props.patchData.front[imgDomIndex].imageUrl = data
|
||||
let mark = data
|
||||
let full = props.patchData.front[props.imgDomIndex].undividedLayer
|
||||
let size = {
|
||||
width: Math.round(exportWH * ratio[0]),
|
||||
height: Math.round(exportWH * ratio[1]),
|
||||
}
|
||||
segmentImage(mark,full,size).then((rv)=>{
|
||||
props.patchData.front[props.imgDomIndex].imageUrl = rv.targetFrontUrl
|
||||
props.patchData.back[props.imgDomIndex].imageUrl = rv.targetBackUrl
|
||||
props.patchData.front[props.imgDomIndex].maskUrl = data
|
||||
store.commit('DesignDetailCopy/updataDetailItem',{maskUrl:data})
|
||||
})
|
||||
}
|
||||
onBeforeUnmount(()=>{
|
||||
frontBackCanvasObj.canvasClear()
|
||||
document.removeEventListener('mousemove', mouseMove);
|
||||
document.removeEventListener('touchmove', touchmove);
|
||||
document.removeEventListener('mousedown', mousedown);
|
||||
document.removeEventListener('mouseup', mouseup);
|
||||
})
|
||||
return {
|
||||
frontBackCanvasObj,
|
||||
presentState,
|
||||
loadingShow,
|
||||
imgData,
|
||||
pencilbtnStyle,
|
||||
t,
|
||||
...toRefs(canvasBtn),
|
||||
setBackground,
|
||||
init,
|
||||
setSubmit,
|
||||
setClone,
|
||||
};
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
};
|
||||
},
|
||||
mounted() {},
|
||||
methods: {
|
||||
|
||||
},
|
||||
});
|
||||
</script>
|
||||
<style lang="less" scoped>
|
||||
.editFrontBack_center{
|
||||
position: relative;
|
||||
// width: calc(512px / 2);
|
||||
// width: 256px;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
// height: calc(512px / 2);
|
||||
margin: 0 auto;
|
||||
.editFrontBack_center_item{
|
||||
// position: relative;
|
||||
background: #ffffff;
|
||||
position: absolute;
|
||||
|
||||
display: flex;
|
||||
border: 0.2rem solid #c4c4c4;
|
||||
width: 35rem;
|
||||
border-radius: 4px; /* 设置圆角半径 */
|
||||
flex-wrap: wrap;
|
||||
align-items: center;
|
||||
.editFrontBack_center_btn_item{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding: 1rem 0;
|
||||
|
||||
}
|
||||
}
|
||||
.editFrontBack_center_btn{
|
||||
z-index: 2;
|
||||
left: 50%;
|
||||
// transform: translate(-50%,-135%);
|
||||
// transition: all .3s;
|
||||
padding: 1rem 1.5rem;
|
||||
transform: translate(-50%,0);
|
||||
position: relative;
|
||||
width: 100%;
|
||||
flex-direction: row;
|
||||
input{
|
||||
// width: 100%;
|
||||
flex: 1;
|
||||
max-width: 30%;
|
||||
}
|
||||
.icon-xiala{
|
||||
position: absolute;
|
||||
width: 2rem;
|
||||
bottom: 0;
|
||||
transform: translate(-50%, 90%);
|
||||
left: 50%;
|
||||
width: 6rem;
|
||||
background: #fff;
|
||||
text-align: center;
|
||||
cursor: pointer;
|
||||
&.icon-xiala::before{
|
||||
transition: all .3s;
|
||||
}
|
||||
&.btnRotate::before{
|
||||
transform: rotate(180deg);
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.editFrontBack_center_btn_colorRed,.editFrontBack_center_btn_colorGreen,.editFrontBack_center_btn_colorWhite{
|
||||
width: 9rem;
|
||||
line-height: 3rem;
|
||||
text-align: center;
|
||||
height: 3rem;
|
||||
border-radius: 4px;
|
||||
margin: 0 .5rem;
|
||||
cursor: pointer;
|
||||
padding: .5rem 1;
|
||||
border: 1px solid rgba(0,0,0,.5);
|
||||
&.active{
|
||||
border: 2px solid;
|
||||
border-radius: .4rem;
|
||||
}
|
||||
}
|
||||
.editFrontBack_center_btn_colorRed{
|
||||
background: rgba(255,0,0);
|
||||
}
|
||||
.editFrontBack_center_btn_colorGreen{
|
||||
background: rgba(0,255,0);
|
||||
}
|
||||
.editFrontBack_center_btn_colorWhite{
|
||||
background: rgba(255,255,255);
|
||||
}
|
||||
i{
|
||||
font-size: 2.5rem;
|
||||
cursor: pointer;
|
||||
width: 4rem;
|
||||
height: 4rem;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
&.active{
|
||||
border: 1px solid;
|
||||
border-radius: .4rem;
|
||||
}
|
||||
}
|
||||
&.spread{
|
||||
transform: translate(-50%,0);
|
||||
}
|
||||
}
|
||||
.exportCanvasBox_center_box{
|
||||
height: 100%;
|
||||
flex: 1;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
width: 100%;
|
||||
background: #e6e6e6;
|
||||
cursor: auto;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
&:hover{
|
||||
cursor: none;
|
||||
}
|
||||
.editFrontBack_pencilbtn{
|
||||
position: absolute;
|
||||
z-index: 1;
|
||||
border-radius: 50%;
|
||||
border: 1px solid #000;
|
||||
pointer-events: none;
|
||||
transform: translate(-50%,-50%);
|
||||
}
|
||||
}
|
||||
.exportCanvasBox_center{
|
||||
margin: 0 auto;
|
||||
overflow: hidden;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
// overflow: scroll;
|
||||
cursor: none;
|
||||
:deep(.canvas-container){
|
||||
left: 50%;
|
||||
top: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
// opacity: .5;
|
||||
// background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQAQMAAAAlPW0iAAAAA3NCSVQICAjb4U/gAAAABlBMVEXMzMz////TjRV2AAAACXBIWXMAAArrAAAK6wGCiw1aAAAAHHRFWHRTb2Z0d2FyZQBBZG9iZSBGaXJld29ya3MgQ1M26LyyjAAAABFJREFUCJlj+M/AgBVhF/0PAH6/D/HkDxOGAAAAAElFTkSuQmCC);
|
||||
}
|
||||
.editFrontBack_bgImg{
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
top: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
z-index: 2;
|
||||
pointer-events:none;
|
||||
opacity: .5;
|
||||
img{
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
.exportCanvasBox_center:hover{
|
||||
.editFrontBack_center_btn{
|
||||
transform: translate(-50%,-101%);
|
||||
&.spread{
|
||||
transform: translate(-50%,0);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -1,155 +0,0 @@
|
||||
<template>
|
||||
<div class="magnifyingGlass">
|
||||
<div class="initial">
|
||||
<div class="initial_mask" v-mousemove>
|
||||
<img class="initial_img" :src="imageUrl" alt="">
|
||||
<div class="initial_haver"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="big"></div>
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import { getUploadUrl,isMoible } from "@/tool/util";
|
||||
import { defineComponent, createVNode, ref,Ref} from "vue";
|
||||
import { UserOutlined, DownOutlined } from "@ant-design/icons-vue";
|
||||
export default defineComponent({
|
||||
components: {
|
||||
DownOutlined,
|
||||
UserOutlined,
|
||||
},
|
||||
props: ['designItemDetailUrl'],
|
||||
setup(props){
|
||||
let imageUrl = ref()
|
||||
let showGlass = ref(false)
|
||||
return{
|
||||
imageUrl,
|
||||
showGlass
|
||||
}
|
||||
},
|
||||
watch:{
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
};
|
||||
},
|
||||
mounted() {
|
||||
},
|
||||
directives:{
|
||||
mousemove:{
|
||||
|
||||
mounted (el,binding) {
|
||||
if(isMoible()){
|
||||
let touchstart = (event)=>{//移入
|
||||
const mask = document.getElementsByClassName('magnifyingGlass')[0].querySelector('.initial_haver')
|
||||
const initialImg = document.getElementsByClassName('magnifyingGlass')[0].querySelector(".initial_img");
|
||||
const bigImg = document.getElementsByClassName('magnifyingGlass')[0].querySelector(".big");
|
||||
const maskW = mask.getBoundingClientRect().width;
|
||||
const bigImgW = bigImg.getBoundingClientRect().width;
|
||||
const num = bigImgW / maskW
|
||||
bigImg.style.backgroundImage = `url(${initialImg.src})`;
|
||||
const { left, top} = initialImg.getBoundingClientRect();
|
||||
const initialImgH = initialImg.getBoundingClientRect().height
|
||||
const initialImgW = initialImg.getBoundingClientRect().width;
|
||||
const {width,height} = mask.getBoundingClientRect();
|
||||
let touchmove = (event)=>{//移动
|
||||
const x = event.targetTouches[0].pageX - left;
|
||||
const y = event.targetTouches[0].pageY - top;
|
||||
const bgPosX = (-x+width/2 )* num;
|
||||
const bgPosY = (-y+height/2) * num;
|
||||
const bgPosW = initialImgW * num;
|
||||
const bgPosH = initialImgH * num;
|
||||
mask.style.top = y-height/2+'px';
|
||||
mask.style.left = x-width/2+'px';
|
||||
bigImg.style.backgroundPosition = `${bgPosX}px ${bgPosY}px`;
|
||||
bigImg.style.backgroundSize = `${bgPosW}px ${bgPosH}px`;
|
||||
}
|
||||
document.addEventListener('touchmove',touchmove,{passive:true})
|
||||
el.addEventListener('touchend',()=>{
|
||||
document.removeEventListener('touchmove',touchmove)
|
||||
document.removeEventListener('touchstart',touchstart)
|
||||
})
|
||||
}
|
||||
el.addEventListener('touchstart',touchstart)
|
||||
}else{
|
||||
let mouseover = (event)=>{//移入
|
||||
const mask = document.getElementsByClassName('magnifyingGlass')[0].querySelector('.initial_haver')
|
||||
const initialImg = document.getElementsByClassName('magnifyingGlass')[0].querySelector(".initial_img");
|
||||
const bigImg = document.getElementsByClassName('magnifyingGlass')[0].querySelector(".big");
|
||||
const maskW = mask.getBoundingClientRect().width;
|
||||
const bigImgW = bigImg.getBoundingClientRect().width;
|
||||
const num = bigImgW / maskW
|
||||
bigImg.style.backgroundImage = `url(${initialImg.src})`;
|
||||
const { left, top} = initialImg.getBoundingClientRect();
|
||||
const initialImgH = initialImg.getBoundingClientRect().height
|
||||
const initialImgW = initialImg.getBoundingClientRect().width;
|
||||
const {width,height} = mask.getBoundingClientRect();
|
||||
let mousemove = (event)=>{//移动
|
||||
const x = event.clientX - left;
|
||||
const y = event.clientY - top;
|
||||
const bgPosX = (-x+width/2 )* num;
|
||||
const bgPosY = (-y+height/2) * num;
|
||||
const bgPosW = initialImgW * num;
|
||||
const bgPosH = initialImgH * num;
|
||||
mask.style.top = y-height/2+'px';
|
||||
mask.style.left = x-width/2+'px';
|
||||
bigImg.style.backgroundPosition = `${bgPosX}px ${bgPosY}px`;
|
||||
bigImg.style.backgroundSize = `${bgPosW}px ${bgPosH}px`;
|
||||
}
|
||||
document.addEventListener('mousemove',mousemove)
|
||||
el.addEventListener('mouseout',()=>{
|
||||
document.removeEventListener('mousemove',mousemove)
|
||||
document.removeEventListener('mouseover',mouseover)
|
||||
})
|
||||
}
|
||||
el.addEventListener('mouseover',mouseover)
|
||||
}
|
||||
|
||||
},
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
handleMouseMove(event) {
|
||||
|
||||
},
|
||||
},
|
||||
});
|
||||
</script>
|
||||
<style lang="less" scoped>
|
||||
.magnifyingGlass{
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
.initial{
|
||||
justify-content: center;
|
||||
width: 40%;
|
||||
text-align: center;
|
||||
.initial_mask{
|
||||
overflow: hidden;
|
||||
width: auto;
|
||||
height: 100%;
|
||||
display: inline-block;
|
||||
position: relative;
|
||||
.initial_img{
|
||||
height: 100%;
|
||||
width: auto;
|
||||
max-width: 100%;
|
||||
}
|
||||
.initial_haver{
|
||||
width: calc(10rem*1.2);
|
||||
height: calc(10rem*1.2);
|
||||
position: absolute;
|
||||
background-color: rgba(0,0,0,.2);
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
.big{
|
||||
width: 40%;
|
||||
background-position: 0 0;
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
}
|
||||
</style>
|
||||
@@ -48,7 +48,7 @@ export default defineComponent({
|
||||
})
|
||||
const setRevocation:any = inject('setRevocation')
|
||||
const getDetailListData = reactive({
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
isEditPattern:inject('isEditPattern') as any,
|
||||
imgDesignImg:false,
|
||||
})
|
||||
@@ -61,29 +61,29 @@ export default defineComponent({
|
||||
}
|
||||
const showDesignImgDetail = (str:any)=>{
|
||||
new Promise((resolve, reject) => {
|
||||
if(
|
||||
getDetailListData.isEditPattern.value&&
|
||||
detailData?.getCanvasIfEdit?.fun&&detailData?.getCanvasIfEdit?.fun() > 0
|
||||
){
|
||||
Modal.confirm({
|
||||
title: t('collectionModal.jsContent2'),
|
||||
icon: createVNode(ExclamationCircleOutlined),
|
||||
okText: 'Yes',
|
||||
cancelText: 'No',
|
||||
mask:false,
|
||||
centered:true,
|
||||
onOk() {
|
||||
resolve(true)
|
||||
emit('detailEdit',str)
|
||||
},
|
||||
onCancel(){
|
||||
resolve(false)
|
||||
}
|
||||
});
|
||||
}else{
|
||||
// if(
|
||||
// getDetailListData.isEditPattern.value&&
|
||||
// detailData?.getCanvasIfEdit?.fun&&detailData?.getCanvasIfEdit?.fun() > 0
|
||||
// ){
|
||||
// Modal.confirm({
|
||||
// title: t('collectionModal.jsContent2'),
|
||||
// icon: createVNode(ExclamationCircleOutlined),
|
||||
// okText: 'Yes',
|
||||
// cancelText: 'No',
|
||||
// mask:false,
|
||||
// centered:true,
|
||||
// onOk() {
|
||||
// resolve(true)
|
||||
// emit('detailEdit',str)
|
||||
// },
|
||||
// onCancel(){
|
||||
// resolve(false)
|
||||
// }
|
||||
// });
|
||||
// }else{
|
||||
resolve(true)
|
||||
emit('detailEdit',str)
|
||||
}
|
||||
// }
|
||||
})
|
||||
}
|
||||
const deleteItem = ()=>{
|
||||
@@ -107,7 +107,7 @@ export default defineComponent({
|
||||
const handleResize = ()=>{
|
||||
clearTimeout(time)
|
||||
time = setTimeout(()=>{
|
||||
store.commit('DesignDetailCopy/setDesignDetail',getDetailListData.designDetail)
|
||||
store.commit('DesignDetail/setDesignDetail',getDetailListData.designDetail)
|
||||
getDetailListDom.position.updataPosition()
|
||||
|
||||
},1000)
|
||||
@@ -11,7 +11,7 @@
|
||||
<img :src="item.path" alt="">
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="singleOveral.value == 'overall'" v-if="currentDetailType == 'sketch' || currentDetailType == '' " :class="{active:!selectDetail?.id && currentDetailType == 'sketch'}" class="modelNav_item add" @click="addSketch">
|
||||
<div v-show="singleOveral.value == 'overall'" v-if="(currentDetailType == 'sketch' || currentDetailType == '') && designDetail.clothes.length < 5 " :class="{active:!selectDetail?.id && currentDetailType == 'sketch'}" class="modelNav_item add" @click="addSketch">
|
||||
+
|
||||
</div>
|
||||
</div>
|
||||
@@ -35,10 +35,10 @@ export default defineComponent({
|
||||
const store = useStore();
|
||||
const {t} = useI18n()
|
||||
const detailData = reactive({
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
frontBack_:computed(()=>store.state.DesignDetailCopy.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
frontBack_:computed(()=>store.state.DesignDetail.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetail.currentDetailType),
|
||||
isEditPattern:inject('isEditPattern') as any,
|
||||
singleOveral:inject('singleOveral') as any,
|
||||
getCanvasIfEdit:inject('getCanvasIfEdit')as any,
|
||||
@@ -67,33 +67,32 @@ export default defineComponent({
|
||||
})
|
||||
},{immediate:true})
|
||||
const selectDetailItem = (item:any,index:number)=>{
|
||||
console.log(detailData?.getCanvasIfEdit?.fun)
|
||||
new Promise((resolve, reject) => {
|
||||
if(detailData.isEditPattern.value &&
|
||||
detailData.selectDetail?.id &&
|
||||
detailData?.getCanvasIfEdit?.fun&&detailData?.getCanvasIfEdit?.fun() > 0
|
||||
){
|
||||
Modal.confirm({
|
||||
title: t('collectionModal.jsContent2'),
|
||||
icon: createVNode(ExclamationCircleOutlined),
|
||||
okText: 'Yes',
|
||||
cancelText: 'No',
|
||||
mask:false,
|
||||
centered:true,
|
||||
onOk() {
|
||||
resolve(true)
|
||||
emit('canvasReload')
|
||||
},
|
||||
onCancel(){
|
||||
resolve(false)
|
||||
}
|
||||
});
|
||||
}else{
|
||||
// if(detailData.isEditPattern.value &&
|
||||
// detailData.selectDetail?.id &&
|
||||
// detailData?.getCanvasIfEdit?.fun&&detailData?.getCanvasIfEdit?.fun() > 0
|
||||
// ){
|
||||
// Modal.confirm({
|
||||
// title: t('collectionModal.jsContent2'),
|
||||
// icon: createVNode(ExclamationCircleOutlined),
|
||||
// okText: 'Yes',
|
||||
// cancelText: 'No',
|
||||
// mask:false,
|
||||
// centered:true,
|
||||
// onOk() {
|
||||
// resolve(true)
|
||||
// emit('canvasReload')
|
||||
// },
|
||||
// onCancel(){
|
||||
// resolve(false)
|
||||
// }
|
||||
// });
|
||||
// }else{
|
||||
resolve(true)
|
||||
emit('canvasReload')
|
||||
}
|
||||
// }
|
||||
}).then((rv)=>{
|
||||
if(rv)store.commit('DesignDetailCopy/setDesignColthes',item.id)
|
||||
if(rv)store.commit('DesignDetail/setDesignColthes',item.id)
|
||||
})
|
||||
}
|
||||
const deleteDetailItem = (id:number)=>{
|
||||
@@ -103,8 +102,8 @@ export default defineComponent({
|
||||
emit('deleteItem')
|
||||
}
|
||||
const addSketch = ()=>{
|
||||
if(detailData.currentDetailType != 'sketch')store.commit('DesignDetailCopy/setCurrentDetailType','sketch')
|
||||
store.commit('DesignDetailCopy/addDesignColthes')
|
||||
if(detailData.currentDetailType != 'sketch')store.commit('DesignDetail/setCurrentDetailType','sketch')
|
||||
store.commit('DesignDetail/addDesignColthes')
|
||||
emit('addSketch')
|
||||
}
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="designOpenrtion_imgMask" v-else>
|
||||
<img :src="selectDetail.undividedLayer" style="object-fit: cover;" alt="">
|
||||
<img :src="designDetail.currentFullBodyView || selectDetail.undividedLayer" style="object-fit: cover;" alt="">
|
||||
</div>
|
||||
</div>
|
||||
<div class="molepositon" :class="{active:imgDesignImg}">
|
||||
@@ -53,16 +53,16 @@ export default defineComponent({
|
||||
const {t} = useI18n()
|
||||
const store = useStore();
|
||||
const detailData = reactive({
|
||||
frontBack:computed(()=>store.state.DesignDetailCopy.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
frontBack:computed(()=>store.state.DesignDetail.frontBack),
|
||||
designDetail:computed(()=>store.state.DesignDetail.designDetail),
|
||||
isEditPattern:inject('isEditPattern') as any,
|
||||
singleOveral:inject('singleOveral') as any,
|
||||
detailBody:null as any,
|
||||
})
|
||||
const selectItem = reactive({
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
selectDetail:computed(()=>store.state.DesignDetail.selectDetail),
|
||||
imgDomIndex:-1,
|
||||
printZIndex:store.state.DesignDetailCopy.printZIndex,
|
||||
printZIndex:store.state.DesignDetail.printZIndex,
|
||||
imgDom:null as any,
|
||||
direction:'',
|
||||
})
|
||||
@@ -257,13 +257,13 @@ export default defineComponent({
|
||||
}).then((rv)=>{
|
||||
})
|
||||
if(isOpen){
|
||||
store.commit('DesignDetailCopy/setDesignColthes',detailData.frontBack.front[index].id)
|
||||
store.commit('DesignDetail/setDesignColthes',detailData.frontBack.front[index].id)
|
||||
emit('canvasReload')
|
||||
return
|
||||
}
|
||||
|
||||
if(isModal)return
|
||||
store.commit('DesignDetailCopy/setDesignColthes',detailData.frontBack.front[index].id)
|
||||
store.commit('DesignDetail/setDesignColthes',detailData.frontBack.front[index].id)
|
||||
selectItem.imgDomIndex = index
|
||||
detailData.frontBack.front.forEach((v:any)=>{
|
||||
v.designOpenrtionBtn = false
|
||||
@@ -1,763 +0,0 @@
|
||||
<template>
|
||||
<div class="design_compile_content" id="design_compile_content">
|
||||
<div class="designOpenrtion_centent" id="designOpenrtionCentent">
|
||||
<div class="detail_modal_body_title">
|
||||
<div class="detail_modal_body_nav">
|
||||
<div v-for="item,index in designItemDetail?.clothes" v-show="item.id" :class="{active:item.clothesOpenItem}" @click="clothesOpen(index)">
|
||||
<img :src="item?.path" alt="">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="designOpenrtion_imgMask" :style="frontBack?.body?.style">
|
||||
<!-- <div
|
||||
v-for="item,index in frontBack.back"
|
||||
:key="item"
|
||||
:style="item.style"
|
||||
@mousedown.stop="itemMoveMousedown(index,$event)"
|
||||
class="modal_imgItem"
|
||||
@click="setpitch(item,index)" ref="content" >
|
||||
<img crossOrigin="anonymous" :src="item.path" class="designOpenrtion_imgItme" draggable="false">
|
||||
</div> -->
|
||||
<div class="designOpenrtion_print" v-for="item,index in frontBack.back" @mousedown.stop="itemMoveMousedown(index,getMousePosition($event,false))" @touchstart.passive="itemMoveMousedown(index,getMousePosition($event,true))" @click="setpitch(item,index)" :style="frontBack.front[index].style">
|
||||
<img :style="item.imageUrl?'':'display:none;'" :src="item.imageUrl" alt="">
|
||||
</div>
|
||||
<img class="perview_img" :style="'width:'+ frontBack?.body?.layersObject?.[0].imageSize?.[0] +';height:' + frontBack?.body?.layersObject?.[0].imageSize?.[0] +';'" v-lazy="frontBack?.body?.layersObject?.[0].imageUrl || ''" :key="designItemDetail.designItemUrl">
|
||||
<div class="detail_modal_item_front" v-for="item,index in frontBack.front" @mousedown.stop="itemMoveMousedown(index,getMousePosition($event,false))" @touchstart.passive="itemMoveMousedown(index,getMousePosition($event,true))" @click="setpitch(item,index)" :style="item.style">
|
||||
<img :src="item.imageUrl" alt="">
|
||||
</div>
|
||||
<div class="designOpenrtion_btn" v-if="!isBody">
|
||||
<ul v-for="item,index in frontBack.front" :key="item" :class="{active:item.designOpenrtionBtn}" class="designOpenrtion_btn" :style="item.style" @mousedown.stop="itemMoveMousedown(index,getMousePosition($event,false))" @touchstart.passive="itemMoveMousedown(index,getMousePosition($event,true))">
|
||||
<li class="designOpenrtion_btn_top" @mousedown.stop="itemSizeMousedown('top',getMousePosition($event,false))" @touchstart.passive="itemSizeMousedown('top',getMousePosition($event,true))"></li>
|
||||
<li class="designOpenrtion_btn_bottom" @mousedown.stop="itemSizeMousedown('bottom',getMousePosition($event,false))" @touchstart.passive="itemSizeMousedown('bottom',getMousePosition($event,true))"></li>
|
||||
<li class="designOpenrtion_btn_left" @mousedown.stop="itemSizeMousedown('left',getMousePosition($event,false))" @touchstart.passive="itemSizeMousedown('left',getMousePosition($event,true))"></li>
|
||||
<li class="designOpenrtion_btn_right" @mousedown.stop="itemSizeMousedown('right',getMousePosition($event,false))" @touchstart.passive="itemSizeMousedown('right',getMousePosition($event,true))"></li>
|
||||
<!-- <li class="designOpenrtion_rotote" v-rotote.stop="[index,item.transform]"></li> -->
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="subitOkPreviewBtn" @click="imgClear" style="margin-bottom: 0rem;">{{ $t('LibraryPage.Reset') }}</div>
|
||||
<div @click="setPreviewData" class="subitOkPreviewBtn">OK</div>
|
||||
</div>
|
||||
<div class="designOpenrtion_imgMask_open" @click.stop="deleteBorder"></div>
|
||||
</div>
|
||||
<!-- <div class="design_compile_content">
|
||||
<editFrontBack :patchData="frontBack" :imgDomIndex="imgDomIndex" ref="editFrontBack"></editFrontBack>
|
||||
</div> -->
|
||||
|
||||
</template>
|
||||
|
||||
<script >
|
||||
import { defineComponent, h,createVNode, ref ,computed, inject,nextTick} from "vue";
|
||||
// import { LoadingOutlined } from "@ant-design/icons-vue";
|
||||
import { useStore } from "vuex";
|
||||
// import { Modal,message } from 'ant-design-vue';
|
||||
import { Https } from "@/tool/https";
|
||||
import editFrontBack from '@/component/Detail/editFrontBack.vue'
|
||||
import { getMousePosition } from "@/tool/mdEvent";
|
||||
export default defineComponent({
|
||||
props: ["isBody"],
|
||||
emits:['setParentLoadingShow','setDesignCoverage','setSubmit'],
|
||||
components:{editFrontBack},
|
||||
setup(prop) {
|
||||
const store = useStore();
|
||||
|
||||
let designItemDetail = computed(()=>{
|
||||
return store.state.DesignDetailModule.designItemDetail
|
||||
})
|
||||
let current = inject('current')//父组件传过来的数据
|
||||
let setRevocation = inject('setRevocation')//父组件传过来的数据
|
||||
let printZIndex = ref(4)//印花优先级
|
||||
let printStyleList = ref([
|
||||
{
|
||||
centers:{
|
||||
left:0,
|
||||
top:0,
|
||||
},
|
||||
style:{
|
||||
left:0+"px",
|
||||
top:0+"px",
|
||||
right:"auto",
|
||||
bottom:"auto",
|
||||
width:100+'px',
|
||||
height:100+'px',
|
||||
// zIndex:1,
|
||||
},
|
||||
transform:{
|
||||
scale:1,
|
||||
rotateZ:0,
|
||||
},
|
||||
designOpenrtionBtn:false
|
||||
}
|
||||
]);
|
||||
let direction = ref('')
|
||||
let imgDom = ref()
|
||||
let imgDomIndex = ref(-1)
|
||||
let frontBack = ref({})
|
||||
let frontBackOld = ref({})
|
||||
let editFrontBack = ref(null)
|
||||
return {
|
||||
designItemDetail,
|
||||
current,
|
||||
printZIndex,
|
||||
printStyleList,
|
||||
direction,//判断点击的是li那个边
|
||||
imgDom,
|
||||
imgDomIndex,
|
||||
frontBack,
|
||||
setRevocation,
|
||||
frontBackOld,
|
||||
editFrontBack,
|
||||
getMousePosition,
|
||||
};
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
loadingShow:false,//加载中
|
||||
store: useStore(),
|
||||
setImgSizeTimeout:null
|
||||
};
|
||||
},
|
||||
mounted () {
|
||||
window.addEventListener('resize', this.setImgSizeTime);
|
||||
},
|
||||
methods: {
|
||||
init(){
|
||||
let DesignParent = this.$parent
|
||||
// this.clearModal()
|
||||
// console.log(this.current,DesignParent.frontBack);
|
||||
this.printStyleList.push({
|
||||
centers:{
|
||||
left:0,
|
||||
top:0,
|
||||
},
|
||||
style:{
|
||||
left:0+"px",
|
||||
top:0+"px",
|
||||
right:"auto",
|
||||
bottom:"auto",
|
||||
width:100+'px',
|
||||
height:100+'px',
|
||||
// zIndex:1,
|
||||
},
|
||||
transform:{
|
||||
scale:1,
|
||||
rotateZ:0,
|
||||
},
|
||||
designOpenrtionBtn:false
|
||||
})
|
||||
this.setImgSize()
|
||||
},
|
||||
setImgSizeTime(){
|
||||
clearTimeout(this.setImgSizeTimeout)
|
||||
this.setImgSizeTimeout = setTimeout(()=>{
|
||||
this.setImgSize()
|
||||
},300)
|
||||
},
|
||||
async setImgSize(){
|
||||
this.frontBack.body = null
|
||||
let designItemDetail = JSON.parse(JSON.stringify(this.store.state.DesignDetailModule.designItemDetail))
|
||||
let front = []
|
||||
let back = []
|
||||
let body = {}
|
||||
if(designItemDetail.others.length > 0){
|
||||
designItemDetail.others.forEach((item) => {
|
||||
if(item.type == 'Body'){
|
||||
body = item
|
||||
}
|
||||
});
|
||||
}else{
|
||||
designItemDetail.clothes.forEach((item) => {
|
||||
body = item
|
||||
});
|
||||
}
|
||||
|
||||
let ratio = await this.setPostition(body.layersObject[0]?.imageUrl)
|
||||
let frontIndex = 6
|
||||
let backIndex = 3
|
||||
// let front = 3
|
||||
// let back = 3
|
||||
designItemDetail.clothes.forEach((v,index)=>{
|
||||
for (let i = v.layersObject.length-1; i >= 0; i--) {
|
||||
v.layersObject[i].style = {
|
||||
top:v.layersObject[i].position?.[0]*ratio+'px',
|
||||
left:v.layersObject[i].position?.[1]*ratio+'px',
|
||||
width:v.layersObject[i].imageSize?.[0]*ratio+'px',
|
||||
height:v.layersObject[i].imageSize?.[1]*ratio+'px',
|
||||
// zIndex:zIndex-=1
|
||||
}
|
||||
v.layersObject[i].centers={
|
||||
left:0,
|
||||
top:0,
|
||||
}
|
||||
v.layersObject[i].designOpenrtionBtn = false
|
||||
if(v.layersObject[i].imageCategory.indexOf("back") == -1){
|
||||
front[index] = v.layersObject[i]
|
||||
front[index].style.zIndex = v.priority
|
||||
front[index].id = v.id
|
||||
front[index].undividedLayer = v.undividedLayer
|
||||
}else{
|
||||
back[index] = v.layersObject[i]
|
||||
back[index].style.zIndex = v.priority
|
||||
back[index].id = v.id
|
||||
back[index].undividedLayer = v.undividedLayer
|
||||
// back[index].style.zIndex = backIndex==0?v.layersObject[i]:backIndex++
|
||||
}
|
||||
if(this.printZIndex < v.priority){
|
||||
this.printZIndex = v.priority
|
||||
}
|
||||
}
|
||||
this.printZIndex++
|
||||
})
|
||||
if(body){
|
||||
body.style = {
|
||||
width:body.layersObject[0].imageSize?.[0]*ratio+'px',
|
||||
height:body.layersObject[0].imageSize?.[1]*ratio+'px',
|
||||
}
|
||||
}
|
||||
|
||||
this.frontBack = {
|
||||
front:front,
|
||||
back:back,
|
||||
body:body,
|
||||
}
|
||||
this.frontBackOld = JSON.parse(JSON.stringify({
|
||||
front:front,
|
||||
back:back,
|
||||
body:body,
|
||||
}))
|
||||
},
|
||||
imgClear(){
|
||||
this.frontBack = JSON.parse(JSON.stringify(this.frontBackOld))
|
||||
},
|
||||
//按比设置单件衣服宽高位置
|
||||
async setPostition(url){
|
||||
let img = await loadImage(url)
|
||||
let modal_body = document.getElementsByClassName('designOpenrtion_imgMask')[0]
|
||||
const num = modal_body?.offsetHeight / img.height;
|
||||
function loadImage(url) {
|
||||
return new Promise((resolve, reject) => {
|
||||
const img = new Image();
|
||||
img.onload = () => {
|
||||
resolve(img)
|
||||
img.remove()
|
||||
};
|
||||
img.onerror = reject;
|
||||
img.src = url;
|
||||
});
|
||||
}
|
||||
return num
|
||||
},
|
||||
clear(){
|
||||
this.imgDomIndex = -1
|
||||
this.clothesOpenActive(-1)
|
||||
if(this.editFrontBack)this.editFrontBack.setClone()
|
||||
window.removeEventListener('resize', this.setImgSizeTime);
|
||||
},
|
||||
setpitch(item,index){
|
||||
this.frontBack.front.forEach((v)=>{
|
||||
v.designOpenrtionBtn = false
|
||||
})
|
||||
this.frontBack.front[index].designOpenrtionBtn = true
|
||||
this.frontBack.front[index].style.zIndex = this.printZIndex++
|
||||
this.frontBack.back[index].style.zIndex = this.printZIndex
|
||||
this.clothesOpenActive(index)
|
||||
},
|
||||
// 设置移动
|
||||
itemMoveMousedown(index,e){
|
||||
this.imgDomIndex = index
|
||||
this.frontBack.front.forEach((v)=>{
|
||||
v.designOpenrtionBtn = false
|
||||
})
|
||||
this.clothesOpenActive(index)
|
||||
let event = e||window.event
|
||||
this.imgDom = document.getElementsByClassName('design_compile_content')[0].getElementsByClassName("detail_modal_item_front")[this.imgDomIndex]
|
||||
this.frontBack.front[index].designOpenrtionBtn = true
|
||||
this.frontBack.front[index].style.zIndex = this.printZIndex++
|
||||
this.frontBack.back[index].style.zIndex = this.printZIndex
|
||||
let imgDomWH = this.imgDom.getBoundingClientRect()
|
||||
let left = Number(this.frontBack.front[index].style.left.replace(/px/g,''))
|
||||
let top = Number(this.frontBack.front[index].style.top.replace(/px/g,''))
|
||||
this.frontBack.front[index].centers.left = imgDomWH.x+event.offsetX-left
|
||||
this.frontBack.front[index].centers.top = imgDomWH.y+event.offsetY-top
|
||||
// document.addEventListener("mouseup", this.mouseup);
|
||||
// document.addEventListener("mousemove", this.moveMousemove);
|
||||
document.addEventListener('mousemove', this.mouseMove);
|
||||
document.addEventListener('touchmove', this.touchmove);
|
||||
document.addEventListener('mouseup', this.mouseup);
|
||||
document.addEventListener('touchend', this.mouseup);
|
||||
},
|
||||
//设置尺寸
|
||||
itemSizeMousedown(direction,event){
|
||||
this.direction = direction
|
||||
this.imgDom = document.getElementsByClassName('design_compile_content')[0].getElementsByClassName("detail_modal_item_front")[this.imgDomIndex]
|
||||
this.frontBack.front[this.imgDomIndex].designOpenrtionBtn = true
|
||||
let imgDomWH = this.imgDom.getBoundingClientRect()
|
||||
let li = document.getElementsByClassName('design_compile_content')[0].getElementsByClassName("designOpenrtion_btn_top")[0].offsetWidth/2
|
||||
if(this.direction == 'right' || this.direction == 'bottom'){
|
||||
this.frontBack.front[this.imgDomIndex].centers.left = imgDomWH.x+event.offsetX-li
|
||||
this.frontBack.front[this.imgDomIndex].centers.top = imgDomWH.y+event.offsetY-li
|
||||
}else{
|
||||
this.frontBack.front[this.imgDomIndex].centers.left = imgDomWH.x+event.offsetX+imgDomWH.width-li
|
||||
this.frontBack.front[this.imgDomIndex].centers.top = imgDomWH.y+event.offsetY+imgDomWH.height-li
|
||||
}
|
||||
|
||||
document.addEventListener('mousemove', this.sizeMouseMove);
|
||||
document.addEventListener('touchmove', this.sizeTouchmove);
|
||||
document.addEventListener('mouseup', this.sizeMouseup);
|
||||
document.addEventListener('touchend', this.sizeMouseup);
|
||||
},
|
||||
mouseMove(event){
|
||||
let e = getMousePosition(event,false)
|
||||
this.mouseMoveOperation(e)
|
||||
},
|
||||
touchmove(event){
|
||||
let e = getMousePosition(event,true)
|
||||
this.mouseMoveOperation(e)
|
||||
},
|
||||
//鼠标移动
|
||||
mouseMoveOperation(e) {
|
||||
let imgDomWH = this.imgDom.getBoundingClientRect()
|
||||
let parentNode = document.getElementsByClassName('design_compile_content')[0].getElementsByClassName("designOpenrtion_imgMask")[0].getBoundingClientRect()
|
||||
let x = (e.clientX - this.frontBack.front[this.imgDomIndex].centers.left)+'px'
|
||||
let y = ( e.clientY - this.frontBack.front[this.imgDomIndex].centers.top)+'px'
|
||||
this.frontBack.front[this.imgDomIndex].style.left = x
|
||||
this.frontBack.front[this.imgDomIndex].style.top = y
|
||||
// if(x.replace(/px/g,'') >= parentNode.width - imgDomWH.width){
|
||||
// this.frontBack.front[this.imgDomIndex].style.left = parentNode.width - imgDomWH.width+'px'
|
||||
// }
|
||||
// if(x.replace(/px/g,'') <= 0){
|
||||
// this.frontBack.front[this.imgDomIndex].style.left = 0+'px'
|
||||
// }
|
||||
// if(y.replace(/px/g,'') >= parentNode.height - imgDomWH.height){
|
||||
// this.frontBack.front[this.imgDomIndex].style.top = parentNode.height - imgDomWH.height+'px'
|
||||
// }
|
||||
// if(y.replace(/px/g,'') <= 0){
|
||||
// this.frontBack.front[this.imgDomIndex].style.top = 0+'px'
|
||||
// }
|
||||
},
|
||||
sizeMouseMove(event){
|
||||
let e = getMousePosition(event,false)
|
||||
this.sizeMouseMoveOperation(e)
|
||||
},
|
||||
sizeTouchmove(event){
|
||||
let e = getMousePosition(event,true)
|
||||
this.sizeMouseMoveOperation(e)
|
||||
},
|
||||
sizeMouseMoveOperation(e) {
|
||||
let imgDomWH = this.imgDom.getBoundingClientRect()
|
||||
let parentNode =this.imgDom.parentNode
|
||||
let width = imgDomWH.width
|
||||
let height = imgDomWH.height
|
||||
let w,h
|
||||
let num = height/width
|
||||
//判断移动四个边
|
||||
if(this.direction == 'right'){
|
||||
w = (e.clientX - this.frontBack.front[this.imgDomIndex].centers.left)
|
||||
h = (e.clientX - this.frontBack.front[this.imgDomIndex].centers.left)*num
|
||||
width = w+'px'
|
||||
// height = w*num+'px'
|
||||
}else if(this.direction == 'top'){
|
||||
num = width/height
|
||||
this.frontBack.front[this.imgDomIndex].style.top = 'auto'
|
||||
// this.printStyleList[this.imgDomIndex].style.left = 'auto'
|
||||
this.frontBack.front[this.imgDomIndex].style.bottom = parentNode.offsetHeight -imgDomWH.height - this.imgDom.offsetTop+'px'
|
||||
w = (e.clientX - this.frontBack.front[this.imgDomIndex].centers.left)*num
|
||||
h = (this.frontBack.front[this.imgDomIndex].centers.top - e.clientY)
|
||||
|
||||
height = h+'px'
|
||||
// width = h*num+'px'
|
||||
}else if(this.direction == 'bottom'){
|
||||
num = width/height
|
||||
h = (e.clientY - this.frontBack.front[this.imgDomIndex].centers.top)
|
||||
height = h+'px'
|
||||
// width = h*num+'px'
|
||||
}else if(this.direction == 'left'){
|
||||
this.frontBack.front[this.imgDomIndex].style.left = 'auto'
|
||||
this.frontBack.front[this.imgDomIndex].style.right = parentNode.offsetWidth -imgDomWH.width - this.imgDom.offsetLeft+'px'
|
||||
w = (this.frontBack.front[this.imgDomIndex].centers.left - e.clientX)
|
||||
|
||||
width = w+'px'
|
||||
// height = w*num+'px'
|
||||
}
|
||||
//判断尺寸是否到边
|
||||
this.frontBack.front[this.imgDomIndex].style.width = width
|
||||
this.frontBack.front[this.imgDomIndex].style.height = height
|
||||
},
|
||||
//鼠标抬起
|
||||
sizeMouseup(e){
|
||||
this.frontBack.front[this.imgDomIndex].style={
|
||||
right:'auto',
|
||||
left:this.imgDom.offsetLeft+'px',
|
||||
bottom:'auto',
|
||||
top:this.imgDom.offsetTop+'px',
|
||||
height:this.imgDom.offsetHeight+'px',
|
||||
width:this.imgDom.offsetWidth+'px',
|
||||
zIndex:this.printZIndex
|
||||
}
|
||||
this.frontBack.back[this.imgDomIndex].style.zIndex = this.printZIndex
|
||||
document.removeEventListener('mousemove',this.sizeMouseMove)
|
||||
document.removeEventListener('touchmove',this.sizeTouchmove)
|
||||
document.removeEventListener('mouseup',this.sizeMouseup)
|
||||
document.removeEventListener('touchend',this.sizeMouseup)
|
||||
},
|
||||
mouseup(e) {
|
||||
|
||||
// document.removeEventListener("mouseup", this.mouseup);
|
||||
// document.removeEventListener("mousemove", this.moveMousemove);
|
||||
document.removeEventListener('mousemove',this.mouseMove)
|
||||
document.removeEventListener('touchmove',this.touchmove)
|
||||
document.removeEventListener('mouseup',this.mouseup)
|
||||
document.removeEventListener('touchend',this.mouseup)
|
||||
},
|
||||
clearModal(){
|
||||
this.printZIndex = 2//点击图片z-index
|
||||
this.imgDomIndex = 0//点击图片下标
|
||||
this.clothes = []
|
||||
this.printStyleList.splice(1,this.printStyleList.length-1)
|
||||
},
|
||||
capitalizeFirstLetter(str) {
|
||||
return str.charAt(0).toUpperCase() + str.slice(1);
|
||||
},
|
||||
setPreviewData(){
|
||||
this.$emit('setSubmit','preview');
|
||||
},
|
||||
deleteBorder(){
|
||||
this.frontBack?.front?.forEach((item)=>{
|
||||
item.designOpenrtionBtn = false
|
||||
})
|
||||
},
|
||||
clothesOpen(index){
|
||||
this.imgDomIndex = index
|
||||
this.clothesOpenActive(index)
|
||||
this.setpitch('',index)
|
||||
},
|
||||
clothesOpenActive(index){
|
||||
this.designItemDetail.clothes.forEach((item)=>{
|
||||
item.clothesOpenItem = false
|
||||
})
|
||||
if(index != -1){
|
||||
this.designItemDetail.clothes[index].clothesOpenItem = true
|
||||
}
|
||||
},
|
||||
sort(arr){
|
||||
arr.sort((a, b) => {
|
||||
var a_num = a.style.zIndex;
|
||||
var b_num = b.style.zIndex;
|
||||
return a_num - b_num;
|
||||
});
|
||||
return arr
|
||||
},
|
||||
async setPreview(data){
|
||||
let ratio = this.frontBack.body.layersObject[0].imageSize[0]/this.frontBack.body.style.width.replace(/px/g,'')
|
||||
let designItemDetail = this.store.state.DesignDetailModule.designItemDetail
|
||||
// this.frontBack.back.sort((a, b) => {
|
||||
// var a_num = a.style.zIndex;
|
||||
// var b_num = b.style.zIndex;
|
||||
// return a_num - b_num;
|
||||
// });
|
||||
let arr = this.sort(JSON.parse(JSON.stringify(this.frontBack.front)))
|
||||
let num = 10
|
||||
arr.forEach((item)=>{
|
||||
item.priority = num++
|
||||
item.similarity = false//新增衣服传的是衣服id会存在两件衣服id相同所以设置为false让每次赋值都是不一样的
|
||||
})
|
||||
let front = arr
|
||||
let imageCategory1
|
||||
data.designSingleItemDTOList.forEach((item)=>{
|
||||
if(arr.length > 1){
|
||||
imageCategory1 = arr[1].imageCategory
|
||||
}
|
||||
for (let index = 0; index < arr.length; index++) {
|
||||
if(item.id == arr[index].id && !arr[index].similarity){
|
||||
let y = ((arr[index]?.style?.top.replace(/px/g,'')*ratio).toFixed(0) - arr[index]?.position[0])
|
||||
let x = ((arr[index]?.style?.left.replace(/px/g,'')*ratio).toFixed(0) - arr[index]?.position[1])
|
||||
let scaleWidth = arr[index]?.imageSize?Number(((arr[index]?.style?.width.replace(/px/g,'')*ratio)/(arr[index]?.imageSize[0]/arr[index].scale[0])).toFixed(2)):1
|
||||
let scaleHeight = arr[index]?.imageSize?Number(((arr[index]?.style?.height.replace(/px/g,'')*ratio)/(arr[index]?.imageSize[1]/arr[index].scale[1])).toFixed(2)):1
|
||||
// let widthScale = (arr[index].style.width.replace(/px/g,'')/arr[index].style.height.replace(/px/g,'')).toFixed(2)
|
||||
item.scale = [scaleWidth,scaleHeight]
|
||||
let top = y == 0 ? item.offset[1]:y+item.offset[1]
|
||||
let left = x == 0 ? item.offset[0]:x+item.offset[0]
|
||||
item.offset = [left,top]
|
||||
item.maskUrl = arr[index].maskUrl
|
||||
item.priority = arr[index].priority
|
||||
arr[index].similarity = true
|
||||
// item.offset = [(arr[index]?.style?.left.replace(/px/g,'')*ratio).toFixed(0),(i?.style?.top.replace(/px/g,'')*ratio).toFixed(0)]
|
||||
break
|
||||
}
|
||||
}
|
||||
if(arr.length > 1 && item.type == this.capitalizeFirstLetter(imageCategory1)){
|
||||
item.scale = front?.imageSize?Number(((front?.style?.width.replace(/px/g,'')*ratio)/front?.imageSize[0]).toFixed(2)):1
|
||||
}
|
||||
})
|
||||
Https.axiosPost(Https.httpUrls.designSingle, data).then(
|
||||
(rv) => {
|
||||
// this.$parent.loadingShow = false
|
||||
// let designItemDetail = JSON.parse(JSON.stringify(this.store.state.DesignDetailModule.designItemDetail))
|
||||
// designItemDetail.designItemUrl = rv.designItemUrl
|
||||
// designItemDetail.ifSubmit = true
|
||||
// designItemDetail.currentFullBodyView = rv.currentFullBodyView
|
||||
// rv.clothes.forEach((item)=>{
|
||||
// designItemDetail.clothes.forEach((i)=>{
|
||||
// if(item.id === i.id){
|
||||
// i.layersObject = item.layersObject
|
||||
// i.priority = item.layersObject[0].priority
|
||||
// }
|
||||
// })
|
||||
// })
|
||||
let designItemDetail = JSON.parse(JSON.stringify(this.store.state.DesignDetailModule.designItemDetail))
|
||||
rv.clothes.forEach((i)=>{
|
||||
i.similarity = false//新增衣服传的是衣服id会存在两件衣服id相同所以设置为false让每次赋值都是不一样的
|
||||
})
|
||||
designItemDetail.designItemUrl = rv.designItemUrl
|
||||
designItemDetail.ifSubmit = true
|
||||
designItemDetail.currentFullBodyView = rv.currentFullBodyView
|
||||
designItemDetail.clothes.forEach((item)=>{
|
||||
for (let index = 0; index < rv.clothes.length; index++) {
|
||||
if(rv.clothes[index].id === item.id && !rv.clothes[index].similarity){
|
||||
item.layersObject = rv.clothes[index].layersObject
|
||||
item.undividedLayer = rv.clothes[index].undividedLayer
|
||||
item.priority = rv.clothes[index].layersObject[0].priority
|
||||
rv.clothes[index].similarity = true
|
||||
break
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
// rv.clothes.forEach((item)=>{
|
||||
// for (let index = 0; index < designItemDetail.clothes.length; index++) {
|
||||
// if(item.id === designItemDetail.clothes[index].id && !designItemDetail.clothes[index].similarity){
|
||||
// designItemDetail.clothes[index].layersObject = item.layersObject
|
||||
// designItemDetail.clothes[index].priority = item.layersObject[0].priority
|
||||
// break
|
||||
// }
|
||||
// }
|
||||
// })
|
||||
this.$emit('setDesignCoverage');
|
||||
this.store.commit("setDesignItemDetail", designItemDetail);
|
||||
this.setRevocation(designItemDetail,data)
|
||||
this.clear()
|
||||
}
|
||||
).catch(res=>{
|
||||
// this.$parent.loadingShow = false
|
||||
this.$emit('setParentLoadingShow');
|
||||
});
|
||||
},
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.designOpenrtion_modal {
|
||||
// max-width: 1440px;
|
||||
user-select: none; /* 对现代浏览器有效 */
|
||||
-webkit-user-select: none; /* Safari */
|
||||
-moz-user-select: none; /* Firefox */
|
||||
-ms-user-select: none; /* Internet Explorer/Edge */
|
||||
.ant-modal-body{
|
||||
padding: calc(5rem*1.2) calc(6rem*1.2) calc(0rem*1.2)!important;
|
||||
// height: calc(65vh - 6.4rem*1.2));
|
||||
height: calc(65rem*1.2);
|
||||
display: flex;
|
||||
overflow-y: hidden;
|
||||
flex-direction: column;
|
||||
}
|
||||
.ant-modal-content{
|
||||
border-radius: calc(1rem*1.2);
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
.design_compile_content {
|
||||
// background: #f2f3fb;
|
||||
// padding-bottom: 2.9rem*1.2);
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
width: 50%;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
.designOpenrtion_centent{
|
||||
// flex: 1;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-content: space-around;
|
||||
flex-wrap: nowrap;
|
||||
margin: 0 auto;
|
||||
// overflow: hidden;
|
||||
justify-content: space-between;
|
||||
user-select:none;
|
||||
z-index: 2;
|
||||
&.active{
|
||||
flex-direction: row;
|
||||
}
|
||||
.designOpenrtion_imgMask{
|
||||
width: auto;
|
||||
height: auto;
|
||||
position: relative;
|
||||
height: calc(100% - 1.2rem - 4.8rem - 20%);
|
||||
// overflow: hidden;
|
||||
>img{
|
||||
z-index: 2;
|
||||
position: relative;
|
||||
}
|
||||
>div{
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
.detail_modal_body_nav{
|
||||
display: flex;
|
||||
position: relative;
|
||||
top: 0;
|
||||
left: 50%;
|
||||
z-index: 999;
|
||||
transform: translate(-50%,-0%);
|
||||
transition: all .3s;
|
||||
justify-content: center;
|
||||
margin-bottom: calc(1rem*1.2);
|
||||
>div{
|
||||
width: calc(4rem*1.2);
|
||||
height: calc(4rem*1.2);
|
||||
cursor: pointer;
|
||||
text-align: center;
|
||||
margin-left: calc(.3rem*1.2);
|
||||
img{
|
||||
// width: 100%;
|
||||
height: 100%;
|
||||
max-width: 100%;
|
||||
object-fit: cover;
|
||||
}
|
||||
&.active{
|
||||
border: 2px solid rgba(0,0,0,0.4);
|
||||
img{
|
||||
transform: scale(.8);
|
||||
opacity: .8;
|
||||
}
|
||||
}
|
||||
}
|
||||
>div:nth-child(1){
|
||||
margin-left: calc(0rem*1.2);
|
||||
}
|
||||
}
|
||||
.designOpenrtion_print,.detail_modal_item_front{
|
||||
z-index: 1;
|
||||
img{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
float: left;
|
||||
user-select:none;
|
||||
-webkit-user-drag: none;
|
||||
}
|
||||
.modal_imgItem{
|
||||
position: absolute;
|
||||
top: 0;
|
||||
|
||||
}
|
||||
}
|
||||
.designOpenrtion_print{
|
||||
z-index: 1 !important;
|
||||
}
|
||||
.designOpenrtion_btn{
|
||||
z-index: 9999;
|
||||
ul{
|
||||
list-style: none;
|
||||
// width: 100%;
|
||||
// height: 100%;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
box-sizing: border-box;
|
||||
border: 2px solid rgb(20, 188, 255);
|
||||
padding: 0;
|
||||
-webkit-user-drag: none;
|
||||
user-select:none;
|
||||
opacity: 0;
|
||||
margin: 0;
|
||||
|
||||
li{
|
||||
cursor: pointer;
|
||||
// border-radius: 50%;
|
||||
width: calc(2rem*1.2);
|
||||
height: calc(2rem*1.2);
|
||||
background-color: rgb(20, 188, 255);
|
||||
position: absolute;
|
||||
pointer-events: none;
|
||||
}
|
||||
&.active{
|
||||
opacity: 1;
|
||||
li{
|
||||
pointer-events: auto;
|
||||
}
|
||||
}
|
||||
.designOpenrtion_btn_top,.designOpenrtion_btn_bottom{
|
||||
left: 50%;
|
||||
transform: translate(-50%,-50%) ;
|
||||
cursor: n-resize;
|
||||
}
|
||||
.designOpenrtion_btn_top{
|
||||
top: 0;
|
||||
}
|
||||
.designOpenrtion_btn_bottom{
|
||||
top: 100%;
|
||||
}
|
||||
.designOpenrtion_btn_left,.designOpenrtion_btn_right{
|
||||
top: 50%;
|
||||
transform: translate(-50%,-50%) ;
|
||||
cursor: e-resize;
|
||||
}
|
||||
.designOpenrtion_btn_left{
|
||||
left: 0;
|
||||
}
|
||||
.designOpenrtion_btn_right{
|
||||
left: 100%;
|
||||
}
|
||||
.designOpenrtion_rotote{
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
width: 0;
|
||||
height: 0;
|
||||
}
|
||||
.designOpenrtion_rotote::after{
|
||||
position: absolute;
|
||||
content: "";
|
||||
background-color: #14bcff;
|
||||
width: 2px;
|
||||
height: 30px;
|
||||
left: 50%;
|
||||
bottom: 0;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
.designOpenrtion_rotote::before{
|
||||
position: absolute;
|
||||
content: "";
|
||||
background-color: #14bcff;
|
||||
top: calc(50% - 30px);
|
||||
left: 50%;
|
||||
transform: translate(-50%,-50%) ;
|
||||
width: calc(1.5rem*1.2);
|
||||
height: calc(1.5rem*1.2);
|
||||
border-radius: 50%;
|
||||
}
|
||||
}
|
||||
}
|
||||
.subitOkPreviewBtn{
|
||||
z-index: 2;
|
||||
// margin-bottom: calc(1rem*1.2);
|
||||
margin-bottom: 4rem;
|
||||
width: calc(10rem*1.2);
|
||||
text-align: center;
|
||||
bottom: 0;
|
||||
position: relative;
|
||||
}
|
||||
}
|
||||
.designOpenrtion_imgMask_open{
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -1,304 +0,0 @@
|
||||
<template>
|
||||
<div class="canvasArgument">
|
||||
<!-- <div class="label_item wH">
|
||||
<div class="title">{{ $t('exportModel.Width') }}</div>
|
||||
<input type="number" @input="canvasGeneral.setCanvasWH('width')" v-model="canvasGeneral.canvasWH.width">
|
||||
</div>
|
||||
<div class="label_item wH">
|
||||
<div class="title">{{ $t('exportModel.Height') }}</div>
|
||||
<input type="number" @input="canvasGeneral.setCanvasWH('height')" v-model="canvasGeneral.canvasWH.height">
|
||||
</div> -->
|
||||
<div v-show="isEditFrontBack" class="frontBack">
|
||||
<div class="label_item" @click.stop="setOperation('print')">
|
||||
<div class="title">Masking :</div>
|
||||
<a-select
|
||||
v-model:value="frontBackData"
|
||||
:options="frontBackDataList"
|
||||
size="large"
|
||||
:fieldNames="{ label: 'name', value: 'value' }"
|
||||
style="width:18rem;"
|
||||
@change="changeFrontBackData"
|
||||
>
|
||||
<template #suffixIcon
|
||||
><span
|
||||
class="icon iconfont icon-xiala"
|
||||
style="color: #000"
|
||||
></span
|
||||
></template>
|
||||
</a-select>
|
||||
</div>
|
||||
<div class="label_item">
|
||||
<div class="title">{{ $t('exportModel.Size') }} :</div>
|
||||
<input @change="frontBackCanvas.setFontFamily" type="range" @input="frontBackCanvas.setPencilWidth" min="3" max="50" v-model="frontBackCanvas.brushwork.width[frontBackCanvas.operation]">
|
||||
|
||||
<!-- <input type="range" @input="frontBackCanvas.setPencilWidth" min="3" max="50" v-model="frontBackCanvas.brushwork.width[frontBackCanvas.operation]"> -->
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="!isEditFrontBack" class="sketch">
|
||||
<div class="label_item" @click.stop="setOperation('print')" v-show="isDashedShow">
|
||||
<div class="title">print</div>
|
||||
<div class="current"></div>
|
||||
<div class="drop" v-show="operation == 'print'">
|
||||
<selectList @selectImgItem="selectImgItem" level1Type="Printboard" type="print" :catecoryList="printCatecoryList"></selectList>
|
||||
</div>
|
||||
</div>
|
||||
<div class="label_item" @click.stop="setOperation('element')" v-show="isDashedShow">
|
||||
<div class="title">element</div>
|
||||
<div class="current"></div>
|
||||
<div class="drop" v-show="operation == 'element'">
|
||||
<selectList @selectImgItem="selectImgItem" level1Type="DesignElements" type="element" :catecoryList="designElementsType"></selectList>
|
||||
</div>
|
||||
</div>
|
||||
<div class="label_item" v-show="
|
||||
canvasGeneral.operation != 'movePosition' &&
|
||||
canvasGeneral.operation != 'move' &&
|
||||
canvasGeneral.operation != 'eraser' &&
|
||||
canvasGeneral.operation != 'texture' &&
|
||||
canvasGeneral.operation != 'zoomIn' &&
|
||||
canvasGeneral.operation != 'zoomOut' &&
|
||||
canvasGeneral.operation != 'dashedPencil' &&
|
||||
canvasGeneral.operation != 'dashed'">
|
||||
<div class="title">{{ $t('exportModel.Color') }}</div>
|
||||
<input style="width: 7rem;" type="color" @input="canvasGeneral.setPencilColor" v-model="canvasGeneral.brushwork.color">
|
||||
<span class="icon iconfont icon-xiala" @click.stop="setOperation('color')" :class="{active: operation == 'color'}"></span>
|
||||
<div class="labelHover_show" v-show="operation == 'color'" @click.stop="">
|
||||
<div v-for="item in canvasGeneral.colorHistoryList" :style="{'background':item}" @click="canvasGeneral.setColorHistory(item)"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="label_item texture" v-show="canvasGeneral.operation == 'texture'">
|
||||
<div class="title">{{ $t('exportModel.Texture') }}:</div>
|
||||
<a-select ref="select" class="label_select" size="small" v-model:value="canvasGeneral.texture.value"
|
||||
style="width: 12rem "
|
||||
@change="canvasGeneral.textureValueChange"
|
||||
>
|
||||
<a-select-option class="label_select_item" v-for="item in canvasGeneral.texture.list" :value="item.value">
|
||||
<img :src="item.url" alt="">
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</div>
|
||||
<div class="label_item" v-show="
|
||||
canvasGeneral.operation != 'movePosition' &&
|
||||
canvasGeneral.operation != 'move' &&
|
||||
canvasGeneral.brushwork.value != 'RibbonBrush' &&
|
||||
canvasGeneral.brushwork.value != 'LongfurBrush'&&
|
||||
canvasGeneral.operation != 'zoomIn' &&
|
||||
canvasGeneral.operation != 'zoomOut' &&
|
||||
canvasGeneral.operation != 'dashedPencil' &&
|
||||
canvasGeneral.operation != 'dashed'">
|
||||
<div class="title">{{ $t('exportModel.Size') }}:</div>
|
||||
<input @change="canvasGeneral.setFontFamily" type="range" @input="canvasGeneral.setPencilWidth" min="3" max="50" v-model="canvasGeneral.brushwork.width[canvasGeneral.operation]">
|
||||
</div>
|
||||
<div class="label_item" v-show="canvasGeneral.operation == 'pencil'">
|
||||
<div class="title">{{ $t('exportModel.Brushwork') }}:</div>
|
||||
<a-select ref="select" class="label_select" size="small" v-model:value="canvasGeneral.brushwork.value"
|
||||
style="width: 12rem ;"
|
||||
@change="canvasGeneral.brushworkChange"
|
||||
>
|
||||
<a-select-option class="label_select_item" v-for="item in canvasGeneral.pencilList.brushList" :value="item.value">
|
||||
<img style="width: 100%;" :src="item.url" alt="">
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</div>
|
||||
|
||||
<div class="label_item" v-show="
|
||||
canvasGeneral.operation != 'pencil' &&
|
||||
canvasGeneral.operation != 'eraser'&&
|
||||
canvasGeneral.operation != 'movePosition' &&
|
||||
canvasGeneral.operation != 'move'&&
|
||||
canvasGeneral.operation != 'text'&&
|
||||
canvasGeneral.operation != 'texture'&&
|
||||
canvasGeneral.operation != ''&&
|
||||
canvasGeneral.operation != 'zoomIn' &&
|
||||
canvasGeneral.operation != 'zoomOut' &&
|
||||
canvasGeneral.operation != 'dashedPencil' &&
|
||||
canvasGeneral.operation != 'dashed'">
|
||||
<div class="title">{{ $t('exportModel.FillBack') }}:</div>
|
||||
<div class="leftAlign">
|
||||
<i class="icon iconfont icon-tuceng1" @click="canvasGeneral.setOperationMode('fill')" :class="{active:canvasGeneral.operationMode == 'fill'}"></i>
|
||||
<i class="icon iconfont icon-tuceng" @click="canvasGeneral.setOperationMode('border')" :class="{active:canvasGeneral.operationMode == 'border'}"></i>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- <div class="label_item" v-show="canvasGeneral.operation == 'movePosition'">
|
||||
<div >{{ $t('exportModel.Layer') }}:</div>
|
||||
<div class="leftAlign">
|
||||
<i class="icon iconfont icon-shangyiceng" @click="canvasGeneral.setLayerIndex('Front')"></i>
|
||||
<i class="icon iconfont icon-shangyiceng2" @click="canvasGeneral.setLayerIndex('Forward')"></i>
|
||||
<i class="icon iconfont icon-xiayiceng" @click="canvasGeneral.setLayerIndex('Backwards')"></i>
|
||||
<i class="icon iconfont icon-shangyiceng1" @click="canvasGeneral.setLayerIndex('Back')"></i>
|
||||
</div>
|
||||
</div> -->
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineComponent,ref,reactive,computed,toRefs,inject, watch, nextTick} from 'vue'
|
||||
import library from '../detailLeft/module/libraryList.vue'
|
||||
import upload from '../detailLeft/module/uploadList.vue'
|
||||
import selectList from '../detailLeft/module/selectList.vue'
|
||||
|
||||
import { useStore } from "vuex";
|
||||
export default defineComponent({
|
||||
components:{selectList},
|
||||
props: ['isEditFrontBack'],
|
||||
emits: ['setFrontBackColor'],
|
||||
setup(props,{emit}){
|
||||
const store = useStore();
|
||||
let testModal = ref(true)
|
||||
let canvasGeneral:any = inject('canvasObj')
|
||||
let frontBackCanvas:any = inject('frontBackCanvasObj')
|
||||
const data = reactive({
|
||||
colorHistoryList:[],
|
||||
operation:'',
|
||||
printCatecoryList:computed(()=>{
|
||||
return store.state.UserHabit.printType
|
||||
}),
|
||||
designElementsType:computed(()=>{
|
||||
return store.state.UserHabit.designElementsType;
|
||||
}),
|
||||
isDashedShow:computed(()=>{
|
||||
return canvasGeneral.dashed.isDashedShow;
|
||||
}),
|
||||
frontBackData:'#ff0000',
|
||||
frontBackDataList:[
|
||||
{
|
||||
name:'Front Piece',
|
||||
value:'#ff0000'
|
||||
},{
|
||||
name:'Back Piece',
|
||||
value:'#00ff00'
|
||||
},{
|
||||
name:'Surroundings',
|
||||
value:'background'
|
||||
},
|
||||
]
|
||||
})
|
||||
watch(()=>props.isEditFrontBack,(newVal)=>{
|
||||
if(newVal){
|
||||
nextTick(()=>{
|
||||
data.frontBackData = '#ff0000'
|
||||
})
|
||||
}
|
||||
})
|
||||
const setOperation = (str:any)=>{
|
||||
data.operation = str
|
||||
}
|
||||
const setOper = ()=>{
|
||||
setOperation('')
|
||||
}
|
||||
document.addEventListener('click',setOper)
|
||||
const closeModal = ()=>{
|
||||
document.removeEventListener('click',setOper)
|
||||
}
|
||||
const selectImgItem = (value:any)=>{
|
||||
value.minioUrl = value.url
|
||||
canvasGeneral.addPartImg(value,'print')
|
||||
data.operation = ''
|
||||
}
|
||||
const changeFrontBackData = (value:any)=>{
|
||||
emit('setFrontBackColor',value)
|
||||
}
|
||||
return {
|
||||
canvasGeneral,
|
||||
frontBackCanvas,
|
||||
...toRefs(data),
|
||||
testModal,
|
||||
setOperation,
|
||||
closeModal,
|
||||
selectImgItem,
|
||||
changeFrontBackData,
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang='less' scoped>
|
||||
.canvasArgument{
|
||||
height: 100%;
|
||||
>div{
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
.label_item{
|
||||
margin-right: 2rem;
|
||||
position: relative;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.leftAlign{
|
||||
display: flex;
|
||||
}
|
||||
> .current{
|
||||
border-radius: 1rem;
|
||||
height: 3rem;
|
||||
width: 7rem;
|
||||
border: 1px solid #000;
|
||||
}
|
||||
> .drop{
|
||||
position: absolute;
|
||||
z-index: 22;
|
||||
top: 4rem;
|
||||
background: #fff;
|
||||
border: 1px solid #000;
|
||||
border-radius: 1rem;
|
||||
padding: 2.4rem;
|
||||
width: 40rem;
|
||||
height: 50rem;
|
||||
display: flex;
|
||||
}
|
||||
.labelHover_show{
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 10rem;
|
||||
top: 100%;
|
||||
z-index: 2;
|
||||
display: block;
|
||||
border-radius: 4px;
|
||||
border: 1px solid;
|
||||
padding: .5rem 1rem;
|
||||
background: #fff;
|
||||
div{
|
||||
width: 2rem;
|
||||
height: 2rem;
|
||||
margin-right: .5rem;
|
||||
margin-bottom: .5rem;
|
||||
display: inline-block;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
|
||||
&.wH input{
|
||||
width: 5rem;
|
||||
}
|
||||
.title{
|
||||
margin-right: 1rem;
|
||||
font-weight: 600;
|
||||
font-size: 1.8rem;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
&.sketch{
|
||||
.icon-xiala{
|
||||
cursor: pointer;
|
||||
transform: rotate(0deg);
|
||||
height: 4rem;
|
||||
width: 4rem;
|
||||
transition: all .3s;
|
||||
line-height: 1;
|
||||
text-align: center;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
&.active{
|
||||
transform: rotate(180deg);
|
||||
}
|
||||
}
|
||||
}
|
||||
.label_item:hover{
|
||||
// .labelHover_show{
|
||||
// display: flex;
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
||||
@@ -1,138 +0,0 @@
|
||||
<template>
|
||||
<div class="canvasContent_box">
|
||||
<div class="canvasContent" ref="canvasScaleDom">
|
||||
<div class="generalCanvas_center canvas" ref="canvasDom">
|
||||
<div class="editFrontBack_pencilbtn" v-show="!isShowMark"></div>
|
||||
<div class="editFrontBack_pencilbtn" v-show="!isShowMark" :style="canvasGeneral.pencilbtnStyle"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineComponent,computed,reactive,nextTick,toRefs,inject,createVNode, onMounted, onBeforeUnmount} from 'vue'
|
||||
import { Modal,message } from 'ant-design-vue';
|
||||
import { ExclamationCircleOutlined } from '@ant-design/icons-vue';
|
||||
import { useStore } from "vuex";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
export default defineComponent({
|
||||
component:{},
|
||||
setup(){
|
||||
const store = useStore();
|
||||
let {t} = useI18n()
|
||||
let canvasType = inject('canvasType')
|
||||
let getCanvasIfEdit:any = inject('getCanvasIfEdit')
|
||||
let canvasGeneral:any = inject('canvasObj')
|
||||
const data:any = reactive({
|
||||
canvasScaleDom:null,
|
||||
canvasDom:null,
|
||||
isShowMark:false,
|
||||
pencilbtnStyle:{},
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
|
||||
|
||||
})
|
||||
getCanvasIfEdit.fun = ()=>{
|
||||
return canvasGeneral.getElement()
|
||||
}
|
||||
const createCanvas = (canvasSize:any)=>{
|
||||
nextTick(async ()=>{
|
||||
let img = data.selectDetail.undividedLayer
|
||||
let WH = {
|
||||
width:data.canvasDom.offsetWidth,
|
||||
height:data.canvasDom.offsetHeight,
|
||||
}
|
||||
let image = new Image()
|
||||
image.onload = async ()=>{
|
||||
let wScale = 1
|
||||
let hScale = 1
|
||||
wScale = image.width/image.height
|
||||
|
||||
// if(image.width>image.height){
|
||||
// hScale = image.height/image.width
|
||||
// }else{
|
||||
// wScale = mnnmmmimage.width/image.height
|
||||
// }
|
||||
let size = {
|
||||
width:WH.height*wScale,
|
||||
height:WH.height*hScale,
|
||||
}
|
||||
// let editGroupImg = data.selectDetail.partialDesign.partialDesignPath || data.selectDetail.partialDesign.partialDesignBase64
|
||||
let editGroupImg = data.selectDetail.partialDesign.partialDesignPath
|
||||
await canvasGeneral.canvasInit(data.canvasDom,size,img,editGroupImg,{dashedIsDetail:true})
|
||||
}
|
||||
image.src = img
|
||||
// canvasGeneral.canvasInit(data.canvasDom,canvasSize)
|
||||
})
|
||||
}
|
||||
const openMode = (data:any)=>{
|
||||
let {yes,no} = data
|
||||
console.log(yes,no);
|
||||
Modal.confirm({
|
||||
title: '是否栅格化',
|
||||
icon: createVNode(ExclamationCircleOutlined),
|
||||
okText: 'Yes',
|
||||
cancelText: 'No',
|
||||
mask:false,
|
||||
centered:true,
|
||||
onOk() {
|
||||
yes()
|
||||
},
|
||||
onCancel(){
|
||||
no()
|
||||
}
|
||||
});
|
||||
yes()
|
||||
|
||||
}
|
||||
onMounted(()=>{
|
||||
createCanvas({})
|
||||
})
|
||||
onBeforeUnmount(()=>{
|
||||
canvasGeneral.canvasClear()
|
||||
})
|
||||
return {
|
||||
canvasGeneral,
|
||||
...toRefs(data),
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang='less' scoped>
|
||||
.canvasContent_box{
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
// padding: 2rem;
|
||||
background: #e6e6e6;
|
||||
.canvasContent{
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
}
|
||||
}
|
||||
|
||||
.generalCanvas_center{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
&.canvas{
|
||||
}
|
||||
.editFrontBack_pencilbtn{
|
||||
position: absolute;
|
||||
z-index: 1;
|
||||
border-radius: 50%;
|
||||
border: 1px solid #000;
|
||||
pointer-events: none;
|
||||
transform: translate(-50%,-50%);
|
||||
}
|
||||
:deep(.canvas-container){
|
||||
left: 50%;
|
||||
top: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
// background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQAQMAAAAlPW0iAAAAA3NCSVQICAjb4U/gAAAABlBMVEXMzMz////TjRV2AAAACXBIWXMAAArrAAAK6wGCiw1aAAAAHHRFWHRTb2Z0d2FyZQBBZG9iZSBGaXJld29ya3MgQ1M26LyyjAAAABFJREFUCJlj+M/AgBVhF/0PAH6/D/HkDxOGAAAAAElFTkSuQmCC);
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
||||
@@ -1,243 +0,0 @@
|
||||
<template>
|
||||
<div class="canvasBox">
|
||||
<!-- designDetailShow -->
|
||||
<!-- :class="[driver__.driver?'hideEvents':'']" -->
|
||||
<div class="canvasContent">
|
||||
<div class="argument-box">
|
||||
<argument
|
||||
ref="argument"
|
||||
class="argument"
|
||||
v-if="canvasObj.id || frontBackCanvasObj.id"
|
||||
@toolLiquefaction="toolLiquefaction"
|
||||
@setFrontBackColor="setFrontBackColor"
|
||||
:isEditFrontBack="isEditFrontBack">
|
||||
</argument>
|
||||
</div>
|
||||
<div class="content-bottom">
|
||||
<div class="tool-box">
|
||||
<tool ref="tool" class="tool" v-if="canvasObj.id || frontBackCanvasObj.id" @toolLiquefaction="toolLiquefaction" @editFront="editFront" :isEditFrontBack="isEditFrontBack"></tool>
|
||||
</div>
|
||||
<div class="contet">
|
||||
<div class="canvas" v-show="!isEditFrontBack" @click.stop>
|
||||
<canvasContent ref="canvasContent"></canvasContent>
|
||||
</div>
|
||||
<div class="editFrontBack" v-if="isEditFrontBack" @click.stop>
|
||||
<editFrontBack
|
||||
:patchData="frontBack"
|
||||
:imgDomIndex="imgDomIndex"
|
||||
|
||||
ref="editFrontBack">
|
||||
</editFrontBack>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- <div class="Finish">
|
||||
<div class="gallery_btn" @click="privewDetail">Finish</div>
|
||||
</div> -->
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- <div class="mark_loading" v-show="isShowMark">
|
||||
<a-spin size="large" />
|
||||
</div> -->
|
||||
</div>
|
||||
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import { defineComponent,computed,onBeforeUnmount,provide,nextTick,watch,toRefs, reactive} from 'vue'
|
||||
import { Https } from "@/tool/https";
|
||||
import { Modal,message } from 'ant-design-vue';
|
||||
import {getUploadUrl,isMoible,setGradual} from '@/tool/util'
|
||||
import { useStore } from "vuex";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import editFrontBack from '@/component/Detail/editFrontBack.vue'
|
||||
|
||||
|
||||
import canvasGeneral from "@/tool/canvasGeneralCopy";
|
||||
import argument from './argument.vue'
|
||||
import canvasContent from './canvasContent.vue'
|
||||
import tool from "./tool.vue"
|
||||
|
||||
export default defineComponent({
|
||||
components:{
|
||||
tool,argument,canvasContent,editFrontBack
|
||||
},
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
const {t} = useI18n();
|
||||
|
||||
const detailDom = reactive({
|
||||
editFrontBack:null as any,
|
||||
model:null,
|
||||
})
|
||||
const userDetail = computed(()=>{
|
||||
return store.state.UserHabit.userDetail
|
||||
})
|
||||
const detailData = reactive({
|
||||
canvasObj:new canvasGeneral('aa'),
|
||||
frontBackCanvasObj:new canvasGeneral('vv'),
|
||||
isShowMark:false,
|
||||
liquefactionData:null as any,
|
||||
liquefaction:null as any,
|
||||
canvasType:'export',
|
||||
imgDomIndex:-1,
|
||||
isEditFrontBack:false,
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
frontBack:computed(()=>store.state.DesignDetailCopy.frontBack),
|
||||
})
|
||||
watch(()=>detailData.selectDetail,(newValue,oldValue)=>{
|
||||
detailData.imgDomIndex = detailData.frontBack.front.findIndex((item:any)=>item.id == newValue.id)
|
||||
// privewDetail(oldValue)
|
||||
},{immediate: true})
|
||||
provide('frontBackCanvasObj',detailData.frontBackCanvasObj)
|
||||
provide('canvasObj',detailData.canvasObj)
|
||||
provide('isShowMark',detailData.isShowMark)
|
||||
provide('canvasType',detailData.canvasType)
|
||||
|
||||
const setLiquefaction = async ()=>{//进入液化页面
|
||||
detailData.canvasObj.getLiquefactionImgObj().then((data)=>{
|
||||
if(data?.img){
|
||||
detailData.liquefactionData = data
|
||||
detailData.liquefaction.init(data.img)
|
||||
}else {
|
||||
message.info(t('exportModel.jsContent6'))
|
||||
return null;
|
||||
}
|
||||
})
|
||||
}
|
||||
const toolLiquefaction = ()=>{//工具点击按钮
|
||||
setLiquefaction()
|
||||
}
|
||||
const editFront = ()=>{//编辑前后片
|
||||
detailData.isEditFrontBack = !detailData.isEditFrontBack
|
||||
if(detailData.isEditFrontBack){
|
||||
nextTick(()=>{
|
||||
detailDom.editFrontBack.init(detailData.frontBack.front[detailData.imgDomIndex],'')
|
||||
//关闭开启键盘事件
|
||||
detailData.canvasObj.currentOperation = false
|
||||
detailData.frontBackCanvasObj.currentOperation = true
|
||||
})
|
||||
}else{
|
||||
detailData.canvasObj.currentOperation = true
|
||||
detailData.frontBackCanvasObj.currentOperation = false
|
||||
}
|
||||
}
|
||||
const privewDetail = async (oldSelectDetail = detailData.selectDetail)=>{
|
||||
let data = await detailData.canvasObj.detailSubmit()
|
||||
if(oldSelectDetail.partialDesign)oldSelectDetail.partialDesign.partialDesignBase64 = data
|
||||
}
|
||||
const setFrontBackColor = (data:any)=>{
|
||||
detailDom.editFrontBack.setBackground(data)
|
||||
}
|
||||
onBeforeUnmount(()=>{
|
||||
privewDetail()
|
||||
})
|
||||
return{
|
||||
...toRefs(detailDom),
|
||||
...toRefs(detailData),
|
||||
toolLiquefaction,
|
||||
editFront,
|
||||
privewDetail,
|
||||
setFrontBackColor,
|
||||
}
|
||||
},
|
||||
provide() {
|
||||
return {
|
||||
}
|
||||
},
|
||||
mounted(){
|
||||
},
|
||||
|
||||
})
|
||||
</script>
|
||||
<style lang="less" scoped>
|
||||
.canvasBox{
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
// top: -100%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.tool-box{
|
||||
width: 4rem;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
}
|
||||
.Finish{
|
||||
margin-top: auto;
|
||||
> .gallery_btn{
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
.argument-box{
|
||||
height: 4rem;
|
||||
width: 100%;
|
||||
margin-bottom: 3rem;
|
||||
margin-left: 4rem;
|
||||
}
|
||||
.argument-box,
|
||||
.content-bottom,
|
||||
.detail-box{
|
||||
|
||||
:deep(i){
|
||||
font-size: 2.5rem;
|
||||
cursor: pointer;
|
||||
width: 3rem;
|
||||
height: 3rem;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
flex-shrink: 0;
|
||||
transition: all .3s;
|
||||
margin-bottom: .5rem;
|
||||
&.active{
|
||||
border: 1px solid;
|
||||
border-radius: .4rem;
|
||||
}
|
||||
&.icon-xiala{
|
||||
transform: rotate(-90deg);
|
||||
}
|
||||
&.icon-xialaActive{
|
||||
transform: rotate(90deg);
|
||||
}
|
||||
&.eventNone{
|
||||
cursor: no-drop;
|
||||
border: none;
|
||||
opacity: .5;
|
||||
}
|
||||
}
|
||||
}
|
||||
.canvasContent{
|
||||
height: 100%;
|
||||
// height: 70rem;
|
||||
width: 100%;
|
||||
border: 2px solid #000;
|
||||
border-radius: 3rem;
|
||||
padding: 4rem;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
.content-bottom{
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
display: flex;
|
||||
> .contet{
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
position: relative;
|
||||
.canvas,.editFrontBack{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
.editFrontBack{
|
||||
z-index: 2;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
</style>
|
||||
@@ -1,179 +0,0 @@
|
||||
<template>
|
||||
<div class="canvasTool">
|
||||
|
||||
<i class="icon iconfont icon-chehui" @click="historyState('')"></i>
|
||||
<i class="icon iconfont icon-fanchehui" @click="historyState('reverse')"></i>
|
||||
<i class="icon iconfont icon-bianji" @click="setOperation('pencil')" :class="{active:canvasGeneral.operation == 'pencil',eventNone:isEditFrontBack}"></i>
|
||||
<i class="icon iconfont icon-caizhi" @click="setOperation('texture')" :class="{active:canvasGeneral.operation == 'texture',eventNone:isEditFrontBack}"></i>
|
||||
<i class="fi fi-rr-hand-paper" @click="setOperation('move')" :class="{active:canvasGeneral.operation == 'move',eventNone:isEditFrontBack}"></i>
|
||||
<i class="icon iconfont icon-move" @click="setOperation('movePosition')" :class="{active:canvasGeneral.operation == 'movePosition',eventNone:isEditFrontBack}"></i>
|
||||
<i class="icon iconfont icon-xiangpi_huaban1" @click="setOperation('eraser')" :class="{active:canvasGeneral.operation == 'eraser',eventNone:isEditFrontBack}"></i>
|
||||
<i class="fi fi-rr-square-dashed" @click="setOperation('dashed')" :class="{active:canvasGeneral.operation == 'dashed',eventNone:isEditFrontBack}"></i>
|
||||
<i class="fi fi-rr-scalpel-path" @click="setOperation('dashedPencil')" :class="{active:canvasGeneral.operation == 'dashedPencil',eventNone:isEditFrontBack}"></i>
|
||||
<i class="fi fi-rr-zoom-in" @click="setOperation('zoomIn')" :class="{active:canvasGeneral.operation == 'zoomIn',eventNone:isEditFrontBack}"></i>
|
||||
<i class="fi fi-rr-zoom-out" @click="setOperation('zoomOut')" :class="{active:canvasGeneral.operation == 'zoomOut',eventNone:isEditFrontBack}"></i>
|
||||
<!-- <div v-show="isEditFrontBack">
|
||||
<i class="icon iconfont icon-chehui" @click="historyState('')"></i>
|
||||
<i class="icon iconfont icon-fanchehui" @click="historyState('reverse')"></i>
|
||||
</div> -->
|
||||
<i @click="setEditFront" :class="{active:isEditFrontBack || false}" class="fi fi-sr-layers"></i>
|
||||
|
||||
<!-- <i class="icon iconfont icon-IC-yehua" @click="setLiquefaction()"></i> -->
|
||||
|
||||
<!-- <div class="label_item uploadImage">
|
||||
<i class="icon fi fi-br-upload" ></i>
|
||||
<input type="file" @change="uploadImage">
|
||||
</div> -->
|
||||
<!-- <i class="icon iconfont" @click="setOperation('text')" :class="{active:canvasGeneral.operation == 'text'}">T</i>
|
||||
<i class="icon iconfont icon-xiala" :class="{'icon-xialaActive':isMove}" @click.stop="openMore"></i>
|
||||
<div class="btnModal" v-show="isMove" :style="moveStyle">
|
||||
<i class="icon iconfont icon-checkbox-full" @click="setOperation('rect')" :class="{active:canvasGeneral.operation == 'rect'}"></i>
|
||||
<i class="icon iconfont icon-sanjiaoxing" @click="setOperation('triangle')" :class="{active:canvasGeneral.operation == 'triangle'}"></i>
|
||||
<i class="icon iconfont icon-tx-fill-tuoyuanxing" @click="setOperation('ellipse')" :class="{active:canvasGeneral.operation == 'ellipse'}"></i>
|
||||
</div> -->
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineComponent,ref,reactive,nextTick,toRefs,inject} from 'vue'
|
||||
import {base64ToFile} from '@/tool/util'
|
||||
import { Https } from "@/tool/https";
|
||||
export default defineComponent({
|
||||
component:{},
|
||||
emits:['toolLiquefaction','editFront'],
|
||||
props: ['isEditFrontBack'],
|
||||
setup(props,{emit}){
|
||||
let canvasGeneral:any = inject('canvasObj')
|
||||
let isShowMark:any = inject('isShowMark')
|
||||
const data:any = reactive({
|
||||
isMove:false,
|
||||
moveStyle:{},
|
||||
isShowMark,
|
||||
})
|
||||
const uploadImage = (event:any)=>{
|
||||
data.isShowMark = true
|
||||
const file = event.target.files[0];
|
||||
let input = event.target
|
||||
setOperation('movePosition')
|
||||
if (file) {
|
||||
const reader = new FileReader();
|
||||
reader.onload = (e:any) => {
|
||||
let file = base64ToFile(e.target.result,'upload')
|
||||
let formData = new FormData();
|
||||
formData.append("file", file);
|
||||
let config = {headers:{'Content-Type':'multipart/form-data','Accept':'*/*' }}
|
||||
Https.axiosPost(Https.httpUrls.canvasElementUpload, formData,config).then((rv)=>{
|
||||
rv.imgUrl = rv.minioUrl
|
||||
data.isShowMark = false
|
||||
canvasGeneral.addImage(rv)
|
||||
})
|
||||
input.value = ''
|
||||
};
|
||||
reader.readAsDataURL(file);
|
||||
}
|
||||
}
|
||||
const historyState = (str:any)=>{
|
||||
canvasGeneral.historyState(str)
|
||||
}
|
||||
const setOperation = (str:any)=>{
|
||||
if(props.isEditFrontBack)return
|
||||
canvasGeneral.setOperation(str)
|
||||
}
|
||||
const openMore = (e:any)=>{
|
||||
data.isMove=!data.isMove
|
||||
if(data.isMove){
|
||||
let domPoint = e.target.getBoundingClientRect()
|
||||
let domParentPoint = e.target.parentElement.getBoundingClientRect()
|
||||
const left = domPoint.left - domParentPoint.left;
|
||||
const top = domPoint.top - domParentPoint.top;
|
||||
|
||||
data.moveStyle.top = top + 'px'
|
||||
data.moveStyle.left = left + domPoint.width + 2 + 'px'
|
||||
}
|
||||
}
|
||||
const setMore = ()=>{
|
||||
data.isMove = false
|
||||
}
|
||||
let setLiquefaction = ()=>{
|
||||
emit('toolLiquefaction')
|
||||
}
|
||||
document.addEventListener('click',setMore)
|
||||
const closeModal = ()=>{
|
||||
document.removeEventListener('click',setMore)
|
||||
}
|
||||
const setEditFront = ()=>{
|
||||
emit('editFront')
|
||||
// setOperation('movePosition')
|
||||
}
|
||||
return {
|
||||
canvasGeneral,
|
||||
...toRefs(data),
|
||||
uploadImage,
|
||||
historyState,
|
||||
setOperation,
|
||||
openMore,
|
||||
closeModal,
|
||||
setLiquefaction,
|
||||
setEditFront,
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang='less' scoped>
|
||||
.canvasTool::-webkit-scrollbar{
|
||||
display: none;
|
||||
}
|
||||
.canvasTool{
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
position: relative;
|
||||
align-items: center;
|
||||
&.leftAlign{
|
||||
justify-content: flex-start;
|
||||
}
|
||||
&.leftAlign{
|
||||
justify-content: flex-start;
|
||||
}
|
||||
.uploadImage{
|
||||
width: 3rem;
|
||||
height: 3rem;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
cursor: pointer;
|
||||
i{
|
||||
zoom:.8;
|
||||
}
|
||||
input{
|
||||
height: 0;
|
||||
width: 0;
|
||||
border: none;
|
||||
}
|
||||
}
|
||||
.uploadImage{
|
||||
position: relative;
|
||||
input{
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
left: 0;
|
||||
top: 0;
|
||||
opacity: 0;
|
||||
z-index: 2;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
.btnModal{
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
background: #fff;
|
||||
top: 0;
|
||||
border: 1px solid;
|
||||
display: flex;
|
||||
padding: .5rem 1rem;
|
||||
border-radius: 4px;
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
||||
@@ -1,609 +0,0 @@
|
||||
<template>
|
||||
<div ref="designDetailModal" class="designDetailModal" v-if="designDetailShow">
|
||||
<!-- designDetailShow -->
|
||||
<!-- :class="[driver__.driver?'hideEvents':'']" -->
|
||||
<a-modal class="Guide_1_18 generalModel fullScreen"
|
||||
v-model:visible="designDetailShow"
|
||||
:footer="null"
|
||||
:get-container="() => $refs.designDetailModal"
|
||||
width="100%"
|
||||
height="100%"
|
||||
:maskClosable="false"
|
||||
:mask="false"
|
||||
:centered="true"
|
||||
:keyboard="false"
|
||||
:destroyOnClose="true"
|
||||
:closable="false"
|
||||
>
|
||||
<div class="content">
|
||||
<div class="nav" :class="{isEditPattern:isEditPattern.value}">
|
||||
<div class="back_home">
|
||||
<div class="gallery_btn" @click="closeModal()">
|
||||
<i class="fi fi-rs-house-chimney"></i>
|
||||
</div>
|
||||
</div>
|
||||
<div class="nav_list">
|
||||
<div class="nav_item" :class="{active:currentDetailType == 'sketch'}" @click="setCurrentDetail('sketch')">
|
||||
<img src="@/assets/images/icon/details_sketch.png" alt="">
|
||||
<div class="detailText">{{$t('DesignPrintOperation.Apparel')}}</div>
|
||||
</div>
|
||||
<div class="nav_item" :class="{active:currentDetailType == 'print'}" @click="setCurrentDetail('print')">
|
||||
<img src="@/assets/images/icon/details_print.png" alt="">
|
||||
<div class="detailText">{{$t('DesignPrintOperation.Print')}}</div>
|
||||
</div>
|
||||
<div class="nav_item" :class="{active:currentDetailType == 'color'}" @click="setCurrentDetail('color')">
|
||||
<img src="@/assets/images/icon/details_color.png" alt="">
|
||||
<div class="detailText">{{$t('DesignPrintOperation.Color')}}</div>
|
||||
</div>
|
||||
<div class="nav_item" :class="{active:currentDetailType == 'element'}" @click="setCurrentDetail('element')">
|
||||
<img src="@/assets/images/icon/details_elements.png" alt="">
|
||||
<div class="detailText">{{$t('DesignPrintOperation.Elements')}}</div>
|
||||
</div>
|
||||
<div class="nav_item" v-if="selectObject.type == 'seriesDesign'" :class="{active:currentDetailType == 'models'}" @click="setCurrentDetail('models')">
|
||||
<img src="@/assets/images/icon/details_model.svg" alt="">
|
||||
<div class="detailText">{{$t('DesignPrintOperation.Model')}}</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="item detailLeft" :class="{isEditPattern:isEditPattern.value}">
|
||||
<detailLeft v-if="currentDetailType"></detailLeft>
|
||||
<!-- <detailLeft v-if="selectDetail && selectDetail.id && currentDetailType"></detailLeft> -->
|
||||
<div class="btn" style="margin: 0;" v-show="currentDetailType == 'color'">
|
||||
<div class="gallery_btn" @click="previwe">{{$t('DesignPrintOperation.Preview')}}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="item model">
|
||||
<model
|
||||
ref="model"
|
||||
@canvasReload="canvasReload"
|
||||
@detailEdit="detailEdit"
|
||||
@addSketch="()=>isEditPattern.value=false"
|
||||
@revocation="revocation"
|
||||
@oppositeRevocation="oppositeRevocation"
|
||||
></model>
|
||||
<div class="btn">
|
||||
<div class="gallery_btn" style="margin-right: 0;" @click="submit">{{$t('DesignPrintOperation.Submit')}}</div>
|
||||
<div v-show="isEditPattern.value" style="margin-left: 2rem;" class="gallery_btn" @click="previwe">{{$t('DesignPrintOperation.Preview')}}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="item detailRight">
|
||||
<div class="submit">
|
||||
</div>
|
||||
<div class="contentRight" v-if="currentDetailType && !isEditPattern.value">
|
||||
<detailRight ref="detailRight"></detailRight>
|
||||
<div class="btn"
|
||||
v-show="
|
||||
currentDetailType !== 'color' &&
|
||||
(currentDetailType === 'element' ||
|
||||
currentDetailType === 'print' ||
|
||||
(currentDetailType === 'sketch' && selectDetail?.newDetail?.[currentDetailType])||
|
||||
(currentDetailType === 'sketch' && selectDetail?.sketchString)||
|
||||
(currentDetailType === 'models' && designDetail?.newModel))
|
||||
"
|
||||
>
|
||||
<div class="gallery_btn" @click="previwe">{{$t('DesignPrintOperation.Preview')}}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="contentRight" v-if="selectDetail && selectDetail.id && currentDetailType && isEditPattern.value">
|
||||
<canvasBox ref="canvasBox" :key="childKey"></canvasBox>
|
||||
</div>
|
||||
<!-- 画布 -->
|
||||
<!-- <div class="content" v-else-if="selectDetail && selectDetail.id">
|
||||
</div> -->
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</a-modal>
|
||||
<div class="mark_loading" v-show="loadingShow">
|
||||
<a-spin size="large" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import { defineComponent,computed,onBeforeUnmount,provide,nextTick,createVNode,toRefs, reactive, onMounted, watch} from 'vue'
|
||||
import detailLeft from './detailLeft/index.vue'
|
||||
import model from './model/index.vue'
|
||||
import detailRight from './detailRight/index.vue'
|
||||
import canvasBox from './canvas/index.vue'
|
||||
|
||||
// import setDesignItem from '@/component/Detail/setDesignItem2.vue'
|
||||
import { ExclamationCircleOutlined } from '@ant-design/icons-vue';
|
||||
import { Https } from "@/tool/https";
|
||||
import { Modal,message } from 'ant-design-vue';
|
||||
import {getUploadUrl,isMoible,setGradual} from '@/tool/util'
|
||||
import { useStore } from "vuex";
|
||||
import { openGuide,driverObj__ } from "@/tool/guide";
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import addDetails from '@/component/Detail/addDetails.vue'
|
||||
export default defineComponent({
|
||||
components:{
|
||||
detailLeft,model,detailRight,canvasBox
|
||||
},
|
||||
emits:['destroy'],
|
||||
setup(props,{emit}) {
|
||||
const store = useStore();
|
||||
|
||||
const detailDom = reactive({
|
||||
model:null,
|
||||
canvasBox,
|
||||
detailRight,
|
||||
})
|
||||
const userDetail = computed(()=>{
|
||||
return store.state.UserHabit.userDetail
|
||||
})
|
||||
const detailData = reactive({
|
||||
selectObject:computed(()=>store.state.Workspace.probjects) as any,//选择的项目
|
||||
designDetail:computed(()=>store.state.DesignDetailCopy.designDetail),
|
||||
currentDetailType:computed(()=>store.state.DesignDetailCopy.currentDetailType),
|
||||
selectDetail:computed(()=>store.state.DesignDetailCopy.selectDetail),
|
||||
designDetailShow:false,
|
||||
loadingShow:false,
|
||||
oppositeRevocationShow:-1,
|
||||
revocationShow:-1,
|
||||
isEditPattern:{
|
||||
value:false,
|
||||
},// 是否编辑图案
|
||||
childKey:0,
|
||||
singleOveral:{
|
||||
value:'overall'
|
||||
},
|
||||
getCanvasIfEdit:{
|
||||
fun:null,
|
||||
},
|
||||
})
|
||||
|
||||
provide('getCanvasIfEdit',detailData.getCanvasIfEdit)
|
||||
provide('singleOveral',detailData.singleOveral)
|
||||
provide('isEditPattern',detailData.isEditPattern)
|
||||
const closeModal = ()=>{
|
||||
sessionStorage.removeItem('oppositeRevocation')
|
||||
sessionStorage.removeItem('revocation')
|
||||
detailData.designDetailShow = false
|
||||
emit('destroy')
|
||||
}
|
||||
|
||||
const showDesignDetailModal = (data:any,str:any)=>{
|
||||
// let url = Https.httpUrls.getDesignDetail + `?designItemId=${77770}&designPythonOutfitId=${77423}`
|
||||
let url = Https.httpUrls.getDesignDetail + `?designItemId=${data.design.designItemId}&designPythonOutfitId=${data.design.designOutfitId}`
|
||||
detailData.loadingShow = true
|
||||
Https.axiosGet(url).then(
|
||||
async (rv: any) => {
|
||||
rv.clothes.forEach((item:any)=>{
|
||||
let a
|
||||
item.designType='Library'
|
||||
if(item.layersObject[0].imageCategory.indexOf("back") == -1){
|
||||
a = item.layersObject[0]
|
||||
item.layersObject[0] = item.layersObject[1]
|
||||
item.layersObject[1] = a
|
||||
}
|
||||
if(item.color){
|
||||
item.color.rgba = {
|
||||
r:item.color.r,
|
||||
g:item.color.g,
|
||||
b:item.color.b,
|
||||
}
|
||||
}else{
|
||||
item.color = {
|
||||
// rgba:{
|
||||
// r:undefined,
|
||||
// g:undefined,
|
||||
// b:undefined,
|
||||
// }
|
||||
}
|
||||
}
|
||||
if(item.gradient){
|
||||
item.color.gradient = item.gradient
|
||||
}
|
||||
if(item.printObject.prints == null)item.printObject.prints = []
|
||||
item.printObject.prints.forEach((element:any) => {
|
||||
if(!element.designType){
|
||||
element.designType = 'Library'
|
||||
}
|
||||
});
|
||||
})
|
||||
detailData.singleOveral.value = rv.singleOverall
|
||||
detailData.designDetailShow = true
|
||||
store.commit('DesignDetailCopy/setDesignDetail',rv)
|
||||
// this.deleteShow = false
|
||||
|
||||
setRevocation()
|
||||
detailData.loadingShow = false
|
||||
|
||||
store.commit('DesignDetailCopy/setDesignColthes',rv.clothes[0].id)
|
||||
}
|
||||
|
||||
).catch(rv=>{
|
||||
detailData.loadingShow = false
|
||||
})
|
||||
}
|
||||
const initialize = ()=>{//design后初始化
|
||||
|
||||
|
||||
sessionStorage.removeItem('oppositeRevocation')
|
||||
sessionStorage.removeItem('revocation')
|
||||
}
|
||||
//撤回
|
||||
const setRevocation = ()=>{//设置撤销
|
||||
let itemDetail = JSON.parse(JSON.stringify(detailData.designDetail))
|
||||
let revocation:any = JSON.parse((sessionStorage.getItem("revocation") as any))
|
||||
// let oppositeRevocation = JSON.parse((sessionStorage.getItem("oppositeRevocation") as any))
|
||||
if(revocation?.[0]?.designItemId != itemDetail.designItemId || revocation?.[0]?.designItemId == undefined){
|
||||
// sessionStorage.setItem('revocation', JSON.stringify([]));
|
||||
// sessionStorage.setItem('oppositeRevocation',JSON.stringify([]));
|
||||
revocation = []
|
||||
}
|
||||
revocation.push(itemDetail)
|
||||
detailData.revocationShow = revocation?.length
|
||||
detailData.oppositeRevocationShow = 0
|
||||
sessionStorage.setItem('revocation', JSON.stringify(revocation));
|
||||
sessionStorage.setItem('oppositeRevocation',JSON.stringify([]));
|
||||
}
|
||||
provide('setRevocation',setRevocation)
|
||||
|
||||
const revocation = ()=>{//撤回
|
||||
let oppositeRevocation = JSON.parse((sessionStorage.getItem("oppositeRevocation") as any))
|
||||
let revocation = JSON.parse((sessionStorage.getItem("revocation") as any))
|
||||
if(detailData.revocationShow <= 1)return
|
||||
oppositeRevocation.push(revocation[revocation.length-1])
|
||||
detailData.oppositeRevocationShow = oppositeRevocation.length
|
||||
revocation.splice(revocation.length-1,1)
|
||||
detailData.revocationShow = revocation.length
|
||||
store.commit("DesignDetailCopy/setDesignDetail", revocation[revocation.length-1]);
|
||||
sessionStorage.setItem('oppositeRevocation', JSON.stringify(oppositeRevocation));
|
||||
sessionStorage.setItem('revocation', JSON.stringify(revocation));
|
||||
// clearSelect()
|
||||
}
|
||||
const oppositeRevocation = ()=>{//反撤回
|
||||
let oppositeRevocation = JSON.parse((sessionStorage.getItem("oppositeRevocation") as any))
|
||||
let revocation = JSON.parse((sessionStorage.getItem("revocation") as any))
|
||||
if(!oppositeRevocation[oppositeRevocation.length-1])return
|
||||
store.commit("DesignDetailCopy/setDesignDetail", oppositeRevocation[oppositeRevocation.length-1]);
|
||||
revocation.push(oppositeRevocation[oppositeRevocation.length-1])
|
||||
detailData.revocationShow = revocation.length
|
||||
oppositeRevocation.splice(oppositeRevocation.length-1,1)
|
||||
detailData.oppositeRevocationShow = oppositeRevocation.length
|
||||
sessionStorage.setItem('oppositeRevocation', JSON.stringify(oppositeRevocation));
|
||||
sessionStorage.setItem('revocation', JSON.stringify(revocation));
|
||||
// this.clearSelect()
|
||||
}
|
||||
const setCurrentDetail = (str:string)=>{
|
||||
store.commit('DesignDetailCopy/setCurrentDetailType',str)
|
||||
}
|
||||
const setClothes = async (list:any)=>{
|
||||
let clothesList:any = []
|
||||
for(let i = 0;i<list.length;i++){
|
||||
detailData.selectDetail
|
||||
let {scale,offset,priority,maskUrl,maskMinioUrl} = (detailDom.model as any).getSubmitData(list[i])
|
||||
if(detailDom.canvasBox?.privewDetail)await (detailDom.canvasBox as any).privewDetail()
|
||||
if(detailDom.detailRight?.privewDetail)await (detailDom.detailRight as any).privewDetail()
|
||||
let gradient = null
|
||||
let newData = list[i]?.newDetail?.[detailData.currentDetailType]
|
||||
let isCurrent = list[i].id == detailData?.selectDetail?.id
|
||||
let data:any = {
|
||||
changed:false,
|
||||
color:(detailData.currentDetailType == 'color' && isCurrent)?(newData?.rgba?.r?`${newData.rgba.r} ${newData.rgba.g} ${newData.rgba.b}`:''):(list[i].color?.rgba?.r?`${list[i].color.rgba.r} ${list[i].color.rgba.g} ${list[i].color.rgba.b}`:''),
|
||||
designType:(newData && detailData.currentDetailType == 'sketch' && isCurrent)?newData.designType:list[i].designType,
|
||||
id:(newData && detailData.currentDetailType == 'sketch' && isCurrent)?newData.id:list[i].id,
|
||||
// maskMinioUrl:'',
|
||||
// maskUrl:'',
|
||||
maskUrl:list[i].maskUrl,
|
||||
offset,
|
||||
partialDesign:list[i].partialDesign,
|
||||
path:(newData && detailData.currentDetailType == 'sketch' && isCurrent)?newData.minIOPath:list[i].minIOPath,
|
||||
printObject:(newData && detailData.currentDetailType == 'print' && isCurrent)?{prints:newData}:list[i].printObject?list[i].printObject:{prints:[]},
|
||||
priority,
|
||||
scale,
|
||||
type:(newData && detailData.currentDetailType == 'sketch' && isCurrent)?newData.level2Type || newData.categoryValue:list[i].type,
|
||||
sketchString:list[i].sketchString?list[i].sketchString:'',
|
||||
trims:(newData && detailData.currentDetailType == 'element' && isCurrent)?{prints:newData}:list[i].trims?list[i].trims:{prints:[]},
|
||||
}
|
||||
if((list[i].color?.gradient || list[i].newDetail?.color?.gradient)){
|
||||
gradient = list[i].newDetail?.color?.gradient || list[i].color.gradient
|
||||
gradient.colorImg = await setGradual(gradient,320,700)
|
||||
data.gradient = gradient
|
||||
}
|
||||
clothesList.push(data)
|
||||
}
|
||||
return clothesList
|
||||
}
|
||||
const getSubmitData = async (str:string)=>{
|
||||
// return
|
||||
let workspace = store.state.Workspace.probjects
|
||||
if(!detailData.selectDetail.path && !detailData.selectDetail.newDetail?.sketch?.minIOPath)return
|
||||
let clothes:any
|
||||
if(detailData.currentDetailType == 'models'){
|
||||
clothes = await setClothes(detailData.designDetail.clothes)
|
||||
}else{
|
||||
clothes = await setClothes([detailData.selectDetail])
|
||||
}
|
||||
let data = {
|
||||
designItemId:detailData.designDetail.designItemId,
|
||||
designSingleItemDTOList:clothes,
|
||||
isPreview:true,
|
||||
// ifSubmit:designItemDetail.isPreview,
|
||||
gender:workspace?.sex == 'Male'?1:0,
|
||||
sketchString:'',
|
||||
modelId:(detailData.currentDetailType == 'models' && detailData.designDetail.newModel)?detailData.designDetail.newModel.id:detailData.designDetail.oldModel?detailData.designDetail.oldModel.id:'',
|
||||
modelType:(detailData.currentDetailType == 'models' && detailData.designDetail.newModel)?detailData.designDetail.newModel.type:detailData.designDetail.oldModel?detailData.designDetail.oldModel.type:'',
|
||||
timeZone:Intl.DateTimeFormat().resolvedOptions().timeZone,
|
||||
processId:userDetail.value.userId,
|
||||
probjectId:store.state.Workspace.probjects,
|
||||
}
|
||||
detailData.loadingShow = true
|
||||
Https.axiosPost(Https.httpUrls.designSingle, data).then((rv)=>{
|
||||
let value = {
|
||||
currentType : JSON.parse(JSON.stringify(detailData.currentDetailType)),
|
||||
rv:rv,
|
||||
}
|
||||
detailData.designDetail.oldModel = detailData.designDetail.newModel
|
||||
delete detailData.designDetail.newModel
|
||||
store.commit('DesignDetailCopy/setPraeview',value)
|
||||
detailData.loadingShow = false
|
||||
}).catch(res=>{
|
||||
detailData.loadingShow = false
|
||||
});
|
||||
}
|
||||
const submit = async ()=>{
|
||||
let workspace = store.state.Workspace.probjects
|
||||
let clothes:any = await setClothes(detailData.designDetail.clothes)
|
||||
let data = {
|
||||
designItemId:detailData.designDetail.designItemId,
|
||||
designSingleItemDTOList:clothes,
|
||||
isPreview:false,
|
||||
// ifSubmit:designItemDetail.isPreview,
|
||||
gender:workspace?.sex == 'Male'?1:0,
|
||||
sketchString:'',
|
||||
modelId:(detailData.currentDetailType == 'models' && detailData.designDetail.newModel)?detailData.designDetail.newModel.id:detailData.designDetail.oldModel?detailData.designDetail.oldModel.id:'',
|
||||
modelType:(detailData.currentDetailType == 'models' && detailData.designDetail.newModel)?detailData.designDetail.newModel.type:detailData.designDetail.oldModel?detailData.designDetail.oldModel.type:'',
|
||||
timeZone:Intl.DateTimeFormat().resolvedOptions().timeZone,
|
||||
processId:userDetail.value.userId,
|
||||
probjectId:store.state.Workspace.probjects,
|
||||
}
|
||||
detailData.loadingShow = true
|
||||
Https.axiosPost(Https.httpUrls.designSingle, data).then((rv)=>{
|
||||
// store.commit('DesignDetailCopy/setPraeview',rv)
|
||||
let designCollectionList = store.state.HomeStoreModule.designCollectionList
|
||||
let likeDesignCollectionList = store.state.HomeStoreModule.likeDesignCollectionList
|
||||
designCollectionList.forEach((item:any) => {
|
||||
if(item.designItemId == rv.designItemId){
|
||||
item.designOutfitUrl = rv.designItemUrl
|
||||
}
|
||||
});
|
||||
likeDesignCollectionList.forEach((item:any) => {
|
||||
if(item.designItemId == rv.designItemId){
|
||||
item.designOutfitUrl = rv.designItemUrl
|
||||
}
|
||||
});
|
||||
store.commit('setDesignCollectionList',designCollectionList)
|
||||
store.commit('setLikeDesignCollectionList',likeDesignCollectionList)
|
||||
closeModal()
|
||||
detailData.loadingShow = false
|
||||
}).catch(res=>{
|
||||
detailData.loadingShow = false
|
||||
});
|
||||
}
|
||||
const previwe = ()=>{
|
||||
let data = getSubmitData('preview')
|
||||
store.dispatch('DesignDetailCopy/setSubmit',data)
|
||||
}
|
||||
const detailEdit = (str:any)=>{
|
||||
if(str == 'edit'){
|
||||
detailData.isEditPattern.value = !detailData.isEditPattern.value
|
||||
}
|
||||
}
|
||||
const canvasReload = ()=>{
|
||||
detailData.childKey += 1
|
||||
}
|
||||
let time = null as any
|
||||
const handleResize = ()=>{
|
||||
clearTimeout(time)
|
||||
time = setTimeout(()=>{
|
||||
store.commit('DesignDetailCopy/setDesignDetail',detailData.designDetail)
|
||||
},1000)
|
||||
}
|
||||
onMounted(()=>{
|
||||
window.addEventListener('resize', handleResize);
|
||||
})
|
||||
onBeforeUnmount(()=>{
|
||||
sessionStorage.removeItem('oppositeRevocation')
|
||||
sessionStorage.removeItem('revocation')
|
||||
store.commit('DesignDetailCopy/clearDesignDetail')
|
||||
|
||||
window.removeEventListener('resize', handleResize);
|
||||
})
|
||||
|
||||
return{
|
||||
...toRefs(detailDom),
|
||||
...toRefs(detailData),
|
||||
closeModal,
|
||||
showDesignDetailModal,
|
||||
setCurrentDetail,
|
||||
previwe,
|
||||
submit,
|
||||
revocation,
|
||||
oppositeRevocation,
|
||||
detailEdit,
|
||||
canvasReload,
|
||||
}
|
||||
},
|
||||
provide() {
|
||||
return {
|
||||
}
|
||||
},
|
||||
mounted(){
|
||||
let beforeunload = () => {
|
||||
window.removeEventListener('beforeunload',beforeunload)
|
||||
}
|
||||
window.addEventListener('beforeunload',beforeunload)
|
||||
// let url = Https.httpUrls.getDesignDetail + `?designItemId=34242&designPythonOutfitId=34004`
|
||||
// this.loadingShow = true
|
||||
// Https.axiosGet(url).then(
|
||||
// async (rv: any) => {
|
||||
// rv.clothes.forEach((item:any)=>{
|
||||
// let a
|
||||
// if(item.layersObject[0].imageCategory.indexOf("back") == -1){
|
||||
// a = item.layersObject[0]
|
||||
// item.layersObject[0] = item.layersObject[1]
|
||||
// item.layersObject[1] = a
|
||||
// }
|
||||
// if(item.printObject.prints == null){
|
||||
// item.printObject.prints = [{}]
|
||||
// }
|
||||
// })
|
||||
// this.store.commit('setDesignItemDetail',rv)
|
||||
// if(rv.others[0].printObject.path == null){
|
||||
// this.body = false
|
||||
// }else{
|
||||
// this.body = true
|
||||
// }
|
||||
// this.setImgSize()
|
||||
// this.generateHighDesignImg = rv.highDesignUrl
|
||||
// this.designShowPrview = 1
|
||||
// this.designDetailShow = true
|
||||
// this.loadingShow = false
|
||||
// }
|
||||
// ).catch(rv=>{
|
||||
// this.loadingShow = false
|
||||
// })
|
||||
},
|
||||
|
||||
})
|
||||
</script>
|
||||
<style lang="less" scoped>
|
||||
:deep(.detailText){
|
||||
font-size: 1.8rem;
|
||||
font-weight: 600;
|
||||
|
||||
}
|
||||
.designDetailModal{
|
||||
position: absolute;
|
||||
// top: -100%;
|
||||
width: 100.5%;
|
||||
height: 100.5%;
|
||||
left: 50%;
|
||||
top: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
z-index: 2;
|
||||
:deep(>div){
|
||||
> .ant-modal-root{
|
||||
> .ant-modal-centered{
|
||||
> .fullScreen{
|
||||
> .ant-modal-content{
|
||||
box-shadow: none;
|
||||
> .ant-modal-body{
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
:deep(.ant-modal-wrap){
|
||||
.ant-modal-body{
|
||||
// padding: 0;
|
||||
}
|
||||
// position: absolute;
|
||||
// top: 0;
|
||||
// left: 0;
|
||||
}
|
||||
}
|
||||
.content{
|
||||
display: flex;
|
||||
align-items: flex-start;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
> .item{
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
&.detailLeft{
|
||||
width: 34rem;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
&.isEditPattern{width: 0px;}
|
||||
&.model{
|
||||
width: 50rem;
|
||||
margin: 0 10rem;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
&.detailRight{
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
// padding-bottom: calc(6rem + 1rem);
|
||||
overflow: hidden;
|
||||
> .contentRight{
|
||||
text-align: center;
|
||||
display: flex;
|
||||
flex: 1;
|
||||
flex-direction: column;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
.btn{
|
||||
margin-top: auto;
|
||||
}
|
||||
> .submit{
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
margin-bottom: 1rem;
|
||||
&.bottom{
|
||||
margin-top: 1rem;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
> .btn{
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
margin-left: 12rem;
|
||||
}
|
||||
}
|
||||
> .nav{
|
||||
margin-right: 5rem;
|
||||
overflow: hidden;
|
||||
// transition: all .3s;
|
||||
&.isEditPattern{width: 0px;margin: 0;}
|
||||
> .back_home{
|
||||
width: 9rem;
|
||||
text-align: center;
|
||||
> .gallery_btn{
|
||||
width: 6rem;
|
||||
height: 6rem;
|
||||
margin-top: 2rem;
|
||||
border-radius: 50%;
|
||||
}
|
||||
}
|
||||
> .nav_list{
|
||||
margin-top: 2.7rem;
|
||||
// height: 38rem;
|
||||
width: 9rem;
|
||||
background: #f4f4f4;
|
||||
border-radius: 1.4rem;
|
||||
padding: 1.4rem 0;
|
||||
> .nav_item{
|
||||
text-align: center;
|
||||
width: 100%;
|
||||
height: calc((38rem - 1.4rem * 2) / 4);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
> img{
|
||||
width: 4rem;
|
||||
height: 3.6rem;
|
||||
object-fit: contain;
|
||||
}
|
||||
&.active{
|
||||
background: #bdbdbd;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
</style>
|
||||
@@ -3,7 +3,7 @@
|
||||
<div class="eventsDetail_title ">
|
||||
<div class="modal_title_text" @click="setBack">
|
||||
<i class="fi fi-sr-left"></i>
|
||||
<div class="eventsDetail_title_text">Back</div>
|
||||
<div class="eventsDetail_title_text">{{ $t('event.back') }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="eventsDetail_content">
|
||||
|
||||
@@ -294,7 +294,7 @@ export default defineComponent({
|
||||
value:'wx',
|
||||
},{
|
||||
title:'',
|
||||
label:t('speedList.generateFlux'),
|
||||
label:t('speedList.toproductFlus'),
|
||||
value:'high',
|
||||
},{
|
||||
title:'',
|
||||
@@ -466,7 +466,7 @@ export default defineComponent({
|
||||
scene:{
|
||||
handler(newVal,oldVal){
|
||||
if(this.type_.type2 == 'Printboard' && newVal.value == 'Slogan'){
|
||||
let sloganType = ['Blue and Yellow Starry Night','Green Cthulhu','Red and yellow fire style','Cyberpunk style','City skyline buildings','Red maple leaves','Golden Sunflower','Emerald Jungle Canopy','Pink Sakura Blossom']
|
||||
let sloganType = [this.t('Generate.BlueYelStarryNight'),this.t('Generate.GreenCthulhu'),this.t('Generate.RedYelFireStyle'),this.t('Generate.CyberpunkStyle'),this.t('Generate.CitySkyline'),this.t('Generate.RedMaple'),this.t('Generate.GoldSunflower'),this.t('Generate.EmrldJungle'),this.t('Generate.PinkSakura')]
|
||||
var randomNumber = Math.floor(Math.random() * sloganType.length);
|
||||
this.isSloganHint = sloganType[randomNumber]
|
||||
}else{
|
||||
|
||||
@@ -335,7 +335,6 @@ export default defineComponent({
|
||||
|
||||
.color_des{
|
||||
font-size: 1rem;
|
||||
font-family: Roboto;
|
||||
font-weight: 500;
|
||||
color: #000;
|
||||
margin-bottom: .5rem;
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<!-- <i class="fi fi-rr-cross-small"></i> -->
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
>
|
||||
<div class="generalModel_btn" v-if="bindType == 'Modify'">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -26,7 +26,7 @@
|
||||
<div class="generalModel_btn back" v-if="bindType != 'Modify'">
|
||||
<div class="generalModel_closeIcon" @click.stop="setBack()">
|
||||
<span>←</span>
|
||||
<span class="back_text">{{ $t('account.back') }}</span>
|
||||
<span class="back_text">{{ $t('account.logOut') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="login_page">
|
||||
@@ -87,6 +87,7 @@
|
||||
optionFilterProp="label"
|
||||
style="width: 100%;"
|
||||
:options="countryList"
|
||||
:field-names="{ label: locale == 'CHINESE_SIMPLIFIED'?'labelCn':'label' }"
|
||||
:placeholder="$t('account.plaseCountry')"
|
||||
allowClear
|
||||
show-search
|
||||
@@ -101,12 +102,12 @@
|
||||
<div class="login_form_email" :class="{active:emailStap===2}">
|
||||
<div v-show="emailStap === 2" class="email_last_step">
|
||||
|
||||
<div class="email_last_step_block" >
|
||||
<!-- <div class="email_last_step_block" >
|
||||
<span class="email_last_step_content"
|
||||
>Verify using a one-time verification code</span
|
||||
>
|
||||
<i class="fi fi-br-cross email_last_step_block_icon" @click="emailLastStepFun()"></i>
|
||||
</div>
|
||||
</div> -->
|
||||
<div class="email_last_step_bottom">
|
||||
<div class="email_last_step_des">
|
||||
<div class="sent_email_content">
|
||||
@@ -202,6 +203,7 @@ export default defineComponent({
|
||||
registerModel:computed(()=>{
|
||||
return store.state.UserHabit.bindEmail.isBindEmail
|
||||
}),
|
||||
// registerModel:false,
|
||||
bindType:computed(()=>{
|
||||
return store.state.UserHabit.bindEmail.type
|
||||
}),
|
||||
@@ -436,6 +438,7 @@ export default defineComponent({
|
||||
},
|
||||
cancelDsign(){
|
||||
this.store.commit('setIsBindEmail', false)
|
||||
this.emailStap = 1
|
||||
},
|
||||
setBack(){
|
||||
this.router.push({path:'/login'})
|
||||
@@ -524,8 +527,8 @@ export default defineComponent({
|
||||
background: #fff;
|
||||
transform: scale(0);
|
||||
transition: .3s all;
|
||||
border: 2px solid;
|
||||
border-radius: 20px;
|
||||
// border: 2px solid;
|
||||
// border-radius: 20px;
|
||||
.email_last_step{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
@@ -557,9 +560,9 @@ export default defineComponent({
|
||||
}
|
||||
}
|
||||
.login_form_title {
|
||||
font-size: 1.6rem;
|
||||
font-size: 1.8rem;
|
||||
// color: #666666;
|
||||
font-weight: 900;
|
||||
font-weight: 500;
|
||||
color: #000;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
@@ -605,7 +608,7 @@ export default defineComponent({
|
||||
position: absolute;
|
||||
font-size: 2.4rem;
|
||||
right: 2rem;
|
||||
top:1.7rem;
|
||||
top: 3.3rem;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
@@ -623,13 +626,14 @@ export default defineComponent({
|
||||
}
|
||||
.login_form_input {
|
||||
width: 100%;
|
||||
height: 5rem;
|
||||
margin-top: 1rem;
|
||||
// height: 6.75rem;
|
||||
height: 5rem;
|
||||
margin-top: 1rem;
|
||||
border: 0.1rem solid #dfdfdf;
|
||||
border-radius: 2.5rem;
|
||||
border-radius: 4.2rem;
|
||||
padding-left: 2.1rem;
|
||||
line-height: 5rem;
|
||||
font-size: 1.4rem;
|
||||
font-size: 1.6rem;
|
||||
box-sizing: border-box;
|
||||
outline: none;
|
||||
transition: all .3s;
|
||||
@@ -648,12 +652,10 @@ export default defineComponent({
|
||||
|
||||
.email_last_step {
|
||||
// margin-top: 4rem;
|
||||
.email_last_step_bottom{
|
||||
padding: 0 40px;
|
||||
}
|
||||
|
||||
.email_last_step_block{
|
||||
padding: 10px;
|
||||
border-bottom: 2px solid;
|
||||
// border-bottom: 2px solid;
|
||||
box-sizing: border-box;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
<div class="generalModel_btn" :class="[driver__.driver?'hideEvents':'']">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<!-- <i class="fi fi-rr-cross-small"></i> -->
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -105,7 +105,7 @@ export default defineComponent({
|
||||
let showPayOrder = ref(false);
|
||||
let loadingShow = ref(false);
|
||||
let textBtnShow = ref(false)
|
||||
let { t } = useI18n();
|
||||
let { t, locale} = useI18n();
|
||||
let canvas = reactive({});
|
||||
let scale = 2;
|
||||
let exportWH = 512
|
||||
@@ -150,7 +150,7 @@ export default defineComponent({
|
||||
nextTick(()=>{
|
||||
let canvasBox = document.querySelector(".clearSlogan_modal .exportCanvasBox_center");
|
||||
let height = canvasBox.offsetHeight;
|
||||
textData.fontSize = (height/10*1.9).toFixed(0)
|
||||
textData.fontSize = locale.value == "ENGLISH"?(height/10*1).toFixed(0):(height/10*1.9).toFixed(0)
|
||||
canvasBox.style.width = height+'px'
|
||||
canvasWH.value = height
|
||||
scale = exportWH/canvasWH.value
|
||||
@@ -177,7 +177,7 @@ export default defineComponent({
|
||||
isDrawingMode: false, // 开启绘图模式
|
||||
});
|
||||
canvas.on('object:moving',canvasMoving)
|
||||
setTextFun('请输入\n一段话吧~')
|
||||
setTextFun(t('createSlogan.paragraph'))
|
||||
}
|
||||
|
||||
if(!fabric.Object.prototype.controls.deleteControl){
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
</div>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<div class="newPosted_generalMessage_title modal_title_text">
|
||||
<span>动态</span>
|
||||
<span>{{$t('account.update')}}</span>
|
||||
<!-- <div class="newPosted_generalMessage_title_setting pointer" @click="allRead">全部已读</div> -->
|
||||
</div>
|
||||
<div class="newPosted_generalMessage_center modal_title_text">
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -552,6 +552,7 @@ export default defineComponent({
|
||||
})
|
||||
|
||||
productImgData.generateList.unshift(...rv)
|
||||
generateProceedList = rv.map(user => user.taskId);
|
||||
setPrductimg(arr)
|
||||
}
|
||||
).catch(res=>{
|
||||
@@ -653,12 +654,24 @@ export default defineComponent({
|
||||
}
|
||||
Https.axiosGet(Https.httpUrls.generateStopWaiting, {params:data}).then(
|
||||
(rv) => {
|
||||
generateProceedList = []
|
||||
productImgData.generateList = productImgData.generateList.filter((item:any)=>item.status == 'Success')
|
||||
}
|
||||
).catch(res=>{
|
||||
productImgData.generateList = productImgData.generateList.filter((item:any)=>item.status == 'Success')
|
||||
});
|
||||
generateProceedList.forEach((taskId:any)=>{
|
||||
const index = productImgData.generateList[props.productimgMenu.value].findIndex(item => (taskId == item.taskId));
|
||||
let value = {
|
||||
str:'delete',
|
||||
index,
|
||||
list:true,
|
||||
}
|
||||
console.log(value)
|
||||
if(props.productimgMenu.value == 'ToProductImage'){
|
||||
store.commit("setToProductImage", value);
|
||||
}else{
|
||||
store.commit("setRelightList", value);
|
||||
}
|
||||
})
|
||||
generateProceedList = []
|
||||
}
|
||||
}
|
||||
let scaleImage = ref()
|
||||
|
||||
@@ -19,13 +19,12 @@
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<!-- <i class="fi fi-rr-cross-small"></i> -->
|
||||
<svg
|
||||
width="46"
|
||||
height="46"
|
||||
width="100%" height="100%"
|
||||
viewBox="0 0 46 46"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3" />
|
||||
<circle cx="23" cy="23" r="23" fill="black" fill-opacity="0.3" />
|
||||
<rect
|
||||
x="32.5063"
|
||||
y="12"
|
||||
@@ -126,7 +125,7 @@
|
||||
:key="item.price"
|
||||
@click="setPromotionData(item)"
|
||||
>
|
||||
<div class="popular" v-show="item.sellWell">MOST POPULAR</div>
|
||||
<div class="popular" v-show="item.sellWell">{{ $t("Renew.MOSTPOPULAR") }}</div>
|
||||
<div class="priceBox">
|
||||
<div class="left">
|
||||
<p class="productType">1 {{ item.type.label }}</p>
|
||||
@@ -303,7 +302,7 @@ export default defineComponent({
|
||||
activity: false, //活动打折
|
||||
type: {
|
||||
value: "Month",
|
||||
label: "Monthly",
|
||||
label: computed(()=>t("Renew.Monthly")),
|
||||
},
|
||||
PaymentType: "CreditCard",
|
||||
promotionData: {
|
||||
@@ -320,7 +319,7 @@ export default defineComponent({
|
||||
typeValue: "year",
|
||||
type: {
|
||||
value: "Year",
|
||||
label: "Yearly",
|
||||
label: computed(()=>t("Renew.Yearly")),
|
||||
},
|
||||
PaymentType: "",
|
||||
promotionData: {
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="#000" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -92,6 +92,7 @@
|
||||
<textarea
|
||||
ref="textarea"
|
||||
class="textarea "
|
||||
|
||||
:placeholder="$t('Generate.inputContent1')"
|
||||
@input="ifMaximumLength"
|
||||
@keydown.enter="getPrductimg()"
|
||||
@@ -322,7 +323,7 @@ export default defineComponent({
|
||||
rv.forEach((item:any)=>{
|
||||
arr.push(item.taskId)
|
||||
})
|
||||
|
||||
generateProceedList = rv.map(user => user.taskId);
|
||||
// productimg.generateList.unshift(...rv)
|
||||
setPrductimg(arr)
|
||||
}
|
||||
@@ -371,9 +372,11 @@ export default defineComponent({
|
||||
// generateProceedList = rv.filter((item:any)=>item.status != 'Success' && item.status != 'Fail' && item.status != 'Invalid')
|
||||
let isEnd = false
|
||||
if(rv[0].status == 'Success'){
|
||||
rv[0].imgUrl = rv[0].url
|
||||
rv[0].resultType = scaleImageList.value[scaleImageIndex.value]?.resultType
|
||||
scaleImageList.value[scaleImageIndex.value] = rv[0]
|
||||
// rv[0].imgUrl = rv[0].url
|
||||
// rv[0].resultType = scaleImageList.value[scaleImageIndex.value]?.resultType
|
||||
// scaleImageList.value[scaleImageIndex.value] = rv[0]
|
||||
scaleImageList.value[scaleImageIndex.value].imgUrl = rv[0].url
|
||||
scaleImageList.value[scaleImageIndex.value].url = rv[0].url
|
||||
isEnd = true
|
||||
clearInterval(remPrductimgTime)
|
||||
}else if(rv[0].status == 'Fail'){
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="white"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="white"/>
|
||||
@@ -39,7 +39,7 @@
|
||||
{{ $t('selectImgList.Clear') }}
|
||||
</div>
|
||||
<div class="started_btn" @click="setOk()">
|
||||
OK
|
||||
{{ $t('selectImgList.ok') }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<div style="flex:1;text-align: right;" v-show="fall?.list?.length > 0">
|
||||
<div class="gallery_btn" v-show="schedule.num == 1||(schedule.num == 0 && !schedule.state)" @click="compute">Compute</div>
|
||||
<div class="gallery_btn" v-show="schedule.num == 1||(schedule.num == 0 && !schedule.state)" @click="compute">{{$t('brandDNA.Compute')}}</div>
|
||||
<div v-show="schedule.num != 1">
|
||||
<a-progress style="width:20rem;" :percent="schedule.num * 100" size="small" :showInfo="false" />
|
||||
</div>
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="black"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="black"/>
|
||||
@@ -84,7 +84,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<div style="width: 100%; display: flex;">
|
||||
<div class="gallery_btn" @click="submitAddBrand" style="width: 13rem; margin-left: auto;">OK</div>
|
||||
<div class="gallery_btn" @click="submitAddBrand" style="width: 13rem; margin-left: auto;">{{ $t('Habit.ok') }}</div>
|
||||
</div>
|
||||
<div class="mark_loading" v-show="isShowMark">
|
||||
<a-spin size="large" />
|
||||
|
||||
@@ -14,7 +14,7 @@
|
||||
>
|
||||
<div class="generalModel_btn">
|
||||
<div class="generalModel_closeIcon" @click.stop="cancelDsign()">
|
||||
<svg width="46" height="46" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<svg width="100%" height="100%" viewBox="0 0 46 46" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<circle cx="23" cy="23" r="23" fill="white" fill-opacity="0.3"/>
|
||||
<rect x="32.5063" y="12" width="3" height="29" rx="1.5" transform="rotate(45 32.5063 12)" fill="black"/>
|
||||
<rect x="34.6274" y="32.5059" width="3" height="29" rx="1.5" transform="rotate(135 34.6274 32.5059)" fill="black"/>
|
||||
|
||||