Using three.js to cast rays on a mesh with skinning simulation

Attempting to perform a raycast on a skinned mesh post-skeleton alterations, with no animations involved to prioritize performance.

The challenge in this endeavor includes:

  1. Load skinned mesh and add it to the scene
  2. Make changes to the positions of specific bones in the loaded mesh
  3. Copy geometries of the transformed loaded mesh (potentially from a buffer?)
  4. Create a new mesh (a ghost mesh imitation) from the copied geometries and apply it
  5. Set up a raycast on the ghost mesh with an opacity material of 0.0

Though the aforementioned steps should function, I've been stuck on point 3 for three days now because I'm unable to retrieve transformed vertices after skinning.

var scene, camera, renderer, mesh, ghostMesh;

var raycaster = new THREE.Raycaster();
var raycasterMeshHelper;

// Rest of the code can be checked in the original text for reference.
// The code involves the initialization of the scene, camera, lighting, skeleton manipulation, 
// and raycasting functions for the ghost mesh.
// The code snippet deals with creating a ghost mesh and setting up raycasting functionality.

Seeking assistance in resolving this issue using THREE.js build r98 or earlier, and without morph tangents, solely focusing on skinning bones. Apologies for any lack of clarity in my explanation, as I'm not an expert in this field.

I have refrained from sharing my method of computing transformed geometries due to my failures in the process. I've extensively researched this problem, encountering issues such as issue6440, which remains unresolved to date.

Although there are methods available for addressing this, such as https://jsfiddle.net/fnjkeg9x/1/, I've faced challenges, possibly due to differences in approach from projects like Stormtrooper that involve morph tangents.

EDIT:

I've created a codepen based on related discussions here and Stormtrooper. Starting with a simple box to create a bounding box around the skinned transformed mesh.

Unfortunately, there's a setback as it returns 0 at the following line:

boneMatrix.fromArray(skeleton.boneMatrices, si * 16);

Comparing the output from Stormtrooper with my example's console log: Screenshot image

Codepen showcasing the latest progress: https://codepen.io/donkeyLuck0/pen/XQbBMQ

Another idea is to programmatically apply the bones from the loaded model and rig them as a morph tangent (although unsure of the feasibility and approach).

Discovered an example of an animated model here with points tracking.

Answer №1

Even though it's coming in late, I wanted to share an innovative approach to GPU picking that is compatible with skinned meshes. What's great about this method is that it eliminates the need for a separate picking scene to stay synchronized with your main scene and doesn't rely on the user to manage custom materials.

Check out the GPU picking example here: https://github.com/bzztbomb/three_js_gpu_picking

The key to easily override materials and reuse scenes can be found in this snippet: https://github.com/bzztbomb/three_js_gpu_picking/blob/master/gpupicker.js#L58

Answer №3

Utilizing GPU picking allows for the selection of skinned objects, although it does not provide positional information.

Keep in mind that GPU picking necessitates rendering each pickable object with a customized material. The implementation method is left to your discretion. This article demonstrates the use of two scenes for this purpose, which may not be as effective for skinned objects.

Regrettably, three.js does not offer a built-in way to override materials. The following example showcases a technique where materials on pickable objects are replaced before rendering for picking purposes and then restored afterward. Additionally, any unwanted objects should be hidden during the process.

// JavaScript code snippet
const renderer = new THREE.WebGLRenderer({
  antialias: true,
  canvas: document.querySelector('canvas'),
});
const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, 2, 0.1, 200);
camera.position.set(20, 7, 3);

const orbit = new THREE.OrbitControls(camera, renderer.domElement);

// Lighting setup
const ambientLight = new THREE.AmbientLight(0xffffff, 0.3);
scene.add(ambientLight);
const lights = [];
lights[0] = new THREE.PointLight(0xffffff, 1, 0);
lights[1] = new THREE.PointLight(0xffffff, 1, 0);
lights[2] = new THREE.PointLight(0xffffff, 1, 0);
lights[0].position.set(0, 200, 0);
lights[1].position.set(100, 200, 100);
lights[2].position.set(-100, -200, -100);
scene.add(lights[0]);
scene.add(lights[1]);
scene.add(lights[2]);

// Additional settings for raycaster mesh and model loading (omitted for brevity)
// Ensure to set up pickable objects, loading meshes, and necessary rendering logic as per your application requirements.
// CSS styling for the snippet
body {
  margin: 0;
}
canvas {
  width: 100vw;
  height: 100vh;
  display: block;
}
// Include necessary Three.js scripts
<script src="https://threejsfundamentals.org/threejs/resources/threejs/r98/three.min.js"></script>
<script src="https://threejsfundamentals.org/threejs/resources/threejs/r98/js/controls/OrbitControls.js"></script>
<canvas></canvas>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Toggle Form Section Visibility

I am working on a table with five rows that have upload buttons. Each time I submit a row, the page refreshes, but I want to hide all but one row at a time. When the first submit button is clicked, it should show the next row and hide the previous ones. Th ...

Understanding the Usage of FormData in NextJS

I'm trying to read fetch's body contents. Here's the code I'm using: fetch('/api/foo', { method: 'POST', body: new FormData(formRef.current), }); https://i.sstatic.net/6YB1V.png Now I need to parse the body dat ...

Counting Clicks with the Button Counter

I'm having an issue with my jQuery code that is supposed to count button clicks - it stops after just one click. I need help fixing this problem. $(function() { $('.btn').click(function() { $(this).val(this.textContent + 1); }); } ...

What is the most effective method to avoid duplicating elements in the DOM tree?

Seeking a solution for appending a span element to the DOM. if (check something...) { const newSpan = createElement('span'); newSpan.id = '_span'; const container = document.getElementById('container'); conta ...

Encountered an issue when deploying a Gatsby JS site on Netlify due to a non-zero exit code returned by the build script

Recently, I discovered Gatsby JS (https://github.com/gatsbyjs/gatsby) and chose to construct my portfolio website using this generator. To begin, I forked their default starter site (gatsby-starter-default) and developed my portfolio from there (https://g ...

"Retrieve an image source using a jQuery Ajax call and swap it on

I am working on a webpage that includes an <img src="..." /> tag with a default src set. My goal is to use jQuery to make an ajax request to fetch another image, and only once this new image has fully loaded, update the src attribute of the <img ...

Is there a way to retrieve a single value using AJAX instead of returning the entire HTML page?

(edited after initial version) I'm facing an issue where my AJAX call is returning the header.php page instead of just the $result value which should be 0 or 1. The AJAX function calls generateTicket.php, where I want to generate tickets only if no o ...

Using JavaScript to trigger an event when there is a change in the innerHTML or attributes

I have come across a jQuery calendar with the capability to scroll through months, and I am interested in triggering an event each time the month changes so that I can assign event listeners to every td element within the table (with days represented by ...

Updating the content of a div when the mouse hovers over it

Looking for some help here - I have a few divs with paragraphs of text inside. My goal is to change the text in each div when it's being hovered over. I know this can be done using JavaScript (jquery perhaps?), but my coding skills are pretty basic. A ...

Do not reveal result of coin flip using Javascript and API

Even though I meticulously copied my professor's parsing process, the display isn't turning out as expected. It seems like something is off in my code. <div class="main"> <p>Heads or tails? click to toss the coin</p> & ...

An error popped up out of the blue while attempting to execute Webpack

Looking to deploy my React website on IIS but encountering an error when running npm run build:prod. The error message states: index.js Line 1: Unexpected reserved word. You may need an appropriate loader to handle this file type. Below is the snippet fro ...

What order does JavaScript async code get executed in?

Take a look at the angular code below: // 1. var value = 0; // 2. value = 1; $http.get('some_url') .then(function() { // 3. value = 2; }) .catch(function(){}) // 4. value = 3 // 5. value = 4 // 6. $http.get('some_url') ...

Turn a textfield on and off in real-time

Hey everyone, I've been working on making a textfield dynamic and I wanted to share my code with you: <input type="text" id="test1" value ="dynamic" onfocus="this.disabled=true" onblur="this.disabled=false"> <input type="text" id="test2 ...

Ways to retrieve all elements based on their class names?

What is the equivalent of using $('.class') in JQuery to get all elements by class name with pure JavaScript? ...

Display the latest distinct records in Vue.js

I've hit a roadblock in my project. @StephenThomas kindly assisted me with this issue: Vue.js only show objects with a unique property but I still need to make some adjustments. My current task involves creating a leaderboard for a game using Firest ...

Discovering the method to access a getter from a different JavaScript file

In a laravel + vuejs project, I am trying to access my currentUser role in my Acces.js file using store.getters.currentUser but encountering an error: Error in render: "TypeError: Cannot read property 'getters' of undefined I have tried mu ...

Having difficulty arranging the material ui components in a left-to-right alignment

Hello, I need assistance with my bilingual website that supports English and Arabic. I am looking to align the MUI text fields and dropdowns in a right-to-left direction. The labels of the text fields and dropdowns are not styled properly. Currently, I am ...

ReactJS component state fails to update accurately

Let's say I have a component named Test import {useEffect, useState} from "react"; const Test = (props) => { const [Amount, setAmount] = useState(1); useEffect(()=>{ if(props.defaultAmount){ setAmount(prop ...

Ways to expedite the process of retrieving data for a JavaScript array

Looking to acquire the creation date of 20000 files and save it in an array. The total time taken is 35 minutes, which seems quite lengthy. (Image Processing Time) Is there a method to generate the array with a quicker processing time? Are there any i ...

What is the method for displaying a cube map reflection on an object without revealing the cubemap in the backdrop?

Is it possible to display a cube map reflection on an object without showing the cubemap in the background? I am interested in achieving a reflection on a lever mechanism without the cubemap being visible in the background. Instead, I would like the backg ...