-
-
Notifications
You must be signed in to change notification settings - Fork 2.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[rmodels] Meshes doesn't reliably represent gltf/m3d/obj/vox data #4650
Comments
@rmn20 raylib is focused on simplicity and current approach follows that line. Supporting multiple materials "per mesh" actually means supporting differents materials per groups of triangles, that, in practice, it's the same as splitting to multiple meshes. Afaik, it's not possible to support multiple Materials by the same Mesh, and even if it was possible it would require multiple render passes and a more advance rendering pipeline.
I do not agree with this statement. A model file-format is an intermediate format and it must be always adapted to the native engine supported format, in this case, raylib, despite its potential limitations.
I'm afraid this is out of scope for raylib, and sincerely I can't see the use-case for multiple Materials per Mesh, could you provide some example? |
Yep, it is, no advanced rendering is required. It's just about more convenient data structure that would group submeshes with different materials into one mesh structure for simplified usage and direct mapping between raylib meshes and meshes in model file.
Some of the more obvious examples:
|
Just a quick note: LODs can use different amount of materials than the base mesh |
This all sounds way out of scope for what the model structure is designed to do. Raylib is not an engine. |
Issue description
Current raylib Mesh structure is limited to only one material, while most 3D model formats supported by raylib (all except vox and iqm) allow the use of multiple materials per Mesh.
This limitation disables the direct association between meshes in the model files and the raylib meshes, since meshes with multiple materials had to be split to multiple raylib meshes to be fully represented. Moreover, I tested models in different formats, and formats workaround this problem in different ways by joining or splitting meshes in a unique way, making working with meshes in raylib even more unreliable.
Testing of each model format
I created a simple model consisting of 3 meshes:
I exported/converted model into several file formats and tested how each would work in raylib:
While IQM stores only one material per mesh (see IQM specs) I still decided to check how it would work.
Obviously meshes with multiple materials got separated into multiple meshes on model convertation stage, but this is expected behavior.
For some reason Z and Y axes got swapped but I think this is intended? Can't say for sure with this rare format.
Meshes got loaded in raylib in correct order, but it looks like raylib doesn't account for IQM materials and just create separate material for each IQM mesh.
M3D specs allow for models with multiple meshes with multiple materials, but for some reason both m3dconv and io_scene_m3d Blender plugin combine all meshes into one when converting Wavefront OBJ to M3D (I checked this using m3dconv builtin validation tool).
Also it looks like m3d.h from M3D SDK doesn't allow to load meshes separately anyways, so I don't think raylib has to do anything with this.
Meshes got loaded in correct order, but meshes with multiple materials got split into multiple raylib meshes, resulting in this mesh list:
For some reason all materials specified in OBJ file is ignored and joined if MTL file is not present. I think that even tho material file is not present material names from OBJ file itself still can be useful for end user (maybe material name field can be added to raylib Material structure?).
This one is really weird. While original mesh order is present in raylib, meshes got joined and separated into multiple raylib meshes in some weird way, resulting in this mesh list:
While MagicaVoxel file format doesn't have materials at all it still allows for multiple "models" in one file, so I decided to try it too and created a project with 3 cube models in MagicaVoxel.
For some reason raylib loads only last model provided in VOX file.
Why this is important?
Establishing a direct association between meshes in the model file and raylib meshes is important because it will allow users to reliably and efficiently use and manage model meshes in raylib.
For example, the end user would be able to save the entire level model in a single file and use different meshes as different level zones, disabling or enabling rendering of specified meshes for optimization purposes.
Or, if we are talking about small props on the level, user could store multiple LODs in a single file as separate meshes and render only selected mesh.
Separate meshes also could be used to add variety to game without complicating the editing and loading of models. For example, you could switch accessories or weapons on enemy/npc/player models or on some background props. Meshes could also be used for key frame animation on models, such as in the original Quake, but this applies only to retro-styled games.
Of course, all this is possible in the current version of raylib, but it requires user to spend additional time researching each model format supported by raylib to find out which one is most stable in raylib, and to practically limit use of materials, since they can easily break mesh indexing.
How this can be fixed?
Obviously, the model loading needs to be improved.
There are several ways how raylib meshes could represent model meshes better.
The straightforward way is to add multiple materials support to the Mesh structure itself, by replacing almost all fields with arrays of these fields... Or you could move the data from the Mesh structure to a new structure named Submesh and just store the array of submeshes in the Mesh structure. Obviously, one way or another, this is a breaking change.
Another way is to store an additional array of integers in the Model structure with indexes of Meshes in original model file. This shouldn't cause breaking changes, but I don't think this method is really convenient.
Environment
I checked both 5.5 and 5.6-dev (commit f355d6f) raylib versions.
Code and model examples
This archive contains the aforementioned model in several file format and a simple raylib application that loads model file and allows to switch between different meshes.
The text was updated successfully, but these errors were encountered: