RigsOfRods / rigs-of-rods

Main development repository for Rigs of Rods soft-body physics simulator
https://www.rigsofrods.org
GNU General Public License v3.0
995 stars 175 forks source link

Allow custom materials in managedmaterials/managedmaterials2 #2990

Closed danmackey closed 1 year ago

danmackey commented 1 year ago

I want the ability to use materials included in my .zip in the managedmaterials section.

Currently managedmaterials work statically, parsing the parameters in order into the expected parts of the specified material (flexmesh_standard, flexmesh_transparent, mesh_standard, or mesh_transparent). This works well for those satisfied by the way these materials work and look, but does not help anyone looking to use more advanced materials in the same way.

There would need to be a different way of providing arguments since there could be N arguments for a given material.

I think it would make sense to use the script variables in the user defined material and use a key=value syntax to define all the variables in the .truck file, however maybe some other format would work better.

Example materials ``` abstract material spec_shine_mat { technique { pass { scene_blend alpha_blend vertex_program_ref NiceMetal_VS {} fragment_program_ref SimpleMetal_PS {} texture_unit { texture $texture tex_coord_set 0 } texture_unit { texture $texture_shine tex_coord_set 1 } } pass { depth_write off scene_blend add vertex_program_ref NiceMetal_Reflect_VS {} fragment_program_ref NiceMetal_Reflect_nocolor_PS {} texture_unit { texture $texture_spec tex_coord_set 0 } texture_unit { texture EnvironmentTexture cubic tex_address_mode clamp tex_coord_set 1 } } } } abstract material simple_alpha_mat { technique { pass { alpha_rejection greater $alpha texture_unit { texture $texture } } } } abstract material simple_scale_mat { technique { pass { texture_unit { texture $texture scale $scale } } } } ```

Example managedmaterials2

managedmaterials2
; material        template_material k1=v1                     k2=v2                         k3=v3
body_mat          spec_shine_mat    texture=body.png          texture_spec=body-spec.png    texture_shine=body-shine.png
chassis_mat       spec_shine_mat    texture=chassis.png       texture_spec=chassis-spec.png texture_shine=chassis-shine.png
window_mat        simple_alpha_mat  texture=window.png        alpha=128
tinted_window_mat simple_alpha_mat  texture=tinted_window.png alpha=128
seat_pattern_mat  simple_scale_mat  texture=seat_pattern.png  scale="0.1 0.1"
diamond_plate_mat simple_scale_mat  texture=diamond_plate.png scale="2.0 2.0"

This would provide a more advanced system for reusing materials and props as well as replacing parameters in materials.

ohlidalp commented 1 year ago

Closing because this functionality is already provided by OGRE itself in it's material scripts:

danmackey commented 1 year ago

I may not have made the purpose of this clear enough or I do not understand something about material scripting.

The problem is if I want to apply different textures to a mesh I have across multiple truck files in a single resource zip I have two options:

  1. Re-export the mesh multiple times with a different material name, allowing me to have a custom material. This would also require re-exporting the same mesh multiple times for every change I want to make.
  2. Export the mesh once and use managedmaterials, with no ability to modify the material on the mesh.

Also, I am aware of skinzips, but that may not be an option if I need to change anything about the props or placement across multiple truck files.

I think having this feature would be useful because it simplifies the process for reusing meshes in a single resource and, in turn, reduces file size of resource zips, along with the existing benefits of managedmaterials.

I have read up on script inheritance, variables, and imports, so I am not sure if I am missing something that provides what I am looking for already.

ohlidalp commented 1 year ago

Reopening to find a solution for your problem. Your updated description makes sense, and I also skimmed over the discussion in Discord#general.

To explain my attitude towards 'managedmaterials': I'm not a modder so I may be wrong here, but technically they feel like a duplication of the OGRE material script features I linked above: script inheritance and variables. It makes sense historically because OGRE gained these proper feats around v1.10 (under Paroj's supervision), so former ROR devs (using OGRE 1.6-1.8) had no choice but to create their own material generator. But novadays, you should technically be able to produce the exact same materials by writing your own .material file, using inheritance to obtain the behavior of managedmaterial types, and using variables to specify the textures. The same effect as "adding more managedmaterial types" would be simply a matter of defining more builtin materials to inherit from, and with the advantage of using the official supported feats. But I haven't explored this further yet.

Your problem feels related to #2909 which discusses skinzips vs. the "Default skin". I have an approach in mind which should address both problems: Add new truck directive default_skin <skin name or GUID> referencing a skin from .skin file.

This would enable modder to export their meshes with placeholder materials and enforce skinning using existing .skin files and the truck file. It also nicely fits theOGRE model, where a mesh has 1-N submeshes, each submesh references exactly 1 material by name. The modder simply needs to substitute each material individually by .skin.