@neurodyn/react-room-viewer 0.0.21 → 0.0.23
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/dist/index.js +159 -89
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -19,7 +19,7 @@ import { Swiper, SwiperSlide } from "swiper/react";
|
|
|
19
19
|
import { TransformComponent, TransformWrapper } from "react-zoom-pan-pinch";
|
|
20
20
|
import { Clone, DragControls, Environment, Html, useGLTF, useProgress, useTexture } from "@react-three/drei";
|
|
21
21
|
import { Canvas, useFrame, useLoader, useThree } from "@react-three/fiber";
|
|
22
|
-
import { ACESFilmicToneMapping, Box3, BufferGeometry, CanvasTexture, ClampToEdgeWrapping, Color, DataTexture, DoubleSide, Float32BufferAttribute, LinearFilter, LoadingManager, MathUtils, Matrix4, Mesh, MeshBasicMaterial,
|
|
22
|
+
import { ACESFilmicToneMapping, Box3, BufferGeometry, CanvasTexture, ClampToEdgeWrapping, Color, DataTexture, DoubleSide, Float32BufferAttribute, LinearFilter, LoadingManager, MathUtils, Matrix4, Mesh, MeshBasicMaterial, PerspectiveCamera, Plane, Quaternion, RGBAFormat, RedFormat, SRGBColorSpace, Scene, TextureLoader, Vector2, Vector3, WebGLRenderTarget } from "three";
|
|
23
23
|
import { MeshoptDecoder } from "three/examples/jsm/libs/meshopt_decoder.module.js";
|
|
24
24
|
import { DRACOLoader } from "three/examples/jsm/loaders/DRACOLoader.js";
|
|
25
25
|
import { GLTFLoader } from "three/examples/jsm/loaders/GLTFLoader.js";
|
|
@@ -15345,6 +15345,106 @@ function useFlooringRotation(enabled, isPointerOnSurface, roomId) {
|
|
|
15345
15345
|
setRotation
|
|
15346
15346
|
]);
|
|
15347
15347
|
}
|
|
15348
|
+
const MASK_EDGE_START = 0.4;
|
|
15349
|
+
const MASK_EDGE_END = 0.7;
|
|
15350
|
+
const MASK_DISCARD_ALPHA = 0.001;
|
|
15351
|
+
const UPSCALE = 2;
|
|
15352
|
+
const BLUR_SIGMA = 3;
|
|
15353
|
+
const BLUR_RADIUS = 9;
|
|
15354
|
+
const plane_visibility_mask_kernel = new Float32Array(2 * BLUR_RADIUS + 1);
|
|
15355
|
+
let kernelSum = 0;
|
|
15356
|
+
for(let offset = -BLUR_RADIUS; offset <= BLUR_RADIUS; offset++){
|
|
15357
|
+
const weight = Math.exp(-offset * offset / (2 * BLUR_SIGMA * BLUR_SIGMA));
|
|
15358
|
+
plane_visibility_mask_kernel[offset + BLUR_RADIUS] = weight;
|
|
15359
|
+
kernelSum += weight;
|
|
15360
|
+
}
|
|
15361
|
+
for(let index = 0; index < plane_visibility_mask_kernel.length; index++)plane_visibility_mask_kernel[index] /= kernelSum;
|
|
15362
|
+
function plane_visibility_mask_clamp(value1, max) {
|
|
15363
|
+
return Math.max(0, Math.min(max, value1));
|
|
15364
|
+
}
|
|
15365
|
+
function createPlaneVisibilityMask(map, planeId) {
|
|
15366
|
+
const width = map.width * UPSCALE;
|
|
15367
|
+
const height = map.height * UPSCALE;
|
|
15368
|
+
const upscaled = new Float32Array(width * height);
|
|
15369
|
+
const horizontal = new Float32Array(width * height);
|
|
15370
|
+
const data = new Uint8Array(width * height);
|
|
15371
|
+
let minX = map.width;
|
|
15372
|
+
let minY = map.height;
|
|
15373
|
+
let maxX = -1;
|
|
15374
|
+
let maxY = -1;
|
|
15375
|
+
for(let y = 0; y < map.height; y++)for(let x = 0; x < map.width; x++)if (map.data[y * map.width + x] === planeId) {
|
|
15376
|
+
minX = Math.min(minX, x);
|
|
15377
|
+
minY = Math.min(minY, y);
|
|
15378
|
+
maxX = Math.max(maxX, x);
|
|
15379
|
+
maxY = Math.max(maxY, y);
|
|
15380
|
+
}
|
|
15381
|
+
const margin = BLUR_RADIUS + UPSCALE;
|
|
15382
|
+
const startX = maxX < 0 ? width : Math.max(0, minX * UPSCALE - margin);
|
|
15383
|
+
const startY = maxY < 0 ? height : Math.max(0, minY * UPSCALE - margin);
|
|
15384
|
+
const endX = maxX < 0 ? -1 : Math.min(width - 1, (maxX + 1) * UPSCALE + margin);
|
|
15385
|
+
const endY = maxY < 0 ? -1 : Math.min(height - 1, (maxY + 1) * UPSCALE + margin);
|
|
15386
|
+
for(let y = startY; y <= endY; y++){
|
|
15387
|
+
const sourceY = (y + 0.5) / UPSCALE - 0.5;
|
|
15388
|
+
const sourceY0 = Math.floor(sourceY);
|
|
15389
|
+
const y0 = plane_visibility_mask_clamp(sourceY0, map.height - 1);
|
|
15390
|
+
const y1 = plane_visibility_mask_clamp(sourceY0 + 1, map.height - 1);
|
|
15391
|
+
const fy = sourceY - sourceY0;
|
|
15392
|
+
for(let x = startX; x <= endX; x++){
|
|
15393
|
+
const sourceX = (x + 0.5) / UPSCALE - 0.5;
|
|
15394
|
+
const sourceX0 = Math.floor(sourceX);
|
|
15395
|
+
const x0 = plane_visibility_mask_clamp(sourceX0, map.width - 1);
|
|
15396
|
+
const x1 = plane_visibility_mask_clamp(sourceX0 + 1, map.width - 1);
|
|
15397
|
+
const fx = sourceX - sourceX0;
|
|
15398
|
+
const top = (map.data[y0 * map.width + x0] === planeId ? 1 - fx : 0) + (map.data[y0 * map.width + x1] === planeId ? fx : 0);
|
|
15399
|
+
const bottom = (map.data[y1 * map.width + x0] === planeId ? 1 - fx : 0) + (map.data[y1 * map.width + x1] === planeId ? fx : 0);
|
|
15400
|
+
upscaled[y * width + x] = top * (1 - fy) + bottom * fy;
|
|
15401
|
+
}
|
|
15402
|
+
}
|
|
15403
|
+
for(let y = startY; y <= endY; y++)for(let x = startX; x <= endX; x++){
|
|
15404
|
+
let value1 = 0;
|
|
15405
|
+
for(let offset = -BLUR_RADIUS; offset <= BLUR_RADIUS; offset++)value1 += upscaled[y * width + plane_visibility_mask_clamp(x + offset, width - 1)] * plane_visibility_mask_kernel[offset + BLUR_RADIUS];
|
|
15406
|
+
horizontal[y * width + x] = value1;
|
|
15407
|
+
}
|
|
15408
|
+
for(let y = startY; y <= endY; y++)for(let x = startX; x <= endX; x++){
|
|
15409
|
+
let value1 = 0;
|
|
15410
|
+
for(let offset = -BLUR_RADIUS; offset <= BLUR_RADIUS; offset++)value1 += horizontal[plane_visibility_mask_clamp(y + offset, height - 1) * width + x] * plane_visibility_mask_kernel[offset + BLUR_RADIUS];
|
|
15411
|
+
data[y * width + x] = Math.round(255 * value1);
|
|
15412
|
+
}
|
|
15413
|
+
const texture = new DataTexture(data, width, height, RedFormat);
|
|
15414
|
+
texture.minFilter = LinearFilter;
|
|
15415
|
+
texture.magFilter = LinearFilter;
|
|
15416
|
+
texture.wrapS = ClampToEdgeWrapping;
|
|
15417
|
+
texture.wrapT = ClampToEdgeWrapping;
|
|
15418
|
+
texture.generateMipmaps = false;
|
|
15419
|
+
texture.unpackAlignment = 1;
|
|
15420
|
+
texture.needsUpdate = true;
|
|
15421
|
+
return {
|
|
15422
|
+
data,
|
|
15423
|
+
width,
|
|
15424
|
+
height,
|
|
15425
|
+
texture
|
|
15426
|
+
};
|
|
15427
|
+
}
|
|
15428
|
+
function samplePlaneVisibilityMask(mask, u, v) {
|
|
15429
|
+
if (u < 0 || u > 1 || v < 0 || v > 1) return 0;
|
|
15430
|
+
const x = u * mask.width - 0.5;
|
|
15431
|
+
const y = v * mask.height - 0.5;
|
|
15432
|
+
const sourceX0 = Math.floor(x);
|
|
15433
|
+
const sourceY0 = Math.floor(y);
|
|
15434
|
+
const x0 = plane_visibility_mask_clamp(sourceX0, mask.width - 1);
|
|
15435
|
+
const y0 = plane_visibility_mask_clamp(sourceY0, mask.height - 1);
|
|
15436
|
+
const x1 = plane_visibility_mask_clamp(sourceX0 + 1, mask.width - 1);
|
|
15437
|
+
const y1 = plane_visibility_mask_clamp(sourceY0 + 1, mask.height - 1);
|
|
15438
|
+
const fx = x - Math.floor(x);
|
|
15439
|
+
const fy = y - Math.floor(y);
|
|
15440
|
+
const top = mask.data[y0 * mask.width + x0] * (1 - fx) + mask.data[y0 * mask.width + x1] * fx;
|
|
15441
|
+
const bottom = mask.data[y1 * mask.width + x0] * (1 - fx) + mask.data[y1 * mask.width + x1] * fx;
|
|
15442
|
+
return (top * (1 - fy) + bottom * fy) / 255;
|
|
15443
|
+
}
|
|
15444
|
+
function planeVisibilityAlpha(value1) {
|
|
15445
|
+
const t = plane_visibility_mask_clamp((value1 - MASK_EDGE_START) / (MASK_EDGE_END - MASK_EDGE_START), 1);
|
|
15446
|
+
return t * t * (3 - 2 * t);
|
|
15447
|
+
}
|
|
15348
15448
|
new Set();
|
|
15349
15449
|
function warnOnce(key, message) {}
|
|
15350
15450
|
const RESOURCE_BASE_NORMAL = new Vector3(0, 0, 1);
|
|
@@ -15483,11 +15583,12 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15483
15583
|
const placementKey = `${roomId}:${[
|
|
15484
15584
|
...surfaces
|
|
15485
15585
|
].sort().join(',')}`;
|
|
15486
|
-
const
|
|
15487
|
-
value:
|
|
15586
|
+
const activeMaskTextureUniform = (0, __rspack_external_react.useMemo)(()=>({
|
|
15587
|
+
value: null
|
|
15488
15588
|
}), []);
|
|
15489
15589
|
const [placementState, dispatchPlacementState] = (0, __rspack_external_react.useReducer)(reduceRoomScenePlacementState, placementKey, createInitialRoomScenePlacementState);
|
|
15490
15590
|
const activePlaneIdRef = (0, __rspack_external_react.useRef)(null);
|
|
15591
|
+
const planeMasksRef = (0, __rspack_external_react.useRef)(new Map());
|
|
15491
15592
|
const planeMapRef = (0, __rspack_external_react.useRef)(new Map());
|
|
15492
15593
|
const pointerDragOffsetRef = (0, __rspack_external_react.useRef)(null);
|
|
15493
15594
|
const isCurrentPlacementKey = placementState.placementKey === placementKey;
|
|
@@ -15520,7 +15621,16 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15520
15621
|
placementKey
|
|
15521
15622
|
});
|
|
15522
15623
|
decodePlaneIdsDataPng(scene.planeIds.dataPng, scene.planeIds.width, scene.planeIds.height).then((map)=>{
|
|
15523
|
-
if (
|
|
15624
|
+
if (isCancelled) return;
|
|
15625
|
+
const masks = new Map();
|
|
15626
|
+
try {
|
|
15627
|
+
for (const plane of scene.planes)if (surfaces.includes(plane.kind) && plane.id > 0) masks.set(plane.id, createPlaneVisibilityMask(map, plane.id));
|
|
15628
|
+
} catch (error) {
|
|
15629
|
+
masks.forEach((mask)=>mask.texture.dispose());
|
|
15630
|
+
throw error;
|
|
15631
|
+
}
|
|
15632
|
+
planeMasksRef.current = masks;
|
|
15633
|
+
dispatchPlacementState({
|
|
15524
15634
|
type: 'set-plane-id-map',
|
|
15525
15635
|
placementKey,
|
|
15526
15636
|
planeIdMap: map
|
|
@@ -15534,10 +15644,16 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15534
15644
|
});
|
|
15535
15645
|
return ()=>{
|
|
15536
15646
|
isCancelled = true;
|
|
15647
|
+
planeMasksRef.current.forEach((mask)=>mask.texture.dispose());
|
|
15648
|
+
planeMasksRef.current = new Map();
|
|
15649
|
+
activeMaskTextureUniform.value = null;
|
|
15537
15650
|
};
|
|
15538
15651
|
}, [
|
|
15652
|
+
activeMaskTextureUniform,
|
|
15539
15653
|
placementKey,
|
|
15540
|
-
scene.planeIds
|
|
15654
|
+
scene.planeIds,
|
|
15655
|
+
scene.planes,
|
|
15656
|
+
surfaces
|
|
15541
15657
|
]);
|
|
15542
15658
|
(0, __rspack_external_react.useEffect)(()=>{
|
|
15543
15659
|
dispatchPlacementState({
|
|
@@ -15545,17 +15661,17 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15545
15661
|
placementKey
|
|
15546
15662
|
});
|
|
15547
15663
|
activePlaneIdRef.current = null;
|
|
15548
|
-
|
|
15664
|
+
activeMaskTextureUniform.value = null;
|
|
15549
15665
|
pointerDragOffsetRef.current = null;
|
|
15550
15666
|
}, [
|
|
15551
|
-
|
|
15667
|
+
activeMaskTextureUniform,
|
|
15552
15668
|
placementKey
|
|
15553
15669
|
]);
|
|
15554
15670
|
const updatePoseFromPlane = (0, __rspack_external_react.useCallback)((mesh, point, pointerDragOffset = null)=>{
|
|
15555
15671
|
const pointerPose = createPoseFromPlane(mesh, point, camera);
|
|
15556
15672
|
const pose = pointerDragOffset ? applyPointerDragOffset(pointerPose, pointerDragOffset) : pointerPose;
|
|
15557
15673
|
activePlaneIdRef.current = pose.activePlaneId;
|
|
15558
|
-
|
|
15674
|
+
activeMaskTextureUniform.value = planeMasksRef.current.get(pose.activePlaneId)?.texture ?? null;
|
|
15559
15675
|
dispatchPlacementState({
|
|
15560
15676
|
type: 'set-resource-pose',
|
|
15561
15677
|
placementKey,
|
|
@@ -15563,7 +15679,7 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15563
15679
|
});
|
|
15564
15680
|
invalidate();
|
|
15565
15681
|
}, [
|
|
15566
|
-
|
|
15682
|
+
activeMaskTextureUniform,
|
|
15567
15683
|
camera,
|
|
15568
15684
|
invalidate,
|
|
15569
15685
|
placementKey
|
|
@@ -15594,7 +15710,7 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15594
15710
|
});
|
|
15595
15711
|
if (!pose) return;
|
|
15596
15712
|
activePlaneIdRef.current = pose.activePlaneId;
|
|
15597
|
-
|
|
15713
|
+
activeMaskTextureUniform.value = planeMasksRef.current.get(pose.activePlaneId)?.texture ?? null;
|
|
15598
15714
|
dispatchPlacementState({
|
|
15599
15715
|
type: 'set-resource-pose',
|
|
15600
15716
|
placementKey,
|
|
@@ -15602,7 +15718,7 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15602
15718
|
});
|
|
15603
15719
|
invalidate();
|
|
15604
15720
|
}, [
|
|
15605
|
-
|
|
15721
|
+
activeMaskTextureUniform,
|
|
15606
15722
|
allowedPlanes,
|
|
15607
15723
|
camera,
|
|
15608
15724
|
invalidate,
|
|
@@ -15636,19 +15752,14 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15636
15752
|
pointerDragOffsetRef.current = null;
|
|
15637
15753
|
}, []);
|
|
15638
15754
|
const isPointVisible = (0, __rspack_external_react.useCallback)((point)=>{
|
|
15639
|
-
|
|
15755
|
+
const activePlaneId = activePlaneIdRef.current;
|
|
15756
|
+
const mask = null === activePlaneId ? null : planeMasksRef.current.get(activePlaneId);
|
|
15757
|
+
if (!mask) return false;
|
|
15640
15758
|
const projected = point.clone().project(camera);
|
|
15641
|
-
const
|
|
15642
|
-
|
|
15643
|
-
for(let dy = -2; dy <= 2; dy++)for(let dx = -2; dx <= 2; dx++){
|
|
15644
|
-
const px = Math.max(0, Math.min(planeIdMap.width - 1, x + dx));
|
|
15645
|
-
const py = Math.max(0, Math.min(planeIdMap.height - 1, y + dy));
|
|
15646
|
-
if (planeIdMap.data[py * planeIdMap.width + px] === activePlaneIdRef.current) return true;
|
|
15647
|
-
}
|
|
15648
|
-
return false;
|
|
15759
|
+
const value1 = samplePlaneVisibilityMask(mask, (projected.x + 1) * 0.5, (1 - projected.y) * 0.5);
|
|
15760
|
+
return planeVisibilityAlpha(value1) > MASK_DISCARD_ALPHA;
|
|
15649
15761
|
}, [
|
|
15650
|
-
camera
|
|
15651
|
-
planeIdMap
|
|
15762
|
+
camera
|
|
15652
15763
|
]);
|
|
15653
15764
|
const isPointerOnSurface = (0, __rspack_external_react.useCallback)((point)=>{
|
|
15654
15765
|
const id = planeIdMap ? findPlaneIdAtPointer(point, planeIdMap) : null;
|
|
@@ -15659,7 +15770,7 @@ function useRoomScenePlacement({ camera, invalidate, pointer, raycaster, roomId,
|
|
|
15659
15770
|
]);
|
|
15660
15771
|
return {
|
|
15661
15772
|
isPointerOnSurface,
|
|
15662
|
-
|
|
15773
|
+
activeMaskTextureUniform,
|
|
15663
15774
|
isPointVisible,
|
|
15664
15775
|
failure,
|
|
15665
15776
|
handleDrag,
|
|
@@ -15813,19 +15924,13 @@ function createRoomLightingTexture(planeIds, shading, neutral = 128) {
|
|
|
15813
15924
|
texture.needsUpdate = true;
|
|
15814
15925
|
return texture;
|
|
15815
15926
|
}
|
|
15816
|
-
const CACHE_KEY = 'neurodyn-room-scene-
|
|
15927
|
+
const CACHE_KEY = 'neurodyn-room-scene-v5';
|
|
15817
15928
|
const GLSL_DEFINE = 'NEURODYN_ROOM_SCENE_PATCH';
|
|
15818
15929
|
function patchShader(shader, patch, shading) {
|
|
15819
|
-
shader.uniforms.
|
|
15820
|
-
value: patch.planeIdsTexture
|
|
15821
|
-
};
|
|
15930
|
+
shader.uniforms.uMask = patch.activeMaskTextureUniform;
|
|
15822
15931
|
shader.uniforms.uRoomLighting = {
|
|
15823
15932
|
value: patch.lightingTexture
|
|
15824
15933
|
};
|
|
15825
|
-
shader.uniforms.uActiveId = patch.activePlaneIdUniform;
|
|
15826
|
-
shader.uniforms.uPlaneIdsSize = {
|
|
15827
|
-
value: patch.planeIdsSize
|
|
15828
|
-
};
|
|
15829
15934
|
shader.uniforms.uViewport = {
|
|
15830
15935
|
value: patch.viewport
|
|
15831
15936
|
};
|
|
@@ -15833,54 +15938,25 @@ function patchShader(shader, patch, shading) {
|
|
|
15833
15938
|
const inject = `
|
|
15834
15939
|
{
|
|
15835
15940
|
vec2 _neurodynRoomUv = gl_FragCoord.xy / uViewport;
|
|
15836
|
-
float
|
|
15941
|
+
float _neurodynRoomMask = texture2D(uMask, vec2(_neurodynRoomUv.x, 1.0 - _neurodynRoomUv.y)).r;
|
|
15942
|
+
float _neurodynRoomCoverage = smoothstep(${MASK_EDGE_START}, ${MASK_EDGE_END}, _neurodynRoomMask);
|
|
15837
15943
|
|
|
15838
|
-
if (_neurodynRoomCoverage <=
|
|
15944
|
+
if (_neurodynRoomCoverage <= ${MASK_DISCARD_ALPHA}) discard;
|
|
15839
15945
|
|
|
15840
15946
|
${shading ? `
|
|
15841
|
-
float _neurodynRoomGain = texture2D(uRoomLighting, vec2(_neurodynRoomUv.x, 1.0 - _neurodynRoomUv.y)).r * (255.0 / 128.0);
|
|
15947
|
+
float _neurodynRoomGain = min(texture2D(uRoomLighting, vec2(_neurodynRoomUv.x, 1.0 - _neurodynRoomUv.y)).r * (255.0 / 128.0), ${patch.maxRoomGain.toFixed(3)});
|
|
15842
15948
|
outgoingLight = (outgoingLight - ${emissive}) * _neurodynRoomGain + ${emissive};
|
|
15843
15949
|
` : ''}
|
|
15844
|
-
diffuseColor.a *=
|
|
15950
|
+
diffuseColor.a *= _neurodynRoomCoverage;
|
|
15845
15951
|
}
|
|
15846
15952
|
`;
|
|
15847
15953
|
const fragmentWithUniforms = shader.fragmentShader.replace('#include <common>', `
|
|
15848
15954
|
#include <common>
|
|
15849
15955
|
#ifndef ${GLSL_DEFINE}
|
|
15850
15956
|
#define ${GLSL_DEFINE}
|
|
15851
|
-
uniform sampler2D
|
|
15957
|
+
uniform sampler2D uMask;
|
|
15852
15958
|
uniform sampler2D uRoomLighting;
|
|
15853
|
-
uniform float uActiveId;
|
|
15854
|
-
uniform vec2 uPlaneIdsSize;
|
|
15855
15959
|
uniform vec2 uViewport;
|
|
15856
|
-
|
|
15857
|
-
float neurodynRoomScenePlaneMatch(vec2 uv) {
|
|
15858
|
-
float id = floor(texture2D(uPlaneIds, uv).r * 255.0 + 0.5);
|
|
15859
|
-
return 1.0 - step(0.5, abs(id - uActiveId));
|
|
15860
|
-
}
|
|
15861
|
-
|
|
15862
|
-
// uPlaneIds is a low-res nearest-filtered id map, so its edges are blocky.
|
|
15863
|
-
// A single-texel tent filter isn't wide enough to hide that — it just
|
|
15864
|
-
// softens each block's corner, which reads as a staircase. Supersample
|
|
15865
|
-
// a wider neighbourhood (5x5 taps, 2-texel radius) with Gaussian-like
|
|
15866
|
-
// falloff so the boundary is both denser-sampled and properly blurred.
|
|
15867
|
-
float neurodynRoomScenePlaneCoverage(vec2 uv) {
|
|
15868
|
-
vec2 texel = 1.0 / uPlaneIdsSize;
|
|
15869
|
-
float coverage = 0.0;
|
|
15870
|
-
float totalWeight = 0.0;
|
|
15871
|
-
|
|
15872
|
-
for (int y = -2; y <= 2; y++) {
|
|
15873
|
-
for (int x = -2; x <= 2; x++) {
|
|
15874
|
-
vec2 offset = vec2(float(x), float(y));
|
|
15875
|
-
float weight = 1.0 / (1.0 + dot(offset, offset));
|
|
15876
|
-
|
|
15877
|
-
coverage += neurodynRoomScenePlaneMatch(uv + offset * texel) * weight;
|
|
15878
|
-
totalWeight += weight;
|
|
15879
|
-
}
|
|
15880
|
-
}
|
|
15881
|
-
|
|
15882
|
-
return coverage / totalWeight;
|
|
15883
|
-
}
|
|
15884
15960
|
#endif
|
|
15885
15961
|
`);
|
|
15886
15962
|
if (fragmentWithUniforms.includes('#include <output_fragment>')) {
|
|
@@ -15902,7 +15978,7 @@ function patchMaterialWithRoomScene(material, patch, { shading = true } = {}) {
|
|
|
15902
15978
|
previousOnBeforeCompile?.call(material, shader, renderer);
|
|
15903
15979
|
patchShader(shader, patch, shading);
|
|
15904
15980
|
};
|
|
15905
|
-
material.customProgramCacheKey = ()=>`${previousCustomProgramCacheKey()}|${CACHE_KEY}|shading:${shading}`;
|
|
15981
|
+
material.customProgramCacheKey = ()=>`${previousCustomProgramCacheKey()}|${CACHE_KEY}|shading:${shading}|maxRoomGain:${patch.maxRoomGain}`;
|
|
15906
15982
|
material.needsUpdate = true;
|
|
15907
15983
|
return ()=>{
|
|
15908
15984
|
material.onBeforeCompile = previousOnBeforeCompile;
|
|
@@ -17124,6 +17200,7 @@ function RoomPlane({ plane, geometry, setPlaneRef }) {
|
|
|
17124
17200
|
})
|
|
17125
17201
|
});
|
|
17126
17202
|
}
|
|
17203
|
+
const MAX_ROOM_GAIN = 1.1;
|
|
17127
17204
|
function Room() {
|
|
17128
17205
|
const { type } = useRoomViewerMetadata();
|
|
17129
17206
|
const panelGroup = usePanelGroup();
|
|
@@ -17150,10 +17227,6 @@ function Room() {
|
|
|
17150
17227
|
});
|
|
17151
17228
|
useFlooringRotation('rotate-on-floor' === resolveResourceProfile(type).manipulation, scenePlacement.isPointerOnSurface, room.id);
|
|
17152
17229
|
const viewport = (0, __rspack_external_react.useMemo)(()=>new Vector2(1, 1), []);
|
|
17153
|
-
const planeIdsSize = (0, __rspack_external_react.useMemo)(()=>new Vector2(scene.planeIds.width, scene.planeIds.height), [
|
|
17154
|
-
scene.planeIds.height,
|
|
17155
|
-
scene.planeIds.width
|
|
17156
|
-
]);
|
|
17157
17230
|
const lightingTexture = (0, __rspack_external_react.useMemo)(()=>createRoomLightingTexture(planeIdsTexture, shadingTexture, scene.shading?.neutral), [
|
|
17158
17231
|
planeIdsTexture,
|
|
17159
17232
|
shadingTexture,
|
|
@@ -17163,15 +17236,12 @@ function Room() {
|
|
|
17163
17236
|
lightingTexture
|
|
17164
17237
|
]);
|
|
17165
17238
|
const materialPatch = (0, __rspack_external_react.useMemo)(()=>({
|
|
17166
|
-
planeIdsTexture,
|
|
17167
17239
|
lightingTexture,
|
|
17168
|
-
planeIdsSize,
|
|
17169
17240
|
viewport,
|
|
17170
|
-
|
|
17241
|
+
activeMaskTextureUniform: scenePlacement.activeMaskTextureUniform,
|
|
17242
|
+
maxRoomGain: MAX_ROOM_GAIN
|
|
17171
17243
|
}), [
|
|
17172
|
-
scenePlacement.
|
|
17173
|
-
planeIdsSize,
|
|
17174
|
-
planeIdsTexture,
|
|
17244
|
+
scenePlacement.activeMaskTextureUniform,
|
|
17175
17245
|
lightingTexture,
|
|
17176
17246
|
viewport
|
|
17177
17247
|
]);
|
|
@@ -17187,16 +17257,6 @@ function Room() {
|
|
|
17187
17257
|
invalidate,
|
|
17188
17258
|
scene.camera.fovYDeg
|
|
17189
17259
|
]);
|
|
17190
|
-
(0, __rspack_external_react.useLayoutEffect)(()=>{
|
|
17191
|
-
planeIdsTexture.minFilter = NearestFilter;
|
|
17192
|
-
planeIdsTexture.magFilter = NearestFilter;
|
|
17193
|
-
planeIdsTexture.wrapS = ClampToEdgeWrapping;
|
|
17194
|
-
planeIdsTexture.wrapT = ClampToEdgeWrapping;
|
|
17195
|
-
planeIdsTexture.generateMipmaps = false;
|
|
17196
|
-
planeIdsTexture.needsUpdate = true;
|
|
17197
|
-
}, [
|
|
17198
|
-
planeIdsTexture
|
|
17199
|
-
]);
|
|
17200
17260
|
(0, __rspack_external_react.useLayoutEffect)(()=>{
|
|
17201
17261
|
gl.getDrawingBufferSize(viewport);
|
|
17202
17262
|
viewport.set(Math.max(1, viewport.x), Math.max(1, viewport.y));
|
|
@@ -17273,6 +17333,13 @@ const ROOM_VIEWER_CONFIG_QUERY_KEY = [
|
|
|
17273
17333
|
'room-viewer',
|
|
17274
17334
|
'layout-config'
|
|
17275
17335
|
];
|
|
17336
|
+
const HDR_ROTATION = [
|
|
17337
|
+
Math.PI / 2,
|
|
17338
|
+
0,
|
|
17339
|
+
0
|
|
17340
|
+
];
|
|
17341
|
+
const REMOTE_HDR_INTENSITY = 0.5;
|
|
17342
|
+
const FALLBACK_ENVIRONMENT_INTENSITY = 0.9;
|
|
17276
17343
|
function getNeutralHdrUrl(config) {
|
|
17277
17344
|
const url = config?.internal?.links?.find((link)=>link.type === HDR_NEUTRAL_LINK_TYPE)?.url?.trim();
|
|
17278
17345
|
return url || void 0;
|
|
@@ -17289,14 +17356,17 @@ function RemoteNeutralHdrEnvironment() {
|
|
|
17289
17356
|
files: hdrUrl ? [
|
|
17290
17357
|
hdrUrl
|
|
17291
17358
|
] : void 0,
|
|
17292
|
-
preset: hdrUrl ? void 0 : 'warehouse'
|
|
17359
|
+
preset: hdrUrl ? void 0 : 'warehouse',
|
|
17360
|
+
environmentRotation: HDR_ROTATION,
|
|
17361
|
+
environmentIntensity: hdrUrl ? REMOTE_HDR_INTENSITY : FALLBACK_ENVIRONMENT_INTENSITY
|
|
17293
17362
|
});
|
|
17294
17363
|
}
|
|
17295
17364
|
function StaticNeutralHdrEnvironment() {
|
|
17296
17365
|
return /*#__PURE__*/ jsx_runtime_jsx(Environment, {
|
|
17297
17366
|
files: [
|
|
17298
17367
|
HDR_URL
|
|
17299
|
-
]
|
|
17368
|
+
],
|
|
17369
|
+
environmentRotation: HDR_ROTATION
|
|
17300
17370
|
});
|
|
17301
17371
|
}
|
|
17302
17372
|
function RoomEnvironment({ lighting }) {
|