I’ve been going through the web to learn about raycaster, I have a glb model made in blender, I am using a “mousedown” event on the canvas to get the object clicked by the raycaster, But the raycaster itself is not working as intended, I also don’t know what is going wrong, Please help,
This is my main code,
import * as THREE from "./three.js/build/three.module.js";
import { GLTFLoader } from "./three.js/examples/jsm/loaders/GLTFLoader.js";
import { OrbitControls } from "./three.js/examples/jsm/controls/OrbitControls.js";
import { RGBELoader } from "./three.js/examples/jsm/loaders/RGBELoader.js";
var canvas;
var renderer;
var camera;
var scene;
var clock;
var directionalLight;
var orbitControls;
var raycaster
var mouse = { x : 0, y : 0 };
var mainScene;
var mainAnimation;
var mainAnimationMixer;
var animationAction;
var rotateClockwise;
var rotateAntiClockwise;
const animationState = {
RotateForward : "ROTATEFORWARDS",
RotateBackward : "ROTATEBACKWARDS"
}
let animationStateToggle = animationState.RotateForward;
function init(){
// Canvas
canvas = document.querySelector('#threejscanvas');
var animateButton = document.getElementById('animate-button');
animateButton.onclick = function(){
ToggleAnimation();
}
// Renderer
renderer = new THREE.WebGLRenderer({canvas, antialias: true, alpha: true, logarithmicDepthBuffer: true});
renderer.toneMapping = THREE.ACESFilmicToneMapping;
renderer.toneMappingExposure = 1;
renderer.outputEncoding = THREE.sRGBEncoding;
// Scene
scene = new THREE.Scene();
clock = new THREE.Clock();
// HDRI
setupHDRI("three.js/main/hdr/", "christmas_photo_studio_04_1k.hdr");
// Camera
setupCamera();
// Lights
setupLights();
// GLFT Model Import
importGltfModel("three.js/main/glb/NeonCorridor.glb");
raycaster = new THREE.Raycaster();
canvas.addEventListener( 'mousedown',onMouseDown , false );
// Render
renderer.render(scene, camera);
}
function animate(){
requestAnimationFrame(animate);
if (mainAnimationMixer !== undefined ){
mainAnimationMixer.update(clock.getDelta());
}
}
function render(time){
time *= 0.001; // Time in seconds
// Responsive display
if(resizeRendererToDisplaySize(renderer)){
camera.aspect = canvas.clientWidth / canvas.clientHeight;
camera.updateProjectionMatrix();
}
renderer.render(scene, camera);
// Called to start the loop
requestAnimationFrame(render);
}
function resizeRendererToDisplaySize(renderer){
const pixelRatio = window.devicePixelRatio;
const width = canvas.clientWidth * pixelRatio | 0;
const height = canvas.clientHeight * pixelRatio | 0;
const isResized = canvas.width !== width|| canvas.height !== height;
if(isResized){
renderer.setSize(canvas.clientWidth, canvas.clientHeight, false);
}
return isResized;
}
function setupLights(){
// Directional Light
const color = 0xffffff;
const intensity = 1;
directionalLight = new THREE.DirectionalLight(color, intensity);
directionalLight.position.set(-1, 2, 4);
scene.add(directionalLight);
}
function setupCamera() {
const fov = 60;
const aspect = 2; // the canvas default
const near = 0.1;
const far = 100;
camera = new THREE.PerspectiveCamera(fov, aspect, near, far);
camera.position.z = 2;
orbitControls = new OrbitControls(camera, canvas);
orbitControls.target.set(0, 0, 0);
orbitControls.update();
}
function setupHDRI(path, name){
new RGBELoader()
.setDataType(THREE.UnsignedByteType)
.setPath(path)
.load(name, function (texture) {
const envMap = pmremGenerator.fromEquirectangular(texture).texture;
//scene.background = envMap;
scene.environment = envMap;
texture.dispose();
pmremGenerator.dispose();
});
const pmremGenerator = new THREE.PMREMGenerator(renderer);
pmremGenerator.compileEquirectangularShader();
}
function importGltfModel(path){
const gltfLoader = new GLTFLoader();
gltfLoader.load(path, (loadedModel) => {
mainScene = loadedModel.scene;
mainScene.traverse(meshes => {
if (meshes.isMesh) {
meshes.castShadow = true;
meshes.receiveShadow = true;
}
});
mainAnimationMixer = new THREE.AnimationMixer(mainScene);
mainAnimation = loadedModel.animations;
rotateClockwise = THREE.AnimationClip.findByName(mainAnimation, "NeonRotation");
rotateAntiClockwise = THREE.AnimationClip.findByName(mainAnimation, "Neon_Rotate_Reverse");
scene.add(mainScene);
});
}
function PlayAnimation(clipName, timeScale){
animationAction = mainAnimationMixer.clipAction(clipName);
animationAction.reset();
animationAction.setLoop(THREE.LoopOnce);
animationAction.timeScale = timeScale;
animationAction.play();
animate();
}
function ToggleAnimation(){
if(animationStateToggle == animationState.RotateBackward){
animationStateToggle = animationState.RotateForward;
PlayAnimation(rotateClockwise, 1);
}
else{
animationStateToggle = animationState.RotateBackward;
PlayAnimation(rotateAntiClockwise, 1);
}
}
function onMouseDown() {
//1. sets the mouse position with a coordinate system where the center
// of the screen is the origin
mouse.x = ( event.clientX / renderer.domElement.innerWidth ) * 2 - 1;
mouse.y = - ( event.clientY / renderer.domElement.innerHeight ) * 2 + 1;
//2. set the picking ray from the camera position and mouse coordinates
raycaster.setFromCamera( mouse, camera );
//3. compute intersections
var intersects = raycaster.intersectObjects( scene.children );
if(intersects.length > 0){
for ( var i = 0; i < intersects.length; i++ ) {
console.log( intersects[ i ] );
intersects[0].object.material.color.setHex("0x2f2f2f");
/*
An intersection has the following properties :
- object : intersected object (THREE.Mesh)
- distance : distance from camera to intersection (number)
- face : intersected face (THREE.Face3)
- faceIndex : intersected face index (number)
- point : intersection point (THREE.Vector3)
- uv : intersection point in the object's UV coordinates (THREE.Vector2)
*/
}
}
}
requestAnimationFrame(render);
init();