我试图更新一个统一的vec2当鼠标移动,但我得到一个错误:类型错误:未能在“WebGL2RenderingContext”上执行“统一2fv”:重载解析失败。
为此我设计了一套裁判制服
const uniformRef = useRef({
uAlpha: 0,
uOffset: { x: 0.0, y: 0.0 },
uTexture: imageTexture,
});
然后我创建了一个useEffect来监听"mousemove"事件
useEffect(() => {
document.addEventListener("mousemove", onMouseMove);
return () => document.removeEventListener("mousemove", onMouseMove);
}, [onMouseMove]);
最后我创建了对"mousemove"的函数调用
const onMouseMove = useCallback((e: MouseEvent) => {
if (!planeRef.current || planeRef.current === undefined) return;
// mouse coordinate
let x = (e.clientX / window.innerWidth) * 2 - 1;
let y = -(e.clientY / window.innerHeight) * 2 + 1;
const position = new THREE.Vector3(x, y, 0);
// change position of the mesh
gsap.to(planeRef.current?.position, {
duration: 1,
x,
y,
ease: Power4.easeOut,
onUpdate: () => onPositionUpdate(position),
});
}, []);
// update the offset
const onPositionUpdate = (position: THREE.Vector3) => {
if (planeRef.current) {
let offset = planeRef.current.position
.clone()
.sub(position)
.multiplyScalar(-0.25);
gsap.to(uniformRef.current, {
uOffset: { x: offset.x, y: offset.y },
duration: 1,
ease: Power4.easeOut,
});
}
};
这是着色器的初始化
const ColorShiftMaterial = shaderMaterial(
{
uTexture: new THREE.Texture(),
uOffset: new THREE.Vector2(0.0, 0.0),
uAlpha: 0,
},
...)
如果你能在这方面帮助我或者只是给点提示,这会帮我很大的忙!谢谢
我尝试了很多方法,但是每次我尝试新的方法,我仍然会得到错误,我想这可能是因为我给了uOffset一个vec3,所以我换了一个vec2,但是即使这样我仍然会得到错误。
1条答案
按热度按时间kq4fsx7k1#
首先,你应该使用react-three纤维处理3JS和React。
按照命名约定,您应该将制服命名为u_mouse(带下划线)。
在three fiber中,有一个onPointerMove,您可以使用它来获取鼠标移动。
例如:
若要将值传递到着色器,需要具有制服。
你可以使用useEffect来获取屏幕大小的值,并在你的分辨率统一中使用这些值。然后你可以在你的着色器中使用这些值来计算鼠标的移动,而不管屏幕大小如何。
我不知道你是如何编写着色器的,但是你可以为鼠标创建一个vec2,为分辨率创建一个vec2,并执行如下操作
这完全取决于你想发生什么,你想它看起来如何。