瀏覽代碼

【功能新增】IOT: 产品物模型,30%

puhui999 8 月之前
父節點
當前提交
94d74f1a09

+ 30 - 18
src/views/iot/product/product/detail/ThingModel/ThingModelDataSpecs.vue

@@ -1,31 +1,43 @@
 <template>
-  <el-select
-    v-model="formData.property.dataType.type"
-    :disabled="!!formData.id"
-    placeholder="请选择数据类型"
-  >
-    <el-option key="int" label="int32 (整数型)" value="int" />
-    <el-option key="float" label="float (单精度浮点型)" value="float" />
-    <el-option key="double" label="double (双精度浮点型)" value="double" />
-    <el-option key="enum" label="enum(枚举型)" value="enum" />
-    <el-option key="bool" label="bool (布尔型)" value="bool" />
-    <el-option key="text" label="text (文本型)" value="text" />
-    <el-option key="date" label="date (时间型)" value="date" />
-    <el-option key="struct" label="struct (结构体)" value="struct" />
-    <el-option key="array" label="array (数组)" value="array" />
-  </el-select>
-  <!-- 情况一:数值型 -->
+  <el-form-item label="数据类型" prop="dataType">
+    <ThingModelDataType v-model="formData.dataType" @change="handleChange" />
+  </el-form-item>
+  <!-- 数值型配置 -->
+  <ThingModelNumberTypeDataSpecs
+    v-if="
+      [DataSpecsDataType.INT, DataSpecsDataType.DOUBLE, DataSpecsDataType.FLOAT].includes(
+        formData.dataType || ''
+      )
+    "
+    v-model="formData.dataSpecs"
+  />
+  <!-- 枚举型配置 -->
+  <ThingModelEnumTypeDataSpecs
+    v-if="formData.dataType === DataSpecsDataType.ENUM"
+    v-model="formData.dataSpecsList"
+  />
 </template>
 
 <script lang="ts" setup>
 import { useVModel } from '@vueuse/core'
+import { DataSpecsDataType } from './config'
+import {
+  ThingModelDataType,
+  ThingModelEnumTypeDataSpecs,
+  ThingModelNumberTypeDataSpecs
+} from './dataSpecs'
 
-/** 物模型数据类型 */
+/** 物模型数据 */
 defineOptions({ name: 'ThingModelDataSpecs' })
 const props = defineProps<{ modelValue: any }>()
 const emits = defineEmits(['update:modelValue'])
-const formData = useVModel(props, 'modelValue', emits)
+const formData = useVModel(props, 'modelValue', emits) as Ref<any>
 
+/** 属性值的数据类型切换时 */
+const handleChange = () => {
+  formData.value.dataSpecsList = []
+  formData.value.dataSpecs = {}
+}
 // dataType为INT的dataSpecs示例:
 //
 // {

+ 0 - 29
src/views/iot/product/product/detail/ThingModel/ThingModelDataType.vue

@@ -1,29 +0,0 @@
-<template>
-  <el-select
-    v-model="formData.property.dataType.type"
-    :disabled="!!formData.id"
-    placeholder="请选择数据类型"
-  >
-    <el-option key="int" label="int32 (整数型)" value="int" />
-    <el-option key="float" label="float (单精度浮点型)" value="float" />
-    <el-option key="double" label="double (双精度浮点型)" value="double" />
-    <el-option key="enum" label="enum(枚举型)" value="enum" />
-    <el-option key="bool" label="bool (布尔型)" value="bool" />
-    <el-option key="text" label="text (文本型)" value="text" />
-    <el-option key="date" label="date (时间型)" value="date" />
-    <el-option key="struct" label="struct (结构体)" value="struct" />
-    <el-option key="array" label="array (数组)" value="array" />
-  </el-select>
-</template>
-
-<script lang="ts" setup>
-import { useVModel } from '@vueuse/core'
-
-/** 物模型数据类型 */
-defineOptions({ name: 'ThingModelDataType' })
-const props = defineProps<{ modelValue: any }>()
-const emits = defineEmits(['update:modelValue'])
-const formData = useVModel(props, 'modelValue', emits)
-</script>
-
-<style lang="scss" scoped></style>

+ 13 - 49
src/views/iot/product/product/detail/ThingModel/ThingModelForm.vue

@@ -18,28 +18,17 @@
         <el-input v-model="formData.name" placeholder="请输入功能名称" />
       </el-form-item>
       <el-form-item label="标识符" prop="identifier">
-        <el-input
-          v-model="formData.identifier"
-          :disabled="formType === 'update'"
-          placeholder="请输入标识符"
-        />
+        <el-input v-model="formData.identifier" placeholder="请输入标识符" />
       </el-form-item>
-      <el-form-item label="数据类型" prop="type">
-        <ThingModelDataType v-model="formData" />
-      </el-form-item>
-      <ThingModelNumberTypeDataSpecs v-model="formData" />
+      <ThingModelDataSpecs v-model="formData" />
       <el-form-item label="读写类型" prop="accessMode">
-        <el-radio-group v-model="formData.property.accessMode">
+        <el-radio-group v-model="formData.accessMode">
           <el-radio label="rw">读写</el-radio>
           <el-radio label="r">只读</el-radio>
         </el-radio-group>
       </el-form-item>
       <el-form-item label="属性描述" prop="property.description">
-        <el-input
-          v-model="formData.property.description"
-          placeholder="请输入属性描述"
-          type="textarea"
-        />
+        <el-input v-model="formData.description" placeholder="请输入属性描述" type="textarea" />
       </el-form-item>
     </el-form>
 
@@ -51,10 +40,9 @@
 </template>
 
 <script lang="ts" setup>
-import ThingModelNumberTypeDataSpecs from './ThingModelNumberTypeDataSpecs.vue'
 import { ProductVO } from '@/api/iot/product/product'
+import ThingModelDataSpecs from './ThingModelDataSpecs.vue'
 import {
-  ProductFunctionAccessModeEnum,
   ProductFunctionTypeEnum,
   ThinkModelFunctionApi,
   ThinkModelFunctionVO
@@ -80,22 +68,10 @@ const formData = ref({
   name: undefined,
   description: undefined,
   type: ProductFunctionTypeEnum.PROPERTY,
-  property: {
-    identifier: undefined,
-    name: undefined,
-    accessMode: ProductFunctionAccessModeEnum.READ_WRITE,
-    required: true,
-    dataType: {
-      type: undefined,
-      specs: {
-        min: undefined,
-        max: undefined,
-        step: undefined,
-        unit: undefined
-      }
-    },
-    description: undefined // 添加这一行
-  }
+  dataType: undefined,
+  dataSpecsList: [],
+  dataSpecs: undefined,
+  accessMode: undefined
 })
 const formRules = reactive({
   name: [
@@ -188,22 +164,10 @@ const resetForm = () => {
     name: undefined,
     description: undefined,
     type: ProductFunctionTypeEnum.PROPERTY,
-    property: {
-      identifier: undefined,
-      name: undefined,
-      accessMode: ProductFunctionAccessModeEnum.READ_WRITE,
-      required: true,
-      dataType: {
-        type: undefined,
-        specs: {
-          min: undefined,
-          max: undefined,
-          step: undefined,
-          unit: undefined
-        }
-      },
-      description: undefined // 确保重置 description 字段
-    }
+    dataType: undefined,
+    dataSpecsList: [],
+    dataSpecs: undefined,
+    accessMode: undefined
   }
   formRef.value?.resetFields()
 }

+ 38 - 0
src/views/iot/product/product/detail/ThingModel/config.ts

@@ -0,0 +1,38 @@
+/** dataSpecs 数值型数据结构 */
+export interface DataSpecsNumberDataVO {
+  dataType: 'INT' | 'FLOAT' | 'DOUBLE' // 数据类型,取值为 INT、FLOAT 或 DOUBLE
+  max: string // 最大值,必须与 dataType 设置一致,且为 STRING 类型
+  min: string // 最小值,必须与 dataType 设置一致,且为 STRING 类型
+  step: string // 步长,必须与 dataType 设置一致,且为 STRING 类型
+  precise?: string // 精度,当 dataType 为 FLOAT 或 DOUBLE 时可选
+  defaultValue?: string // 默认值,可选
+  unit: string // 单位的符号
+  unitName: string // 单位的名称
+}
+
+/** dataSpecs 文本型数据结构 */
+export interface DataSpecsTextDataVO {
+  dataType: 'TEXT'
+  length: number
+}
+
+/** dataSpecs 枚举型数据结构 */
+export interface DataSpecsEnumDataVO {
+  dataType: 'ENUM' | 'BOOL'
+  defaultValue?: string // 默认值,可选
+  name: string // 枚举项的名称
+  value: number // 枚举值
+}
+
+/** 属性值的数据类型 */
+export const DataSpecsDataType = {
+  INT: 'int',
+  FLOAT: 'float',
+  DOUBLE: 'double',
+  ENUM: 'enum',
+  BOOL: 'bool',
+  TEXT: 'text',
+  DATE: 'date',
+  STRUCT: 'struct',
+  ARRAY: 'array'
+}

+ 38 - 0
src/views/iot/product/product/detail/ThingModel/dataSpecs/ThingModelDataType.vue

@@ -0,0 +1,38 @@
+<template>
+  <el-select v-model="dataType" placeholder="请选择数据类型" @change="handleChange">
+    <el-option
+      v-for="option in dataTypeOptions"
+      :key="option.value"
+      :label="option.label"
+      :value="option.value"
+    />
+  </el-select>
+</template>
+
+<script lang="ts" setup>
+import { useVModel } from '@vueuse/core'
+import { DataSpecsDataType } from '../config'
+
+/** 物模型数据类型 */
+defineOptions({ name: 'ThingModelDataType' })
+const props = defineProps<{ modelValue: any }>()
+const emits = defineEmits(['update:modelValue', 'change'])
+const dataType = useVModel(props, 'modelValue', emits)
+
+const dataTypeOptions = [
+  { value: DataSpecsDataType.INT, label: 'int32 (整数型)' },
+  { value: DataSpecsDataType.FLOAT, label: 'float (单精度浮点型)' },
+  { value: DataSpecsDataType.DOUBLE, label: 'double (双精度浮点型)' },
+  { value: DataSpecsDataType.ENUM, label: 'enum(枚举型)' },
+  { value: DataSpecsDataType.BOOL, label: 'bool (布尔型)' },
+  { value: DataSpecsDataType.TEXT, label: 'text (文本型)' },
+  { value: DataSpecsDataType.DATE, label: 'date (时间型)' },
+  { value: DataSpecsDataType.STRUCT, label: 'struct (结构体)' },
+  { value: DataSpecsDataType.ARRAY, label: 'array (数组)' }
+]
+const handleChange = () => {
+  emits('change')
+}
+</script>
+
+<style lang="scss" scoped></style>

+ 26 - 0
src/views/iot/product/product/detail/ThingModel/dataSpecs/ThingModelEnumTypeDataSpecs.vue

@@ -0,0 +1,26 @@
+<template>
+  <el-form-item label="枚举项" prop="enumItem">
+    <div class="flex items-center justify-between">
+      <span> 参数值 </span>
+      <span> 参数描述 </span>
+    </div>
+    <div v-for="(item, index) in formData" :key="index" class="flex items-center justify-between">
+      <el-input v-model="item.value" placeholder="请输入参数值" />
+      <span class="mx-2">~</span>
+      <el-input v-model="item.name" placeholder="请输入参数描述" />
+    </div>
+    <el-button link type="primary">+添加枚举项</el-button>
+  </el-form-item>
+</template>
+
+<script lang="ts" setup>
+import { useVModel } from '@vueuse/core'
+
+/** 枚举型的 dataSpecs 配置组件 */
+defineOptions({ name: 'ThingModelEnumTypeDataSpecs' })
+const props = defineProps<{ modelValue: any }>()
+const emits = defineEmits(['update:modelValue'])
+const formData = useVModel(props, 'modelValue', emits)
+</script>
+
+<style lang="scss" scoped></style>

+ 3 - 13
src/views/iot/product/product/detail/ThingModel/ThingModelNumberTypeDataSpecs.vue → src/views/iot/product/product/detail/ThingModel/dataSpecs/ThingModelNumberTypeDataSpecs.vue

@@ -30,23 +30,13 @@
 <script lang="ts" setup>
 import { useVModel } from '@vueuse/core'
 import { UnifyUnitSpecsDTO } from '@/views/iot/utils/constants'
+import { DataSpecsNumberDataVO } from '../config'
 
+/** 数值型的 dataSpecs 配置组件 */
 defineOptions({ name: 'ThingModelNumberTypeDataSpecs' })
 const props = defineProps<{ modelValue: any }>()
 const emits = defineEmits(['update:modelValue'])
-const formData = useVModel(props, 'modelValue', emits) as Ref<DataConfig>
-type DataType = 'INT' | 'FLOAT' | 'DOUBLE'
-
-interface DataConfig {
-  dataType: DataType // 数据类型,取值为 INT、FLOAT 或 DOUBLE
-  max: string // 最大值,必须与 dataType 设置一致,且为 STRING 类型
-  min: string // 最小值,必须与 dataType 设置一致,且为 STRING 类型
-  step: string // 步长,必须与 dataType 设置一致,且为 STRING 类型
-  precise?: string // 精度,当 dataType 为 FLOAT 或 DOUBLE 时可选
-  defaultValue?: string // 默认值,可选
-  unit: string // 单位的符号
-  unitName: string // 单位的名称
-}
+const formData = useVModel(props, 'modelValue', emits) as Ref<DataSpecsNumberDataVO>
 
 /** 单位发生变化时触发 */
 const unitChange = (UnitSpecs: string) => {

+ 5 - 0
src/views/iot/product/product/detail/ThingModel/dataSpecs/index.ts

@@ -0,0 +1,5 @@
+import ThingModelDataType from './ThingModelDataType.vue'
+import ThingModelEnumTypeDataSpecs from './ThingModelEnumTypeDataSpecs.vue'
+import ThingModelNumberTypeDataSpecs from './ThingModelNumberTypeDataSpecs.vue'
+
+export { ThingModelDataType, ThingModelEnumTypeDataSpecs, ThingModelNumberTypeDataSpecs }