[Bf-blender-cvs] [a8993dd12a9] temp-T96709-painting-target: Show all paint resources of material slots.

Jeroen Bakker noreply at git.blender.org
Fri Mar 25 15:25:35 CET 2022


Commit: a8993dd12a9bb475702281cb130630954c8e4862
Author: Jeroen Bakker
Date:   Fri Mar 25 12:21:09 2022 +0100
Branches: temp-T96709-painting-target
https://developer.blender.org/rBa8993dd12a9bb475702281cb130630954c8e4862

Show all paint resources of material slots.

===================================================================

M	release/scripts/startup/bl_ui/space_view3d_toolbar.py
M	source/blender/editors/include/ED_paint.h
M	source/blender/editors/sculpt_paint/CMakeLists.txt
A	source/blender/editors/sculpt_paint/paint_canvas_material.cc
M	source/blender/makesdna/DNA_scene_types.h
M	source/blender/makesrna/intern/rna_sculpt_paint.c

===================================================================

diff --git a/release/scripts/startup/bl_ui/space_view3d_toolbar.py b/release/scripts/startup/bl_ui/space_view3d_toolbar.py
index be62784bb52..3eb82e57ceb 100644
--- a/release/scripts/startup/bl_ui/space_view3d_toolbar.py
+++ b/release/scripts/startup/bl_ui/space_view3d_toolbar.py
@@ -2221,7 +2221,7 @@ class VIEW3D_PT_gpencil_brush_presets(Panel, PresetPanel):
 class VIEW3D_PT_tools_paint_canvas(View3DPanel, Panel):
     bl_category = "Tool"
     bl_context = ".sculpt_mode"  # dot on purpose (access from topbar)
-    bl_label = "Painting Canvas"
+    bl_label = "Canvas"
 
     @classmethod
     def poll(cls, context):
@@ -2248,19 +2248,14 @@ class VIEW3D_PT_tools_paint_canvas(View3DPanel, Panel):
         ob = context.active_object
         settings = context.tool_settings.paint_mode
 
-        layout.prop(settings, "canvas_type")
-        match settings.canvas_type:
-            case 'VERTEX':
+        layout.prop(settings, "canvas_source")
+        match settings.canvas_source:
+            case 'COLOR_ATTRIBUTE':
                 me = ob.data
                 layout.template_list("MESH_UL_vcols", "vcols", me, "vertex_colors", me.vertex_colors, "active_index", rows=2)
 
             case 'MATERIAL':
-                layout.template_list(
-                    "MATERIAL_UL_matslots", "",
-                    ob, "material_slots",
-                    ob, "active_material_index",
-                    rows=2,
-                )
+                layout.prop(settings, "canvas")
 
             case 'IMAGE':
                 layout.template_ID(settings, "image", new="image.new", open="image.open")
diff --git a/source/blender/editors/include/ED_paint.h b/source/blender/editors/include/ED_paint.h
index ca3b232f51c..abaa701bf42 100644
--- a/source/blender/editors/include/ED_paint.h
+++ b/source/blender/editors/include/ED_paint.h
@@ -10,6 +10,8 @@
 extern "C" {
 #endif
 
+struct EnumPropertyItem;
+struct PaintModeSettings;
 struct ImBuf;
 struct Image;
 struct ImageUser;
@@ -107,6 +109,17 @@ void ED_paintcurve_undo_push_end(struct bContext *C);
 /** Export for ED_undo_sys. */
 void ED_paintcurve_undosys_type(struct UndoType *ut);
 
+/* paint_canvas_material.cc */
+int ED_paint_canvas_material_get(const struct bContext *C,
+                                 const struct PaintModeSettings *settings);
+void ED_paint_canvas_material_set(struct bContext *C,
+                                  const struct PaintModeSettings *settings,
+                                  int new_value);
+void ED_paint_canvas_material_itemf(const struct bContext *C,
+                                    const struct PaintModeSettings *settings,
+                                    struct EnumPropertyItem **r_items,
+                                    int *r_totitem);
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/source/blender/editors/sculpt_paint/CMakeLists.txt b/source/blender/editors/sculpt_paint/CMakeLists.txt
index a08ec49d9c4..503664d57de 100644
--- a/source/blender/editors/sculpt_paint/CMakeLists.txt
+++ b/source/blender/editors/sculpt_paint/CMakeLists.txt
@@ -32,6 +32,7 @@ set(SRC
   curves_sculpt_delete.cc
   curves_sculpt_ops.cc
   curves_sculpt_snake_hook.cc
+  paint_canvas_material.cc
   paint_cursor.c
   paint_curve.c
   paint_curve_undo.c
diff --git a/source/blender/editors/sculpt_paint/paint_canvas_material.cc b/source/blender/editors/sculpt_paint/paint_canvas_material.cc
new file mode 100644
index 00000000000..6349dae68c7
--- /dev/null
+++ b/source/blender/editors/sculpt_paint/paint_canvas_material.cc
@@ -0,0 +1,204 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+
+#include "ED_paint.h"
+
+#include "BLI_string_ref.hh"
+#include "BLI_vector.hh"
+
+#include "DNA_image_types.h"
+#include "DNA_material_types.h"
+#include "DNA_mesh_types.h"
+#include "DNA_node_types.h"
+
+#include "BKE_context.h"
+#include "BKE_customdata.h"
+#include "BKE_material.h"
+
+#include "NOD_shader.h"
+
+#include "UI_resources.h"
+
+#include "RNA_access.h"
+#include "RNA_define.h"
+
+namespace blender::ed::sculpt_paint::canvas {
+struct CanvasDef {
+  Material *ma;
+  bNode *node;
+  EnumPropertyItem rna_enum_item;
+
+  CanvasDef(Material *ma, bNode *node) : ma(ma), node(node)
+  {
+    init_rna_enum_item();
+  }
+
+ private:
+  void init_rna_enum_item()
+  {
+    switch (node->type) {
+      case SH_NODE_TEX_IMAGE: {
+        Image *image = static_cast<Image *>(static_cast<void *>(node->id));
+        init_rna_enum_item_image(image);
+        break;
+      }
+
+      case SH_NODE_ATTRIBUTE: {
+        NodeShaderAttribute *attribute = static_cast<NodeShaderAttribute *>(node->storage);
+        init_rna_enum_item_color_attribute(attribute);
+      }
+      default:
+        break;
+    }
+  }
+
+  void init_rna_enum_item_image(Image *image)
+  {
+    BLI_assert(image != nullptr);
+    rna_enum_item.value = 0;
+    rna_enum_item.identifier = "IMAGE1";
+    rna_enum_item.icon = ICON_IMAGE;
+    rna_enum_item.name = image->id.name + 2;
+    rna_enum_item.description = image->id.name + 2;
+  }
+
+  void init_rna_enum_item_color_attribute(const NodeShaderAttribute *attribute)
+  {
+    rna_enum_item.value = 0;
+    rna_enum_item.identifier = "COLOR_1";
+    rna_enum_item.icon = ICON_COLOR;
+    rna_enum_item.name = attribute->name;
+    rna_enum_item.description = attribute->name;
+  }
+
+ public:
+  static bool supports(const Object *ob, bNode *node)
+  {
+    switch (node->type) {
+      case SH_NODE_TEX_IMAGE:
+        return node->id != nullptr;
+
+      case SH_NODE_ATTRIBUTE: {
+        NodeShaderAttribute *attribute = static_cast<NodeShaderAttribute *>(node->storage);
+        if (attribute->type != SHD_ATTRIBUTE_GEOMETRY) {
+          return false;
+        }
+        if (ob->type != OB_MESH) {
+          return false;
+        }
+
+        const struct Mesh *mesh = static_cast<Mesh *>(ob->data);
+        int layer = CustomData_get_named_layer_index(&mesh->vdata, CD_PROP_COLOR, attribute->name);
+        return layer != -1;
+      }
+
+      default:
+        return false;
+    }
+  }
+
+  bool operator<(const CanvasDef &rhs) const
+  {
+    if (node->type != rhs.node->type) {
+      return node->type == SH_NODE_TEX_IMAGE;
+    }
+    return StringRef(rna_enum_item.name) < StringRef(rhs.rna_enum_item.name);
+  }
+};
+
+struct MaterialWrapper {
+  Material *ma;
+
+  MaterialWrapper(Material *ma) : ma(ma)
+  {
+  }
+
+  Vector<CanvasDef> canvases(const Object *ob)
+  {
+    Vector<CanvasDef> result;
+    if (!ma->use_nodes) {
+      return result;
+    }
+
+    BLI_assert(ma->nodetree != nullptr);
+    LISTBASE_FOREACH (bNode *, node, &ma->nodetree->nodes) {
+      if (!CanvasDef::supports(ob, node)) {
+        continue;
+      }
+      result.append(CanvasDef(ma, node));
+    }
+    std::sort(result.begin(), result.end());
+
+    return result;
+  }
+
+  void append_rna_itemf(struct EnumPropertyItem **r_items, int *r_totitem)
+  {
+    EnumPropertyItem item;
+    item.value = 0;
+    item.identifier = "";
+    item.icon = ICON_MATERIAL;
+    item.name = ma->id.name + 2;
+    item.description = ma->id.name + 2;
+    RNA_enum_item_add(r_items, r_totitem, &item);
+  }
+};
+
+static Vector<MaterialWrapper> list_materials(Object *ob)
+{
+  Vector<MaterialWrapper> result;
+  struct Material ***matarar = BKE_object_material_array_p(ob);
+  short *tot_colp = BKE_object_material_len_p(ob);
+  if (tot_colp == nullptr || matarar == nullptr) {
+    return result;
+  }
+
+  for (int a = 0; a < *tot_colp; a++) {
+    Material *ma = (*matarar)[a];
+    if (ma == nullptr) {
+      continue;
+    }
+    result.append(ma);
+  }
+
+  return result;
+}
+
+}  // namespace blender::ed::sculpt_paint::canvas
+
+extern "C" {
+
+using namespace blender;
+using namespace blender::ed::sculpt_paint::canvas;
+
+int ED_paint_canvas_material_get(const struct bContext *C,
+                                 const struct PaintModeSettings *settings)
+{
+  return 0;
+}
+
+void ED_paint_canvas_material_set(struct bContext *C,
+                                  const struct PaintModeSettings *settings,
+                                  int new_value)
+{
+}
+
+void ED_paint_canvas_material_itemf(const struct bContext *C,
+                                    const struct PaintModeSettings *settings,
+                                    struct EnumPropertyItem **r_items,
+                                    int *r_totitem)
+{
+  Object *ob = CTX_data_active_object(C);
+  blender::Vector<MaterialWrapper> materials = list_materials(ob);
+  for (MaterialWrapper &mat : materials) {
+    Vector<CanvasDef> canvases = mat.canvases(ob);
+    if (canvases.is_empty()) {
+      continue;
+    }
+
+    mat.append_rna_itemf(r_items, r_totitem);
+    for (const CanvasDef &canvas : canvases) {
+      RNA_enum_item_add(r_items, r_totitem, &canvas.rna_enum_item);
+    }
+  }
+}
+}
\ No newline at end of file
diff --git a/source/blender/makesdna/DNA_scene_types.h b/source/blender/makesdna/DNA_scene_types.h
index c1fa4bf40e9..936d9d6a203 100644
--- a/source/blender/makesdna/DNA_scene_types.h
+++ b/source/blender/makesdna/DNA_scene_types.h
@@ -926,11 +926,11 @@ typedef struct ImagePaintSettings {
 /* Paint mode settings */
 
 typedef struct PaintModeSettings {
-  /** Type of canvas to paint on (ePaintCanvasType) */
-  char canvas_type;
+  /** Source to select canvas from to paint on (ePaintCanvasSource) */
+  char canvas_source;
   char _pad[7];
 
-  /** Selected image when canvas_type=PAINT_CANVAS_IMAGE. */
+  /** Selected image when canvas_source=PAINT_CANVAS_IMAGE. */
   Image *image;
 
 } PaintModeSettings;
@@ -2289,15 +2289,15 @@ typedef enum eImagePaintMode {
   IMAGEPAINT_MODE_IMAGE = 1,    /* select texture paint image directly */
 } eImagePaintMode;
 
-/** PaintModeSettings.canvas_type */
-typedef enum ePaintCanvasType {
-  /** Paint on the active vertex color layer. */
-  PAINT_CANVAS_VERTEX = 0,
+/** PaintModeSettings.canvas_source */
+typedef enum ePaintCanvasSource {
+  /** Paint on the active color attribute (vertex color) layer. */
+  PAINT_CANVAS_COLOR_ATTRIBUTE = 0,
   /** Paint on the active texture of the active material slot. */
   PAINT_CANVAS_MATERIAL = 1,
   /** Paint on a selected image. */
   PAINT_CANVAS_IMAGE = 2,
-} ePain

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list