Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/sequencer/intern')
-rw-r--r--source/blender/sequencer/intern/disk_cache.c5
-rw-r--r--source/blender/sequencer/intern/effects.c21
-rw-r--r--source/blender/sequencer/intern/image_cache.c19
-rw-r--r--source/blender/sequencer/intern/proxy.c8
-rw-r--r--source/blender/sequencer/intern/render.c22
-rw-r--r--source/blender/sequencer/intern/sequence_lookup.c94
-rw-r--r--source/blender/sequencer/intern/sequencer.h26
-rw-r--r--source/blender/sequencer/intern/sound.c10
-rw-r--r--source/blender/sequencer/intern/strip_add.c41
-rw-r--r--source/blender/sequencer/intern/strip_edit.c73
-rw-r--r--source/blender/sequencer/intern/strip_relations.c9
-rw-r--r--source/blender/sequencer/intern/strip_time.c217
-rw-r--r--source/blender/sequencer/intern/strip_time.h5
-rw-r--r--source/blender/sequencer/intern/strip_transform.c150
-rw-r--r--source/blender/sequencer/intern/utils.c68
15 files changed, 373 insertions, 395 deletions
diff --git a/source/blender/sequencer/intern/disk_cache.c b/source/blender/sequencer/intern/disk_cache.c
index f8e8fc32a5d..cc34066c432 100644
--- a/source/blender/sequencer/intern/disk_cache.c
+++ b/source/blender/sequencer/intern/disk_cache.c
@@ -37,6 +37,7 @@
#include "SEQ_relations.h"
#include "SEQ_render.h"
#include "SEQ_sequencer.h"
+#include "SEQ_time.h"
#include "disk_cache.h"
#include "image_cache.h"
@@ -411,8 +412,8 @@ void seq_disk_cache_invalidate(SeqDiskCache *disk_cache,
BLI_mutex_lock(&disk_cache->read_write_mutex);
- start = seq_changed->startdisp - DCACHE_IMAGES_PER_FILE;
- end = seq_changed->enddisp;
+ start = SEQ_time_left_handle_frame_get(seq_changed) - DCACHE_IMAGES_PER_FILE;
+ end = SEQ_time_right_handle_frame_get(seq_changed);
seq_disk_cache_delete_invalid_files(disk_cache, scene, seq, invalidate_types, start, end);
diff --git a/source/blender/sequencer/intern/effects.c b/source/blender/sequencer/intern/effects.c
index d9d21ee3b05..0e5e56908b0 100644
--- a/source/blender/sequencer/intern/effects.c
+++ b/source/blender/sequencer/intern/effects.c
@@ -49,6 +49,7 @@
#include "SEQ_proxy.h"
#include "SEQ_relations.h"
#include "SEQ_render.h"
+#include "SEQ_time.h"
#include "SEQ_utils.h"
#include "BLF_api.h"
@@ -2431,7 +2432,7 @@ static ImBuf *do_multicam(const SeqRenderData *context,
if (!ed) {
return NULL;
}
- ListBase *seqbasep = SEQ_get_seqbase_by_seq(&ed->seqbase, seq);
+ ListBase *seqbasep = SEQ_get_seqbase_by_seq(context->scene, seq);
ListBase *channels = SEQ_get_channels_by_seq(&ed->seqbase, &ed->channels, seq);
if (!seqbasep) {
return NULL;
@@ -2467,13 +2468,15 @@ static ImBuf *do_adjustment_impl(const SeqRenderData *context, Sequence *seq, fl
ed = context->scene->ed;
- ListBase *seqbasep = SEQ_get_seqbase_by_seq(&ed->seqbase, seq);
+ ListBase *seqbasep = SEQ_get_seqbase_by_seq(context->scene, seq);
ListBase *channels = SEQ_get_channels_by_seq(&ed->seqbase, &ed->channels, seq);
/* Clamp timeline_frame to strip range so it behaves as if it had "still frame" offset (last
* frame is static after end of strip). This is how most strips behave. This way transition
* effects that doesn't overlap or speed effect can't fail rendering outside of strip range. */
- timeline_frame = clamp_i(timeline_frame, seq->startdisp, seq->enddisp - 1);
+ timeline_frame = clamp_i(timeline_frame,
+ SEQ_time_left_handle_frame_get(seq),
+ SEQ_time_right_handle_frame_get(seq) - 1);
if (seq->machine > 1) {
i = seq_render_give_ibuf_seqbase(
@@ -2583,7 +2586,7 @@ static int early_out_speed(Sequence *UNUSED(seq), float UNUSED(fac))
static int seq_effect_speed_get_strip_content_length(const Sequence *seq)
{
if ((seq->type & SEQ_TYPE_EFFECT) != 0 && SEQ_effect_get_num_inputs(seq->type) == 0) {
- return seq->enddisp - seq->startdisp;
+ return SEQ_time_right_handle_frame_get(seq) - SEQ_time_left_handle_frame_get(seq);
}
return seq->len;
@@ -2610,13 +2613,14 @@ void seq_effect_speed_rebuild_map(Scene *scene, Sequence *seq)
MEM_freeN(v->frameMap);
}
- const int effect_strip_length = seq->enddisp - seq->startdisp;
+ const int effect_strip_length = SEQ_time_right_handle_frame_get(seq) -
+ SEQ_time_left_handle_frame_get(seq);
v->frameMap = MEM_mallocN(sizeof(float) * effect_strip_length, __func__);
v->frameMap[0] = 0.0f;
float target_frame = 0;
for (int frame_index = 1; frame_index < effect_strip_length; frame_index++) {
- target_frame += evaluate_fcurve(fcu, seq->startdisp + frame_index);
+ target_frame += evaluate_fcurve(fcu, SEQ_time_left_handle_frame_get(seq) + frame_index);
CLAMP(target_frame, 0, seq->seq1->len);
v->frameMap[frame_index] = target_frame;
}
@@ -2652,7 +2656,8 @@ float seq_speed_effect_target_frame_get(Scene *scene,
/* Only right handle controls effect speed! */
const float target_content_length = seq_effect_speed_get_strip_content_length(source) -
source->startofs;
- const float speed_effetct_length = seq_speed->enddisp - seq_speed->startdisp;
+ const float speed_effetct_length = SEQ_time_right_handle_frame_get(seq_speed) -
+ SEQ_time_left_handle_frame_get(seq_speed);
const float ratio = frame_index / speed_effetct_length;
target_frame = target_content_length * ratio;
break;
@@ -3509,7 +3514,7 @@ static void get_default_fac_noop(Sequence *UNUSED(seq), float UNUSED(timeline_fr
static void get_default_fac_fade(Sequence *seq, float timeline_frame, float *fac)
{
- *fac = (float)(timeline_frame - seq->startdisp);
+ *fac = (float)(timeline_frame - SEQ_time_left_handle_frame_get(seq));
*fac /= seq->len;
}
diff --git a/source/blender/sequencer/intern/image_cache.c b/source/blender/sequencer/intern/image_cache.c
index e1ff0ff64b3..59de24930d6 100644
--- a/source/blender/sequencer/intern/image_cache.c
+++ b/source/blender/sequencer/intern/image_cache.c
@@ -36,6 +36,7 @@
#include "SEQ_prefetch.h"
#include "SEQ_relations.h"
#include "SEQ_sequencer.h"
+#include "SEQ_time.h"
#include "disk_cache.h"
#include "image_cache.h"
@@ -558,8 +559,9 @@ void seq_cache_free_temp_cache(Scene *scene, short id, int timeline_frame)
/* Use frame_index here to avoid freeing raw images if they are used for multiple frames. */
float frame_index = seq_cache_timeline_frame_to_frame_index(
key->seq, timeline_frame, key->type);
- if (frame_index != key->frame_index || timeline_frame > key->seq->enddisp ||
- timeline_frame < key->seq->startdisp) {
+ if (frame_index != key->frame_index ||
+ timeline_frame > SEQ_time_right_handle_frame_get(key->seq) ||
+ timeline_frame < SEQ_time_left_handle_frame_get(key->seq)) {
BLI_ghash_remove(cache->hash, key, seq_cache_keyfree, seq_cache_valfree);
}
}
@@ -634,8 +636,8 @@ void seq_cache_cleanup_sequence(Scene *scene,
seq_cache_lock(scene);
- int range_start = seq_changed->startdisp;
- int range_end = seq_changed->enddisp;
+ int range_start = SEQ_time_left_handle_frame_get(seq_changed);
+ int range_end = SEQ_time_right_handle_frame_get(seq_changed);
if (!force_seq_changed_range) {
if (seq->startdisp > range_start) {
@@ -668,8 +670,8 @@ void seq_cache_cleanup_sequence(Scene *scene,
}
if (key->type & invalidate_source && key->seq == seq &&
- key->timeline_frame >= seq_changed->startdisp &&
- key->timeline_frame <= seq_changed->enddisp) {
+ key->timeline_frame >= SEQ_time_left_handle_frame_get(seq_changed) &&
+ key->timeline_frame <= SEQ_time_right_handle_frame_get(seq_changed)) {
if (key->link_next || key->link_prev) {
seq_cache_relink_keys(key->link_next, key->link_prev);
}
@@ -700,11 +702,12 @@ void seq_cache_thumbnail_cleanup(Scene *scene, rctf *view_area_safe)
SeqCacheKey *key = BLI_ghashIterator_getKey(&gh_iter);
BLI_ghashIterator_step(&gh_iter);
- const int frame_index = key->timeline_frame - key->seq->startdisp;
+ const int frame_index = key->timeline_frame - SEQ_time_left_handle_frame_get(key->seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(key->seq);
const int relative_base_frame = round_fl_to_int((frame_index / (float)frame_step)) *
frame_step;
- const int nearest_guaranted_absolute_frame = relative_base_frame + key->seq->startdisp;
+ const int nearest_guaranted_absolute_frame = relative_base_frame +
+ SEQ_time_left_handle_frame_get(key->seq);
if (nearest_guaranted_absolute_frame == key->timeline_frame) {
continue;
diff --git a/source/blender/sequencer/intern/proxy.c b/source/blender/sequencer/intern/proxy.c
index 59b4c6de1ef..464580f5bed 100644
--- a/source/blender/sequencer/intern/proxy.c
+++ b/source/blender/sequencer/intern/proxy.c
@@ -43,6 +43,7 @@
#include "SEQ_relations.h"
#include "SEQ_render.h"
#include "SEQ_sequencer.h"
+#include "SEQ_time.h"
#include "multiview.h"
#include "proxy.h"
@@ -523,7 +524,9 @@ void SEQ_proxy_rebuild(SeqIndexBuildContext *context,
SeqRenderState state;
seq_render_state_init(&state);
- for (timeline_frame = seq->startdisp; timeline_frame < seq->enddisp; timeline_frame++) {
+ for (timeline_frame = SEQ_time_left_handle_frame_get(seq);
+ timeline_frame < SEQ_time_right_handle_frame_get(seq);
+ timeline_frame++) {
if (context->size_flags & IMB_PROXY_25) {
seq_proxy_build_frame(&render_context, &state, seq, timeline_frame, 25, overwrite);
}
@@ -537,7 +540,8 @@ void SEQ_proxy_rebuild(SeqIndexBuildContext *context,
seq_proxy_build_frame(&render_context, &state, seq, timeline_frame, 100, overwrite);
}
- *progress = (float)(timeline_frame - seq->startdisp) / (seq->enddisp - seq->startdisp);
+ *progress = (float)(timeline_frame - SEQ_time_left_handle_frame_get(seq)) /
+ (SEQ_time_right_handle_frame_get(seq) - SEQ_time_left_handle_frame_get(seq));
*do_update = true;
if (*stop || G.is_break) {
diff --git a/source/blender/sequencer/intern/render.c b/source/blender/sequencer/intern/render.c
index b0898be3765..e7a1bbeb9d0 100644
--- a/source/blender/sequencer/intern/render.c
+++ b/source/blender/sequencer/intern/render.c
@@ -1994,11 +1994,12 @@ ImBuf *SEQ_render_give_ibuf_direct(const SeqRenderData *context,
float SEQ_render_thumbnail_first_frame_get(Sequence *seq, float frame_step, rctf *view_area)
{
- int first_drawable_frame = max_iii(seq->startdisp, seq->start, view_area->xmin);
+ int first_drawable_frame = max_iii(
+ SEQ_time_left_handle_frame_get(seq), seq->start, view_area->xmin);
/* First frame should correspond to handle position. */
- if (first_drawable_frame == seq->startdisp) {
- return seq->startdisp;
+ if (first_drawable_frame == SEQ_time_left_handle_frame_get(seq)) {
+ return SEQ_time_left_handle_frame_get(seq);
}
float aligned_frame_offset = (int)((first_drawable_frame - seq->start) / frame_step) *
@@ -2011,7 +2012,7 @@ float SEQ_render_thumbnail_next_frame_get(Sequence *seq, float last_frame, float
float next_frame = last_frame + frame_step;
/* If handle position was displayed, align next frame with `seq->start`. */
- if (last_frame == seq->startdisp) {
+ if (last_frame == SEQ_time_left_handle_frame_get(seq)) {
next_frame = seq->start + ((int)((last_frame - seq->start) / frame_step) + 1) * frame_step;
}
@@ -2088,8 +2089,9 @@ void SEQ_render_thumbnails(const SeqRenderData *context,
/* Adding the hold offset value (seq->anim_startofs) to the start frame. Position of image not
* affected, but frame loaded affected. */
- float upper_thumb_bound = SEQ_time_has_right_still_frames(seq) ? (seq->start + seq->len) :
- seq->enddisp;
+ float upper_thumb_bound = SEQ_time_has_right_still_frames(seq) ?
+ (seq->start + seq->len) :
+ SEQ_time_right_handle_frame_get(seq);
upper_thumb_bound = (upper_thumb_bound > view_area->xmax) ? view_area->xmax + frame_step :
upper_thumb_bound;
@@ -2122,8 +2124,8 @@ void SEQ_render_thumbnails(const SeqRenderData *context,
int SEQ_render_thumbnails_guaranteed_set_frame_step_get(const Sequence *seq)
{
- const int content_start = max_ii(seq->startdisp, seq->start);
- const int content_end = min_ii(seq->enddisp, seq->start + seq->len);
+ const int content_start = max_ii(SEQ_time_left_handle_frame_get(seq), seq->start);
+ const int content_end = min_ii(SEQ_time_right_handle_frame_get(seq), seq->start + seq->len);
const int content_len = content_end - content_start;
/* Arbitrary, but due to performance reasons should be as low as possible. */
@@ -2143,10 +2145,10 @@ void SEQ_render_thumbnails_base_set(const SeqRenderData *context,
SeqRenderState state;
seq_render_state_init(&state);
- int timeline_frame = seq->startdisp;
+ int timeline_frame = SEQ_time_left_handle_frame_get(seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(seq);
- while (timeline_frame < seq->enddisp && !*stop) {
+ while (timeline_frame < SEQ_time_right_handle_frame_get(seq) && !*stop) {
ImBuf *ibuf = seq_cache_get(
context, seq_orig, roundf(timeline_frame), SEQ_CACHE_STORE_THUMBNAIL);
if (ibuf) {
diff --git a/source/blender/sequencer/intern/sequence_lookup.c b/source/blender/sequencer/intern/sequence_lookup.c
index 2a2626d8abf..8d18e381171 100644
--- a/source/blender/sequencer/intern/sequence_lookup.c
+++ b/source/blender/sequencer/intern/sequence_lookup.c
@@ -6,6 +6,7 @@
*/
#include "SEQ_sequencer.h"
+#include "sequencer.h"
#include "DNA_listBase.h"
#include "DNA_scene_types.h"
@@ -14,6 +15,7 @@
#include "SEQ_iterator.h"
#include "BLI_ghash.h"
+#include "BLI_listbase.h"
#include "BLI_string.h"
#include "BLI_sys_types.h"
#include "BLI_threads.h"
@@ -24,24 +26,66 @@
static ThreadMutex lookup_lock = BLI_MUTEX_INITIALIZER;
typedef struct SequenceLookup {
- GHash *by_name;
+ GHash *seq_by_name;
+ GHash *meta_by_seq;
+ GHash *effects_by_seq;
eSequenceLookupTag tag;
} SequenceLookup;
static void seq_sequence_lookup_init(struct SequenceLookup *lookup)
{
- lookup->by_name = BLI_ghash_str_new(__func__);
+ lookup->seq_by_name = BLI_ghash_str_new(__func__);
+ lookup->meta_by_seq = BLI_ghash_ptr_new(__func__);
+ lookup->effects_by_seq = BLI_ghash_ptr_new(__func__);
lookup->tag |= SEQ_LOOKUP_TAG_INVALID;
}
-static void seq_sequence_lookup_build(const struct Scene *scene, struct SequenceLookup *lookup)
+static void seq_sequence_lookup_append_effect(Sequence *input,
+ Sequence *effect,
+ struct SequenceLookup *lookup)
+{
+ if (input == NULL) {
+ return;
+ }
+
+ SeqCollection *effects = BLI_ghash_lookup(lookup->effects_by_seq, input);
+ if (effects == NULL) {
+ effects = SEQ_collection_create(__func__);
+ BLI_ghash_insert(lookup->effects_by_seq, input, effects);
+ }
+
+ SEQ_collection_append_strip(effect, effects);
+}
+
+static void seq_sequence_lookup_build_effect(Sequence *seq, struct SequenceLookup *lookup)
{
- SeqCollection *all_strips = SEQ_query_all_strips_recursive(&scene->ed->seqbase);
- Sequence *seq;
- SEQ_ITERATOR_FOREACH (seq, all_strips) {
- BLI_ghash_insert(lookup->by_name, seq->name + 2, seq);
+ if ((seq->type & SEQ_TYPE_EFFECT) == 0) {
+ return;
}
- SEQ_collection_free(all_strips);
+
+ seq_sequence_lookup_append_effect(seq->seq1, seq, lookup);
+ seq_sequence_lookup_append_effect(seq->seq2, seq, lookup);
+}
+
+static void seq_sequence_lookup_build_from_seqbase(Sequence *parent_meta,
+ const ListBase *seqbase,
+ struct SequenceLookup *lookup)
+{
+ LISTBASE_FOREACH (Sequence *, seq, seqbase) {
+ BLI_ghash_insert(lookup->seq_by_name, seq->name + 2, seq);
+ BLI_ghash_insert(lookup->meta_by_seq, seq, parent_meta);
+ seq_sequence_lookup_build_effect(seq, lookup);
+
+ if (seq->type == SEQ_TYPE_META) {
+ seq_sequence_lookup_build_from_seqbase(seq, &seq->seqbase, lookup);
+ }
+ }
+}
+
+static void seq_sequence_lookup_build(const struct Scene *scene, struct SequenceLookup *lookup)
+{
+ Editing *ed = SEQ_editing_get(scene);
+ seq_sequence_lookup_build_from_seqbase(NULL, &ed->seqbase, lookup);
lookup->tag &= ~SEQ_LOOKUP_TAG_INVALID;
}
@@ -58,8 +102,12 @@ static void seq_sequence_lookup_free(struct SequenceLookup **lookup)
return;
}
- BLI_ghash_free((*lookup)->by_name, NULL, NULL);
- (*lookup)->by_name = NULL;
+ BLI_ghash_free((*lookup)->seq_by_name, NULL, NULL);
+ BLI_ghash_free((*lookup)->meta_by_seq, NULL, NULL);
+ BLI_ghash_free((*lookup)->effects_by_seq, NULL, SEQ_collection_free_void_p);
+ (*lookup)->seq_by_name = NULL;
+ (*lookup)->meta_by_seq = NULL;
+ (*lookup)->effects_by_seq = NULL;
MEM_freeN(*lookup);
*lookup = NULL;
}
@@ -98,17 +146,39 @@ void SEQ_sequence_lookup_free(const Scene *scene)
BLI_mutex_unlock(&lookup_lock);
}
-Sequence *SEQ_sequence_lookup_by_name(const Scene *scene, const char *key)
+Sequence *SEQ_sequence_lookup_seq_by_name(const Scene *scene, const char *key)
+{
+ BLI_assert(scene->ed);
+ BLI_mutex_lock(&lookup_lock);
+ seq_sequence_lookup_update_if_needed(scene, &scene->ed->runtime.sequence_lookup);
+ SequenceLookup *lookup = scene->ed->runtime.sequence_lookup;
+ Sequence *seq = BLI_ghash_lookup(lookup->seq_by_name, key);
+ BLI_mutex_unlock(&lookup_lock);
+ return seq;
+}
+
+Sequence *seq_sequence_lookup_meta_by_seq(const Scene *scene, const Sequence *key)
{
BLI_assert(scene->ed);
BLI_mutex_lock(&lookup_lock);
seq_sequence_lookup_update_if_needed(scene, &scene->ed->runtime.sequence_lookup);
SequenceLookup *lookup = scene->ed->runtime.sequence_lookup;
- Sequence *seq = BLI_ghash_lookup(lookup->by_name, key);
+ Sequence *seq = BLI_ghash_lookup(lookup->meta_by_seq, key);
BLI_mutex_unlock(&lookup_lock);
return seq;
}
+SeqCollection *seq_sequence_lookup_effects_by_seq(const Scene *scene, const Sequence *key)
+{
+ BLI_assert(scene->ed);
+ BLI_mutex_lock(&lookup_lock);
+ seq_sequence_lookup_update_if_needed(scene, &scene->ed->runtime.sequence_lookup);
+ SequenceLookup *lookup = scene->ed->runtime.sequence_lookup;
+ SeqCollection *effects = BLI_ghash_lookup(lookup->effects_by_seq, key);
+ BLI_mutex_unlock(&lookup_lock);
+ return effects;
+}
+
void SEQ_sequence_lookup_tag(const Scene *scene, eSequenceLookupTag tag)
{
if (!scene->ed) {
diff --git a/source/blender/sequencer/intern/sequencer.h b/source/blender/sequencer/intern/sequencer.h
index 9f5bdf672c0..5e78c8c6f96 100644
--- a/source/blender/sequencer/intern/sequencer.h
+++ b/source/blender/sequencer/intern/sequencer.h
@@ -14,13 +14,37 @@ extern "C" {
struct Scene;
struct Sequence;
struct StripProxy;
+struct SeqCollection;
/**
* Cache must be freed before calling this function
* since it leaves the seqbase in an invalid state.
*/
void seq_free_sequence_recurse(struct Scene *scene, struct Sequence *seq, bool do_id_user);
struct StripProxy *seq_strip_proxy_alloc(void);
-
+/**
+ * Find meta strip, that contains strip `key`.
+ * If lookup hash doesn't exist, it will be created. If hash is tagged as invalid, it will be
+ * rebuilt.
+ *
+ * \param scene: scene that owns lookup hash
+ * \param key: pointer to Sequence inside of meta strip
+ *
+ * \return pointer to meta strip
+ */
+struct Sequence *seq_sequence_lookup_meta_by_seq(const struct Scene *scene,
+ const struct Sequence *key);
+/**
+ * Find effect strips, that use strip `seq` as one of inputs.
+ * If lookup hash doesn't exist, it will be created. If hash is tagged as invalid, it will be
+ * rebuilt.
+ *
+ * \param scene: scene that owns lookup hash
+ * \param key: pointer to Sequence inside of meta strip
+ *
+ * \return collection of effect strips
+ */
+struct SeqCollection *seq_sequence_lookup_effects_by_seq(const struct Scene *scene,
+ const struct Sequence *key);
#ifdef __cplusplus
}
#endif
diff --git a/source/blender/sequencer/intern/sound.c b/source/blender/sequencer/intern/sound.c
index 8076c600560..50c8b76a9a0 100644
--- a/source/blender/sequencer/intern/sound.c
+++ b/source/blender/sequencer/intern/sound.c
@@ -35,7 +35,6 @@ static bool sequencer_refresh_sound_length_recursive(Main *bmain, Scene *scene,
for (seq = seqbase->first; seq; seq = seq->next) {
if (seq->type == SEQ_TYPE_META) {
if (sequencer_refresh_sound_length_recursive(bmain, scene, &seq->seqbase)) {
- SEQ_time_update_sequence(scene, seqbase, seq);
changed = true;
}
}
@@ -55,7 +54,6 @@ static bool sequencer_refresh_sound_length_recursive(Main *bmain, Scene *scene,
seq->endofs *= fac;
seq->start += (old - seq->startofs); /* So that visual/"real" start frame does not change! */
- SEQ_time_update_sequence(scene, seqbase, seq);
changed = true;
}
}
@@ -99,8 +97,12 @@ void SEQ_sound_update_bounds(Scene *scene, Sequence *seq)
/* We have to take into account start frame of the sequence's scene! */
int startofs = seq->startofs + seq->anim_startofs + seq->scene->r.sfra;
- BKE_sound_move_scene_sound(
- scene, seq->scene_sound, seq->startdisp, seq->enddisp, startofs, 0.0);
+ BKE_sound_move_scene_sound(scene,
+ seq->scene_sound,
+ SEQ_time_left_handle_frame_get(seq),
+ SEQ_time_right_handle_frame_get(seq),
+ startofs,
+ 0.0);
}
}
else {
diff --git a/source/blender/sequencer/intern/strip_add.c b/source/blender/sequencer/intern/strip_add.c
index 77b0fc946d9..4f0b2e38f56 100644
--- a/source/blender/sequencer/intern/strip_add.c
+++ b/source/blender/sequencer/intern/strip_add.c
@@ -51,6 +51,8 @@
#include "multiview.h"
#include "proxy.h"
+#include "sequencer.h"
+#include "strip_time.h"
#include "utils.h"
void SEQ_add_load_data_init(SeqLoadData *load_data,
@@ -70,12 +72,12 @@ void SEQ_add_load_data_init(SeqLoadData *load_data,
load_data->channel = channel;
}
-static void seq_add_generic_update(Scene *scene, ListBase *seqbase, Sequence *seq)
+static void seq_add_generic_update(Scene *scene, Sequence *seq)
{
SEQ_sequence_base_unique_name_recursive(scene, &scene->ed->seqbase, seq);
- SEQ_time_update_sequence(scene, seqbase, seq);
- SEQ_sort(seqbase);
SEQ_relations_invalidate_cache_composite(scene, seq);
+ SEQ_sequence_lookup_tag(scene, SEQ_LOOKUP_TAG_INVALID);
+ SEQ_time_update_meta_strip_range(scene, seq_sequence_lookup_meta_by_seq(scene, seq));
}
static void seq_add_set_name(Scene *scene, Sequence *seq, SeqLoadData *load_data)
@@ -128,7 +130,7 @@ Sequence *SEQ_add_scene_strip(Scene *scene, ListBase *seqbase, struct SeqLoadDat
seq->len = load_data->scene->r.efra - load_data->scene->r.sfra + 1;
id_us_ensure_real((ID *)load_data->scene);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
return seq;
}
@@ -140,7 +142,7 @@ Sequence *SEQ_add_movieclip_strip(Scene *scene, ListBase *seqbase, struct SeqLoa
seq->len = BKE_movieclip_get_duration(load_data->clip);
id_us_ensure_real((ID *)load_data->clip);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
return seq;
}
@@ -152,7 +154,7 @@ Sequence *SEQ_add_mask_strip(Scene *scene, ListBase *seqbase, struct SeqLoadData
seq->len = BKE_mask_get_duration(load_data->mask);
id_us_ensure_real((ID *)load_data->mask);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
return seq;
}
@@ -174,11 +176,12 @@ Sequence *SEQ_add_effect_strip(Scene *scene, ListBase *seqbase, struct SeqLoadDa
if (!load_data->effect.seq1) {
seq->len = 1; /* Effect is generator, set non zero length. */
- SEQ_time_right_handle_frame_set(seq, load_data->effect.end_frame);
+ SEQ_time_right_handle_frame_set(scene, seq, load_data->effect.end_frame);
}
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
+ seq_time_effect_range_set(seq);
return seq;
}
@@ -264,7 +267,7 @@ Sequence *SEQ_add_image_strip(Main *bmain, Scene *scene, ListBase *seqbase, SeqL
BLI_strncpy(scene->ed->act_imagedir, seq->strip->dir, sizeof(scene->ed->act_imagedir));
seq_add_set_view_transform(scene, seq, load_data);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
return seq;
}
@@ -335,7 +338,7 @@ Sequence *SEQ_add_sound_strip(Main *bmain, Scene *scene, ListBase *seqbase, SeqL
/* Set Last active directory. */
BLI_strncpy(scene->ed->act_sounddir, strip->dir, FILE_MAXDIR);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
return seq;
}
@@ -362,7 +365,6 @@ Sequence *SEQ_add_meta_strip(Scene *scene, ListBase *seqbase, SeqLoadData *load_
/* Set frames start and length. */
seqm->start = load_data->start_frame;
seqm->len = 1;
- SEQ_time_update_sequence(scene, seqbase, seqm);
return seqm;
}
@@ -484,7 +486,7 @@ Sequence *SEQ_add_movie_strip(Main *bmain, Scene *scene, ListBase *seqbase, SeqL
seq_add_set_view_transform(scene, seq, load_data);
seq_add_set_name(scene, seq, load_data);
- seq_add_generic_update(scene, seqbase, seq);
+ seq_add_generic_update(scene, seq);
MEM_freeN(anim_arr);
return seq;
@@ -509,11 +511,8 @@ void SEQ_add_reload_new_file(Main *bmain, Scene *scene, Sequence *seq, const boo
if (lock_range) {
/* keep so we don't have to move the actual start and end points (only the data) */
- Editing *ed = SEQ_editing_get(scene);
- ListBase *seqbase = SEQ_get_seqbase_by_seq(&ed->seqbase, seq);
- SEQ_time_update_sequence(scene, seqbase, seq);
- prev_startdisp = seq->startdisp;
- prev_enddisp = seq->enddisp;
+ prev_startdisp = SEQ_time_left_handle_frame_get(seq);
+ prev_enddisp = SEQ_time_right_handle_frame_get(seq);
}
switch (seq->type) {
@@ -656,13 +655,11 @@ void SEQ_add_reload_new_file(Main *bmain, Scene *scene, Sequence *seq, const boo
free_proxy_seq(seq);
if (lock_range) {
- SEQ_time_left_handle_frame_set(seq, prev_startdisp);
- SEQ_time_right_handle_frame_set(seq, prev_enddisp);
- SEQ_transform_fix_single_image_seq_offsets(seq);
+ SEQ_time_left_handle_frame_set(scene, seq, prev_startdisp);
+ SEQ_time_right_handle_frame_set(scene, seq, prev_enddisp);
+ SEQ_transform_fix_single_image_seq_offsets(scene, seq);
}
- ListBase *seqbase = SEQ_active_seqbase_get(SEQ_editing_get(scene));
- SEQ_time_update_sequence(scene, seqbase, seq);
SEQ_relations_invalidate_cache_raw(scene, seq);
}
diff --git a/source/blender/sequencer/intern/strip_edit.c b/source/blender/sequencer/intern/strip_edit.c
index 96bfce8f740..bd439e3c9f8 100644
--- a/source/blender/sequencer/intern/strip_edit.c
+++ b/source/blender/sequencer/intern/strip_edit.c
@@ -84,8 +84,8 @@ int SEQ_edit_sequence_swap(Sequence *seq_a, Sequence *seq_b, const char **error_
SWAP(int, seq_a->startofs, seq_b->startofs);
SWAP(int, seq_a->endofs, seq_b->endofs);
SWAP(int, seq_a->machine, seq_b->machine);
- SWAP(int, seq_a->startdisp, seq_b->startdisp);
- SWAP(int, seq_a->enddisp, seq_b->enddisp);
+ seq_time_effect_range_set(seq_a);
+ seq_time_effect_range_set(seq_b);
return 1;
}
@@ -230,7 +230,7 @@ bool SEQ_edit_move_strip_to_meta(Scene *scene,
{
/* Find the appropriate seqbase */
Editing *ed = SEQ_editing_get(scene);
- ListBase *seqbase = SEQ_get_seqbase_by_seq(&ed->seqbase, src_seq);
+ ListBase *seqbase = SEQ_get_seqbase_by_seq(scene, src_seq);
if (dst_seqm->type != SEQ_TYPE_META) {
*error_str = N_("Can not move strip to non-meta strip");
@@ -272,11 +272,11 @@ bool SEQ_edit_move_strip_to_meta(Scene *scene,
return true;
}
-static void seq_split_set_left_hold_offset(Sequence *seq, int timeline_frame)
+static void seq_split_set_left_hold_offset(const Scene *scene, Sequence *seq, int timeline_frame)
{
/* Adjust within range of extended stillframes before strip. */
if (timeline_frame < seq->start) {
- SEQ_time_left_handle_frame_set(seq, timeline_frame);
+ SEQ_time_left_handle_frame_set(scene, seq, timeline_frame);
}
/* Adjust within range of strip contents. */
else if ((timeline_frame >= seq->start) && (timeline_frame <= (seq->start + seq->len))) {
@@ -290,19 +290,19 @@ static void seq_split_set_left_hold_offset(Sequence *seq, int timeline_frame)
seq->start += timeline_frame - seq->start;
seq->anim_startofs += seq->len - 1;
seq->len = 1;
- SEQ_time_left_handle_frame_set(seq, timeline_frame);
- SEQ_time_right_handle_frame_set(seq, right_handle_backup);
+ SEQ_time_left_handle_frame_set(scene, seq, timeline_frame);
+ SEQ_time_right_handle_frame_set(scene, seq, right_handle_backup);
}
}
-static void seq_split_set_right_hold_offset(Sequence *seq, int timeline_frame)
+static void seq_split_set_right_hold_offset(const Scene *scene, Sequence *seq, int timeline_frame)
{
/* Adjust within range of extended stillframes before strip. */
if (timeline_frame < seq->start) {
const int left_handle_backup = SEQ_time_left_handle_frame_get(seq);
seq->start = timeline_frame - 1;
- SEQ_time_left_handle_frame_set(seq, left_handle_backup);
- SEQ_time_right_handle_frame_set(seq, timeline_frame);
+ SEQ_time_left_handle_frame_set(scene, seq, left_handle_backup);
+ SEQ_time_right_handle_frame_set(scene, seq, timeline_frame);
}
/* Adjust within range of strip contents. */
else if ((timeline_frame >= seq->start) && (timeline_frame <= (seq->start + seq->len))) {
@@ -311,11 +311,11 @@ static void seq_split_set_right_hold_offset(Sequence *seq, int timeline_frame)
}
/* Adjust within range of extended stillframes after strip. */
else if ((seq->start + seq->len) < timeline_frame) {
- SEQ_time_right_handle_frame_set(seq, timeline_frame);
+ SEQ_time_right_handle_frame_set(scene, seq, timeline_frame);
}
}
-static void seq_split_set_right_offset(Sequence *seq, int timeline_frame)
+static void seq_split_set_right_offset(const Scene *scene, Sequence *seq, int timeline_frame)
{
/* Adjust within range of extended stillframes before strip. */
if (timeline_frame < seq->start) {
@@ -324,10 +324,10 @@ static void seq_split_set_right_offset(Sequence *seq, int timeline_frame)
seq->startofs += content_offset;
}
- SEQ_time_right_handle_frame_set(seq, timeline_frame);
+ SEQ_time_right_handle_frame_set(scene, seq, timeline_frame);
}
-static void seq_split_set_left_offset(Sequence *seq, int timeline_frame)
+static void seq_split_set_left_offset(const Scene *scene, Sequence *seq, int timeline_frame)
{
/* Adjust within range of extended stillframes after strip. */
if (timeline_frame > seq->start + seq->len) {
@@ -336,17 +336,17 @@ static void seq_split_set_left_offset(Sequence *seq, int timeline_frame)
seq->endofs += content_offset;
}
- SEQ_time_left_handle_frame_set(seq, timeline_frame);
+ SEQ_time_left_handle_frame_set(scene, seq, timeline_frame);
}
static bool seq_edit_split_effect_intersect_check(const Sequence *seq, const int timeline_frame)
{
- return timeline_frame > seq->startdisp && timeline_frame < seq->enddisp;
+ return timeline_frame > SEQ_time_left_handle_frame_get(seq) &&
+ timeline_frame < SEQ_time_right_handle_frame_get(seq);
}
static void seq_edit_split_handle_strip_offsets(Main *bmain,
Scene *scene,
- ListBase *seqbase,
Sequence *left_seq,
Sequence *right_seq,
const int timeline_frame,
@@ -355,27 +355,25 @@ static void seq_edit_split_handle_strip_offsets(Main *bmain,
if (seq_edit_split_effect_intersect_check(right_seq, timeline_frame)) {
switch (method) {
case SEQ_SPLIT_SOFT:
- seq_split_set_left_offset(right_seq, timeline_frame);
+ seq_split_set_left_offset(scene, right_seq, timeline_frame);
break;
case SEQ_SPLIT_HARD:
- seq_split_set_left_hold_offset(right_seq, timeline_frame);
+ seq_split_set_left_hold_offset(scene, right_seq, timeline_frame);
SEQ_add_reload_new_file(bmain, scene, right_seq, false);
break;
}
- SEQ_time_update_sequence(scene, seqbase, right_seq);
}
if (seq_edit_split_effect_intersect_check(left_seq, timeline_frame)) {
switch (method) {
case SEQ_SPLIT_SOFT:
- seq_split_set_right_offset(left_seq, timeline_frame);
+ seq_split_set_right_offset(scene, left_seq, timeline_frame);
break;
case SEQ_SPLIT_HARD:
- seq_split_set_right_hold_offset(left_seq, timeline_frame);
+ seq_split_set_right_hold_offset(scene, left_seq, timeline_frame);
SEQ_add_reload_new_file(bmain, scene, left_seq, false);
break;
}
- SEQ_time_update_sequence(scene, seqbase, left_seq);
}
}
@@ -468,10 +466,6 @@ Sequence *SEQ_edit_strip_split(Main *bmain,
SEQ_collection_free(collection);
- /* Sort list, so that no strip can depend on next strip in list.
- * This is important for SEQ_time_update_sequence functionality. */
- SEQ_sort(&left_strips);
-
/* Duplicate ListBase. */
ListBase right_strips = {NULL, NULL};
SEQ_sequence_base_dupli_recursive(scene, scene, &right_strips, &left_strips, SEQ_DUPE_ALL, 0);
@@ -480,18 +474,23 @@ Sequence *SEQ_edit_strip_split(Main *bmain,
Sequence *right_seq = right_strips.first;
Sequence *return_seq = NULL;
- /* Move strips from detached `ListBase`, otherwise they can't be flagged for removal,
- * SEQ_time_update_sequence can fail to update meta strips and they can't be renamed.
- * This is because these functions check all strips in `Editing` to manage relationships. */
+ /* Move strips from detached `ListBase`, otherwise they can't be flagged for removal. */
BLI_movelisttolist(seqbase, &left_strips);
BLI_movelisttolist(seqbase, &right_strips);
+ /* Rename duplicated strips. This has to be done immediately after adding
+ * strips to seqbase, for lookup cache to work correctly. */
+ Sequence *seq_rename = right_seq;
+ for (; seq_rename; seq_rename = seq_rename->next) {
+ SEQ_ensure_unique_name(seq_rename, scene);
+ }
+
/* Split strips. */
while (left_seq && right_seq) {
- if (left_seq->startdisp >= timeline_frame) {
+ if (SEQ_time_left_handle_frame_get(left_seq) >= timeline_frame) {
SEQ_edit_flag_for_removal(scene, seqbase, left_seq);
}
- if (right_seq->enddisp <= timeline_frame) {
+ else if (SEQ_time_right_handle_frame_get(right_seq) <= timeline_frame) {
SEQ_edit_flag_for_removal(scene, seqbase, right_seq);
}
else if (return_seq == NULL) {
@@ -499,20 +498,12 @@ Sequence *SEQ_edit_strip_split(Main *bmain,
return_seq = right_seq;
}
- seq_edit_split_handle_strip_offsets(
- bmain, scene, seqbase, left_seq, right_seq, timeline_frame, method);
+ seq_edit_split_handle_strip_offsets(bmain, scene, left_seq, right_seq, timeline_frame, method);
left_seq = left_seq->next;
right_seq = right_seq->next;
}
SEQ_edit_remove_flagged_sequences(scene, seqbase);
-
- /* Rename duplicated strips. */
- Sequence *seq_rename = return_seq;
- for (; seq_rename; seq_rename = seq_rename->next) {
- SEQ_ensure_unique_name(seq_rename, scene);
- }
-
SEQ_animation_restore_original(scene, &fcurves_original_backup);
return return_seq;
diff --git a/source/blender/sequencer/intern/strip_relations.c b/source/blender/sequencer/intern/strip_relations.c
index 1899cc99263..4acf2763ce5 100644
--- a/source/blender/sequencer/intern/strip_relations.c
+++ b/source/blender/sequencer/intern/strip_relations.c
@@ -47,7 +47,8 @@ static bool seq_relations_check_depend(Sequence *seq, Sequence *cur)
}
/* sequences are not intersecting in time, assume no dependency exists between them */
- if (cur->enddisp < seq->startdisp || cur->startdisp > seq->enddisp) {
+ if (SEQ_time_right_handle_frame_get(cur) < SEQ_time_left_handle_frame_get(seq) ||
+ SEQ_time_left_handle_frame_get(cur) > SEQ_time_right_handle_frame_get(seq)) {
return false;
}
@@ -290,8 +291,8 @@ static void sequencer_all_free_anim_ibufs(Editing *ed,
}
else {
/* Limit frame range to meta strip. */
- meta_range[0] = max_ii(frame_range[0], seq->startdisp);
- meta_range[1] = min_ii(frame_range[1], seq->enddisp);
+ meta_range[0] = max_ii(frame_range[0], SEQ_time_left_handle_frame_get(seq));
+ meta_range[1] = min_ii(frame_range[1], SEQ_time_right_handle_frame_get(seq));
}
sequencer_all_free_anim_ibufs(ed, &seq->seqbase, timeline_frame, meta_range);
@@ -345,7 +346,7 @@ bool SEQ_relations_check_scene_recursion(Scene *scene, ReportList *reports)
RPT_WARNING,
"Recursion detected in video sequencer. Strip %s at frame %d will not be rendered",
recursive_seq->name + 2,
- recursive_seq->startdisp);
+ SEQ_time_left_handle_frame_get(recursive_seq));
LISTBASE_FOREACH (Sequence *, seq, &ed->seqbase) {
if (seq->type != SEQ_TYPE_SCENE && sequencer_seq_generates_image(seq)) {
diff --git a/source/blender/sequencer/intern/strip_time.c b/source/blender/sequencer/intern/strip_time.c
index e4f7a5e87e8..25d4f08be82 100644
--- a/source/blender/sequencer/intern/strip_time.c
+++ b/source/blender/sequencer/intern/strip_time.c
@@ -27,6 +27,7 @@
#include "SEQ_time.h"
#include "SEQ_transform.h"
+#include "sequencer.h"
#include "strip_time.h"
#include "utils.h"
@@ -37,7 +38,7 @@ float seq_give_frame_index(Sequence *seq, float timeline_frame)
int end = seq->start + seq->len - 1;
if (seq->type & SEQ_TYPE_EFFECT) {
- end = seq->enddisp;
+ end = SEQ_time_right_handle_frame_get(seq);
}
if (end < sta) {
@@ -89,7 +90,7 @@ static int metaseq_end(Sequence *metaseq)
return metaseq->start + metaseq->len - metaseq->endofs;
}
-static void seq_update_sound_bounds_recursive_impl(Scene *scene,
+static void seq_update_sound_bounds_recursive_impl(const Scene *scene,
Sequence *metaseq,
int start,
int end)
@@ -131,33 +132,31 @@ static void seq_update_sound_bounds_recursive_impl(Scene *scene,
}
}
-void seq_update_sound_bounds_recursive(Scene *scene, Sequence *metaseq)
+void seq_update_sound_bounds_recursive(const Scene *scene, Sequence *metaseq)
{
seq_update_sound_bounds_recursive_impl(
scene, metaseq, metaseq_start(metaseq), metaseq_end(metaseq));
}
-static void seq_time_update_sequence_bounds(Scene *scene, Sequence *seq)
+/* Update meta strip content start and end, update sound playback range. */
+void SEQ_time_update_meta_strip_range(const Scene *scene, Sequence *seq_meta)
{
- seq->startdisp = seq->start + seq->startofs;
- seq->enddisp = seq->start + seq->len - seq->endofs;
-
- if (seq->type == SEQ_TYPE_META) {
- seq_update_sound_bounds_recursive(scene, seq);
+ if (seq_meta == NULL) {
+ return;
}
-}
-static void seq_time_update_meta_strip(Scene *scene, Sequence *seq_meta)
-{
if (BLI_listbase_is_empty(&seq_meta->seqbase)) {
return;
}
+ const int strip_start = SEQ_time_left_handle_frame_get(seq_meta);
+ const int strip_end = SEQ_time_right_handle_frame_get(seq_meta);
+
int min = MAXFRAME * 2;
int max = -MAXFRAME * 2;
LISTBASE_FOREACH (Sequence *, seq, &seq_meta->seqbase) {
- min = min_ii(seq->startdisp, min);
- max = max_ii(seq->enddisp, max);
+ min = min_ii(SEQ_time_left_handle_frame_get(seq), min);
+ max = max_ii(SEQ_time_right_handle_frame_get(seq), max);
}
seq_meta->start = min + seq_meta->anim_startofs;
@@ -166,144 +165,54 @@ static void seq_time_update_meta_strip(Scene *scene, Sequence *seq_meta)
seq_meta->len -= seq_meta->anim_endofs;
seq_update_sound_bounds_recursive(scene, seq_meta);
-}
-
-void SEQ_time_update_meta_strip_range(Scene *scene, Sequence *seq_meta)
-{
- if (seq_meta == NULL) {
- return;
- }
-
- seq_time_update_meta_strip(scene, seq_meta);
/* Prevent meta-strip to move in timeline. */
- SEQ_time_left_handle_frame_set(seq_meta, seq_meta->startdisp);
- SEQ_time_right_handle_frame_set(seq_meta, seq_meta->enddisp);
+ SEQ_time_left_handle_frame_set(scene, seq_meta, strip_start);
+ SEQ_time_right_handle_frame_set(scene, seq_meta, strip_end);
}
-void SEQ_time_update_sequence(Scene *scene, ListBase *seqbase, Sequence *seq)
+void seq_time_effect_range_set(Sequence *seq)
{
- Sequence *seqm;
-
- /* Check all meta-strips recursively. */
- seqm = seq->seqbase.first;
- while (seqm) {
- if (seqm->seqbase.first) {
- SEQ_time_update_sequence(scene, &seqm->seqbase, seqm);
- }
- seqm = seqm->next;
+ if (seq->seq1 && seq->seq2) { /* 2 - input effect. */
+ seq->startdisp = max_ii(SEQ_time_left_handle_frame_get(seq->seq1),
+ SEQ_time_left_handle_frame_get(seq->seq2));
+ seq->enddisp = min_ii(SEQ_time_right_handle_frame_get(seq->seq1),
+ SEQ_time_right_handle_frame_get(seq->seq2));
}
-
- /* effects and meta: automatic start and end */
- if (seq->type & SEQ_TYPE_EFFECT) {
- if (seq->seq1) {
- seq->startofs = seq->endofs = 0;
- if (seq->seq3) {
- seq->start = seq->startdisp = max_iii(
- seq->seq1->startdisp, seq->seq2->startdisp, seq->seq3->startdisp);
- seq->enddisp = min_iii(seq->seq1->enddisp, seq->seq2->enddisp, seq->seq3->enddisp);
- }
- else if (seq->seq2) {
- seq->start = seq->startdisp = max_ii(seq->seq1->startdisp, seq->seq2->startdisp);
- seq->enddisp = min_ii(seq->seq1->enddisp, seq->seq2->enddisp);
- }
- else {
- seq->start = seq->startdisp = seq->seq1->startdisp;
- seq->enddisp = seq->seq1->enddisp;
- }
- /* we can't help if strips don't overlap, it won't give useful results.
- * but at least ensure 'len' is never negative which causes bad bugs elsewhere. */
- if (seq->enddisp < seq->startdisp) {
- /* simple start/end swap */
- seq->start = seq->enddisp;
- seq->enddisp = seq->startdisp;
- seq->startdisp = seq->start;
- seq->flag |= SEQ_INVALID_EFFECT;
- }
- else {
- seq->flag &= ~SEQ_INVALID_EFFECT;
- }
-
- seq->len = seq->enddisp - seq->startdisp;
- }
- else {
- seq_time_update_sequence_bounds(scene, seq);
- }
+ else if (seq->seq1) { /* Single input effect. */
+ seq->startdisp = SEQ_time_right_handle_frame_get(seq->seq1);
+ seq->enddisp = SEQ_time_left_handle_frame_get(seq->seq1);
}
- else if (seq->type == SEQ_TYPE_META) {
- seq_time_update_meta_strip(scene, seq);
+ else if (seq->seq2) { /* Strip may be missing one of inputs. */
+ seq->startdisp = SEQ_time_right_handle_frame_get(seq->seq2);
+ seq->enddisp = SEQ_time_left_handle_frame_get(seq->seq2);
}
- else {
- seq_time_update_sequence_bounds(scene, seq);
- }
-
- Editing *ed = SEQ_editing_get(scene);
- /* Strip is inside meta strip */
- if (seqbase != &ed->seqbase) {
- Sequence *meta = SEQ_get_meta_by_seqbase(&ed->seqbase, seqbase);
- SEQ_time_update_meta_strip_range(scene, meta);
+ if (seq->startdisp > seq->enddisp) {
+ SWAP(int, seq->startdisp, seq->enddisp);
}
- seq_time_update_sequence_bounds(scene, seq);
+ /* Values unusable for effects, these should be always 0. */
+ seq->startofs = seq->endofs = seq->anim_startofs = seq->anim_endofs = 0;
}
-static bool update_changed_seq_recurs(Scene *scene, Sequence *seq, Sequence *changed_seq)
+/* Update strip startdisp and enddisp (n-input effects have no len to calculate these). */
+void seq_time_update_effects_strip_range(const Scene *scene, SeqCollection *effects)
{
- Sequence *subseq;
- bool do_update = false;
-
- /* recurse downwards to see if this seq depends on the changed seq */
-
- if (seq == NULL) {
- return false;
- }
-
- if (seq == changed_seq) {
- do_update = true;
- }
-
- for (subseq = seq->seqbase.first; subseq; subseq = subseq->next) {
- if (update_changed_seq_recurs(scene, subseq, changed_seq)) {
- do_update = true;
- }
- }
-
- if (seq->seq1) {
- if (update_changed_seq_recurs(scene, seq->seq1, changed_seq)) {
- do_update = true;
- }
- }
- if (seq->seq2 && (seq->seq2 != seq->seq1)) {
- if (update_changed_seq_recurs(scene, seq->seq2, changed_seq)) {
- do_update = true;
- }
- }
- if (seq->seq3 && (seq->seq3 != seq->seq1) && (seq->seq3 != seq->seq2)) {
- if (update_changed_seq_recurs(scene, seq->seq3, changed_seq)) {
- do_update = true;
- }
- }
-
- if (do_update) {
- ListBase *seqbase = SEQ_active_seqbase_get(SEQ_editing_get(scene));
- SEQ_time_update_sequence(scene, seqbase, seq);
+ if (effects == NULL) {
+ return;
}
- return do_update;
-}
-
-void SEQ_time_update_recursive(Scene *scene, Sequence *changed_seq)
-{
- Editing *ed = SEQ_editing_get(scene);
Sequence *seq;
-
- if (ed == NULL) {
- return;
+ /* First pass: Update length of immediate effects. */
+ SEQ_ITERATOR_FOREACH (seq, effects) {
+ seq_time_effect_range_set(seq);
}
- for (seq = ed->seqbase.first; seq; seq = seq->next) {
- update_changed_seq_recurs(scene, seq, changed_seq);
+ /* Second pass: Recursive call to update effects in chain and in order, so they inherit length
+ * correctly. */
+ SEQ_ITERATOR_FOREACH (seq, effects) {
+ seq_time_update_effects_strip_range(scene, seq_sequence_lookup_effects_by_seq(scene, seq));
}
}
@@ -342,12 +251,14 @@ int SEQ_time_find_next_prev_edit(Scene *scene,
}
if (do_center) {
- seq_frames[0] = (seq->startdisp + seq->enddisp) / 2;
+ seq_frames[0] = (SEQ_time_left_handle_frame_get(seq) +
+ SEQ_time_right_handle_frame_get(seq)) /
+ 2;
seq_frames_tot = 1;
}
else {
- seq_frames[0] = seq->startdisp;
- seq_frames[1] = seq->enddisp;
+ seq_frames[0] = SEQ_time_left_handle_frame_get(seq);
+ seq_frames[1] = SEQ_time_right_handle_frame_get(seq);
seq_frames_tot = 2;
}
@@ -431,11 +342,11 @@ void SEQ_timeline_expand_boundbox(const ListBase *seqbase, rctf *rect)
}
LISTBASE_FOREACH (Sequence *, seq, seqbase) {
- if (rect->xmin > seq->startdisp - 1) {
- rect->xmin = seq->startdisp - 1;
+ if (rect->xmin > SEQ_time_left_handle_frame_get(seq) - 1) {
+ rect->xmin = SEQ_time_left_handle_frame_get(seq) - 1;
}
- if (rect->xmax < seq->enddisp + 1) {
- rect->xmax = seq->enddisp + 1;
+ if (rect->xmax < SEQ_time_right_handle_frame_get(seq) + 1) {
+ rect->xmax = SEQ_time_right_handle_frame_get(seq) + 1;
}
if (rect->ymax < seq->machine) {
rect->ymax = seq->machine;
@@ -507,7 +418,8 @@ void seq_time_gap_info_get(const Scene *scene,
bool SEQ_time_strip_intersects_frame(const Sequence *seq, const int timeline_frame)
{
- return (seq->startdisp <= timeline_frame) && (seq->enddisp > timeline_frame);
+ return (SEQ_time_left_handle_frame_get(seq) <= timeline_frame) &&
+ (SEQ_time_right_handle_frame_get(seq) > timeline_frame);
}
bool SEQ_time_has_left_still_frames(const Sequence *seq)
@@ -525,21 +437,36 @@ bool SEQ_time_has_still_frames(const Sequence *seq)
return SEQ_time_has_right_still_frames(seq) || SEQ_time_has_left_still_frames(seq);
}
-int SEQ_time_left_handle_frame_get(Sequence *seq)
+int SEQ_time_left_handle_frame_get(const Sequence *seq)
{
+ if (seq->seq1 || seq->seq2) {
+ return seq->startdisp;
+ }
+
return seq->start + seq->startofs;
}
-int SEQ_time_right_handle_frame_get(Sequence *seq)
+
+int SEQ_time_right_handle_frame_get(const Sequence *seq)
{
+ if (seq->seq1 || seq->seq2) {
+ return seq->enddisp;
+ }
+
return seq->start + seq->len - seq->endofs;
}
-void SEQ_time_left_handle_frame_set(Sequence *seq, int val)
+void SEQ_time_left_handle_frame_set(const Scene *scene, Sequence *seq, int val)
{
seq->startofs = val - seq->start;
+ seq->startdisp = val; /* Only to make files usable in older versions. */
+ SEQ_time_update_meta_strip_range(scene, seq_sequence_lookup_meta_by_seq(scene, seq));
+ seq_time_update_effects_strip_range(scene, seq_sequence_lookup_effects_by_seq(scene, seq));
}
-void SEQ_time_right_handle_frame_set(Sequence *seq, int val)
+void SEQ_time_right_handle_frame_set(const Scene *scene, Sequence *seq, int val)
{
seq->endofs = seq->start + seq->len - val;
+ seq->enddisp = val; /* Only to make files usable in older versions. */
+ SEQ_time_update_meta_strip_range(scene, seq_sequence_lookup_meta_by_seq(scene, seq));
+ seq_time_update_effects_strip_range(scene, seq_sequence_lookup_effects_by_seq(scene, seq));
}
diff --git a/source/blender/sequencer/intern/strip_time.h b/source/blender/sequencer/intern/strip_time.h
index c96a016e646..7a75aeac1a6 100644
--- a/source/blender/sequencer/intern/strip_time.h
+++ b/source/blender/sequencer/intern/strip_time.h
@@ -14,9 +14,10 @@ extern "C" {
struct ListBase;
struct Scene;
struct Sequence;
+struct SeqCollection;
float seq_give_frame_index(struct Sequence *seq, float timeline_frame);
-void seq_update_sound_bounds_recursive(struct Scene *scene, struct Sequence *metaseq);
+void seq_update_sound_bounds_recursive(const struct Scene *scene, struct Sequence *metaseq);
/* Describes gap between strips in timeline. */
typedef struct GapInfo {
@@ -37,6 +38,8 @@ void seq_time_gap_info_get(const struct Scene *scene,
struct ListBase *seqbase,
int initial_frame,
struct GapInfo *r_gap_info);
+void seq_time_effect_range_set(Sequence *seq);
+void seq_time_update_effects_strip_range(const struct Scene *scene, struct SeqCollection *effects);
#ifdef __cplusplus
}
diff --git a/source/blender/sequencer/intern/strip_transform.c b/source/blender/sequencer/intern/strip_transform.c
index 8ff577240d6..051dc3961ba 100644
--- a/source/blender/sequencer/intern/strip_transform.c
+++ b/source/blender/sequencer/intern/strip_transform.c
@@ -25,6 +25,9 @@
#include "SEQ_time.h"
#include "SEQ_transform.h"
+#include "strip_time.h"
+#include "sequencer.h"
+
#include "CLG_log.h"
static CLG_LogRef LOG = {"seq.strip_transform"};
@@ -86,16 +89,16 @@ bool SEQ_transform_seqbase_isolated_sel_check(ListBase *seqbase)
return true;
}
-void SEQ_transform_handle_xlimits(Sequence *seq, int leftflag, int rightflag)
+void SEQ_transform_handle_xlimits(const Scene *scene, Sequence *seq, int leftflag, int rightflag)
{
if (leftflag) {
if (SEQ_time_left_handle_frame_get(seq) >= SEQ_time_right_handle_frame_get(seq)) {
- SEQ_time_left_handle_frame_set(seq, SEQ_time_right_handle_frame_get(seq) - 1);
+ SEQ_time_left_handle_frame_set(scene, seq, SEQ_time_right_handle_frame_get(seq) - 1);
}
if (SEQ_transform_single_image_check(seq) == 0) {
if (SEQ_time_left_handle_frame_get(seq) >= seq_tx_get_end(seq)) {
- SEQ_time_left_handle_frame_set(seq, seq_tx_get_end(seq) - 1);
+ SEQ_time_left_handle_frame_set(scene, seq, seq_tx_get_end(seq) - 1);
}
/* TODO: This doesn't work at the moment. */
@@ -112,12 +115,12 @@ void SEQ_transform_handle_xlimits(Sequence *seq, int leftflag, int rightflag)
if (rightflag) {
if (SEQ_time_right_handle_frame_get(seq) <= SEQ_time_left_handle_frame_get(seq)) {
- SEQ_time_right_handle_frame_set(seq, SEQ_time_left_handle_frame_get(seq) + 1);
+ SEQ_time_right_handle_frame_set(scene, seq, SEQ_time_left_handle_frame_get(seq) + 1);
}
if (SEQ_transform_single_image_check(seq) == 0) {
if (SEQ_time_right_handle_frame_get(seq) <= seq_tx_get_start(seq)) {
- SEQ_time_right_handle_frame_set(seq, seq_tx_get_start(seq) + 1);
+ SEQ_time_right_handle_frame_set(scene, seq, seq_tx_get_start(seq) + 1);
}
}
}
@@ -129,7 +132,7 @@ void SEQ_transform_handle_xlimits(Sequence *seq, int leftflag, int rightflag)
}
}
-void SEQ_transform_fix_single_image_seq_offsets(Sequence *seq)
+void SEQ_transform_fix_single_image_seq_offsets(const Scene *scene, Sequence *seq)
{
int left, start, offset;
if (!SEQ_transform_single_image_check(seq)) {
@@ -142,8 +145,8 @@ void SEQ_transform_fix_single_image_seq_offsets(Sequence *seq)
start = seq->start;
if (start != left) {
offset = left - start;
- SEQ_time_left_handle_frame_set(seq, SEQ_time_left_handle_frame_get(seq) - offset);
- SEQ_time_right_handle_frame_set(seq, SEQ_time_right_handle_frame_get(seq) - offset);
+ SEQ_time_left_handle_frame_set(scene, seq, SEQ_time_left_handle_frame_get(seq) - offset);
+ SEQ_time_right_handle_frame_set(scene, seq, SEQ_time_right_handle_frame_get(seq) - offset);
seq->start += offset;
}
}
@@ -156,7 +159,8 @@ bool SEQ_transform_sequence_can_be_translated(Sequence *seq)
bool SEQ_transform_test_overlap_seq_seq(Sequence *seq1, Sequence *seq2)
{
return (seq1 != seq2 && seq1->machine == seq2->machine &&
- ((seq1->enddisp <= seq2->startdisp) || (seq1->startdisp >= seq2->enddisp)) == 0);
+ ((SEQ_time_right_handle_frame_get(seq1) <= SEQ_time_left_handle_frame_get(seq2)) ||
+ (SEQ_time_left_handle_frame_get(seq1) >= SEQ_time_right_handle_frame_get(seq2))) == 0);
}
bool SEQ_transform_test_overlap(ListBase *seqbasep, Sequence *test)
@@ -180,9 +184,6 @@ void SEQ_transform_translate_sequence(Scene *evil_scene, Sequence *seq, int delt
return;
}
- SEQ_offset_animdata(evil_scene, seq, delta);
- seq->start += delta;
-
/* Meta strips requires special handling: their content is to be translated, and then frame range
* of the meta is to be updated for the updated content. */
if (seq->type == SEQ_TYPE_META) {
@@ -190,16 +191,21 @@ void SEQ_transform_translate_sequence(Scene *evil_scene, Sequence *seq, int delt
for (seq_child = seq->seqbase.first; seq_child; seq_child = seq_child->next) {
SEQ_transform_translate_sequence(evil_scene, seq_child, delta);
}
- /* Ensure that meta bounds are updated, but this function prevents resets seq->start and
- * start/end point in timeline. */
- SEQ_time_update_meta_strip_range(evil_scene, seq);
/* Move meta start/end points. */
- SEQ_time_left_handle_frame_set(seq, seq->startdisp + delta);
- SEQ_time_right_handle_frame_set(seq, seq->enddisp + delta);
+ SEQ_time_left_handle_frame_set(evil_scene, seq, SEQ_time_left_handle_frame_get(seq) + delta);
+ SEQ_time_right_handle_frame_set(evil_scene, seq, SEQ_time_right_handle_frame_get(seq) + delta);
+ }
+ else { /* All other strip types. */
+ seq->start += delta;
+ /* Only to make files usable in older versions. */
+ seq->startdisp = SEQ_time_left_handle_frame_get(seq);
+ seq->enddisp = SEQ_time_right_handle_frame_get(seq);
}
- ListBase *seqbase = SEQ_active_seqbase_get(SEQ_editing_get(evil_scene));
- SEQ_time_update_sequence(evil_scene, seqbase, seq);
+ SEQ_offset_animdata(evil_scene, seq, delta);
+ SEQ_time_update_meta_strip_range(evil_scene, seq_sequence_lookup_meta_by_seq(evil_scene, seq));
+ seq_time_update_effects_strip_range(evil_scene,
+ seq_sequence_lookup_effects_by_seq(evil_scene, seq));
}
bool SEQ_transform_seqbase_shuffle_ex(ListBase *seqbasep,
@@ -211,16 +217,12 @@ bool SEQ_transform_seqbase_shuffle_ex(ListBase *seqbasep,
BLI_assert(ELEM(channel_delta, -1, 1));
test->machine += channel_delta;
- SEQ_time_update_sequence(evil_scene, seqbasep, test);
while (SEQ_transform_test_overlap(seqbasep, test)) {
if ((channel_delta > 0) ? (test->machine >= MAXSEQ) : (test->machine < 1)) {
break;
}
test->machine += channel_delta;
-
- /* XXX: I don't think this is needed since were only moving vertically, Campbell. */
- SEQ_time_update_sequence(evil_scene, seqbasep, test);
}
if (!SEQ_valid_strip_channel(test)) {
@@ -228,19 +230,18 @@ bool SEQ_transform_seqbase_shuffle_ex(ListBase *seqbasep,
* nicer to move it to the end */
Sequence *seq;
- int new_frame = test->enddisp;
+ int new_frame = SEQ_time_right_handle_frame_get(test);
for (seq = seqbasep->first; seq; seq = seq->next) {
if (seq->machine == orig_machine) {
- new_frame = max_ii(new_frame, seq->enddisp);
+ new_frame = max_ii(new_frame, SEQ_time_right_handle_frame_get(seq));
}
}
test->machine = orig_machine;
- new_frame = new_frame + (test->start - test->startdisp); /* adjust by the startdisp */
+ new_frame = new_frame +
+ (test->start - SEQ_time_left_handle_frame_get(test)); /* adjust by the startdisp */
SEQ_transform_translate_sequence(evil_scene, test, new_frame - test->start);
-
- SEQ_time_update_sequence(evil_scene, seqbasep, test);
return false;
}
@@ -252,61 +253,57 @@ bool SEQ_transform_seqbase_shuffle(ListBase *seqbasep, Sequence *test, Scene *ev
return SEQ_transform_seqbase_shuffle_ex(seqbasep, test, evil_scene, 1);
}
-static int shuffle_seq_time_offset_test(SeqCollection *strips_to_shuffle,
- ListBase *seqbasep,
- char dir)
+static bool shuffle_seq_test_overlap(const Sequence *seq1, const Sequence *seq2, const int offset)
{
- int offset = 0;
- Sequence *seq;
-
- SEQ_ITERATOR_FOREACH (seq, strips_to_shuffle) {
- LISTBASE_FOREACH (Sequence *, seq_other, seqbasep) {
- if (!SEQ_transform_test_overlap_seq_seq(seq, seq_other)) {
- continue;
- }
- if (SEQ_relation_is_effect_of_strip(seq_other, seq)) {
- continue;
- }
- if (UNLIKELY(SEQ_collection_has_strip(seq_other, strips_to_shuffle))) {
- CLOG_WARN(&LOG,
- "Strip overlaps with itself or another strip, that is to be shuffled. "
- "This should never happen.");
- continue;
- }
- if (dir == 'L') {
- offset = min_ii(offset, seq_other->startdisp - seq->enddisp);
- }
- else {
- offset = max_ii(offset, seq_other->enddisp - seq->startdisp);
- }
- }
- }
- return offset;
+ return (
+ seq1 != seq2 && seq1->machine == seq2->machine &&
+ ((SEQ_time_right_handle_frame_get(seq1) + offset <= SEQ_time_left_handle_frame_get(seq2)) ||
+ (SEQ_time_left_handle_frame_get(seq1) + offset >= SEQ_time_right_handle_frame_get(seq2))) ==
+ 0);
}
-static int shuffle_seq_time_offset(SeqCollection *strips_to_shuffle,
- ListBase *seqbasep,
- Scene *scene,
- char dir)
+static int shuffle_seq_time_offset_get(SeqCollection *strips_to_shuffle,
+ ListBase *seqbasep,
+ char dir)
{
- int ofs = 0;
- int tot_ofs = 0;
+ int offset = 0;
Sequence *seq;
- while ((ofs = shuffle_seq_time_offset_test(strips_to_shuffle, seqbasep, dir))) {
+ bool all_conflicts_resolved = false;
+
+ while (!all_conflicts_resolved) {
+ all_conflicts_resolved = true;
SEQ_ITERATOR_FOREACH (seq, strips_to_shuffle) {
- /* seq_test_overlap only tests display values */
- seq->startdisp += ofs;
- seq->enddisp += ofs;
- }
+ LISTBASE_FOREACH (Sequence *, seq_other, seqbasep) {
+ if (!shuffle_seq_test_overlap(seq, seq_other, offset)) {
+ continue;
+ }
+ if (SEQ_relation_is_effect_of_strip(seq_other, seq)) {
+ continue;
+ }
+ if (UNLIKELY(SEQ_collection_has_strip(seq_other, strips_to_shuffle))) {
+ CLOG_WARN(&LOG,
+ "Strip overlaps with itself or another strip, that is to be shuffled. "
+ "This should never happen.");
+ continue;
+ }
- tot_ofs += ofs;
- }
+ all_conflicts_resolved = false;
- SEQ_ITERATOR_FOREACH (seq, strips_to_shuffle) {
- SEQ_time_update_sequence(scene, seqbasep, seq); /* corrects dummy startdisp/enddisp values */
+ if (dir == 'L') {
+ offset = min_ii(offset,
+ SEQ_time_left_handle_frame_get(seq_other) -
+ SEQ_time_right_handle_frame_get(seq));
+ }
+ else {
+ offset = max_ii(offset,
+ SEQ_time_right_handle_frame_get(seq_other) -
+ SEQ_time_left_handle_frame_get(seq));
+ }
+ }
+ }
}
- return tot_ofs;
+ return offset;
}
bool SEQ_transform_seqbase_shuffle_time(SeqCollection *strips_to_shuffle,
@@ -315,8 +312,8 @@ bool SEQ_transform_seqbase_shuffle_time(SeqCollection *strips_to_shuffle,
ListBase *markers,
const bool use_sync_markers)
{
- int offset_l = shuffle_seq_time_offset(strips_to_shuffle, seqbasep, evil_scene, 'L');
- int offset_r = shuffle_seq_time_offset(strips_to_shuffle, seqbasep, evil_scene, 'R');
+ int offset_l = shuffle_seq_time_offset_get(strips_to_shuffle, seqbasep, 'L');
+ int offset_r = shuffle_seq_time_offset_get(strips_to_shuffle, seqbasep, 'R');
int offset = (-offset_l < offset_r) ? offset_l : offset_r;
if (offset) {
@@ -346,9 +343,8 @@ void SEQ_transform_offset_after_frame(Scene *scene,
const int timeline_frame)
{
LISTBASE_FOREACH (Sequence *, seq, seqbase) {
- if (seq->startdisp >= timeline_frame) {
+ if (SEQ_time_left_handle_frame_get(seq) >= timeline_frame) {
SEQ_transform_translate_sequence(scene, seq, delta);
- SEQ_time_update_sequence(scene, seqbase, seq);
SEQ_relations_invalidate_cache_preprocessed(scene, seq);
}
}
diff --git a/source/blender/sequencer/intern/utils.c b/source/blender/sequencer/intern/utils.c
index 0cf47420d8f..260f82310fb 100644
--- a/source/blender/sequencer/intern/utils.c
+++ b/source/blender/sequencer/intern/utils.c
@@ -39,55 +39,9 @@
#include "multiview.h"
#include "proxy.h"
+#include "sequencer.h"
#include "utils.h"
-void SEQ_sort(ListBase *seqbase)
-{
- if (seqbase == NULL) {
- return;
- }
-
- /* all strips together per kind, and in order of y location ("machine") */
- ListBase inputbase, effbase;
- Sequence *seq, *seqt;
-
- BLI_listbase_clear(&inputbase);
- BLI_listbase_clear(&effbase);
-
- while ((seq = BLI_pophead(seqbase))) {
-
- if (seq->type & SEQ_TYPE_EFFECT) {
- seqt = effbase.first;
- while (seqt) {
- if (seqt->machine >= seq->machine) {
- BLI_insertlinkbefore(&effbase, seqt, seq);
- break;
- }
- seqt = seqt->next;
- }
- if (seqt == NULL) {
- BLI_addtail(&effbase, seq);
- }
- }
- else {
- seqt = inputbase.first;
- while (seqt) {
- if (seqt->machine >= seq->machine) {
- BLI_insertlinkbefore(&inputbase, seqt, seq);
- break;
- }
- seqt = seqt->next;
- }
- if (seqt == NULL) {
- BLI_addtail(&inputbase, seq);
- }
- }
- }
-
- BLI_movelisttolist(seqbase, &inputbase);
- BLI_movelisttolist(seqbase, &effbase);
-}
-
typedef struct SeqUniqueInfo {
Sequence *seq;
char name_src[SEQ_NAME_MAXSTR];
@@ -414,20 +368,18 @@ const Sequence *SEQ_get_topmost_sequence(const Scene *scene, int frame)
return best_seq;
}
-ListBase *SEQ_get_seqbase_by_seq(ListBase *seqbase, Sequence *seq)
+ListBase *SEQ_get_seqbase_by_seq(const Scene *scene, Sequence *seq)
{
- Sequence *iseq;
- ListBase *lb = NULL;
+ Editing *ed = SEQ_editing_get(scene);
+ ListBase *main_seqbase = &ed->seqbase;
+ Sequence *seq_meta = seq_sequence_lookup_meta_by_seq(scene, seq);
- for (iseq = seqbase->first; iseq; iseq = iseq->next) {
- if (seq == iseq) {
- return seqbase;
- }
- if (iseq->seqbase.first && (lb = SEQ_get_seqbase_by_seq(&iseq->seqbase, seq))) {
- return lb;
- }
+ if (seq_meta != NULL) {
+ return &seq_meta->seqbase;
+ }
+ if (BLI_findindex(main_seqbase, seq) >= 0) {
+ return main_seqbase;
}
-
return NULL;
}