There is a way to import mesh synchronously without async/await?

Hi,

I need to import mesh synchronoulsy to do something with the mesh after.
I already try ImportMesh without expected effect.

To example i have this following code

main.js :

let obj = new Obj_Asset(objName, filePath, fileNameWithExtension);
obj.loadObj(babylonPositionXYZ);
// do something with obj.mesh, for example the folowing console.log
console.log(obj.mesh);  // currently return undefined

Obj_Asset :

class Obj_Asset {
  constructor (objName, filePath, fileNameWithExtension) {
    this.mesh = undefined
    this.objName = objName
    this.filePath = filePath
    this.fileNameWithExtension = fileNameWithExtension
  }

  loadObj(positionXYZ) {
    BABYLON.SceneLoader.ShowLoadingScreen = false;

    let importedMeshes = BABYLON.SceneLoader.ImportMesh(null, this.filePath, this.fileNameWithExtension, scene);

    this.mesh = BABYLON.Mesh.MergeMeshes(importedMeshes.meshes, true, true, undefined, false, true);
  }
}

I don’t want to put make loadObj async and put an await on ImportMesh, it force me to put an await on obj.loadObj on main an a asyn on his parent function, so it force me to put an await to… bla… bla… bla…

did someone have an idea ?
thanks by advance

Is this topic from the old forum of any use?

https://www.html5gamedevs.com/topic/32480-loading-asynchronous-objects-into-array-for-later-use/?do=findComment&comment=187590

1 Like

Hi VerandaLouis,

Formally, I believe the answer to the question “Is it possible to load a mesh synchronously?” is, “No, not really.” If I’m understanding this correctly, this is because of the way JavaScript works: synchronous in this sense means blocking, and because loading a mesh can involve operations that leave JavaScript and then have to come back, blocking becomes problematic. I know adding asynchrony will have cascading effects, but I really think it’s much better to embrace asynchrony early on and design around it. Because it’s a reality of JavaScript and Web code, this situation will keep popping up, and without a solid asynchrony pattern it’s going to be a fight every time.

1 Like

Something like that. (use async and await)

the MergeMesh function will be executed after the file is imported

async loadObj(positionXYZ) {
    BABYLON.SceneLoader.ShowLoadingScreen = false;

    let importedMeshes = await BABYLON.SceneLoader.ImportMesh(null, this.filePath, this.fileNameWithExtension, scene);

	if(importedMeshes)
		this.mesh = BABYLON.Mesh.MergeMeshes(importedMeshes.meshes, true, true, undefined, false, true);
}
2 Likes

Hello @VerandaLouis just checking in, was your question answered?

hello,

my question is not really answered, i know that is it possible to make loadObj() async and use await but it force me to use async and await on my main.js :confused:, I already do it but I don’t find it clean.

my question is more like “There is a way to import mesh synchronously without using async/await ?” (i edit my post title)

Loading a mesh is asynchronous by nature as it fetches data from the network for example.

If you do not like the async version why not simply relying on the callback or importAsync.then(…)?

2 Likes

asynchronous is natural process for reading/loading file in any programming language, because it takes time, possibly something going wrong, etc. so, it can’t be avoided.

but, you can preload all/some the assets before showing anything.

I agree. This question doesn’t make sense. You cannot

using js, without committing that the mesh information is actually loaded. No matter the method you choose for that. BJS is sure smart and versatile but is not an oracle.

As per @sebavan post, I use the importAsync + then method quite often with obj objects, combined with onload for external scripts. It’s fair enough since it lets you do the transform on your imported mesh or scripts only once ready yet, meanwhile, potentially continues to process the rest of the code. I believe this is the closest you can have to a seamless ‘synchronous’ processing of the scene and imported assets. Though, I believe I can understand what you mean by “not clean”. It can be a bit tricky to track the parts relying on whatever ‘then’ or ‘onload’ when you imbricate a number of these. All I can say (and what I do) is comment the start and end of (then or onload). A bit tedious but in the end not dramatic I believe.

It would be nice for a synchronous method to exist which operates on a base 64 data uri, which is perhaps what OP was asking for. I’m likewise running into a situation right now where it’d be helpful!

I guess so. Well, if you have enough insight on this and are willing to synthetize, you could still try your luck making a feature request. May be you’ll get lucky. I am constantly amazed to see new complex or specific methods being implemented on simple demand. Who knows, may be you can trigger something and someone will absolutely want to do this…

When you say “synchronous”, do you mean a method with a callback? Because the callback methods do work with base64 URIs :slight_smile:

1 Like

In this context I mean that there are no ticks of the event loop before the mesh/geometry is ready

i.e. i can do

meshdata = meshloader.loadmesh
// do things that require loaded mesh here

Loading an image from base64 will also require to wait for the onLoad event. The only way would be to also store those in a binary form that you upload as a texture. It would basically require a different format being potentially way bigger or some tools to parse/decode pngs inline.

1 Like