Merge branch 'main' of ssh://18.167.251.121:10002/aidlab/FiDA_Front
This commit is contained in:
@@ -1,8 +1,9 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/prettierrc",
|
||||
"semi": false,
|
||||
"tabWidth": 4,
|
||||
"singleQuote": true,
|
||||
"printWidth": 100,
|
||||
"trailingComma": "none"
|
||||
}
|
||||
"$schema": "https://json.schemastore.org/prettierrc",
|
||||
"semi": false,
|
||||
"tabWidth": 4,
|
||||
"singleQuote": true,
|
||||
"printWidth": 100,
|
||||
"useTabs": true,
|
||||
"trailingComma": "none"
|
||||
}
|
||||
|
||||
3
src/assets/icons/generateSketchEdit.svg
Normal file
3
src/assets/icons/generateSketchEdit.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="8" height="8" viewBox="0 0 8 8" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M7.11396 0C7.52817 -2.21271e-07 7.86396 0.335786 7.86396 0.75V6.0533C7.86396 6.46751 7.52817 6.8033 7.11396 6.8033C6.69975 6.8033 6.36396 6.46751 6.36396 6.0533V2.56066L1.28033 7.64429C0.987437 7.93718 0.512563 7.93718 0.21967 7.64429C-0.0732232 7.3514 -0.0732235 6.87652 0.21967 6.58363L5.3033 1.5H1.81066C1.39645 1.5 1.06066 1.16421 1.06066 0.75C1.06066 0.335786 1.39645 -2.21271e-07 1.81066 0H7.11396Z" fill="black"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 529 B |
3
src/assets/icons/sketchDelete.svg
Normal file
3
src/assets/icons/sketchDelete.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="12" height="13" viewBox="0 0 12 13" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M11.4781 2H8.9829V1.5C8.9829 1.1 8.82277 0.72043 8.5433 0.44043C8.26384 0.16043 7.88499 0 7.48575 0H4.49145C4.09221 0 3.71336 0.16043 3.43389 0.44043C3.15442 0.72043 2.9943 1.1 2.9943 1.5V2H0.49905C0.369297 2 0.239934 2.05039 0.150105 2.15039C0.0502949 2.24039 0 2.37 0 2.5C0 2.63 0.0502949 2.75961 0.150105 2.84961C0.239934 2.94961 0.369297 3 0.49905 3H0.9981V12C0.9981 12.27 1.10793 12.52 1.28759 12.71C1.47723 12.89 1.72671 13 1.9962 13H9.981C10.2505 13 10.5 12.89 10.6896 12.71C10.8693 12.52 10.9791 12.27 10.9791 12V3H11.4781C11.6079 3 11.7373 2.94961 11.8271 2.84961C11.9269 2.75961 11.9772 2.63 11.9772 2.5C11.9772 2.37 11.9269 2.24039 11.8271 2.15039C11.7373 2.05039 11.6079 2 11.4781 2ZM3.9924 1.5C3.9924 1.37 4.04269 1.24039 4.1425 1.15039C4.23233 1.05039 4.3617 1 4.49145 1H7.48575C7.6155 1 7.74486 1.05039 7.83469 1.15039C7.9345 1.24039 7.9848 1.37 7.9848 1.5V2H3.9924V1.5ZM9.981 12H1.9962V3H9.981V12ZM4.9905 5.5V9.5C4.9905 9.63 4.9402 9.75961 4.84039 9.84961C4.75056 9.94961 4.6212 10 4.49145 10C4.3617 10 4.23233 9.94961 4.1425 9.84961C4.04269 9.75961 3.9924 9.63 3.9924 9.5V5.5C3.9924 5.37 4.04269 5.24039 4.1425 5.15039C4.23233 5.05039 4.3617 5 4.49145 5C4.6212 5 4.75056 5.05039 4.84039 5.15039C4.9402 5.24039 4.9905 5.37 4.9905 5.5ZM7.9848 5.5V9.5C7.9848 9.63 7.9345 9.75961 7.83469 9.84961C7.74486 9.94961 7.6155 10 7.48575 10C7.35599 10 7.22663 9.94961 7.1368 9.84961C7.03699 9.75961 6.9867 9.63 6.9867 9.5V5.5C6.9867 5.37 7.03699 5.24039 7.1368 5.15039C7.22663 5.05039 7.35599 5 7.48575 5C7.6155 5 7.74486 5.05039 7.83469 5.15039C7.9345 5.24039 7.9848 5.37 7.9848 5.5Z" fill="#FF4747"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.7 KiB |
3
src/assets/icons/sketchRestore.svg
Normal file
3
src/assets/icons/sketchRestore.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="15" height="14" viewBox="0 0 15 14" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M7.08333 1.41667C3.91503 1.41667 1.41667 3.83275 1.41667 6.72917C1.41667 7.93035 1.84139 9.04043 2.56442 9.93465C2.69502 10.0962 2.74814 10.3069 2.70973 10.511C2.64157 10.8732 2.55238 11.2273 2.44848 11.5742C2.89512 11.5055 3.3283 11.4111 3.75296 11.2905C3.92954 11.2404 4.11868 11.2607 4.28054 11.3473C5.10515 11.7883 6.06096 12.0417 7.08333 12.0417C10.2516 12.0417 12.75 9.62558 12.75 6.72917C12.75 3.83275 10.2516 1.41667 7.08333 1.41667ZM0 6.72917C0 2.97515 3.21001 0 7.08333 0C10.9567 0 14.1667 2.97515 14.1667 6.72917C14.1667 10.4832 10.9567 13.4583 7.08333 13.4583C5.92831 13.4583 4.83503 13.1953 3.8685 12.727C3.09341 12.9276 2.29663 13.0513 1.46026 13.1028C1.21968 13.1177 0.988073 13.0091 0.845512 12.8148C0.70295 12.6204 0.669005 12.3669 0.755415 12.1419C0.960947 11.6067 1.13362 11.0817 1.25408 10.5534C0.465327 9.47006 0 8.15203 0 6.72917ZM7.08333 3.89583C7.47454 3.89583 7.79167 4.21296 7.79167 4.60417V6.02083H9.20833C9.59954 6.02083 9.91667 6.33796 9.91667 6.72917C9.91667 7.12037 9.59954 7.4375 9.20833 7.4375H7.79167V8.85417C7.79167 9.24537 7.47454 9.5625 7.08333 9.5625C6.69213 9.5625 6.375 9.24537 6.375 8.85417V7.4375H4.95833C4.56713 7.4375 4.25 7.12037 4.25 6.72917C4.25 6.33796 4.56713 6.02083 4.95833 6.02083H6.375V4.60417C6.375 4.21296 6.69213 3.89583 7.08333 3.89583Z" fill="#0D0D0D"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.4 KiB |
3
src/assets/icons/versionDelete.svg
Normal file
3
src/assets/icons/versionDelete.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="18" height="18" viewBox="0 0 18 18" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M13.5 4.5L4.5 13.5M4.5 4.5L13.5 13.5" stroke="#5A5A5A" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 235 B |
3
src/assets/icons/versionNewChat.svg
Normal file
3
src/assets/icons/versionNewChat.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="18" height="18" viewBox="0 0 18 18" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M9 1.89474C4.97439 1.89474 1.8 5.12616 1.8 9C1.8 10.6065 2.33964 12.0912 3.25832 13.2872C3.42426 13.5032 3.49176 13.785 3.44296 14.058C3.35635 14.5425 3.24302 15.0161 3.11101 15.4801C3.6785 15.3881 4.2289 15.2619 4.76847 15.1006C4.99282 15.0335 5.23315 15.0608 5.43881 15.1766C6.48655 15.7664 7.70098 16.1053 9 16.1053C13.0256 16.1053 16.2 12.8738 16.2 9C16.2 5.12616 13.0256 1.89474 9 1.89474ZM0 9C0 3.97915 4.0786 0 9 0C13.9214 0 18 3.97915 18 9C18 14.0209 13.9214 18 9 18C7.53244 18 6.14334 17.6482 4.91527 17.0218C3.93045 17.2902 2.91807 17.4555 1.85539 17.5245C1.54972 17.5444 1.25543 17.3992 1.0743 17.1393C0.89316 16.8793 0.85003 16.5403 0.959821 16.2393C1.22097 15.5235 1.44036 14.8213 1.59342 14.1148C0.591239 12.6658 0 10.903 0 9ZM9 5.21053C9.49706 5.21053 9.9 5.63468 9.9 6.1579V8.05263H11.7C12.1971 8.05263 12.6 8.47678 12.6 9C12.6 9.52322 12.1971 9.94737 11.7 9.94737H9.9V11.8421C9.9 12.3653 9.49706 12.7895 9 12.7895C8.50294 12.7895 8.1 12.3653 8.1 11.8421V9.94737H6.3C5.80294 9.94737 5.4 9.52322 5.4 9C5.4 8.47678 5.80294 8.05263 6.3 8.05263H8.1V6.1579C8.1 5.63468 8.50294 5.21053 9 5.21053Z" fill="#5A5A5A"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.2 KiB |
3
src/assets/icons/versionRestore.svg
Normal file
3
src/assets/icons/versionRestore.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M1.64029 0C2.1068 0 2.48498 0.377023 2.48498 0.842105V2.16586C3.91988 0.823234 5.85092 0 7.97546 0C12.4073 0 16 3.58172 16 8C16 12.4183 12.4073 16 7.97546 16C3.86242 16 0.473169 12.9158 0.00582232 8.94012C-0.0484778 8.4782 0.283113 8.05986 0.746451 8.00572C1.20979 7.95159 1.62942 8.28217 1.68372 8.74409C2.05249 11.8812 4.72939 14.3158 7.97546 14.3158C11.4743 14.3158 14.3106 11.4881 14.3106 8C14.3106 4.51189 11.4743 1.68421 7.97546 1.68421C6.09992 1.68421 4.41391 2.49658 3.25326 3.78947H5.46514C5.93164 3.78947 6.30982 4.1665 6.30982 4.63158C6.30982 5.09666 5.93164 5.47368 5.46514 5.47368H1.64029C1.1847 5.47368 0.813351 5.1141 0.796223 4.66408C0.795462 4.64649 0.795254 4.62886 0.795606 4.6112V0.842105C0.795606 0.377023 1.17379 0 1.64029 0Z" fill="#5A5A5A"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 878 B |
234
src/lang/en.ts
234
src/lang/en.ts
@@ -1,118 +1,122 @@
|
||||
export default {
|
||||
AlphaVersion: '2026 Alpha Version',
|
||||
Login: {
|
||||
login: 'Log in',
|
||||
register: 'Register',
|
||||
signUp: 'Sign up',
|
||||
loginTo: 'Log on to <span>FiDA</span>',
|
||||
loginTitle: 'A multi-agent canvas for rapid, trend driven design iteration.',
|
||||
name: 'Name',
|
||||
email: 'Email',
|
||||
password: 'Password',
|
||||
enterName: 'Enter your name',
|
||||
enterEmail: 'Enter your email',
|
||||
enterPassword: 'Enter your password',
|
||||
forgetPassword: 'Forget password?',
|
||||
pleaseInputName: 'Please input the name',
|
||||
nameLengthError: 'Name length must be between {min} and {max} characters',
|
||||
pleaseInputEmail: 'Please input the email',
|
||||
emailFormatError: 'Please input the email again',
|
||||
pleaseInputPassword: 'Please input the password',
|
||||
passwordLengthError: 'Password length must be between {min} and {max} characters',
|
||||
pleaseTermsPolicy: 'Please agree to the Terms, Policy and Fees',
|
||||
agreeTermsPolicy:
|
||||
'I agree to the <span onclick="onClickPrivacy()">Terms, Policy</span> and Fees.',
|
||||
noAccountToSignUp: `Don't have an account? <span onclick="onClickRegister()">Sign up</span>`,
|
||||
signUpFor: 'Sign up for <span>FiDA</span>',
|
||||
registerTip: 'A multi-agent canvas for rapid, trend driven design iteration.',
|
||||
havenAccountToLogin: `Already have an account? <span onclick="onClickLogin()">Log in</span>`,
|
||||
verifyEmail: 'Verify your email address',
|
||||
verifyCodeHasSent: 'A verification code has been sent to <span>{email}</span>',
|
||||
verify: 'Verify',
|
||||
resendCode: 'Resend Code',
|
||||
resendCodeIn: 'Resend Code in {time}',
|
||||
orContinueWith: 'or continue with',
|
||||
googleLogin: 'Sign in with Google',
|
||||
wechatLogin: 'Sign in with Wechat',
|
||||
indexTip: 'A multi-agent canvas for rapid, trend driven design iteration.',
|
||||
},
|
||||
Nuic: {
|
||||
hiName: 'Hi, {name}. This is Fiphant.',
|
||||
nuic1Title: `Help him discover the <b>"YOU"</b> in your space.`,
|
||||
nuic1Tip: `Let's set up your profile. A few quick details will help Fiphant understand<br />your needs and find exactly what you're looking for.`,
|
||||
letsGo: 'Let’s go, Fiphant!',
|
||||
skip: 'Skip',
|
||||
next: 'Next',
|
||||
nuic2Title: `What <b>vibe</b> do you usually go for?`,
|
||||
loadMore: 'Load more',
|
||||
nuic3Title: `<b>Where</b> are you based? What do you <b>do</b>?`,
|
||||
basedIn: 'Based in',
|
||||
role: 'Role',
|
||||
allSet: 'All set!',
|
||||
loadingTip: 'We’re customizing your dashboard.',
|
||||
},
|
||||
Home: {
|
||||
creditsNum: 'Credits: {num}',
|
||||
newProject: 'New Project',
|
||||
home: 'Home',
|
||||
history: 'History',
|
||||
today: 'Today',
|
||||
yesterday: 'Yesterday',
|
||||
earlierChat: 'Earlier Chat'
|
||||
},
|
||||
Input: {
|
||||
placeholder: 'Please input',
|
||||
selectPlaceholder: 'Please select',
|
||||
typePlaceholder: 'Type',
|
||||
areaPlaceholder: 'Region',
|
||||
stylePlaceholder: 'Style',
|
||||
types: {
|
||||
sofa: 'Sofa',
|
||||
desk: 'Desk',
|
||||
chair: 'Chair'
|
||||
},
|
||||
styles: {
|
||||
Coastal: 'Coastal',
|
||||
Verdant: 'Verdant',
|
||||
Traditional: 'Traditional',
|
||||
CenturyChrome: 'Century\nChrome',
|
||||
ModernRevival: 'Modern\nRevival',
|
||||
Tuscan2000s: "Tuscan\n2000's",
|
||||
Bauhaus: 'Bauhaus',
|
||||
Constructivism: 'Constructivism',
|
||||
NordicNoir: 'Nordic\nNoir'
|
||||
},
|
||||
chooseStyle: 'Choose Style',
|
||||
setting: 'Setting',
|
||||
settingOptions: {
|
||||
creativity: 'Creativity',
|
||||
diversity: 'Diversity',
|
||||
relevance: 'Relevance'
|
||||
},
|
||||
confirm: 'Confirm',
|
||||
styleTitle: 'Settings',
|
||||
createProject: 'Create Project',
|
||||
trendingReport: 'Trending Report'
|
||||
},
|
||||
area: {
|
||||
unitedStates: 'United States',
|
||||
singapore: 'Singapore',
|
||||
australia: 'Australia',
|
||||
southKorea: 'South Korea',
|
||||
china: 'China',
|
||||
italy: 'Italy',
|
||||
france: 'France',
|
||||
japan: 'Japan',
|
||||
canada: 'Canada',
|
||||
germany: 'Germany'
|
||||
},
|
||||
Login: {
|
||||
Login: 'Log in',
|
||||
SignUp: 'Sign up',
|
||||
LoginTo: 'Log on to',
|
||||
LoginTitle: 'A multi-agent canvas for rapid, trend driven design iteration.',
|
||||
name: 'Name',
|
||||
email: 'Email',
|
||||
password: 'Password',
|
||||
enterName: 'Enter your name',
|
||||
enterEmail: 'Enter your email',
|
||||
enterPassword: 'Enter your password',
|
||||
forgetPassword: 'Forget password?',
|
||||
pleaseInputName: 'Please input the name',
|
||||
nameLengthError: 'Name length must be between {min} and {max} characters',
|
||||
pleaseInputEmail: 'Please input the email',
|
||||
emailFormatError: 'Please input the email again',
|
||||
pleaseInputPassword: 'Please input the password',
|
||||
passwordLengthError: 'Password length must be between {min} and {max} characters',
|
||||
pleaseTermsPolicy: 'Please agree to the Terms, Policy and Fees',
|
||||
agreeTermsPolicy:
|
||||
'I agree to the <span onclick="onClickPrivacy()">Terms, Policy</span> and Fees.',
|
||||
noAccountToSignUp: `Don't have an account? <span onclick="onClickRegister()">Sign up</span>`,
|
||||
registerFor: 'Register for',
|
||||
registerTip: 'A multi-agent canvas for rapid, trend driven design iteration.',
|
||||
havenAccountToLogin: `Already have an account? <span onclick="onClickLogin()">Log in</span>`,
|
||||
verifyEmail: 'Verify your email address',
|
||||
verifyCodeHasSent: 'A verification code has been sent to <span>{email}</span>',
|
||||
verify: 'Verify',
|
||||
resendCode: 'Resend Code',
|
||||
resendCodeIn: 'Resend Code in {time}',
|
||||
orContinueWith: 'or continue with',
|
||||
googleLogin: 'Sign in with Google',
|
||||
wechatLogin: 'Sign in with Wechat'
|
||||
},
|
||||
Nuic: {
|
||||
hiName: 'Hi, {name}.',
|
||||
nuic1Title: `Help Fiphant discover the <b>'YOU'</b> in your space.`,
|
||||
nuic1Tip: `Let's set up your profile. A few quick details will help Fiphant understand<br />your needs and find exactly what you're looking for.`,
|
||||
letsGo: 'Let’s go, Fiphant!',
|
||||
skip: 'Skip',
|
||||
next: 'Next',
|
||||
nuic2Title: `What's your dream <b>home vibe</b> ?`,
|
||||
loadMore: 'Load more',
|
||||
nuic3Title: `Where <b>are you based</b>? What do you <b>do</b> ?`,
|
||||
basedIn: 'Based in',
|
||||
role: 'Role',
|
||||
allSet: 'All set!'
|
||||
},
|
||||
Home: {
|
||||
creditsNum: 'Credits: {num}',
|
||||
newProject: 'New Project',
|
||||
home: 'Home',
|
||||
history: 'History',
|
||||
today: 'Today',
|
||||
yesterday: 'Yesterday',
|
||||
earlierChat: 'Earlier Chat'
|
||||
},
|
||||
Input: {
|
||||
placeholder: 'Please input',
|
||||
selectPlaceholder: 'Please select',
|
||||
typePlaceholder: 'Type',
|
||||
areaPlaceholder: 'Region',
|
||||
stylePlaceholder: 'Style',
|
||||
types: {
|
||||
sofa: 'Sofa',
|
||||
desk: 'Desk',
|
||||
chair: 'Chair'
|
||||
},
|
||||
styles: {
|
||||
Coastal: 'Coastal',
|
||||
Verdant: 'Verdant',
|
||||
Traditional: 'Traditional',
|
||||
CenturyChrome: 'Century\nChrome',
|
||||
ModernRevival: 'Modern\nRevival',
|
||||
Tuscan2000s: "Tuscan\n2000's",
|
||||
Bauhaus: 'Bauhaus',
|
||||
Constructivism: 'Constructivism',
|
||||
NordicNoir: 'Nordic\nNoir'
|
||||
},
|
||||
chooseStyle: 'Choose Style',
|
||||
setting: 'Setting',
|
||||
settingOptions: {
|
||||
creativity: 'Creativity',
|
||||
diversity: 'Diversity',
|
||||
relevance: 'Relevance'
|
||||
},
|
||||
confirm: 'Confirm'
|
||||
},
|
||||
area: {
|
||||
unitedStates: 'United States',
|
||||
singapore: 'Singapore',
|
||||
australia: 'Australia',
|
||||
southKorea: 'South Korea',
|
||||
china: 'China',
|
||||
italy: 'Italy',
|
||||
france: 'France',
|
||||
japan: 'Japan',
|
||||
canada: 'Canada',
|
||||
germany: 'Germany'
|
||||
},
|
||||
|
||||
// Version Tree
|
||||
VersionTree: {
|
||||
versionInformation: 'Version Information',
|
||||
input: 'Input',
|
||||
userRequest: 'User Request',
|
||||
sketch: 'Sketch',
|
||||
generateResult: 'Generate Result'
|
||||
}
|
||||
// Version Tree
|
||||
VersionTree: {
|
||||
versionInformation: 'Version Information',
|
||||
input: 'Input',
|
||||
userRequest: 'User Request',
|
||||
sketch: 'Sketch',
|
||||
generateResult: 'Generate Result',
|
||||
linearNodeTree: 'Linear Node Tree',
|
||||
branchingNodeTree: 'Branching Node Tree',
|
||||
restore: 'Restore',
|
||||
newChat: 'New Chat',
|
||||
delete: 'Delete'
|
||||
},
|
||||
//generateSketch
|
||||
generateSketch: {
|
||||
restore: 'Restore',
|
||||
delete: 'Delete',
|
||||
edit: 'Edit'
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<script setup lang="ts">
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs, computed } from "vue";
|
||||
import VersionTreeIndex from './versionTree/index.vue'
|
||||
import GenerateSketch from './generateSketch/index.vue'
|
||||
//const props = defineProps({
|
||||
//})
|
||||
//const emit = defineEmits([
|
||||
@@ -13,6 +14,73 @@ const versionTreeData = ref({
|
||||
return []
|
||||
})
|
||||
})
|
||||
const generateData = ref({
|
||||
list:[
|
||||
{
|
||||
id:'1',
|
||||
type:'waiting',
|
||||
},
|
||||
{
|
||||
id:'2',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'3',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'4',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'5',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'6',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'7',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'8',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
{
|
||||
id:'9',
|
||||
type:'success',
|
||||
img:'/img/success.png',
|
||||
},
|
||||
]
|
||||
})
|
||||
const generateSketch = ()=>{
|
||||
generateData.value.list.push(
|
||||
{
|
||||
id:'2',
|
||||
type:'waiting',
|
||||
img:'/img/success.png',
|
||||
}
|
||||
)
|
||||
sketchRestore('2')
|
||||
}
|
||||
|
||||
const sketchRestore = (id)=>{
|
||||
generateData.value.list.forEach((item)=>{
|
||||
if(item.id == id){
|
||||
item.type = 'waiting'
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
onMounted(()=>{
|
||||
})
|
||||
onUnmounted(()=>{
|
||||
@@ -22,8 +90,14 @@ const {} = toRefs(data);
|
||||
</script>
|
||||
<template>
|
||||
<div class="homeNavBox">
|
||||
<el-button type="primary" @click="versionTreeData.drawer = true">open Version Tree</el-button>
|
||||
<div>
|
||||
<el-button type="primary" @click="versionTreeData.drawer = true">open Version Tree</el-button>
|
||||
<el-button type="primary" @click="generateSketch">Generate</el-button>
|
||||
</div>
|
||||
<VersionTreeIndex v-model:versionTreeData="versionTreeData" />
|
||||
<div class="generateSketchBox">
|
||||
<GenerateSketch v-model:generateData="generateData"></GenerateSketch>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style lang="less" scoped>
|
||||
@@ -31,5 +105,14 @@ const {} = toRefs(data);
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
display: flex;
|
||||
> .generateSketchBox{
|
||||
height: 100%;
|
||||
width: 50%;
|
||||
overflow-y: auto;
|
||||
&::-webkit-scrollbar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
164
src/views/home/generateSketch/generateItem.vue
Normal file
164
src/views/home/generateSketch/generateItem.vue
Normal file
@@ -0,0 +1,164 @@
|
||||
<script setup lang="ts">
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs } from "vue";
|
||||
const props = defineProps({
|
||||
item: {
|
||||
type: Object,
|
||||
default: () => ({})
|
||||
} as any,
|
||||
})
|
||||
const emit = defineEmits([
|
||||
'sketchRestore','sketchDelete'
|
||||
])
|
||||
let data = reactive({
|
||||
})
|
||||
|
||||
const morePopoverRef = ref(null)
|
||||
const handleClick = ()=>{
|
||||
morePopoverRef.value?.hide()
|
||||
}
|
||||
|
||||
const sketchRestore = ()=>{
|
||||
emit('sketchRestore')
|
||||
handleClick()
|
||||
}
|
||||
const sketchDelete = ()=>{
|
||||
emit('sketchDelete')
|
||||
handleClick()
|
||||
}
|
||||
|
||||
onMounted(()=>{
|
||||
})
|
||||
onUnmounted(()=>{
|
||||
})
|
||||
defineExpose({})
|
||||
const {} = toRefs(data);
|
||||
</script>
|
||||
<template>
|
||||
<div class="generateItem">
|
||||
<div v-if="item.type === 'waiting'" class="waitingItem">
|
||||
等待
|
||||
<!-- <el-spinner style="display: inline-block;" /> -->
|
||||
</div>
|
||||
|
||||
<div v-else-if="item.type === 'success'" class="successItem">
|
||||
<img :src="item.img" alt="">
|
||||
<div class="more">
|
||||
<el-popover
|
||||
width="10rem"
|
||||
min-width="10rem"
|
||||
ref="morePopoverRef"
|
||||
trigger="click"
|
||||
popper-class="moreBox"
|
||||
placement="bottom-end"
|
||||
>
|
||||
<template #reference>
|
||||
<span class="icon"><svg-icon name="more" size="25" /></span>
|
||||
</template>
|
||||
<template #default>
|
||||
<div class="item" @click="sketchRestore">
|
||||
<div class="icon">
|
||||
<SvgIcon name="sketchRestore" size="14" />
|
||||
</div>
|
||||
<span>{{ $t('generateSketch.restore') }}</span>
|
||||
</div>
|
||||
<div class="item delete" @click="sketchDelete">
|
||||
<div class="icon">
|
||||
<SvgIcon name="sketchDelete" size="14" />
|
||||
</div>
|
||||
<span>{{ $t('generateSketch.delete') }}</span>
|
||||
</div>
|
||||
</template>
|
||||
</el-popover>
|
||||
</div>
|
||||
<div class="edit" @click="$emit('edit')">
|
||||
<span>{{ $t('generateSketch.edit') }}</span>
|
||||
<div class="icon">
|
||||
<SvgIcon name="generateSketchEdit" size="7" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style lang="less">
|
||||
.el-popover.el-popper.moreBox{
|
||||
border-radius: 1rem;
|
||||
padding: .6rem .7rem;
|
||||
min-width: 10rem;
|
||||
.item{
|
||||
display: flex;
|
||||
cursor: pointer;
|
||||
border-radius: .4rem;
|
||||
align-items: center;
|
||||
padding: .6rem .7rem;
|
||||
margin-bottom: 1.2rem;
|
||||
&.delete{
|
||||
margin-bottom: 0rem;
|
||||
color: #ff4747;
|
||||
}
|
||||
&:hover{
|
||||
background-color: #f6f6f6;
|
||||
}
|
||||
> .icon{
|
||||
margin-right: .7rem;
|
||||
}
|
||||
> span{
|
||||
color: #000;
|
||||
font-weight: 500;
|
||||
font-size: 1.3rem;
|
||||
line-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
<style lang="less" scoped>
|
||||
.generateItem{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
> div{
|
||||
position: relative;
|
||||
}
|
||||
> .waitingItem,.successItem{
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
> .successItem{
|
||||
> .more{
|
||||
position: absolute;
|
||||
top: 1.2rem;
|
||||
right: 1.2rem;
|
||||
transition: all .3s;
|
||||
border-radius: .3rem;
|
||||
&:hover{
|
||||
background-color: #e8e8e8;
|
||||
}
|
||||
.icon{
|
||||
width: 2.4rem;
|
||||
height: 2.4rem;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
> .edit{
|
||||
position: absolute;
|
||||
bottom: 1rem;
|
||||
right: 1rem;
|
||||
border-radius: 2rem;
|
||||
border: 2px solid #e5e5e5;
|
||||
background-color: #fff;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
padding: .65rem 1.2rem;
|
||||
cursor: pointer;
|
||||
> span{
|
||||
margin-right: .6rem;
|
||||
font-weight: 500;
|
||||
font-size: 1.4rem;
|
||||
line-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
52
src/views/home/generateSketch/index.vue
Normal file
52
src/views/home/generateSketch/index.vue
Normal file
@@ -0,0 +1,52 @@
|
||||
<script setup lang="ts">
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs } from "vue";
|
||||
import GenerateItem from './generateItem.vue'
|
||||
|
||||
const props = defineProps({
|
||||
generateData:{
|
||||
type:Object,
|
||||
default:()=>{
|
||||
return {
|
||||
list:[]
|
||||
}
|
||||
},
|
||||
},
|
||||
})
|
||||
//const emit = defineEmits([
|
||||
//])
|
||||
let data = reactive({
|
||||
})
|
||||
onMounted(()=>{
|
||||
})
|
||||
onUnmounted(()=>{
|
||||
})
|
||||
defineExpose({})
|
||||
const {} = toRefs(data);
|
||||
</script>
|
||||
<template>
|
||||
<div class="generateSketch">
|
||||
<div v-for="item in generateData.list" :key="item.id" class="item">
|
||||
<GenerateItem :item="item" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.generateSketch{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
align-content: flex-start;
|
||||
gap: 1.2rem;
|
||||
.item{
|
||||
width: calc((100% - 1.2rem * 3) / 4);
|
||||
//设置比例属性 1 / 1
|
||||
aspect-ratio: 1 / 1;
|
||||
background-color: #fff;
|
||||
border-radius: 1.6rem;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -36,7 +36,6 @@ const {} = toRefs(data);
|
||||
<div class="infoTitle">{{ type == 'user'? $t('VersionTree.userRequest'): $t('VersionTree.generateResult') }}</div>
|
||||
<div class="history">
|
||||
Design a modern yellow sofa that combines comfort, elegance, and contemporary aesthetics.
The sofa features a warm, soft yellow tone (mustard or light ochre), with a minimalist silhouette and clean lines.
Upholstered in high-quality fabric with a subtle texture, offering a cozy and inviting feel.
The seat is deep and plush, with generous cushioning for relaxation, while the backrest and armrests are softly rounded to enhance comfort.
|
||||
Design a modern yellow sofa that combines comfort, elegance, and contemporary aesthetics.
The sofa features a warm, soft yellow tone (mustard or light ochre), with a minimalist silhouette and clean lines.
Upholstered in high-quality fabric with a subtle texture, offering a cozy and inviting feel.
The seat is deep and plush, with generous cushioning for relaxation, while the backrest and armrests are softly rounded to enhance comfort.
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
@@ -91,12 +90,16 @@ const {} = toRefs(data);
|
||||
flex: 1;
|
||||
overflow-y: auto;
|
||||
margin-left: 3rem;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: #ababab #f1f5f9;
|
||||
-ms-overflow-style: -ms-autohiding-scrollbar;
|
||||
&::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
&::-webkit-scrollbar-thumb {
|
||||
border-radius: 4px;
|
||||
background: #ababab;
|
||||
}
|
||||
&::-webkit-scrollbar-track {
|
||||
background: #f1f5f9;
|
||||
border-radius: 10px;
|
||||
border-radius: 4px;
|
||||
background: #d9d9d9;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,8 +4,10 @@ import VersionDetail from './versionDetail.vue'
|
||||
import ChatHistory from './chatHistory.vue'
|
||||
//const props = defineProps({
|
||||
//})
|
||||
//const emit = defineEmits([
|
||||
//])
|
||||
const emit = defineEmits([
|
||||
'versionRestore',
|
||||
'versionDelete',
|
||||
])
|
||||
const detailData = ref({
|
||||
id:1,
|
||||
versionDetail:{
|
||||
@@ -30,7 +32,11 @@ defineExpose({})
|
||||
<template>
|
||||
<div class="detailBox">
|
||||
<div class="versionDetail">
|
||||
<VersionDetail :versionDetail="detailData.versionDetail"></VersionDetail>
|
||||
<VersionDetail
|
||||
:versionDetail="detailData.versionDetail"
|
||||
@versionRestore="()=>emit('versionRestore')"
|
||||
@versionDelete="emit('versionDelete')"
|
||||
></VersionDetail>
|
||||
</div>
|
||||
<div class="useInput">
|
||||
<ChatHistory type="user"></ChatHistory>
|
||||
|
||||
@@ -8,10 +8,28 @@ const props = defineProps({
|
||||
default: () => ({})
|
||||
}
|
||||
})
|
||||
//const emit = defineEmits([
|
||||
//])
|
||||
const emit = defineEmits([
|
||||
'versionRestore',
|
||||
'versionDelete',
|
||||
])
|
||||
let data = reactive({
|
||||
})
|
||||
|
||||
const morePopoverRef = ref(null)
|
||||
const handleClick = ()=>{
|
||||
morePopoverRef.value?.hide()
|
||||
}
|
||||
|
||||
const versionRestore = ()=>{
|
||||
emit('versionRestore')
|
||||
handleClick()
|
||||
}
|
||||
|
||||
const versionDelete = ()=>{
|
||||
emit('versionDelete')
|
||||
handleClick()
|
||||
}
|
||||
|
||||
onMounted(()=>{
|
||||
})
|
||||
onUnmounted(()=>{
|
||||
@@ -25,7 +43,41 @@ const {} = toRefs(data);
|
||||
<span class="titleText">
|
||||
{{ $t('VersionTree.versionInformation') }}
|
||||
</span>
|
||||
<span class="icon"><svg-icon name="more" size="25" /></span>
|
||||
<el-popover
|
||||
width="24rem"
|
||||
ref="morePopoverRef"
|
||||
trigger="click"
|
||||
popper-class="moreBox"
|
||||
placement="bottom-end"
|
||||
>
|
||||
<template #reference>
|
||||
<span class="icon"><svg-icon name="more" size="25" /></span>
|
||||
</template>
|
||||
<template #default>
|
||||
<div class="topBtn">
|
||||
<div class="item" @click="versionRestore">
|
||||
<div class="icon">
|
||||
<SvgIcon name="versionRestore" size="18" />
|
||||
</div>
|
||||
<span>{{ $t('VersionTree.restore') }}</span>
|
||||
</div>
|
||||
<!-- <div class="item" @click="$emit('versionNewChat')">
|
||||
<div class="icon">
|
||||
<SvgIcon name="versionNewChat" size="18" />
|
||||
</div>
|
||||
<span>{{ $t('VersionTree.newChat') }}</span>
|
||||
</div> -->
|
||||
</div>
|
||||
<div class="bottomBtn">
|
||||
<div class="item" @click="versionDelete">
|
||||
<div class="icon">
|
||||
<SvgIcon name="versionDelete" size="18" />
|
||||
</div>
|
||||
<span>{{ $t('VersionTree.delete') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
</el-popover>
|
||||
</div>
|
||||
<div class="version">{{versionDetail.version}}</div>
|
||||
<div class="time marBott1">{{versionDetail.versionTime}}</div>
|
||||
@@ -33,26 +85,71 @@ const {} = toRefs(data);
|
||||
<div class="time gray">{{versionDetail.versionSketchTime}}</div>
|
||||
</div>
|
||||
</template>
|
||||
<style lang="less">
|
||||
.el-popover.el-popper.moreBox{
|
||||
border-radius: .8rem;
|
||||
padding: 0;
|
||||
.topBtn,.bottomBtn{
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
padding: .8rem;
|
||||
.item{
|
||||
display: flex;
|
||||
padding: 0rem 1rem;
|
||||
cursor: pointer;
|
||||
line-height: 3.2rem;
|
||||
border-radius: .4rem;
|
||||
height: 3.2rem;
|
||||
align-items: center;
|
||||
&:hover{
|
||||
background-color: #f6f6f6;
|
||||
}
|
||||
> .icon{
|
||||
margin-right: 1rem;
|
||||
}
|
||||
> span{
|
||||
color: #000;
|
||||
font-weight: 500;
|
||||
font-size: 1.5rem;
|
||||
line-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
.topBtn{
|
||||
border-bottom: 1px solid #d4d4d4;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
<style lang="less" scoped>
|
||||
.versionDetail{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
> .title{
|
||||
line-height: 2rem;
|
||||
line-height: 3.2rem;
|
||||
font-size: 1.4rem;
|
||||
color: #000;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
height: 2rem;
|
||||
margin-bottom: 2.8rem;
|
||||
height: 3.2rem;
|
||||
margin-bottom: 2rem;
|
||||
> .titleText{
|
||||
opacity: .5;
|
||||
font-weight: 600;
|
||||
font-family: 'SemiBold';
|
||||
}
|
||||
> .icon{
|
||||
.icon{
|
||||
color: #5a5a5a;
|
||||
width: 3.6rem;
|
||||
height: 100%;
|
||||
border-radius: .6rem;
|
||||
cursor: pointer;
|
||||
transition: all .3s;
|
||||
&:hover{
|
||||
background-color: #E5E5E5;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
> .version{
|
||||
|
||||
@@ -2,6 +2,9 @@
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs } from "vue";
|
||||
import Tree from './tree/index.vue'
|
||||
import Detail from './detail/index.vue'
|
||||
import { versionsList } from './tools/versionsData'
|
||||
import { findAndAddChild, findAndRemoveChild } from './tools/tools'
|
||||
|
||||
const props = defineProps({
|
||||
versionTreeData:{
|
||||
type:Object,
|
||||
@@ -15,13 +18,51 @@ const props = defineProps({
|
||||
})
|
||||
//const emit = defineEmits([
|
||||
//])
|
||||
|
||||
const treeRef = ref(null)
|
||||
const treeKey = ref(0)
|
||||
const treeState = ref(true)//
|
||||
|
||||
const selectItem = ref({})
|
||||
const selectItem:any = ref({})
|
||||
|
||||
const openTree = ()=>{
|
||||
treeState.value = !treeState.value
|
||||
|
||||
const openTree = (state)=>{
|
||||
treeState.value = state
|
||||
}
|
||||
|
||||
const versionRestore = ()=>{
|
||||
let id = ''
|
||||
if(selectItem.value?.child?.length > 0){
|
||||
function findMaxForYourFormat(items) {
|
||||
let max = 0
|
||||
|
||||
for (const item of items) {
|
||||
// 直接分割并取最后一部分
|
||||
const parts = item.id.split('-')
|
||||
const lastNumber = parseInt(parts[parts.length - 1], 10)
|
||||
|
||||
if (lastNumber > max) {
|
||||
max = lastNumber
|
||||
}
|
||||
}
|
||||
|
||||
return max
|
||||
}
|
||||
id = `${selectItem.value?.id}-${findMaxForYourFormat(selectItem.value?.child) + 1}`
|
||||
}else{
|
||||
id = `${selectItem.value?.id}-1`
|
||||
}
|
||||
let addObj = {
|
||||
id,
|
||||
name:`V${id}`
|
||||
}
|
||||
findAndAddChild(versionsList, selectItem.value?.id, addObj)
|
||||
selectItem.value = {...addObj}
|
||||
treeKey.value++
|
||||
}
|
||||
const versionDelete = (versionDetail)=>{
|
||||
if(!selectItem.value.id)return
|
||||
findAndRemoveChild(versionsList, selectItem.value.id)
|
||||
treeKey.value++
|
||||
}
|
||||
|
||||
let data = reactive({
|
||||
@@ -50,16 +91,32 @@ const {} = toRefs(data);
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div style="display: flex;" class="expandBtnBox">
|
||||
<el-button class="expandBtn" @click="openTree" style="width: 5rem;">+</el-button>
|
||||
<el-button class="expandBtn" @click="openTree" style="width: 5rem;">-</el-button>
|
||||
<div class="expandBtnBox">
|
||||
<div class="btn" @click="openTree(true)">
|
||||
<div class="bg left" :class="{'active':treeState}"></div>
|
||||
<span>{{ $t('VersionTree.linearNodeTree') }}</span>
|
||||
</div>
|
||||
<div class="btn" @click="openTree(false)">
|
||||
<div class="bg right" :class="{'active':!treeState}"></div>
|
||||
<span>{{ $t('VersionTree.branchingNodeTree') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="versionTreeBox">
|
||||
<div class="tree">
|
||||
<Tree :treeState="treeState" v-model:selectItem="selectItem"></Tree>
|
||||
<Tree
|
||||
ref="treeRef"
|
||||
:versionsList="versionsList"
|
||||
:treeState="treeState"
|
||||
v-model:selectItem="selectItem"
|
||||
:key="treeKey"
|
||||
></Tree>
|
||||
</div>
|
||||
<div class="detail">
|
||||
<Detail v-model:selectItem="selectItem"></Detail>
|
||||
<Detail
|
||||
v-model:selectItem="selectItem"
|
||||
@versionRestore="versionRestore"
|
||||
@versionDelete="versionDelete"
|
||||
></Detail>
|
||||
</div>
|
||||
</div>
|
||||
</el-drawer>
|
||||
@@ -71,7 +128,7 @@ const {} = toRefs(data);
|
||||
--treeItem-width: 5.4rem;
|
||||
--treeItem-height: 5.4rem;
|
||||
--treeItem-raduis: 50%;
|
||||
--treeItem-border: 2px solid #000;
|
||||
--treeItem-border: 2px solid #C1C1C1;
|
||||
--treeItem-background: #ffffff;
|
||||
--treeItem-active-background: #e6e6e6;
|
||||
|
||||
@@ -100,7 +157,43 @@ const {} = toRefs(data);
|
||||
}
|
||||
}
|
||||
.expandBtnBox{
|
||||
|
||||
padding: .4rem .7rem;
|
||||
border-radius: 1.1rem;
|
||||
background-color: #f3f3f3;
|
||||
display: flex;
|
||||
margin-left: auto;
|
||||
margin-top: 2.1rem;
|
||||
margin-right: 3rem;
|
||||
> .btn{
|
||||
padding: .6rem .5rem;
|
||||
position: relative;
|
||||
cursor: pointer;
|
||||
> .bg{
|
||||
position: absolute;
|
||||
background-color: #fff;
|
||||
border-radius: .6rem;
|
||||
width: 0;
|
||||
height: 100%;
|
||||
transition: all .3s;
|
||||
top: 0;
|
||||
&.active{
|
||||
width: 100%;
|
||||
}
|
||||
&.left{
|
||||
right: 0;
|
||||
}
|
||||
&.right{
|
||||
left: 0;
|
||||
}
|
||||
}
|
||||
> span{
|
||||
position: relative;
|
||||
font-size: 1.3rem;
|
||||
line-height: 1.8rem;
|
||||
font-weight: 500;
|
||||
letter-spacing: -0.08px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.versionTreeBox{
|
||||
flex: 1;
|
||||
|
||||
@@ -36,7 +36,10 @@ export function useLayout() {
|
||||
// if you need width+height of nodes for your layout, you can use the dimensions property of the internal node (`GraphNode` type)
|
||||
const graphNode = findNode(node.id)
|
||||
|
||||
dagreGraph.setNode(node.id, { width: graphNode.dimensions.width || 150, height: graphNode.dimensions.height || 50 })
|
||||
dagreGraph.setNode(node.id, {
|
||||
width: graphNode.dimensions.width || 150,
|
||||
height: graphNode.dimensions.height || 50
|
||||
})
|
||||
}
|
||||
|
||||
for (const edge of edges) {
|
||||
@@ -53,11 +56,11 @@ export function useLayout() {
|
||||
let targetPosition, sourcePosition
|
||||
switch (layoutDirection) {
|
||||
case 'BT': // 从上到下 (Top to Bottom)
|
||||
targetPosition = Position.Bottom // 目标节点连接点在下方
|
||||
targetPosition = Position.Bottom // 目标节点连接点在下方
|
||||
sourcePosition = Position.Top // 源节点连接点在上方
|
||||
break
|
||||
case 'TB': // 从下到上 (Bottom to Top)
|
||||
targetPosition = Position.Top // 目标节点连接点在上方
|
||||
targetPosition = Position.Top // 目标节点连接点在上方
|
||||
sourcePosition = Position.Bottom // 源节点连接点在下方
|
||||
break
|
||||
case 'LR': // 从左到右 (Left to Right)
|
||||
@@ -77,10 +80,66 @@ export function useLayout() {
|
||||
...node,
|
||||
targetPosition,
|
||||
sourcePosition,
|
||||
position: { x: nodeWithPosition.x, y: nodeWithPosition.y },
|
||||
position: { x: nodeWithPosition.x, y: nodeWithPosition.y }
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
return { graph, layout, previousDirection }
|
||||
}
|
||||
}
|
||||
/**
|
||||
* 递归查找指定ID的节点并添加子节点
|
||||
* @param {Array} items - 要搜索的数组
|
||||
* @param {string} targetId - 要查找的节点ID
|
||||
* @param {Object} newChild - 要添加的新子节点
|
||||
* @returns {boolean} 是否成功添加
|
||||
*/
|
||||
export function findAndAddChild(items, targetId, newChild) {
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
const item = items[i]
|
||||
|
||||
// 如果找到目标节点
|
||||
if (item.id === targetId) {
|
||||
// 初始化child数组(如果不存在)
|
||||
if (!item.child) {
|
||||
item.child = []
|
||||
}
|
||||
// 添加新子节点
|
||||
item.child.push(newChild)
|
||||
return true
|
||||
}
|
||||
|
||||
// 递归搜索子节点
|
||||
if (item.child && item.child.length > 0) {
|
||||
const found = findAndAddChild(item.child, targetId, newChild)
|
||||
if (found) return true
|
||||
}
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
/**
|
||||
* 递归删除指定ID的节点
|
||||
* @param {Array} items - 要搜索的数组
|
||||
* @param {string} targetId - 要删除的节点ID
|
||||
* @returns {boolean} 是否成功删除
|
||||
*/
|
||||
export function findAndRemoveChild(items, targetId) {
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
const item = items[i]
|
||||
|
||||
// 如果找到目标节点,从当前数组中删除
|
||||
if (item.id === targetId) {
|
||||
items.splice(i, 1)
|
||||
return true
|
||||
}
|
||||
|
||||
// 递归搜索子节点
|
||||
if (item.child && item.child.length > 0) {
|
||||
const found = findAndRemoveChild(item.child, targetId)
|
||||
if (found) return true
|
||||
}
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
@@ -10,19 +10,15 @@ export const versionsList = [
|
||||
{
|
||||
id: '1-1-1',
|
||||
name:'V1-1-1',
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
id: '1-2',
|
||||
name:'V1-2',
|
||||
child:[
|
||||
{
|
||||
id: '1-2-1',
|
||||
name:'V1-2-1',
|
||||
},{
|
||||
id: '1-2-2',
|
||||
name:'V1-2-2',
|
||||
child:[
|
||||
{
|
||||
id: '1-1-1-1',
|
||||
name:'V1-1-1-1',
|
||||
},{
|
||||
id: '1-1-1-2',
|
||||
name:'V1-1-1-2',
|
||||
},
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -1,10 +1,13 @@
|
||||
<script setup lang="ts">
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs, watch } from "vue";
|
||||
import { ref, onMounted, onUnmounted, reactive, toRefs, watch, nextTick } from "vue";
|
||||
import view1Item from './view1Item.vue'
|
||||
import view2 from './view2/index.vue'
|
||||
import { versionsList } from './view2/tools/versionsData'
|
||||
|
||||
const props = defineProps({
|
||||
versionsList: {
|
||||
type: Array,
|
||||
default: () => []
|
||||
},
|
||||
treeState:{
|
||||
default:false,
|
||||
},
|
||||
@@ -19,6 +22,8 @@ const emit = defineEmits([
|
||||
let data = reactive({
|
||||
})
|
||||
|
||||
const view1Ref = ref(null)
|
||||
|
||||
const isLoad = ref(false)
|
||||
const treeStateTime = ref(true)
|
||||
|
||||
@@ -35,13 +40,7 @@ const pushView2Item = (item)=>{
|
||||
}
|
||||
|
||||
const treeList = ref([
|
||||
{
|
||||
name:'P1',
|
||||
},{
|
||||
name:'V1',
|
||||
},{
|
||||
name:'V1-1',
|
||||
}
|
||||
|
||||
])
|
||||
|
||||
function traverseArray(items, callback) {
|
||||
@@ -53,22 +52,44 @@ function traverseArray(items, callback) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const initialize = ()=>{
|
||||
isLoad.value = false
|
||||
setSelectItem(versionsList[0])
|
||||
treeList.value = []
|
||||
traverseArray(versionsList, (item, index) => {
|
||||
treeList.value.push({id: null,name:'index',})
|
||||
traverseArray(props.versionsList, (item, index) => {
|
||||
treeList.value.push(item)
|
||||
})
|
||||
isLoad.value = true
|
||||
if(!props.selectItem?.id)setSelectItem(treeList.value[treeList.value.length - 1])
|
||||
}
|
||||
|
||||
const setSelectItem = (item)=>{
|
||||
console.log(item[0])
|
||||
if(!item.id)return
|
||||
emit('update:selectItem', {...item})
|
||||
}
|
||||
|
||||
// 滚动到选中项
|
||||
const scrollToActive = ()=>{
|
||||
nextTick(() => {
|
||||
const activeEl = view1Ref.value?.querySelector('.active')
|
||||
console.log(activeEl)
|
||||
activeEl.scrollIntoView({
|
||||
behavior: 'smooth',
|
||||
block: 'nearest'
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
watch(()=>treeStateTime.value,(newVal,oldVal)=>{
|
||||
if((props.treeState + '') == 'false'){
|
||||
scrollToActive()
|
||||
}
|
||||
})
|
||||
|
||||
watch(()=>props.selectItem,(newVal,oldVal)=>{
|
||||
scrollToActive()
|
||||
},{immediate: true})
|
||||
|
||||
onMounted(()=>{
|
||||
initialize()
|
||||
})
|
||||
@@ -79,8 +100,8 @@ const {} = toRefs(data);
|
||||
</script>
|
||||
<template>
|
||||
<div class="tree" v-show="treeStateTime" v-if="isLoad">
|
||||
<div v-show="!treeState" class="box view1">
|
||||
<view1Item v-for="item in treeList" :key="item.name" :item="item" @click="emit('selectItem', item)"></view1Item>
|
||||
<div v-show="!treeState" class="box view1" ref="view1Ref">
|
||||
<view1Item v-for="item in treeList" :key="item.name" :selectItem="props.selectItem" :item="item" @click="setSelectItem(item)"></view1Item>
|
||||
</div>
|
||||
<div v-show="treeState" class="box view2">
|
||||
<view2
|
||||
|
||||
@@ -4,7 +4,11 @@ const props = defineProps({
|
||||
item: {
|
||||
type: Object,
|
||||
default: () => ({})
|
||||
}
|
||||
},
|
||||
selectItem: {
|
||||
type: Object,
|
||||
default: () => {},
|
||||
},
|
||||
})
|
||||
//const emit = defineEmits([
|
||||
//])
|
||||
@@ -18,7 +22,7 @@ defineExpose({})
|
||||
const {} = toRefs(data);
|
||||
</script>
|
||||
<template>
|
||||
<div class="btn">
|
||||
<div class="btn" :class="{'active': item.id === props.selectItem?.id}">
|
||||
{{ item.name }}
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -5,7 +5,7 @@ import { VueFlow, useVueFlow } from '@vue-flow/core'
|
||||
import SpecialEdge from './speciaiEdge.vue'
|
||||
import InputNode from './InputNode.vue'//主
|
||||
import SecondaryNode from './secondaryNode.vue'//分支
|
||||
import { useLayout } from './tools/tools'
|
||||
import { useLayout } from '../../tools/tools'
|
||||
const props = defineProps({
|
||||
selectItem: {
|
||||
type: Object,
|
||||
@@ -49,14 +49,15 @@ async function layoutGraph(direction) {
|
||||
}
|
||||
|
||||
const push = (item)=>{
|
||||
if(nodes.value.length == 0){
|
||||
if(!item.id){
|
||||
nodes.value.push({ id: '0', type: 'InputNode', class: 'custom-node', position })
|
||||
}else{
|
||||
let className = `custom-node item${item.id.replace(/-/g, "_")}`
|
||||
let id = item.id
|
||||
let source = edges.value.length == 0?'0':item.id.slice(0, -2)
|
||||
nodes.value.push({id,type:'SecondaryNode',class:className,position,data:item})
|
||||
edges.value.push({ id, target:id, source, type: 'smoothstep' })
|
||||
}
|
||||
let className = `custom-node item${item.id.replace(/-/g, "_")}`
|
||||
let id = item.id
|
||||
let source = edges.value.length == 0?'0':item.id.slice(0, -2)
|
||||
nodes.value.push({id,type:'SecondaryNode',class:className,position,data:item})
|
||||
edges.value.push({ id, target:id, source, type: 'smoothstep' })
|
||||
}
|
||||
|
||||
const initialized = ()=>{
|
||||
@@ -129,7 +130,7 @@ defineExpose({push})
|
||||
}
|
||||
:deep(.custom-node){
|
||||
.node{
|
||||
--vf-handle: #000;
|
||||
--vf-handle: #c1c1c1;
|
||||
--vf-node-color: #000;
|
||||
--vf-box-shadow: #000;
|
||||
font-size: 1.2rem;
|
||||
|
||||
@@ -20,8 +20,8 @@ const props = defineProps<{
|
||||
<div class="node" :class="{active:props.selectItem.id == props.data.id}">
|
||||
<Handle type="target" id="Top" :position="Position.Top" />
|
||||
<Handle type="source" id="Bottom" :position="Position.Bottom" />
|
||||
<!-- <Handle type="target" id="Bottom" :position="Position.Bottom" />
|
||||
<Handle type="source" id="Top" :position="Position.Top" /> -->
|
||||
<!-- <Handle type="source" id="Right" :position="Position.Right" />
|
||||
<Handle type="target" id="Left" :position="Position.Left" /> -->
|
||||
<div>{{ props.data.id }}</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
Reference in New Issue
Block a user