@needle-tools/gltf-progressive 1.2.0-alpha.3 → 1.2.0-alpha.5
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/CHANGELOG.md +20 -0
- package/README.md +12 -4
- package/examples/threejs/index.html +1 -0
- package/examples/threejs/main.js +74 -5
- package/gltf-progressive.js +381 -347
- package/gltf-progressive.min.js +4 -4
- package/gltf-progressive.umd.cjs +4 -4
- package/lib/extension.js +10 -0
- package/lib/utils.d.ts +17 -1
- package/lib/utils.js +64 -10
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,26 @@ All notable changes to this package will be documented in this file.
|
|
|
4
4
|
The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/)
|
|
5
5
|
and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
|
|
6
6
|
|
|
7
|
+
## [1.2.0-alpha.5] - 2023-06-10
|
|
8
|
+
- fix: safeguard when `registerMesh` or `registerTexture` are being called with invalid data
|
|
9
|
+
- examples: update vanilla threejs example
|
|
10
|
+
|
|
11
|
+
## [1.2.0-alpha.4] - 2023-06-07
|
|
12
|
+
- add: `useRaycastMeshes` method:
|
|
13
|
+
```ts
|
|
14
|
+
// call to enable raycasting with low poly raycast meshes
|
|
15
|
+
// this can be done once in your project
|
|
16
|
+
useRaycastMeshes(true);
|
|
17
|
+
|
|
18
|
+
// then use the raycaster as usual
|
|
19
|
+
const raycaster = new Raycaster();
|
|
20
|
+
raycaster.setFromCamera(mouse, camera);
|
|
21
|
+
const intersects = raycaster.intersectObjects(scene.children, true);
|
|
22
|
+
|
|
23
|
+
// call to disable raycasting with low polwy meshes
|
|
24
|
+
useRaycastMeshes(false);
|
|
25
|
+
```
|
|
26
|
+
|
|
7
27
|
## [1.2.0-alpha.3] - 2023-06-06
|
|
8
28
|
- add: automatically load the highest LOD first to show a slightly better quality level as soon as possible
|
|
9
29
|
- fix: improve Texture LOD selection by taking LOD level height into account
|
package/README.md
CHANGED
|
@@ -12,11 +12,17 @@ Support for loading of glTF or GLB files with progressive mesh or texture data f
|
|
|
12
12
|
|
|
13
13
|
Examples are in the `/examples` directory. Live versions can be found in the links below.
|
|
14
14
|
|
|
15
|
-
- [Vanilla three.js](https://engine.needle.tools/demos/gltf-progressive/threejs/)
|
|
15
|
+
- [Vanilla three.js](https://engine.needle.tools/demos/gltf-progressive/threejs/) - multiple models and animations
|
|
16
16
|
- [\<model-viewer\>](https://engine.needle.tools/demos/gltf-progressive/modelviewer)
|
|
17
17
|
- [React Three Fiber](https://engine.needle.tools/demos/gltf-progressive/r3f/)
|
|
18
18
|
|
|
19
19
|
|
|
20
|
+
<br/>
|
|
21
|
+
<video width="320" controls autoplay src="https://engine.needle.tools/demos/gltf-progressive/video.mp4">
|
|
22
|
+
<source src="https://engine.needle.tools/demos/gltf-progressive/video.mp4" type="video/mp4">
|
|
23
|
+
</video>
|
|
24
|
+
|
|
25
|
+
|
|
20
26
|
## Usage
|
|
21
27
|
|
|
22
28
|
### react three fiber
|
|
@@ -74,11 +80,11 @@ gltfLoader.load(url, gltf => {
|
|
|
74
80
|
|
|
75
81
|
### \<model-viewer\>
|
|
76
82
|
|
|
77
|
-
The
|
|
83
|
+
The example can be found in `examples/modelviewer.html`
|
|
78
84
|
|
|
79
85
|
```html
|
|
80
86
|
<head>
|
|
81
|
-
<!-- Include
|
|
87
|
+
<!-- Include threejs import map -->
|
|
82
88
|
<script type="importmap">
|
|
83
89
|
{
|
|
84
90
|
"imports": {
|
|
@@ -87,14 +93,16 @@ The full example can be found in `examples/modelviewer.html`
|
|
|
87
93
|
}
|
|
88
94
|
}
|
|
89
95
|
</script>
|
|
96
|
+
<!-- Include gltf-progressive -->
|
|
90
97
|
<script type="module" src="https://www.unpkg.com/@needle-tools/gltf-progressive@latest"></script>
|
|
98
|
+
<!-- Include model-viewer -->
|
|
91
99
|
<script type="module" src="https://ajax.googleapis.com/ajax/libs/model-viewer/3.4.0/model-viewer.min.js"></script>
|
|
92
100
|
</head>
|
|
93
101
|
<body>
|
|
94
102
|
|
|
95
103
|
<model-viewer src="https://engine.needle.tools/demos/gltf-progressive/assets/church/model.glb" camera-controls auto-rotate></model-viewer>
|
|
96
104
|
|
|
97
|
-
|
|
105
|
+
</body>
|
|
98
106
|
```
|
|
99
107
|
|
|
100
108
|
|
package/examples/threejs/main.js
CHANGED
|
@@ -2,7 +2,7 @@ import * as THREE from 'three';
|
|
|
2
2
|
import { EXRLoader } from 'three/addons/loaders/EXRLoader.js';
|
|
3
3
|
import { OrbitControls } from 'three/addons/controls/OrbitControls.js';
|
|
4
4
|
import { GLTFLoader } from 'three/addons/loaders/GLTFLoader.js';
|
|
5
|
-
import { useNeedleProgressive, getRaycastMesh } from "https://www.unpkg.com/@needle-tools/gltf-progressive@latest"
|
|
5
|
+
import { useNeedleProgressive, getRaycastMesh, useRaycastMeshes } from "https://www.unpkg.com/@needle-tools/gltf-progressive@latest"
|
|
6
6
|
import { Pane } from 'https://cdn.jsdelivr.net/npm/tweakpane@4.0.3/dist/tweakpane.min.js';
|
|
7
7
|
|
|
8
8
|
|
|
@@ -58,6 +58,7 @@ new EXRLoader().load(environmentTextureUrl, texture => {
|
|
|
58
58
|
|
|
59
59
|
const modelUrls = [
|
|
60
60
|
"https://engine.needle.tools/demos/gltf-progressive/assets/putti gruppe/model.glb",
|
|
61
|
+
"https://engine.needle.tools/demos/gltf-progressive/assets/cyberpunk/model.glb",
|
|
61
62
|
"https://engine.needle.tools/demos/gltf-progressive/assets/robot/model.glb",
|
|
62
63
|
"https://engine.needle.tools/demos/gltf-progressive/assets/vase/model.glb",
|
|
63
64
|
"https://engine.needle.tools/demos/gltf-progressive/assets/jupiter_und_ganymed/model.glb",
|
|
@@ -66,6 +67,9 @@ const modelUrls = [
|
|
|
66
67
|
let currentUrl = "";
|
|
67
68
|
/** @type {null | THREE.Scene} */
|
|
68
69
|
let currentScene = null;
|
|
70
|
+
let wireframe = false;
|
|
71
|
+
/** @type {null | THREE.AnimationMixer} */
|
|
72
|
+
let animationMixer = null;
|
|
69
73
|
|
|
70
74
|
function loadScene() {
|
|
71
75
|
let currentIndex = modelUrls.indexOf(currentUrl);
|
|
@@ -75,7 +79,11 @@ function loadScene() {
|
|
|
75
79
|
}
|
|
76
80
|
const url = modelUrls[currentIndex];
|
|
77
81
|
currentUrl = url;
|
|
78
|
-
|
|
82
|
+
wireframe = false;
|
|
83
|
+
if (animationMixer) {
|
|
84
|
+
animationMixer.stopAllAction();
|
|
85
|
+
animationMixer = null;
|
|
86
|
+
}
|
|
79
87
|
|
|
80
88
|
// Integrate @needle-tools/gltf-progressive
|
|
81
89
|
// Create a new GLTFLoader instance
|
|
@@ -98,15 +106,76 @@ function loadScene() {
|
|
|
98
106
|
if (url.includes("church")) {
|
|
99
107
|
gltf.scene.scale.multiplyScalar(.1);
|
|
100
108
|
}
|
|
109
|
+
else if (url.includes("cyberpunk")) {
|
|
110
|
+
gltf.scene.scale.multiplyScalar(15);
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
if (gltf.animations?.length) {
|
|
114
|
+
console.log("Playing animation", gltf.animations)
|
|
115
|
+
animationMixer = new THREE.AnimationMixer(gltf.scene);
|
|
116
|
+
const action = animationMixer.clipAction(gltf.animations[0]);
|
|
117
|
+
action.setLoop(THREE.LoopRepeat);
|
|
118
|
+
action.play();
|
|
119
|
+
}
|
|
101
120
|
})
|
|
102
121
|
}
|
|
103
122
|
loadScene();
|
|
104
123
|
|
|
105
124
|
|
|
125
|
+
const clock = new THREE.Clock();
|
|
126
|
+
function loop() {
|
|
127
|
+
const dt = clock.getDelta();
|
|
128
|
+
if (animationMixer) {
|
|
129
|
+
animationMixer.update(dt);
|
|
130
|
+
}
|
|
131
|
+
window.requestAnimationFrame(loop);
|
|
132
|
+
}
|
|
133
|
+
window.requestAnimationFrame(loop);
|
|
134
|
+
|
|
135
|
+
|
|
136
|
+
useRaycastMeshes();
|
|
137
|
+
const raycaster = new THREE.Raycaster();
|
|
138
|
+
raycaster.params.Line.threshold = 0;
|
|
139
|
+
window.addEventListener("click", evt => {
|
|
140
|
+
const mousePos = {
|
|
141
|
+
x: (evt.clientX / window.innerWidth) * 2 - 1,
|
|
142
|
+
y: -(evt.clientY / window.innerHeight) * 2 + 1
|
|
143
|
+
}
|
|
144
|
+
raycaster.setFromCamera(mousePos, camera);
|
|
145
|
+
const hits = raycaster.intersectObjects(scene.children, true);
|
|
146
|
+
if (hits?.length) {
|
|
147
|
+
const hit = hits[0];
|
|
148
|
+
const obj = hit.object;
|
|
149
|
+
console.log("HIT", obj.name, hit)
|
|
150
|
+
const raycastMesh = getRaycastMesh(obj);
|
|
151
|
+
if (raycastMesh) {
|
|
152
|
+
const newMesh = new THREE.Mesh(raycastMesh, new THREE.MeshBasicMaterial({ color: 0xffddff, wireframe: true, transparent: true, opacity: .5, depthTest: false }));
|
|
153
|
+
newMesh.matrix.copy(obj.matrixWorld);
|
|
154
|
+
newMesh.matrixAutoUpdate = false;
|
|
155
|
+
scene.add(newMesh);
|
|
156
|
+
setTimeout(() => {
|
|
157
|
+
newMesh.removeFromParent();
|
|
158
|
+
}, 1000)
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
})
|
|
162
|
+
|
|
163
|
+
|
|
164
|
+
|
|
165
|
+
|
|
106
166
|
|
|
107
167
|
const pane = new Pane();
|
|
108
|
-
|
|
168
|
+
pane.addButton({
|
|
109
169
|
title: 'Change Scene',
|
|
170
|
+
}).on('click', loadScene);
|
|
171
|
+
|
|
172
|
+
pane.addButton({
|
|
173
|
+
title: 'Toggle Wireframe',
|
|
174
|
+
}).on('click', () => {
|
|
175
|
+
wireframe = !wireframe;
|
|
176
|
+
scene.traverse(child => {
|
|
177
|
+
if (child instanceof THREE.Mesh) {
|
|
178
|
+
child.material.wireframe = wireframe;
|
|
179
|
+
}
|
|
180
|
+
})
|
|
110
181
|
});
|
|
111
|
-
|
|
112
|
-
btn.on('click', loadScene);
|