GPv3: Add API to copy and add a layer

This adds a core API to add a new layer by copying a source layer.
This commit is contained in:
Falk David
2023-10-17 15:41:39 +02:00
parent 79cbeae939
commit f59827de74
3 changed files with 60 additions and 9 deletions

View File

@@ -503,6 +503,7 @@ class LayerGroup : public ::GreasePencilLayerTreeGroup {
* Adds a new layer named \a name at the end of this group and returns it.
*/
Layer &add_layer(StringRefNull name);
Layer &add_layer(const Layer &duplicate_layer);
/**
* Adds a new group named \a name at the end of this group and returns it.
*/

View File

@@ -869,6 +869,12 @@ Layer &LayerGroup::add_layer(StringRefNull name)
return this->add_node(new_layer->as_node()).as_layer();
}
Layer &LayerGroup::add_layer(const Layer &duplicate_layer)
{
Layer *new_layer = MEM_new<Layer>(__func__, duplicate_layer);
return this->add_node(new_layer->as_node()).as_layer();
}
LayerGroup &LayerGroup::add_group(StringRefNull name)
{
LayerGroup *new_group = MEM_new<LayerGroup>(__func__, name);
@@ -1664,6 +1670,24 @@ void GreasePencil::remove_drawings_with_no_users()
remove_drawings_unchecked(*this, drawings_to_be_removed.as_span());
}
void GreasePencil::update_drawing_users_for_layer(const blender::bke::greasepencil::Layer &layer)
{
using namespace blender;
for (auto [key, value] : layer.frames().items()) {
if (value.drawing_index > 0 && value.drawing_index < this->drawings().size()) {
GreasePencilDrawingBase *drawing_base = this->drawing(value.drawing_index);
if (drawing_base->type != GP_DRAWING) {
continue;
}
bke::greasepencil::Drawing &drawing =
reinterpret_cast<GreasePencilDrawing *>(drawing_base)->wrap();
if (!drawing.has_users()) {
drawing.add_user();
}
}
}
}
void GreasePencil::move_frames(blender::bke::greasepencil::Layer &layer,
const blender::Map<int, int> &frame_number_destinations)
{
@@ -2029,23 +2053,42 @@ static int find_layer_insertion_index(
return index;
}
static void grow_or_init_customdata(GreasePencil *grease_pencil,
const blender::bke::greasepencil::LayerGroup &parent_group)
{
using namespace blender;
const Span<const bke::greasepencil::Layer *> layers = grease_pencil->layers();
if (layers.is_empty()) {
CustomData_realloc(&grease_pencil->layers_data, 0, 1);
}
else {
int insertion_index = find_layer_insertion_index(layers, parent_group, false);
grow_customdata(grease_pencil->layers_data, insertion_index, layers.size());
}
}
blender::bke::greasepencil::Layer &GreasePencil::add_layer(
blender::bke::greasepencil::LayerGroup &parent_group, const blender::StringRefNull name)
{
using namespace blender;
std::string unique_name = unique_layer_name(*this, name);
const Span<const bke::greasepencil::Layer *> layers = this->layers();
if (layers.is_empty()) {
CustomData_realloc(&this->layers_data, 0, 1);
return parent_group.add_layer(unique_name);
}
int insertion_index = find_layer_insertion_index(layers, parent_group, false);
grow_customdata(this->layers_data, insertion_index, layers.size());
grow_or_init_customdata(this, parent_group);
return parent_group.add_layer(unique_name);
}
blender::bke::greasepencil::Layer &GreasePencil::add_layer(
blender::bke::greasepencil::LayerGroup &parent_group,
const blender::bke::greasepencil::Layer &duplicate_layer)
{
using namespace blender;
std::string unique_name = unique_layer_name(*this, duplicate_layer.name());
grow_or_init_customdata(this, parent_group);
bke::greasepencil::Layer &new_layer = parent_group.add_layer(duplicate_layer);
this->update_drawing_users_for_layer(new_layer);
new_layer.set_name(unique_name);
return new_layer;
}
blender::bke::greasepencil::LayerGroup &GreasePencil::add_layer_group(
blender::bke::greasepencil::LayerGroup &parent_group, const blender::StringRefNull name)
{

View File

@@ -467,6 +467,9 @@ typedef struct GreasePencil {
/* Adding layers and layer groups. */
blender::bke::greasepencil::Layer &add_layer(
blender::bke::greasepencil::LayerGroup &parent_group, blender::StringRefNull name);
blender::bke::greasepencil::Layer &add_layer(
blender::bke::greasepencil::LayerGroup &parent_group,
const blender::bke::greasepencil::Layer &duplicate_layer);
blender::bke::greasepencil::LayerGroup &add_layer_group(
blender::bke::greasepencil::LayerGroup &parent_group, blender::StringRefNull name);
@@ -545,6 +548,10 @@ typedef struct GreasePencil {
* drawings array.
*/
void remove_drawings_with_no_users();
/**
* Makes sure all the drawings that the layer points to have a user.
*/
void update_drawing_users_for_layer(const blender::bke::greasepencil::Layer &layer);
/**
* Returns a drawing on \a layer at frame \a frame_number or `nullptr` if no such