ctrlPolygon.js 29 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774
  1. import * as THREE from "../../../../libs/three.js/build/three.module.js";
  2. import {LineDraw, MeshDraw} from "../../utils/DrawUtil.js";
  3. import math from "../../utils/math.js";
  4. import browser from "../../utils/browser.js";
  5. const verticalLine = new THREE.Line3()
  6. //控制点和边的合集。具有可以拖拽修改的功能,拖拽时能防止线相交。
  7. export class ctrlPolygon extends THREE.Object3D {
  8. constructor (type, prop) {
  9. super()
  10. this.type = type
  11. this.maxMarkers = Number.MAX_SAFE_INTEGER;
  12. this.transformData(prop);
  13. for(let i in prop){
  14. this[i] = prop[i]
  15. }
  16. if(this.atPlane && this.closed && this.dimension == '2d'){
  17. this.areaPlane = this.createAreaPlane();
  18. this.add(this.areaPlane)
  19. }
  20. //数据--刚开始一定是空的
  21. this.points = [];
  22. //mesh 不一定有
  23. this.markers = [];
  24. this.edges = [];
  25. this.center
  26. }
  27. initData(prop){
  28. //开始加数据
  29. if(Potree.settings.editType == 'merge'){ //融合页面没有地图,measure的不需要指定datasetId,每个点都有各自的datasetId,跟着各自的模型走
  30. if(this.dataset_points){
  31. this.dataset_points = this.dataset_points.map(e=>{
  32. return e && new THREE.Vector3().copy(e)
  33. })
  34. prop.points = this.dataset_points.map((p,i)=>{
  35. return Potree.Utils.datasetPosTransform({fromDataset:true, datasetId:this.points_datasets[i], position: p})
  36. })
  37. if(prop.points.some(e=>e == void 0)){
  38. return false
  39. }
  40. }else{
  41. this.dataset_points = []
  42. }
  43. }
  44. if(prop.points){
  45. for(const p of prop.points){
  46. const pos = new THREE.Vector3().copy(p)
  47. this.addMarker({point:pos});
  48. }
  49. /* if(Potree.settings.editType != 'merge'){
  50. if(this.datasetId != void 0){//初始化位置
  51. if(this.dataset_points){
  52. this.dataset_points = this.dataset_points.map(e=>{
  53. return e && new THREE.Vector3().copy(e)
  54. })
  55. this.transformByPointcloud() //根据dataset_points生成points
  56. }
  57. }else{
  58. if(prop.dataset_points && prop.dataset_points.some(e=>e != void 0)){
  59. console.error('存在测量线的datasetId为空而dataset_points有值,请检查并删除:'+this.sid)//存在过的bug,原因未知,可能是后台处理dataset时替换的错误:http://192.168.0.21/index.php?m=bug&f=view&bugID=23601
  60. console.log(this)
  61. }
  62. }
  63. } */
  64. this.getFacePlane()
  65. this.getPoint2dInfo(this.points)
  66. this.update({ifUpdateMarkers:true})
  67. //this.dragChange(new THREE.Vector3().copy(prop.points[prop.points.length-1]), prop.points.length-1);
  68. this.setSelected(false )
  69. this.markers.forEach(marker=>{marker.dispatchEvent('addHoverEvent') })
  70. return true
  71. }
  72. }
  73. addMarker(o={}){
  74. var index = o.index == void 0 ? this.points.length : o.index //要当第几个
  75. this.points = [...this.points.slice(0,index), o.point, ...this.points.slice(index,this.points.length)]
  76. //this.points.push(o.point);
  77. if(o.marker){
  78. this.add(o.marker)
  79. this.markers = [...this.markers.slice(0,index), o.marker, ...this.markers.slice(index,this.markers.length)]
  80. this.updateMarker(o.marker, o.point)
  81. if(!this.unableDrag){
  82. o.marker.addEventListener('drag', this.dragMarker.bind(this));
  83. o.marker.addEventListener('drop', this.dropMarker.bind(this));
  84. }
  85. let addHoverEvent = (e)=>{
  86. o.marker.removeEventListener('addHoverEvent',addHoverEvent)
  87. if(this.unableDrag)return
  88. let mouseover = (e) => {
  89. this.setMarkerSelected(e.object, 'hover', 'single');
  90. viewer.dispatchEvent({
  91. type : "CursorChange", action : "add", name:"markerMove"
  92. })
  93. };
  94. let mouseleave = (e) => {
  95. this.setMarkerSelected(e.object, 'unhover', 'single');
  96. viewer.dispatchEvent({
  97. type : "CursorChange", action : "remove", name:"markerMove"
  98. })
  99. }
  100. o.marker.addEventListener('mouseover', mouseover);
  101. o.marker.addEventListener('mouseleave', mouseleave);
  102. o.marker.addEventListener('startDragging', (e)=>{//for mobile
  103. this.setMarkerSelected(o.marker, 'hover', 'single');
  104. });
  105. o.marker.addEventListener('drop', (e)=>{//for mobile
  106. this.setMarkerSelected(o.marker, 'unhover', 'single');
  107. });
  108. }
  109. o.marker.addEventListener('addHoverEvent',addHoverEvent)//当非isNew时才添加事件
  110. if(!this.isNew){
  111. o.marker.dispatchEvent('addHoverEvent')
  112. }
  113. }
  114. if(o.edge){
  115. this.add(o.edge)
  116. this.edges = [...this.edges.slice(0,index), o.edge, ...this.edges.slice(index,this.edges.length)]
  117. }
  118. }
  119. dragMarker(e){
  120. var I, atMap
  121. if(e.hoverViewport != e.drag.dragViewport){//不能使用e.dragViewport,要使用drag中的,因为drag中存储的要一直继承下来,不因mouseup了而改变。
  122. viewer.dispatchEvent({
  123. type : "CursorChange", action : "add", name:"polygon_AtWrongPlace"
  124. })
  125. return
  126. }
  127. if(e.drag.pointerDelta.length() == 0 && !this.isNew){ //部分设备(华为matePad11)在touchstart后立即执行了touchmove,导致marker立即移动,需要屏蔽
  128. //console.error('e.drag.pointerDelta.length() == 0')
  129. return
  130. }
  131. viewer.dispatchEvent({
  132. type : "CursorChange", action : "remove", name:"polygon_AtWrongPlace"
  133. })
  134. atMap = e.drag.dragViewport.name == 'mapViewport'
  135. if(atMap && this.unableDragAtMap){
  136. e.drag.object = null //取消拖拽
  137. return
  138. }
  139. e.drag.object.isDragging = true
  140. I = e.intersect && (/* e.intersect.orthoIntersect || */ e.intersect.location)
  141. //记录数据集
  142. //在三维中脱离点云(在map中拉到周围都没有点云的地方)的顶点,无法拖拽怎么办
  143. if (I) {
  144. let i = this.markers.indexOf(e.drag.object);
  145. if (i !== -1) {
  146. this.dragChange(I.clone(), i, atMap)
  147. if(this.points_datasets){
  148. if(e.intersect.pointcloud) this.points_datasets[i] = e.intersect.pointcloud.dataset_id
  149. else if(e.intersect.object) this.points_datasets[i] = e.intersect.object.dataset_id
  150. else this.points_datasets[i] = null
  151. }
  152. }
  153. this.editStateChange(true)
  154. //console.log('pointerDelta',e.drag.pointerDelta)
  155. viewer.dispatchEvent({type:'dragMarker', object:this})
  156. return true
  157. }
  158. };
  159. dragChange(intersectPos, i, atMap){
  160. let len = this.markers.length
  161. let oldPoint = this.points[i];
  162. if(atMap){
  163. intersectPos.setZ(oldPoint.z) //在地图上拖拽,不改变其高度。
  164. }
  165. let location = intersectPos.clone()
  166. //console.log('dragChange', oldPoint, intersectPos)
  167. if(this.faceDirection && this.maxMarkers == 2 && len == 2){//add 固定方向的点不直接拖拽
  168. var p1 = this.markers[0].position
  169. if(this.faceDirection == 'horizontal'){
  170. var projectPos = location.clone().setZ(p1.z)
  171. }else{
  172. var projectPos = p1.clone().setZ(location.z)
  173. }
  174. //var p2 = p1.clone().add(this.direction)
  175. //var projectPos = math.getFootPoint(location, p1, p2)
  176. LineDraw.updateLine(this.guideLine, [location, projectPos])
  177. location = projectPos
  178. this.guideLine.visible = true
  179. }else if( len > 1 ){
  180. var points = this.points.map(e=>e.clone())
  181. points[i].copy(location) //算normal需要提前确认point
  182. //若为定义了面朝向的矩形
  183. if(this.faceDirection == 'horizontal'){
  184. if(len == 2){
  185. location.setZ(points[0].z)
  186. }
  187. if(!this.facePlane){//一个点就能确定面
  188. this.facePlane = new THREE.Plane().setFromNormalAndCoplanarPoint( new THREE.Vector3(0,0,1), this.points[0] )
  189. }
  190. }else if(this.faceDirection == 'vertical'){//当有两个点时, 有两个方向的可能
  191. if(len == 2){
  192. if(this.isRect){
  193. let vec = points[0].clone().sub(location)
  194. if(Math.sqrt(vec.x*vec.x+vec.y*vec.y) > Math.abs(vec.z) ){//水平(高度差小于水平距离时)
  195. location.setZ(points[0].z)
  196. //this.cannotConfirmNormal = false;//能确定面为水平方向
  197. }else{//垂直 (当两点一样时也属于这种)
  198. location.setX(points[0].x);
  199. location.setY(points[0].y);
  200. //this.cannotConfirmNormal = true; //不能确定面,因第三点可绕着纵轴线自由移动
  201. }
  202. }
  203. }else{
  204. {//判断cannotConfirmNormal. 如果前几段都在竖直线上,就不能固定出面方向。
  205. this.cannotConfirmNormal = true
  206. let max = this.isRect ? 1 : len-2
  207. for(let i=0;i<max;i++){
  208. let p1 = points[i].clone()
  209. let p2 = points[i+1].clone()
  210. let vec = p1.sub(p2);
  211. if(vec.x != 0 || vec.y != 0){
  212. this.cannotConfirmNormal = false
  213. break;
  214. }
  215. }
  216. }
  217. if(!this.facePlane || this.cannotConfirmNormal){//三个点且为水平方向时,计算面
  218. var points_ = points.map(e=>new THREE.Vector2(e.x,e.y))
  219. var points2 = getDifferentPoint(points_, 2);
  220. if(points2){
  221. let normal = math.getNormal2d({p1:points2[0], p2:points2[1]})
  222. normal = new THREE.Vector3(normal.x, normal.y, 0)
  223. this.facePlane = new THREE.Plane().setFromNormalAndCoplanarPoint( normal, this.points[0] )
  224. }
  225. }
  226. }
  227. }
  228. if(len > 2){
  229. if(!this.faceDirection && this.showArea){
  230. if(len == 3 || this.isRect) this.cannotConfirmNormal = true //当第三个点固定后(有四个点时)才能固定面
  231. if(!this.facePlane || this.cannotConfirmNormal){
  232. var points3 = getDifferentPoint(points, 3);//只有找到三个不同的点算拥有面和area
  233. if(points3){
  234. this.facePlane = new THREE.Plane().setFromCoplanarPoints(...points3 )
  235. }
  236. }
  237. }
  238. if( this.facePlane && !this.cannotConfirmNormal ){//之后加的点一定要在面上
  239. if(atMap){
  240. //地图上用垂直线,得到和面的交点。
  241. verticalLine.set(location.clone().setZ(100000), location.clone().setZ(-100000))//确保长度范围覆盖所有测量面
  242. location = this.facePlane.intersectLine(verticalLine, new THREE.Vector3() )
  243. if(!location) return;
  244. }else{
  245. location = this.facePlane.projectPoint(intersectPos, new THREE.Vector3() )
  246. }
  247. }
  248. points[i].copy(location)//再copy确认一次
  249. if(this.isRect){ //是矩形 (即使没有faceDirection也能执行)
  250. //根据前两个点计算当前和下一个点
  251. var p1 = points[(i-2+len)%len]
  252. var p2 = points[(i-1+len)%len]
  253. if(p1.equals(p2)){//意外情况:重复点两次 ( bug点,改了好多遍)
  254. if(this.faceDirection == 'vertical'){
  255. p2.add(new THREE.Vector3(0,0,0.0001))
  256. }else{
  257. p2.add(new THREE.Vector3(0,0.0001,0))
  258. }
  259. }
  260. //p3 : location
  261. var foot = math.getFootPoint(location, p1, p2)//p2 修改p2到垂足的位置
  262. var vec = foot.clone().sub(location)
  263. var p4 = p1.clone().sub(vec)
  264. points[(i-1+len)%len].copy(foot)
  265. points[(i+1)%len].copy(p4)
  266. this.setPosition((i-1+len)%len, foot);//p2
  267. this.setPosition((i+1)%len, p4);
  268. }
  269. /* let points2d;
  270. if(this.facePlane){
  271. var originPoint0 = points[0].clone()
  272. var qua = math.getQuaBetween2Vector(this.facePlane.normal, new THREE.Vector3(0,0,1), new THREE.Vector3(0,0,1));
  273. points2d = points.map(e=>e.clone().applyQuaternion(qua))
  274. } */
  275. this.getPoint2dInfo(points)
  276. var isIntersectSelf = this.atPlane && this.closed && !this.isRect && this.point2dInfo && this.intersectSelf(this.point2dInfo.points2d)//检测相交
  277. this.isIntersectSelf = isIntersectSelf
  278. if(isIntersectSelf){//not-allowed
  279. if(!this.isNew && isIntersectSelf == 'lastLine') this.isIntersectSelf = 'all' //已经画好了就不用特别对待最后一条线
  280. if(this.isIntersectSelf == 'lastLine'){
  281. Potree.Utils.updateVisible(this.areaPlane, 'intersectLastLine', false)
  282. Potree.Utils.updateVisible(this.areaLabel, 'intersectLastLine', false)
  283. }else{
  284. viewer.dispatchEvent({
  285. type : "CursorChange", action : "add", name:"polygon_isIntersectSelf"
  286. })
  287. return
  288. }
  289. }
  290. if(!this.isIntersectSelf){
  291. this.areaPlane && Potree.Utils.updateVisible(this.areaPlane, 'intersectLastLine', true)
  292. this.areaLabel && Potree.Utils.updateVisible(this.areaLabel, 'intersectLastLine', true)
  293. }
  294. if(!this.isIntersectSelf || this.isIntersectSelf == 'lastLine' ){
  295. viewer.dispatchEvent({
  296. type : "CursorChange", action : "remove", name:"polygon_isIntersectSelf"
  297. })
  298. }
  299. }
  300. var showGuideLine = len>1 && (this.faceDirection || len > 3)
  301. if(showGuideLine && this.guideLine){
  302. LineDraw.updateLine(this.guideLine, [intersectPos, location])
  303. this.guideLine.visible = true
  304. }
  305. //console.log(this.points.map(e=>e.toArray()))
  306. }
  307. if(this.restrictArea){
  308. let holes = this.restrictArea.holes.concat(this.restrictArea.parentHoles)
  309. let holesPoints = holes.filter(e=>e!=this && e.points.length>2).map(e=>e.points)
  310. if(!math.isPointInArea(this.restrictArea.points, holesPoints, location)){
  311. viewer.dispatchEvent({
  312. type : "CursorChange", action : "add", name:"polygon_AtWrongPlace"
  313. })
  314. this.isAtWrongPlace = true
  315. return
  316. }
  317. //就不处理相交线了。 有个缺点:floor上的hole可以限制room,但hole不受room限制,会导致room的marker被框在hole里而动不了。只能去调整hole了
  318. }
  319. viewer.dispatchEvent({
  320. type : "CursorChange", action : "remove", name:"polygon_AtWrongPlace"
  321. })
  322. this.isAtWrongPlace = false
  323. this.setPosition(i, location);
  324. this.update()
  325. this.dispatchEvent({type:'dragChange', index:i})
  326. }
  327. dropMarker(e){
  328. if (this.isNew && !browser.isMobile() && e.pressDistance>Potree.config.clickMaxDragDis){//拖拽的话返回
  329. return this.continueDrag(null,e)
  330. }
  331. if(e.hoverViewport != e.drag.dragViewport){//copy from dragMarker, for sitemodel, only mapViewport can be dropped
  332. return this.continueDrag(null,e)
  333. }
  334. if(e.isTouch){
  335. if(e.hoverViewport != viewer.mainViewport && this.unableDragAtMap){
  336. viewer.dispatchEvent({type:'reticule_forbit', v:true})
  337. //console.log('reticule_forbit',true)
  338. return this.continueDrag(null,e)
  339. }else{
  340. viewer.dispatchEvent({type:'reticule_forbit', v:false})
  341. //console.log('reticule_forbit',false)
  342. }
  343. this.isNew && this.dragMarker(e) //isNew触屏点击时必须先更新下点,因为指尖不在屏幕上时没更新。但对已经创建的marker点击时不应该更新
  344. }
  345. viewer.dispatchEvent({type:'dropMarker', object:this})
  346. if (e.button != THREE.MOUSE.RIGHT && (//右键click的话继续执行,因为会停止
  347. this.isIntersectSelf == 'all' && this.isNew //有线相交了
  348. || this.isAtWrongPlace && this.isNew
  349. || !e.isAtDomElement && this.isNew//如果是刚添加时在其他dom点击, 不要响应
  350. || e.hoverViewport != viewer.mainViewport && this.unableDragAtMap //垂直的测量线不允许在地图上放点
  351. || this.isNew && !getDifferentPoint(this.points, this.points.length ) //不允许和之前的点相同, 但这句在点云稀疏时会导致难结束
  352. || this.isNew && (Date.now() - this.beginAddTime) < Potree.config.clickMaxPressTime/5 && e.pressDistance < Potree.config.clickMaxDragDis/* && e.pressTime<Potree.config.clickMaxPressTime */ //有的设备过于灵敏,点击一下就结束测量了,是因为滑动了被判断为拖拽。所以判断下如果滑动距离过近不时间过短就算单击
  353. )
  354. ){
  355. return this.continueDrag(null,e)
  356. }
  357. let i = this.markers.indexOf(e.drag.object);
  358. if (i !== -1) {
  359. this.dispatchEvent({
  360. 'type': 'marker_dropped',
  361. 'index': i
  362. });
  363. if(this.markers.length>2 && this.facePlane)this.cannotConfirmNormal = false
  364. this.guideLine &&(this.guideLine.visible = false)
  365. }
  366. this.setMarkerSelected(e.drag.object, 'unhover', 'single')
  367. this.editStateChange(false)
  368. e.drag.endDragFun && e.drag.endDragFun(e)// addmarker
  369. //if(this.changeCallBack)this.changeCallBack()
  370. return true
  371. };
  372. getFacePlane(){//最普通一种get方法,根据顶点。且假设所有点已经共面,且不重合
  373. if(!this.atPlane || this.points.length<3) return
  374. this.facePlane = new THREE.Plane().setFromCoplanarPoints(...this.points.slice(0,3) )
  375. }
  376. getPoint2dInfo(points){ //在更新areaplane之前必须更新过point2dInfo
  377. if(this.facePlane){
  378. var originPoint0 = points[0].clone()
  379. var qua = math.getQuaBetween2Vector(this.facePlane.normal, new THREE.Vector3(0,0,1), new THREE.Vector3(0,0,1));
  380. let points2d = points.map(e=>e.clone().applyQuaternion(qua))
  381. this.point2dInfo = {
  382. originPoint0 ,
  383. points2d,
  384. quaInverse : qua.clone().invert()
  385. }
  386. }
  387. }
  388. setPosition (index, position) {//拖拽后设置位置
  389. let point = this.points[index];
  390. point.copy(position);
  391. /* if(this.datasetId){
  392. this.dataset_points[index] = Potree.Utils.datasetPosTransform({toDataset:true, datasetId:this.datasetId, position:point.clone()})
  393. } */
  394. /* if(Potree.settings.editType == 'merge'){
  395. this.dataset_points[index] = Potree.Utils.datasetPosTransform({toDataset:true,this.points_datasets[i], position:point.clone()})
  396. } */
  397. let marker = this.markers[index];
  398. this.updateMarker(marker, point)
  399. }
  400. updateMarker(marker, pos){
  401. marker.position.copy(pos);
  402. marker.waitUpdate();
  403. }
  404. intersectSelf(points2d){//add
  405. var len = points2d.length
  406. for(var i=0;i<len;i++){
  407. for(var j=i+2;j<len;j++){
  408. if(Math.abs(j-len-i)<2)continue;//不和邻边比
  409. var p1 = points2d[i]
  410. var p2 = points2d[i+1]
  411. var p3 = points2d[j]
  412. var p4 = points2d[(j+1)%len]
  413. if(p1.equals(p2) || p3.equals(p4) || p1.equals(p3) || p2.equals(p3) || p1.equals(p4) || p2.equals(p4))continue
  414. var line1 = [p1,p2]
  415. var line2 = [p3,p4]
  416. var intersect = math.isLineIntersect(line1, line2, false, 0.001)
  417. if(intersect){
  418. if(i==len-1 || j==len-1){//最后一条线。如果还没绘制完,最后的线还没定下,可被允许继续绘制,但无法显示面积。
  419. return 'lastLine'
  420. }else{
  421. return 'all'
  422. }
  423. break
  424. }
  425. }
  426. }
  427. }
  428. removeMarker (index) {
  429. this.points.splice(index, 1);
  430. const marker = this.markers[index]
  431. //this.remove(marker);
  432. this.markers.splice(index, 1);
  433. marker.dispatchEvent({type:'dispose'})
  434. let edgeIndex = index //(index === 0) ? 0 : (index - 1);
  435. const edge = this.edges[edgeIndex]
  436. if(edge){
  437. this.remove(edge);
  438. this.edges.splice(edgeIndex, 1);
  439. edge.dispatchEvent({type:'dispose'})
  440. }
  441. this.point2dInfo && this.point2dInfo.points2d.splice(index, 1); //add
  442. this.dispatchEvent({type:'removeMarker',index,marker})
  443. }
  444. createAreaPlane(mat){
  445. var geometry = new THREE.Geometry();
  446. var mesh = new THREE.Mesh(geometry, mat)
  447. return mesh
  448. }
  449. updateAreaPlane(){
  450. if(!this.point2dInfo)return
  451. this.areaPlane.geometry.dispose()
  452. if(this.points.length>2){
  453. this.areaPlane.geometry = MeshDraw.getShapeGeo(this.point2dInfo.points2d)
  454. var center = math.getCenterOfGravityPoint(this.point2dInfo.points2d) //重心
  455. var firstPos = this.point2dInfo.points2d[0].clone()
  456. firstPos.z = 0 //因为shape只读取了xy,所以位移下, 再算出最终位置,得到差距
  457. firstPos.applyQuaternion(this.point2dInfo.quaInverse)
  458. var vec = this.point2dInfo.originPoint0.clone().sub(firstPos)
  459. center = new THREE.Vector3(center.x, center.y, 0)
  460. center.applyQuaternion(this.point2dInfo.quaInverse)
  461. this.areaPlane.quaternion.copy(this.point2dInfo.quaInverse)
  462. this.areaPlane.position.copy(vec)
  463. center.add(vec)
  464. this.center = center
  465. }else{
  466. this.areaPlane.geometry = new THREE.Geometry()
  467. }
  468. }
  469. update(options={}){
  470. if(this.points.length === 0){
  471. return;
  472. }
  473. let lastIndex = this.points.length - 1
  474. for (let index = 0; index <= lastIndex; index++) {
  475. let nextIndex = (index + 1 > lastIndex) ? 0 : index + 1;
  476. let previousIndex = (index === 0) ? lastIndex : index - 1;
  477. let point = this.points[index];
  478. let nextPoint = this.points[nextIndex];
  479. let previousPoint = this.points[previousIndex];
  480. if(options.ifUpdateMarkers){
  481. this.updateMarker(this.markers[index], point)
  482. }
  483. if(!this.closed && nextIndex == 0 )break; //add
  484. { // edges
  485. let edge = this.edges[index];
  486. if(edge){
  487. LineDraw.updateLine(edge, [point, nextPoint])
  488. //edge.visible = index < lastIndex || this.isRect || (this.closed && !this.isNew);
  489. }
  490. }
  491. }
  492. if(this.areaPlane){
  493. this.updateAreaPlane()
  494. }
  495. //this.dispatchEvent({type:'update'})
  496. viewer.mapViewer && viewer.mapViewer.dispatchEvent('content_changed') //暂时先这么都通知
  497. }
  498. dispose(){//add
  499. this.parent.remove(this)
  500. this.markers.concat(this.edges).forEach(e=>e.dispatchEvent({type:'dispose'}))
  501. }
  502. reDraw(restMarkerCount=0){//重新开始画
  503. let pointCount = this.points.length - restMarkerCount // restMarkerCount为需要留下的marker数量
  504. while(pointCount > 0){
  505. this.removeMarker(--pointCount)
  506. }
  507. this.point2dInfo = null
  508. this.facePlane = null
  509. }
  510. setMarkerSelected(){}
  511. editStateChange(state){
  512. if(!state){
  513. viewer.dispatchEvent({
  514. type : "CursorChange", action : "remove", name:"polygon_isIntersectSelf"
  515. })
  516. viewer.dispatchEvent({
  517. type : "CursorChange", action : "remove", name:"polygon_AtWrongPlace"
  518. })
  519. viewer.dispatchEvent({type:'reticule_forbit', v:false})
  520. this.markers.forEach(e=>e.isDragging = false )
  521. }
  522. }
  523. transformData(prop){
  524. const pick = (defaul, alternative) => {
  525. if(defaul != null){
  526. return defaul;
  527. }else{
  528. return alternative;
  529. }
  530. };
  531. prop.showDistances = (prop.showDistances === null) ? true : prop.showDistances;
  532. prop.showArea = pick(prop.showArea, false);
  533. prop.showAngles = pick(prop.showAngles, false);
  534. prop.showCoordinates = pick(prop.showCoordinates, false);
  535. prop.showHeight = pick(prop.showHeight, false);
  536. prop.showCircle = pick(prop.showCircle, false);
  537. prop.showAzimuth = pick(prop.showAzimuth, false);
  538. prop.showEdges = pick(prop.showEdges, true);
  539. prop.closed = pick(prop.closed, false);
  540. prop.maxMarkers = pick(prop.maxMarkers, Infinity);
  541. prop.direction = prop.direction//add
  542. prop.type = prop.type
  543. prop.showGuideLine = pick(prop.showGuideLine, false);
  544. prop.isRect = pick(prop.isRect, false);
  545. }
  546. setSelected(){}
  547. continueDrag(marker, e){
  548. let object = marker || e.drag.object
  549. object.isDragging = true
  550. this.editStateChange(true)
  551. var timer = setTimeout(()=>{//等 drag=null之后 //右键拖拽结束后需要重新得到drag
  552. if(this.parent && object.parent && object.isDragging){
  553. console.log('continueDrag', object.uuid)
  554. viewer.inputHandler.startDragging( object ,
  555. {endDragFun: e.drag.endDragFun, notPressMouse:e.drag.notPressMouse, dragViewport:e.drag.dragViewport}
  556. )
  557. }
  558. },1)
  559. return timer
  560. }
  561. }
  562. function getDifferentPoint(points, count){//for facePlane
  563. var result = [];
  564. for(let i=0;i<points.length;i++){
  565. var p = points[i];
  566. if(result.find(e=>e.equals(p)))continue;
  567. else result.push(p)
  568. if(result.length == count)break
  569. }
  570. if(result.length == count)return result
  571. }