Performing matrix manipulations using Mirror.js (Three.js)

I am currently working on creating water effects in three.js and I haven't come across any examples in three.js that incorporate both reflection and refraction. If you know of any examples, please feel free to share the links with me. Currently, I am building on top of Mirror.js by Slayvin, which you can find here.

My approach involves using a second rendertarget to render the refraction texture in a similar manner as the reflection and then blending the two textures in the shader.

Currently, I am using a temporary refraction rendertarget for blending, which is working. However, the temporary refraction is distorted because I am not applying the correct matrix multiplications to the texture. While I believe it should be simpler than the mirror, the results are not as expected. How can I determine the initial texture matrix settings?

this.updateMatrixWorld();
this.camera.updateMatrixWorld();

// Update the texture matrix
this.textureMatrixRefraction.set( 0.5, 0.0, 0.0, 0.5,
                        0.0, 0.5, 0.0, 0.5,
                        0.0, 0.0, 0.5, 0.5,
                        0.0, 0.0, 0.0, 1.0 );

this.textureMatrixMirror.multiply( this.camera.projectionMatrix );
this.textureMatrixMirror.multiply( this.camera.matrixWorldInverse );

I am currently trying to understand how the matrix operations for the mirror work as I seem to be missing an important element. I attempted to simplify the process with the code above, with comments indicating my uncertainties. Any help in clarifying those points would be greatly appreciated.

THREE.Water.prototype.updateTextureMatrixMirror = function () {

    //UPDATE TO CURRENT WORLD AND CAMERA FOR MIRROROBJECT
this.updateMatrixWorld();
this.camera.updateMatrixWorld();
//COPY VALUES FROM WORLD AND CAMERA, GETTING TRANSFORMATIONS IN WORLD
this.mirrorWorldPosition.setFromMatrixPosition( this.matrixWorld );
this.cameraWorldPosition.setFromMatrixPosition( this.camera.matrixWorld );

this.rotationMatrix.extractRotation( this.matrixWorld );
//SET NORMAL AND APPLY ROTATION
this.normal.set( 0, 0, 1 );
this.normal.applyMatrix4( this.rotationMatrix );
//CREATE NEW CAMERA VIEW, THIS IS ONLY RELEVANT FOR THE REFLECTION
var view = this.mirrorWorldPosition.clone().sub( this.cameraWorldPosition );
view.reflect( this.normal ).negate();   //tHIS IS NOT NEEDED FOR REFRACTION?
view.add( this.mirrorWorldPosition );

//Further code omitted for brevity.

Update: I have made some progress in achieving a visually acceptable result, but I am facing several issues. I suspect that I am not properly creating the refraction texture due to the flawed matrix transformations. Additionally, I am struggling to achieve a smooth flow for the offset of the dudv-map I implemented. Currently, I am using a sine-function which results in a swaying motion that looks unnatural. I am looking for a better solution to avoid a sudden "jump cut" effect. You can view the current result and full code here.

Answer №1

Below, you'll find some detailed explanations:

While the 'lookatPosition' part may seem unnecessary, it plays a crucial role in determining a point that is exactly 1 unit in front of the current view on the Z axis:

this.lookAtPosition.set( 0, 0, -1 ); // -1 unit on Z (depth axis)
this.lookAtPosition.applyMatrix4( this.rotationMatrix ); // applying camera rotation to match the lookat vector
this.lookAtPosition.add( this.cameraWorldPosition ); // adding this vector to camera position

This position is chosen arbitrarily for convenience in further calculations. It could have been any number such as -10 or -0.5 units away from the camera; the specific value (-1) was selected for ease of use.

Once we have the camera position, a known point in space where the camera is looking, and the mirror's position and orientation established, we can proceed to determining the orientation of the mirrored view:

var target = this.mirrorWorldPosition.clone().sub( this.lookAtPosition );
target.reflect( this.normal ).negate();
target.add( this.mirrorWorldPosition );

A target vector is created as the disparity between target and mirror positions. This vector is then reflected along the mirror's normal axis and negated for addition to the mirror position, yielding the final mirrored target position.

Subsequently, the mirror camera is configured with the correct up, target, and position...

this.mirrorCamera.position.copy( view );
this.mirrorCamera.up = this.up;
this.mirrorCamera.lookAt( target );

...and the projection matrix calculations are carried out.

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

What is preventing me from making an inline call to res.json?

In my expressjs application, I encountered an issue with inlining a callback when using the res.json method to respond with a database document. While inlined calls to console.log worked fine, the program failed when I attempted the same approach with res. ...

Is there a way to restrict the amount of user input that is allowed?

Is it possible to restrict the input quantity when using the built-in arrow icon in the text field, but not when typing manually? https://i.sstatic.net/jjogP.png <TextField variant="outlined" label="Quantity" onChan ...

Detecting incorrect serialized data entries based on data types

In the scenario where the type MyRequest specifies the requirement of the ID attribute, the function process is still capable of defining a variable of type MyRequest even in the absence of the ID attribute: export type MyRequest = { ID: string, ...

Leveraging IntersectionObserver to identify the video in view on the screen

Our Objective I aim to implement a swipe functionality for videos where the URL changes dynamically based on the ID of the currently displayed video. Challenges Faced Although I managed to achieve this with code, there is an issue where the screen flashe ...

Guide to adding information to an .xml document

Currently, I am working on building a website for a school project, specifically an online shop. I am focusing on the shop section, where I need to store data such as name, price, image, and description in either a text file or XML format. Right now, the w ...

What is the best way to implement colorful opening hours in code?

I found this code on a different platform and decided to tweak it to display only Monday - Friday, Saturday, and Sunday. However, I'm stuck trying to update the Javascript code to match my modifications. Any help would be appreciated! You can view th ...

"Implementing a click event on a dynamically generated element is triggering the event for all of its parent elements

I have a task to generate a dynamic table with data retrieved from the server. Each row in the table contains a tag that I am trying to link to a click event. The code snippet below demonstrates how the dynamic table is created: function ProcessResponse ...

Access a designated Dropbox directory using the Dropbox API in either PHP or JavaScript

Can the Dropbox API be used to recursively list all files and directories from a specified path? For example, I am interested in listing all files located in Projects/Customers/CustomerXY/ on my account's website. ...

I want to use the enter key for posting, but also have the ability to use the shift and enter key to create a

$("#post_text").keydown(function(e){ // Checking if Enter key was pressed without shift key if (e.keyCode == 13) { // Prevent default behavior e.preventDefault(); } if (e.keyCode == 13 && !e.shiftKey) { alert('test'); } }); I a ...

Switch from using `widthWidth` to `useWidth` in MUI v5 ReactJS

Currently, I am in the process of updating a project that utilizes MUI as the UI Library for my React application. I have started migrating to version 5 today, and one issue I've encountered is related to all functional components wrapped by withWidth ...

Calculating the sum of values in a JSON array using a specific parameter in Typescript

A flat JSON array contains repetitive identifier, categoryId, and category: data: [ { "identifier": "data", "categoryId": "1", "category": "Baked goods", "product": "Aunt Hattie's", "price": "375" } ...

Ways to update a specific div upon clicking an image

Is there a way to refresh a div using an image click? I have an image with the id 'sellhide' and another div with the id 'sellChart'. Below is the code: <div class="col-xs-12 col-lg-6 col-sm-6 col-md-6 index_table_three" id="sellCha ...

Refinement of chosen selection

Is there a way to dynamically filter the content of a table based on the selected option? I want the table to refresh every time I change the option in the select dropdown. HTML <select ng-model="selectedGrade" ng-options="grade.Id as grade.Title f ...

Exploring the Three JS Perspective Camera's Field of View and Distance Range

We have a model loaded on Three JS Fiber and notice that other projects with similar models have a more steady camera view, giving the illusion of the object being larger. However, our camera settings seem to be different: https://i.sstatic.net/xxYkB.png ...

Press the button within the table as its name undergoes periodic changes

I am using Python along with Selenium to automate the process of selecting and reserving a room on a website. The site displays a table containing available rooms, and my goal is to locate a specific room and click on the corresponding button within the ta ...

AngularJS Resource GET Request Unsuccessful

Is there a way to verify if a resource failed to be fetched in AngularJS? For instance: //this is valid syntax $scope.word = Word.get({ id : $routeParams.id },function() { //this is valid, but won't be triggered if the HTTP response is 404 or an ...

Unable to fetch information from the local host using an AJAX request and PHP script

I'm having trouble retrieving the <p> elements echoed in my PHP script. I need a solution that allows me to style these <p> nodes using a JavaScript function without refreshing the page. Can someone help me with this issue? Here is my PHP ...

The JavaScript and CSS properties are not functioning properly with the HTML text field

I came across this CodePen example by dsholmes and made some modifications: Here Furthermore, I have developed my own form on another CodePen pen: Link The issue I'm facing is related to the placeholders/labels not disappearing when typing in text f ...

Bringing in X3d documents into three.js

Does anyone know if X3d files can be imported into three.js? Perhaps converting the X3d file to a format that three.js can recognize, such as OBJ or STL? Appreciate any assistance with this! ...

Is it possible to utilize the System.import or import() function for any JavaScript file, or is it restricted to single module-specific files?

After reading an intriguing article about the concept of dynamic component loading: I am interested in learning more about the use of System.import. The author demonstrates a specific syntax for loading the JavaScript file of the module that needs to be d ...