- 在 contenteditable.vue 中添加了 errorMessage属性和对应的样式 - 在多个组件中为 contenteditable 添加了 errorMessage 属性 - 优化了部分代码格式,如空格、换行等
136 lines
2.9 KiB
Vue
136 lines
2.9 KiB
Vue
<template>
|
|
<div class="content">
|
|
<van-field
|
|
v-model="element.stem"
|
|
:label="element.stem"
|
|
:required="element.config.is_required === 1"
|
|
label-align="top"
|
|
class="contenteditable-question-title"
|
|
>
|
|
<template #left-icon>
|
|
{{ index + 1 }}
|
|
</template>
|
|
<template #label>
|
|
<contenteditable
|
|
v-model="element.stem"
|
|
:active="active"
|
|
@blur="saveStem"
|
|
:errorMessage="errorMessage"
|
|
></contenteditable>
|
|
</template>
|
|
<template #input>
|
|
<div
|
|
v-for="(optionItem, optionItemIndex) in isPreview ? element.list : element.options"
|
|
:key="optionItemIndex"
|
|
class="rate-content"
|
|
>
|
|
<div
|
|
v-for="(item, optionIndex) in isPreview ? optionItem.options : optionItem"
|
|
:key="optionIndex"
|
|
@click="chooseOption(item)"
|
|
>
|
|
<div class="tips mb5">
|
|
<p>{{ element.config.prompt_left }}</p>
|
|
<p>{{ element.config.prompt_center }}</p>
|
|
<p>{{ element.config.prompt_right }}</p>
|
|
</div>
|
|
<RateCharacter
|
|
v-model:model="value"
|
|
:config="element.config"
|
|
:index="optionIndex"
|
|
@change="handleRateChange"
|
|
/>
|
|
</div>
|
|
</div>
|
|
</template>
|
|
</van-field>
|
|
</div>
|
|
</template>
|
|
|
|
<script setup>
|
|
import { defineModel, ref } from 'vue';
|
|
import RateCharacter from './RateCharacter.vue';
|
|
|
|
const value = defineModel('value', { default: -1, type: Number });
|
|
const isPreview = defineModel('isPreview', { default: false, type: Boolean });
|
|
/* const props = */ defineProps({
|
|
index: {
|
|
type: Number,
|
|
default: 0
|
|
},
|
|
active: {
|
|
type: Boolean,
|
|
default: false
|
|
},
|
|
sn: { type: String, default: '' },
|
|
questionType: { type: [String, Number], default: 4 }
|
|
});
|
|
const errorMessage = defineModel('errorMessage', {
|
|
type: String,
|
|
default: ''
|
|
});
|
|
/**
|
|
* element === question
|
|
* @type {ModelRef<Object, string, Object, Object>}
|
|
*/
|
|
const element = defineModel('element', {
|
|
type: Object,
|
|
default: () => {
|
|
return {};
|
|
}
|
|
});
|
|
|
|
/**
|
|
*
|
|
* @param index {number} 索引
|
|
* @param rate {number} 具体数值
|
|
*/
|
|
function handleRateChange(/* index, rate */) {
|
|
// 占位
|
|
}
|
|
|
|
const chooseId = ref('');
|
|
const emit = defineEmits(['update:element']);
|
|
const saveStem = () => {
|
|
emit('update:element', element.value);
|
|
};
|
|
|
|
const chooseOption = (item) => {
|
|
chooseId.value = item.id;
|
|
};
|
|
</script>
|
|
|
|
<style scoped lang="scss">
|
|
.content {
|
|
background-color: #fff;
|
|
|
|
& .rate-content {
|
|
width: 100%;
|
|
margin-top: 12px;
|
|
|
|
& .rate-item {
|
|
margin-bottom: 8px;
|
|
padding: 11px 13px;
|
|
border: 1px solid #f4f4f4;
|
|
border-radius: 8px;
|
|
background: #fafbfc;
|
|
}
|
|
}
|
|
}
|
|
|
|
.mb10 {
|
|
margin-bottom: 10px;
|
|
}
|
|
|
|
.mb5 {
|
|
margin-bottom: 5px;
|
|
}
|
|
|
|
.tips {
|
|
display: flex;
|
|
justify-content: space-between;
|
|
color: #b8b8b8;
|
|
font-size: 12px;
|
|
}
|
|
</style>
|