[Bf-blender-cvs] [a99a62231e0] master: obj: implement support for PBR .mtl extensions
Aras Pranckevicius
noreply at git.blender.org
Tue Sep 13 14:04:25 CEST 2022
Commit: a99a62231e040a15c93add9ffa582ec9e1d9c4f1
Author: Aras Pranckevicius
Date: Tue Sep 13 13:28:57 2022 +0300
Branches: master
https://developer.blender.org/rBa99a62231e040a15c93add9ffa582ec9e1d9c4f1
obj: implement support for PBR .mtl extensions
Implement import & export support for "PBR extensions" in .mtl files
(T101029, also fixes T86736).
Newly supported parameters:
- Roughness (Pr, map_Pr)
- Metallic (Pm, map_Pm)
- Sheen (Ps, map_Ps)
- Clearcoat thickness (Pc) and roughness (Pcr)
- Anisotropy (aniso) and rotation (anisor)
- Transmittance (Tf / Kt)
Exporter has an option to enable these additional PBR parameters
export; defaults to off since not all software understands that.
Exporter UI tweaked and all material-related options were put into
their own separate box.
Added/extended test files in Subversion repository for test coverage.
===================================================================
M source/blender/editors/io/io_obj.c
M source/blender/io/wavefront_obj/IO_wavefront_obj.h
M source/blender/io/wavefront_obj/exporter/obj_export_file_writer.cc
M source/blender/io/wavefront_obj/exporter/obj_export_file_writer.hh
M source/blender/io/wavefront_obj/exporter/obj_export_mtl.cc
M source/blender/io/wavefront_obj/exporter/obj_export_mtl.hh
M source/blender/io/wavefront_obj/exporter/obj_exporter.cc
M source/blender/io/wavefront_obj/importer/obj_import_file_reader.cc
M source/blender/io/wavefront_obj/importer/obj_import_mtl.cc
M source/blender/io/wavefront_obj/tests/obj_exporter_tests.cc
M source/blender/io/wavefront_obj/tests/obj_exporter_tests.hh
M source/blender/io/wavefront_obj/tests/obj_mtl_parser_tests.cc
===================================================================
diff --git a/source/blender/editors/io/io_obj.c b/source/blender/editors/io/io_obj.c
index 619d8a34132..cb8eafeb52d 100644
--- a/source/blender/editors/io/io_obj.c
+++ b/source/blender/editors/io/io_obj.c
@@ -93,6 +93,7 @@ static int wm_obj_export_exec(bContext *C, wmOperator *op)
export_params.path_mode = RNA_enum_get(op->ptr, "path_mode");
export_params.export_triangulated_mesh = RNA_boolean_get(op->ptr, "export_triangulated_mesh");
export_params.export_curves_as_nurbs = RNA_boolean_get(op->ptr, "export_curves_as_nurbs");
+ export_params.export_pbr_extensions = RNA_boolean_get(op->ptr, "export_pbr_extensions");
export_params.export_object_groups = RNA_boolean_get(op->ptr, "export_object_groups");
export_params.export_material_groups = RNA_boolean_get(op->ptr, "export_material_groups");
@@ -118,7 +119,6 @@ static void ui_obj_export_settings(uiLayout *layout, PointerRNA *imfptr)
/* Object Transform options. */
box = uiLayoutBox(layout);
- uiItemL(box, IFACE_("Object Properties"), ICON_OBJECT_DATA);
col = uiLayoutColumn(box, false);
sub = uiLayoutColumnWithHeading(col, false, IFACE_("Limit to"));
uiItemR(sub, imfptr, "export_selected_objects", 0, IFACE_("Selected Only"), ICON_NONE);
@@ -134,27 +134,31 @@ static void ui_obj_export_settings(uiLayout *layout, PointerRNA *imfptr)
sub = uiLayoutColumnWithHeading(col, false, IFACE_("Objects"));
uiItemR(sub, imfptr, "apply_modifiers", 0, IFACE_("Apply Modifiers"), ICON_NONE);
uiItemR(sub, imfptr, "export_eval_mode", 0, IFACE_("Properties"), ICON_NONE);
- sub = uiLayoutColumn(sub, false);
- uiLayoutSetEnabled(sub, export_materials);
- uiItemR(sub, imfptr, "path_mode", 0, IFACE_("Path Mode"), ICON_NONE);
- /* Options for what to write. */
+ /* Geometry options. */
box = uiLayoutBox(layout);
- uiItemL(box, IFACE_("Geometry"), ICON_EXPORT);
col = uiLayoutColumn(box, false);
- sub = uiLayoutColumnWithHeading(col, false, IFACE_("Export"));
+ sub = uiLayoutColumnWithHeading(col, false, IFACE_("Geometry"));
uiItemR(sub, imfptr, "export_uv", 0, IFACE_("UV Coordinates"), ICON_NONE);
uiItemR(sub, imfptr, "export_normals", 0, IFACE_("Normals"), ICON_NONE);
uiItemR(sub, imfptr, "export_colors", 0, IFACE_("Colors"), ICON_NONE);
- uiItemR(sub, imfptr, "export_materials", 0, IFACE_("Materials"), ICON_NONE);
uiItemR(sub, imfptr, "export_triangulated_mesh", 0, IFACE_("Triangulated Mesh"), ICON_NONE);
uiItemR(sub, imfptr, "export_curves_as_nurbs", 0, IFACE_("Curves as NURBS"), ICON_NONE);
+ /* Material options. */
+ box = uiLayoutBox(layout);
+ col = uiLayoutColumn(box, false);
+ sub = uiLayoutColumnWithHeading(col, false, IFACE_("Materials"));
+ uiItemR(sub, imfptr, "export_materials", 0, IFACE_("Export"), ICON_NONE);
+ sub = uiLayoutColumn(sub, false);
+ uiLayoutSetEnabled(sub, export_materials);
+ uiItemR(sub, imfptr, "export_pbr_extensions", 0, IFACE_("PBR Extensions"), ICON_NONE);
+ uiItemR(sub, imfptr, "path_mode", 0, IFACE_("Path Mode"), ICON_NONE);
+
/* Grouping options. */
box = uiLayoutBox(layout);
- uiItemL(box, IFACE_("Grouping"), ICON_GROUP);
col = uiLayoutColumn(box, false);
- sub = uiLayoutColumnWithHeading(col, false, IFACE_("Export"));
+ sub = uiLayoutColumnWithHeading(col, false, IFACE_("Grouping"));
uiItemR(sub, imfptr, "export_object_groups", 0, IFACE_("Object Groups"), ICON_NONE);
uiItemR(sub, imfptr, "export_material_groups", 0, IFACE_("Material Groups"), ICON_NONE);
uiItemR(sub, imfptr, "export_vertex_groups", 0, IFACE_("Vertex Groups"), ICON_NONE);
@@ -165,14 +169,13 @@ static void ui_obj_export_settings(uiLayout *layout, PointerRNA *imfptr)
/* Animation options. */
box = uiLayoutBox(layout);
- uiItemL(box, IFACE_("Animation"), ICON_ANIM);
col = uiLayoutColumn(box, false);
- sub = uiLayoutColumn(col, false);
- uiItemR(sub, imfptr, "export_animation", 0, NULL, ICON_NONE);
+ sub = uiLayoutColumnWithHeading(col, false, IFACE_("Animation"));
+ uiItemR(sub, imfptr, "export_animation", 0, IFACE_("Export"), ICON_NONE);
sub = uiLayoutColumn(sub, true);
+ uiLayoutSetEnabled(sub, export_animation);
uiItemR(sub, imfptr, "start_frame", 0, IFACE_("Frame Start"), ICON_NONE);
uiItemR(sub, imfptr, "end_frame", 0, IFACE_("End"), ICON_NONE);
- uiLayoutSetEnabled(sub, export_animation);
}
static void wm_obj_export_draw(bContext *UNUSED(C), wmOperator *op)
@@ -336,6 +339,12 @@ void WM_OT_obj_export(struct wmOperatorType *ot)
"Export Materials",
"Export MTL library. There must be a Principled-BSDF node for image textures to "
"be exported to the MTL file");
+ RNA_def_boolean(ot->srna,
+ "export_pbr_extensions",
+ false,
+ "Export Materials with PBR Extensions",
+ "Export MTL library using PBR extensions (roughness, metallic, sheen, "
+ "clearcoat, anisotropy, transmission)");
RNA_def_enum(ot->srna,
"path_mode",
io_obj_path_mode,
diff --git a/source/blender/io/wavefront_obj/IO_wavefront_obj.h b/source/blender/io/wavefront_obj/IO_wavefront_obj.h
index 544630c9cc0..0a92bbca477 100644
--- a/source/blender/io/wavefront_obj/IO_wavefront_obj.h
+++ b/source/blender/io/wavefront_obj/IO_wavefront_obj.h
@@ -48,18 +48,15 @@ struct OBJExportParams {
bool export_triangulated_mesh;
bool export_curves_as_nurbs;
ePathReferenceMode path_mode;
+ bool export_pbr_extensions;
/* Grouping options. */
bool export_object_groups;
bool export_material_groups;
bool export_vertex_groups;
- /**
- * Calculate smooth groups from sharp edges.
- */
+ /* Calculate smooth groups from sharp edges. */
bool export_smooth_groups;
- /**
- * Create bitflags instead of the default "0"/"1" group IDs.
- */
+ /* Create bitflags instead of the default "0"/"1" group IDs. */
bool smooth_groups_bitflags;
};
diff --git a/source/blender/io/wavefront_obj/exporter/obj_export_file_writer.cc b/source/blender/io/wavefront_obj/exporter/obj_export_file_writer.cc
index 27526734624..f2547e6fc14 100644
--- a/source/blender/io/wavefront_obj/exporter/obj_export_file_writer.cc
+++ b/source/blender/io/wavefront_obj/exporter/obj_export_file_writer.cc
@@ -493,11 +493,14 @@ void OBJWriter::write_nurbs_curve(FormatHandler &fh, const OBJCurve &obj_nurbs_d
static const char *tex_map_type_to_string[] = {
"map_Kd",
+ "map_Pm",
"map_Ks",
"map_Ns",
- "map_d",
+ "map_Pr",
+ "map_Ps",
"map_refl",
"map_Ke",
+ "map_d",
"map_Bump",
};
BLI_STATIC_ASSERT(ARRAY_SIZE(tex_map_type_to_string) == (int)MTLTexMapType::Count,
@@ -553,16 +556,20 @@ StringRefNull MTLWriter::mtl_file_path() const
return mtl_filepath_;
}
-void MTLWriter::write_bsdf_properties(const MTLMaterial &mtl)
+void MTLWriter::write_bsdf_properties(const MTLMaterial &mtl, bool write_pbr)
{
/* For various material properties, we only capture information
* coming from the texture, or the default value of the socket.
* When the texture is present, do not emit the default value. */
- if (!mtl.tex_map_of_type(MTLTexMapType::SpecularExponent).is_valid()) {
- fmt_handler_.write_mtl_float("Ns", mtl.spec_exponent);
+
+ /* Do not write Ns & Ka when writing in PBR mode. */
+ if (!write_pbr) {
+ if (!mtl.tex_map_of_type(MTLTexMapType::SpecularExponent).is_valid()) {
+ fmt_handler_.write_mtl_float("Ns", mtl.spec_exponent);
+ }
+ fmt_handler_.write_mtl_float3(
+ "Ka", mtl.ambient_color.x, mtl.ambient_color.y, mtl.ambient_color.z);
}
- fmt_handler_.write_mtl_float3(
- "Ka", mtl.ambient_color.x, mtl.ambient_color.y, mtl.ambient_color.z);
if (!mtl.tex_map_of_type(MTLTexMapType::Color).is_valid()) {
fmt_handler_.write_mtl_float3("Kd", mtl.color.x, mtl.color.y, mtl.color.z);
}
@@ -578,6 +585,35 @@ void MTLWriter::write_bsdf_properties(const MTLMaterial &mtl)
fmt_handler_.write_mtl_float("d", mtl.alpha);
}
fmt_handler_.write_mtl_illum(mtl.illum_mode);
+
+ if (write_pbr) {
+ if (!mtl.tex_map_of_type(MTLTexMapType::Roughness).is_valid() && mtl.roughness >= 0.0f) {
+ fmt_handler_.write_mtl_float("Pr", mtl.roughness);
+ }
+ if (!mtl.tex_map_of_type(MTLTexMapType::Metallic).is_valid() && mtl.metallic >= 0.0f) {
+ fmt_handler_.write_mtl_float("Pm", mtl.metallic);
+ }
+ if (!mtl.tex_map_of_type(MTLTexMapType::Sheen).is_valid() && mtl.sheen >= 0.0f) {
+ fmt_handler_.write_mtl_float("Ps", mtl.sheen);
+ }
+ if (mtl.cc_thickness >= 0.0f) {
+ fmt_handler_.write_mtl_float("Pc", mtl.cc_thickness);
+ }
+ if (mtl.cc_roughness >= 0.0f) {
+ fmt_handler_.write_mtl_float("Pcr", mtl.cc_roughness);
+ }
+ if (mtl.aniso >= 0.0f) {
+ fmt_handler_.write_mtl_float("aniso", mtl.aniso);
+ }
+ if (mtl.aniso_rot >= 0.0f) {
+ fmt_handler_.write_mtl_float("anisor", mtl.aniso_rot);
+ }
+ if (mtl.transmit_color.x > 0.0f || mtl.transmit_color.y > 0.0f ||
+ mtl.transmit_color.z > 0.0f) {
+ fmt_handler_.write_mtl_float3(
+ "Tf", mtl.transmit_color.x, mtl.transmit_color.y, mtl.transmit_color.z);
+ }
+ }
}
void MTLWriter::write_texture_map(const MTLMaterial &mtl_material,
@@ -608,9 +644,21 @@ void MTLWriter::write_texture_map(const MTLMaterial &mtl_material,
fmt_handler_.write_mtl_map(tex_map_type_to_string[(int)texture_key], options, path);
}
+static bool is_pbr_map(MTLTexMapType type)
+{
+ return type == MTLTexMapType::Metallic || type == MTLTexMapType::Roughness ||
+ type == MTLTexMapType::Sheen;
+}
+
+static bool is_non_pbr_map(MTLTexMapType type)
+{
+ return type == MTLTexMapType::SpecularExponent || type == MTLTexMapType::Reflection;
+}
+
void MTLWriter::write_materials(const char *blen_filepath,
ePathReferenceMode path_mode,
- const char *dest_dir)
+ const char *dest_dir,
+ bool write_pbr)
{
if (mtlmaterials_.size() == 0) {
return;
@@ -628,12 +676,18 @@ void MTLWriter::write_materials(const char *blen_filepath,
for (const MTLMaterial &mtlmat : mtlmate
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list