From 4e09bebde26ffce4242ad20d56f197e65816f1e5 Mon Sep 17 00:00:00 2001 From: Falk David Date: Mon, 24 Jun 2024 14:36:15 +0200 Subject: [PATCH 01/13] WIP --- source/blender/blenkernel/BKE_attribute.h | 3 + .../blender/blenkernel/BKE_grease_pencil.hh | 3 + source/blender/blenkernel/intern/attribute.cc | 24 ++ .../blenkernel/intern/grease_pencil.cc | 8 + .../makesdna/DNA_grease_pencil_types.h | 2 + .../blender/makesrna/intern/rna_attribute.cc | 48 ++- .../makesrna/intern/rna_grease_pencil.cc | 342 ++++++++++++++++++ 7 files changed, 428 insertions(+), 2 deletions(-) diff --git a/source/blender/blenkernel/BKE_attribute.h b/source/blender/blenkernel/BKE_attribute.h index 174d217695b..9d70c93fe7e 100644 --- a/source/blender/blenkernel/BKE_attribute.h +++ b/source/blender/blenkernel/BKE_attribute.h @@ -27,6 +27,7 @@ struct Mesh; struct PointCloud; struct Curves; struct GreasePencil; +struct GreasePencilDrawing; typedef enum AttrDomainMask { ATTR_DOMAIN_MASK_POINT = (1 << 0), @@ -44,6 +45,7 @@ enum class AttributeOwnerType { PointCloud, Curves, GreasePencil, + GreasePencilDrawing, }; class AttributeOwner { @@ -63,6 +65,7 @@ class AttributeOwner { PointCloud *get_pointcloud() const; Curves *get_curves() const; GreasePencil *get_grease_pencil() const; + GreasePencilDrawing *get_grease_pencil_drawing() const; }; #define ATTR_DOMAIN_AS_MASK(domain) ((AttrDomainMask)((1 << (int)(domain)))) diff --git a/source/blender/blenkernel/BKE_grease_pencil.hh b/source/blender/blenkernel/BKE_grease_pencil.hh index 4e00d0d901b..a384c3db28b 100644 --- a/source/blender/blenkernel/BKE_grease_pencil.hh +++ b/source/blender/blenkernel/BKE_grease_pencil.hh @@ -1003,6 +1003,9 @@ inline bool GreasePencil::has_active_group() const return (this->active_node != nullptr) && (this->active_node->wrap().is_group()); } +bool BKE_grease_pencil_drawing_attribute_required(const GreasePencilDrawing * /*drawing*/, + const char *name); + void *BKE_grease_pencil_add(Main *bmain, const char *name); GreasePencil *BKE_grease_pencil_new_nomain(); GreasePencil *BKE_grease_pencil_copy_for_eval(const GreasePencil *grease_pencil_src); diff --git a/source/blender/blenkernel/intern/attribute.cc b/source/blender/blenkernel/intern/attribute.cc index d099d9eeb70..5a442fad1e4 100644 --- a/source/blender/blenkernel/intern/attribute.cc +++ b/source/blender/blenkernel/intern/attribute.cc @@ -97,6 +97,13 @@ GreasePencil *AttributeOwner::get_grease_pencil() const return reinterpret_cast(ptr_); } +GreasePencilDrawing *AttributeOwner::get_grease_pencil_drawing() const +{ + BLI_assert(this->is_valid()); + BLI_assert(type_ == AttributeOwnerType::GreasePencilDrawing); + return reinterpret_cast(ptr_); +} + struct DomainInfo { CustomData *customdata = nullptr; int length = 0; @@ -152,6 +159,14 @@ static std::array get_domains(const AttributeOwner info[int(AttrDomain::Layer)].length = grease_pencil->layers().size(); break; } + case AttributeOwnerType::GreasePencilDrawing: { + blender::bke::greasepencil::Drawing &drawing = owner.get_grease_pencil_drawing()->wrap(); + info[int(AttrDomain::Point)].customdata = &drawing.geometry.point_data; + info[int(AttrDomain::Point)].length = drawing.geometry.point_num; + info[int(AttrDomain::Curve)].customdata = &drawing.geometry.curve_data; + info[int(AttrDomain::Curve)].length = drawing.geometry.curve_num; + break; + } } return info; @@ -182,6 +197,10 @@ static std::optional get_attribute_acces GreasePencil &grease_pencil = *owner.get_grease_pencil(); return grease_pencil.attributes_for_write(); } + case AttributeOwnerType::GreasePencilDrawing: { + blender::bke::greasepencil::Drawing &drawing = owner.get_grease_pencil_drawing()->wrap(); + return drawing.strokes_for_write().attributes_for_write(); + } } return {}; } @@ -763,6 +782,8 @@ bool BKE_attribute_required(const AttributeOwner &owner, const char *name) return BKE_mesh_attribute_required(name); case AttributeOwnerType::GreasePencil: return false; + case AttributeOwnerType::GreasePencilDrawing: + return BKE_grease_pencil_drawing_attribute_required(owner.get_grease_pencil_drawing(), name); } return false; } @@ -825,6 +846,9 @@ int *BKE_attributes_active_index_p(AttributeOwner &owner) case AttributeOwnerType::GreasePencil: { return &(owner.get_grease_pencil())->attributes_active_index; } + case AttributeOwnerType::GreasePencilDrawing: { + return &(owner.get_grease_pencil_drawing())->attributes_active_index; + } } return nullptr; } diff --git a/source/blender/blenkernel/intern/grease_pencil.cc b/source/blender/blenkernel/intern/grease_pencil.cc index f952896d1de..fbfb4ef7d65 100644 --- a/source/blender/blenkernel/intern/grease_pencil.cc +++ b/source/blender/blenkernel/intern/grease_pencil.cc @@ -70,6 +70,8 @@ using blender::Span; using blender::uint3; using blender::VectorSet; +static const char *ATTR_POSITION = "position"; + /* Forward declarations. */ static void read_drawing_array(GreasePencil &grease_pencil, BlendDataReader *reader); static void write_drawing_array(GreasePencil &grease_pencil, BlendWriter *writer); @@ -1735,6 +1737,12 @@ std::optional> GreasePencilDrawingEditHints::positions_for_w /** \name Grease Pencil kernel functions * \{ */ +bool BKE_grease_pencil_drawing_attribute_required(const GreasePencilDrawing * /*drawing*/, + const char *name) +{ + return STREQ(name, ATTR_POSITION); +} + void *BKE_grease_pencil_add(Main *bmain, const char *name) { GreasePencil *grease_pencil = reinterpret_cast(BKE_id_new(bmain, ID_GP, name)); diff --git a/source/blender/makesdna/DNA_grease_pencil_types.h b/source/blender/makesdna/DNA_grease_pencil_types.h index 9a5ea66751d..81125f5242b 100644 --- a/source/blender/makesdna/DNA_grease_pencil_types.h +++ b/source/blender/makesdna/DNA_grease_pencil_types.h @@ -105,6 +105,8 @@ typedef struct GreasePencilDrawing { * The stroke data for this drawing. */ CurvesGeometry geometry; + int attributes_active_index; + char _pad[4]; /** * Runtime data on the drawing. */ diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 2a6e9f61141..2a2b80d27dd 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -16,6 +16,7 @@ #include "DNA_curves_types.h" #include "DNA_customdata_types.h" +#include "DNA_grease_pencil_types.h" #include "DNA_mesh_types.h" #include "DNA_meshdata_types.h" #include "DNA_pointcloud_types.h" @@ -181,6 +182,49 @@ const EnumPropertyItem rna_enum_attribute_curves_domain_items[] = { # include "WM_api.hh" +static AttributeOwner owner_from_attribute_pointer_rna(PointerRNA *ptr) +{ + ID *owner_id = static_cast(ptr->owner_id); + const CustomDataLayer *layer = static_cast(ptr->data); + if (GS(owner_id->name) == ID_GP) { + GreasePencil *grease_pencil = reinterpret_cast(owner_id); + /* First check the layer attributes. */ + CustomData *layers_data = &grease_pencil->layers_data; + for (int i = 0; i < layers_data->totlayer; i++) { + if (&layers_data->layers[i] == layer) { + return AttributeOwner(AttributeOwnerType::GreasePencil, grease_pencil); + } + } + /* Now check all the drawings. */ + for (GreasePencilDrawingBase *base : grease_pencil->drawings()) { + if (base->type == GP_DRAWING) { + GreasePencilDrawing *drawing = reinterpret_cast(base); + CustomData *curve_data = &drawing->geometry.curve_data; + for (int i = 0; i < curve_data->totlayer; i++) { + if (&curve_data->layers[i] == layer) { + return AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + } + } + CustomData *point_data = &drawing->geometry.point_data; + for (int i = 0; i < point_data->totlayer; i++) { + if (&point_data->layers[i] == layer) { + return AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + } + } + } + } + } + return AttributeOwner::from_id(ptr->owner_id); +} + +static AttributeOwner owner_from_pointer_rna(PointerRNA *ptr) +{ + if (ptr->type == &RNA_GreasePencilDrawing) { + return AttributeOwner(AttributeOwnerType::GreasePencilDrawing, ptr->data); + } + return AttributeOwner::from_id(ptr->owner_id); +} + /* Attribute */ static std::optional rna_Attribute_path(const PointerRNA *ptr) @@ -232,14 +276,14 @@ static StructRNA *rna_Attribute_refine(PointerRNA *ptr) static void rna_Attribute_name_set(PointerRNA *ptr, const char *value) { const CustomDataLayer *layer = (const CustomDataLayer *)ptr->data; - AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); + AttributeOwner owner = owner_from_attribute_pointer_rna(ptr); BKE_attribute_rename(owner, layer->name, value, nullptr); } static int rna_Attribute_name_editable(const PointerRNA *ptr, const char **r_info) { CustomDataLayer *layer = static_cast(ptr->data); - AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); + AttributeOwner owner = owner_from_attribute_pointer_rna(const_cast(ptr)); if (BKE_attribute_required(owner, layer->name)) { *r_info = N_("Cannot modify name of required geometry attribute"); return false; diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index cf6e2515390..8bf212ec89d 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -11,6 +11,7 @@ #include "BLI_string.h" #include "DNA_grease_pencil_types.h" +#include "DNA_scene_types.h" #include "RNA_access.hh" #include "RNA_define.hh" @@ -73,6 +74,174 @@ static void rna_grease_pencil_dependency_update(Main *bmain, Scene * /*scene*/, WM_main_add_notifier(NC_GPENCIL | NA_EDITED, rna_grease_pencil(ptr)); } +static void rna_GreasePencilLayer_frames_begin(CollectionPropertyIterator *iter, PointerRNA *ptr) +{ + using namespace blender::bke::greasepencil; + Layer &layer = static_cast(ptr->data)->wrap(); + blender::Span sorted_keys = layer.sorted_keys(); + + rna_iterator_array_begin( + iter, (void *)sorted_keys.data(), sizeof(FramesMapKeyT), sorted_keys.size(), false, nullptr); +} + +static PointerRNA rna_GreasePencilLayer_frames_get(CollectionPropertyIterator *iter) +{ + using namespace blender::bke::greasepencil; + const FramesMapKeyT frame_key = *static_cast(rna_iterator_array_get(iter)); + const Layer &layer = static_cast(iter->parent.data)->wrap(); + const GreasePencilFrame *frame = layer.frames().lookup_ptr(frame_key); + return rna_pointer_inherit_refine(&iter->parent, + &RNA_GreasePencilFrame, + static_cast(const_cast(frame))); +} + +static int rna_GreasePencilLayer_frames_length(PointerRNA *ptr) +{ + using namespace blender::bke::greasepencil; + Layer &layer = static_cast(ptr->data)->wrap(); + return layer.frames().size(); +} + +static bool rna_GreasePencilLayer_frames_lookup_int(PointerRNA *ptr, int index, PointerRNA *r_ptr) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *rna_grease_pencil(ptr); + Layer &layer = static_cast(ptr->data)->wrap(); + if (index < 0 || index >= layer.sorted_keys().size()) { + return false; + } + const FramesMapKeyT frame_key = layer.sorted_keys()[index]; + const GreasePencilFrame *frame = layer.frames().lookup_ptr(frame_key); + + r_ptr->owner_id = &grease_pencil.id; + r_ptr->type = &RNA_GreasePencilFrame; + r_ptr->data = static_cast(const_cast(frame)); + return true; +} + +static GreasePencilFrame *rna_Frames_frame_new(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int frame_number) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (layer.frames().contains(frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", frame_number); + return nullptr; + } + + grease_pencil.insert_frame(layer, frame_number, 0, BEZT_KEYTYPE_KEYFRAME); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + + return layer.frame_at(frame_number); +} + +static void rna_Frames_frame_remove(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int frame_number) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (!layer.frames().contains(frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", frame_number); + return; + } + + if (grease_pencil.remove_frames(layer, {frame_number})) { + DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + } +} + +static GreasePencilFrame *rna_Frames_frame_copy(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int from_frame_number, + int to_frame_number, + bool instance_drawing) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (!layer.frames().contains(from_frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", from_frame_number); + return nullptr; + } + if (layer.frames().contains(to_frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", to_frame_number); + return nullptr; + } + + grease_pencil.insert_duplicate_frame( + layer, from_frame_number, to_frame_number, instance_drawing); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + + return layer.frame_at(to_frame_number); +} + +static std::pair find_layer_of_frame( + const GreasePencil &grease_pencil, const GreasePencilFrame &find_frame) +{ + using namespace blender::bke::greasepencil; + for (const Layer *layer : grease_pencil.layers()) { + for (const auto &[key, frame] : layer->frames().items()) { + if (&frame == &find_frame) { + return {int(key), layer}; + } + } + } + return {0, nullptr}; +} + +static PointerRNA rna_Frame_drawing_get(PointerRNA *ptr) +{ + using namespace blender::bke::greasepencil; + const GreasePencil &grease_pencil = *rna_grease_pencil(ptr); + GreasePencilFrame &frame_to_find = *static_cast(ptr->data); + if (frame_to_find.is_end()) { + return PointerRNA_NULL; + } + + /* RNA doesn't give access to the parented layer object, so we have to iterate over all layers + * and search for the matching GreasePencilFrame pointer in the frames collection. */ + auto [frame_number, this_layer] = find_layer_of_frame(grease_pencil, frame_to_find); + if (this_layer == nullptr) { + return PointerRNA_NULL; + } + + const Drawing *drawing = grease_pencil.get_drawing_at(*this_layer, frame_number); + return rna_pointer_inherit_refine( + ptr, &RNA_GreasePencilDrawing, static_cast(const_cast(drawing))); +} + +static int rna_Frame_frame_number_get(PointerRNA *ptr) +{ + using namespace blender::bke::greasepencil; + const GreasePencil &grease_pencil = *rna_grease_pencil(ptr); + GreasePencilFrame &frame_to_find = *static_cast(ptr->data); + + /* RNA doesn't give access to the parented layer object, so we have to iterate over all layers + * and search for the matching GreasePencilFrame pointer in the frames collection. */ + auto [frame_number, this_layer] = find_layer_of_frame(grease_pencil, frame_to_find); + /* Layer should exist. */ + BLI_assert(this_layer != nullptr); + return frame_number; +} + +static void rna_Frame_frame_number_index_range( + PointerRNA * /*ptr*/, int *min, int *max, int * /*softmin*/, int * /*softmax*/) +{ + *min = MINAFRAME; + *max = MAXFRAME; +} + static void rna_grease_pencil_layer_mask_name_get(PointerRNA *ptr, char *dst) { using namespace blender; @@ -127,6 +296,13 @@ static void rna_grease_pencil_active_mask_index_range( *max = max_ii(0, BLI_listbase_count(&layer->masks) - 1); } +static GreasePencilFrame *rna_GreasePencilLayer_get_frame_at(GreasePencilLayer *layer, + int frame_number) +{ + using namespace blender::bke::greasepencil; + return static_cast(layer)->frame_at(frame_number); +} + static void rna_iterator_grease_pencil_layers_begin(CollectionPropertyIterator *iter, PointerRNA *ptr) { @@ -541,6 +717,139 @@ static int rna_iterator_grease_pencil_layer_groups_length(PointerRNA *ptr) #else +static void rna_def_grease_pencil_drawing(BlenderRNA *brna) +{ + StructRNA *srna; + PropertyRNA *prop; + + static const EnumPropertyItem rna_enum_drawing_type_items[] = { + {GP_DRAWING, "DRAWING", 0, "Drawing", ""}, + {GP_DRAWING_REFERENCE, "REFERENCE", 0, "Reference", ""}, + {0, nullptr, 0, nullptr, nullptr}}; + + srna = RNA_def_struct(brna, "GreasePencilDrawing", nullptr); + RNA_def_struct_sdna(srna, "GreasePencilDrawing"); + RNA_def_struct_ui_text(srna, "Grease Pencil Drawing", "A Grease Pencil drawing"); + + /* Type. */ + prop = RNA_def_property(srna, "type", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, nullptr, "base.type"); + RNA_def_property_enum_items(prop, rna_enum_drawing_type_items); + RNA_def_parameter_clear_flags(prop, PROP_EDITABLE, ParameterFlag(0)); + RNA_def_property_ui_text(prop, "Type", "Drawing type"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + + /* Attributes. */ + rna_def_attributes_common(srna); +} + +static void rna_def_grease_pencil_frame(BlenderRNA *brna) +{ + StructRNA *srna; + PropertyRNA *prop; + + srna = RNA_def_struct(brna, "GreasePencilFrame", nullptr); + RNA_def_struct_sdna(srna, "GreasePencilFrame"); + RNA_def_struct_ui_text(srna, "Grease Pencil Frame", "A Grease Pencil keyframe"); + + /* Drawing. */ + prop = RNA_def_property(srna, "drawing", PROP_POINTER, PROP_NONE); + RNA_def_property_struct_type(prop, "GreasePencilDrawing"); + RNA_def_property_pointer_funcs(prop, "rna_Frame_drawing_get", nullptr, nullptr, nullptr); + RNA_def_property_ui_text(prop, "Drawing", "A Grease Pencil drawing"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + + /* Frame number. */ + prop = RNA_def_property(srna, "frame_number", PROP_INT, PROP_NONE); + /* TODO: Make property editable, ensure frame number isn't already in use. */ + RNA_def_property_clear_flag(prop, PROP_EDITABLE); + RNA_def_property_int_funcs( + prop, "rna_Frame_frame_number_get", nullptr, "rna_Frame_frame_number_index_range"); + RNA_def_property_range(prop, MINAFRAME, MAXFRAME); + RNA_def_property_ui_text(prop, "Frame Number", "The frame number in the scene"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + + /* Selection status. */ + prop = RNA_def_property(srna, "select", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, nullptr, "flag", GP_FRAME_SELECTED); + RNA_def_property_ui_text(prop, "Select", "Frame Selection in the Dope Sheet"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); +} + +static void rna_def_grease_pencil_frames_api(BlenderRNA *brna, PropertyRNA *cprop) +{ + StructRNA *srna; + + FunctionRNA *func; + PropertyRNA *parm; + + RNA_def_property_srna(cprop, "GreasePencilFrames"); + srna = RNA_def_struct(brna, "GreasePencilFrames", nullptr); + RNA_def_struct_sdna(srna, "GreasePencilLayer"); + RNA_def_struct_ui_text(srna, "Grease Pencil Frames", "Collection of Grease Pencil frames"); + + func = RNA_def_function(srna, "new", "rna_Frames_frame_new"); + RNA_def_function_ui_description(func, "Add a new Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Frame Number", + "The frame on which the drawing appears", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "", "The newly created frame"); + RNA_def_function_return(func, parm); + + func = RNA_def_function(srna, "remove", "rna_Frames_frame_remove"); + RNA_def_function_ui_description(func, "Remove a Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Frame Number", + "The frame number of the frame to remove", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + func = RNA_def_function(srna, "copy", "rna_Frames_frame_copy"); + RNA_def_function_ui_description(func, "Copy a Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "from_frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Source Frame Number", + "The frame number of the source frame", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_int(func, + "to_frame_number", + 2, + MINAFRAME, + MAXFRAME, + "Frame Number of Copy", + "The frame number to copy the frame to", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_boolean(func, + "instance_drawing", + false, + "Instance Drawing", + "Let the copied frame use the same drawing as the source"); + parm = RNA_def_pointer(func, "copy", "GreasePencilFrame", "", "The newly copied frame"); + RNA_def_function_return(func, parm); +} + static void rna_def_grease_pencil_layers_mask_api(BlenderRNA *brna, PropertyRNA *cprop) { StructRNA *srna; @@ -595,6 +904,20 @@ static void rna_def_grease_pencil_layer_mask(BlenderRNA *brna) RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); } +static void rna_def_grease_pencil_layer_api(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func = RNA_def_function(srna, "get_frame_at", "rna_GreasePencilLayer_get_frame_at"); + RNA_def_function_ui_description(func, "Get the frame at given frame number"); + parm = RNA_def_int( + func, "frame_number", 1, MINAFRAME, MAXFRAME, "Frame Number", "", MINAFRAME, MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "Frame", ""); + RNA_def_function_return(func, parm); +} + static void rna_def_grease_pencil_layer(BlenderRNA *brna) { StructRNA *srna; @@ -626,6 +949,21 @@ static void rna_def_grease_pencil_layer(BlenderRNA *brna) RNA_def_struct_name_property(srna, prop); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA | NA_RENAME, "rna_grease_pencil_update"); + /* Frames. */ + prop = RNA_def_property(srna, "frames", PROP_COLLECTION, PROP_NONE); + RNA_def_property_struct_type(prop, "GreasePencilFrame"); + RNA_def_property_ui_text(prop, "Frames", "Grease Pencil frames"); + RNA_def_property_collection_funcs(prop, + "rna_GreasePencilLayer_frames_begin", + "rna_iterator_array_next", + "rna_iterator_array_end", + "rna_GreasePencilLayer_frames_get", + "rna_GreasePencilLayer_frames_length", + "rna_GreasePencilLayer_frames_lookup_int", + nullptr, + nullptr); + rna_def_grease_pencil_frames_api(brna, prop); + /* Mask Layers */ prop = RNA_def_property(srna, "mask_layers", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, nullptr, "masks", nullptr); @@ -794,6 +1132,8 @@ static void rna_def_grease_pencil_layer(BlenderRNA *brna) prop, "rna_GreasePencilLayer_parent_layer_group_get", nullptr, nullptr, nullptr); RNA_def_property_ui_text( prop, "Parent Layer Group", "The parent layer group this layer is part of"); + + rna_def_grease_pencil_layer_api(srna); } static void rna_def_grease_pencil_layers_api(BlenderRNA *brna, PropertyRNA *cprop) @@ -1274,6 +1614,8 @@ void RNA_def_grease_pencil(BlenderRNA *brna) rna_def_grease_pencil_layer(brna); rna_def_grease_pencil_layer_mask(brna); rna_def_grease_pencil_layer_group(brna); + rna_def_grease_pencil_frame(brna); + rna_def_grease_pencil_drawing(brna); } #endif -- 2.30.2 From 89893905e8aa55020bc274adb28b0154e0bd74cf Mon Sep 17 00:00:00 2001 From: Falk David Date: Tue, 16 Jul 2024 14:45:38 +0200 Subject: [PATCH 02/13] Attribute API for grease pencil drawings --- .../makesdna/DNA_grease_pencil_types.h | 3 + .../blender/makesrna/intern/rna_attribute.cc | 303 +++++++++++++----- .../makesrna/intern/rna_grease_pencil.cc | 2 +- 3 files changed, 227 insertions(+), 81 deletions(-) diff --git a/source/blender/makesdna/DNA_grease_pencil_types.h b/source/blender/makesdna/DNA_grease_pencil_types.h index 8af6d2420a5..4c98837f54d 100644 --- a/source/blender/makesdna/DNA_grease_pencil_types.h +++ b/source/blender/makesdna/DNA_grease_pencil_types.h @@ -105,6 +105,9 @@ typedef struct GreasePencilDrawing { * The stroke data for this drawing. */ CurvesGeometry geometry; + /** + * Active attribute in the UI. + */ int attributes_active_index; char _pad[4]; /** diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 84a4666da45..99d7bb32431 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -182,10 +182,14 @@ const EnumPropertyItem rna_enum_attribute_curves_domain_items[] = { # include "WM_api.hh" +/* Attribute */ + static AttributeOwner owner_from_attribute_pointer_rna(PointerRNA *ptr) { - ID *owner_id = static_cast(ptr->owner_id); + ID *owner_id = ptr->owner_id; const CustomDataLayer *layer = static_cast(ptr->data); + /* TODO: Because we don't know the path to the `ptr`, we need to look though all possible + * candidates and search for the `layer` currently. This should be just a simple lookup. */ if (GS(owner_id->name) == ID_GP) { GreasePencil *grease_pencil = reinterpret_cast(owner_id); /* First check the layer attributes. */ @@ -214,35 +218,19 @@ static AttributeOwner owner_from_attribute_pointer_rna(PointerRNA *ptr) } } } - return AttributeOwner::from_id(ptr->owner_id); + return AttributeOwner::from_id(owner_id); } static AttributeOwner owner_from_pointer_rna(PointerRNA *ptr) { + /* For non-ID attribute owners, check the `ptr->type` to derive the `AttributeOwnerType` + * and construct an `AttributeOwner` from that type and `ptr->data`. */ if (ptr->type == &RNA_GreasePencilDrawing) { return AttributeOwner(AttributeOwnerType::GreasePencilDrawing, ptr->data); } return AttributeOwner::from_id(ptr->owner_id); } -/* Attribute */ - -static AttributeOwner owner_from_attribute_pointer_rna(PointerRNA *ptr) -{ - ID *id = ptr->owner_id; - /* TODO: For non-ID attribute owners, iterate through the ID and find the owner that owns the - * `CustomDataLayer` that points to `ptr->data`. */ - return AttributeOwner::from_id(id); -} - -static AttributeOwner owner_from_pointer_rna(PointerRNA *ptr) -{ - ID *id = ptr->owner_id; - /* TODO: For non-ID attribute owners, check the `ptr->type` to derive the `AttributeOwnerType` - * and construct an `AttributeOwner` from that type and `ptr->data`. */ - return AttributeOwner::from_id(id); -} - static std::optional rna_Attribute_path(const PointerRNA *ptr) { const CustomDataLayer *layer = static_cast(ptr->data); @@ -500,7 +488,7 @@ static void rna_StringAttributeValue_s_set(PointerRNA *ptr, const char *value) /* Attribute Group */ -static PointerRNA rna_AttributeGroup_new( +static PointerRNA rna_AttributeGroupID_new( ID *id, ReportList *reports, const char *name, const int type, const int domain) { AttributeOwner owner = AttributeOwner::from_id(id); @@ -528,7 +516,7 @@ static PointerRNA rna_AttributeGroup_new( return ptr; } -static void rna_AttributeGroup_remove(ID *id, ReportList *reports, PointerRNA *attribute_ptr) +static void rna_AttributeGroupID_remove(ID *id, ReportList *reports, PointerRNA *attribute_ptr) { AttributeOwner owner = AttributeOwner::from_id(id); const CustomDataLayer *layer = (const CustomDataLayer *)attribute_ptr->data; @@ -648,40 +636,40 @@ int rna_AttributeGroup_length(PointerRNA *ptr) return BKE_attributes_length(owner, ATTR_DOMAIN_MASK_ALL, CD_MASK_PROP_ALL); } -static int rna_AttributeGroup_active_index_get(PointerRNA *ptr) +static int rna_AttributeGroupID_active_index_get(PointerRNA *ptr) { - AttributeOwner owner = owner_from_pointer_rna(ptr); + AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); return *BKE_attributes_active_index_p(owner); } -static PointerRNA rna_AttributeGroup_active_get(PointerRNA *ptr) +static PointerRNA rna_AttributeGroupID_active_get(PointerRNA *ptr) { - AttributeOwner owner = owner_from_pointer_rna(ptr); + AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); CustomDataLayer *layer = BKE_attributes_active_get(owner); PointerRNA attribute_ptr = RNA_pointer_create(ptr->owner_id, &RNA_Attribute, layer); return attribute_ptr; } -static void rna_AttributeGroup_active_set(PointerRNA *ptr, - PointerRNA attribute_ptr, - ReportList * /*reports*/) +static void rna_AttributeGroupID_active_set(PointerRNA *ptr, + PointerRNA attribute_ptr, + ReportList * /*reports*/) { - AttributeOwner owner = owner_from_pointer_rna(ptr); + AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); CustomDataLayer *layer = static_cast(attribute_ptr.data); BKE_attributes_active_set(owner, layer->name); } -static void rna_AttributeGroup_active_index_set(PointerRNA *ptr, int value) +static void rna_AttributeGroupID_active_index_set(PointerRNA *ptr, int value) { - AttributeOwner owner = owner_from_pointer_rna(ptr); + AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); *BKE_attributes_active_index_p(owner) = value; } -static void rna_AttributeGroup_active_index_range( +static void rna_AttributeGroupID_active_index_range( PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax) { - AttributeOwner owner = owner_from_pointer_rna(ptr); + AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); *min = 0; *max = BKE_attributes_length(owner, ATTR_DOMAIN_MASK_ALL, CD_MASK_PROP_ALL); @@ -689,12 +677,12 @@ static void rna_AttributeGroup_active_index_range( *softmax = *max; } -static void rna_AttributeGroup_update_active(Main *bmain, Scene *scene, PointerRNA *ptr) +static void rna_AttributeGroupID_update_active(Main *bmain, Scene *scene, PointerRNA *ptr) { rna_Attribute_update_data(bmain, scene, ptr); } -static PointerRNA rna_AttributeGroup_active_color_get(PointerRNA *ptr) +static PointerRNA rna_AttributeGroupMesh_active_color_get(PointerRNA *ptr) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); CustomDataLayer *layer = BKE_attribute_search_for_write( @@ -707,16 +695,16 @@ static PointerRNA rna_AttributeGroup_active_color_get(PointerRNA *ptr) return attribute_ptr; } -static void rna_AttributeGroup_active_color_set(PointerRNA *ptr, - PointerRNA attribute_ptr, - ReportList * /*reports*/) +static void rna_AttributeGroupMesh_active_color_set(PointerRNA *ptr, + PointerRNA attribute_ptr, + ReportList * /*reports*/) { ID *id = ptr->owner_id; CustomDataLayer *layer = static_cast(attribute_ptr.data); BKE_id_attributes_active_color_set(id, layer->name); } -static int rna_AttributeGroup_active_color_index_get(PointerRNA *ptr) +static int rna_AttributeGroupMesh_active_color_index_get(PointerRNA *ptr) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); const CustomDataLayer *layer = BKE_attribute_search( @@ -728,7 +716,7 @@ static int rna_AttributeGroup_active_color_index_get(PointerRNA *ptr) return BKE_attribute_to_index(owner, layer, ATTR_DOMAIN_MASK_COLOR, CD_MASK_COLOR_ALL); } -static void rna_AttributeGroup_active_color_index_set(PointerRNA *ptr, int value) +static void rna_AttributeGroupMesh_active_color_index_set(PointerRNA *ptr, int value) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); CustomDataLayer *layer = BKE_attribute_from_index( @@ -742,7 +730,7 @@ static void rna_AttributeGroup_active_color_index_set(PointerRNA *ptr, int value BKE_id_attributes_active_color_set(ptr->owner_id, layer->name); } -static void rna_AttributeGroup_active_color_index_range( +static void rna_AttributeGroupMesh_active_color_index_range( PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); @@ -753,9 +741,9 @@ static void rna_AttributeGroup_active_color_index_range( *softmax = *max; } -static void rna_AttributeGroup_update_active_color(Main * /*bmain*/, - Scene * /*scene*/, - PointerRNA *ptr) +static void rna_AttributeGroupID_update_active_color(Main * /*bmain*/, + Scene * /*scene*/, + PointerRNA *ptr) { ID *id = ptr->owner_id; @@ -766,7 +754,7 @@ static void rna_AttributeGroup_update_active_color(Main * /*bmain*/, } } -static int rna_AttributeGroup_render_color_index_get(PointerRNA *ptr) +static int rna_AttributeGroupMesh_render_color_index_get(PointerRNA *ptr) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); const CustomDataLayer *layer = BKE_id_attributes_color_find( @@ -775,7 +763,7 @@ static int rna_AttributeGroup_render_color_index_get(PointerRNA *ptr) return BKE_attribute_to_index(owner, layer, ATTR_DOMAIN_MASK_COLOR, CD_MASK_COLOR_ALL); } -static void rna_AttributeGroup_render_color_index_set(PointerRNA *ptr, int value) +static void rna_AttributeGroupMesh_render_color_index_set(PointerRNA *ptr, int value) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); CustomDataLayer *layer = BKE_attribute_from_index( @@ -789,7 +777,7 @@ static void rna_AttributeGroup_render_color_index_set(PointerRNA *ptr, int value BKE_id_attributes_default_color_set(ptr->owner_id, layer->name); } -static void rna_AttributeGroup_render_color_index_range( +static void rna_AttributeGroupMesh_render_color_index_range( PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); @@ -800,7 +788,7 @@ static void rna_AttributeGroup_render_color_index_range( *softmax = *max; } -static void rna_AttributeGroup_default_color_name_get(PointerRNA *ptr, char *value) +static void rna_AttributeGroupMesh_default_color_name_get(PointerRNA *ptr, char *value) { const ID *id = ptr->owner_id; const char *name = BKE_id_attributes_default_color_name(id); @@ -811,14 +799,14 @@ static void rna_AttributeGroup_default_color_name_get(PointerRNA *ptr, char *val strcpy(value, name); } -static int rna_AttributeGroup_default_color_name_length(PointerRNA *ptr) +static int rna_AttributeGroupMesh_default_color_name_length(PointerRNA *ptr) { const ID *id = ptr->owner_id; const char *name = BKE_id_attributes_default_color_name(id); return name ? strlen(name) : 0; } -static void rna_AttributeGroup_default_color_name_set(PointerRNA *ptr, const char *value) +static void rna_AttributeGroupMesh_default_color_name_set(PointerRNA *ptr, const char *value) { ID *id = ptr->owner_id; if (GS(id->name) == ID_ME) { @@ -830,7 +818,7 @@ static void rna_AttributeGroup_default_color_name_set(PointerRNA *ptr, const cha } } -static void rna_AttributeGroup_active_color_name_get(PointerRNA *ptr, char *value) +static void rna_AttributeGroupMesh_active_color_name_get(PointerRNA *ptr, char *value) { const ID *id = ptr->owner_id; const char *name = BKE_id_attributes_active_color_name(id); @@ -841,14 +829,14 @@ static void rna_AttributeGroup_active_color_name_get(PointerRNA *ptr, char *valu strcpy(value, name); } -static int rna_AttributeGroup_active_color_name_length(PointerRNA *ptr) +static int rna_AttributeGroupMesh_active_color_name_length(PointerRNA *ptr) { const ID *id = ptr->owner_id; const char *name = BKE_id_attributes_active_color_name(id); return name ? strlen(name) : 0; } -static void rna_AttributeGroup_active_color_name_set(PointerRNA *ptr, const char *value) +static void rna_AttributeGroupMesh_active_color_name_set(PointerRNA *ptr, const char *value) { ID *id = ptr->owner_id; if (GS(id->name) == ID_ME) { @@ -860,6 +848,88 @@ static void rna_AttributeGroup_active_color_name_set(PointerRNA *ptr, const char } } +static PointerRNA rna_AttributeGroupGreasePencilDrawing_new(ID *grease_pencil_id, + GreasePencilDrawing *drawing, + ReportList *reports, + const char *name, + const int type, + const int domain) +{ + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + CustomDataLayer *layer = BKE_attribute_new( + owner, name, eCustomDataType(type), AttrDomain(domain), reports); + + if (!layer) { + return PointerRNA_NULL; + } + + DEG_id_tag_update(grease_pencil_id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GEOM | ND_DATA, grease_pencil_id); + + PointerRNA ptr = RNA_pointer_create(grease_pencil_id, &RNA_Attribute, layer); + return ptr; +} + +static void rna_AttributeGroupGreasePencilDrawing_remove(ID *grease_pencil_id, + GreasePencilDrawing *drawing, + ReportList *reports, + PointerRNA *attribute_ptr) +{ + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + const CustomDataLayer *layer = (const CustomDataLayer *)attribute_ptr->data; + BKE_attribute_remove(owner, layer->name, reports); + RNA_POINTER_INVALIDATE(attribute_ptr); + + DEG_id_tag_update(grease_pencil_id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GEOM | ND_DATA, grease_pencil_id); +} + +static PointerRNA rna_AttributeGroupGreasePencilDrawing_active_get(PointerRNA *ptr) +{ + GreasePencilDrawing *drawing = static_cast(ptr->data); + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + CustomDataLayer *layer = BKE_attributes_active_get(owner); + + PointerRNA attribute_ptr = RNA_pointer_create(ptr->owner_id, &RNA_Attribute, layer); + return attribute_ptr; +} + +static void rna_AttributeGroupGreasePencilDrawing_active_set(PointerRNA *ptr, + PointerRNA attribute_ptr, + ReportList * /*reports*/) +{ + GreasePencilDrawing *drawing = static_cast(ptr->data); + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + CustomDataLayer *layer = static_cast(attribute_ptr.data); + BKE_attributes_active_set(owner, layer->name); +} + +static int rna_AttributeGroupGreasePencilDrawing_active_index_get(PointerRNA *ptr) +{ + GreasePencilDrawing *drawing = static_cast(ptr->data); + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + return *BKE_attributes_active_index_p(owner); +} + +static void rna_AttributeGroupGreasePencilDrawing_active_index_set(PointerRNA *ptr, int value) +{ + GreasePencilDrawing *drawing = static_cast(ptr->data); + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + *BKE_attributes_active_index_p(owner) = value; +} + +static void rna_AttributeGroupGreasePencilDrawing_active_index_range( + PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax) +{ + GreasePencilDrawing *drawing = static_cast(ptr->data); + AttributeOwner owner = AttributeOwner(AttributeOwnerType::GreasePencilDrawing, drawing); + *min = 0; + *max = BKE_attributes_length(owner, ATTR_DOMAIN_MASK_ALL, CD_MASK_PROP_ALL); + + *softmin = *min; + *softmax = *max; +} + #else static void rna_def_attribute_float(BlenderRNA *brna) @@ -1359,7 +1429,7 @@ static void rna_def_attribute_group_id_common(StructRNA *srna) PropertyRNA *parm; /* API */ - func = RNA_def_function(srna, "new", "rna_AttributeGroup_new"); + func = RNA_def_function(srna, "new", "rna_AttributeGroupID_new"); RNA_def_function_ui_description(func, "Add attribute to geometry"); RNA_def_function_flag(func, FUNC_USE_REPORTS); parm = RNA_def_string(func, "name", "Attribute", 0, "Name", "Name of geometry attribute"); @@ -1381,7 +1451,7 @@ static void rna_def_attribute_group_id_common(StructRNA *srna) RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); RNA_def_function_return(func, parm); - func = RNA_def_function(srna, "remove", "rna_AttributeGroup_remove"); + func = RNA_def_function(srna, "remove", "rna_AttributeGroupID_remove"); RNA_def_function_ui_description(func, "Remove attribute from geometry"); RNA_def_function_flag(func, FUNC_USE_REPORTS); parm = RNA_def_pointer(func, "attribute", "Attribute", "", "Geometry Attribute"); @@ -1392,19 +1462,22 @@ static void rna_def_attribute_group_id_common(StructRNA *srna) prop = RNA_def_property(srna, "active", PROP_POINTER, PROP_NONE); RNA_def_property_struct_type(prop, "Attribute"); RNA_def_property_ui_text(prop, "Active Attribute", "Active attribute"); - RNA_def_property_pointer_funcs( - prop, "rna_AttributeGroup_active_get", "rna_AttributeGroup_active_set", nullptr, nullptr); + RNA_def_property_pointer_funcs(prop, + "rna_AttributeGroupID_active_get", + "rna_AttributeGroupID_active_set", + nullptr, + nullptr); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); - RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); prop = RNA_def_property(srna, "active_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, "Active Attribute Index", "Active attribute index"); RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); RNA_def_property_int_funcs(prop, - "rna_AttributeGroup_active_index_get", - "rna_AttributeGroup_active_index_set", - "rna_AttributeGroup_active_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); + "rna_AttributeGroupID_active_index_get", + "rna_AttributeGroupID_active_index_set", + "rna_AttributeGroupID_active_index_range"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); } static void rna_def_attribute_group_mesh(BlenderRNA *brna) @@ -1424,21 +1497,21 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) RNA_def_property_struct_type(prop, "Attribute"); RNA_def_property_ui_text(prop, "Active Color", "Active color attribute for display and editing"); RNA_def_property_pointer_funcs(prop, - "rna_AttributeGroup_active_color_get", - "rna_AttributeGroup_active_color_set", + "rna_AttributeGroupMesh_active_color_get", + "rna_AttributeGroupMesh_active_color_set", nullptr, nullptr); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); - RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); prop = RNA_def_property(srna, "active_color_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, "Active Color Index", "Active color attribute index"); RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); RNA_def_property_int_funcs(prop, - "rna_AttributeGroup_active_color_index_get", - "rna_AttributeGroup_active_color_index_set", - "rna_AttributeGroup_active_color_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); + "rna_AttributeGroupMesh_active_color_index_get", + "rna_AttributeGroupMesh_active_color_index_set", + "rna_AttributeGroupMesh_active_color_index_range"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); prop = RNA_def_property(srna, "render_color_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, @@ -1446,17 +1519,17 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) "The index of the color attribute used as a fallback for rendering"); RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); RNA_def_property_int_funcs(prop, - "rna_AttributeGroup_render_color_index_get", - "rna_AttributeGroup_render_color_index_set", - "rna_AttributeGroup_render_color_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); + "rna_AttributeGroupMesh_render_color_index_get", + "rna_AttributeGroupMesh_render_color_index_set", + "rna_AttributeGroupMesh_render_color_index_range"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); prop = RNA_def_property(srna, "default_color_name", PROP_STRING, PROP_NONE); RNA_def_property_string_maxlength(prop, MAX_CUSTOMDATA_LAYER_NAME_NO_PREFIX); RNA_def_property_string_funcs(prop, - "rna_AttributeGroup_default_color_name_get", - "rna_AttributeGroup_default_color_name_length", - "rna_AttributeGroup_default_color_name_set"); + "rna_AttributeGroupMesh_default_color_name_get", + "rna_AttributeGroupMesh_default_color_name_length", + "rna_AttributeGroupMesh_default_color_name_set"); RNA_def_property_ui_text( prop, "Default Color Attribute", @@ -1465,9 +1538,9 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) prop = RNA_def_property(srna, "active_color_name", PROP_STRING, PROP_NONE); RNA_def_property_string_maxlength(prop, MAX_CUSTOMDATA_LAYER_NAME_NO_PREFIX); RNA_def_property_string_funcs(prop, - "rna_AttributeGroup_active_color_name_get", - "rna_AttributeGroup_active_color_name_length", - "rna_AttributeGroup_active_color_name_set"); + "rna_AttributeGroupMesh_active_color_name_get", + "rna_AttributeGroupMesh_active_color_name_length", + "rna_AttributeGroupMesh_active_color_name_set"); RNA_def_property_ui_text(prop, "Active Color Attribute", "The name of the active color attribute for display and editing"); @@ -1506,6 +1579,69 @@ static void rna_def_attribute_group_grease_pencil(BlenderRNA *brna) rna_def_attribute_group_id_common(srna); } +static void rna_def_attribute_group_grease_pencil_drawing(BlenderRNA *brna) +{ + PropertyRNA *prop; + FunctionRNA *func; + PropertyRNA *parm; + StructRNA *srna; + + srna = RNA_def_struct(brna, "AttributeGroupGreasePencilDrawing", nullptr); + RNA_def_struct_ui_text(srna, "Attribute Group", "Group of geometry attributes"); + RNA_def_struct_sdna(srna, "GreasePencilDrawing"); + + /* API */ + func = RNA_def_function(srna, "new", "rna_AttributeGroupGreasePencilDrawing_new"); + RNA_def_function_ui_description(func, "Add attribute to geometry"); + RNA_def_function_flag(func, FUNC_USE_SELF_ID | FUNC_USE_REPORTS); + parm = RNA_def_string(func, "name", "Attribute", 0, "Name", "Name of geometry attribute"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + parm = RNA_def_enum( + func, "type", rna_enum_attribute_type_items, CD_PROP_FLOAT, "Type", "Attribute type"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + parm = RNA_def_enum(func, + "domain", + rna_enum_attribute_domain_items, + int(AttrDomain::Point), + "Domain", + "Type of element that attribute is stored on"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + parm = RNA_def_pointer(func, "attribute", "Attribute", "", "New geometry attribute"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); + RNA_def_function_return(func, parm); + + func = RNA_def_function(srna, "remove", "rna_AttributeGroupGreasePencilDrawing_remove"); + RNA_def_function_ui_description(func, "Remove attribute from geometry"); + RNA_def_function_flag(func, FUNC_USE_SELF_ID | FUNC_USE_REPORTS); + parm = RNA_def_pointer(func, "attribute", "Attribute", "", "Geometry Attribute"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + /* Active */ + prop = RNA_def_property(srna, "active", PROP_POINTER, PROP_NONE); + RNA_def_property_struct_type(prop, "Attribute"); + RNA_def_property_ui_text(prop, "Active Attribute", "Active attribute"); + RNA_def_property_pointer_funcs(prop, + "rna_AttributeGroupGreasePencilDrawing_active_get", + "rna_AttributeGroupGreasePencilDrawing_active_set", + nullptr, + nullptr); + RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); + + prop = RNA_def_property(srna, "active_index", PROP_INT, PROP_NONE); + RNA_def_property_ui_text(prop, "Active Attribute Index", "Active attribute index"); + RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); + RNA_def_property_int_funcs(prop, + "rna_AttributeGroupGreasePencilDrawing_active_index_get", + "rna_AttributeGroupGreasePencilDrawing_active_index_set", + "rna_AttributeGroupGreasePencilDrawing_active_index_range"); + RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); +} + void rna_def_attributes_common(StructRNA *srna, const AttributeOwnerType type) { PropertyRNA *prop; @@ -1536,6 +1672,9 @@ void rna_def_attributes_common(StructRNA *srna, const AttributeOwnerType type) case AttributeOwnerType::GreasePencil: RNA_def_property_srna(prop, "AttributeGroupGreasePencil"); break; + case AttributeOwnerType::GreasePencilDrawing: + RNA_def_property_srna(prop, "AttributeGroupGreasePencilDrawing"); + break; } prop = RNA_def_property(srna, "color_attributes", PROP_COLLECTION, PROP_NONE); @@ -1563,6 +1702,9 @@ void rna_def_attributes_common(StructRNA *srna, const AttributeOwnerType type) case AttributeOwnerType::GreasePencil: RNA_def_property_srna(prop, "AttributeGroupGreasePencil"); break; + case AttributeOwnerType::GreasePencilDrawing: + RNA_def_property_srna(prop, "AttributeGroupGreasePencilDrawing"); + break; } } @@ -1573,5 +1715,6 @@ void RNA_def_attribute(BlenderRNA *brna) rna_def_attribute_group_point_cloud(brna); rna_def_attribute_group_curves(brna); rna_def_attribute_group_grease_pencil(brna); + rna_def_attribute_group_grease_pencil_drawing(brna); } #endif diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index 6b6f23010a1..b60b0ac8192 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -741,7 +741,7 @@ static void rna_def_grease_pencil_drawing(BlenderRNA *brna) RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); /* Attributes. */ - rna_def_attributes_common(srna); + rna_def_attributes_common(srna, AttributeOwnerType::GreasePencilDrawing); } static void rna_def_grease_pencil_frame(BlenderRNA *brna) -- 2.30.2 From 638633ff12d020b8bea4e4a5bf4b9caba75f8131 Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 18 Jul 2024 11:08:57 +0200 Subject: [PATCH 03/13] Remove comment --- source/blender/blenkernel/BKE_grease_pencil.hh | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/source/blender/blenkernel/BKE_grease_pencil.hh b/source/blender/blenkernel/BKE_grease_pencil.hh index 34d9d6b8a43..102ee9b4e31 100644 --- a/source/blender/blenkernel/BKE_grease_pencil.hh +++ b/source/blender/blenkernel/BKE_grease_pencil.hh @@ -1018,8 +1018,7 @@ inline bool GreasePencil::has_active_group() const return (this->active_node != nullptr) && (this->active_node->wrap().is_group()); } -bool BKE_grease_pencil_drawing_attribute_required(const GreasePencilDrawing * /*drawing*/, - const char *name); +bool BKE_grease_pencil_drawing_attribute_required(const GreasePencilDrawing *, const char *name); void *BKE_grease_pencil_add(Main *bmain, const char *name); GreasePencil *BKE_grease_pencil_new_nomain(); -- 2.30.2 From 96050f62187f3ce721325a9431f53f6f170d1c7b Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 18 Jul 2024 11:09:09 +0200 Subject: [PATCH 04/13] Move `rna_AttributeGroupID_update_active_color` up --- .../blender/makesrna/intern/rna_attribute.cc | 26 +++++++++---------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 99d7bb32431..9c566e3fb00 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -682,6 +682,19 @@ static void rna_AttributeGroupID_update_active(Main *bmain, Scene *scene, Pointe rna_Attribute_update_data(bmain, scene, ptr); } +static void rna_AttributeGroupID_update_active_color(Main * /*bmain*/, + Scene * /*scene*/, + PointerRNA *ptr) +{ + ID *id = ptr->owner_id; + + /* Cheating way for importers to avoid slow updates. */ + if (id->us > 0) { + DEG_id_tag_update(id, 0); + WM_main_add_notifier(NC_GEOM | ND_DATA, id); + } +} + static PointerRNA rna_AttributeGroupMesh_active_color_get(PointerRNA *ptr) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); @@ -741,19 +754,6 @@ static void rna_AttributeGroupMesh_active_color_index_range( *softmax = *max; } -static void rna_AttributeGroupID_update_active_color(Main * /*bmain*/, - Scene * /*scene*/, - PointerRNA *ptr) -{ - ID *id = ptr->owner_id; - - /* Cheating way for importers to avoid slow updates. */ - if (id->us > 0) { - DEG_id_tag_update(id, 0); - WM_main_add_notifier(NC_GEOM | ND_DATA, id); - } -} - static int rna_AttributeGroupMesh_render_color_index_get(PointerRNA *ptr) { AttributeOwner owner = AttributeOwner::from_id(ptr->owner_id); -- 2.30.2 From 01a3a19bde8f12b1b8f410e6a51827f0521af22e Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 18 Jul 2024 11:12:16 +0200 Subject: [PATCH 05/13] Add `frame.keyframe_type` --- .../makesrna/intern/rna_grease_pencil.cc | 42 +++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index b60b0ac8192..1972012168b 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -28,6 +28,40 @@ const EnumPropertyItem rna_enum_tree_node_move_type_items[] = { {0, nullptr, 0, nullptr, nullptr}, }; +static const EnumPropertyItem rna_enum_keyframe_type_items[] = { + {BEZT_KEYTYPE_KEYFRAME, + "KEYFRAME", + ICON_KEYTYPE_KEYFRAME_VEC, + "Keyframe", + "Normal keyframe, e.g. for key poses"}, + {BEZT_KEYTYPE_BREAKDOWN, + "BREAKDOWN", + ICON_KEYTYPE_BREAKDOWN_VEC, + "Breakdown", + "A breakdown pose, e.g. for transitions between key poses"}, + {BEZT_KEYTYPE_MOVEHOLD, + "MOVING_HOLD", + ICON_KEYTYPE_MOVING_HOLD_VEC, + "Moving Hold", + "A keyframe that is part of a moving hold"}, + {BEZT_KEYTYPE_EXTREME, + "EXTREME", + ICON_KEYTYPE_EXTREME_VEC, + "Extreme", + "An 'extreme' pose, or some other purpose as needed"}, + {BEZT_KEYTYPE_JITTER, + "JITTER", + ICON_KEYTYPE_JITTER_VEC, + "Jitter", + "A filler or baked keyframe for keying on ones, or some other purpose as needed"}, + {BEZT_KEYTYPE_GENERATED, + "GENERATED", + ICON_KEYTYPE_GENERATED_VEC, + "Generated", + "A key generated automatically by a tool, not manually created"}, + {0, nullptr, 0, nullptr, nullptr}, +}; + #ifdef RNA_RUNTIME # include @@ -775,6 +809,14 @@ static void rna_def_grease_pencil_frame(BlenderRNA *brna) RNA_def_property_boolean_sdna(prop, nullptr, "flag", GP_FRAME_SELECTED); RNA_def_property_ui_text(prop, "Select", "Frame Selection in the Dope Sheet"); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + + /* Keyframe type. */ + prop = RNA_def_property(srna, "keyframe_type", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, nullptr, "type"); + RNA_def_parameter_clear_flags(prop, PROP_ANIMATABLE, ParameterFlag(0)); + RNA_def_property_enum_items(prop, rna_enum_keyframe_type_items); + RNA_def_property_ui_text(prop, "Keyframe Type", "Type of keyframe"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); } static void rna_def_grease_pencil_frames_api(BlenderRNA *brna, PropertyRNA *cprop) -- 2.30.2 From 92225140f5d13401b15d449b0e9f9a2d3094446a Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 18 Jul 2024 11:22:56 +0200 Subject: [PATCH 06/13] Add poll function for `active` drawing attribute setter --- source/blender/makesrna/intern/rna_attribute.cc | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 9c566e3fb00..634b57fb374 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -904,6 +904,14 @@ static void rna_AttributeGroupGreasePencilDrawing_active_set(PointerRNA *ptr, BKE_attributes_active_set(owner, layer->name); } +static bool rna_AttributeGroupGreasePencilDrawing_active_poll(PointerRNA *ptr, + const PointerRNA value) +{ + AttributeOwner owner = owner_from_attribute_pointer_rna(&value); + return owner.is_valid() && owner.type() == AttributeOwnerType::GreasePencilDrawing && + owner.get_grease_pencil_drawing() == static_cast(ptr->data); +} + static int rna_AttributeGroupGreasePencilDrawing_active_index_get(PointerRNA *ptr) { GreasePencilDrawing *drawing = static_cast(ptr->data); @@ -1628,7 +1636,7 @@ static void rna_def_attribute_group_grease_pencil_drawing(BlenderRNA *brna) "rna_AttributeGroupGreasePencilDrawing_active_get", "rna_AttributeGroupGreasePencilDrawing_active_set", nullptr, - nullptr); + "rna_AttributeGroupGreasePencilDrawing_active_poll"); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); -- 2.30.2 From 35c9c6678de36411e6f9f6ad055567d9618bce7c Mon Sep 17 00:00:00 2001 From: Falk David Date: Fri, 19 Jul 2024 11:39:24 +0200 Subject: [PATCH 07/13] Use `const_cast` --- source/blender/makesrna/intern/rna_attribute.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 634b57fb374..226a95a1ef0 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -907,7 +907,7 @@ static void rna_AttributeGroupGreasePencilDrawing_active_set(PointerRNA *ptr, static bool rna_AttributeGroupGreasePencilDrawing_active_poll(PointerRNA *ptr, const PointerRNA value) { - AttributeOwner owner = owner_from_attribute_pointer_rna(&value); + AttributeOwner owner = owner_from_attribute_pointer_rna(const_cast(&value)); return owner.is_valid() && owner.type() == AttributeOwnerType::GreasePencilDrawing && owner.get_grease_pencil_drawing() == static_cast(ptr->data); } -- 2.30.2 From d5d345d70b034bd92755aa6e02a06c14f6956ed1 Mon Sep 17 00:00:00 2001 From: Falk David Date: Mon, 22 Jul 2024 17:36:42 +0200 Subject: [PATCH 08/13] Add API to get the user count of a drawing --- source/blender/blenkernel/BKE_grease_pencil.hh | 11 +++++++++++ .../blender/makesrna/intern/rna_grease_pencil.cc | 14 ++++++++++++++ 2 files changed, 25 insertions(+) diff --git a/source/blender/blenkernel/BKE_grease_pencil.hh b/source/blender/blenkernel/BKE_grease_pencil.hh index 102ee9b4e31..930be2e71f7 100644 --- a/source/blender/blenkernel/BKE_grease_pencil.hh +++ b/source/blender/blenkernel/BKE_grease_pencil.hh @@ -151,7 +151,14 @@ class Drawing : public ::GreasePencilDrawing { * Returns true for when this drawing has more than one user. */ bool is_instanced() const; + /** + * Return true if this drawing has at least one user. + */ bool has_users() const; + /** + * Return the number of users (keyframes) of this drawing. + */ + int user_count() const; }; static_assert(sizeof(Drawing) == sizeof(::GreasePencilDrawing)); @@ -742,6 +749,10 @@ inline bool Drawing::has_users() const { return this->runtime->user_count.load(std::memory_order_relaxed) > 0; } +inline int Drawing::user_count() const +{ + return this->runtime->user_count.load(std::memory_order_relaxed); +} inline bool TreeNode::is_group() const { diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index 1972012168b..814252c0d48 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -109,6 +109,13 @@ static void rna_grease_pencil_dependency_update(Main *bmain, Scene * /*scene*/, WM_main_add_notifier(NC_GPENCIL | NA_EDITED, rna_grease_pencil(ptr)); } +static int rna_Drawing_user_count_get(PointerRNA *ptr) +{ + using namespace blender::bke::greasepencil; + const GreasePencilDrawing *drawing = static_cast(ptr->data); + return drawing->wrap().user_count(); +} + static void rna_GreasePencilLayer_frames_begin(CollectionPropertyIterator *iter, PointerRNA *ptr) { using namespace blender::bke::greasepencil; @@ -774,6 +781,13 @@ static void rna_def_grease_pencil_drawing(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Type", "Drawing type"); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + /* User Count. */ + prop = RNA_def_property(srna, "user_count", PROP_INT, PROP_NONE); + RNA_def_property_int_funcs(prop, "rna_Drawing_user_count_get", nullptr, nullptr); + RNA_def_parameter_clear_flags(prop, PROP_EDITABLE, ParameterFlag(0)); + RNA_def_property_ui_text(prop, "User Count", "The number of keyframes this drawing is used by"); + RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); + /* Attributes. */ rna_def_attributes_common(srna, AttributeOwnerType::GreasePencilDrawing); } -- 2.30.2 From cb8af52555ec4f6eb844818598bf33057eab6d19 Mon Sep 17 00:00:00 2001 From: Falk David Date: Mon, 22 Jul 2024 17:48:26 +0200 Subject: [PATCH 09/13] Move `rna_enum_keyframe_type_items` --- .../makesrna/intern/rna_grease_pencil.cc | 68 +++++++++---------- 1 file changed, 34 insertions(+), 34 deletions(-) diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index 814252c0d48..46ee9d8ee66 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -28,40 +28,6 @@ const EnumPropertyItem rna_enum_tree_node_move_type_items[] = { {0, nullptr, 0, nullptr, nullptr}, }; -static const EnumPropertyItem rna_enum_keyframe_type_items[] = { - {BEZT_KEYTYPE_KEYFRAME, - "KEYFRAME", - ICON_KEYTYPE_KEYFRAME_VEC, - "Keyframe", - "Normal keyframe, e.g. for key poses"}, - {BEZT_KEYTYPE_BREAKDOWN, - "BREAKDOWN", - ICON_KEYTYPE_BREAKDOWN_VEC, - "Breakdown", - "A breakdown pose, e.g. for transitions between key poses"}, - {BEZT_KEYTYPE_MOVEHOLD, - "MOVING_HOLD", - ICON_KEYTYPE_MOVING_HOLD_VEC, - "Moving Hold", - "A keyframe that is part of a moving hold"}, - {BEZT_KEYTYPE_EXTREME, - "EXTREME", - ICON_KEYTYPE_EXTREME_VEC, - "Extreme", - "An 'extreme' pose, or some other purpose as needed"}, - {BEZT_KEYTYPE_JITTER, - "JITTER", - ICON_KEYTYPE_JITTER_VEC, - "Jitter", - "A filler or baked keyframe for keying on ones, or some other purpose as needed"}, - {BEZT_KEYTYPE_GENERATED, - "GENERATED", - ICON_KEYTYPE_GENERATED_VEC, - "Generated", - "A key generated automatically by a tool, not manually created"}, - {0, nullptr, 0, nullptr, nullptr}, -}; - #ifdef RNA_RUNTIME # include @@ -797,6 +763,40 @@ static void rna_def_grease_pencil_frame(BlenderRNA *brna) StructRNA *srna; PropertyRNA *prop; + static const EnumPropertyItem rna_enum_keyframe_type_items[] = { + {BEZT_KEYTYPE_KEYFRAME, + "KEYFRAME", + ICON_KEYTYPE_KEYFRAME_VEC, + "Keyframe", + "Normal keyframe, e.g. for key poses"}, + {BEZT_KEYTYPE_BREAKDOWN, + "BREAKDOWN", + ICON_KEYTYPE_BREAKDOWN_VEC, + "Breakdown", + "A breakdown pose, e.g. for transitions between key poses"}, + {BEZT_KEYTYPE_MOVEHOLD, + "MOVING_HOLD", + ICON_KEYTYPE_MOVING_HOLD_VEC, + "Moving Hold", + "A keyframe that is part of a moving hold"}, + {BEZT_KEYTYPE_EXTREME, + "EXTREME", + ICON_KEYTYPE_EXTREME_VEC, + "Extreme", + "An 'extreme' pose, or some other purpose as needed"}, + {BEZT_KEYTYPE_JITTER, + "JITTER", + ICON_KEYTYPE_JITTER_VEC, + "Jitter", + "A filler or baked keyframe for keying on ones, or some other purpose as needed"}, + {BEZT_KEYTYPE_GENERATED, + "GENERATED", + ICON_KEYTYPE_GENERATED_VEC, + "Generated", + "A key generated automatically by a tool, not manually created"}, + {0, nullptr, 0, nullptr, nullptr}, + }; + srna = RNA_def_struct(brna, "GreasePencilFrame", nullptr); RNA_def_struct_sdna(srna, "GreasePencilFrame"); RNA_def_struct_ui_text(srna, "Grease Pencil Frame", "A Grease Pencil keyframe"); -- 2.30.2 From 721509d8bf885f73d8ccfcab25ff233c32184269 Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 25 Jul 2024 16:06:28 +0200 Subject: [PATCH 10/13] Rename `rna_AttributeGroupID_update_active` to `rna_AttributeGroup_update_active` --- .../blender/makesrna/intern/rna_attribute.cc | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 226a95a1ef0..09285adc328 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -677,12 +677,12 @@ static void rna_AttributeGroupID_active_index_range( *softmax = *max; } -static void rna_AttributeGroupID_update_active(Main *bmain, Scene *scene, PointerRNA *ptr) +static void rna_AttributeGroup_update_active(Main *bmain, Scene *scene, PointerRNA *ptr) { rna_Attribute_update_data(bmain, scene, ptr); } -static void rna_AttributeGroupID_update_active_color(Main * /*bmain*/, +static void rna_AttributeGroup_update_active_color(Main * /*bmain*/, Scene * /*scene*/, PointerRNA *ptr) { @@ -1476,7 +1476,7 @@ static void rna_def_attribute_group_id_common(StructRNA *srna) nullptr, nullptr); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); prop = RNA_def_property(srna, "active_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, "Active Attribute Index", "Active attribute index"); @@ -1485,7 +1485,7 @@ static void rna_def_attribute_group_id_common(StructRNA *srna) "rna_AttributeGroupID_active_index_get", "rna_AttributeGroupID_active_index_set", "rna_AttributeGroupID_active_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); } static void rna_def_attribute_group_mesh(BlenderRNA *brna) @@ -1510,7 +1510,7 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) nullptr, nullptr); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); prop = RNA_def_property(srna, "active_color_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, "Active Color Index", "Active color attribute index"); @@ -1519,7 +1519,7 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) "rna_AttributeGroupMesh_active_color_index_get", "rna_AttributeGroupMesh_active_color_index_set", "rna_AttributeGroupMesh_active_color_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); prop = RNA_def_property(srna, "render_color_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, @@ -1530,7 +1530,7 @@ static void rna_def_attribute_group_mesh(BlenderRNA *brna) "rna_AttributeGroupMesh_render_color_index_get", "rna_AttributeGroupMesh_render_color_index_set", "rna_AttributeGroupMesh_render_color_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active_color"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active_color"); prop = RNA_def_property(srna, "default_color_name", PROP_STRING, PROP_NONE); RNA_def_property_string_maxlength(prop, MAX_CUSTOMDATA_LAYER_NAME_NO_PREFIX); @@ -1638,7 +1638,7 @@ static void rna_def_attribute_group_grease_pencil_drawing(BlenderRNA *brna) nullptr, "rna_AttributeGroupGreasePencilDrawing_active_poll"); RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); prop = RNA_def_property(srna, "active_index", PROP_INT, PROP_NONE); RNA_def_property_ui_text(prop, "Active Attribute Index", "Active attribute index"); @@ -1647,7 +1647,7 @@ static void rna_def_attribute_group_grease_pencil_drawing(BlenderRNA *brna) "rna_AttributeGroupGreasePencilDrawing_active_index_get", "rna_AttributeGroupGreasePencilDrawing_active_index_set", "rna_AttributeGroupGreasePencilDrawing_active_index_range"); - RNA_def_property_update(prop, 0, "rna_AttributeGroupID_update_active"); + RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active"); } void rna_def_attributes_common(StructRNA *srna, const AttributeOwnerType type) -- 2.30.2 From 3acb6e412960fd75ac3306efe340ee03db35565c Mon Sep 17 00:00:00 2001 From: Falk David Date: Thu, 25 Jul 2024 16:06:38 +0200 Subject: [PATCH 11/13] Remove `rna_Frame_frame_number_index_range` --- source/blender/makesrna/intern/rna_grease_pencil.cc | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index d6ea9658557..0dcb292f523 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -243,13 +243,6 @@ static int rna_Frame_frame_number_get(PointerRNA *ptr) return frame_number; } -static void rna_Frame_frame_number_index_range( - PointerRNA * /*ptr*/, int *min, int *max, int * /*softmin*/, int * /*softmax*/) -{ - *min = MINAFRAME; - *max = MAXFRAME; -} - static void rna_grease_pencil_layer_mask_name_get(PointerRNA *ptr, char *dst) { using namespace blender; @@ -812,8 +805,7 @@ static void rna_def_grease_pencil_frame(BlenderRNA *brna) prop = RNA_def_property(srna, "frame_number", PROP_INT, PROP_NONE); /* TODO: Make property editable, ensure frame number isn't already in use. */ RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_int_funcs( - prop, "rna_Frame_frame_number_get", nullptr, "rna_Frame_frame_number_index_range"); + RNA_def_property_int_funcs(prop, "rna_Frame_frame_number_get", nullptr, nullptr); RNA_def_property_range(prop, MINAFRAME, MAXFRAME); RNA_def_property_ui_text(prop, "Frame Number", "The frame number in the scene"); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); -- 2.30.2 From d255ffb45776b3cf40d0ab35ef5bff08f5c4ea44 Mon Sep 17 00:00:00 2001 From: Falk David Date: Fri, 26 Jul 2024 11:38:24 +0200 Subject: [PATCH 12/13] Move grease pencil API into its own file --- source/blender/makesrna/intern/CMakeLists.txt | 1 + source/blender/makesrna/intern/makesrna.cc | 2 +- .../makesrna/intern/rna_grease_pencil.cc | 551 +----------------- .../makesrna/intern/rna_grease_pencil_api.cc | 533 +++++++++++++++++ .../blender/makesrna/intern/rna_internal.hh | 4 + 5 files changed, 569 insertions(+), 522 deletions(-) create mode 100644 source/blender/makesrna/intern/rna_grease_pencil_api.cc diff --git a/source/blender/makesrna/intern/CMakeLists.txt b/source/blender/makesrna/intern/CMakeLists.txt index f475b114c4b..1d28af34e8a 100644 --- a/source/blender/makesrna/intern/CMakeLists.txt +++ b/source/blender/makesrna/intern/CMakeLists.txt @@ -120,6 +120,7 @@ set(APISRC rna_camera_api.cc rna_curve_api.cc rna_fcurve_api.cc + rna_grease_pencil_api.cc rna_image_api.cc rna_lattice_api.cc rna_main_api.cc diff --git a/source/blender/makesrna/intern/makesrna.cc b/source/blender/makesrna/intern/makesrna.cc index fa2d7963bbd..359c45d155b 100644 --- a/source/blender/makesrna/intern/makesrna.cc +++ b/source/blender/makesrna/intern/makesrna.cc @@ -4815,7 +4815,7 @@ static RNAProcessItem PROCESS_ITEMS[] = { {"rna_dynamicpaint.cc", nullptr, RNA_def_dynamic_paint}, {"rna_fcurve.cc", "rna_fcurve_api.cc", RNA_def_fcurve}, {"rna_gpencil_legacy.cc", nullptr, RNA_def_gpencil}, - {"rna_grease_pencil.cc", nullptr, RNA_def_grease_pencil}, + {"rna_grease_pencil.cc", "rna_grease_pencil_api.cc", RNA_def_grease_pencil}, {"rna_curves.cc", nullptr, RNA_def_curves}, {"rna_image.cc", "rna_image_api.cc", RNA_def_image}, {"rna_key.cc", nullptr, RNA_def_key}, diff --git a/source/blender/makesrna/intern/rna_grease_pencil.cc b/source/blender/makesrna/intern/rna_grease_pencil.cc index 0dcb292f523..da10a7fd569 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil.cc @@ -1,4 +1,4 @@ -/* SPDX-FileCopyrightText: 2023 Blender Authors +/* SPDX-FileCopyrightText: 2024 Blender Authors * * SPDX-License-Identifier: GPL-2.0-or-later */ @@ -22,12 +22,6 @@ #include "WM_api.hh" -const EnumPropertyItem rna_enum_tree_node_move_type_items[] = { - {-1, "DOWN", 0, "Down", ""}, - {1, "UP", 0, "Up", ""}, - {0, nullptr, 0, nullptr, nullptr}, -}; - #ifdef RNA_RUNTIME # include @@ -127,73 +121,6 @@ static bool rna_GreasePencilLayer_frames_lookup_int(PointerRNA *ptr, int index, return true; } -static GreasePencilFrame *rna_Frames_frame_new(ID *id, - GreasePencilLayer *layer_in, - ReportList *reports, - int frame_number) -{ - using namespace blender::bke::greasepencil; - GreasePencil &grease_pencil = *reinterpret_cast(id); - Layer &layer = static_cast(layer_in)->wrap(); - - if (layer.frames().contains(frame_number)) { - BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", frame_number); - return nullptr; - } - - grease_pencil.insert_frame(layer, frame_number, 0, BEZT_KEYTYPE_KEYFRAME); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); - - return layer.frame_at(frame_number); -} - -static void rna_Frames_frame_remove(ID *id, - GreasePencilLayer *layer_in, - ReportList *reports, - int frame_number) -{ - using namespace blender::bke::greasepencil; - GreasePencil &grease_pencil = *reinterpret_cast(id); - Layer &layer = static_cast(layer_in)->wrap(); - - if (!layer.frames().contains(frame_number)) { - BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", frame_number); - return; - } - - if (grease_pencil.remove_frames(layer, {frame_number})) { - DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); - } -} - -static GreasePencilFrame *rna_Frames_frame_copy(ID *id, - GreasePencilLayer *layer_in, - ReportList *reports, - int from_frame_number, - int to_frame_number, - bool instance_drawing) -{ - using namespace blender::bke::greasepencil; - GreasePencil &grease_pencil = *reinterpret_cast(id); - Layer &layer = static_cast(layer_in)->wrap(); - - if (!layer.frames().contains(from_frame_number)) { - BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", from_frame_number); - return nullptr; - } - if (layer.frames().contains(to_frame_number)) { - BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", to_frame_number); - return nullptr; - } - - grease_pencil.insert_duplicate_frame( - layer, from_frame_number, to_frame_number, instance_drawing); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); - - return layer.frame_at(to_frame_number); -} - static std::pair find_layer_of_frame( const GreasePencil &grease_pencil, const GreasePencilFrame &find_frame) { @@ -297,13 +224,6 @@ static void rna_grease_pencil_active_mask_index_range( *max = max_ii(0, BLI_listbase_count(&layer->masks) - 1); } -static GreasePencilFrame *rna_GreasePencilLayer_get_frame_at(GreasePencilLayer *layer, - int frame_number) -{ - using namespace blender::bke::greasepencil; - return static_cast(layer)->frame_at(frame_number); -} - static void rna_iterator_grease_pencil_layers_begin(CollectionPropertyIterator *iter, PointerRNA *ptr) { @@ -430,206 +350,6 @@ static PointerRNA rna_GreasePencilLayer_parent_layer_group_get(PointerRNA *ptr) ptr, &RNA_GreasePencilLayerGroup, static_cast(layer_group)); } -static PointerRNA rna_GreasePencil_layer_group_new(GreasePencil *grease_pencil, - const char *name, - PointerRNA *parent_group_ptr) -{ - using namespace blender::bke::greasepencil; - LayerGroup *parent_group; - if (parent_group_ptr && parent_group_ptr->data) { - parent_group = static_cast(parent_group_ptr->data); - } - else { - parent_group = &grease_pencil->root_group(); - } - LayerGroup *new_layer_group = &grease_pencil->add_layer_group(*parent_group, name); - - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); - - PointerRNA ptr = RNA_pointer_create( - &grease_pencil->id, &RNA_GreasePencilLayerGroup, new_layer_group); - return ptr; -} - -static void rna_GreasePencil_layer_group_remove(GreasePencil *grease_pencil, - PointerRNA *layer_group_ptr, - bool keep_children) -{ - using namespace blender::bke::greasepencil; - LayerGroup &layer_group = *static_cast(layer_group_ptr->data); - grease_pencil->remove_group(layer_group, keep_children); - - RNA_POINTER_INVALIDATE(layer_group_ptr); - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | ND_DATA | NA_SELECTED, grease_pencil); -} - -static void rna_GreasePencil_layer_group_move(GreasePencil *grease_pencil, - PointerRNA *layer_group_ptr, - int direction) -{ - if (direction == 0) { - return; - } - - blender::bke::greasepencil::TreeNode &layer_group_node = - static_cast(layer_group_ptr->data)->as_node(); - switch (direction) { - case -1: - grease_pencil->move_node_down(layer_group_node, 1); - break; - case 1: - grease_pencil->move_node_up(layer_group_node, 1); - break; - } - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_group_move_top(GreasePencil *grease_pencil, - PointerRNA *layer_group_ptr) -{ - blender::bke::greasepencil::TreeNode &layer_group_node = - static_cast(layer_group_ptr->data)->as_node(); - grease_pencil->move_node_top(layer_group_node); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_group_move_bottom(GreasePencil *grease_pencil, - PointerRNA *layer_group_ptr) -{ - blender::bke::greasepencil::TreeNode &layer_group_node = - static_cast(layer_group_ptr->data)->as_node(); - grease_pencil->move_node_bottom(layer_group_node); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_group_move_to_layer_group(GreasePencil *grease_pencil, - PointerRNA *layer_group_ptr, - PointerRNA *parent_group_ptr) -{ - using namespace blender::bke::greasepencil; - TreeNode &layer_group_node = static_cast(layer_group_ptr->data)->as_node(); - LayerGroup *parent_group; - if (parent_group_ptr && parent_group_ptr->data) { - parent_group = static_cast(parent_group_ptr->data); - } - else { - parent_group = &grease_pencil->root_group(); - } - grease_pencil->move_node_into(layer_group_node, *parent_group); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static GreasePencilLayer *rna_GreasePencil_layer_new(GreasePencil *grease_pencil, - const char *name, - const bool set_active, - PointerRNA *layer_group_ptr) -{ - using namespace blender::bke::greasepencil; - LayerGroup *layer_group = nullptr; - if (layer_group_ptr && layer_group_ptr->data) { - layer_group = static_cast(layer_group_ptr->data); - } - Layer *layer; - if (layer_group) { - layer = &grease_pencil->add_layer(*layer_group, name); - } - else { - layer = &grease_pencil->add_layer(name); - } - if (set_active) { - grease_pencil->set_active_layer(layer); - } - - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); - - return layer; -} - -static void rna_GreasePencil_layer_remove(GreasePencil *grease_pencil, PointerRNA *layer_ptr) -{ - blender::bke::greasepencil::Layer &layer = *static_cast( - layer_ptr->data); - grease_pencil->remove_layer(layer); - - RNA_POINTER_INVALIDATE(layer_ptr); - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | ND_DATA | NA_SELECTED, grease_pencil); -} - -static void rna_GreasePencil_layer_move(GreasePencil *grease_pencil, - PointerRNA *layer_ptr, - const int direction) -{ - if (direction == 0) { - return; - } - - blender::bke::greasepencil::TreeNode &layer_node = - static_cast(layer_ptr->data)->as_node(); - switch (direction) { - case -1: - grease_pencil->move_node_down(layer_node, 1); - break; - case 1: - grease_pencil->move_node_up(layer_node, 1); - break; - } - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_move_top(GreasePencil *grease_pencil, PointerRNA *layer_ptr) -{ - blender::bke::greasepencil::TreeNode &layer_node = - static_cast(layer_ptr->data)->as_node(); - grease_pencil->move_node_top(layer_node); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_move_bottom(GreasePencil *grease_pencil, PointerRNA *layer_ptr) -{ - blender::bke::greasepencil::TreeNode &layer_node = - static_cast(layer_ptr->data)->as_node(); - grease_pencil->move_node_bottom(layer_node); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - -static void rna_GreasePencil_layer_move_to_layer_group(GreasePencil *grease_pencil, - PointerRNA *layer_ptr, - PointerRNA *layer_group_ptr) -{ - using namespace blender::bke::greasepencil; - TreeNode &layer_node = static_cast(layer_ptr->data)->as_node(); - LayerGroup *layer_group; - if (layer_group_ptr && layer_group_ptr->data) { - layer_group = static_cast(layer_group_ptr->data); - } - else { - layer_group = &grease_pencil->root_group(); - } - if (layer_group == nullptr) { - return; - } - grease_pencil->move_node_into(layer_node, *layer_group); - - DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); - WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); -} - static PointerRNA rna_GreasePencil_active_layer_get(PointerRNA *ptr) { GreasePencil *grease_pencil = rna_grease_pencil(ptr); @@ -825,98 +545,16 @@ static void rna_def_grease_pencil_frame(BlenderRNA *brna) RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); } -static void rna_def_grease_pencil_frames_api(BlenderRNA *brna, PropertyRNA *cprop) +static void rna_def_grease_pencil_frames(BlenderRNA *brna, PropertyRNA *cprop) { StructRNA *srna; - FunctionRNA *func; - PropertyRNA *parm; - RNA_def_property_srna(cprop, "GreasePencilFrames"); srna = RNA_def_struct(brna, "GreasePencilFrames", nullptr); RNA_def_struct_sdna(srna, "GreasePencilLayer"); RNA_def_struct_ui_text(srna, "Grease Pencil Frames", "Collection of Grease Pencil frames"); - func = RNA_def_function(srna, "new", "rna_Frames_frame_new"); - RNA_def_function_ui_description(func, "Add a new Grease Pencil frame"); - RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); - parm = RNA_def_int(func, - "frame_number", - 1, - MINAFRAME, - MAXFRAME, - "Frame Number", - "The frame on which the drawing appears", - MINAFRAME, - MAXFRAME); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "", "The newly created frame"); - RNA_def_function_return(func, parm); - - func = RNA_def_function(srna, "remove", "rna_Frames_frame_remove"); - RNA_def_function_ui_description(func, "Remove a Grease Pencil frame"); - RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); - parm = RNA_def_int(func, - "frame_number", - 1, - MINAFRAME, - MAXFRAME, - "Frame Number", - "The frame number of the frame to remove", - MINAFRAME, - MAXFRAME); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - - func = RNA_def_function(srna, "copy", "rna_Frames_frame_copy"); - RNA_def_function_ui_description(func, "Copy a Grease Pencil frame"); - RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); - parm = RNA_def_int(func, - "from_frame_number", - 1, - MINAFRAME, - MAXFRAME, - "Source Frame Number", - "The frame number of the source frame", - MINAFRAME, - MAXFRAME); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - parm = RNA_def_int(func, - "to_frame_number", - 2, - MINAFRAME, - MAXFRAME, - "Frame Number of Copy", - "The frame number to copy the frame to", - MINAFRAME, - MAXFRAME); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - parm = RNA_def_boolean(func, - "instance_drawing", - false, - "Instance Drawing", - "Let the copied frame use the same drawing as the source"); - parm = RNA_def_pointer(func, "copy", "GreasePencilFrame", "", "The newly copied frame"); - RNA_def_function_return(func, parm); -} - -static void rna_def_grease_pencil_layers_mask_api(BlenderRNA *brna, PropertyRNA *cprop) -{ - StructRNA *srna; - PropertyRNA *prop; - - RNA_def_property_srna(cprop, "GreasePencilLayerMasks"); - srna = RNA_def_struct(brna, "GreasePencilLayerMasks", nullptr); - RNA_def_struct_sdna(srna, "GreasePencilLayer"); - RNA_def_struct_ui_text( - srna, "Grease Pencil Mask Layers", "Collection of grease pencil masking layers"); - - prop = RNA_def_property(srna, "active_mask_index", PROP_INT, PROP_UNSIGNED); - RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); - RNA_def_property_int_funcs(prop, - "rna_grease_pencil_active_mask_index_get", - "rna_grease_pencil_active_mask_index_set", - "rna_grease_pencil_active_mask_index_range"); - RNA_def_property_ui_text(prop, "Active Layer Mask Index", "Active index in layer mask array"); + RNA_api_grease_pencil_frames(srna); } static void rna_def_grease_pencil_layer_mask(BlenderRNA *brna) @@ -953,18 +591,24 @@ static void rna_def_grease_pencil_layer_mask(BlenderRNA *brna) RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); } -static void rna_def_grease_pencil_layer_api(StructRNA *srna) +static void rna_def_grease_pencil_layer_masks(BlenderRNA *brna, PropertyRNA *cprop) { - FunctionRNA *func; - PropertyRNA *parm; + StructRNA *srna; + PropertyRNA *prop; - func = RNA_def_function(srna, "get_frame_at", "rna_GreasePencilLayer_get_frame_at"); - RNA_def_function_ui_description(func, "Get the frame at given frame number"); - parm = RNA_def_int( - func, "frame_number", 1, MINAFRAME, MAXFRAME, "Frame Number", "", MINAFRAME, MAXFRAME); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "Frame", ""); - RNA_def_function_return(func, parm); + RNA_def_property_srna(cprop, "GreasePencilLayerMasks"); + srna = RNA_def_struct(brna, "GreasePencilLayerMasks", nullptr); + RNA_def_struct_sdna(srna, "GreasePencilLayer"); + RNA_def_struct_ui_text( + srna, "Grease Pencil Mask Layers", "Collection of grease pencil masking layers"); + + prop = RNA_def_property(srna, "active_mask_index", PROP_INT, PROP_UNSIGNED); + RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); + RNA_def_property_int_funcs(prop, + "rna_grease_pencil_active_mask_index_get", + "rna_grease_pencil_active_mask_index_set", + "rna_grease_pencil_active_mask_index_range"); + RNA_def_property_ui_text(prop, "Active Layer Mask Index", "Active index in layer mask array"); } static void rna_def_grease_pencil_layer(BlenderRNA *brna) @@ -1011,14 +655,14 @@ static void rna_def_grease_pencil_layer(BlenderRNA *brna) "rna_GreasePencilLayer_frames_lookup_int", nullptr, nullptr); - rna_def_grease_pencil_frames_api(brna, prop); + rna_def_grease_pencil_frames(brna, prop); /* Mask Layers */ prop = RNA_def_property(srna, "mask_layers", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, nullptr, "masks", nullptr); RNA_def_property_struct_type(prop, "GreasePencilLayerMask"); RNA_def_property_ui_text(prop, "Masks", "List of Masking Layers"); - rna_def_grease_pencil_layers_mask_api(brna, prop); + rna_def_grease_pencil_layer_masks(brna, prop); /* Visibility */ prop = RNA_def_property(srna, "hide", PROP_BOOLEAN, PROP_NONE); @@ -1182,83 +826,19 @@ static void rna_def_grease_pencil_layer(BlenderRNA *brna) RNA_def_property_ui_text( prop, "Parent Layer Group", "The parent layer group this layer is part of"); - rna_def_grease_pencil_layer_api(srna); + RNA_api_grease_pencil_layer(srna); } -static void rna_def_grease_pencil_layers_api(BlenderRNA *brna, PropertyRNA *cprop) +static void rna_def_grease_pencil_layers(BlenderRNA *brna, PropertyRNA *cprop) { StructRNA *srna; PropertyRNA *prop; - FunctionRNA *func; - PropertyRNA *parm; - RNA_def_property_srna(cprop, "GreasePencilv3Layers"); srna = RNA_def_struct(brna, "GreasePencilv3Layers", nullptr); RNA_def_struct_sdna(srna, "GreasePencil"); RNA_def_struct_ui_text(srna, "Grease Pencil Layers", "Collection of Grease Pencil layers"); - func = RNA_def_function(srna, "new", "rna_GreasePencil_layer_new"); - RNA_def_function_ui_description(func, "Add a new Grease Pencil layer"); - parm = RNA_def_string(func, "name", "GreasePencilLayer", MAX_NAME, "Name", "Name of the layer"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - RNA_def_boolean( - func, "set_active", true, "Set Active", "Set the newly created layer as the active layer"); - parm = RNA_def_pointer( - func, - "layer_group", - "GreasePencilLayerGroup", - "", - "The layer group the new layer will be created in (use None for the main stack)"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The newly created layer"); - RNA_def_function_return(func, parm); - - func = RNA_def_function(srna, "remove", "rna_GreasePencil_layer_remove"); - RNA_def_function_ui_description(func, "Remove a Grease Pencil layer"); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to remove"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - - func = RNA_def_function(srna, "move", "rna_GreasePencil_layer_move"); - RNA_def_function_ui_description(func, - "Move a Grease Pencil layer in the layer group or main stack"); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - parm = RNA_def_enum( - func, "type", rna_enum_tree_node_move_type_items, 1, "", "Direction of movement"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - - func = RNA_def_function(srna, "move_top", "rna_GreasePencil_layer_move_top"); - RNA_def_function_ui_description( - func, "Move a Grease Pencil layer to the top of the layer group or main stack"); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - - func = RNA_def_function(srna, "move_bottom", "rna_GreasePencil_layer_move_bottom"); - RNA_def_function_ui_description( - func, "Move a Grease Pencil layer to the bottom of the layer group or main stack"); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - - func = RNA_def_function( - srna, "move_to_layer_group", "rna_GreasePencil_layer_move_to_layer_group"); - RNA_def_function_ui_description(func, "Move a Grease Pencil layer into a layer group"); - parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - parm = RNA_def_pointer( - func, - "layer_group", - "GreasePencilLayerGroup", - "", - "The layer group the layer will be moved into (use None for the main stack)"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - prop = RNA_def_property(srna, "active", PROP_POINTER, PROP_NONE); RNA_def_property_struct_type(prop, "GreasePencilLayer"); RNA_def_property_pointer_funcs(prop, @@ -1269,6 +849,8 @@ static void rna_def_grease_pencil_layers_api(BlenderRNA *brna, PropertyRNA *cpro RNA_def_property_flag(prop, PROP_EDITABLE); RNA_def_property_ui_text(prop, "Active Layer", "Active Grease Pencil layer"); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA | NA_SELECTED, nullptr); + + RNA_api_grease_pencil_layers(srna); } static void rna_def_grease_pencil_layer_group(BlenderRNA *brna) @@ -1327,91 +909,16 @@ static void rna_def_grease_pencil_layer_group(BlenderRNA *brna) RNA_def_property_update(prop, NC_GPENCIL | ND_DATA, "rna_grease_pencil_update"); } -static void rna_def_grease_pencil_layer_group_api(BlenderRNA *brna, PropertyRNA *cprop) +static void rna_def_grease_pencil_layer_groups(BlenderRNA *brna, PropertyRNA *cprop) { StructRNA *srna; PropertyRNA *prop; - FunctionRNA *func; - PropertyRNA *parm; - RNA_def_property_srna(cprop, "GreasePencilv3LayerGroup"); srna = RNA_def_struct(brna, "GreasePencilv3LayerGroup", nullptr); RNA_def_struct_sdna(srna, "GreasePencil"); RNA_def_struct_ui_text(srna, "Grease Pencil Group", "Collection of Grease Pencil layers"); - func = RNA_def_function(srna, "new", "rna_GreasePencil_layer_group_new"); - RNA_def_function_ui_description(func, "Add a new Grease Pencil layer group"); - parm = RNA_def_string( - func, "name", "GreasePencilLayerGroup", MAX_NAME, "Name", "Name of the layer group"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - parm = RNA_def_pointer( - func, - "parent_group", - "GreasePencilLayerGroup", - "", - "The parent layer group the new group will be created in (use None for the main stack)"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The newly created layer group"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); - RNA_def_function_return(func, parm); - - func = RNA_def_function(srna, "remove", "rna_GreasePencil_layer_group_remove"); - RNA_def_function_ui_description(func, "Remove a new Grease Pencil layer group"); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to remove"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - parm = RNA_def_boolean(func, - "keep_children", - false, - "", - "Keep the children nodes of the group and only delete the group itself"); - - func = RNA_def_function(srna, "move", "rna_GreasePencil_layer_group_move"); - RNA_def_function_ui_description(func, - "Move a layer group in the parent layer group or main stack"); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - parm = RNA_def_enum( - func, "type", rna_enum_tree_node_move_type_items, 1, "", "Direction of movement"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); - - func = RNA_def_function(srna, "move_top", "rna_GreasePencil_layer_group_move_top"); - RNA_def_function_ui_description( - func, "Move a layer group to the top of the parent layer group or main stack"); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - - func = RNA_def_function(srna, "move_bottom", "rna_GreasePencil_layer_group_move_bottom"); - RNA_def_function_ui_description( - func, "Move a layer group to the bottom of the parent layer group or main stack"); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - - func = RNA_def_function( - srna, "move_to_layer_group", "rna_GreasePencil_layer_group_move_to_layer_group"); - RNA_def_function_ui_description(func, "Move a layer group into a parent layer group"); - parm = RNA_def_pointer( - func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); - RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - parm = RNA_def_pointer( - func, - "parent_group", - "GreasePencilLayerGroup", - "", - "The parent layer group the layer group will be moved into (use None for the main stack)"); - RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED | PARM_RNAPTR); - RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); - prop = RNA_def_property(srna, "active", PROP_POINTER, PROP_NONE); RNA_def_property_struct_type(prop, "GreasePencilLayerGroup"); RNA_def_property_pointer_funcs(prop, @@ -1422,6 +929,8 @@ static void rna_def_grease_pencil_layer_group_api(BlenderRNA *brna, PropertyRNA RNA_def_property_flag(prop, PROP_EDITABLE); RNA_def_property_ui_text(prop, "Active Layer Group", "Active Grease Pencil layer group"); RNA_def_property_update(prop, NC_GPENCIL | ND_DATA | NA_SELECTED, nullptr); + + RNA_api_grease_pencil_layer_groups(srna); } static void rna_def_grease_pencil_onion_skinning(StructRNA *srna) @@ -1618,7 +1127,7 @@ static void rna_def_grease_pencil_data(BlenderRNA *brna) nullptr, /* TODO */ nullptr); RNA_def_property_ui_text(prop, "Layers", "Grease Pencil layers"); - rna_def_grease_pencil_layers_api(brna, prop); + rna_def_grease_pencil_layers(brna, prop); /* Layer Groups */ prop = RNA_def_property(srna, "layer_groups", PROP_COLLECTION, PROP_NONE); @@ -1633,7 +1142,7 @@ static void rna_def_grease_pencil_data(BlenderRNA *brna) nullptr, /* TODO */ nullptr); RNA_def_property_ui_text(prop, "Layer Groups", "Grease Pencil layer groups"); - rna_def_grease_pencil_layer_group_api(brna, prop); + rna_def_grease_pencil_layer_groups(brna, prop); prop = RNA_def_property(srna, "use_autolock_layers", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, nullptr, "flag", GREASE_PENCIL_AUTOLOCK_LAYERS); diff --git a/source/blender/makesrna/intern/rna_grease_pencil_api.cc b/source/blender/makesrna/intern/rna_grease_pencil_api.cc new file mode 100644 index 00000000000..e159bda26aa --- /dev/null +++ b/source/blender/makesrna/intern/rna_grease_pencil_api.cc @@ -0,0 +1,533 @@ +/* SPDX-FileCopyrightText: 2024 Blender Authors + * + * SPDX-License-Identifier: GPL-2.0-or-later */ + +/** \file + * \ingroup RNA + */ + +#include "DNA_grease_pencil_types.h" +#include "DNA_scene_types.h" + +#include "RNA_define.hh" + +#include "WM_api.hh" + +#include "rna_internal.hh" /* own include */ + +const EnumPropertyItem rna_enum_tree_node_move_type_items[] = { + {-1, "DOWN", 0, "Down", ""}, + {1, "UP", 0, "Up", ""}, + {0, nullptr, 0, nullptr, nullptr}, +}; + +#ifdef RNA_RUNTIME + +# include "BKE_report.hh" +# include "BKE_grease_pencil.hh" + +# include "DEG_depsgraph.hh" + +static GreasePencilFrame *rna_Frames_frame_new(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int frame_number) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (layer.frames().contains(frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", frame_number); + return nullptr; + } + + grease_pencil.insert_frame(layer, frame_number, 0, BEZT_KEYTYPE_KEYFRAME); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + + return layer.frame_at(frame_number); +} + +static void rna_Frames_frame_remove(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int frame_number) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (!layer.frames().contains(frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", frame_number); + return; + } + + if (grease_pencil.remove_frames(layer, {frame_number})) { + DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + } +} + +static GreasePencilFrame *rna_Frames_frame_copy(ID *id, + GreasePencilLayer *layer_in, + ReportList *reports, + int from_frame_number, + int to_frame_number, + bool instance_drawing) +{ + using namespace blender::bke::greasepencil; + GreasePencil &grease_pencil = *reinterpret_cast(id); + Layer &layer = static_cast(layer_in)->wrap(); + + if (!layer.frames().contains(from_frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame doesn't exists on frame number %d", from_frame_number); + return nullptr; + } + if (layer.frames().contains(to_frame_number)) { + BKE_reportf(reports, RPT_ERROR, "Frame already exists on frame number %d", to_frame_number); + return nullptr; + } + + grease_pencil.insert_duplicate_frame( + layer, from_frame_number, to_frame_number, instance_drawing); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, &grease_pencil); + + return layer.frame_at(to_frame_number); +} + +static GreasePencilFrame *rna_GreasePencilLayer_get_frame_at(GreasePencilLayer *layer, + int frame_number) +{ + using namespace blender::bke::greasepencil; + return static_cast(layer)->frame_at(frame_number); +} + +static GreasePencilLayer *rna_GreasePencil_layer_new(GreasePencil *grease_pencil, + const char *name, + const bool set_active, + PointerRNA *layer_group_ptr) +{ + using namespace blender::bke::greasepencil; + LayerGroup *layer_group = nullptr; + if (layer_group_ptr && layer_group_ptr->data) { + layer_group = static_cast(layer_group_ptr->data); + } + Layer *layer; + if (layer_group) { + layer = &grease_pencil->add_layer(*layer_group, name); + } + else { + layer = &grease_pencil->add_layer(name); + } + if (set_active) { + grease_pencil->set_active_layer(layer); + } + + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); + + return layer; +} + +static void rna_GreasePencil_layer_remove(GreasePencil *grease_pencil, PointerRNA *layer_ptr) +{ + blender::bke::greasepencil::Layer &layer = *static_cast( + layer_ptr->data); + grease_pencil->remove_layer(layer); + + RNA_POINTER_INVALIDATE(layer_ptr); + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | ND_DATA | NA_SELECTED, grease_pencil); +} + +static void rna_GreasePencil_layer_move(GreasePencil *grease_pencil, + PointerRNA *layer_ptr, + const int direction) +{ + if (direction == 0) { + return; + } + + blender::bke::greasepencil::TreeNode &layer_node = + static_cast(layer_ptr->data)->as_node(); + switch (direction) { + case -1: + grease_pencil->move_node_down(layer_node, 1); + break; + case 1: + grease_pencil->move_node_up(layer_node, 1); + break; + } + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_move_top(GreasePencil *grease_pencil, PointerRNA *layer_ptr) +{ + blender::bke::greasepencil::TreeNode &layer_node = + static_cast(layer_ptr->data)->as_node(); + grease_pencil->move_node_top(layer_node); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_move_bottom(GreasePencil *grease_pencil, PointerRNA *layer_ptr) +{ + blender::bke::greasepencil::TreeNode &layer_node = + static_cast(layer_ptr->data)->as_node(); + grease_pencil->move_node_bottom(layer_node); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_move_to_layer_group(GreasePencil *grease_pencil, + PointerRNA *layer_ptr, + PointerRNA *layer_group_ptr) +{ + using namespace blender::bke::greasepencil; + TreeNode &layer_node = static_cast(layer_ptr->data)->as_node(); + LayerGroup *layer_group; + if (layer_group_ptr && layer_group_ptr->data) { + layer_group = static_cast(layer_group_ptr->data); + } + else { + layer_group = &grease_pencil->root_group(); + } + if (layer_group == nullptr) { + return; + } + grease_pencil->move_node_into(layer_node, *layer_group); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static PointerRNA rna_GreasePencil_layer_group_new(GreasePencil *grease_pencil, + const char *name, + PointerRNA *parent_group_ptr) +{ + using namespace blender::bke::greasepencil; + LayerGroup *parent_group; + if (parent_group_ptr && parent_group_ptr->data) { + parent_group = static_cast(parent_group_ptr->data); + } + else { + parent_group = &grease_pencil->root_group(); + } + LayerGroup *new_layer_group = &grease_pencil->add_layer_group(*parent_group, name); + + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); + + PointerRNA ptr = RNA_pointer_create( + &grease_pencil->id, &RNA_GreasePencilLayerGroup, new_layer_group); + return ptr; +} + +static void rna_GreasePencil_layer_group_remove(GreasePencil *grease_pencil, + PointerRNA *layer_group_ptr, + bool keep_children) +{ + using namespace blender::bke::greasepencil; + LayerGroup &layer_group = *static_cast(layer_group_ptr->data); + grease_pencil->remove_group(layer_group, keep_children); + + RNA_POINTER_INVALIDATE(layer_group_ptr); + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | ND_DATA | NA_SELECTED, grease_pencil); +} + +static void rna_GreasePencil_layer_group_move(GreasePencil *grease_pencil, + PointerRNA *layer_group_ptr, + int direction) +{ + if (direction == 0) { + return; + } + + blender::bke::greasepencil::TreeNode &layer_group_node = + static_cast(layer_group_ptr->data)->as_node(); + switch (direction) { + case -1: + grease_pencil->move_node_down(layer_group_node, 1); + break; + case 1: + grease_pencil->move_node_up(layer_group_node, 1); + break; + } + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_group_move_top(GreasePencil *grease_pencil, + PointerRNA *layer_group_ptr) +{ + blender::bke::greasepencil::TreeNode &layer_group_node = + static_cast(layer_group_ptr->data)->as_node(); + grease_pencil->move_node_top(layer_group_node); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_group_move_bottom(GreasePencil *grease_pencil, + PointerRNA *layer_group_ptr) +{ + blender::bke::greasepencil::TreeNode &layer_group_node = + static_cast(layer_group_ptr->data)->as_node(); + grease_pencil->move_node_bottom(layer_group_node); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +static void rna_GreasePencil_layer_group_move_to_layer_group(GreasePencil *grease_pencil, + PointerRNA *layer_group_ptr, + PointerRNA *parent_group_ptr) +{ + using namespace blender::bke::greasepencil; + TreeNode &layer_group_node = static_cast(layer_group_ptr->data)->as_node(); + LayerGroup *parent_group; + if (parent_group_ptr && parent_group_ptr->data) { + parent_group = static_cast(parent_group_ptr->data); + } + else { + parent_group = &grease_pencil->root_group(); + } + grease_pencil->move_node_into(layer_group_node, *parent_group); + + DEG_id_tag_update(&grease_pencil->id, ID_RECALC_GEOMETRY); + WM_main_add_notifier(NC_GPENCIL | NA_EDITED, grease_pencil); +} + +#else + +void RNA_api_grease_pencil_frames(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func = RNA_def_function(srna, "new", "rna_Frames_frame_new"); + RNA_def_function_ui_description(func, "Add a new Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Frame Number", + "The frame on which the drawing appears", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "", "The newly created frame"); + RNA_def_function_return(func, parm); + + func = RNA_def_function(srna, "remove", "rna_Frames_frame_remove"); + RNA_def_function_ui_description(func, "Remove a Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Frame Number", + "The frame number of the frame to remove", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + func = RNA_def_function(srna, "copy", "rna_Frames_frame_copy"); + RNA_def_function_ui_description(func, "Copy a Grease Pencil frame"); + RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID); + parm = RNA_def_int(func, + "from_frame_number", + 1, + MINAFRAME, + MAXFRAME, + "Source Frame Number", + "The frame number of the source frame", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_int(func, + "to_frame_number", + 2, + MINAFRAME, + MAXFRAME, + "Frame Number of Copy", + "The frame number to copy the frame to", + MINAFRAME, + MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_boolean(func, + "instance_drawing", + false, + "Instance Drawing", + "Let the copied frame use the same drawing as the source"); + parm = RNA_def_pointer(func, "copy", "GreasePencilFrame", "", "The newly copied frame"); + RNA_def_function_return(func, parm); +} + +void RNA_api_grease_pencil_layer(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func = RNA_def_function(srna, "get_frame_at", "rna_GreasePencilLayer_get_frame_at"); + RNA_def_function_ui_description(func, "Get the frame at given frame number"); + parm = RNA_def_int( + func, "frame_number", 1, MINAFRAME, MAXFRAME, "Frame Number", "", MINAFRAME, MAXFRAME); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_pointer(func, "frame", "GreasePencilFrame", "Frame", ""); + RNA_def_function_return(func, parm); +} + +void RNA_api_grease_pencil_layers(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func = RNA_def_function(srna, "new", "rna_GreasePencil_layer_new"); + RNA_def_function_ui_description(func, "Add a new Grease Pencil layer"); + parm = RNA_def_string(func, "name", "GreasePencilLayer", MAX_NAME, "Name", "Name of the layer"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + RNA_def_boolean( + func, "set_active", true, "Set Active", "Set the newly created layer as the active layer"); + parm = RNA_def_pointer( + func, + "layer_group", + "GreasePencilLayerGroup", + "", + "The layer group the new layer will be created in (use None for the main stack)"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The newly created layer"); + RNA_def_function_return(func, parm); + + func = RNA_def_function(srna, "remove", "rna_GreasePencil_layer_remove"); + RNA_def_function_ui_description(func, "Remove a Grease Pencil layer"); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to remove"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + func = RNA_def_function(srna, "move", "rna_GreasePencil_layer_move"); + RNA_def_function_ui_description(func, + "Move a Grease Pencil layer in the layer group or main stack"); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + parm = RNA_def_enum( + func, "type", rna_enum_tree_node_move_type_items, 1, "", "Direction of movement"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + func = RNA_def_function(srna, "move_top", "rna_GreasePencil_layer_move_top"); + RNA_def_function_ui_description( + func, "Move a Grease Pencil layer to the top of the layer group or main stack"); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + func = RNA_def_function(srna, "move_bottom", "rna_GreasePencil_layer_move_bottom"); + RNA_def_function_ui_description( + func, "Move a Grease Pencil layer to the bottom of the layer group or main stack"); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + func = RNA_def_function( + srna, "move_to_layer_group", "rna_GreasePencil_layer_move_to_layer_group"); + RNA_def_function_ui_description(func, "Move a Grease Pencil layer into a layer group"); + parm = RNA_def_pointer(func, "layer", "GreasePencilLayer", "", "The layer to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + parm = RNA_def_pointer( + func, + "layer_group", + "GreasePencilLayerGroup", + "", + "The layer group the layer will be moved into (use None for the main stack)"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); +} + +void RNA_api_grease_pencil_layer_groups(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func = RNA_def_function(srna, "new", "rna_GreasePencil_layer_group_new"); + RNA_def_function_ui_description(func, "Add a new Grease Pencil layer group"); + parm = RNA_def_string( + func, "name", "GreasePencilLayerGroup", MAX_NAME, "Name", "Name of the layer group"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + parm = RNA_def_pointer( + func, + "parent_group", + "GreasePencilLayerGroup", + "", + "The parent layer group the new group will be created in (use None for the main stack)"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The newly created layer group"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_RNAPTR); + RNA_def_function_return(func, parm); + + func = RNA_def_function(srna, "remove", "rna_GreasePencil_layer_group_remove"); + RNA_def_function_ui_description(func, "Remove a new Grease Pencil layer group"); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to remove"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + parm = RNA_def_boolean(func, + "keep_children", + false, + "", + "Keep the children nodes of the group and only delete the group itself"); + + func = RNA_def_function(srna, "move", "rna_GreasePencil_layer_group_move"); + RNA_def_function_ui_description(func, + "Move a layer group in the parent layer group or main stack"); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + parm = RNA_def_enum( + func, "type", rna_enum_tree_node_move_type_items, 1, "", "Direction of movement"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + + func = RNA_def_function(srna, "move_top", "rna_GreasePencil_layer_group_move_top"); + RNA_def_function_ui_description( + func, "Move a layer group to the top of the parent layer group or main stack"); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + func = RNA_def_function(srna, "move_bottom", "rna_GreasePencil_layer_group_move_bottom"); + RNA_def_function_ui_description( + func, "Move a layer group to the bottom of the parent layer group or main stack"); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + + func = RNA_def_function( + srna, "move_to_layer_group", "rna_GreasePencil_layer_group_move_to_layer_group"); + RNA_def_function_ui_description(func, "Move a layer group into a parent layer group"); + parm = RNA_def_pointer( + func, "layer_group", "GreasePencilLayerGroup", "", "The layer group to move"); + RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); + parm = RNA_def_pointer( + func, + "parent_group", + "GreasePencilLayerGroup", + "", + "The parent layer group the layer group will be moved into (use None for the main stack)"); + RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED | PARM_RNAPTR); + RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, ParameterFlag(0)); +} + +#endif diff --git a/source/blender/makesrna/intern/rna_internal.hh b/source/blender/makesrna/intern/rna_internal.hh index 30f666adfbb..2d56e289d22 100644 --- a/source/blender/makesrna/intern/rna_internal.hh +++ b/source/blender/makesrna/intern/rna_internal.hh @@ -427,6 +427,10 @@ void RNA_api_operator(StructRNA *srna); void RNA_api_macro(StructRNA *srna); void RNA_api_gizmo(StructRNA *srna); void RNA_api_gizmogroup(StructRNA *srna); +void RNA_api_grease_pencil_frames(StructRNA *srna); +void RNA_api_grease_pencil_layer(StructRNA *srna); +void RNA_api_grease_pencil_layers(StructRNA *srna); +void RNA_api_grease_pencil_layer_groups(StructRNA *srna); void RNA_api_keyconfig(StructRNA *srna); void RNA_api_keyconfigs(StructRNA *srna); void RNA_api_keyingset(StructRNA *srna); -- 2.30.2 From 98ab9ee5cbfee6bd222d09fbfa555c1d6d15b0cc Mon Sep 17 00:00:00 2001 From: Falk David Date: Fri, 26 Jul 2024 16:02:59 +0200 Subject: [PATCH 13/13] Formatting --- source/blender/makesrna/intern/rna_attribute.cc | 4 ++-- source/blender/makesrna/intern/rna_grease_pencil_api.cc | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/source/blender/makesrna/intern/rna_attribute.cc b/source/blender/makesrna/intern/rna_attribute.cc index 09285adc328..ead9b58cb63 100644 --- a/source/blender/makesrna/intern/rna_attribute.cc +++ b/source/blender/makesrna/intern/rna_attribute.cc @@ -683,8 +683,8 @@ static void rna_AttributeGroup_update_active(Main *bmain, Scene *scene, PointerR } static void rna_AttributeGroup_update_active_color(Main * /*bmain*/, - Scene * /*scene*/, - PointerRNA *ptr) + Scene * /*scene*/, + PointerRNA *ptr) { ID *id = ptr->owner_id; diff --git a/source/blender/makesrna/intern/rna_grease_pencil_api.cc b/source/blender/makesrna/intern/rna_grease_pencil_api.cc index e159bda26aa..1bb08cfa10d 100644 --- a/source/blender/makesrna/intern/rna_grease_pencil_api.cc +++ b/source/blender/makesrna/intern/rna_grease_pencil_api.cc @@ -23,8 +23,8 @@ const EnumPropertyItem rna_enum_tree_node_move_type_items[] = { #ifdef RNA_RUNTIME -# include "BKE_report.hh" # include "BKE_grease_pencil.hh" +# include "BKE_report.hh" # include "DEG_depsgraph.hh" -- 2.30.2