Merge branch 'feature/feature-20250331-h5' of https://e.coding.yili.com/yldc/ylst/ylst-survey-h5 into feature
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -19,6 +19,7 @@ coverage
|
|||||||
|
|
||||||
# Editor directories and files
|
# Editor directories and files
|
||||||
.idea
|
.idea
|
||||||
|
.vscode
|
||||||
*.suo
|
*.suo
|
||||||
*.ntvs*
|
*.ntvs*
|
||||||
*.njsproj
|
*.njsproj
|
||||||
|
|||||||
18
.vscode/settings.json
vendored
18
.vscode/settings.json
vendored
@@ -2,7 +2,7 @@
|
|||||||
"explorer.confirmDelete": false,
|
"explorer.confirmDelete": false,
|
||||||
"editor.fontSize": 18,
|
"editor.fontSize": 18,
|
||||||
"workbench.editorAssociations": {
|
"workbench.editorAssociations": {
|
||||||
"*.ipynb": "jupyter.notebook.ipynb"
|
"*.ipynb": "jupyter.notebook.ipynb"
|
||||||
},
|
},
|
||||||
"window.zoomLevel": 1,
|
"window.zoomLevel": 1,
|
||||||
"workbench.iconTheme": "vscode-icons",
|
"workbench.iconTheme": "vscode-icons",
|
||||||
@@ -32,13 +32,14 @@
|
|||||||
"editor.formatOnSave": true
|
"editor.formatOnSave": true
|
||||||
},
|
},
|
||||||
"[vue]": {
|
"[vue]": {
|
||||||
"editor.defaultFormatter": "octref.vetur",
|
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
||||||
"editor.formatOnSave": true
|
"editor.formatOnSave": true
|
||||||
},
|
},
|
||||||
"css.validate": false, //用来校验CSS文件中的语法错误和潜在的问题
|
"css.validate": false, //用来校验CSS文件中的语法错误和潜在的问题
|
||||||
"less.validate": false, //用来校验LESS文件中的语法错误和潜在的问题
|
"less.validate": false, //用来校验LESS文件中的语法错误和潜在的问题
|
||||||
"scss.validate": false, //用来校验SCSS文件中的语法错误和潜在的问题
|
"scss.validate": false, //用来校验SCSS文件中的语法错误和潜在的问题
|
||||||
"editor.codeActionsOnSave": { // 用于在保存文件时自动执行代码操作
|
"editor.codeActionsOnSave": {
|
||||||
|
// 用于在保存文件时自动执行代码操作
|
||||||
"source.fixAll.eslint": "explicit", // 自动执行ESlint
|
"source.fixAll.eslint": "explicit", // 自动执行ESlint
|
||||||
"source.fixAll.stylelint": "explicit" // 自动执行stylelint
|
"source.fixAll.stylelint": "explicit" // 自动执行stylelint
|
||||||
},
|
},
|
||||||
@@ -54,15 +55,16 @@
|
|||||||
"xml",
|
"xml",
|
||||||
"gql",
|
"gql",
|
||||||
"graphql",
|
"graphql",
|
||||||
"astro",
|
"astro"
|
||||||
],
|
],
|
||||||
"eslint.nodePath": "./node_modules/@yl/yili-fe-lint-config/node_modules", // 指定ESLint可执行文件路径
|
"eslint.nodePath": "./node_modules/@yl/yili-fe-lint-config/node_modules", // 指定ESLint可执行文件路径
|
||||||
"eslint.options": { // 用于配置
|
"eslint.options": {
|
||||||
|
// 用于配置
|
||||||
"overrideConfigFile": "./node_modules/@yl/yili-fe-lint-config/eslintrc.vue3.js" //该选项指定了 ESLint 应使用的配置文件路径。此项设置会覆盖所有其他位置查找的 ESLint 配置文件。
|
"overrideConfigFile": "./node_modules/@yl/yili-fe-lint-config/eslintrc.vue3.js" //该选项指定了 ESLint 应使用的配置文件路径。此项设置会覆盖所有其他位置查找的 ESLint 配置文件。
|
||||||
},
|
},
|
||||||
"stylelint.configBasedir": "./node_modules/@yl/yili-fe-lint-config/", //该选项用于定义 Stylelint 配置文件所基于的基础目录。当您的配置文件中使用 extends、plugins 或其他引用时,这个基础目录将作为解析路径的起点
|
"stylelint.configBasedir": "./node_modules/@yl/yili-fe-lint-config/", //该选项用于定义 Stylelint 配置文件所基于的基础目录。当您的配置文件中使用 extends、plugins 或其他引用时,这个基础目录将作为解析路径的起点
|
||||||
"stylelint.configFile": "./node_modules/@yl/yili-fe-lint-config/stylelintrc.js", // 该选项指定了 stylelint 应使用的配置文件路径。此项设置会覆盖所有其他位置查找的 stylelint 配置文件
|
"stylelint.configFile": "./node_modules/@yl/yili-fe-lint-config/stylelintrc.js", // 该选项指定了 stylelint 应使用的配置文件路径。此项设置会覆盖所有其他位置查找的 stylelint 配置文件
|
||||||
"stylelint.customSyntax": "postcss-scss", // 配置stylelint使用的预处理器
|
"stylelint.customSyntax": "postcss-scss", // 配置stylelint使用的预处理器
|
||||||
"stylelint.stylelintPath": "./node_modules/@yl/yili-fe-lint-config/node_modules/stylelint", // 指定stylelint安装路径
|
"stylelint.stylelintPath": "./node_modules/@yl/yili-fe-lint-config/node_modules/stylelint", // 指定stylelint安装路径
|
||||||
"stylelint.validate": ["html", "css", "scss", "less", "vue"]
|
"stylelint.validate": ["html", "css", "scss", "less", "vue"]
|
||||||
}
|
}
|
||||||
|
|||||||
11
components.d.ts
vendored
11
components.d.ts
vendored
@@ -7,16 +7,9 @@ export {}
|
|||||||
/* prettier-ignore */
|
/* prettier-ignore */
|
||||||
declare module 'vue' {
|
declare module 'vue' {
|
||||||
export interface GlobalComponents {
|
export interface GlobalComponents {
|
||||||
ElButton: typeof import('element-plus/es')['ElButton']
|
|
||||||
ElContainer: typeof import('element-plus/es')['ElContainer']
|
|
||||||
ElHeader: typeof import('element-plus/es')['ElHeader']
|
|
||||||
ElMain: typeof import('element-plus/es')['ElMain']
|
|
||||||
Index: typeof import('./src/components/VanCellModel/Index.vue')['default']
|
|
||||||
RouterLink: typeof import('vue-router')['RouterLink']
|
RouterLink: typeof import('vue-router')['RouterLink']
|
||||||
RouterView: typeof import('vue-router')['RouterView']
|
RouterView: typeof import('vue-router')['RouterView']
|
||||||
Van: typeof import('vant/es')['default']
|
|
||||||
VanActionSheet: typeof import('vant/es')['ActionSheet']
|
VanActionSheet: typeof import('vant/es')['ActionSheet']
|
||||||
VanButton: typeof import('vant/es')['Button']
|
|
||||||
VanCell: typeof import('vant/es')['Cell']
|
VanCell: typeof import('vant/es')['Cell']
|
||||||
VanCellGroup: typeof import('vant/es')['CellGroup']
|
VanCellGroup: typeof import('vant/es')['CellGroup']
|
||||||
VanCheckbox: typeof import('vant/es')['Checkbox']
|
VanCheckbox: typeof import('vant/es')['Checkbox']
|
||||||
@@ -24,5 +17,9 @@ declare module 'vue' {
|
|||||||
VanDivider: typeof import('vant/es')['Divider']
|
VanDivider: typeof import('vant/es')['Divider']
|
||||||
VanField: typeof import('vant/es')['Field']
|
VanField: typeof import('vant/es')['Field']
|
||||||
VanIcon: typeof import('vant/es')['Icon']
|
VanIcon: typeof import('vant/es')['Icon']
|
||||||
|
VanSearch: typeof import('vant/es')['Search']
|
||||||
|
VanSwitch: typeof import('vant/es')['Switch']
|
||||||
|
VanTabbar: typeof import('vant/es')['Tabbar']
|
||||||
|
VanTabbarItem: typeof import('vant/es')['TabbarItem']
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,3 +1,11 @@
|
|||||||
.van-cell {
|
.van-cell {
|
||||||
padding: 8px !important;
|
padding: 8px !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.van-divider {
|
||||||
|
margin: 5px 0 !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.van-popup--bottom.van-popup--round {
|
||||||
|
border-radius: 10px 10px 0 0 !important;
|
||||||
|
}
|
||||||
|
|||||||
@@ -4,11 +4,11 @@
|
|||||||
src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834');
|
src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834');
|
||||||
src:
|
src:
|
||||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834#iefix')
|
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834#iefix')
|
||||||
format('embedded-opentype'),
|
format('embedded-opentype'),
|
||||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.woff?t=1545807318834') format('woff'),
|
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.woff?t=1545807318834') format('woff'),
|
||||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.ttf?t=1545807318834') format('truetype'),
|
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.ttf?t=1545807318834') format('truetype'),
|
||||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.svg?t=1545807318834#iconfont')
|
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.svg?t=1545807318834#iconfont')
|
||||||
format('svg');
|
format('svg');
|
||||||
}
|
}
|
||||||
|
|
||||||
.logo {
|
.logo {
|
||||||
|
|||||||
@@ -26,39 +26,41 @@ import { RouterView } from 'vue-router';
|
|||||||
import { ref } from 'vue';
|
import { ref } from 'vue';
|
||||||
|
|
||||||
const active = ref();
|
const active = ref();
|
||||||
const table = [{
|
const table = [
|
||||||
title: '首页',
|
{
|
||||||
path: '/',
|
title: '首页',
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u18.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
path: '/',
|
||||||
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u18.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
}, {
|
},
|
||||||
title: '问卷',
|
{
|
||||||
path: '/survey',
|
title: '问卷',
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u21.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
path: '/survey',
|
||||||
}, {
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u21.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
title: '新建问卷',
|
},
|
||||||
path: '/survey/create',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/首页_1/u15.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '新建问卷',
|
||||||
|
path: '/survey/create',
|
||||||
}, {
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/首页_1/u15.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
title: '模板',
|
},
|
||||||
path: '/market',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u24.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '模板',
|
||||||
}];
|
path: '/market',
|
||||||
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u24.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
|
}
|
||||||
|
];
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
.common-layout {
|
.common-layout {
|
||||||
min-height: calc(100vh);
|
min-height: calc(100vh);
|
||||||
background-color: #E9EEF3;
|
background-color: #e9eef3;
|
||||||
color: #333;
|
color: #333;
|
||||||
text-align: center;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.header {
|
.header {
|
||||||
position: sticky;
|
position: sticky;
|
||||||
top: 0;
|
top: 0;
|
||||||
background-color: #B9F8CF;
|
background-color: #b9f8cf;
|
||||||
|
|
||||||
.title {
|
.title {
|
||||||
display: flex;
|
display: flex;
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ import { createApp } from 'vue';
|
|||||||
import { createPinia } from 'pinia';
|
import { createPinia } from 'pinia';
|
||||||
import App from './App.vue';
|
import App from './App.vue';
|
||||||
import router from './router';
|
import router from './router';
|
||||||
|
// 2. 引入组件样式
|
||||||
|
import 'vant/lib/index.css';
|
||||||
const app = createApp(App);
|
const app = createApp(App);
|
||||||
app.use(createPinia());
|
app.use(createPinia());
|
||||||
app.use(router);
|
app.use(router);
|
||||||
|
|||||||
@@ -93,7 +93,96 @@ export const useCommonStore = defineStore('common', {
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
logics: [],
|
logics: [
|
||||||
|
{
|
||||||
|
id: 472148,
|
||||||
|
question_index: 24,
|
||||||
|
sample_number: 0,
|
||||||
|
skip_question_index: 27,
|
||||||
|
skip_type: 0,
|
||||||
|
question_id: '17852294',
|
||||||
|
logic: [
|
||||||
|
{
|
||||||
|
value: '',
|
||||||
|
location: 0,
|
||||||
|
date: '',
|
||||||
|
time: '',
|
||||||
|
type: 0,
|
||||||
|
row_type: 0,
|
||||||
|
cell_type: 0,
|
||||||
|
logic: 'if',
|
||||||
|
operator: '=',
|
||||||
|
is_answer: 1,
|
||||||
|
is_select: 0,
|
||||||
|
row_index: 0,
|
||||||
|
cell_index: 0,
|
||||||
|
question_type: 1,
|
||||||
|
question_index: 24,
|
||||||
|
relation_question_index: 0,
|
||||||
|
relation_question_row_index: 0,
|
||||||
|
relation_question_cell_index: 0,
|
||||||
|
is_option_group: 0,
|
||||||
|
option_index: 1,
|
||||||
|
skip_type: null,
|
||||||
|
question_id: null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
autofill: {
|
||||||
|
value: '',
|
||||||
|
date: '',
|
||||||
|
time: '',
|
||||||
|
question_type: 1,
|
||||||
|
option_indexs: [],
|
||||||
|
row_indexs: [],
|
||||||
|
cell_indexs: []
|
||||||
|
},
|
||||||
|
hide_option_index: []
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 472149,
|
||||||
|
question_index: 24,
|
||||||
|
sample_number: 0,
|
||||||
|
skip_question_index: 0,
|
||||||
|
skip_type: 0,
|
||||||
|
question_id: '17852294',
|
||||||
|
logic: [
|
||||||
|
{
|
||||||
|
value: '',
|
||||||
|
location: 0,
|
||||||
|
date: '',
|
||||||
|
time: '',
|
||||||
|
type: 0,
|
||||||
|
row_type: 0,
|
||||||
|
cell_type: 0,
|
||||||
|
logic: 'if',
|
||||||
|
operator: '=',
|
||||||
|
is_answer: 1,
|
||||||
|
is_select: 0,
|
||||||
|
row_index: 0,
|
||||||
|
cell_index: 0,
|
||||||
|
question_type: 1,
|
||||||
|
question_index: 24,
|
||||||
|
relation_question_index: 0,
|
||||||
|
relation_question_row_index: 0,
|
||||||
|
relation_question_cell_index: 0,
|
||||||
|
is_option_group: 0,
|
||||||
|
option_index: 0,
|
||||||
|
skip_type: null,
|
||||||
|
question_id: null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
autofill: {
|
||||||
|
value: '',
|
||||||
|
date: '',
|
||||||
|
time: '',
|
||||||
|
question_type: 1,
|
||||||
|
option_indexs: [],
|
||||||
|
row_indexs: [],
|
||||||
|
cell_indexs: []
|
||||||
|
},
|
||||||
|
hide_option_index: []
|
||||||
|
}
|
||||||
|
],
|
||||||
questions: [
|
questions: [
|
||||||
{
|
{
|
||||||
id: '17852294',
|
id: '17852294',
|
||||||
@@ -274,7 +363,7 @@ export const useCommonStore = defineStore('common', {
|
|||||||
id: '1048968',
|
id: '1048968',
|
||||||
type: 0,
|
type: 0,
|
||||||
is_other: 0,
|
is_other: 0,
|
||||||
is_fixed: 0,
|
is_fixed: 1,
|
||||||
is_remove_other: 0,
|
is_remove_other: 0,
|
||||||
created_at: null,
|
created_at: null,
|
||||||
created_user_id: null,
|
created_user_id: null,
|
||||||
@@ -1406,7 +1495,7 @@ export const useCommonStore = defineStore('common', {
|
|||||||
{
|
{
|
||||||
id: '17835010',
|
id: '17835010',
|
||||||
title: 'A6',
|
title: 'A6',
|
||||||
stem: '<p>请问您为什么<span style="text-decoration: underline; color: #2dc26b;" data-mce-style="text-decoration: underline; color: #2dc26b;"><strong>喜欢</strong></span>这些地方?</p><p><img style="height: 50px; max-height: 440px;" src="https://test-cxp-public-web-1302259445.cos.ap-beijing.myqcloud.com/uat-yls/packing/imgs/1725421981418_809_mao-23.jpg"></p>',
|
stem: '<p>请问您为什么<span style="text-decoration: underline; color: #2dc26b;" data-mce-style="text-decoration: underline; color: #2dc26b;"><strong>喜欢</strong></span>这些地方?</p>',
|
||||||
other: '概念诊断问卷配置概念诊断1',
|
other: '概念诊断问卷配置概念诊断1',
|
||||||
question_index: 6,
|
question_index: 6,
|
||||||
question_type: 4,
|
question_type: 4,
|
||||||
@@ -2743,7 +2832,7 @@ export const useCommonStore = defineStore('common', {
|
|||||||
{
|
{
|
||||||
id: '17835015',
|
id: '17835015',
|
||||||
title: 'B4',
|
title: 'B4',
|
||||||
stem: '<p>请问您为什么<span style="text-decoration: underline; color: #e03e2d;" data-mce-style="text-decoration: underline; color: #e03e2d;"><strong>不喜欢</strong></span>这些地方?</p><p><img style="height: 50px; max-height: 440px;" src="https://test-cxp-public-web-1302259445.cos.ap-beijing.myqcloud.com/uat-yls/packing/imgs/1725421988964_889_mao-012-small.jpg"></p>',
|
stem: '<p>请问您为什么<span style="text-decoration: underline; color: #e03e2d;" data-mce-style="text-decoration: underline; color: #e03e2d;"><strong>不喜欢</strong></span>这些地方?</p>',
|
||||||
other: '概念诊断问卷配置概念诊断2',
|
other: '概念诊断问卷配置概念诊断2',
|
||||||
question_index: 11,
|
question_index: 11,
|
||||||
question_type: 4,
|
question_type: 4,
|
||||||
|
|||||||
@@ -11,6 +11,7 @@
|
|||||||
<template #item="{ element, index }">
|
<template #item="{ element, index }">
|
||||||
<choose-question
|
<choose-question
|
||||||
:element="element"
|
:element="element"
|
||||||
|
:questions="questionInfo.questions"
|
||||||
:index="index"
|
:index="index"
|
||||||
:chooseQuestionId="chooseQuestionId"
|
:chooseQuestionId="chooseQuestionId"
|
||||||
@get-choose-question-id="getChooseQuestionId"
|
@get-choose-question-id="getChooseQuestionId"
|
||||||
@@ -20,7 +21,14 @@
|
|||||||
:element="element"
|
:element="element"
|
||||||
:active="chooseQuestionId === element.id"
|
:active="chooseQuestionId === element.id"
|
||||||
></base-select>
|
></base-select>
|
||||||
|
<Completion
|
||||||
|
v-if="element.question_type === 4"
|
||||||
|
:element="element"
|
||||||
|
:active="chooseQuestionId === element.id"
|
||||||
|
sn="lXEBBpE2"
|
||||||
|
></Completion>
|
||||||
</choose-question>
|
</choose-question>
|
||||||
|
|
||||||
<!-- {{ element.question_type }}-->
|
<!-- {{ element.question_type }}-->
|
||||||
<!-- {{questionInfo.survey.pages.length}}-->
|
<!-- {{questionInfo.survey.pages.length}}-->
|
||||||
<paging
|
<paging
|
||||||
@@ -42,6 +50,7 @@ import Draggable from './components/Draggable.vue';
|
|||||||
import BaseSelect from './components/Questions/BaseSelect.vue';
|
import BaseSelect from './components/Questions/BaseSelect.vue';
|
||||||
import ChooseQuestion from './components/ChooseQuestion.vue';
|
import ChooseQuestion from './components/ChooseQuestion.vue';
|
||||||
import Paging from './components/Questions/paging/Paging.vue';
|
import Paging from './components/Questions/paging/Paging.vue';
|
||||||
|
import Completion from './components/Questions/Completion.vue';
|
||||||
|
|
||||||
const activeIndex = ref(-1);
|
const activeIndex = ref(-1);
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,30 +1,53 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="option-action">
|
<div class="option-action">
|
||||||
<template v-for="(item, index) in data" :key="item.id">
|
<template v-for="(item, index) in data" :key="index">
|
||||||
<div class="flex align-center option-action-container">
|
<div class="flex align-center option-action-container">
|
||||||
<slot name="item" :element="item" :index="index"></slot>
|
<slot name="item" :element="item" :index="index"></slot>
|
||||||
<span v-if="active" class="flex">
|
<span v-if="active" class="flex">
|
||||||
<van-icon name="close"></van-icon>
|
<van-icon name="close" @click="deleteOption(index)"></van-icon>
|
||||||
<van-icon name="more-o" @click="openOptionActionModel"></van-icon>
|
<van-icon name="more-o" @click="openOptionActionModel(item, index)"></van-icon>
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
</div>
|
</div>
|
||||||
|
<!-- 操作项弹窗-->
|
||||||
<van-action-sheet v-model:show="show">
|
<van-action-sheet v-model:show="show">
|
||||||
<template #description>
|
<template #description>
|
||||||
<div class="flex flex-start">操作选项</div>
|
<div class="flex flex-start">操作选项</div>
|
||||||
</template>
|
</template>
|
||||||
<div class="">
|
<van-cell-group :border="false" class="ml10">
|
||||||
<van-cell title="固定置底"></van-cell>
|
<van-cell title="固定置底" :border="false">
|
||||||
<van-cell title="固定置底"></van-cell>
|
<template #right-icon>
|
||||||
<van-cell title="固定置底"></van-cell>
|
<van-switch
|
||||||
<van-cell title="固定置底"></van-cell>
|
v-model="activeOption.is_fixed"
|
||||||
</div>
|
class="option-action-sheet-switch"
|
||||||
|
size="0.5rem"
|
||||||
|
:active-value="1"
|
||||||
|
:inactive-value="0"
|
||||||
|
></van-switch>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-cell title="设为其他项" :border="false">
|
||||||
|
<template #right-icon>
|
||||||
|
<van-switch
|
||||||
|
v-model="activeOption.is_other"
|
||||||
|
class="option-action-sheet-switch"
|
||||||
|
size="0.5rem"
|
||||||
|
:active-value="1"
|
||||||
|
:inactive-value="0"
|
||||||
|
></van-switch>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-divider></van-divider>
|
||||||
|
<van-cell title="下移选项" :border="false" @click="optionMove('down')"></van-cell>
|
||||||
|
<van-cell title="上移选项" :border="false" @click="optionMove('up')"></van-cell>
|
||||||
|
</van-cell-group>
|
||||||
</van-action-sheet>
|
</van-action-sheet>
|
||||||
</template>
|
</template>
|
||||||
<script setup>
|
<script setup>
|
||||||
import { ref } from 'vue';
|
import { ref } from 'vue';
|
||||||
defineProps({
|
import { showConfirmDialog } from 'vant';
|
||||||
|
const props = defineProps({
|
||||||
data: {
|
data: {
|
||||||
type: Object,
|
type: Object,
|
||||||
default: () => {
|
default: () => {
|
||||||
@@ -40,17 +63,66 @@ defineProps({
|
|||||||
});
|
});
|
||||||
// const emit = defineEmits(['update:data']);
|
// const emit = defineEmits(['update:data']);
|
||||||
const show = ref(false);
|
const show = ref(false);
|
||||||
|
const activeOption = ref({});
|
||||||
|
const activeIndex = ref(-1);
|
||||||
|
const element = ref(props.data);
|
||||||
|
|
||||||
|
// emit('update:data');
|
||||||
/**
|
/**
|
||||||
* @name 打开model弹窗
|
* @name 打开model弹窗
|
||||||
* @created_date 2025/3/4
|
* @created_date 2025/3/4
|
||||||
* @description
|
* @description
|
||||||
**/
|
**/
|
||||||
const openOptionActionModel = () => {
|
const openOptionActionModel = (item, index) => {
|
||||||
show.value = true;
|
show.value = true;
|
||||||
|
activeOption.value = item;
|
||||||
|
activeIndex.value = index;
|
||||||
|
};
|
||||||
|
|
||||||
|
// 上下移动
|
||||||
|
const optionMove = (action) => {
|
||||||
|
switch (action) {
|
||||||
|
case 'up':
|
||||||
|
if (activeIndex.value === 0) {
|
||||||
|
show.value = false;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 向上移动
|
||||||
|
element.value.splice(activeIndex.value - 1, 0, element.value.splice(activeIndex.value, 1)[0]);
|
||||||
|
activeIndex.value -= 1;
|
||||||
|
break;
|
||||||
|
case 'down':
|
||||||
|
if (activeIndex.value === element.value.length) {
|
||||||
|
show.value = false;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
element.value.splice(activeIndex.value + 1, 0, element.value.splice(activeIndex.value, 1)[0]);
|
||||||
|
activeIndex.value += 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// 删除当前选项
|
||||||
|
|
||||||
|
const deleteOption = (index) => {
|
||||||
|
showConfirmDialog({
|
||||||
|
title: '提示',
|
||||||
|
message: '是否删除选项?'
|
||||||
|
})
|
||||||
|
.then(() => {
|
||||||
|
// on confirm
|
||||||
|
element.value.splice(index, 1);
|
||||||
|
})
|
||||||
|
.catch(() => {
|
||||||
|
// on cancel
|
||||||
|
});
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
|
.ml10 {
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
.option-action {
|
.option-action {
|
||||||
font-size: 20px;
|
font-size: 20px;
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,139 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container question-action-container flex">
|
<div class="container question-action-container flex">
|
||||||
<van-icon name="delete"></van-icon>
|
<van-icon name="delete" @click="deleteQuestion"></van-icon>
|
||||||
<van-icon name="more"></van-icon>
|
<van-icon name="more" @click="openQuestionActionModel"></van-icon>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<!-- 操作项弹窗-->
|
||||||
|
<van-action-sheet v-model:show="show">
|
||||||
|
<template #description>
|
||||||
|
<div class="flex flex-start">操作选项</div>
|
||||||
|
</template>
|
||||||
|
<van-cell-group :border="false" class="ml10">
|
||||||
|
<van-cell title="此题必答" :border="false" label-align="left">
|
||||||
|
<template #right-icon>
|
||||||
|
<van-switch
|
||||||
|
v-model="activeQuestion.config.is_required"
|
||||||
|
class="option-action-sheet-switch"
|
||||||
|
size="0.5rem"
|
||||||
|
:active-value="1"
|
||||||
|
:inactive-value="0"
|
||||||
|
></van-switch>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-cell title="选项随机" :border="false">
|
||||||
|
<template #right-icon>
|
||||||
|
<van-switch
|
||||||
|
v-model="activeQuestion.config.select_random"
|
||||||
|
class="option-action-sheet-switch"
|
||||||
|
size="0.5rem"
|
||||||
|
:active-value="1"
|
||||||
|
:inactive-value="0"
|
||||||
|
></van-switch>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-divider></van-divider>
|
||||||
|
<van-cell title="题前隐藏" :border="false">
|
||||||
|
<template #right-icon>
|
||||||
|
<span> {{ getSkipTypeText() }} <van-icon name="arrow"></van-icon></span>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-cell title="题后跳转" :border="false">
|
||||||
|
<template #right-icon>
|
||||||
|
<span> 设置 <van-icon name="arrow"></van-icon></span>
|
||||||
|
</template>
|
||||||
|
</van-cell>
|
||||||
|
<van-divider></van-divider>
|
||||||
|
<van-cell title="下移选项" :border="false" @click="questionMove('down')"></van-cell>
|
||||||
|
<van-cell title="上移选项" :border="false" @click="questionMove('up')"></van-cell>
|
||||||
|
</van-cell-group>
|
||||||
|
</van-action-sheet>
|
||||||
</template>
|
</template>
|
||||||
<script setup></script>
|
<script setup>
|
||||||
|
import { showConfirmDialog } from 'vant';
|
||||||
|
import { ref } from 'vue';
|
||||||
|
import { useCounterStore } from '@/stores/counter';
|
||||||
|
import { storeToRefs } from 'pinia';
|
||||||
|
|
||||||
|
const store = useCounterStore();
|
||||||
|
const { questionsInfo } = storeToRefs(store);
|
||||||
|
const logics = questionsInfo.value.logics;
|
||||||
|
|
||||||
|
const props = defineProps({
|
||||||
|
index: {
|
||||||
|
type: Number,
|
||||||
|
default: 0
|
||||||
|
},
|
||||||
|
data: {
|
||||||
|
type: Object,
|
||||||
|
default: () => {
|
||||||
|
// 传递
|
||||||
|
}
|
||||||
|
},
|
||||||
|
questions: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
questionIndex: {
|
||||||
|
type: Number,
|
||||||
|
default: 0
|
||||||
|
}
|
||||||
|
});
|
||||||
|
const questions = ref(props.questions);
|
||||||
|
// 当前题目
|
||||||
|
const activeQuestion = ref(props.data);
|
||||||
|
|
||||||
|
const show = ref(false);
|
||||||
|
const deleteQuestion = () => {
|
||||||
|
showConfirmDialog({
|
||||||
|
title: '提示',
|
||||||
|
message: '是否删除问题?'
|
||||||
|
})
|
||||||
|
.then(() => {
|
||||||
|
// on confirm
|
||||||
|
questions.value.splice(props.questionIndex, 1);
|
||||||
|
})
|
||||||
|
.catch(() => {
|
||||||
|
// on cancel
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
// 打开题目弹窗
|
||||||
|
const openQuestionActionModel = () => {
|
||||||
|
show.value = true;
|
||||||
|
};
|
||||||
|
// 题目上下移动
|
||||||
|
const questionMove = (action) => {
|
||||||
|
if (action === 'down') {
|
||||||
|
if (props.questionIndex === questions.value.length - 1) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const temp = questions.value[props.questionIndex];
|
||||||
|
questions.value.splice(props.questionIndex, 1);
|
||||||
|
questions.value.splice(props.questionIndex + 1, 0, temp);
|
||||||
|
} else {
|
||||||
|
if (props.questionIndex === 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const temp = questions.value[props.questionIndex];
|
||||||
|
questions.value.splice(props.questionIndex, 1);
|
||||||
|
questions.value.splice(props.questionIndex - 1, 0, temp);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// 获取题前隐藏 和题后 跳转 文字
|
||||||
|
const getSkipTypeText = () => {
|
||||||
|
setTimeout(() => {
|
||||||
|
logics[0].id = 123;
|
||||||
|
}, 2000);
|
||||||
|
return logics[0].id;
|
||||||
|
};
|
||||||
|
</script>
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
|
.ml10 {
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
.question-action-container {
|
.question-action-container {
|
||||||
font-size: 20px;
|
font-size: 20px;
|
||||||
|
|
||||||
|
|||||||
@@ -16,7 +16,11 @@
|
|||||||
</template>
|
</template>
|
||||||
<template #title>{{}}</template>
|
<template #title>{{}}</template>
|
||||||
<template #right-icon>
|
<template #right-icon>
|
||||||
<question-action></question-action>
|
<question-action
|
||||||
|
v-model:data="element"
|
||||||
|
:questions="questions"
|
||||||
|
:questionIndex="index"
|
||||||
|
></question-action>
|
||||||
</template>
|
</template>
|
||||||
<!-- <div-->
|
<!-- <div-->
|
||||||
<!-- v-for="item in questionAction"-->
|
<!-- v-for="item in questionAction"-->
|
||||||
@@ -51,6 +55,10 @@ const props = defineProps({
|
|||||||
type: Number,
|
type: Number,
|
||||||
default: 0
|
default: 0
|
||||||
},
|
},
|
||||||
|
questions: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
chooseQuestionId: {
|
chooseQuestionId: {
|
||||||
type: String,
|
type: String,
|
||||||
default: '0'
|
default: '0'
|
||||||
|
|||||||
@@ -16,7 +16,7 @@
|
|||||||
</template>
|
</template>
|
||||||
<template #input>
|
<template #input>
|
||||||
<van-checkbox-group>
|
<van-checkbox-group>
|
||||||
<template v-for="(item, index) in element.options" :key="item.id">
|
<template v-for="(item, index) in element.options" :key="index">
|
||||||
<option-action v-model:data="element.options[index]" :active="active">
|
<option-action v-model:data="element.options[index]" :active="active">
|
||||||
<template #item="{ element: it, index: itIndex }">
|
<template #item="{ element: it, index: itIndex }">
|
||||||
<van-checkbox
|
<van-checkbox
|
||||||
@@ -27,13 +27,16 @@
|
|||||||
icon-size="0.45rem"
|
icon-size="0.45rem"
|
||||||
>
|
>
|
||||||
<template #default>
|
<template #default>
|
||||||
<div class="flex align-center space-between">
|
<div class="flex align-center van-cell">
|
||||||
<div
|
<div
|
||||||
class="van-cell van-cell--borderless"
|
class="van-cell--borderless"
|
||||||
:contenteditable="active"
|
:contenteditable="active"
|
||||||
@blur="saveOption($event, it)"
|
@blur="saveOption($event, it)"
|
||||||
v-html="it.option"
|
v-html="it.option"
|
||||||
></div>
|
></div>
|
||||||
|
<div v-if="it.is_other">
|
||||||
|
<input class="other-input" type="text" />
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
</van-checkbox>
|
</van-checkbox>
|
||||||
@@ -83,5 +86,15 @@ const saveStem = (e, ele) => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
& .other-input {
|
||||||
|
width: 100px;
|
||||||
|
height: 20px;
|
||||||
|
margin-left: 20px;
|
||||||
|
padding: 3px 5px;
|
||||||
|
border: 1px solid #ccc;
|
||||||
|
border-radius: 5px;
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
67
src/views/Design/components/Questions/Completion.vue
Normal file
67
src/views/Design/components/Questions/Completion.vue
Normal file
@@ -0,0 +1,67 @@
|
|||||||
|
<template>
|
||||||
|
<div class="cont">
|
||||||
|
<van-field
|
||||||
|
v-model="element.stem"
|
||||||
|
:label="element.stem"
|
||||||
|
:required="element.config.is_required === 1"
|
||||||
|
label-align="top"
|
||||||
|
>
|
||||||
|
<template #label>
|
||||||
|
<div
|
||||||
|
:contenteditable="active"
|
||||||
|
class="van-field"
|
||||||
|
@blur="saveStem($event, element)"
|
||||||
|
v-html="element.stem"
|
||||||
|
></div>
|
||||||
|
</template>
|
||||||
|
<template #input>
|
||||||
|
<div contenteditable="true" class="input other_input"></div>
|
||||||
|
</template>
|
||||||
|
</van-field>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup>
|
||||||
|
import { ref } from 'vue';
|
||||||
|
const props = defineProps({
|
||||||
|
element: {
|
||||||
|
type: Object,
|
||||||
|
default: () => {
|
||||||
|
// 补充
|
||||||
|
}
|
||||||
|
},
|
||||||
|
active: {
|
||||||
|
type: Boolean,
|
||||||
|
default: false
|
||||||
|
},
|
||||||
|
sn: { type: String, default: '' },
|
||||||
|
questionType: { type: [String, Number], default: 4 }
|
||||||
|
});
|
||||||
|
const element = ref(props.element);
|
||||||
|
// 创建一个本地副本以保存更改
|
||||||
|
const localElement = ref({ ...props.element });
|
||||||
|
|
||||||
|
const saveStem = (e) => {
|
||||||
|
localElement.value.stem = e.target.innerHTML;
|
||||||
|
// 如果需要,可以在这里发出事件以通知父组件
|
||||||
|
// this.$emit('update:element', localElement.value);
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped lang="scss">
|
||||||
|
.cont {
|
||||||
|
.other_input {
|
||||||
|
width: 100%;
|
||||||
|
height: 40px;
|
||||||
|
margin-bottom: 10px;
|
||||||
|
padding: 3px 5px;
|
||||||
|
border: 1px solid #ccc;
|
||||||
|
border-radius: 5px;
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.text_value {
|
||||||
|
border: 1px solid #ccc !important;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -11,8 +11,7 @@
|
|||||||
class="iconfont active-icon"
|
class="iconfont active-icon"
|
||||||
:style="{ marginRight: isLastPage ? '0' : '16px' }"
|
:style="{ marginRight: isLastPage ? '0' : '16px' }"
|
||||||
@click="activePage"
|
@click="activePage"
|
||||||
></i
|
></i>
|
||||||
>
|
|
||||||
<template v-if="!isLastPage">
|
<template v-if="!isLastPage">
|
||||||
<i class="iconfont moverQues" style="margin-right: 16px"></i>
|
<i class="iconfont moverQues" style="margin-right: 16px"></i>
|
||||||
<i class="iconfont" @click="deleteHandle"></i>
|
<i class="iconfont" @click="deleteHandle"></i>
|
||||||
|
|||||||
@@ -1,23 +1,24 @@
|
|||||||
<script setup>
|
<script setup>
|
||||||
import Survey from './components/Suvrey/Index.vue';
|
import Survey from './components/Suvrey/Index.vue';
|
||||||
import Template from './components/Market/Index.vue';
|
|
||||||
|
|
||||||
const func = [{
|
const func = [
|
||||||
title: '报名签到',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u48.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '报名签到',
|
||||||
},
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u48.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
{
|
},
|
||||||
title: '问卷调查',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u51.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '问卷调查',
|
||||||
},
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u51.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
{
|
},
|
||||||
title: '活动模板',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u54.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '活动模板',
|
||||||
},
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u54.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
{
|
},
|
||||||
title: '活动管理',
|
{
|
||||||
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u57.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
title: '活动管理',
|
||||||
}];
|
icon: 'https://files.axshare.com/gsc/DR6075/de/a0/49/dea049d6ad3e4c2c80af44258c6c76d6/images/%E9%A6%96%E9%A1%B5_1/u57.png?pageId=74b3e5b2-848e-4258-8a34-9e220127c8a6'
|
||||||
|
}
|
||||||
|
];
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@@ -34,26 +35,21 @@ const func = [{
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<Survey />
|
<Survey />
|
||||||
|
|
||||||
<Template />
|
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
.container {
|
.container {
|
||||||
padding: 0 10px;
|
padding: 0 10px;
|
||||||
background: linear-gradient(0deg,
|
background: linear-gradient(0deg, #f5f5f5 0%, #f5f5f5 84%, rgba(185, 248, 207, 1) 100%);
|
||||||
#f5f5f5 0%,
|
|
||||||
#f5f5f5 84%,
|
|
||||||
rgba(185, 248, 207, 1) 100%);
|
|
||||||
|
|
||||||
&>:first-child {
|
& > :first-child {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: space-around;
|
justify-content: space-around;
|
||||||
border-radius: 6px;
|
border-radius: 6px;
|
||||||
background-color: white;
|
background-color: white;
|
||||||
|
|
||||||
&>div {
|
& > div {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
width: 50px;
|
width: 50px;
|
||||||
|
|||||||
Reference in New Issue
Block a user