What is the best method for generating axis helpers with WebGL and Three.js?

Is there a way to create an axis helper similar to the images below, positioned in both the top left corner and center of the scene? Currently, when using axesHelper in Three.js, the lines lack arrows at the end and appear too thin. Here is the code snippet I have been using:

// Create and add axis helpers
const axesHelper = new THREE.AxesHelper(10); // Adjust length as needed
scene.add(axesHelper);

The current output looks like this: https://i.sstatic.net/UxGx6rED.png

However, what I am aiming for is something more like the image shown below: https://i.sstatic.net/oSDYa5A4.png

Answer №1

There are multiple ways to achieve this, with varying levels of cleanliness. One approach could be to set up distinct scenes for the primary objects and a separate one for the helper.

<script type="importmap">
  {
"imports": {
  "three": "https://unpkg.com/<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="d3a7bba1b6b693e3fde2e5eafde3">[email protected]</a>/build/three.module.js",
  "three/addons/": "https://unpkg.com/<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="eb9f83998e8eabdbc5daddd2c5db">[email protected]</a>/examples/jsm/"
}
  }
</script>

<script type="module">
import * as THREE from 'three';
import { OrbitControls } from 'three/addons/controls/OrbitControls.js';

const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.z = 10;

const renderer = new THREE.WebGLRenderer();
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

const g = new THREE.BoxGeometry(1, 1, 1);
const m = new THREE.MeshBasicMaterial({ color: 0x00ff00 });
const c = new THREE.Mesh(g, m);
scene.add(c);

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

const hudScene = new THREE.Scene();
const hudCamera = new THREE.OrthographicCamera(-1, 1, 1, -1, 0.1, 10);
hudCamera.position.z = 5;

const axesHelper = new THREE.AxesHelper(0.5);
hudScene.add(axesHelper);


axesHelper.position.set(-1.3, 0.3, 0);

function updateHUD() {
  hudCamera.left = -window.innerWidth / window.innerHeight;
  hudCamera.right = window.innerWidth / window.innerHeight;
  hudCamera.top = 1;
  hudCamera.bottom = -1;
  hudCamera.updateProjectionMatrix();
}
window.addEventListener("resize", () => {
  camera.aspect = window.innerWidth / window.innerHeight;
  camera.updateProjectionMatrix();
  renderer.setSize(window.innerWidth, window.innerHeight);
  updateHUDPositionAndCamera();
});
updateHUD();

function a() {
  requestAnimationFrame(a);
  axesHelper.quaternion.copy(camera.quaternion);

  renderer.autoClear = true;
  renderer.render(scene, camera);

  renderer.autoClear = false;
  renderer.clearDepth();
  renderer.render(hudScene, hudCamera);
}

a();

</script>

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 the best way to retrieve an object instead of an array?

When attempting to retrieve a JSON Object, I unexpectedly received an array instead. My query is based on the primary key, so I anticipate only one result. This is my current method : router.get("/student_info/:id", (req, res, next) => { connecti ...

Using val() on a checkbox will give you an element, not a string literal

How can I retrieve only the literal values of all checked checkboxes without any additional data? My current approach is: $('input:checked').map(function() { return $(this).val(); }) The result that I am getting looks like this: e.fn.init[1]0 ...

Conditionally display action icons using state.value in ReactJS

If the data status is set to "APPROVED" in MaterialTable, I need to hide the button that shows as approved/disapproved. const [data, setData] = useState([ {ID: 1, STATUS: "APPROVED"}, {ID: 2, STATUS: "FOR APPROVAL"}, {ID: 3, STATUS: &qu ...

Having difficulty locating audio files within a Next.js project

I am facing challenges when trying to import my audio files into a redux slice. Currently, I am attempting to retrieve my audio files from the app > public > audio directory. I have made efforts to access my audio files through 2 different director ...

Creating a group object based on ID using react-native and JavaScript - a step-by-step guide

I have an array of objects that I need to reorganize so that each object with the same guid is grouped together. For instance, given this array; [ {"guid":"3a03a0a3-ddad-4607-9464-9d139d9989bf","comment":"text&quo ...

Troubles with concealing dropdown menu when hovering

I have noticed that this issue has been raised before, but none of the solutions provided seem to fix my problem specifically. The submenu in my menu is not functioning as intended. It should be displayed when hovered over and hidden when not being hovere ...

Would you prefer to generate fresh HTML using JavaScript or dynamically load an existing HTML layout using AJAX?

I have a project where I need to generate a large amount of HTML that isn't currently on the page. Up until now, I've been using jQuery to construct the page piece by piece with JavaScript, adding divs and adjusting layouts as needed. Lately, I ...

Retrieving a nested sub collection within each object of a Firebase collection in a React application

I'm working on a React app that retrieves elements from Firebase and displays them in a grid. I want to show a list of subcollection elements for each grid line, but I'm unsure how to achieve this. Here's where I currently stand: export defa ...

Give a radio button some class

<input id="radio1" type="radio" name="rgroup" value="1" > <label for="radio1"><span><span></span></span>1</label> <input id="radio2" type="radio" name="rgroup" value="2" > <label for="radio2"><span ...

Tips for updating contact form without reloading the page using HTML, PHP, and JavaScript

Struggling to grasp this concept, didn't realize a basic form could be so complex. I'm still learning the ropes when it comes to the back-end development. The form I'm working on has 3 fields: name, email, and message. All I want is a simpl ...

Cease adding to the list once the condition is no longer valid

I am currently working on a project that requires me to clone span.response11, attach it to #parent, and then insert a new div into the cloned span.response11. I have successfully completed the cloning process, but I am facing an issue where my IF statemen ...

Dynamic variable declarations in JavaScript

Imagine having an object: function obj() { this.prop1; this.prop2; this.prop3; } and a collection of these objects objects = [new obj(),new obj(),new obj()]; The goal is to smoothly loop through each object using jQuery where the class name ma ...

Utilizing Node.js with Express and the less-middleware in combination with Bootstrap 3

I have recently delved into learning Node.js and I am currently in the process of setting up an express installation with less-middleware while also incorporating Bootstrap 3 less files. However, my search for tutorials has only yielded results related to ...

The basic evaluation of jQuery elements does not result in a comparison

Wondering what's going wrong in this code: employee_ids = $('[data-employee_id="'+employee+'"]'); timestamp_ids = $('[data-scheduled_on="'+timestamp+'"]'); var common = $.grep(timestamp_ids, function(element) ...

Updating button appearance when clicked using Vue.js and Tailwind CSS

As part of my learning journey, I have expanded this code to enhance my frontend skills. While I am aware that the code can be significantly shortened, I am focused on learning and broadening my experience in frontend development. The code below functions ...

Sending mongodb data and an HTML page in a single GET request: A step-by-step guide

I have created a form on an HTML page that, when submitted, should trigger the serving of a new HTML page. This new page will then query a MongoDB database, retrieve the results, and render them on the client side. How can I achieve this using a GET reques ...

"Why isn't the reordering functionality functioning properly after the button has been clicked

I have a question regarding menu options that contain text and a button. I need to open the menu option when the button is clicked. Unfortunately, I am facing an issue where rerendering is not working when I click on the button. Here is the link for refer ...

Tips for resizing the background to match the font size on a canvas marker in Google Maps

Check out my jsFiddle code below: var marker = new google.maps.Marker({ position: new google.maps.LatLng(-25.363882,131.044922), map: map, title:"Hello World!", icon: CanvasCrear("hola", 15) ...

Discovering the right row to input the data and successfully integrating it: What is the best

Below is the code I am using to add a new task: <fieldset> <legend>Create New Task</legend> <input type="text" ng-model="subtaskname" placeholder="Subtask Name" ><br /> <select id="s1" ng-model="selectedItem" ng-options=" ...

Rotating Three.js around its own axis

I've been experimenting with creating a 3D spaceship that moves in a straight path. By adjusting the angles, you can make it roll and pitch up and down. Changing the Z angle causes the spaceship to roll correctly, while adjusting the X angle tips the ...