Hu Cheng 2 年 前
コミット
ccd3942488
6 ファイル変更252 行追加108 行削除
  1. 5 5
      src/App.vue
  2. 8 13
      src/login/index.vue
  3. 6 0
      src/plugin/naive-ui.js
  4. 7 0
      src/router/index.js
  5. 10 6
      src/utils/axios.js
  6. 216 84
      src/views/project/data/edit/index.vue

+ 5 - 5
src/App.vue

@@ -13,8 +13,8 @@ const themeOverrides = {
     primaryColorSuppl: "#2d8cf0",
   },
   Tabs: {
-    colorSegment: "#f0f2f5"
-  }
+    colorSegment: "#f0f2f5",
+  },
 };
 </script>
 
@@ -27,9 +27,9 @@ const themeOverrides = {
     <n-loading-bar-provider>
       <n-message-provider>
         <n-notification-provider>
-        <n-dialog-provider>
-          <RouterView />
-        </n-dialog-provider>
+          <n-dialog-provider>
+            <RouterView />
+          </n-dialog-provider>
         </n-notification-provider>
       </n-message-provider>
     </n-loading-bar-provider>

+ 8 - 13
src/login/index.vue

@@ -56,8 +56,6 @@ import md5 from "md5";
 import { setToken } from "@/utils/storage/sessionToken";
 import { darkTheme } from "naive-ui";
 
-const loadingBar = useLoadingBar();
-
 const formRef = ref(null);
 
 const router = useRouter();
@@ -90,15 +88,14 @@ const generalOptions = ["管理员", "用户"].map((v) => ({
 const handleLogin = async () => {
   formRef.value.validate(async (errors) => {
     if (!errors) {
-      try {
-        loadingBar.start();
-        const { data: res } = await login(
-          {
-            bzd_username: formValue.username,
-            bzd_password: md5(formValue.password),
-          },
-          formValue.role
-        );
+      const { data: res } = await login(
+        {
+          bzd_username: formValue.username,
+          bzd_password: md5(formValue.password),
+        },
+        formValue.role
+      );
+      if (res.Code === 200) {
         router.replace("/");
         notification.success({
           content: `您好,${formValue.username}`,
@@ -108,8 +105,6 @@ const handleLogin = async () => {
         });
         setToken(res.Data);
         window.sessionStorage.setItem("username", formValue.username);
-      } finally {
-        loadingBar.finish();
       }
     } else {
       message.error("验证失败,请填写完整信息");

+ 6 - 0
src/plugin/naive-ui.js

@@ -0,0 +1,6 @@
+import { createDiscreteApi } from "naive-ui";
+
+export const { message, loadingBar } = createDiscreteApi([
+  "message",
+  "loadingBar",
+]);

+ 7 - 0
src/router/index.js

@@ -2,6 +2,7 @@ import { createRouter, createWebHashHistory } from "vue-router";
 import LayoutView from "../layout/index.vue";
 import LoginView from "../login/index.vue";
 import { getToken } from "@/utils/storage/sessionToken";
+import { loadingBar } from "@/plugin/naive-ui";
 
 const router = createRouter({
   history: createWebHashHistory(import.meta.env.BASE_URL),
@@ -68,6 +69,7 @@ const router = createRouter({
 
 // 全局前置路由守卫
 router.beforeEach((to, from, next) => {
+  loadingBar.start();
   const token = getToken();
   if (to.path === "/login") {
     if (!token) {
@@ -84,4 +86,9 @@ router.beforeEach((to, from, next) => {
   }
 });
 
+// 全局后置路由守卫
+router.afterEach(() => {
+  loadingBar.finish();
+});
+
 export default router;

+ 10 - 6
src/utils/axios.js

@@ -1,9 +1,14 @@
 import axios from "axios";
 import { getToken } from "@/utils/storage/sessionToken";
 import { TOKEN } from "@/constant";
-import { createDiscreteApi } from "naive-ui";
+import { loadingBar, message } from "@/plugin/naive-ui";
 
-const { message } = createDiscreteApi(["message"]);
+// 显示消息
+const showMessage = (res) => {
+  if (res.Code !== 200) {
+    message.error(res.Msg);
+  }
+};
 
 const service = axios.create({
   baseURL: import.meta.env.VITE_API_BASE_URL,
@@ -14,6 +19,7 @@ const service = axios.create({
 service.interceptors.request.use(
   function (config) {
     // 在发送请求之前做些什么
+    loadingBar.start();
     const formData = new FormData();
     if (
       config.url !== "/Login_Admin_verification" &&
@@ -40,15 +46,13 @@ service.interceptors.response.use(
     // 2xx 范围内的状态码都会触发该函数。
     // 对响应数据做点什么
     const { data: res } = response;
-    if (res.Code !== 200) {
-      return message.error(res.Msg);
-    }
+    showMessage(res);
+    loadingBar.finish();
     return response;
   },
   function (error) {
     // 超出 2xx 范围的状态码都会触发该函数。
     // 对响应错误做点什么
-    console.log(error);
     return Promise.reject(error);
   }
 );

+ 216 - 84
src/views/project/data/edit/index.vue

@@ -9,8 +9,7 @@
         <n-card class="h-full">
           <n-list>
             <template #header>
-              <n-checkbox v-model:checked="value"> 全选 </n-checkbox>
-              <n-button text>反选</n-button>
+              <n-checkbox v-model:value="selectedAll" />
             </template>
             <template #footer>
               <n-space align="center">
@@ -20,25 +19,29 @@
                 <n-gradient-text type="info"> 传感器总数:861 </n-gradient-text>
               </n-space>
             </template>
-            <n-list-item>
-              <template #prefix>
-                <n-checkbox v-model:checked="value" />
+            <n-checkbox-group @update:value="onUpdateValues">
+              <template v-for="item of generalOptions" :key="item.value">
+                <n-list-item>
+                  <template #prefix>
+                    <n-checkbox :value="item.value" />
+                  </template>
+                  <template #suffix>
+                    <n-button type="error" size="small" text>删除</n-button>
+                  </template>
+                  <n-thing>
+                    <template #avatar>
+                      <n-avatar
+                        round
+                        size="small"
+                        src="https://07akioni.oss-cn-beijing.aliyuncs.com/07akioni.jpeg"
+                      />
+                    </template>
+                    <template #header> ID:001 </template>
+                    <template #description> 001 </template>
+                  </n-thing>
+                </n-list-item>
               </template>
-              <template #suffix>
-                <n-button type="error" size="small" text>删除</n-button>
-              </template>
-              <n-thing>
-                <template #avatar>
-                  <n-avatar
-                    round
-                    size="small"
-                    src="https://07akioni.oss-cn-beijing.aliyuncs.com/07akioni.jpeg"
-                  />
-                </template>
-                <template #header> ID:001 </template>
-                <template #description> 001 </template>
-              </n-thing>
-            </n-list-item>
+            </n-checkbox-group>
           </n-list>
         </n-card>
       </n-gi>
@@ -52,24 +55,19 @@
             />
             <n-button type="primary">搜索</n-button>
             <n-button type="primary">导出数据</n-button>
-            <n-button type="primary">导入数据</n-button>
-            <n-button type="primary">导入数(冷链平台)</n-button>
-            <n-button type="primary">添加数据</n-button>
-            <n-button type="primary">温湿度上下限设置</n-button>
-          </n-space>
-          <n-space>
-            <n-button type="primary">开箱时间</n-button>
-            <n-button type="primary">关箱时间</n-button>
-            <n-button type="primary">开门时间</n-button>
-            <n-button type="primary">开门结束时间</n-button>
-            <n-button type="primary">开箱测点选择</n-button>
+            <n-button type="primary" @click="showImportModal"
+              >导入数据</n-button
+            >
+            <n-button type="primary" @click="showAddModal">添加数据</n-button>
+            <n-button type="primary" @click="showSetModal"
+              >温湿度上下限设置</n-button
+            >
           </n-space>
           <n-card>
             <n-scrollbar style="max-height: 600px">
               <highcharts
                 constructor-type="stockChart"
                 :options="chartOptions"
-                :callback="chartCallback"
               ></highcharts>
             </n-scrollbar>
           </n-card>
@@ -82,40 +80,180 @@
     :show-icon="false"
     preset="dialog"
     :title="modal.title"
-    content="你确认?"
-    positive-text="确认"
-    negative-text="删除该节点"
-    :negative-button-props="{ type: 'error', onClick: handleDelete }"
-    @positive-click="submitCallback"
   >
-    <n-form-item>
-      <n-input v-model:value="value" type="text" />
-    </n-form-item>
+    <template v-if="modal.title === '详情'">
+      <n-form-item>
+        <n-input v-model:value="value" type="text" />
+      </n-form-item>
+      <n-space justify="end">
+        <n-popconfirm @positive-click="handleDelete">
+          <template #trigger>
+            <n-button type="error">删除该点</n-button>
+          </template>
+          是否确认删除?
+        </n-popconfirm>
+        <n-button type="primary">确定</n-button>
+      </n-space>
+    </template>
+    <template v-if="modal.title === '导入'">
+      <n-form
+        ref="formRef"
+        :model="formValue"
+        :rules="rules"
+        label-placement="left"
+        label-width="auto"
+      >
+        <n-form-item label="开始时间" path="datetimeValue">
+          <n-date-picker
+            v-model:value="formValue.datetimeValue"
+            type="datetime"
+            class="w-full"
+          />
+        </n-form-item>
+        <n-form-item label="结束时间" path="datetimeValue">
+          <n-date-picker
+            v-model:value="formValue.datetimeValue"
+            type="datetime"
+            class="w-full"
+          />
+        </n-form-item>
+        <n-form-item label="SN" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <n-form-item label="探头编号" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <div class="flex justify-end">
+          <n-button type="primary">查询</n-button>
+        </div>
+      </n-form>
+    </template>
+    <template v-if="modal.title === '添加'">
+      <n-form
+        ref="formRef"
+        :model="formValue"
+        :rules="rules"
+        label-placement="left"
+        label-width="auto"
+      >
+        <n-form-item label="测点" path="selectValue">
+          <n-select
+            v-model:value="formValue.selectValue"
+            :options="generalOptions"
+          />
+        </n-form-item>
+        <n-form-item label="温度" path="value">
+          <n-input v-model:value="formValue.value">
+            <template #suffix> C </template>
+          </n-input>
+        </n-form-item>
+        <n-form-item label="湿度" path="value">
+          <n-input v-model:value="formValue.value">
+            <template #suffix> % </template>
+          </n-input>
+        </n-form-item>
+        <n-form-item label="时间" path="datetimeValue">
+          <n-date-picker
+            v-model:value="formValue.datetimeValue"
+            type="datetime"
+            class="w-full"
+          />
+        </n-form-item>
+        <div class="flex justify-end">
+          <n-button type="primary">添加</n-button>
+        </div>
+      </n-form>
+    </template>
+    <template v-if="modal.title === '设置'">
+      <n-form
+        ref="formRef"
+        :model="formValue"
+        :rules="rules"
+        label-placement="left"
+        label-width="auto"
+      >
+        <n-divider title-placement="center"> 温度 </n-divider>
+        <n-form-item label="上限" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <n-form-item label="下限" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <n-divider title-placement="center"> 湿度 </n-divider>
+        <n-form-item label="上限" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <n-form-item label="下限" path="value">
+          <n-input v-model:value="formValue.value" />
+        </n-form-item>
+        <div class="flex justify-end">
+          <n-button type="primary">确定</n-button>
+        </div>
+      </n-form>
+    </template>
   </n-modal>
 </template>
 
 <script setup>
 import { Chart as highcharts } from "highcharts-vue";
 
-const chartCallback = () => {
-  console.time("line");
+const onUpdateValues = (val) => {
+  console.log(val);
+  console.log(chartOptions);
+  //  val.forEach(() => {
+  //    chartOptions.series.push({
+  //      data: getData(n),
+  //      lineWidth: 0.5,
+  //      cursor: "pointer",
+  //      events: {
+  //        click() {
+  //          modal.showModal = true;
+  //          modal.title = "详情";
+  //        },
+  //      },
+  //    })
+  // });
 };
 
-const message = useMessage();
-
-const dialog = useDialog();
 const handleDelete = () => {
-  dialog.create({
-    content: "确定是否删除?",
-    positiveText: "确定",
-    negativeText: "取消",
-  });
+  console.log("delete");
 };
 
 const value = ref(false);
 
 const range = ref(null);
 
+const generalOptions = ["groode", "veli good", "emazing", "lidiculous"].map(
+  (v) => ({
+    label: v,
+    value: v,
+  })
+);
+
+const selectedAll = ref(false);
+
+// 表单数据
+const formValue = reactive({
+  value: null,
+  datetimeValue: null,
+  selectValue: null,
+});
+
+// 表单规则
+const rules = {
+  datetimeValue: {
+    type: "number",
+    required: true,
+    trigger: ["blur", "change"],
+    message: "不能为空",
+  },
+  value: {
+    required: true,
+    trigger: ["blur"],
+    message: "不能为空",
+  },
+};
+
 function getData(n) {
   let arr = [],
     i,
@@ -143,77 +281,71 @@ function getData(n) {
   return arr;
 }
 let n = 1000000;
-let data1 = getData(n);
-let data2 = getData(n);
-let data3 = getData(n);
+let data = getData(n);
 
+// 图表配置
 const chartOptions = {
   accessibility: {
     enabled: false,
   },
+
   chart: {
-    height: 500,
     zoomType: "x",
   },
+
   boost: {
     useGPUTranslations: true,
   },
+
   title: {
-    text: "Highcharts drawing " + n + " points",
+    text: `Highcharts drawing ${n} points`,
   },
+
   subtitle: {
     text: "Using the Boost module",
   },
+
   tooltip: {
     valueDecimals: 2,
   },
-  xAxis: {
-    labels: {
-      format: "{value:%H:%M:%S}",
-    },
-  },
+
   series: [
     {
-      data: data1,
-      lineWidth: 0.5,
-      cursor: "pointer",
-      events: {
-        click() {
-          modal.showModal = true;
-        },
-      },
-    },
-    {
-      data: data2,
-      lineWidth: 0.5,
-      cursor: "pointer",
-      events: {
-        click() {
-          modal.showModal = true;
-        },
-      },
-    },
-    {
-      data: data3,
+      data,
       lineWidth: 0.5,
       cursor: "pointer",
       events: {
         click() {
           modal.showModal = true;
+          modal.title = "详情";
         },
       },
     },
   ],
 };
 
+// 对话框数据源
 const modal = reactive({
   showModal: false,
   title: "",
 });
 
-// 执行 positive 时执行的回调函数
-const submitCallback = () => {
-  message.success("Submit");
+// 显示添加
+const showSetModal = () => {
+  modal.showModal = true;
+  modal.title = "设置";
+};
+
+// 显示添加
+const showAddModal = () => {
+  modal.showModal = true;
+  modal.title = "添加";
+};
+
+// 显示导入
+const showImportModal = () => {
+  modal.showModal = true;
+  modal.title = "导入";
 };
 </script>