Skip to content

Commit 5305474

Browse files
authored
WebGPURenderer: ReflectorNode + Examples (#787)
* WebGPURenderer: ReflectorNode + Examples * Fix * Update three.js * Add examples * getMaxAnisotropy * Updates * Update patch * Delete examples * Fix
1 parent 8b5efd3 commit 5305474

File tree

12 files changed

+141
-28
lines changed

12 files changed

+141
-28
lines changed

examples-testing/changes.patch

Lines changed: 60 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -13861,12 +13861,53 @@ index b8fb383..0bcc65c 100644
1386113861

1386213862
const gui = new GUI();
1386313863

13864+
diff --git a/examples-testing/examples/webgpu_materials_texture_anisotropy.ts b/examples-testing/examples/webgpu_materials_texture_anisotropy.ts
13865+
index 00672da..cf96e31 100644
13866+
--- a/examples-testing/examples/webgpu_materials_texture_anisotropy.ts
13867+
+++ b/examples-testing/examples/webgpu_materials_texture_anisotropy.ts
13868+
@@ -3,9 +3,9 @@ import * as THREE from 'three';
13869+
import Stats from 'three/addons/libs/stats.module.js';
13870+
import WebGPURenderer from 'three/addons/renderers/webgpu/WebGPURenderer.js';
13871+
13872+
-let container, stats;
13873+
+let container: HTMLDivElement, stats: Stats;
13874+
13875+
-let camera, scene1, scene2, renderer;
13876+
+let camera: THREE.PerspectiveCamera, scene1: THREE.Scene, scene2: THREE.Scene, renderer: WebGPURenderer;
13877+
13878+
let mouseX = 0,
13879+
mouseY = 0;
13880+
@@ -76,11 +76,11 @@ async function init() {
13881+
texture2.repeat.set(512, 512);
13882+
13883+
if (maxAnisotropy > 0) {
13884+
- document.getElementById('val_left').innerHTML = texture1.anisotropy;
13885+
- document.getElementById('val_right').innerHTML = texture2.anisotropy;
13886+
+ document.getElementById('val_left')!.innerHTML = texture1.anisotropy.toString();
13887+
+ document.getElementById('val_right')!.innerHTML = texture2.anisotropy.toString();
13888+
} else {
13889+
- document.getElementById('val_left').innerHTML = 'not supported';
13890+
- document.getElementById('val_right').innerHTML = 'not supported';
13891+
+ document.getElementById('val_left')!.innerHTML = 'not supported';
13892+
+ document.getElementById('val_right')!.innerHTML = 'not supported';
13893+
}
13894+
13895+
//
13896+
@@ -115,7 +115,7 @@ function onWindowResize() {
13897+
renderer.setSize(window.innerWidth, window.innerHeight);
13898+
}
13899+
13900+
-function onDocumentMouseMove(event) {
13901+
+function onDocumentMouseMove(event: MouseEvent) {
13902+
const windowHalfX = window.innerWidth / 2;
13903+
const windowHalfY = window.innerHeight / 2;
13904+
1386413905
diff --git a/examples-testing/examples/webgpu_materials_video.ts b/examples-testing/examples/webgpu_materials_video.ts
13865-
index f50456f..59ec321 100644
13906+
index fbbabfc..a1a82bd 100644
1386613907
--- a/examples-testing/examples/webgpu_materials_video.ts
1386713908
+++ b/examples-testing/examples/webgpu_materials_video.ts
13868-
@@ -3,11 +3,14 @@ import * as THREE from 'three';
13869-
import WebGPU from 'three/addons/capabilities/WebGPU.js';
13909+
@@ -2,11 +2,14 @@ import * as THREE from 'three';
13910+
1387013911
import WebGPURenderer from 'three/addons/renderers/webgpu/WebGPURenderer.js';
1387113912

1387213913
-let container;
@@ -13883,7 +13924,7 @@ index f50456f..59ec321 100644
1388313924

1388413925
let mouseX = 0;
1388513926
let mouseY = 0;
13886-
@@ -15,14 +18,14 @@ let mouseY = 0;
13927+
@@ -14,20 +17,20 @@ let mouseY = 0;
1388713928
let windowHalfX = window.innerWidth / 2;
1388813929
let windowHalfY = window.innerHeight / 2;
1388913930

@@ -13902,16 +13943,14 @@ index f50456f..59ec321 100644
1390213943
startButton.addEventListener('click', function () {
1390313944
init();
1390413945
});
13905-
@@ -34,7 +37,7 @@ function init() {
13906-
throw new Error('No WebGPU support');
13907-
}
1390813946

13947+
function init() {
1390913948
- const overlay = document.getElementById('overlay');
1391013949
+ const overlay = document.getElementById('overlay')!;
1391113950
overlay.remove();
1391213951

1391313952
container = document.createElement('div');
13914-
@@ -55,7 +58,7 @@ function init() {
13953+
@@ -48,7 +51,7 @@ function init() {
1391513954
renderer.setAnimationLoop(render);
1391613955
container.appendChild(renderer.domElement);
1391713956

@@ -13920,7 +13959,7 @@ index f50456f..59ec321 100644
1392013959
video.play();
1392113960
video.addEventListener('play', function () {
1392213961
this.currentTime = 3;
13923-
@@ -131,7 +134,7 @@ function onWindowResize() {
13962+
@@ -124,7 +127,7 @@ function onWindowResize() {
1392413963
renderer.setSize(window.innerWidth, window.innerHeight);
1392513964
}
1392613965

@@ -13929,7 +13968,7 @@ index f50456f..59ec321 100644
1392913968
const uvs = geometry.attributes.uv.array;
1393013969

1393113970
for (let i = 0; i < uvs.length; i += 2) {
13932-
@@ -140,7 +143,7 @@ function change_uvs(geometry, unitx, unity, offsetx, offsety) {
13971+
@@ -133,7 +136,7 @@ function change_uvs(geometry, unitx, unity, offsetx, offsety) {
1393313972
}
1393413973
}
1393513974

@@ -13938,7 +13977,7 @@ index f50456f..59ec321 100644
1393813977
mouseX = event.clientX - windowHalfX;
1393913978
mouseY = (event.clientY - windowHalfY) * 0.3;
1394013979
}
13941-
@@ -161,20 +164,20 @@ function render() {
13980+
@@ -154,20 +157,20 @@ function render() {
1394213981
for (let i = 0; i < cube_count; i++) {
1394313982
material = materials[i];
1394413983

@@ -13966,7 +14005,7 @@ index f50456f..59ec321 100644
1396614005
}
1396714006
}
1396814007

13969-
@@ -182,8 +185,8 @@ function render() {
14008+
@@ -175,8 +178,8 @@ function render() {
1397014009
for (let i = 0; i < cube_count; i++) {
1397114010
mesh = meshes[i];
1397214011

@@ -14114,28 +14153,28 @@ index 4184cb4..f6d36c0 100644
1411414153

1411514154
torusKnot.rotation.x += 0.25 * delta;
1411614155
diff --git a/examples-testing/examples/webgpu_video_panorama.ts b/examples-testing/examples/webgpu_video_panorama.ts
14117-
index 527cc17..eb03f96 100644
14156+
index c6e051f..dca0db3 100644
1411814157
--- a/examples-testing/examples/webgpu_video_panorama.ts
1411914158
+++ b/examples-testing/examples/webgpu_video_panorama.ts
14120-
@@ -3,7 +3,7 @@ import * as THREE from 'three';
14121-
import WebGPU from 'three/addons/capabilities/WebGPU.js';
14159+
@@ -2,7 +2,7 @@ import * as THREE from 'three';
14160+
1412214161
import WebGPURenderer from 'three/addons/renderers/webgpu/WebGPURenderer.js';
1412314162

1412414163
-let camera, scene, renderer;
1412514164
+let camera: THREE.PerspectiveCamera, scene: THREE.Scene, renderer: WebGPURenderer;
1412614165

1412714166
let isUserInteracting = false,
1412814167
lon = 0,
14129-
@@ -26,7 +26,7 @@ function init() {
14130-
throw new Error('No WebGPU support');
14131-
}
14168+
@@ -19,7 +19,7 @@ const distance = 0.5;
14169+
init();
1413214170

14171+
function init() {
1413314172
- const container = document.getElementById('container');
1413414173
+ const container = document.getElementById('container')!;
1413514174

1413614175
camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.25, 10);
1413714176

14138-
@@ -36,7 +36,7 @@ function init() {
14177+
@@ -29,7 +29,7 @@ function init() {
1413914178
// invert the geometry on the x-axis so that all of the faces point inward
1414014179
geometry.scale(-1, 1, 1);
1414114180

@@ -14144,7 +14183,7 @@ index 527cc17..eb03f96 100644
1414414183
video.play();
1414514184

1414614185
const texture = new THREE.VideoTexture(video);
14147-
@@ -68,7 +68,7 @@ function onWindowResize() {
14186+
@@ -61,7 +61,7 @@ function onWindowResize() {
1414814187
renderer.setSize(window.innerWidth, window.innerHeight);
1414914188
}
1415014189

@@ -14153,7 +14192,7 @@ index 527cc17..eb03f96 100644
1415314192
isUserInteracting = true;
1415414193

1415514194
onPointerDownPointerX = event.clientX;
14156-
@@ -78,7 +78,7 @@ function onPointerDown(event) {
14195+
@@ -71,7 +71,7 @@ function onPointerDown(event) {
1415714196
onPointerDownLat = lat;
1415814197
}
1415914198

examples-testing/index.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -361,6 +361,7 @@ const files = {
361361
// 'webgpu_occlusion',
362362
// 'webgpu_particles',
363363
// 'webgpu_portal',
364+
// 'webgpu_reflection',
364365
// 'webgpu_rtt',
365366
// 'webgpu_sandbox',
366367
// 'webgpu_shadertoy',
@@ -374,7 +375,9 @@ const files = {
374375
// 'webgpu_tsl_transpiler',
375376
'webgpu_video_panorama',
376377
'webgpu_postprocessing_afterimage',
378+
// 'webgpu_mirror',
377379
// 'webgpu_multisampled_renderbuffers',
380+
'webgpu_materials_texture_anisotropy',
378381
],
379382
webaudio: ['webaudio_orientation', 'webaudio_sandbox', 'webaudio_timing', 'webaudio_visualizer'],
380383
webxr: [

three.js

Submodule three.js updated 38 files

types/three/examples/jsm/nodes/Nodes.d.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -179,6 +179,7 @@ export {
179179
triplanarTextures,
180180
triplanarTexture,
181181
} from './utils/TriplanarTexturesNode.js';
182+
export { default as ReflectorNode, reflector, ReflectorNodeParameters } from './utils/ReflectorNode.js';
182183

183184
// shader node
184185
export * from './shadernode/ShaderNode.js';
@@ -322,6 +323,7 @@ export {
322323
depthPixel,
323324
ViewportDepthNodeScope,
324325
} from './display/ViewportDepthNode.js';
326+
export { default as GaussianBlurNode, gaussianBlur } from './display/GaussianBlurNode.js';
325327
export { default as AfterImageNode, afterImage } from './display/AfterImageNode.js';
326328

327329
export { default as PassNode, pass, depthPass, PassNodeScope } from './display/PassNode.js';

types/three/examples/jsm/nodes/accessors/CubeTextureNode.d.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@ import { NodeRepresentation, ShaderNodeObject } from '../shadernode/ShaderNode.j
55

66
export default class CubeTextureNode extends TextureNode {
77
isCubeTextureNode: boolean;
8-
uvNode: Node | null;
9-
levelNode: Node | null;
8+
uvNode: ShaderNodeObject<Node> | null;
9+
levelNode: ShaderNodeObject<Node> | null;
1010

1111
constructor(value: CubeTexture, uvNode?: Node | null, levelNode?: Node | null);
1212

types/three/examples/jsm/nodes/accessors/TextureNode.d.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,10 @@ import { NodeRepresentation, ShaderNodeObject } from '../shadernode/ShaderNode.j
66
export default class TextureNode extends UniformNode<Texture> {
77
isTextureNode: true;
88

9-
uvNode: Node | null;
10-
levelNode: Node | null;
9+
uvNode: ShaderNodeObject<Node> | null;
10+
levelNode: ShaderNodeObject<Node> | null;
1111

12-
constructor(value: Texture, uvNode?: Node, levelNode?: Node | null);
12+
constructor(value: Texture, uvNode?: ShaderNodeObject<Node>, levelNode?: ShaderNodeObject<Node> | null);
1313

1414
getDefaultUV(): Node;
1515

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import { Vector2 } from '../../../../src/Three.js';
2+
import TempNode from '../core/TempNode.js';
3+
import TextureNode from '../accessors/TextureNode.js';
4+
import Node from '../core/Node.js';
5+
import { NodeRepresentation, ShaderNodeObject } from '../shadernode/ShaderNode.js';
6+
7+
export default class GaussianBlurNode extends TempNode {
8+
textureNode: TextureNode;
9+
sigma: number;
10+
11+
directionNode: Node;
12+
13+
resolution: Vector2;
14+
15+
constructor(textureNode: TextureNode, sigma?: number);
16+
17+
setSize(width: number, height: number): void;
18+
}
19+
20+
export const gaussianBlur: (node: NodeRepresentation, sigma?: number) => ShaderNodeObject<GaussianBlurNode>;
21+
22+
declare module '../shadernode/ShaderNode.js' {
23+
interface NodeElements {
24+
gaussianBlur: typeof gaussianBlur;
25+
}
26+
}

types/three/examples/jsm/nodes/display/PassNode.d.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { Camera, RenderTarget, Scene, Texture } from '../../../../src/Three.js';
22
import { ShaderNodeObject } from '../shadernode/ShaderNode.js';
33
import TempNode from '../core/TempNode.js';
44
import TextureNode from '../accessors/TextureNode.js';
5+
import Node from '../core/Node.js';
56

67
declare class PassTextureNode extends TextureNode {
78
passNode: PassNode;
@@ -24,7 +25,7 @@ export default class PassNode extends TempNode {
2425

2526
getTextureDepthNode(): ShaderNodeObject<PassTextureNode>;
2627

27-
getDepthNode(): Node;
28+
getDepthNode(): ShaderNodeObject<Node>;
2829

2930
setSize(width: number, height: number): void;
3031

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import { Camera, Object3D, RenderTarget } from '../../../../src/Three.js';
2+
import TextureNode from '../accessors/TextureNode.js';
3+
import { ShaderNodeObject } from '../shadernode/ShaderNode.js';
4+
5+
export interface ReflectorNodeParameters {
6+
target?: Object3D | undefined;
7+
resolution?: number | undefined;
8+
generateMipmaps?: boolean | undefined;
9+
bounces?: boolean | undefined;
10+
}
11+
12+
export default class ReflectorNode extends TextureNode {
13+
target: Object3D;
14+
resolution: number;
15+
generateMipmaps: boolean;
16+
bounces: boolean;
17+
18+
virtualCameras: WeakMap<Camera, Camera>;
19+
renderTargets: WeakMap<Camera, RenderTarget>;
20+
21+
constructor(parameters?: ReflectorNodeParameters);
22+
23+
getTextureNode(): TextureNode;
24+
25+
getVirtualCamera(camera: Camera): Camera;
26+
27+
getRenderTarget(camera: Camera): RenderTarget;
28+
}
29+
30+
export const reflector: (parameters?: ReflectorNodeParameters) => ShaderNodeObject<ReflectorNode>;

types/three/examples/jsm/renderers/common/Renderer.d.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,12 @@ export default class Renderer {
103103

104104
renderAsync(scene: Scene, camera: Camera): Promise<void>;
105105

106+
getMaxAnisotropy(): number;
107+
108+
getActiveCubeFace(): number;
109+
110+
getActiveMipmapLevel(): number;
111+
106112
setAnimationLoop(callback: ((time: DOMHighResTimeStamp) => void) | null): Promise<void>;
107113

108114
/**

0 commit comments

Comments
 (0)