"Troubleshooting 3D Models not appearing correctly in Mapbox when using Three.js

My issue lies in the inability to load any .gltf file, only a standard one. For further details, please continue reading. The map on my application showcases a 3D model indicated by the red arrow:

https://i.sstatic.net/3Ce09.png

The model is a GLTF file accessible here. The code I am using is provided by Mapbox themselves within their documentation, available here.

Here's how it's implemented:

var modelOrigin = [-8.629134, 41.157902];
    var modelAltitude = 0;
    var modelRotate = [Math.PI / 2, 0, 0];
    
    var modelAsMercatorCoordinate = mapboxgl.MercatorCoordinate.fromLngLat(modelOrigin,modelAltitude);

    var modelTransform = {translateX: modelAsMercatorCoordinate.x,translateY: modelAsMercatorCoordinate.y,translateZ: modelAsMercatorCoordinate.z,rotateX: modelRotate[0],rotateY: modelRotate[1],rotateZ: modelRotate[2],scale: modelAsMercatorCoordinate.meterInMercatorCoordinateUnits()};

    var THREE = window.THREE;
    var customLayer = {
      id: '3d-model',
      type: 'custom',
      renderingMode: '3d',
      onAdd: function (map, gl) {
      this.camera = new THREE.Camera();
      this.scene = new THREE.Scene();
       
      // create two three.js lights to illuminate the model
      var directionalLight = new THREE.DirectionalLight(0xffffff);
      directionalLight.position.set(0, -70, 100).normalize();
      this.scene.add(directionalLight);
       
      var directionalLight2 = new THREE.DirectionalLight(0xffffff);
      directionalLight2.position.set(0, 70, 100).normalize();
      this.scene.add(directionalLight2);
       
      // utilize the three.js GLTF loader to incorporate the 3D model into the scene
      var loader = new THREE.GLTFLoader();
      loader.load('https://docs.mapbox.com/mapbox-gl-js/assets/34M_17/34M_17.gltf',function (gltf) {
        this.scene.add(gltf.scene);
      }.bind(this));
      this.map = map;
       
      this.renderer = new THREE.WebGLRenderer({
        canvas: map.getCanvas(),
        context: gl,
        antialias: true
      });
       
      this.renderer.autoClear = false;
      },
      render: function (gl, matrix) {
      var rotationX = new THREE.Matrix4().makeRotationAxis(
      new THREE.Vector3(1, 0, 0),
      modelTransform.rotateX
      );
      var rotationY = new THREE.Matrix4().makeRotationAxis(
      new THREE.Vector3(0, 1, 0),
      modelTransform.rotateY
      );
      var rotationZ = new THREE.Matrix4().makeRotationAxis(
      new THREE.Vector3(0, 0, 1),
      modelTransform.rotateZ
      );
       
      var m = new THREE.Matrix4().fromArray(matrix);
      var l = new THREE.Matrix4().makeTranslation(
        modelTransform.translateX,
        modelTransform.translateY,
        modelTransform.translateZ).scale(
          new THREE.Vector3(
          modelTransform.scale,
          -modelTransform.scale,
          modelTransform.scale)).multiply(rotationX).multiply(rotationY).multiply(rotationZ);
       
      this.camera.projectionMatrix = m.multiply(l);
      this.renderer.state.reset();
      this.renderer.render(this.scene, this.camera);
      this.map.triggerRepaint();
      }
    };
map.on('load', async () => {
      map.addLayer(customLayer, 'waterway-label');
});

Notably, the model link within the loader.load() function functions flawlessly for THAT specific model. However, when attempting other models, whether local or referenced as ('./models/file.gltf), it fails to work. The reason behind this remains unclear, and efforts to resolve the issue have proved unsuccessful.

Answer №1

It seems like there may have been an issue with your code, possibly related to the relative path of the files.

I've gone ahead and prepared a PR in your repository for you. It includes a basic node project with 2 examples. The first example demonstrates how to load a 3D model using the standard Mapbox code. The second example showcases the same process using threebox, with additional features such as selection, rotation, dragging, bounding box, and tooltips.

https://i.sstatic.net/BNmka.gif

Answer №2

When I integrate the GLTF loader using a link from the mapbox documentation, the object loads perfectly:

var loader = new THREE.GLTFLoader();
        loader.load('https://docs.mapbox.com/mapbox-gl-js/assets/34M_17/34M_17.gltf',function (gltf) {
          this.scene.add(gltf.scene);
        }.bind(this));
        this.map = map;

However, swapping out that link for the original repo link causes it to not work:

https://github.com/jscastro76/threebox/blob/master/examples/models/radar/34M_17.gltf

It doesn't crash the application; rather, it fails to load and displays an error message like this: https://i.sstatic.net/VKRLV.png

The same issue occurs when attempting to use a local file path like ./folder/34M_17.gltf. The object still does not load and the same error is shown. It's puzzling how it works with one method but not the others...

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

Tips for retrieving user input and displaying it on an HTML page

I have encountered an issue with displaying user input in a table. The code for the table display is as follows: <tr ng-repeat="user in users" ng-class-even="'bg-light-grey'" ng-if="isLoading==false"> <td> ...

using a ternary operator within the map function

Currently, I'm developing a web application that allows users to view a list of items and mark certain items as favorites. The favorites are stored in an array of IDs assigned to a prop (this.props.favorites). To ensure there are no duplicate entries, ...

The Gatsby plugin image is encountering an error due to a property that it cannot read, specifically 'startsWith

While browsing the site, I couldn't find a solution to my issue, but I stumbled upon an open bug on Github. The only workaround mentioned at the moment is to utilize GatsbyImage. As I delve into converting a Gatsby project from version 2 to 3, I have ...

Oops! There was an error: Unable to find a solution for all the parameters needed by CountdownComponent: (?)

I'm currently working on creating a simple countdown component for my app but I keep encountering an error when I try to run it using ng serve. I would really appreciate some assistance as I am stuck. app.module.ts import { BrowserModule } from &apo ...

Angular JS: Implementing a click event binding once Angular has completed rendering the HTML DOM

Exploring AngularJS for the first time, I've researched extensively but haven't found a satisfying solution. My goal is to retrieve data from the server and bind it to HTML elements on page load. However, I also need to bind click events to these ...

Attempting to display my ejs template from a node server following the activation of a delete button, all without utilizing ajax

I have created a basic blog application using node.js for the backend and ejs for the frontend. Posting blogs using a web form works well by calling a post route. Now, I am facing an issue with implementing a delete button for each blog post. The current s ...

Understanding the concept of event bubbling through the use of querySelector

I am currently working on implementing an event listener that filters out specific clicks within a container. For instance, in the code snippet below I am filtering out clicks on elements with the class UL.head. <div> <ul class="head"> < ...

Easy selector for choosing jquery css backgrounds

Here is a simple background selector that I created. <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> <hea ...

Exploring the capabilities of Google Apps Script for looping and generating output

I have two spreadsheets named rawData and processedData. The content of rawData is as follows: Status Title Options Live Title1 Option1, Option2, Option3, Option4 Live Title2 Option1, Option2, Option3, Option4, Option5 Live Title3 Option1, O ...

A guide on calling a function from a different component in vuejs2

I am facing a situation where I need to trigger an event whenever my sidebar opens. This event should be called every time the sidebar is opened. For example, when I click on an element, it triggers the opening of my sidebar which then calls a function th ...

retrieve information from various components identified by the common class name by employing ajax requests

I have a component labeled with the class tclick indicating a sample class <label class="btn btn-default tclick" data-tloc="value1" data-tkey="key1" > <label class="btn btn-default tclick" data-tloc="value2" data-tkey="key2" > <label class= ...

Using an External JavaScript Library in TypeScript and Angular 4: A Comprehensive Guide

My current project involves implementing Google Login and Jquery in Typescript. I have ensured that the necessary files are included in the project: jquery.min and the import of Google using <script defer src="https://apis.google.com/js/platform.js"> ...

Exploring ways to utilize removeEventListener in React Native

Can someone assist me with converting this code to React? I am new to using React and struggling with the implementation. Thank you in advance! <progress id="bar" value="0" max="110"></progress> <button onClick={i ...

Editing an XML file on the browser and saving it in its original location on the local file system

Seeking assistance with editing an XML file directly from the browser on a local file system and saving it back to its original location. I have conducted extensive research using Google, but have not been able to find a suitable solution. Any help or gu ...

Dealing with multiple POST requests at once in Node Express JS - Best Practices

I've been working on a Node project with Express to handle incoming GET/POST requests. I have set up routes to manage various types of requests. One specific route, /api/twitter/search, calls a function that uses promises to retrieve Twitter feeds and ...

What could be causing the Gruntfile to throw an error?

Getting an unexpected error while trying to run grunt $ grunt Loading "Gruntfile.js" tasks...ERROR >> SyntaxError: Unexpected token : Warning: Task "default" not found. Use --force to continue. Execution terminated due to warnings. Here is my ...

Steps for referencing an autogenerated id in a Firestore collection

I need assistance updating a 'progress' field in a document with an autogenerated ID (using Firestore) every time the progress button is clicked. https://i.stack.imgur.com/hZieN.png Despite my attempts, nothing seems to work. Here is the method ...

What is the best way to delay a method in vue.js?

In the tab element called competences, there is an input field with the reference search. <ul class="nav nav-tabs" id="myTab" role="tablist"> <li class="nav-item"> <a @click="competencesTabClick" aria-controls="Company" aria-sel ...

What is the correct way to establish a Cookie (header) using XMLHttpRequest in JavaScript?

I am attempting to set a cookie in an XSS request using XMLHttpRequest. After reviewing the XMLHttpRequest Specification, I discovered that section 4.6.2-5 indicates that setting certain headers like Cookie and Cookie2 may not be allowed. However, I am lo ...

jQuery code runs smoothly on Firefox but encounters issues on Chrome

I'm experiencing an issue with a script that is supposed to post a comment and load the answer from a server. The script works fine in Firefox, but in Chrome, it seems that no event is triggered. You can click the button, but nothing happens. I'v ...