月球大数据地理空间分析展示平台-【前端】-月球2期前端
WX
2023-09-13 051f46b4ee09ef92df932a5463f5f6bffa1e2274
点面标绘查询
已添加1个文件
已修改4个文件
464 ■■■■■ 文件已修改
package.json 5 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/api/api.js 16 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/utils/downloadCSV.js 223 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/plotting/plotting.vue 52 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/plotting/plottingInquire.vue 168 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
package.json
@@ -17,6 +17,7 @@
    "default-passive-events": "^2.0.0",
    "echarts": "^5.4.3",
    "element-plus": "^2.3.0",
    "file-saver": "^2.0.5",
    "jquery": "^3.7.1",
    "js-base64": "^3.7.5",
    "jsencrypt": "^3.3.2",
@@ -30,7 +31,9 @@
    "vue-drag-resize": "^1.5.4",
    "vue-router": "^4.0.3",
    "vuedraggable": "^4.1.0",
    "vuex": "^4.0.0"
    "vuex": "^4.0.0",
    "xlsx": "^0.18.5",
    "xlsx-js-style": "^1.2.0"
  },
  "devDependencies": {
    "@typescript-eslint/eslint-plugin": "^5.4.0",
src/api/api.js
@@ -79,14 +79,24 @@
  return request.get("/publish/selectSjColorTables", { params: params });
}
//数据管理=>更新数简服务
export function publish_updateSjService(params) {
  return request.post("/publish/updateSjService", params);
}
//在线制图=>分页查询
export function exportSelectByPage(params) {
  return request.get('/export/selectByPage', { params: params });
  return request.get("/export/selectByPage", { params: params });
}
//栅格分析=>查询点分析
export function selectByPoint(params) {
  return request.get("/rasterAnalysis/selectByPoint", { params: params });
}
//栅格分析=>查询面分析
export function selectByPolygon(params) {
  return request.get("/rasterAnalysis/selectByPolygon", { params: params });
}
//栅格分析=>查询线分析
export function selectByPolyline(params) {
  return request.get("/rasterAnalysis/selectByPolyline", { params: params });
}
src/utils/downloadCSV.js
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,223 @@
import XLSXS from "xlsx-js-style";
export function saveFSDZJsonToExcel(data, name, merges) {
  //   const data = [
  //     { å§“名: "张三", å¹´é¾„: 18, æ€§åˆ«: "男" },
  //     { å§“名: "李四", å¹´é¾„: 20, æ€§åˆ«: "女" },
  //     { å§“名: "王五", å¹´é¾„: 22, æ€§åˆ«: "男" },
  //   ];
  //   const wb = XLSX.utils.book_new();
  //   const ws = XLSX.utils.json_to_sheet(data);
  //   ws["!cols"] = [
  //     {
  //       wpx: 150,
  //     },
  //     {
  //       wpx: 500,
  //     },
  //     {
  //       wpx: 100,
  //     },
  //   ];
  //   XLSXS.utils.book_append_sheet(wb, ws, "Sheet1");
  //   XLSXS.writeFile(wb, "data-region.xlsx");
  //============================================================================
  console.log(data, name, merges);
  // data是点击导出按钮传递过来要导出的数据,name是导出的文件名,merges是合并的单元格
  // å°†æ•°æ®æºè½¬æˆæˆ‘们需要的二维数组,序号、姓名这些是表格的表头
  const body = data.map((x) => [
    x["layerName"],
    x["min"],
    x["max"],
    x["avg"],
    x["lng"],
    x["lat"],
  ]);
  const header = [
    // è¿™ä¸ªæ˜¯è®¾ç½®excel表格的标题,即在A1单元格的标题
    [
      {
        v: ``,
        t: "s", // æŒ‡å®šæ ‡é¢˜çš„æ ·å¼
      },
    ],
    // è¿™æ˜¯å¯¹åº”body常量的表头
    ["layerName", "min", "max", "avg", "lng", "lat"],
  ];
  body.unshift(...header); // å°†å®šä¹‰å¥½çš„表头添加到 body ä¸­
  const sheet = XLSXS.utils.aoa_to_sheet(body); // aoa_to_sheet å°†äºŒç»´æ•°ç»„转成 sheet
  // æ­¤å¤„开始合并列,即相同名字的表格合并单元格
  let includeB = [];
  let includesBnumber = [];
  for (let key in sheet) {
    // console.log(sheet[key]);
    // if (key.includes("B")) {
    //   // ç¬¬ä¸€åˆ—是A,代表序号;第二列是B,代表姓名
    //   includeB.push(sheet[key]);
    // }
    // includeB.push(sheet[key]);
  }
  //   includeB.forEach((e, i) => {
  //     if (!(e.v.includes("姓名") || e.v.includes("共计"))) {
  //       includesBnumber.push({
  //         name: e.v,
  //         number: i + 1, // å› ä¸ºæœ‰æ ‡é¢˜ï¼Œæ‰€ä»¥è¦ä»Žç¬¬2行开始
  //       });
  //     }
  //   });
  // åŽ»é‡
  //   let cancelTwice = () => {
  //     let map = new Map();
  //     for (let item of includesBnumber) {
  //       if (!map.has(item.name)) {
  //         map.set(item.name, item);
  //       }
  //     }
  //     return [...map.values()];
  //   };
  //   let newArr = cancelTwice();
  // åˆå¹¶
  //   let newMerges = [];
  //   merges.forEach((e, i) => {
  //     if (i != 0) {
  //       newMerges.push(
  //         // åˆå¹¶ï¼šs代表合并的开始单元格,c是列,r是行,e是代表合并的结束单元格
  //         {
  //           s: {
  //             c: e.s.c,
  //             r: e.s.r + 1, //r加1是因为加了表格的标题
  //           },
  //           e: {
  //             c: e.e.c,
  //             r: e.e.r + 1,
  //           },
  //         }
  //       );
  //     } else {
  //       newMerges.push(e); // æ ‡é¢˜åˆå¹¶
  //     }
  //   });
  //   merges = newMerges;
  //   // è®¾ç½®åˆå¹¶å§“名列的单元格
  //   newArr.forEach((e, i) => {
  //     merges.push({
  //       s: { r: e.number, c: 1 },
  //       e: {
  //         r: newArr[i + 1]?.number ? newArr[i + 1].number - 2 : data.length - 1,
  //         c: 1,
  //       },
  //     });
  //   });
  //   sheet["!merges"] = merges; // å°†merges添加到sheet中
  // è®¾ç½®åˆ—宽
  const cols = [{ wch: 100 }, { wch: 15 }, { wch: 12 }, { wch: 12 }];
  sheet["!cols"] = cols; // å°†cols添加到sheet中
  //   const rows = [{ hpx: 20 }, { hpx: 16 }, { hpx: 18 }];
  //   sheet["!rows"] = rows; // å°†rows添加到sheet中,设置行高
  Object.keys(sheet).forEach((key, i) => {
    // è®¾ç½®å•元格样式
    if (key.indexOf("!") < 0) {
      if (key == "A1") {
        // è®¾ç½®æ ‡é¢˜
        sheet[key].s = {
          alignment: {
            horizontal: "center", //水平居中
            vertical: "center", //竖直居中
          },
          font: {
            bold: true,
            // sz: 14,
            // name: "宋体",
          },
        };
      } else if (
        key == "A2" ||
        key == "B2" ||
        key == "C2" ||
        key == "D2" ||
        key == "E2" ||
        key == "F2" ||
        key == "G2" ||
        key == "H2" ||
        key == "I2"
      ) {
        // è®¾ç½®è¡¨å¤´
        sheet[key].s = {
          fill: {
            fgColor: { rgb: "A6A6A6" },
          },
          border: {
            top: { style: "thin" },
            left: { style: "thin" },
            bottom: { style: "thin" },
            right: { style: "thin" },
          },
          font: {
            bold: true,
            // sz: 12,
            // name: "宋体",
          },
        };
      } else {
        if (key.includes("A")) {
          // åºåˆ—所在列
          if (typeof sheet[key].v == "number") {
            // åˆ—表列要求序号要居中,合计和总合计居左(应该是系统默认的,如果要设置居左或居右,也可以自己设置下alignment属性)
            sheet[key].s = {
              alignment: {
                horizontal: "center",
                vertical: "center",
              },
              border: {
                top: { style: "thin" },
                left: { style: "thin" },
                bottom: { style: "thin" },
                right: { style: "thin" },
              },
            };
          } else {
            sheet[key].s = {
              border: {
                top: { style: "thin" },
                left: { style: "thin" },
                bottom: { style: "thin" },
                right: { style: "thin" },
              },
            };
          }
        } else {
          sheet[key].s = {
            border: {
              top: { style: "thin" },
              left: { style: "thin" },
              bottom: { style: "thin" },
              right: { style: "thin" },
            },
            alignment: {
              horizontal: "left",
              vertical: "center",
            },
          };
        }
      }
    }
  });
  // è®¾ç½®ç»“尾的表格
  //   let sheetBorder = sheet["!ref"].substring(4); // å› ä¸ºå¯¼å‡ºçš„单元格行数不确定,所以拿到最后一行的数字
  //   let endSheetBorder = ["C", "D", "E", "F", "G", "H"]; //因为最后一行的合并的列是一样的,所以这里可以直接将列的单元格序号写个定值
  //   endSheetBorder.forEach((e) => {
  //     let addBorder = e + sheetBorder;
  //     sheet[addBorder] = {
  //       v: "",
  //       t: "s",
  //       s: {
  //         border: {
  //           top: { style: "thin" },
  //           bottom: { style: "thin" },
  //         },
  //       },
  //     };
  //   });
  const workbook = XLSXS.utils.book_new(); // åˆ›å»ºè™šæ‹Ÿçš„ workbook
  XLSXS.utils.book_append_sheet(workbook, sheet); // å‘ workbook ä¸­æ·»åŠ  sheet
  XLSXS.writeFile(workbook, "data-region" + ".xlsx"); // å¯¼å‡º workbook
}
src/views/plotting/plotting.vue
@@ -53,6 +53,9 @@
  watch,
} from "vue";
import { useStore } from "vuex"; // å¼•å…¥useStore æ–¹æ³•
import { selectByPoint, selectByPolygon } from "@/api/api";
import WKT from "terraformer-wkt-parser";
import * as turf from "@turf/turf";
const emits = defineEmits(["setCloseplotting"]);
const store = useStore(); // è¯¥æ–¹æ³•用于返回store å®žä¾‹
let list = ref([]);
@@ -64,7 +67,14 @@
});
const lineColor = ref(null);
const metiaColor = ref(null);
//点查询接口
const selectPoint = async () => {
  const dt = await selectByPoint();
};
//线查询接口
const selectPolygon = async () => {
  const dt = await selectByPolygon();
};
const setLayerLocation = (res) => {
  var entities = Viewer.entities._entities._array;
  for (var i in entities) {
@@ -132,10 +142,17 @@
      disableDepthTestDistance: Number.POSITIVE_INFINITY,
    },
  });
  var point = turf.point([geom.lat, geom.lng]);
  var wkt = WKT.convert(point.geometry);
  list.value.push({
    name: name,
    layer: layer,
    icon: "d.png",
    wkt: wkt,
    lng: geom.lng,
    lat: geom.lat,
  });
  plotNum.value.point++;
};
@@ -157,7 +174,16 @@
      clampToGround: true,
    },
  });
  var linestring = turf.lineString([
    [-24, 63],
    [-23, 60],
    [-25, 65],
    [-20, 69],
  ]);
  var wkt = WKT.convert(linestring.geometry);
  list.value.push({
    wkt: wkt,
    name: name,
    layer: layer,
    icon: "x.png",
@@ -167,10 +193,12 @@
const setAddEntityPolygon = (res) => {
  var std = [];
  var res_val = res.polygon.hierarchy.getValue().positions;
  var geom;
  var coord = [];
  for (var i in res_val) {
    var geom = setCartesianToEightFour(res_val[i]);
    geom = setCartesianToEightFour(res_val[i]);
    std.push(Cesium.Cartesian3.fromDegrees(geom.lng, geom.lat));
    coord.push([geom.lng, geom.lat]);
  }
  var name = "Polygon#" + plotNum.value.polygon;
  var layer = Viewer.entities.add({
@@ -186,10 +214,27 @@
      height: 0,
    },
  });
  coord.push(coord[0]);
  var polygon = turf.polygon([coord]);
  var wkt = WKT.convert(polygon.geometry);
  console.log(polygon.geometry);
  let turfPoint = [];
  polygon.geometry.coordinates[0].forEach((e) => {
    turfPoint.push(turf.point(e));
  });
  var features = turf.featureCollection(turfPoint);
  var center = turf.center(features);
  console.log(center);
  list.value.push({
    wkt: wkt,
    name: name,
    layer: layer,
    icon: "m.png",
    lng: center.geometry.coordinates[0],
    lat: center.geometry.coordinates[1],
  });
  plotNum.value.polygon++;
};
@@ -224,7 +269,6 @@
      if (nVal.entitiesData != {} && nVal.entitiesData.name) {
        for (var i in list.value) {
          if (list.value[i].name == nVal.entitiesData.name) {
            console.log(list.value[i].name);
            list.value.splice(i, 1);
            break;
          }
src/views/plotting/plottingInquire.vue
@@ -28,7 +28,7 @@
              <Bar-graph :width="'100%'" :height="'260px'"></Bar-graph>
            </div>
            <div class="inquireContent_input" v-if="!chartIsshow">
              <div class="inquireContent_input_left">
              <!-- <div class="inquireContent_input_left">
                <div class="label">范围框</div>
                <el-input
                  v-model="ScopeBox.Scop"
@@ -37,14 +37,15 @@
                >
                  <template #append>km</template>
                </el-input>
              </div>
              <div class="inquireContent_input_right">
              </div> -->
              <div class="inquireContent_input_right" v-show="pixelIsShow">
                <div class="label">范围框内最大像素值</div>
                <el-select
                  v-model="ScopeBox.pixel"
                  class="m-2"
                  placeholder="像素值"
                  size="small"
                  @change="pixelChange"
                >
                  <el-option
                    v-for="item in options"
@@ -58,15 +59,15 @@
            <div class="inquireContent_msg" v-if="!chartIsshow">
              <div class="inquireContent_msg_k">
                <span>提取的边界框</span>
                <span>{{ ScopeBox.pixel }}</span>
                <span>{{ ScopeBox.pixel }}×{{ ScopeBox.pixel }}</span>
              </div>
              <div class="inquireContent_msg_k">
              <!-- <div class="inquireContent_msg_k">
                <span>使用</span>
                <span
                  >{{ ScopeBox.Scop * 1000 }}.00,{{ ScopeBox.Scop * 1000 }}.00
                  m/px</span
                >
              </div>
              </div> -->
            </div>
            <div class="inquireContent_table" v-if="!chartIsshow">
              <div class="table">
@@ -78,22 +79,18 @@
                  </div>
                </div>
                <div class="table_content">
                  <div class="table_tr">
                    <div class="table_td">1</div>
                  <div class="table_tr" v-for="(e, i) in resultList" :key="i">
                    <div class="table_td">{{ i + 1 }}</div>
                    <div class="table_td">
                      <span> å¹³å‡åœ°çƒèƒ½è§åº¦120m [1]: </span>
                      <span> 112.993 </span>
                    </div>
                  </div>
                  <div class="table_tr">
                    <div class="table_td">2</div>
                    <div class="table_td">
                      <span> å¹³å‡åœ°çƒèƒ½è§åº¦120m [1]: </span>
                      <span> 112.993 </span>
                      <span> {{ e.layerName }}</span>
                      <span> {{ e.avg }}</span>
                    </div>
                  </div>
                </div>
              </div>
            </div>
            <div class="download">
              <el-button link @click="download">下载 CSV</el-button>
            </div>
          </el-tab-pane>
        </el-tabs>
@@ -116,9 +113,13 @@
import { useStore } from "vuex"; // å¼•å…¥useStore æ–¹æ³•
//echarts
import BarGraph from "@/components/BarGraph.vue";
import { saveFSDZJsonToExcel } from "@/utils/downloadCSV.js";
import { selectByPoint, selectByPolygon, selectByPolyline } from "@/api/api";
import { ElMessage } from "element-plus";
const store = useStore(); // è¯¥æ–¹æ³•用于返回store å®žä¾‹
const emits = defineEmits(["setCloseplotting"]);
let isShow = ref(false);
let pixelIsShow = ref(true);
let inquireData = ref({
  name: "path #9",
  icon: "d.png",
@@ -126,50 +127,97 @@
const activeName = ref("second");
const ScopeBox = ref({
  Scop: "",
  pixel: "",
  pixel: "1",
});
const options = [
  {
    value: "1×1",
    value: "1",
    label: "1×1",
  },
  {
    value: "2×2",
    value: "2",
    label: "2×2",
  },
  {
    value: "4×4",
    value: "4",
    label: "4×4",
  },
  {
    value: "8×8",
    value: "8",
    label: "8×8",
  },
  {
    value: "16×16",
    value: "16",
    label: "16×16",
  },
  {
    value: "32×32",
    value: "32",
    label: "32×32",
  },
  {
    value: "64×64",
    value: "64",
    label: "64×64",
  },
  {
    value: "Option3",
    label: "Option3",
  },
  {
    value: "128×128",
    value: "128",
    label: "128×128",
  },
  {
    value: "256×256",
    value: "256",
    label: "256×256",
  },
];
let resultList = ref([]);
//像素选择
const pixelChange = (val) => {
  selectPoint({
    pixel: val,
    wkt: `POINT (${store.state.plottingInquireData.entitiesData.lng} ${store.state.plottingInquireData.entitiesData.lat})`,
  });
};
//下载csv
const download = () => {
  saveFSDZJsonToExcel(resultList.value, "123", "");
};
//点查询接口
const selectPoint = async (res) => {
  const dt = await selectByPoint(res);
  if (dt.code !== 200) {
    return ElMessage.error("查询错误");
  }
  dt.result.forEach((e) => {
    if (e.code != 200) {
      e.avg = "-";
      e.max = "-";
      e.min = "-";
    }
    e.lng = store.state.plottingInquireData.entitiesData.lng;
    e.lat = store.state.plottingInquireData.entitiesData.lat;
    resultList.value.push(e);
  });
};
//面查询接口
const selectPolygon = async (res) => {
  const dt = await selectByPolygon(res);
  dt.result.forEach((e) => {
    if (e.code != 200) {
      e.avg = "-";
      e.max = "-";
      e.min = "-";
    }
    e.lng = store.state.plottingInquireData.entitiesData.lng;
    e.lat = store.state.plottingInquireData.entitiesData.lat;
    resultList.value.push(e);
  });
};
//线查询接口
const selectPolyline = async (res) => {
  const dt = await selectByPolyline(res);
  console.log(dt);
};
const setLayerLocation = () => {
  var entities = Viewer.entities._entities._array;
  for (var i in entities) {
@@ -211,6 +259,24 @@
    inquireData.value = nVal.entitiesData;
    if (nVal.entitiesData.icon == "x.png") {
      chartIsshow.value = true;
      // selectPolyline({
      //   pixel: ScopeBox.value.pixel,
      //   wkt: `POINT (${nVal.entitiesData.lng})`,
      // })
    }
    if (nVal.entitiesData.icon == "m.png") {
      if (nVal.entitiesData.name == oVal.entitiesData.name) {
        return;
      }
      pixelIsShow.value = false;
      selectPolygon({ wkt: nVal.entitiesData.wkt });
      // console.log(nVal);
    }
    if (nVal.entitiesData.icon == "d.png") {
      selectPoint({
        pixel: ScopeBox.value.pixel,
        wkt: nVal.entitiesData.wkt,
      });
    }
  },
  { deep: true }
@@ -332,7 +398,7 @@
    .inquireContent_table {
      padding-right: 15px;
      padding-left: 15px;
      padding-bottom: 14px;
      padding-bottom: 10px;
      .table {
        background: rgba(0, 0, 0, 0, 4);
        border: 1px solid rgba(214, 228, 255, 0.4);
@@ -353,6 +419,7 @@
            justify-content: center;
            align-items: center;
            border-right: 1px solid rgba(214, 228, 255, 0.4);
            box-sizing: border-box;
          }
          .table_head_td:nth-child(2) {
            width: 237px;
@@ -367,26 +434,44 @@
          height: 440px;
          overflow: auto;
          .table_tr {
            height: 27px;
            // height: 27px;
            display: flex;
            background: #000000;
            // padding: 5px 0;
            .table_td {
              width: 50px;
              font-size: 14px;
              font-size: 12px;
              font-weight: 400;
              color: #d6e4ff;
              display: flex;
              justify-content: center;
              align-items: center;
              border-right: 1px solid rgba(214, 228, 255, 0.4);
              white-space: nowrap;
              box-sizing: border-box;
              // padding: 5px;
              // white-space: nowrap;
              span {
                display: block;
                width: 50%;
                word-wrap: break-word;
                // white-space: pre;
              }
              span:nth-child(2) {
                display: flex;
                justify-content: flex-end;
              }
            }
            .table_td:nth-child(2) {
              width: 237px;
              display: flex;
              justify-content: space-between;
              align-items: center;
              padding: 0 10px;
              // padding: 0 10px;
              padding-left: 10px;
              padding-right: 10px;
              padding-top: 5px;
              padding-bottom: 5px;
              border-right: 0;
            }
          }
@@ -407,6 +492,17 @@
        }
      }
    }
    .download {
      padding-right: 15px;
      padding-left: 15px;
      padding-bottom: 14px;
      display: flex;
      justify-content: flex-end;
      .el-button {
        font-size: 12px;
        color: #d6e4ff;
      }
    }
  }
}
</style>