本文適合對vue,arcgis4.x,threejs,ES6較熟悉的人群食用。
(資料圖片)
效果圖:
素材:
主要思路:
先用arcgisexternalRenderers封裝了一個ExternalRendererLayer,在里面把arcgis和threejs的context關聯,然后再寫個子類繼承它,這部分類容在上一個帖子里面有講過。
子類AreaLayer繼承它,并在里面實現繪制流光邊界線的方法,我這里其實就是繪制城市區域的邊界線。嘗試過直線LineCurve3,三維二次貝塞爾曲線QuadraticBezierCurve3,三維三次貝塞爾曲線CubicBezierCurve3,結果感覺差不多=_=,所以最后還是用CatmullRomCurve3這個來構建管道,這個類使用也比其他的方便。
1:創建一個基于圖片的材質
1 const lineImg = require("../../../../public/static/img/line.png") 2 let lineTexture = new THREE.TextureLoader().load(lineImg) 3 lineTexture.wrapS = lineTexture.wrapT = THREE.RepeatWrapping; //每個都重復 4 lineTexture.repeat.set(1, 1) 5 lineTexture.needsUpdate = true 6 7 let lineMaterial = new THREE.MeshBasicMaterial({ 8 map: lineTexture, 9 side: THREE.DoubleSide,10 transparent: true11 })
2:處理坐標轉換數據
1 let linePoints = []2 for(let i = 0; i < pointList.length; i++) {3 var item = pointList[i];4 var renderLinePoints = this.lngLatToXY(this.view, [item[0], item[1], 10]);5 var vector3List = renderLinePoints.vector3List;6 7 linePoints.push(new THREE.Vector3(vector3List.x, vector3List.y, vector3List.z));8 }
3:構建TubeGeometry,創建Mesh
1 const curvePath = new THREE.CatmullRomCurve3(linePoints) // 曲線路徑2 3 let geometry = new THREE.TubeGeometry(curvePath, 64, 30, 8, true )4 let lineMesh = new THREE.Mesh(geometry, lineMaterial);
4:最后再updateModels里面更新貼圖的位置(其實就是render事件)。
1 updateModels(context) {2 super.updateModels(context);3 4 if (this.textures.length > 0) {5 this.textures.forEach(texture => {6 if (texture) texture.offset.x -= 0.01;7 })8 }9 }
ExternalRendererLayer:
1 import * as THREE from "three" 2 import Stats from "three/examples/jsm/libs/stats.module.js" 3 import * as webMercatorUtils from "@arcgis/core/geometry/support/webMercatorUtils" 4 import * as externalRenderers from "@arcgis/core/views/3d/externalRenderers" 5 6 export default class ExternalRendererLayer { 7 constructor({ 8 view, 9 options 10 }) { 11 this.view = view 12 this.options = options 13 14 this.objects = [] 15 this.scene = null 16 this.camera = null 17 this.renderer = null 18 19 this.setup(); 20 } 21 22 setup() { 23 if (process.env.NODE_ENV !== "production") { 24 const sid = setTimeout(() => { 25 clearTimeout(sid) 26 //構建幀率查看器 27 let stats = new Stats() 28 stats.setMode(0) 29 stats.domElement.style.position = "absolute" 30 stats.domElement.style.left = "0px" 31 stats.domElement.style.top = "0px" 32 document.body.appendChild(stats.domElement) 33 function render() { 34 stats.update() 35 requestAnimationFrame(render) 36 } 37 render() 38 }, 5000) 39 } 40 } 41 42 apply() { 43 let myExternalRenderer = { 44 setup: context => { 45 this.createSetup(context) 46 }, 47 render: context => { 48 this.createRender(context) 49 } 50 } 51 52 externalRenderers.add(this.view, myExternalRenderer); 53 } 54 55 createSetup(context) { 56 this.scene = new THREE.Scene(); // 場景 57 this.camera = new THREE.PerspectiveCamera(); // 相機 58 59 this.setLight(); 60 61 // 添加坐標軸輔助工具 62 const axesHelper = new THREE.AxesHelper(10000000); 63 this.scene.Helpers = axesHelper; 64 this.scene.add(axesHelper); 65 66 this.renderer = new THREE.WebGLRenderer({ 67 context: context.gl, // 可用于將渲染器附加到已有的渲染環境(RenderingContext)中 68 premultipliedAlpha: false, // renderer是否假設顏色有 premultiplied alpha. 默認為true 69 // antialias: true 70 // logarithmicDepthBuffer: false 71 // logarithmicDepthBuffer: true 72 }); 73 this.renderer.setPixelRatio(window.devicePixelRatio); // 設置設備像素比。通常用于避免HiDPI設備上繪圖模糊 74 this.renderer.setViewport(0, 0, this.view.width, this.view.height); // 視口大小設置 75 76 // 防止Three.js清除ArcGIS JS API提供的緩沖區。 77 this.renderer.autoClearDepth = false; // 定義renderer是否清除深度緩存 78 this.renderer.autoClearStencil = false; // 定義renderer是否清除模板緩存 79 this.renderer.autoClearColor = false; // 定義renderer是否清除顏色緩存 80 // this.renderer.autoClear = false; 81 82 // ArcGIS JS API渲染自定義離屏緩沖區,而不是默認的幀緩沖區。 83 // 我們必須將這段代碼注入到three.js運行時中,以便綁定這些緩沖區而不是默認的緩沖區。 84 const originalSetRenderTarget = this.renderer.setRenderTarget.bind( 85 this.renderer 86 ); 87 this.renderer.setRenderTarget = target => { 88 originalSetRenderTarget(target); 89 if (target == null) { 90 // 綁定外部渲染器應該渲染到的顏色和深度緩沖區 91 context.bindRenderTarget(); 92 } 93 }; 94 95 this.addModels(context); 96 97 context.resetWebGLState(); 98 } 99 100 createRender(context) {101 const cam = context.camera;102 this.camera.position.set(cam.eye[0], cam.eye[1], cam.eye[2]);103 this.camera.up.set(cam.up[0], cam.up[1], cam.up[2]);104 this.camera.lookAt(105 new THREE.Vector3(cam.center[0], cam.center[1], cam.center[2])106 );107 // this.camera.near = 1;108 // this.camera.far = 100;109 110 // 投影矩陣可以直接復制111 this.camera.projectionMatrix.fromArray(cam.projectionMatrix);112 113 this.updateModels(context);114 115 this.renderer.state.reset();116 117 context.bindRenderTarget();118 119 this.renderer.render(this.scene, this.camera);120 121 // 請求重繪視圖。122 externalRenderers.requestRender(this.view);123 124 // cleanup125 context.resetWebGLState();126 }127 128 //經緯度坐標轉成三維空間坐標129 lngLatToXY(view, points) {130 131 let vector3List; // 頂點數組132 133 let pointXYs;134 135 136 // 計算頂點137 let transform = new THREE.Matrix4(); // 變換矩陣138 let transformation = new Array(16);139 140 // 將經緯度坐標轉換為xy值\141 let pointXY = webMercatorUtils.lngLatToXY(points[0], points[1]);142 143 // 先轉換高度為0的點144 transform.fromArray(145 externalRenderers.renderCoordinateTransformAt(146 view,147 [pointXY[0], pointXY[1], points[148 2]], // 坐標在地面上的點[x值, y值, 高度值]149 view.spatialReference,150 transformation151 )152 );153 154 pointXYs = pointXY;155 156 vector3List =157 new THREE.Vector3(158 transform.elements[12],159 transform.elements[13],160 transform.elements[14]161 )162 163 return {164 vector3List: vector3List,165 pointXYs: pointXYs166 };167 }168 169 setLight() {170 console.log("setLight")171 let ambient = new THREE.AmbientLight(0xffffff, 0.7);172 this.scene.add(ambient);173 let directionalLight = new THREE.DirectionalLight(0xffffff, 0.7);174 directionalLight.position.set(100, 300, 200);175 this.scene.add(directionalLight);176 }177 178 addModels(context) {179 console.log("addModels")180 }181 182 updateModels(context) {183 // console.log("updateModels")184 }185 186 }View Code
AreaLayer:源碼中mapx.queryTask是封裝了arcgis的query查詢,這個可以替換掉,我只是要接收返回的rings數組,自行構建靜態數據也行
1 import * as THREE from "three" 2 import ExternalRendererLayer from "./ExternalRendererLayer.js" 3 import Graphic from "@arcgis/core/Graphic"; 4 import SpatialReference from "@arcgis/core/geometry/SpatialReference" 5 import * as externalRenderers from "@arcgis/core/views/3d/externalRenderers" 6 7 import mapx from "@/utils/mapUtils.js"; 8 9 export default class AreaLayer extends ExternalRendererLayer { 10 constructor({ 11 view, 12 options 13 }) { 14 super({ 15 view, 16 options 17 }) 18 } 19 20 setup() { 21 super.setup() 22 23 this.textures = [] 24 } 25 26 addModels(context) { 27 // super.addModels(context) 28 // =====================mesh加載=================================// 29 const url = config.mapservice[1].base_url + config.mapservice[1].jd_url; 30 // const url = "http://10.100.0.132:6080/arcgis/rest/services/wuchang_gim/gim_region/MapServer/2"; 31 mapx.queryTask(url, { 32 where: "1=1", 33 returnGeometry: true 34 }).then(featureSet => { 35 if (featureSet.length > 0) { 36 featureSet.forEach(feature => { 37 const polygon = feature.geometry; 38 const rings = polygon.rings; 39 rings.forEach(ring => { 40 this._addModel(ring); 41 }) 42 }) 43 } 44 }).catch(error => { 45 console.log(error) 46 }) 47 } 48 49 _addModel(pointList) { 50 const lineImg = require("../../../../public/static/img/line.png") 51 let lineTexture = new THREE.TextureLoader().load(lineImg) 52 lineTexture.wrapS = lineTexture.wrapT = THREE.RepeatWrapping; //每個都重復 53 lineTexture.repeat.set(1, 1) 54 lineTexture.needsUpdate = true 55 56 let lineMaterial = new THREE.MeshBasicMaterial({ 57 map: lineTexture, 58 side: THREE.DoubleSide, 59 transparent: true 60 }) 61 62 //確定幾何體位置 63 let linePoints = [] 64 // let curvePath = new THREE.CurvePath(); 65 for(let i = 0; i < pointList.length; i++) { 66 var item = pointList[i]; 67 var renderLinePoints = this.lngLatToXY(this.view, [item[0], item[1], 10]); 68 var vector3List = renderLinePoints.vector3List; 69 70 linePoints.push(new THREE.Vector3(vector3List.x, vector3List.y, vector3List.z)); 71 72 // if(i < pointList.length - 1) { 73 // var item1 = pointList[i + 1]; 74 // var renderLinePoints1 = this.lngLatToXY(this.view, [item1[0], item1[1], 10]); 75 // var vector3List1 = renderLinePoints1.vector3List; 76 77 // // var item2 = pointList[i + 1]; 78 // // var renderLinePoints2 = this.lngLatToXY(this.view, [item2[0], item2[1], 10]); 79 // // var vector3List2 = renderLinePoints2.vector3List; 80 81 // const line = new THREE.LineCurve3(vector3List, vector3List1); 82 // // const line = new THREE.QuadraticBezierCurve3(vector3List, vector3List1, vector3List2); 83 // curvePath.curves.push(line) 84 // } 85 } 86 87 // console.log(curvePath) 88 89 // CatmullRomCurve3創建一條平滑的三維樣條曲線 90 const curvePath = new THREE.CatmullRomCurve3(linePoints) // 曲線路徑 91 92 let geometry = new THREE.TubeGeometry(curvePath, 64, 30, 8, true ) 93 let lineMesh = new THREE.Mesh(geometry, lineMaterial); 94 95 this.scene.add(lineMesh); 96 97 this.textures.push(lineTexture); 98 this.objects.push(lineMesh); 99 }100 101 102 updateModels(context) {103 super.updateModels(context);104 105 if (this.textures.length > 0) {106 this.textures.forEach(texture => {107 if (texture) texture.offset.x -= 0.01;108 })109 }110 }111 112 }View Code
標簽:
成都車展|電動車大降價,某豪華品牌優惠30萬?
新車在線|近日亮相的三款自主新能源新車分享
線下體驗奔騰T90:上駝峰橋,過涉水路面,一腳油門輕松搞定
一波未平又來一波,豐田暫停日本工廠生產,日系車徹底“火了”?
本文適合對vue,arcgis4 x,threejs,ES6較熟悉的人群食用。效果圖:素
綻放綠色低碳魅力嵐圖夢想家助力2023綠色低碳高質量發展大會
踢球者:莫里巴被萊比錫從一線隊除名,巴薩未來難以獲得轉會分成,夏窗,
途銳評測由新車評網專業汽車評測團隊為您提供途銳試駕測評,包括途銳底
中國建筑主要從三個方面來做好應對風險的工作:一是源頭治理,預防為主
CB4-4-47、48兩宗地均位于西安浐灞生態區濕地文旅產業園版塊(行政轄區
不少房企似乎仍未找回節奏,而靈活調整銷售節奏的五礦卻實現了增長。
華遠地產上半年營收45 99億元,同比增長16 91%;歸屬于上市公司股東的
富瑞表示,將中國海外在2023年至24年盈利預測上調3%至5%,并將其目標價
BigC行政總裁AswinTechajareonvikul發表聲明指,管理層考慮到股東及其
8月29日,蔚來汽車發布了2023年第二季度財報。財報數據顯示,第二季度
據恒生滬深港通AH股溢價(HSAHP)指數顯示,AH股溢價于8月22日上升至近50
OvoloSouthside位于黃竹坑道64號,樓高24層,設有162間客房,于2014年
每經AI快訊,有投資者在投資者互動平臺提問:請問一下貴公司具有中低放
中國人民銀行金融市場司副司長馬賤陽介紹稱,金融支持民營企業發展有關
中信銀行福州分行通過阿里資產拍賣網發布“關于福建省福州市喜來登酒店
路特斯官方發布了首款純電高性能轎車的預告視頻,新車將于9月7日全球首
中國男籃背水一戰,姚明作出鐵血決定,陪喬帥周琦走完最后3條路,姚明,
“臺商臺青走晉來”晉臺農業合作交流會召開,主流媒體,山西門戶。山西新
作為汽車從業者,我們也會非常注意關注身邊朋友的選車動態,發現雖然比
8月29日,華勤技術西安研發中心舉行開園儀式,標志著絲路軟件城又一省
美的置業一年內到期有息負債為124億元,月均還債僅10 31億元,還債壓力
杭州玖航房地產開發有限公司擬在湘湖旅游度假區內,東至規劃金西路,南
央行上海總部通報上海市銀行跨境人民幣業務結算量情況:截至7月末,上
據悉,共有18個重點項目在會上簽約,總投資170億元,涉及汽車“新四化
本次集中開工的9個項目包括5個新能源大基地項目和4個文旅產業集群項目
8月29日,天津濱海新區發布9宗地塊掛牌公告,總出讓面積約43 70萬平方
“今年美的置業廣州佛山、長沙等地新拿地3個項目,三宗地塊增加權益貨
具體原因包括,1、因公司存續債務的問題,公司正積極與相關債權人溝通
報告期內,公司主營業務板塊實現營收7 41億元,毛利率25 4%。其中工程
中信證券研報指出,展望下半年,一方面安卓品牌逐步迎來秋季旗艦機型發
MSCI與谷歌云深化合作伙伴關系加速開發投資行業生成式人工智能解決方案
官張村,關于官張村介紹這個很多人還不知道,現在讓我們一起來看看吧!1
近期,在古裝劇市場上有一部非常吸引人的大劇,叫做《鵲刀門傳奇》。這
歐曼智藍底部換電重卡以技術進階直面續航、安全難題
晉力十足燃動未來JH6燃氣車新品在山西隆重上市
江蘇淮安市發布關于調整住房公積金有關政策的通知,提高多子女家庭住房
深圳市南山區寶能城花園(東區)四期工程1單元1301等260套公寓即將拍賣
8月30日,地產服務板塊午后回暖,特發服務漲超3%,新大正、我愛我家等
標的建筑面積73642 90平方米,含地下面積18575 97平方米,其中地下三層
報告期內,公司主營業務實現營收73 85億元,毛利率為18 27%。其中房地
該項目片策范圍共6 15公頃,位于百興路兩邊,東至大?工業街、西至擁軍
【環球網財經訊】8月29日晚間,湯姆貓(300459 SZ)發布2023年半年度報
2023年8月18日0:00前簽訂個人住房貸款合同的,按原政策執行。2023年8月
值得關注的是,張甦毅將成為費列羅集團任命進入中國市場以來的首位本土
新政策支持靈活就業人員“靈活存,靈活取”“多繳快貸”“長繳多貸”。
售28 28-41 98萬元,起亞EV6正式上市
理想汽車官方發文稱,為慶祝理想L系列交付一周年,累計交付突破25萬輛
最終,北京華融綜合投資有限公司及重慶市江北區國有資本投資運營管理集
傳祺又一銷冠:真7座全能MPV傳祺M6Pro!
特斯拉ModelY車身開裂被曝光!特斯拉:車沒問題!
“布局者”吉利:是否“輕舟已過萬重山”?
就在今日,家庭六座旗艦SUV——理想L9迎來交付一周年,并順利完成第十
日前,有媒體獲得了一張寶馬新世代概念車的預告圖。據悉,新車將在9月2
油耗低的才是王者皓瀚DH-i和宋ProDM-i怎么選?
當地時間8月29日,被稱為“越南特斯拉”的越南電動車生廠商VinFastAuto
日前,騰勢銷售事業部總經理趙長江透露,騰勢汽車將在3年內推出8車型。
?D?a?-μ??D?á′ó?áé??÷????????×÷?·?
法拉利488Pista,這是一輛令人矚目的超級跑車,以其驚人的性能和令人印
朝陽區八里莊街道八里莊西里1號樓、2號樓的污水管道因為老化等原因時
每經AI快訊,國金證券08月30日發布研報稱,給予中遠海控(601919 SH,
北京住總房地產開發有限責任公司會議決議批準子公司北京住總眾邦地產有
報告期內,該集團的營業額及毛利分別為人民幣200 02億元及人民幣20 07
仲量聯行香港研究部資深董事鐘楚如表示,上月整體市場租金按月下跌0 6%
支持公積金“又提又貸”。繳存職工家庭無住房公積金貸款記錄且商業性個
根據協議,瀘州老窖將借助螞蟻鏈的智能合約、跨鏈等技術,通過數字人民
本次擬出讓清單分別位于14個區域,包括南開區、河西區、河東區、和平區
隔夜HIBOR跌7點子至1 76869%。
地塊位于廣花公路以東、雅瑤路以北,是二類居住用地,占地面積43169 84
佳源服務預計借以審議及批準集團的2023年中期業績的董事會會議將延遲至
8月30日,中國建筑(SH601668,股價5 64元,市值2360億元)召開2023年
2022年10月27日,金周軌道獲取到金周路站TOD綜合開發項目用地,土地位
就在今日,比亞迪汽車官宣,比亞迪汽車App 小程序將于8月31日正式升級
如果想買一款沃爾沃中型車30萬左右車型,很多人糾結怎么選擇才不后悔,
在紅旗15萬左右車型中,有不少的車型賣點很足,有的省油、有的空間大、
1、只提供上門服務400-011-6181壁掛爐維修公司名稱:啄木鳥家庭維修通
此頁面是否是列表頁或首頁?未找到合適正文內容。
嬴徹卡車NOA(導航輔助駕駛)率先突破5000萬公里,并與申通快遞、中通
明雋提供76個單位,涵蓋開放式及1房單位,標準戶實用面積231至260方呎。
房地產經紀機構要合理降低住房買賣和租賃經紀服務費用。鼓勵按照成交價
報告期內,上海電影營業收入371,957,699 30元(上年同期223,443,369 73
李家超表示,歡迎中央公布《河套深港科技創新合作區深圳園區發展規劃》
海航集團財務有限公司應立即停止一切經營活動,將金融許可證繳回國家金
據中國汽車工業協會整理的海關總署數據顯示,2023年7月,汽車整車進口
其中,北京華融綜合投資有限公司拍得30 31%股權,重慶市江北區國有資本
報告期內,天恒置業錄得營業收入52 38億元,歸屬于母公司股東的凈利潤4
該公司上半年營業總收入9 0億元,同比增長約12 30%,其中,安置房銷售
發行人合并口徑有息債務方面,報告期初和報告期末,發行人合并報表范圍
截至2023年6月30日財務數據,標的企業營業收入87 77萬元,營業利潤8 14
一代人有一代人的“惡作劇之吻”,向往甜蜜愛情的當代年輕人,開始在短
美銀證券發表報告指,小米今年第二季實際經營利潤為40億元,按年增長19
想要買一輛稱心的車型,對大多數人來說,都需要花費不少時間和精力,如
手握13萬左右,想購置一款13萬左右福特5座SUV,市面上的車型那么多,到
我省征集醫藥領域商業賄賂問題線索,主流媒體,山西門戶。山西新聞網是經
內部非常棒!有一輛超豪華的“流行車”!有趣的是,所有這些東西在時尚
“免費送戲進景區”惠民演出壺關站活動落下帷幕,主流媒體,山西門戶。山
摘要:攜程美食林圍場美食定制榜單同步發布8月18日,首屆木蘭圍場御
8月11日-8月12日晚,以“讓音樂響徹云丘山”為主題的,云丘山音樂節
7月24日,我市第六屆運動會開幕式在鄉寧縣第一中學校體育場舉行。市
2023年7月25日,藍電汽車在雙福工廠正式向重慶市公安局沙坪壩公安分