three.ez icon indicating copy to clipboard operation
three.ez copied to clipboard

Troubleshooting InstancedMesh2 in R3F: culling issues / manual instance creation

Open raptyk opened this issue 7 months ago • 4 comments

I am trying to use component InstancedMesh2 in my R3F based project. I am manually creating instances and adding to the scene. Before rendering I call updateCulling however nothing happens, i.e. the number of rendered objects remains the same despite, for example, a different camera placement. What am I doing wrong ? Can I use InstancedMesh2 in this way (e.g. without initializing the “main” object from the library) ?

chrome_rwGQt6rrN5

const GridPureJSIM2: React.FC<GridProps> = ({ grid, size = 200 }) => {
    const { scene, camera } = useThree();
    const gridHalfSize = size / 2;
    const countX = grid.length;
    const countY = grid[0].length;

    const visibleSquares = useMemo(() => {
        const squares = [];
        for (let x = 0; x < countX; x++) {
            for (let y = 0; y < countY; y++) {
                if (grid[x][y].visible) {
                    squares.push([x - gridHalfSize, y - gridHalfSize]);
                }
            }
        }
        return squares;
    }, []);

    const geometry = new THREE.BoxGeometry(1, 1, 0.1);
    const material = new THREE.MeshBasicMaterial({ color: 'darkblue' });


// MAIN PART :

    const trees = new InstancedMesh2(geometry, material, visibleSquares.length, {
        behaviour: CullingStatic,
        onInstanceCreation: (obj, i) => {
            // const [x, y, z] = visibleSquares[i];
            // obj.applyMatrix4(new THREE.Matrix4().makeRotationX(Math.PI / 2).setPosition(x + 0.5, 0.01, y + 0.5));
        }
    });

    React.useEffect(() => {
        for (let i = 0; i < visibleSquares.length; i++) {
            const [x, y, z] = visibleSquares[i];
            trees.setMatrixAt(i, new THREE.Matrix4().makeRotationX(Math.PI / 2).setPosition(x + 0.5, 0.01, y + 0.5));
        }

        trees.updateMatrix();
        camera.updateMatrixWorld(true);
        scene.add(trees);

        return () => {
            scene.remove(trees);
            trees.dispose();
            geometry.dispose();
            material.dispose();
        };
    }, [visibleSquares, scene]);

    useFrame(() => {
        trees.updateCulling(camera);
    }, -1); //before render**

    return null;
};

export default GridPureJSIM2;

raptyk avatar Jul 30 '24 21:07 raptyk