代码迁移
This commit is contained in:
		
							
								
								
									
										253
									
								
								src/Global/Contour/index.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										253
									
								
								src/Global/Contour/index.js
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,253 @@ | ||||
| /** | ||||
|  * 等高线 | ||||
|  */ | ||||
| import Dialog from "../../Obj/Element/Dialog"; | ||||
| import Tools from "../../Tools"; | ||||
|  | ||||
| let _DialogObject = null; | ||||
| let material = null; | ||||
| let handler = null; | ||||
| let activeHeightElm = null; | ||||
| let tools | ||||
| activeHeightElm = document.createElement('div') | ||||
| activeHeightElm.className = 'YJ-customize-active-height-elm' | ||||
| activeHeightElm.style.position = 'absolute' | ||||
| activeHeightElm.style.left = '10px' | ||||
| activeHeightElm.style.top = '10px' | ||||
| activeHeightElm.style.width = '100px' | ||||
| // activeHeightElm.style.backgroundColor = 'rgba(0, 0, 0, 0.5)' | ||||
| activeHeightElm.style.textAlign = 'center' | ||||
| activeHeightElm.style.pointerEvents = 'none' | ||||
| activeHeightElm.style.color = '#ff0000' | ||||
| activeHeightElm.style.display = 'none' | ||||
| async function dialog(sdk) { | ||||
|   if (!sdk || _DialogObject) { | ||||
|     return | ||||
|   } | ||||
|   if (!material) { | ||||
|     createMaterial() | ||||
|   } | ||||
|   if (!tools) { | ||||
|     tools = new Tools() | ||||
|   } | ||||
|  | ||||
|   _DialogObject = await new Dialog(sdk, {}, { | ||||
|     title: "等高线", left: '180px', | ||||
|     top: '100px', | ||||
|     confirmCallBack: options => { }, | ||||
|     closeCallBack: () => { | ||||
|       _DialogObject = null | ||||
|     } | ||||
|   }); | ||||
|  | ||||
|   _DialogObject._element.body.className = | ||||
|     _DialogObject._element.body.className + ' contour' | ||||
|   let contentElm = document.createElement('div') | ||||
|   contentElm.innerHTML = ` | ||||
|   <span class="custom-divider"></span> | ||||
|   <div class="div-item"> | ||||
|       <div class="row"> | ||||
|           <div class="col input-select-unit-box"> | ||||
|               <span class="label">高差</span> | ||||
|               <div class="input-number input-number-unit-1"> | ||||
|                   <input class="input gap" type="number" title="" min="0" max="1000"> | ||||
|                   <span class="unit">m</span> | ||||
|                   <span class="arrow"></span> | ||||
|               </div> | ||||
|           </div> | ||||
|           <div class="col input-select-unit-box" style="flex: 0 0 120px;"> | ||||
|               <span class="label">主线颜色</span> | ||||
|               <div class="primary-lice-color"></div> | ||||
|           </div> | ||||
|       </div> | ||||
|       <div class="row"> | ||||
|           <div class="col input-select-unit-box"> | ||||
|               <span class="label">次线条数</span> | ||||
|               <div class="input-number input-number-unit-1"> | ||||
|                   <input class="input gap2" type="number" title="" min="0" max="10"> | ||||
|                   <span class="unit"></span> | ||||
|                   <span class="arrow"></span> | ||||
|               </div> | ||||
|           </div> | ||||
|           <div class="col input-select-unit-box" style="flex: 0 0 120px;"> | ||||
|               <span class="label">次线颜色</span> | ||||
|               <div class="secondary-lice-color"></div> | ||||
|           </div> | ||||
|       </div> | ||||
|       <div class="row" style="align-items: flex-start;"> | ||||
|           <div class="col"> | ||||
|           </div> | ||||
|           <div class="col" style="flex: 0 0 120px;"> | ||||
|               <span class="label">开关</span> | ||||
|               <input class="btn-switch" type="checkbox"> | ||||
|           </div> | ||||
|       </div> | ||||
|   </div> | ||||
|   <span class="custom-divider"></span> | ||||
|   ` | ||||
|   contentElm.innerHTML = ` | ||||
|   <span class="custom-divider"></span> | ||||
|   <div class="div-item"> | ||||
|       <div class="row" style="align-items: flex-start;"> | ||||
|           <div class="col" style="flex: 0 0 120px;"> | ||||
|               <span class="label">开关</span> | ||||
|               <input class="btn-switch" type="checkbox"> | ||||
|           </div> | ||||
|       </div> | ||||
|   </div> | ||||
|   ` | ||||
|   _DialogObject.contentAppChild(contentElm) | ||||
|  | ||||
|   contentElm.getElementsByClassName('btn-switch')[0].addEventListener('change', (e) => { | ||||
|     if (e.target.checked) { | ||||
|       if (handler) { | ||||
|         handler.destroy() | ||||
|       } | ||||
|       if (!sdk.viewer.container.getElementsByClassName('YJ-customize-active-height-elm')[0]) { | ||||
|         sdk.viewer.container.appendChild(activeHeightElm) | ||||
|       } | ||||
|  | ||||
|       handler = new Cesium.ScreenSpaceEventHandler( | ||||
|         sdk.viewer.canvas | ||||
|       ) | ||||
|       handler.setInputAction((movement) => { | ||||
|         let cartesian = sdk.viewer.scene.pickPosition(movement.endPosition) | ||||
|         if (cartesian) { | ||||
|           let top = 0 | ||||
|           let left = 0 | ||||
|           if (sdk.viewer && sdk.viewer._element) { | ||||
|             let element = sdk.viewer._element.getElementsByClassName('cesium-widget')[0].getElementsByTagName('canvas')[0] | ||||
|             top = element.getBoundingClientRect().top + window.scrollY | ||||
|             left = element.getBoundingClientRect().left + window.scrollX | ||||
|           } | ||||
|           activeHeightElm.style.left = movement.endPosition.x - 50 + left + 'px' | ||||
|           activeHeightElm.style.top = movement.endPosition.y - 40 + top + 'px' | ||||
|           activeHeightElm.style.display = 'block' | ||||
|           let pos84 = tools.cartesian3Towgs84(cartesian, sdk.viewer) | ||||
|           let mainContourHeight = Math.floor(pos84.alt / material.uniforms.spacing) * material.uniforms.spacing | ||||
|           let gap = pos84.alt - mainContourHeight | ||||
|           let gap2 = material.uniforms.spacing / (material.uniforms.secondaryLinesCount + 1) | ||||
|           let activeHeight = Math.floor(gap / gap2) * gap2 + mainContourHeight | ||||
|           if ((pos84.alt - activeHeight) > gap2 / 2) { | ||||
|             activeHeight = activeHeight + gap2 | ||||
|           } | ||||
|           material.uniforms.mouseHeight = pos84.alt | ||||
|           material.uniforms.mousePosition = cartesian | ||||
|           activeHeightElm.innerHTML = `${activeHeight.toFixed(0)}` | ||||
|         } | ||||
|         else { | ||||
|           activeHeightElm.style.display = 'none' | ||||
|         } | ||||
|       }, Cesium.ScreenSpaceEventType.MOUSE_MOVE) | ||||
|       sdk.viewer.scene.globe.material = material; | ||||
|     } else { | ||||
|       if (handler) { | ||||
|         handler.destroy() | ||||
|         handler = null | ||||
|       } | ||||
|       if (sdk.viewer.container.getElementsByClassName('YJ-customize-active-height-elm')[0]) { | ||||
|         activeHeightElm.style.display = 'none' | ||||
|         sdk.viewer.container.removeChild(activeHeightElm) | ||||
|       } | ||||
|       sdk.viewer.scene.globe.material = null; | ||||
|     } | ||||
|   }) | ||||
| } | ||||
|  | ||||
| function createMaterial() { | ||||
|   Cesium.Material._materialCache._materials.ElevationContour.fabric.source = ` | ||||
| uniform vec4 color; | ||||
| uniform vec4 secondaryLinesColor; | ||||
| uniform float spacing; | ||||
| uniform float width; | ||||
| uniform float secondaryLinesWidth; | ||||
| uniform float mouseHeight; | ||||
| uniform float secondaryLinesCount; // 0=无次线, 1=1条次线, 2=2条次线... | ||||
|  | ||||
| czm_material czm_getMaterial(czm_materialInput materialInput) | ||||
| { | ||||
|     czm_material material = czm_getDefaultMaterial(materialInput); | ||||
|  | ||||
|     // 主等高线计算 | ||||
|     float distanceToMainContour = mod(materialInput.height, spacing); | ||||
|      | ||||
|     // 抗锯齿计算 | ||||
| #if (__VERSION__ == 300 || defined(GL_OES_standard_derivatives)) | ||||
|     float dxc = abs(dFdx(materialInput.height)); | ||||
|     float dyc = abs(dFdy(materialInput.height)); | ||||
|     float dFMain = max(dxc, dyc) * czm_pixelRatio * width; | ||||
| #else | ||||
|     float dFMain = czm_pixelRatio * width; | ||||
| #endif | ||||
|  | ||||
|     bool isMainContour = distanceToMainContour < dFMain; | ||||
|     bool isSecondaryContour = false; | ||||
|     float dFSecondary = 0.0; | ||||
|     float secondarySpacing = 0.0; | ||||
|  | ||||
|     // 只有当存在次线时才计算次线 | ||||
|     if(secondaryLinesCount > 0.0) { | ||||
|         secondarySpacing = spacing / (secondaryLinesCount + 1.0); | ||||
|         float distanceToSecondaryContour = mod(materialInput.height, secondarySpacing); | ||||
|          | ||||
|         // 确保次线不会与主线重叠 | ||||
|         float minDistanceToMain = min(distanceToMainContour, spacing - distanceToMainContour); | ||||
|         bool notCloseToMain = minDistanceToMain > dFMain * 2.0; // 2倍线宽缓冲 | ||||
|          | ||||
| #if (__VERSION__ == 300 || defined(GL_OES_standard_derivatives)) | ||||
|         dFSecondary = max(dxc, dyc) * czm_pixelRatio * secondaryLinesWidth; | ||||
| #else | ||||
|         dFSecondary = czm_pixelRatio * secondaryLinesWidth; | ||||
| #endif | ||||
|  | ||||
|         isSecondaryContour = (distanceToSecondaryContour < dFSecondary) && notCloseToMain; | ||||
|     } | ||||
|  | ||||
|     // 计算当前高度所属的等高线高度 | ||||
|     float mainContourHeight = floor(materialInput.height / spacing) * spacing; | ||||
|     float secondaryContourHeight = floor(materialInput.height / spacing * (secondaryLinesCount + 1.0)) * spacing / (secondaryLinesCount + 1.0); | ||||
|  | ||||
|     // 高亮判断 | ||||
|     bool shouldHighlight = false; | ||||
|     if(isMainContour && abs(mainContourHeight - mouseHeight) < 0.5 * (spacing/(secondaryLinesCount+1.0))) { | ||||
|         shouldHighlight = true; | ||||
|     } else if(isSecondaryContour && abs(secondaryContourHeight - mouseHeight) < 0.5 * (spacing/(secondaryLinesCount+1.0))) { | ||||
|         shouldHighlight = true; | ||||
|     } | ||||
|  | ||||
|     // 颜色输出 | ||||
|     vec4 outColor; | ||||
|     if(shouldHighlight) { | ||||
|         outColor = vec4(1.0, 0.0, 0.0, 1.0); | ||||
|     } else if(isMainContour) { | ||||
|         outColor = czm_gammaCorrect(vec4(color.rgb, color.a)); | ||||
|     } else if(isSecondaryContour) { | ||||
|         outColor = czm_gammaCorrect(vec4(secondaryLinesColor.rgb, secondaryLinesColor.a)); | ||||
|     } else { | ||||
|         outColor = vec4(0.0); | ||||
|     } | ||||
|  | ||||
|     material.diffuse = outColor.rgb; | ||||
|     material.alpha = outColor.a; | ||||
|     return material; | ||||
| } | ||||
| ` | ||||
|  | ||||
|   material = new Cesium.Material({ | ||||
|     fabric: { | ||||
|       type: "ElevationContour", | ||||
|       uniforms: { | ||||
|         width: 2, | ||||
|         secondaryLinesWidth: 1, // 次级线宽度 | ||||
|         spacing: 200, | ||||
|         color: Cesium.Color.fromCssColorString('#ffd000'), | ||||
|         secondaryLinesColor: Cesium.Color.fromCssColorString('#0dff00').withAlpha(0.5), | ||||
|         mouseHeight: -100000, | ||||
|         mousePosition: new Cesium.Cartesian3(0, 0, 0), | ||||
|         secondaryLinesCount: 3 | ||||
|       }, | ||||
|     } | ||||
|   }); | ||||
| } | ||||
|  | ||||
| export { dialog } | ||||
		Reference in New Issue
	
	Block a user