Browse Source

2021/03/26

lxs 3 years ago
parent
commit
befdcd3e0f
4 changed files with 1194 additions and 368 deletions
  1. 10 0
      src/api/rtp/send_log.js
  2. 979 368
      src/pages/data/visual.vue
  3. 196 0
      src/pages/rtp/send_log.vue
  4. 9 0
      src/router/auth.js

+ 10 - 0
src/api/rtp/send_log.js

@@ -0,0 +1,10 @@
+import request from '@/utils/request'
+
+// list
+export function sendList(params) {
+  return request({
+    url: '/index/GetSendGoodLog',
+    method: 'get',
+    params
+  })
+}

+ 979 - 368
src/pages/data/visual.vue

@@ -1,174 +1,389 @@
 <template>
-  <div v-if="data" class="data-screen1">
-    <el-backtop />
-    <!-- <div class="title">
-      <div class="name">活动订货数据实时追踪</div>
-      <div>五月重启 强力回归 (20200512-14)</div>
-      <div class="countDown">距活动结束仅剩: {{ countDown }}</div>
-    </div> -->
-    <div class="topData">
-      <div class="topData_left">
-        <div class="cardItem">
-          <div class="data">
-            <div class="left">销售金额</div>
-            <div class="right">{{ data.money | toThousandFilter }}<span class="small">元</span></div>
-          </div>
-        </div>
+  <div class="data-screen1">
+    <template v-if="data">
+      <div class="title">
+        <span class="name">活动订货数据实时追踪</span>
+        <span>{{ data.activity_title }} ({{ data.activity_time }})</span>
+        <!-- <div class="countDown">距活动结束仅剩: {{ countDown }}</div> -->
       </div>
-      <div class="topData_right">
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg2.png">
-          <div class="main">
-            <p class="name">精装版</p>
-            <p class="all">{{ data.hard | toThousandFilter }}<span class="small">套</span></p>
-            <p class="today">今日新增:{{ data.hard_today | toThousandFilter }}</p>
+      <div class="style_data">
+        <div class="style_left">
+          <div class="style s_all">
+            <p class="s_all_num">{{ data.hard * 3 + data.simple * 12 + data.old * 12 + data.newold * 18 }}</p>
+            <p class="s_all_text">总条数</p>
           </div>
-        </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg3.png">
-          <div class="main">
-            <p class="name">简约版</p>
-            <p class="all">{{ data.simple | toThousandFilter }}<span class="small">套</span></p>
-            <p class="today">今日新增:{{ data.simple_today | toThousandFilter }}</p>
+          <div class="style s_cotton">
+            <div class="s_title">
+              <img src="@/assets/order_goods/style_icon1.png" alt="">
+              <span>大卫博士纯棉老人版</span>
+            </div>
+            <div class="s_detail">
+              <div class="s_detail_item">
+                <p>{{ data.newold }}</p>
+                <p>数量</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.newold_money }}</p>
+                <p>金额</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.newold_today }}</p>
+                <p>新增</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ getPer(data.newold_money) }}%</p>
+                <p>金额占比</p>
+              </div>
+            </div>
           </div>
-        </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg4.png">
-          <div class="main">
-            <p class="name">老人版</p>
-            <p class="all">{{ data.old | toThousandFilter }}<span class="small">件</span></p>
-            <p class="today">今日新增:{{ data.old | toThousandFilter }}</p>
+          <div class="style s_old">
+            <div class="s_title">
+              <img src="@/assets/order_goods/style_icon2.png" alt="">
+              <span>大卫博士老人版</span>
+            </div>
+            <div class="s_detail">
+              <div class="s_detail_item">
+                <p>{{ data.old }}</p>
+                <p>数量</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.old_money }}</p>
+                <p>金额</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.old_today }}</p>
+                <p>新增</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ getPer(data.old_money) }}%</p>
+                <p>金额占比</p>
+              </div>
+            </div>
           </div>
-        </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg5.png">
-          <div class="main">
-            <p class="name">纯棉老人版</p>
-            <p class="all">{{ data.newold | toThousandFilter }}<span class="small">件</span></p>
-            <p class="today">今日新增:{{ data.newold_today | toThousandFilter }}</p>
+          <div class="style s_smiple">
+            <div class="s_title">
+              <img src="@/assets/order_goods/style_icon3.png" alt="">
+              <span>大卫博士简约版</span>
+            </div>
+            <div class="s_detail">
+              <div class="s_detail_item">
+                <p>{{ data.simple }}</p>
+                <p>数量</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.simple_money }}</p>
+                <p>金额</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.simple_today }}</p>
+                <p>新增</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ getPer(data.simple_money) }}%</p>
+                <p>金额占比</p>
+              </div>
+            </div>
           </div>
-        </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg2.png">
-          <div class="main">
-            <p class="name">手环</p>
-            <p class="all">{{ data.shouhuan | toThousandFilter }}<span class="small">件</span></p>
+          <div class="style s_tester">
+            <div class="s_title">
+              <img src="../../assets/order_goods/style_icon4.png" alt="">
+              <span>大卫博士精装版</span>
+            </div>
+            <div class="s_detail">
+              <div class="s_detail_item">
+                <p>{{ data.hard }}</p>
+                <p>数量</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.hard_money }}</p>
+                <p>金额</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ data.hard_today }}</p>
+                <p>新增</p>
+              </div>
+              <div class="s_detail_item">
+                <p>{{ getPer(data.hard_money) }}%</p>
+                <p>金额占比</p>
+              </div>
+            </div>
           </div>
         </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg3.png">
-          <div class="main">
-            <p class="name">项链</p>
-            <p class="all">{{ data.xianglian | toThousandFilter }}<span class="small">件</span></p>
+        <div class="style_right">
+          <div class="right_top">
+            <div
+              v-for="(v, k, i) in data.honor_num"
+              :key="k"
+              class="gift"
+              :style="
+                `background-image: url(${require(`@/assets/order_goods/gift_bg_${i %
+                  3}.png`)})`
+              "
+              @click="toSeeHonorUser(v.user, '大礼包名单')"
+            >
+              <p>{{ v.count }}</p>
+              <p>{{ k }}</p>
+            </div>
           </div>
+          <div class="right_bottom">
+            <div class="sum">
+              <img src="@/assets/order_goods/money_bg.png" alt="">
+              <div class="sum_del">
+                <p>
+                  {{ data.money }}
+                </p>
+                <p>金额/元</p>
+              </div>
+            </div>
+            <div class="experience">
+              <div>
+                <p>吴桥体验店金额: {{ data["吴桥体验店"] }}</p>
+                <p>临沭体验店金额: {{ data["临沭体验店"] }}</p>
+              </div>
+              <div>
+                <p>
+                  占比:{{
+                    (
+                      Math.floor((data["吴桥体验店"] / data.money) * 10000) / 100
+                    ).toFixed(1) + "%"
+                  }}
+                </p>
+                <p>
+                  占比:
+                  {{
+                    (
+                      Math.floor((data["临沭体验店"] / data.money) * 10000) / 100
+                    ).toFixed(1) + "%"
+                  }}
+                </p>
+              </div>
+            </div>
+          </div>
+          <div class="s_standard">
+            <div
+              class="s_standard_item"
+              :style="`background-image: url(${require(`@/assets/data_display/standard_0.png`)})`"
+              @click="toSeeHonorUser(data.down_user.up, '达标名单')"
+            >
+              <p>{{ data.down_info.up }}</p>
+              <p>达标</p>
+            </div>
+            <div
+              class="s_standard_item"
+              :style="`background-image: url(${require(`@/assets/data_display/standard_1.png`)})`"
+              @click="toSeeHonorUser(data.down_user.down, '未达标名单')"
+            >
+              <p>{{ data.down_info.down }}</p>
+              <p>未达标</p>
+            </div>
+          </div>
+        </div>
+      </div>
+      <!-- <div class="gift_box">
+        <div class="gift_detail">
+          <img src="@/assets/order_goods/bracelet.png" alt="">
+          <p>{{ data.gifts_num['新年台历'] }}</p>
+          <span>新年台历</span>
+        </div>
+        <div class="gift_detail">
+          <img src="@/assets/order_goods/socks.png" alt="">
+          <p>{{ data.gifts_num['远红外项链'] }}</p>
+          <span>远红外项链</span>
         </div>
-        <div class="cardItem">
-          <img class="bg" src="@/assets/databg4.png">
-          <div class="main">
-            <p class="name">大礼包</p>
-            <p class="all">{{ data.big_gift | toThousandFilter }}<span class="small">件</span></p>
+        <div class="gift_detail">
+          <div class="more">
+            +
           </div>
+          <span>待定</span>
+        </div>
+      </div> -->
+      <div class="gift_box s_gift">
+        <div
+          v-for="(v, k, i) in data.gifts_num"
+          :key="`${k}_${i}`"
+          class="s_honor_item s_gift_item"
+        >
+          <p :style="`color: ${i % 3 === 0 ? '#3394F8' : i % 3 === 1 ? '#F76454' : '#FF9E00' }`">{{ v }}</p>
+          <p />
+          <p>{{ k }}</p>
         </div>
       </div>
-    </div>
-    <div v-if="data.list" class="map">
-      <div id="china3" style="width:100%;height:100%;" />
-    </div>
-    <div class="chooseBar">
-      <div class="chooseItem" style="background: #A583F3;" @click="showDataType = 0;">各省排名</div>
-      <div class="chooseItem" style="background: #24A8E8;" @click="showDataType = 1">代理公司排名</div>
-      <div class="chooseItem" style="background: #7fd74d;" @click="showDataType = 2">尺码明细</div>
-      <!-- <div class="chooseItem" style="background: #617FF1;" @click="showDataType = 1">代理公司排名</div>
-      <div class="chooseItem" style="background: #25C1CA;" @click="showDataType = 3">政委战区排名</div>
-      <div class="chooseItem" style="background: #617FF1;" @click="showDataType = 4">销售排名</div>
-      <div class="chooseItem" style="background: #25C1CA;" @click="showDataType = 5">数据分析</div>
-      <div class="chooseItem" style="background: #A583F3;" @click="showDataType = 6">往期对比</div>
-      <div class="chooseItem" style="background: #24A8E8;" @click="showDataType = 7">报名数据</div> -->
-    </div>
-    <div v-show="showDataType === 0" class="header">
-      <span>各省排名</span>
-    </div>
-    <div v-show="showDataType === 0" id="table-wrapper" class="table-wrapper">
-      <el-table v-if="data.list" ref="table" :data="data.list" style="width: 100%" border>
-        <el-table-column label="排名" type="index" align="center" :index="index => index + 1" />
-        <el-table-column label="地区" prop="name" align="center" />
-        <el-table-column label="精装版数量" prop="hard" align="center" />
-        <el-table-column label="简约版数量" prop="simple" align="center" />
-        <el-table-column label="老人版数量" prop="old" align="center" />
-        <el-table-column label="纯棉老人版数量" prop="newold" align="center" />
-        <el-table-column label="总金额" prop="value" align="center" />
-      </el-table>
-    </div>
-    <div v-if="showDataType === 1" class="header">
-      <span>代理公司排名</span>
-    </div>
-    <div v-if="showDataType === 1" class="table-wrapper table-wrapper-rank">
-      <el-table :data="crownRank" style="width: 100%" border>
-        <el-table-column label="排名" type="index" align="center" :index="index => index + 1" />
-        <el-table-column label="代理公司" prop="nickname" align="center" />
-        <el-table-column label="精装版" prop="hard" align="center" />
-        <el-table-column label="简约版" prop="simple" align="center" />
-        <el-table-column label="老人版" prop="old" align="center" />
-        <el-table-column label="纯棉老人版数量" prop="newold" align="center" />
-        <el-table-column label="销售金额" prop="money" align="center" />
-      </el-table>
-    </div>
-    <div v-if="showDataType === 2" class="header">
-      <span>尺码明细</span>
-    </div>
-    <div v-if="showDataType === 2" class="table-wrapper">
-      <el-table :data="sizeList" border>
-        <el-table-column label="商品名称" prop="goods_name" align="center" />
-        <el-table-column label="商品类型" prop="goods_size" align="center" />
-        <el-table-column label="销量" prop="num" align="center" sortable :sort-method="sizeNumSort" />
-      </el-table>
-    </div>
+
+      <div v-if="data.list" class="map">
+        <div id="china3" style="width:100%;height:100%;" />
+      </div>
+      <div class="chooseBar">
+        <div
+          class="chooseItem"
+          style="background: #A583F3;"
+          @click="showDataType = 0"
+        >
+          各省排名
+        </div>
+        <div
+          class="chooseItem"
+          style="background: #24A8E8;"
+          @click="showDataType = 1"
+        >
+          代理公司排名
+        </div>
+        <div
+          class="chooseItem"
+          style="background: #7fd74d;"
+          @click="showDataType = 2"
+        >
+          尺码明细
+        </div>
+      </div>
+      <div v-show="showDataType === 0" class="header">
+        <span>各省排名</span>
+      </div>
+      <div v-show="showDataType === 0" id="table-wrapper" class="table-wrapper">
+        <el-table
+          v-if="data.list"
+          ref="table"
+          :key="showDataType"
+          :data="data.list"
+          style="width: 100%"
+          border
+        >
+          <el-table-column
+            label="排名"
+            type="index"
+            align="center"
+            :index="index => index + 1"
+          />
+          <el-table-column label="地区" prop="name" align="center" />
+          <el-table-column label="精装版数量" prop="hard" align="center" />
+          <el-table-column label="简约版数量" prop="simple" align="center" />
+          <el-table-column label="老人版数量" prop="old" align="center" />
+          <el-table-column label="纯棉老人版数量" prop="newold" align="center" />
+          <el-table-column label="总金额" prop="value" align="center" />
+        </el-table>
+      </div>
+      <div v-if="showDataType === 1" class="header">
+        <span>代理公司排名</span>
+      </div>
+      <div v-if="showDataType === 1" class="table-wrapper table-wrapper-rank">
+        <el-table :key="showDataType" :data="crownRank" style="width: 100%" border>
+          <el-table-column
+            label="排名"
+            type="index"
+            align="center"
+            :index="index => index + 1"
+          />
+          <el-table-column label="代理公司" prop="nickname" align="center" />
+          <el-table-column label="精装版" prop="hard" align="center" />
+          <el-table-column label="简约版" prop="simple" align="center" />
+          <el-table-column label="老人版" prop="old" align="center" />
+          <el-table-column label="纯棉老人版数量" prop="newold" align="center" />
+          <el-table-column label="销售金额" prop="money" align="center" />
+        </el-table>
+      </div>
+      <div v-if="showDataType === 2" class="header">
+        <span>尺码明细</span>
+      </div>
+      <div v-if="showDataType === 2" class="table-wrapper">
+        <el-table :key="showDataType" :data="sizeList" border>
+          <el-table-column label="商品名称" prop="goods_name" align="center" />
+          <el-table-column label="商品类型" prop="goods_size" align="center" />
+          <el-table-column
+            label="销量"
+            prop="num"
+            align="center"
+            sortable
+            :sort-method="sizeNumSort"
+          />
+        </el-table>
+      </div>
+    </template>
+    <!-- 已达标/未达标 -->
+    <el-dialog
+      :title="dialogUser.title"
+      :visible.sync="dialogUser.vis"
+      width="90%"
+      top="50px"
+    >
+      <template v-if="data">
+        <el-table
+          :data="dialogUser.list"
+        >
+          <el-table-column
+            type="index"
+            label="序号"
+            align="center"
+          />
+          <el-table-column
+            prop="nickname"
+            label="昵称"
+            align="center"
+          />
+          <el-table-column
+            prop="realname"
+            label="真实姓名"
+            align="center"
+          />
+          <el-table-column
+            prop="account"
+            label="总金额"
+            align="center"
+          />
+          <!-- <el-table-column
+            prop="pay_account"
+            label="已支付"
+            align="center"
+          /> -->
+        </el-table>
+      </template>
+    </el-dialog>
   </div>
 </template>
 
 <script>
+document.title = '活动-订货数据实时更新'
 import axios from 'axios'
 import { isPC, offset } from '@/utils'
 import { deepClone } from '@/utils'
 import { getSizeList } from '@/api/datascreen'
+
+// import { getSizeList, goodTypeList, provinceTeam, baseData } from '@/api/datascreen'
 export default {
-  name: 'DataVisual',
+  name: 'DataScreen1',
   data() {
     return {
-      data: {},
+      data: null,
       showDataType: -1,
       crownRank: [],
-      s: 1589205600000,
-      e: 1589471999000,
       n: 0,
-      sizeList: []
-    }
-  },
-  computed: {
-    countDown() {
-      const add0 = num => num < 10 ? '0' + num : num
-      const sec = Math.floor((this.e - this.n) / 1000)
-      const day = Math.floor(sec / 86400)
-      const hour = Math.floor((sec % 86400) / 3600)
-      const minite = Math.floor((sec - 86400 * day - hour * 3600) / 60)
-      const second = Math.floor(sec - 86400 * day - hour * 3600 - minite * 60)
-      return `${add0(day)}天${add0(hour)}时${add0(minite)}分${add0(second)}秒`
+      sizeList: [],
+      dataPassword: '',
+      dialogUser: {
+        list: [],
+        title: '',
+        vis: false
+      }
     }
   },
   watch: {
-    showDataType(n) { // 点击数据类型
+    showDataType(n) {
+      // 点击数据类型
       if (n === 1) {
         this.loading = this.$loading()
-        axios.get('//api.admin.app.jiuweiyun.cn/api/data/get_crown').then(({ data: { data: { list }}}) => {
-          list.sort((a, b) => b.money - a.money)
-          this.crownRank = list
-          this.loading.close()
-        })
+        axios
+          .get('//api.admin.app.jiuweiyun.cn/api/data/get_crown')
+          .then(({ data: { data: { list }}}) => {
+            list.sort((a, b) => b.money - a.money)
+            this.crownRank = list
+            this.loading.close()
+          })
       } else if (n === 2) {
         this.getSizeList()
       }
       this.$nextTick(() => {
-        window.scrollTo(0, document.getElementsByClassName('chooseBar')[0].offsetTop)
+        window.scrollTo(
+          0,
+          document.getElementsByClassName('chooseBar')[0].offsetTop
+        )
       })
     }
   },
@@ -177,25 +392,33 @@ export default {
       this.$router.replace({ path: '/2' })
       return
     }
-    this.loading = this.$loading()
-    this.request()
-    // this.timer = setInterval(() => this.request(), 30000)
-  },
-  mounted() {
-    this.n = Date.now()
-    // if (this.n >= this.s && this.n <= this.e) {
-    this.timer = setInterval(() => {
-      // if (this.n > this.e) {
-      //   clearInterval(this.timer)
-      // }
-      this.request()
-    }, 1000 * 30)
-    // }
+    this.init()
   },
   beforeDestroy() {
     clearInterval(this.timer)
   },
-  methods: { // 然而实际的需求却是
+  methods: {
+    toSeeHonorUser(list, title) {
+      this.dialogUser.list = list
+      this.dialogUser.title = title
+      this.dialogUser.vis = true
+    },
+    init() {
+      this.request()
+      this.timer = setInterval(() => {
+        this.requset()
+      }, 1000 * 30)
+    },
+    getPer(num) {
+      const all =
+        this.data.hard_money +
+        this.data.old_money +
+        this.data.simple_money +
+        this.data.newold_money
+      const per = Math.floor((num / all) * 10000) / 100
+      const last = per.toFixed(1)
+      return last
+    },
     sizeNumSort(a, b) {
       return a.num - b.num
     },
@@ -207,29 +430,33 @@ export default {
       })
     },
     request() {
-      axios.get('//api.admin.app.jiuweiyun.cn/api/data/data').then(({ data: res }) => {
-        this.loading.close()
-        this.data = res.data
-        res.data.list.sort((a, b) => b.value - a.value)
-        let max = 0
-        let maxIndex = 0
-        this.data.list.forEach((e, i) => {
-          if (e.value > max) {
-            max = e.value
-            maxIndex = i
-          }
-        })
-        const step = Math.floor(max / 6)
-        this.$nextTick(() => {
-          const echarts = window.echarts.init(document.getElementById('china3'))
-          echarts.setOption({
-            backgroundColor: '#FFFFFF',
-            tooltip: {
-              trigger: 'item',
-              alwaysShowContent: true,
-              formatter: params => {
-                console.log(params)
-                return `
+      this.loading = this.$loading()
+      axios
+        .get('//api.admin.app.jiuweiyun.cn/api/data/data')
+        .then(({ data: res }) => {
+          this.loading.close()
+          this.data = res.data
+          res.data.list.sort((a, b) => b.value - a.value)
+          let max = 0
+          let maxIndex = 0
+          this.data.list.forEach((e, i) => {
+            if (e.value > max) {
+              max = e.value
+              maxIndex = i
+            }
+          })
+          const step = Math.floor(max / 6)
+          this.$nextTick(() => {
+            const echarts = window.echarts.init(
+              document.getElementById('china3')
+            )
+            echarts.setOption({
+              backgroundColor: '#FFFFFF',
+              tooltip: {
+                trigger: 'item',
+                alwaysShowContent: true,
+                formatter: params => {
+                  return `
                   省份:${params.name} <br />
                   排名:${params.dataIndex + 1} <br />
                   总订货金额:${params.value} <br />
@@ -237,257 +464,641 @@ export default {
                   简约版件数:${this.data.list[params.dataIndex].simple} <br />
                   老人版件数:${this.data.list[params.dataIndex].old} <br />
                 `
-              }
-            },
-            visualMap: {
-              show: true,
-              x: 'left',
-              y: 'bottom',
-              splitList: [
-                { start: step * 6, end: step * 7, label: `${step * 6} - ${step * 7} 元` },
-                { start: step * 5, end: step * 6, label: `${step * 5} - ${step * 6} 元` },
-                { start: step * 4, end: step * 5, label: `${step * 4} - ${step * 5} 元` },
-                { start: step * 3, end: step * 4, label: `${step * 3} - ${step * 4} 元` },
-                { start: step * 2, end: step * 3, label: `${step * 2} - ${step * 3} 元` },
-                { start: step * 1, end: step * 2, label: `${step * 1} - ${step * 2} 元` },
-                { start: 1, end: step * 1, label: `${1} - ${step * 1} 元` },
-                { start: 0, end: 0, label: '0 元' }
-              ],
-              color: ['#30A6FE', '#44AFFE', '#5CB9FE', '#71C2FE', '#89CDFF', '#A5D8FE', '#C5E5FD', '#EFEFEF']
-            },
-            series: [{
-              name: '销售套数',
-              type: 'map',
-              mapType: 'china',
-              aspectScale: 1,
-              zoom: 1.23,
-              label: {
-                normal: { show: true },
-                emphasis: { show: true }
+                }
               },
-              data: this.data.list
-            }]
-          })
-          if (!this.click) {
-            this.click = true
-            echarts.on('click', params => {
-              this.tabbleChartData = deepClone(this.data.list)
-              this.dispatchClick = true
-              this.showDataType = 0
-              this.$nextTick(() => {
-                const to = document.getElementsByClassName('el-table__row')[params.dataIndex]
-                window.scrollTo(0, offset(to).top)
+              visualMap: {
+                show: true,
+                x: 'left',
+                y: 'bottom',
+                splitList: [
+                  {
+                    start: step * 6,
+                    end: step * 7,
+                    label: `${step * 6} - ${step * 7} 元`
+                  },
+                  {
+                    start: step * 5,
+                    end: step * 6,
+                    label: `${step * 5} - ${step * 6} 元`
+                  },
+                  {
+                    start: step * 4,
+                    end: step * 5,
+                    label: `${step * 4} - ${step * 5} 元`
+                  },
+                  {
+                    start: step * 3,
+                    end: step * 4,
+                    label: `${step * 3} - ${step * 4} 元`
+                  },
+                  {
+                    start: step * 2,
+                    end: step * 3,
+                    label: `${step * 2} - ${step * 3} 元`
+                  },
+                  {
+                    start: step * 1,
+                    end: step * 2,
+                    label: `${step * 1} - ${step * 2} 元`
+                  },
+                  { start: 1, end: step * 1, label: `${1} - ${step * 1} 元` },
+                  { start: 0, end: 0, label: '0 元' }
+                ],
+                color: [
+                  '#30A6FE',
+                  '#44AFFE',
+                  '#5CB9FE',
+                  '#71C2FE',
+                  '#89CDFF',
+                  '#A5D8FE',
+                  '#C5E5FD',
+                  '#EFEFEF'
+                ]
+              },
+              series: [
+                {
+                  name: '销售套数',
+                  type: 'map',
+                  mapType: 'china',
+                  aspectScale: 1,
+                  zoom: 1.23,
+                  label: {
+                    normal: { show: true },
+                    emphasis: { show: true }
+                  },
+                  data: this.data.list
+                }
+              ]
+            })
+            if (!this.click) {
+              this.click = true
+              echarts.on('click', params => {
+                this.tabbleChartData = deepClone(this.data.list)
+                this.dispatchClick = true
+                this.showDataType = 0
+                this.$nextTick(() => {
+                  const to = document.getElementsByClassName('el-table__row')[
+                    params.dataIndex
+                  ]
+                  window.scrollTo(0, offset(to).top)
+                })
               })
+            }
+            echarts.dispatchAction({
+              type: 'showTip',
+              seriesIndex: 0,
+              dataIndex: maxIndex
             })
-          }
-          echarts.dispatchAction({
-            type: 'showTip',
-            seriesIndex: 0,
-            dataIndex: maxIndex
           })
         })
-      })
     }
   }
 }
 </script>
 
 <style lang="scss" scoped>
-  .data-screen1 {
-    padding: 0.5vw 1vw;
-    box-sizing: border-box;
-    background: #F2F4F5;
-    .title {
-      height: 128px;
-      background: #ffffff;
-      display: flex;
-      justify-content: space-around;
-      align-items: center;
-      flex-direction: column;
-      font-weight: bold;
-      .name {
-        font-size: 34px;
+.data-screen1 {
+  // padding: 0.5vw 1vw;
+  box-sizing: border-box;
+  background: #f2f4f5;
+  .title {
+    // height: 128px;
+    text-align: left;
+    height: 88px;
+    line-height: 88px;
+    padding-left: 41px;
+    width: 100%;
+    background: #ffffff;
+    // display: flex;
+    // justify-content: space-around;
+    // align-items: center;
+    // flex-direction: column;
+    font-weight: bold;
+    div {
+      font-size: 18px;
+    }
+    .name {
+      font-size: 24px;
+      color: #ea4a41;
+    }
+    .countDown {
+      color: red;
+    }
+  }
+  .topData {
+    background: white;
+    display: flex;
+    justify-content: space-between;
+    .topData_left {
+      width: 240px;
+      height: 240px;
+      box-sizing: border-box;
+      padding: 22px 10px;
+      .cardItem {
+        .right {
+          font-size: 30px !important;
+        }
       }
-      .countDown {
-        color: red;
+      background-image: url(../../assets/databg1.png);
+      background-size: 100% 100%;
+      .small {
+        font-size: 20px;
       }
     }
-    .topData {
-      background: white;
+    .topData_right {
+      width: calc(100% - 250px);
+      margin-left: 10px;
       display: flex;
-      justify-content: space-between;
-      .topData_left {
-        width: 240px;
-        height: 240px;
+      justify-content: flex-start;
+      flex-wrap: wrap;
+      .cardItem {
+        width: calc(100% / 4 - 10px);
+        height: 115px;
         box-sizing: border-box;
-        padding: 22px 10px;
-        .cardItem {
-          .right{
-            font-size: 30px !important;
+        &:nth-of-type(5),
+        &:nth-of-type(6),
+        &:nth-of-type(7) {
+          width: calc(100% / 3 - 10px);
+        }
+        .main {
+          width: 100%;
+          height: 100%;
+          color: #ffffff;
+          display: flex;
+          justify-content: space-between;
+          flex-direction: column;
+          padding: 10px;
+        }
+        p {
+          margin: 0 !important;
+        }
+        .name {
+          font-size: 22px !important;
+        }
+        .all {
+          font-size: 36px !important;
+          text-align: right;
+          .small {
+            font-size: 20px;
           }
         }
-        background-image: url(../../assets/databg1.png);
-        background-size: 100% 100%;
-        .small {
-          font-size: 20px;
+        .today {
+          font-size: 16px !important;
         }
       }
-      .topData_right {
-        width: calc(100% - 250px);
-        margin-left: 10px;
+    }
+    .cards {
+      height: 8vw;
+      display: flex;
+      justify-content: space-between;
+    }
+    .cardItem {
+      margin-right: 10px;
+      &:nth-last-of-type(1) {
+        margin-right: 0;
+      }
+      height: 100%;
+      position: relative;
+      z-index: 1;
+      > .bg {
+        position: absolute;
+        width: 100%;
+        height: 100%;
+        z-index: -1;
+      }
+      > .data {
+        height: 100%;
+        color: white;
+        box-sizing: border-box;
+        padding: 1vw;
         display: flex;
-        justify-content: flex-start;
-        flex-wrap: wrap;
-        .cardItem {
-          width: calc(100% / 4 - 10px);
-          height: 115px;
-          box-sizing: border-box;
-          &:nth-of-type(5), &:nth-of-type(6), &:nth-of-type(7) {
-            width: calc(100% / 3 - 10px);
-          }
-          .main {
-            width: 100%;
-            height: 100%;
-            color: #ffffff;
-            display: flex;
-            justify-content: space-between;
-            flex-direction: column;
-            padding: 10px;
+        flex-direction: column;
+        justify-content: space-between;
+        > .top {
+          display: flex;
+          justify-content: space-between;
+          > .left {
+            font-size: 1.5vw;
           }
-          p{
-            margin: 0 !important;
+          > .right {
+            font-size: 2vw;
+            > span {
+              font-size: 1.5vw;
+            }
           }
-          .name {
-            font-size: 22px !important;
+        }
+        > .bottom {
+          display: flex;
+          justify-content: space-between;
+          align-items: flex-end;
+          > .left {
+            font-size: 2vw;
           }
-          .all {
-            font-size: 36px !important;
-            text-align: right;
-            .small {
-              font-size: 20px;
+          > .right {
+            font-size: 0.83vw;
+            > .reduce {
+              color: #f7534f;
             }
           }
-          .today {
-            font-size: 16px !important;
+          &.small {
+            > .left {
+              font-size: 1vw !important;
+            }
           }
         }
       }
-      .cards {
-        height: 8vw;
-        display: flex;
-        justify-content: space-between;
+    }
+  }
+  .chooseBar {
+    overflow: hidden;
+    .chooseItem {
+      float: left;
+      width: 10vw;
+      height: 4.17vw;
+      margin: 0.5vw 1.05vw;
+      line-height: 4.17vw;
+      text-align: center;
+      cursor: pointer;
+    }
+  }
+  .map {
+    height: 567px;
+    padding: 0 30px;
+  }
+  .header {
+    height: 60px;
+    display: flex;
+    justify-content: space-between;
+    align-items: center;
+    color: #43464d;
+    font-size: 18px;
+    font-weight: bold;
+    box-sizing: border-box;
+    padding: 0 40px;
+    background: #f5f5f5;
+  }
+  .el-table {
+    td,
+    th,
+    .label {
+      padding: 8px 0;
+      text-align: center;
+    }
+  }
+  .table-wrapper {
+    padding: 0 32px;
+  }
+  .table-wrapper5 {
+    > .el-table {
+      >>> td[class^="el-table_6_column_"] {
+        padding: 0;
+        display: table-cell;
       }
-      .cardItem {
-        margin-right: 10px;
-        &:nth-last-of-type(1) {
-          margin-right: 0;
-        }
-        height: 100%;
+      >>> .cell {
+        padding: 0;
+      }
+      .merge-item-item {
+        font-size: 14px;
+        line-height: 40px;
+        border-bottom: 1px solid rgb(223, 230, 236);
+      }
+      .merge-item-item:last-child {
+        border-bottom: none;
+      }
+    }
+  }
+}
+.style_data {
+  padding: 0 30px;
+  box-sizing: border-box;
+  display: flex;
+  justify-content: space-between;
+  align-items: flex-start;
+  .style_left {
+    flex: 1;
+    min-width: 0;
+    margin-right: 30px;
+    .style {
+      width: 100%;
+      height: 233px;
+      margin-top: 30px;
+      &.s_all {
+        background: url(../../assets/data_display/all.png) no-repeat center;
+        background-size: 100%;
         position: relative;
-        z-index: 1;
-        >.bg {
+        overflow: hidden;
+        .s_all_num {
           position: absolute;
-          width: 100%;
-          height: 100%;
-          z-index: -1;
+          font-size: 58px;
+          color: #333333;
+          left: 190px;
+          bottom: 45px;
+          width: max-content;
+          text-align: center;
+          color: #3394f8 !important;
         }
-        >.data {
-          height: 100%;
-          color: white;
-          box-sizing: border-box;
-          padding: 1vw;
-          display: flex;
-          flex-direction: column;
-          justify-content: space-between;
-          >.top {
-            display: flex;
-            justify-content: space-between;
-            >.left {
-              font-size: 1.5vw;
-            }
-            >.right {
-              font-size: 2vw;
-              >span {
-                font-size: 1.5vw;
-              }
+        .s_all_text {
+          color: #000000;
+          font-size: 28px;
+          position: absolute;
+          left: 185px;
+          bottom: 35px;
+        }
+      }
+      .s_title {
+        padding: 30px 0 0 30px;
+        span {
+          font: size 24px;
+          color: #333;
+          font-weight: bold;
+          margin-left:15px;
+        }
+      }
+      img {
+        background-size: 100% 100%;
+        vertical-align: middle;
+      }
+      .s_detail {
+        display: flex;
+        justify-content: space-around;
+        align-items: center;
+        .s_detail_item {
+          text-align: center;
+          &:nth-of-type(1) {
+            p:nth-of-type(1) {
+              color: #3394f8 !important;
             }
           }
-          >.bottom {
-            display: flex;
-            justify-content: space-between;
-            align-items: flex-end;
-            >.left {
-              font-size: 2vw;
+          &:nth-of-type(2) {
+            p:nth-of-type(1) {
+              color: #ea4a41 !important;
             }
-            >.right {
-              font-size: 0.83vw;
-              >.reduce {
-                color: #F7534F;
-              }
+          }
+          &:nth-of-type(3) {
+            p:nth-of-type(1) {
+              color: #ff9e00 !important;
             }
-            &.small {
-              >.left {
-                font-size: 1vw!important;
-              }
+          }
+          &:nth-of-type(4) {
+            p:nth-of-type(1) {
+              color: #333333 !important;
             }
           }
+          p:first-child {
+            font-size: 42px;
+            margin-bottom: 5px;
+          }
+          p:last-child {
+            font-size: 18px;
+          }
         }
       }
     }
-    .chooseBar {
-      overflow: hidden;
-      .chooseItem {
-        float: left;
-        width: 10vw;
-        height: 4.17vw;
-        margin: 0.5vw 1.05vw;
-        line-height: 4.17vw;
-        text-align: center;
-        cursor: pointer;
+    .s_cotton {
+      background: url("../../assets/order_goods/style_bg1.png") no-repeat;
+      img {
+        width: 30px;
+        height: 34px;
+      }
+    }
+    .s_old {
+      background: url("../../assets/order_goods/style_bg2.png") no-repeat;
+      img {
+        width: 30px;
+        height: 29px;
+      }
+    }
+    .s_smiple {
+      background: url("../../assets/order_goods/style_bg3.png") no-repeat;
+      img {
+        width: 25px;
+        height: 30px;
       }
     }
-    .map {
-      height: 567px;
+    .s_tester {
+      background: url("../../assets/order_goods/style_bg4.png") no-repeat;
+      img {
+        width: 30px;
+        height: 30px;
+      }
     }
-    .header {
-      height: 60px;
+  }
+  .style_right {
+    width: 50%;
+    margin-top: 30px;
+    height: 100%;
+    .right_top {
       display: flex;
       justify-content: space-between;
       align-items: center;
-      color: #43464D;
-      font-size: 18px;
-      font-weight: bold;
-      box-sizing: border-box;
-      padding: 0 40px;
-      background: #F5F5F5;
+      .gift {
+        color: #fff;
+        width: 301px;
+        height: 233px;
+        background-repeat: no-repeat;
+        background-size: 100% 100%;
+        position: relative;
+        &:not(:first-child) {
+          margin-left: 30px;
+        }
+        p {
+          position: absolute;
+          color: #ffffff;
+          left: 15px;
+          &:first-child {
+            font-size: 42px;
+            bottom: 30px;
+          }
+          &:last-child {
+            font-size: 18px;
+            bottom: 15px;
+          }
+        }
+      }
     }
-    .el-table {
-      td, th, .label {
-        padding: 8px 0;
-        text-align: center;
+    .right_bottom {
+      background: #fff;
+      margin-top: 30px;
+      text-align: center;
+      padding: 67px 0;
+      border-radius: 12px;
+      flex: 1;
+      margin-bottom: 30px;
+      .sum {
+        position: relative;
+        image {
+          width: 100%;
+          height: 472px;
+        }
+        .sum_del {
+          position: absolute;
+          top: 78px;
+          left: 50%;
+          transform: translateX(-50%);
+          color: #fff;
+          text-align: center;
+          p {
+            &:first-child {
+              font-size: 77px;
+              margin-bottom: 30px;
+            }
+            &:last-child {
+              font-size: 43px;
+            }
+          }
+        }
+      }
+      .experience {
+        width: 100%;
+        display: flex;
+        justify-content: center;
+        align-items: center;
+        div {
+          &:last-child {
+            margin-left: 170px;
+          }
+        }
+        p {
+          font-size: 28px;
+        }
       }
     }
-    .table-wrapper {
-      padding: 0 32px;
+    .s_standard {
+      width: 100%;
+      height: 233px;
+      margin: 0 auto;
+      display: flex;
+      align-items: center;
+      justify-content: space-between;
+      .s_standard_item {
+        flex: 1;
+        overflow: hidden;
+        height: 100%;
+        background-repeat: no-repeat;
+        background-size: cover;
+        background-position: 50% 50%;
+        position: relative;
+        margin-right: 15px;
+        &:nth-last-of-type(1) {
+          margin-right: 0;
+          margin-left: 15px;
+        }
+        p{
+          position: absolute;
+          color: #ffffff;
+          left: 50px;
+          &:nth-of-type(1) {
+            font-size: 58px;
+            bottom: 40px;
+          }
+          &:nth-last-of-type(1) {
+            font-size: 28px;
+            bottom: 15px;
+          }
+        }
+      }
     }
-    .table-wrapper5 {
-      >.el-table {
-        >>> td[class^="el-table_6_column_"] {
-          padding: 0;
-          display: table-cell;
+  }
+}
+.gift_box {
+  width: 100%;
+  display: flex;
+  justify-content: flex-start;
+  align-items: center;
+  margin: 30px 0;
+  padding: 0 30px;
+  // .gift_detail {
+  //   width: 442px;
+  //   height: 293px;
+  //   background-color: #fff;
+  //   display: flex;
+  //   flex-direction: column;
+  //   align-items: center;
+  //   justify-content: center;
+  //   border-radius: 12px;
+  //   &:not(:first-child) {
+  //     margin-left: 20px;
+  //   }
+  //   p {
+  //     font-size: 53px;
+  //     margin: 20px 0;
+  //   }
+  //   span {
+  //     font-size: 22px;
+  //   }
+  //   .more {
+  //     width: 76px;
+  //     height: 76px;
+  //     text-align: center;
+  //     line-height: 76px;
+  //     border-radius: 50%;
+  //     background: #f8f8f8;
+  //     font-size: 50px;
+  //     color: #999;
+  //     margin-bottom: 20px;
+  //   }
+  // }
+}
+
+    .s_gift{
+      .s_gift_item {
+        width: 442px;
+        height: 293px;
+        margin-right: 30px;
+        background: #ffffff;
+        display: flex;
+        align-items: center;
+        justify-content: center;
+        flex-direction: column;
+        padding: 18px 0;
+        box-sizing: border-box;
+        &:nth-of-type(1) {
+          p:nth-of-type(2) {
+            background: linear-gradient(to right, #A3CFF9, #487FE5)
+          }
         }
-        >>> .cell {
-          padding: 0;
+        &:nth-of-type(2) {
+          p:nth-of-type(2) {
+            background: linear-gradient(to right, #FF7801, #FE1F00)
+          }
         }
-        .merge-item-item {
-          font-size: 14px;
-          line-height: 40px;
-          border-bottom: 1px solid rgb(223, 230, 236);
+        &:nth-of-type(3) {
+          p:nth-of-type(2) {
+            background: linear-gradient(to right, #FBA753, #FA803C)
+          }
         }
-        .merge-item-item:last-child {
-          border-bottom: none;
+        p{
+          text-align: center;
+          width: 100%;
+          position: initial;
+          margin: 0;
+          &:nth-of-type(1) {
+            font-size: 58px;
+          }
+          &:nth-of-type(2) {
+            width: 30px;
+            height: 4px;
+            border-radius: 4px;
+            margin: 30px 0;
+          }
+          &:nth-last-of-type(1) {
+            color: #333333;
+            font-size: 28px;
+          }
         }
       }
     }
-  }
+.data_password {
+  position: fixed;
+  top: 0;
+  left: 0;
+  right: 0;
+  bottom: 0;
+  z-index: 99;
+  display: flex;
+  align-items: center;
+  justify-content: center;
+  flex-direction: column;
+  background: #fff;
+}
 </style>

+ 196 - 0
src/pages/rtp/send_log.vue

@@ -0,0 +1,196 @@
+<template>
+  <div class="app-container">
+    <el-input
+      v-model="params.search_name"
+      type="text"
+      placeholder="所属人昵称 / 手机号"
+      style="width: 250px"
+    />
+    <el-input
+      v-model="params.code"
+      type="text"
+      placeholder="防伪码"
+      style="width: 400px"
+      :readonly="true"
+    >
+      <template slot="append">
+        <el-upload
+          style="display: inline-block;"
+          action=""
+          :show-file-list="false"
+          :http-request="uploadQrocdeDecode"
+          accept=".jpeg, .jpg, .png"
+        >
+          <span style="cursor: pointer">上传图片</span>
+        </el-upload>
+      </template>
+    </el-input>
+    <el-select v-model="params.op_phone" placeholder="请选择仓库">
+      <el-option
+        v-for="item in opNames"
+        :key="item.phone"
+        :label="item.name"
+        :value="item.phone"
+      />
+    </el-select>
+    <el-select v-model="params.good_select_id" placeholder="请选择商品类型">
+      <el-option
+        v-for="item in goodSelects"
+        :key="item.id"
+        :label="item.name"
+        :value="item.id"
+      />
+    </el-select>
+    <el-date-picker
+      v-model="params.time"
+      type="datetimerange"
+      range-separator="至"
+      start-placeholder="开始日期"
+      end-placeholder="结束日期"
+      value-format="yyyy-MM-dd hh:mm:ss"
+    />
+    <el-button type="primary" @click="toSearch">搜索</el-button>
+    <el-table
+      :data="list"
+      :header-cell-style="{ background: '#f8fbfc' }"
+      border
+      stripe
+      style="margin-top: 20px"
+    >
+      <el-table-column
+        type="index"
+        label="序号"
+        width="50"
+        :index="i => (params.page_index - 1) * params.page_size + i + 1"
+        align="center"
+      />
+      <el-table-column
+        label="发货仓库"
+        align="center"
+        prop="op_name"
+      />
+      <el-table-column
+        prop="accept_name"
+        label="所属人昵称"
+        align="center"
+      />
+      <el-table-column
+        prop="accept_phone"
+        label="所属人手机号"
+        align="center"
+      />
+      <el-table-column
+        label="商品名称"
+        align="center"
+      >
+        <template slot-scope="{ row: { code } }">
+          {{ code.get_goods.good_name }}
+        </template>
+      </el-table-column>
+      <el-table-column
+        label="防伪码类型"
+        align="center"
+      >
+        <template slot-scope="{ row: { code } }">
+          {{ code.model }}
+        </template>
+      </el-table-column>
+      <el-table-column
+        label="发货时间"
+        align="center"
+        prop="created_at"
+      />
+    </el-table>
+    <pagination
+      :total="total"
+      :limit="params.page_size"
+      :page="params.page_index"
+      @pagination="changeTracePagination"
+      @update:limit="changeTracePagination"
+    />
+  </div>
+</template>
+<script>
+import Qrcode from 'qrcode-decoder'
+import { sendList } from '@/api/rtp/send_log'
+export default {
+  data() {
+    return {
+      opNames: [
+        { phone: '15220141101', name: '公司仓库' },
+        { phone: '17333738670', name: '吴桥体验店' },
+        { phone: '13581056035', name: '临沭体验店' }
+      ],
+      goodSelects: [
+        { id: 1, name: '精装版' },
+        { id: 2, name: '简约版' },
+        { id: 3, name: '老人版' },
+        { id: 4, name: '纯棉版' }
+      ],
+      params: {
+        page_index: 1,
+        page_size: 20,
+        search_name: '',
+        op_phone: '',
+        code: '',
+        start_time: '',
+        end_time: '',
+        good_select_id: '',
+        time: ''
+      },
+      list: [],
+      total: 0
+    }
+  },
+  mounted() {
+    this.getSendList()
+  },
+  methods: {
+    toSearch() {
+      this.params.page_index = 1
+      this.getSendList()
+    },
+    changeTracePagination({ page, limit }) {
+      this.params.page_index = page
+      this.params.page_size = limit
+      this.getSendList()
+    },
+    getSendList() {
+      const { time } = this.params
+      const _p = Object.assign({}, this.params)
+      Reflect.deleteProperty(_p, 'time')
+      _p.start_time = time ? time[0] : ''
+      _p.end_time = time ? time[1] : ''
+      const loading = this.$loading()
+      sendList(_p).then(res => {
+        loading.close()
+        if (res.code === 200) {
+          this.list = res.data.list
+          this.total = res.data.total
+        } else {
+          this.$message.error(res.message || '获取发货日志失败')
+        }
+      }).catch(e => {
+        loading.close()
+        this.$message.error('获取发货日志失败')
+      })
+    },
+    uploadQrocdeDecode({ file }) {
+      const url = window.URL.createObjectURL(file)
+      const qrcode = new Qrcode()
+      qrcode.decodeFromImage(url).then(({ data }) => {
+        if (data) {
+          const _a = data.split('/')
+          const _c = _a[_a.length - 1]
+          this.params.code = _c
+        } else {
+          this.$message.error('该图片未解析出任何内容')
+        }
+      })
+    }
+  }
+}
+</script>
+<style lang="scss" scoped>
+
+</style>

+ 9 - 0
src/router/auth.js

@@ -1013,6 +1013,15 @@ export const asyncRoutes = [
           title: '防伪追溯',
           noCache: true
         }
+      },
+      {
+        path: 'send_log',
+        component: '/rtp/send_log',
+        name: 'productRtpSendLog',
+        meta: {
+          title: '发货日志',
+          noCache: true
+        }
       }
     ]
   },