index.js 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441
  1. import mitt from 'mitt'
  2. import axios from 'axios' //{ axios } from '@/api'
  3. export const enter = (dom) => {
  4. Potree.settings.isOfficial = true //标记为正式、非测试版本
  5. //Potree.fileServer = axios
  6. Potree.settings.libsUrl = '../lib/'
  7. let {THREE} = Potree.mergeEditStart(dom)
  8. let MergeEditor = viewer.modules.MergeEditor
  9. let sceneBus = mitt()
  10. viewer.addEventListener('camera_changed', e => {
  11. var camera = e.viewport.camera
  12. var pos = camera.position
  13. if (e.viewport.name == 'MainView') {
  14. sceneBus.emit('cameraChange', { x: pos.x, y: pos.y, z: pos.z, rotate: camera.rotation })
  15. }
  16. })
  17. let sdk = {
  18. sceneBus,
  19. getPositionByScreen(pos2d, mustModelId ){//通过屏幕坐标获取真实坐标 . mustModelId: 如果指定了模型,modelId必须为mustModelId才有效
  20. let worldPos, localPos, modelId, intersect
  21. let Handler = viewer.inputHandler
  22. let reGet = ()=>{//不使用当前鼠标所在位置的intersect,单独算
  23. pos2d.clientX = pos2d.x
  24. pos2d.clientY = pos2d.y
  25. pos2d.onlyGetIntersect = true
  26. pos2d.whichPointcloud = true
  27. if(mustModelId != void 0){//隐藏其他的模型
  28. let models = MergeEditor.getAllObjects()
  29. models.forEach(model=>{
  30. viewer.updateVisible(model, 'forPick', model.dataset_id == mustModelId)
  31. })
  32. }
  33. intersect = Handler.onMouseMove(pos2d)
  34. if(mustModelId != void 0){//恢复
  35. let models = MergeEditor.getAllObjects()
  36. models.forEach(model=>{
  37. viewer.updateVisible(model, 'forPick', true)
  38. })
  39. }
  40. }
  41. if (pos2d && pos2d.inDrag) {
  42. reGet()
  43. } else {
  44. intersect = Handler.intersect
  45. if(intersect){
  46. modelId = intersect.pointcloud ? intersect.pointcloud.dataset_id : intersect.object.dataset_id
  47. if(mustModelId != void 0 && modelId != mustModelId){
  48. reGet()
  49. }
  50. }
  51. }
  52. if (intersect && intersect.location) {
  53. modelId = intersect.pointcloud ? intersect.pointcloud.dataset_id : intersect.object.dataset_id
  54. if(mustModelId != void 0 && modelId != mustModelId){
  55. return null
  56. }
  57. worldPos = intersect.location.clone()
  58. localPos = Potree.Utils.datasetPosTransform({ toDataset: true, datasetId:modelId, position:worldPos })
  59. } else return null
  60. return { worldPos, modelId, localPos }
  61. },
  62. getScreenByPosition(pos3d, modelId){//通过模型局部坐标获取屏幕坐标
  63. let isLocal = modelId != void 0
  64. pos3d = new THREE.Vector3().copy(pos3d)
  65. let worldPos = isLocal ? Potree.Utils.datasetPosTransform({ fromDataset: true, datasetId: modelId, position:pos3d}) : pos3d
  66. if(!worldPos)return
  67. var viewport = viewer.mainViewport
  68. var camera = viewport.camera
  69. var dom = viewer.renderArea
  70. //console.log('getScreenByPoint ' + pos3d.toArray())
  71. return Potree.Utils.getPos2d(worldPos, camera, dom, viewport)
  72. },
  73. screenshot: (width, height) => {
  74. //截图
  75. var promise = viewer.startScreenshot({ type: 'default' }, width, height)
  76. promise.done(() => {
  77. })
  78. return promise
  79. },
  80. getPose() {//获取当前点位和朝向
  81. const camera = viewer.scene.getActiveCamera()
  82. const target = viewer.scene.view.getPivot()
  83. const position = viewer.scene.view.position
  84. console.log('getPose',position, target)
  85. return { position, target }
  86. },
  87. comeTo(o = {}) {
  88. console.log('comeTo',o.position, o.target)
  89. //飞到某个点
  90. if(o.modelId){
  91. ['position','target'].forEach(e=>{
  92. if(o[e]){
  93. o[e] = Potree.Utils.datasetPosTransform({ fromDataset: true, datasetId: o.modelId, position:o[e]})
  94. }
  95. })
  96. }
  97. if(o.distance){
  98. let position = o.target || o.position
  99. return viewer.focusOnObject({ position, distance:o.distance }, 'tag').promise
  100. }
  101. let deferred = $.Deferred()
  102. viewer.scene.view.setView($.extend({},o, {
  103. duration: o.dur,
  104. callback:()=>{
  105. o.callback && o.callback()
  106. deferred.resolve(true)
  107. }
  108. }))
  109. return deferred.promise()
  110. },
  111. /* getPose(o={}) {
  112. //获取相对于第一个数据集的初始画面。(当数据集校准后,如果初始画面设置在被修改的数据集上,且该数据集非初始数据集的话,还是会偏移的)
  113. var deferred = o.deferred || $.Deferred();
  114. console.log('getPose')
  115. if(viewer.mainViewport.view.isFlying()){
  116. let f = ()=>{
  117. this.getPose(o)
  118. viewer.mainViewport.view.removeEventListener('flyingDone', f)
  119. }
  120. viewer.mainViewport.view.addEventListener('flyingDone', f) //once
  121. o.deferred = deferred
  122. return deferred.promise()
  123. }
  124. var camera = viewer.scene.getActiveCamera()
  125. var rotation = camera.rotation
  126. var pos_In_dataset = Potree.Utils.datasetPosTransform({ toDataset: true, position: camera.position.clone(), datasetId: Potree.settings.originDatasetId })
  127. var rot_In_dataset = Potree.Utils.datasetRotTransform({ toDataset: true, rotation, getRotation: true, datasetId: Potree.settings.originDatasetId }) //拿第一个数据集
  128. var view = viewer.scene.view.clone()
  129. view.rotation = rot_In_dataset //获取yaw pitch
  130. var pose = {
  131. //displayMode: Potree.settings.displayMode,
  132. position: pos_In_dataset,
  133. yaw: view.yaw,
  134. pitch: view.pitch,
  135. displayMode : Potree.settings.displayMode,
  136. panoSid: viewer.images360.currentPano.sid
  137. }
  138. //return pose
  139. setTimeout(()=>{
  140. deferred.resolve(pose)
  141. console.log('getPose resolve',pose)
  142. },1)
  143. return deferred.promise()
  144. },
  145. setPose(o = {}, duration=0) {
  146. //设置相机位置和朝向
  147. var deferred = o.deferred || $.Deferred();
  148. console.warn('setPose 初始画面', o)
  149. var quaternion
  150. let view = viewer.scene.view.clone()
  151. if(viewer.mainViewport.view.isFlying()){
  152. let f = ()=>{
  153. this.setPose(o, duration)
  154. viewer.mainViewport.view.removeEventListener('flyingDone', f)
  155. }
  156. viewer.mainViewport.view.addEventListener('flyingDone', f) //once
  157. o.deferred = deferred
  158. return deferred.promise()
  159. }
  160. var getQuaternion = ()=>{
  161. view.pitch = o.pitch
  162. view.yaw = o.yaw
  163. quaternion = Potree.Utils.datasetRotTransform({ fromDataset: true, rotation: view.rotation, getQuaternion: true, datasetId: Potree.settings.originDatasetId }) //拿第一个数据集
  164. }
  165. viewer.images360.cancelFlyToPano()//防止旧的在之后继续执行
  166. let pano
  167. if(o.panoSid != void 0){//好像都不存这个
  168. pano = viewer.images360.panos.find(e=>e.sid == o.panoSid)
  169. if(pano == void 0)return deferred.reject('没有找到该panoSid').promise()
  170. getQuaternion()
  171. viewer.images360.flyToPano({pano, duration, quaternion},()=>{
  172. deferred.resolve()
  173. })
  174. }else{
  175. if(Potree.settings.displayMode == 'showPanos'){
  176. return deferred.reject('全景模式下不允许设置位置').promise()
  177. }
  178. let position = Potree.Utils.datasetPosTransform({ fromDataset: true, position: o.position, datasetId: Potree.settings.originDatasetId })
  179. //view.position.copy(position)
  180. getQuaternion()
  181. pano = viewer.images360.panos.find(e=>Potree.math.closeTo(e.position, position))
  182. if(pano){//如果原来在某pano上最好也使currentPano为此pano,否则isAtPano会返回false
  183. viewer.images360.flyToPano({pano, duration, quaternion},()=>{
  184. deferred.resolve()
  185. })
  186. }else{
  187. viewer.scene.view.setView({position,quaternion,duration, callback:()=>{
  188. //setTimeout(()=>{
  189. deferred.resolve()
  190. console.log('setPose resolve')
  191. //},1)
  192. } })
  193. viewer.mapViewer.moveTo(position, null, duration) //初始位置在地图居中
  194. }
  195. }
  196. return deferred.promise()
  197. },
  198. */
  199. enterSceneGuide(pathArr){//导览 (不需要修改参数)
  200. let editor = viewer.modules.CamAniEditor
  201. console.log('pathArr',pathArr)
  202. /* type SceneGuidec = {
  203. position: {x,y,z}
  204. target: {x,y,z}
  205. time: number
  206. speed: number
  207. }
  208. sceneGuide = enterSceneGuide(sceneGuidePaths)
  209. let posTran = function (position, target) {
  210. position = Potree.Utils.datasetPosTransform({ fromDataset: true, position: position, datasetId: Potree.settings.originDatasetId })
  211. target = Potree.Utils.datasetPosTransform({ fromDataset: true, position: target, datasetId: Potree.settings.originDatasetId })
  212. return { position, target }
  213. }
  214. if (data) {
  215. data.points.forEach(e => {
  216. //let { position, target } = posTran(e.position, e.target)
  217. e.position = position
  218. e.target = target
  219. })
  220. }*/
  221. let data = {
  222. duration: pathArr.reduce(function(total, currentValue ){return total+currentValue.time}, 0),
  223. points: pathArr
  224. }
  225. let animation = editor.createAnimation(data)
  226. //注:最多只存在一条导览
  227. animation.useDurSlice = true
  228. let bus = mitt()
  229. //播放完成
  230. animation.addEventListener('playDone', () => {
  231. bus.emit('playComplete')
  232. })
  233. //切换点
  234. animation.addEventListener('updateCurrentIndex', e => {
  235. bus.emit('changePoint', e.currentIndex + 1)
  236. })
  237. return {
  238. bus,
  239. /* addPoint(index, position_, target_) {
  240. let { position, target } = posTran(position_, target_)
  241. animation.createControlPoint(index, { position, target })
  242. animation.changeCallback()
  243. },
  244. deletePoint(index) {
  245. animation.removeControlPoint(index)
  246. animation.changeCallback()
  247. }, */
  248. play() {
  249. /* var modeOld = Potree.settings.displayMode;
  250. Potree.settings.displayMode = 'showPointCloud' */
  251. animation.play()
  252. },
  253. pause() {
  254. animation.pause()
  255. },
  256. /*setDuration(dur) {
  257. animation.setDuration(dur)
  258. }, */
  259. clear() {
  260. //删除
  261. editor.removeAnimation(animation)
  262. },
  263. }
  264. },
  265. addModel(props){
  266. let bus = mitt()
  267. console.log('addModel',props)
  268. let model
  269. let done = (model_)=>{
  270. model = model_
  271. props.opacity != void 0 && result.changeOpacity(props.opacity)
  272. model.addEventListener('changeSelect',(e)=>{
  273. bus.emit('changeSelect',e.selected)
  274. })
  275. model.addEventListener('transformChanged',(e)=>{
  276. bus.emit('transformChanged', {
  277. position : model.position.clone(),
  278. scale: model.scale.x,
  279. rotation: model.rotation.clone(),
  280. bottom: model.btmHeight
  281. })
  282. })
  283. bus.emit('loadDone')
  284. console.log('loadDone' )
  285. }
  286. let progressFun = (progress)=>{
  287. bus.emit('loadProgress',progress)
  288. }
  289. if(props.type == "glb"){////////////////////////////test
  290. props.url = '/lib/potree/resources/models/glb/coffeemat.glb'
  291. }
  292. Potree.addModel(props, done , progressFun)
  293. let result = {
  294. bus,
  295. changeShow(show){
  296. if(model){
  297. viewer.updateVisible(model, 'changeShow', show)
  298. }
  299. },
  300. changeSelect(state){
  301. if(model){
  302. MergeEditor.selectModel(model, state, true, true)
  303. if(state && viewer.inputHandler.selection[0]){
  304. viewer.transformObject(model); //交换
  305. }
  306. }
  307. },
  308. changeScale(s){
  309. if(model){
  310. model.scale.set(s,s,s)
  311. model.dispatchEvent("scale_changed")
  312. }
  313. },
  314. changeOpacity(opacity){
  315. if(model){
  316. if(model.isPointcloud){
  317. model.material.opacity = opacity
  318. }else{
  319. model.traverse(e=>e.material && (e.material.opacity = opacity))
  320. }
  321. }
  322. },
  323. changeBottom(z){
  324. model && MergeEditor.setModelBtmHeight(model,z)
  325. },
  326. enterRotateMode(){
  327. if(model){
  328. viewer.transformObject(model);
  329. viewer.transformationTool.setModeEnable('rotation',true)
  330. viewer.transformationTool.setModeEnable('translation',false)
  331. }
  332. },
  333. enterMoveMode(){
  334. if(model){
  335. viewer.transformObject(model);
  336. viewer.transformationTool.setModeEnable('rotation',false)
  337. viewer.transformationTool.setModeEnable('translation',true)
  338. }
  339. },
  340. leaveTransform(){
  341. viewer.transformObject(null);
  342. },
  343. destroy(){
  344. MergeEditor.removeModel(model)
  345. }
  346. }
  347. return result
  348. }
  349. }
  350. return sdk
  351. }
  352. export default enter