VSE: Improved Retiming system

Patch implements better way to control playback speed than it is
possible to do with speed effect. Speed factor property can be set in
Time panel.

There are 2 layers of control:

Option to retime movie to match scene FPS rate.
Custom speed factor to control playback rate.
Since playback rate is strip property, it is now possible to manipulate
strip as normal one even if it is retimed.

To facilitate manipulation, some functions need to consider speed factor
and apply necessary corrections to strip offset or strip start. These
corrections may need to be float numbers, so start and offsets must be
float as well.

Sound strips now use speed factor instead of pitch. This means, that
strips will change length to match usable length. In addition, it is
possible to group movie and sound strip and change speed of meta strip.
This commit is contained in:
Richard Antalik 2022-06-29 12:45:59 +02:00
parent c51b8ec863
commit 302b04a5a3
Notes: blender-bot 2023-05-25 09:26:27 +02:00
Referenced by commit 957cb173f2, Fix T101447: Hold split not working correctly
Referenced by commit 66de653784, Fix incorrect strip position if pitch was animated
Referenced by issue #103662, VSE: Adding packed sound via python API produces strip with incorrect length
Referenced by issue #102663, Regression: Meta strips from older versions are broken
Referenced by issue #100688, Python API: sequencer_strip.frame_start inconsistancy
Referenced by issue #108157, Regression: VSE: Copy-Paste of strips from one scene to another offsets the data
48 changed files with 1063 additions and 780 deletions

View File

@ -1870,6 +1870,12 @@ class SEQUENCER_PT_time(SequencerButtonsPanel, Panel):
split.label(text="Channel")
split.prop(strip, "channel", text="")
if not is_effect:
split = layout.split(factor=0.5 + max_factor)
split.alignment = 'RIGHT'
split.label(text="Speed Factor")
split.prop(strip, "speed_factor", text="")
sub = layout.column(align=True)
split = sub.split(factor=0.5 + max_factor, align=True)
split.alignment = 'RIGHT'
@ -1982,11 +1988,6 @@ class SEQUENCER_PT_adjust_sound(SequencerButtonsPanel, Panel):
split.label(text="Volume")
split.prop(strip, "volume", text="")
split = col.split(factor=0.4)
split.alignment = 'RIGHT'
split.label(text="Pitch")
split.prop(strip, "pitch", text="")
audio_channels = context.scene.render.ffmpeg.audio_channels
pan_enabled = sound.use_mono and audio_channels != 'MONO'
pan_text = "%.2f°" % (strip.pan * 90)

View File

@ -25,7 +25,7 @@ extern "C" {
/* Blender file format version. */
#define BLENDER_FILE_VERSION BLENDER_VERSION
#define BLENDER_FILE_SUBVERSION 3
#define BLENDER_FILE_SUBVERSION 5
/* Minimum Blender version that supports reading file written with the current
* version. Older Blender versions will test this and show a warning if the file

View File

@ -720,8 +720,8 @@ void *BKE_sound_scene_add_scene_sound_defaults(Scene *scene, Sequence *sequence)
{
return BKE_sound_scene_add_scene_sound(scene,
sequence,
SEQ_time_left_handle_frame_get(sequence),
SEQ_time_right_handle_frame_get(sequence),
SEQ_time_left_handle_frame_get(scene, sequence),
SEQ_time_right_handle_frame_get(scene, sequence),
sequence->startofs + sequence->anim_startofs);
}
@ -746,8 +746,8 @@ void *BKE_sound_add_scene_sound_defaults(Scene *scene, Sequence *sequence)
{
return BKE_sound_add_scene_sound(scene,
sequence,
SEQ_time_left_handle_frame_get(sequence),
SEQ_time_right_handle_frame_get(sequence),
SEQ_time_left_handle_frame_get(scene, sequence),
SEQ_time_right_handle_frame_get(scene, sequence),
sequence->startofs + sequence->anim_startofs);
}
@ -779,8 +779,8 @@ void BKE_sound_move_scene_sound_defaults(Scene *scene, Sequence *sequence)
if (sequence->scene_sound) {
BKE_sound_move_scene_sound(scene,
sequence->scene_sound,
SEQ_time_left_handle_frame_get(sequence),
SEQ_time_right_handle_frame_get(sequence),
SEQ_time_left_handle_frame_get(scene, sequence),
SEQ_time_right_handle_frame_get(scene, sequence),
sequence->startofs + sequence->anim_startofs,
0.0);
}

View File

@ -160,7 +160,7 @@ static void seq_convert_transform_crop(const Scene *scene,
const uint32_t use_transform_flag = (1 << 16);
const uint32_t use_crop_flag = (1 << 17);
const StripElem *s_elem = SEQ_render_give_stripelem(seq, seq->start);
const StripElem *s_elem = SEQ_render_give_stripelem(scene, seq, seq->start);
if (s_elem != NULL) {
image_size_x = s_elem->orig_width;
image_size_y = s_elem->orig_height;
@ -285,7 +285,7 @@ static void seq_convert_transform_crop_2(const Scene *scene,
Sequence *seq,
const eSpaceSeq_Proxy_RenderSize render_size)
{
const StripElem *s_elem = SEQ_render_give_stripelem(seq, seq->start);
const StripElem *s_elem = SEQ_render_give_stripelem(scene, seq, seq->start);
if (s_elem == NULL) {
return;
}
@ -350,6 +350,7 @@ static void seq_convert_transform_crop_lb_2(const Scene *scene,
static void seq_update_meta_disp_range(Scene *scene)
{
Editing *ed = SEQ_editing_get(scene);
if (ed == NULL) {
return;
}
@ -357,8 +358,8 @@ static void seq_update_meta_disp_range(Scene *scene)
LISTBASE_FOREACH_BACKWARD (MetaStack *, ms, &ed->metastack) {
/* Update ms->disp_range from meta. */
if (ms->disp_range[0] == ms->disp_range[1]) {
ms->disp_range[0] = SEQ_time_left_handle_frame_get(ms->parseq);
ms->disp_range[1] = SEQ_time_right_handle_frame_get(ms->parseq);
ms->disp_range[0] = SEQ_time_left_handle_frame_get(scene, ms->parseq);
ms->disp_range[1] = SEQ_time_right_handle_frame_get(scene, ms->parseq);
}
/* Update meta strip endpoints. */
@ -366,6 +367,14 @@ static void seq_update_meta_disp_range(Scene *scene)
SEQ_time_right_handle_frame_set(scene, ms->parseq, ms->disp_range[1]);
SEQ_transform_fix_single_image_seq_offsets(scene, ms->parseq);
/* Recalculate effects using meta strip. */
LISTBASE_FOREACH (Sequence *, seq, ms->oldbasep) {
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);
}
}
/* Ensure that active seqbase points to active meta strip seqbase. */
MetaStack *active_ms = SEQ_meta_stack_active_get(ed);
SEQ_seqbase_active_set(ed, &active_ms->parseq->seqbase);

View File

@ -408,7 +408,7 @@ static void do_versions_sequencer_speed_effect_recursive(Scene *scene, const Lis
v->speed_control_type = SEQ_SPEED_MULTIPLY;
v->speed_fader = globalSpeed *
((float)seq->seq1->len /
max_ff((float)(SEQ_time_right_handle_frame_get(seq->seq1) -
max_ff((float)(SEQ_time_right_handle_frame_get(scene, seq->seq1) -
seq->seq1->start),
1.0f));
}
@ -1235,6 +1235,17 @@ static bool version_merge_still_offsets(Sequence *seq, void *UNUSED(user_data))
return true;
}
static bool seq_speed_factor_set(Sequence *seq, void *UNUSED(user_data))
{
if (seq->type == SEQ_TYPE_SOUND_RAM) {
seq->speed_factor = seq->pitch;
}
else {
seq->speed_factor = 1.0f;
}
return true;
}
/* Those `version_liboverride_rnacollections_*` functions mimic the old, pre-3.0 code to find
* anchor and source items in the given list of modifiers, constraints etc., using only the
* `subitem_local` data of the override property operation.
@ -3171,18 +3182,7 @@ void blo_do_versions_300(FileData *fd, Library *UNUSED(lib), Main *bmain)
}
}
/**
* Versioning code until next subversion bump goes here.
*
* \note Be sure to check when bumping the version:
* - "versioning_userdef.c", #blo_do_versions_userdef
* - "versioning_userdef.c", #do_versions_theme
*
* \note Keep this message at the bottom of the function.
*/
{
/* Keep this block, even when empty. */
if (!MAIN_VERSION_ATLEAST(bmain, 303, 5)) {
/* Fix for T98925 - remove channels region, that was initialized in incorrect editor types. */
for (bScreen *screen = bmain->screens.first; screen; screen = screen->id.next) {
LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
@ -3201,5 +3201,25 @@ void blo_do_versions_300(FileData *fd, Library *UNUSED(lib), Main *bmain)
}
}
}
LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
Editing *ed = SEQ_editing_get(scene);
if (ed == NULL) {
continue;
}
SEQ_for_each_callback(&ed->seqbase, seq_speed_factor_set, NULL);
}
}
/**
* Versioning code until next subversion bump goes here.
*
* \note Be sure to check when bumping the version:
* - "versioning_userdef.c", #blo_do_versions_userdef
* - "versioning_userdef.c", #do_versions_theme
*
* \note Keep this message at the bottom of the function.
*/
{
/* Keep this block, even when empty. */
}
}

View File

@ -111,9 +111,9 @@ static int seq_frame_apply_snap(bContext *C, Scene *scene, const int timeline_fr
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, strips) {
seq_frame_snap_update_best(
SEQ_time_left_handle_frame_get(seq), timeline_frame, &best_frame, &best_distance);
SEQ_time_left_handle_frame_get(scene, seq), timeline_frame, &best_frame, &best_distance);
seq_frame_snap_update_best(
SEQ_time_right_handle_frame_get(seq), timeline_frame, &best_frame, &best_distance);
SEQ_time_right_handle_frame_get(scene, seq), timeline_frame, &best_frame, &best_distance);
}
SEQ_collection_free(strips);

View File

@ -85,6 +85,7 @@ typedef struct SequencerAddData {
#define SEQPROP_NOCHAN (1 << 3)
#define SEQPROP_FIT_METHOD (1 << 4)
#define SEQPROP_VIEW_TRANSFORM (1 << 5)
#define SEQPROP_PLAYBACK_RATE (1 << 6)
static const EnumPropertyItem scale_fit_methods[] = {
{SEQ_SCALE_TO_FIT, "FIT", 0, "Scale to Fit", "Scale image to fit within the canvas"},
@ -158,6 +159,14 @@ static void sequencer_generic_props__internal(wmOperatorType *ot, int flag)
"Set View Transform",
"Set appropriate view transform based on media color space");
}
if (flag & SEQPROP_PLAYBACK_RATE) {
ot->prop = RNA_def_boolean(ot->srna,
"adjust_playback_rate",
true,
"Adjust Playback Rate",
"Play at normal speed regardless of scene FPS");
}
}
static void sequencer_generic_invoke_path__internal(bContext *C,
@ -191,7 +200,7 @@ static int sequencer_generic_invoke_xy_guess_channel(bContext *C, int type)
}
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
const int strip_end = SEQ_time_right_handle_frame_get(seq);
const int strip_end = SEQ_time_right_handle_frame_get(scene, seq);
if ((ELEM(type, -1, seq->type)) && (strip_end < timeline_frame) &&
(timeline_frame - strip_end < proximity)) {
tgt = seq;
@ -250,6 +259,10 @@ static void load_data_init_from_operator(SeqLoadData *load_data, bContext *C, wm
SEQ_tool_settings_fit_method_set(CTX_data_scene(C), load_data->fit_method);
}
if ((prop = RNA_struct_find_property(op->ptr, "adjust_playback_rate"))) {
load_data->adjust_playback_rate = RNA_boolean_get(op->ptr, "adjust_playback_rate");
}
if ((prop = RNA_struct_find_property(op->ptr, "filepath"))) {
RNA_property_string_get(op->ptr, prop, load_data->path);
BLI_strncpy(load_data->name, BLI_path_basename(load_data->path), sizeof(load_data->name));
@ -327,7 +340,7 @@ static void seq_load_apply_generic_options(bContext *C, wmOperator *op, Sequence
}
if (RNA_boolean_get(op->ptr, "overlap") == true ||
!SEQ_transform_test_overlap(ed->seqbasep, seq)) {
!SEQ_transform_test_overlap(scene, ed->seqbasep, seq)) {
/* No overlap should be handled or the strip is not overlapping, exit early. */
return;
}
@ -370,7 +383,7 @@ static bool seq_load_apply_generic_options_only_test_overlap(bContext *C,
SEQ_collection_append_strip(seq, strip_col);
return SEQ_transform_test_overlap(ed->seqbasep, seq);
return SEQ_transform_test_overlap(scene, ed->seqbasep, seq);
}
static bool seq_effect_add_properties_poll(const bContext *UNUSED(C),
@ -793,8 +806,10 @@ static void sequencer_add_movie_clamp_sound_strip_length(Scene *scene,
return;
}
SEQ_time_right_handle_frame_set(scene, seq_sound, SEQ_time_right_handle_frame_get(seq_movie));
SEQ_time_left_handle_frame_set(scene, seq_sound, SEQ_time_left_handle_frame_get(seq_movie));
SEQ_time_right_handle_frame_set(
scene, seq_sound, SEQ_time_right_handle_frame_get(scene, seq_movie));
SEQ_time_left_handle_frame_set(
scene, seq_sound, SEQ_time_left_handle_frame_get(scene, seq_movie));
}
static void sequencer_add_movie_multiple_strips(bContext *C,
@ -841,8 +856,8 @@ static void sequencer_add_movie_multiple_strips(bContext *C,
}
}
load_data->start_frame += SEQ_time_right_handle_frame_get(seq_movie) -
SEQ_time_left_handle_frame_get(seq_movie);
load_data->start_frame += SEQ_time_right_handle_frame_get(scene, seq_movie) -
SEQ_time_left_handle_frame_get(scene, seq_movie);
if (overlap_shuffle_override) {
has_seq_overlap |= seq_load_apply_generic_options_only_test_overlap(
C, op, seq_sound, strip_col);
@ -976,6 +991,7 @@ static int sequencer_add_movie_strip_invoke(bContext *C,
sequencer_disable_one_time_properties(C, op);
RNA_enum_set(op->ptr, "fit_method", SEQ_tool_settings_fit_method_get(scene));
RNA_boolean_set(op->ptr, "adjust_playback_rate", true);
/* This is for drag and drop. */
if ((RNA_struct_property_is_set(op->ptr, "files") &&
@ -1042,8 +1058,9 @@ void SEQUENCER_OT_movie_strip_add(struct wmOperatorType *ot)
WM_FILESEL_SHOW_PROPS | WM_FILESEL_DIRECTORY,
FILE_DEFAULTDISPLAY,
FILE_SORT_DEFAULT);
sequencer_generic_props__internal(
ot, SEQPROP_STARTFRAME | SEQPROP_FIT_METHOD | SEQPROP_VIEW_TRANSFORM);
sequencer_generic_props__internal(ot,
SEQPROP_STARTFRAME | SEQPROP_FIT_METHOD |
SEQPROP_VIEW_TRANSFORM | SEQPROP_PLAYBACK_RATE);
RNA_def_boolean(ot->srna, "sound", true, "Sound", "Load sound with the movie");
RNA_def_boolean(ot->srna,
"use_framerate",
@ -1073,8 +1090,8 @@ static void sequencer_add_sound_multiple_strips(bContext *C,
}
else {
seq_load_apply_generic_options(C, op, seq);
load_data->start_frame += SEQ_time_right_handle_frame_get(seq) -
SEQ_time_left_handle_frame_get(seq);
load_data->start_frame += SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, seq);
}
}
RNA_END;
@ -1250,8 +1267,12 @@ static int sequencer_add_image_strip_calculate_length(wmOperator *op,
return RNA_property_collection_length(op->ptr, RNA_struct_find_property(op->ptr, "files"));
}
static void sequencer_add_image_strip_load_files(
wmOperator *op, Sequence *seq, SeqLoadData *load_data, const int minframe, const int numdigits)
static void sequencer_add_image_strip_load_files(wmOperator *op,
Scene *scene,
Sequence *seq,
SeqLoadData *load_data,
const int minframe,
const int numdigits)
{
const bool use_placeholders = RNA_boolean_get(op->ptr, "use_placeholders");
/* size of Strip->dir. */
@ -1267,7 +1288,7 @@ static void sequencer_add_image_strip_load_files(
size_t strip_frame = 0;
RNA_BEGIN (op->ptr, itemptr, "files") {
char *filename = RNA_string_get_alloc(&itemptr, "name", NULL, 0, NULL);
SEQ_add_image_load_file(seq, strip_frame, filename);
SEQ_add_image_load_file(scene, seq, strip_frame, filename);
MEM_freeN(filename);
strip_frame++;
}
@ -1296,7 +1317,7 @@ static int sequencer_add_image_strip_exec(bContext *C, wmOperator *op)
}
Sequence *seq = SEQ_add_image_strip(CTX_data_main(C), scene, ed->seqbasep, &load_data);
sequencer_add_image_strip_load_files(op, seq, &load_data, minframe, numdigits);
sequencer_add_image_strip_load_files(op, scene, seq, &load_data, minframe, numdigits);
SEQ_add_image_init_alpha_mode(seq);
/* Adjust length. */

View File

@ -97,7 +97,7 @@ static void displayed_channel_range_get(const SeqChannelDrawContext *context,
rctf strip_boundbox;
BLI_rctf_init(&strip_boundbox, 0.0f, 0.0f, 1.0f, r_channel_range[1]);
SEQ_timeline_expand_boundbox(context->seqbase, &strip_boundbox);
SEQ_timeline_expand_boundbox(context->scene, context->seqbase, &strip_boundbox);
CLAMP(r_channel_range[0], strip_boundbox.ymin, strip_boundbox.ymax);
CLAMP(r_channel_range[1], strip_boundbox.ymin, MAXSEQ);
}

View File

@ -167,7 +167,7 @@ static void sequencer_drop_copy(bContext *C, wmDrag *drag, wmDropBox *drop)
SpaceSeq *sseq = CTX_wm_space_seq(C);
SeqCollection *strips = SEQ_query_rendered_strips(
channels, seqbase, scene->r.cfra, sseq->chanshown);
scene, channels, seqbase, scene->r.cfra, sseq->chanshown);
/* Get the top most strip channel that is in view.*/
Sequence *seq;
@ -236,7 +236,7 @@ static void update_overlay_strip_poistion_data(bContext *C, const int mval[2])
Editing *ed = SEQ_editing_get(scene);
for (int i = 0; i < coords->channel_len && !coords->is_intersecting; i++) {
coords->is_intersecting = SEQ_transform_test_overlap(ed->seqbasep, &dummy_seq);
coords->is_intersecting = SEQ_transform_test_overlap(scene, ed->seqbasep, &dummy_seq);
dummy_seq.machine++;
}
}

View File

@ -617,8 +617,8 @@ static void drawmeta_contents(Scene *scene,
/* Draw only immediate children (1 level depth). */
for (seq = meta_seqbase->first; seq; seq = seq->next) {
const int startdisp = SEQ_time_left_handle_frame_get(seq) + offset;
const int enddisp = SEQ_time_right_handle_frame_get(seq) + offset;
const int startdisp = SEQ_time_left_handle_frame_get(scene, seq) + offset;
const int enddisp = SEQ_time_right_handle_frame_get(scene, seq) + offset;
if ((startdisp > x2 || enddisp < x1) == 0) {
float y_chan = (seq->machine - chan_min) / (float)(chan_range)*draw_range;
@ -663,19 +663,20 @@ static void drawmeta_contents(Scene *scene,
GPU_blend(GPU_BLEND_NONE);
}
float sequence_handle_size_get_clamped(Sequence *seq, const float pixelx)
float sequence_handle_size_get_clamped(const Scene *scene, Sequence *seq, const float pixelx)
{
const float maxhandle = (pixelx * SEQ_HANDLE_SIZE) * U.pixelsize;
/* Ensure that handle is not wider, than quarter of strip. */
return min_ff(
maxhandle,
((float)(SEQ_time_right_handle_frame_get(seq) - SEQ_time_left_handle_frame_get(seq)) /
4.0f));
return min_ff(maxhandle,
((float)(SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, seq)) /
4.0f));
}
/* Draw a handle, on left or right side of strip. */
static void draw_seq_handle(View2D *v2d,
static void draw_seq_handle(const Scene *scene,
View2D *v2d,
Sequence *seq,
const float handsize_clamped,
const short direction,
@ -689,8 +690,8 @@ static void draw_seq_handle(View2D *v2d,
uint whichsel = 0;
uchar col[4];
x1 = SEQ_time_left_handle_frame_get(seq);
x2 = SEQ_time_right_handle_frame_get(seq);
x1 = SEQ_time_left_handle_frame_get(scene, seq);
x2 = SEQ_time_right_handle_frame_get(scene, seq);
y1 = seq->machine + SEQ_STRIP_OFSBOTTOM;
y2 = seq->machine + SEQ_STRIP_OFSTOP;
@ -745,8 +746,8 @@ static void draw_seq_handle(View2D *v2d,
numstr_len = BLI_snprintf_rlen(numstr,
sizeof(numstr),
"%d%d",
SEQ_time_left_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(seq));
SEQ_time_left_handle_frame_get(scene, seq),
SEQ_time_right_handle_frame_get(scene, seq));
float tot_width = BLF_width(fontid, numstr, numstr_len);
if ((x2 - x1) / pixelx > 20 + tot_width) {
@ -755,13 +756,13 @@ static void draw_seq_handle(View2D *v2d,
if (direction == SEQ_LEFTHANDLE) {
numstr_len = BLI_snprintf_rlen(
numstr, sizeof(numstr), "%d", SEQ_time_left_handle_frame_get(seq));
numstr, sizeof(numstr), "%d", SEQ_time_left_handle_frame_get(scene, seq));
x1 += text_margin;
y1 += 0.09f;
}
else {
numstr_len = BLI_snprintf_rlen(
numstr, sizeof(numstr), "%d", SEQ_time_right_handle_frame_get(seq) - 1);
numstr, sizeof(numstr), "%d", SEQ_time_right_handle_frame_get(scene, seq) - 1);
x1 = x2 - (text_margin + pixelx * BLF_width(fontid, numstr, numstr_len));
y1 += 0.09f;
}
@ -896,7 +897,8 @@ static void draw_seq_text_get_source(Sequence *seq, char *r_source, size_t sourc
}
}
static size_t draw_seq_text_get_overlay_string(SpaceSeq *sseq,
static size_t draw_seq_text_get_overlay_string(const Scene *scene,
SpaceSeq *sseq,
Sequence *seq,
char *r_overlay_string,
size_t overlay_string_len)
@ -922,8 +924,8 @@ static size_t draw_seq_text_get_overlay_string(SpaceSeq *sseq,
char strip_duration_text[16];
if (sseq->timeline_overlay.flag & SEQ_TIMELINE_SHOW_STRIP_DURATION) {
const int strip_duration = SEQ_time_right_handle_frame_get(seq) -
SEQ_time_left_handle_frame_get(seq);
const int strip_duration = SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, seq);
SNPRINTF(strip_duration_text, "%d", strip_duration);
if (i != 0) {
text_array[i++] = text_sep;
@ -952,7 +954,7 @@ static void draw_seq_text_overlay(Scene *scene,
ListBase *channels = SEQ_channels_displayed_get(ed);
char overlay_string[FILE_MAX];
size_t overlay_string_len = draw_seq_text_get_overlay_string(
sseq, seq, overlay_string, sizeof(overlay_string));
scene, sseq, seq, overlay_string, sizeof(overlay_string));
if (overlay_string_len == 0) {
return;
@ -990,8 +992,8 @@ static void draw_sequence_extensions_overlay(
float x1, x2, y1, y2;
uchar col[4], blend_col[3];
x1 = SEQ_time_left_handle_frame_get(seq);
x2 = SEQ_time_right_handle_frame_get(seq);
x1 = SEQ_time_left_handle_frame_get(scene, seq);
x2 = SEQ_time_right_handle_frame_get(scene, seq);
y1 = seq->machine + SEQ_STRIP_OFSBOTTOM;
y2 = seq->machine + SEQ_STRIP_OFSTOP;
@ -1005,28 +1007,32 @@ static void draw_sequence_extensions_overlay(
col[3] = SEQ_render_is_muted(channels, seq) ? MUTE_ALPHA : 200;
UI_GetColorPtrShade3ubv(col, blend_col, 10);
if (seq->startofs) {
const float strip_content_start = SEQ_time_start_frame_get(seq);
const float strip_content_end = SEQ_time_start_frame_get(seq) +
SEQ_time_strip_length_get(scene, seq);
float right_handle_frame = SEQ_time_right_handle_frame_get(scene, seq);
float left_handle_frame = SEQ_time_left_handle_frame_get(scene, seq);
if (left_handle_frame > strip_content_start) {
immUniformColor4ubv(col);
immRectf(pos, (float)(seq->start), y1 - pixely, x1, y1 - SEQ_STRIP_OFSBOTTOM);
immRectf(pos, strip_content_start, y1 - pixely, x1, y1 - SEQ_STRIP_OFSBOTTOM);
/* Outline. */
immUniformColor3ubv(blend_col);
imm_draw_box_wire_2d(pos, x1, y1 - pixely, (float)(seq->start), y1 - SEQ_STRIP_OFSBOTTOM);
imm_draw_box_wire_2d(pos, x1, y1 - pixely, strip_content_start, y1 - SEQ_STRIP_OFSBOTTOM);
}
if (seq->endofs) {
if (right_handle_frame < strip_content_end) {
immUniformColor4ubv(col);
immRectf(pos, x2, y2 + pixely, (float)(seq->start + seq->len), y2 + SEQ_STRIP_OFSBOTTOM);
immRectf(pos, x2, y2 + pixely, strip_content_end, y2 + SEQ_STRIP_OFSBOTTOM);
/* Outline. */
immUniformColor3ubv(blend_col);
imm_draw_box_wire_2d(
pos, x2, y2 + pixely, (float)(seq->start + seq->len), y2 + SEQ_STRIP_OFSBOTTOM);
/* Outline. */ immUniformColor3ubv(blend_col);
imm_draw_box_wire_2d(pos, x2, y2 + pixely, strip_content_end, y2 + SEQ_STRIP_OFSBOTTOM);
}
GPU_blend(GPU_BLEND_NONE);
}
static void draw_color_strip_band(
ListBase *channels, Sequence *seq, uint pos, float text_margin_y, float y1)
const Scene *scene, ListBase *channels, Sequence *seq, uint pos, float text_margin_y, float y1)
{
uchar col[4];
SolidColorVars *colvars = (SolidColorVars *)seq->effectdata;
@ -1049,9 +1055,9 @@ static void draw_color_strip_band(
immUniformColor4ubv(col);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
y1,
SEQ_time_right_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(scene, seq),
text_margin_y);
/* 1px line to better separate the color band. */
@ -1059,8 +1065,8 @@ static void draw_color_strip_band(
immUniformColor4ubv(col);
immBegin(GPU_PRIM_LINES, 2);
immVertex2f(pos, SEQ_time_left_handle_frame_get(seq), text_margin_y);
immVertex2f(pos, SEQ_time_right_handle_frame_get(seq), text_margin_y);
immVertex2f(pos, SEQ_time_left_handle_frame_get(scene, seq), text_margin_y);
immVertex2f(pos, SEQ_time_right_handle_frame_get(scene, seq), text_margin_y);
immEnd();
GPU_blend(GPU_BLEND_NONE);
@ -1112,25 +1118,31 @@ static void draw_seq_background(Scene *scene,
/* Draw the main strip body. */
if (is_single_image) {
immRectf(
pos, SEQ_time_left_handle_frame_get(seq), y1, SEQ_time_right_handle_frame_get(seq), y2);
immRectf(pos,
SEQ_time_left_handle_frame_get(scene, seq),
y1,
SEQ_time_right_handle_frame_get(scene, seq),
y2);
}
else {
immRectf(pos, x1, y1, x2, y2);
}
/* Draw background for hold still regions. */
if (!is_single_image && SEQ_time_has_still_frames(seq)) {
if (!is_single_image) {
UI_GetColorPtrShade3ubv(col, col, -35);
immUniformColor4ubv(col);
if (SEQ_time_has_left_still_frames(seq)) {
const float content_start = min_ff(SEQ_time_right_handle_frame_get(seq), seq->start);
immRectf(pos, SEQ_time_left_handle_frame_get(seq), y1, content_start, y2);
if (SEQ_time_has_left_still_frames(scene, seq)) {
float left_handle_frame = SEQ_time_left_handle_frame_get(scene, seq);
const float content_start = SEQ_time_start_frame_get(seq);
immRectf(pos, left_handle_frame, y1, content_start, y2);
}
if (SEQ_time_has_right_still_frames(seq)) {
const float content_end = max_ff(SEQ_time_left_handle_frame_get(seq), seq->start + seq->len);
immRectf(pos, content_end, y1, SEQ_time_right_handle_frame_get(seq), y2);
if (SEQ_time_has_right_still_frames(scene, seq)) {
float right_handle_frame = SEQ_time_right_handle_frame_get(scene, seq);
const float content_end = SEQ_time_start_frame_get(seq) +
SEQ_time_strip_length_get(scene, seq);
immRectf(pos, content_end, y1, right_handle_frame, y2);
}
}
@ -1200,9 +1212,9 @@ static void draw_seq_invalid(float x1, float x2, float y2, float text_margin_y)
}
static void calculate_seq_text_offsets(
View2D *v2d, Sequence *seq, float *x1, float *x2, float pixelx)
const Scene *scene, View2D *v2d, Sequence *seq, float *x1, float *x2, float pixelx)
{
const float handsize_clamped = sequence_handle_size_get_clamped(seq, pixelx);
const float handsize_clamped = sequence_handle_size_get_clamped(scene, seq, pixelx);
float text_margin = 2.0f * handsize_clamped;
*x1 += text_margin;
@ -1336,7 +1348,7 @@ static void draw_seq_strip(const bContext *C,
View2D *v2d = &region->v2d;
float x1, x2, y1, y2;
const float handsize_clamped = sequence_handle_size_get_clamped(seq, pixelx);
const float handsize_clamped = sequence_handle_size_get_clamped(scene, seq, pixelx);
float pixely = BLI_rctf_size_y(&v2d->cur) / BLI_rcti_size_y(&v2d->mask);
/* Check if we are doing "solo preview". */
@ -1347,15 +1359,17 @@ static void draw_seq_strip(const bContext *C,
SEQ_TIMELINE_SHOW_STRIP_COLOR_TAG);
/* Draw strip body. */
x1 = SEQ_time_has_left_still_frames(seq) ? seq->start : SEQ_time_left_handle_frame_get(seq);
x1 = SEQ_time_has_left_still_frames(scene, seq) ? SEQ_time_start_frame_get(seq) :
SEQ_time_left_handle_frame_get(scene, seq);
y1 = seq->machine + SEQ_STRIP_OFSBOTTOM;
x2 = SEQ_time_has_right_still_frames(seq) ? (seq->start + seq->len) :
SEQ_time_right_handle_frame_get(seq);
x2 = SEQ_time_has_right_still_frames(scene, seq) ?
SEQ_time_start_frame_get(seq) + SEQ_time_strip_length_get(scene, seq) :
SEQ_time_right_handle_frame_get(scene, seq);
y2 = seq->machine + SEQ_STRIP_OFSTOP;
/* Limit body to strip bounds. Meta strip can end up with content outside of strip range. */
x1 = min_ff(x1, SEQ_time_right_handle_frame_get(seq));
x2 = max_ff(x2, SEQ_time_left_handle_frame_get(seq));
x1 = min_ff(x1, SEQ_time_right_handle_frame_get(scene, seq));
x2 = max_ff(x2, SEQ_time_left_handle_frame_get(scene, seq));
float text_margin_y;
bool y_threshold;
@ -1381,12 +1395,12 @@ static void draw_seq_strip(const bContext *C,
/* Draw a color band inside color strip. */
if (seq->type == SEQ_TYPE_COLOR && y_threshold) {
draw_color_strip_band(channels, seq, pos, text_margin_y, y1);
draw_color_strip_band(scene, channels, seq, pos, text_margin_y, y1);
}
/* Draw strip offsets when flag is enabled or during "solo preview". */
if (sseq->flag & SEQ_SHOW_OVERLAY) {
if (!is_single_image && (seq->startofs || seq->endofs) && pixely > 0) {
if (!is_single_image && pixely > 0) {
if ((sseq->timeline_overlay.flag & SEQ_TIMELINE_SHOW_STRIP_OFFSETS) ||
(seq == special_seq_update)) {
draw_sequence_extensions_overlay(scene, seq, pos, pixely, show_strip_color_tag);
@ -1395,8 +1409,8 @@ static void draw_seq_strip(const bContext *C,
}
immUnbindProgram();
x1 = SEQ_time_left_handle_frame_get(seq);
x2 = SEQ_time_right_handle_frame_get(seq);
x1 = SEQ_time_left_handle_frame_get(scene, seq);
x2 = SEQ_time_right_handle_frame_get(scene, seq);
if ((seq->type == SEQ_TYPE_META) ||
((seq->type == SEQ_TYPE_SCENE) && (seq->flag & SEQ_SCENE_STRIPS))) {
@ -1444,16 +1458,16 @@ static void draw_seq_strip(const bContext *C,
if (!SEQ_transform_is_locked(channels, seq)) {
draw_seq_handle(
v2d, seq, handsize_clamped, SEQ_LEFTHANDLE, pos, seq_active, pixelx, y_threshold);
scene, v2d, seq, handsize_clamped, SEQ_LEFTHANDLE, pos, seq_active, pixelx, y_threshold);
draw_seq_handle(
v2d, seq, handsize_clamped, SEQ_RIGHTHANDLE, pos, seq_active, pixelx, y_threshold);
scene, v2d, seq, handsize_clamped, SEQ_RIGHTHANDLE, pos, seq_active, pixelx, y_threshold);
}
draw_seq_outline(scene, seq, pos, x1, x2, y1, y2, pixelx, pixely, seq_active);
immUnbindProgram();
calculate_seq_text_offsets(v2d, seq, &x1, &x2, pixelx);
calculate_seq_text_offsets(scene, v2d, seq, &x1, &x2, pixelx);
/* If a waveform is drawn, avoid drawing text when there is not enough vertical space. */
if (seq->type == SEQ_TYPE_SOUND_RAM) {
@ -1474,7 +1488,7 @@ static void draw_seq_strip(const bContext *C,
}
}
static void draw_effect_inputs_highlight(Sequence *seq)
static void draw_effect_inputs_highlight(const Scene *scene, Sequence *seq)
{
Sequence *seq1 = seq->seq1;
Sequence *seq2 = seq->seq2;
@ -1486,23 +1500,23 @@ static void draw_effect_inputs_highlight(Sequence *seq)
immUniformColor4ub(255, 255, 255, 48);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq1),
SEQ_time_left_handle_frame_get(scene, seq1),
seq1->machine + SEQ_STRIP_OFSBOTTOM,
SEQ_time_right_handle_frame_get(seq1),
SEQ_time_right_handle_frame_get(scene, seq1),
seq1->machine + SEQ_STRIP_OFSTOP);
if (seq2 && seq2 != seq1) {
immRectf(pos,
SEQ_time_left_handle_frame_get(seq2),
SEQ_time_left_handle_frame_get(scene, seq2),
seq2->machine + SEQ_STRIP_OFSBOTTOM,
SEQ_time_right_handle_frame_get(seq2),
SEQ_time_right_handle_frame_get(scene, seq2),
seq2->machine + SEQ_STRIP_OFSTOP);
}
if (seq3 && !ELEM(seq3, seq1, seq2)) {
immRectf(pos,
SEQ_time_left_handle_frame_get(seq3),
SEQ_time_left_handle_frame_get(scene, seq3),
seq3->machine + SEQ_STRIP_OFSBOTTOM,
SEQ_time_right_handle_frame_get(seq3),
SEQ_time_right_handle_frame_get(scene, seq3),
seq3->machine + SEQ_STRIP_OFSTOP);
}
immUnbindProgram();
@ -1591,7 +1605,8 @@ ImBuf *sequencer_ibuf_get(struct Main *bmain,
}
if (viewport) {
/* Follows same logic as wm_draw_window_offscreen to make sure to restore the same viewport. */
/* Follows same logic as wm_draw_window_offscreen to make sure to restore the same
* viewport. */
int view = (sseq->multiview_eye == STEREO_RIGHT_ID) ? 1 : 0;
GPU_viewport_bind(viewport, view, &region->winrct);
}
@ -2096,10 +2111,10 @@ static int sequencer_draw_get_transform_preview_frame(Scene *scene)
int preview_frame;
if (last_seq->flag & SEQ_RIGHTSEL) {
preview_frame = SEQ_time_right_handle_frame_get(last_seq) - 1;
preview_frame = SEQ_time_right_handle_frame_get(scene, last_seq) - 1;
}
else {
preview_frame = SEQ_time_left_handle_frame_get(last_seq);
preview_frame = SEQ_time_left_handle_frame_get(scene, last_seq);
}
return preview_frame;
@ -2253,7 +2268,7 @@ void sequencer_draw_preview(const bContext *C,
Editing *ed = SEQ_editing_get(scene);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *collection = SEQ_query_rendered_strips(
channels, ed->seqbasep, timeline_frame, 0);
scene, channels, ed->seqbasep, timeline_frame, 0);
Sequence *seq;
Sequence *active_seq = SEQ_select_active_get(scene);
SEQ_ITERATOR_FOREACH (seq, collection) {
@ -2325,10 +2340,13 @@ static void draw_seq_strips(const bContext *C, Editing *ed, ARegion *region)
if (seq == last_seq && (last_seq->flag & SELECT)) {
continue;
}
if (min_ii(SEQ_time_left_handle_frame_get(seq), seq->start) > v2d->cur.xmax) {
if (min_ii(SEQ_time_left_handle_frame_get(scene, seq), SEQ_time_start_frame_get(seq)) >
v2d->cur.xmax) {
continue;
}
if (max_ii(SEQ_time_right_handle_frame_get(seq), seq->start + seq->len) < v2d->cur.xmin) {
if (max_ii(SEQ_time_right_handle_frame_get(scene, seq),
SEQ_time_start_frame_get(seq) + SEQ_time_strip_length_get(scene, seq)) <
v2d->cur.xmin) {
continue;
}
if (seq->machine + 1.0f < v2d->cur.ymin) {
@ -2353,7 +2371,7 @@ static void draw_seq_strips(const bContext *C, Editing *ed, ARegion *region)
/* When active strip is an effect, highlight its inputs. */
if (SEQ_effect_get_num_inputs(last_seq->type) > 0) {
draw_effect_inputs_highlight(last_seq);
draw_effect_inputs_highlight(scene, last_seq);
}
/* When active is a Multi-cam strip, highlight its source channel. */
else if (last_seq->type == SEQ_TYPE_MULTICAM) {
@ -2383,9 +2401,9 @@ static void draw_seq_strips(const bContext *C, Editing *ed, ARegion *region)
immUniformColor4ub(255, 255, 255, 48);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
seq->machine + SEQ_STRIP_OFSBOTTOM,
SEQ_time_right_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(scene, seq),
seq->machine + SEQ_STRIP_OFSTOP);
immUnbindProgram();
@ -2612,8 +2630,8 @@ static void draw_cache_view(const bContext *C)
continue;
}
if (SEQ_time_left_handle_frame_get(seq) > v2d->cur.xmax ||
SEQ_time_right_handle_frame_get(seq) < v2d->cur.xmin) {
if (SEQ_time_left_handle_frame_get(scene, seq) > v2d->cur.xmax ||
SEQ_time_right_handle_frame_get(scene, seq) < v2d->cur.xmin) {
continue;
}
@ -2624,9 +2642,9 @@ static void draw_cache_view(const bContext *C)
const float bg_color[4] = {1.0f, 0.1f, 0.02f, 0.1f};
immUniformColor4f(bg_color[0], bg_color[1], bg_color[2], bg_color[3]);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
stripe_bot,
SEQ_time_right_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(scene, seq),
stripe_top);
}
@ -2637,9 +2655,9 @@ static void draw_cache_view(const bContext *C)
const float bg_color[4] = {0.1f, 0.1f, 0.75f, 0.1f};
immUniformColor4f(bg_color[0], bg_color[1], bg_color[2], bg_color[3]);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
stripe_bot,
SEQ_time_right_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(scene, seq),
stripe_top);
}
@ -2650,9 +2668,9 @@ static void draw_cache_view(const bContext *C)
const float bg_color[4] = {1.0f, 0.6f, 0.0f, 0.1f};
immUniformColor4f(bg_color[0], bg_color[1], bg_color[2], bg_color[3]);
immRectf(pos,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
stripe_bot,
SEQ_time_right_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(scene, seq),
stripe_top);
}
}

View File

@ -81,6 +81,7 @@ typedef struct TransSeq {
int anim_startofs, anim_endofs;
/* int final_left, final_right; */ /* UNUSED */
int len;
float content_start;
} TransSeq;
/** \} */
@ -369,8 +370,6 @@ static int sequencer_snap_exec(bContext *C, wmOperator *op)
else { /* SEQ_RIGHTSEL */
SEQ_time_right_handle_frame_set(scene, seq, snap_frame);
}
SEQ_transform_handle_xlimits(
scene, seq, seq->flag & SEQ_LEFTSEL, seq->flag & SEQ_RIGHTSEL);
SEQ_transform_fix_single_image_seq_offsets(scene, seq);
}
}
@ -380,7 +379,7 @@ static int sequencer_snap_exec(bContext *C, wmOperator *op)
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
if (seq->flag & SELECT && !SEQ_transform_is_locked(channels, seq)) {
seq->flag &= ~SEQ_OVERLAP;
if (SEQ_transform_test_overlap(ed->seqbasep, seq)) {
if (SEQ_transform_test_overlap(scene, ed->seqbasep, seq)) {
SEQ_transform_seqbase_shuffle(ed->seqbasep, seq, scene);
}
}
@ -393,17 +392,20 @@ static int sequencer_snap_exec(bContext *C, wmOperator *op)
if (seq->seq1 && (seq->seq1->flag & SELECT)) {
if (!either_handle_selected) {
SEQ_offset_animdata(scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(seq)));
SEQ_offset_animdata(
scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(scene, seq)));
}
}
else if (seq->seq2 && (seq->seq2->flag & SELECT)) {
if (!either_handle_selected) {
SEQ_offset_animdata(scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(seq)));
SEQ_offset_animdata(
scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(scene, seq)));
}
}
else if (seq->seq3 && (seq->seq3->flag & SELECT)) {
if (!either_handle_selected) {
SEQ_offset_animdata(scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(seq)));
SEQ_offset_animdata(
scene, seq, (snap_frame - SEQ_time_left_handle_frame_get(scene, seq)));
}
}
}
@ -473,6 +475,7 @@ typedef struct SlipData {
static void transseq_backup(TransSeq *ts, Sequence *seq)
{
ts->content_start = SEQ_time_start_frame_get(seq);
ts->start = seq->start;
ts->machine = seq->machine;
ts->startofs = seq->startofs;
@ -603,7 +606,7 @@ static void sequencer_slip_recursively(Scene *scene, SlipData *data, int offset)
}
/* Make sure, that each strip contains at least 1 frame of content. */
static void sequencer_slip_apply_limits(SlipData *data, int *offset)
static void sequencer_slip_apply_limits(const Scene *scene, SlipData *data, int *offset)
{
for (int i = 0; i < data->num_seq; i++) {
if (data->trim[i]) {
@ -612,12 +615,12 @@ static void sequencer_slip_apply_limits(SlipData *data, int *offset)
int seq_content_end = seq_content_start + seq->len + seq->anim_startofs + seq->anim_endofs;
int diff = 0;
if (seq_content_start >= SEQ_time_right_handle_frame_get(seq)) {
diff = SEQ_time_right_handle_frame_get(seq) - seq_content_start - 1;
if (seq_content_start >= SEQ_time_right_handle_frame_get(scene, seq)) {
diff = SEQ_time_right_handle_frame_get(scene, seq) - seq_content_start - 1;
}
if (seq_content_end <= SEQ_time_left_handle_frame_get(seq)) {
diff = SEQ_time_left_handle_frame_get(seq) - seq_content_end + 1;
if (seq_content_end <= SEQ_time_left_handle_frame_get(scene, seq)) {
diff = SEQ_time_left_handle_frame_get(scene, seq) - seq_content_end + 1;
}
*offset += diff;
}
@ -649,7 +652,7 @@ static int sequencer_slip_exec(bContext *C, wmOperator *op)
transseq_backup(data->ts + i, data->seq_array[i]);
}
sequencer_slip_apply_limits(data, &offset);
sequencer_slip_apply_limits(scene, data, &offset);
sequencer_slip_recursively(scene, data, offset);
MEM_freeN(data->seq_array);
@ -695,7 +698,7 @@ static int sequencer_slip_modal(bContext *C, wmOperator *op, const wmEvent *even
applyNumInput(&data->num_input, &offset_fl);
int offset = round_fl_to_int(offset_fl);
sequencer_slip_apply_limits(data, &offset);
sequencer_slip_apply_limits(scene, data, &offset);
sequencer_slip_update_header(scene, area, data, offset);
RNA_int_set(op->ptr, "offset", offset);
@ -727,7 +730,7 @@ static int sequencer_slip_modal(bContext *C, wmOperator *op, const wmEvent *even
UI_view2d_region_to_view(v2d, mouse_x, 0, &mouseloc[0], &mouseloc[1]);
offset = mouseloc[0] - data->init_mouseloc[0];
sequencer_slip_apply_limits(data, &offset);
sequencer_slip_apply_limits(scene, data, &offset);
sequencer_slip_update_header(scene, area, data, offset);
RNA_int_set(op->ptr, "offset", offset);
@ -804,7 +807,7 @@ static int sequencer_slip_modal(bContext *C, wmOperator *op, const wmEvent *even
applyNumInput(&data->num_input, &offset_fl);
int offset = round_fl_to_int(offset_fl);
sequencer_slip_apply_limits(data, &offset);
sequencer_slip_apply_limits(scene, data, &offset);
sequencer_slip_update_header(scene, area, data, offset);
RNA_int_set(op->ptr, "offset", offset);
@ -1052,7 +1055,7 @@ static int sequencer_reload_exec(bContext *C, wmOperator *op)
SEQ_add_reload_new_file(bmain, scene, seq, !adjust_length);
if (adjust_length) {
if (SEQ_transform_test_overlap(ed->seqbasep, seq)) {
if (SEQ_transform_test_overlap(scene, ed->seqbasep, seq)) {
SEQ_transform_seqbase_shuffle(ed->seqbasep, seq, scene);
}
}
@ -1415,14 +1418,14 @@ static int sequencer_split_exec(bContext *C, wmOperator *op)
if (ignore_selection) {
if (use_cursor_position) {
LISTBASE_FOREACH (Sequence *, seq, SEQ_active_seqbase_get(ed)) {
if (SEQ_time_right_handle_frame_get(seq) == split_frame &&
if (SEQ_time_right_handle_frame_get(scene, seq) == split_frame &&
seq->machine == split_channel) {
seq_selected = seq->flag & SEQ_ALLSEL;
}
}
if (!seq_selected) {
LISTBASE_FOREACH (Sequence *, seq, SEQ_active_seqbase_get(ed)) {
if (SEQ_time_left_handle_frame_get(seq) == split_frame &&
if (SEQ_time_left_handle_frame_get(scene, seq) == split_frame &&
seq->machine == split_channel) {
seq->flag &= ~SEQ_ALLSEL;
}
@ -1434,12 +1437,12 @@ static int sequencer_split_exec(bContext *C, wmOperator *op)
if (split_side != SEQ_SIDE_BOTH) {
LISTBASE_FOREACH (Sequence *, seq, SEQ_active_seqbase_get(ed)) {
if (split_side == SEQ_SIDE_LEFT) {
if (SEQ_time_left_handle_frame_get(seq) >= split_frame) {
if (SEQ_time_left_handle_frame_get(scene, seq) >= split_frame) {
seq->flag &= ~SEQ_ALLSEL;
}
}
else {
if (SEQ_time_right_handle_frame_get(seq) <= split_frame) {
if (SEQ_time_right_handle_frame_get(scene, seq) <= split_frame) {
seq->flag &= ~SEQ_ALLSEL;
}
}
@ -1766,7 +1769,7 @@ static int sequencer_offset_clear_exec(bContext *C, wmOperator *UNUSED(op))
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
if ((seq->type & SEQ_TYPE_EFFECT) == 0 && (seq->flag & SELECT)) {
if (SEQ_transform_test_overlap(ed->seqbasep, seq)) {
if (SEQ_transform_test_overlap(scene, ed->seqbasep, seq)) {
SEQ_transform_seqbase_shuffle(ed->seqbasep, seq, scene);
}
}
@ -1825,12 +1828,12 @@ static int sequencer_separate_images_exec(bContext *C, wmOperator *op)
/* TODO: remove f-curve and assign to split image strips.
* The old animation system would remove the user of `seq->ipo`. */
start_ofs = timeline_frame = SEQ_time_left_handle_frame_get(seq);
frame_end = SEQ_time_right_handle_frame_get(seq);
start_ofs = timeline_frame = SEQ_time_left_handle_frame_get(scene, seq);
frame_end = SEQ_time_right_handle_frame_get(scene, seq);
while (timeline_frame < frame_end) {
/* New seq. */
se = SEQ_render_give_stripelem(seq, timeline_frame);
se = SEQ_render_give_stripelem(scene, seq, timeline_frame);
seq_new = SEQ_sequence_dupli_recursive(scene, scene, seqbase, seq, SEQ_DUPE_UNIQUE_NAME);
@ -1852,7 +1855,7 @@ static int sequencer_separate_images_exec(bContext *C, wmOperator *op)
if (step > 1) {
seq_new->flag &= ~SEQ_OVERLAP;
if (SEQ_transform_test_overlap(seqbase, seq_new)) {
if (SEQ_transform_test_overlap(scene, seqbase, seq_new)) {
SEQ_transform_seqbase_shuffle(seqbase, seq_new, scene);
}
}
@ -1978,8 +1981,8 @@ static int sequencer_meta_make_exec(bContext *C, wmOperator *op)
BLI_addtail(&seqm->seqbase, seq);
SEQ_relations_invalidate_cache_preprocessed(scene, seq);
channel_max = max_ii(seq->machine, channel_max);
meta_start_frame = min_ii(SEQ_time_left_handle_frame_get(seq), meta_start_frame);
meta_end_frame = max_ii(SEQ_time_right_handle_frame_get(seq), meta_end_frame);
meta_start_frame = min_ii(SEQ_time_left_handle_frame_get(scene, seq), meta_start_frame);
meta_end_frame = max_ii(SEQ_time_right_handle_frame_get(scene, seq), meta_end_frame);
}
}
@ -1989,7 +1992,7 @@ static int sequencer_meta_make_exec(bContext *C, wmOperator *op)
seqm->start = meta_start_frame;
seqm->len = meta_end_frame - meta_start_frame;
SEQ_select_active_set(scene, seqm);
if (SEQ_transform_test_overlap(active_seqbase, seqm)) {
if (SEQ_transform_test_overlap(scene, active_seqbase, seqm)) {
SEQ_transform_seqbase_shuffle(active_seqbase, seqm, scene);
}
@ -2049,7 +2052,7 @@ static int sequencer_meta_separate_exec(bContext *C, wmOperator *UNUSED(op))
LISTBASE_FOREACH (Sequence *, seq, active_seqbase) {
if (seq->flag & SELECT) {
seq->flag &= ~SEQ_OVERLAP;
if (SEQ_transform_test_overlap(active_seqbase, seq)) {
if (SEQ_transform_test_overlap(scene, active_seqbase, seq)) {
SEQ_transform_seqbase_shuffle(active_seqbase, seq, scene);
}
}
@ -2160,17 +2163,18 @@ static const EnumPropertyItem prop_side_lr_types[] = {
static void swap_sequence(Scene *scene, Sequence *seqa, Sequence *seqb)
{
int gap = SEQ_time_left_handle_frame_get(seqb) - SEQ_time_right_handle_frame_get(seqa);
int gap = SEQ_time_left_handle_frame_get(scene, seqb) -
SEQ_time_right_handle_frame_get(scene, seqa);
int seq_a_start;
int seq_b_start;
seq_b_start = (seqb->start - SEQ_time_left_handle_frame_get(seqb)) +
SEQ_time_left_handle_frame_get(seqa);
seq_b_start = (seqb->start - SEQ_time_left_handle_frame_get(scene, seqb)) +
SEQ_time_left_handle_frame_get(scene, seqa);
SEQ_transform_translate_sequence(scene, seqb, seq_b_start - seqb->start);
SEQ_relations_invalidate_cache_preprocessed(scene, seqb);
seq_a_start = (seqa->start - SEQ_time_left_handle_frame_get(seqa)) +
SEQ_time_right_handle_frame_get(seqb) + gap;
seq_a_start = (seqa->start - SEQ_time_left_handle_frame_get(scene, seqa)) +
SEQ_time_right_handle_frame_get(scene, seqb) + gap;
SEQ_transform_translate_sequence(scene, seqa, seq_a_start - seqa->start);
SEQ_relations_invalidate_cache_preprocessed(scene, seqa);
}
@ -2196,13 +2200,17 @@ static Sequence *find_next_prev_sequence(Scene *scene, Sequence *test, int lr, i
switch (lr) {
case SEQ_SIDE_LEFT:
if (SEQ_time_right_handle_frame_get(seq) <= SEQ_time_left_handle_frame_get(test)) {
dist = SEQ_time_right_handle_frame_get(test) - SEQ_time_left_handle_frame_get(seq);
if (SEQ_time_right_handle_frame_get(scene, seq) <=
SEQ_time_left_handle_frame_get(scene, test)) {
dist = SEQ_time_right_handle_frame_get(scene, test) -
SEQ_time_left_handle_frame_get(scene, seq);
}
break;
case SEQ_SIDE_RIGHT:
if (SEQ_time_left_handle_frame_get(seq) >= SEQ_time_right_handle_frame_get(test)) {
dist = SEQ_time_left_handle_frame_get(seq) - SEQ_time_right_handle_frame_get(test);
if (SEQ_time_left_handle_frame_get(scene, seq) >=
SEQ_time_right_handle_frame_get(scene, test)) {
dist = SEQ_time_left_handle_frame_get(scene, seq) -
SEQ_time_right_handle_frame_get(scene, test);
}
break;
}
@ -2267,7 +2275,7 @@ static int sequencer_swap_exec(bContext *C, wmOperator *op)
if ((iseq->type & SEQ_TYPE_EFFECT) &&
(seq_is_parent(iseq, active_seq) || seq_is_parent(iseq, seq))) {
/* This may now overlap. */
if (SEQ_transform_test_overlap(seqbase, iseq)) {
if (SEQ_transform_test_overlap(scene, seqbase, iseq)) {
SEQ_transform_seqbase_shuffle(seqbase, iseq, scene);
}
}
@ -2317,7 +2325,7 @@ static int sequencer_rendersize_exec(bContext *C, wmOperator *UNUSED(op))
switch (active_seq->type) {
case SEQ_TYPE_IMAGE:
se = SEQ_render_give_stripelem(active_seq, scene->r.cfra);
se = SEQ_render_give_stripelem(scene, active_seq, scene->r.cfra);
break;
case SEQ_TYPE_MOVIE:
se = active_seq->strip->stripdata;
@ -2528,8 +2536,8 @@ static int sequencer_paste_exec(bContext *C, wmOperator *op)
else {
int min_seq_startdisp = INT_MAX;
LISTBASE_FOREACH (Sequence *, seq, &seqbase_clipboard) {
if (SEQ_time_left_handle_frame_get(seq) < min_seq_startdisp) {
min_seq_startdisp = SEQ_time_left_handle_frame_get(seq);
if (SEQ_time_left_handle_frame_get(scene, seq) < min_seq_startdisp) {
min_seq_startdisp = SEQ_time_left_handle_frame_get(scene, seq);
}
}
/* Paste strips relative to the current-frame. */
@ -2575,7 +2583,7 @@ static int sequencer_paste_exec(bContext *C, wmOperator *op)
* strip. */
SEQ_transform_translate_sequence(scene, iseq, ofs);
/* Ensure, that pasted strips don't overlap. */
if (SEQ_transform_test_overlap(ed->seqbasep, iseq)) {
if (SEQ_transform_test_overlap(scene, ed->seqbasep, iseq)) {
SEQ_transform_seqbase_shuffle(ed->seqbasep, iseq, scene);
}
}
@ -2632,7 +2640,7 @@ static int sequencer_swap_data_exec(bContext *C, wmOperator *op)
return OPERATOR_CANCELLED;
}
if (SEQ_edit_sequence_swap(seq_act, seq_other, &error_msg) == 0) {
if (SEQ_edit_sequence_swap(scene, seq_act, seq_other, &error_msg) == 0) {
BKE_report(op->reports, RPT_ERROR, error_msg);
return OPERATOR_CANCELLED;
}
@ -3057,15 +3065,16 @@ void SEQUENCER_OT_change_scene(struct wmOperatorType *ot)
* \{ */
/** Comparison function suitable to be used with BLI_listbase_sort(). */
static int seq_cmp_time_startdisp_channel(const void *a, const void *b)
static int seq_cmp_time_startdisp_channel(void *thunk, const void *a, const void *b)
{
const Scene *scene = thunk;
Sequence *seq_a = (Sequence *)a;
Sequence *seq_b = (Sequence *)b;
int seq_a_start = SEQ_time_left_handle_frame_get(seq_a);
int seq_b_start = SEQ_time_left_handle_frame_get(seq_b);
int seq_a_start = SEQ_time_left_handle_frame_get(scene, seq_a);
int seq_b_start = SEQ_time_left_handle_frame_get(scene, seq_b);
/* If strips have the same start frame favor the one with a higher channel. */
/* If strips have the same start frame favor the one with a higher channel.*/
if (seq_a_start == seq_b_start) {
return seq_a->machine > seq_b->machine;
}
@ -3109,7 +3118,7 @@ static bool seq_get_text_strip_cb(Sequence *seq, void *user_data)
ListBase *channels = SEQ_channels_displayed_get(ed);
/* Only text strips that are not muted and don't end with negative frame. */
if ((seq->type == SEQ_TYPE_TEXT) && !SEQ_render_is_muted(channels, seq) &&
(SEQ_time_right_handle_frame_get(seq) > cd->scene->r.sfra)) {
(SEQ_time_right_handle_frame_get(cd->scene, seq) > cd->scene->r.sfra)) {
BLI_addtail(cd->text_seq, MEM_dupallocN(seq));
}
return true;
@ -3156,7 +3165,7 @@ static int sequencer_export_subtitles_exec(bContext *C, wmOperator *op)
return OPERATOR_CANCELLED;
}
BLI_listbase_sort(&text_seq, seq_cmp_time_startdisp_channel);
BLI_listbase_sort_r(&text_seq, seq_cmp_time_startdisp_channel, scene);
/* Open and write file. */
file = BLI_fopen(filepath, "w");
@ -3171,15 +3180,16 @@ static int sequencer_export_subtitles_exec(bContext *C, wmOperator *op)
timecode_str_start,
sizeof(timecode_str_start),
-2,
FRA2TIME(max_ii(SEQ_time_left_handle_frame_get(seq) - scene->r.sfra, 0)),
FRA2TIME(max_ii(SEQ_time_left_handle_frame_get(scene, seq) - scene->r.sfra, 0)),
FPS,
USER_TIMECODE_SUBRIP);
BLI_timecode_string_from_time(
timecode_str_end,
sizeof(timecode_str_end),
-2,
FRA2TIME(SEQ_time_right_handle_frame_get(scene, seq) - scene->r.sfra),
FPS,
USER_TIMECODE_SUBRIP);
BLI_timecode_string_from_time(timecode_str_end,
sizeof(timecode_str_end),
-2,
FRA2TIME(SEQ_time_right_handle_frame_get(seq) - scene->r.sfra),
FPS,
USER_TIMECODE_SUBRIP);
fprintf(
file, "%d\n%s --> %s\n%s\n\n", iter++, timecode_str_start, timecode_str_end, data->text);
@ -3245,8 +3255,8 @@ static int sequencer_set_range_to_strips_exec(bContext *C, wmOperator *op)
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
if (seq->flag & SELECT) {
selected = true;
sfra = min_ii(sfra, SEQ_time_left_handle_frame_get(seq));
efra = max_ii(efra, SEQ_time_right_handle_frame_get(seq) - 1);
sfra = min_ii(sfra, SEQ_time_left_handle_frame_get(scene, seq));
efra = max_ii(efra, SEQ_time_right_handle_frame_get(scene, seq) - 1);
}
}
@ -3399,7 +3409,7 @@ static int sequencer_strip_transform_fit_exec(bContext *C, wmOperator *op)
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
if (seq->flag & SELECT && seq->type != SEQ_TYPE_SOUND_RAM) {
const int timeline_frame = CFRA;
StripElem *strip_elem = SEQ_render_give_stripelem(seq, timeline_frame);
StripElem *strip_elem = SEQ_render_give_stripelem(scene, seq, timeline_frame);
if (strip_elem == NULL) {
continue;

View File

@ -70,7 +70,9 @@ void color3ubv_from_seq(const struct Scene *curscene,
void sequencer_special_update_set(Sequence *seq);
/* Get handle width in 2d-View space. */
float sequence_handle_size_get_clamped(struct Sequence *seq, float pixelx);
float sequence_handle_size_get_clamped(const struct Scene *scene,
struct Sequence *seq,
float pixelx);
/* UNUSED */
/* void seq_reset_imageofs(struct SpaceSeq *sseq); */
@ -113,7 +115,7 @@ void channel_draw_context_init(const struct bContext *C,
/* sequencer_edit.c */
struct View2D;
void seq_rectf(struct Sequence *seq, struct rctf *rectf);
void seq_rectf(const struct Scene *scene, struct Sequence *seq, struct rctf *rectf);
struct Sequence *find_nearest_seq(struct Scene *scene,
struct View2D *v2d,
int *hand,

View File

@ -59,7 +59,7 @@ SeqCollection *all_strips_from_context(bContext *C)
const bool is_preview = sequencer_view_has_preview_poll(C);
if (is_preview) {
return SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
return SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
}
return SEQ_query_all_strips(seqbase);
@ -74,7 +74,7 @@ SeqCollection *selected_strips_from_context(bContext *C)
const bool is_preview = sequencer_view_has_preview_poll(C);
if (is_preview) {
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
return strips;
}
@ -108,7 +108,8 @@ static void select_surrounding_handles(Scene *scene, Sequence *test) /* XXX BRIN
}
/* Used for mouse selection in SEQUENCER_OT_select. */
static void select_active_side(ListBase *seqbase, int sel_side, int channel, int frame)
static void select_active_side(
const Scene *scene, ListBase *seqbase, int sel_side, int channel, int frame)
{
Sequence *seq;
@ -116,13 +117,13 @@ static void select_active_side(ListBase *seqbase, int sel_side, int channel, int
if (channel == seq->machine) {
switch (sel_side) {
case SEQ_SIDE_LEFT:
if (frame > (SEQ_time_left_handle_frame_get(seq))) {
if (frame > (SEQ_time_left_handle_frame_get(scene, seq))) {
seq->flag &= ~(SEQ_RIGHTSEL | SEQ_LEFTSEL);
seq->flag |= SELECT;
}
break;
case SEQ_SIDE_RIGHT:
if (frame < (SEQ_time_left_handle_frame_get(seq))) {
if (frame < (SEQ_time_left_handle_frame_get(scene, seq))) {
seq->flag &= ~(SEQ_RIGHTSEL | SEQ_LEFTSEL);
seq->flag |= SELECT;
}
@ -137,7 +138,8 @@ static void select_active_side(ListBase *seqbase, int sel_side, int channel, int
}
/* Used for mouse selection in SEQUENCER_OT_select_side. */
static void select_active_side_range(ListBase *seqbase,
static void select_active_side_range(const Scene *scene,
ListBase *seqbase,
const int sel_side,
const int frame_ranges[MAXSEQ],
const int frame_ignore)
@ -152,13 +154,13 @@ static void select_active_side_range(ListBase *seqbase,
}
switch (sel_side) {
case SEQ_SIDE_LEFT:
if (frame > (SEQ_time_left_handle_frame_get(seq))) {
if (frame > (SEQ_time_left_handle_frame_get(scene, seq))) {
seq->flag &= ~(SEQ_RIGHTSEL | SEQ_LEFTSEL);
seq->flag |= SELECT;
}
break;
case SEQ_SIDE_RIGHT:
if (frame < (SEQ_time_left_handle_frame_get(seq))) {
if (frame < (SEQ_time_left_handle_frame_get(scene, seq))) {
seq->flag &= ~(SEQ_RIGHTSEL | SEQ_LEFTSEL);
seq->flag |= SELECT;
}
@ -173,14 +175,14 @@ static void select_active_side_range(ListBase *seqbase,
}
/* Used for mouse selection in SEQUENCER_OT_select */
static void select_linked_time(ListBase *seqbase, Sequence *seq_link)
static void select_linked_time(const Scene *scene, ListBase *seqbase, Sequence *seq_link)
{
Sequence *seq;
for (seq = seqbase->first; seq; seq = seq->next) {
if (seq_link->machine != seq->machine) {
int left_match = (SEQ_time_left_handle_frame_get(seq) == seq_link->startdisp) ? 1 : 0;
int right_match = (SEQ_time_right_handle_frame_get(seq) == seq_link->enddisp) ? 1 : 0;
int left_match = (SEQ_time_left_handle_frame_get(scene, seq) == seq_link->startdisp) ? 1 : 0;
int right_match = (SEQ_time_right_handle_frame_get(scene, seq) == seq_link->enddisp) ? 1 : 0;
if (left_match && right_match) {
/* Direct match, copy the selection settings. */
@ -245,10 +247,10 @@ void ED_sequencer_select_sequence_single(Scene *scene, Sequence *seq, bool desel
recurs_sel_seq(seq);
}
void seq_rectf(Sequence *seq, rctf *rect)
void seq_rectf(const Scene *scene, Sequence *seq, rctf *rect)
{
rect->xmin = SEQ_time_left_handle_frame_get(seq);
rect->xmax = SEQ_time_right_handle_frame_get(seq);
rect->xmin = SEQ_time_left_handle_frame_get(scene, seq);
rect->xmax = SEQ_time_right_handle_frame_get(scene, seq);
rect->ymin = seq->machine + SEQ_STRIP_OFSBOTTOM;
rect->ymax = seq->machine + SEQ_STRIP_OFSTOP;
}
@ -273,12 +275,14 @@ Sequence *find_neighboring_sequence(Scene *scene, Sequence *test, int lr, int se
(sel == 0 && (seq->flag & SELECT) == 0))) {
switch (lr) {
case SEQ_SIDE_LEFT:
if (SEQ_time_left_handle_frame_get(test) == (SEQ_time_right_handle_frame_get(seq))) {
if (SEQ_time_left_handle_frame_get(scene, test) ==
(SEQ_time_right_handle_frame_get(scene, seq))) {
return seq;
}
break;
case SEQ_SIDE_RIGHT:
if (SEQ_time_right_handle_frame_get(test) == (SEQ_time_left_handle_frame_get(seq))) {
if (SEQ_time_right_handle_frame_get(scene, test) ==
(SEQ_time_left_handle_frame_get(scene, seq))) {
return seq;
}
break;
@ -311,18 +315,20 @@ Sequence *find_nearest_seq(Scene *scene, View2D *v2d, int *hand, const int mval[
while (seq) {
if (seq->machine == (int)y) {
/* Check for both normal strips, and strips that have been flipped horizontally. */
if (((SEQ_time_left_handle_frame_get(seq) < SEQ_time_right_handle_frame_get(seq)) &&
(SEQ_time_left_handle_frame_get(seq) <= x &&
SEQ_time_right_handle_frame_get(seq) >= x)) ||
((SEQ_time_left_handle_frame_get(seq) > SEQ_time_right_handle_frame_get(seq)) &&
(SEQ_time_left_handle_frame_get(seq) >= x &&
SEQ_time_right_handle_frame_get(seq) <= x))) {
if (((SEQ_time_left_handle_frame_get(scene, seq) <
SEQ_time_right_handle_frame_get(scene, seq)) &&
(SEQ_time_left_handle_frame_get(scene, seq) <= x &&
SEQ_time_right_handle_frame_get(scene, seq) >= x)) ||
((SEQ_time_left_handle_frame_get(scene, seq) >
SEQ_time_right_handle_frame_get(scene, seq)) &&
(SEQ_time_left_handle_frame_get(scene, seq) >= x &&
SEQ_time_right_handle_frame_get(scene, seq) <= x))) {
if (SEQ_transform_sequence_can_be_translated(seq)) {
/* Clamp handles to defined size in pixel space. */
handsize = 2.0f * sequence_handle_size_get_clamped(seq, pixelx);
displen = (float)abs(SEQ_time_left_handle_frame_get(seq) -
SEQ_time_right_handle_frame_get(seq));
handsize = 2.0f * sequence_handle_size_get_clamped(scene, seq, pixelx);
displen = (float)abs(SEQ_time_left_handle_frame_get(scene, seq) -
SEQ_time_right_handle_frame_get(scene, seq));
/* Don't even try to grab the handles of small strips. */
if (displen / pixelx > 16) {
@ -337,10 +343,10 @@ Sequence *find_nearest_seq(Scene *scene, View2D *v2d, int *hand, const int mval[
CLAMP(handsize, 7 * pixelx, 30 * pixelx);
}
if (handsize + SEQ_time_left_handle_frame_get(seq) >= x) {
if (handsize + SEQ_time_left_handle_frame_get(scene, seq) >= x) {
*hand = SEQ_SIDE_LEFT;
}
else if (-handsize + SEQ_time_right_handle_frame_get(seq) <= x) {
else if (-handsize + SEQ_time_right_handle_frame_get(scene, seq) <= x) {
*hand = SEQ_SIDE_RIGHT;
}
}
@ -583,8 +589,8 @@ static void sequencer_select_side_of_frame(const bContext *C,
const float x = UI_view2d_region_to_view_x(v2d, mval[0]);
LISTBASE_FOREACH (Sequence *, seq_iter, SEQ_active_seqbase_get(ed)) {
if (((x < CFRA) && (SEQ_time_right_handle_frame_get(seq_iter) <= CFRA)) ||
((x >= CFRA) && (SEQ_time_left_handle_frame_get(seq_iter) >= CFRA))) {
if (((x < CFRA) && (SEQ_time_right_handle_frame_get(scene, seq_iter) <= CFRA)) ||
((x >= CFRA) && (SEQ_time_left_handle_frame_get(scene, seq_iter) >= CFRA))) {
/* Select left or right. */
seq_iter->flag |= SELECT;
recurs_sel_seq(seq_iter);
@ -639,8 +645,11 @@ static void sequencer_select_linked_handle(const bContext *C,
case SEQ_SIDE_LEFT:
if ((seq->flag & SEQ_LEFTSEL) && (neighbor->flag & SEQ_RIGHTSEL)) {
seq->flag |= SELECT;
select_active_side(
ed->seqbasep, SEQ_SIDE_LEFT, seq->machine, SEQ_time_left_handle_frame_get(seq));
select_active_side(scene,
ed->seqbasep,
SEQ_SIDE_LEFT,
seq->machine,
SEQ_time_left_handle_frame_get(scene, seq));
}
else {
seq->flag |= SELECT;
@ -653,8 +662,11 @@ static void sequencer_select_linked_handle(const bContext *C,
case SEQ_SIDE_RIGHT:
if ((seq->flag & SEQ_RIGHTSEL) && (neighbor->flag & SEQ_LEFTSEL)) {
seq->flag |= SELECT;
select_active_side(
ed->seqbasep, SEQ_SIDE_RIGHT, seq->machine, SEQ_time_left_handle_frame_get(seq));
select_active_side(scene,
ed->seqbasep,
SEQ_SIDE_RIGHT,
seq->machine,
SEQ_time_left_handle_frame_get(scene, seq));
}
else {
seq->flag |= SELECT;
@ -669,7 +681,7 @@ static void sequencer_select_linked_handle(const bContext *C,
else {
select_active_side(
ed->seqbasep, sel_side, seq->machine, SEQ_time_left_handle_frame_get(seq));
scene, ed->seqbasep, sel_side, seq->machine, SEQ_time_left_handle_frame_get(scene, seq));
}
}
}
@ -734,7 +746,7 @@ static Sequence *seq_select_seq_from_preview(
const bool use_cycle = (!WM_cursor_test_motion_and_update(mval) || extend || toggle);
SeqCollection *strips = SEQ_query_rendered_strips(
channels, seqbase, scene->r.cfra, sseq->chanshown);
scene, channels, seqbase, scene->r.cfra, sseq->chanshown);
/* Allow strips this far from the closest center to be included.
* This allows cycling over center points which are near enough
@ -921,7 +933,7 @@ static int sequencer_select_exec(bContext *C, wmOperator *op)
ED_sequencer_deselect_all(scene);
}
sequencer_select_strip_impl(ed, seq, handle_clicked, extend, deselect, toggle);
select_linked_time(ed->seqbasep, seq);
select_linked_time(scene, ed->seqbasep, seq);
sequencer_select_do_updates(C, scene);
sequencer_select_set_active(scene, seq);
return OPERATOR_FINISHED;
@ -1436,13 +1448,13 @@ static int sequencer_select_side_of_frame_exec(bContext *C, wmOperator *op)
bool test = false;
switch (side) {
case -1:
test = (timeline_frame >= SEQ_time_right_handle_frame_get(seq));
test = (timeline_frame >= SEQ_time_right_handle_frame_get(scene, seq));
break;
case 1:
test = (timeline_frame <= SEQ_time_left_handle_frame_get(seq));
test = (timeline_frame <= SEQ_time_left_handle_frame_get(scene, seq));
break;
case 2:
test = SEQ_time_strip_intersects_frame(seq, timeline_frame);
test = SEQ_time_strip_intersects_frame(scene, seq, timeline_frame);
break;
}
@ -1513,10 +1525,10 @@ static int sequencer_select_side_exec(bContext *C, wmOperator *op)
if (seq->flag & SELECT) {
selected = true;
if (sel_side == SEQ_SIDE_LEFT) {
*frame_limit_p = max_ii(*frame_limit_p, SEQ_time_left_handle_frame_get(seq));
*frame_limit_p = max_ii(*frame_limit_p, SEQ_time_left_handle_frame_get(scene, seq));
}
else {
*frame_limit_p = min_ii(*frame_limit_p, SEQ_time_left_handle_frame_get(seq));
*frame_limit_p = min_ii(*frame_limit_p, SEQ_time_left_handle_frame_get(scene, seq));
}
}
}
@ -1525,7 +1537,7 @@ static int sequencer_select_side_exec(bContext *C, wmOperator *op)
return OPERATOR_CANCELLED;
}
select_active_side_range(ed->seqbasep, sel_side, frame_ranges, frame_init);
select_active_side_range(scene, ed->seqbasep, sel_side, frame_ranges, frame_init);
ED_outliner_select_sync_from_sequence_tag(C);
@ -1595,7 +1607,7 @@ static void seq_box_select_seq_from_preview(const bContext *C, rctf *rect, const
SpaceSeq *sseq = CTX_wm_space_seq(C);
SeqCollection *strips = SEQ_query_rendered_strips(
channels, seqbase, scene->r.cfra, sseq->chanshown);
scene, channels, seqbase, scene->r.cfra, sseq->chanshown);
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, strips) {
if (!seq_box_select_rect_image_isect(scene, seq, rect)) {
@ -1648,15 +1660,15 @@ static int sequencer_box_select_exec(bContext *C, wmOperator *op)
LISTBASE_FOREACH (Sequence *, seq, ed->seqbasep) {
rctf rq;
seq_rectf(seq, &rq);
seq_rectf(scene, seq, &rq);
if (BLI_rctf_isect(&rq, &rectf, NULL)) {
if (handles) {
/* Get the handles draw size. */
float pixelx = BLI_rctf_size_x(&v2d->cur) / BLI_rcti_size_x(&v2d->mask);
float handsize = sequence_handle_size_get_clamped(seq, pixelx);
float handsize = sequence_handle_size_get_clamped(scene, seq, pixelx);
/* Right handle. */
if (rectf.xmax > (SEQ_time_right_handle_frame_get(seq) - handsize)) {
if (rectf.xmax > (SEQ_time_right_handle_frame_get(scene, seq) - handsize)) {
if (select) {
seq->flag |= SELECT | SEQ_RIGHTSEL;
}
@ -1669,7 +1681,7 @@ static int sequencer_box_select_exec(bContext *C, wmOperator *op)
}
}
/* Left handle. */
if (rectf.xmin < (SEQ_time_left_handle_frame_get(seq) + handsize)) {
if (rectf.xmin < (SEQ_time_left_handle_frame_get(scene, seq) + handsize)) {
if (select) {
seq->flag |= SELECT | SEQ_LEFTSEL;
}
@ -1953,7 +1965,8 @@ static bool select_grouped_effect(SeqCollection *strips,
return changed;
}
static bool select_grouped_time_overlap(SeqCollection *strips,
static bool select_grouped_time_overlap(const Scene *scene,
SeqCollection *strips,
ListBase *UNUSED(seqbase),
Sequence *actseq)
{
@ -1961,8 +1974,10 @@ static bool select_grouped_time_overlap(SeqCollection *strips,
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, strips) {
if (SEQ_time_left_handle_frame_get(seq) < SEQ_time_right_handle_frame_get(actseq) &&
SEQ_time_right_handle_frame_get(seq) > SEQ_time_left_handle_frame_get(actseq)) {
if (SEQ_time_left_handle_frame_get(scene, seq) <
SEQ_time_right_handle_frame_get(scene, actseq) &&
SEQ_time_right_handle_frame_get(scene, seq) >
SEQ_time_left_handle_frame_get(scene, actseq)) {
seq->flag |= SELECT;
changed = true;
}
@ -1972,7 +1987,8 @@ static bool select_grouped_time_overlap(SeqCollection *strips,
}
/* Query strips that are in lower channel and intersect in time with seq_reference. */
static void query_lower_channel_strips(Sequence *seq_reference,
static void query_lower_channel_strips(const Scene *scene,
Sequence *seq_reference,
ListBase *seqbase,
SeqCollection *collection)
{
@ -1980,10 +1996,10 @@ static void query_lower_channel_strips(Sequence *seq_reference,
if (seq_test->machine > seq_reference->machine) {
continue; /* Not lower channel. */
}
if (SEQ_time_right_handle_frame_get(seq_test) <=
SEQ_time_left_handle_frame_get(seq_reference) ||
SEQ_time_left_handle_frame_get(seq_test) >=
SEQ_time_right_handle_frame_get(seq_reference)) {
if (SEQ_time_right_handle_frame_get(scene, seq_test) <=
SEQ_time_left_handle_frame_get(scene, seq_reference) ||
SEQ_time_left_handle_frame_get(scene, seq_test) >=
SEQ_time_right_handle_frame_get(scene, seq_reference)) {
continue; /* Not intersecting in time. */
}
SEQ_collection_append_strip(seq_test, collection);
@ -1992,7 +2008,8 @@ static void query_lower_channel_strips(Sequence *seq_reference,
/* Select all strips within time range and with lower channel of initial selection. Then select
* effect chains of these strips. */
static bool select_grouped_effect_link(SeqCollection *strips,
static bool select_grouped_effect_link(const Scene *scene,
SeqCollection *strips,
ListBase *seqbase,
Sequence *UNUSED(actseq),
const int UNUSED(channel))
@ -2000,8 +2017,10 @@ static bool select_grouped_effect_link(SeqCollection *strips,
/* Get collection of strips. */
SEQ_filter_selected_strips(strips);
const int selected_strip_count = SEQ_collection_len(strips);
SEQ_collection_expand(seqbase, strips, query_lower_channel_strips);
SEQ_collection_expand(seqbase, strips, SEQ_query_strip_effect_chain);
// XXX this uses scene as arg, so it does not work with iterator :( I had thought about this, but
// expand function is just so useful... I can just add scene and inject it I guess.....
SEQ_collection_expand(scene, seqbase, strips, query_lower_channel_strips);
SEQ_collection_expand(scene, seqbase, strips, SEQ_query_strip_effect_chain);
/* Check if other strips will be affected. */
const bool changed = SEQ_collection_len(strips) > selected_strip_count;
@ -2067,10 +2086,10 @@ static int sequencer_select_grouped_exec(bContext *C, wmOperator *op)
changed |= select_grouped_effect(strips, seqbase, actseq, channel);
break;
case SEQ_SELECT_GROUP_EFFECT_LINK:
changed |= select_grouped_effect_link(strips, seqbase, actseq, channel);
changed |= select_grouped_effect_link(scene, strips, seqbase, actseq, channel);
break;
case SEQ_SELECT_GROUP_OVERLAP:
changed |= select_grouped_time_overlap(strips, seqbase, actseq);
changed |= select_grouped_time_overlap(scene, strips, seqbase, actseq);
break;
default:
BLI_assert(0);

View File

@ -69,15 +69,16 @@ static void thumbnail_endjob(void *data)
WM_main_add_notifier(NC_SCENE | ND_SEQUENCER, tj->scene);
}
static bool check_seq_need_thumbnails(Sequence *seq, rctf *view_area)
static bool check_seq_need_thumbnails(const Scene *scene, Sequence *seq, rctf *view_area)
{
if (!ELEM(seq->type, SEQ_TYPE_MOVIE, SEQ_TYPE_IMAGE)) {
return false;
}
if (min_ii(SEQ_time_left_handle_frame_get(seq), seq->start) > view_area->xmax) {
if (min_ii(SEQ_time_left_handle_frame_get(scene, seq), seq->start) > view_area->xmax) {
return false;
}
if (max_ii(SEQ_time_right_handle_frame_get(seq), seq->start + seq->len) < view_area->xmin) {
if (max_ii(SEQ_time_right_handle_frame_get(scene, seq), seq->start + seq->len) <
view_area->xmin) {
return false;
}
if (seq->machine + 1.0f < view_area->ymin) {
@ -135,6 +136,7 @@ static void thumbnail_start_job(void *data,
float *UNUSED(progress))
{
ThumbnailDrawJob *tj = data;
const Scene *scene = tj->scene;
float frame_step;
GHashIterator gh_iter;
@ -145,7 +147,7 @@ static void thumbnail_start_job(void *data,
Sequence *seq_orig = BLI_ghashIterator_getKey(&gh_iter);
ThumbDataItem *val = BLI_ghash_lookup(tj->sequences_ghash, seq_orig);
if (check_seq_need_thumbnails(seq_orig, tj->view_area)) {
if (check_seq_need_thumbnails(scene, seq_orig, tj->view_area)) {
seq_get_thumb_image_dimensions(
val->seq_dupli, tj->pixelx, tj->pixely, &frame_step, tj->thumb_height, NULL, NULL);
SEQ_render_thumbnails(
@ -161,7 +163,7 @@ static void thumbnail_start_job(void *data,
Sequence *seq_orig = BLI_ghashIterator_getKey(&gh_iter);
ThumbDataItem *val = BLI_ghash_lookup(tj->sequences_ghash, seq_orig);
if (check_seq_need_thumbnails(seq_orig, tj->view_area)) {
if (check_seq_need_thumbnails(scene, seq_orig, tj->view_area)) {
seq_get_thumb_image_dimensions(
val->seq_dupli, tj->pixelx, tj->pixely, &frame_step, tj->thumb_height, NULL, NULL);
SEQ_render_thumbnails_base_set(&tj->context, val->seq_dupli, seq_orig, tj->view_area, stop);
@ -197,7 +199,7 @@ static GHash *sequencer_thumbnail_ghash_init(const bContext *C, View2D *v2d, Edi
LISTBASE_FOREACH (Sequence *, seq, ed->seqbasep) {
ThumbDataItem *val_need_update = BLI_ghash_lookup(thumb_data_hash, seq);
if (val_need_update == NULL && check_seq_need_thumbnails(seq, &v2d->cur)) {
if (val_need_update == NULL && check_seq_need_thumbnails(scene, seq, &v2d->cur)) {
ThumbDataItem *val = MEM_callocN(sizeof(ThumbDataItem), "Thumbnail Hash Values");
val->seq_dupli = SEQ_sequence_dupli_recursive(scene, scene, NULL, seq, 0);
val->scene = scene;
@ -206,7 +208,7 @@ static GHash *sequencer_thumbnail_ghash_init(const bContext *C, View2D *v2d, Edi
else {
if (val_need_update != NULL) {
val_need_update->seq_dupli->start = seq->start;
val_need_update->seq_dupli->startdisp = SEQ_time_left_handle_frame_get(seq);
val_need_update->seq_dupli->startdisp = SEQ_time_left_handle_frame_get(scene, seq);
}
}
}
@ -361,18 +363,20 @@ static int sequencer_thumbnail_closest_previous_frame_get(int timeline_frame,
return best_frame;
}
static int sequencer_thumbnail_closest_guaranteed_frame_get(Sequence *seq, int timeline_frame)
static int sequencer_thumbnail_closest_guaranteed_frame_get(struct Scene *scene,
Sequence *seq,
int timeline_frame)
{
if (timeline_frame <= SEQ_time_left_handle_frame_get(seq)) {
return SEQ_time_left_handle_frame_get(seq);
if (timeline_frame <= SEQ_time_left_handle_frame_get(scene, seq)) {
return SEQ_time_left_handle_frame_get(scene, seq);
}
/* Set of "guaranteed" thumbnails. */
const int frame_index = timeline_frame - SEQ_time_left_handle_frame_get(seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(seq);
const int frame_index = timeline_frame - SEQ_time_left_handle_frame_get(scene, seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(scene, 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 +
SEQ_time_left_handle_frame_get(seq);
SEQ_time_left_handle_frame_get(scene, seq);
return nearest_guaranted_absolute_frame;
}
@ -387,7 +391,8 @@ static ImBuf *sequencer_thumbnail_closest_from_memory(const SeqRenderData *conte
previously_displayed);
ImBuf *ibuf_previous = SEQ_get_thumbnail(context, seq, frame_previous, crop, clipped);
int frame_guaranteed = sequencer_thumbnail_closest_guaranteed_frame_get(seq, timeline_frame);
int frame_guaranteed = sequencer_thumbnail_closest_guaranteed_frame_get(
context->scene, seq, timeline_frame);
ImBuf *ibuf_guaranteed = SEQ_get_thumbnail(context, seq, frame_guaranteed, crop, clipped);
ImBuf *closest_in_memory = NULL;
@ -450,14 +455,14 @@ void draw_seq_strip_thumbnail(View2D *v2d,
float thumb_y_end = y1 + thumb_height;
float cut_off = 0;
float upper_thumb_bound = SEQ_time_has_right_still_frames(seq) ?
float upper_thumb_bound = SEQ_time_has_right_still_frames(scene, seq) ?
(seq->start + seq->len) :
SEQ_time_right_handle_frame_get(seq);
SEQ_time_right_handle_frame_get(scene, seq);
if (seq->type == SEQ_TYPE_IMAGE) {
upper_thumb_bound = SEQ_time_right_handle_frame_get(seq);
upper_thumb_bound = SEQ_time_right_handle_frame_get(scene, seq);
}
float timeline_frame = SEQ_render_thumbnail_first_frame_get(seq, thumb_width, &v2d->cur);
float timeline_frame = SEQ_render_thumbnail_first_frame_get(scene, seq, thumb_width, &v2d->cur);
float thumb_x_end;
GSet *last_displayed_thumbnails = last_displayed_thumbnails_list_ensure(C, seq);
@ -480,8 +485,8 @@ void draw_seq_strip_thumbnail(View2D *v2d,
}
/* Set the clipping bound to show the left handle moving over thumbs and not shift thumbs. */
if (IN_RANGE_INCL(SEQ_time_left_handle_frame_get(seq), timeline_frame, thumb_x_end)) {
cut_off = SEQ_time_left_handle_frame_get(seq) - timeline_frame;
if (IN_RANGE_INCL(SEQ_time_left_handle_frame_get(scene, seq), timeline_frame, thumb_x_end)) {
cut_off = SEQ_time_left_handle_frame_get(scene, seq) - timeline_frame;
clipped = true;
}
@ -558,7 +563,7 @@ void draw_seq_strip_thumbnail(View2D *v2d,
IMB_freeImBuf(ibuf);
GPU_blend(GPU_BLEND_NONE);
cut_off = 0;
timeline_frame = SEQ_render_thumbnail_next_frame_get(seq, timeline_frame, thumb_width);
timeline_frame = SEQ_render_thumbnail_next_frame_get(scene, seq, timeline_frame, thumb_width);
}
last_displayed_thumbnails_list_cleanup(last_displayed_thumbnails, timeline_frame, FLT_MAX);
}

View File

@ -84,7 +84,7 @@ static int sequencer_view_all_exec(bContext *C, wmOperator *op)
box.xmin = ms->disp_range[0] - 1;
box.xmax = ms->disp_range[1] + 1;
}
SEQ_timeline_expand_boundbox(SEQ_active_seqbase_get(ed), &box);
SEQ_timeline_expand_boundbox(scene, SEQ_active_seqbase_get(ed), &box);
View2D *v2d = &region->v2d;
rcti scrub_rect;
@ -306,8 +306,8 @@ static void seq_view_collection_rect_timeline(Scene *scene, SeqCollection *strip
int xmargin = FPS;
SEQ_ITERATOR_FOREACH (seq, strips) {
xmin = min_ii(xmin, SEQ_time_left_handle_frame_get(seq));
xmax = max_ii(xmax, SEQ_time_right_handle_frame_get(seq));
xmin = min_ii(xmin, SEQ_time_left_handle_frame_get(scene, seq));
xmax = max_ii(xmax, SEQ_time_right_handle_frame_get(scene, seq));
ymin = min_ii(ymin, seq->machine);
ymax = max_ii(ymax, seq->machine);

View File

@ -548,7 +548,8 @@ static void sequencer_main_clamp_view(const bContext *C, ARegion *region)
}
View2D *v2d = &region->v2d;
Editing *ed = SEQ_editing_get(CTX_data_scene(C));
Scene *scene = CTX_data_scene(C);
Editing *ed = SEQ_editing_get(scene);
if (ed == NULL) {
return;
@ -563,7 +564,7 @@ static void sequencer_main_clamp_view(const bContext *C, ARegion *region)
/* Initialize default view with 7 channels, that are visible even if empty. */
rctf strip_boundbox;
BLI_rctf_init(&strip_boundbox, 0.0f, 0.0f, 1.0f, 7.0f);
SEQ_timeline_expand_boundbox(ed->seqbasep, &strip_boundbox);
SEQ_timeline_expand_boundbox(scene, ed->seqbasep, &strip_boundbox);
/* Clamp Y max. Scrubbing area height must be added, so strips aren't occluded. */
rcti scrub_rect;

View File

@ -91,8 +91,8 @@ static void SeqTransInfo(TransInfo *t, Sequence *seq, int *r_count, int *r_flag)
/* *** Extend Transform *** */
int cfra = CFRA;
int left = SEQ_time_left_handle_frame_get(seq);
int right = SEQ_time_right_handle_frame_get(seq);
int left = SEQ_time_left_handle_frame_get(scene, seq);
int right = SEQ_time_right_handle_frame_get(scene, seq);
if (((seq->flag & SELECT) == 0 || SEQ_transform_is_locked(channels, seq))) {
*r_count = 0;
@ -163,8 +163,13 @@ static int SeqTransCount(TransInfo *t, ListBase *seqbase)
return tot;
}
static TransData *SeqToTransData(
TransData *td, TransData2D *td2d, TransDataSeq *tdsq, Sequence *seq, int flag, int sel_flag)
static TransData *SeqToTransData(Scene *scene,
TransData *td,
TransData2D *td2d,
TransDataSeq *tdsq,
Sequence *seq,
int flag,
int sel_flag)
{
int start_left;
@ -173,16 +178,16 @@ static TransData *SeqToTransData(
/* Use seq_tx_get_final_left() and an offset here
* so transform has the left hand location of the strip.
* tdsq->start_offset is used when flushing the tx data back */
start_left = SEQ_time_left_handle_frame_get(seq);
start_left = SEQ_time_left_handle_frame_get(scene, seq);
td2d->loc[0] = start_left;
tdsq->start_offset = start_left - seq->start; /* use to apply the original location */
break;
case SEQ_LEFTSEL:
start_left = SEQ_time_left_handle_frame_get(seq);
start_left = SEQ_time_left_handle_frame_get(scene, seq);
td2d->loc[0] = start_left;
break;
case SEQ_RIGHTSEL:
td2d->loc[0] = SEQ_time_right_handle_frame_get(seq);
td2d->loc[0] = SEQ_time_right_handle_frame_get(scene, seq);
break;
}
@ -227,6 +232,7 @@ static int SeqToTransData_build(
TransInfo *t, ListBase *seqbase, TransData *td, TransData2D *td2d, TransDataSeq *tdsq)
{
Sequence *seq;
Scene *scene = t->scene;
int count, flag;
int tot = 0;
@ -238,16 +244,16 @@ static int SeqToTransData_build(
if (flag & SELECT) {
if (flag & (SEQ_LEFTSEL | SEQ_RIGHTSEL)) {
if (flag & SEQ_LEFTSEL) {
SeqToTransData(td++, td2d++, tdsq++, seq, flag, SEQ_LEFTSEL);
SeqToTransData(scene, td++, td2d++, tdsq++, seq, flag, SEQ_LEFTSEL);
tot++;
}
if (flag & SEQ_RIGHTSEL) {
SeqToTransData(td++, td2d++, tdsq++, seq, flag, SEQ_RIGHTSEL);
SeqToTransData(scene, td++, td2d++, tdsq++, seq, flag, SEQ_RIGHTSEL);
tot++;
}
}
else {
SeqToTransData(td++, td2d++, tdsq++, seq, flag, SELECT);
SeqToTransData(scene, td++, td2d++, tdsq++, seq, flag, SELECT);
tot++;
}
}
@ -275,7 +281,7 @@ static void seq_transform_cancel(TransInfo *t, SeqCollection *transformed_strips
SEQ_ITERATOR_FOREACH (seq, transformed_strips) {
/* Handle pre-existing overlapping strips even when operator is canceled.
* This is necessary for SEQUENCER_OT_duplicate_move macro for example. */
if (SEQ_transform_test_overlap(seqbase, seq)) {
if (SEQ_transform_test_overlap(t->scene, seqbase, seq)) {
SEQ_transform_seqbase_shuffle(seqbase, seq, t->scene);
}
}
@ -318,7 +324,8 @@ static void freeSeqData(TransInfo *t, TransDataContainer *tc, TransCustomData *c
}
SeqCollection *transformed_strips = seq_transform_collection_from_transdata(tc);
SEQ_collection_expand(seqbase_active_get(t), transformed_strips, SEQ_query_strip_effect_chain);
SEQ_collection_expand(
t->scene, seqbase_active_get(t), transformed_strips, SEQ_query_strip_effect_chain);
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, transformed_strips) {
@ -363,11 +370,11 @@ typedef enum SeqInputSide {
SEQ_INPUT_RIGHT = 1,
} SeqInputSide;
static Sequence *effect_input_get(Sequence *effect, SeqInputSide side)
static Sequence *effect_input_get(const Scene *scene, Sequence *effect, SeqInputSide side)
{
Sequence *input = effect->seq1;
if (effect->seq2 && (SEQ_time_left_handle_frame_get(effect->seq2) -
SEQ_time_left_handle_frame_get(effect->seq1)) *
if (effect->seq2 && (SEQ_time_left_handle_frame_get(scene, effect->seq2) -
SEQ_time_left_handle_frame_get(scene, effect->seq1)) *
side >
0) {
input = effect->seq2;
@ -375,12 +382,12 @@ static Sequence *effect_input_get(Sequence *effect, SeqInputSide side)
return input;
}
static Sequence *effect_base_input_get(Sequence *effect, SeqInputSide side)
static Sequence *effect_base_input_get(const Scene *scene, Sequence *effect, SeqInputSide side)
{
Sequence *input = effect, *seq_iter = effect;
while (seq_iter != NULL) {
input = seq_iter;
seq_iter = effect_input_get(seq_iter, side);
seq_iter = effect_input_get(scene, seq_iter, side);
}
return input;
}
@ -400,7 +407,7 @@ static SeqCollection *query_time_dependent_strips_strips(TransInfo *t)
SeqCollection *strips_no_handles = query_selected_strips_no_handles(seqbase);
/* Selection is needed as reference for related strips. */
SeqCollection *dependent = SEQ_collection_duplicate(strips_no_handles);
SEQ_collection_expand(seqbase, strips_no_handles, SEQ_query_strip_effect_chain);
SEQ_collection_expand(t->scene, seqbase, strips_no_handles, SEQ_query_strip_effect_chain);
bool strip_added = true;
while (strip_added) {
@ -430,7 +437,7 @@ static SeqCollection *query_time_dependent_strips_strips(TransInfo *t)
* With single input effect, it is less likely desirable to move animation. */
SeqCollection *selected_strips = SEQ_query_selected_strips(seqbase);
SEQ_collection_expand(seqbase, selected_strips, SEQ_query_strip_effect_chain);
SEQ_collection_expand(t->scene, seqbase, selected_strips, SEQ_query_strip_effect_chain);
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, selected_strips) {
/* Check only 2 input effects. */
@ -439,8 +446,8 @@ static SeqCollection *query_time_dependent_strips_strips(TransInfo *t)
}
/* Find immediate base inputs(left and right side). */
Sequence *input_left = effect_base_input_get(seq, SEQ_INPUT_LEFT);
Sequence *input_right = effect_base_input_get(seq, SEQ_INPUT_RIGHT);
Sequence *input_left = effect_base_input_get(t->scene, seq, SEQ_INPUT_LEFT);
Sequence *input_right = effect_base_input_get(t->scene, seq, SEQ_INPUT_RIGHT);
if ((input_left->flag & SEQ_RIGHTSEL) != 0 && (input_right->flag & SEQ_LEFTSEL) != 0) {
SEQ_collection_append_strip(seq, dependent);
@ -571,6 +578,8 @@ static void flushTransSeq(TransInfo *t)
TransDataSeq *tdsq = NULL;
Sequence *seq;
Scene *scene = t->scene;
TransDataContainer *tc = TRANS_DATA_CONTAINER_FIRST_SINGLE(t);
/* This is calculated for offsetting animation of effects that change position with inputs.
@ -594,7 +603,7 @@ static void flushTransSeq(TransInfo *t)
case SELECT: {
if (SEQ_transform_sequence_can_be_translated(seq)) {
offset = new_frame - tdsq->start_offset - seq->start;
SEQ_transform_translate_sequence(t->scene, seq, offset);
SEQ_transform_translate_sequence(scene, seq, offset);
if (abs(offset) > abs(max_offset)) {
max_offset = offset;
}
@ -604,24 +613,22 @@ static void flushTransSeq(TransInfo *t)
break;
}
case SEQ_LEFTSEL: { /* No vertical transform. */
int old_startdisp = SEQ_time_left_handle_frame_get(seq);
int old_startdisp = SEQ_time_left_handle_frame_get(scene, seq);
SEQ_time_left_handle_frame_set(t->scene, seq, new_frame);
SEQ_transform_handle_xlimits(
t->scene, seq, tdsq->flag & SEQ_LEFTSEL, tdsq->flag & SEQ_RIGHTSEL);
SEQ_transform_fix_single_image_seq_offsets(t->scene, seq);
if (abs(SEQ_time_left_handle_frame_get(seq) - old_startdisp) > abs(max_offset)) {
max_offset = SEQ_time_left_handle_frame_get(seq) - old_startdisp;
if (abs(SEQ_time_left_handle_frame_get(scene, seq) - old_startdisp) > abs(max_offset)) {
max_offset = SEQ_time_left_handle_frame_get(scene, seq) - old_startdisp;
}
break;
}
case SEQ_RIGHTSEL: { /* No vertical transform. */
int old_enddisp = SEQ_time_right_handle_frame_get(seq);
int old_enddisp = SEQ_time_right_handle_frame_get(scene, seq);
SEQ_time_right_handle_frame_set(t->scene, seq, new_frame);
SEQ_transform_handle_xlimits(
t->scene, seq, tdsq->flag & SEQ_LEFTSEL, tdsq->flag & SEQ_RIGHTSEL);
SEQ_transform_fix_single_image_seq_offsets(t->scene, seq);
if (abs(SEQ_time_right_handle_frame_get(seq) - old_enddisp) > abs(max_offset)) {
max_offset = SEQ_time_right_handle_frame_get(seq) - old_enddisp;
if (abs(SEQ_time_right_handle_frame_get(scene, seq) - old_enddisp) > abs(max_offset)) {
max_offset = SEQ_time_right_handle_frame_get(scene, seq) - old_enddisp;
}
break;
}
@ -638,12 +645,13 @@ static void flushTransSeq(TransInfo *t)
/* need to do the overlap check in a new loop otherwise adjacent strips
* will not be updated and we'll get false positives */
SeqCollection *transformed_strips = seq_transform_collection_from_transdata(tc);
SEQ_collection_expand(seqbase_active_get(t), transformed_strips, SEQ_query_strip_effect_chain);
SEQ_collection_expand(
t->scene, seqbase_active_get(t), transformed_strips, SEQ_query_strip_effect_chain);
SEQ_ITERATOR_FOREACH (seq, transformed_strips) {
/* test overlap, displays red outline */
seq->flag &= ~SEQ_OVERLAP;
if (SEQ_transform_test_overlap(seqbasep, seq)) {
if (SEQ_transform_test_overlap(scene, seqbasep, seq)) {
seq->flag |= SEQ_OVERLAP;
}
}

View File

@ -123,7 +123,8 @@ void createTransSeqImageData(TransInfo *t)
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, t->scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(
t->scene, channels, seqbase, t->scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
const int count = SEQ_collection_len(strips);

View File

@ -247,7 +247,7 @@ static bool gizmo2d_calc_bounds(const bContext *C, float *r_center, float *r_min
Editing *ed = SEQ_editing_get(scene);
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
int selected_strips = SEQ_collection_len(strips);
if (selected_strips > 0) {
@ -299,7 +299,7 @@ static int gizmo2d_calc_transform_orientation(const bContext *C)
Editing *ed = SEQ_editing_get(scene);
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
bool use_local_orient = SEQ_collection_len(strips) == 1;
@ -322,7 +322,7 @@ static float gizmo2d_calc_rotation(const bContext *C)
Editing *ed = SEQ_editing_get(scene);
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
if (SEQ_collection_len(strips) == 1) {
@ -348,7 +348,7 @@ static bool seq_get_strip_pivot_median(const Scene *scene, float r_pivot[2])
Editing *ed = SEQ_editing_get(scene);
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
bool has_select = SEQ_collection_len(strips) != 0;
@ -387,7 +387,8 @@ static bool gizmo2d_calc_transform_pivot(const bContext *C, float r_pivot[2])
Editing *ed = SEQ_editing_get(scene);
ListBase *seqbase = SEQ_active_seqbase_get(ed);
ListBase *channels = SEQ_channels_displayed_get(ed);
SeqCollection *strips = SEQ_query_rendered_strips(channels, seqbase, scene->r.cfra, 0);
SeqCollection *strips = SEQ_query_rendered_strips(
scene, channels, seqbase, scene->r.cfra, 0);
SEQ_filter_selected_strips(strips);
has_select = SEQ_collection_len(strips) != 0;
SEQ_collection_free(strips);

View File

@ -59,21 +59,23 @@ static int cmp_fn(const void *a, const void *b)
return (*(int *)a - *(int *)b);
}
static void seq_snap_source_points_build(TransSeqSnapData *snap_data, SeqCollection *snap_sources)
static void seq_snap_source_points_build(const Scene *scene,
TransSeqSnapData *snap_data,
SeqCollection *snap_sources)
{
int i = 0;
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, snap_sources) {
int left = 0, right = 0;
if (seq->flag & SEQ_LEFTSEL) {
left = right = SEQ_time_left_handle_frame_get(seq);
left = right = SEQ_time_left_handle_frame_get(scene, seq);
}
else if (seq->flag & SEQ_RIGHTSEL) {
left = right = SEQ_time_right_handle_frame_get(seq);
left = right = SEQ_time_right_handle_frame_get(scene, seq);
}
else {
left = SEQ_time_left_handle_frame_get(seq);
right = SEQ_time_right_handle_frame_get(seq);
left = SEQ_time_left_handle_frame_get(scene, seq);
right = SEQ_time_right_handle_frame_get(scene, seq);
}
snap_data->source_snap_points[i] = left;
@ -92,7 +94,8 @@ static void seq_snap_source_points_build(TransSeqSnapData *snap_data, SeqCollect
* \{ */
/* Add effect strips directly or indirectly connected to `seq_reference` to `collection`. */
static void query_strip_effects_fn(Sequence *seq_reference,
static void query_strip_effects_fn(const Scene *scene,
Sequence *seq_reference,
ListBase *seqbase,
SeqCollection *collection)
{
@ -103,7 +106,7 @@ static void query_strip_effects_fn(Sequence *seq_reference,
/* Find all strips connected to `seq_reference`. */
LISTBASE_FOREACH (Sequence *, seq_test, seqbase) {
if (SEQ_relation_is_effect_of_strip(seq_test, seq_reference)) {
query_strip_effects_fn(seq_test, seqbase, collection);
query_strip_effects_fn(scene, seq_test, seqbase, collection);
}
}
}
@ -145,7 +148,7 @@ static SeqCollection *query_snap_targets(Scene *scene,
/* Effects will always change position with strip to which they are connected and they don't have
* to be selected. Remove such strips from `snap_targets` collection. */
SeqCollection *snap_sources_temp = SEQ_collection_duplicate(snap_sources);
SEQ_collection_expand(seqbase, snap_sources_temp, query_strip_effects_fn);
SEQ_collection_expand(scene, seqbase, snap_sources_temp, query_strip_effects_fn);
SeqCollection *snap_sources_effects = seq_collection_extract_effects(snap_sources_temp);
SEQ_collection_exclude(snap_targets, snap_sources_effects);
SEQ_collection_free(snap_sources_temp);
@ -194,24 +197,25 @@ static void seq_snap_target_points_build(Scene *scene,
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, snap_targets) {
snap_data->target_snap_points[i] = SEQ_time_left_handle_frame_get(seq);
snap_data->target_snap_points[i + 1] = SEQ_time_right_handle_frame_get(seq);
snap_data->target_snap_points[i] = SEQ_time_left_handle_frame_get(scene, seq);
snap_data->target_snap_points[i + 1] = SEQ_time_right_handle_frame_get(scene, seq);
i += 2;
if (snap_mode & SEQ_SNAP_TO_STRIP_HOLD) {
int content_start = min_ii(SEQ_time_right_handle_frame_get(seq), seq->start);
int content_end = max_ii(SEQ_time_left_handle_frame_get(seq), seq->start + seq->len);
int content_start = min_ii(SEQ_time_right_handle_frame_get(scene, seq), seq->start);
int content_end = max_ii(SEQ_time_left_handle_frame_get(scene, seq), seq->start + seq->len);
/* Effects and single image strips produce incorrect content length. Skip these strips. */
if ((seq->type & SEQ_TYPE_EFFECT) != 0 || seq->len == 1) {
content_start = SEQ_time_left_handle_frame_get(seq);
content_end = SEQ_time_right_handle_frame_get(seq);
content_start = SEQ_time_left_handle_frame_get(scene, seq);
content_end = SEQ_time_right_handle_frame_get(scene, seq);
}
CLAMP(content_start,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(seq));
CLAMP(
content_end, SEQ_time_left_handle_frame_get(seq), SEQ_time_right_handle_frame_get(seq));
SEQ_time_left_handle_frame_get(scene, seq),
SEQ_time_right_handle_frame_get(scene, seq));
CLAMP(content_end,
SEQ_time_left_handle_frame_get(scene, seq),
SEQ_time_right_handle_frame_get(scene, seq));
snap_data->target_snap_points[i] = content_start;
snap_data->target_snap_points[i + 1] = content_end;
@ -260,7 +264,7 @@ TransSeqSnapData *transform_snap_sequencer_data_alloc(const TransInfo *t)
/* Build arrays of snap points. */
seq_snap_source_points_alloc(snap_data, snap_sources);
seq_snap_source_points_build(snap_data, snap_sources);
seq_snap_source_points_build(scene, snap_data, snap_sources);
SEQ_collection_free(snap_sources);
short snap_mode = t->tsnap.mode;

View File

@ -151,17 +151,17 @@ typedef struct Sequence {
* Start frame of contents of strip in absolute frame coordinates.
* For metastrips start of first strip startdisp.
*/
int start;
float start;
/**
* Frames after the first frame where display starts,
* frames before the last frame where display ends.
*/
int startofs, endofs;
float startofs, endofs;
/**
* Frames that use the first frame before data begins,
* frames that use the last frame after data ends.
*/
int startstill, endstill;
float startstill, endstill;
/** Machine: the strip channel */
int machine;
int _pad3;
@ -213,7 +213,7 @@ typedef struct Sequence {
float volume;
/** Pitch (-0.1..10), pan -2..2. */
float pitch, pan;
float pitch DNA_DEPRECATED, pan;
float strobe;
/** Struct pointer for effect settings. */
@ -249,6 +249,11 @@ typedef struct Sequence {
/* modifiers */
ListBase modifiers;
/* Playback rate of strip content in frames per second. */
float media_playback_rate;
/* Multiply strip playback speed. */
float speed_factor;
SequenceRuntime runtime;
} Sequence;
@ -563,7 +568,7 @@ enum {
SEQ_LOCK = (1 << 14),
SEQ_USE_PROXY = (1 << 15),
SEQ_IGNORE_CHANNEL_LOCK = (1 << 16),
SEQ_FLAG_UNUSED_22 = (1 << 17), /* cleared */
SEQ_AUTO_PLAYBACK_RATE = (1 << 17),
SEQ_FLAG_UNUSED_18 = (1 << 18), /* cleared */
SEQ_FLAG_UNUSED_19 = (1 << 19), /* cleared */
SEQ_FLAG_UNUSED_21 = (1 << 21), /* cleared */

View File

@ -292,7 +292,7 @@ static void do_sequence_frame_change_update(Scene *scene, Sequence *seq)
{
ListBase *seqbase = SEQ_get_seqbase_by_seq(scene, seq);
if (SEQ_transform_test_overlap(seqbase, seq)) {
if (SEQ_transform_test_overlap(scene, seqbase, seq)) {
SEQ_transform_seqbase_shuffle(seqbase, seq, scene);
}
@ -314,15 +314,17 @@ static void rna_Sequence_frame_change_update(Main *UNUSED(bmain),
static int rna_Sequence_frame_final_start_get(PointerRNA *ptr)
{
return SEQ_time_left_handle_frame_get((Sequence *)ptr->data);
Scene *scene = (Scene *)ptr->owner_id;
return SEQ_time_left_handle_frame_get(scene, (Sequence *)ptr->data);
}
static int rna_Sequence_frame_final_end_get(PointerRNA *ptr)
{
return SEQ_time_right_handle_frame_get((Sequence *)ptr->data);
Scene *scene = (Scene *)ptr->owner_id;
return SEQ_time_right_handle_frame_get(scene, (Sequence *)ptr->data);
}
static void rna_Sequence_start_frame_final_set(PointerRNA *ptr, int value)
static void rna_Sequence_start_frame_final_set(PointerRNA *ptr, float value)
{
Sequence *seq = (Sequence *)ptr->data;
Scene *scene = (Scene *)ptr->owner_id;
@ -354,7 +356,7 @@ static void rna_Sequence_start_frame_set(PointerRNA *ptr, int value)
SEQ_relations_invalidate_cache_composite(scene, seq);
}
static void rna_Sequence_frame_offset_start_set(PointerRNA *ptr, int value)
static void rna_Sequence_frame_offset_start_set(PointerRNA *ptr, float value)
{
Sequence *seq = (Sequence *)ptr->data;
Scene *scene = (Scene *)ptr->owner_id;
@ -363,7 +365,7 @@ static void rna_Sequence_frame_offset_start_set(PointerRNA *ptr, int value)
seq->startofs = value;
}
static void rna_Sequence_frame_offset_end_set(PointerRNA *ptr, int value)
static void rna_Sequence_frame_offset_end_set(PointerRNA *ptr, float value)
{
Sequence *seq = (Sequence *)ptr->data;
Scene *scene = (Scene *)ptr->owner_id;
@ -413,7 +415,7 @@ static void rna_Sequence_anim_startofs_final_range(
}
static void rna_Sequence_frame_offset_start_range(
PointerRNA *ptr, int *min, int *max, int *UNUSED(softmin), int *UNUSED(softmax))
PointerRNA *ptr, float *min, float *max, float *UNUSED(softmin), float *UNUSED(softmax))
{
Sequence *seq = (Sequence *)ptr->data;
*min = ELEM(seq->type, SEQ_TYPE_SOUND_RAM, SEQ_TYPE_SOUND_HD) ? 0 : INT_MIN;
@ -421,7 +423,7 @@ static void rna_Sequence_frame_offset_start_range(
}
static void rna_Sequence_frame_offset_end_range(
PointerRNA *ptr, int *min, int *max, int *UNUSED(softmin), int *UNUSED(softmax))
PointerRNA *ptr, float *min, float *max, float *UNUSED(softmin), float *UNUSED(softmax))
{
Sequence *seq = (Sequence *)ptr->data;
*min = ELEM(seq->type, SEQ_TYPE_SOUND_RAM, SEQ_TYPE_SOUND_HD) ? 0 : INT_MIN;
@ -433,7 +435,7 @@ static void rna_Sequence_frame_length_set(PointerRNA *ptr, int value)
Sequence *seq = (Sequence *)ptr->data;
Scene *scene = (Scene *)ptr->owner_id;
SEQ_time_right_handle_frame_set(scene, seq, SEQ_time_left_handle_frame_get(seq) + value);
SEQ_time_right_handle_frame_set(scene, seq, SEQ_time_left_handle_frame_get(scene, seq) + value);
do_sequence_frame_change_update(scene, seq);
SEQ_relations_invalidate_cache_composite(scene, seq);
}
@ -441,7 +443,8 @@ static void rna_Sequence_frame_length_set(PointerRNA *ptr, int value)
static int rna_Sequence_frame_length_get(PointerRNA *ptr)
{
Sequence *seq = (Sequence *)ptr->data;
return SEQ_time_right_handle_frame_get(seq) - SEQ_time_left_handle_frame_get(seq);
Scene *scene = (Scene *)ptr->owner_id;
return SEQ_time_right_handle_frame_get(scene, seq) - SEQ_time_left_handle_frame_get(scene, seq);
}
static int rna_Sequence_frame_editable(PointerRNA *ptr, const char **UNUSED(r_info))
@ -461,7 +464,7 @@ static void rna_Sequence_channel_set(PointerRNA *ptr, int value)
const int channel_delta = (value >= seq->machine) ? 1 : -1;
seq->machine = value;
if (SEQ_transform_test_overlap(seqbase, seq)) {
if (SEQ_transform_test_overlap(scene, seqbase, seq)) {
SEQ_transform_seqbase_shuffle_ex(seqbase, seq, scene, channel_delta);
}
SEQ_relations_invalidate_cache_composite(scene, seq);
@ -815,7 +818,20 @@ static int rna_Sequence_proxy_filepath_length(PointerRNA *ptr)
static void rna_Sequence_audio_update(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr)
{
DEG_id_tag_update(ptr->owner_id, ID_RECALC_SEQUENCER_STRIPS);
DEG_id_tag_update(ptr->owner_id, ID_RECALC_SEQUENCER_STRIPS | ID_RECALC_AUDIO);
}
static void rna_Sequence_speed_factor_update(Main *bmain, Scene *scene, PointerRNA *ptr)
{
SEQ_cache_cleanup(scene);
rna_Sequence_audio_update(bmain, scene, ptr);
}
static void rna_Sequence_speed_factor_set(PointerRNA *ptr, float value)
{
Sequence *seq = (Sequence *)ptr->data;
Scene *scene = (Scene *)ptr->owner_id;
SEQ_time_speed_factor_set(scene, seq, value);
}
static void rna_Sequence_pan_range(
@ -1969,11 +1985,12 @@ static void rna_def_sequence(BlenderRNA *brna)
RNA_def_property_ui_text(
prop, "Length", "The length of the contents of this strip before the handles are applied");
prop = RNA_def_property(srna, "frame_start", PROP_INT, PROP_TIME);
RNA_def_property_int_sdna(prop, NULL, "start");
prop = RNA_def_property(srna, "frame_start", PROP_FLOAT, PROP_TIME);
RNA_def_property_float_sdna(prop, NULL, "start");
RNA_def_property_clear_flag(prop, PROP_ANIMATABLE);
RNA_def_property_ui_text(prop, "Start Frame", "X position where the strip begins");
RNA_def_property_int_funcs(
RNA_def_property_ui_range(prop, MINFRAME, MAXFRAME, 3, 0);
RNA_def_property_float_funcs(
prop, NULL, "rna_Sequence_start_frame_set", NULL); /* overlap tests and calc_seq_disp */
RNA_def_property_editable_func(prop, "rna_Sequence_frame_editable");
RNA_def_property_update(
@ -2006,19 +2023,21 @@ static void rna_def_sequence(BlenderRNA *brna)
RNA_def_property_update(
prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_invalidate_preprocessed_update");
prop = RNA_def_property(srna, "frame_offset_start", PROP_INT, PROP_TIME);
RNA_def_property_int_sdna(prop, NULL, "startofs");
prop = RNA_def_property(srna, "frame_offset_start", PROP_FLOAT, PROP_TIME);
RNA_def_property_float_sdna(prop, NULL, "startofs");
// RNA_def_property_clear_flag(prop, PROP_EDITABLE); /* overlap tests */
RNA_def_property_ui_text(prop, "Start Offset", "");
RNA_def_property_int_funcs(
RNA_def_property_ui_range(prop, MINFRAME, MAXFRAME, 3, 0);
RNA_def_property_float_funcs(
prop, NULL, "rna_Sequence_frame_offset_start_set", "rna_Sequence_frame_offset_start_range");
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_frame_change_update");
prop = RNA_def_property(srna, "frame_offset_end", PROP_INT, PROP_TIME);
RNA_def_property_int_sdna(prop, NULL, "endofs");
prop = RNA_def_property(srna, "frame_offset_end", PROP_FLOAT, PROP_TIME);
RNA_def_property_float_sdna(prop, NULL, "endofs");
// RNA_def_property_clear_flag(prop, PROP_EDITABLE); /* overlap tests */
RNA_def_property_ui_text(prop, "End Offset", "");
RNA_def_property_int_funcs(
RNA_def_property_ui_range(prop, MINFRAME, MAXFRAME, 3, 0);
RNA_def_property_float_funcs(
prop, NULL, "rna_Sequence_frame_offset_end_set", "rna_Sequence_frame_offset_end_range");
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_frame_change_update");
@ -2305,6 +2324,20 @@ static void rna_def_editor(BlenderRNA *brna)
RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
}
static void rna_def_speed_factor(StructRNA *srna)
{
PropertyRNA *prop = RNA_def_property(srna, "speed_factor", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_sdna(prop, NULL, "speed_factor");
RNA_def_property_float_default(prop, 1.0f);
RNA_def_property_range(prop, 0.1f, FLT_MAX);
RNA_def_property_ui_range(prop, 1.0f, 100.0f, 10.0, 3);
RNA_def_property_clear_flag(prop, PROP_ANIMATABLE);
RNA_def_property_ui_text(prop, "Speed Factor", "Multiply playback speed");
RNA_def_property_float_funcs(
prop, NULL, "rna_Sequence_speed_factor_set", NULL); /* overlap test */
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_speed_factor_update");
}
static void rna_def_filter_video(StructRNA *srna)
{
PropertyRNA *prop;
@ -2537,6 +2570,7 @@ static void rna_def_image(BlenderRNA *brna)
rna_def_proxy(srna);
rna_def_input(srna);
rna_def_color_management(srna);
rna_def_speed_factor(srna);
}
static void rna_def_meta(BlenderRNA *brna)
@ -2568,6 +2602,7 @@ static void rna_def_meta(BlenderRNA *brna)
rna_def_filter_video(srna);
rna_def_proxy(srna);
rna_def_input(srna);
rna_def_speed_factor(srna);
}
static void rna_def_scene(BlenderRNA *brna)
@ -2616,6 +2651,7 @@ static void rna_def_scene(BlenderRNA *brna)
rna_def_proxy(srna);
rna_def_input(srna);
rna_def_movie_types(srna);
rna_def_speed_factor(srna);
}
static void rna_def_movie(BlenderRNA *brna)
@ -2699,6 +2735,7 @@ static void rna_def_movie(BlenderRNA *brna)
rna_def_input(srna);
rna_def_color_management(srna);
rna_def_movie_types(srna);
rna_def_speed_factor(srna);
}
static void rna_def_movieclip(BlenderRNA *brna)
@ -2726,6 +2763,7 @@ static void rna_def_movieclip(BlenderRNA *brna)
rna_def_filter_video(srna);
rna_def_input(srna);
rna_def_movie_types(srna);
rna_def_speed_factor(srna);
}
static void rna_def_mask(BlenderRNA *brna)
@ -2744,6 +2782,7 @@ static void rna_def_mask(BlenderRNA *brna)
rna_def_filter_video(srna);
rna_def_input(srna);
rna_def_speed_factor(srna);
}
static void rna_def_sound(BlenderRNA *brna)
@ -2770,13 +2809,6 @@ static void rna_def_sound(BlenderRNA *brna)
RNA_def_property_translation_context(prop, BLT_I18NCONTEXT_ID_SOUND);
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_audio_update");
prop = RNA_def_property(srna, "pitch", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_sdna(prop, NULL, "pitch");
RNA_def_property_range(prop, 0.1f, 10.0f);
RNA_def_property_ui_text(prop, "Pitch", "Playback pitch of the sound");
RNA_def_property_translation_context(prop, BLT_I18NCONTEXT_ID_SOUND);
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, "rna_Sequence_audio_update");
prop = RNA_def_property(srna, "pan", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_sdna(prop, NULL, "pan");
RNA_def_property_range(prop, -FLT_MAX, FLT_MAX);
@ -2792,6 +2824,7 @@ static void rna_def_sound(BlenderRNA *brna)
RNA_def_property_update(prop, NC_SCENE | ND_SEQUENCER, NULL);
rna_def_input(srna);
rna_def_speed_factor(srna);
}
static void rna_def_effect(BlenderRNA *brna)

View File

@ -49,13 +49,21 @@
# include "WM_api.h"
static void rna_Sequence_swap_internal(Sequence *seq_self,
static StripElem *rna_Sequence_strip_elem_from_frame(ID *id, Sequence *self, int timeline_frame)
{
Scene *scene = (Scene *)id;
return SEQ_render_give_stripelem(scene, self, timeline_frame);
}
static void rna_Sequence_swap_internal(ID *id,
Sequence *seq_self,
ReportList *reports,
Sequence *seq_other)
{
const char *error_msg;
Scene *scene = (Scene *)id;
if (SEQ_edit_sequence_swap(seq_self, seq_other, &error_msg) == 0) {
if (SEQ_edit_sequence_swap(scene, seq_self, seq_other, &error_msg) == 0) {
BKE_report(reports, RPT_ERROR, error_msg);
}
}
@ -247,7 +255,7 @@ static Sequence *rna_Sequences_new_image(ID *id,
char dir[FILE_MAX], filename[FILE_MAX];
BLI_split_dirfile(file, dir, filename, sizeof(dir), sizeof(filename));
SEQ_add_image_set_directory(seq, dir);
SEQ_add_image_load_file(seq, 0, filename);
SEQ_add_image_load_file(scene, seq, 0, filename);
SEQ_add_image_init_alpha_mode(seq);
DEG_relations_tag_update(bmain);
@ -647,7 +655,8 @@ void RNA_api_sequence_strip(StructRNA *srna)
{0, NULL, 0, NULL, NULL},
};
func = RNA_def_function(srna, "strip_elem_from_frame", "SEQ_render_give_stripelem");
func = RNA_def_function(srna, "strip_elem_from_frame", "rna_Sequence_strip_elem_from_frame");
RNA_def_function_flag(func, FUNC_USE_SELF_ID);
RNA_def_function_ui_description(func, "Return the strip element from a given frame or None");
parm = RNA_def_int(func,
"frame",
@ -664,6 +673,7 @@ void RNA_api_sequence_strip(StructRNA *srna)
RNA_def_pointer(func, "elem", "SequenceElement", "", "strip element of the current frame"));
func = RNA_def_function(srna, "swap", "rna_Sequence_swap_internal");
RNA_def_function_flag(func, FUNC_USE_REPORTS | FUNC_USE_SELF_ID);
RNA_def_function_flag(func, FUNC_USE_REPORTS);
parm = RNA_def_pointer(func, "other", "Sequence", "Other", "");
RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED);

View File

@ -50,6 +50,7 @@ typedef struct SeqLoadData {
struct Stereo3dFormat *stereo3d_format;
bool allow_invalid_file; /* Used by RNA API to create placeholder strips. */
double r_video_stream_start; /* For AV synchronization. Set by `SEQ_add_movie_strip`. */
bool adjust_playback_rate;
} SeqLoadData;
/**
@ -176,7 +177,10 @@ void SEQ_add_image_set_directory(struct Sequence *seq, char *path);
* \param strip_frame: frame index of strip to be changed
* \param filename: image filename (only filename, not complete path)
*/
void SEQ_add_image_load_file(struct Sequence *seq, size_t strip_frame, char *filename);
void SEQ_add_image_load_file(struct Scene *scene,
struct Sequence *seq,
size_t strip_frame,
char *filename);
/**
* Set image strip alpha mode
*

View File

@ -16,7 +16,10 @@ struct Main;
struct Scene;
struct Sequence;
int SEQ_edit_sequence_swap(struct Sequence *seq_a, struct Sequence *seq_b, const char **error_str);
int SEQ_edit_sequence_swap(struct Scene *scene,
struct Sequence *seq_a,
struct Sequence *seq_b,
const char **error_str);
/**
* Move sequence to seqbase.
*

View File

@ -55,7 +55,10 @@ struct SeqEffectHandle {
int (*early_out)(struct Sequence *seq, float fac);
/* sets the default `fac` value */
void (*get_default_fac)(struct Sequence *seq, float timeline_frame, float *fac);
void (*get_default_fac)(const struct Scene *scene,
struct Sequence *seq,
float timeline_frame,
float *fac);
/* execute the effect
* sequence effects are only required to either support

View File

@ -157,9 +157,11 @@ void SEQ_collection_exclude(SeqCollection *collection, SeqCollection *exclude_el
* \param collection: SeqCollection to be expanded
* \param seq_query_func: query function callback
*/
void SEQ_collection_expand(struct ListBase *seqbase,
void SEQ_collection_expand(const struct Scene *scene,
struct ListBase *seqbase,
SeqCollection *collection,
void seq_query_func(struct Sequence *seq_reference,
void seq_query_func(const struct Scene *scene,
struct Sequence *seq_reference,
struct ListBase *seqbase,
SeqCollection *collection));
/**
@ -171,8 +173,10 @@ void SEQ_collection_expand(struct ListBase *seqbase,
* \return strip collection
*/
SeqCollection *SEQ_query_by_reference(struct Sequence *seq_reference,
const struct Scene *scene,
struct ListBase *seqbase,
void seq_query_func(struct Sequence *seq_reference,
void seq_query_func(const struct Scene *scene,
struct Sequence *seq_reference,
struct ListBase *seqbase,
SeqCollection *collection));
/**
@ -211,7 +215,8 @@ SeqCollection *SEQ_query_all_strips_recursive(ListBase *seqbase);
* \param displayed_channel: viewed channel. when set to 0, no channel filter is applied
* \return strip collection
*/
SeqCollection *SEQ_query_rendered_strips(ListBase *channels,
SeqCollection *SEQ_query_rendered_strips(const struct Scene *scene,
ListBase *channels,
ListBase *seqbase,
int timeline_frame,
int displayed_channel);
@ -224,7 +229,8 @@ SeqCollection *SEQ_query_rendered_strips(ListBase *channels,
* \param seqbase: ListBase in which strips are queried
* \param collection: collection to be filled
*/
void SEQ_query_strip_effect_chain(struct Sequence *seq_reference,
void SEQ_query_strip_effect_chain(const struct Scene *scene,
struct Sequence *seq_reference,
struct ListBase *seqbase,
SeqCollection *collection);
void SEQ_filter_selected_strips(SeqCollection *collection);

View File

@ -79,20 +79,23 @@ struct ImBuf *SEQ_get_thumbnail(const struct SeqRenderData *context,
/**
* Get frame for first thumbnail.
*/
float SEQ_render_thumbnail_first_frame_get(struct Sequence *seq,
float SEQ_render_thumbnail_first_frame_get(const struct Scene *scene,
struct Sequence *seq,
float frame_step,
struct rctf *view_area);
/**
* Get frame for first thumbnail.
*/
float SEQ_render_thumbnail_next_frame_get(struct Sequence *seq,
float SEQ_render_thumbnail_next_frame_get(const struct Scene *scene,
struct Sequence *seq,
float last_frame,
float frame_step);
/**
* Get frame step for equally spaced thumbnails. These thumbnails should always be present in
* memory, so they can be used when zooming.
*/
int SEQ_render_thumbnails_guaranteed_set_frame_step_get(const struct Sequence *seq);
int SEQ_render_thumbnails_guaranteed_set_frame_step_get(const struct Scene *scene,
const struct Sequence *seq);
/**
* Render set of evenly spaced thumbnails that are drawn when zooming..
*/
@ -112,7 +115,9 @@ void SEQ_render_new_render_data(struct Main *bmain,
int for_render,
SeqRenderData *r_context);
int SEQ_render_evaluate_frame(struct ListBase *seqbase, int timeline_frame);
struct StripElem *SEQ_render_give_stripelem(struct Sequence *seq, int timeline_frame);
struct StripElem *SEQ_render_give_stripelem(const struct Scene *scene,
struct Sequence *seq,
int timeline_frame);
void SEQ_render_imbuf_from_sequencer_space(struct Scene *scene, struct ImBuf *ibuf);
void SEQ_render_pixel_from_sequencer_space_v4(struct Scene *scene, float pixel[4]);

View File

@ -20,6 +20,7 @@ void SEQ_sound_update_bounds_all(struct Scene *scene);
void SEQ_sound_update_bounds(struct Scene *scene, struct Sequence *seq);
void SEQ_sound_update(struct Scene *scene, struct bSound *sound);
void SEQ_sound_update_length(struct Main *bmain, struct Scene *scene);
float SEQ_sound_pitch_get(const struct Scene *scene, const struct Sequence *seq);
#ifdef __cplusplus
}

View File

@ -29,7 +29,9 @@ void SEQ_timeline_init_boundbox(const struct Scene *scene, struct rctf *rect);
* \param seqbase: ListBase in which strips are located
* \param rect: output parameter to be filled with strips' boundaries
*/
void SEQ_timeline_expand_boundbox(const struct ListBase *seqbase, struct rctf *rect);
void SEQ_timeline_expand_boundbox(const struct Scene *scene,
const struct ListBase *seqbase,
struct rctf *rect);
/**
* Define boundary rectangle of sequencer timeline and fill in rect data
*
@ -56,15 +58,23 @@ int SEQ_time_find_next_prev_edit(struct Scene *scene,
* \param timeline_frame: absolute frame position
* \return true if strip intersects with timeline frame.
*/
bool SEQ_time_strip_intersects_frame(const struct Sequence *seq, int timeline_frame);
bool SEQ_time_has_still_frames(const struct Sequence *seq);
bool SEQ_time_has_left_still_frames(const struct Sequence *seq);
bool SEQ_time_has_right_still_frames(const struct Sequence *seq);
bool SEQ_time_strip_intersects_frame(const struct Scene *scene,
const struct Sequence *seq,
int timeline_frame);
bool SEQ_time_has_still_frames(const struct Scene *scene, const struct Sequence *seq);
bool SEQ_time_has_left_still_frames(const struct Scene *scene, const struct Sequence *seq);
bool SEQ_time_has_right_still_frames(const struct Scene *scene, const struct Sequence *seq);
int SEQ_time_left_handle_frame_get(const struct Sequence *seq);
int SEQ_time_right_handle_frame_get(const struct Sequence *seq);
int SEQ_time_left_handle_frame_get(const struct Scene *scene, const struct Sequence *seq);
int SEQ_time_right_handle_frame_get(const struct Scene *scene, const struct Sequence *seq);
void SEQ_time_left_handle_frame_set(const struct Scene *scene, struct Sequence *seq, int val);
void SEQ_time_right_handle_frame_set(const struct Scene *scene, struct Sequence *seq, int val);
int SEQ_time_strip_length_get(const struct Scene *scene, const struct Sequence *seq);
void SEQ_time_speed_factor_set(const struct Scene *scene,
struct Sequence *seq,
const float speed_factor);
float SEQ_time_start_frame_get(const struct Sequence *seq);
void SEQ_time_start_frame_set(const struct Scene *scene, struct Sequence *seq, int timeline_frame);
void SEQ_time_update_meta_strip_range(const struct Scene *scene, struct Sequence *seq_meta);
#ifdef __cplusplus

View File

@ -17,14 +17,6 @@ struct Scene;
struct SeqCollection;
struct Sequence;
/**
* Use to impose limits when dragging/extending - so impossible situations don't happen.
* Can't use the #SEQ_LEFTSEL and #SEQ_LEFTSEL directly because the strip may be in a meta-strip.
*/
void SEQ_transform_handle_xlimits(const struct Scene *scene,
struct Sequence *seq,
int leftflag,
int rightflag);
bool SEQ_transform_sequence_can_be_translated(struct Sequence *seq);
/**
* Used so we can do a quick check for single image seq
@ -32,8 +24,12 @@ bool SEQ_transform_sequence_can_be_translated(struct Sequence *seq);
*/
bool SEQ_transform_single_image_check(struct Sequence *seq);
void SEQ_transform_fix_single_image_seq_offsets(const struct Scene *scene, struct Sequence *seq);
bool SEQ_transform_test_overlap(struct ListBase *seqbasep, struct Sequence *test);
bool SEQ_transform_test_overlap_seq_seq(struct Sequence *seq1, struct Sequence *seq2);
bool SEQ_transform_test_overlap(const struct Scene *scene,
struct ListBase *seqbasep,
struct Sequence *test);
bool SEQ_transform_test_overlap_seq_seq(const struct Scene *scene,
struct Sequence *seq1,
struct Sequence *seq2);
void SEQ_transform_translate_sequence(struct Scene *scene, struct Sequence *seq, int delta);
/**
* \return 0 if there weren't enough space.

View File

@ -412,8 +412,8 @@ void seq_disk_cache_invalidate(SeqDiskCache *disk_cache,
BLI_mutex_lock(&disk_cache->read_write_mutex);
start = SEQ_time_left_handle_frame_get(seq_changed) - DCACHE_IMAGES_PER_FILE;
end = SEQ_time_right_handle_frame_get(seq_changed);
start = SEQ_time_left_handle_frame_get(scene, seq_changed) - DCACHE_IMAGES_PER_FILE;
end = SEQ_time_right_handle_frame_get(scene, seq_changed);
seq_disk_cache_delete_invalid_files(disk_cache, scene, seq, invalidate_types, start, end);

View File

@ -2475,8 +2475,8 @@ static ImBuf *do_adjustment_impl(const SeqRenderData *context, Sequence *seq, fl
* 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_time_left_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(seq) - 1);
SEQ_time_left_handle_frame_get(context->scene, seq),
SEQ_time_right_handle_frame_get(context->scene, seq) - 1);
if (seq->machine > 1) {
i = seq_render_give_ibuf_seqbase(
@ -2583,13 +2583,14 @@ static int early_out_speed(Sequence *UNUSED(seq), float UNUSED(fac))
* useful to use speed effect on these strips because they can be animated. This can be done by
* using their length as is on timeline as content length. See T82698.
*/
static int seq_effect_speed_get_strip_content_length(const Sequence *seq)
static int seq_effect_speed_get_strip_content_length(Scene *scene, const Sequence *seq)
{
if ((seq->type & SEQ_TYPE_EFFECT) != 0 && SEQ_effect_get_num_inputs(seq->type) == 0) {
return SEQ_time_right_handle_frame_get(seq) - SEQ_time_left_handle_frame_get(seq);
return SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, seq);
}
return seq->len;
return SEQ_time_strip_length_get(scene, seq);
}
static FCurve *seq_effect_speed_speed_factor_curve_get(Scene *scene, Sequence *seq)
@ -2613,14 +2614,14 @@ void seq_effect_speed_rebuild_map(Scene *scene, Sequence *seq)
MEM_freeN(v->frameMap);
}
const int effect_strip_length = SEQ_time_right_handle_frame_get(seq) -
SEQ_time_left_handle_frame_get(seq);
const int effect_strip_length = SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, 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_time_left_handle_frame_get(seq) + frame_index);
target_frame += evaluate_fcurve(fcu, SEQ_time_left_handle_frame_get(scene, seq) + frame_index);
CLAMP(target_frame, 0, seq->seq1->len);
v->frameMap[frame_index] = target_frame;
}
@ -2646,7 +2647,7 @@ float seq_speed_effect_target_frame_get(Scene *scene,
}
SEQ_effect_handle_get(seq_speed); /* Ensure, that data are initialized. */
int frame_index = seq_give_frame_index(seq_speed, timeline_frame);
int frame_index = seq_give_frame_index(scene, seq_speed, timeline_frame);
SpeedControlVars *s = (SpeedControlVars *)seq_speed->effectdata;
const Sequence *source = seq_speed->seq1;
@ -2654,10 +2655,11 @@ float seq_speed_effect_target_frame_get(Scene *scene,
switch (s->speed_control_type) {
case SEQ_SPEED_STRETCH: {
/* Only right handle controls effect speed! */
const float target_content_length = seq_effect_speed_get_strip_content_length(source) -
const float target_content_length = seq_effect_speed_get_strip_content_length(scene,
source) -
source->startofs;
const float speed_effetct_length = SEQ_time_right_handle_frame_get(seq_speed) -
SEQ_time_left_handle_frame_get(seq_speed);
const float speed_effetct_length = SEQ_time_right_handle_frame_get(scene, seq_speed) -
SEQ_time_left_handle_frame_get(scene, seq_speed);
const float ratio = frame_index / speed_effetct_length;
target_frame = target_content_length * ratio;
break;
@ -2674,7 +2676,7 @@ float seq_speed_effect_target_frame_get(Scene *scene,
break;
}
case SEQ_SPEED_LENGTH:
target_frame = seq_effect_speed_get_strip_content_length(source) *
target_frame = seq_effect_speed_get_strip_content_length(scene, source) *
(s->speed_fader_length / 100.0f);
break;
case SEQ_SPEED_FRAME_NUMBER:
@ -2682,7 +2684,7 @@ float seq_speed_effect_target_frame_get(Scene *scene,
break;
}
CLAMP(target_frame, 0, seq_effect_speed_get_strip_content_length(source));
CLAMP(target_frame, 0, seq_effect_speed_get_strip_content_length(scene, source));
target_frame += seq_speed->start;
/* No interpolation. */
@ -3507,15 +3509,21 @@ static int early_out_mul_input1(Sequence *UNUSED(seq), float fac)
return EARLY_DO_EFFECT;
}
static void get_default_fac_noop(Sequence *UNUSED(seq), float UNUSED(timeline_frame), float *fac)
static void get_default_fac_noop(const Scene *UNUSED(scene),
Sequence *UNUSED(seq),
float UNUSED(timeline_frame),
float *fac)
{
*fac = 1.0f;
}
static void get_default_fac_fade(Sequence *seq, float timeline_frame, float *fac)
static void get_default_fac_fade(const Scene *scene,
Sequence *seq,
float timeline_frame,
float *fac)
{
*fac = (float)(timeline_frame - SEQ_time_left_handle_frame_get(seq));
*fac /= seq->len;
*fac = (float)(timeline_frame - SEQ_time_left_handle_frame_get(scene, seq));
*fac /= SEQ_time_strip_length_get(scene, seq);
}
static struct ImBuf *init_execution(const SeqRenderData *context,

View File

@ -133,21 +133,24 @@ static bool seq_cache_hashcmp(const void *a_, const void *b_)
seq_cmp_render_data(&a->context, &b->context));
}
static float seq_cache_timeline_frame_to_frame_index(Sequence *seq, float timeline_frame, int type)
static float seq_cache_timeline_frame_to_frame_index(Scene *scene,
Sequence *seq,
float timeline_frame,
int type)
{
/* With raw images, map timeline_frame to strip input media frame range. This means that static
* images or extended frame range of movies will only generate one cache entry. No special
* treatment in converting frame index to timeline_frame is needed. */
if (ELEM(type, SEQ_CACHE_STORE_RAW, SEQ_CACHE_STORE_THUMBNAIL)) {
return seq_give_frame_index(seq, timeline_frame);
return seq_give_frame_index(scene, seq, timeline_frame);
}
return timeline_frame - seq->start;
return timeline_frame - SEQ_time_start_frame_get(seq);
}
float seq_cache_frame_index_to_timeline_frame(Sequence *seq, float frame_index)
{
return frame_index + seq->start;
return frame_index + SEQ_time_start_frame_get(seq);
}
static SeqCache *seq_cache_get_from_scene(Scene *scene)
@ -518,7 +521,8 @@ static void seq_cache_populate_key(SeqCacheKey *key,
key->cache_owner = seq_cache_get_from_scene(context->scene);
key->seq = seq;
key->context = *context;
key->frame_index = seq_cache_timeline_frame_to_frame_index(seq, timeline_frame, type);
key->frame_index = seq_cache_timeline_frame_to_frame_index(
context->scene, seq, timeline_frame, type);
key->timeline_frame = timeline_frame;
key->type = type;
key->link_prev = NULL;
@ -558,10 +562,10 @@ void seq_cache_free_temp_cache(Scene *scene, short id, int timeline_frame)
if (key->is_temp_cache && key->task_id == id && key->type != SEQ_CACHE_STORE_THUMBNAIL) {
/* 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);
scene, key->seq, timeline_frame, key->type);
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)) {
timeline_frame > SEQ_time_right_handle_frame_get(scene, key->seq) ||
timeline_frame < SEQ_time_left_handle_frame_get(scene, key->seq)) {
BLI_ghash_remove(cache->hash, key, seq_cache_keyfree, seq_cache_valfree);
}
}
@ -636,12 +640,12 @@ void seq_cache_cleanup_sequence(Scene *scene,
seq_cache_lock(scene);
int range_start = SEQ_time_left_handle_frame_get(seq_changed);
int range_end = SEQ_time_right_handle_frame_get(seq_changed);
int range_start = SEQ_time_left_handle_frame_get(scene, seq_changed);
int range_end = SEQ_time_right_handle_frame_get(scene, seq_changed);
if (!force_seq_changed_range) {
range_start = max_ii(range_start, SEQ_time_left_handle_frame_get(seq));
range_end = min_ii(range_end, SEQ_time_right_handle_frame_get(seq));
range_start = max_ii(range_start, SEQ_time_left_handle_frame_get(scene, seq));
range_end = min_ii(range_end, SEQ_time_right_handle_frame_get(scene, seq));
}
int invalidate_composite = invalidate_types & SEQ_CACHE_STORE_FINAL_OUT;
@ -665,8 +669,8 @@ void seq_cache_cleanup_sequence(Scene *scene,
}
if (key->type & invalidate_source && key->seq == seq &&
key->timeline_frame >= SEQ_time_left_handle_frame_get(seq_changed) &&
key->timeline_frame <= SEQ_time_right_handle_frame_get(seq_changed)) {
key->timeline_frame >= SEQ_time_left_handle_frame_get(scene, seq_changed) &&
key->timeline_frame <= SEQ_time_right_handle_frame_get(scene, seq_changed)) {
if (key->link_next || key->link_prev) {
seq_cache_relink_keys(key->link_next, key->link_prev);
}
@ -697,12 +701,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 - SEQ_time_left_handle_frame_get(key->seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(key->seq);
const int frame_index = key->timeline_frame - SEQ_time_left_handle_frame_get(scene, key->seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(scene, 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 +
SEQ_time_left_handle_frame_get(key->seq);
SEQ_time_left_handle_frame_get(scene, key->seq);
if (nearest_guaranted_absolute_frame == key->timeline_frame) {
continue;

View File

@ -103,13 +103,15 @@ bool SEQ_collection_has_strip(const Sequence *seq, const SeqCollection *collecti
}
SeqCollection *SEQ_query_by_reference(Sequence *seq_reference,
const Scene *scene,
ListBase *seqbase,
void seq_query_func(Sequence *seq_reference,
void seq_query_func(const Scene *scene,
Sequence *seq_reference,
ListBase *seqbase,
SeqCollection *collection))
{
SeqCollection *collection = SEQ_collection_create(__func__);
seq_query_func(seq_reference, seqbase, collection);
seq_query_func(scene, seq_reference, seqbase, collection);
return collection;
}
bool SEQ_collection_append_strip(Sequence *seq, SeqCollection *collection)
@ -146,9 +148,11 @@ void SEQ_collection_exclude(SeqCollection *collection, SeqCollection *exclude_el
SEQ_collection_free(exclude_elements);
}
void SEQ_collection_expand(ListBase *seqbase,
void SEQ_collection_expand(const Scene *scene,
ListBase *seqbase,
SeqCollection *collection,
void seq_query_func(Sequence *seq_reference,
void seq_query_func(const Scene *scene,
Sequence *seq_reference,
ListBase *seqbase,
SeqCollection *collection))
{
@ -157,7 +161,8 @@ void SEQ_collection_expand(ListBase *seqbase,
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, collection) {
SEQ_collection_merge(query_matches, SEQ_query_by_reference(seq, seqbase, seq_query_func));
SEQ_collection_merge(query_matches,
SEQ_query_by_reference(seq, scene, seqbase, seq_query_func));
}
/* Merge all expanded results in provided SeqIteratorCollection. */
@ -219,12 +224,14 @@ SeqCollection *SEQ_query_selected_strips(ListBase *seqbase)
return collection;
}
static SeqCollection *query_strips_at_frame(ListBase *seqbase, const int timeline_frame)
static SeqCollection *query_strips_at_frame(const Scene *scene,
ListBase *seqbase,
const int timeline_frame)
{
SeqCollection *collection = SEQ_collection_create(__func__);
LISTBASE_FOREACH (Sequence *, seq, seqbase) {
if (SEQ_time_strip_intersects_frame(seq, timeline_frame)) {
if (SEQ_time_strip_intersects_frame(scene, seq, timeline_frame)) {
SEQ_collection_append_strip(seq, collection);
}
}
@ -299,12 +306,13 @@ static void collection_filter_rendered_strips(ListBase *channels, SeqCollection
}
}
SeqCollection *SEQ_query_rendered_strips(ListBase *channels,
SeqCollection *SEQ_query_rendered_strips(const Scene *scene,
ListBase *channels,
ListBase *seqbase,
const int timeline_frame,
const int displayed_channel)
{
SeqCollection *collection = query_strips_at_frame(seqbase, timeline_frame);
SeqCollection *collection = query_strips_at_frame(scene, seqbase, timeline_frame);
if (displayed_channel != 0) {
collection_filter_channel_up_to_incl(collection, displayed_channel);
}
@ -324,7 +332,8 @@ SeqCollection *SEQ_query_unselected_strips(ListBase *seqbase)
return collection;
}
void SEQ_query_strip_effect_chain(Sequence *seq_reference,
void SEQ_query_strip_effect_chain(const Scene *scene,
Sequence *seq_reference,
ListBase *seqbase,
SeqCollection *collection)
{
@ -335,13 +344,13 @@ void SEQ_query_strip_effect_chain(Sequence *seq_reference,
/* Find all strips that seq_reference is connected to. */
if (seq_reference->type & SEQ_TYPE_EFFECT) {
if (seq_reference->seq1) {
SEQ_query_strip_effect_chain(seq_reference->seq1, seqbase, collection);
SEQ_query_strip_effect_chain(scene, seq_reference->seq1, seqbase, collection);
}
if (seq_reference->seq2) {
SEQ_query_strip_effect_chain(seq_reference->seq2, seqbase, collection);
SEQ_query_strip_effect_chain(scene, seq_reference->seq2, seqbase, collection);
}
if (seq_reference->seq3) {
SEQ_query_strip_effect_chain(seq_reference->seq3, seqbase, collection);
SEQ_query_strip_effect_chain(scene, seq_reference->seq3, seqbase, collection);
}
}
@ -349,7 +358,7 @@ void SEQ_query_strip_effect_chain(Sequence *seq_reference,
LISTBASE_FOREACH (Sequence *, seq_test, seqbase) {
if (seq_test->seq1 == seq_reference || seq_test->seq2 == seq_reference ||
seq_test->seq3 == seq_reference) {
SEQ_query_strip_effect_chain(seq_test, seqbase, collection);
SEQ_query_strip_effect_chain(scene, seq_test, seqbase, collection);
}
}
}

View File

@ -395,7 +395,7 @@ static bool seq_prefetch_scene_strip_is_rendered(PrefetchJob *pfjob,
{
float cfra = seq_prefetch_cfra(pfjob);
Sequence *seq_arr[MAXSEQ + 1];
int count = seq_get_shown_sequences(channels, seqbase, cfra, 0, seq_arr);
int count = seq_get_shown_sequences(pfjob->scene_eval, channels, seqbase, cfra, 0, seq_arr);
/* Iterate over rendered strips. */
for (int i = 0; i < count; i++) {

View File

@ -123,7 +123,7 @@ bool seq_proxy_get_custom_file_fname(Sequence *seq, char *name, const int view_i
return true;
}
static bool seq_proxy_get_fname(Editing *ed,
static bool seq_proxy_get_fname(Scene *scene,
Sequence *seq,
int timeline_frame,
eSpaceSeq_Proxy_RenderSize render_size,
@ -132,6 +132,7 @@ static bool seq_proxy_get_fname(Editing *ed,
{
char dir[PROXY_MAXFILE];
char suffix[24] = {'\0'};
Editing *ed = SEQ_editing_get(scene);
StripProxy *proxy = seq->strip->proxy;
if (proxy == NULL) {
@ -179,7 +180,7 @@ static bool seq_proxy_get_fname(Editing *ed,
"%s/images/%d/%s_proxy%s",
dir,
proxy_size_number,
SEQ_render_give_stripelem(seq, timeline_frame)->name,
SEQ_render_give_stripelem(scene, seq, timeline_frame)->name,
suffix);
BLI_path_abs(name, BKE_main_blendfile_path_from_global());
strcat(name, ".jpg");
@ -202,7 +203,6 @@ ImBuf *seq_proxy_fetch(const SeqRenderData *context, Sequence *seq, int timeline
char name[PROXY_MAXFILE];
StripProxy *proxy = seq->strip->proxy;
const eSpaceSeq_Proxy_RenderSize psize = context->preview_render_size;
Editing *ed = context->scene->ed;
StripAnim *sanim;
/* only use proxies, if they are enabled (even if present!) */
@ -211,9 +211,11 @@ ImBuf *seq_proxy_fetch(const SeqRenderData *context, Sequence *seq, int timeline
}
if (proxy->storage & SEQ_STORAGE_PROXY_CUSTOM_FILE) {
int frameno = (int)seq_give_frame_index(seq, timeline_frame) + seq->anim_startofs;
int frameno = (int)seq_give_frame_index(context->scene, seq, timeline_frame) +
seq->anim_startofs;
if (proxy->anim == NULL) {
if (seq_proxy_get_fname(ed, seq, timeline_frame, psize, name, context->view_id) == 0) {
if (seq_proxy_get_fname(
context->scene, seq, timeline_frame, psize, name, context->view_id) == 0) {
return NULL;
}
@ -232,7 +234,8 @@ ImBuf *seq_proxy_fetch(const SeqRenderData *context, Sequence *seq, int timeline
return IMB_anim_absolute(proxy->anim, frameno, IMB_TC_NONE, IMB_PROXY_NONE);
}
if (seq_proxy_get_fname(ed, seq, timeline_frame, psize, name, context->view_id) == 0) {
if (seq_proxy_get_fname(context->scene, seq, timeline_frame, psize, name, context->view_id) ==
0) {
return NULL;
}
@ -260,9 +263,10 @@ static void seq_proxy_build_frame(const SeqRenderData *context,
int quality;
int rectx, recty;
ImBuf *ibuf_tmp, *ibuf;
Editing *ed = context->scene->ed;
Scene *scene = context->scene;
if (!seq_proxy_get_fname(ed, seq, timeline_frame, proxy_render_size, name, context->view_id)) {
if (!seq_proxy_get_fname(
scene, seq, timeline_frame, proxy_render_size, name, context->view_id)) {
return;
}
@ -524,8 +528,8 @@ void SEQ_proxy_rebuild(SeqIndexBuildContext *context,
SeqRenderState state;
seq_render_state_init(&state);
for (timeline_frame = SEQ_time_left_handle_frame_get(seq);
timeline_frame < SEQ_time_right_handle_frame_get(seq);
for (timeline_frame = SEQ_time_left_handle_frame_get(scene, seq);
timeline_frame < SEQ_time_right_handle_frame_get(scene, seq);
timeline_frame++) {
if (context->size_flags & IMB_PROXY_25) {
seq_proxy_build_frame(&render_context, &state, seq, timeline_frame, 25, overwrite);
@ -540,8 +544,9 @@ void SEQ_proxy_rebuild(SeqIndexBuildContext *context,
seq_proxy_build_frame(&render_context, &state, seq, timeline_frame, 100, overwrite);
}
*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));
*progress = (float)(timeline_frame - SEQ_time_left_handle_frame_get(scene, seq)) /
(SEQ_time_right_handle_frame_get(scene, seq) -
SEQ_time_left_handle_frame_get(scene, seq));
*do_update = true;
if (*stop || G.is_break) {

View File

@ -233,7 +233,7 @@ void seq_render_state_init(SeqRenderState *state)
state->scene_parents = NULL;
}
StripElem *SEQ_render_give_stripelem(Sequence *seq, int timeline_frame)
StripElem *SEQ_render_give_stripelem(const Scene *scene, Sequence *seq, int timeline_frame)
{
StripElem *se = seq->strip->stripdata;
@ -242,7 +242,7 @@ StripElem *SEQ_render_give_stripelem(Sequence *seq, int timeline_frame)
* all other strips don't use this...
*/
int frame_index = (int)seq_give_frame_index(seq, timeline_frame);
int frame_index = (int)seq_give_frame_index(scene, seq, timeline_frame);
if (frame_index == -1 || se == NULL) {
return NULL;
@ -258,14 +258,15 @@ static int seq_channel_cmp_fn(const void *a, const void *b)
return (*(Sequence **)a)->machine - (*(Sequence **)b)->machine;
}
int seq_get_shown_sequences(ListBase *channels,
int seq_get_shown_sequences(const Scene *scene,
ListBase *channels,
ListBase *seqbase,
const int timeline_frame,
const int chanshown,
Sequence **r_seq_arr)
{
SeqCollection *collection = SEQ_query_rendered_strips(
channels, seqbase, timeline_frame, chanshown);
scene, channels, seqbase, timeline_frame, chanshown);
const int strip_count = BLI_gset_len(collection->set);
if (strip_count > MAXSEQ) {
@ -795,7 +796,7 @@ static ImBuf *seq_render_effect_strip_impl(const SeqRenderData *context,
}
if (seq->flag & SEQ_USE_EFFECT_DEFAULT_FADE) {
sh.get_default_fac(seq, timeline_frame, &fac);
sh.get_default_fac(scene, seq, timeline_frame, &fac);
}
else {
fcu = id_data_find_fcurve(&scene->id, seq, &RNA_Sequence, "effect_fader", 0, NULL);
@ -936,7 +937,7 @@ static ImBuf *seq_render_image_strip(const SeqRenderData *context,
char prefix[FILE_MAX];
ImBuf *ibuf = NULL;
StripElem *s_elem = SEQ_render_give_stripelem(seq, timeline_frame);
StripElem *s_elem = SEQ_render_give_stripelem(context->scene, seq, timeline_frame);
if (s_elem == NULL) {
return NULL;
}
@ -1024,7 +1025,8 @@ static ImBuf *seq_render_movie_strip_custom_file_proxy(const SeqRenderData *cont
}
}
int frameno = (int)seq_give_frame_index(seq, timeline_frame) + seq->anim_startofs;
int frameno = (int)seq_give_frame_index(context->scene, seq, timeline_frame) +
seq->anim_startofs;
return IMB_anim_absolute(proxy->anim, frameno, IMB_TC_NONE, IMB_PROXY_NONE);
}
@ -1622,7 +1624,7 @@ static ImBuf *do_render_strip_uncached(const SeqRenderData *context,
bool *r_is_proxy_image)
{
ImBuf *ibuf = NULL;
float frame_index = seq_give_frame_index(seq, timeline_frame);
float frame_index = seq_give_frame_index(context->scene, seq, timeline_frame);
int type = (seq->type & SEQ_TYPE_EFFECT) ? SEQ_TYPE_EFFECT : seq->type;
switch (type) {
case SEQ_TYPE_META: {
@ -1826,7 +1828,7 @@ static ImBuf *seq_render_strip_stack(const SeqRenderData *context,
ImBuf *out = NULL;
count = seq_get_shown_sequences(
channels, seqbasep, timeline_frame, chanshown, (Sequence **)&seq_arr);
context->scene, channels, seqbasep, timeline_frame, chanshown, (Sequence **)&seq_arr);
if (count == 0) {
return NULL;
@ -1940,7 +1942,7 @@ ImBuf *SEQ_render_give_ibuf(const SeqRenderData *context, float timeline_frame,
Sequence *seq_arr[MAXSEQ + 1];
int count;
count = seq_get_shown_sequences(channels, seqbasep, timeline_frame, chanshown, seq_arr);
count = seq_get_shown_sequences(scene, channels, seqbasep, timeline_frame, chanshown, seq_arr);
if (count) {
out = seq_cache_get(context, seq_arr[count - 1], timeline_frame, SEQ_CACHE_STORE_FINAL_OUT);
@ -1992,14 +1994,17 @@ ImBuf *SEQ_render_give_ibuf_direct(const SeqRenderData *context,
return ibuf;
}
float SEQ_render_thumbnail_first_frame_get(Sequence *seq, float frame_step, rctf *view_area)
float SEQ_render_thumbnail_first_frame_get(const Scene *scene,
Sequence *seq,
float frame_step,
rctf *view_area)
{
int first_drawable_frame = max_iii(
SEQ_time_left_handle_frame_get(seq), seq->start, view_area->xmin);
SEQ_time_left_handle_frame_get(scene, seq), seq->start, view_area->xmin);
/* First frame should correspond to handle position. */
if (first_drawable_frame == SEQ_time_left_handle_frame_get(seq)) {
return SEQ_time_left_handle_frame_get(seq);
if (first_drawable_frame == SEQ_time_left_handle_frame_get(scene, seq)) {
return SEQ_time_left_handle_frame_get(scene, seq);
}
float aligned_frame_offset = (int)((first_drawable_frame - seq->start) / frame_step) *
@ -2007,12 +2012,15 @@ float SEQ_render_thumbnail_first_frame_get(Sequence *seq, float frame_step, rctf
return seq->start + aligned_frame_offset;
}
float SEQ_render_thumbnail_next_frame_get(Sequence *seq, float last_frame, float frame_step)
float SEQ_render_thumbnail_next_frame_get(const Scene *scene,
Sequence *seq,
float last_frame,
float frame_step)
{
float next_frame = last_frame + frame_step;
/* If handle position was displayed, align next frame with `seq->start`. */
if (last_frame == SEQ_time_left_handle_frame_get(seq)) {
if (last_frame == SEQ_time_left_handle_frame_get(scene, seq)) {
next_frame = seq->start + ((int)((last_frame - seq->start) / frame_step) + 1) * frame_step;
}
@ -2086,22 +2094,23 @@ void SEQ_render_thumbnails(const SeqRenderData *context,
{
SeqRenderState state;
seq_render_state_init(&state);
const Scene *scene = context->scene;
/* 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) ?
float upper_thumb_bound = SEQ_time_has_right_still_frames(scene, seq) ?
(seq->start + seq->len) :
SEQ_time_right_handle_frame_get(seq);
SEQ_time_right_handle_frame_get(scene, seq);
upper_thumb_bound = (upper_thumb_bound > view_area->xmax) ? view_area->xmax + frame_step :
upper_thumb_bound;
float timeline_frame = SEQ_render_thumbnail_first_frame_get(seq, frame_step, view_area);
float timeline_frame = SEQ_render_thumbnail_first_frame_get(scene, seq, frame_step, view_area);
while ((timeline_frame < upper_thumb_bound) & !*stop) {
ImBuf *ibuf = seq_cache_get(
context, seq_orig, round_fl_to_int(timeline_frame), SEQ_CACHE_STORE_THUMBNAIL);
if (ibuf) {
IMB_freeImBuf(ibuf);
timeline_frame = SEQ_render_thumbnail_next_frame_get(seq, timeline_frame, frame_step);
timeline_frame = SEQ_render_thumbnail_next_frame_get(scene, seq, timeline_frame, frame_step);
continue;
}
@ -2118,14 +2127,15 @@ void SEQ_render_thumbnails(const SeqRenderData *context,
return;
}
timeline_frame = SEQ_render_thumbnail_next_frame_get(seq, timeline_frame, frame_step);
timeline_frame = SEQ_render_thumbnail_next_frame_get(scene, seq, timeline_frame, frame_step);
}
}
int SEQ_render_thumbnails_guaranteed_set_frame_step_get(const Sequence *seq)
int SEQ_render_thumbnails_guaranteed_set_frame_step_get(const Scene *scene, const Sequence *seq)
{
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_start = max_ii(SEQ_time_left_handle_frame_get(scene, seq), seq->start);
const int content_end = min_ii(SEQ_time_right_handle_frame_get(scene, 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. */
@ -2144,11 +2154,12 @@ void SEQ_render_thumbnails_base_set(const SeqRenderData *context,
{
SeqRenderState state;
seq_render_state_init(&state);
const Scene *scene = context->scene;
int timeline_frame = SEQ_time_left_handle_frame_get(seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(seq);
int timeline_frame = SEQ_time_left_handle_frame_get(scene, seq);
const int frame_step = SEQ_render_thumbnails_guaranteed_set_frame_step_get(scene, seq);
while (timeline_frame < SEQ_time_right_handle_frame_get(seq) && !*stop) {
while (timeline_frame < SEQ_time_right_handle_frame_get(scene, seq) && !*stop) {
ImBuf *ibuf = seq_cache_get(
context, seq_orig, roundf(timeline_frame), SEQ_CACHE_STORE_THUMBNAIL);
if (ibuf) {

View File

@ -44,7 +44,8 @@ struct ImBuf *seq_render_effect_execute_threaded(struct SeqEffectHandle *sh,
struct ImBuf *ibuf2,
struct ImBuf *ibuf3);
void seq_imbuf_to_sequencer_space(struct Scene *scene, struct ImBuf *ibuf, bool make_float);
int seq_get_shown_sequences(struct ListBase *channels,
int seq_get_shown_sequences(const struct Scene *scene,
struct ListBase *channels,
struct ListBase *seqbase,
int timeline_frame,
int chanshown,

View File

@ -127,9 +127,10 @@ Sequence *SEQ_sequence_alloc(ListBase *lb, int timeline_frame, int machine, int
seq->mul = 1.0;
seq->blend_opacity = 100.0;
seq->volume = 1.0f;
seq->pitch = 1.0f;
seq->scene_sound = NULL;
seq->type = type;
seq->media_playback_rate = 0.0f;
seq->speed_factor = 1.0f;
if (seq->type == SEQ_TYPE_ADJUSTMENT) {
seq->blend_mode = SEQ_TYPE_CROSS;
@ -411,8 +412,8 @@ static MetaStack *seq_meta_stack_alloc(const Scene *scene, Sequence *seq_meta)
ms->oldbasep = higher_level_meta ? &higher_level_meta->seqbase : &ed->seqbase;
ms->old_channels = higher_level_meta ? &higher_level_meta->channels : &ed->channels;
ms->disp_range[0] = SEQ_time_left_handle_frame_get(ms->parseq);
ms->disp_range[1] = SEQ_time_right_handle_frame_get(ms->parseq);
ms->disp_range[0] = SEQ_time_left_handle_frame_get(scene, ms->parseq);
ms->disp_range[1] = SEQ_time_right_handle_frame_get(scene, ms->parseq);
return ms;
}
@ -965,8 +966,9 @@ static bool seq_update_seq_cb(Sequence *seq, void *user_data)
}
BKE_sound_set_scene_sound_volume(
seq->scene_sound, seq->volume, (seq->flag & SEQ_AUDIO_VOLUME_ANIMATED) != 0);
BKE_sound_set_scene_sound_pitch(
seq->scene_sound, seq->pitch, (seq->flag & SEQ_AUDIO_PITCH_ANIMATED) != 0);
BKE_sound_set_scene_sound_pitch(seq->scene_sound,
SEQ_sound_pitch_get(scene, seq),
(seq->flag & SEQ_AUDIO_PITCH_ANIMATED) != 0);
BKE_sound_set_scene_sound_pan(
seq->scene_sound, seq->pan, (seq->flag & SEQ_AUDIO_PAN_ANIMATED) != 0);
}

View File

@ -23,6 +23,7 @@
#include "SEQ_sound.h"
#include "SEQ_time.h"
#include "sequencer.h"
#include "strip_time.h"
/* Unlike _update_sound_ funcs, these ones take info from audaspace to update sequence length! */
@ -99,8 +100,8 @@ void SEQ_sound_update_bounds(Scene *scene, Sequence *seq)
BKE_sound_move_scene_sound(scene,
seq->scene_sound,
SEQ_time_left_handle_frame_get(seq),
SEQ_time_right_handle_frame_get(seq),
SEQ_time_left_handle_frame_get(scene, seq),
SEQ_time_right_handle_frame_get(scene, seq),
startofs,
0.0);
}
@ -133,3 +134,12 @@ void SEQ_sound_update(Scene *scene, bSound *sound)
seq_update_sound_recursive(scene, &scene->ed->seqbase, sound);
}
}
float SEQ_sound_pitch_get(const Scene *scene, const Sequence *seq)
{
Sequence *meta_parent = seq_sequence_lookup_meta_by_seq(scene, seq);
if (meta_parent != NULL) {
return seq->speed_factor * SEQ_sound_pitch_get(scene, meta_parent);
}
return seq->speed_factor;
}

View File

@ -181,7 +181,7 @@ Sequence *SEQ_add_effect_strip(Scene *scene, ListBase *seqbase, struct SeqLoadDa
seq_add_set_name(scene, seq, load_data);
seq_add_generic_update(scene, seq);
seq_time_effect_range_set(seq);
seq_time_effect_range_set(scene, seq);
return seq;
}
@ -191,9 +191,10 @@ void SEQ_add_image_set_directory(Sequence *seq, char *path)
BLI_strncpy(seq->strip->dir, path, sizeof(seq->strip->dir));
}
void SEQ_add_image_load_file(Sequence *seq, size_t strip_frame, char *filename)
void SEQ_add_image_load_file(Scene *scene, Sequence *seq, size_t strip_frame, char *filename)
{
StripElem *se = SEQ_render_give_stripelem(seq, seq->start + strip_frame);
StripElem *se = SEQ_render_give_stripelem(
scene, seq, SEQ_time_start_frame_get(seq) + strip_frame);
BLI_strncpy(se->name, filename, sizeof(se->name));
}
@ -468,9 +469,19 @@ Sequence *SEQ_add_movie_strip(Main *bmain, Scene *scene, ListBase *seqbase, SeqL
orig_height = IMB_anim_get_image_height(anim_arr[0]);
SEQ_set_scale_to_fit(
seq, orig_width, orig_height, scene->r.xsch, scene->r.ysch, load_data->fit_method);
short frs_sec;
float frs_sec_base;
if (IMB_anim_get_fps(anim_arr[0], &frs_sec, &frs_sec_base, true)) {
seq->media_playback_rate = (float)frs_sec / frs_sec_base;
}
}
seq->len = MAX2(1, seq->len);
if (load_data->adjust_playback_rate) {
seq->flag |= SEQ_AUTO_PLAYBACK_RATE;
}
BLI_strncpy(seq->strip->colorspace_settings.name,
colorspace,
sizeof(seq->strip->colorspace_settings.name));
@ -511,8 +522,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) */
prev_startdisp = SEQ_time_left_handle_frame_get(seq);
prev_enddisp = SEQ_time_right_handle_frame_get(seq);
prev_startdisp = SEQ_time_left_handle_frame_get(scene, seq);
prev_enddisp = SEQ_time_right_handle_frame_get(scene, seq);
}
switch (seq->type) {

View File

@ -37,11 +37,11 @@
#include "SEQ_transform.h"
#include "SEQ_utils.h"
int SEQ_edit_sequence_swap(Sequence *seq_a, Sequence *seq_b, const char **error_str)
int SEQ_edit_sequence_swap(Scene *scene, Sequence *seq_a, Sequence *seq_b, const char **error_str)
{
char name[sizeof(seq_a->name)];
if (seq_a->len != seq_b->len) {
if (SEQ_time_strip_length_get(scene, seq_a) != SEQ_time_strip_length_get(scene, seq_b)) {
*error_str = N_("Strips must be the same length");
return 0;
}
@ -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);
seq_time_effect_range_set(seq_a);
seq_time_effect_range_set(seq_b);
seq_time_effect_range_set(scene, seq_a);
seq_time_effect_range_set(scene, seq_b);
return 1;
}
@ -203,7 +203,7 @@ bool SEQ_edit_move_strip_to_seqbase(Scene *scene,
SEQ_relations_invalidate_cache_preprocessed(scene, seq);
/* Update meta. */
if (SEQ_transform_test_overlap(dst_seqbase, seq)) {
if (SEQ_transform_test_overlap(scene, dst_seqbase, seq)) {
SEQ_transform_seqbase_shuffle(dst_seqbase, seq, scene);
}
@ -246,7 +246,7 @@ bool SEQ_edit_move_strip_to_meta(Scene *scene,
SeqCollection *collection = SEQ_collection_create(__func__);
SEQ_collection_append_strip(src_seq, collection);
SEQ_collection_expand(seqbase, collection, SEQ_query_strip_effect_chain);
SEQ_collection_expand(scene, seqbase, collection, SEQ_query_strip_effect_chain);
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, collection) {
@ -259,77 +259,58 @@ bool SEQ_edit_move_strip_to_meta(Scene *scene,
return true;
}
static void seq_split_set_left_hold_offset(const Scene *scene, Sequence *seq, int timeline_frame)
static void seq_split_set_left_hold_offset(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(scene, seq, timeline_frame);
seq->start = timeline_frame - 1;
seq->anim_endofs += SEQ_time_strip_length_get(scene, seq) - 1;
seq->startstill = timeline_frame - seq->startdisp - 1;
seq->endstill = 0;
}
/* Adjust within range of strip contents. */
else if ((timeline_frame >= seq->start) && (timeline_frame <= (seq->start + seq->len))) {
else if ((timeline_frame >= seq->start) &&
(timeline_frame <= (seq->start + SEQ_time_strip_length_get(scene, seq)))) {
seq->endofs = 0;
seq->endstill = 0;
seq->anim_endofs += (seq->start + SEQ_time_strip_length_get(scene, seq)) - timeline_frame;
}
/* Adjust within range of extended stillframes after strip. */
else if ((seq->start + SEQ_time_strip_length_get(scene, seq)) < timeline_frame) {
seq->endstill = timeline_frame - seq->start - SEQ_time_strip_length_get(scene, seq);
}
}
static void seq_split_set_right_hold_offset(Scene *scene, Sequence *seq, int timeline_frame)
{
/* Adjust within range of extended stillframes before strip. */
if (timeline_frame < seq->start) {
seq->startstill = seq->start - timeline_frame;
}
/* Adjust within range of strip contents. */
else if ((timeline_frame >= seq->start) &&
(timeline_frame <= (seq->start + SEQ_time_strip_length_get(scene, seq)))) {
seq->anim_startofs += timeline_frame - seq->start;
seq->start = timeline_frame;
seq->startstill = 0;
seq->startofs = 0;
}
/* Adjust within range of extended stillframes after strip. */
else if ((seq->start + seq->len) < timeline_frame) {
const int right_handle_backup = SEQ_time_right_handle_frame_get(seq);
seq->start += timeline_frame - seq->start;
seq->anim_startofs += seq->len - 1;
seq->len = 1;
SEQ_time_left_handle_frame_set(scene, seq, timeline_frame);
SEQ_time_right_handle_frame_set(scene, seq, right_handle_backup);
else if ((seq->start + SEQ_time_strip_length_get(scene, seq)) < timeline_frame) {
seq->start = timeline_frame;
seq->startofs = 0;
seq->anim_startofs += SEQ_time_strip_length_get(scene, seq) - 1;
seq->endstill = seq->enddisp - timeline_frame - 1;
seq->startstill = 0;
}
}
static void seq_split_set_right_hold_offset(const Scene *scene, Sequence *seq, int timeline_frame)
static bool seq_edit_split_effect_intersect_check(const Scene *scene,
const Sequence *seq,
const 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(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))) {
seq->anim_endofs += seq->start + seq->len - timeline_frame;
seq->endofs = 0;
}
/* Adjust within range of extended stillframes after strip. */
else if ((seq->start + seq->len) < timeline_frame) {
SEQ_time_right_handle_frame_set(scene, seq, 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) {
const int content_offset = seq->start - timeline_frame + 1;
seq->start = timeline_frame - 1;
seq->startofs += content_offset;
}
SEQ_time_right_handle_frame_set(scene, seq, 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) {
const int content_offset = timeline_frame - (seq->start + seq->len) + 1;
seq->start += content_offset;
seq->endofs += content_offset;
}
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_time_left_handle_frame_get(seq) &&
timeline_frame < SEQ_time_right_handle_frame_get(seq);
return timeline_frame > SEQ_time_left_handle_frame_get(scene, seq) &&
timeline_frame < SEQ_time_right_handle_frame_get(scene, seq);
}
static void seq_edit_split_handle_strip_offsets(Main *bmain,
@ -339,10 +320,10 @@ static void seq_edit_split_handle_strip_offsets(Main *bmain,
const int timeline_frame,
const eSeqSplitMethod method)
{
if (seq_edit_split_effect_intersect_check(right_seq, timeline_frame)) {
if (seq_edit_split_effect_intersect_check(scene, right_seq, timeline_frame)) {
switch (method) {
case SEQ_SPLIT_SOFT:
seq_split_set_left_offset(scene, right_seq, timeline_frame);
SEQ_time_left_handle_frame_set(scene, right_seq, timeline_frame);
break;
case SEQ_SPLIT_HARD:
seq_split_set_left_hold_offset(scene, right_seq, timeline_frame);
@ -351,10 +332,10 @@ static void seq_edit_split_handle_strip_offsets(Main *bmain,
}
}
if (seq_edit_split_effect_intersect_check(left_seq, timeline_frame)) {
if (seq_edit_split_effect_intersect_check(scene, left_seq, timeline_frame)) {
switch (method) {
case SEQ_SPLIT_SOFT:
seq_split_set_right_offset(scene, left_seq, timeline_frame);
SEQ_time_right_handle_frame_set(scene, left_seq, timeline_frame);
break;
case SEQ_SPLIT_HARD:
seq_split_set_right_hold_offset(scene, left_seq, timeline_frame);
@ -364,31 +345,40 @@ static void seq_edit_split_handle_strip_offsets(Main *bmain,
}
}
static bool seq_edit_split_effect_inputs_intersect(const Sequence *seq, const int timeline_frame)
static bool seq_edit_split_effect_inputs_intersect(const Scene *scene,
const Sequence *seq,
const int timeline_frame)
{
bool input_does_intersect = false;
if (seq->seq1) {
input_does_intersect |= seq_edit_split_effect_intersect_check(seq->seq1, timeline_frame);
input_does_intersect |= seq_edit_split_effect_intersect_check(
scene, seq->seq1, timeline_frame);
if ((seq->seq1->type & SEQ_TYPE_EFFECT) != 0) {
input_does_intersect |= seq_edit_split_effect_inputs_intersect(seq->seq1, timeline_frame);
input_does_intersect |= seq_edit_split_effect_inputs_intersect(
scene, seq->seq1, timeline_frame);
}
}
if (seq->seq2) {
input_does_intersect |= seq_edit_split_effect_intersect_check(seq->seq2, timeline_frame);
input_does_intersect |= seq_edit_split_effect_intersect_check(
scene, seq->seq2, timeline_frame);
if ((seq->seq1->type & SEQ_TYPE_EFFECT) != 0) {
input_does_intersect |= seq_edit_split_effect_inputs_intersect(seq->seq2, timeline_frame);
input_does_intersect |= seq_edit_split_effect_inputs_intersect(
scene, seq->seq2, timeline_frame);
}
}
if (seq->seq3) {
input_does_intersect |= seq_edit_split_effect_intersect_check(seq->seq3, timeline_frame);
input_does_intersect |= seq_edit_split_effect_intersect_check(
scene, seq->seq3, timeline_frame);
if ((seq->seq1->type & SEQ_TYPE_EFFECT) != 0) {
input_does_intersect |= seq_edit_split_effect_inputs_intersect(seq->seq3, timeline_frame);
input_does_intersect |= seq_edit_split_effect_inputs_intersect(
scene, seq->seq3, timeline_frame);
}
}
return input_does_intersect;
}
static bool seq_edit_split_operation_permitted_check(SeqCollection *strips,
static bool seq_edit_split_operation_permitted_check(const Scene *scene,
SeqCollection *strips,
const int timeline_frame,
const char **r_error)
{
@ -397,7 +387,7 @@ static bool seq_edit_split_operation_permitted_check(SeqCollection *strips,
if ((seq->type & SEQ_TYPE_EFFECT) == 0) {
continue;
}
if (!seq_edit_split_effect_intersect_check(seq, timeline_frame)) {
if (!seq_edit_split_effect_intersect_check(scene, seq, timeline_frame)) {
continue;
}
if (SEQ_effect_get_num_inputs(seq->type) <= 1) {
@ -407,7 +397,7 @@ static bool seq_edit_split_operation_permitted_check(SeqCollection *strips,
*r_error = "Splitting transition effect is not permitted.";
return false;
}
if (!seq_edit_split_effect_inputs_intersect(seq, timeline_frame)) {
if (!seq_edit_split_effect_inputs_intersect(scene, seq, timeline_frame)) {
*r_error = "Effect inputs don't overlap. Can not split such effect.";
return false;
}
@ -423,16 +413,16 @@ Sequence *SEQ_edit_strip_split(Main *bmain,
const eSeqSplitMethod method,
const char **r_error)
{
if (!seq_edit_split_effect_intersect_check(seq, timeline_frame)) {
if (!seq_edit_split_effect_intersect_check(scene, seq, timeline_frame)) {
return NULL;
}
/* Whole strip chain must be duplicated in order to preserve relationships. */
SeqCollection *collection = SEQ_collection_create(__func__);
SEQ_collection_append_strip(seq, collection);
SEQ_collection_expand(seqbase, collection, SEQ_query_strip_effect_chain);
SEQ_collection_expand(scene, seqbase, collection, SEQ_query_strip_effect_chain);
if (!seq_edit_split_operation_permitted_check(collection, timeline_frame, r_error)) {
if (!seq_edit_split_operation_permitted_check(scene, collection, timeline_frame, r_error)) {
SEQ_collection_free(collection);
return NULL;
}
@ -474,10 +464,10 @@ Sequence *SEQ_edit_strip_split(Main *bmain,
/* Split strips. */
while (left_seq && right_seq) {
if (SEQ_time_left_handle_frame_get(left_seq) >= timeline_frame) {
if (SEQ_time_left_handle_frame_get(scene, left_seq) >= timeline_frame) {
SEQ_edit_flag_for_removal(scene, seqbase, left_seq);
}
else if (SEQ_time_right_handle_frame_get(right_seq) <= timeline_frame) {
else if (SEQ_time_right_handle_frame_get(scene, right_seq) <= timeline_frame) {
SEQ_edit_flag_for_removal(scene, seqbase, right_seq);
}
else if (return_seq == NULL) {

View File

@ -29,6 +29,7 @@
#include "SEQ_relations.h"
#include "SEQ_sequencer.h"
#include "SEQ_time.h"
#include "SEQ_transform.h"
#include "effects.h"
#include "image_cache.h"
@ -40,15 +41,15 @@ bool SEQ_relation_is_effect_of_strip(const Sequence *effect, const Sequence *inp
}
/* check whether sequence cur depends on seq */
static bool seq_relations_check_depend(Sequence *seq, Sequence *cur)
static bool seq_relations_check_depend(const Scene *scene, Sequence *seq, Sequence *cur)
{
if (SEQ_relation_is_effect_of_strip(cur, seq)) {
return true;
}
/* sequences are not intersecting in time, assume no dependency exists between them */
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)) {
if (SEQ_time_right_handle_frame_get(scene, cur) < SEQ_time_left_handle_frame_get(scene, seq) ||
SEQ_time_left_handle_frame_get(scene, cur) > SEQ_time_right_handle_frame_get(scene, seq)) {
return false;
}
@ -78,7 +79,7 @@ static void sequence_do_invalidate_dependent(Scene *scene, Sequence *seq, ListBa
continue;
}
if (seq_relations_check_depend(seq, cur)) {
if (seq_relations_check_depend(scene, seq, cur)) {
/* Effect must be invalidated completely if they depend on invalidated seq. */
if ((cur->type & SEQ_TYPE_EFFECT) != 0) {
seq_cache_cleanup_sequence(scene, cur, seq, SEQ_CACHE_ALL_TYPES, false);
@ -249,7 +250,7 @@ void SEQ_relations_free_imbuf(Scene *scene, ListBase *seqbase, bool for_render)
SEQ_prefetch_stop(scene);
for (seq = seqbase->first; seq; seq = seq->next) {
if (for_render && SEQ_time_strip_intersects_frame(seq, CFRA)) {
if (for_render && SEQ_time_strip_intersects_frame(scene, seq, CFRA)) {
continue;
}
@ -271,13 +272,14 @@ void SEQ_relations_free_imbuf(Scene *scene, ListBase *seqbase, bool for_render)
}
}
static void sequencer_all_free_anim_ibufs(Editing *ed,
static void sequencer_all_free_anim_ibufs(const Scene *scene,
ListBase *seqbase,
int timeline_frame,
const int frame_range[2])
{
Editing *ed = SEQ_editing_get(scene);
for (Sequence *seq = seqbase->first; seq != NULL; seq = seq->next) {
if (!SEQ_time_strip_intersects_frame(seq, timeline_frame) ||
if (!SEQ_time_strip_intersects_frame(scene, seq, timeline_frame) ||
!((frame_range[0] <= timeline_frame) && (frame_range[1] > timeline_frame))) {
SEQ_relations_sequence_free_anim(seq);
}
@ -291,11 +293,11 @@ 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_time_left_handle_frame_get(seq));
meta_range[1] = min_ii(frame_range[1], SEQ_time_right_handle_frame_get(seq));
meta_range[0] = max_ii(frame_range[0], SEQ_time_left_handle_frame_get(scene, seq));
meta_range[1] = min_ii(frame_range[1], SEQ_time_right_handle_frame_get(scene, seq));
}
sequencer_all_free_anim_ibufs(ed, &seq->seqbase, timeline_frame, meta_range);
sequencer_all_free_anim_ibufs(scene, &seq->seqbase, timeline_frame, meta_range);
}
}
}
@ -308,7 +310,7 @@ void SEQ_relations_free_all_anim_ibufs(Scene *scene, int timeline_frame)
}
const int frame_range[2] = {-MAXFRAME, MAXFRAME};
sequencer_all_free_anim_ibufs(ed, &ed->seqbase, timeline_frame, frame_range);
sequencer_all_free_anim_ibufs(scene, &ed->seqbase, timeline_frame, frame_range);
}
static Sequence *sequencer_check_scene_recursion(Scene *scene, ListBase *seqbase)
@ -346,7 +348,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,
SEQ_time_left_handle_frame_get(recursive_seq));
SEQ_time_left_handle_frame_get(scene, recursive_seq));
LISTBASE_FOREACH (Sequence *, seq, &ed->seqbase) {
if (seq->type != SEQ_TYPE_SCENE && sequencer_seq_generates_image(seq)) {

View File

@ -31,14 +31,32 @@
#include "strip_time.h"
#include "utils.h"
float seq_give_frame_index(Sequence *seq, float timeline_frame)
static float seq_time_media_playback_rate_factor_get(const Scene *scene, const Sequence *seq)
{
if ((seq->flag & SEQ_AUTO_PLAYBACK_RATE) == 0) {
return 1.0f;
}
if (seq->media_playback_rate == 0.0f) {
return 1.0f;
}
float scene_playback_rate = (float)scene->r.frs_sec / scene->r.frs_sec_base;
return seq->media_playback_rate / scene_playback_rate;
}
static float seq_time_playback_rate_factor_get(const Scene *scene, const Sequence *seq)
{
return seq_time_media_playback_rate_factor_get(scene, seq) * seq->speed_factor;
}
float seq_give_frame_index(const Scene *scene, Sequence *seq, float timeline_frame)
{
float frame_index;
int sta = seq->start;
int end = seq->start + seq->len - 1;
float sta = SEQ_time_start_frame_get(seq);
float end = SEQ_time_start_frame_get(seq) + SEQ_time_strip_length_get(scene, seq) - 1;
if (seq->type & SEQ_TYPE_EFFECT) {
end = SEQ_time_right_handle_frame_get(seq);
end = SEQ_time_right_handle_frame_get(scene, seq);
}
if (end < sta) {
@ -46,29 +64,16 @@ float seq_give_frame_index(Sequence *seq, float timeline_frame)
}
if (seq->flag & SEQ_REVERSE_FRAMES) {
/* Reverse frame in this sequence. */
if (timeline_frame <= sta) {
frame_index = end - sta;
}
else if (timeline_frame >= end) {
frame_index = 0;
}
else {
frame_index = end - timeline_frame;
}
frame_index = end - timeline_frame;
}
else {
if (timeline_frame <= sta) {
frame_index = 0;
}
else if (timeline_frame >= end) {
frame_index = end - sta;
}
else {
frame_index = timeline_frame - sta;
}
frame_index = timeline_frame - sta;
}
/* Clamp frame index to strip frame range. */
frame_index = clamp_f(frame_index, 0, end - sta);
frame_index *= seq_time_playback_rate_factor_get(scene, seq);
if (seq->strobe < 1.0f) {
seq->strobe = 1.0f;
}
@ -149,14 +154,14 @@ void SEQ_time_update_meta_strip_range(const Scene *scene, Sequence *seq_meta)
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);
const int strip_start = SEQ_time_left_handle_frame_get(scene, seq_meta);
const int strip_end = SEQ_time_right_handle_frame_get(scene, seq_meta);
int min = MAXFRAME * 2;
int max = -MAXFRAME * 2;
LISTBASE_FOREACH (Sequence *, seq, &seq_meta->seqbase) {
min = min_ii(SEQ_time_left_handle_frame_get(seq), min);
max = max_ii(SEQ_time_right_handle_frame_get(seq), max);
min = min_ii(SEQ_time_left_handle_frame_get(scene, seq), min);
max = max_ii(SEQ_time_right_handle_frame_get(scene, seq), max);
}
seq_meta->start = min + seq_meta->anim_startofs;
@ -171,25 +176,25 @@ void SEQ_time_update_meta_strip_range(const Scene *scene, Sequence *seq_meta)
SEQ_time_right_handle_frame_set(scene, seq_meta, strip_end);
}
void seq_time_effect_range_set(Sequence *seq)
void seq_time_effect_range_set(const Scene *scene, Sequence *seq)
{
if (seq->seq1 == NULL && seq->seq2 == NULL) {
return;
}
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));
seq->startdisp = max_ii(SEQ_time_left_handle_frame_get(scene, seq->seq1),
SEQ_time_left_handle_frame_get(scene, seq->seq2));
seq->enddisp = min_ii(SEQ_time_right_handle_frame_get(scene, seq->seq1),
SEQ_time_right_handle_frame_get(scene, seq->seq2));
}
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);
seq->startdisp = SEQ_time_right_handle_frame_get(scene, seq->seq1);
seq->enddisp = SEQ_time_left_handle_frame_get(scene, seq->seq1);
}
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);
seq->startdisp = SEQ_time_right_handle_frame_get(scene, seq->seq2);
seq->enddisp = SEQ_time_left_handle_frame_get(scene, seq->seq2);
}
if (seq->startdisp > seq->enddisp) {
@ -210,7 +215,7 @@ void seq_time_update_effects_strip_range(const Scene *scene, SeqCollection *effe
Sequence *seq;
/* First pass: Update length of immediate effects. */
SEQ_ITERATOR_FOREACH (seq, effects) {
seq_time_effect_range_set(seq);
seq_time_effect_range_set(scene, seq);
}
/* Second pass: Recursive call to update effects in chain and in order, so they inherit length
@ -255,14 +260,14 @@ int SEQ_time_find_next_prev_edit(Scene *scene,
}
if (do_center) {
seq_frames[0] = (SEQ_time_left_handle_frame_get(seq) +
SEQ_time_right_handle_frame_get(seq)) /
seq_frames[0] = (SEQ_time_left_handle_frame_get(scene, seq) +
SEQ_time_right_handle_frame_get(scene, seq)) /
2;
seq_frames_tot = 1;
}
else {
seq_frames[0] = SEQ_time_left_handle_frame_get(seq);
seq_frames[1] = SEQ_time_right_handle_frame_get(seq);
seq_frames[0] = SEQ_time_left_handle_frame_get(scene, seq);
seq_frames[1] = SEQ_time_right_handle_frame_get(scene, seq);
seq_frames_tot = 2;
}
@ -339,18 +344,18 @@ void SEQ_timeline_init_boundbox(const Scene *scene, rctf *rect)
rect->ymax = 8.0f;
}
void SEQ_timeline_expand_boundbox(const ListBase *seqbase, rctf *rect)
void SEQ_timeline_expand_boundbox(const Scene *scene, const ListBase *seqbase, rctf *rect)
{
if (seqbase == NULL) {
return;
}
LISTBASE_FOREACH (Sequence *, seq, seqbase) {
if (rect->xmin > SEQ_time_left_handle_frame_get(seq) - 1) {
rect->xmin = SEQ_time_left_handle_frame_get(seq) - 1;
if (rect->xmin > SEQ_time_left_handle_frame_get(scene, seq) - 1) {
rect->xmin = SEQ_time_left_handle_frame_get(scene, seq) - 1;
}
if (rect->xmax < SEQ_time_right_handle_frame_get(seq) + 1) {
rect->xmax = SEQ_time_right_handle_frame_get(seq) + 1;
if (rect->xmax < SEQ_time_right_handle_frame_get(scene, seq) + 1) {
rect->xmax = SEQ_time_right_handle_frame_get(scene, seq) + 1;
}
if (rect->ymax < seq->machine) {
rect->ymax = seq->machine;
@ -361,14 +366,16 @@ void SEQ_timeline_expand_boundbox(const ListBase *seqbase, rctf *rect)
void SEQ_timeline_boundbox(const Scene *scene, const ListBase *seqbase, rctf *rect)
{
SEQ_timeline_init_boundbox(scene, rect);
SEQ_timeline_expand_boundbox(seqbase, rect);
SEQ_timeline_expand_boundbox(scene, seqbase, rect);
}
static bool strip_exists_at_frame(SeqCollection *all_strips, const int timeline_frame)
static bool strip_exists_at_frame(const Scene *scene,
SeqCollection *all_strips,
const int timeline_frame)
{
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, all_strips) {
if (SEQ_time_strip_intersects_frame(seq, timeline_frame)) {
if (SEQ_time_strip_intersects_frame(scene, seq, timeline_frame)) {
return true;
}
}
@ -390,10 +397,10 @@ void seq_time_gap_info_get(const Scene *scene,
SeqCollection *collection = SEQ_query_all_strips(seqbase);
if (!strip_exists_at_frame(collection, initial_frame)) {
if (!strip_exists_at_frame(scene, collection, initial_frame)) {
/* Search backward for gap_start_frame. */
for (; timeline_frame >= sfra; timeline_frame--) {
if (strip_exists_at_frame(collection, timeline_frame)) {
if (strip_exists_at_frame(scene, collection, timeline_frame)) {
break;
}
}
@ -403,7 +410,7 @@ void seq_time_gap_info_get(const Scene *scene,
else {
/* Search forward for gap_start_frame. */
for (; timeline_frame <= efra; timeline_frame++) {
if (!strip_exists_at_frame(collection, timeline_frame)) {
if (!strip_exists_at_frame(scene, collection, timeline_frame)) {
r_gap_info->gap_start_frame = timeline_frame;
break;
}
@ -411,7 +418,7 @@ void seq_time_gap_info_get(const Scene *scene,
}
/* Search forward for gap_end_frame. */
for (; timeline_frame <= efra; timeline_frame++) {
if (strip_exists_at_frame(collection, timeline_frame)) {
if (strip_exists_at_frame(scene, collection, timeline_frame)) {
const int gap_end_frame = timeline_frame;
r_gap_info->gap_length = gap_end_frame - r_gap_info->gap_start_frame;
r_gap_info->gap_exists = true;
@ -420,28 +427,67 @@ void seq_time_gap_info_get(const Scene *scene,
}
}
bool SEQ_time_strip_intersects_frame(const Sequence *seq, const int timeline_frame)
bool SEQ_time_strip_intersects_frame(const Scene *scene,
const Sequence *seq,
const int timeline_frame)
{
return (SEQ_time_left_handle_frame_get(seq) <= timeline_frame) &&
(SEQ_time_right_handle_frame_get(seq) > timeline_frame);
return (SEQ_time_left_handle_frame_get(scene, seq) <= timeline_frame) &&
(SEQ_time_right_handle_frame_get(scene, seq) > timeline_frame);
}
bool SEQ_time_has_left_still_frames(const Sequence *seq)
void SEQ_time_speed_factor_set(const Scene *scene, Sequence *seq, const float speed_factor)
{
return seq->startofs < 0;
const float left_handle_frame = SEQ_time_left_handle_frame_get(scene, seq);
const float unity_start_offset = seq->startofs * seq->speed_factor;
const float unity_end_offset = seq->endofs * seq->speed_factor;
/* Left handle is pivot point for content scaling - it must always show same frame. */
seq->speed_factor = speed_factor;
seq->startofs = unity_start_offset / speed_factor;
seq->start = left_handle_frame - seq->startofs;
seq->endofs = unity_end_offset / speed_factor;
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));
}
bool SEQ_time_has_right_still_frames(const Sequence *seq)
bool SEQ_time_has_left_still_frames(const Scene *scene, const Sequence *seq)
{
return seq->endofs < 0;
return SEQ_time_left_handle_frame_get(scene, seq) < SEQ_time_start_frame_get(seq);
}
bool SEQ_time_has_still_frames(const Sequence *seq)
bool SEQ_time_has_right_still_frames(const Scene *scene, const Sequence *seq)
{
return SEQ_time_has_right_still_frames(seq) || SEQ_time_has_left_still_frames(seq);
return SEQ_time_right_handle_frame_get(scene, seq) >
SEQ_time_start_frame_get(seq) + SEQ_time_strip_length_get(scene, seq);
}
int SEQ_time_left_handle_frame_get(const Sequence *seq)
bool SEQ_time_has_still_frames(const Scene *scene, const Sequence *seq)
{
return SEQ_time_has_right_still_frames(scene, seq) || SEQ_time_has_left_still_frames(scene, seq);
}
/* Length of strip content in frames. This is number of original frames adjusted by playback rate
* factor */
int SEQ_time_strip_length_get(const Scene *scene, const Sequence *seq)
{
return seq->len / seq_time_playback_rate_factor_get(scene, seq);
}
/* Return timeline frame, where strip content starts. */
float SEQ_time_start_frame_get(const Sequence *seq)
{
return seq->start;
}
void SEQ_time_start_frame_set(const Scene *scene, Sequence *seq, int timeline_frame)
{
seq->start = timeline_frame;
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));
}
int SEQ_time_left_handle_frame_get(const Scene *UNUSED(scene), const Sequence *seq)
{
if (seq->seq1 || seq->seq2) {
return seq->startdisp;
@ -450,27 +496,42 @@ int SEQ_time_left_handle_frame_get(const Sequence *seq)
return seq->start + seq->startofs;
}
int SEQ_time_right_handle_frame_get(const Sequence *seq)
int SEQ_time_right_handle_frame_get(const Scene *scene, const Sequence *seq)
{
if (seq->seq1 || seq->seq2) {
return seq->enddisp;
}
return seq->start + seq->len - seq->endofs;
return seq->start + SEQ_time_strip_length_get(scene, seq) - seq->endofs;
}
void SEQ_time_left_handle_frame_set(const Scene *scene, Sequence *seq, int val)
{
const float right_handle_orig_frame = SEQ_time_right_handle_frame_get(scene, seq);
if (val >= right_handle_orig_frame) {
val = right_handle_orig_frame - 1;
}
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(const Scene *scene, Sequence *seq, int val)
{
seq->endofs = seq->start + seq->len - val;
const float strip_content_end_frame = seq->start + SEQ_time_strip_length_get(scene, seq);
const float left_handle_orig_frame = SEQ_time_left_handle_frame_get(scene, seq);
if (val <= left_handle_orig_frame) {
val = left_handle_orig_frame + 1;
}
seq->endofs = strip_content_end_frame - 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));
}

View File

@ -16,7 +16,7 @@ struct Scene;
struct Sequence;
struct SeqCollection;
float seq_give_frame_index(struct Sequence *seq, float timeline_frame);
float seq_give_frame_index(const struct Scene *scene, struct Sequence *seq, float timeline_frame);
void seq_update_sound_bounds_recursive(const struct Scene *scene, struct Sequence *metaseq);
/* Describes gap between strips in timeline. */
@ -38,7 +38,7 @@ 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_effect_range_set(const struct Scene *scene, Sequence *seq);
void seq_time_update_effects_strip_range(const struct Scene *scene, struct SeqCollection *effects);
#ifdef __cplusplus

View File

@ -34,15 +34,6 @@
static CLG_LogRef LOG = {"seq.strip_transform"};
static int seq_tx_get_start(Sequence *seq)
{
return seq->start;
}
static int seq_tx_get_end(Sequence *seq)
{
return seq->start + seq->len;
}
bool SEQ_transform_single_image_check(Sequence *seq)
{
return ((seq->len == 1) &&
@ -91,49 +82,6 @@ bool SEQ_transform_seqbase_isolated_sel_check(ListBase *seqbase)
return true;
}
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(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(scene, seq, seq_tx_get_end(seq) - 1);
}
/* TODO: This doesn't work at the moment. */
#if 0
if (seq_tx_get_start(seq) >= seq_tx_get_final_right(seq, 0)) {
int ofs;
ofs = seq_tx_get_start(seq) - seq_tx_get_final_right(seq, 0);
seq->start -= ofs;
seq_tx_set_final_left(seq, seq_tx_get_final_left(seq, 0) + ofs);
}
#endif
}
}
if (rightflag) {
if (SEQ_time_right_handle_frame_get(seq) <= SEQ_time_left_handle_frame_get(seq)) {
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(scene, seq, seq_tx_get_start(seq) + 1);
}
}
}
/* sounds cannot be extended past their endpoints */
if (seq->type == SEQ_TYPE_SOUND_RAM) {
CLAMP(seq->startofs, 0, MAXFRAME);
CLAMP(seq->endofs, 0, MAXFRAME);
}
}
void SEQ_transform_fix_single_image_seq_offsets(const Scene *scene, Sequence *seq)
{
int left, start, offset;
@ -143,12 +91,14 @@ void SEQ_transform_fix_single_image_seq_offsets(const Scene *scene, Sequence *se
/* make sure the image is always at the start since there is only one,
* adjusting its start should be ok */
left = SEQ_time_left_handle_frame_get(seq);
left = SEQ_time_left_handle_frame_get(scene, seq);
start = seq->start;
if (start != left) {
offset = left - start;
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_time_left_handle_frame_set(
scene, seq, SEQ_time_left_handle_frame_get(scene, seq) - offset);
SEQ_time_right_handle_frame_set(
scene, seq, SEQ_time_right_handle_frame_get(scene, seq) - offset);
seq->start += offset;
}
}
@ -158,20 +108,22 @@ bool SEQ_transform_sequence_can_be_translated(Sequence *seq)
return !(seq->type & SEQ_TYPE_EFFECT) || (SEQ_effect_get_num_inputs(seq->type) == 0);
}
bool SEQ_transform_test_overlap_seq_seq(Sequence *seq1, Sequence *seq2)
bool SEQ_transform_test_overlap_seq_seq(const Scene *scene, Sequence *seq1, Sequence *seq2)
{
return (seq1 != seq2 && seq1->machine == seq2->machine &&
((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);
((SEQ_time_right_handle_frame_get(scene, seq1) <=
SEQ_time_left_handle_frame_get(scene, seq2)) ||
(SEQ_time_left_handle_frame_get(scene, seq1) >=
SEQ_time_right_handle_frame_get(scene, seq2))) == 0);
}
bool SEQ_transform_test_overlap(ListBase *seqbasep, Sequence *test)
bool SEQ_transform_test_overlap(const Scene *scene, ListBase *seqbasep, Sequence *test)
{
Sequence *seq;
seq = seqbasep->first;
while (seq) {
if (SEQ_transform_test_overlap_seq_seq(test, seq)) {
if (SEQ_transform_test_overlap_seq_seq(scene, test, seq)) {
return true;
}
@ -194,14 +146,16 @@ void SEQ_transform_translate_sequence(Scene *evil_scene, Sequence *seq, int delt
SEQ_transform_translate_sequence(evil_scene, seq_child, delta);
}
/* Move meta start/end points. */
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);
SEQ_time_left_handle_frame_set(
evil_scene, seq, SEQ_time_left_handle_frame_get(evil_scene, seq) + delta);
SEQ_time_right_handle_frame_set(
evil_scene, seq, SEQ_time_right_handle_frame_get(evil_scene, 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);
seq->startdisp = SEQ_time_left_handle_frame_get(evil_scene, seq);
seq->enddisp = SEQ_time_right_handle_frame_get(evil_scene, seq);
}
SEQ_offset_animdata(evil_scene, seq, delta);
@ -219,7 +173,7 @@ bool SEQ_transform_seqbase_shuffle_ex(ListBase *seqbasep,
BLI_assert(ELEM(channel_delta, -1, 1));
test->machine += channel_delta;
while (SEQ_transform_test_overlap(seqbasep, test)) {
while (SEQ_transform_test_overlap(evil_scene, seqbasep, test)) {
if ((channel_delta > 0) ? (test->machine >= MAXSEQ) : (test->machine < 1)) {
break;
}
@ -232,17 +186,17 @@ bool SEQ_transform_seqbase_shuffle_ex(ListBase *seqbasep,
* nicer to move it to the end */
Sequence *seq;
int new_frame = SEQ_time_right_handle_frame_get(test);
int new_frame = SEQ_time_right_handle_frame_get(evil_scene, test);
for (seq = seqbasep->first; seq; seq = seq->next) {
if (seq->machine == orig_machine) {
new_frame = max_ii(new_frame, SEQ_time_right_handle_frame_get(seq));
new_frame = max_ii(new_frame, SEQ_time_right_handle_frame_get(evil_scene, seq));
}
}
test->machine = orig_machine;
new_frame = new_frame +
(test->start - SEQ_time_left_handle_frame_get(test)); /* adjust by the startdisp */
new_frame = new_frame + (test->start - SEQ_time_left_handle_frame_get(
evil_scene, test)); /* adjust by the startdisp */
SEQ_transform_translate_sequence(evil_scene, test, new_frame - test->start);
return false;
}
@ -255,16 +209,20 @@ bool SEQ_transform_seqbase_shuffle(ListBase *seqbasep, Sequence *test, Scene *ev
return SEQ_transform_seqbase_shuffle_ex(seqbasep, test, evil_scene, 1);
}
static bool shuffle_seq_test_overlap(const Sequence *seq1, const Sequence *seq2, const int offset)
static bool shuffle_seq_test_overlap(const Scene *scene,
const Sequence *seq1,
const Sequence *seq2,
const int 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);
return (seq1 != seq2 && seq1->machine == seq2->machine &&
((SEQ_time_right_handle_frame_get(scene, seq1) + offset <=
SEQ_time_left_handle_frame_get(scene, seq2)) ||
(SEQ_time_left_handle_frame_get(scene, seq1) + offset >=
SEQ_time_right_handle_frame_get(scene, seq2))) == 0);
}
static int shuffle_seq_time_offset_get(SeqCollection *strips_to_shuffle,
static int shuffle_seq_time_offset_get(const Scene *scene,
SeqCollection *strips_to_shuffle,
ListBase *seqbasep,
char dir)
{
@ -276,7 +234,7 @@ static int shuffle_seq_time_offset_get(SeqCollection *strips_to_shuffle,
all_conflicts_resolved = true;
SEQ_ITERATOR_FOREACH (seq, strips_to_shuffle) {
LISTBASE_FOREACH (Sequence *, seq_other, seqbasep) {
if (!shuffle_seq_test_overlap(seq, seq_other, offset)) {
if (!shuffle_seq_test_overlap(scene, seq, seq_other, offset)) {
continue;
}
if (SEQ_relation_is_effect_of_strip(seq_other, seq)) {
@ -293,13 +251,13 @@ static int shuffle_seq_time_offset_get(SeqCollection *strips_to_shuffle,
if (dir == 'L') {
offset = min_ii(offset,
SEQ_time_left_handle_frame_get(seq_other) -
SEQ_time_right_handle_frame_get(seq));
SEQ_time_left_handle_frame_get(scene, seq_other) -
SEQ_time_right_handle_frame_get(scene, seq));
}
else {
offset = max_ii(offset,
SEQ_time_right_handle_frame_get(seq_other) -
SEQ_time_left_handle_frame_get(seq));
SEQ_time_right_handle_frame_get(scene, seq_other) -
SEQ_time_left_handle_frame_get(scene, seq));
}
}
}
@ -315,8 +273,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_get(strips_to_shuffle, seqbasep, 'L');
int offset_r = shuffle_seq_time_offset_get(strips_to_shuffle, seqbasep, 'R');
int offset_l = shuffle_seq_time_offset_get(evil_scene, strips_to_shuffle, seqbasep, 'L');
int offset_r = shuffle_seq_time_offset_get(evil_scene, strips_to_shuffle, seqbasep, 'R');
int offset = (-offset_l < offset_r) ? offset_l : offset_r;
if (offset) {
@ -359,7 +317,8 @@ static SeqCollection *extract_standalone_strips(SeqCollection *transformed_strip
}
/* Query strips positioned after left edge of transformed strips bound-box. */
static SeqCollection *query_right_side_strips(ListBase *seqbase,
static SeqCollection *query_right_side_strips(const Scene *scene,
ListBase *seqbase,
SeqCollection *transformed_strips,
SeqCollection *time_dependent_strips)
{
@ -367,7 +326,7 @@ static SeqCollection *query_right_side_strips(ListBase *seqbase,
{
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, transformed_strips) {
minframe = min_ii(minframe, SEQ_time_left_handle_frame_get(seq));
minframe = min_ii(minframe, SEQ_time_left_handle_frame_get(scene, seq));
}
}
@ -380,7 +339,7 @@ static SeqCollection *query_right_side_strips(ListBase *seqbase,
continue;
}
if ((seq->flag & SELECT) == 0 && SEQ_time_left_handle_frame_get(seq) >= minframe) {
if ((seq->flag & SELECT) == 0 && SEQ_time_left_handle_frame_get(scene, seq) >= minframe) {
SEQ_collection_append_strip(seq, collection);
}
}
@ -398,7 +357,7 @@ static void seq_transform_handle_expand_to_fit(Scene *scene,
ListBase *markers = &scene->markers;
SeqCollection *right_side_strips = query_right_side_strips(
seqbasep, transformed_strips, time_dependent_strips);
scene, seqbasep, transformed_strips, time_dependent_strips);
/* Temporarily move right side strips beyond timeline boundary. */
Sequence *seq;
@ -424,7 +383,8 @@ static void seq_transform_handle_expand_to_fit(Scene *scene,
SEQ_collection_free(right_side_strips);
}
static SeqCollection *query_overwrite_targets(ListBase *seqbasep,
static SeqCollection *query_overwrite_targets(const Scene *scene,
ListBase *seqbasep,
SeqCollection *transformed_strips)
{
SeqCollection *collection = SEQ_query_unselected_strips(seqbasep);
@ -438,7 +398,7 @@ static SeqCollection *query_overwrite_targets(ListBase *seqbasep,
if (seq == seq_transformed) {
SEQ_collection_remove_strip(seq, collection);
}
if (SEQ_transform_test_overlap_seq_seq(seq, seq_transformed)) {
if (SEQ_transform_test_overlap_seq_seq(scene, seq, seq_transformed)) {
does_overlap = true;
}
}
@ -463,23 +423,32 @@ typedef enum eOvelapDescrition {
STRIP_OVERLAP_RIGHT_SIDE,
} eOvelapDescrition;
static eOvelapDescrition overlap_description_get(const Sequence *transformed,
static eOvelapDescrition overlap_description_get(const Scene *scene,
const Sequence *transformed,
const Sequence *target)
{
if (SEQ_time_left_handle_frame_get(transformed) <= SEQ_time_left_handle_frame_get(target) &&
SEQ_time_right_handle_frame_get(transformed) >= SEQ_time_right_handle_frame_get(target)) {
if (SEQ_time_left_handle_frame_get(scene, transformed) <=
SEQ_time_left_handle_frame_get(scene, target) &&
SEQ_time_right_handle_frame_get(scene, transformed) >=
SEQ_time_right_handle_frame_get(scene, target)) {
return STRIP_OVERLAP_IS_FULL;
}
if (SEQ_time_left_handle_frame_get(transformed) > SEQ_time_left_handle_frame_get(target) &&
SEQ_time_right_handle_frame_get(transformed) < SEQ_time_right_handle_frame_get(target)) {
if (SEQ_time_left_handle_frame_get(scene, transformed) >
SEQ_time_left_handle_frame_get(scene, target) &&
SEQ_time_right_handle_frame_get(scene, transformed) <
SEQ_time_right_handle_frame_get(scene, target)) {
return STRIP_OVERLAP_IS_INSIDE;
}
if (SEQ_time_left_handle_frame_get(transformed) <= SEQ_time_left_handle_frame_get(target) &&
SEQ_time_left_handle_frame_get(target) <= SEQ_time_right_handle_frame_get(transformed)) {
if (SEQ_time_left_handle_frame_get(scene, transformed) <=
SEQ_time_left_handle_frame_get(scene, target) &&
SEQ_time_left_handle_frame_get(scene, target) <=
SEQ_time_right_handle_frame_get(scene, transformed)) {
return STRIP_OVERLAP_LEFT_SIDE;
}
if (SEQ_time_left_handle_frame_get(transformed) <= SEQ_time_right_handle_frame_get(target) &&
SEQ_time_right_handle_frame_get(target) <= SEQ_time_right_handle_frame_get(transformed)) {
if (SEQ_time_left_handle_frame_get(scene, transformed) <=
SEQ_time_right_handle_frame_get(scene, target) &&
SEQ_time_right_handle_frame_get(scene, target) <=
SEQ_time_right_handle_frame_get(scene, transformed)) {
return STRIP_OVERLAP_RIGHT_SIDE;
}
return STRIP_OVERLAP_NONE;
@ -499,14 +468,14 @@ static void seq_transform_handle_overwrite_split(Scene *scene,
scene,
seqbasep,
target,
SEQ_time_left_handle_frame_get(transformed),
SEQ_time_left_handle_frame_get(scene, transformed),
SEQ_SPLIT_SOFT,
NULL);
SEQ_edit_strip_split(bmain,
scene,
seqbasep,
split_strip,
SEQ_time_right_handle_frame_get(transformed),
SEQ_time_right_handle_frame_get(scene, transformed),
SEQ_SPLIT_SOFT,
NULL);
SEQ_edit_flag_for_removal(scene, seqbasep, split_strip);
@ -521,11 +490,12 @@ static void seq_transform_handle_overwrite_trim(Scene *scene,
Sequence *target,
const eOvelapDescrition overlap)
{
SeqCollection *targets = SEQ_query_by_reference(target, seqbasep, SEQ_query_strip_effect_chain);
SeqCollection *targets = SEQ_query_by_reference(
target, scene, seqbasep, SEQ_query_strip_effect_chain);
/* Expand collection by adding all target's children, effects and their children. */
if ((target->type & SEQ_TYPE_EFFECT) != 0) {
SEQ_collection_expand(seqbasep, targets, SEQ_query_strip_effect_chain);
SEQ_collection_expand(scene, seqbasep, targets, SEQ_query_strip_effect_chain);
}
/* Trim all non effects, that have influence on effect length which is overlapping. */
@ -535,11 +505,13 @@ static void seq_transform_handle_overwrite_trim(Scene *scene,
continue;
}
if (overlap == STRIP_OVERLAP_LEFT_SIDE) {
SEQ_time_left_handle_frame_set(scene, seq, SEQ_time_right_handle_frame_get(transformed));
SEQ_time_left_handle_frame_set(
scene, seq, SEQ_time_right_handle_frame_get(scene, transformed));
}
else {
BLI_assert(overlap == STRIP_OVERLAP_RIGHT_SIDE);
SEQ_time_right_handle_frame_set(scene, seq, SEQ_time_left_handle_frame_get(transformed));
SEQ_time_right_handle_frame_set(
scene, seq, SEQ_time_left_handle_frame_get(scene, transformed));
}
}
SEQ_collection_free(targets);
@ -549,7 +521,7 @@ static void seq_transform_handle_overwrite(Scene *scene,
ListBase *seqbasep,
SeqCollection *transformed_strips)
{
SeqCollection *targets = query_overwrite_targets(seqbasep, transformed_strips);
SeqCollection *targets = query_overwrite_targets(scene, seqbasep, transformed_strips);
SeqCollection *strips_to_delete = SEQ_collection_create(__func__);
Sequence *target;
@ -560,7 +532,7 @@ static void seq_transform_handle_overwrite(Scene *scene,
continue;
}
const eOvelapDescrition overlap = overlap_description_get(transformed, target);
const eOvelapDescrition overlap = overlap_description_get(scene, transformed, target);
if (overlap == STRIP_OVERLAP_IS_FULL) {
SEQ_collection_append_strip(target, strips_to_delete);
@ -629,7 +601,7 @@ void SEQ_transform_handle_overlap(Scene *scene,
* In some cases other strips can be overlapping still, see T90646. */
Sequence *seq;
SEQ_ITERATOR_FOREACH (seq, transformed_strips) {
if (SEQ_transform_test_overlap(seqbasep, seq)) {
if (SEQ_transform_test_overlap(scene, seqbasep, seq)) {
SEQ_transform_seqbase_shuffle(seqbasep, seq, scene);
}
seq->flag &= ~SEQ_OVERLAP;
@ -642,7 +614,7 @@ void SEQ_transform_offset_after_frame(Scene *scene,
const int timeline_frame)
{
LISTBASE_FOREACH (Sequence *, seq, seqbase) {
if (SEQ_time_left_handle_frame_get(seq) >= timeline_frame) {
if (SEQ_time_left_handle_frame_get(scene, seq) >= timeline_frame) {
SEQ_transform_translate_sequence(scene, seq, delta);
SEQ_relations_invalidate_cache_preprocessed(scene, seq);
}

View File

@ -187,7 +187,7 @@ ListBase *SEQ_get_seqbase_from_sequence(Sequence *seq, ListBase **r_channels, in
case SEQ_TYPE_META: {
seqbase = &seq->seqbase;
*r_channels = &seq->channels;
*r_offset = seq->start;
*r_offset = SEQ_time_start_frame_get(seq);
break;
}
case SEQ_TYPE_SCENE: {
@ -347,7 +347,8 @@ const Sequence *SEQ_get_topmost_sequence(const Scene *scene, int frame)
}
for (seq = ed->seqbasep->first; seq; seq = seq->next) {
if (SEQ_render_is_muted(channels, seq) || !SEQ_time_strip_intersects_frame(seq, frame)) {
if (SEQ_render_is_muted(channels, seq) ||
!SEQ_time_strip_intersects_frame(scene, seq, frame)) {
continue;
}
/* Only use strips that generate an image, not ones that combine