shaogen1995 2 tahun lalu
induk
melakukan
1670c2d92b

+ 13 - 14
后台/src/pages/A1Stat/index.tsx

@@ -3,17 +3,23 @@ import styles from "./index.module.scss";
 import { DatePicker } from "antd";
 import dayjs from "dayjs";
 import classNames from "classnames";
+import { useDispatch, useSelector } from "react-redux";
+import { A1API_getNumList } from "@/store/action/A1Stat";
+import { RootState } from "@/store";
 const { RangePicker } = DatePicker;
 
 function A1Stat() {
+  const dispatch = useDispatch();
+
   const [formData, setFormData] = useState({
     startTime: dayjs().subtract(30, "day").format("YYYY-MM-DD") + " 00:00:00",
     endTime: dayjs().format("YYYY-MM-DD") + " 23:59:59",
   });
 
   const getListFu = useCallback(() => {
-    console.log("发送请求", formData);
-  }, [formData]);
+    // console.log("发送请求", formData);
+    dispatch(A1API_getNumList(formData));
+  }, [dispatch, formData]);
 
   useEffect(() => {
     getListFu();
@@ -30,14 +36,7 @@ function A1Stat() {
     setFormData({ startTime, endTime });
   }, []);
 
-  const [data, setData] = useState([
-    { id: 1, name: "收集问卷", pcs: 1341 },
-    { id: 2, name: "产品手册下载量", pcs: 20023 },
-    { id: 3, name: "访客量", pcs: 13123 },
-    { id: 4, name: "线上展厅访问量", pcs: 16446 },
-    { id: 5, name: "导航区域访问量", pcs: 2134 },
-    { id: 6, name: "热点访问量", pcs: 6446 },
-  ]);
+  const { totalData } = useSelector((state: RootState) => state.A1Stat);
 
   return (
     <div className={styles.A1Stat}>
@@ -58,11 +57,11 @@ function A1Stat() {
       </div>
       {/* 统计主体 */}
       <div className="A1StatMain">
-        {data.map((v, i) => (
-          <div className='row' key={v.id}>
-            <div className={classNames('rowSon',`rowSon${i+1}`)}></div>
+        {totalData.map((v, i) => (
+          <div className="row" key={v.groupKey}>
+            <div className={classNames("rowSon", `rowSon${i + 1}`)}></div>
             <h3>{v.pcs}</h3>
-            <p>{v.name}</p>
+            <p>{v.groupKey}</p>
           </div>
         ))}
       </div>

+ 1 - 1
后台/src/pages/A2Gather/index.tsx

@@ -89,7 +89,7 @@ function A2Gather() {
   const deriveFu = useCallback(async () => {
     if (tableInfo.list.length === 0)
       return MessageFu.warning("当前搜索条件没有数据!");
-    const name = dayjs(new Date()).format("YYYYMMDDHHmmss");
+    const name = "收集问卷" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
 
     const res = await A2API_getListToXls({
       ...formData,

+ 1 - 0
后台/src/pages/A3Book/index.module.scss

@@ -12,6 +12,7 @@
       height: calc(100% - 65px);
       border: 1px solid #f0f0f0;
       border-radius: 6px;
+
       .ant-table-body {
         height: 605px;
         overflow-y: auto !important;

+ 1 - 1
后台/src/pages/A3Book/index.tsx

@@ -69,7 +69,7 @@ function A3Book() {
   const deriveFu = useCallback(async () => {
     if (tableInfo.list.length === 0)
       return MessageFu.warning("当前搜索条件没有数据!");
-    const name = dayjs(new Date()).format("YYYYMMDDHHmmss");
+      const name = "产品手册" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
 
     const res = await A3API_getListToXls({
       ...formData,

+ 26 - 3
后台/src/pages/A4Visit/index.module.scss

@@ -1,5 +1,28 @@
-.A4Visit{
-  :global{
-    
+.A4Visit {
+  padding: 20px 30px 0;
+
+  :global {
+    .searchBox {
+      display: flex;
+      justify-content: space-between;
+    }
+
+    .tableBox {
+      margin-top: 20px;
+      height: calc(100% - 65px);
+      border: 1px solid #f0f0f0;
+      border-radius: 6px;
+      .ant-table-body {
+        height: 605px;
+        overflow-y: auto !important;
+        overflow-y: overlay !important;
+
+        .ant-table-row {
+          .ant-table-cell {
+            padding: 10px;
+          }
+        }
+      }
+    }
   }
 }

+ 132 - 5
后台/src/pages/A4Visit/index.tsx

@@ -1,12 +1,139 @@
-import React from "react";
+import React, { useCallback, useEffect, useMemo, useState } from "react";
 import styles from "./index.module.scss";
- function A4Visit() {
-  
+import { Button, DatePicker, Table } from "antd";
+import dayjs from "dayjs";
+import { useDispatch, useSelector } from "react-redux";
+import ExportJsonExcel from "js-export-excel";
+import { RootState } from "@/store";
+import { MessageFu } from "@/utils/message";
+import { A4API_getList, A4API_getListToXls } from "@/store/action/A4Visit";
+const { RangePicker } = DatePicker;
+function A4Visit() {
+  const dispatch = useDispatch();
+
+  const [formData, setFormData] = useState({
+    startTime: dayjs().subtract(30, "day").format("YYYY-MM-DD") + " 00:00:00",
+    endTime: dayjs().format("YYYY-MM-DD") + " 23:59:59",
+    pageSize: 10,
+    pageNum: 1,
+  });
+
+  const getListFu = useCallback(() => {
+    // console.log("发送请求", formData);
+    dispatch(A4API_getList(formData));
+  }, [dispatch, formData]);
+
+  useEffect(() => {
+    getListFu();
+  }, [getListFu]);
+
+  // 时间选择器改变
+  const timeChange = useCallback(
+    (_: any, dateString: string[]) => {
+      let startTime = "";
+      let endTime = "";
+      if (dateString[0] && dateString[1]) {
+        startTime = dateString[0] + " 00:00:00";
+        endTime = dateString[1] + " 23:59:59";
+      }
+      setFormData({ ...formData, startTime, endTime });
+    },
+    [formData]
+  );
+
+  // 从仓库获取表格列表信息
+  const tableInfo = useSelector((state: RootState) => state.A4Visit.tableInfo);
+
+  const columns = useMemo(() => {
+    return [
+      {
+        title: "日期",
+        dataIndex: "groupKey",
+      },
+      {
+        title: "访客量",
+        dataIndex: "pcs",
+      },
+    ];
+  }, []);
+
+  // 页码变化
+  const paginationChange = useCallback(
+    () => (pageNum: number, pageSize: number) => {
+      setFormData({ ...formData, pageNum, pageSize });
+    },
+    [formData]
+  );
+
+  // 点击导出
+  const deriveFu = useCallback(async () => {
+    if (tableInfo.list.length === 0)
+      return MessageFu.warning("当前搜索条件没有数据!");
+      const name = "访客量" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
+
+    const res = await A4API_getListToXls({
+      ...formData,
+      pageNum: 1,
+      pageSize: 99999,
+    });
+
+    if (res.code === 0) {
+      const option = {
+        fileName: name,
+        datas: [
+          {
+            sheetData: res.data.records,
+            sheetName: name,
+            sheetFilter: ["groupKey", "pcs"],
+            sheetHeader: ["日期", "访客量"],
+            columnWidths: [10, 10],
+          },
+        ],
+      };
+
+      const toExcel = new ExportJsonExcel(option); //new
+      toExcel.saveExcel(); //保存
+    }
+  }, [formData, tableInfo.list]);
+
   return (
     <div className={styles.A4Visit}>
-      <h1>A4Visit</h1>
+      <div className="pageTitle">访客量</div>
+      {/* 日期选择框 */}
+      <div className="searchBox">
+        <RangePicker
+          style={{ width: 320 }}
+          defaultValue={[
+            dayjs(
+              dayjs().subtract(30, "day").format("YYYY-MM-DD"),
+              "YYYY-MM-DD"
+            ),
+            dayjs(dayjs().format("YYYY-MM-DD"), "YYYY-MM-DD"),
+          ]}
+          onChange={timeChange}
+        />
+        <Button onClick={deriveFu}>导出表格</Button>
+      </div>
+      {/* 表格主体 */}
+      <div className="tableBox">
+        <Table
+          scroll={{ y: 605 }}
+          dataSource={tableInfo.list}
+          columns={columns}
+          rowKey="groupKey"
+          pagination={{
+            showQuickJumper: true,
+            position: ["bottomCenter"],
+            showSizeChanger: true,
+            current: formData.pageNum,
+            pageSize: formData.pageSize,
+            total: tableInfo.total,
+            onChange: paginationChange(),
+          }}
+        />
+      </div>
     </div>
-  )
+  );
 }
 
 const MemoA4Visit = React.memo(A4Visit);

+ 26 - 3
后台/src/pages/A5Gallery/index.module.scss

@@ -1,5 +1,28 @@
-.A5Gallery{
-  :global{
-    
+.A5Gallery {
+  padding: 20px 30px 0;
+
+  :global {
+    .searchBox {
+      display: flex;
+      justify-content: space-between;
+    }
+
+    .tableBox {
+      margin-top: 20px;
+      height: calc(100% - 65px);
+      border: 1px solid #f0f0f0;
+      border-radius: 6px;
+      .ant-table-body {
+        height: 605px;
+        overflow-y: auto !important;
+        overflow-y: overlay !important;
+
+        .ant-table-row {
+          .ant-table-cell {
+            padding: 10px;
+          }
+        }
+      }
+    }
   }
 }

+ 134 - 5
后台/src/pages/A5Gallery/index.tsx

@@ -1,12 +1,141 @@
-import React from "react";
+import React, { useCallback, useEffect, useMemo, useState } from "react";
 import styles from "./index.module.scss";
- function A5Gallery() {
-  
+import { Button, DatePicker, Table } from "antd";
+import dayjs from "dayjs";
+import { useDispatch, useSelector } from "react-redux";
+import ExportJsonExcel from "js-export-excel";
+import { RootState } from "@/store";
+import { MessageFu } from "@/utils/message";
+import { A5API_getList, A5API_getListToXls } from "@/store/action/A5Gallery";
+const { RangePicker } = DatePicker;
+function A5Gallery() {
+  const dispatch = useDispatch();
+
+  const [formData, setFormData] = useState({
+    startTime: dayjs().subtract(30, "day").format("YYYY-MM-DD") + " 00:00:00",
+    endTime: dayjs().format("YYYY-MM-DD") + " 23:59:59",
+    pageSize: 10,
+    pageNum: 1,
+  });
+
+  const getListFu = useCallback(() => {
+    // console.log("发送请求", formData);
+    dispatch(A5API_getList(formData));
+  }, [dispatch, formData]);
+
+  useEffect(() => {
+    getListFu();
+  }, [getListFu]);
+
+  // 时间选择器改变
+  const timeChange = useCallback(
+    (_: any, dateString: string[]) => {
+      let startTime = "";
+      let endTime = "";
+      if (dateString[0] && dateString[1]) {
+        startTime = dateString[0] + " 00:00:00";
+        endTime = dateString[1] + " 23:59:59";
+      }
+      setFormData({ ...formData, startTime, endTime });
+    },
+    [formData]
+  );
+
+  // 从仓库获取表格列表信息
+  const tableInfo = useSelector(
+    (state: RootState) => state.A5Gallery.tableInfo
+  );
+
+  const columns = useMemo(() => {
+    return [
+      {
+        title: "日期",
+        dataIndex: "groupKey",
+      },
+      {
+        title: "访问量",
+        dataIndex: "pcs",
+      },
+    ];
+  }, []);
+
+  // 页码变化
+  const paginationChange = useCallback(
+    () => (pageNum: number, pageSize: number) => {
+      setFormData({ ...formData, pageNum, pageSize });
+    },
+    [formData]
+  );
+
+  // 点击导出
+  const deriveFu = useCallback(async () => {
+    if (tableInfo.list.length === 0)
+      return MessageFu.warning("当前搜索条件没有数据!");
+    const name = "线上展厅" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
+
+    const res = await A5API_getListToXls({
+      ...formData,
+      pageNum: 1,
+      pageSize: 99999,
+    });
+
+    if (res.code === 0) {
+      const option = {
+        fileName: name,
+        datas: [
+          {
+            sheetData: res.data.records,
+            sheetName: name,
+            sheetFilter: ["groupKey", "pcs"],
+            sheetHeader: ["日期", "访问量"],
+            columnWidths: [10, 10],
+          },
+        ],
+      };
+
+      const toExcel = new ExportJsonExcel(option); //new
+      toExcel.saveExcel(); //保存
+    }
+  }, [formData, tableInfo.list]);
+
   return (
     <div className={styles.A5Gallery}>
-      <h1>A5Gallery</h1>
+      <div className="pageTitle">线上展厅访问量</div>
+      {/* 日期选择框 */}
+      <div className="searchBox">
+        <RangePicker
+          style={{ width: 320 }}
+          defaultValue={[
+            dayjs(
+              dayjs().subtract(30, "day").format("YYYY-MM-DD"),
+              "YYYY-MM-DD"
+            ),
+            dayjs(dayjs().format("YYYY-MM-DD"), "YYYY-MM-DD"),
+          ]}
+          onChange={timeChange}
+        />
+        <Button onClick={deriveFu}>导出表格</Button>
+      </div>
+      {/* 表格主体 */}
+      <div className="tableBox">
+        <Table
+          scroll={{ y: 605 }}
+          dataSource={tableInfo.list}
+          columns={columns}
+          rowKey="groupKey"
+          pagination={{
+            showQuickJumper: true,
+            position: ["bottomCenter"],
+            showSizeChanger: true,
+            current: formData.pageNum,
+            pageSize: formData.pageSize,
+            total: tableInfo.total,
+            onChange: paginationChange(),
+          }}
+        />
+      </div>
     </div>
-  )
+  );
 }
 
 const MemoA5Gallery = React.memo(A5Gallery);

+ 27 - 3
后台/src/pages/A6Guide/index.module.scss

@@ -1,5 +1,29 @@
-.A6Guide{
-  :global{
-    
+.A6Guide {
+  padding: 20px 30px 0;
+
+  :global {
+    .searchBox {
+      display: flex;
+      justify-content: space-between;
+    }
+
+    .tableBox {
+      margin-top: 20px;
+      height: calc(100% - 65px);
+      border: 1px solid #f0f0f0;
+      border-radius: 6px;
+
+      .ant-table-body {
+        height: 580px;
+        overflow-y: auto !important;
+        overflow-y: overlay !important;
+
+        .ant-table-row {
+          .ant-table-cell {
+            padding: 10px;
+          }
+        }
+      }
+    }
   }
 }

+ 288 - 5
后台/src/pages/A6Guide/index.tsx

@@ -1,12 +1,295 @@
-import React from "react";
+import React, { useCallback, useEffect, useMemo, useState } from "react";
 import styles from "./index.module.scss";
- function A6Guide() {
-  
+import { Button, DatePicker, Table } from "antd";
+import dayjs from "dayjs";
+import { useDispatch, useSelector } from "react-redux";
+import ExportJsonExcel from "js-export-excel";
+import { RootState } from "@/store";
+import { MessageFu } from "@/utils/message";
+import { A6API_getList, A6API_getListToXls } from "@/store/action/A6Guide";
+import { A6TableType } from "@/types";
+const { RangePicker } = DatePicker;
+function A6Guide() {
+  const dispatch = useDispatch();
+
+  const [formData, setFormData] = useState({
+    startTime: dayjs().subtract(30, "day").format("YYYY-MM-DD") + " 00:00:00",
+    endTime: dayjs().format("YYYY-MM-DD") + " 23:59:59",
+    pageSize: 10,
+    pageNum: 1,
+  });
+
+  const getListFu = useCallback(() => {
+    // console.log("发送请求", formData);
+    dispatch(A6API_getList(formData));
+  }, [dispatch, formData]);
+
+  useEffect(() => {
+    getListFu();
+  }, [getListFu]);
+
+  // 时间选择器改变
+  const timeChange = useCallback(
+    (_: any, dateString: string[]) => {
+      let startTime = "";
+      let endTime = "";
+      if (dateString[0] && dateString[1]) {
+        startTime = dateString[0] + " 00:00:00";
+        endTime = dateString[1] + " 23:59:59";
+      }
+      setFormData({ ...formData, startTime, endTime });
+    },
+    [formData]
+  );
+
+  // 结算合计的函数
+  const resAllNumFu = useCallback((item: A6TableType) => {
+    let num = 0;
+    num =
+      item.speedMasterCx +
+      item.speedMasterXl +
+      item.speedMasterSx +
+      item.digitalFactory +
+      item.prinectCenter +
+      item.polarCuttingSystem +
+      item.stahlfolderKh +
+      item.versafireEp +
+      item.versafireEv +
+      item.suprasetter +
+      item.lifecycle +
+      item.training +
+      item.consultancy +
+      item.gallus +
+      item.financialService +
+      item.livestreamingRoom;
+    return num;
+  }, []);
+
+  // 从仓库获取表格列表信息
+  const tableInfo = useSelector((state: RootState) => state.A6Guide.tableInfo);
+
+  const columns = useMemo<any>(() => {
+    return [
+      {
+        title: "日期",
+        dataIndex: "today",
+        width: 100,
+        fixed: "left",
+      },
+      {
+        title: "合计",
+        width: 100,
+        fixed: "left",
+        render: (item: A6TableType) => resAllNumFu(item),
+      },
+      {
+        width: 150,
+        title: "Speedmaster CX 104-8+LYYL",
+        dataIndex: "speedMasterCx",
+      },
+      {
+        width: 150,
+        title: "Speedmaster XL 75-7+L",
+        dataIndex: "speedMasterXl",
+      },
+      {
+        width: 150,
+        title: "Speedmaster SX 102-4-P",
+        dataIndex: "speedMasterSx",
+      },
+      {
+        width: 150,
+        title: "Digital Factory",
+        dataIndex: "digitalFactory",
+      },
+      {
+        width: 150,
+        title: "Prinect Center",
+        dataIndex: "prinectCenter",
+      },
+      {
+        width: 150,
+        title: "Polar Cutting System 300",
+        dataIndex: "polarCuttingSystem",
+      },
+      {
+        width: 160,
+        title: "Stahlfolder KH 82-P",
+        dataIndex: "stahlfolderKh",
+      },
+      {
+        width: 150,
+        title: "Versafire EP",
+        dataIndex: "versafireEp",
+      },
+      {
+        width: 150,
+        title: "Versafire EV",
+        dataIndex: "versafireEv",
+      },
+      {
+        width: 150,
+        title: "Suprasetter 106",
+        dataIndex: "suprasetter",
+      },
+      {
+        width: 150,
+        title: "Lifecycle",
+        dataIndex: "lifecycle",
+      },
+      {
+        width: 150,
+        title: "Training",
+        dataIndex: "training",
+      },
+      {
+        width: 150,
+        title: "Consultancy",
+        dataIndex: "consultancy",
+      },
+      {
+        width: 150,
+        title: "Gallus",
+        dataIndex: "gallus",
+      },
+      {
+        width: 150,
+        title: "Financial Service",
+        dataIndex: "financialService",
+      },
+      {
+        width: 150,
+        title: "Livestreaming Room",
+        dataIndex: "livestreamingRoom",
+      },
+    ];
+  }, [resAllNumFu]);
+
+  // 页码变化
+  const paginationChange = useCallback(
+    () => (pageNum: number, pageSize: number) => {
+      setFormData({ ...formData, pageNum, pageSize });
+    },
+    [formData]
+  );
+
+  // 点击导出
+  const deriveFu = useCallback(async () => {
+    if (tableInfo.list.length === 0)
+      return MessageFu.warning("当前搜索条件没有数据!");
+    const name = "导航区域" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
+
+    const res = await A6API_getListToXls({
+      ...formData,
+      pageNum: 1,
+      pageSize: 99999,
+    });
+
+    if (res.code === 0) {
+      const sheetData = res.data.records.map((v: A6TableType) => {
+        return {
+          ...v,
+          all: resAllNumFu(v),
+        };
+      });
+
+      const option = {
+        fileName: name,
+        datas: [
+          {
+            sheetData,
+            sheetName: name,
+            sheetFilter: [
+              "today",
+              "all",
+              "speedMasterCx",
+              "speedMasterXl",
+              "speedMasterSx",
+              "digitalFactory",
+              "prinectCenter",
+              "polarCuttingSystem",
+              "stahlfolderKh",
+              "versafireEp",
+              "versafireEv",
+              "suprasetter",
+              "lifecycle",
+              "training",
+              "consultancy",
+              "gallus",
+              "financialService",
+              "livestreamingRoom",
+            ],
+            sheetHeader: [
+              "日期",
+              "合计",
+              "Speedmaster CX 104-8+LYYL",
+              "Speedmaster XL 75-7+L",
+              "Speedmaster SX 102-4-P",
+              "Digital Factory",
+              "Prinect Center",
+              "Polar Cutting System 300",
+              "Stahlfolder KH 82-P",
+              "Versafire EP",
+              "Versafire EV",
+              "Suprasetter 106",
+              "Lifecycle",
+              "Training",
+              "Consultancy",
+              "Gallus",
+              "Financial Service",
+              "Livestreaming Room",
+            ],
+            columnWidths: [
+              10, 4, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10,
+              10,
+            ],
+          },
+        ],
+      };
+
+      const toExcel = new ExportJsonExcel(option); //new
+      toExcel.saveExcel(); //保存
+    }
+  }, [formData, resAllNumFu, tableInfo.list.length]);
+
   return (
     <div className={styles.A6Guide}>
-      <h1>A6Guide</h1>
+      <div className="pageTitle">导航区域访问量</div>
+      {/* 日期选择框 */}
+      <div className="searchBox">
+        <RangePicker
+          style={{ width: 320 }}
+          defaultValue={[
+            dayjs(
+              dayjs().subtract(30, "day").format("YYYY-MM-DD"),
+              "YYYY-MM-DD"
+            ),
+            dayjs(dayjs().format("YYYY-MM-DD"), "YYYY-MM-DD"),
+          ]}
+          onChange={timeChange}
+        />
+        <Button onClick={deriveFu}>导出表格</Button>
+      </div>
+      {/* 表格主体 */}
+      <div className="tableBox">
+        <Table
+          scroll={{ y: 580, x: 1000 }}
+          dataSource={tableInfo.list}
+          columns={columns}
+          rowKey="id"
+          pagination={{
+            showQuickJumper: true,
+            position: ["bottomCenter"],
+            showSizeChanger: true,
+            current: formData.pageNum,
+            pageSize: formData.pageSize,
+            total: tableInfo.total,
+            onChange: paginationChange(),
+          }}
+        />
+      </div>
     </div>
-  )
+  );
 }
 
 const MemoA6Guide = React.memo(A6Guide);

+ 26 - 3
后台/src/pages/A7Hotspot/index.module.scss

@@ -1,5 +1,28 @@
-.A7Hotspot{
-  :global{
-    
+.A7Hotspot {
+  padding: 20px 30px 0;
+
+  :global {
+    .searchBox {
+      display: flex;
+      justify-content: space-between;
+    }
+
+    .tableBox {
+      margin-top: 20px;
+      height: calc(100% - 65px);
+      border: 1px solid #f0f0f0;
+      border-radius: 6px;
+      .ant-table-body {
+        height: 605px;
+        overflow-y: auto !important;
+        overflow-y: overlay !important;
+
+        .ant-table-row {
+          .ant-table-cell {
+            padding: 10px;
+          }
+        }
+      }
+    }
   }
 }

+ 134 - 5
后台/src/pages/A7Hotspot/index.tsx

@@ -1,12 +1,141 @@
-import React from "react";
+import React, { useCallback, useEffect, useMemo, useState } from "react";
 import styles from "./index.module.scss";
- function A7Hotspot() {
-  
+import { Button, DatePicker, Table } from "antd";
+import dayjs from "dayjs";
+import { useDispatch, useSelector } from "react-redux";
+import ExportJsonExcel from "js-export-excel";
+import { RootState } from "@/store";
+import { MessageFu } from "@/utils/message";
+import { A7API_getList, A7API_getListToXls } from "@/store/action/A7Hotspot";
+const { RangePicker } = DatePicker;
+function A7Hotspot() {
+  const dispatch = useDispatch();
+
+  const [formData, setFormData] = useState({
+    startTime: dayjs().subtract(30, "day").format("YYYY-MM-DD") + " 00:00:00",
+    endTime: dayjs().format("YYYY-MM-DD") + " 23:59:59",
+    pageSize: 10,
+    pageNum: 1,
+  });
+
+  const getListFu = useCallback(() => {
+    // console.log("发送请求", formData);
+    dispatch(A7API_getList(formData));
+  }, [dispatch, formData]);
+
+  useEffect(() => {
+    getListFu();
+  }, [getListFu]);
+
+  // 时间选择器改变
+  const timeChange = useCallback(
+    (_: any, dateString: string[]) => {
+      let startTime = "";
+      let endTime = "";
+      if (dateString[0] && dateString[1]) {
+        startTime = dateString[0] + " 00:00:00";
+        endTime = dateString[1] + " 23:59:59";
+      }
+      setFormData({ ...formData, startTime, endTime });
+    },
+    [formData]
+  );
+
+  // 从仓库获取表格列表信息
+  const tableInfo = useSelector(
+    (state: RootState) => state.A7Hotspot.tableInfo
+  );
+
+  const columns = useMemo(() => {
+    return [
+      {
+        title: "日期",
+        dataIndex: "groupKey",
+      },
+      {
+        title: "访问量",
+        dataIndex: "pcs",
+      },
+    ];
+  }, []);
+
+  // 页码变化
+  const paginationChange = useCallback(
+    () => (pageNum: number, pageSize: number) => {
+      setFormData({ ...formData, pageNum, pageSize });
+    },
+    [formData]
+  );
+
+  // 点击导出
+  const deriveFu = useCallback(async () => {
+    if (tableInfo.list.length === 0)
+      return MessageFu.warning("当前搜索条件没有数据!");
+    const name = "热点" + dayjs(new Date()).format("YYYY-MM-DD HH:mm");
+
+    const res = await A7API_getListToXls({
+      ...formData,
+      pageNum: 1,
+      pageSize: 99999,
+    });
+
+    if (res.code === 0) {
+      const option = {
+        fileName: name,
+        datas: [
+          {
+            sheetData: res.data.records,
+            sheetName: name,
+            sheetFilter: ["groupKey", "pcs"],
+            sheetHeader: ["日期", "访问量"],
+            columnWidths: [10, 10],
+          },
+        ],
+      };
+
+      const toExcel = new ExportJsonExcel(option); //new
+      toExcel.saveExcel(); //保存
+    }
+  }, [formData, tableInfo.list]);
+
   return (
     <div className={styles.A7Hotspot}>
-      <h1>A7Hotspot</h1>
+      <div className="pageTitle">线上展厅访问量</div>
+      {/* 日期选择框 */}
+      <div className="searchBox">
+        <RangePicker
+          style={{ width: 320 }}
+          defaultValue={[
+            dayjs(
+              dayjs().subtract(30, "day").format("YYYY-MM-DD"),
+              "YYYY-MM-DD"
+            ),
+            dayjs(dayjs().format("YYYY-MM-DD"), "YYYY-MM-DD"),
+          ]}
+          onChange={timeChange}
+        />
+        <Button onClick={deriveFu}>导出表格</Button>
+      </div>
+      {/* 表格主体 */}
+      <div className="tableBox">
+        <Table
+          scroll={{ y: 605 }}
+          dataSource={tableInfo.list}
+          columns={columns}
+          rowKey="groupKey"
+          pagination={{
+            showQuickJumper: true,
+            position: ["bottomCenter"],
+            showSizeChanger: true,
+            current: formData.pageNum,
+            pageSize: formData.pageSize,
+            total: tableInfo.total,
+            onChange: paginationChange(),
+          }}
+        />
+      </div>
     </div>
-  )
+  );
 }
 
 const MemoA7Hotspot = React.memo(A7Hotspot);

+ 1 - 1
后台/src/pages/Layout/index.tsx

@@ -45,7 +45,7 @@ function Layout() {
       },
       {
         id: 400,
-        name: "访量",
+        name: "访量",
         path: "/visit",
         Com: React.lazy(() => import("../A4Visit")),
       },

+ 24 - 3
后台/src/store/action/A1Stat.ts

@@ -1,9 +1,30 @@
 import http from "@/utils/http";
-// import { AppDispatch } from "..";
+import { AppDispatch } from "..";
+import { A1TotalDataType } from "@/types";
+import { A1DataChangeObj } from "@/utils/dataChange";
 
 /**
  * 获取统计看板
  */
-export const A1getNumInfoAPI = (data: any) => {
-  return http.post("admin/login", { ...data });
+
+export const A1API_getNumList = (data: any) => {
+  return async (dispatch: AppDispatch) => {
+    const res = await http.post("cms/report/total", data);
+    // console.log(123, res);
+
+    const arr: A1TotalDataType[] = [];
+    for (const k in res.data) {
+      arr.push({
+        groupKey: Reflect.get(A1DataChangeObj, k),
+        pcs: Reflect.get(res.data, k),
+      });
+    }
+
+    if (res.code === 0) {
+      dispatch({
+        type: "stat/getData",
+        payload: arr,
+      });
+    }
+  };
 };

+ 24 - 0
后台/src/store/action/A4Visit.ts

@@ -0,0 +1,24 @@
+import http from "@/utils/http";
+import { AppDispatch } from "..";
+
+/**
+ * 访客量列表-页面显示
+ */
+export const A4API_getList = (data: any) => {
+  return async (dispatch: AppDispatch) => {
+    const res = await http.post("cms/report/user/pageList", data);
+    if (res.code === 0) {
+      dispatch({
+        type: "visit/getList",
+        payload: { list: res.data.records, total: res.data.total },
+      });
+    }
+  };
+};
+
+/**
+ * 访客量列表-导出表格
+ */
+export const A4API_getListToXls = (data: any) => {
+  return http.post("cms/report/user/pageList", data);
+};

+ 24 - 0
后台/src/store/action/A5Gallery.ts

@@ -0,0 +1,24 @@
+import http from "@/utils/http";
+import { AppDispatch } from "..";
+
+/**
+ * 线上展厅访问量列表-页面显示
+ */
+export const A5API_getList = (data: any) => {
+  return async (dispatch: AppDispatch) => {
+    const res = await http.post("cms/report/scene/pageList", data);
+    if (res.code === 0) {
+      dispatch({
+        type: "gallery/getList",
+        payload: { list: res.data.records, total: res.data.total },
+      });
+    }
+  };
+};
+
+/**
+ * 线上展厅访问量列表-导出表格
+ */
+export const A5API_getListToXls = (data: any) => {
+  return http.post("cms/report/scene/pageList", data);
+};

+ 24 - 0
后台/src/store/action/A6Guide.ts

@@ -0,0 +1,24 @@
+import http from "@/utils/http";
+import { AppDispatch } from "..";
+
+/**
+ * 导航区域列表-页面显示
+ */
+export const A6API_getList = (data: any) => {
+  return async (dispatch: AppDispatch) => {
+    const res = await http.post("cms/report/zone/pageList", data);
+    if (res.code === 0) {
+      dispatch({
+        type: "guide/getList",
+        payload: { list: res.data.records, total: res.data.total },
+      });
+    }
+  };
+};
+
+/**
+ * 导航区域列表-导出表格
+ */
+export const A6API_getListToXls = (data: any) => {
+  return http.post("cms/report/zone/pageList", data);
+};

+ 24 - 0
后台/src/store/action/A7Hotspot.ts

@@ -0,0 +1,24 @@
+import http from "@/utils/http";
+import { AppDispatch } from "..";
+
+/**
+ * 导航区域列表-页面显示
+ */
+export const A7API_getList = (data: any) => {
+  return async (dispatch: AppDispatch) => {
+    const res = await http.post("cms/report/hot/pageList", data);
+    if (res.code === 0) {
+      dispatch({
+        type: 'hotspot/getList',
+        payload: { list: res.data.records, total: res.data.total },
+      });
+    }
+  };
+};
+
+/**
+ * 导航区域列表-导出表格
+ */
+export const A7API_getListToXls = (data: any) => {
+  return http.post("cms/report/hot/pageList", data);
+};

+ 24 - 0
后台/src/store/reducer/A1Stat.ts

@@ -0,0 +1,24 @@
+import { A1TotalDataType } from "@/types";
+
+// 初始化状态
+const initState = {
+  // 总访问量
+  totalData: [] as A1TotalDataType[],
+};
+
+// 定义 action 类型
+type Props = {
+  type: "stat/getData";
+  payload: A1TotalDataType[];
+};
+
+// 频道 reducer
+export default function reducerFu(state = initState, action: Props) {
+  switch (action.type) {
+    // 获取总访问量
+    case "stat/getData":
+      return { ...state, totalData: action.payload };
+    default:
+      return state;
+  }
+}

+ 1 - 1
后台/src/store/reducer/A2Gather.ts

@@ -16,7 +16,7 @@ type Props = {
 };
 
 // 频道 reducer
-export default function gatherReducer(state = initState, action: Props) {
+export default function reducerFu(state = initState, action: Props) {
   switch (action.type) {
     // 获取列表数据
     case "gather/getList":

+ 1 - 1
后台/src/store/reducer/A3Book.ts

@@ -1,4 +1,4 @@
-import { A3TableType } from "@/types/api/A3Book";
+import { A3TableType } from "@/types";
 
 // 初始化状态
 const initState = {

+ 27 - 0
后台/src/store/reducer/A4Visit.ts

@@ -0,0 +1,27 @@
+import { A3TableType } from "@/types";
+
+// 初始化状态
+const initState = {
+  // 列表数据
+  tableInfo: {
+    list: [] as A3TableType[],
+    total: 0,
+  },
+};
+
+// 定义 action 类型
+type Props = {
+  type: "visit/getList";
+  payload: { list: A3TableType[]; total: number };
+};
+
+// 频道 reducer
+export default function reducerFu(state = initState, action: Props) {
+  switch (action.type) {
+    // 获取列表数据
+    case "visit/getList":
+      return { ...state, tableInfo: action.payload };
+    default:
+      return state;
+  }
+}

+ 27 - 0
后台/src/store/reducer/A5Gallery.ts

@@ -0,0 +1,27 @@
+import { A3TableType } from "@/types";
+
+// 初始化状态
+const initState = {
+  // 列表数据
+  tableInfo: {
+    list: [] as A3TableType[],
+    total: 0,
+  },
+};
+
+// 定义 action 类型
+type Props = {
+  type: "gallery/getList";
+  payload: { list: A3TableType[]; total: number };
+};
+
+// 频道 reducer
+export default function reducerFu(state = initState, action: Props) {
+  switch (action.type) {
+    // 获取列表数据
+    case "gallery/getList":
+      return { ...state, tableInfo: action.payload };
+    default:
+      return state;
+  }
+}

+ 27 - 0
后台/src/store/reducer/A6Guide.ts

@@ -0,0 +1,27 @@
+import { A6TableType } from "@/types";
+
+// 初始化状态
+const initState = {
+  // 列表数据
+  tableInfo: {
+    list: [] as A6TableType[],
+    total: 0,
+  },
+};
+
+// 定义 action 类型
+type Props = {
+  type: "guide/getList";
+  payload: { list: A6TableType[]; total: number };
+};
+
+// 频道 reducer
+export default function reducerFu(state = initState, action: Props) {
+  switch (action.type) {
+    // 获取列表数据
+    case "guide/getList":
+      return { ...state, tableInfo: action.payload };
+    default:
+      return state;
+  }
+}

+ 27 - 0
后台/src/store/reducer/A7Hotspot.ts

@@ -0,0 +1,27 @@
+import { A3TableType } from "@/types";
+
+// 初始化状态
+const initState = {
+  // 列表数据
+  tableInfo: {
+    list: [] as A3TableType[],
+    total: 0,
+  },
+};
+
+// 定义 action 类型
+type Props = {
+  type: "hotspot/getList";
+  payload: { list: A3TableType[]; total: number };
+};
+
+// 频道 reducer
+export default function reducerFu(state = initState, action: Props) {
+  switch (action.type) {
+    // 获取列表数据
+    case "hotspot/getList":
+      return { ...state, tableInfo: action.payload };
+    default:
+      return state;
+  }
+}

+ 10 - 0
后台/src/store/reducer/index.ts

@@ -1,14 +1,24 @@
 import { combineReducers } from "redux";
 
 import A0layout from "./layout";
+import A1Stat from "./A1Stat";
 import A2Gather from "./A2Gather";
 import A3Book from "./A3Book";
+import A4Visit from "./A4Visit";
+import A5Gallery from "./A5Gallery";
+import A6Guide from "./A6Guide";
+import A7Hotspot from "./A7Hotspot";
 
 // 合并 reducer
 const rootReducer = combineReducers({
   A0layout,
+  A1Stat,
   A2Gather,
   A3Book,
+  A4Visit,
+  A5Gallery,
+  A6Guide,
+  A7Hotspot,
 });
 
 // 默认导出

+ 4 - 0
后台/src/types/api/A1Stat.d.ts

@@ -0,0 +1,4 @@
+export type A1TotalDataType ={
+  pcs:number
+  groupKey:string
+}

+ 1 - 0
后台/src/types/api/A3Book.d.ts

@@ -1,4 +1,5 @@
 export type A3TableType ={
+  id:number
   name:string
   pcs:number
 }

+ 25 - 0
后台/src/types/api/A6Guide.d.ts

@@ -0,0 +1,25 @@
+export type A6TableType =  {
+	consultancy: number;
+	createTime: string;
+	creatorId?: any;
+	creatorName: string;
+	digitalFactory: number;
+	financialService: number;
+	gallus: number;
+	id: number;
+	lifecycle: number;
+	livestreamingRoom: number;
+	polarCuttingSystem: number;
+	prinectCenter: number;
+	speedMasterCx: number;
+	speedMasterSx: number;
+	speedMasterXl: number;
+	stahlfolderKh: number;
+	suprasetter: number;
+	today: string;
+	training: number;
+	updateTime: string;
+	versafireEp: number;
+	versafireEv: number;
+	all?:number
+}

+ 3 - 1
后台/src/types/index.d.ts

@@ -1,3 +1,5 @@
+export * from './api/A1Stat'
 export * from './api/A2Gather'
-export * from './api/A2Gather'
+export * from './api/A3Book'
+export * from './api/A6Guide'
 

+ 8 - 0
后台/src/utils/dataChange.ts

@@ -0,0 +1,8 @@
+export const A1DataChangeObj ={
+  'visit_hot':'热点访问量',
+  'visit_product':'产品手册下载量',
+  'visit_questionnaire':'收集问卷',
+  'visit_scene':'线上展厅访问量',
+  'visit_user':'访客量',
+  'visit_zone':'导航区域访问量',
+}