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

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/blenkernel/intern/sequencer.c')
-rw-r--r--source/blender/blenkernel/intern/sequencer.c419
1 files changed, 267 insertions, 152 deletions
diff --git a/source/blender/blenkernel/intern/sequencer.c b/source/blender/blenkernel/intern/sequencer.c
index 9fb28fe250a..90edebfaa97 100644
--- a/source/blender/blenkernel/intern/sequencer.c
+++ b/source/blender/blenkernel/intern/sequencer.c
@@ -39,6 +39,7 @@
#include "DNA_sequence_types.h"
#include "DNA_sound_types.h"
#include "DNA_space_types.h"
+#include "DNA_windowmanager_types.h"
#include "BLI_fileops.h"
#include "BLI_linklist.h"
@@ -58,6 +59,7 @@
#include "BLT_translation.h"
+#include "BKE_anim_data.h"
#include "BKE_animsys.h"
#include "BKE_fcurve.h"
#include "BKE_global.h"
@@ -68,6 +70,7 @@
#include "BKE_main.h"
#include "BKE_mask.h"
#include "BKE_movieclip.h"
+#include "BKE_report.h"
#include "BKE_scene.h"
#include "BKE_sequencer.h"
#include "BKE_sequencer_offscreen.h"
@@ -105,6 +108,14 @@ static ImBuf *seq_render_strip_stack(const SeqRenderData *context,
ListBase *seqbasep,
float cfra,
int chanshown);
+static ImBuf *seq_render_preprocess_ibuf(const SeqRenderData *context,
+ Sequence *seq,
+ ImBuf *ibuf,
+ float cfra,
+ clock_t begin,
+ bool use_preprocess,
+ const bool is_proxy_image,
+ const bool is_preprocessed);
static ImBuf *seq_render_strip(const SeqRenderData *context,
SeqRenderState *state,
Sequence *seq,
@@ -120,7 +131,8 @@ static ThreadMutex seq_render_mutex = BLI_MUTEX_INITIALIZER;
#define SELECT 1
ListBase seqbase_clipboard;
int seqbase_clipboard_frame;
-SequencerDrawView sequencer_view3d_cb = NULL; /* NULL in background mode */
+
+SequencerDrawView sequencer_view3d_fn = NULL; /* NULL in background mode */
#if 0 /* unused function */
static void printf_strip(Sequence *seq)
@@ -152,28 +164,28 @@ static void sequencer_state_init(SeqRenderState *state)
}
int BKE_sequencer_base_recursive_apply(ListBase *seqbase,
- int (*apply_func)(Sequence *seq, void *),
+ int (*apply_fn)(Sequence *seq, void *),
void *arg)
{
Sequence *iseq;
for (iseq = seqbase->first; iseq; iseq = iseq->next) {
- if (BKE_sequencer_recursive_apply(iseq, apply_func, arg) == -1) {
+ if (BKE_sequencer_recursive_apply(iseq, apply_fn, arg) == -1) {
return -1; /* bail out */
}
}
return 1;
}
-int BKE_sequencer_recursive_apply(Sequence *seq, int (*apply_func)(Sequence *, void *), void *arg)
+int BKE_sequencer_recursive_apply(Sequence *seq, int (*apply_fn)(Sequence *, void *), void *arg)
{
- int ret = apply_func(seq, arg);
+ int ret = apply_fn(seq, arg);
if (ret == -1) {
return -1; /* bail out */
}
if (ret && seq->seqbase.first) {
- ret = BKE_sequencer_base_recursive_apply(&seq->seqbase, apply_func, arg);
+ ret = BKE_sequencer_base_recursive_apply(&seq->seqbase, apply_fn, arg);
}
return ret;
@@ -227,7 +239,8 @@ static void seq_free_strip(Strip *strip)
static void BKE_sequence_free_ex(Scene *scene,
Sequence *seq,
const bool do_cache,
- const bool do_id_user)
+ const bool do_id_user,
+ const bool do_clean_animdata)
{
if (seq->strip) {
seq_free_strip(seq->strip);
@@ -262,7 +275,10 @@ static void BKE_sequence_free_ex(Scene *scene,
BKE_sound_remove_scene_sound(scene, seq->scene_sound);
}
- seq_free_animdata(scene, seq);
+ /* XXX This must not be done in BKE code. */
+ if (do_clean_animdata) {
+ seq_free_animdata(scene, seq);
+ }
}
if (seq->prop) {
@@ -290,9 +306,9 @@ static void BKE_sequence_free_ex(Scene *scene,
MEM_freeN(seq);
}
-void BKE_sequence_free(Scene *scene, Sequence *seq)
+void BKE_sequence_free(Scene *scene, Sequence *seq, const bool do_clean_animdata)
{
- BKE_sequence_free_ex(scene, seq, true, true);
+ BKE_sequence_free_ex(scene, seq, true, true, do_clean_animdata);
}
/* Function to free imbuf and anim data on changes */
@@ -322,7 +338,7 @@ static void seq_free_sequence_recurse(Scene *scene, Sequence *seq, const bool do
seq_free_sequence_recurse(scene, iseq, do_id_user);
}
- BKE_sequence_free_ex(scene, seq, false, do_id_user);
+ BKE_sequence_free_ex(scene, seq, false, do_id_user, true);
}
Editing *BKE_sequencer_editing_get(Scene *scene, bool alloc)
@@ -492,7 +508,7 @@ void BKE_sequencer_editing_free(Scene *scene, const bool do_id_user)
SEQ_BEGIN (ed, seq) {
/* handle cache freeing above */
- BKE_sequence_free_ex(scene, seq, false, do_id_user);
+ BKE_sequence_free_ex(scene, seq, false, do_id_user, false);
}
SEQ_END;
@@ -752,10 +768,10 @@ static int metaseq_end(Sequence *metaseq)
return metaseq->start + metaseq->len - metaseq->endofs;
}
-static void seq_update_sound_bounds_recursive_rec(Scene *scene,
- Sequence *metaseq,
- int start,
- int end)
+static void seq_update_sound_bounds_recursive_impl(Scene *scene,
+ Sequence *metaseq,
+ int start,
+ int end)
{
Sequence *seq;
@@ -763,7 +779,7 @@ static void seq_update_sound_bounds_recursive_rec(Scene *scene,
* since sound is played outside of evaluating the imbufs, */
for (seq = metaseq->seqbase.first; seq; seq = seq->next) {
if (seq->type == SEQ_TYPE_META) {
- seq_update_sound_bounds_recursive_rec(
+ seq_update_sound_bounds_recursive_impl(
scene, seq, max_ii(start, metaseq_start(seq)), min_ii(end, metaseq_end(seq)));
}
else if (ELEM(seq->type, SEQ_TYPE_SOUND_RAM, SEQ_TYPE_SCENE)) {
@@ -790,7 +806,7 @@ static void seq_update_sound_bounds_recursive_rec(Scene *scene,
static void seq_update_sound_bounds_recursive(Scene *scene, Sequence *metaseq)
{
- seq_update_sound_bounds_recursive_rec(
+ seq_update_sound_bounds_recursive_impl(
scene, metaseq, metaseq_start(metaseq), metaseq_end(metaseq));
}
@@ -1138,7 +1154,7 @@ int BKE_sequencer_cmp_time_startdisp(const void *a, const void *b)
return (seq_a->startdisp > seq_b->startdisp);
}
-static int clear_scene_in_allseqs_cb(Sequence *seq, void *arg_pt)
+static int clear_scene_in_allseqs_fn(Sequence *seq, void *arg_pt)
{
if (seq->scene == (Scene *)arg_pt) {
seq->scene = NULL;
@@ -1154,7 +1170,7 @@ void BKE_sequencer_clear_scene_in_allseqs(Main *bmain, Scene *scene)
for (scene_iter = bmain->scenes.first; scene_iter; scene_iter = scene_iter->id.next) {
if (scene_iter != scene && scene_iter->ed) {
BKE_sequencer_base_recursive_apply(
- &scene_iter->ed->seqbase, clear_scene_in_allseqs_cb, scene);
+ &scene_iter->ed->seqbase, clear_scene_in_allseqs_fn, scene);
}
}
}
@@ -1184,7 +1200,7 @@ static void seqbase_unique_name(ListBase *seqbasep, SeqUniqueInfo *sui)
}
}
-static int seqbase_unique_name_recursive_cb(Sequence *seq, void *arg_pt)
+static int seqbase_unique_name_recursive_fn(Sequence *seq, void *arg_pt)
{
if (seq->seqbase.first) {
seqbase_unique_name(&seq->seqbase, (SeqUniqueInfo *)arg_pt);
@@ -1216,7 +1232,7 @@ void BKE_sequence_base_unique_name_recursive(ListBase *seqbasep, Sequence *seq)
while (sui.match) {
sui.match = 0;
seqbase_unique_name(seqbasep, &sui);
- BKE_sequencer_base_recursive_apply(seqbasep, seqbase_unique_name_recursive_cb, &sui);
+ BKE_sequencer_base_recursive_apply(seqbasep, seqbase_unique_name_recursive_fn, &sui);
}
BLI_strncpy(seq->name + 2, sui.name_dest, sizeof(seq->name) - 2);
@@ -1381,7 +1397,7 @@ static void multibuf(ImBuf *ibuf, const float fmul)
}
}
-static float give_stripelem_index(Sequence *seq, float cfra)
+float BKE_sequencer_give_stripelem_index(Sequence *seq, float cfra)
{
float nr;
int sta = seq->start;
@@ -1439,7 +1455,7 @@ StripElem *BKE_sequencer_give_stripelem(Sequence *seq, int cfra)
* all other strips don't use this...
*/
- int nr = (int)give_stripelem_index(seq, cfra);
+ int nr = (int)BKE_sequencer_give_stripelem_index(seq, cfra);
if (nr == -1 || se == NULL) {
return NULL;
@@ -1458,7 +1474,7 @@ static int evaluate_seq_frame_gen(Sequence **seq_arr, ListBase *seqbase, int cfr
memset(seq_arr, 0, sizeof(Sequence *) * (MAXSEQ + 1));
- for (Sequence *seq = seqbase->first; seq; seq = seq->next) {
+ LISTBASE_FOREACH (Sequence *, seq, seqbase) {
if ((seq->startdisp <= cfra) && (seq->enddisp > cfra)) {
if ((seq->type & SEQ_TYPE_EFFECT) && !(seq->flag & SEQ_MUTE)) {
@@ -1522,7 +1538,10 @@ static bool video_seq_is_rendered(Sequence *seq)
return (seq && !(seq->flag & SEQ_MUTE) && seq->type != SEQ_TYPE_SOUND_RAM);
}
-static int get_shown_sequences(ListBase *seqbasep, int cfra, int chanshown, Sequence **seq_arr_out)
+int BKE_sequencer_get_shown_sequences(ListBase *seqbasep,
+ int cfra,
+ int chanshown,
+ Sequence **seq_arr_out)
{
Sequence *seq_arr[MAXSEQ + 1];
int b = chanshown;
@@ -1876,7 +1895,7 @@ static bool seq_proxy_get_fname(Editing *ed,
frameno = 1;
}
else {
- frameno = (int)give_stripelem_index(seq, cfra) + seq->anim_startofs;
+ frameno = (int)BKE_sequencer_give_stripelem_index(seq, cfra) + seq->anim_startofs;
BLI_snprintf(name, PROXY_MAXFILE, "%s/proxy_misc/%d/####%s", dir, proxy_size_number, suffix);
}
@@ -1891,9 +1910,10 @@ static bool seq_proxy_get_fname(Editing *ed,
static ImBuf *seq_proxy_fetch(const SeqRenderData *context, Sequence *seq, int cfra)
{
char name[PROXY_MAXFILE];
- IMB_Proxy_Size psize = seq_rendersize_to_proxysize(context->preview_render_size);
- int size_flags;
StripProxy *proxy = seq->strip->proxy;
+ const eSpaceSeq_Proxy_RenderSize psize = context->preview_render_size;
+ const IMB_Proxy_Size psize_flag = seq_rendersize_to_proxysize(psize);
+ int size_flags;
Editing *ed = context->scene->ed;
StripAnim *sanim;
@@ -1904,12 +1924,12 @@ static ImBuf *seq_proxy_fetch(const SeqRenderData *context, Sequence *seq, int c
size_flags = proxy->build_size_flags;
/* only use proxies, if they are enabled (even if present!) */
- if (psize == IMB_PROXY_NONE || (size_flags & psize) == 0) {
+ if (psize_flag == IMB_PROXY_NONE || (size_flags & psize_flag) == 0) {
return NULL;
}
if (proxy->storage & SEQ_STORAGE_PROXY_CUSTOM_FILE) {
- int frameno = (int)give_stripelem_index(seq, cfra) + seq->anim_startofs;
+ int frameno = (int)BKE_sequencer_give_stripelem_index(seq, cfra) + seq->anim_startofs;
if (proxy->anim == NULL) {
if (seq_proxy_get_fname(ed, seq, cfra, psize, name, context->view_id) == 0) {
return NULL;
@@ -2874,15 +2894,15 @@ static void *render_effect_execute_do_thread(void *thread_data_v)
return NULL;
}
-static ImBuf *seq_render_effect_execute_threaded(struct SeqEffectHandle *sh,
- const SeqRenderData *context,
- Sequence *seq,
- float cfra,
- float facf0,
- float facf1,
- ImBuf *ibuf1,
- ImBuf *ibuf2,
- ImBuf *ibuf3)
+ImBuf *BKE_sequencer_effect_execute_threaded(struct SeqEffectHandle *sh,
+ const SeqRenderData *context,
+ Sequence *seq,
+ float cfra,
+ float facf0,
+ float facf1,
+ ImBuf *ibuf1,
+ ImBuf *ibuf2,
+ ImBuf *ibuf3)
{
RenderEffectInitData init_data;
ImBuf *out = sh->init_execution(context, ibuf1, ibuf2, ibuf3);
@@ -2956,14 +2976,21 @@ static ImBuf *seq_render_effect_strip_impl(const SeqRenderData *context,
break;
case EARLY_DO_EFFECT:
for (i = 0; i < 3; i++) {
- if (input[i]) {
- ibuf[i] = seq_render_strip(context, state, input[i], cfra);
+ /* Speed effect requires time remapping of cfra for input(s). */
+ if (input[1] && seq->type == SEQ_TYPE_SPEED) {
+ float target_frame = BKE_sequencer_speed_effect_target_frame_get(context, seq, cfra, i);
+ ibuf[i] = seq_render_strip(context, state, input[i], target_frame);
+ }
+ else { /* Other effects. */
+ if (input[i]) {
+ ibuf[i] = seq_render_strip(context, state, input[i], cfra);
+ }
}
}
if (ibuf[0] && ibuf[1]) {
if (sh.multithreaded) {
- out = seq_render_effect_execute_threaded(
+ out = BKE_sequencer_effect_execute_threaded(
&sh, context, seq, cfra, fac, facf, ibuf[0], ibuf[1], ibuf[2]);
}
else {
@@ -3025,7 +3052,6 @@ static ImBuf *seq_render_image_strip(const SeqRenderData *context,
struct ImBuf **ibufs_arr;
char prefix[FILE_MAX];
const char *ext = NULL;
- int i;
if (totfiles > 1) {
BKE_scene_multiview_view_prefix_get(context->scene, name, prefix, &ext);
@@ -3040,21 +3066,21 @@ static ImBuf *seq_render_image_strip(const SeqRenderData *context,
totviews = BKE_scene_multiview_num_views_get(&context->scene->r);
ibufs_arr = MEM_callocN(sizeof(ImBuf *) * totviews, "Sequence Image Views Imbufs");
- for (i = 0; i < totfiles; i++) {
+ for (int view_id = 0; view_id < totfiles; view_id++) {
if (prefix[0] == '\0') {
- ibufs_arr[i] = IMB_loadiffname(name, flag, seq->strip->colorspace_settings.name);
+ ibufs_arr[view_id] = IMB_loadiffname(name, flag, seq->strip->colorspace_settings.name);
}
else {
char str[FILE_MAX];
- seq_multiview_name(context->scene, i, prefix, ext, str, FILE_MAX);
- ibufs_arr[i] = IMB_loadiffname(str, flag, seq->strip->colorspace_settings.name);
+ seq_multiview_name(context->scene, view_id, prefix, ext, str, FILE_MAX);
+ ibufs_arr[view_id] = IMB_loadiffname(str, flag, seq->strip->colorspace_settings.name);
}
- if (ibufs_arr[i]) {
+ if (ibufs_arr[view_id]) {
/* we don't need both (speed reasons)! */
- if (ibufs_arr[i]->rect_float && ibufs_arr[i]->rect) {
- imb_freerectImBuf(ibufs_arr[i]);
+ if (ibufs_arr[view_id]->rect_float && ibufs_arr[view_id]->rect) {
+ imb_freerectImBuf(ibufs_arr[view_id]);
}
}
}
@@ -3063,17 +3089,17 @@ static ImBuf *seq_render_image_strip(const SeqRenderData *context,
IMB_ImBufFromStereo3d(seq->stereo3d_format, ibufs_arr[0], &ibufs_arr[0], &ibufs_arr[1]);
}
- for (i = 0; i < totviews; i++) {
- if (ibufs_arr[i]) {
+ for (int view_id = 0; view_id < totviews; view_id++) {
+ if (ibufs_arr[view_id]) {
SeqRenderData localcontext = *context;
- localcontext.view_id = i;
+ localcontext.view_id = view_id;
/* all sequencer color is done in SRGB space, linear gives odd crossfades */
- BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibufs_arr[i], false);
+ BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibufs_arr[view_id], false);
- if (i != context->view_id) {
- BKE_sequencer_cache_put(
- &localcontext, seq, cfra, SEQ_CACHE_STORE_PREPROCESSED, ibufs_arr[i], 0, false);
+ if (view_id != context->view_id) {
+ ibufs_arr[view_id] = seq_render_preprocess_ibuf(
+ &localcontext, seq, ibufs_arr[view_id], cfra, clock(), true, false, false);
}
}
}
@@ -3086,9 +3112,9 @@ static ImBuf *seq_render_image_strip(const SeqRenderData *context,
}
/* "remove" the others (decrease their refcount) */
- for (i = 0; i < totviews; i++) {
- if (ibufs_arr[i] != ibuf) {
- IMB_freeImBuf(ibufs_arr[i]);
+ for (int view_id = 0; view_id < totviews; view_id++) {
+ if (ibufs_arr[view_id] != ibuf) {
+ IMB_freeImBuf(ibufs_arr[view_id]);
}
}
@@ -3136,7 +3162,7 @@ static ImBuf *seq_render_movie_strip(const SeqRenderData *context,
ImBuf **ibuf_arr;
const int totfiles = seq_num_files(context->scene, seq->views_format, true);
int totviews;
- int i;
+ int ibuf_view_id;
if (totfiles != BLI_listbase_count_at_most(&seq->anims, totfiles + 1)) {
goto monoview_movie;
@@ -3145,28 +3171,28 @@ static ImBuf *seq_render_movie_strip(const SeqRenderData *context,
totviews = BKE_scene_multiview_num_views_get(&context->scene->r);
ibuf_arr = MEM_callocN(sizeof(ImBuf *) * totviews, "Sequence Image Views Imbufs");
- for (i = 0, sanim = seq->anims.first; sanim; sanim = sanim->next, i++) {
+ for (ibuf_view_id = 0, sanim = seq->anims.first; sanim; sanim = sanim->next, ibuf_view_id++) {
if (sanim->anim) {
IMB_anim_set_preseek(sanim->anim, seq->anim_preseek);
- ibuf_arr[i] = IMB_anim_absolute(sanim->anim,
- nr + seq->anim_startofs,
- seq->strip->proxy ? seq->strip->proxy->tc :
- IMB_TC_RECORD_RUN,
- psize);
+ ibuf_arr[ibuf_view_id] = IMB_anim_absolute(sanim->anim,
+ nr + seq->anim_startofs,
+ seq->strip->proxy ? seq->strip->proxy->tc :
+ IMB_TC_RECORD_RUN,
+ psize);
/* fetching for requested proxy size failed, try fetching the original instead */
- if (!ibuf_arr[i] && psize != IMB_PROXY_NONE) {
- ibuf_arr[i] = IMB_anim_absolute(sanim->anim,
- nr + seq->anim_startofs,
- seq->strip->proxy ? seq->strip->proxy->tc :
- IMB_TC_RECORD_RUN,
- IMB_PROXY_NONE);
+ if (!ibuf_arr[ibuf_view_id] && psize != IMB_PROXY_NONE) {
+ ibuf_arr[ibuf_view_id] = IMB_anim_absolute(sanim->anim,
+ nr + seq->anim_startofs,
+ seq->strip->proxy ? seq->strip->proxy->tc :
+ IMB_TC_RECORD_RUN,
+ IMB_PROXY_NONE);
}
- if (ibuf_arr[i]) {
+ if (ibuf_arr[ibuf_view_id]) {
/* we don't need both (speed reasons)! */
- if (ibuf_arr[i]->rect_float && ibuf_arr[i]->rect) {
- imb_freerectImBuf(ibuf_arr[i]);
+ if (ibuf_arr[ibuf_view_id]->rect_float && ibuf_arr[ibuf_view_id]->rect) {
+ imb_freerectImBuf(ibuf_arr[ibuf_view_id]);
}
}
}
@@ -3183,17 +3209,17 @@ static ImBuf *seq_render_movie_strip(const SeqRenderData *context,
}
}
- for (i = 0; i < totviews; i++) {
+ for (int view_id = 0; view_id < totviews; view_id++) {
SeqRenderData localcontext = *context;
- localcontext.view_id = i;
+ localcontext.view_id = view_id;
- if (ibuf_arr[i]) {
+ if (ibuf_arr[view_id]) {
/* all sequencer color is done in SRGB space, linear gives odd crossfades */
- BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibuf_arr[i], false);
+ BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibuf_arr[view_id], false);
}
- if (i != context->view_id) {
- BKE_sequencer_cache_put(
- &localcontext, seq, cfra, SEQ_CACHE_STORE_PREPROCESSED, ibuf_arr[i], 0, false);
+ if (view_id != context->view_id) {
+ ibuf_arr[view_id] = seq_render_preprocess_ibuf(
+ &localcontext, seq, ibuf_arr[view_id], cfra, clock(), true, false, false);
}
}
@@ -3205,9 +3231,9 @@ static ImBuf *seq_render_movie_strip(const SeqRenderData *context,
}
/* "remove" the others (decrease their refcount) */
- for (i = 0; i < totviews; i++) {
- if (ibuf_arr[i] != ibuf) {
- IMB_freeImBuf(ibuf_arr[i]);
+ for (int view_id = 0; view_id < totviews; view_id++) {
+ if (ibuf_arr[view_id] != ibuf) {
+ IMB_freeImBuf(ibuf_arr[view_id]);
}
}
@@ -3318,8 +3344,7 @@ static ImBuf *seq_render_mask(const SeqRenderData *context, Mask *mask, float nr
/* anim-data */
adt = BKE_animdata_from_id(&mask->id);
- BKE_animsys_evaluate_animdata(
- context->scene, &mask_temp->id, adt, mask->sfra + nr, ADT_RECALC_ANIM, false);
+ BKE_animsys_evaluate_animdata(&mask_temp->id, adt, mask->sfra + nr, ADT_RECALC_ANIM, false);
maskbuf = MEM_mallocN(sizeof(float) * context->rectx * context->recty, __func__);
@@ -3450,6 +3475,11 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
return NULL;
}
+ /* Prevent rendering scene recursively. */
+ if (seq->scene == context->scene) {
+ return NULL;
+ }
+
scene = seq->scene;
frame = (double)scene->r.sfra + (double)nr + (double)seq->anim_startofs;
@@ -3498,7 +3528,7 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
is_frame_update = (orig_data.cfra != scene->r.cfra) || (orig_data.subframe != scene->r.subframe);
- if ((sequencer_view3d_cb && do_seq_gl && camera) && is_thread_main) {
+ if ((sequencer_view3d_fn && do_seq_gl && camera) && is_thread_main) {
char err_out[256] = "unknown";
const int width = (scene->r.xsch * scene->r.size) / 100;
const int height = (scene->r.ysch * scene->r.size) / 100;
@@ -3519,7 +3549,7 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
/* opengl offscreen render */
depsgraph = BKE_scene_get_depsgraph(context->bmain, scene, view_layer, true);
BKE_scene_graph_update_for_newframe(depsgraph, context->bmain);
- ibuf = sequencer_view3d_cb(
+ ibuf = sequencer_view3d_fn(
/* set for OpenGL render (NULL when scrubbing) */
depsgraph,
scene,
@@ -3541,7 +3571,6 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
else {
Render *re = RE_GetSceneRender(scene);
const int totviews = BKE_scene_multiview_num_views_get(&scene->r);
- int i;
ImBuf **ibufs_arr;
ibufs_arr = MEM_callocN(sizeof(ImBuf *) * totviews, "Sequence Image Views Imbufs");
@@ -3566,34 +3595,37 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
G.is_rendering = is_rendering;
}
- for (i = 0; i < totviews; i++) {
+ for (int view_id = 0; view_id < totviews; view_id++) {
SeqRenderData localcontext = *context;
RenderResult rres;
- localcontext.view_id = i;
+ localcontext.view_id = view_id;
- RE_AcquireResultImage(re, &rres, i);
+ RE_AcquireResultImage(re, &rres, view_id);
if (rres.rectf) {
- ibufs_arr[i] = IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rectfloat);
- memcpy(ibufs_arr[i]->rect_float, rres.rectf, 4 * sizeof(float) * rres.rectx * rres.recty);
+ ibufs_arr[view_id] = IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rectfloat);
+ memcpy(ibufs_arr[view_id]->rect_float,
+ rres.rectf,
+ 4 * sizeof(float) * rres.rectx * rres.recty);
if (rres.rectz) {
- addzbuffloatImBuf(ibufs_arr[i]);
- memcpy(ibufs_arr[i]->zbuf_float, rres.rectz, sizeof(float) * rres.rectx * rres.recty);
+ addzbuffloatImBuf(ibufs_arr[view_id]);
+ memcpy(
+ ibufs_arr[view_id]->zbuf_float, rres.rectz, sizeof(float) * rres.rectx * rres.recty);
}
/* float buffers in the sequencer are not linear */
- BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibufs_arr[i], false);
+ BKE_sequencer_imbuf_to_sequencer_space(context->scene, ibufs_arr[view_id], false);
}
else if (rres.rect32) {
- ibufs_arr[i] = IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rect);
- memcpy(ibufs_arr[i]->rect, rres.rect32, 4 * rres.rectx * rres.recty);
+ ibufs_arr[view_id] = IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rect);
+ memcpy(ibufs_arr[view_id]->rect, rres.rect32, 4 * rres.rectx * rres.recty);
}
- if (i != context->view_id) {
+ if (view_id != context->view_id) {
BKE_sequencer_cache_put(
- &localcontext, seq, cfra, SEQ_CACHE_STORE_RAW, ibufs_arr[i], 0, false);
+ &localcontext, seq, cfra, SEQ_CACHE_STORE_RAW, ibufs_arr[view_id], 0, false);
}
RE_ReleaseResultImage(re);
@@ -3603,9 +3635,9 @@ static ImBuf *seq_render_scene_strip(const SeqRenderData *context,
ibuf = ibufs_arr[context->view_id];
/* "remove" the others (decrease their refcount) */
- for (i = 0; i < totviews; i++) {
- if (ibufs_arr[i] != ibuf) {
- IMB_freeImBuf(ibufs_arr[i]);
+ for (int view_id = 0; view_id < totviews; view_id++) {
+ if (ibufs_arr[view_id] != ibuf) {
+ IMB_freeImBuf(ibufs_arr[view_id]);
}
}
MEM_freeN(ibufs_arr);
@@ -3646,8 +3678,7 @@ static ImBuf *do_render_strip_seqbase(const SeqRenderData *context,
if (seqbase && !BLI_listbase_is_empty(seqbase)) {
if (seq->flag & SEQ_SCENE_STRIPS && seq->scene) {
- BKE_animsys_evaluate_all_animation(
- context->bmain, context->depsgraph, seq->scene, nr + offset);
+ BKE_animsys_evaluate_all_animation(context->bmain, context->depsgraph, nr + offset);
}
ibuf = seq_render_strip_stack(context,
@@ -3667,9 +3698,8 @@ static ImBuf *do_render_strip_uncached(const SeqRenderData *context,
float cfra)
{
ImBuf *ibuf = NULL;
- float nr = give_stripelem_index(seq, cfra);
- int type = (seq->type & SEQ_TYPE_EFFECT && seq->type != SEQ_TYPE_SPEED) ? SEQ_TYPE_EFFECT :
- seq->type;
+ float nr = BKE_sequencer_give_stripelem_index(seq, cfra);
+ int type = (seq->type & SEQ_TYPE_EFFECT) ? SEQ_TYPE_EFFECT : seq->type;
switch (type) {
case SEQ_TYPE_META: {
ibuf = do_render_strip_seqbase(context, state, seq, nr);
@@ -3711,21 +3741,8 @@ static ImBuf *do_render_strip_uncached(const SeqRenderData *context,
break;
}
- case SEQ_TYPE_SPEED: {
- float f_cfra;
- SpeedControlVars *s = (SpeedControlVars *)seq->effectdata;
-
- BKE_sequence_effect_speed_rebuild_map(context->scene, seq, false);
-
- /* weeek! */
- f_cfra = seq->start + s->frameMap[(int)nr];
- ibuf = seq_render_strip(context, state, seq->seq1, f_cfra);
-
- break;
- }
-
case SEQ_TYPE_EFFECT: {
- ibuf = seq_render_effect_strip_impl(context, state, seq, seq->start + nr);
+ ibuf = seq_render_effect_strip_impl(context, state, seq, cfra);
break;
}
@@ -3790,6 +3807,34 @@ static float seq_estimate_render_cost_end(Scene *scene, clock_t begin)
}
}
+static ImBuf *seq_render_preprocess_ibuf(const SeqRenderData *context,
+ Sequence *seq,
+ ImBuf *ibuf,
+ float cfra,
+ clock_t begin,
+ bool use_preprocess,
+ const bool is_proxy_image,
+ const bool is_preprocessed)
+{
+ if (context->is_proxy_render == false &&
+ (ibuf->x != context->rectx || ibuf->y != context->recty)) {
+ use_preprocess = true;
+ }
+
+ if (use_preprocess) {
+ float cost = seq_estimate_render_cost_end(context->scene, begin);
+ BKE_sequencer_cache_put(context, seq, cfra, SEQ_CACHE_STORE_RAW, ibuf, cost, false);
+
+ /* Reset timer so we can get partial render time. */
+ begin = seq_estimate_render_cost_begin();
+ ibuf = input_preprocess(context, seq, cfra, ibuf, is_proxy_image, is_preprocessed);
+ }
+
+ float cost = seq_estimate_render_cost_end(context->scene, begin);
+ BKE_sequencer_cache_put(context, seq, cfra, SEQ_CACHE_STORE_PREPROCESSED, ibuf, cost, false);
+ return ibuf;
+}
+
static ImBuf *seq_render_strip(const SeqRenderData *context,
SeqRenderState *state,
Sequence *seq,
@@ -3838,22 +3883,8 @@ static ImBuf *seq_render_strip(const SeqRenderData *context,
sequencer_imbuf_assign_spaces(context->scene, ibuf);
}
- if (context->is_proxy_render == false &&
- (ibuf->x != context->rectx || ibuf->y != context->recty)) {
- use_preprocess = true;
- }
-
- if (use_preprocess) {
- float cost = seq_estimate_render_cost_end(context->scene, begin);
- BKE_sequencer_cache_put(context, seq, cfra, SEQ_CACHE_STORE_RAW, ibuf, cost, false);
-
- /* reset timer so we can get partial render time */
- begin = seq_estimate_render_cost_begin();
- ibuf = input_preprocess(context, seq, cfra, ibuf, is_proxy_image, is_preprocessed);
- }
-
- float cost = seq_estimate_render_cost_end(context->scene, begin);
- BKE_sequencer_cache_put(context, seq, cfra, SEQ_CACHE_STORE_PREPROCESSED, ibuf, cost, false);
+ ibuf = seq_render_preprocess_ibuf(
+ context, seq, ibuf, cfra, begin, use_preprocess, is_proxy_image, is_preprocessed);
}
return ibuf;
}
@@ -3905,7 +3936,7 @@ static ImBuf *seq_render_strip_stack_apply_effect(
if (swap_input) {
if (sh.multithreaded) {
- out = seq_render_effect_execute_threaded(
+ out = BKE_sequencer_effect_execute_threaded(
&sh, context, seq, cfra, facf, facf, ibuf2, ibuf1, NULL);
}
else {
@@ -3914,7 +3945,7 @@ static ImBuf *seq_render_strip_stack_apply_effect(
}
else {
if (sh.multithreaded) {
- out = seq_render_effect_execute_threaded(
+ out = BKE_sequencer_effect_execute_threaded(
&sh, context, seq, cfra, facf, facf, ibuf1, ibuf2, NULL);
}
else {
@@ -3937,7 +3968,7 @@ static ImBuf *seq_render_strip_stack(const SeqRenderData *context,
ImBuf *out = NULL;
clock_t begin;
- count = get_shown_sequences(seqbasep, cfra, chanshown, (Sequence **)&seq_arr);
+ count = BKE_sequencer_get_shown_sequences(seqbasep, cfra, chanshown, (Sequence **)&seq_arr);
if (count == 0) {
return NULL;
@@ -4045,7 +4076,7 @@ ImBuf *BKE_sequencer_give_ibuf(const SeqRenderData *context, float cfra, int cha
Sequence *seq_arr[MAXSEQ + 1];
int count;
- count = get_shown_sequences(seqbasep, cfra, chanshown, seq_arr);
+ count = BKE_sequencer_get_shown_sequences(seqbasep, cfra, chanshown, seq_arr);
if (count) {
out = BKE_sequencer_cache_get(
@@ -4138,8 +4169,15 @@ static void sequence_do_invalidate_dependent(Scene *scene, Sequence *seq, ListBa
}
if (BKE_sequence_check_depend(seq, cur)) {
- BKE_sequencer_cache_cleanup_sequence(
- scene, cur, seq, SEQ_CACHE_STORE_COMPOSITE | SEQ_CACHE_STORE_FINAL_OUT);
+ /* Effect must be invalidated completely if they depend on invalidated seq. */
+ if ((cur->type & SEQ_TYPE_EFFECT) != 0) {
+ BKE_sequencer_cache_cleanup_sequence(scene, cur, seq, SEQ_CACHE_ALL_TYPES, false);
+ }
+ else {
+ /* In case of alpha over for example only invalidate composite image */
+ BKE_sequencer_cache_cleanup_sequence(
+ scene, cur, seq, SEQ_CACHE_STORE_COMPOSITE | SEQ_CACHE_STORE_FINAL_OUT, false);
+ }
}
if (cur->seqbase.first) {
@@ -4157,7 +4195,7 @@ static void sequence_invalidate_cache(Scene *scene,
if (invalidate_self) {
BKE_sequence_free_anim(seq);
- BKE_sequencer_cache_cleanup_sequence(scene, seq, seq, invalidate_types);
+ BKE_sequencer_cache_cleanup_sequence(scene, seq, seq, invalidate_types, false);
}
if (seq->effectdata && seq->type == SEQ_TYPE_SPEED) {
@@ -4169,6 +4207,14 @@ static void sequence_invalidate_cache(Scene *scene,
BKE_sequencer_prefetch_stop(scene);
}
+void BKE_sequence_invalidate_cache_in_range(Scene *scene,
+ Sequence *seq,
+ Sequence *range_mask,
+ int invalidate_types)
+{
+ BKE_sequencer_cache_cleanup_sequence(scene, seq, range_mask, invalidate_types, true);
+}
+
void BKE_sequence_invalidate_cache_raw(Scene *scene, Sequence *seq)
{
sequence_invalidate_cache(scene, seq, true, SEQ_CACHE_ALL_TYPES);
@@ -4568,6 +4614,10 @@ bool BKE_sequence_test_overlap(ListBase *seqbasep, Sequence *test)
void BKE_sequence_translate(Scene *evil_scene, Sequence *seq, int delta)
{
+ if (delta == 0) {
+ return;
+ }
+
BKE_sequencer_offset_animdata(evil_scene, seq, delta);
seq->start += delta;
@@ -5069,7 +5119,7 @@ void BKE_sequencer_dupe_animdata(Scene *scene, const char *name_src, const char
for (fcu = scene->adt->action->curves.first; fcu && fcu->prev != fcu_last; fcu = fcu->next) {
if (STREQLEN(fcu->rna_path, str_from, str_from_len)) {
- fcu_cpy = copy_fcurve(fcu);
+ fcu_cpy = BKE_fcurve_copy(fcu);
BLI_addtail(&lb, fcu_cpy);
}
}
@@ -5102,7 +5152,7 @@ static void seq_free_animdata(Scene *scene, Sequence *seq)
FCurve *next_fcu = fcu->next;
BLI_remlink(&scene->adt->action->curves, fcu);
- free_fcurve(fcu);
+ BKE_fcurve_free(fcu);
fcu = next_fcu;
}
@@ -5775,7 +5825,7 @@ void BKE_sequence_base_dupli_recursive(const Scene *scene_src,
Sequence *seqn = NULL;
Sequence *last_seq = BKE_sequencer_active_get((Scene *)scene_src);
/* always include meta's strips */
- int dupe_flag_recursive = dupe_flag | SEQ_DUPE_ALL;
+ int dupe_flag_recursive = dupe_flag | SEQ_DUPE_ALL | SEQ_DUPE_IS_RECURSIVE_CALL;
for (seq = seqbase->first; seq; seq = seq->next) {
seq->tmp = NULL;
@@ -5801,6 +5851,12 @@ void BKE_sequence_base_dupli_recursive(const Scene *scene_src,
}
}
+ /* Fix modifier links recursively from the top level only, when all sequences have been
+ * copied. */
+ if (dupe_flag & SEQ_DUPE_IS_RECURSIVE_CALL) {
+ return;
+ }
+
/* fix modifier linking */
for (seq = nseqbase->first; seq; seq = seq->next) {
seq_new_fix_links_recursive(seq);
@@ -5921,3 +5977,62 @@ void BKE_sequencer_all_free_anim_ibufs(Scene *scene, int cfra)
sequencer_all_free_anim_ibufs(&ed->seqbase, cfra);
BKE_sequencer_cache_cleanup(scene);
}
+
+static bool sequencer_seq_generates_image(Sequence *seq)
+{
+ switch (seq->type) {
+ case SEQ_TYPE_IMAGE:
+ case SEQ_TYPE_SCENE:
+ case SEQ_TYPE_MOVIE:
+ case SEQ_TYPE_MOVIECLIP:
+ case SEQ_TYPE_MASK:
+ case SEQ_TYPE_COLOR:
+ case SEQ_TYPE_TEXT:
+ return true;
+ }
+ return false;
+}
+
+static Sequence *sequencer_check_scene_recursion(Scene *scene, ListBase *seqbase)
+{
+ LISTBASE_FOREACH (Sequence *, seq, seqbase) {
+ if (seq->type == SEQ_TYPE_SCENE && seq->scene == scene) {
+ return seq;
+ }
+
+ if (seq->type == SEQ_TYPE_META && sequencer_check_scene_recursion(scene, &seq->seqbase)) {
+ return seq;
+ }
+ }
+
+ return NULL;
+}
+
+bool BKE_sequencer_check_scene_recursion(Scene *scene, ReportList *reports)
+{
+ Editing *ed = BKE_sequencer_editing_get(scene, false);
+ if (ed == NULL) {
+ return false;
+ }
+
+ Sequence *recursive_seq = sequencer_check_scene_recursion(scene, &ed->seqbase);
+
+ if (recursive_seq != NULL) {
+ BKE_reportf(reports,
+ RPT_WARNING,
+ "Recursion detected in video sequencer. Strip %s at frame %d will not be rendered",
+ recursive_seq->name + 2,
+ recursive_seq->startdisp);
+
+ LISTBASE_FOREACH (Sequence *, seq, &ed->seqbase) {
+ if (seq->type != SEQ_TYPE_SCENE && sequencer_seq_generates_image(seq)) {
+ /* There are other strips to render, so render them. */
+ return false;
+ }
+ }
+ /* No other strips to render - cancel operator. */
+ return true;
+ }
+
+ return false;
+}