Maintain Label Size in ThreeJS Zooming Feature

Currently, I am working on a solar system project in three.js and have been wondering if there is a simple way to ensure that the labels for the planets are displayed at the same size regardless of their distance from the camera. Unfortunately, I haven't been able to find a solution for this yet. One possible approach could be calculating the distance from each label to the camera and then establishing a scaling factor based on this information. However, it seems like there should be a more straightforward method to achieve this. Any suggestions would be greatly appreciated!

Thank you!

https://i.sstatic.net/3lEvn.jpg

Recently updated with an answer provided by prisoner849, which has proven to work excellently!

https://i.sstatic.net/FE3Pj.jpg

Answer №1

To solve this issue, one possible approach is to calculate the distance between each label and the camera and then establish a scaling factor based on that information.

It's quite straightforward. For instance, if a THREE.Sprite() object (label) is nested within a THREE.Mesh() object (planet), during your animation loop, you can implement the following:

var scaleVector = new THREE.Vector3();
var scaleFactor = 4;
var sprite = planet.children[0];
var scale = scaleVector.subVectors(planet.position, camera.position).length() / scaleFactor;
sprite.scale.set(scale, scale, 1); 

I have created a simple demonstration of the Solar System using this method.

Answer №2

To assist future visitors, the example of transform controls demonstrates the following:

Here is a snippet from the sample code showing how it is implemented:

var factor;
if ( this.camera.isOrthographicCamera ) {
factor = ( this.camera.top - this.camera.bottom ) / this.camera.zoom;
} else {
factor = this.worldPosition.distanceTo( this.cameraPosition ) * Math.min( 1.9 * Math.tan( Math.PI * this.camera.fov / 360 ) / this.camera.zoom, 7 );
}
handle.scale.set( 1, 1, 1 ).multiplyScalar( factor * this.size / 7 );

Answer №3

At long last, I have uncovered the solution to your inquiry:

To begin with, create a DOM Element:

<div class="element">Not Earth</div>

Next, apply CSS styles to it:

.element {position: absolute; top:0; left:0; color: white}
//        |-------------------------------|  |-----------|
//            position element on top of         canvas is 
//               the canvas                       black, so text
//                                                must be white

Then, establish the moveDom() function and execute it each time you render the scene using requestAnimationFrame()

  • geometry represents the geometry of the mesh
  • cube refers to the mesh where you want to place the label
for loop to assign labels to all meshes in your scene.

Keep in mind that this method only sets the 2D position of the DOM Element, so the size of the label remains constant even if you zoom in or out (the label is not part of the three.js scene).

Complete test case: https://jsfiddle.net/0L1rpayz/1/

... (text continues)

Answer №4

If you're utilizing spriteMaterial to display your text, consider disabling the sizeAttenuation attribute.

var spriteMaterial = new THREE.SpriteMaterial( { map: spriteMap, color: 0xffffff, sizeAttenuation:false } );

For more details, check 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

Transmit a JSON array from Javascript to PHP using the POST method

After spending hours searching for a simple solution to send a pre-made JSON string to a PHP method, I finally came across this JavaScript snippet: form = document.createElement("form"), node = document.createElement("input"); var element1 = document.crea ...

Obtaining the value and other attributes of a select option in Vue.js 2

I have implemented vuejs in my project and encountered a situation where I need to work with a select element containing multiple options. Here is an example of the code: <select v-model='line.unit' name='unit[]' required @change=& ...

Difficulty arises when attempting to run code when a checkbox is not selected

In my form validation process, I am facing an issue where I need to validate certain values only if a checkbox is unchecked. If the checkbox is checked, I want to use the values that were previously added. However, none of the existing code snippets seem t ...

When you click on `window.open('my-app://', '_blank');`, it won't directly open the desktop app from the browser. However, typing `my-app://`

When I open Chrome and enter my-app:// in the URL or search bar, a dialog box pops up saying "Open my-app? A website wants to open this application". Clicking ok opens my Electron app. I'm looking to add similar functionality to my React app, where t ...

JavaScript function for submitting form data using AJAX and performing validation

This is the code I have been working on: $(function () { $('.contact-form').submit(function (event) { $(this).find("input , textarea").each(function () { var input = $(this); if (input.val() == "") { ...

In what ways can we utilize a consistent state across various tabs or pages?

One feature of my application is a dynamic chart with various settings such as filters and time ranges. I want to save these settings in the app's state so they can be shared with other components on different pages. However, when switching tabs and r ...

Move the divs within the overflow container by sliding them, then take out the initial element and append it to the end

Currently, when I utilize .appendTo(".wrapper") as shown in the code below, it eliminates the animation effect. My goal is to have the div on the far left slide out of view, triggering an overflow hidden effect, and then be placed at the end of the slide c ...

There was an issue with retrieving the image URL from the source, causing an error message to display: "

I encountered an error while trying to access my product. Here is the error message https://i.stack.imgur.com/fTmL0.png It seems that the image URL from the sanity database cannot be rendered, even though it worked fine in the tutorial I was following. I ...

Incorrect Request Method for WCF json POST Request Leads to 405 Error (Method Not Allowed)

Hey there, I'm facing an issue with using Microsoft Visual Studio to create a WCF web service. Everything runs smoothly within Visual Studio, but when I try to connect to the service from outside, it fails to establish a connection. At first, I encoun ...

Shall we Combine JavaScript Files with Import and Require Statements?

Apologies for the vague description, I am trying to be concise while acknowledging my limited understanding and potential incorrect assumptions. I currently have a website that consists of one large HTML file with scripts defined in-line within <script ...

Creating a 2D coordinate plane within a 3D space through the utilization of equations and vectors

For my math project, I am working on creating a visualization tool for a linear regression plane. I have completed the mathematical aspects of the project, but I am unsure of how to graph the plane. The equation I am working with is z=C+xD+yE, where C, D, ...

What is the reason behind external JavaScript files being able to access the functions of other external JavaScript files, and what measures can

While I may not be an expert in JavaScript, I find it intriguing that within a project containing 3 JavaScript files, any of these files can access functions from the others. The real puzzle lies in figuring out how to prevent this from happening. For in ...

What are the best methods for capturing individual and time-sensitive occurrences within a service?

I am currently working on structuring the events within a service to enable a mechanism for subscribing/unsubscribing listeners when a controller's scope is terminated. Previously, I utilized $rootScope.$on in this manner: if(!$rootScope.$$listeners[& ...

How can I retrieve routing parameters in a Vue.js/Nuxt/TypeScript app?

In the process of developing my website based on the Nuxt TypeScript Starter template, I've encountered a challenge. Specifically, I have created a dynamically routed page named _id.vue within my pages folder and am looking to access the id property i ...

Error: guild is not defined | discord.js

Having trouble with a ReferenceError that says guild is not defined? I recently encountered a similar issue with members but managed to fix it by adding a constant. As someone new to javascript and node.js, I could use some assistance. I've even tried ...

Invoke the REST API when a checkbox is selected

I have a React component that I need help with: import * as React from 'react'; import './Pless.css'; interface Props { handleClose: () => void; showPless: boolean; } export class Pless extends React.Component<Props> ...

Is it possible to apply fog to a specific area in Three.js instead of being dependent on the distance from

Picture this: a vast THREE.PlaneGeometry representing the floor with a camera placed at an arbitrary spot within the scene. By manually adjusting the near and far values of the fog, I can effectively conceal the outer edges of the plane to create the illu ...

What is this error: "Unknown authentication strategy 'loca'"?

Whenever I try to utilize passport.js, it keeps throwing the following error: Unknown authentication strategy "local"! config/configuration.js var passport = require('passport') , LocalStrategy = require('passport-local').Strategy; ...

Tips for utilizing console log within a react form component

I'm currently exploring ways to communicate with a React form in order to provide it with an object.id for updating purposes. While I can successfully console log the object.id within the update button and modal, I am struggling to confirm if the val ...

When the ASPxComboBox component is situated within two ASPxPageControl tab pages, I am unable to access it

I am encountering an issue with accessing the ASPxComboBox component when it is within an ASPxPageControl that has multiple tab pages. To handle this, I have added a function to the ClientSideEvents using string.Format: function(s, e) {{ if (window[ ...