Fix: VSE: Propagate split to connected strips by default
Currently, attempting to split connected strips that are not both selected means that only one of the strips are affected. This violates the "connected" principle, so this PR makes the split operator propagate the split to connected strips by default. Holding alt returns old behavior (ignores connections), similar to selection logic. Pull Request: https://projects.blender.org/blender/blender/pulls/146380
This commit is contained in:
committed by
John Kiril Swenson
parent
1af6ac57f5
commit
412b5b3b3f
@@ -8628,6 +8628,14 @@ def km_sequencer_tool_blade(_params):
|
||||
("use_cursor_position", True),
|
||||
("ignore_selection", True),
|
||||
]}),
|
||||
("sequencer.split", {"type": 'LEFTMOUSE', "value": 'PRESS', "alt": True},
|
||||
{"properties": [
|
||||
("type", 'SOFT'),
|
||||
("side", 'NO_CHANGE'),
|
||||
("use_cursor_position", True),
|
||||
("ignore_selection", True),
|
||||
("ignore_connections", True),
|
||||
]}),
|
||||
]},
|
||||
)
|
||||
|
||||
|
||||
@@ -1757,6 +1757,7 @@ static wmOperatorStatus sequencer_split_exec(bContext *C, wmOperator *op)
|
||||
const seq::eSplitMethod method = seq::eSplitMethod(RNA_enum_get(op->ptr, "type"));
|
||||
const int split_side = sequence_split_side_for_exec_get(op);
|
||||
const bool ignore_selection = RNA_boolean_get(op->ptr, "ignore_selection");
|
||||
const bool ignore_connections = RNA_boolean_get(op->ptr, "ignore_connections");
|
||||
|
||||
seq::prefetch_stop(scene);
|
||||
|
||||
@@ -1767,9 +1768,14 @@ static wmOperatorStatus sequencer_split_exec(bContext *C, wmOperator *op)
|
||||
|
||||
if (ignore_selection || strip->flag & SELECT) {
|
||||
const char *error_msg = nullptr;
|
||||
if (seq::edit_strip_split(
|
||||
bmain, scene, ed->current_strips(), strip, split_frame, method, &error_msg) !=
|
||||
nullptr)
|
||||
if (seq::edit_strip_split(bmain,
|
||||
scene,
|
||||
ed->current_strips(),
|
||||
strip,
|
||||
split_frame,
|
||||
method,
|
||||
ignore_connections,
|
||||
&error_msg) != nullptr)
|
||||
{
|
||||
changed = true;
|
||||
}
|
||||
@@ -1881,6 +1887,10 @@ static void sequencer_split_ui(bContext * /*C*/, wmOperator *op)
|
||||
if (RNA_boolean_get(op->ptr, "use_cursor_position")) {
|
||||
layout->prop(op->ptr, "channel", UI_ITEM_NONE, std::nullopt, ICON_NONE);
|
||||
}
|
||||
|
||||
layout->separator();
|
||||
|
||||
layout->prop(op->ptr, "ignore_connections", UI_ITEM_NONE, std::nullopt, ICON_NONE);
|
||||
}
|
||||
|
||||
void SEQUENCER_OT_split(wmOperatorType *ot)
|
||||
@@ -1948,6 +1958,12 @@ void SEQUENCER_OT_split(wmOperatorType *ot)
|
||||
"Make cut even if strip is not selected preserving selection state after cut");
|
||||
|
||||
RNA_def_property_flag(prop, PROP_HIDDEN);
|
||||
|
||||
RNA_def_boolean(ot->srna,
|
||||
"ignore_connections",
|
||||
false,
|
||||
"Ignore Connections",
|
||||
"Don't propagate split to connected strips");
|
||||
}
|
||||
|
||||
/** \} */
|
||||
|
||||
@@ -88,15 +88,26 @@ static void rna_Strips_move_strip_to_meta(
|
||||
WM_main_add_notifier(NC_SCENE | ND_SEQUENCER, scene);
|
||||
}
|
||||
|
||||
static Strip *rna_Strip_split(
|
||||
ID *id, Strip *strip, Main *bmain, ReportList *reports, int frame, int split_method)
|
||||
static Strip *rna_Strip_split(ID *id,
|
||||
Strip *strip,
|
||||
Main *bmain,
|
||||
ReportList *reports,
|
||||
int frame,
|
||||
int split_method,
|
||||
bool ignore_connections)
|
||||
{
|
||||
Scene *scene = (Scene *)id;
|
||||
ListBase *seqbase = blender::seq::get_seqbase_by_strip(scene, strip);
|
||||
|
||||
const char *error_msg = nullptr;
|
||||
Strip *strip_split = blender::seq::edit_strip_split(
|
||||
bmain, scene, seqbase, strip, frame, blender::seq::eSplitMethod(split_method), &error_msg);
|
||||
Strip *strip_split = blender::seq::edit_strip_split(bmain,
|
||||
scene,
|
||||
seqbase,
|
||||
strip,
|
||||
frame,
|
||||
blender::seq::eSplitMethod(split_method),
|
||||
ignore_connections,
|
||||
&error_msg);
|
||||
if (error_msg != nullptr) {
|
||||
BKE_report(reports, RPT_ERROR, error_msg);
|
||||
}
|
||||
@@ -754,6 +765,8 @@ void RNA_api_strip(StructRNA *srna)
|
||||
RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED);
|
||||
parm = RNA_def_enum(func, "split_method", strip_split_method_items, 0, "", "");
|
||||
RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED);
|
||||
parm = RNA_def_boolean(
|
||||
func, "ignore_connections", false, "", "Don't propagate split to connected strips");
|
||||
/* Return type. */
|
||||
parm = RNA_def_pointer(func, "sequence", "Strip", "", "Right side Strip");
|
||||
RNA_def_function_return(func, parm);
|
||||
|
||||
@@ -73,6 +73,7 @@ Strip *edit_strip_split(Main *bmain,
|
||||
Strip *strip,
|
||||
int timeline_frame,
|
||||
eSplitMethod method,
|
||||
bool ignore_connections,
|
||||
const char **r_error);
|
||||
/**
|
||||
* Find gap after initial_frame and move strips on right side to close the gap
|
||||
|
||||
@@ -409,6 +409,7 @@ Strip *edit_strip_split(Main *bmain,
|
||||
Strip *strip,
|
||||
const int timeline_frame,
|
||||
const eSplitMethod method,
|
||||
const bool ignore_connections,
|
||||
const char **r_error)
|
||||
{
|
||||
if (!seq_edit_split_intersect_check(scene, strip, timeline_frame)) {
|
||||
@@ -418,21 +419,11 @@ Strip *edit_strip_split(Main *bmain,
|
||||
/* Whole strip effect chain must be duplicated in order to preserve relationships. */
|
||||
blender::VectorSet<Strip *> strips;
|
||||
strips.add(strip);
|
||||
iterator_set_expand(scene, seqbase, strips, query_strip_effect_chain);
|
||||
|
||||
/* All connected strips (that are selected and at the cut frame) must also be duplicated. */
|
||||
blender::VectorSet<Strip *> strips_old(strips);
|
||||
for (Strip *strip : strips_old) {
|
||||
blender::VectorSet<Strip *> connections = connected_strips_get(strip);
|
||||
connections.remove_if([&](Strip *connection) {
|
||||
return !(connection->flag & SELECT) ||
|
||||
!seq_edit_split_intersect_check(scene, connection, timeline_frame);
|
||||
});
|
||||
strips.add_multiple(connections.as_span());
|
||||
}
|
||||
|
||||
/* In case connected strips had effects, duplicate those too: */
|
||||
iterator_set_expand(scene, seqbase, strips, query_strip_effect_chain);
|
||||
iterator_set_expand(scene,
|
||||
seqbase,
|
||||
strips,
|
||||
ignore_connections ? query_strip_effect_chain :
|
||||
query_strip_connected_and_effect_chain);
|
||||
|
||||
if (!seq_edit_split_operation_permitted_check(scene, strips, timeline_frame, r_error)) {
|
||||
return nullptr;
|
||||
@@ -448,6 +439,10 @@ Strip *edit_strip_split(Main *bmain,
|
||||
BLI_remlink(seqbase, strip_iter);
|
||||
BLI_addtail(&left_strips, strip_iter);
|
||||
|
||||
if (ignore_connections) {
|
||||
seq::disconnect(strip_iter);
|
||||
}
|
||||
|
||||
/* Duplicate curves from backup, so they can be renamed along with split strips. */
|
||||
animation_duplicate_backup_to_scene(scene, strip_iter, &animation_backup);
|
||||
}
|
||||
|
||||
@@ -410,6 +410,7 @@ static void strip_transform_handle_overwrite_split(Scene *scene,
|
||||
target,
|
||||
time_left_handle_frame_get(scene, transformed),
|
||||
SPLIT_SOFT,
|
||||
true,
|
||||
nullptr);
|
||||
edit_strip_split(bmain,
|
||||
scene,
|
||||
@@ -417,6 +418,7 @@ static void strip_transform_handle_overwrite_split(Scene *scene,
|
||||
split_strip,
|
||||
time_right_handle_frame_get(scene, transformed),
|
||||
SPLIT_SOFT,
|
||||
true,
|
||||
nullptr);
|
||||
edit_flag_for_removal(scene, seqbasep, split_strip);
|
||||
edit_remove_flagged_strips(scene, seqbasep);
|
||||
|
||||
Reference in New Issue
Block a user