business.vue 53 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311
  1. <template>
  2. <div ref="graphyMain" class="canvasGraphy" style="width:100%;" v-loading="loading.show" :element-loading-text="loading.num + '/' + loading.total">
  3. <div v-show="hasMap" class="header-search">
  4. <!-- 初始两个按钮 -->
  5. <div v-show="type == 1">
  6. <el-button @click=" type = 2" icon="el-icon-search">查找业务空间</el-button>
  7. <el-button @click="myDialogVisible = true">创建业务空间</el-button>
  8. <span style="font-size:13px;color:#606266;margin-left:40px;display:inline-block;">
  9. 提示:
  10. <i style="color:red;">红色字体</i>的业务空间为不相邻元空间组成,请检查是否要修改
  11. </span>
  12. </div>
  13. <!-- 搜索下拉列表定位 -->
  14. <div v-show="type == 2">
  15. <el-autocomplete popper-class="my-autocomplete" v-model="search" :fetch-suggestions="querySearch" placeholder="输入平面图中已有的业务空间名称进行查找" width="180px" @select="handleSelect">
  16. <i class="el-icon-search el-input__icon" slot="suffix" @click="handleIconClick"></i>
  17. <template slot-scope="{ item }">
  18. <div class="name" style="position: relative;">
  19. {{ item.infos.RoomLocalName |cutString(8) }}
  20. <span
  21. class="addr"
  22. style="position: absolute;right:10px;color:#409EFF;"
  23. >定位</span>
  24. </div>
  25. </template>
  26. </el-autocomplete>
  27. <el-button style="margin-left:10px;" type="text" @click="clearDimension">收起</el-button>
  28. </div>
  29. <!-- 点击元空间显示 -->
  30. <div v-show="type == 3">
  31. <div class="div50">
  32. <el-button
  33. class="float-right"
  34. @click="SpaceDialog"
  35. type="primary"
  36. plain
  37. >从未关联元空间的业务空间中选择</el-button>
  38. </div>
  39. <div class="div50">
  40. <el-button @click="clearDimension" plain>取 消</el-button>
  41. <el-button @click="createSP" type="primary">创建新的业务空间</el-button>
  42. </div>
  43. </div>
  44. <!-- 点击业务空间显示 -->
  45. <div v-show="type == 4">
  46. <div class="div50">
  47. <el-button class="float-right" @click="divide" type="primary" plain>重新划分业务空间</el-button>
  48. </div>
  49. <div class="div50">
  50. <el-button @click="clearDimension" plain>取 消</el-button>
  51. <el-button @click="bussinDea" type="primary">查看详情</el-button>
  52. </div>
  53. </div>
  54. <!-- 点击业务空间后点击元空间 -->
  55. <div v-show="type == 5">
  56. <div class="div50">
  57. <el-button @click="clearDimension" class="float-right" plain>取 消</el-button>
  58. </div>
  59. <div class="div50">
  60. <el-button @click="saveChange" type="primary">保存修改</el-button>
  61. </div>
  62. </div>
  63. <el-button
  64. v-show="type == 1"
  65. @click="getPiss"
  66. style="position: absolute;top: 10px;right: 10px;"
  67. type="text"
  68. >未关联元空间的业务空间 {{num}} 条</el-button>
  69. </div>
  70. <div
  71. v-show="hasMap"
  72. ref="canvasWidth"
  73. class="canvasWidth"
  74. v-loading="myLoading"
  75. style="width:100%;"
  76. >
  77. <canvas :id="canvasId + 'canvas' " :width="canvasW" :height="canvasH"></canvas>
  78. <div
  79. style="height: 35px;overflow: hidden;z-index:99;transform: translateX(-50%);position: absolute;bottom: 10%;left: 50%;"
  80. >
  81. <el-button @click="smallSize" type="primary">- 缩小</el-button>
  82. <el-button @click="suitableSize" type="primary">合适比例</el-button>
  83. <el-button @click="bigSize" type="primary">+ 放大</el-button>
  84. </div>
  85. </div>
  86. <div
  87. v-show="!hasMap"
  88. class="center"
  89. style="height: 400px;padding-top:200px;box-sizing:border-box;"
  90. >
  91. <i class="iconwushuju iconfont"></i>
  92. {{!!buildMess ? '请初始化平面图' : '请选择楼层'}}
  93. </div>
  94. <el-dialog title="提示" :visible.sync="dialogVisible" :before-close="clearDimension" width="30%">
  95. <p style="color:red;line-height:24px;margin-bottom: 10px;" v-show="isAbutMsg">注意:您选择的元空间并未相邻!</p>
  96. <p style="line-height:24px;margin-bottom: 10px;">请输入创建的业务空间名:</p>
  97. <!-- <p>
  98. <el-input
  99. placeholder="请输入业务空间名"
  100. v-model="name"
  101. clearable>
  102. </el-input>
  103. </p>-->
  104. <el-form
  105. :model="ruleForm"
  106. :rules="rules"
  107. ref="ruleForm"
  108. label-width="100px"
  109. class="demo-ruleForm"
  110. >
  111. <el-form-item label label-width="0" prop="name">
  112. <el-input v-model="ruleForm.name"></el-input>
  113. </el-form-item>
  114. </el-form>
  115. <span slot="footer" class="dialog-footer">
  116. <el-button @click="clearDimension">取 消</el-button>
  117. <el-button type="primary" @click="isTrue">确 定</el-button>
  118. </span>
  119. </el-dialog>
  120. <el-dialog title="提示" :visible.sync="myDialogVisible" width="30%">
  121. <p style="line-height:26px;">方法1:直接在平面图中点击单个或多个带⬇️标记的元空间创建业务空间</p>
  122. <p style="line-height:26px;">方法2:根据未关联业务空间的元空间批量创建业务空间</p>
  123. <span slot="footer" class="dialog-footer">
  124. <el-button @click="createBatchSq">批量创建业务空间</el-button>
  125. <el-button type="primary" @click="myDialogVisible = false">返回平面图手动选择</el-button>
  126. </span>
  127. </el-dialog>
  128. </div>
  129. </template>
  130. <script>
  131. import axios from "axios";
  132. //引擎的引用
  133. import {
  134. SGraphyView,
  135. SGraphyScene,
  136. SGraphyRectItem,
  137. SGraphyLineItem,
  138. SGraphyPolygonItem,
  139. SGraphyVirtualItem,
  140. SGraphyImageItem,
  141. SGraphyPillarItems
  142. } from "@/assets/graphy";
  143. import pako from '@/assets/pako/pako'
  144. //ele动画组件
  145. import tools from "@/utils/scan/tools";
  146. let data = "";
  147. let scale = 120; //缩放比例
  148. let myData = [{
  149. Id: "1221512",
  150. PointList: {
  151. X: -35146.875,
  152. Y: 40680
  153. }
  154. }];
  155. // let colorArr = [
  156. // "rgba(0,245,255,.2)",
  157. // "rgba(255,218,185,.2)",
  158. // "rgba(132,112,255,.2)",
  159. // "rgba(127,255,0,.2)",
  160. // "rgba(238,92,66,.2)",
  161. // "rgba(255,255,224,.2)",
  162. // "rgba(238,233,233,.2)",
  163. // "rgba(156,156,156,.2)",
  164. // "rgba(144,238,144,.2)",
  165. // "rgba(180,205,205,.2)"
  166. // ];
  167. let colorArr = [
  168. "#F9C3C3",
  169. "#FFD1BF",
  170. "#FFF3BF",
  171. "#D8F7C6",
  172. "#C6F2F6",
  173. "#DCE3C0",
  174. "#FAE6C9",
  175. "#E3D7F7",
  176. "#C4CBF8",
  177. "#DEC3F6"
  178. ];
  179. // function hexify(color) {
  180. // var values = color
  181. // .replace(/rgba?\(/, '')
  182. // .replace(/\)/, '')
  183. // .replace(/[\s+]/g, '')
  184. // .split(',');
  185. // var a = parseFloat(values[3] || 1),
  186. // r = Math.floor(a * parseInt(values[0]) + (1 - a) * 255),
  187. // g = Math.floor(a * parseInt(values[1]) + (1 - a) * 255),
  188. // b = Math.floor(a * parseInt(values[2]) + (1 - a) * 255);
  189. // return "#" +
  190. // ("0" + r.toString(16)).slice(-2) +
  191. // ("0" + g.toString(16)).slice(-2) +
  192. // ("0" + b.toString(16)).slice(-2);
  193. // }
  194. // colorArr = colorArr.map(item => {
  195. // return hexify(item)
  196. // })
  197. class MainScene extends SGraphyScene {
  198. constructor() {
  199. super();
  200. //资产id
  201. } // Function constructor()
  202. /**
  203. * 绘制背景
  204. *
  205. * @param canvas 画布
  206. * @param rect 更新绘制区域
  207. */
  208. // drawBackground(canvas, rect) {}
  209. }
  210. import {
  211. formBIMToPri, // 将bimId转换成物理世界id
  212. createBusiness, //添加业务空间
  213. createRelation, //添加关系
  214. getGraphyId, //获取图类型
  215. getBussines2, //获取业务空间
  216. getRelation, //获取业务空间下的元空间id
  217. deleteRelation, //删除关系
  218. isAbut
  219. } from "@/api/scan/request";
  220. import {mapGetters, mapActions} from "vuex";
  221. export default {
  222. name: "HelloWorld",
  223. props: {
  224. canvasId: {
  225. type: String
  226. }
  227. },
  228. computed: {
  229. ...mapGetters("layout", [
  230. "projectId",
  231. "secret",
  232. "userId"
  233. ])
  234. },
  235. data() {
  236. return {
  237. view: "",
  238. num: "",
  239. mainScene: new MainScene(),
  240. dataMax: "", //最大值最小值数据
  241. scene: {
  242. x: 0,
  243. y: 0
  244. },
  245. dialogVisible: false, //浮层
  246. id: null,
  247. canvasH: 600,
  248. canvasW: 800,
  249. param: {
  250. ProjId: "", //项目id
  251. UserId: "", //用户id
  252. secret: ""
  253. },
  254. myDialogVisible: false,
  255. wallList: [], //处理后的墙的线条
  256. type: 1, //1 默认显示初始按钮, 2搜索下拉, 3点击元空间, 4点击业务空间
  257. restaurants: [],
  258. search: "",
  259. idList: [],
  260. buildMess: null,
  261. loading: {
  262. show: false,
  263. num: 0,
  264. total: 0,
  265. errorNum: 0
  266. },
  267. graphyId: "",
  268. relationList: [],
  269. myLoading: false,
  270. hasMap: false,
  271. ruleForm: {
  272. name: ""
  273. },
  274. rules: {
  275. name: [{
  276. required: true,
  277. message: "请输入需要创建的业务空间名称",
  278. trigger: "blur"
  279. }]
  280. },
  281. isAbutMsg: false, //是否相邻提示
  282. businessData: "", //新建业务空间数据
  283. spaceType: {}, //space类型code
  284. };
  285. },
  286. created() {
  287. this.param.ProjId = this.projectId
  288. this.param.secret = this.secret
  289. this.param.UserId = this.userId
  290. // this.getJson("Fl110108000327d8f006c39f49feb40e24a7ef22323220181119025802bim.jsonz")
  291. // this.getJson("bim.jsonz")
  292. },
  293. mounted() {
  294. console.log(this.canvasId)
  295. // this.resetSize();
  296. // window.addEventListener("click",this.typeTo1)
  297. },
  298. methods: {
  299. //获取数据
  300. getData(floorMap, buildMess, data) {
  301. this.spaceType = data
  302. this.loading.show = false;
  303. this.type = 1;
  304. this.idList = [];
  305. this.buildMess = buildMess;
  306. if (!floorMap) {
  307. this.hasMap = false;
  308. } else {
  309. this.getJson(floorMap);
  310. this.hasMap = true;
  311. }
  312. },
  313. clearList() {
  314. this.idList = []
  315. },
  316. //未关联元空间的业务空间
  317. getPiss() {
  318. this.$emit("getSp", [{}], this.buildMess, this.graphyId);
  319. },
  320. //查询绑定了元空间的业务空间
  321. getHasSpace() {
  322. console.log(this.spaceType, "spaceType")
  323. let param = {
  324. data: {
  325. criteria: {
  326. id: this.buildMess.code,
  327. // graphId: this.graphyId,
  328. // relType: this.spaceType.rel_type,
  329. // exclude: false,
  330. // side: 1,
  331. type: [this.spaceType.code],
  332. "include": [ // 可选, 只查询指定图/关系中的对象
  333. {
  334. "graphId": this.graphyId,
  335. "graphType": this.spaceType.code,
  336. "relType": this.spaceType.rel_type,
  337. "side": "toId",
  338. // "fromId": "", // 选填
  339. // "toId": "" // 选填
  340. }
  341. ]
  342. },
  343. },
  344. ProjId: this.param.ProjId,
  345. secret: this.param.secret
  346. }
  347. getBussines2(param)
  348. .then(res => {
  349. if (res.data.Result == "success") {
  350. this.restaurants = res.data.Content;
  351. let nameList = [];
  352. if (res.data.Content && res.data.Content.length) {
  353. this.relationList = res.data.Content.map(item => {
  354. nameList.push(item.infos.RoomLocalName);
  355. return item.id;
  356. });
  357. this.locationPath(this.relationList, nameList);
  358. }
  359. } else {
  360. this.$message.error(res.data.ResultMsg);
  361. }
  362. this.myLoading = false;
  363. })
  364. .catch(() => {
  365. // console.log("请求出错");
  366. });
  367. },
  368. //确定新建
  369. isTrue() {
  370. this.$refs.ruleForm.validate(valid => {
  371. if (valid) {
  372. this.loading.show = true;
  373. this.loading.num = 0;
  374. this.loading.total = 1 * 2;
  375. this.businessData.infos.RoomLocalName[0].value = this.ruleForm.name;
  376. this.createSpace(this.businessData, this.idList, true);
  377. this.dialogVisible = false;
  378. } else {
  379. // console.log("error submit!!");
  380. return false;
  381. }
  382. });
  383. },
  384. //查询未绑定元空间的业务空间
  385. getNoSpace() {
  386. getBussines2({
  387. data: {
  388. criteria: {
  389. id: this.buildMess.code,
  390. // graphId: this.graphyId,
  391. // relType: this.spaceType.rel_type,
  392. // exclude: false,
  393. // side: 1,
  394. type: [this.spaceType.code],
  395. "exclude": [ // 可选, 只查询指定图/关系中的对象
  396. {
  397. "graphId": this.graphyId,
  398. "graphType": this.spaceType.code,
  399. "relType": this.spaceType.rel_type,
  400. "side": "toId",
  401. // "fromId": "", // 选填
  402. // "toId": "" // 选填
  403. }
  404. ]
  405. },
  406. },
  407. ProjId: this.projectId,
  408. secret: this.secret
  409. })
  410. .then(res => {
  411. if (res.data.Result == "success") {
  412. this.num = res.data.Content.length;
  413. } else {
  414. this.$message.error(res.data.ResultMsg);
  415. }
  416. })
  417. .catch(() => {
  418. // console.log("请求出错");
  419. });
  420. },
  421. //当type=2时点击变成1
  422. typeTo1() {
  423. if (this.type == 2) {
  424. this.type = 1;
  425. }
  426. },
  427. getJson(jsonId) {
  428. axios({
  429. method: 'get',
  430. url: "/image-service/common/file_get/" + jsonId + "?systemId=revit",
  431. data: {},
  432. responseType: 'blob',
  433. // contentType: "charset=utf-8"
  434. })
  435. .then(res => {
  436. // console.log(res.data, "res.data")
  437. let data = null
  438. var blob = res.data;
  439. var reader = new FileReader();
  440. reader.readAsBinaryString(blob)
  441. // console.log("获取到了数据")
  442. let _this = this
  443. reader.onload = function(readerEvt) {
  444. // console.log("reader获取完毕")
  445. var binaryString = readerEvt.target.result;
  446. // let base64Data = btoa(binaryString)
  447. //解压数据
  448. let base64Data = btoa(binaryString)
  449. let unGzipData = pako.unzip(base64Data)
  450. // console.log(unGzipData)
  451. // console.log(unGzipData, "atob")
  452. data = unGzipData
  453. _this.dataMax = tools.getPoint(data);
  454. console.log(unGzipData, data)
  455. if (data.WallList && data.WallList.length) {
  456. tools.changeMap(data.WallList, -1, "PointList");
  457. }
  458. if (data.SpaceList && data.SpaceList.length) {
  459. tools.changeMap(data.SpaceList, -1, "Paths");
  460. }
  461. if (data.ColumnList && data.ColumnList.length) {
  462. tools.changeMap(data.ColumnList, -1, "Path");
  463. }
  464. if (data.VirtualWallList && data.VirtualWallList.length) {
  465. tools.changeMap(data.VirtualWallList, -1, "PointList");
  466. }
  467. if (data.EquipmentList && data.EquipmentList.length) {
  468. tools.changeMap(data.EquipmentList, -1, "PointList");
  469. }
  470. let ids = [];
  471. if (data.SpaceList && data.SpaceList.length) {
  472. data.SpaceList.map(items => {
  473. items.BimId = _this.buildMess.code + ":" + items.BimId;
  474. ids.push(items.BimId);
  475. });
  476. } else {
  477. _this.$message("没有元空间数据")
  478. }
  479. console.log(ids,'ids')
  480. if(!!ids && ids.length){
  481. _this.bimIdToId(ids, data);
  482. }else{
  483. //没有id没有map
  484. _this.hasMap = false
  485. }
  486. _this.myLoading = true;
  487. };
  488. // console.log(reader)
  489. });
  490. },
  491. //获取图实例关系
  492. getGraphy() {
  493. getGraphyId({
  494. type: "ElementSptoSpace",
  495. ProjId: this.projectId,
  496. secret: this.secret
  497. })
  498. .then(res => {
  499. if (res.data.Result == "success") {
  500. this.graphyId = res.data.graph_id;
  501. this.getHasSpace();
  502. this.getNoSpace();
  503. } else {
  504. this.$message.error(res.data.ResultMsg);
  505. }
  506. })
  507. .catch(() => {
  508. this.$message.error("请求错误");
  509. });
  510. },
  511. bimIdToId(ids, data) {
  512. formBIMToPri({
  513. type: ["Si"],
  514. ids: ids,
  515. ProjId: this.param.ProjId,
  516. secret: this.param.secret
  517. })
  518. .then(res => {
  519. if (res.data.Result == "success") {
  520. data.SpaceList.map((item, index) => {
  521. res.data.Content.map((i, li) => {
  522. //判断bimId是否相同
  523. if (item.BimId == i.infos.BIMID) {
  524. item.id = i.id;
  525. }
  526. });
  527. });
  528. this.createCanvas();
  529. this.initGraphy(data);
  530. console.log("请求完毕")
  531. } else {
  532. this.$message.error(res.data.ResultMsg);
  533. }
  534. })
  535. .catch(() => {
  536. this.$message.error("请求出错");
  537. });
  538. },
  539. //创建实例
  540. createCanvas() {
  541. //初始化
  542. if (this.view.scene) {
  543. this.view.scene.root.children = [];
  544. this.view = null;
  545. }
  546. this.view = new SGraphyView(this.canvasId + "canvas", this.mainScene);
  547. this.view.onDraw();
  548. // this.view.canvasView.addEventListener("mouseup", this.dataChange);
  549. // this.view.canvasView.addEventListener("mousemove", this.canvasMove);
  550. },
  551. //初始化canvas大小
  552. resetSize() {
  553. this.canvasW =
  554. document.getElementById("businessSpace").offsetWidth - 2;
  555. this.canvasH = document.getElementById("app").offsetHeight - 240;
  556. let classs = document.getElementsByClassName("canvasWidth");
  557. // for(let i = 0; i < classs.length;i++){
  558. // classs[i].style.height = this.canvasH + 'px'
  559. // }
  560. this.$refs.canvasWidth.style.height = this.canvasH + "px";
  561. },
  562. //实例化视图
  563. initGraphy(data) {
  564. this.resetSize();
  565. this.view.pos.x = this.view.pos.y = -50;
  566. let equip = data.EquipmentList,
  567. wall = data.WallList,
  568. virtual = data.VirtualWallList,
  569. space = data.SpaceList,
  570. column = data.ColumnList,
  571. spaceStr;
  572. //空间
  573. if (space && space.length) {
  574. for (let i = 0; i < space.length; i++) {
  575. if (space[i].Paths[1] && space[i].Paths[1].length >= 2) {
  576. spaceStr = new SGraphyPolygonItem(
  577. space[i].Paths[0],
  578. 1,
  579. "rgba(111,111,111,0.5)",
  580. "#fff",
  581. space[i].id, {
  582. x: space[i].LocationPoint.X,
  583. y: space[i].LocationPoint.Y * -1
  584. },
  585. space[i].Name,
  586. space[i].Paths
  587. );
  588. this.mainScene.addItem(spaceStr);
  589. }
  590. }
  591. for (let i = 0; i < space.length; i++) {
  592. if (space[i].Paths[0] && space[i].Paths[0].length >= 2 && !!!space[i].Paths[1]) {
  593. spaceStr = new SGraphyPolygonItem(
  594. space[i].Paths[0],
  595. 1,
  596. "rgba(111,111,111,0.5)",
  597. "#fff",
  598. space[i].id, {
  599. x: space[i].LocationPoint.X,
  600. y: space[i].LocationPoint.Y * -1
  601. },
  602. space[i].Name
  603. );
  604. this.mainScene.addItem(spaceStr);
  605. }
  606. }
  607. }
  608. //获取中心点
  609. let rect = this.view.scene.worldRect();
  610. //初始化画布缩放比例
  611. this.view.scale = 1;
  612. //计算缩放比例
  613. this.view.scale = Math.min(
  614. this.view.width / (rect.width * 1.2),
  615. this.view.height / (rect.height * 1.2)
  616. );
  617. this.view.minScale = this.view.scale / 10
  618. this.view.maxScale = this.view.scale * 10
  619. // 移动画布
  620. this.view.pos.x =
  621. (-(rect.right + rect.left) / 2) * this.view.scale + this.view.width / 2;
  622. this.view.pos.y =
  623. (-(rect.bottom + rect.top) / 2) * this.view.scale +
  624. this.view.height / 2;
  625. //点击事件
  626. this.view.canvasView.addEventListener("click", this.checkSpace);
  627. this.getGraphy();
  628. },
  629. /** canvas事件------------------------------------------------------------------------------------*/
  630. //点击元空间
  631. checkSpace(e) {
  632. let item = tools.mouseInElement(this.view, e);
  633. console.log(item)
  634. let items = this.mainScene.root.children;
  635. //点击业务空间
  636. if (
  637. item.falg &&
  638. item.item.businessId &&
  639. (item.item.isBusiness == 2 || item.item.isBusiness == 7)
  640. ) {
  641. // console.log("点击不可点击的业务空间", item);
  642. if (this.type == 2) {
  643. this.idList = [];
  644. items.map(i => {
  645. if (i.isBusiness == 3) {
  646. i.isBusiness = 2;
  647. }
  648. });
  649. }
  650. items.map(i => {
  651. if (i.isBusiness == 6) {
  652. i.isBusiness = 2;
  653. } else if (i.isBusiness == 3) {
  654. i.isBusiness = 1;
  655. }
  656. });
  657. this.type = 4;
  658. items.map(i => {
  659. if (i.isBusiness == 6) {
  660. i.isBusiness = 2;
  661. }
  662. if (i.businessId == item.item.businessId) {
  663. i.isBusiness = 6;
  664. }
  665. });
  666. this.idList.push({
  667. id: item.item.businessId,
  668. name: item.item.businessName || item.item.name
  669. });
  670. }
  671. //点击没有业务空间的元空间
  672. if (
  673. item.falg &&
  674. !item.item.businessId &&
  675. (item.item.isBusiness == 4 || item.item.isBusiness == 1) &&
  676. this.type != 5
  677. ) {
  678. // console.log("点击的是没有业务空间的元空间", item);
  679. if (this.type == 4) {
  680. this.idList = [];
  681. items.map(i => {
  682. if (i.isBusiness == 6) {
  683. i.isBusiness = 2;
  684. } else if (i.isBusiness == 3) {
  685. i.isBusiness = 1;
  686. }
  687. });
  688. // console.log("清空", this.idList);
  689. }
  690. this.type = 3;
  691. item.item.isBusiness = 3;
  692. this.idList.push({
  693. id: item.item.id,
  694. name: item.item.businessName || item.item.name
  695. });
  696. }
  697. //在重新编辑业务空间状态
  698. if (
  699. this.type == 5 &&
  700. item.falg &&
  701. !item.item.businessId &&
  702. (item.item.isBusiness == 4 || item.item.isBusiness == 1)
  703. ) {
  704. item.item.isBusiness = 3;
  705. this.idList.push({
  706. id: item.item.id,
  707. name: item.item.businessName || item.item.name
  708. });
  709. }
  710. //在重新编辑时的提示
  711. if (
  712. item.falg &&
  713. item.item.businessId &&
  714. (item.item.isBusiness == 4 || item.item.isBusiness == 1)
  715. ) {
  716. // console.log("44444");
  717. item.item.isBusiness = 3;
  718. this.idList.push({
  719. id: item.item.id,
  720. name: item.item.businessName || item.item.name,
  721. parentId: item.item.businessId
  722. });
  723. }
  724. if (item.falg && item.item.isBusiness == 5) {
  725. this.$message("该空间为业务空间,请勿点击");
  726. }
  727. // if(item.falg && item.item.businessId)
  728. },
  729. /** 搜索 ------------------------------------------------------------------------------ */
  730. querySearch(queryString, cb) {
  731. var restaurants = this.restaurants;
  732. var results = queryString ?
  733. restaurants.filter(this.createFilter(queryString)) :
  734. restaurants;
  735. // 调用 callback 返回建议列表的数据
  736. cb(results);
  737. },
  738. createFilter(queryString) {
  739. return restaurant => {
  740. return restaurant.infos.RoomLocalName.indexOf(queryString) > -1;
  741. };
  742. },
  743. handleSelect(item) {
  744. this.locationPath(item.id);
  745. },
  746. handleIconClick(ev) {
  747. this.locationPath(ev.id);
  748. },
  749. //定位
  750. locationPath(id, name) {
  751. let param = {
  752. criterias: {},
  753. ProjId: this.projectId,
  754. secret: this.secret
  755. },
  756. falg = false;
  757. //查询多个关系
  758. if (id instanceof Array) {
  759. falg = true;
  760. param.criterias.criterias = [];
  761. id.map(item => {
  762. param.criterias.criterias.push({
  763. to_id: item,
  764. graph_id: this.graphyId,
  765. rel_type: this.spaceType.rel_type
  766. });
  767. });
  768. } else {
  769. //查询单个关系
  770. param.criterias.criteria = {
  771. to_id: id,
  772. graph_id: this.graphyId,
  773. rel_type: this.spaceType.rel_type
  774. };
  775. }
  776. getRelation(param)
  777. .then(res => {
  778. if (res.data.Result == "success") {
  779. if (falg) {
  780. //多个关系渲染颜色
  781. this.relationList = [];
  782. id.map((item, index) => {
  783. let children = res.data.Content[index].Content.map(i => {
  784. if (!!i) {
  785. return i.from_id;
  786. } else {
  787. return undefined;
  788. }
  789. });
  790. this.relationList.push({
  791. id: item,
  792. name: name[index],
  793. children: children,
  794. isAdjacent: true
  795. });
  796. });
  797. this.relationList.reverse();
  798. // this.getColor(this.relationList);
  799. //判断相邻代码
  800. this.spaceIsAbut(this.relationList);
  801. } else {
  802. //单个是定位
  803. this.getPathToCanvas(res.data.Content[0].from_id);
  804. }
  805. } else {
  806. this.$message.error(res.data.ResultMsg);
  807. }
  808. })
  809. .catch(() => {
  810. this.$message.error("请求错误");
  811. });
  812. },
  813. //给canvas的items渲染色彩
  814. getColor(list) {
  815. let items = this.mainScene.root.children;
  816. list.map(item => {
  817. if (item.children && item.children.length) {
  818. item.children.map(space => {
  819. items.map(canvas => {
  820. if (canvas.id == space) {
  821. canvas.businessId = item.id;
  822. canvas.businessName = item.name;
  823. }
  824. });
  825. });
  826. }
  827. });
  828. this.applyColor(list);
  829. },
  830. //渲染业务空间色彩
  831. applyColor(list) {
  832. let items = this.mainScene.root.children;
  833. items.map(item => {
  834. item.businessId = null;
  835. item.businessName = null;
  836. item.businessColor = "rgba(0,0,0,0)";
  837. item.isBusiness = 1;
  838. });
  839. list.map((item, index) => {
  840. if (item.children && item.children.length) {
  841. item.children.map(space => {
  842. items.map(canvas => {
  843. if (canvas.id == space) {
  844. canvas.businessId = item.id;
  845. canvas.businessName = item.name;
  846. canvas.businessColor = colorArr[index % 10];
  847. canvas.isBusiness = 2;
  848. //判断相邻代码
  849. if (!item.isAbut) {
  850. canvas.isBusiness = 7;
  851. }
  852. }
  853. });
  854. });
  855. }
  856. });
  857. },
  858. spaceIsAbut(list) {
  859. let data = list.map(item => {
  860. return {
  861. ids: item.children
  862. };
  863. });
  864. let param = {
  865. data: {
  866. floor: this.buildMess.code,
  867. criterias: data
  868. },
  869. ProjId: this.projectId,
  870. secret: this.secret
  871. };
  872. // console.log(param);
  873. isAbut(param)
  874. .then(res => {
  875. if (res.data.Result == "success") {
  876. res.data.Content.map((item, index) => {
  877. this.relationList[index].isAbut = item.abut;
  878. });
  879. this.getColor(this.relationList);
  880. } else {
  881. this.$message.error(res.data.ResultMsg);
  882. }
  883. })
  884. .catch(() => {
  885. this.$message.error("请求出错");
  886. });
  887. },
  888. getPathToCanvas(id) {
  889. let items = this.mainScene.root.children;
  890. items.map(item => {
  891. if (item.id == id) {
  892. //定位算法
  893. this.view.pos.x = -item.centerOfGravityPoint.x * this.view.scale +
  894. this.view.width / 2;
  895. this.view.pos.y = -item.centerOfGravityPoint.y * this.view.scale +
  896. this.view.height / 2;
  897. this.view.scale = this.view.scale;
  898. item.isBusiness = 3;
  899. this.idList = [];
  900. console.log(item)
  901. this.idList.push({
  902. id: item.businessId,
  903. name: item.businessName || '--'
  904. });
  905. } else if (item.businessId) {
  906. item.isBusiness = 2;
  907. } else {
  908. item.isBusiness = 1;
  909. }
  910. });
  911. },
  912. /** 按钮事件 ---------------------------------------------------------------------- */
  913. SpaceDialog() {
  914. this.$emit("dimension", this.idList, this.buildMess, this.graphyId);
  915. },
  916. bussinDea() {
  917. this.$emit("businessDetails", this.idList[this.idList.length - 1]);
  918. },
  919. //保存修改
  920. saveChange() {
  921. let id = ""
  922. this.idList.map(item => {
  923. if (!!item.parentId) {
  924. id = item.parentId
  925. }
  926. })
  927. this.deleteRela(id);
  928. },
  929. //调整到合适比例
  930. suitableSize() {
  931. //获取中心点
  932. let rect = this.view.scene.worldRect();
  933. //计算缩放比例
  934. this.view.scale = Math.min(
  935. this.view.width / (rect.width * 1.2),
  936. this.view.height / (rect.height * 1.2)
  937. );
  938. // 移动画布
  939. this.view.pos.x =
  940. (-(rect.right + rect.left) / 2) * this.view.scale + this.view.width / 2;
  941. this.view.pos.y =
  942. (-(rect.bottom + rect.top) / 2) * this.view.scale +
  943. this.view.height / 2;
  944. },
  945. //调整到小比例
  946. smallSize() {
  947. //获取中心点
  948. let rect = this.view.scene.worldRect();
  949. //计算缩放比例
  950. this.view.scale = this.view.scale * 0.9;
  951. // 移动画布
  952. this.view.pos.x =
  953. (-(rect.right + rect.left) / 2) * this.view.scale + this.view.width / 2;
  954. this.view.pos.y =
  955. (-(rect.bottom + rect.top) / 2) * this.view.scale +
  956. this.view.height / 2;
  957. },
  958. bigSize() {
  959. //获取中心点
  960. let rect = this.view.scene.worldRect();
  961. //计算缩放比例
  962. this.view.scale = this.view.scale * 1.1;
  963. // 移动画布
  964. this.view.pos.x =
  965. (-(rect.right + rect.left) / 2) * this.view.scale + this.view.width / 2;
  966. this.view.pos.y =
  967. (-(rect.bottom + rect.top) / 2) * this.view.scale +
  968. this.view.height / 2;
  969. },
  970. //删除关系
  971. deleteRela(id) {
  972. let param = {
  973. data: {
  974. criterias: [{
  975. to_id: id, //选填
  976. graph_id: this.graphyId, //选填
  977. rel_type: this.spaceType.rel_type //选填
  978. }]
  979. },
  980. ProjId: this.projectId,
  981. secret: this.secret
  982. };
  983. if (id) {
  984. deleteRelation(param)
  985. .then(res => {
  986. if (res.data.Result == "success") {
  987. this.loading.show = true;
  988. this.loading.num = 0;
  989. this.loading.total = 1;
  990. this.addRelation(id, this.idList);
  991. } else {
  992. this.$message.error(res.data.ResultMsg);
  993. }
  994. })
  995. .catch(() => {
  996. this.$message.error("请求失败");
  997. });
  998. } else {
  999. this.$message.error("请选择包含原业务空间的区域块")
  1000. }
  1001. },
  1002. //点击元空间后点击取消
  1003. clearDimension() {
  1004. this.myLoading = true;
  1005. let indexs = tools.clear(
  1006. this.mainScene.root.children,
  1007. 3,
  1008. this.idList,
  1009. "id"
  1010. );
  1011. this.myDialogVisible = false;
  1012. this.dialogVisible = false;
  1013. for (let i = 0; i < indexs.length; i++) {
  1014. this.mainScene.root.children[indexs[i]].isBusiness = 1;
  1015. }
  1016. this.idList = [];
  1017. this.type = 1;
  1018. this.getHasSpace();
  1019. },
  1020. //创建新的业务空间
  1021. createSP() {
  1022. let businessData = {
  1023. building_id: this.buildMess.buildCode,
  1024. floor_id: this.buildMess.code,
  1025. business_type: this.spaceType.code,
  1026. infos: {
  1027. RoomLocalName: [{
  1028. value: tools.getText(this.idList, "name")
  1029. }]
  1030. }
  1031. };
  1032. let data = [];
  1033. this.idList.map(i => {
  1034. data.push(i.id);
  1035. });
  1036. let param = {
  1037. data: {
  1038. floor: this.buildMess.code,
  1039. criterias: [{
  1040. ids: data
  1041. }]
  1042. },
  1043. ProjId: this.projectId,
  1044. secret: this.secret
  1045. };
  1046. // this.createSpace(businessData, this.idList, true);
  1047. //判断相邻代码
  1048. isAbut(param)
  1049. .then(res => {
  1050. if (res.data.Result == "success") {
  1051. this.dialogVisible = true;
  1052. this.ruleForm.name = businessData.infos.RoomLocalName[0].value;
  1053. this.businessData = businessData;
  1054. if (res.data.Content[0].abut) {
  1055. this.isAbutMsg = false;
  1056. // this.createSpace(businessData, this.idList, true);
  1057. } else {
  1058. this.isAbutMsg = true;
  1059. // this.$confirm(
  1060. // "您选择的元空间并未相邻,确定继续创建业务空间?",
  1061. // "提示",
  1062. // {
  1063. // confirmButtonText: "确定",
  1064. // cancelButtonText: "取消",
  1065. // type: "warning"
  1066. // }
  1067. // )
  1068. // .then(() => {
  1069. // this.loading.show = true;
  1070. // this.loading.num = 0;
  1071. // this.loading.total = 1 * 2;
  1072. // this.createSpace(businessData, this.idList, true);
  1073. // })
  1074. // .catch(() => {
  1075. // this.$message({
  1076. // type: "info",
  1077. // message: "已取消"
  1078. // });
  1079. // this.clearDimension();
  1080. // this.loading.show = false;
  1081. // });
  1082. }
  1083. } else {
  1084. this.$message.error(res.data.ResultMsg);
  1085. }
  1086. })
  1087. .catch(() => {
  1088. this.$message.error("请求失败");
  1089. });
  1090. },
  1091. //比较两个元空间是否相邻
  1092. compareSpace(ids) {
  1093. // console.log(ids);
  1094. },
  1095. //重新划分业务空间
  1096. divide() {
  1097. this.type = 5;
  1098. let id = this.idList[this.idList.length - 1],
  1099. items = this.mainScene.root.children;
  1100. items.map(item => {
  1101. if (item.businessId == id.id) {
  1102. item.isBusiness = 4;
  1103. } else if (item.businessId) {
  1104. item.isBusiness = 5;
  1105. }
  1106. });
  1107. this.idList = [];
  1108. },
  1109. //批量生成业务空间
  1110. createBatchSq() {
  1111. let items = this.mainScene.root.children;
  1112. let map = [];
  1113. items.map(item => {
  1114. if (!item.businessId) {
  1115. map.push({
  1116. id: item.id,
  1117. name: item.name
  1118. });
  1119. }
  1120. });
  1121. let text = tools.getText(map, "name");
  1122. this.$confirm(
  1123. // "您确定批量创建业务空间:" +
  1124. // tools.cutString(text, 10, "等业务空间") +
  1125. // ", 是否继续?",
  1126. "<p>确定根据未关联业务空间的元空间批量创建业务空间</p>" +
  1127. "<p>涉及的元空间:</p>" +
  1128. "<p style='line-height:20px;max-height:60px;overflow-y:auto;'>" +
  1129. text +
  1130. "</p>",
  1131. // tools.cutString(text, 60, "等业务空间")
  1132. "提示", {
  1133. dangerouslyUseHTMLString: true,
  1134. confirmButtonText: "确定",
  1135. cancelButtonText: "取消",
  1136. type: "warning"
  1137. }
  1138. )
  1139. .then(() => {
  1140. this.loading.show = true;
  1141. this.loading.num = 0;
  1142. this.loading.total = map.length * 2;
  1143. this.myDialogVisible = false;
  1144. map.map(item => {
  1145. this.createSpace({
  1146. building_id: this.buildMess.buildCode,
  1147. floor_id: this.buildMess.code,
  1148. business_type: this.spaceType.code,
  1149. infos: {
  1150. RoomLocalName: [{
  1151. value: item.name
  1152. }]
  1153. }
  1154. },
  1155. item.id,
  1156. true
  1157. );
  1158. });
  1159. })
  1160. .catch(() => {
  1161. this.$message({
  1162. type: "info",
  1163. message: "已取消批量创建"
  1164. });
  1165. });
  1166. },
  1167. //创建空间
  1168. createSpace(data, id, falg) {
  1169. let param = {
  1170. ProjId: this.projectId,
  1171. secret: this.secret,
  1172. data: data
  1173. };
  1174. createBusiness(param).then(res => {
  1175. if (res.data.Result == "success") {
  1176. if (falg) {
  1177. this.loading.num++;
  1178. this.addRelation(res.data.id, id);
  1179. } else {}
  1180. } else {
  1181. this.loading.num++;
  1182. this.$message.error("修改发生错误:" + res.data.ResultMsg);
  1183. }
  1184. });
  1185. },
  1186. //添加关系
  1187. addRelation(SpId, SiId) {
  1188. let data = {};
  1189. if (SiId instanceof Array) {
  1190. data.criterias = [];
  1191. SiId.map(item => {
  1192. data.criterias.push({
  1193. from_id: item.id,
  1194. to_id: SpId,
  1195. graph_id: this.graphyId,
  1196. rel_type: this.spaceType.rel_type
  1197. });
  1198. });
  1199. } else {
  1200. data = {
  1201. from_id: SiId,
  1202. to_id: SpId,
  1203. graph_id: this.graphyId,
  1204. rel_type: this.spaceType.rel_type
  1205. };
  1206. }
  1207. createRelation({
  1208. data: data,
  1209. ProjId: this.projectId,
  1210. secret: this.secret
  1211. })
  1212. .then(res => {
  1213. if (res.data.Result == "success") {
  1214. this.loading.num++;
  1215. if (this.loading.num == this.loading.total) {
  1216. this.loading.show = false;
  1217. this.getHasSpace();
  1218. this.idList = [];
  1219. this.$message.success("添加成功");
  1220. this.type = 1;
  1221. }
  1222. } else {
  1223. this.$message.error(res.data.ResultMsg);
  1224. this.loading.errorNum++;
  1225. }
  1226. })
  1227. .catch(() => {
  1228. this.$message.error("请求出错");
  1229. this.loading.errorNum++;
  1230. });
  1231. }
  1232. },
  1233. filters: {
  1234. cutString: function(str, len) {
  1235. //length属性读出来的汉字长度为1
  1236. if (!!str && typeof str == "string" && str.length > len) {
  1237. return str.substring(0, len) + "...";
  1238. } else {
  1239. return str || "--";
  1240. }
  1241. }
  1242. },
  1243. watch: {
  1244. projectId(){
  1245. this.buildMess = null
  1246. this.param.ProjId = this.projectId
  1247. this.param.secret = this.secret
  1248. this.param.UserId = this.userId
  1249. this.hasMap = false
  1250. }
  1251. }
  1252. };
  1253. </script>
  1254. <!-- Add "scoped" attribute to limit CSS to this component only -->
  1255. <style lang="less">
  1256. .canvasGraphy {
  1257. position: relative;
  1258. canvas {
  1259. border: 1px solid #ccc;
  1260. }
  1261. .header-search {
  1262. position: absolute;
  1263. top: 0;
  1264. height: 50px;
  1265. line-height: 50px;
  1266. padding-left: 20px;
  1267. background-color: rgba(205, 197, 191, 0.4);
  1268. left: 0;
  1269. right: 0;
  1270. top: 0;
  1271. z-index: 99;
  1272. >div {
  1273. height: 50px;
  1274. }
  1275. .div50 {
  1276. float: left;
  1277. width: 50%;
  1278. height: 100%;
  1279. .float-right {
  1280. float: right;
  1281. margin-top: 11px;
  1282. margin-right: 10%;
  1283. }
  1284. }
  1285. }
  1286. .el-autocomplete {
  1287. width: 320px;
  1288. }
  1289. .my-autocomplete {
  1290. li {
  1291. line-height: normal;
  1292. padding: 7px;
  1293. .name {
  1294. text-overflow: ellipsis;
  1295. overflow: hidden;
  1296. }
  1297. .addr {
  1298. font-size: 12px;
  1299. color: #b4b4b4;
  1300. }
  1301. .highlighted .addr {
  1302. color: #ddd;
  1303. }
  1304. }
  1305. }
  1306. }
  1307. </style>