瀏覽代碼

fix:"优化部分页面样式,修复设备清洗功能"

soobin 2 天之前
父節點
當前提交
8edd26b082

+ 1 - 1
package.json

@@ -1,6 +1,6 @@
 {
   "name": "shenze-vue3-app",
-  "version": "1.5.816",
+  "version": "1.5.826",
   "private": true,
   "scripts": {
     "start": "vue-cli-service serve",

+ 2 - 2
public/version.json

@@ -1,5 +1,5 @@
 {
-  "version": "1.5.814",
-  "timestamp": "2025-08-13T11:47:59.373",
+  "version": "1.5.826",
+  "timestamp": "2025-08-25T16:05:15.044",
   "commitHash": "dev-build"
 }

+ 15 - 8
src/assets/language/en.json

@@ -58,7 +58,7 @@
     "ICE": "Ice Cream",
     "ifForeignes": "Account Type",
     "mainland": "Mainland",
-    "overseas": "Overseas"
+    "overseas": "Abroad/HKMT"
   },
   "navBar": {
     "homePage": "Home",
@@ -228,7 +228,12 @@
     "equipmentName": "Machine Name",
     "creationTime": "Alert Time",
     "alarmContent": "Alert Details",
-    "allDevices": "All Machines"
+    "allDevices": "All Machines",
+    "level1": "Info",
+    "level2": "Minor",
+    "level3": "Moderate",
+    "level4": "Severe",
+    "level5": "Critical"
   },
   "apkManage": {
     "apkManagement": "Apk management",
@@ -366,6 +371,8 @@
     "remoteDoorOpening": "Remote Lock Control",
     "banPaper": "Bill Validator Disable",
     "openRemindPaper": "Toggle bill validator disable mode?",
+    "openRemindClean": "Toggle equipment cleaning?",
+    "openRemindCleanRemind": "Toggle cleaning reminder?",
     "outDoor": "Outer Door",
     "inDoor": "Inner Door",
     "status": "Status",
@@ -1112,7 +1119,7 @@
       "mainOver": "Region",
       "mainOverPlace": "Select region",
       "mainland": "Mainland",
-      "overseas": "Overseas",
+      "overseas": "Abroad/HKMT",
       "companyTypeLabel": "Vendor",
       "companyTypePlaceholder": "Select vendor",
       "whole": "All",
@@ -1458,7 +1465,7 @@
     "chooseCountryCity": "Select Region",
     "country": "Region",
     "chinese": "Mainland China",
-    "other": "Overseas",
+    "other": "Abroad/HKMT",
     "areaLabel": "Area",
     "areaPlaceholder": "Select area",
     "areaRequired": "Select area",
@@ -1741,10 +1748,10 @@
     "successfully": "Command sent. Refresh in 5s"
   },
   "alramClean": {
-    "openCleanFunction": "Maintenance Mode: On",
-    "closeCleanFunction": "Maintenance Mode: Off",
-    "openStatus": "Maintenance Alerts: On",
-    "closeStatus": "Maintenance Alerts: Off",
+    "openCleanFunction": "Maintenance Mode",
+    "closeCleanFunction": "Maintenance Mode",
+    "openStatus": "Maintenance Alerts",
+    "closeStatus": "Maintenance Alerts",
     "tips": "Alert",
     "content": "Toggle mode?",
     "successfully": "Command sent. Refresh in 5s"

+ 12 - 5
src/assets/language/es.json

@@ -228,7 +228,12 @@
         "equipmentName": "Equipo",
         "creationTime": "Fecha alarma",
         "alarmContent": "Detalles",
-        "allDevices": "Todos equipos"
+        "allDevices": "Todos equipos",
+        "level1": "Información",
+        "level2": "Leve",
+        "level3": "Moderado",
+        "level4": "Grave",
+        "level5": "Crítico"
     },
     "apkManage": {
         "apkManagement": "Gestión APK",
@@ -366,6 +371,8 @@
         "remoteDoorOpening": "Control remoto de puerta",
         "banPaper": "Deshabilitar validador",
         "openRemindPaper": "¿Cambiar modo deshabilitación de validador?",
+        "openRemindClean": "¿Activar limpieza de equipo?",
+        "openRemindCleanRemind": "¿Activar recordatorio de limpieza?",
         "outDoor": "Puerta exterior",
         "inDoor": "Puerta interior",
         "status": "Estado",
@@ -1740,10 +1747,10 @@
         "successfully": "Actualizado. Espere 5 seg."
     },
     "alramClean": {
-        "openCleanFunction": "Limpieza: Activada",
-        "closeCleanFunction": "Limpieza: Desactivada",
-        "openStatus": "Recordatorio: ON",
-        "closeStatus": "Recordatorio: OFF",
+        "openCleanFunction": "Limpieza",
+        "closeCleanFunction": "Limpieza",
+        "openStatus": "Recordatorio",
+        "closeStatus": "Recordatorio",
         "tips": "Confirmar",
         "content": "¿Cambiar estado?",
         "successfully": "Actualizado. Espere 5 seg."

+ 12 - 5
src/assets/language/fr.json

@@ -228,7 +228,12 @@
         "equipmentName": "Appareil",
         "creationTime": "Date alarme",
         "alarmContent": "Description",
-        "allDevices": "Tous appareils"
+        "allDevices": "Tous appareils",
+        "level1": "Information",
+        "level2": "Mineur",
+        "level3": "Modéré",
+        "level4": "Sévère",
+        "level5": "Critique"
     },
     "apkManage": {
         "apkManagement": "Gestion APK",
@@ -366,6 +371,8 @@
         "remoteDoorOpening": "Contrôle à distance de porte",
         "banPaper": "Désactivation validateur billets",
         "openRemindPaper": "Basculer le mode désactivation du validateur billets ?",
+        "openRemindClean": "Activer le nettoyage de l'équipement?",
+        "openRemindCleanRemind": "Activer le rappel de nettoyage?",
         "outDoor": "Porte ext.",
         "inDoor": "Porte int.",
         "status": "État",
@@ -1771,10 +1778,10 @@
         "successfully": "Requête envoyée - Actualiser dans 5s"
     },
     "alramClean": {
-        "openCleanFunction": "Nettoyage : Activé",
-        "closeCleanFunction": "Nettoyage : Désactivé",
-        "openStatus": "Rappels nettoyage : Activés",
-        "closeStatus": "Rappels nettoyage : Désactivés",
+        "openCleanFunction": "Nettoyage",
+        "closeCleanFunction": "Nettoyage",
+        "openStatus": "Rappels nettoyage",
+        "closeStatus": "Rappels nettoyage",
         "tips": "Alerte",
         "content": "Confirmer changement ?",
         "successfully": "Requête envoyée - Actualiser dans 5s"

+ 12 - 5
src/assets/language/ja.json

@@ -223,7 +223,12 @@
         "equipmentName": "機器名",
         "creationTime": "作成時間",
         "alarmContent": "アラーム内容",
-        "allDevices": "全てのデバイス"
+        "allDevices": "全てのデバイス",
+        "level1": "情報",
+        "level2": "軽微",
+        "level3": "中程度",
+        "level4": "深刻",
+        "level5": "緊急"
     },
     "apkManage": {
         "apkManagement": "APK管理",
@@ -358,6 +363,8 @@
         "remoteDoorOpening": "リモートドア制御",
         "banPaper": "紙幣受け取り停止",
         "openRemindPaper": "紙幣識別機の停止モードを切り替えますか?",
+        "openRemindClean": "装置洗浄機能を切り替えますか?",
+        "openRemindCleanRemind": "洗浄リマインダーを切り替えますか?",
         "outDoor": "外部ドア",
         "inDoor": "内部ドア",
         "status": "ステータス",
@@ -1732,10 +1739,10 @@
         "successfully": "送信に成功しました。数秒待ってから再入力してください"
     },
     "alramClean": {
-        "openCleanFunction": "洗浄機能です:オン",
-        "closeCleanFunction": "洗浄機能です:オフ",
-        "openStatus": "装置のクリーニングリマインダースイッチの状態:オン",
-        "closeStatus": "装置のクリーニングリマインダースイッチの状態:オフ",
+        "openCleanFunction": "洗浄機能です",
+        "closeCleanFunction": "洗浄機能です",
+        "openStatus": "設備洗浄アラートです",
+        "closeStatus": "設備洗浄アラートです",
         "tips": "リマインダー",
         "content": "スイッチを切り替えますか?",
         "successfully": "送信成功、数秒後に再度確認してください"

+ 12 - 5
src/assets/language/pt.json

@@ -228,7 +228,12 @@
         "equipmentName": "Equipamento",
         "creationTime": "Horário do alerta",
         "alarmContent": "Detalhes do alerta",
-        "allDevices": "Todos equipamentos"
+        "allDevices": "Todos equipamentos",
+        "level1": "Informação",
+        "level2": "Leve",
+        "level3": "Moderado",
+        "level4": "Grave",
+        "level5": "Crítico"
     },
     "apkManage": {
         "apkManagement": "Gerenciar APK",
@@ -366,6 +371,8 @@
         "remoteDoorOpening": "Controle remoto de tranca",
         "banPaper": "Desativar leitor de cédulas",
         "openRemindPaper": "Alternar modo desativação do leitor?",
+        "openRemindClean": "Ativar limpeza do equipamento?",
+        "openRemindCleanRemind": "Ativar lembrete de limpeza?",
         "outDoor": "Porta Externa",
         "inDoor": "Porta Interna",
         "status": "Status",
@@ -1740,10 +1747,10 @@
         "successfully": "Comando enviado - Atualize em 5s"
     },
     "alramClean": {
-        "openCleanFunction": "Limpeza Automática: Ativada",
-        "closeCleanFunction": "Limpeza Automática: Desativada",
-        "openStatus": "Lembrete Limpeza: Ativado",
-        "closeStatus": "Lembrete Limpeza: Desativado",
+        "openCleanFunction": "Limpeza Automática",
+        "closeCleanFunction": "Limpeza Automática",
+        "openStatus": "Lembrete Limpeza",
+        "closeStatus": "Lembrete Limpeza",
         "tips": "Confirmação",
         "content": "Confirmar alteração?",
         "successfully": "Comando enviado - Atualize em 5s"

+ 10 - 5
src/assets/language/ru.json

@@ -228,7 +228,12 @@
         "equipmentName": "Название",
         "creationTime": "Время",
         "alarmContent": "Описание",
-        "allDevices": "Все устройства"
+        "allDevices": "Все устройства",
+        "level1": "Информация",
+        "level2": "Незначительный",
+        "level3": "Умеренный",
+        "level4": "Серьёзный",
+        "level5": "Критический"
     },
     "apkManage": {
         "apkManagement": "APK",
@@ -1771,10 +1776,10 @@
         "successfully": "Успешно. Обновите страницу через 5 сек."
     },
     "alramClean": {
-        "openCleanFunction": "Функция очистки: Включена",
-        "closeCleanFunction": "Функция очистки: Выключена",
-        "openStatus": "Напоминания об очистке: Вкл.",
-        "closeStatus": "Напоминания об очистке: Выкл.",
+        "openCleanFunction": "Функция очистки",
+        "closeCleanFunction": "Функция очистки",
+        "openStatus": "Напоминания об очистке",
+        "closeStatus": "Напоминания об очистке",
         "tips": "Подтверждение",
         "content": "Подтвердите изменение",
         "successfully": "Успешно. Обновите страницу через 5 сек."

+ 12 - 5
src/assets/language/uk.json

@@ -228,7 +228,12 @@
         "equipmentName": "Пристрій",
         "creationTime": "Дата",
         "alarmContent": "Опис",
-        "allDevices": "Всі пристрої"
+        "allDevices": "Всі пристрої",
+        "level1": "Інформація",
+        "level2": "Незначний",
+        "level3": "Помірний",
+        "level4": "Серйозний",
+        "level5": "Критичний"
     },
     "apkManage": {
         "apkManagement": "APK",
@@ -366,6 +371,8 @@
         "remoteDoorOpening": "Віддалене керування замком",
         "banPaper": "Вимкнення банкнотоприймача",
         "openRemindPaper": "Змінити режим вимкнення банкнотоприймача?",
+        "openRemindClean": "Перемкнути очищення обладнання?",
+        "openRemindCleanRemind": "Перемкнути нагадування про очищення?",
         "outDoor": "Зовнішні",
         "inDoor": "Внутрішні",
         "status": "Стан",
@@ -1741,10 +1748,10 @@
         "successfully": "Команда відправлена. Оновіть сторінку через 5 сек"
     },
     "alramClean": {
-        "openCleanFunction": "Функція очищення: Увімкнено",
-        "closeCleanFunction": "Функція очищення: Вимкнено",
-        "openStatus": "Сповіщення про очищення: Активні",
-        "closeStatus": "Сповіщення про очищення: Вимкнені",
+        "openCleanFunction": "Функція очищення",
+        "closeCleanFunction": "Функція очищення",
+        "openStatus": "Сповіщення про очищення",
+        "closeStatus": "Сповіщення про очищення",
         "tips": "Попередження",
         "content": "Змінити стан?",
         "successfully": "Команда відправлена. Оновіть сторінку через 5 сек"

+ 7 - 4
src/assets/language/zh.json

@@ -381,6 +381,8 @@
     "openRemindOut": "是否切换外门开关?",
     "openRemindIn": "是否切换内门开关?",
     "openRemindPaper": "是否切换纸币器禁能开关?",
+    "openRemindClean": "是否切换设备清洗功能开关?",
+    "openRemindCleanRemind": "是否切换设备清洗提醒开关?",
     "remoteSugarMaking": "远程制作",
     "remoteProduction": "远程制作",
     "modulation": "音量调节",
@@ -568,6 +570,7 @@
     "enterProductPrice": "请输入商品价格",
     "materialMonitor": "物料监控",
     "openRemindMaterial": "是否切换物料监控开关?",
+
     "showGoodsPage": {
       "title": "商品显示设置",
       "equipmentName": "设备名称"
@@ -1750,10 +1753,10 @@
     "successfully": "发送成功,请等待几秒后重新进入查看"
   },
   "alramClean": {
-    "openCleanFunction": "设备清洗功能:开启",
-    "closeCleanFunction": "设备清洗功能:关闭",
-    "openStatus": "设备清洗提醒开关状态:开启",
-    "closeStatus": "设备清洗提醒开关状态:关闭",
+    "openCleanFunction": "设备清洗功能",
+    "closeCleanFunction": "设备清洗功能",
+    "openStatus": "设备清洗提醒",
+    "closeStatus": "设备清洗提醒",
     "tips": "提醒",
     "content": "是否切换开关?",
     "successfully": "发送成功,请等待几秒后重新进入查看"

+ 1 - 1
src/common/js/utils.js

@@ -46,7 +46,7 @@ export const remoteMenus = {
   "C14": t("remote.C14"),
   "C15": t("remote.C15"),
   "C16": t("remote.C16"),
-  "C17": t("remote.C17"),
+  // "C17": t("remote.C17"),
   "C18": t("remote.C18"),
   "C19": t("remote.C19"),
   "C20": t("remote.C20"),

+ 0 - 20
src/views/device/deviceOper.vue

@@ -511,26 +511,6 @@
           <span class="operation-text">{{ $t("device.restartAndroid") }}</span>
         </div>
       </div>
-      <!-- 设备清洗提醒 -->
-      <div
-        class="operation-item"
-        v-if="
-          (device.machineType === '0' || device.machineType === null) &&
-          controlList.includes('C17')
-        "
-        @click="alramCleanClk()"
-      >
-        <div class="icon-wrapper">
-          <img
-            class="operation-icon"
-            src="../../assets/device/operIcon/alramClean.png"
-            alt="alramClean"
-          />
-        </div>
-        <div class="text-wrapper">
-          <span class="operation-text">{{ $t("device.alramClean") }}</span>
-        </div>
-      </div>
       <!-- 远程退币 -->
       <div
         class="operation-item"

+ 434 - 123
src/views/device/diyFlower/index.vue

@@ -1,64 +1,161 @@
 <template>
-  <div class="showGoodsIdx">
-    <s-header :name="$t('device.diyFlower')" :noback="false"></s-header>
-    <div class="headerCon kBordBott o-plr-10 o-ptb-16 l-flex-RC">
-      <div class="line o-mr-6"></div>
-      <div>
-        <span class="c-color c-text-14">{{ $t('device.showGoodsPage.equipmentName') }}:</span>
-        <span class="c-text-color c-text-14">{{ equipmentName }}</span>
+  <div class="diy-flower-device-page">
+    <!-- 自定义头部 -->
+    <s-header
+      :name="$t('device.diyFlower')"
+      :noback="false"
+      class="device-header"
+    />
+
+    <!-- 设备信息区域 -->
+    <div class="device-card">
+      <div class="device-header">
+        <van-icon name="desktop-o" class="icon" />
+        <h3 class="device-name">
+          {{ equipmentName }}
+        </h3>
+      </div>
+    </div>
+
+    <!-- 设备控制卡片 -->
+    <div class="control-card">
+      <div class="control-status">
+        <span class="status-text">
+          {{
+            checked ? $t("DIYFlower.openStatus") : $t("DIYFlower.closeStatus")
+          }}
+        </span>
+        <van-switch
+          :model-value="checked"
+          @update:model-value="updateStatus"
+          size="24"
+          inactive-color="#d1d5db"
+        />
       </div>
     </div>
-    <van-cell center :title="checked ? $t('DIYFlower.openStatus') : $t('DIYFlower.closeStatus')" size="large"
-      title-style="color: #404d74;">
-      <template #right-icon>
-        <van-switch :model-value="checked" @update:model-value="updateStatus" size="24" />
-      </template>
-    </van-cell>
-    <van-collapse v-if="checked" v-model="activeNames">
-      <van-collapse-item :title="$t('DIYFlower.shape')" name="1" size="large" title-style="color: #404d74;">
-        <van-row class="goods">
-          <van-col v-for="(item, index) in shapeData" :key="index" class="goodsCon o-mlr-5 o-mb-20" span="11">
-            <div class="l-flex-RC">
-              <van-image width="50" height="50" fit="contain" :src="showSugerPhoto(item)" />
-              <span class="o-ml-10" style="color: #000;word-wrap: break-word; width: 50px;">{{ item.name }}</span>
-              <van-checkbox class="o-ml-10" shape="square" v-model="shapeStates[index]" @change="shapeChange(index)" />
+
+    <!-- 配置选项 - 只在设备开启时显示 -->
+    <div v-if="checked">
+      <!-- 形状选择 -->
+      <div class="config-section">
+        <div class="section-header">
+          <div class="section-title">
+            <van-icon name="apps-o" class="section-icon" />
+            {{ $t("DIYFlower.shape") }}
+          </div>
+        </div>
+
+        <div class="options-container">
+          <div class="options-grid">
+            <div
+              v-for="(item, index) in shapeData"
+              @click="clickShape(index)"
+              :key="index"
+              class="option-item"
+              :class="{ 'option-selected': shapeStates[index] }"
+            >
+              <div class="option-image-wrapper">
+                <van-image
+                  width="70"
+                  height="70"
+                  fit="contain"
+                  :src="showSugerPhoto(item)"
+                  :alt="item.name"
+                  class="option-image"
+                >
+                  <template v-slot:loading>
+                    <van-loading type="spinner" size="20" />
+                  </template>
+                </van-image>
+              </div>
+              <div class="option-name">{{ item.name }}</div>
+              <van-checkbox
+                v-model="shapeStates[index]"
+                @click="clickShape(index)"
+                shape="square"
+                class="option-checkbox"
+              />
             </div>
-          </van-col>
-        </van-row>
-      </van-collapse-item>
-      <van-collapse-item :title="$t('DIYFlower.sugar')" name="2" size="large" title-style="color: #404d74;">
-        <van-row class="goods">
-          <van-col v-for="(item, index) in sugarData" :key="index" class="goodsCon o-mlr-5 o-mb-20" span="11">
-            <div class="l-flex-RC">
-              <van-image width="50" height="50" fit="contain" :src="showSugerPhoto(item)" />
-              <span class="o-ml-10" style="color: #000;word-wrap: break-word; width: 50px;">{{ item.name }}</span>
-              <van-checkbox class="o-ml-10" shape="square" v-model="sugarStates[index]" @change="sugarChange(index)" />
+          </div>
+        </div>
+      </div>
+
+      <!-- 糖分选择 -->
+      <div class="config-section">
+        <div class="section-header">
+          <div class="section-title">
+            <van-icon name="gem-o" class="section-icon" />
+            {{ $t("DIYFlower.sugar") }}
+          </div>
+        </div>
+
+        <div class="options-container">
+          <div class="options-grid">
+            <div
+              v-for="(item, index) in sugarData"
+              @click="clickSugar(index)"
+              :key="index"
+              class="option-item"
+              :class="{ 'option-selected': sugarStates[index] }"
+            >
+              <div class="option-image-wrapper">
+                <van-image
+                  width="70"
+                  height="70"
+                  fit="contain"
+                  :src="showSugerPhoto(item)"
+                  :alt="item.name"
+                  class="option-image"
+                >
+                  <template v-slot:loading>
+                    <van-loading type="spinner" size="20" />
+                  </template>
+                </van-image>
+              </div>
+              <div class="option-name">{{ item.name }}</div>
+              <van-checkbox
+                v-model="sugarStates[index]"
+                @click="clickSugar(index)"
+                shape="square"
+                class="option-checkbox"
+              />
             </div>
-          </van-col>
-        </van-row>
-      </van-collapse-item>
-    </van-collapse>
-    <div class="l-flex-center" v-if="checked" style="margin: 16px">
-      <van-button round block class="Btn" type="primary" native-type="submit" @click="updateShowGoods()">
-        {{ $t('device.submitAndPushDeviceUpdates') }}
-      </van-button>
+          </div>
+        </div>
+      </div>
+
+      <!-- 操作按钮 -->
+      <div class="action-buttons">
+        <van-button
+          round
+          block
+          class="update-button"
+          type="primary"
+          @click="updateShowGoods()"
+        >
+          <span>{{ $t("device.submitAndPushDeviceUpdates") }}</span>
+        </van-button>
+      </div>
     </div>
   </div>
 </template>
 
 <script>
 // 导入接口
-import { selectDIYFlowers, updateDIYFlowerStatus, updateDIYProductShow } from '@/service/device/index';
+import {
+  selectDIYFlowers,
+  updateDIYFlowerStatus,
+  updateDIYProductShow,
+} from "@/service/device/index";
 import sHeader from "@/components/SimpleHeader";
 import { ref, reactive } from "@vue/reactivity";
-import { onMounted } from '@vue/runtime-core';
-import { useRoute, useRouter } from 'vue-router';
-import { showDialog, showConfirmDialog, showFailToast, showToast } from 'vant';
+import { onMounted } from "@vue/runtime-core";
+import { useRoute, useRouter } from "vue-router";
+import { showDialog, showConfirmDialog, showFailToast, showToast } from "vant";
 import { useI18n } from "vue-i18n";
-import { styleUrl } from '../../../common/js/utils';
 export default {
   components: {
-    sHeader
+    sHeader,
   },
   setup() {
     // 引入语言
@@ -75,14 +172,12 @@ export default {
     const sugarStates = ref([]);
 
     // 设备名称
-    const equipmentName = ref('');
+    const equipmentName = route.query.name;
     const checked = ref(false);
     // 刚进页面
     onMounted(() => {
       // 加载样式
-      styleUrl('showGoods');
       const id = route.query.deviceId || "";
-      const name = route.query.name || "";
       const diyFlowerStatus = route.query.diyFlowerStatus || "";
 
       cofficentForm.equipmentId = id;
@@ -90,9 +185,7 @@ export default {
         checked.value = true;
         getList();
       }
-      if (id) {
-        equipmentName.value = name;
-      }
+      console.log("check", checked.value);
     });
     const showSugerPhoto = (row) => {
       let imgId = row.no;
@@ -105,58 +198,74 @@ export default {
     const getList = () => {
       const flower = route.query.flower || "";
       selectDIYFlowers({
-        equipmentId: cofficentForm.equipmentId
-      }).then(res => {
-        console.log('res', res)
-        const {
-          data
-        } = res.data;
+        equipmentId: cofficentForm.equipmentId,
+      }).then((res) => {
+        console.log("res", res);
+        const { data } = res.data;
         if (data) {
           if (data.length > 0) {
             // 是否修改状态
-            data.forEach(item => {
+            data.forEach((item) => {
               flowerNumber(item, flower);
-              if (item.no.includes('T')) {
+              if (item.no.includes("T")) {
                 sugarData.value.push(item);
-                if (item.showType == null || item.showType == '0') {
+                if (item.showType == null || item.showType == "0") {
                   sugarStates.value.push(false);
                 } else {
                   sugarStates.value.push(true);
                 }
               }
-            })
+            });
           }
         }
-      })
-    }
+      });
+    };
     // 修改的价格
     const cofficentForm = reactive({
-      equipmentId: '',
+      equipmentId: "",
     });
 
     // 判断花型数目
     const flowerNumber = (item, number) => {
       var shape = null;
-      if (number == '18') {
-        shape = ['S01', 'S02', 'S03'];
-      } else if (number == '22') {
-        shape = ['S01', 'S02', 'S03', 'S04'];
-      } else if (number == '26') {
-        shape = ['S01', 'S02', 'S03', 'S04', 'S05'];
-      } else if (number == '30') {
-        shape = ['S01', 'S02', 'S03', 'S04', 'S05', 'S06'];
+      if (number == "18") {
+        shape = ["S01", "S02", "S03"];
+      } else if (number == "22") {
+        shape = ["S01", "S02", "S03", "S04"];
+      } else if (number == "26") {
+        shape = ["S01", "S02", "S03", "S04", "S05"];
+      } else if (number == "30") {
+        shape = ["S01", "S02", "S03", "S04", "S05", "S06"];
       } else {
-        shape = ['S01', 'S02', 'S03', 'S04', 'S05', 'S06', 'S07', 'S08', 'S09'];
+        shape = ["S01", "S02", "S03", "S04", "S05", "S06", "S07", "S08", "S09"];
       }
       if (shape.includes(item.no)) {
         shapeData.value.push(item);
-        if (item.showType == null || item.showType == '0') {
+        if (item.showType == null || item.showType == "0") {
           shapeStates.value.push(false);
         } else {
           shapeStates.value.push(true);
         }
       }
-    }
+    };
+
+    const clickShape = (index) => {
+      shapeStates.value[index] = !shapeStates.value[index];
+      if (shapeStates.value[index]) {
+        shapeData.value[index].showType = 1;
+      } else {
+        shapeData.value[index].showType = 0;
+      }
+    };
+
+    const clickSugar = (index) => {
+      sugarStates.value[index] = !sugarStates.value[index];
+      if (sugarStates.value[index]) {
+        sugarData.value[index].showType = 1;
+      } else {
+        sugarData.value[index].showType = 0;
+      }
+    };
 
     // 更改状态
     const shapeChange = (index) => {
@@ -168,6 +277,7 @@ export default {
       console.log("形状", shapeData.value[index]);
     };
     const sugarChange = (index) => {
+      console.log("index", sugarStates.value[index]);
       if (sugarStates.value[index]) {
         sugarData.value[index].showType = 1;
       } else {
@@ -179,61 +289,60 @@ export default {
     const updateStatus = (newValue) => {
       const params = {
         equipmentId: cofficentForm.equipmentId,
-        DIYFlowerStatus: newValue ? '1' : '0',
+        DIYFlowerStatus: newValue ? "1" : "0",
       };
       showConfirmDialog({
-        title: t('DIYFlower.tips'),
-        message: t('DIYFlower.content'),
-      }).then(async () => {
-        const { data } = await updateDIYFlowerStatus(params);
-        if (data.code) {
-          // checked.value = newValue;
-          showToast(t('DIYFlower.successfully'));
-          setTimeout(() => {
-            router.go(-1);
-          }, 1500);
-        } else {
-          showFailToast(data.message);
-        }
-      }).catch((error) => {
-        console.log(error);
-        // showFailToast(t('device.unknownError'));
-      });
-    }
+        title: t("DIYFlower.tips"),
+        message: t("DIYFlower.content"),
+      })
+        .then(async () => {
+          const { data } = await updateDIYFlowerStatus(params);
+          if (data.code) {
+            showToast(t("DIYFlower.successfully"));
+            setTimeout(() => {
+              router.go(-1);
+            }, 1500);
+          } else {
+            showFailToast(data.message);
+          }
+        })
+        .catch((error) => {
+          console.log(error);
+        });
+    };
 
     // 点击提交
     const updateShowGoods = () => {
       showConfirmDialog({
-        title: t('device.openRemind'),
-        message: t('device.editCheck'),
-      }).then(() => {
-        var products = shapeData.value.concat(sugarData.value);
-        var list = JSON.stringify(products);
-        console.log(list);
-
-        updateDIYProductShow({
-          productList: list
-        }).then((res) => {
-          console.log(res.data.message);
-          showDialog({
-            message: t('DIYFlower.successfully'),
-          }).then(() => {
-            //返回上一页
-            router.go(-1);
-          });
-          // setTimeout(() => {
-          //   getList();
-          // }, 1000);
-        }).catch((error) => {
+        title: t("device.openRemind"),
+        message: t("device.editCheck"),
+      })
+        .then(() => {
+          var products = shapeData.value.concat(sugarData.value);
+          var list = JSON.stringify(products);
+          console.log(list);
+
+          updateDIYProductShow({
+            productList: list,
+          })
+            .then((res) => {
+              console.log(res.data.message);
+              showDialog({
+                message: t("DIYFlower.successfully"),
+              }).then(() => {
+                //返回上一页
+                router.go(-1);
+              });
+            })
+            .catch((error) => {
+              console.log(error);
+            });
+        })
+        .catch((error) => {
           console.log(error);
-          // showFailToast(t('device.unknownError'));
         });
-      }).catch((error) => {
-        console.log(error);
-        // showFailToast(t('device.unknownError'));
-      });
     };
-    const activeNames = ref(['1', '2']);
+    const activeNames = ref(["1", "2"]);
 
     return {
       cofficentForm,
@@ -249,10 +358,212 @@ export default {
       checked,
       showSugerPhoto,
       activeNames,
-      updateStatus
+      updateStatus,
+      clickShape,
+      clickSugar,
     };
   },
 };
 </script>
 
-<style lang="less" scoped></style>
+<style lang="less" scoped>
+@primary-color: #4d6add;
+@card-bg: #ffffff;
+@border-color: #e2e8f0;
+@text-dark: #1e293b;
+@text-light: #64748b;
+
+.diy-flower-device-page {
+  min-height: 100vh;
+  background-color: #f8fafc;
+  padding-bottom: 60px;
+}
+
+.device-card {
+  background: @card-bg;
+  border-radius: 12px;
+  box-shadow: 0 2px 12px rgba(0, 0, 0, 0.06);
+  margin: 10px;
+  padding: 16px;
+
+  .device-header {
+    display: flex;
+    align-items: center;
+
+    .icon {
+      font-size: 18px;
+      color: @primary-color;
+      margin-right: 10px;
+    }
+
+    .device-name {
+      margin: 0;
+      font-size: 15px;
+      color: #404d74;
+      font-weight: 550;
+
+      // 长名称处理
+      overflow: hidden;
+      text-overflow: ellipsis;
+      white-space: nowrap;
+      max-width: 70vw;
+    }
+  }
+}
+
+.control-card {
+  background-color: @card-bg;
+  border-radius: 16px;
+  margin: 20px 16px;
+  padding: 16px;
+  box-shadow: 0 4px 6px rgba(0, 0, 0, 0.03);
+
+  .control-status {
+    display: flex;
+    justify-content: space-between;
+    align-items: center;
+
+    .status-text {
+      font-size: 15px;
+      font-weight: 500;
+      color: @text-dark;
+    }
+  }
+}
+
+.config-section {
+  background-color: @card-bg;
+  border-radius: 16px;
+  margin: 16px;
+  padding: 16px;
+  box-shadow: 0 4px 6px rgba(0, 0, 0, 0.03);
+
+  .section-header {
+    display: flex;
+    justify-content: space-between;
+    align-items: center;
+    margin-bottom: 16px;
+    padding-bottom: 12px;
+    border-bottom: 1px dashed @border-color;
+
+    .section-title {
+      display: flex;
+      align-items: center;
+      font-size: 16px;
+      font-weight: 600;
+      color: @text-dark;
+
+      .section-icon {
+        font-size: 20px;
+        color: @primary-color;
+        margin-right: 10px;
+      }
+    }
+  }
+
+  .options-container {
+    margin-top: 10px;
+  }
+
+  .options-grid {
+    display: grid;
+    grid-template-columns: repeat(2, 1fr);
+    gap: 16px;
+
+    .option-item {
+      position: relative;
+      padding: 12px;
+      border-radius: 12px;
+      background-color: #f8fafc;
+      border: 1px solid @border-color;
+      transition: all 0.3s ease;
+      cursor: pointer;
+
+      &:hover {
+        transform: translateY(-3px);
+        box-shadow: 0 4px 10px rgba(0, 0, 0, 0.08);
+      }
+
+      &.option-selected {
+        border-color: @primary-color;
+        background-color: #ede9fe;
+      }
+
+      .option-image-wrapper {
+        position: relative;
+        background: white;
+        border-radius: 10px;
+        padding: 8px;
+        text-align: center;
+        margin-bottom: 8px;
+        transition: all 0.3s ease;
+        height: 100px;
+        display: flex;
+        justify-content: center;
+        align-items: center;
+      }
+
+      .option-name {
+        font-size: 13px;
+        text-align: center;
+        color: @text-dark;
+        font-weight: 500;
+        margin-top: 6px;
+        min-height: 36px;
+        display: flex;
+        align-items: center;
+        justify-content: center;
+      }
+
+      .option-checkbox {
+        position: absolute;
+        top: 8px;
+        right: 8px;
+        z-index: 2;
+      }
+    }
+  }
+}
+
+.action-buttons {
+  padding: 16px;
+
+  .update-button {
+    height: 50px;
+    background: linear-gradient(to right, #4d6add, #98a7e0);
+    border: none;
+    font-size: 16px;
+    font-weight: 600;
+    box-shadow: 0 4px 10px rgba(124, 58, 237, 0.3);
+
+    .button-loading {
+      margin-right: 8px;
+    }
+  }
+}
+
+@media (max-width: 480px) {
+  .device-info-card,
+  .control-card,
+  .config-section {
+    margin: 12px;
+  }
+
+  .options-grid {
+    gap: 12px !important;
+  }
+
+  .update-button {
+    height: 46px !important;
+    font-size: 15px !important;
+  }
+
+  .option-item {
+    padding: 8px !important;
+  }
+
+  .option-image-wrapper {
+    height: 80px !important;
+  }
+}
+</style>

+ 9 - 18
src/views/device/index.vue

@@ -33,17 +33,7 @@
               {{ $t("device.dataOverview") }}
             </h3>
             <div class="action-icons">
-              <van-popover
-                v-model:show="showPopover"
-                placement="left-start"
-                theme="dark"
-                :actions="actions"
-                @select="selectLabel"
-              >
-                <template #reference>
-                  <van-icon name="bars" class="icon-filter" />
-                </template>
-              </van-popover>
+              <van-icon name="bars" class="icon-filter" @click="selectLabel"/>
               <van-icon
                 name="search"
                 class="icon-search"
@@ -993,14 +983,15 @@ export default {
       { text: t("device.group"), value: "0" },
       { text: t("device.addGroup"), value: "1" },
     ];
-    const selectLabel = (action) => {
+    const selectLabel = () => {
       // showToast(action.value);
-      if (action.value == "0") {
-        router.push("/labelMan");
-      }
-      if (action.value == "1") {
-        router.push("/labelManAdd");
-      }
+      router.push("/labelMan");
+      // if (action.value == "0") {
+      //   router.push("/labelMan");
+      // }
+      // if (action.value == "1") {
+      //   router.push("/labelManAdd");
+      // }
     };
 
     // 睡眠切换

+ 123 - 11
src/views/device/openDoor.vue

@@ -116,8 +116,8 @@
       <div
         class="door-item"
         v-if="
-          (machineType == '0' || deviceDetal.equimentType == 'P30') &&
-          (user.ifForegin == '1' || user.type == '0')
+          (machineType === '0' || deviceDetal.equimentType == 'P30') &&
+          (user.ifForeign == '1' || user.type == '0')
         "
       >
         <div class="door-info">
@@ -143,6 +143,58 @@
           inactive-color="#dcdee0"
         />
       </div>
+
+      <!-- 设备清洗功能 -->
+      <div class="door-item" v-if="machineType == '0'">
+        <div class="door-info">
+          <div class="door-detail">
+            <h3 class="door-title">{{ $t("alramClean.openCleanFunction") }}</h3>
+            <p class="door-status">
+              {{ $t("device.status") }}:
+              <span
+                :class="
+                  deviceDetal.cleanFunction ? 'status-open' : 'status-closed'
+                "
+              >
+                {{
+                  deviceDetal.cleanFunction
+                    ? $t("device.open")
+                    : $t("device.closed")
+                }}
+              </span>
+            </p>
+          </div>
+        </div>
+        <van-switch
+          :model-value="deviceDetal.cleanFunction"
+          @update:model-value="cleanFunctionChg"
+          size="24px"
+          active-color="#4d6add"
+          inactive-color="#dcdee0"
+        />
+      </div>
+
+      <!-- 设备清洗提醒 -->
+      <div class="door-item" v-if="deviceDetal.cleanFunction">
+        <div class="door-info">
+          <div class="door-detail">
+            <h3 class="door-title">{{ $t("alramClean.openStatus") }}</h3>
+            <p class="door-status">
+              {{ $t("device.status") }}:
+              <span :class="remindStatus ? 'status-open' : 'status-closed'">
+                {{ remindStatus ? $t("device.open") : $t("device.closed") }}
+              </span>
+            </p>
+          </div>
+        </div>
+        <van-switch
+          :model-value="remindStatus"
+          @update:model-value="cleanRemindChg"
+          size="24px"
+          active-color="#4d6add"
+          inactive-color="#dcdee0"
+        />
+      </div>
     </div>
   </div>
 </template>
@@ -156,6 +208,9 @@ import {
   Api_openDoor,
   banMoney,
   changeMaterial,
+  getAlarmClean,
+  updateAlarmCleanStatus,
+  changeCleanFunction,
 } from "@/service/device";
 import { showFailToast, showToast, showConfirmDialog } from "vant";
 import { useI18n } from "vue-i18n";
@@ -169,13 +224,15 @@ export default {
     const deviceId = route.query.deviceId;
     const machineType = route.query.machineType;
     const deviceDetal = ref({});
+    const remindStatus = ref(false);
     const equipmentName = ref(route.query.name);
     const { t } = useI18n();
 
     // 初始化页面获取列表
     onMounted(async () => {
       // 加载样式
-      getDeviceDetalFun();
+      await getDeviceDetalFun();
+      await cleanRemindStatus(deviceDetal.value.clientId);
     });
 
     // 获取设备列表数据
@@ -199,6 +256,21 @@ export default {
       }
     };
 
+    const cleanRemindStatus = async (clientId) => {
+      try {
+        const { data } = await getAlarmClean(clientId); // 使用await等待异步函数执行完毕并返回结果
+        if (data.code === "00000") {
+          if (data.data != null) {
+            if (data.data.status === "1") {
+              remindStatus.value = true;
+            }
+          }
+        }
+      } catch (error) {
+        console.error("Error fetching data:", error);
+      }
+    };
+
     // 点击外门开关
     const outDoorChg = (outDoor) => {
       showConfirmDialog({
@@ -256,10 +328,12 @@ export default {
         }).then((res) => {
           if (res.data.code == "00000") {
             showToast(t("device.sentSuccessfully"));
+            setTimeout(() => {
+              router.go(-1);
+            }, 1500);
+          } else {
+            showFailToast(res.data.message);
           }
-          setTimeout(() => {
-            getDeviceDetalFun();
-          }, 1500);
         });
       });
     };
@@ -284,15 +358,58 @@ export default {
       });
     };
 
+    const cleanFunctionChg = (cleanFunction) => {
+      showConfirmDialog({
+        title: t("device.openRemind"),
+        message: t("device.openRemindClean"),
+      }).then(async () => {
+        const { data } = await changeCleanFunction({
+          equipmentId: deviceDetal.value.id,
+          cleanFunction: cleanFunction ? "1" : "0",
+        });
+        if (data.code === "00000") {
+          showToast(t("device.changeSleepSuccess"));
+          setTimeout(() => {
+            router.go(-1);
+          }, 1500);
+        } else {
+          showFailToast(data.message);
+        }
+      });
+    };
+
+    const cleanRemindChg = (cleanRemind) => {
+      showConfirmDialog({
+        title: t("device.openRemind"),
+        message: t("device.openRemindCleanRemind"),
+      }).then(async () => {
+        const { data } = await updateAlarmCleanStatus({
+          clientId: deviceDetal.value.clientId,
+          status: cleanRemind ? "1" : "0",
+        });
+        if (data.code === "00000") {
+          showToast(t("device.changeSleepSuccess"));
+          setTimeout(() => {
+            router.go(-1);
+          }, 1500);
+        } else {
+          showFailToast(data.message);
+        }
+      });
+    };
+
     return {
       deviceDetal,
       outDoorChg,
       inDoorChg,
       banPaperChg,
       materialChg,
+      cleanFunctionChg,
       machineType,
       equipmentName,
       user,
+      remindStatus,
+      cleanRemindChg,
     };
   },
   components: {
@@ -365,11 +482,6 @@ export default {
   align-items: center;
   padding: 16px 0;
   border-bottom: 1px solid rgba(0, 0, 0, 0.05);
-
-  // &:last-child {
-  //   border-bottom: none;
-  //   padding-bottom: 0;
-  // }
 }
 
 .door-info {

+ 17 - 0
src/views/forgetPassword.vue

@@ -138,6 +138,7 @@ export default {
     const email = ref(""); // 邮箱
     const phone = ref(""); // 手机号
     const code = ref(""); // 验证码
+    const hostName = ref("");
     const verCodeTime = reactive({
       time: 0,
     }); // 验证码间隔时间及状态
@@ -146,6 +147,7 @@ export default {
     const seedVerCode = async () => {
       const { data } = await sentForgetCode({
         phoneOrEmail: ifForeign.value === "0" ? phone.value : email.value,
+        hostName: hostName.value,
       });
       if (data.code === "00000") {
         showToast("验证码发送成功");
@@ -194,7 +196,22 @@ export default {
       } else {
         verCodeTime.time = 0;
       }
+      getCurrentDomain();
     });
+    
+    const getCurrentDomain = () => {
+      const currentDomain = window.location.href;
+      switch (true) {
+        case currentDomain.includes("sevencloud.com.cn"):
+          hostName.value = "Sevencloud";
+          break;
+        case currentDomain.includes("portalmcc.com.cn"):
+          hostName.value = "Portalmcc";
+          break;
+        default:
+          hostName.value = "Sunzee";
+      }
+    };
 
     return {
       ...toRefs(verCodeTime),

+ 36 - 24
src/views/home/index.vue

@@ -157,6 +157,11 @@
                 class="sale-cell"
               />
               <van-cell
+                :title="$t('home.electronicPayment')"
+                :value="currencySymbol + item.electronicPayment || '0'"
+                class="sale-cell"
+              />
+              <van-cell
                 :title="$t('home.allPayTypeTotal')"
                 :value="currencySymbol + calculateTotal(item)"
                 class="total-cell"
@@ -205,31 +210,22 @@
         </div>
       </div>
     </van-dialog>
-
-    <!-- <template v-if="isShowRobot">
-    <van-floating-bubble
+    <!-- <van-floating-bubble
       v-model:offset="offset"
       axis="xy"
-      :icon="robotIcon"
       magnetic="x"
-      @offset-change="onOffsetChange"
-      @click="onClickBot"
-    >
-    </van-floating-bubble>
+      icon="chat"
+      position="bottom-right"
+      @click="showPopup = true"
+    />
+
     <van-popup
-      v-model:show="popupVisible"
+      v-model:show="showPopup"
       position="bottom"
-      :style="{ height: '90%' }"
-      round
-      @click="onClose"
+      :style="{ height: '70%', width: '100%' }"
     >
-      <iframe
-        :src="aiUrl"
-        sandbox="allow-same-origin allow-scripts allow-popups allow-forms"
-        style="width: 100%; height: 100%"
-      ></iframe>
-    </van-popup>
-    </template> -->
+    <iframe src=http://ai.sunzee.com.cn/webhook/home/b271bff129da742c0d9d905cccd73cb674fe31b50188ab1a439ec139447794ee94970dc0451e8a65f3/index width='100%' height='100%' frameborder='0'></iframe>
+  </van-popup> -->
   </div>
 </template>
 
@@ -586,6 +582,10 @@ export default {
       if (typeof item.creditCard === "number" && !isNaN(item.creditCard)) {
         total += item.creditCard;
       }
+
+      if (typeof item.electronicPayment === "number" && !isNaN(item.electronicPayment)) {
+        total += item.electronicPayment;
+      }
       return total;
     };
 
@@ -602,16 +602,16 @@ export default {
         if (data.code === "00000" && data.data) {
           for (let i = 0; i < data.data.categories.length; i++) {
             const machineNameVal = data.data.categories[i]; // 设备名称
-            const coinsVal = data.data.series[0].data[i]; // 硬币销额
-            const billsVal = data.data.series[1].data[i]; // 纸币销额
-            const coinsBillsVal = data.data.series[2].data[i]; // 硬币+纸币销额
+            // const coinsVal = data.data.series[0].data[i]; // 硬币销额
+            // const billsVal = data.data.series[1].data[i]; // 纸币销额
+            const coinsBillsVal = data.data.series[0].data[i]+ data.data.series[1].data[i]+ data.data.series[2].data[i]; // 硬币+纸币销额
             const creditCardVal = data.data.series[3].data[i]; // 信用卡销额
             const electronicPaymentVal = data.data.series[4].data[i]; // 电子支付销额
 
             const machineSalesData = {
               machineName: machineNameVal,
-              coins: coinsVal,
-              bills: billsVal,
+              // coins: coinsVal,
+              // bills: billsVal,
               coinsBills: coinsBillsVal,
               creditCard: creditCardVal,
               electronicPayment: electronicPaymentVal,
@@ -804,6 +804,10 @@ export default {
       popupVisible.value = false;
     };
 
+    const showPopup = ref(false);
+    const inputText = ref("");
+    const messages = ref([]);
+
     return {
       user,
       userName,
@@ -847,6 +851,10 @@ export default {
       combinedList,
       isOrderData,
       calculateTotal,
+
+      showPopup,
+      inputText,
+      messages,
     };
   },
 };
@@ -1152,4 +1160,8 @@ export default {
     }
   }
 }
+
+.van-popup {
+  overflow: hidden;
+}
 </style>

+ 185 - 81
src/views/labelMan/add.vue

@@ -1,81 +1,85 @@
 <template>
-  <div class="addIdx">
-    <s-header :name="titleName" :noback="false"></s-header>
-    <van-form show-error-message @submit="onSubmit">
-      <div class="kBordBott cust_vantBorder">
-        <van-field colon :border="false" required v-model="cofficentForm.name" clearable name="name"
-                   :label="$t('labelMan.add.name')" :placeholder="$t('labelMan.add.namePlace')" :rules="[
-            {
-              required: true,
-              message: $t('labelMan.add.namePlace'),
-            },
-          ]" />
-      </div>
-      <!-- <div class="kBordBott">
-        <van-field colon :border="false" required clearable name="type" :label="$t('labelMan.add.type')"
-                   :placeholder="$t('labelMan.add.typePlace')" :rules="[
-            {
-              required: true,
-              message: $t('labelMan.add.typePlace'),
-              trigger: ['onChange', 'onSubmit'],
-            },
-          ]">
-          <template #input>
-            <van-radio-group v-model="cofficentForm.type" direction="horizontal">
-              <van-radio name="0">{{ $t("labelMan.merchant") }}</van-radio>
-              <van-radio name="1">{{ $t("labelMan.machine") }}</van-radio>
-            </van-radio-group>
-          </template>
-        </van-field>
-      </div> -->
-      <div v-if="cofficentForm.type === '0'" class="kBordBott cust_vantBorder">
-        <van-field colon :border="false" required @click-input="busiAdminInpClk" readonly clearable
-                   v-model="cofficentForm.adminNames" name="adminNames" :label="$t('labelMan.add.merchant')"
-                   :placeholder="$t('labelMan.add.merchantPlace')" :rules="[
-            {
-              required: true,
-              message: $t('labelMan.add.merchantPlace'),
-            },
-          ]">
-          <template #right-icon>
-            <div class="l-flex-RC">
-              <van-icon v-if="cofficentForm.adminNames" @click="cofficentForm.adminNames = ''" class="o-mr-6"
-                        name="clear" />
-              <van-icon @click="busiAdminInpClk" name="arrow-down" />
-            </div>
+  <div class="add-label-page">
+    <!-- 自定义头部 -->
+    <s-header :name="titleName" :noback="false" class="label-header" />
+
+    <!-- 表单区域 -->
+    <van-form @submit="onSubmit" class="label-form">
+      <!-- 标签名称 -->
+      <div class="form-section">
+        <van-field
+          v-model="cofficentForm.name"
+          name="name"
+          clearable
+          required
+          :border="false"
+          :label="$t('labelMan.add.name')"
+          :placeholder="$t('labelMan.add.namePlace')"
+          :rules="[{ required: true, message: $t('labelMan.add.namePlace') }]"
+          class="name-field"
+        >
+          <template #left-icon>
+            <van-icon name="label-o" class="field-icon" />
           </template>
         </van-field>
       </div>
-      <div v-if="cofficentForm.type === '1'" class="kBordBott cust_vantBorder">
-        <van-field colon :border="false" required @click-input="busiEquipInpClk" readonly clearable
-                   v-model="cofficentForm.equipmentNames" name="equipmentNames" :label="$t('labelMan.add.machine')"
-                   :placeholder="$t('labelMan.add.machinePlace')" :rules="[
-            {
-              required: true,
-              message: $t('labelMan.add.machinePlace'),
-            },
-          ]">
+
+      <!-- 机器选择 -->
+      <div v-if="cofficentForm.type === '1'" class="form-section">
+        <van-field
+          v-model="cofficentForm.equipmentNames"
+          name="equipmentNames"
+          readonly
+          required
+          :border="false"
+          :label="$t('labelMan.add.machine')"
+          :placeholder="$t('labelMan.add.machinePlace')"
+          :rules="[
+            { required: true, message: $t('labelMan.add.machinePlace') },
+          ]"
+          class="select-field"
+          @click="busiEquipInpClk"
+        >
+          <template #left-icon>
+            <van-icon name="desktop-o" class="field-icon" />
+          </template>
+
           <template #right-icon>
-            <div class="l-flex-RC">
-              <van-icon v-if="cofficentForm.equipmentNames" @click="cofficentForm.equipmentNames = ''" class="o-mr-6"
-                        name="clear" />
-              <van-icon @click="busiEquipInpClk" name="arrow-down" />
+            <div class="field-actions">
+              <van-icon
+                v-if="cofficentForm.equipmentNames"
+                name="clear"
+                class="clear-icon"
+                @click="cofficentForm.equipmentNames = ''"
+              />
+              <van-icon name="arrow-down" class="arrow-icon" />
             </div>
           </template>
         </van-field>
       </div>
-      <div style="margin: 16px">
-        <van-button round block type="primary" native-type="submit">
+
+      <!-- 提交按钮 -->
+      <div class="form-actions">
+        <van-button
+          round
+          block
+          type="primary"
+          native-type="submit"
+          class="submit-button"
+        >
           {{ titleName }}
         </van-button>
       </div>
     </van-form>
-    <!-- 商家弹窗 -->
-    <kSelectPop @selconfirm="selAdminConfirm" ref="kSelectPopAdminRef" :selOptions="selAdminOptions" @searchData="searchAdminData"
-                :selTitleAndName="['username', 'id']"></kSelectPop>
-    <!-- 机器弹窗 -->
-    <kSelectPop @selconfirm="selEquipConfirm" ref="kSelectPopEquipRef" :selOptions="selEquipOptions" @searchData="searchEquData"
-                :selTitleAndName="['name', 'id']"></kSelectPop>
+
+    <!-- 机器选择弹窗 -->
+    <kSelectPop
+      ref="kSelectPopEquipRef"
+      :selOptions="selEquipOptions"
+      @selconfirm="selEquipConfirm"
+      @searchData="searchEquData"
+      :selTitleAndName="['name', 'id']"
+    />
   </div>
 </template>
 
@@ -83,7 +87,7 @@
 // 导入选择组件
 import kSelectPop from "../../components/commom/kSelectPop/index.vue";
 // 导入公用方法
-import { getLoginUser, styleUrl } from "../../common/js/utils";
+import { getLoginUser } from "../../common/js/utils";
 // 导入接口
 import {
   Api_getListAdmin,
@@ -114,7 +118,6 @@ export default {
         const { data } = res;
         if (data.code === "00000") {
           selEquipOptions.value = data.data;
-          // selEquipOptions.value = data.data.slice(0, 8);
         }
       });
     };
@@ -142,21 +145,18 @@ export default {
     };
 
     const searchAdminData = (e) => {
-      // console.log("用户列表", e);
       selAdminOptions.value = e;
-    }
+    };
 
     const searchEquData = (e) => {
-      // console.log("设备列表", e);
       selEquipOptions.value = e;
-    }
-    
+    };
 
     // 点击机器列表
     const busiEquipInpClk = () => {
       if (cofficentForm.value.equipmentNames) {
         let list = cofficentForm.value.equipmentNames.split(",");
-        console.log(list, 'list')
+        console.log(list, "list");
         kSelectPopEquipRef.value.selPopOpen(list);
       } else {
         kSelectPopEquipRef.value.selPopOpen();
@@ -185,7 +185,6 @@ export default {
     const route = useRoute();
     // 刚进页面
     onMounted(() => {
-      styleUrl('labelMan');
       // 获取商家列表
       getAdminList();
       // 获取机器列表
@@ -197,12 +196,12 @@ export default {
         cofficentForm.value = row;
         // 处理商家列表,把选中的显示在商家列表
         cofficentForm.value.adminNames = cofficentForm.value.adminNames
-            ? JSON.parse(cofficentForm.value.adminNames).join(",")
-            : "";
+          ? JSON.parse(cofficentForm.value.adminNames).join(",")
+          : "";
         // 处理机器列表,把选中的显示在机器列表
         cofficentForm.value.equipmentNames = cofficentForm.value.equipmentNames
-            ? JSON.parse(cofficentForm.value.equipmentNames).join(",")
-            : "";
+          ? JSON.parse(cofficentForm.value.equipmentNames).join(",")
+          : "";
       }
     });
     // 表单参数
@@ -241,12 +240,12 @@ export default {
       }
       const { data } = res;
       if (data.code === "00000" && cofficentForm.value.id) {
-        showToast(t('labelMan.add.editSuccess'));
+        showToast(t("labelMan.add.editSuccess"));
         setTimeout(() => {
           router.go(-1);
         }, 1000);
       } else if (data.code === "00000" && !cofficentForm.value.id) {
-        showToast(t('labelMan.add.addSuccess'));
+        showToast(t("labelMan.add.addSuccess"));
         setTimeout(() => {
           router.go(-1);
         }, 1000);
@@ -272,4 +271,109 @@ export default {
 </script>
 
 <style lang="less" scoped>
-</style>
+@primary-color: #4d6add;
+@card-bg: #ffffff;
+@text-dark: #333;
+@text-light: #666;
+@border-color: #e4e7ec;
+
+.add-label-page {
+  min-height: 100vh;
+  background-color: #f5f8ff;
+}
+
+.label-header {
+  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+}
+
+.label-form {
+  padding: 16px;
+}
+
+.form-section {
+  background-color: @card-bg;
+  border-radius: 12px;
+  margin-bottom: 16px;
+  box-shadow: 0 4px 12px rgba(77, 106, 221, 0.1);
+  overflow: hidden;
+
+  &:last-child {
+    margin-bottom: 20px;
+  }
+}
+
+.name-field,
+.select-field {
+  padding: 16px;
+
+  :deep(.van-field__label) {
+    font-weight: 500;
+    color: @text-dark;
+  }
+
+  :deep(.van-field__control) {
+    font-size: 15px;
+    color: @text-dark;
+  }
+
+  .field-icon {
+    font-size: 20px;
+    color: @primary-color;
+    margin-right: 10px;
+  }
+
+  .field-actions {
+    display: flex;
+    align-items: center;
+
+    .clear-icon {
+      color: #999;
+      font-size: 18px;
+      margin-right: 8px;
+      padding: 4px;
+
+      &:active {
+        color: @primary-color;
+      }
+    }
+
+    .arrow-icon {
+      color: #999;
+      font-size: 18px;
+    }
+  }
+}
+
+.form-actions {
+  padding: 0 16px;
+
+  .submit-button {
+    height: 50px;
+    background: linear-gradient(to right, #4d6add, #6a89ff);
+    border: none;
+    font-size: 16px;
+    font-weight: 500;
+    box-shadow: 0 6px 16px rgba(77, 106, 221, 0.3);
+  }
+}
+
+@media (max-width: 480px) {
+  .label-form {
+    padding: 12px;
+  }
+
+  .form-section {
+    margin-bottom: 12px;
+  }
+
+  .name-field,
+  .select-field {
+    padding: 12px;
+  }
+
+  .submit-button {
+    height: 46px;
+    font-size: 15px;
+  }
+}
+</style>

+ 318 - 69
src/views/labelMan/index.vue

@@ -1,86 +1,120 @@
 <template>
-  <div class="advertRuleIdx">
-    <s-header :name="$t('labelMan.title')" :noback="false"></s-header>
-    <div v-if="isDelete" class="headCon l-flex-between o-plr-15 o-pt-5 o-pb-5 kBordBott">
-      <div class="l-flex-RC c-text-15 c-text-color c-text-b">
-        {{ $t("advertManage.advertRule.selected") }}
-        {{ selectTotals }}
-        {{ $t("advertManage.advertRule.individual") }}
-      </div>
-      <div class="l-flex-RC">
-        <div @click="cancelClk" class="c-text-c c-text-13 c-color">
-          {{ $t("advertManage.advertRule.cancel") }}
-        </div>
-        <div @click="noticeClk" class="c-text-c o-ml-24 c-text-13" style="color: #df5e4c">
-          {{ $t("advertManage.advertRule.confirmDel") }}
+  <div class="advert-rule-page">
+    <!-- 自定义头部 -->
+    <s-header
+      :name="$t('labelMan.title')"
+      :noback="false"
+    />
+
+    <!-- 顶部操作栏 -->
+    <div class="top-action-bar">
+      <div v-if="isDelete" class="delete-mode-bar">
+        <div class="selected-count">
+          <van-icon name="checked" class="count-icon" />
+          {{ $t("advertManage.advertRule.selected") }}
+          <span class="highlight">{{ selectTotals }}</span>
+          {{ $t("advertManage.advertRule.individual") }}
         </div>
-      </div>
-    </div>
-    <div v-else class="headCon l-flex-between o-plr-15 o-pt-5 o-pb-5 kBordBott">
-      <div class="l-flex-RC">
-        <!-- <img class="ruleIcon o-mr-10" src="@/assets/advertManage/ruleIcon.png" alt="" /> -->
-        <div class="ruleIcon o-mr-10"></div>
-        <div class="c-text-color c-text-b c-text-15">
-          {{ $t("advertManage.advertRule.total")
-          }}<span class="c-text-20" style="color: #df5e4c">{{
-            ruleTotal
-          }}</span>
-          {{ $t("alarmHistory.recordsTotal") }}
+        <div class="action-buttons">
+          <van-button size="small" class="cancel-btn" @click="cancelClk">
+            {{ $t("advertManage.advertRule.cancel") }}
+          </van-button>
+          <van-button
+            size="small"
+            type="danger"
+            class="confirm-btn"
+            @click="noticeClk"
+          >
+            {{ $t("advertManage.advertRule.confirmDel") }}
+          </van-button>
         </div>
       </div>
-      <div class="l-flex-RC">
-        <div @click="toAdd" class="c-text-c">
-          <div>
-            <van-icon size="18" name="add-o" />
+
+      <div v-else class="normal-mode-bar">
+        <div class="rule-info">
+          <div class="rule-icon">
+            <van-icon name="description" class="icon" />
           </div>
-          <div class="c-text-color c-text-12">
-            {{ $t("advertManage.advertRule.add") }}
+          <div class="rule-count">
+            {{ $t("advertManage.advertRule.total") }}
+            <span class="highlight">{{ ruleTotal }}</span>
+            {{ $t("alarmHistory.recordsTotal") }}
           </div>
         </div>
-        <div @click="isDelete = true" class="c-text-c o-ml-24">
-          <div>
-            <van-icon size="18" name="close" />
-          </div>
-          <div class="c-text-color c-text-12">
+
+        <div class="action-buttons">
+          <van-button icon="plus" size="small" class="add-btn" @click="toAdd">
+            {{ $t("advertManage.advertRule.add") }}
+          </van-button>
+          <van-button
+            icon="delete"
+            size="small"
+            type="danger"
+            plain
+            class="delete-btn"
+            @click="isDelete = true"
+          >
             {{ $t("advertManage.advertRule.delete") }}
-          </div>
+          </van-button>
         </div>
       </div>
     </div>
-    <div class="intervalRow"></div>
-    <!-- <kTabs tabWidth="100%" @tabchg="tabChg" :tabList="tabList"></kTabs> -->
-    <div class="contentCon">
-      <div @click.self="toEdit(item)" v-for="item in tableData" :key="item.id"
-           class="o-plr-20 o-pt-24 o-pb-12 l-flex-between kBordBott content">
-        <div>
-          <div class="l-flex-RC">
-            <span class="c-color c-text-12">{{ $t("labelMan.labelName") }}:</span>
-            <span class="c-text-color c-text-12">{{ item.name }}</span>
+
+    <!-- 规则列表 -->
+    <div class="rule-list">
+      <div
+        v-for="item in tableData"
+        :key="item.id"
+        class="rule-card"
+        :class="{ 'rule-card-delete-mode': isDelete }"
+      >
+        <div class="rule-content" @click="toEdit(item)">
+          <div class="rule-field">
+            <van-icon name="label-o" class="field-icon" />
+            <span class="field-label">{{ $t("labelMan.labelName") }}:</span>
+            <span class="field-value">{{ item.name }}</span>
           </div>
-          <div class="l-flex-RC">
-            <span class="c-color c-text-12">{{ $t("advertManage.advertRule.createTime") }}:</span>
-            <span class="c-text-color c-text-12">{{
-                Format_time(item.createDate)
-              }}</span>
+
+          <div class="rule-field">
+            <van-icon name="clock-o" class="field-icon" />
+            <span class="field-label"
+              >{{ $t("advertManage.advertRule.createTime") }}:</span
+            >
+            <span class="field-value">{{ Format_time(item.createDate) }}</span>
           </div>
         </div>
-        <div class="rightCon">
+
+        <div class="rule-action">
           <template v-if="isDelete">
-            <van-checkbox v-model="item.checked">{{ " " }}</van-checkbox>
+            <van-checkbox
+              v-model="item.checked"
+              shape="square"
+              checked-color="#df5e4c"
+            />
           </template>
           <template v-else>
-            <div @click="toEdit(item)" class="editBtn c-text-14">
+            <van-button
+              icon="edit"
+              size="small"
+              class="edit-btn"
+              @click.stop="toEdit(item)"
+            >
               {{ $t("advertManage.advertRule.edit") }}
-            </div>
+            </van-button>
           </template>
         </div>
       </div>
     </div>
+
     <!-- 删除确认弹窗 -->
-    <kDialog :dialogTitle="$t('advertManage.delPopTitle')" :cancelBtnTxt="$t('advertManage.cancelTxt')"
-             :confirmBtnTxt="$t('advertManage.confirmDel')" ref="kDialogRef" :dialogContent="$t('advertManage.delPopContent')"
-             @confirmclk="confirmClk">
-    </kDialog>
+    <kDialog
+      :dialogTitle="$t('advertManage.delPopTitle')"
+      :cancelBtnTxt="$t('advertManage.cancelTxt')"
+      :confirmBtnTxt="$t('advertManage.confirmDel')"
+      ref="kDialogRef"
+      :dialogContent="$t('advertManage.delPopContent')"
+      @confirmclk="confirmClk"
+    />
   </div>
 </template>
 
@@ -88,7 +122,7 @@
 // 导入tab组件
 // import kTabs from "../../components/commom/kTabs/index.vue";
 // 导入公用方法
-import { Format_time, getLoginUser, styleUrl } from "../../common/js/utils";
+import { Format_time, getLoginUser } from "../../common/js/utils";
 // 导入弹窗
 import kDialog from "../../components/commom/kDialog/index.vue";
 // 导入接口
@@ -99,9 +133,10 @@ import { useRouter } from "vue-router";
 import { showToast } from "vant";
 import { useI18n } from "vue-i18n";
 export default {
-  components: { sHeader, 
-    kDialog, 
-    // kTabs 
+  components: {
+    sHeader,
+    kDialog,
+    // kTabs
   },
   setup() {
     const { t } = useI18n();
@@ -113,12 +148,12 @@ export default {
     // tab栏
     const tabList = ref([
       {
-        name: t('labelMan.merchant'),
+        name: t("labelMan.merchant"),
         icon: "",
         id: 1,
       },
       {
-        name: t('labelMan.machine'),
+        name: t("labelMan.machine"),
         icon: "",
         id: 2,
       },
@@ -188,14 +223,14 @@ export default {
     });
     // 刚进入页面
     onMounted(() => {
-      styleUrl('labelMan');
+      // styleUrl("labelMan");
       getList();
     });
     // 筛选条件
     const searchParam = {
       adminId: user.id,
       type: 1,
-    }
+    };
     // 获取列表
     const getList = () => {
       Api_getLabelList(searchParam).then((res) => {
@@ -250,4 +285,218 @@ export default {
 };
 </script>
 
-<style lang="less" scoped></style>
+<style lang="less" scoped>
+@primary-color: #4d6add;
+@danger-color: #df5e4c;
+@text-dark: #333;
+@text-light: #666;
+@border-color: #e4e7ec;
+@card-bg: #ffffff;
+
+.advert-rule-page {
+  min-height: 100vh;
+  overflow: hidden;
+}
+
+.top-action-bar {
+  background-color: @card-bg;
+  padding: 12px 16px;
+  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+  position: sticky;
+  top: 46px;
+  z-index: 10;
+}
+
+.delete-mode-bar {
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+
+  .selected-count {
+    display: flex;
+    align-items: center;
+    font-size: 14px;
+    color: @text-dark;
+
+    .count-icon {
+      color: @danger-color;
+      margin-right: 6px;
+    }
+
+    .highlight {
+      color: @danger-color;
+      font-weight: bold;
+      margin: 0 4px;
+    }
+  }
+
+  .action-buttons {
+    display: flex;
+    gap: 12px;
+
+    .cancel-btn {
+      border-color: @border-color;
+      color: @text-dark;
+    }
+
+    .confirm-btn {
+      background-color: @danger-color;
+      border-color: @danger-color;
+    }
+  }
+}
+
+.normal-mode-bar {
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+
+  .rule-info {
+    display: flex;
+    align-items: center;
+
+    .rule-icon {
+      width: 32px;
+      height: 32px;
+      background-color: #e8ecff;
+      border-radius: 8px;
+      display: flex;
+      align-items: center;
+      justify-content: center;
+      margin-right: 10px;
+
+      .icon {
+        font-size: 18px;
+        color: @primary-color;
+      }
+    }
+
+    .rule-count {
+      font-size: 14px;
+      color: @text-dark;
+
+      .highlight {
+        color: @danger-color;
+        font-weight: bold;
+        margin: 0 4px;
+      }
+    }
+  }
+
+  .action-buttons {
+    display: flex;
+    gap: 10px;
+
+    .add-btn {
+      background-color: @primary-color;
+      border-color: @primary-color;
+      color: white;
+    }
+
+    .delete-btn {
+      border-color: @danger-color;
+      color: @danger-color;
+    }
+  }
+}
+
+.rule-list {
+  padding: 16px;
+  background: #f5f6fa;
+  height: calc(100% - 110px);
+  overflow: auto;
+  overflow-x: hidden;
+}
+
+.rule-card {
+  background-color: @card-bg;
+  border-radius: 12px;
+  padding: 16px;
+  margin-bottom: 16px;
+  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+  transition: all 0.3s ease;
+
+  &:hover {
+    transform: translateY(-2px);
+    box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+  }
+
+  &.rule-card-delete-mode {
+    background-color: #fff9f9;
+    border: 1px solid rgba(223, 94, 76, 0.2);
+  }
+}
+
+.rule-content {
+  flex: 1;
+  cursor: pointer;
+
+  .rule-field {
+    display: flex;
+    align-items: center;
+    margin-bottom: 10px;
+
+    &:last-child {
+      margin-bottom: 0;
+    }
+
+    .field-icon {
+      color: @primary-color;
+      margin-right: 8px;
+      font-size: 16px;
+    }
+
+    .field-label {
+      font-size: 14px;
+      color: @text-light;
+    }
+
+    .field-value {
+      font-size: 14px;
+      color: @text-dark;
+      font-weight: 500;
+    }
+  }
+}
+
+.rule-action {
+  margin-left: 15px;
+
+  .edit-btn {
+    background-color: #e8ecff;
+    border: none;
+    color: @primary-color;
+  }
+}
+
+@media (max-width: 480px) {
+  .top-action-bar {
+    padding: 10px 12px;
+  }
+
+  .rule-card {
+    padding: 12px;
+    flex-direction: column;
+    align-items: flex-start;
+  }
+
+  .rule-action {
+    margin-left: 0;
+    margin-top: 12px;
+    width: 100%;
+    display: flex;
+    justify-content: flex-end;
+  }
+
+  .delete-mode-bar {
+    gap: 10px;
+
+    .action-buttons {
+      justify-content: flex-end;
+    }
+  }
+}
+</style>