管道基础大数据平台系统开发-【前端】-新系統界面
TreeWish
2023-02-28 234409bb4a612c5b69b78b1e844492f0a7122521
工程&管线接口对接
已添加2个文件
已修改12个文件
1230 ■■■■ 文件已修改
src/api/screen.js 44 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/img/Screen/all.png 补丁 | 查看 | 原始文档 | blame | 历史
src/components/Screen/bottom.vue 100 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/Screen/left.vue 89 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/Screen/right.vue 85 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/Screen/top.vue 57 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/BaseBarChart.vue 55 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/BaseLineChart.vue 46 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/BasePieChart .vue 66 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/DataStorageType.vue 429 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/FileFormat.vue 19 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/ServiceType.vue 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/chart/projectintroduction.vue 214 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Thematic/index.vue 24 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/api/screen.js
@@ -1,6 +1,6 @@
import request from "@/utils/request"
// ä¸€å¼ å›¾æ•°æ®æŽ¥å£
// ä¸€å¼ å›¾æ•°æ®æŽ¥å£
// æ•°æ®ç”³è¯·
export function countDataApply(params) {
@@ -45,11 +45,45 @@
}
//服务访问次数
export  function  GetServicesVisitsCount(){
  return  request.get("/oneMap/countDataServiceType")
export function GetServicesVisitsCount(params) {
  return request.get("/oneMap/countDataServiceType", { params: params })
}
//按照类别访问统计访问次数
export  function  GetTypeVisitsCount(){
  return  request.get("/oneMap/countLargeCategories")
export function GetTypeVisitsCount(params) {
  return request.get("/oneMap/countLargeCategories", { params: params })
}
//全国站场座数、阀室、管道数等
export function countZhPipeStations(params) {
  return request.get("/oneMap/countZhPipeStations", { params: params })
}
//全国管网图输送介质长度
export function countZhPipeMapLength(params) {
  return request.get("/oneMap/countZhPipeMapLength", { params: params })
}
//地灾countLargeCategories
export function countLargeCategories(params) {
  return request.get("/oneMap/countLargeCategories", { params: params })
}
// èŽ·å–é¡¹ç›®åˆ—è¡¨  éƒ¨åˆ†ä¿¡æ¯ä¸å…¨
export function selectProjectFileList(params) {
  return request.get("/oneMap/selectProjectFileList", { params: params })
}
// å•个项目文件下载
export function countProjectType(params) {
  return request.get("/oneMap/countProjectType", { params: params })
}
// å•个项目数据存储量
export function countProjectStorage(params) {
  return request.get("/oneMap/countProjectStorage", { params: params })
}
// å•个项目下载量
export function countProjectDown(params) {
  return request.get("/oneMap/countProjectDown", { params: params })
}
// å•个项目信息
export function selectProjectInfo(params) {
  return request.get("/oneMap/selectProjectInfo", { params: params })
}
src/assets/img/Screen/all.png
src/components/Screen/bottom.vue
@@ -3,33 +3,61 @@
    <div class="bottom1">
      <div class="bottom11"></div>
      <div class="bottom12">
        <div :class="currMenu == item.menuName ? 'active' : ''" v-for="item in menuList" :key="item.menuName"
          class="bottombtn" @click="handleMenuClick(item)">
          <el-popover popper-class="popover" placement="top" width="100" trigger="click">
        <div
          :class="currMenu == item.menuName ? 'active' : ''"
          v-for="item in menuList"
          :key="item.menuName"
          class="bottombtn"
          @click="handleMenuClick(item)"
        >
          <el-popover
            popper-class="popover"
            placement="top"
            width="100"
            trigger="click"
          >
            <!-- å†…容 -->
            <span slot="reference">{{ item.menuName }}</span>
            <div class="popover-content">
              <div class="popover-content__header">项目信息</div>
              <div class="popover-content__search">
                <el-input size="mini" placeholder="请输入内容" v-model="searchName" @change="handleSearchChange(item)">
                <el-input
                  size="mini"
                  placeholder="请输入内容"
                  v-model="searchName"
                  @change="handleSearchChange(item)"
                >
                  <el-button slot="append" icon="el-icon-search"></el-button>
                </el-input>
              </div>
              <div class="popover-content__list">
                <div class="popover-content__list__item" v-for="(child, i) in currMenuList" :key="child.id + i"
                  :class="currProject == child.name ? 'active' : ''" @click="handlePopoverClick(child)"
                  :title="child.name">
                <div
                  class="popover-content__list__item"
                  v-for="(child, i) in currMenuList"
                  :key="child.id + i"
                  :class="currProject == child.name ? 'active' : ''"
                  @click="handlePopoverClick(child)"
                  :title="child.name"
                >
                  {{ child.name.slice(0, 8) }}
                </div>
              </div>
            </div>
          </el-popover>
        </div>
        <div
          class="bottombtn"
          :class="showTree ? 'active' : ''"
          @click="handleTree"
        >
          å›¾å±‚管理
        </div>
      </div>
      <div class="bottom13">
        <img :src="yxImg" @click="ChangeBaseLayer('yx')"  title="影像图" />
        <img :src="xrImg" @click="ChangeBaseLayer('xr')"  title="晕渲图"/>
        <img :src="yxImg" @click="ChangeBaseLayer('yx')" title="影像图" />
        <img :src="xrImg" @click="ChangeBaseLayer('xr')" title="晕渲图" />
      </div>
    </div>
    <div class="bottom2">
@@ -44,6 +72,7 @@
  countProjectTour,
  countProjectDisplay,
  countProjectLocation,
  selectProjectFileList,
} from "@/api/screen.js"
import { wktToGeoJSON } from "@terraformer/wkt"
@@ -52,7 +81,7 @@
    return {
      YXState: true,
      XRState: true,
      yunxuanLayer: null,//全球眩晕图
      yunxuanLayer: null, //全球眩晕图
      yxImg: require("../../assets/img/Screen/yximg.png"),
      xrImg: require("../../assets/img/Screen/bdimg.png"),
      currMenu: "专题展示",
@@ -139,6 +168,7 @@
          ],
        },
      ],
      showTree: false,
    }
  },
  computed: {
@@ -160,7 +190,7 @@
  },
  methods: {
    ChangeBaseLayer(parm) {
      if (parm == 'yx') {
      if (parm == "yx") {
        if (this.YXState) {
          //this.yxImg = require("../../assets/img/Screen/bdimg.png")
          //加载百度影像
@@ -176,7 +206,7 @@
        this.YXState = !this.YXState
      }
      if (parm == 'xr') {
      if (parm == "xr") {
        if (yunxuanLayer == null) {
          var urls = "https://tiles3.geovisearth.com/base/v1/ter"
          // æ˜Ÿå›¾åœ°çƒåœ°å½¢æ™•渲
@@ -194,15 +224,12 @@
          )
        }
        if (this.XRState) {
          yunxuanLayer.item.show = true;
          yunxuanLayer.item.show = true
        } else {
          yunxuanLayer.item.show = false;
          yunxuanLayer.item.show = false
        }
        this.XRState = !this.XRState;
        this.XRState = !this.XRState
      }
    },
    handleMenuClick(menu) {
      this.currMenu = menu.menuName
@@ -215,12 +242,15 @@
          this.showPathLine(child)
          break
        case "项目展示":
          this.DisplayCurrentProject(child)
          // this.DisplayCurrentProject(child)
          this.changeProject(child)
          this.$bus.$emit("changeProjectCode", child.id)
          break
        case "专题展示":
          this.changeProject(child)
          break
        default:
          break
      }
@@ -265,8 +295,6 @@
    //项目展示
    DisplayCurrentProject(params) {
      //打开或者加载图层
      //飞到指定位置
@@ -294,20 +322,31 @@
      return menu.children
      // return menu.children.filter(item => item.name.indexOf(searchName) > -1)
    },
    handleSearchChange(currMenu) { },
    handleSearchChange(currMenu) {},
    async getCountProjectDisplay() {
      const res = await countProjectLocation()
      // const res = await countProjectLocation()
      // if (res.code === 200) {
      //   const menu = this.menuList.find(item => item.menuName == "项目展示")
      //   menu.children = res.result.map(item => {
      //     return {
      //       name: item.projname,
      //       id: item.projname,
      //       wkt: item.wkt,
      //     }
      //   })
      // }
      const res = await selectProjectFileList()
      if (res.code === 200) {
        const menu = this.menuList.find(item => item.menuName == "项目展示")
        menu.children = res.result.map(item => {
          return {
            name: item.projname,
            id: item.projname,
            name: item.name,
            id: item.code,
            wkt: item.wkt,
          }
        })
      }
      selectProjectFileList
    },
    async getCountProjectTour() {
      const res = await countProjectTour()
@@ -320,13 +359,16 @@
            wkt: item.wkt,
          }
        })
      }
    },
    //专题展示
    changeProject(params) {
      this.$bus.$emit('changeProject', params.name)
    }
      this.$bus.$emit("changeProject", params.name)
    },
    handleTree(params) {
      this.showTree = !this.showTree
      this.$bus.$emit("changeTree", this.showTree)
    },
  },
}
</script>
src/components/Screen/left.vue
@@ -20,33 +20,47 @@
    <!-- å…¨çƒã€å…¨å›½ç»Ÿè®¡æ¬¡æ•° -->
    <div class="leftContainer" v-if="currentDisplay == '项目'">
      <div class="current1" id="leftCurrent1">
        <div class="aside-title">国内、国外</div>
        <div class="aside-title">数据总览</div>
        <div class="wrapper">
          <div class="title">{{ currentProject }}</div>
          <dv-digital-flop style="height: 40px" :config="xmCountConfig" />
        </div>
      </div>
      <div class="current1" id="leftCurrent2">
        <div class="aside-title">统计地灾、洞库等专业数据存储量</div>
        <base-line-chart :project="currProject"></base-line-chart>
        <div class="aside-title">存储信息</div>
        <base-line-chart
          :requsetFn="requsetFn"
          :project="currentProject"
          title="数据存储量"
        ></base-line-chart>
      </div>
      <div class="current1" id="leftCurrent3">
        <div class="aside-title">数据存储量</div>
        <data-storage></data-storage>
        <data-storage-type></data-storage-type>
      </div>
    </div>
    <!-- å…¨çƒã€å…¨å›½ç®¡ç½‘图 -->
    <div class="leftContainer" v-if="currentDisplay == '管网'">
      <div class="current1" id="leftCurrent1">
        <div class="aside-title">管网国内、国外</div>
        <!-- <base-bar-chart :project="currProject"></base-bar-chart> -->
        <!-- <count-data-apply></count-data-apply> -->
        <div class="aside-title">数据总览</div>
        <div class="wrapper">
          <div class="title">{{ currentProject }}</div>
          <dv-digital-flop style="height: 40px" :config="xmCountConfig" />
        </div>
      </div>
      <div class="current1" id="leftCurrent2">
        <div class="aside-title">输送介质类别统计长度</div>
        <base-line-chart :project="currProject"></base-line-chart>
        <!-- <base-pie-chart :project="currProject"></base-pie-chart> -->
        <div class="aside-title">管网长度</div>
        <base-line-chart
          :requsetFn="requsetFn"
          :project="currentProject"
          title="管网长度"
        ></base-line-chart>
        <!-- <base-pie-chart :project="currentProject"></base-pie-chart> -->
        <!-- <service-type></service-type> -->
      </div>
      <div class="current1" id="leftCurrent3">
        <div class="aside-title">数据存储量</div>
        <data-storage></data-storage>
        <data-storage-type></data-storage-type>
      </div>
    </div>
    <!-- å•个工程展示 -->
@@ -64,9 +78,6 @@
        <projectTime></projectTime>
      </div>
    </div>
    <!-- <div class="leftContainer" v-if="ProjectreeDisplay">
      <project-tree></project-tree>
    </div> -->
  </div>
</template>
<script>
@@ -74,13 +85,28 @@
import countDataApply from "@/components/chart/CountDataApply.vue"
import ServiceType from "../chart/ServiceType.vue"
import DataStorage from "../chart/DataStorage.vue"
import DataStorageType from "../chart/DataStorageType.vue"
import BaseBarChart from "../chart/BaseBarChart.vue"
import BaseLineChart from "../chart/BaseLineChart.vue"
import BasePieChart from "../chart/BasePieChart .vue"
import projectintroduction from "../chart/projectintroduction.vue"
import projectState from "../chart/projectState.vue"
import projectTime from "../chart/projectTime.vue"
import {
  countCountryDimension,
  countProvinceDimension,
  countZhPipeStations,
  countZhPipeMapLength,
} from "@/api/screen.js"
function formatter(number) {
  const numbers = number.toString().split("").reverse()
  const segs = []
  while (numbers.length) segs.push(numbers.splice(0, 3).join(""))
  return segs.join(",").split("").reverse().join("")
}
export default {
  components: {
    ProjectTree,
@@ -93,6 +119,7 @@
    projectintroduction,
    projectState,
    projectTime,
    DataStorageType
  },
  data() {
    return {
@@ -102,8 +129,14 @@
      GlobleChartDisplay: false,
      CountryChartDisplay: false,
      leftImg: require("../../assets/img/Screen/rightArrow.png"),
      currProject: "全球项目",
      currentProject: "全球项目",
      currentDisplay: "大屏",
      requsetFn: countZhPipeMapLength,
      xmCountConfig: {
        number: [0],
        content: "{nt}",
        formatter,
      },
    }
  },
  mounted() {
@@ -118,7 +151,16 @@
      } else {
        this.currentDisplay = "工程"
      }
      this.currentProject = name
    })
    this.$bus.$on("changeCount", count => {
      if (typeof count == "number") {
        this.xmCountConfig.number = [count]
        this.xmCountConfig = {
          ...this.xmCountConfig,
        }
      }
    })
  },
  methods: {
@@ -639,6 +681,23 @@
      background-size: 100% 100%;
      background-repeat: no-repeat;
    }
    .wrapper {
      display: flex;
      flex-direction: column;
      justify-content: center;
      margin: 15px auto;
      width: 180px;
      height: 180px;
      background: url(../../assets/img/Screen/all.png);
      background-size: 100% 100%;
      background-repeat: no-repeat;
      .title {
        color: #fff;
        font-size: 20px;
        width: 100%;
        text-align: center;
      }
    }
  }
}
</style>
src/components/Screen/right.vue
@@ -17,9 +17,9 @@
    <!-- å…¨çƒã€å…¨å›½é¡¹ç›® -->
    <div class="rightContainer" v-if="currentDisplay == '项目'">
      <div class="current1">
        <div class="aside-title">项目柱状图</div>
        <div class="aside-title"></div>
        <!-- <country-dimension-bar ref="barRef"></country-dimension-bar> -->
        <base-bar-chart :project="currentProject"></base-bar-chart>
        <base-bar-chart title="项目个数" :project="currentProject"></base-bar-chart>
      </div>
      <div class="current1">
        <div class="aside-title">项目饼状图</div>
@@ -32,7 +32,10 @@
      </div>
      <div class="current1">
        <div class="aside-title">项目数据使用情况</div>
        <dv-capsule-chart :config="config" style="width: 360px; height: 85%" />
        <dv-capsule-chart
          :config="barConfig"
          style="width: 360px; height: 85%"
        />
      </div>
    </div>
    <!-- å…¨å›½ã€å…¨çƒç®¡ç½‘ -->
@@ -40,7 +43,7 @@
      <div class="current1">
        <div class="aside-title">站场座数</div>
        <!-- <country-dimension-bar ref="barRef"></country-dimension-bar> -->
        <base-bar-chart :project="currentProject"></base-bar-chart>
        <base-bar-chart title="站场座数" :project="currentProject"></base-bar-chart>
      </div>
      <div class="current1">
        <div class="aside-title">阀室座数</div>
@@ -61,11 +64,11 @@
    <div class="rightContainer" v-if="currentDisplay == '工程'">
      <div class="current1">
        <div class="aside-title">数据存储量</div>
        <base-line-chart :project="currentProject"></base-line-chart>
        <base-line-chart title="数据存储量" :project="currentProject" :params="params"></base-line-chart>
      </div>
      <div class="current1">
        <div class="aside-title">数据下载次数</div>
        <base-pie-chart height="90%" :project="currentProject"></base-pie-chart>
        <base-pie-chart height="90%" :project="currentProject" :params="params"></base-pie-chart>
      </div>
      <div class="current1">
        <div class="aside-title">统计不同输送介质管道条数</div>
@@ -75,7 +78,7 @@
            <div>数量</div>
          </div>
        </div>
        <file-format></file-format>
        <file-format :params="params"></file-format>
      </div>
    </div>
@@ -100,7 +103,11 @@
import BasePieChart from "../chart/BasePieChart .vue"
import VisitCount from "../chart/VisitCount.vue"
import { countCountryDimension, countProvinceDimension } from "@/api/screen.js"
import {
  countCountryDimension,
  countProvinceDimension,
  countZhPipeStations,
} from "@/api/screen.js"
export default {
  components: {
@@ -180,9 +187,37 @@
        ],
        lineWidth: 10,
      },
      barConfig: {
        data: [
          {
            name: "南阳",
            value: 167,
          },
          {
            name: "周口",
            value: 123,
          },
          {
            name: "漯河",
            value: 98,
          },
          {
            name: "郑州",
            value: 75,
          },
          {
            name: "西峡",
            value: 66,
          },
        ],
        showValue: true,
      },
      params: {}
    }
  },
  created() {
    this.getZhPipeStations()
  },
  mounted() {
    this.OpenLeftInit()
    this.$bus.$on("changeProject", name => {
@@ -195,7 +230,14 @@
      }
      this.currentProject = name
    })
    this.$bus.$on('changeProjectCode', code => {
      this.params = {
        projectCode: code
      }
    })
  },
  methods: {
    ChangeRight() {
      if (this.leftMessage == "init") {
@@ -236,6 +278,31 @@
    //   this.leftMessage = "projectree"
    //   this.$parent.ChangeWidth("leftTree")
    // },
    async getZhPipeStations() {
      const res = await countZhPipeStations()
      if (res.code == 200) {
        const data = res.result
        this.pieconfig.data = res.result.map(item => {
          return {
            name: item.输送介质,
            value: item.管道数量,
          }
        })
        this.pieconfig = {
          ...this.pieconfig,
        }
        this.config.data = res.result.map(item => {
          return {
            name: item.输送介质,
            value: item.管道数量,
          }
        })
        this.config = {
          ...this.config,
        }
      }
    },
  },
}
</script>
src/components/Screen/top.vue
@@ -1,14 +1,14 @@
<template>
  <div class="top">
    <div class="topleft">
      <div
      <!-- <div
        class="topleft1"
        :class="currView == 'chart' ? 'active' : ''"
        @click="OpenInitChart"
      >
        <img src="../../assets/img/Screen/bigST.png" />
        <span>大屏视图</span>
      </div>
      </div> -->
      <!-- <div
        class="topleft1"
        @click="OpenProjectree"
@@ -17,15 +17,24 @@
        <img src="../../assets/img/Screen/ptree.png" />
        <span>工程项目</span>
      </div> -->
      <div class="topleft__curr">
        <img src="../../assets/img/Screen/ptree.png" />
        <span :title="currentProject">{{ currentProject }}</span>
      </div>
    </div>
    <div class="topCenter">
      <div>管网一张图</div>
    </div>
    <div class="topRight">
      <div
        class="topright1 toprightC"
        @click="ReturnLast"
        class="topright1"
        :class="currView == 'chart' ? 'active' : ''"
        @click="OpenInitChart"
      >
        <img src="../../assets/img/Screen/bigST.png" />
        <span>返回大屏</span>
      </div>
      <div class="topright1 toprightC" @click="ReturnLast">
        <img src="../../assets/img/Screen/return.png" />
        <span>返回上级</span>
      </div>
@@ -39,18 +48,21 @@
      tree: false,
      screen: false,
      currView: "chart",
      currentProject: "大屏视图",
    }
  },
  mounted() {
    // this.$bus.$on('changeProject', name => {
    //   if (name == '全国项目' || name == '全球项目') {
    //     this.OpenProjectree()
    //   }
    // })
    this.$bus.$on("changeProject", name => {
      // if (name == '全国项目' || name == '全球项目') {
      //   this.OpenProjectree()
      // }
      this.currView = "tree"
      this.currentProject = name
    })
  },
  methods: {
    ReturnLast() {
      sessionStorage.setItem("changeSelectStyle", 1);
      sessionStorage.setItem("changeSelectStyle", 1)
      this.$router.push("/Synthesis")
    },
@@ -60,6 +72,7 @@
      this.screen = true
      this.$parent.$refs.mapleft.OpenLeftInit()
      this.$parent.$refs.mapright.OpenLeftInit()
      this.currentProject = "大屏视图"
    },
    //打开工程树
@@ -89,6 +102,22 @@
    align-items: flex-end;
    // justify-content: space-around;
    cursor: pointer;
    .topleft__curr {
      // overflow: hidden;
      text-overflow: ellipsis;
      white-space: nowrap;
      height: 36px;
      border-radius: 4px;
      background-image: url(../../assets/img/Screen/btnbg.png);
      background-repeat: no-repeat;
      background-size: 100% 100%;
      display: flex;
      align-items: center;
      margin-left: 5%;
      span {
        padding-right: 10px;
      }
    }
    .topleft1 {
      width: 127px;
      height: 36px;
@@ -143,13 +172,19 @@
    .topright1 {
      width: 131px;
      height: 40px;
      background-image: url(../../assets/img/Screen/btnc.png);
      background-image: url(../../assets/img/Screen/btnbg.png);
      background-repeat: no-repeat;
      background-size: 100% 100%;
      display: flex;
      align-items: center;
      margin-right: 10%;
      &.active {
        background-image: url(../../assets/img/Screen/btnc.png);
        background-repeat: no-repeat;
        background-size: 100% 100%;
      }
    }
    .toprightC {
      width: 131px;
      height: 40px;
src/components/chart/BaseBarChart.vue
@@ -4,7 +4,11 @@
<script>
import * as echarts from "echarts"
import { countCountryDimension, countProvinceDimension } from "@/api/screen.js"
import {
  countCountryDimension,
  countProvinceDimension,
  countZhPipeStations,
} from "@/api/screen.js"
export default {
  props: {
    width: {
@@ -30,6 +34,10 @@
    project: {
      type: String,
      default: "全国项目",
    },
    title: {
      type: String,
      default: "",
    },
  },
  data() {
@@ -92,11 +100,36 @@
      if (this.dataList) {
        data = this.dataList
      }
      let count = 0
      let countVal = 0
      const title = this.title
      data.forEach(item => {
        let name = item.province || item.country
        let name = item.province || item.country || item.输送介质
        let value = item.count || item.站场数量
        if (title == "站场座数" && item.管道数量) {
          count += item.管道数量
        } else {
          count += item.count || 0
        }
        // switch (title) {
        //   case "站场座数":
        //     countVal = item.管道数量
        //     break
        //   case "项目个数":
        //     countVal = item.count
        //     break
        // }
        xAxisData.push(name)
        yAxisData.push(item.count)
        yAxisData.push(value)
      })
      console.log("管道数量", countVal)
      if (typeof count === "number") {
        this.$bus.$emit("changeCount", count)
      }
      let option = {
        backgroundColor: "transparent",
        tooltip: {
@@ -134,6 +167,9 @@
                var maxLength = 2 //每项显示文字个数
                var valLength = value.length //X轴类目项的文字个数
                var rowN = Math.ceil(valLength / maxLength) //类目项需要换行的行数
                if (xAxisData.length < 7) {
                  return value
                }
                if (rowN > 1) {
                  //如果类目项的文字大于3,
                  for (var i = 0; i < rowN; i++) {
@@ -170,6 +206,7 @@
        ],
        series: [
          {
            name: this.title,
            type: "bar",
            data: yAxisData,
            barWidth: "12px",
@@ -252,6 +289,7 @@
    },
    project: {
      deep: true,
      immediate: true,
      handler(newVal) {
        let requsetFn = null
        switch (newVal) {
@@ -261,7 +299,12 @@
          case "全国项目":
            requsetFn = countProvinceDimension
            break
          case "全球管网图":
            requsetFn = countZhPipeStations
            break
          case "全国管网图":
            requsetFn = countZhPipeStations
            break
          default:
            break
        }
@@ -271,7 +314,7 @@
    },
  },
  mounted() {
    this.initData()
    // this.initData()
    this.initChart()
    if (this.autoResize) {
      window.addEventListener("resize", this.resizeHandler)
@@ -289,7 +332,7 @@
  },
  methods: {
    resizeHandler() {
      this.chart.resize()
      this.chart && this.chart.resize()
    },
    initChart() {
      this.chart = echarts.init(this.$refs.chart, "", {
src/components/chart/BaseLineChart.vue
@@ -8,6 +8,10 @@
  countCountryDimension,
  countProvinceDimension,
  GetServicesVisitsCount,
  countZhPipeMapLength,
  countLargeCategories,
  countProjectType,
  countProjectDown
} from "@/api/screen.js"
export default {
  props: {
@@ -34,6 +38,18 @@
    project: {
      type: String,
      default: "全国项目",
    },
    params: {
      type: Object,
      default: () => null,
    },
    project: {
      type: String,
      default: "全国项目",
    },
    title: {
      type: String,
      default: "",
    },
  },
  data() {
@@ -66,10 +82,10 @@
        },
        grid: {
          right: "5%",
          top: '10%',
          top: "10%",
          left: "5%",
          bottom: "17%",
          containLabel: true
          containLabel: true,
        },
        xAxis: {
@@ -77,9 +93,9 @@
          boundaryGap: true,
          axisLine: {
            lineStyle: {
              color: "#fff"
              color: "#fff",
            },
            show: false
            show: false,
          },
          nameRotate: 45,
          axisTick: {
@@ -116,7 +132,7 @@
        },
        series: [
          {
            name: "服务访问次数",
            name: this.title,
            type: "line",
            showAllSymbol: false,
            lineStyle: {
@@ -143,17 +159,25 @@
    },
    project: {
      deep: true,
      immediate: true,
      handler(newVal) {
        let requsetFn = null
        switch (newVal) {
          case "全球项目":
            requsetFn = countCountryDimension
            requsetFn = countLargeCategories
            break
          case "全国项目":
            requsetFn = countProvinceDimension
            requsetFn = countLargeCategories
            break
          case "全球管网图":
            requsetFn = countZhPipeMapLength
            break
          case "全国管网图":
            requsetFn = countZhPipeMapLength
            break
          default:
            requsetFn = GetServicesVisitsCount
            break
        }
        requsetFn && this.initData(requsetFn)
@@ -163,7 +187,7 @@
    },
  },
  mounted() {
    this.initData()
    // this.initData()
    this.initChart()
    if (this.autoResize) {
      window.addEventListener("resize", this.resizeHandler)
@@ -181,7 +205,7 @@
  },
  methods: {
    resizeHandler() {
      this.chart.resize()
      this.chart && this.chart.resize()
    },
    initChart() {
      this.chart = echarts.init(this.$refs.chart, "", {
@@ -207,7 +231,7 @@
      this.chart && this.chart.clear()
    },
    async initData(requsetFn = GetServicesVisitsCount) {
      const res = await requsetFn()
      const res = await requsetFn(this.params)
      if (res.code == 200) {
        this.dataList = res.result
        console.log("requsetFn", res)
src/components/chart/BasePieChart .vue
@@ -4,7 +4,11 @@
<script>
import * as echarts from "echarts"
import { countCountryDimension, countProvinceDimension } from "@/api/screen.js"
import {
  countCountryDimension,
  countProvinceDimension,
  countProjectStorage,
} from "@/api/screen.js"
export default {
  props: {
    width: {
@@ -31,6 +35,10 @@
      type: String,
      default: "全国项目",
    },
    params: {
      type: Object,
      default: () => null,
    },
  },
  data() {
    return {
@@ -40,32 +48,7 @@
  },
  computed: {
    option() {
      let echartData = [
        {
          value: 2154,
          name: "曲阜师范大学",
        },
        {
          value: 3854,
          name: "潍坊学院",
        },
        {
          value: 3515,
          name: "青岛职业技术学院",
        },
        {
          value: 3515,
          name: "淄博师范高等专科",
        },
        {
          value: 3854,
          name: "鲁东大学",
        },
        {
          value: 2154,
          name: "山东师范大学",
        },
      ]
      let echartData = []
      let data = []
      let xAxisData = []
      let yAxisData = []
@@ -73,7 +56,7 @@
      if (this.dataList) {
        data = this.dataList
        echartData = data.map(item => {
          let name = item.province || item.country
          let name = item.province || item.country || item.name
          // xAxisData.push(name)
          // yAxisData.push(item.count)
          count += item.count
@@ -183,8 +166,8 @@
              "#18edc9",
              "#6ac5fa",
            ],
            // minAngle: 15,
            // startAngle: 270,
            minAngle: 15,
            startAngle: 270,
            label: {
              normal: {
                formatter: function (params, ticket, callback) {
@@ -209,7 +192,7 @@
            },
            labelLine: {
              normal: {
                length: 55 * scale,
                length: 30,
                length2: 0,
                lineStyle: {
                  color: "#0b5263",
@@ -233,6 +216,7 @@
    },
    project: {
      deep: true,
      immediate: true,
      handler(newVal) {
        let requsetFn = null
        switch (newVal) {
@@ -242,17 +226,28 @@
          case "全国项目":
            requsetFn = countProvinceDimension
            break
          case "全球管网图":
            requsetFn = countProvinceDimension
            break
          case "全国管网图":
            requsetFn = countProvinceDimension
            break
          default:
            requsetFn = countProjectStorage
            break
        }
        requsetFn && this.initData(requsetFn)
        this.setOptions(this.option)
      },
    },
  },
  created() {
    // this.initData()
  },
  mounted() {
    this.initData()
    this.initChart()
    if (this.autoResize) {
      window.addEventListener("resize", this.resizeHandler)
@@ -270,7 +265,7 @@
  },
  methods: {
    resizeHandler() {
      this.chart.resize()
      this.chart && this.chart.resize()
    },
    initChart() {
      this.chart = echarts.init(this.$refs.chart, "", {
@@ -288,6 +283,7 @@
      if (this.chart) {
        this.chart.setOption(option)
      }
    },
    refresh() {
      this.setOptions(this.option)
@@ -295,8 +291,8 @@
    clearChart() {
      this.chart && this.chart.clear()
    },
    async initData(requsetFn = countCountryDimension) {
      const res = await requsetFn()
    async initData(requsetFn) {
      const res = await requsetFn(this.params)
      if (res.code == 200) {
        this.dataList = res.result
        console.log("requsetFn", res)
src/components/chart/DataStorageType.vue
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,429 @@
<template>
  <div class="data-storage">
    <div class="data-storage__header">
      <div class="text">
        <img
          class="img"
          src="@/assets/img/Screen/cunchu.png"
          alt=""
          srcset=""
        />
        <div class="title">共存储文件数量</div>
      </div>
      <div class="num">
        <dv-digital-flop :config="config1" style="width: 70px; height: 20px" />
        <!-- <div class="value">5</div> -->
      </div>
    </div>
    <div class="data-storage__content">
      <ul class="contentTitle">
        <li class="title">编号</li>
        <li class="name">名称</li>
        <li class="num">数量</li>
        <li class="size">文件大小(MB)</li>
      </ul>
      <div class="scroolData">
        <vue-seamless-scroll
          :data="tableData"
          class="ClassScroll"
          :class-option="defaultOption"
        >
          <ul class="item">
            <li v-for="(item, index) in tableData" :key="index">
              <span class="title">
                <div>{{ item.index }}</div></span
              >
              <span class="name" :title="item.name">{{
                item.name.substring(0, 15)
              }}</span>
              <span class="num">{{ item.num || 0 }}</span>
              <span class="size">{{ item.size || 0 }}</span>
            </li>
          </ul>
        </vue-seamless-scroll>
      </div>
    </div>
  </div>
  <!-- <dv-scroll-board :config="config" style="width: 330px; height: 220px" /> -->
  <!-- <el-scrollbar class="scrollbar">
        <el-table
          :data="tableData"
          :row-style="{ background: 'rgba(135,180,248,0.10)' }"
          :cell-style="{ background: 'rgba(135,180,248,0.10)' }"
          :header-row-style="{
            background: 'rgba(57,128,236,0.29)',
            color: '#fff',
          }"
          :header-cell-style="{
            background: 'rgba(57,128,236,0.29)',
            color: '#fff',
          }"
        >
          <el-table-column prop="index" label="编号" width="50">
            <template slot-scope="scope">
              <div
                style="
                  background: rgba(180, 188, 235, 0.25);
                  text-align: center;
                "
              >
                {{ scope.row.index }}
              </div>
            </template>
          </el-table-column>
          <el-table-column align="center" prop="name" label="名称">
            <template slot-scope="scope">
              <div
                style="
                  overflow: hidden;
                  text-overflow: ellipsis;
                  white-space: nowrap;
                "
                :title="scope.row.name"
              >
                {{ scope.row.name }}
              </div>
            </template>
          </el-table-column>
          <el-table-column prop="num" label="文件数" width="70">
          </el-table-column>
        </el-table>
      </el-scrollbar> -->
</template>
<script>
import vueSeamlessScroll from "vue-seamless-scroll"
import { countDataStorage, countLargeCategories } from "@/api/screen.js"
export default {
  components: {
    vueSeamlessScroll,
  },
  data() {
    return {
      tableData: [
        {
          date: "2016-05-02",
          name: "王小虎",
          address: "上海市普陀区金沙江路 1518 å·",
        },
        {
          date: "2016-05-04",
          name: "王小虎",
          address: "上海市普陀区金沙江路 1517 å¼„",
        },
        {
          date: "2016-05-01",
          name: "王小虎",
          address: "上海市普陀区金沙江路 1519 å¼„",
        },
        {
          date: "2016-05-03",
          name: "王小虎",
          address: "上海市普陀区金沙江路 1516 å¼„",
        },
      ],
      config: {
        header: ["编号", "名称", "文件数"],
        data: [
          ["行1列1", "行1列2", "行1列3"],
          ["行2列1", "行2列2", "行2列3"],
          ["行3列1", "行3列2", "行3列3"],
          ["行4列1", "行4列2", "行4列3"],
          ["行5列1", "行5列2", "行5列3"],
          ["行6列1", "行6列2", "行6列3"],
          ["行7列1", "行7列2", "行7列3"],
          ["行8列1", "行8列2", "行8列3"],
          ["行9列1", "行9列2", "行9列3"],
          ["行10列1", "行10列2", "行10列3"],
        ],
        columnWidth: [40, 300, 50],
        align: ["center"],
        carousel: "page",
      },
      config1: {
        number: [0],
        content: "{nt}个",
        style: {
          fontSize: 12,
          fill: "#00baff",
        },
      },
    }
  },
  computed: {
    defaultOption() {
      return {
        step: 0.2, // æ•°å€¼è¶Šå¤§é€Ÿåº¦æ»šåŠ¨è¶Šå¿«
        limitMoveNum: this.tableData.length, // å¼€å§‹æ— ç¼æ»šåŠ¨çš„æ•°æ®é‡ this.dataList.length
        hoverStop: true, // æ˜¯å¦å¼€å¯é¼ æ ‡æ‚¬åœstop
        direction: 1, // 0向下 1向上 2向左 3向右
        openWatch: true, // å¼€å¯æ•°æ®å®žæ—¶ç›‘控刷新dom
        singleHeight: 0, // å•步运动停止的高度(默认值0是无缝不停止的滚动) direction => 0/1
        singleWidth: 0, // å•步运动停止的宽度(默认值0是无缝不停止的滚动) direction => 2/3
        waitTime: 1000, // å•步运动停止的时间(默认值1000ms)
      }
    },
  },
  created() {
    this.initTable()
  },
  methods: {
    async initTable() {
      const res = await countLargeCategories()
      if (res.code == 200) {
        let count = 0
        this.tableData = res.result.map((item, i) => {
          count += item.count
          return {
            index: i + 1,
            name: item.name,
            num: item.count,
            sizes: item.sizes,
          }
        })
        this.config1.number = [count]
        this.config1 = {
          ...this.config1,
        }
      }
    },
  },
}
</script>
<style lang="scss" scoped>
.data-storage {
  height: calc(100% - 30px);
  width: 100%;
}
.data-storage__header {
  height: 40px;
  width: 100%;
  display: flex;
  flex-direction: row;
  justify-content: space-between;
  .text {
    display: flex;
    align-items: center;
  }
  .title {
    font-family: Source Han Sans CN, Source Han Sans CN-Regular;
    color: #ffffff;
  }
  .img {
    margin-right: 4px;
    width: 16px;
    height: 16px;
  }
  .num {
    display: flex;
    align-items: center;
    justify-content: center;
  }
}
.data-storage__content {
  height: calc(100% - 40px);
  width: 100%;
  .contentTitle {
    height: 40px;
    width: 100%;
    display: flex;
    background-color: rgba(52, 78, 147, 0.5);
    flex-direction: row;
    li {
      align-items: center;
      justify-content: space-around;
      color: #ffffff;
    }
    .title {
      width: 15%;
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
    }
    .name {
      width: 60%;
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
    }
    .num {
      width: 25%;
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
    }
  }
}
.scroolData {
  height: calc(100% - 40px);
  width: 100%;
  overflow: hidden;
}
.ClassScroll {
  height: 100%;
  width: 100%;
  .item {
    width: 100%;
    height: 100%;
    color: #ffffff;
    li {
      height: 40px;
      width: 100%;
      display: flex;
      flex-direction: row;
      align-items: center;
      justify-content: space-around;
      .title {
        width: 15%;
        height: 100%;
        display: flex;
        align-items: center;
        justify-content: center;
        div {
          height: 20px;
          width: 20px;
          background-color: #495477;
          display: flex;
          align-items: center;
          justify-content: center;
        }
      }
      .name {
        width: 50%;
        height: 100%;
        display: flex;
        align-items: center;
        justify-content: center;
      }
      .num {
        width: 25%;
        height: 100%;
        display: flex;
        align-items: center;
        justify-content: center;
      }
      .size {
        width: 25%;
        height: 100%;
        display: flex;
        align-items: center;
        justify-content: center;
      }
    }
  }
}
// .data-storage {
//   margin: 10px;
//   width: 377px;
//   &__header {
//     margin-bottom: 10px;
//     display: flex;
//     align-items: center;
//     justify-content: space-between;
//     height: 20px;
//     width: 340px;
//     box-sizing: border-box;
//     .text {
//       display: flex;
//       align-items: center;
//     }
//     .title {
//       font-family: Source Han Sans CN, Source Han Sans CN-Regular;
//       color: #ffffff;
//     }
//     .img {
//       margin-right: 4px;
//       width: 16px;
//       height: 16px;
//     }
//     .value {
//       text-align: center;
//       color: #ffffff;
//       width: 16px;
//       height: 20px;
//       background: url("~@/assets/img/Screen/numBg.png");
//       background-size: 100% 100%;
//     }
//   }
//   &__content {
//     width: 95%;
//     height: 220px;
//   }
// }
//
</style>
<style lang="scss">
// .data-storage {
//   .index-wrap {
//     margin: 0 auto;
//     width: 14px;
//     height: 14px;
//     background: rgba(180, 188, 235, 0.25);
//   }
//   .scrollbar {
//     width: 100%;
//     overflow-x: hidden;
//     height: 200px;
//     .el-scrollbar__wrap {
//       overflow-x: hidden;
//     }
//     .el-table {
//       height: 100%;
//       width: 100%;
//       background-color: transparent;
//       color: #fff;
//     }
//     .el-table th.el-table__cell.is-leaf,
//     .el-table td.el-table__cell {
//       border: none;
//     }
//     .el-table--group::after,
//     .el-table--border::after,
//     .el-table::before {
//       border: none;
//     }
//     .el-table::before {
//       height: 0;
//     }
//   }
// }
</style>
src/components/chart/FileFormat.vue
@@ -4,12 +4,27 @@
<script>
import * as echarts from "echarts"
import { countFileFormat } from "@/api/screen.js"
import { countFileFormat, countProjectType } from "@/api/screen.js"
export default {
  props: {
    params: {
      type: Object,
      default: () => null,
    },
  },
  data() {
    return {
      option: {},
    }
  },
  watch: {
    params : {
      deep: true,
      immediate: true,
      handler(newVal) {
        this.initChart()
      },
    },
  },
  mounted() {
    this.initChart()
@@ -58,7 +73,7 @@
          value: 20,
        },
      ]
      const res = await countFileFormat()
      const res = await countProjectType(this.params)
      if (res.code == 200) {
        data = res.result.map(item => {
          return {
src/components/chart/ServiceType.vue
@@ -115,7 +115,7 @@
      let option = {
        backgroundColor: "transparent",
        title: {
          text: "服务类型总数量",
          text: "用户访问总量",
          subtext: count,
          textStyle: {
            color: "#fff",
src/components/chart/projectintroduction.vue
@@ -1,105 +1,133 @@
<template>
    <div class="projectintroduction">
        <div class="item">
            <div class="itemName">项目名称:</div>
            <div class="itemValue" :title="result.projname">{{ result.projname.length>15?result.projname.substring(0,15):result.projname }}</div>
        </div>
        <div class="item">
            <div class="itemName">项目状态:</div>
            <div class="itemValue">{{ result.projstate }}</div>
        </div>
        <div class="item">
            <div class="itemName">项目种类:</div>
            <div class="itemValue">{{ result.projtype }}</div>
        </div>
        <div class="item">
            <div class="itemName">所属部门:</div>
            <div class="itemValue">{{ result.corpname }}</div>
        </div>
        <div class="item">
            <div class="itemName">启动时间:</div>
            <div class="itemValue">{{ parseTime(result.createtime) }}</div>
        </div>
        <div class="item">
            <div class="itemName">工程内容:</div>
            <div class="itemValue">{{ result.contents.length>15? result.contents.substring(0,15): result.contents }}</div>
        </div>
  <div class="projectintroduction">
    <div class="item">
      <div class="itemName">项目名称:</div>
      <div class="itemValue" :title="result.projname">
        {{
          result.projname.length > 15
            ? result.projname.substring(0, 15)
            : result.projname
        }}
      </div>
    </div>
    <div class="item">
      <div class="itemName">项目状态:</div>
      <div class="itemValue">{{ result.projstate }}</div>
    </div>
    <div class="item">
      <div class="itemName">项目种类:</div>
      <div class="itemValue">{{ result.projtype }}</div>
    </div>
    <div class="item">
      <div class="itemName">所属部门:</div>
      <div class="itemValue">{{ result.corpname }}</div>
    </div>
    <div class="item">
      <div class="itemName">启动时间:</div>
      <div class="itemValue">{{ parseTime(result.createtime) }}</div>
    </div>
    <div class="item">
      <div class="itemName">工程内容:</div>
      <div class="itemValue">
        {{
          result.contents.length > 15
            ? result.contents.substring(0, 15)
            : result.contents
        }}
      </div>
    </div>
  </div>
</template>
<script>
import { selectProjectInfo } from "@/api/screen.js"
export default {
    data() {
        return {
            result:
                {
                    "eventid": "4dfd814a-a262-4a93-880b-5ef488883a35",
                    "country": "中国",
                    "projstate": "施工中",
                    "createtime": 1675071993161,
                    "gid": 38,
                    "conperiod": "24",
                    "datastatus": null,
                    "geom": "01010000208A110000925A28999C225C40F1811DFF05364040",
                    "createuser": 1,
                    "parentid": null,
                    "verid": 0,
                    "province": "湖北省",
                    "projname": "西气东输三线(中卫-枣阳)",
                    "contents": "管道线路施工",
                    "projtype": "管线施工",
                    "location": "武汉",
                    "dirid": "03",
                    "depid": null,
                    "corpname": "管道设计院",
                    "department": "勘察部门",
                    "updatetime": 1675072198376,
                    "belongsid": null,
                    "remarks": "测试用,内容虚构",
                    "updateuser": 1
                },
        }
    },
    methods: {
        //获取时间
        parseTime(timestamp){
            var date = new Date(timestamp);//时间戳为10位需*1000,时间戳为13位的话不需乘1000
            var Y = date.getFullYear() + '-';
            var M = (date.getMonth()+1 < 10 ? '0'+(date.getMonth()+1) : date.getMonth()+1) + '-';
            var D = (date.getDate() < 10 ? '0'+date.getDate() : date.getDate()) + ' ';
            let strDate = Y+M+D;
            return strDate;
        }
  data() {
    return {
      result: {
        eventid: "4dfd814a-a262-4a93-880b-5ef488883a35",
        country: "中国",
        projstate: "施工中",
        createtime: 1675071993161,
        gid: 38,
        conperiod: "24",
        datastatus: null,
        geom: "01010000208A110000925A28999C225C40F1811DFF05364040",
        createuser: 1,
        parentid: null,
        verid: 0,
        province: "湖北省",
        projname: "西气东输三线(中卫-枣阳)",
        contents: "管道线路施工",
        projtype: "管线施工",
        location: "武汉",
        dirid: "03",
        depid: null,
        corpname: "管道设计院",
        department: "勘察部门",
        updatetime: 1675072198376,
        belongsid: null,
        remarks: "测试用,内容虚构",
        updateuser: 1,
      },
    }
  },
  created() {
    this.$bus.$on("changeProjectCode", code => {
      let params = {
        projectCode: code,
      }
      this.getDataList(params)
    })
  },
  methods: {
    async getDataList(params) {
      const res = await selectProjectInfo(params)
      if (res.code == 200) {
        this.result = res.result
      }
    },
    //获取时间
    parseTime(timestamp) {
      var date = new Date(timestamp) //时间戳为10位需*1000,时间戳为13位的话不需乘1000
      var Y = date.getFullYear() + "-"
      var M =
        (date.getMonth() + 1 < 10
          ? "0" + (date.getMonth() + 1)
          : date.getMonth() + 1) + "-"
      var D =
        (date.getDate() < 10 ? "0" + date.getDate() : date.getDate()) + " "
      let strDate = Y + M + D
      return strDate
    },
  },
}
</script>
<style lang="scss">
.projectintroduction {
    height: calc(100% - 30px);
    width: 100%;
    .item{
        margin: 5px;
        height: 30px;
        display: flex;
        flex-direction: row;
        border-bottom: dotted 1px  rgba(48,135,214,.2);
        .itemName{
            width: 40%;
            height: 100%;
            display: flex;
            align-items: center;
            justify-content: center;
            color: #fff;
        }
        .itemValue{
            width: 60%;
            height: 100%;
            display: flex;
            align-items: center;
            justify-content: flex-start;
            color: #9ED2F5;
        }
  height: calc(100% - 30px);
  width: 100%;
  .item {
    margin: 5px;
    height: 30px;
    display: flex;
    flex-direction: row;
    border-bottom: dotted 1px rgba(48, 135, 214, 0.2);
    .itemName {
      width: 40%;
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
      color: #fff;
    }
    .itemValue {
      width: 60%;
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: flex-start;
      color: #9ed2f5;
    }
  }
}
</style>
</style>
src/views/Thematic/index.vue
@@ -7,6 +7,9 @@
      :style="{ width: leftWidth, left: leftWidth == '22%' ? '-19px' : '0' }"
      ref="mapleft"
    ></left>
    <project-tree class="project-tree" v-if="ProjectreeDisplay"></project-tree>
    <right
      class="mapright"
      :style="{ width: rightWidth }"
@@ -22,20 +25,25 @@
import left from "@/components/Screen/left.vue"
import right from "../../components/Screen/right.vue"
import bottom from "../../components/Screen/bottom.vue"
import ProjectTree from "../../components/Screen/ProjectTree.vue"
import axios from "axios"
export default {
  components: { mapsdk, top, left, right, bottom },
  components: { mapsdk, top, left, right, bottom, ProjectTree },
  data() {
    return {
      leftWidth: "22%",
      rightWidth: "22%",
      leftTree: false,
      currTree: false
      currTree: false,
      ProjectreeDisplay: false,
    }
  },
  mounted() {},
  created() {},
  created() {
    this.$bus.$on("changeTree", key => {
      this.ProjectreeDisplay = key
    })
  },
  methods: {
    //修改左侧宽度
    ChangeWidth(parm) {
@@ -113,6 +121,14 @@
  width: 100%;
  z-index: 999;
}
.project-tree {
  position: absolute;
  top: 90px;
  right: 22%;
  width: 15%;
  height: calc(100% - 180px);
  z-index: 999;
}
</style>
<style lang="less">