Переглянути джерело

Merge branch 'feature/大屏2' into dev

@dayan_hjm 2 роки тому
батько
коміт
6b0b2a9533

+ 15 - 0
config/webpack.common.js

@@ -81,6 +81,21 @@ module.exports = {
81 81
         ],
82 82
       },
83 83
       {
84
+        test: /* 匹配文件 */ /\.gif/,
85
+        include: [path.resolve(__dirname, "../node_modules")],
86
+        use: /* 使用loader */[{
87
+          loader: "url-loader",
88
+          options: /* 加载器相关的配置项 */ {
89
+            name: 'static/[name].[ext]',
90
+            limit: /* <=limit的图片转换成base64 */ 8196,
91
+            mimetype: "gif",
92
+            fallback: 'file-loader',
93
+            publicPath: '../../' //采用根路径
94
+          },
95
+        },
96
+        ],
97
+      },
98
+      {
84 99
         test: /* 匹配文件 */ /\.svg/,
85 100
         include: [path.resolve(__dirname, "../src")],
86 101
         use: /* 使用loader */[{

+ 2 - 0
package.json

@@ -56,12 +56,14 @@
56 56
     "echarts-wordcloud": "2.0.0",
57 57
     "es6-symbol": "^3.1.3",
58 58
     "eslint": "^7.25.0",
59
+    "slick-carousel": "^1.8.1",
59 60
     "eslint-config-prettier": "^8.3.0",
60 61
     "eslint-plugin-react": "^7.23.2",
61 62
     "express-mock-server": "^3.2.0",
62 63
     "extract-text-webpack-plugin": "^4.0.0-beta.0",
63 64
     "file-loader": "^6.2.0",
64 65
     "happypack": "^5.0.1",
66
+    "react-slick": "^0.29.0",
65 67
     "html-webpack-plugin": "^4.2.2",
66 68
     "http-server": "^0.12.3",
67 69
     "husky": "^6.0.0",

BIN
public/favicon.ico


+ 1 - 0
src/App/index.less

@@ -1101,6 +1101,7 @@ li[role="menuitem"] {
1101 1101
 
1102 1102
           .item_c {
1103 1103
             width: 90px;
1104
+            //溢出隐藏
1104 1105
             overflow: hidden;
1105 1106
             text-overflow: ellipsis;
1106 1107
             white-space: nowrap;

+ 14 - 7
src/assets/css/styleTemplate.less

@@ -2,7 +2,7 @@
2 2
  * @Author: dayan_hjm 茶百道主题样式
3 3
  * @Date: 2022-10-27 10:56:37 
4 4
  * @Last Modified by: dayan_hjm
5
- * @Last Modified time: 2023-11-08 17:15:55
5
+ * @Last Modified time: 2023-11-21 17:43:56
6 6
  */
7 7
 
8 8
 @import url("../../themes/themes.less");
@@ -268,6 +268,7 @@
268 268
         color: #fff;
269 269
         margin: 0;
270 270
         font-size: 30px;
271
+
271 272
       }
272 273
     }
273 274
 
@@ -349,8 +350,8 @@
349 350
       position: absolute;
350 351
       left: 0;
351 352
       top: 0;
352
-      width: 100%;
353
-      background: url(../imgs/dataVimg/homeBgDataV.png) no-repeat 0 -10em / 100% 120% #041b40;
353
+      width: 98.5%;
354
+      background: url(../imgs/dataVimg/homeBgDataV.png) no-repeat 0 -10em / 108% 120% #041b40;
354 355
       height: 100%;
355 356
       display: flex;
356 357
       align-items: center;
@@ -553,7 +554,7 @@
553 554
 
554 555
         .bottomContent2 {
555 556
           width: 100%;
556
-          height: 42%;
557
+          height: 28%;
557 558
         }
558 559
 
559 560
         .bottomContent {
@@ -597,7 +598,7 @@
597 598
 
598 599
       .rightContent .bottomContent2 {
599 600
         width: 100%;
600
-        height: 28%;
601
+        height: 100%;
601 602
       }
602 603
 
603 604
       .rightContent .bottomContent {
@@ -1145,7 +1146,7 @@
1145 1146
   .cbRightBottomView {
1146 1147
     flex-wrap: wrap;
1147 1148
     position: relative;
1148
-
1149
+    
1149 1150
     .right_b_tip2 {
1150 1151
       width: 46%;
1151 1152
       display: block;
@@ -1166,7 +1167,13 @@
1166 1167
       text-align: right;
1167 1168
     }
1168 1169
   }
1169
-
1170
+.slider_item_box{
1171
+  justify-content: left;
1172
+  .slick-slider{
1173
+    width: 90%;
1174
+    color: #fff;
1175
+  }
1176
+}
1170 1177
   .testDiv {
1171 1178
     width: 4em;
1172 1179
     display: flex;

BIN
src/assets/imgs/gvc/homeBgDataV.png


BIN
src/assets/imgs/gvc/qiu1.png


BIN
src/assets/imgs/gvc/qiu2.png


BIN
src/assets/imgs/gvc/qiu3.png


BIN
src/assets/imgs/gvc/qiu4.png


BIN
src/assets/imgs/gvc/qiuH1.png


BIN
src/assets/imgs/gvc/qiuH2.png


BIN
src/assets/imgs/gvc/qiuH3.png


BIN
src/assets/imgs/gvc/qiuH4.png


BIN
src/assets/imgs/gvc/video1.mp4


BIN
src/assets/imgs/gvc/video2.mp4


+ 98 - 0
src/components/SimpleSlider/index.js

@@ -0,0 +1,98 @@
1
+/*
2
+ * @Author: dayan_hjm 轮播图滑动组件
3
+    settings:{
4
+        title:true,//是否开启移上title展示
5
+        clickUrl:true,//是否开启点击转跳功能
6
+        type 1=茶百道  2=雅居乐
7
+        dots: true,//是否显示小圆点索引
8
+        autoplay: true,//是否自动播放
9
+        infinite: true,//是否无限循环
10
+        autoplaySpeed: 2000,//自动播放的时间
11
+        fade: true,//是否采用淡入淡出的效果
12
+        slidesToShow: 2,一行显示多少个
13
+        slidesPerRow:1,//行显示多少个
14
+          slidesToScroll: 5 //每次滚动多少个元素
15
+    }
16
+    //dataArr 轮播的数据
17
+ * @Date: 2023-03-24 15:32:00 
18
+ * @Last Modified by: dayan_hjm
19
+ * @Last Modified time: 2023-08-17 14:19:43
20
+ */
21
+import utils from "@utils/index";
22
+import { crossMenuClick } from "@utils/util";
23
+import $store from "@store/";
24
+import React, { useState, useEffect, Component } from "react";
25
+import Slider from "react-slick";
26
+import "slick-carousel/slick/slick.css"; 
27
+import "slick-carousel/slick/slick-theme.css";
28
+// import "./slick.css";
29
+// import "./slick-theme.css";
30
+import { Tooltip } from "antd";
31
+
32
+function SimpleSlider(props) {
33
+    const settings = props.settings
34
+    const data_ = props.dataArr && props.dataArr instanceof Array ? props.dataArr : [
35
+        // {
36
+        //     backGroupPicUrl:"http://14.29.205.92:9081/static/bg_sChaBaiDao@2x.png"
37
+        // },
38
+        // {
39
+        //     backGroupPicUrl:"http://14.29.205.92:9081/static/bg2.png"
40
+        // },
41
+    ];
42
+    return (
43
+        <div className='swiper-content'>
44
+            <Slider {...settings} className="swiper-container">
45
+                {
46
+                    settings.type == 1 ? data_.map(url => {
47
+                        return <div className="swiper-div" style={{ cursor: settings.clickUrl && url.redirectUrl ? "pointer" : "auto" }} onClick={() => {
48
+                            // url.redirectUrl = "http://localhost:9003/transfer.html#/home/menu"
49
+                            if (!settings.clickUrl) { return }
50
+                            if (url.redirectUrl) {
51
+                                let newUrl = url.redirectUrl.replace(window.location.origin + window.location.pathname, "");
52
+                                newUrl = newUrl.replace("?ticket=&ssoEmpId=", "");
53
+                                newUrl = newUrl.replace("#", "");
54
+                                props.sliceClick(newUrl);
55
+                            }
56
+                        }}>
57
+                            <Tooltip title={settings.title ? url.alias : ""} placement="right">
58
+                            <img src={url.backGroupPicUrl || require("@assets/imgs/login/yunXiBg.png").default} style={{ width: "90%" }} />
59
+                            </Tooltip>
60
+                        </div> 
61
+                    }) : data_.map((card,index) => {
62
+                        let activeTree = utils.findNodeTree([...$store.sysMenu.norList, ...$store.sysMenu.menuList], card.positive, "resourceUrl");
63
+                        if(activeTree){card.has_positive = card.positive}else{card.has_positive = ''};
64
+                        console.log('dy-------',card.has_positive)
65
+                        return (
66
+                            <div className={`nor_card ${card.has_positive ? 'cur' : ''}` } onClick={()=>{
67
+                                if(!card.has_positive){return}
68
+                                let activeTree = utils.findNodeTree([...$store.sysMenu.norList, ...$store.sysMenu.menuList], card.has_positive, "resourceUrl");
69
+                                if(activeTree){
70
+                                    let activeTreeF = utils.findNodeTree([...$store.sysMenu.norList, ...$store.sysMenu.menuList], activeTree.parentId, "resourceId");
71
+                                    crossMenuClick(activeTreeF.resourceUrl, activeTree.resourceUrl, ((res) => {
72
+                                        props.history.push(res);
73
+                                      }))
74
+                                }
75
+                            }}>
76
+                                {/* <Tooltipplacement="right" defaultVisible="true"> */}
77
+                                    <img src={card.moveDownPicUrl || require(`@assets/imgs/home/agileHome${index + 1}.png`).default} width="95%" className="showImg" />
78
+                                    <img
79
+                                        className="tips_img hideimg"
80
+                                        src={card.has_positive ?card.moveDownPicUrl :(card.moveUpPicUrl || require(`@assets/imgs/home/agileHome6.png`).default)}
81
+                                        width="95%"
82
+                                    />
83
+                                    {
84
+                                        settings.title && card.alias ? <span class="tipsBox">{card.alias}</span> : null
85
+                                    }
86
+                                {/* </Tooltip> */}
87
+                            </div>
88
+                        )
89
+                    })
90
+                }
91
+            </Slider>
92
+            <img src={require("@assets/imgs/login/bg1.png").default} style={{ display: "none" }} />
93
+            <img src={require("@assets/imgs/login/bg2.png").default} style={{ display: "none" }} />
94
+            <img src={require("@assets/imgs/login/bg3.png").default} style={{ display: "none" }} />
95
+        </div>
96
+    )
97
+}
98
+export default SimpleSlider;

+ 165 - 0
src/components/SimpleSlider/slick-theme.css

@@ -0,0 +1,165 @@
1
+@charset 'UTF-8';
2
+
3
+.slick-dots,
4
+.slick-next,
5
+.slick-prev {
6
+    position: absolute;
7
+    display: block;
8
+    padding: 0
9
+}
10
+
11
+.slick-dots li button:before,
12
+.slick-next:before,
13
+.slick-prev:before {
14
+    font-family: slick;
15
+    -webkit-font-smoothing: antialiased;
16
+    -moz-osx-font-smoothing: grayscale
17
+}
18
+
19
+.slick-loading .slick-list {
20
+    background: yellow
21
+}
22
+
23
+.slick-next,
24
+.slick-prev {
25
+    font-size: 0;
26
+    line-height: 0;
27
+    top: 50%;
28
+    width: 20px;
29
+    height: 20px;
30
+    -webkit-transform: translate(0, -50%);
31
+    -ms-transform: translate(0, -50%);
32
+    transform: translate(0, -50%);
33
+    cursor: pointer;
34
+    color: transparent;
35
+    border: none;
36
+    outline: 0;
37
+    background: 0 0
38
+}
39
+
40
+.slick-next:focus,
41
+.slick-next:hover,
42
+.slick-prev:focus,
43
+.slick-prev:hover {
44
+    color: transparent;
45
+    outline: 0;
46
+    background: 0 0
47
+}
48
+
49
+.slick-next:focus:before,
50
+.slick-next:hover:before,
51
+.slick-prev:focus:before,
52
+.slick-prev:hover:before {
53
+    opacity: 1
54
+}
55
+
56
+.slick-next.slick-disabled:before,
57
+.slick-prev.slick-disabled:before {
58
+    opacity: .25
59
+}
60
+
61
+.slick-next:before,
62
+.slick-prev:before {
63
+    font-size: 20px;
64
+    line-height: 1;
65
+    opacity: .75;
66
+    color: #fff
67
+}
68
+
69
+.slick-prev {
70
+    left: -25px
71
+}
72
+
73
+[dir=rtl] .slick-prev {
74
+    right: -25px;
75
+    left: auto
76
+}
77
+
78
+.slick-prev:before {
79
+    content: '←'
80
+}
81
+
82
+.slick-next:before,
83
+[dir=rtl] .slick-prev:before {
84
+    content: '→'
85
+}
86
+
87
+.slick-next {
88
+    right: -25px
89
+}
90
+
91
+[dir=rtl] .slick-next {
92
+    right: auto;
93
+    left: -25px
94
+}
95
+
96
+[dir=rtl] .slick-next:before {
97
+    content: '←'
98
+}
99
+
100
+.slick-dotted.slick-slider {
101
+    margin-bottom: 30px
102
+}
103
+
104
+.slick-dots {
105
+    bottom:-18px;
106
+    width: 100%;
107
+    margin: 0;
108
+    list-style: none;
109
+    text-align: center
110
+}
111
+
112
+.slick-dots li {
113
+    position: relative;
114
+    display: inline-block;
115
+    width: 20px;
116
+    height: 20px;
117
+    margin: 0 5px;
118
+    padding: 0;
119
+    cursor: pointer
120
+}
121
+
122
+.slick-dots li button {
123
+    font-size: 0;
124
+    line-height: 0;
125
+    display: block;
126
+    width: 20px;
127
+    height: 20px;
128
+    padding: 5px;
129
+    cursor: pointer;
130
+    color: transparent;
131
+    border: 0;
132
+    outline: 0;
133
+    background: 0 0
134
+}
135
+
136
+.slick-dots li button:focus,
137
+.slick-dots li button:hover {
138
+    outline: 0
139
+}
140
+
141
+.slick-dots li button:focus:before,
142
+.slick-dots li button:hover:before {
143
+    opacity: 1
144
+}
145
+
146
+.slick-dots li button:before {
147
+    font-size: 13px;
148
+    line-height: 20px;
149
+    position: absolute;
150
+    top: 0;
151
+    left: 0;
152
+    width: 20px;
153
+    height: 20px;
154
+    content: '•';
155
+    text-align: center;
156
+    opacity: .25;
157
+    color: #000
158
+}
159
+
160
+.slick-dots li.slick-active button:before {
161
+    opacity: .75;
162
+    color: #000
163
+}
164
+
165
+/*# sourceMappingURL=slick-theme.min.css.map */

+ 112 - 0
src/components/SimpleSlider/slick.css

@@ -0,0 +1,112 @@
1
+.swiper-content{
2
+    width:100%;
3
+    height: calc(100% - 56px);
4
+}
5
+.swiper-div{
6
+    height: 100%;
7
+    overflow: hidden; 
8
+}
9
+.slick-list,
10
+.slick-slider,
11
+.slick-track {
12
+    position: relative;
13
+    display: block
14
+}
15
+
16
+.slick-loading .slick-slide,
17
+.slick-loading .slick-track {
18
+    visibility: hidden
19
+}
20
+
21
+.slick-slider {
22
+    height: 100%;
23
+    box-sizing: border-box;
24
+    -webkit-user-select: none;
25
+    -moz-user-select: none;
26
+    -ms-user-select: none;
27
+    user-select: none;
28
+    -webkit-touch-callout: none;
29
+    -khtml-user-select: none;
30
+    -ms-touch-action: pan-y;
31
+    touch-action: pan-y;
32
+    -webkit-tap-highlight-color: transparent
33
+}
34
+
35
+.slick-list {
36
+    height: 100%;
37
+    overflow: hidden;
38
+    margin: 0;
39
+    padding: 0;
40
+}
41
+
42
+.slick-list:focus {
43
+    outline: 0
44
+}
45
+
46
+.slick-list.dragging {
47
+    cursor: pointer;
48
+    cursor: hand
49
+}
50
+
51
+.slick-slider .slick-list,
52
+.slick-slider .slick-track {
53
+    -webkit-transform: translate3d(0, 0, 0);
54
+    -moz-transform: translate3d(0, 0, 0);
55
+    -ms-transform: translate3d(0, 0, 0);
56
+    -o-transform: translate3d(0, 0, 0);
57
+    transform: translate3d(0, 0, 0)
58
+}
59
+
60
+.slick-track {
61
+    top: 0;
62
+    left: 0
63
+}
64
+
65
+.slick-track:after,
66
+.slick-track:before {
67
+    display: table;
68
+    content: ''
69
+}
70
+
71
+.slick-track:after {
72
+    clear: both
73
+}
74
+
75
+.slick-slide {
76
+    display: none;
77
+    float: left;
78
+    height: 100%;
79
+    min-height: 1px
80
+}
81
+
82
+[dir=rtl] .slick-slide {
83
+    float: right
84
+}
85
+
86
+.slick-slide img {
87
+    display: block
88
+}
89
+
90
+.slick-slide.slick-loading img {
91
+    display: none
92
+}
93
+
94
+.slick-slide.dragging img {
95
+    pointer-events: none
96
+}
97
+
98
+.slick-initialized .slick-slide {
99
+    display: block
100
+}
101
+
102
+.slick-vertical .slick-slide {
103
+    display: block;
104
+    height: auto;
105
+    border: 1px solid transparent
106
+}
107
+
108
+.slick-arrow.slick-hidden {
109
+    display: none
110
+}
111
+
112
+/*# sourceMappingURL=slick.min.css.map */

+ 2 - 2
src/index.js

@@ -78,9 +78,9 @@ if (ticket && ssoEmpId) {
78 78
 // reportWebVitals();
79 79
 
80 80
 if (process.env.NODE_ENV === "production") {
81
-  document.title = "运营数据中心";
81
+  document.title = "天齐锂业·数据大屏";
82 82
 } else {
83
-  document.title = "(测试)运营数据中心";
83
+  document.title = "(测试)天齐锂业·数据大屏";
84 84
 }
85 85
 
86 86
 // 获取socket id , 建立socket连接

+ 6 - 120
src/pages/frame/component/top/view.jsx

@@ -576,50 +576,8 @@ export default observer(function (props) {
576 576
     console.log($store.app.avator);
577 577
   }, []);
578 578
 
579
-  //表单配置
580
-  const formItemLayout = {
581
-    labelCol: { span: 4 },
582
-    wrapperCol: { span: 20 },
583
-  };
584
-  /**点击联系我们 */
585
-  const handleContact = () => {
586
-    setShowContactModalVisible(true);
587
-  };
588
-  /**点击转换主题 */
589
-  const changeThemesStyle = () => {
590
-    const name = Cookie.get("themesName");
591
-    Cookie.set("themesName", name == "chaBaiDao" ? "yaLeJu" : "chaBaiDao");
592
-    window.location.reload();
593
-  };
594 579
 
595 580
 
596
-  /**提交联系我们 */
597
-  const handleContactOk = () => {
598
-    //判断是否是固定的负责人
599
-    form.validateFields().then(() => {
600
-      // let isFixDirector =
601
-      //   probType === 0 ? copyPeople : directorInfo.itManagerAccountId;
602
-      // let copyAggregate = [...new Set([copyPeople, isFixDirector])];
603
-      form.setFieldsValue({
604
-        problemChargePersonId: "1500661792542593026",
605
-        problemSendPersonId: ["1500661792542593026"],
606
-      });
607
-      const config = form.getFieldValue();
608
-      //固定accountId为1500661792542593026
609
-      const accountId = sessionStorage.getItem("accountId");
610
-      const params = Object.assign({ ...config }, { accountId });
611
-      feedBack(params).then(({ data, resultCode }) => {
612
-        if (+resultCode === 0) {
613
-          message.success("反馈成功");
614
-        }
615
-      });
616
-      form.resetFields();
617
-      setIptValue(0);
618
-      setShowContactModalVisible(false);
619
-      getUnReadNum();
620
-    });
621
-  };
622
-
623 581
   //获取 未读消息的数量
624 582
   const getUnReadNum = () => {
625 583
     let accountId = sessionStorage.getItem("accountId");
@@ -630,83 +588,11 @@ export default observer(function (props) {
630 588
     //   }
631 589
     // });
632 590
   };
633
-
634
-  /**控制输入字数 */
635
-  let timer = null;
636
-  const handleInput = (e) => {
637
-    clearTimeout(timer);
638
-    timer = setTimeout(() => {
639
-      setIptValue(e.target.value.length);
640
-    }, 500);
641
-  };
642
-
643
-  //处理 消息 详情
644
-  const goHandleMessage = () => {
645
-    const { messageDetailType, messageContentObjectId, messageType } = detailInfo || {};
646
-    if (messageType == 'System_bulletin' && (messageDetailType == 'newResourceMsg' || messageDetailType == 'fineReportChange' || messageDetailType == 'fineDataResourceChange') && !hasPermission) {
647
-      message.warning("该报表无权限!");
648
-      return;
649
-    }
650
-    switch (messageDetailType) {
651
-      case "fineDataResourceChange":
652
-        //根据id 找到 该元数据
653
-        getMenuDesc({ resourceId: messageContentObjectId }).then(
654
-          ({ data, resultCode }) => {
655
-            if (+resultCode === 0) {
656
-              $store.app.setMetaData({
657
-                data,
658
-                visible: true,
659
-              });
660
-            }
661
-          }
662
-        );
663
-        break;
664
-      case "fineReportChange":
665
-        getReportInfo({ resourceId: messageContentObjectId }).then(
666
-          ({ data, resultCode }) => {
667
-            if (+resultCode === 0) {
668
-              switchPage({
669
-                // pageId: relationship[key].pageId,
670
-                modelName: data.resourceName,
671
-                pageName: data.resourceName,
672
-                pageUrl: data.resourceUrl,
673
-                resourceId: data.resourceId,
674
-                visitId: sessionStorage.getItem("unionId"),
675
-              });
676
-              let dataOpt = {
677
-                id: data.resourceId,
678
-                name: data.resourceName,
679
-                openType: "self",
680
-                path: data.resourceUrl,
681
-                type: data.resourceType,
682
-              };
683
-              dealDiffSheetType(data).then((response) => {
684
-                $store.app.setNavList({ ...dataOpt });
685
-                $store.app.setCurNav(dataOpt.path);
686
-                if (response.type === "sys") {
687
-                  history.push(response.link);
688
-                } else {
689
-                  history.push(`/home/outer/${response.activeItem.resourceId}`);
690
-                }
691
-              });
692
-            }
693
-          }
694
-        );
695
-        break;
696
-      default:
697
-        setIsShowDetail(false);
698
-    }
699
-
700
-  };
701
-
702
-  const userAvator = sessionStorage.getItem("avator");
703
-  const {
704
-    createTime,
705
-    messageContent,
706
-    messageDetailType,
707
-    messageTypeValue,
708
-    messageSourceName,
709
-  } = detailMessage || {}; /**解构 当前点击的详情数据 */
591
+  const name_arr = {
592
+    "#/home/gvc":"产供销价值链",
593
+    "#/home/operation":"运营数据中心",
594
+  }
595
+   window.lo
710 596
   return (
711 597
     <div class="top2 animate__animated animate__fadeInDown animate__delay-1s animate__slower">
712 598
       <div className={$store.app.styleCommon.theme == 'chaBaiDao' ? [styles.top + ' top'] : styles.top}>
@@ -716,7 +602,7 @@ export default observer(function (props) {
716 602
             width="17"
717 603
           />
718 604
           <span></span>
719
-          <h1>运营数据中心</h1>
605
+          <h1>{name_arr[window.location.hash] || ''}</h1>
720 606
         </div>
721 607
         {/* {history.location.pathname === "/home/index" && (
722 608
           <>

+ 3 - 16
src/pages/frame/view.jsx

@@ -458,13 +458,7 @@ export default observer(function Frame(props) {
458 458
       {/* <div className="nowifi-tip">当前网络状态不佳</div> */}
459 459
 
460 460
       {/* 正文 */}
461
-      <div style={history.location.pathname === "/home/index" || history.location.pathname === '/home/operation'? { display: "flex", height: '100%' } : (history.location.pathname.indexOf("/home/outer") > -1 ?{
462
-        overflow: "hidden",
463
-        display: "flex",
464
-        background: 'rgb(255, 255, 255)',
465
-        height: "100%",
466
-      } : {display: "flex", height: '100%'})}>
467
-
461
+      <div style={{ display: "flex", height: '100%' }}>
468 462
         {$store.sysMenu.submenuList.length > 0 && !collapsed && (
469 463
           <div
470 464
             className="movebar"
@@ -477,18 +471,11 @@ export default observer(function Frame(props) {
477 471
         {isMove && <div className="markmore"></div>}
478 472
 
479 473
         <div
480
-          className={`${history.location.pathname !== "/home/index" && history.location.pathname !== '/home/operation'&&
481
-              $store.app.navList.length > 0
482
-              ? (history.location.pathname.indexOf("/home/outer") > -1 ? "body_box outer_body_box" : 'body_box') : "body_box homePage"
483
-            }`}
474
+          className={"body_box homePage"}
484 475
         >
485 476
           <Navigator
486 477
             style={{
487
-              display:
488
-                history.location.pathname !== "/home/index" && history.location.pathname !== '/home/operation'&&
489
-                  $store.app.navList.length > 0
490
-                  ? "flex"
491
-                  : "none",
478
+              display:"none",
492 479
             }}
493 480
           />
494 481
           <TipMsg onRef={onRef2}></TipMsg>

+ 230 - 0
src/pages/gvc/api.js

@@ -0,0 +1,230 @@
1
+import request from "@utils/request";
2
+
3
+/**登录*/
4
+export function checkToken(params) {
5
+  return request({
6
+    url: `/api/yonghong/checkToken?token=${params}`,
7
+    method: "GEt",
8
+  });
9
+}
10
+
11
+/**各基地库存明细 */
12
+export function smallMaterialService(params) {
13
+  return request({
14
+    url: "/dataengine-center-oneservice/list/1358057393917040084",
15
+    method: "POST",
16
+    data: {
17
+      "apiId": "1358057393917040084",
18
+      "appKey": "200000135",
19
+      "env": "PROD",
20
+      "reqProtocol": 1,
21
+      "returnFields": [
22
+        "factoryCode",
23
+        "factoryName",
24
+        "prodCatgoryCode",
25
+        "prodCatgory",
26
+        "indexValue",
27
+      ],
28
+      "pageNum": 1,
29
+      "pageSize": 50,
30
+      "useResultCache": false
31
+    },
32
+    headers: {
33
+      sign: 'fdb551d8c6a01d87c58970d519752d81',
34
+      account: 'yunxi_fuxue',
35
+      'Cache-Control': 'no-cache',
36
+      apiId: '1358057393917040084',
37
+      appKey: '200000135',
38
+      execType: '3',
39
+      env: 'PROD',
40
+    }
41
+  });
42
+}
43
+
44
+
45
+/**各基地日,月累计,年累计产量 */
46
+export function smallDayService(params) {
47
+  return request({
48
+    url: "/dataengine-center-oneservice/list/1358059456248976873",
49
+    method: "POST",
50
+    data: {
51
+      "apiId": "1358059456248976873",
52
+      "appKey": "200000135",
53
+      "env": "PROD",
54
+      "reqProtocol": 1,
55
+      "returnFields": [
56
+        "factoryCode",
57
+        "factoryNameCode",
58
+        "dateType",
59
+        "indexValue"
60
+      ],
61
+      "pageNum": 1,
62
+      "pageSize": 10,
63
+      "useResultCache": false
64
+    },
65
+    headers: {
66
+      sign: '5f270b133af668b3631fbe7dbff9ebe4',
67
+      account: 'yunxi_fuxue',
68
+      'Cache-Control': 'no-cache',
69
+      apiId: '1358059456248976873',
70
+      appKey: '200000135',
71
+      execType: '3',
72
+      env: 'PROD',
73
+    }
74
+  });
75
+}
76
+
77
+
78
+/**左侧数据*/
79
+export function leftService(params) {
80
+  return request({
81
+    url: "/dataengine-center-oneservice/list/1357592107129541992",
82
+    method: "POST",
83
+    data: {
84
+      "apiId": "1357592107129541992",
85
+      "appKey": "200000135",
86
+      "env": "PROD",
87
+      "reqProtocol": 1,
88
+      "returnFields": [
89
+        "prodCode",
90
+        "production",
91
+        "inventory"
92
+      ],
93
+      "pageNum": 1,
94
+      "pageSize": 10,
95
+      "useResultCache": false
96
+    },
97
+    headers: {
98
+      sign: '2d35f0b798fe2cc8443f95aed6da466a',
99
+      account: 'yunxi_fuxue',
100
+      'Cache-Control': 'no-cache',
101
+      apiId: '1357592107129541992',
102
+      appKey: '200000135',
103
+      execType: '3',
104
+      env: 'PROD',
105
+    }
106
+  });
107
+}
108
+
109
+/**累计销量客户*/
110
+export function rollService(params) {
111
+  return request({
112
+    url: "/dataengine-center-oneservice/list/1357509594900108615",
113
+    method: "POST",
114
+    data: {
115
+      "apiId": "1357509594900108615",
116
+      "appKey": "200000135",
117
+      "env": "PROD",
118
+      "reqProtocol": 1,
119
+      "returnFields": [
120
+        "customerName",
121
+        "salesQty"
122
+      ],
123
+      "pageNum": 1,
124
+      "pageSize": 10,
125
+      "useResultCache": false
126
+    },
127
+    headers: {
128
+      sign: '839f9217d1cf81ec03ff6ccf54c86e37',
129
+      account: 'yunxi_fuxue',
130
+      'Cache-Control': 'no-cache',
131
+      apiId: '1357509594900108615',
132
+      appKey: '200000135',
133
+      execType: '3',
134
+      env: 'PROD',
135
+    }
136
+  });
137
+}
138
+
139
+
140
+/**锂辉石库存*/
141
+export function bigShopService(params) {
142
+  return request({
143
+    url: "/dataengine-center-oneservice/list/1357489941160170789",
144
+    method: "POST",
145
+    data: {
146
+      "apiId": "1357489941160170789",
147
+      "appKey": "200000135",
148
+      "env": "PROD",
149
+      "reqProtocol": 1,
150
+      "returnFields": [
151
+        "warehouseNameCode",
152
+        "indexValue",
153
+      ],
154
+      "pageNum": 1,
155
+      "pageSize": 10,
156
+      "useResultCache": false
157
+    },
158
+    headers: {
159
+      sign: 'ae4c520da5ae882455307324f75f5277',
160
+      account: 'yunxi_fuxue',
161
+      'Cache-Control': 'no-cache',
162
+      apiId: '1357489941160170789',
163
+      appKey: '200000135',
164
+      execType: '3',
165
+      env: 'PROD',
166
+    }
167
+  });
168
+}
169
+
170
+/**个基地年累计产量,库存*/
171
+export function smallShopService(params) {
172
+  return request({
173
+    url: "/dataengine-center-oneservice/list/1357592780709598582",
174
+    method: "POST",
175
+    data: {
176
+      "apiId": "1357592780709598582",
177
+      "appKey": "200000135",
178
+      "env": "PROD",
179
+      "reqProtocol": 1,
180
+      "returnFields": [
181
+        "factoryCode",
182
+        "production",
183
+        "inventory",
184
+      ],
185
+      "pageNum": 1,
186
+      "pageSize": 10,
187
+      "useResultCache": false
188
+    },
189
+    headers: {
190
+      sign: 'a842b5c5c462d7cacd2baad402ea94a7',
191
+      account: 'yunxi_fuxue',
192
+      'Cache-Control': 'no-cache',
193
+      apiId: '1357592780709598582',
194
+      appKey: '200000135',
195
+      execType: '3',
196
+      env: 'PROD',
197
+    }
198
+  });
199
+}
200
+
201
+/**更新时间*/
202
+export function updateTimeService(params) {
203
+  return request({
204
+    url: "/dataengine-center-oneservice/list/1356778817327502618",
205
+    method: "POST",
206
+    data: {
207
+      "apiId": "1356778817327502618",
208
+      "appKey": "200000134",
209
+      "env": "PROD",
210
+      "reqProtocol": 1,
211
+      "returnFields": [
212
+        "etlTime"
213
+      ],
214
+      "pageNum": 1,
215
+      "pageSize": 10,
216
+      "useResultCache": false
217
+    },
218
+    headers: {
219
+      sign: '4365b6564b25c852fcf0228188f48114',
220
+      account: 'yunxi_fuxue',
221
+      'Cache-Control': 'no-cache',
222
+      apiId: '1356778817327502618',
223
+      appKey: '200000134',
224
+      execType: '3',
225
+      env: 'PROD',
226
+    }
227
+  });
228
+}
229
+
230
+

+ 111 - 0
src/pages/gvc/component/mapView2.jsx

@@ -0,0 +1,111 @@
1
+/*
2
+ * @Author: dayan_hjm 中部地图 第一段
3
+ * @Date: 2023-10-25 10:32:44 
4
+ * @Last Modified by: dayan_hjm
5
+ * controls 属性 : 值为 controls , 启用控制按钮 , 由于在不同的浏览器中表现不同 , 一般情况下 , 不显示控制按钮 ;
6
+        autoplay 属性 : 值为 autoplay , 在 Chrome 浏览器中 禁用自动播放 , 其它浏览器不禁用自动播放 ;
7
+        如果为视频设置静音播放 , 则可以在 Chrom 浏览器中 设置 autoplay 实现自动播放 ;
8
+        muted 属性 : 值为 muted , 将视频设置为静音播放 ;
9
+        如果为视频设置静音播放 , 则可以在 Chrom 浏览器中 设置 autoplay 实现自动播放 ;
10
+        width 属性 : 值为像素值 , 设置播放器宽度 ; 播放器的宽高建议只设置一个 , 避免失真 ;
11
+        height 属性 : 值为像素值 , 设置播放器高度 ; 播放器的宽高建议只设置一个 , 避免失真 ;
12
+        loop 属性 : 值为 loop , 设置播放器循环播放 ;
13
+        poster 属性 : 值为 图片 url 路径 , 设置视频位置等待加载时的图片 ;
14
+        preload 属性 :
15
+        设置 auto , 表示 预先加载视频 ;
16
+        设置 none , 表示 不预先加载视频 ;
17
+ * @Last Modified time: 2023-11-14 15:22:36
18
+ */
19
+import React, { useState, useEffect, Component } from "react";
20
+import { useHistory, useLocation, withRouter } from "react-router-dom";
21
+import mod from '../../tqcDataVHome/mod';
22
+import 'animate.css';
23
+@withRouter
24
+
25
+class MapViewTwo extends Component {
26
+  // 构造函数,组件的实例创建时,最先执行
27
+  constructor(props, context) {
28
+    super(props, context);
29
+    this.store = mod;
30
+    this.state = {
31
+      changGif: false,
32
+    };
33
+  }
34
+
35
+  componentDidMount() {
36
+    setTimeout(() => {
37
+      //替换gif
38
+      this.setState({ changGif: true });
39
+      this.videoStart();
40
+    }, 200)
41
+    // setTimeout(() => {
42
+    //   $(".video_box_hide").hide();
43
+    // }, 4000)
44
+  }
45
+  videoStart() {
46
+    /*     Chrome 浏览器的视频自动播放策略
47
+        1.始终允许静音模式下自动播放
48
+        2.在以下的情况中,带声音播放会被允许:
49
+          ①用户已经与当前的域进行了交互(也就是click,tap事件)。
50
+          ②在桌面设备上,用户的媒体参与度指数阈值已经超过,这意味着用户之前播放过有声视频。
51
+          ③用户已经将网站添加到移动设备上的主屏幕或允在桌面上安装了PWA。
52
+        3.顶部帧可以将自动播放权限委派给其iframe,来允许自动播放声音
53
+        
54
+        媒体参与度(Media Engagement)是指用户与媒体内容进行互动的程度,可以通过多个指标来衡量。这些指标主要包括观看时间、观看率、转化率、交互行为等。
55
+        可以通过:chrome://media-engagement/ 查看
56
+     */
57
+    const video = document.querySelector('.video1');
58
+    console.log(video.play());
59
+
60
+    const model = document.querySelector('.model')
61
+    const btn = document.querySelector('button')
62
+    // 第一种方法 引导用户去与页面交互实现播放
63
+    async function play() {
64
+      try {
65
+        await video.play();
66
+        //使用await的原因是因为video.play()方法返回的是一个Promise,所以在这里我们可以对他进行一些处理
67
+        // model.style.display = 'none';
68
+        btn.removeEventListener('click', play);
69
+        // 如果他自动播放了就隐藏按钮,消除点击事件
70
+      } catch (err) {
71
+        // model.style.display = 'block';
72
+        btn.addEventListener('click', play);
73
+        // 如果Promise返回的是error就引导用户点击按钮,在调用play方法
74
+      }
75
+    }
76
+    play();
77
+
78
+    //第二种方法比较主流,类似的有网页版抖音以及B站
79
+    function play() {
80
+      video.muted = true;//设置视频为静音
81
+      video.play();//调用播放方法
82
+      const ctx = new AudioContext();
83
+      const canAutoPlay = ctx.state === 'running'; //通过这个可以判断出视频能不能够自动播放 如何可以它的值就是“running” 否则为"suspended"
84
+      // 如果是不能播放我们就执行下面的逻辑,其实就是类似于第一种方法,让用户与其交互
85
+      ctx.close();
86
+      if (canAutoPlay) {
87
+        video.muted = false;
88
+        model.style.display = 'none';
89
+        btn.removeEventListener('click', play);
90
+      }
91
+      else {
92
+        model.style.display = 'block';
93
+        btn.addEventListener('click', play);
94
+      }
95
+    }
96
+    play()
97
+
98
+  }
99
+
100
+  render() {
101
+    const { changGif } = this.state;
102
+    return (
103
+      <div class="video_box video_box_hide gvc_video animate__animated animate__fadeOut animate__delay-2s animate__slower">
104
+        <div className="alls">
105
+        <video src={require("@assets/imgs/gvc/video1.mp4").default} autoplay="autoplay" class="video1"></video>
106
+        </div>
107
+      </div>
108
+    )
109
+  }
110
+}
111
+export default MapViewTwo;

+ 107 - 0
src/pages/gvc/component/rightBottomView.jsx

@@ -0,0 +1,107 @@
1
+/*
2
+ * @Author: dayan_hjm 累计销量客户
3
+ * @Date: 2023-10-23 09:32:12 
4
+ * @Last Modified by: dayan_hjm
5
+ * @Last Modified time: 2023-11-16 17:05:05
6
+ */
7
+
8
+import React, { useState, useEffect, Component } from "react";
9
+import styles from "../style.less";
10
+import { useHistory, useLocation, withRouter } from "react-router-dom";
11
+import mod from '../mod';
12
+import Slider from "react-slick";
13
+import "slick-carousel/slick/slick.css";
14
+import "slick-carousel/slick/slick-theme.css";
15
+import { Progress } from 'antd';
16
+import { getArrMax,sortby } from "@utils/util";
17
+import {
18
+  rollService,
19
+} from "../api";
20
+import { get, } from "lodash";
21
+
22
+@withRouter
23
+
24
+class RightBottomView extends Component {
25
+  // 构造函数,组件的实例创建时,最先执行
26
+  constructor(props, context) {
27
+    super(props, context);
28
+    this.store = mod;
29
+    this.state = {
30
+      data_item: [],
31
+    };
32
+  }
33
+
34
+  componentDidMount() {
35
+    this.getUrl()
36
+  }
37
+
38
+  async getUrl() {
39
+    await rollService().then(({ data=[], resultCode }) => {
40
+      if (+resultCode === 0) {
41
+        let data_item = [];
42
+        const max1 = data.sort(sortby('salesQty',false));
43
+        const max2 = max1?.[0]?.salesQty / 0.95 || 0;
44
+        data.map((x,i)=>{  
45
+          data_item.push({
46
+            name: x.customerName,
47
+            num: x.salesQty,
48
+            percent:Number(x.salesQty / max2).toFixed(2) * 100
49
+          })
50
+        });
51
+        this.setState({data_item});
52
+      }
53
+    });
54
+
55
+  }
56
+
57
+  render() {
58
+    const { data_item } = this.state;
59
+    const settings = {
60
+      dots: false,
61
+      arrows:false,
62
+      infinite: true,
63
+      autoplay: true,
64
+      autoplaySpeed: 2500,//自动播放的时间
65
+      // fade: true,//是否采用淡入淡出的效果  竖着的滚动方式不能添加此动效
66
+      slidesToShow: data_item.length >= 8 ? 8 : data_item.length,
67
+      slidesToScroll: 1,
68
+      vertical: true,
69
+      verticalSwiping: true,
70
+      beforeChange: function (currentSlide, nextSlide) {
71
+        console.log("before change", currentSlide, nextSlide);
72
+      },
73
+      afterChange: function (currentSlide) {
74
+        console.log("after change", currentSlide);
75
+      }
76
+    };
77
+    return (
78
+      <div className={["eacharView cbRightBottomView slider_item_box"]} style={{height: data_item.length > 8 ? 'auto' : "100%"}}>
79
+        <p className="title_">累计销量客户/吨</p>
80
+        <Slider {...settings}>
81
+          {
82
+            data_item.map((x, i) => {
83
+              return (
84
+                <div className="slider_box">
85
+                  <div className="slider_top">
86
+                    <p>{i + 1}.<span>{x.name}</span></p>
87
+                    <p className="p2">{x.num}</p>
88
+                  </div>
89
+                  <Progress
90
+                    strokeColor={{
91
+                      from: '#a98911cf',
92
+                      to: 'rgb(248,204,41,0.9)',
93
+                    }}
94
+                    percent={x.percent}
95
+                    status="active"
96
+                  />
97
+                </div>
98
+              )
99
+            })
100
+          }
101
+
102
+        </Slider>
103
+      </div>
104
+    )
105
+  }
106
+}
107
+export default RightBottomView;

+ 267 - 0
src/pages/gvc/mod.js

@@ -0,0 +1,267 @@
1
+/*
2
+ * @Author: dayan_hjm 
3
+ * @Date: 2022-10-27 11:11:30 
4
+ * @Last modified by:   dayan_hjm 
5
+ * @Last modified time: 2022-10-27 11:11:30 
6
+ */
7
+
8
+// 状态管理方法
9
+import { observable, action, configure, makeObservable, runInAction } from 'mobx';
10
+// 工具方法
11
+import { cloneDeep, get, groupBy, isEmpty, orderBy, pick, values } from "lodash";
12
+
13
+import { message } from 'antd';
14
+
15
+// 默认状态
16
+const defaultState = {
17
+  imgMsgData: [
18
+    {
19
+      total: 4500,
20
+      totalName: "累计运输锂辉石",
21
+      styles: { left: "0%", top: "19%" },
22
+      cumulativeProduction: null,
23
+      inventory: 0,
24
+    },
25
+    {
26
+      total: 3233,
27
+      totalName: "锂辉石库存量",
28
+      styles: { left: "11%", top: "45%" },
29
+      cumulativeProduction: null,
30
+      inventory: 0,
31
+    },
32
+    {
33
+      total: 3578,
34
+      totalName: "锂辉石库存量",
35
+      styles: { left: "34%", top: "27%" },
36
+      cumulativeProduction: null,
37
+      inventory: 0,
38
+    },
39
+    {
40
+      total: 0,
41
+      totalName: "",
42
+      styles: { left: "11%", top: "88%" },
43
+      cumulativeProduction: 1222,
44
+      inventory: 1000,
45
+      day:222,
46
+      mood:333,
47
+      year:444,
48
+      rawMaterial:[
49
+        {
50
+          prodCatgory:"原料-鲤辉石",
51
+          indexValue:22,
52
+        },
53
+        {
54
+          prodCatgory:"产品-碳酸锂",
55
+          indexValue:33,
56
+        },
57
+        {
58
+          prodCatgory:"原料-氯化锂",
59
+          indexValue:44,
60
+        },
61
+        {
62
+          prodCatgory:"产品-氢氧化锂",
63
+          indexValue:66,
64
+        },
65
+        {
66
+          prodCatgory:"产品-金属锂",
67
+          indexValue:88,
68
+        },
69
+        {
70
+          prodCatgory:"产品-98K",
71
+          indexValue:1000,
72
+        },
73
+      ]
74
+    },
75
+    {
76
+      total: 0,
77
+      totalName: "",
78
+      styles: { left: "30%", top: "73%" },
79
+      cumulativeProduction: 1222,
80
+      inventory: 1000,
81
+      day:222,
82
+      mood:333,
83
+      year:444,
84
+      rawMaterial:[
85
+        {
86
+          prodCatgory:"原料-鲤辉石",
87
+          indexValue:22,
88
+        },
89
+        {
90
+          prodCatgory:"产品-碳酸锂",
91
+          indexValue:33,
92
+        },
93
+        {
94
+          prodCatgory:"原料-氯化锂",
95
+          indexValue:44,
96
+        },
97
+        {
98
+          prodCatgory:"产品-氢氧化锂",
99
+          indexValue:66,
100
+        },
101
+        {
102
+          prodCatgory:"产品-金属锂",
103
+          indexValue:88,
104
+        },
105
+        {
106
+          prodCatgory:"产品-98K",
107
+          indexValue:1000,
108
+        },
109
+      ]
110
+    },
111
+    {
112
+      total: 0,
113
+      totalName: "",
114
+      styles: { left: "52%", top: "56%" },
115
+      cumulativeProduction: 1222,
116
+      inventory: 1000,
117
+      day:222,
118
+      mood:333,
119
+      year:444,
120
+      rawMaterial:[
121
+        {
122
+          prodCatgory:"原料-鲤辉石",
123
+          indexValue:22,
124
+        },
125
+        {
126
+          prodCatgory:"产品-碳酸锂",
127
+          indexValue:33,
128
+        },
129
+        {
130
+          prodCatgory:"原料-氯化锂",
131
+          indexValue:44,
132
+        },
133
+        {
134
+          prodCatgory:"产品-氢氧化锂",
135
+          indexValue:66,
136
+        },
137
+        {
138
+          prodCatgory:"产品-金属锂",
139
+          indexValue:88,
140
+        },
141
+        {
142
+          prodCatgory:"产品-98K",
143
+          indexValue:1000,
144
+        },
145
+      ]
146
+    },
147
+    {
148
+      total: 0,
149
+      totalName: "",
150
+      styles: { left: "70%", top: "42%" },
151
+      cumulativeProduction: 1222,
152
+      inventory: 1000,
153
+      day:222,
154
+      mood:333,
155
+      year:444,
156
+      rawMaterial:[
157
+        {
158
+          prodCatgory:"原料-鲤辉石",
159
+          indexValue:22,
160
+        },
161
+        {
162
+          prodCatgory:"产品-碳酸锂",
163
+          indexValue:33,
164
+        },
165
+        {
166
+          prodCatgory:"原料-氯化锂",
167
+          indexValue:44,
168
+        },
169
+        {
170
+          prodCatgory:"产品-氢氧化锂",
171
+          indexValue:66,
172
+        },
173
+        {
174
+          prodCatgory:"产品-金属锂",
175
+          indexValue:88,
176
+        },
177
+        {
178
+          prodCatgory:"产品-98K",
179
+          indexValue:1000,
180
+        },
181
+      ]
182
+    },
183
+    {
184
+      total: 0,
185
+      totalName: "",
186
+      styles: { left: "88%", top: "28%" },
187
+      cumulativeProduction: 1222,
188
+      inventory: 1000,
189
+      day:222,
190
+      mood:333,
191
+      year:444,
192
+      rawMaterial:[
193
+        {
194
+          prodCatgory:"原料-鲤辉石",
195
+          indexValue:22,
196
+        },
197
+        {
198
+          prodCatgory:"产品-碳酸锂",
199
+          indexValue:33,
200
+        },
201
+        {
202
+          prodCatgory:"原料-氯化锂",
203
+          indexValue:44,
204
+        },
205
+        {
206
+          prodCatgory:"产品-氢氧化锂",
207
+          indexValue:66,
208
+        },
209
+        {
210
+          prodCatgory:"产品-金属锂",
211
+          indexValue:88,
212
+        },
213
+        {
214
+          prodCatgory:"产品-98K",
215
+          indexValue:1000,
216
+        },
217
+      ]
218
+    },
219
+  ],
220
+}
221
+
222
+// 严格模式
223
+configure({
224
+  enforceActions: 'observed'
225
+});
226
+
227
+
228
+/**
229
+ * mod层 - 业务逻辑,数据逻辑应该存储于此
230
+ */
231
+class Mod {
232
+  constructor() {
233
+    makeObservable(this);
234
+  }
235
+  // 监视状态
236
+  @observable state = cloneDeep(defaultState);
237
+
238
+  @action saveState = async (payload) => {
239
+    runInAction(() => {
240
+      this.state = {
241
+        ...this.state,
242
+        ...payload
243
+      };
244
+    });
245
+  };
246
+
247
+
248
+  // 新增/编辑运营商
249
+  // @action customerOperatorsmod = async (par, type) => {
250
+  //   try {
251
+  //     const { data, resultCode, resultMsg } = await Serv.customerOperatorsServ(par, type);
252
+  //     if (resultCode + '' === '0') {
253
+  //       runInAction(() => {
254
+  //         message.success('操作成功!')
255
+  //         this.state.addEditVisiable = false;
256
+  //         this.state.version = Math.random()
257
+  //       });
258
+  //     }
259
+  //   } catch (e) {
260
+  //     console.log('e: ', e);
261
+  //   }
262
+  // }
263
+}
264
+
265
+// 将组件实例化,这意味着组件将不能从别处实例化
266
+const mod = new Mod();
267
+export default mod;

+ 391 - 0
src/pages/gvc/style.less

@@ -0,0 +1,391 @@
1
+@import url("../../themes/themes.less");
2
+
3
+@assetUrl: "../../assets/imgs/home";
4
+
5
+.home_box {
6
+  background: url(../../assets/imgs/gvc/homeBgDataV.png) no-repeat 0 -10em / 100% 120% #041b40;
7
+  // background: #000;
8
+
9
+  :global {
10
+
11
+    .all_box {
12
+      width: 100%;
13
+      height: 100%;
14
+
15
+      .gvc_video {
16
+        align-items: flex-start;
17
+        // background: #000;
18
+
19
+        video {
20
+          width: 100%;
21
+          height: unset;
22
+          padding: 0;
23
+        }
24
+
25
+        .alls {
26
+
27
+          width: 64%;
28
+          height: unset;
29
+          padding: 2% 0 0 0;
30
+          position: relative;
31
+        }
32
+
33
+        @media (min-height: 800px) {
34
+          .alls {
35
+            width: 73%;
36
+          }
37
+        }
38
+
39
+        @media (min-height: 900px) {
40
+          .alls {
41
+            width: 64%;
42
+          }
43
+        }
44
+
45
+        @media (min-height: 1000PX) {
46
+          .alls {
47
+            width: 70%;
48
+          }
49
+        }
50
+
51
+      }
52
+
53
+      .gvcHome {
54
+        height: 100%;
55
+        justify-content: flex-start;
56
+
57
+        .leftContent {
58
+          width: 17%;
59
+          /* padding: 0 1em; */
60
+          height: 70%;
61
+          margin-top: 5%;
62
+          margin-left: 1%;
63
+          padding-right: 7%;
64
+
65
+          >ul {
66
+            width: 100%;
67
+            display: flex;
68
+            justify-content: center;
69
+            height: 100%;
70
+            flex-wrap: wrap;
71
+
72
+            >li {
73
+              height: 20%;
74
+              width: 100%;
75
+              color: #fff;
76
+              display: block;
77
+
78
+              .top_div {
79
+                background: none;
80
+                width: 100%;
81
+                height: 60%;
82
+                display: flex;
83
+                align-items: center;
84
+                justify-content: center;
85
+
86
+                >div {
87
+                  width: 51%;
88
+                  position: relative;
89
+                  display: block;
90
+
91
+                  .img1 {
92
+                    width: 100%;
93
+                  }
94
+
95
+                  >span {
96
+                    font-size: 0.9em;
97
+                    position: absolute;
98
+                    width: 100%;
99
+                    bottom: 15%;
100
+                    left: 63%;
101
+                    transform: skew(4deg, 334deg);
102
+                    font-weight: normal;
103
+                    color: #ededed;
104
+
105
+                  }
106
+
107
+                  .img2 {
108
+                    width: 37%;
109
+                    position: absolute;
110
+                    left: 32%;
111
+                    top: 24%;
112
+                  }
113
+                }
114
+              }
115
+
116
+              .text {
117
+                width: 100%;
118
+                display: flex;
119
+                align-items: center;
120
+                justify-content: space-between;
121
+                margin-top: 1em;
122
+                font-weight: normal;
123
+                font-size: 0.9em;
124
+                color: #CDF1FF;
125
+                padding: 0.8em 0.5em 0.2em;
126
+                background: linear-gradient(0deg, #ffffff26 0%, #ffffff00 100%);
127
+                border-radius: 0.5em;
128
+
129
+                .topMsg_number {
130
+                  color: #69FFDE;
131
+                  font-size: 1.2em;
132
+                  margin-right: 0.2em;
133
+                  margin-top: 0.2em;
134
+                }
135
+              }
136
+            }
137
+          }
138
+        }
139
+
140
+        @media (max-height: 900px) {
141
+          .leftContent li {
142
+            height: 15% !important;
143
+
144
+            .text {
145
+              width: 107% !important;
146
+              margin-top: 1em !important;
147
+
148
+              .topMsg_number {
149
+                font-size: 1em !important;
150
+              }
151
+            }
152
+          }
153
+        }
154
+
155
+        .centerCon {
156
+          width: 62%;
157
+          height: 80%;
158
+          padding: 0;
159
+          position: relative;
160
+          margin: 0% 0 0 -1%;
161
+        }
162
+
163
+        @media (min-height: 800px) {
164
+          .centerCon {
165
+            width: 65%;
166
+            height: 78%;
167
+            padding: 0;
168
+            position: relative;
169
+            margin: 0% 0 0 -3%;
170
+          }
171
+        }
172
+
173
+        @media (min-height: 900px) {
174
+          .centerCon {
175
+            width: 62%;
176
+            height: 80%;
177
+            padding: 0;
178
+            position: relative;
179
+            margin: 0% 0 0 -1%;
180
+          }
181
+        }
182
+
183
+        @media (min-height: 1000PX) {
184
+          .centerCon {
185
+            width: 63%;
186
+            height: 75%;
187
+            padding: 0;
188
+            position: relative;
189
+            margin: 0% 0 0 -3%;
190
+          }
191
+        }
192
+
193
+
194
+        .imgMsg {
195
+          width: 100%;
196
+          position: absolute;
197
+          left: 0;
198
+          top: 0;
199
+          height: 100%;
200
+          color: #fff;
201
+
202
+          li {
203
+            position: absolute;
204
+            width: 17em;
205
+            height: 4em;
206
+            opacity: 1;
207
+            background: linear-gradient(0deg, #ffffff26 0%, #ffffff00 100%);
208
+            border-radius: 0.5em;
209
+            padding: 0.5em;
210
+            box-sizing: border-box;
211
+            font-size: 0.9em;
212
+            color: #CDF1FF;
213
+
214
+            .nums {
215
+              font-size: 1.3em;
216
+              color: #69FFDE;
217
+              display: inline-block !important;
218
+            }
219
+
220
+            .topMsg_number_2 {
221
+              display: inline-block !important;
222
+            }
223
+
224
+            .sma {
225
+              font-size: 0.7em;
226
+              color: #CDF1FF;
227
+              display: inline-block;
228
+              margin-left: 0.2em;
229
+            }
230
+
231
+            .chanL {
232
+              background: unset;
233
+              font-size: 0.9em;
234
+              color: #CDF1FF;
235
+              height: 4em;
236
+              box-sizing: border-box;
237
+              padding: 0 0.5em;
238
+              display: flex;
239
+              justify-content: space-between;
240
+
241
+              >div {
242
+                width: 50%;
243
+              }
244
+            }
245
+
246
+            .hoverR {
247
+              width: 100%;
248
+              height: 12em;
249
+              position: absolute;
250
+              left: 0;
251
+              top: -7em;
252
+              padding-top: 11em;
253
+
254
+
255
+              .hoverDiv {
256
+                display: none;
257
+              }
258
+            }
259
+
260
+            .hoverR:hover {
261
+              .hoverDiv {
262
+                display: flex;
263
+              }
264
+            }
265
+
266
+            .hoverDiv {
267
+              display: flex;
268
+              align-items: center;
269
+              justify-content: space-between;
270
+              padding: 0 1em;
271
+              background: linear-gradient(0deg, #ffffff00 20%, #7a7a7a29 100%);
272
+              width: 100%;
273
+              border-radius: 0.5em;
274
+              box-sizing: border-box;
275
+              margin-top: 0.1em;
276
+              font-size: 0.8em;
277
+              padding: 0.2em 1em 0;
278
+              color: #d7d7d7;
279
+              align-items: flex-start;
280
+              height: auto;
281
+
282
+              >div>span {
283
+                display: block;
284
+              }
285
+            }
286
+          }
287
+
288
+          li:hover {
289
+            background: linear-gradient(0deg, #42ca9840 0%, #42ca9800 98%);
290
+          }
291
+        }
292
+
293
+        .rightContent {
294
+          width: 15%;
295
+          position: absolute;
296
+          right: 0;
297
+          bottom: 10%;
298
+          z-index: 9;
299
+          height: 60%;
300
+
301
+          .title_ {
302
+            text-align: left;
303
+            color: #fff;
304
+            width: 90%;
305
+            height: 2em;
306
+            border-radius: 0 8px 0 0;
307
+            opacity: 1;
308
+            background: linear-gradient(45deg, #ffdf5800 0%, #ffdf584d 100%);
309
+            line-height: 2em;
310
+            color: #F1E9E0;
311
+            margin-bottom: 0.6em;
312
+          }
313
+
314
+          .eacharView {
315
+            height: auto;
316
+            overflow: hidden;
317
+          }
318
+
319
+          .slider_box {
320
+            padding: 0 0.5em;
321
+            box-sizing: border-box;
322
+          }
323
+
324
+          .slider_top {
325
+            width: 100%;
326
+            font-size: 0.9em;
327
+            display: flex;
328
+            align-items: center;
329
+            justify-content: space-between;
330
+            color: #d4d4d4;
331
+            font-weight: normal;
332
+
333
+            >p {
334
+              width: 83%;
335
+              display: flex;
336
+              overflow: hidden;
337
+              text-overflow: ellipsis;
338
+              white-space: nowrap;
339
+
340
+              >span {
341
+                display: inline-block;
342
+                width: 99%;
343
+                overflow: hidden;
344
+                text-overflow: ellipsis;
345
+                white-space: nowrap;
346
+              }
347
+            }
348
+
349
+            .p2 {
350
+              width: 30%;
351
+              display: inline-block;
352
+              text-align: right;
353
+            }
354
+          }
355
+
356
+          .ant-progress {
357
+            height: 10px;
358
+
359
+            .ant-progress-inner {
360
+              top: -5px;
361
+              background-color: #57575759;
362
+
363
+              .ant-progress-bg {
364
+                height: 5px !important;
365
+              }
366
+            }
367
+          }
368
+
369
+        }
370
+
371
+        @media (min-height: 800px) {
372
+          .rightContent {
373
+            bottom: 3%;
374
+          }
375
+        }
376
+
377
+        @media (min-height: 900px) {
378
+          .rightContent {
379
+            bottom: 3%;
380
+          }
381
+        }
382
+
383
+        @media (min-height: 1000px) {
384
+          .rightContent {
385
+            bottom: -5%;
386
+          }
387
+        }
388
+      }
389
+    }
390
+  }
391
+}

+ 486 - 0
src/pages/gvc/view.jsx

@@ -0,0 +1,486 @@
1
+/*
2
+ * @Author: dayan_hjm  产供销价值链
3
+ * @Date: 2023-11-10 10:19:34 
4
+ * @Last Modified by: dayan_hjm
5
+ * @Last Modified time: 2023-11-21 17:46:28
6
+ */
7
+
8
+import React, { useState, useEffect, Component } from "react";
9
+import styles from "./style.less";
10
+import { useHistory, useLocation, withRouter } from "react-router-dom";
11
+import { observer, observable } from "mobx-react";
12
+import { message, Space, Form, Popconfirm, Modal, Tooltip, Icon, Button } from "antd";
13
+import mod from './mod';
14
+import { toJS } from "mobx";
15
+import RightBottomView from "./component/rightBottomView.jsx";
16
+import {
17
+  leftService,
18
+  bigShopService,
19
+  smallShopService,
20
+  smallDayService,
21
+  smallMaterialService,
22
+  checkToken,
23
+  updateTimeService
24
+} from "./api";
25
+import MapViewTwo from "./component/mapView2.jsx";
26
+
27
+import 'animate.css';
28
+import { get } from "lodash";
29
+@withRouter
30
+
31
+class Gvc extends Component {
32
+  // 构造函数,组件的实例创建时,最先执行
33
+  constructor(props, context) {
34
+    super(props, context);
35
+    this.store = mod;
36
+    this.state = {
37
+      LeftHtml: [
38
+      ],
39
+      updateTime: '',
40
+      changGif: false,
41
+      plannedCompletionData: [
42
+      ],
43
+      plannedCompletionNum: 1,
44
+      manHourData: [
45
+      ],
46
+      manHourNum: 1,
47
+    };
48
+    this.timer = null //定时器,用于检测同步状态
49
+  }
50
+  componentWillMount() {
51
+    if (window.location.host.indexOf("localhost") == -1) {
52
+      this.getToken()
53
+    }
54
+  }
55
+
56
+  async getToken() {
57
+    if (!sessionStorage.getItem("tqcVToken")) {
58
+      this.props.history.replace("/home/index");
59
+    } else {
60
+      await checkToken(sessionStorage.getItem("tqcVToken")).then(({ data, resultCode }) => {
61
+        if (data?.userId) {
62
+          // this.props.history.push('/')
63
+        } else {
64
+          this.props.history.replace("/home/index");
65
+        }
66
+      });
67
+    }
68
+  }
69
+  componentDidMount() {
70
+    // this.fontMsgChange();
71
+    this.getUrl();
72
+    this.getUrl2()
73
+    this.getUrl4()
74
+    this.getUrl3();
75
+
76
+
77
+    setTimeout(() => {
78
+      this.videoStart();
79
+    }, 200)
80
+    setTimeout(() => {
81
+      //替换gif
82
+      this.setState({ changGif: true });
83
+      $(".shu1").numScroll();
84
+    }, 3000)
85
+    setTimeout(() => {
86
+      this.getUrl5()
87
+      setTimeout(() => {
88
+        this.getUrl6()
89
+      }, 500)
90
+    }, 2000)
91
+  }
92
+  videoStart() {
93
+    /*     Chrome 浏览器的视频自动播放策略
94
+        1.始终允许静音模式下自动播放
95
+        2.在以下的情况中,带声音播放会被允许:
96
+          ①用户已经与当前的域进行了交互(也就是click,tap事件)。
97
+          ②在桌面设备上,用户的媒体参与度指数阈值已经超过,这意味着用户之前播放过有声视频。
98
+          ③用户已经将网站添加到移动设备上的主屏幕或允在桌面上安装了PWA。
99
+        3.顶部帧可以将自动播放权限委派给其iframe,来允许自动播放声音
100
+        
101
+        媒体参与度(Media Engagement)是指用户与媒体内容进行互动的程度,可以通过多个指标来衡量。这些指标主要包括观看时间、观看率、转化率、交互行为等。
102
+        可以通过:chrome://media-engagement/ 查看
103
+     */
104
+    const video = document.querySelector('.video2');
105
+    console.log(video.play());
106
+
107
+    const model = document.querySelector('.model')
108
+    const btn = document.querySelector('button')
109
+    // 第一种方法 引导用户去与页面交互实现播放
110
+    async function play() {
111
+      try {
112
+        await video.play();
113
+        //使用await的原因是因为video.play()方法返回的是一个Promise,所以在这里我们可以对他进行一些处理
114
+        model.style.display = 'none';
115
+        btn.removeEventListener('click', play);
116
+        // 如果他自动播放了就隐藏按钮,消除点击事件
117
+      } catch (err) {
118
+        model.style.display = 'block';
119
+        btn.addEventListener('click', play);
120
+        // 如果Promise返回的是error就引导用户点击按钮,在调用play方法
121
+      }
122
+    }
123
+    play();
124
+
125
+    //第二种方法比较主流,类似的有网页版抖音以及B站
126
+    function play() {
127
+      video.muted = true;//设置视频为静音
128
+      video.play();//调用播放方法
129
+      const ctx = new AudioContext();
130
+      const canAutoPlay = ctx.state === 'running'; //通过这个可以判断出视频能不能够自动播放 如何可以它的值就是“running” 否则为"suspended"
131
+      // 如果是不能播放我们就执行下面的逻辑,其实就是类似于第一种方法,让用户与其交互
132
+      ctx.close();
133
+      if (canAutoPlay) {
134
+        video.muted = false;
135
+        model.style.display = 'none';
136
+        btn.removeEventListener('click', play);
137
+      }
138
+      else {
139
+        model.style.display = 'block';
140
+        btn.addEventListener('click', play);
141
+      }
142
+    }
143
+    play()
144
+
145
+  }
146
+
147
+  async getUrl() {
148
+    await leftService().then(({ data = [], resultCode }) => {
149
+      if (+resultCode === 0) {
150
+        let LeftHtml = [], name_ = ["碳酸锂", '氢氧化钠', '氯化锂', '金属锂'];
151
+        data.map((x, i) => {
152
+          if (i >= 4) {
153
+            return
154
+          }
155
+          LeftHtml.push(
156
+            {
157
+              txt_name: name_[i],
158
+              num1: x.production,
159
+              num2: x.inventory,
160
+            }
161
+          );
162
+        });
163
+        this.setState({ LeftHtml });
164
+      }
165
+    });
166
+  }
167
+  async getUrl2() {
168
+    await bigShopService().then(({ data = [], resultCode }) => {
169
+      if (+resultCode === 0) {
170
+        const name_ = ["", "锂辉石库存量", "锂辉石库存量", "累计运输锂辉石"];
171
+        const style__ = [{}, { left: "34%", top: "27%" }, { left: "11%", top: "45%" }, { left: "0%", top: "19%" }]
172
+        data = data.map((x, i) => {
173
+          return {
174
+            ...x,
175
+            total: x.indexValue,
176
+            totalName: name_[x.warehouseNameCode],
177
+            styles: style__[x.warehouseNameCode],
178
+            cumulativeProduction: null,
179
+            inventory: 0,
180
+          }
181
+        });
182
+        const d_1 = data.filter(x => { return x.warehouseNameCode == 3 })[0];
183
+        const d_2 = data.filter(x => { return x.warehouseNameCode == 2 })[0];
184
+        const d_3 = data.filter(x => { return x.warehouseNameCode == 1 })[0];
185
+        let old_imgMsgData = this.store.state.imgMsgData;
186
+        old_imgMsgData[0] = d_1;
187
+        old_imgMsgData[1] = d_2;
188
+        old_imgMsgData[2] = d_3;
189
+
190
+        this.store.saveState({ imgMsgData: old_imgMsgData });
191
+      }
192
+    });
193
+  }
194
+  async getUrl4() {
195
+    await smallShopService().then(({ data = [], resultCode }) => {
196
+      if (+resultCode === 0) {
197
+        const style__ = [{}, { left: "88%", top: "28%" }, { left: "70%", top: "46%" }, { left: "52%", top: "59%" }, { left: "11%", top: "92%" }, { left: "29%", top: "76%" }]
198
+        data = data.map((x, i) => {
199
+          return {
200
+            ...x,
201
+            total: 0,
202
+            totalName: "",
203
+            styles: style__[x.factoryCode],
204
+            cumulativeProduction: x.production,
205
+            inventory: x.inventory,
206
+          }
207
+        });
208
+        const d_1 = data.filter(x => { return x.factoryCode == 4 })[0];
209
+        const d_2 = data.filter(x => { return x.factoryCode == 5 })[0];
210
+        const d_3 = data.filter(x => { return x.factoryCode == 3 })[0];
211
+        const d_4 = data.filter(x=>{return x.factoryCode == 2})[0];
212
+        const d_5 = data.filter(x => { return x.factoryCode == 1 })[0];
213
+        let old_imgMsgData = this.store.state.imgMsgData;
214
+        old_imgMsgData[3] = d_1;
215
+        old_imgMsgData[4] = d_2;
216
+        old_imgMsgData[5] = d_3;
217
+        old_imgMsgData[6] = d_4;
218
+        old_imgMsgData[7] = d_5;
219
+        console.log(old_imgMsgData, "old_imgMsgData")
220
+        this.store.saveState({ imgMsgData: old_imgMsgData });
221
+      }
222
+    });
223
+  }
224
+  async getUrl5() {
225
+    await smallDayService().then(({ data = [], resultCode }) => {
226
+      if (+resultCode === 0) {
227
+        function getItems(num) {
228
+          const datas = data.filter(x => { return x.factoryCode == num });
229
+          const par = {
230
+            day: datas?.filter(x => { return x.dateType == 1 })?.[0]?.indexValue || 0,
231
+            mood: datas?.filter(x => { return x.dateType == 2 })?.[0]?.indexValue || 0,
232
+            year: datas?.filter(x => { return x.dateType == 3 })?.[0]?.indexValue || 0,
233
+          }
234
+          return par
235
+        }
236
+
237
+        const d_1 = getItems(5);
238
+        const d_2 = getItems(4);
239
+        const d_3 = getItems(3);
240
+        // const d_4 = data.filter(x=>{return x.factoryCode == 2})[0];
241
+        const d_4 = getItems(2);
242
+        const d_5 = getItems(1);
243
+        let old_imgMsgData = this.store.state.imgMsgData;
244
+        old_imgMsgData[3] = { ...old_imgMsgData[3], ...d_1 };
245
+        old_imgMsgData[4] = { ...old_imgMsgData[4], ...d_2 };
246
+        old_imgMsgData[5] = { ...old_imgMsgData[5], ...d_3 };
247
+        old_imgMsgData[6] = { ...old_imgMsgData[6], ...d_4 };
248
+        old_imgMsgData[7] = { ...old_imgMsgData[7], ...d_5 };
249
+        console.log(old_imgMsgData, "1111old_imgMsgData")
250
+        this.store.saveState({ imgMsgData: old_imgMsgData });
251
+      }
252
+    });
253
+  }
254
+
255
+  async getUrl6() {
256
+    await smallMaterialService().then(({ data = [], resultCode }) => {
257
+      if (+resultCode === 0) {
258
+        function getItems(num) {
259
+          const datas = data.filter(x => { return x.factoryCode == num });
260
+          const rawMaterial = datas.map((item,index)=>{
261
+            return {
262
+              prodCatgory:item.prodCatgory,
263
+              indexValue:item.indexValue,
264
+            }
265
+          })
266
+          // const par = {
267
+          //   rawMaterial: [
268
+          //     {
269
+          //       prodCatgory: "原料-鲤辉石",
270
+          //       indexValue: datas?.filter(x => { return x.prodCatgory == 1 })?.[0]?.indexValue || 0,
271
+          //     },
272
+          //     {
273
+          //       prodCatgory: "产品-碳酸锂",
274
+          //       indexValue: datas?.filter(x => { return x.prodCatgory == 2 })?.[0]?.indexValue || 0,
275
+          //     },
276
+          //     {
277
+          //       prodCatgory: "原料-氯化锂",
278
+          //       indexValue: datas?.filter(x => { return x.prodCatgory == 3 })?.[0]?.indexValue || 0,
279
+          //     },
280
+          //     {
281
+          //       prodCatgory: "产品-氢氧化锂",
282
+          //       indexValue: datas?.filter(x => { return x.prodCatgory == 4 })?.[0]?.indexValue || 0,
283
+          //     },
284
+          //     {
285
+          //       prodCatgory: "产品-金属锂",
286
+          //       indexValue: datas?.filter(x => { return x.prodCatgory == 5 })?.[0]?.indexValue || 0,
287
+          //     }
288
+          //   ]
289
+          // }
290
+          return {rawMaterial:rawMaterial}
291
+        }
292
+
293
+        const d_1 = getItems(5);
294
+        const d_2 = getItems(4);
295
+        const d_3 = getItems(3);
296
+        const d_4 = getItems(2);
297
+        const d_5 = getItems(1);
298
+        let old_imgMsgData = this.store.state.imgMsgData;
299
+        old_imgMsgData[3] = { ...old_imgMsgData[3], ...d_1 };
300
+        old_imgMsgData[4] = { ...old_imgMsgData[4], ...d_2 };
301
+        old_imgMsgData[5] = { ...old_imgMsgData[5], ...d_3 };
302
+        old_imgMsgData[6] = { ...old_imgMsgData[6], ...d_4 };
303
+        old_imgMsgData[7] = { ...old_imgMsgData[7], ...d_5 };
304
+        console.log(old_imgMsgData, "1111old_imgMsgData")
305
+        this.store.saveState({ imgMsgData: old_imgMsgData });
306
+      }
307
+    });
308
+  }
309
+  async getUrl3() {
310
+    await updateTimeService().then(({ data = [], resultCode }) => {
311
+      if (+resultCode === 0) {
312
+        this.setState({ updateTime: data?.[0]?.etlTime || '' })
313
+      }
314
+    });
315
+  }
316
+
317
+  componentDidCatch() {
318
+    clearInterval(this.timer);
319
+    this.timer = null;
320
+  }
321
+
322
+  fontMsgChange() {
323
+    this.timer = setInterval(() => {
324
+      const { plannedCompletionData, plannedCompletionNum, manHourData, manHourNum } = this.state;
325
+
326
+      //产量计划完成率
327
+      var p1 = document.getElementById('plannedCompletionBox');
328
+      const datas_ = plannedCompletionData[plannedCompletionNum - 1];
329
+      var res = '<div class="topMsg_box animate__animated animate__zoomIn"><span class="topMsg_number shu1">' + datas_?.value.toFixed(2) + '</span><span class="topMsg_number_2" style={{fontSize: "0.75em",color: "#fff"}}>%</span><p class="topMsg_number_p">' + datas_.name + '</p></div>';
330
+      p1.innerHTML = res;
331
+
332
+      //百万工时损工率
333
+      var p2 = document.getElementById('manHourBox');
334
+      const datas_2 = manHourData[manHourNum - 1];
335
+      var res2 = '<div class="topMsg_box animate__animated animate__zoomIn"><span class="topMsg_number shu1">' + datas_2?.value.toFixed(2) + '</span><span class="topMsg_number_2">%</span><p class="topMsg_number_p">' + datas_2.name + '</p></div>';
336
+      p2.innerHTML = res2;
337
+
338
+      const num_ = plannedCompletionNum + 1 >= plannedCompletionData.length ? 1 : plannedCompletionNum + 1;
339
+      const num_2 = manHourNum + 1 >= manHourData.length ? 1 : manHourNum + 1;
340
+      this.setState({ plannedCompletionNum: num_, manHourNum: num_2 })
341
+    }, 4000)
342
+  }
343
+
344
+  getLeftHtml(x, i) {
345
+    return (
346
+      <li>
347
+        <div className={"top_div"}>
348
+          <div class="animate__animated animate__pulse animate__slower animate__infinite">
349
+            {i === 0 && <img className={"img1"} src={require("@assets/imgs/gvc/qiu1.png").default} alt="" />}
350
+            {i === 1 && <img className={"img1"} src={require("@assets/imgs/gvc/qiu2.png").default} alt="" />}
351
+            {i === 2 && <img className={"img1"} src={require("@assets/imgs/gvc/qiu3.png").default} alt="" />}
352
+            {i === 3 && <img className={"img1"} src={require("@assets/imgs/gvc/qiu4.png").default} alt="" />}
353
+            {i === 0 && <img src={require("@assets/imgs/gvc/qiuH1.png").default} alt="" class="img2 animate__animated animate__heartBeat animate__slower animate__infinite" />}
354
+            {i === 1 && <img src={require("@assets/imgs/gvc/qiuH2.png").default} alt="" class="img2 animate__animated animate__heartBeat animate__slower animate__infinite" />}
355
+            {i === 2 && <img src={require("@assets/imgs/gvc/qiuH3.png").default} alt="" class="img2 animate__animated animate__heartBeat animate__slower animate__infinite" />}
356
+            {i === 3 && <img src={require("@assets/imgs/gvc/qiuH4.png").default} alt="" class="img2 animate__animated animate__heartBeat animate__slower animate__infinite" />}
357
+            <span>{x.txt_name}</span>
358
+          </div>
359
+        </div>
360
+        <div className="text">
361
+          <div>
362
+            <p>累计产量</p>
363
+            <span class="topMsg_number shu1">{x.num1}</span><span class="topMsg_number_2" style={{ fontSize: "0.75em", color: "#fff" }}>吨</span>
364
+          </div>
365
+          <div>
366
+            <p>产品库存</p>
367
+            <span class="topMsg_number shu1">{x.num2}</span><span class="topMsg_number_2" style={{ fontSize: "0.75em", color: "#fff" }}>吨</span>
368
+          </div>
369
+        </div>
370
+      </li>
371
+
372
+    )
373
+  }
374
+
375
+  render() {
376
+    const stores = this.store.state;
377
+    let { totalValue, yearDecline, yearSend, imgMsgData } = this.store.state;
378
+    let { LeftHtml, updateTime } = this.state;
379
+    return (
380
+      <div className={[styles.home_box + ' home_box']}>
381
+        <div className={"all_box"}>
382
+          {/* 视频播放器 */}
383
+          <MapViewTwo></MapViewTwo>
384
+          <div className={"video_box gvc_video"}>
385
+            <div className="alls">
386
+              <video src={require("@assets/imgs/gvc/video2.mp4").default} autoplay="autoplay" loop="loop" class="video2 center_box2 animate__animated animate__fadeIn animate__delay-2s">
387
+              </video>
388
+            </div>
389
+
390
+          </div>
391
+          <div className={"gvcHome home cbHome"}>
392
+            <div className="leftContent">
393
+              <ul>
394
+                {
395
+                  LeftHtml.map((x, i) => {
396
+                    return this.getLeftHtml(x, i)
397
+                  })
398
+                }
399
+              </ul>
400
+            </div>
401
+
402
+            <div className="centerCon">
403
+              <ul className="imgMsg">
404
+                {
405
+                  toJS(imgMsgData).map((item, index) => {
406
+                    return (
407
+                      <li style={{ ...item.styles }} class="animate__animated animate__bounceInUp animate__slower">
408
+                        {/* 矿产 */}
409
+                        {
410
+                          item.totalName && <p className="name">{item.totalName}</p>
411
+                        }
412
+                        {
413
+                          item.totalName && <span class="shu1 nums">{item.total}</span>
414
+                        }
415
+                        {
416
+                          item.totalName && <span className="sma">吨</span>
417
+                        }
418
+                        {/* 基地 */}
419
+                        {
420
+                          item.cumulativeProduction !== null && <div className="hoverR">
421
+                            <div className="hoverDiv chanL">
422
+                              {/* <div style={{ width: "62%","textAlign":'right' }}> */}
423
+                              <div style={{ width: "70%"}}>
424
+                                <p className="title">
425
+                                  库存/吨
426
+                                </p>
427
+                                {
428
+                                  get(item, "rawMaterial", []).map((ra, rai) => {
429
+                                    return <span>{ra.prodCatgory}:{ra.indexValue}</span>
430
+                                  })
431
+                                }
432
+                              </div>
433
+                              <div style={{ width: "38%" }}>
434
+                                <p className="title">
435
+                                  产量/吨
436
+                                </p>
437
+                                <span>日:{item.day}</span>
438
+                                <span>月:{item.mood}</span>
439
+                                <span>年:{item.year}</span>
440
+                              </div>
441
+                            </div>
442
+                          </div>
443
+                        }
444
+                        {
445
+                          item.cumulativeProduction !== null && <div className="chanL text">
446
+                            <div>
447
+                              <p>累计产量</p>
448
+                              <span class="nums shu1">{item.cumulativeProduction}</span><span class="topMsg_number_2" style={{ fontSize: "0.75em", color: "#fff" }}>吨</span>
449
+                            </div>
450
+                            <div>
451
+                              <p>产品库存</p>
452
+                              <span class="nums shu1">{item.inventory}</span><span class="topMsg_number_2" style={{ fontSize: "0.75em", color: "#fff" }}>吨</span>
453
+                            </div>
454
+
455
+                          </div>
456
+                        }
457
+                      </li>
458
+                    )
459
+                  })
460
+                }
461
+              </ul>
462
+            </div>
463
+
464
+            {/* 右侧信息栏 */}
465
+            <div className="rightContent">
466
+
467
+              <div class="bottomContent2 animate__animated animate__fadeInDown animate__slower  animate__delay-1s">
468
+                <div className="bottomContent bigDivPd">
469
+                  <div className="topMsg_content">
470
+                    <RightBottomView></RightBottomView>
471
+                  </div>
472
+                </div>
473
+              </div>
474
+            </div>
475
+            <div className="bottom_box">
476
+              <p style={{ color: "#6a818d", lineHeight: '2px', width: '100%', textAlign: "center" }}>
477
+                更新时间 : {updateTime}
478
+              </p>
479
+            </div>
480
+          </div>
481
+        </div>
482
+      </div>
483
+    )
484
+  }
485
+}
486
+export default Gvc;

+ 4 - 3
src/pages/jurisDiction/view.jsx

@@ -2,7 +2,7 @@
2 2
  * @Author: dayan_hjm
3 3
  * @Date: 2023-11-07 14:21:24 
4 4
  * @Last Modified by: dayan_hjm
5
- * @Last Modified time: 2023-11-08 17:18:11
5
+ * @Last Modified time: 2023-11-21 18:07:33
6 6
  */
7 7
 
8 8
 import React, { useState, useEffect, Component } from "react";
@@ -32,7 +32,7 @@ class JrisDiction extends Component {
32 32
   componentWillMount() { 
33 33
     let searchInstance = queryToObj(); // url查询参数对象化
34 34
     if(window.location.host.indexOf("localhost") > -1){
35
-      this.props.history.replace("/home/operation");
35
+      this.props.history.replace(searchInstance?.type == 1 ? "/home/operation" : "/home/gvc");
36 36
     }else if(searchInstance?.token){
37 37
       this.getUrl(searchInstance?.token);
38 38
     }else{
@@ -47,7 +47,8 @@ class JrisDiction extends Component {
47 47
     await checkToken(token).then(({ data, resultCode }) => {
48 48
       sessionStorage.setItem("tqcVToken",token)
49 49
       if (data?.userId) {
50
-        this.props.history.replace("/home/operation");
50
+        let searchInstance = queryToObj(); // url查询参数对象化
51
+        this.props.history.replace(searchInstance?.type == 1 ? "/home/operation" : "/home/gvc");
51 52
         // this.props.history.push('/')
52 53
       } else {
53 54
         this.setState({ showMsg: true })

+ 2 - 2
src/pages/tqcDataVHome/component/oneQualified.jsx

@@ -2,7 +2,7 @@
2 2
  * @Author: dayan_hjm 一次合格率
3 3
  * @Date: 2023-10-23 09:32:12 
4 4
  * @Last Modified by: dayan_hjm
5
- * @Last Modified time: 2023-11-08 16:45:11
5
+ * @Last Modified time: 2023-11-08 17:53:47
6 6
  */
7 7
 
8 8
 
@@ -75,7 +75,7 @@ class BottomLineForSend extends Component {
75 75
         legend: {
76 76
           data: ['目标一次及格率', '实际一次及格率'],
77 77
           right: 'center',
78
-          padding: [0, 0, 0, 5],
78
+          padding: [10, 0, 0, 5],
79 79
           top: 0,
80 80
           textStyle: {
81 81
             color: "#fff",

+ 6 - 0
src/router/router.js

@@ -14,6 +14,7 @@ import Login from "@pages/login/view.jsx";
14 14
 import NotFound from "@pages/notFound/view.jsx";
15 15
 import Home from '@pages/home/view.jsx';
16 16
 import HomeForchaBaiDao from '@pages/tqcDataVHome/view.jsx';
17
+import GVC from '@pages/gvc/view.jsx';
17 18
 import JurisDiction from '@pages/jurisDiction/view.jsx';
18 19
 import Loading from "@components/Loading/view.jsx";
19 20
 import $store from "@store/";
@@ -61,6 +62,11 @@ const routes = [
61 62
         // component: $store.app.styleCommon.theme == 'chaBaiDao' ? HomeForchaBaiDao : Home,
62 63
         // navigator: true,
63 64
       },
65
+      {
66
+        name: "产供销价值链",
67
+        path: "/home/gvc",
68
+        component: GVC,
69
+      },
64 70
     ],
65 71
   },
66 72
   {

+ 11 - 0
src/utils/util.js

@@ -29,6 +29,17 @@ export function getParams(url = "") {
29 29
   return args;
30 30
 }
31 31
 
32
+
33
+export function sortby(prop, rev = true) {
34
+  // prop 属性名
35
+  // rev  升序降序 默认升序
36
+   return function(a, b) {
37
+      var val1 = a[prop]; 
38
+      var val2 = b[prop]; 
39
+      return rev ? val1 - val2 : val2 - val1;
40
+   }
41
+}
42
+
32 43
 /**下载文件*/
33 44
 export function download(param) {
34 45
   // 文件类型是否为pdf

+ 21 - 0
yarn.lock

@@ -5662,6 +5662,11 @@ enhanced-resolve@^4.0.0, enhanced-resolve@^4.1.0, enhanced-resolve@^4.1.1, enhan
5662 5662
     memory-fs "^0.5.0"
5663 5663
     tapable "^1.0.0"
5664 5664
 
5665
+enquire.js@^2.1.6:
5666
+  version "2.1.6"
5667
+  resolved "https://registry.yarnpkg.com/enquire.js/-/enquire.js-2.1.6.tgz#3e8780c9b8b835084c3f60e166dbc3c2a3c89814"
5668
+  integrity sha512-/KujNpO+PT63F7Hlpu4h3pE3TokKRHN26JYmQpPyjkRD/N57R7bPDNojMXdi7uveAKjYB7yQnartCxZnFWr0Xw==
5669
+
5665 5670
 enquirer@^2.3.5, enquirer@^2.3.6:
5666 5671
   version "2.3.6"
5667 5672
   resolved "https://registry.npmmirror.com/enquirer/-/enquirer-2.3.6.tgz"
@@ -12992,6 +12997,17 @@ react-simple-verify@^1.0.3, react-simple-verify@^1.0.9:
12992 12997
     webpack-manifest-plugin "^2.2.0"
12993 12998
     workbox-webpack-plugin "^4.3.1"
12994 12999
 
13000
+react-slick@^0.29.0:
13001
+  version "0.29.0"
13002
+  resolved "https://registry.yarnpkg.com/react-slick/-/react-slick-0.29.0.tgz#0bed5ea42bf75a23d40c0259b828ed27627b51bb"
13003
+  integrity sha512-TGdOKE+ZkJHHeC4aaoH85m8RnFyWqdqRfAGkhd6dirmATXMZWAxOpTLmw2Ll/jPTQ3eEG7ercFr/sbzdeYCJXA==
13004
+  dependencies:
13005
+    classnames "^2.2.5"
13006
+    enquire.js "^2.1.6"
13007
+    json2mq "^0.2.0"
13008
+    lodash.debounce "^4.0.8"
13009
+    resize-observer-polyfill "^1.5.0"
13010
+
12995 13011
 react-sortable-hoc@^2.0.0:
12996 13012
   version "2.0.0"
12997 13013
   resolved "https://registry.yarnpkg.com/react-sortable-hoc/-/react-sortable-hoc-2.0.0.tgz#f6780d8aa4b922a21f3e754af542f032677078b7"
@@ -14021,6 +14037,11 @@ slice-ansi@^4.0.0:
14021 14037
     astral-regex "^2.0.0"
14022 14038
     is-fullwidth-code-point "^3.0.0"
14023 14039
 
14040
+slick-carousel@^1.8.1:
14041
+  version "1.8.1"
14042
+  resolved "https://registry.yarnpkg.com/slick-carousel/-/slick-carousel-1.8.1.tgz#a4bfb29014887bb66ce528b90bd0cda262cc8f8d"
14043
+  integrity sha512-XB9Ftrf2EEKfzoQXt3Nitrt/IPbT+f1fgqBdoxO3W/+JYvtEOW6EgxnWfr9GH6nmULv7Y2tPmEX3koxThVmebA==
14044
+
14024 14045
 snapdragon-node@^2.0.1:
14025 14046
   version "2.1.1"
14026 14047
   resolved "https://registry.npmmirror.com/snapdragon-node/-/snapdragon-node-2.1.1.tgz"