itowns 2.35.0 → 2.37.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CONTRIBUTING.md +30 -17
- package/CONTRIBUTORS.md +1 -0
- package/changelog.md +146 -0
- package/dist/debug.js +1 -1
- package/dist/debug.js.LICENSE.txt +1 -1
- package/dist/debug.js.map +1 -1
- package/dist/itowns.js +1 -1
- package/dist/itowns.js.map +1 -1
- package/dist/itowns_widgets.js +2 -0
- package/dist/itowns_widgets.js.map +1 -0
- package/examples/3dtiles_basic.html +2 -2
- package/examples/config.json +25 -6
- package/examples/css/widgets.css +248 -0
- package/examples/geoid_geoidLayer.html +102 -0
- package/examples/images/compass.svg +60 -0
- package/examples/images/widget-logo.svg +66 -0
- package/examples/itowns-potree.html +252 -0
- package/examples/js/GUI/GuiTools.js +17 -0
- package/examples/js/Scale.js +1 -0
- package/examples/js/plugins/CSVnVRTParser.js +0 -1
- package/examples/layers/JSONLayers/Administrative.json +1 -1
- package/examples/layers/JSONLayers/Cada.json +1 -1
- package/examples/layers/JSONLayers/EtatMajor.json +1 -1
- package/examples/layers/JSONLayers/IGN_MNT.json +1 -1
- package/examples/layers/JSONLayers/IGN_MNT_HIGHRES.json +1 -1
- package/examples/layers/JSONLayers/WORLD_DTM.json +1 -1
- package/examples/misc_custom_label.html +0 -2
- package/examples/plugins_vrt.html +0 -1
- package/examples/source_file_from_fetched_data.html +90 -0
- package/examples/source_file_from_format.html +85 -0
- package/examples/source_file_from_methods.html +87 -0
- package/examples/source_file_from_parsed_data.html +104 -0
- package/examples/source_file_geojson_raster.html +21 -48
- package/examples/source_file_gpx_raster.html +28 -36
- package/examples/source_file_kml_raster.html +1 -4
- package/examples/source_file_shapefile.html +39 -35
- package/examples/source_stream_wfs_25d.html +29 -29
- package/examples/source_stream_wfs_3d.html +21 -12
- package/examples/source_stream_wfs_raster.html +20 -20
- package/examples/view_25d_map.html +28 -0
- package/examples/view_immersive.html +13 -14
- package/examples/view_multi_25d.html +1 -1
- package/examples/widgets_minimap.html +122 -0
- package/examples/widgets_navigation.html +119 -0
- package/lib/Controls/FirstPersonControls.js +10 -1
- package/lib/Controls/GlobeControls.js +26 -11
- package/lib/Controls/PlanarControls.js +1 -1
- package/lib/Converter/Feature2Mesh.js +1 -0
- package/lib/Converter/Feature2Texture.js +2 -2
- package/lib/Converter/convertToTile.js +6 -2
- package/lib/Core/3DTiles/C3DTBoundingVolume.js +4 -1
- package/lib/Core/Deprecated/Undeprecator.js +1 -1
- package/lib/Core/Feature.js +42 -42
- package/lib/Core/Geographic/Coordinates.js +56 -0
- package/lib/Core/Geographic/Crs.js +15 -0
- package/lib/Core/Geographic/Extent.js +100 -12
- package/lib/Core/Geographic/GeoidGrid.js +143 -0
- package/lib/Core/MainLoop.js +1 -1
- package/lib/Core/Math/Ellipsoid.js +27 -9
- package/lib/Core/Prefab/Globe/BuilderEllipsoidTile.js +1 -1
- package/lib/Core/Prefab/Globe/SkyShader.js +3 -1
- package/lib/Core/Prefab/Planar/PlanarLayer.js +3 -1
- package/lib/Core/Prefab/PlanarView.js +1 -1
- package/lib/Core/Style.js +2 -1
- package/lib/Core/TileGeometry.js +3 -1
- package/lib/Core/TileMesh.js +11 -16
- package/lib/Core/View.js +43 -5
- package/lib/Layer/ElevationLayer.js +15 -18
- package/lib/Layer/FeatureGeometryLayer.js +3 -1
- package/lib/Layer/GeoidLayer.js +131 -0
- package/lib/Layer/InfoLayer.js +1 -1
- package/lib/Layer/LabelLayer.js +7 -1
- package/lib/Layer/Layer.js +1 -1
- package/lib/Layer/LayerUpdateStrategy.js +1 -1
- package/lib/Layer/PotreeLayer.js +3 -1
- package/lib/Layer/TiledGeometryLayer.js +3 -1
- package/lib/Main.js +214 -174
- package/lib/MainBundle.js +1 -1
- package/lib/Parser/B3dmParser.js +2 -1
- package/lib/Parser/GDFParser.js +118 -0
- package/lib/Parser/GTXParser.js +92 -0
- package/lib/Parser/ISGParser.js +121 -0
- package/lib/Parser/LASParser.js +3 -1
- package/lib/Parser/ShapefileParser.js +0 -1
- package/lib/Parser/VectorTileParser.js +1 -1
- package/lib/Parser/XbilParser.js +1 -1
- package/lib/Process/3dTilesProcessing.js +10 -10
- package/lib/Process/FeatureProcessing.js +3 -1
- package/lib/Process/LayeredMaterialNodeProcessing.js +7 -4
- package/lib/Process/ObjectRemovalHelper.js +5 -2
- package/lib/Provider/URLBuilder.js +1 -1
- package/lib/Renderer/Label2DRenderer.js +14 -11
- package/lib/Renderer/LayeredMaterial.js +4 -3
- package/lib/Renderer/OBB.js +20 -27
- package/lib/Renderer/PointsMaterial.js +5 -6
- package/lib/Renderer/RasterTile.js +23 -5
- package/lib/Renderer/Shader/ShaderChunk.js +3 -3
- package/lib/Renderer/Shader/ShaderUtils.js +4 -2
- package/lib/Source/C3DTilesSource.js +3 -1
- package/lib/Source/EntwinePointTileSource.js +3 -1
- package/lib/Source/FileSource.js +2 -7
- package/lib/Source/PotreeSource.js +3 -1
- package/lib/Source/Source.js +15 -10
- package/lib/Source/VectorTilesSource.js +19 -0
- package/lib/Source/WMTSSource.js +3 -1
- package/lib/ThreeExtended/loaders/GLTFLoader.js +239 -98
- package/lib/Utils/CameraUtils.js +12 -2
- package/lib/Utils/DEMUtils.js +3 -3
- package/lib/Utils/FeaturesUtils.js +8 -4
- package/package.json +25 -25
|
@@ -60,9 +60,9 @@
|
|
|
60
60
|
}
|
|
61
61
|
|
|
62
62
|
var wfsBuildingSource = new itowns.WFSSource({
|
|
63
|
-
url: 'https://wxs.ign.fr/
|
|
63
|
+
url: 'https://wxs.ign.fr/topographie/geoportail/wfs?',
|
|
64
64
|
version: '2.0.0',
|
|
65
|
-
typeName: '
|
|
65
|
+
typeName: 'BDTOPO_V3:batiment',
|
|
66
66
|
crs: 'EPSG:4326',
|
|
67
67
|
extent: {
|
|
68
68
|
west: 4.568,
|
|
@@ -74,31 +74,31 @@
|
|
|
74
74
|
format: 'application/json',
|
|
75
75
|
});
|
|
76
76
|
|
|
77
|
+
function colorBuildings(properties) {
|
|
78
|
+
if (properties.usage_1 === 'Résidentiel') {
|
|
79
|
+
return '#FDFDFF';
|
|
80
|
+
} else if (properties.usage_1 === 'Annexe') {
|
|
81
|
+
return '#C6C5B9';
|
|
82
|
+
} else if (properties.usage_1 === 'Commercial et services') {
|
|
83
|
+
return '#62929E';
|
|
84
|
+
} else if (properties.usage_1 === 'Religieux') {
|
|
85
|
+
return '#393D3F';
|
|
86
|
+
} else if (properties.usage_1 === 'Sportif') {
|
|
87
|
+
return '#546A7B';
|
|
88
|
+
} else {
|
|
89
|
+
return '#555555';
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
|
|
77
93
|
var wfsBuildingLayer = new itowns.ColorLayer('wfsBuilding', {
|
|
78
94
|
transparent: true,
|
|
79
95
|
style: {
|
|
80
96
|
fill: {
|
|
81
|
-
color:
|
|
82
|
-
if (p.geojson.id.indexOf('bati_remarquable') === 0) {
|
|
83
|
-
return '#5555ff';
|
|
84
|
-
}
|
|
85
|
-
if (p.geojson.id.indexOf('bati_industriel') === 0) {
|
|
86
|
-
return '#ff5555';
|
|
87
|
-
}
|
|
88
|
-
return '#eeeeee';
|
|
89
|
-
},
|
|
97
|
+
color: colorBuildings,
|
|
90
98
|
opacity: 0.7
|
|
91
99
|
},
|
|
92
100
|
stroke: {
|
|
93
|
-
color:
|
|
94
|
-
if (p.geojson.id.indexOf('bati_remarquable') === 0) {
|
|
95
|
-
return '#8888ff';
|
|
96
|
-
}
|
|
97
|
-
if (p.geojson.id.indexOf('bati_industriel') === 0) {
|
|
98
|
-
return '#ff8888';
|
|
99
|
-
}
|
|
100
|
-
return '#ffffff';
|
|
101
|
-
},
|
|
101
|
+
color: colorBuildings,
|
|
102
102
|
width: 2.0,
|
|
103
103
|
},
|
|
104
104
|
},
|
|
@@ -97,6 +97,34 @@
|
|
|
97
97
|
|
|
98
98
|
view.addLayer(wmsElevationLayer);
|
|
99
99
|
|
|
100
|
+
var wfsCartoSource = new itowns.WFSSource({
|
|
101
|
+
url: 'https://wxs.ign.fr/cartovecto/geoportail/wfs?',
|
|
102
|
+
version: '2.0.0',
|
|
103
|
+
typeName: 'BDCARTO_BDD_WLD_WGS84G:zone_habitat_mairie',
|
|
104
|
+
crs: 'EPSG:3946',
|
|
105
|
+
ipr: 'IGN',
|
|
106
|
+
format: 'application/json',
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
var wfsCartoStyle = new itowns.Style({
|
|
110
|
+
zoom: { min: 0, max: 20 },
|
|
111
|
+
text: {
|
|
112
|
+
field: '{toponyme}',
|
|
113
|
+
color: 'white',
|
|
114
|
+
transform: 'uppercase',
|
|
115
|
+
size: 15,
|
|
116
|
+
haloColor: 'rgba(20,20,20, 0.8)',
|
|
117
|
+
haloWidth: 3,
|
|
118
|
+
},
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
var wfsCartoLayer = new itowns.LabelLayer('wfsCarto', {
|
|
122
|
+
source: wfsCartoSource,
|
|
123
|
+
style: wfsCartoStyle,
|
|
124
|
+
});
|
|
125
|
+
|
|
126
|
+
view.addLayer(wfsCartoLayer);
|
|
127
|
+
|
|
100
128
|
// Initialize scale :
|
|
101
129
|
const initialScaleSize = 200; // in pixel
|
|
102
130
|
const divScaleWidget = document.getElementById('divScaleWidget');
|
|
@@ -80,7 +80,7 @@
|
|
|
80
80
|
|
|
81
81
|
function altitudeBuildings(properties) {
|
|
82
82
|
// I set altitude building 3 meters down, to be sure building is anchored in the ground
|
|
83
|
-
return properties.
|
|
83
|
+
return properties.altitude_minimale_sol - 3;
|
|
84
84
|
}
|
|
85
85
|
|
|
86
86
|
function extrudeBuildings(properties) {
|
|
@@ -115,22 +115,21 @@
|
|
|
115
115
|
|
|
116
116
|
// when oriented image layer is ready..
|
|
117
117
|
view.addLayer(olayer, view.tileLayer).then(function addWfsLayer(orientedImageLayer) {
|
|
118
|
-
|
|
119
118
|
// prepare WFS source for the buildings
|
|
120
119
|
var wfsBuildingSource = new itowns.WFSSource({
|
|
121
|
-
url: 'https://wxs.ign.fr/
|
|
120
|
+
url: 'https://wxs.ign.fr/topographie/geoportail/wfs?',
|
|
122
121
|
version: '2.0.0',
|
|
123
|
-
typeName: '
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
122
|
+
typeName: 'BDTOPO_V3:batiment',
|
|
123
|
+
crs: 'EPSG:4326',
|
|
124
|
+
ipr: 'IGN',
|
|
125
|
+
format: 'application/json',
|
|
126
|
+
extent: {
|
|
127
|
+
west: 2.334,
|
|
128
|
+
east: 2.335,
|
|
129
|
+
south: 48.849,
|
|
130
|
+
north: 48.851,
|
|
131
|
+
},
|
|
132
|
+
});
|
|
134
133
|
|
|
135
134
|
// create geometry layer for the buildings
|
|
136
135
|
var wfsBuildingLayer = new itowns.FeatureGeometryLayer('Buildings', {
|
|
@@ -81,7 +81,7 @@
|
|
|
81
81
|
|
|
82
82
|
itowns.THREE.Object3D.DefaultUp.set(0, 0, 1);
|
|
83
83
|
|
|
84
|
-
scale = new itowns.THREE.Vector3(1, 1, 1).divideScalar(extent.
|
|
84
|
+
scale = new itowns.THREE.Vector3(1, 1, 1).divideScalar(extent.planarDimensions().x);
|
|
85
85
|
|
|
86
86
|
// Instanciate View
|
|
87
87
|
view = new itowns.View(extent.crs, viewerDiv);
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
<html>
|
|
2
|
+
<head>
|
|
3
|
+
<title>Itowns - Minimap widget</title>
|
|
4
|
+
|
|
5
|
+
<meta charset="UTF-8">
|
|
6
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
7
|
+
|
|
8
|
+
<link rel="stylesheet" type="text/css" href="css/example.css">
|
|
9
|
+
<link rel="stylesheet" type="text/css" href="css/LoadingScreen.css">
|
|
10
|
+
|
|
11
|
+
<!-- Import stylesheet for itowns Widgets plugin -->
|
|
12
|
+
<link rel="stylesheet" type="text/css" href="css/widgets.css">
|
|
13
|
+
|
|
14
|
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/dat-gui/0.7.6/dat.gui.min.js"></script>
|
|
15
|
+
</head>
|
|
16
|
+
<body>
|
|
17
|
+
<!-- Add a description -->
|
|
18
|
+
<div id="description">
|
|
19
|
+
Double click on the minimap to travel to the cursor location.
|
|
20
|
+
</div>
|
|
21
|
+
|
|
22
|
+
<!-- Create a container for itowns viewer -->
|
|
23
|
+
<div id="viewerDiv"></div>
|
|
24
|
+
|
|
25
|
+
<!-- Import iTowns source code -->
|
|
26
|
+
<script src="../dist/itowns.js"></script>
|
|
27
|
+
<script src="../dist/debug.js"></script>
|
|
28
|
+
<!-- Import iTowns Widgets plugin -->
|
|
29
|
+
<script src="../dist/itowns_widgets.js"></script>
|
|
30
|
+
<!-- Import iTowns LoadingScreen and GuiTools plugins -->
|
|
31
|
+
<script src="js/GUI/LoadingScreen.js"></script>
|
|
32
|
+
<script src="js/GUI/GuiTools.js"></script>
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
<script type="text/javascript">
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
// ---------- CREATE A GlobeView FOR SUPPORTING DATA VISUALIZATION : ----------
|
|
40
|
+
|
|
41
|
+
// Define camera initial position
|
|
42
|
+
const placement = {
|
|
43
|
+
coord: new itowns.Coordinates('EPSG:4326', 2.351323, 48.856712),
|
|
44
|
+
range: 6000,
|
|
45
|
+
tilt: 50,
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
// `viewerDiv` contains iTowns' rendering area (`<canvas>`)
|
|
49
|
+
const viewerDiv = document.getElementById('viewerDiv');
|
|
50
|
+
|
|
51
|
+
// Create a GlobeView
|
|
52
|
+
const view = new itowns.GlobeView(viewerDiv, placement);
|
|
53
|
+
|
|
54
|
+
// Setup loading screen and debug menu
|
|
55
|
+
setupLoadingScreen(viewerDiv, view);
|
|
56
|
+
const debugMenu = new GuiTools('menuDiv', view);
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
|
|
60
|
+
// ---------- DISPLAY CONTEXTUAL DATA : ----------
|
|
61
|
+
|
|
62
|
+
// Add one imagery layer to the scene. This layer's properties are defined in a json file, but it could be
|
|
63
|
+
// defined as a plain js object. See `Layer` documentation for more info.
|
|
64
|
+
itowns.Fetcher.json('layers/JSONLayers/Ortho.json').then((config) => {
|
|
65
|
+
config.source = new itowns.WMTSSource(config.source);
|
|
66
|
+
view.addLayer(
|
|
67
|
+
new itowns.ColorLayer(config.id, config),
|
|
68
|
+
).then(debugMenu.addLayerGUI.bind(debugMenu));
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
// Add two elevation layers, each with a different level of detail. Here again, each layer's properties are
|
|
72
|
+
// defined in a json file.
|
|
73
|
+
function addElevationLayerFromConfig(config) {
|
|
74
|
+
config.source = new itowns.WMTSSource(config.source);
|
|
75
|
+
view.addLayer(
|
|
76
|
+
new itowns.ElevationLayer(config.id, config),
|
|
77
|
+
).then(debugMenu.addLayerGUI.bind(debugMenu));
|
|
78
|
+
}
|
|
79
|
+
itowns.Fetcher.json('layers/JSONLayers/WORLD_DTM.json').then(addElevationLayerFromConfig);
|
|
80
|
+
itowns.Fetcher.json('layers/JSONLayers/IGN_MNT_HIGHRES.json').then(addElevationLayerFromConfig);
|
|
81
|
+
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
// ---------- ADD MINIMAP WIDGET : ----------
|
|
85
|
+
|
|
86
|
+
// Create a ColorLayer that shall be displayed on the minimap.
|
|
87
|
+
const minimapColorLayer = new itowns.ColorLayer('minimap', {
|
|
88
|
+
source: new itowns.VectorTilesSource({
|
|
89
|
+
style: 'https://wxs.ign.fr/essentiels/static/vectorTiles/styles/PLAN.IGN/standard.json',
|
|
90
|
+
// We don't display mountains and plot related data to ease visualisation
|
|
91
|
+
filter: (layer) => !layer['source-layer'].includes('oro_')
|
|
92
|
+
&& !layer['source-layer'].includes('parcellaire'),
|
|
93
|
+
}),
|
|
94
|
+
addLabelLayer: true,
|
|
95
|
+
});
|
|
96
|
+
|
|
97
|
+
// Create a minimap.
|
|
98
|
+
const minimap = new itowns_widgets.Minimap(view, minimapColorLayer, {
|
|
99
|
+
cursor: '+',
|
|
100
|
+
size: 200,
|
|
101
|
+
});
|
|
102
|
+
|
|
103
|
+
|
|
104
|
+
|
|
105
|
+
// ---------- ADD INTERACTION WITH MINIMAP : ----------
|
|
106
|
+
|
|
107
|
+
// When double-clicking the minimap, travel to the cursor location.
|
|
108
|
+
const cursorCoordinates = new itowns.Coordinates(minimap.view.referenceCrs);
|
|
109
|
+
minimap.domElement.addEventListener('dblclick', (event) => {
|
|
110
|
+
minimap.view.pickCoordinates(event, cursorCoordinates);
|
|
111
|
+
view.controls.lookAtCoordinate({ coord: cursorCoordinates });
|
|
112
|
+
});
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
|
|
116
|
+
// ---------- DEBUG TOOLS : ----------
|
|
117
|
+
|
|
118
|
+
debug.createTileDebugUI(debugMenu.gui, view);
|
|
119
|
+
|
|
120
|
+
</script>
|
|
121
|
+
</body>
|
|
122
|
+
</html>
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
<html>
|
|
2
|
+
<head>
|
|
3
|
+
<title>Itowns - Navigation widget</title>
|
|
4
|
+
|
|
5
|
+
<meta charset="UTF-8">
|
|
6
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
7
|
+
|
|
8
|
+
<link rel="stylesheet" type="text/css" href="css/example.css">
|
|
9
|
+
<link rel="stylesheet" type="text/css" href="css/LoadingScreen.css">
|
|
10
|
+
|
|
11
|
+
<!-- Import stylesheet for itowns Widgets plugin -->
|
|
12
|
+
<link rel="stylesheet" type="text/css" href="css/widgets.css">
|
|
13
|
+
|
|
14
|
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/dat-gui/0.7.6/dat.gui.min.js"></script>
|
|
15
|
+
</head>
|
|
16
|
+
<body>
|
|
17
|
+
<div id="viewerDiv"></div>
|
|
18
|
+
|
|
19
|
+
<!-- Import iTowns source code -->
|
|
20
|
+
<script src="../dist/itowns.js"></script>
|
|
21
|
+
<script src="../dist/debug.js"></script>
|
|
22
|
+
<!-- Import iTowns Widgets plugin -->
|
|
23
|
+
<script src="../dist/itowns_widgets.js"></script>
|
|
24
|
+
<!-- Import iTowns LoadingScreen and GuiTools plugins -->
|
|
25
|
+
<script src="js/GUI/LoadingScreen.js"></script>
|
|
26
|
+
<script src="js/GUI/GuiTools.js"></script>
|
|
27
|
+
|
|
28
|
+
|
|
29
|
+
<script type="text/javascript">
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
// ---------- CREATE A GlobeView FOR SUPPORTING DATA VISUALIZATION : ----------
|
|
34
|
+
|
|
35
|
+
// Define camera initial position
|
|
36
|
+
const placement = {
|
|
37
|
+
coord: new itowns.Coordinates('EPSG:4326', 2.351323, 48.856712),
|
|
38
|
+
range: 6000,
|
|
39
|
+
tilt: 50,
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
// `viewerDiv` contains iTowns' rendering area (`<canvas>`)
|
|
43
|
+
const viewerDiv = document.getElementById('viewerDiv');
|
|
44
|
+
|
|
45
|
+
// Create a GlobeView
|
|
46
|
+
const view = new itowns.GlobeView(viewerDiv, placement);
|
|
47
|
+
|
|
48
|
+
// Setup loading screen and debug menu
|
|
49
|
+
setupLoadingScreen(viewerDiv, view);
|
|
50
|
+
const debugMenu = new GuiTools('menuDiv', view);
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
// ---------- DISPLAY CONTEXTUAL DATA : ----------
|
|
55
|
+
|
|
56
|
+
// Add one imagery layer to the scene. This layer's properties are defined in a json file, but it could be
|
|
57
|
+
// defined as a plain js object. See `Layer` documentation for more info.
|
|
58
|
+
itowns.Fetcher.json('layers/JSONLayers/Ortho.json').then((config) => {
|
|
59
|
+
config.source = new itowns.WMTSSource(config.source);
|
|
60
|
+
view.addLayer(
|
|
61
|
+
new itowns.ColorLayer(config.id, config),
|
|
62
|
+
).then(debugMenu.addLayerGUI.bind(debugMenu));
|
|
63
|
+
});
|
|
64
|
+
|
|
65
|
+
// Add two elevation layers, each with a different level of detail. Here again, each layer's properties are
|
|
66
|
+
// defined in a json file.
|
|
67
|
+
function addElevationLayerFromConfig(config) {
|
|
68
|
+
config.source = new itowns.WMTSSource(config.source);
|
|
69
|
+
view.addLayer(
|
|
70
|
+
new itowns.ElevationLayer(config.id, config),
|
|
71
|
+
).then(debugMenu.addLayerGUI.bind(debugMenu));
|
|
72
|
+
}
|
|
73
|
+
itowns.Fetcher.json('layers/JSONLayers/WORLD_DTM.json').then(addElevationLayerFromConfig);
|
|
74
|
+
itowns.Fetcher.json('layers/JSONLayers/IGN_MNT_HIGHRES.json').then(addElevationLayerFromConfig);
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
// ---------- ADD NAVIGATION WIDGET : ----------
|
|
79
|
+
|
|
80
|
+
const widgets = new itowns_widgets.Navigation(view);
|
|
81
|
+
|
|
82
|
+
// Example on how to add a new button to the widgets menu
|
|
83
|
+
widgets.addButton(
|
|
84
|
+
'rotate-up',
|
|
85
|
+
'<p style="font-size: 20px">↓</p>',
|
|
86
|
+
() => {
|
|
87
|
+
view.controls.lookAtCoordinate({
|
|
88
|
+
tilt: view.controls.getTilt() - 10,
|
|
89
|
+
time: 500,
|
|
90
|
+
});
|
|
91
|
+
},
|
|
92
|
+
'button-bar-rotation',
|
|
93
|
+
);
|
|
94
|
+
widgets.addButton(
|
|
95
|
+
'rotate-down',
|
|
96
|
+
'<p style="font-size: 20px">↑</p>',
|
|
97
|
+
() => {
|
|
98
|
+
view.controls.lookAtCoordinate({
|
|
99
|
+
tilt: view.controls.getTilt() + 10,
|
|
100
|
+
time: 500,
|
|
101
|
+
});
|
|
102
|
+
},
|
|
103
|
+
'button-bar-rotation',
|
|
104
|
+
);
|
|
105
|
+
widgets.addButton(
|
|
106
|
+
'reset-position',
|
|
107
|
+
'↺',
|
|
108
|
+
() => { view.controls.lookAtCoordinate(placement) },
|
|
109
|
+
);
|
|
110
|
+
|
|
111
|
+
|
|
112
|
+
|
|
113
|
+
// ---------- DEBUG TOOLS : ----------
|
|
114
|
+
|
|
115
|
+
debug.createTileDebugUI(debugMenu.gui, view);
|
|
116
|
+
|
|
117
|
+
</script>
|
|
118
|
+
</body>
|
|
119
|
+
</html>
|
|
@@ -170,13 +170,16 @@ var FirstPersonControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
170
170
|
_this._onMouseWheel = _this.onMouseWheel.bind((0, _assertThisInitialized2["default"])(_this));
|
|
171
171
|
_this._onKeyUp = _this.onKeyUp.bind((0, _assertThisInitialized2["default"])(_this));
|
|
172
172
|
_this._onKeyDown = _this.onKeyDown.bind((0, _assertThisInitialized2["default"])(_this));
|
|
173
|
+
_this._onContextMenu = _this.onContextMenu.bind((0, _assertThisInitialized2["default"])(_this));
|
|
173
174
|
view.domElement.addEventListener('mousedown', _this._onMouseDown, false);
|
|
174
175
|
view.domElement.addEventListener('touchstart', _this._onMouseDown, false);
|
|
175
176
|
view.domElement.addEventListener('mousemove', _this._onMouseMove, false);
|
|
176
177
|
view.domElement.addEventListener('touchmove', _this._onMouseMove, false);
|
|
177
178
|
view.domElement.addEventListener('mouseup', _this._onMouseUp, false);
|
|
178
179
|
view.domElement.addEventListener('touchend', _this._onMouseUp, false);
|
|
179
|
-
view.domElement.addEventListener('wheel', _this._onMouseWheel, false); //
|
|
180
|
+
view.domElement.addEventListener('wheel', _this._onMouseWheel, false); // Disable context menu when right clicking.
|
|
181
|
+
|
|
182
|
+
view.domElement.addEventListener('contextmenu', _this._onContextMenu, false); // TODO: Why windows
|
|
180
183
|
|
|
181
184
|
document.addEventListener('keydown', _this._onKeyDown, false);
|
|
182
185
|
document.addEventListener('keyup', _this._onKeyUp, false);
|
|
@@ -380,6 +383,11 @@ var FirstPersonControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
380
383
|
e.preventDefault();
|
|
381
384
|
}
|
|
382
385
|
}
|
|
386
|
+
}, {
|
|
387
|
+
key: "onContextMenu",
|
|
388
|
+
value: function onContextMenu(event) {
|
|
389
|
+
event.preventDefault();
|
|
390
|
+
}
|
|
383
391
|
}, {
|
|
384
392
|
key: "dispose",
|
|
385
393
|
value: function dispose() {
|
|
@@ -391,6 +399,7 @@ var FirstPersonControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
391
399
|
this.view.domElement.removeEventListener('mouseup', this._onMouseUp, false);
|
|
392
400
|
this.view.domElement.removeEventListener('touchend', this._onMouseUp, false);
|
|
393
401
|
this.view.domElement.removeEventListener('wheel', this._onMouseWheel, false);
|
|
402
|
+
this.view.domElement.removeEventListener('contextmenu', this._onContextMenu, false);
|
|
394
403
|
document.removeEventListener('keydown', this._onKeyDown, false);
|
|
395
404
|
document.removeEventListener('keyup', this._onKeyUp, false);
|
|
396
405
|
}
|
|
@@ -33,6 +33,8 @@ var _CameraUtils = _interopRequireDefault(require("../Utils/CameraUtils"));
|
|
|
33
33
|
|
|
34
34
|
var _StateControl = _interopRequireDefault(require("./StateControl"));
|
|
35
35
|
|
|
36
|
+
var _View = require("../Core/View");
|
|
37
|
+
|
|
36
38
|
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function _getRequireWildcardCache(nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
|
|
37
39
|
|
|
38
40
|
function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || _typeof(obj) !== "object" && typeof obj !== "function") { return { "default": obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj["default"] = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
|
|
@@ -75,6 +77,7 @@ var dollyScale; // Globe move
|
|
|
75
77
|
|
|
76
78
|
var moveAroundGlobe = new THREE.Quaternion();
|
|
77
79
|
var cameraTarget = new THREE.Object3D();
|
|
80
|
+
var coordCameraTarget = new _Coordinates["default"]('EPSG:4978');
|
|
78
81
|
cameraTarget.matrixWorldInverse = new THREE.Matrix4();
|
|
79
82
|
var xyz = new _Coordinates["default"]('EPSG:4978', 0, 0, 0);
|
|
80
83
|
var c = new _Coordinates["default"]('EPSG:4326', 0, 0, 0); // Position object on globe
|
|
@@ -342,6 +345,7 @@ var GlobeControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
342
345
|
|
|
343
346
|
_this.lookAtCoordinate(placement, false);
|
|
344
347
|
|
|
348
|
+
coordCameraTarget.crs = _this.view.referenceCrs;
|
|
345
349
|
return _this;
|
|
346
350
|
}
|
|
347
351
|
|
|
@@ -610,6 +614,14 @@ var GlobeControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
610
614
|
});
|
|
611
615
|
this.player.playLater(durationDampingOrbital, 2);
|
|
612
616
|
}
|
|
617
|
+
|
|
618
|
+
this.view.dispatchEvent({
|
|
619
|
+
type: _View.VIEW_EVENTS.CAMERA_MOVED,
|
|
620
|
+
coord: coordCameraTarget.setFromVector3(cameraTarget.position),
|
|
621
|
+
range: spherical.radius,
|
|
622
|
+
heading: -THREE.MathUtils.radToDeg(spherical.theta),
|
|
623
|
+
tilt: 90 - THREE.MathUtils.radToDeg(spherical.phi)
|
|
624
|
+
});
|
|
613
625
|
}
|
|
614
626
|
}, {
|
|
615
627
|
key: "onStateChange",
|
|
@@ -751,17 +763,19 @@ var GlobeControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
751
763
|
}, {
|
|
752
764
|
key: "updateTarget",
|
|
753
765
|
value: function updateTarget() {
|
|
754
|
-
//
|
|
755
|
-
this.view.getPickingPositionFromDepth(null, pickedPosition)
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
766
|
+
// Check if the middle of the screen is on the globe (to prevent having a dark-screen bug if outside the globe)
|
|
767
|
+
if (this.view.getPickingPositionFromDepth(null, pickedPosition)) {
|
|
768
|
+
// Update camera's target position
|
|
769
|
+
var distance = !isNaN(pickedPosition.x) ? this.camera.position.distanceTo(pickedPosition) : 100;
|
|
770
|
+
targetPosition.set(0, 0, -distance);
|
|
771
|
+
this.camera.localToWorld(targetPosition); // set new camera target on globe
|
|
772
|
+
|
|
773
|
+
positionObject(targetPosition, cameraTarget);
|
|
774
|
+
cameraTarget.matrixWorldInverse.copy(cameraTarget.matrixWorld).invert();
|
|
775
|
+
targetPosition.copy(this.camera.position);
|
|
776
|
+
targetPosition.applyMatrix4(cameraTarget.matrixWorldInverse);
|
|
777
|
+
spherical.setFromVector3(targetPosition);
|
|
778
|
+
}
|
|
765
779
|
}
|
|
766
780
|
}, {
|
|
767
781
|
key: "handlingEvent",
|
|
@@ -1298,6 +1312,7 @@ var GlobeControls = /*#__PURE__*/function (_THREE$EventDispatche) {
|
|
|
1298
1312
|
|
|
1299
1313
|
var params = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
1300
1314
|
var isAnimated = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : this.isAnimationEnabled();
|
|
1315
|
+
this.player.stop();
|
|
1301
1316
|
|
|
1302
1317
|
if (!params.isExtent) {
|
|
1303
1318
|
if (params.zoom) {
|
|
@@ -7,7 +7,7 @@ var _typeof = require("@babel/runtime/helpers/typeof");
|
|
|
7
7
|
Object.defineProperty(exports, "__esModule", {
|
|
8
8
|
value: true
|
|
9
9
|
});
|
|
10
|
-
exports["default"] = exports.
|
|
10
|
+
exports.keys = exports["default"] = exports.STATE = exports.PLANAR_CONTROL_EVENT = void 0;
|
|
11
11
|
|
|
12
12
|
var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime/helpers/classCallCheck"));
|
|
13
13
|
|
|
@@ -176,7 +176,7 @@ function drawPoint(ctx, x, y) {
|
|
|
176
176
|
var coord = new _Coordinates["default"]('EPSG:4326', 0, 0, 0);
|
|
177
177
|
|
|
178
178
|
function drawFeature(ctx, feature, extent, style, invCtxScale) {
|
|
179
|
-
var extentDim = extent.
|
|
179
|
+
var extentDim = extent.planarDimensions();
|
|
180
180
|
var scaleRadius = extentDim.x / ctx.canvas.width;
|
|
181
181
|
var globals = {
|
|
182
182
|
zoom: extent.zoom
|
|
@@ -259,7 +259,7 @@ var _default = {
|
|
|
259
259
|
if (collection) {
|
|
260
260
|
// A texture is instancied drawn canvas
|
|
261
261
|
// origin and dimension are used to transform the feature's coordinates to canvas's space
|
|
262
|
-
extent.
|
|
262
|
+
extent.planarDimensions(dimension);
|
|
263
263
|
var c = document.createElement('canvas');
|
|
264
264
|
coord.crs = extent.crs;
|
|
265
265
|
c.width = sizeTexture;
|
|
@@ -41,7 +41,7 @@ function setTileFromTiledLayer(tile, tileLayer) {
|
|
|
41
41
|
// If the point is below the horizon,
|
|
42
42
|
// the tile is guaranteed to be below the horizon as well.
|
|
43
43
|
tile.horizonCullingPoint = tile.extent.center().as('EPSG:4978').toVector3();
|
|
44
|
-
tile.extent.
|
|
44
|
+
tile.extent.planarDimensions(dimensions).multiplyScalar(THREE.MathUtils.DEG2RAD); // alpha is maximum angle between two points of tile
|
|
45
45
|
|
|
46
46
|
var alpha = dimensions.length();
|
|
47
47
|
var h = Math.abs(1.0 / Math.cos(alpha * 0.5));
|
|
@@ -86,7 +86,11 @@ var _default = {
|
|
|
86
86
|
setTileFromTiledLayer(tile, layer);
|
|
87
87
|
|
|
88
88
|
if (parent) {
|
|
89
|
-
tile.setBBoxZ(
|
|
89
|
+
tile.setBBoxZ({
|
|
90
|
+
min: parent.obb.z.min,
|
|
91
|
+
max: parent.obb.z.max
|
|
92
|
+
});
|
|
93
|
+
tile.geoidHeight = parent.geoidHeight;
|
|
90
94
|
}
|
|
91
95
|
|
|
92
96
|
return tile;
|
|
@@ -74,7 +74,10 @@ var C3DTBoundingVolume = /*#__PURE__*/function () {
|
|
|
74
74
|
extent.set(THREE.MathUtils.radToDeg(region[0]), THREE.MathUtils.radToDeg(region[2]), THREE.MathUtils.radToDeg(region[1]), THREE.MathUtils.radToDeg(region[3]));
|
|
75
75
|
var regionBox = new _OBB["default"]();
|
|
76
76
|
regionBox.setFromExtent(extent);
|
|
77
|
-
regionBox.updateZ(
|
|
77
|
+
regionBox.updateZ({
|
|
78
|
+
min: region[4],
|
|
79
|
+
max: region[5]
|
|
80
|
+
}); // at this point box.matrix = box.epsg4978_from_local, so
|
|
78
81
|
// we transform it in parent_from_local by using parent's
|
|
79
82
|
// epsg4978_from_local which from our point of view is
|
|
80
83
|
// epsg4978_from_parent. box.matrix = (epsg4978_from_parent ^ -1) *
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
Object.defineProperty(exports, "__esModule", {
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
|
-
exports
|
|
6
|
+
exports.deprecatedParsingOptionsToNewOne = exports.deprecatedFeature2MeshOptions = exports.deprecatedColorLayerOptions = exports["default"] = void 0;
|
|
7
7
|
|
|
8
8
|
var _LayeredMaterial = require("../../Renderer/LayeredMaterial");
|
|
9
9
|
|