2.5: code changes to reduce the usage of G.main and pass it along
[blender.git] / source / blender / blenkernel / intern / sequencer.c
1 /**
2 * $Id$
3  *
4  * ***** BEGIN GPL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19  *
20  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
21  * All rights reserved.
22  *
23  * Contributor(s): 
24  * - Blender Foundation, 2003-2009
25  * - Peter Schlaile <peter [at] schlaile [dot] de> 2005/2006
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  */
29
30 #include <stddef.h>
31 #include <stdlib.h>
32 #include <string.h>
33 #include <math.h>
34
35 #include "MEM_guardedalloc.h"
36 #include "MEM_CacheLimiterC-Api.h"
37
38 #include "DNA_sequence_types.h"
39 #include "DNA_scene_types.h"
40 #include "DNA_anim_types.h"
41 #include "DNA_object_types.h"
42
43 #include "BKE_animsys.h"
44 #include "BKE_global.h"
45 #include "BKE_image.h"
46 #include "BKE_main.h"
47 #include "BKE_sequencer.h"
48 #include "BKE_fcurve.h"
49 #include "BKE_scene.h"
50 #include "RNA_access.h"
51 #include "RE_pipeline.h"
52
53 #include "BLI_math.h"
54 #include "BLI_fileops.h"
55 #include "BLI_listbase.h"
56 #include "BLI_path_util.h"
57 #include "BLI_string.h"
58 #include "BLI_threads.h"
59 #include <pthread.h>
60
61 #include "IMB_imbuf.h"
62 #include "IMB_imbuf_types.h"
63
64
65
66 #include "BKE_context.h"
67 #include "BKE_sound.h"
68 #include "AUD_C-API.h"
69
70 #ifdef WIN32
71 #define snprintf _snprintf
72 #endif
73
74 /* **** XXX ******** */
75 //static void waitcursor(int val) {}
76 //static int blender_test_break() {return 0;}
77
78 /* **** XXX ******** */
79 #define SELECT 1
80 ListBase seqbase_clipboard;
81 int seqbase_clipboard_frame;
82 SequencerDrawView sequencer_view3d_cb= NULL; /* NULL in background mode */
83
84
85 void printf_strip(Sequence *seq)
86 {
87         fprintf(stderr, "name: '%s', len:%d, start:%d, (startofs:%d, endofs:%d), (startstill:%d, endstill:%d), machine:%d, (startdisp:%d, enddisp:%d)\n",
88                         seq->name, seq->len, seq->start, seq->startofs, seq->endofs, seq->startstill, seq->endstill, seq->machine, seq->startdisp, seq->enddisp);
89         fprintf(stderr, "\tseq_tx_set_final_left: %d %d\n\n", seq_tx_get_final_left(seq, 0), seq_tx_get_final_right(seq, 0));
90 }
91
92 int seqbase_recursive_apply(ListBase *seqbase, int (*apply_func)(Sequence *seq, void *), void *arg)
93 {
94         Sequence *iseq;
95         for(iseq= seqbase->first; iseq; iseq= iseq->next) {
96                 if(seq_recursive_apply(iseq, apply_func, arg) == -1)
97                         return -1; /* bail out */
98         }
99         return 1;
100 }
101
102 int seq_recursive_apply(Sequence *seq, int (*apply_func)(Sequence *, void *), void *arg)
103 {
104         int ret= apply_func(seq, arg);
105
106         if(ret == -1)
107                 return -1;  /* bail out */
108
109         if(ret && seq->seqbase.first)
110                 ret = seqbase_recursive_apply(&seq->seqbase, apply_func, arg);
111
112         return ret;
113 }
114
115 /* **********************************************************************
116    alloc / free functions
117    ********************************************************************** */
118
119
120
121 void new_tstripdata(Sequence *seq)
122 {
123         if(seq->strip) {
124                 seq->strip->len= seq->len;
125         }
126 }
127
128
129 /* free */
130
131 static void free_proxy_seq(Sequence *seq)
132 {
133         if (seq->strip && seq->strip->proxy && seq->strip->proxy->anim) {
134                 IMB_free_anim(seq->strip->proxy->anim);
135                 seq->strip->proxy->anim = 0;
136         }
137 }
138
139 void seq_free_strip(Strip *strip)
140 {
141         strip->us--;
142         if(strip->us>0) return;
143         if(strip->us<0) {
144                 printf("error: negative users in strip\n");
145                 return;
146         }
147
148         if (strip->stripdata) {
149                 MEM_freeN(strip->stripdata);
150         }
151
152         if (strip->proxy) {
153                 if (strip->proxy->anim) {
154                         IMB_free_anim(strip->proxy->anim);
155                 }
156
157                 MEM_freeN(strip->proxy);
158         }
159         if (strip->crop) {
160                 MEM_freeN(strip->crop);
161         }
162         if (strip->transform) {
163                 MEM_freeN(strip->transform);
164         }
165         if (strip->color_balance) {
166                 MEM_freeN(strip->color_balance);
167         }
168
169         MEM_freeN(strip);
170 }
171
172 static void seq_free_animdata(Scene *scene, Sequence *seq);
173
174 void seq_free_sequence(Scene *scene, Sequence *seq)
175 {
176         if(seq->strip) seq_free_strip(seq->strip);
177
178         if(seq->anim) IMB_free_anim(seq->anim);
179
180         if (seq->type & SEQ_EFFECT) {
181                 struct SeqEffectHandle sh = get_sequence_effect(seq);
182
183                 sh.free(seq);
184         }
185
186         /* clipboard has no scene and will never have a sound handle or be active */
187         if(scene) {
188                 Editing *ed = scene->ed;
189
190                 if (ed->act_seq==seq)
191                         ed->act_seq= NULL;
192
193                 if(seq->scene_sound)
194                         sound_remove_scene_sound(scene, seq->scene_sound);
195
196                 seq_free_animdata(scene, seq);
197         }
198
199         MEM_freeN(seq);
200 }
201
202 Editing *seq_give_editing(Scene *scene, int alloc)
203 {
204         if (scene->ed == NULL && alloc) {
205                 Editing *ed;
206
207                 ed= scene->ed= MEM_callocN( sizeof(Editing), "addseq");
208                 ed->seqbasep= &ed->seqbase;
209         }
210         return scene->ed;
211 }
212
213 void seq_free_clipboard(void)
214 {
215         Sequence *seq, *nseq;
216
217         for(seq= seqbase_clipboard.first; seq; seq= nseq) {
218                 nseq= seq->next;
219                 seq_free_sequence(NULL, seq);
220         }
221         seqbase_clipboard.first= seqbase_clipboard.last= NULL;
222 }
223
224 void seq_free_editing(Scene *scene)
225 {
226         Editing *ed = scene->ed;
227         MetaStack *ms;
228         Sequence *seq;
229
230         if(ed==NULL)
231                 return;
232
233         SEQ_BEGIN(ed, seq) {
234                 seq_free_sequence(scene, seq);
235         }
236         SEQ_END
237
238         while((ms= ed->metastack.first)) {
239                 BLI_remlink(&ed->metastack, ms);
240                 MEM_freeN(ms);
241         }
242
243         MEM_freeN(ed);
244 }
245
246 /* ************************* itterator ************************** */
247 /* *************** (replaces old WHILE_SEQ) ********************* */
248 /* **************** use now SEQ_BEGIN() SEQ_END ***************** */
249
250 /* sequence strip iterator:
251  * - builds a full array, recursively into meta strips */
252
253 static void seq_count(ListBase *seqbase, int *tot)
254 {
255         Sequence *seq;
256
257         for(seq=seqbase->first; seq; seq=seq->next) {
258                 (*tot)++;
259
260                 if(seq->seqbase.first)
261                         seq_count(&seq->seqbase, tot);
262         }
263 }
264
265 static void seq_build_array(ListBase *seqbase, Sequence ***array, int depth)
266 {
267         Sequence *seq;
268
269         for(seq=seqbase->first; seq; seq=seq->next) {
270                 seq->depth= depth;
271
272                 if(seq->seqbase.first)
273                         seq_build_array(&seq->seqbase, array, depth+1);
274
275                 **array= seq;
276                 (*array)++;
277         }
278 }
279
280 void seq_array(Editing *ed, Sequence ***seqarray, int *tot, int use_pointer)
281 {
282         Sequence **array;
283
284         *seqarray= NULL;
285         *tot= 0;
286
287         if(ed == NULL)
288                 return;
289
290         if(use_pointer)
291                 seq_count(ed->seqbasep, tot);
292         else
293                 seq_count(&ed->seqbase, tot);
294
295         if(*tot == 0)
296                 return;
297
298         *seqarray= array= MEM_mallocN(sizeof(Sequence *)*(*tot), "SeqArray");
299         if(use_pointer)
300                 seq_build_array(ed->seqbasep, &array, 0);
301         else
302                 seq_build_array(&ed->seqbase, &array, 0);
303 }
304
305 void seq_begin(Editing *ed, SeqIterator *iter, int use_pointer)
306 {
307         memset(iter, 0, sizeof(*iter));
308         seq_array(ed, &iter->array, &iter->tot, use_pointer);
309
310         if(iter->tot) {
311                 iter->cur= 0;
312                 iter->seq= iter->array[iter->cur];
313                 iter->valid= 1;
314         }
315 }
316
317 void seq_next(SeqIterator *iter)
318 {
319         if(++iter->cur < iter->tot)
320                 iter->seq= iter->array[iter->cur];
321         else
322                 iter->valid= 0;
323 }
324
325 void seq_end(SeqIterator *iter)
326 {
327         if(iter->array)
328                 MEM_freeN(iter->array);
329
330         iter->valid= 0;
331 }
332
333 /*
334   **********************************************************************
335   * build_seqar
336   **********************************************************************
337   * Build a complete array of _all_ sequencies (including those
338   * in metastrips!)
339   **********************************************************************
340 */
341
342 static void do_seq_count(ListBase *seqbase, int *totseq)
343 {
344         Sequence *seq;
345
346         seq= seqbase->first;
347         while(seq) {
348                 (*totseq)++;
349                 if(seq->seqbase.first) do_seq_count(&seq->seqbase, totseq);
350                 seq= seq->next;
351         }
352 }
353
354 static void do_build_seqar(ListBase *seqbase, Sequence ***seqar, int depth)
355 {
356         Sequence *seq;
357
358         seq= seqbase->first;
359         while(seq) {
360                 seq->depth= depth;
361                 if(seq->seqbase.first) do_build_seqar(&seq->seqbase, seqar, depth+1);
362                 **seqar= seq;
363                 (*seqar)++;
364                 seq= seq->next;
365         }
366 }
367
368 void build_seqar(ListBase *seqbase, Sequence  ***seqar, int *totseq)
369 {
370         Sequence **tseqar;
371
372         *totseq= 0;
373         do_seq_count(seqbase, totseq);
374
375         if(*totseq==0) {
376                 *seqar= 0;
377                 return;
378         }
379         *seqar= MEM_mallocN(sizeof(void *)* *totseq, "seqar");
380         tseqar= *seqar;
381
382         do_build_seqar(seqbase, seqar, 0);
383         *seqar= tseqar;
384 }
385
386 static void do_seq_count_cb(ListBase *seqbase, int *totseq,
387                                 int (*test_func)(Sequence * seq))
388 {
389         Sequence *seq;
390
391         seq= seqbase->first;
392         while(seq) {
393                 int test = test_func(seq);
394                 if (test & BUILD_SEQAR_COUNT_CURRENT) {
395                         (*totseq)++;
396                 }
397                 if(seq->seqbase.first && (test & BUILD_SEQAR_COUNT_CHILDREN)) {
398                         do_seq_count_cb(&seq->seqbase, totseq, test_func);
399                 }
400                 seq= seq->next;
401         }
402 }
403
404 static void do_build_seqar_cb(ListBase *seqbase, Sequence ***seqar, int depth,
405                                   int (*test_func)(Sequence * seq))
406 {
407         Sequence *seq;
408
409         seq= seqbase->first;
410         while(seq) {
411                 int test = test_func(seq);
412                 seq->depth= depth;
413
414                 if(seq->seqbase.first && (test & BUILD_SEQAR_COUNT_CHILDREN)) {
415                         do_build_seqar_cb(&seq->seqbase, seqar, depth+1, 
416                                           test_func);
417                 }
418                 if (test & BUILD_SEQAR_COUNT_CURRENT) {
419                         **seqar= seq;
420                         (*seqar)++;
421                 }
422                 seq= seq->next;
423         }
424 }
425
426 void build_seqar_cb(ListBase *seqbase, Sequence  ***seqar, int *totseq,
427                         int (*test_func)(Sequence * seq))
428 {
429         Sequence **tseqar;
430
431         *totseq= 0;
432         do_seq_count_cb(seqbase, totseq, test_func);
433
434         if(*totseq==0) {
435                 *seqar= 0;
436                 return;
437         }
438         *seqar= MEM_mallocN(sizeof(void *)* *totseq, "seqar");
439         tseqar= *seqar;
440
441         do_build_seqar_cb(seqbase, seqar, 0, test_func);
442         *seqar= tseqar;
443 }
444
445
446 void calc_sequence_disp(Scene *scene, Sequence *seq)
447 {
448         if(seq->startofs && seq->startstill) seq->startstill= 0;
449         if(seq->endofs && seq->endstill) seq->endstill= 0;
450         
451         seq->startdisp= seq->start + seq->startofs - seq->startstill;
452         seq->enddisp= seq->start+seq->len - seq->endofs + seq->endstill;
453         
454         seq->handsize= 10.0;    /* 10 frames */
455         if( seq->enddisp-seq->startdisp < 10 ) {
456                 seq->handsize= (float)(0.5*(seq->enddisp-seq->startdisp));
457         }
458         else if(seq->enddisp-seq->startdisp > 250) {
459                 seq->handsize= (float)((seq->enddisp-seq->startdisp)/25);
460         }
461
462         seq_update_sound(scene, seq);
463 }
464
465 static void seq_update_sound_bounds_recursive(Scene *scene, Sequence *metaseq)
466 {
467         Sequence *seq;
468
469         /* for sound we go over full meta tree to update bounds of the sound strips,
470            since sound is played outside of evaluating the imbufs, */
471         for(seq=metaseq->seqbase.first; seq; seq=seq->next) {
472                 if(seq->type == SEQ_META) {
473                         seq_update_sound_bounds_recursive(scene, seq);
474                 }
475                 else if((seq->type == SEQ_SOUND) || (seq->type == SEQ_SCENE)) {
476                         if(seq->scene_sound) {
477                                 int startofs = seq->startofs;
478                                 int endofs = seq->endofs;
479                                 if(seq->startofs + seq->start < metaseq->start + metaseq->startofs)
480                                         startofs = metaseq->start + metaseq->startofs - seq->start;
481
482                                 if(seq->start + seq->len - seq->endofs > metaseq->start + metaseq->len - metaseq->endofs)
483                                         endofs = seq->start + seq->len - metaseq->start - metaseq->len + metaseq->endofs;
484                                 sound_move_scene_sound(scene, seq->scene_sound, seq->start + startofs, seq->start+seq->len - endofs, startofs);
485                         }
486                 }
487         }
488 }
489
490 void calc_sequence(Scene *scene, Sequence *seq)
491 {
492         Sequence *seqm;
493         int min, max;
494
495         /* check all metas recursively */
496         seqm= seq->seqbase.first;
497         while(seqm) {
498                 if(seqm->seqbase.first) calc_sequence(scene, seqm);
499                 seqm= seqm->next;
500         }
501
502         /* effects and meta: automatic start and end */
503
504         if(seq->type & SEQ_EFFECT) {
505                 /* pointers */
506                 if(seq->seq2==0) seq->seq2= seq->seq1;
507                 if(seq->seq3==0) seq->seq3= seq->seq1;
508
509                 /* effecten go from seq1 -> seq2: test */
510
511                 /* we take the largest start and smallest end */
512
513                 // seq->start= seq->startdisp= MAX2(seq->seq1->startdisp, seq->seq2->startdisp);
514                 // seq->enddisp= MIN2(seq->seq1->enddisp, seq->seq2->enddisp);
515
516                 if (seq->seq1) {
517                         seq->start= seq->startdisp= MAX3(seq->seq1->startdisp, seq->seq2->startdisp, seq->seq3->startdisp);
518                         seq->enddisp= MIN3(seq->seq1->enddisp, seq->seq2->enddisp, seq->seq3->enddisp);
519                         seq->len= seq->enddisp - seq->startdisp;
520                 } else {
521                         calc_sequence_disp(scene, seq);
522                 }
523
524                 if(seq->strip && seq->len!=seq->strip->len) {
525                         new_tstripdata(seq);
526                 }
527
528         }
529         else {
530                 if(seq->type==SEQ_META) {
531                         seqm= seq->seqbase.first;
532                         if(seqm) {
533                                 min=  MAXFRAME * 2;
534                                 max= -MAXFRAME * 2;
535                                 while(seqm) {
536                                         if(seqm->startdisp < min) min= seqm->startdisp;
537                                         if(seqm->enddisp > max) max= seqm->enddisp;
538                                         seqm= seqm->next;
539                                 }
540                                 seq->start= min + seq->anim_startofs;
541                                 seq->len = max-min;
542                                 seq->len -= seq->anim_startofs;
543                                 seq->len -= seq->anim_endofs;
544
545                                 if(seq->strip && seq->len!=seq->strip->len) {
546                                         new_tstripdata(seq);
547                                 }
548                         }
549                         seq_update_sound_bounds_recursive(scene, seq);
550                 }
551                 calc_sequence_disp(scene, seq);
552         }
553 }
554
555 /* note: caller should run calc_sequence(scene, seq) after */
556 void reload_sequence_new_file(Scene *scene, Sequence * seq, int lock_range)
557 {
558         char str[FILE_MAXDIR+FILE_MAXFILE];
559         int prev_startdisp, prev_enddisp;
560         /* note: dont rename the strip, will break animation curves */
561
562         if (!(seq->type == SEQ_MOVIE || seq->type == SEQ_IMAGE ||
563                   seq->type == SEQ_SOUND ||
564                   seq->type == SEQ_SCENE || seq->type == SEQ_META)) {
565                 return;
566         }
567
568         if(lock_range) {
569                 /* keep so we dont have to move the actual start and end points (only the data) */
570                 calc_sequence_disp(scene, seq);
571                 prev_startdisp= seq->startdisp;
572                 prev_enddisp= seq->enddisp;
573         }
574
575
576         new_tstripdata(seq);
577
578         if (seq->type != SEQ_SCENE && seq->type != SEQ_META &&
579                 seq->type != SEQ_IMAGE) {
580                 BLI_join_dirfile(str, seq->strip->dir, seq->strip->stripdata->name);
581                 BLI_path_abs(str, G.sce);
582         }
583
584         if (seq->type == SEQ_IMAGE) {
585                 /* Hack? */
586                 size_t olen = MEM_allocN_len(seq->strip->stripdata)/sizeof(struct StripElem);
587
588                 seq->len = olen;
589                 seq->len -= seq->anim_startofs;
590                 seq->len -= seq->anim_endofs;
591                 if (seq->len < 0) {
592                         seq->len = 0;
593                 }
594                 seq->strip->len = seq->len;
595         } else if (seq->type == SEQ_MOVIE) {
596                 if(seq->anim) IMB_free_anim(seq->anim);
597                 seq->anim = openanim(str, IB_rect | ((seq->flag & SEQ_FILTERY) ? IB_animdeinterlace : 0));
598
599                 if (!seq->anim) {
600                         return;
601                 }
602         
603                 seq->len = IMB_anim_get_duration(seq->anim);
604                 
605                 seq->anim_preseek = IMB_anim_get_preseek(seq->anim);
606
607                 seq->len -= seq->anim_startofs;
608                 seq->len -= seq->anim_endofs;
609                 if (seq->len < 0) {
610                         seq->len = 0;
611                 }
612                 seq->strip->len = seq->len;
613         } else if (seq->type == SEQ_SOUND) {
614                 seq->len = ceil(AUD_getInfo(seq->sound->playback_handle).length * FPS);
615                 seq->len -= seq->anim_startofs;
616                 seq->len -= seq->anim_endofs;
617                 if (seq->len < 0) {
618                         seq->len = 0;
619                 }
620                 seq->strip->len = seq->len;
621         } else if (seq->type == SEQ_SCENE) {
622                 /* 'seq->scenenr' should be replaced with something more reliable */
623                 Scene * sce = G.main->scene.first;
624                 int nr = 1;
625                 
626                 while(sce) {
627                         if(nr == seq->scenenr) {
628                                 break;
629                         }
630                         nr++;
631                         sce= sce->id.next;
632                 }
633
634                 if (sce) {
635                         seq->scene = sce;
636                 } else {
637                         sce = seq->scene;
638                 }
639                 
640                 seq->len= seq->scene->r.efra - seq->scene->r.sfra + 1;
641                 seq->len -= seq->anim_startofs;
642                 seq->len -= seq->anim_endofs;
643                 if (seq->len < 0) {
644                         seq->len = 0;
645                 }
646                 seq->strip->len = seq->len;
647         }
648
649         free_proxy_seq(seq);
650
651         if(lock_range) {
652                 seq_tx_set_final_left(seq, prev_startdisp);
653                 seq_tx_set_final_right(seq, prev_enddisp);
654                 seq_single_fix(seq);
655         }
656         
657         calc_sequence(scene, seq);
658 }
659
660 void sort_seq(Scene *scene)
661 {
662         /* all strips together per kind, and in order of y location ("machine") */
663         ListBase seqbase, effbase;
664         Editing *ed= seq_give_editing(scene, FALSE);
665         Sequence *seq, *seqt;
666
667         
668         if(ed==NULL) return;
669
670         seqbase.first= seqbase.last= 0;
671         effbase.first= effbase.last= 0;
672
673         while( (seq= ed->seqbasep->first) ) {
674                 BLI_remlink(ed->seqbasep, seq);
675
676                 if(seq->type & SEQ_EFFECT) {
677                         seqt= effbase.first;
678                         while(seqt) {
679                                 if(seqt->machine>=seq->machine) {
680                                         BLI_insertlinkbefore(&effbase, seqt, seq);
681                                         break;
682                                 }
683                                 seqt= seqt->next;
684                         }
685                         if(seqt==0) BLI_addtail(&effbase, seq);
686                 }
687                 else {
688                         seqt= seqbase.first;
689                         while(seqt) {
690                                 if(seqt->machine>=seq->machine) {
691                                         BLI_insertlinkbefore(&seqbase, seqt, seq);
692                                         break;
693                                 }
694                                 seqt= seqt->next;
695                         }
696                         if(seqt==0) BLI_addtail(&seqbase, seq);
697                 }
698         }
699
700         addlisttolist(&seqbase, &effbase);
701         *(ed->seqbasep)= seqbase;
702 }
703
704
705 static int clear_scene_in_allseqs_cb(Sequence *seq, void *arg_pt)
706 {
707         if(seq->scene==(Scene *)arg_pt)
708                 seq->scene= NULL;
709         return 1;
710 }
711
712 void clear_scene_in_allseqs(Scene *scene)
713 {
714         Scene *scene_iter;
715
716         /* when a scene is deleted: test all seqs */
717         for(scene_iter= G.main->scene.first; scene_iter; scene_iter= scene_iter->id.next) {
718                 if(scene_iter != scene && scene_iter->ed) {
719                         seqbase_recursive_apply(&scene_iter->ed->seqbase, clear_scene_in_allseqs_cb, scene);
720                 }
721         }
722 }
723
724 typedef struct SeqUniqueInfo {
725         Sequence *seq;
726         char name_src[32];
727         char name_dest[32];
728         int count;
729         int match;
730 } SeqUniqueInfo;
731
732 /*
733 static void seqbase_unique_name(ListBase *seqbasep, Sequence *seq)
734 {
735          BLI_uniquename(seqbasep, seq, "Sequence", '.', offsetof(Sequence, name), SEQ_NAME_MAXSTR);
736 }*/
737
738 static void seqbase_unique_name(ListBase *seqbasep, SeqUniqueInfo *sui)
739 {
740         Sequence *seq;
741         for(seq=seqbasep->first; seq; seq= seq->next) {
742                 if (sui->seq != seq && strcmp(sui->name_dest, seq->name+2)==0) {
743                         sprintf(sui->name_dest, "%.17s.%03d",  sui->name_src, sui->count++); /*24 - 2 for prefix, -1 for \0 */
744                         sui->match= 1; /* be sure to re-scan */
745                 }
746         }
747 }
748
749 static int seqbase_unique_name_recursive_cb(Sequence *seq, void *arg_pt)
750 {
751         if(seq->seqbase.first)
752                 seqbase_unique_name(&seq->seqbase, (SeqUniqueInfo *)arg_pt);
753         return 1;
754 }
755
756 void seqbase_unique_name_recursive(ListBase *seqbasep, struct Sequence *seq)
757 {
758         SeqUniqueInfo sui;
759         char *dot;
760         sui.seq= seq;
761         strcpy(sui.name_src, seq->name+2);
762         strcpy(sui.name_dest, seq->name+2);
763
764         sui.count= 1;
765         sui.match= 1; /* assume the worst to start the loop */
766
767         /* Strip off the suffix */
768         if ((dot=strrchr(sui.name_src, '.'))) {
769                 *dot= '\0';
770                 dot++;
771
772                 if(*dot)
773                         sui.count= atoi(dot) + 1;
774         }
775
776         while(sui.match) {
777                 sui.match= 0;
778                 seqbase_unique_name(seqbasep, &sui);
779                 seqbase_recursive_apply(seqbasep, seqbase_unique_name_recursive_cb, &sui);
780         }
781
782         strcpy(seq->name+2, sui.name_dest);
783 }
784
785 static char *give_seqname_by_type(int type)
786 {
787         switch(type) {
788         case SEQ_META:       return "Meta";
789         case SEQ_IMAGE:      return "Image";
790         case SEQ_SCENE:      return "Scene";
791         case SEQ_MOVIE:      return "Movie";
792         case SEQ_SOUND:      return "Audio";
793         case SEQ_CROSS:      return "Cross";
794         case SEQ_GAMCROSS:   return "Gamma Cross";
795         case SEQ_ADD:        return "Add";
796         case SEQ_SUB:        return "Sub";
797         case SEQ_MUL:        return "Mul";
798         case SEQ_ALPHAOVER:  return "Alpha Over";
799         case SEQ_ALPHAUNDER: return "Alpha Under";
800         case SEQ_OVERDROP:   return "Over Drop";
801         case SEQ_WIPE:       return "Wipe";
802         case SEQ_GLOW:       return "Glow";
803         case SEQ_TRANSFORM:  return "Transform";
804         case SEQ_COLOR:      return "Color";
805         case SEQ_MULTICAM:   return "Multicam";
806         case SEQ_SPEED:      return "Speed";
807         default:
808                 return 0;
809         }
810 }
811
812 char *give_seqname(Sequence *seq)
813 {
814         char * name = give_seqname_by_type(seq->type);
815
816         if (!name) {
817                 if(seq->type<SEQ_EFFECT) {
818                         return seq->strip->dir;
819                 } else if(seq->type==SEQ_PLUGIN) {
820                         if(!(seq->flag & SEQ_EFFECT_NOT_LOADED) &&
821                            seq->plugin && seq->plugin->doit) {
822                                 return seq->plugin->pname;
823                         } else {
824                                 return "Plugin";
825                         }
826                 } else {
827                         return "Effect";
828                 }
829         }
830         return name;
831 }
832
833 /* ***************** DO THE SEQUENCE ***************** */
834
835 static void make_black_ibuf(ImBuf *ibuf)
836 {
837         unsigned int *rect;
838         float *rect_float;
839         int tot;
840
841         if(ibuf==0 || (ibuf->rect==0 && ibuf->rect_float==0)) return;
842
843         tot= ibuf->x*ibuf->y;
844
845         rect= ibuf->rect;
846         rect_float = ibuf->rect_float;
847
848         if (rect) {
849                 memset(rect,       0, tot * sizeof(char) * 4);
850         }
851
852         if (rect_float) {
853                 memset(rect_float, 0, tot * sizeof(float) * 4);
854         }
855 }
856
857 static void multibuf(ImBuf *ibuf, float fmul)
858 {
859         char *rt;
860         float *rt_float;
861
862         int a, mul, icol;
863
864         mul= (int)(256.0*fmul);
865         rt= (char *)ibuf->rect;
866         rt_float = ibuf->rect_float;
867
868         if (rt) {
869                 a= ibuf->x*ibuf->y;
870                 while(a--) {
871
872                         icol= (mul*rt[0])>>8;
873                         if(icol>254) rt[0]= 255; else rt[0]= icol;
874                         icol= (mul*rt[1])>>8;
875                         if(icol>254) rt[1]= 255; else rt[1]= icol;
876                         icol= (mul*rt[2])>>8;
877                         if(icol>254) rt[2]= 255; else rt[2]= icol;
878                         icol= (mul*rt[3])>>8;
879                         if(icol>254) rt[3]= 255; else rt[3]= icol;
880                         
881                         rt+= 4;
882                 }
883         }
884         if (rt_float) {
885                 a= ibuf->x*ibuf->y;
886                 while(a--) {
887                         rt_float[0] *= fmul;
888                         rt_float[1] *= fmul;
889                         rt_float[2] *= fmul;
890                         rt_float[3] *= fmul;
891                         
892                         rt_float += 4;
893                 }
894         }
895 }
896
897 static float give_stripelem_index(Sequence *seq, float cfra)
898 {
899         float nr;
900
901         if(seq->startdisp >cfra || seq->enddisp <= cfra) return -1;
902         if(seq->len == 0) return -1;
903         if(seq->flag&SEQ_REVERSE_FRAMES) {      
904                 /*reverse frame in this sequence */
905                 if(cfra <= seq->start) nr= seq->len-1;
906                 else if(cfra >= seq->start+seq->len-1) nr= 0;
907                 else nr= (seq->start + seq->len - 1) - cfra;
908         } else {
909                 if(cfra <= seq->start) nr= 0;
910                 else if(cfra >= seq->start+seq->len-1) nr= seq->len-1;
911                 else nr= cfra-seq->start;
912         }
913         if (seq->strobe < 1.0) seq->strobe = 1.0;
914         if (seq->strobe > 1.0) {
915                 nr -= fmod((double)nr, (double)seq->strobe);
916         }
917
918         return nr;
919 }
920
921 StripElem *give_stripelem(Sequence *seq, int cfra)
922 {
923         StripElem *se= seq->strip->stripdata;
924
925         if(seq->type == SEQ_MOVIE) {
926                 /* use the first */
927         }
928         else {
929                 int nr = (int) give_stripelem_index(seq, cfra);
930
931                 if (nr == -1) return 0;
932                 if (se == 0) return 0;
933         
934                 se += nr + seq->anim_startofs;
935         }
936         return se;
937 }
938
939 static int evaluate_seq_frame_gen(Sequence ** seq_arr, ListBase *seqbase, int cfra)
940 {
941         Sequence *seq;
942         int totseq=0;
943
944         memset(seq_arr, 0, sizeof(Sequence*) * (MAXSEQ+1));
945
946         seq= seqbase->first;
947         while(seq) {
948                 if(seq->startdisp <=cfra && seq->enddisp > cfra) {
949                         seq_arr[seq->machine]= seq;
950                         totseq++;
951                 }
952                 seq= seq->next;
953         }
954
955         return totseq;
956 }
957
958 int evaluate_seq_frame(Scene *scene, int cfra)
959 {
960         Editing *ed= seq_give_editing(scene, FALSE);
961         Sequence *seq_arr[MAXSEQ+1];
962
963         if(ed==NULL) return 0;
964         return evaluate_seq_frame_gen(seq_arr, ed->seqbasep, cfra);
965 }
966
967 static int video_seq_is_rendered(Sequence * seq)
968 {
969         return (seq
970                 && !(seq->flag & SEQ_MUTE)
971                 && seq->type != SEQ_SOUND);
972 }
973
974 static int get_shown_sequences( ListBase * seqbasep, int cfra, int chanshown, Sequence ** seq_arr_out)
975 {
976         Sequence *seq_arr[MAXSEQ+1];
977         int b = chanshown;
978         int cnt = 0;
979
980         if (b > MAXSEQ) {
981                 return 0;
982         }
983
984         if(evaluate_seq_frame_gen(seq_arr, seqbasep, cfra)) {
985                 if (b > 0) {
986                         if (seq_arr[b] == 0) {
987                                 return 0;
988                         }
989                 } else {
990                         for (b = MAXSEQ; b > 0; b--) {
991                                 if (video_seq_is_rendered(seq_arr[b])) {
992                                         break;
993                                 }
994                         }
995                 }
996         }
997         
998         chanshown = b;
999
1000         for (;b > 0; b--) {
1001                 if (video_seq_is_rendered(seq_arr[b])) {
1002                         if (seq_arr[b]->blend_mode == SEQ_BLEND_REPLACE) {
1003                                 break;
1004                         }
1005                 }
1006         }
1007
1008         for (;b <= chanshown; b++) {
1009                 if (video_seq_is_rendered(seq_arr[b])) {
1010                         seq_arr_out[cnt++] = seq_arr[b];
1011                 }
1012         }
1013
1014         return cnt;
1015 }
1016  
1017
1018 /* **********************************************************************
1019    proxy management
1020    ********************************************************************** */
1021
1022 #define PROXY_MAXFILE (2*FILE_MAXDIR+FILE_MAXFILE)
1023
1024 static int seq_proxy_get_fname(Scene *scene, Sequence * seq, int cfra, char * name, int render_size)
1025 {
1026         int frameno;
1027         char dir[FILE_MAXDIR];
1028
1029         if (!seq->strip->proxy) {
1030                 return FALSE;
1031         }
1032
1033         if ((seq->flag & SEQ_USE_PROXY_CUSTOM_DIR)
1034             || (seq->flag & SEQ_USE_PROXY_CUSTOM_FILE)) {
1035                 strcpy(dir, seq->strip->proxy->dir);
1036         } else {
1037                 if (seq->type == SEQ_IMAGE || seq->type == SEQ_MOVIE) {
1038                         snprintf(dir, FILE_MAXDIR, "%s/BL_proxy", 
1039                                  seq->strip->dir);
1040                 } else {
1041                         return FALSE;
1042                 }
1043         }
1044
1045         if (seq->flag & SEQ_USE_PROXY_CUSTOM_FILE) {
1046                 BLI_join_dirfile(name, dir, seq->strip->proxy->file);
1047                 BLI_path_abs(name, G.sce);
1048
1049                 return TRUE;
1050         }
1051
1052         /* generate a separate proxy directory for each preview size */
1053
1054         if (seq->type == SEQ_IMAGE) {
1055                 StripElem * se = give_stripelem(seq, cfra);
1056                 snprintf(name, PROXY_MAXFILE, "%s/images/%d/%s_proxy",
1057                          dir, render_size, se->name);
1058                 frameno = 1;
1059         } else if (seq->type == SEQ_MOVIE) {
1060                 frameno = (int) give_stripelem_index(seq, cfra) 
1061                         + seq->anim_startofs;
1062
1063                 snprintf(name, PROXY_MAXFILE, "%s/%s/%d/####", dir,
1064                          seq->strip->stripdata->name,
1065                          render_size);
1066         } else {
1067                 frameno = (int) give_stripelem_index(seq, cfra) 
1068                         + seq->anim_startofs;
1069
1070                 snprintf(name, PROXY_MAXFILE, "%s/proxy_misc/%d/####", dir,
1071                          render_size);
1072         }
1073
1074         BLI_path_abs(name, G.sce);
1075         BLI_path_frame(name, frameno, 0);
1076
1077
1078         strcat(name, ".jpg");
1079
1080         return TRUE;
1081 }
1082
1083 static struct ImBuf * seq_proxy_fetch(Scene *scene, Sequence * seq, int cfra, int render_size)
1084 {
1085         char name[PROXY_MAXFILE];
1086
1087         if (!(seq->flag & SEQ_USE_PROXY)) {
1088                 return 0;
1089         }
1090
1091         /* rendering at 100% ? No real sense in proxy-ing, right? */
1092         if (render_size == 100) {
1093                 return 0;
1094         }
1095
1096         if (seq->flag & SEQ_USE_PROXY_CUSTOM_FILE) {
1097                 int frameno = (int) give_stripelem_index(seq, cfra) 
1098                         + seq->anim_startofs;
1099                 if (!seq->strip->proxy->anim) {
1100                         if (!seq_proxy_get_fname(
1101                                     scene, seq, cfra, name, render_size)) {
1102                                 return 0;
1103                         }
1104  
1105                         seq->strip->proxy->anim = openanim(name, IB_rect);
1106                 }
1107                 if (!seq->strip->proxy->anim) {
1108                         return 0;
1109                 }
1110  
1111                 return IMB_anim_absolute(seq->strip->proxy->anim, frameno);
1112         }
1113  
1114         if (!seq_proxy_get_fname(scene, seq, cfra, name, render_size)) {
1115                 return 0;
1116         }
1117
1118         if (BLI_exists(name)) {
1119                 return IMB_loadiffname(name, IB_rect);
1120         } else {
1121                 return 0;
1122         }
1123 }
1124
1125 #if 0
1126 static void do_build_seq_ibuf(Scene *scene, Sequence * seq, TStripElem *se, int cfra,
1127                                   int build_proxy_run, int render_size);
1128
1129 static void seq_proxy_build_frame(Scene *scene, Sequence * seq, int cfra, int render_size, int seqrectx, int seqrecty)
1130 {
1131         char name[PROXY_MAXFILE];
1132         int quality;
1133         TStripElem * se;
1134         int ok;
1135         int rectx, recty;
1136         struct ImBuf * ibuf;
1137
1138         if (!(seq->flag & SEQ_USE_PROXY)) {
1139                 return;
1140         }
1141
1142         /* rendering at 100% ? No real sense in proxy-ing, right? */
1143         if (render_size == 100) {
1144                 return;
1145         }
1146
1147         /* that's why it is called custom... */
1148         if (seq->flag & SEQ_USE_PROXY_CUSTOM_FILE) {
1149                 return;
1150         }
1151
1152         if (!seq_proxy_get_fname(scene, seq, cfra, name, render_size)) {
1153                 return;
1154         }
1155
1156         se = give_tstripelem(seq, cfra);
1157         if (!se) {
1158                 return;
1159         }
1160
1161         if(se->ibuf) {
1162                 IMB_freeImBuf(se->ibuf);
1163                 se->ibuf = 0;
1164         }
1165         
1166         do_build_seq_ibuf(scene, seq, se, cfra, TRUE, render_size,
1167                           seqrectx, seqrecty);
1168
1169         if (!se->ibuf) {
1170                 return;
1171         }
1172
1173         rectx= (render_size*scene->r.xsch)/100;
1174         recty= (render_size*scene->r.ysch)/100;
1175
1176         ibuf = se->ibuf;
1177
1178         if (ibuf->x != rectx || ibuf->y != recty) {
1179                 IMB_scalefastImBuf(ibuf, (short)rectx, (short)recty);
1180         }
1181
1182         /* quality is fixed, otherwise one has to generate separate
1183            directories for every quality...
1184
1185            depth = 32 is intentionally left in, otherwise ALPHA channels
1186            won't work... */
1187         quality = seq->strip->proxy->quality;
1188         ibuf->ftype= JPG | quality;
1189
1190         BLI_make_existing_file(name);
1191         
1192         ok = IMB_saveiff(ibuf, name, IB_rect | IB_zbuf | IB_zbuffloat);
1193         if (ok == 0) {
1194                 perror(name);
1195         }
1196
1197         IMB_freeImBuf(ibuf);
1198         se->ibuf = 0;
1199 }
1200
1201 static void seq_proxy_rebuild(Scene *scene, Sequence * seq, int seqrectx,
1202                               int seqrecty)
1203 {
1204         int cfra;
1205         float rsize = seq->strip->proxy->size;
1206
1207         waitcursor(1);
1208
1209         G.afbreek = 0;
1210
1211         /* flag management tries to account for strobe and 
1212            other "non-linearities", that might come in the future...
1213            better way would be to "touch" the files, so that _really_
1214            no one is rebuild twice.
1215          */
1216
1217         for (cfra = seq->startdisp; cfra < seq->enddisp; cfra++) {
1218                 TStripElem * tse = give_tstripelem(seq, cfra);
1219
1220                 tse->flag &= ~STRIPELEM_PREVIEW_DONE;
1221         }
1222
1223         
1224
1225         /* a _lot_ faster for movie files, if we read frames in
1226            sequential order */
1227         if (seq->flag & SEQ_REVERSE_FRAMES) {
1228                 for (cfra = seq->enddisp-seq->endstill-1; 
1229                          cfra >= seq->startdisp + seq->startstill; cfra--) {
1230                         TStripElem * tse = give_tstripelem(seq, cfra);
1231
1232                         if (!(tse->flag & STRIPELEM_PREVIEW_DONE)) {
1233 //XXX                           set_timecursor(cfra);
1234                                 seq_proxy_build_frame(scene, seq, cfra, rsize,
1235                                                       seqrectx, seqrecty);
1236                                 tse->flag |= STRIPELEM_PREVIEW_DONE;
1237                         }
1238                         if (blender_test_break()) {
1239                                 break;
1240                         }
1241                 }
1242         } else {
1243                 for (cfra = seq->startdisp + seq->startstill; 
1244                          cfra < seq->enddisp - seq->endstill; cfra++) {
1245                         TStripElem * tse = give_tstripelem(seq, cfra);
1246
1247                         if (!(tse->flag & STRIPELEM_PREVIEW_DONE)) {
1248 //XXX                           set_timecursor(cfra);
1249                                 seq_proxy_build_frame(scene, seq, cfra, rsize,
1250                                                       seqrectx, seqrecty);
1251                                 tse->flag |= STRIPELEM_PREVIEW_DONE;
1252                         }
1253                         if (blender_test_break()) {
1254                                 break;
1255                         }
1256                 }
1257         }
1258         waitcursor(0);
1259 }
1260 #endif
1261
1262
1263 /* **********************************************************************
1264    color balance 
1265    ********************************************************************** */
1266
1267 static StripColorBalance calc_cb(StripColorBalance * cb_)
1268 {
1269         StripColorBalance cb = *cb_;
1270         int c;
1271
1272         for (c = 0; c < 3; c++) {
1273                 cb.lift[c] = 2.0f - cb.lift[c];
1274         }
1275
1276         if(cb.flag & SEQ_COLOR_BALANCE_INVERSE_LIFT) {
1277                 for (c = 0; c < 3; c++) {
1278                         /* tweak to give more subtle results
1279                          * values above 1.0 are scaled */
1280                         if(cb.lift[c] > 1.0f)
1281                                 cb.lift[c] = pow(cb.lift[c] - 1.0f, 2.0f) + 1.0f;
1282
1283                         cb.lift[c] = 2.0f - cb.lift[c];
1284                 }
1285         }
1286
1287         if (cb.flag & SEQ_COLOR_BALANCE_INVERSE_GAIN) {
1288                 for (c = 0; c < 3; c++) {
1289                         if (cb.gain[c] != 0.0) {
1290                                 cb.gain[c] = 1.0/cb.gain[c];
1291                         } else {
1292                                 cb.gain[c] = 1000000; /* should be enough :) */
1293                         }
1294                 }
1295         }
1296
1297         if (!(cb.flag & SEQ_COLOR_BALANCE_INVERSE_GAMMA)) {
1298                 for (c = 0; c < 3; c++) {
1299                         if (cb.gamma[c] != 0.0) {
1300                                 cb.gamma[c] = 1.0/cb.gamma[c];
1301                         } else {
1302                                 cb.gamma[c] = 1000000; /* should be enough :) */
1303                         }
1304                 }
1305         }
1306
1307         return cb;
1308 }
1309
1310 /* note: lift is actually 2-lift */
1311 MINLINE float color_balance_fl(float in, const float lift, const float gain, const float gamma, const float mul)
1312 {
1313         float x= (((in - 1.0f) * lift) + 1.0f) * gain;
1314
1315         /* prevent NaN */
1316         if (x < 0.f) x = 0.f;
1317
1318         return powf(x, gamma) * mul;
1319 }
1320
1321 static void make_cb_table_byte(float lift, float gain, float gamma,
1322                                    unsigned char * table, float mul)
1323 {
1324         int y;
1325
1326         for (y = 0; y < 256; y++) {
1327                 float v= color_balance_fl((float)y * (1.0 / 255.0f), lift, gain, gamma, mul);
1328                 CLAMP(v, 0.0f, 1.0f);
1329                 table[y] = v * 255;
1330         }
1331 }
1332
1333 static void make_cb_table_float(float lift, float gain, float gamma,
1334                                 float * table, float mul)
1335 {
1336         int y;
1337
1338         for (y = 0; y < 256; y++) {
1339                 float v= color_balance_fl((float)y * (1.0 / 255.0f), lift, gain, gamma, mul);
1340                 table[y] = v;
1341         }
1342 }
1343
1344 static void color_balance_byte_byte(Sequence * seq, ImBuf* ibuf, float mul)
1345 {
1346         unsigned char cb_tab[3][256];
1347         int c;
1348         unsigned char * p = (unsigned char*) ibuf->rect;
1349         unsigned char * e = p + ibuf->x * 4 * ibuf->y;
1350
1351         StripColorBalance cb = calc_cb(seq->strip->color_balance);
1352
1353         for (c = 0; c < 3; c++) {
1354                 make_cb_table_byte(cb.lift[c], cb.gain[c], cb.gamma[c],
1355                                    cb_tab[c], mul);
1356         }
1357
1358         while (p < e) {
1359                 p[0] = cb_tab[0][p[0]];
1360                 p[1] = cb_tab[1][p[1]];
1361                 p[2] = cb_tab[2][p[2]];
1362                 
1363                 p += 4;
1364         }
1365 }
1366
1367 static void color_balance_byte_float(Sequence * seq, ImBuf* ibuf, float mul)
1368 {
1369         float cb_tab[4][256];
1370         int c,i;
1371         unsigned char * p = (unsigned char*) ibuf->rect;
1372         unsigned char * e = p + ibuf->x * 4 * ibuf->y;
1373         float * o;
1374         StripColorBalance cb;
1375
1376         imb_addrectfloatImBuf(ibuf);
1377
1378         o = ibuf->rect_float;
1379
1380         cb = calc_cb(seq->strip->color_balance);
1381
1382         for (c = 0; c < 3; c++) {
1383                 make_cb_table_float(cb.lift[c], cb.gain[c], cb.gamma[c],
1384                                     cb_tab[c], mul);
1385         }
1386
1387         for (i = 0; i < 256; i++) {
1388                 cb_tab[3][i] = ((float)i)*(1.0f/255.0f);
1389         }
1390
1391         while (p < e) {
1392                 o[0] = cb_tab[0][p[0]];
1393                 o[1] = cb_tab[1][p[1]];
1394                 o[2] = cb_tab[2][p[2]];
1395                 o[3] = cb_tab[3][p[3]];
1396
1397                 p += 4; o += 4;
1398         }
1399 }
1400
1401 static void color_balance_float_float(Sequence * seq, ImBuf* ibuf, float mul)
1402 {
1403         float * p = ibuf->rect_float;
1404         float * e = ibuf->rect_float + ibuf->x * 4* ibuf->y;
1405         StripColorBalance cb = calc_cb(seq->strip->color_balance);
1406
1407         while (p < e) {
1408                 int c;
1409                 for (c = 0; c < 3; c++) {
1410                         p[c]= color_balance_fl(p[c], cb.lift[c], cb.gain[c], cb.gamma[c], mul);
1411                 }
1412                 p += 4;
1413         }
1414 }
1415
1416 static void color_balance(Sequence * seq, ImBuf* ibuf, float mul)
1417 {
1418         if (ibuf->rect_float) {
1419                 color_balance_float_float(seq, ibuf, mul);
1420         } else if(seq->flag & SEQ_MAKE_FLOAT) {
1421                 color_balance_byte_float(seq, ibuf, mul);
1422         } else {
1423                 color_balance_byte_byte(seq, ibuf, mul);
1424         }
1425 }
1426
1427 /*
1428   input preprocessing for SEQ_IMAGE, SEQ_MOVIE and SEQ_SCENE
1429
1430   Do all the things you can't really do afterwards using sequence effects
1431   (read: before rescaling to render resolution has been done)
1432
1433   Order is important!
1434
1435   - Deinterlace
1436   - Crop and transform in image source coordinate space
1437   - Flip X + Flip Y (could be done afterwards, backward compatibility)
1438   - Promote image to float data (affects pipeline operations afterwards)
1439   - Color balance (is most efficient in the byte -> float 
1440         (future: half -> float should also work fine!)
1441         case, if done on load, since we can use lookup tables)
1442   - Premultiply
1443
1444 */
1445
1446 int input_have_to_preprocess(
1447         Scene *scene, Sequence * seq, float cfra, int seqrectx, int seqrecty)
1448 {
1449         float mul;
1450
1451         if ((seq->flag & SEQ_FILTERY) || 
1452             (seq->flag & SEQ_USE_CROP) ||
1453             (seq->flag & SEQ_USE_TRANSFORM) ||
1454             (seq->flag & SEQ_FLIPX) ||
1455             (seq->flag & SEQ_FLIPY) ||
1456             (seq->flag & SEQ_USE_COLOR_BALANCE) ||
1457             (seq->flag & SEQ_MAKE_PREMUL)) {
1458                 return TRUE;
1459         }
1460
1461         mul = seq->mul;
1462
1463         if(seq->blend_mode == SEQ_BLEND_REPLACE &&
1464            !(seq->type & SEQ_EFFECT)) {
1465                 mul *= seq->blend_opacity / 100.0;
1466         }
1467
1468         if (mul != 1.0) {
1469                 return TRUE;
1470         }
1471
1472         if (seq->sat != 1.0) {
1473                 return TRUE;
1474         }
1475                 
1476         return FALSE;
1477 }
1478
1479 static ImBuf * input_preprocess(
1480         Scene *scene, Sequence *seq, float cfra, int seqrectx, int seqrecty,
1481         ImBuf * ibuf)
1482 {
1483         float mul;
1484
1485         seq->strip->orx= ibuf->x;
1486         seq->strip->ory= ibuf->y;
1487
1488         if((seq->flag & SEQ_FILTERY) && seq->type != SEQ_MOVIE) {
1489                 IMB_filtery(ibuf);
1490         }
1491
1492         if(seq->flag & SEQ_USE_CROP || seq->flag & SEQ_USE_TRANSFORM) {
1493                 StripCrop c;
1494                 StripTransform t;
1495                 int sx,sy,dx,dy;
1496
1497                 memset(&c, 0, sizeof(StripCrop));
1498                 memset(&t, 0, sizeof(StripTransform));
1499
1500                 if(seq->flag & SEQ_USE_CROP && seq->strip->crop) {
1501                         c = *seq->strip->crop;
1502                 }
1503                 if(seq->flag & SEQ_USE_TRANSFORM && seq->strip->transform) {
1504                         t = *seq->strip->transform;
1505                 }
1506
1507                 sx = ibuf->x - c.left - c.right;
1508                 sy = ibuf->y - c.top - c.bottom;
1509                 dx = sx;
1510                 dy = sy;
1511
1512                 if (seq->flag & SEQ_USE_TRANSFORM) {
1513                         dx = scene->r.xsch;
1514                         dy = scene->r.ysch;
1515                 }
1516
1517                 if (c.top + c.bottom >= ibuf->y ||
1518                         c.left + c.right >= ibuf->x ||
1519                         t.xofs >= dx || t.yofs >= dy) {
1520                         make_black_ibuf(ibuf);
1521                 } else {
1522                         ImBuf * i;
1523
1524                         if (ibuf->rect_float) {
1525                                 i = IMB_allocImBuf(dx, dy,32, IB_rectfloat, 0);
1526                         } else {
1527                                 i = IMB_allocImBuf(dx, dy,32, IB_rect, 0);
1528                         }
1529
1530                         IMB_rectcpy(i, ibuf, 
1531                                     t.xofs, t.yofs, 
1532                                     c.left, c.bottom, 
1533                                     sx, sy);
1534                         
1535                         IMB_freeImBuf(ibuf);
1536
1537                         ibuf = i;
1538                 }
1539         } 
1540
1541         if(seq->flag & SEQ_FLIPX) {
1542                 IMB_flipx(ibuf);
1543         }
1544         
1545         if(seq->flag & SEQ_FLIPY) {
1546                 IMB_flipy(ibuf);
1547         }
1548
1549         if(seq->sat != 1.0f) {
1550                 /* inline for now, could become an imbuf function */
1551                 int i;
1552                 char *rct= (char *)ibuf->rect;
1553                 float *rctf= ibuf->rect_float;
1554                 const float sat= seq->sat;
1555                 float hsv[3];
1556
1557                 if(rct) {
1558                         float rgb[3];
1559                         for (i = ibuf->x * ibuf->y; i > 0; i--, rct+=4) {
1560                                 rgb_byte_to_float(rct, rgb);
1561                                 rgb_to_hsv(rgb[0], rgb[1], rgb[2], hsv, hsv+1, hsv+2);
1562                                 hsv_to_rgb(hsv[0], hsv[1] * sat, hsv[2], rgb, rgb+1, rgb+2);
1563                                 rgb_float_to_byte(rgb, rct);
1564                         }
1565                 }
1566
1567                 if(rctf) {
1568                         for (i = ibuf->x * ibuf->y; i > 0; i--, rctf+=4) {
1569                                 rgb_to_hsv(rctf[0], rctf[1], rctf[2], hsv, hsv+1, hsv+2);
1570                                 hsv_to_rgb(hsv[0], hsv[1] * sat, hsv[2], rctf, rctf+1, rctf+2);
1571                         }
1572                 }
1573         }
1574
1575         mul = seq->mul;
1576
1577         if(seq->blend_mode == SEQ_BLEND_REPLACE) {
1578                 mul *= seq->blend_opacity / 100.0;
1579         }
1580
1581         if(seq->flag & SEQ_USE_COLOR_BALANCE && seq->strip->color_balance) {
1582                 color_balance(seq, ibuf, mul);
1583                 mul = 1.0;
1584         }
1585
1586         if(seq->flag & SEQ_MAKE_FLOAT) {
1587                 if (!ibuf->rect_float)
1588                         IMB_float_from_rect_simple(ibuf);
1589
1590                 if (ibuf->rect) {
1591                         imb_freerectImBuf(ibuf);
1592                 }
1593         }
1594
1595         if(mul != 1.0) {
1596                 multibuf(ibuf, mul);
1597         }
1598
1599         if(seq->flag & SEQ_MAKE_PREMUL) {
1600                 if(ibuf->depth == 32 && ibuf->zbuf == 0) {
1601                         IMB_premultiply_alpha(ibuf);
1602                 }
1603         }
1604
1605
1606         if(ibuf->x != seqrectx || ibuf->y != seqrecty ) {
1607                 if(scene->r.mode & R_OSA) {
1608                         IMB_scaleImBuf(ibuf, 
1609                                        (short)seqrectx, (short)seqrecty);
1610                 } else {
1611                         IMB_scalefastImBuf(ibuf, 
1612                                            (short)seqrectx, (short)seqrecty);
1613                 }
1614         }
1615         return ibuf;
1616 }
1617
1618 static ImBuf * copy_from_ibuf_still(Sequence * seq, float nr,
1619                                     int seqrectx, int seqrecty)
1620 {
1621         ImBuf * rval = 0;
1622         ImBuf * ibuf = 0;
1623
1624         if (nr == 0) {
1625                 ibuf = seq_stripelem_cache_get(
1626                         seq, seqrectx, seqrecty, seq->start, 
1627                         SEQ_STRIPELEM_IBUF_STARTSTILL);
1628         }
1629         if (nr == seq->len - 1) {
1630                 ibuf = seq_stripelem_cache_get(
1631                         seq, seqrectx, seqrecty, seq->start, 
1632                         SEQ_STRIPELEM_IBUF_ENDSTILL);
1633         }
1634
1635         if (ibuf) {
1636                 rval = IMB_dupImBuf(ibuf);
1637                 IMB_freeImBuf(ibuf);
1638         }
1639
1640         return rval;
1641 }
1642
1643 static void copy_to_ibuf_still(Sequence * seq, float nr,
1644                                ImBuf * ibuf)
1645 {
1646         if (nr == 0) {
1647                 seq_stripelem_cache_put(
1648                         seq, 0, 0, seq->start, 
1649                         SEQ_STRIPELEM_IBUF_STARTSTILL, ibuf);
1650         }
1651         if (nr == seq->len - 1) {
1652                 seq_stripelem_cache_put(
1653                         seq, 0, 0, seq->start, 
1654                         SEQ_STRIPELEM_IBUF_ENDSTILL, ibuf);
1655         }
1656 }
1657
1658 /* **********************************************************************
1659    strip rendering functions
1660    ********************************************************************** */
1661
1662 static ImBuf* seq_render_strip_stack(
1663         Scene *scene,
1664         ListBase *seqbasep, float cfra, int chanshown, int render_size,
1665         int seqrectx, int seqrecty);
1666
1667 static ImBuf * seq_render_strip(Scene *scene, Sequence * seq, float cfra,
1668                                 int render_size, 
1669                                 int seqrectx, int seqrecty);
1670
1671
1672 static ImBuf* seq_render_effect_strip_impl(
1673         Scene *scene, float cfra, Sequence *seq, int render_size,
1674         int seqrectx, int seqrecty)
1675 {
1676         float fac, facf;
1677         int early_out;
1678         int i;
1679         int must_preprocess = FALSE;
1680
1681         struct SeqEffectHandle sh = get_sequence_effect(seq);
1682         FCurve *fcu= NULL;
1683         ImBuf * ibuf[3];
1684         ImBuf * out = 0;
1685
1686         ibuf[0] = ibuf[1] = ibuf[2] = 0;
1687
1688         if (!sh.execute) { /* effect not supported in this version... */
1689                 goto finish;
1690         }
1691
1692         if ((seq->flag & SEQ_USE_EFFECT_DEFAULT_FADE) != 0) {
1693                 sh.get_default_fac(seq, cfra, &fac, &facf);
1694                 if( scene->r.mode & R_FIELDS ); else facf= fac;
1695         } else {
1696                 fcu = id_data_find_fcurve(&scene->id, seq, &RNA_Sequence, 
1697                                           "effect_fader", 0);
1698                 if (fcu) {
1699                         fac = facf = evaluate_fcurve(fcu, cfra);
1700                         if( scene->r.mode & R_FIELDS ) {
1701                                 facf = evaluate_fcurve(fcu, cfra + 0.5);
1702                         }
1703                 } else {
1704                         fac = facf = seq->effect_fader;
1705                 }
1706         }
1707
1708         early_out = sh.early_out(seq, fac, facf);
1709
1710         if (early_out == -1) { /* no input needed */
1711                 out = sh.execute(scene, seq, cfra, fac, facf, 
1712                                  seqrectx, seqrecty, render_size,
1713                                  0, 0, 0);
1714                 goto finish;
1715         }
1716
1717
1718         must_preprocess = input_have_to_preprocess(
1719                 scene, seq, cfra, seqrectx, seqrecty);
1720
1721         switch (early_out) {
1722         case 0:
1723                 break;
1724         case 1:
1725                 if (seq->seq1) {
1726                         ibuf[0] = seq_render_strip(scene, seq->seq1, cfra,
1727                                                    render_size, 
1728                                                    seqrectx, seqrecty);
1729                 }
1730                 if (ibuf[0]) {
1731                         if (must_preprocess) {
1732                                 out = IMB_dupImBuf(ibuf[0]);
1733                         } else {
1734                                 out = ibuf[0];
1735                                 IMB_refImBuf(out);
1736                         }
1737                 }
1738                 goto finish;
1739         case 2:
1740                 if (seq->seq2) {
1741                         ibuf[1] = seq_render_strip(scene, seq->seq2, cfra,
1742                                                    render_size, 
1743                                                    seqrectx, seqrecty);
1744                 }
1745                 if (ibuf[1]) {
1746                         if (must_preprocess) {
1747                                 out = IMB_dupImBuf(ibuf[1]);
1748                         } else {
1749                                 out = ibuf[1];
1750                                 IMB_refImBuf(out);
1751                         }
1752                 }
1753                 goto finish;
1754         default:
1755                 goto finish;
1756         }
1757
1758         if (seq->seq1) {
1759                 ibuf[0] = seq_render_strip(scene, seq->seq1, cfra,
1760                                            render_size, 
1761                                            seqrectx, seqrecty);
1762         } 
1763
1764         if (seq->seq2) {
1765                 ibuf[1] = seq_render_strip(scene, seq->seq2, cfra,
1766                                            render_size, 
1767                                            seqrectx, seqrecty);
1768         }
1769
1770         if (seq->seq3) {
1771                 ibuf[2] = seq_render_strip(scene, seq->seq3, cfra,
1772                                            render_size, 
1773                                            seqrectx, seqrecty);
1774         }
1775
1776         if (!ibuf[0] || !ibuf[1]) {
1777                 goto finish;
1778         }
1779
1780         out = sh.execute(scene, seq, cfra, fac, facf, seqrectx, seqrecty, 
1781                          render_size,
1782                          ibuf[0], ibuf[1], ibuf[2]);
1783
1784 finish:
1785         for (i = 0; i < 3; i++) {
1786                 IMB_freeImBuf(ibuf[i]);
1787         }
1788
1789         if (!out) {
1790                 out = IMB_allocImBuf(
1791                         (short)seqrectx, (short)seqrecty, 32, IB_rect, 0);
1792         }
1793
1794         return out;
1795 }
1796
1797
1798 static ImBuf * seq_render_scene_strip_impl(
1799         Scene * scene, Sequence * seq, float nr, int seqrectx, int seqrecty)
1800 {
1801         ImBuf * ibuf = 0;
1802         float frame= seq->sfra + nr + seq->anim_startofs;
1803         float oldcfra;
1804         Object *oldcamera;
1805         ListBase oldmarkers;
1806         
1807         /* Hack! This function can be called from do_render_seq(), in that case
1808            the seq->scene can already have a Render initialized with same name,
1809            so we have to use a default name. (compositor uses scene name to
1810            find render).
1811            However, when called from within the UI (image preview in sequencer)
1812            we do want to use scene Render, that way the render result is defined
1813            for display in render/imagewindow
1814            
1815            Hmm, don't see, why we can't do that all the time,
1816            and since G.rendering is uhm, gone... (Peter)
1817         */
1818
1819         int rendering = G.rendering;
1820         int doseq;
1821         int doseq_gl= G.rendering ? /*(scene->r.seq_flag & R_SEQ_GL_REND)*/ 0 : (scene->r.seq_flag & R_SEQ_GL_PREV);
1822         int have_seq= FALSE;
1823         Scene *sce= seq->scene; /* dont refer to seq->scene above this point!, it can be NULL */
1824         int sce_valid= FALSE;
1825
1826         if(sce) {
1827                 have_seq= (sce->r.scemode & R_DOSEQ) && sce->ed && sce->ed->seqbase.first;
1828                 sce_valid= (sce->camera || have_seq);
1829         }
1830
1831         if (!sce_valid)
1832                 return NULL;
1833
1834         oldcfra= seq->scene->r.cfra;
1835         oldcamera= seq->scene->camera;
1836
1837         /* prevent eternal loop */
1838         doseq= scene->r.scemode & R_DOSEQ;
1839         scene->r.scemode &= ~R_DOSEQ;
1840         
1841         seq->scene->r.cfra= frame;
1842         if(seq->scene_camera)   
1843                 seq->scene->camera= seq->scene_camera;
1844         else    
1845                 scene_camera_switch_update(seq->scene);
1846         
1847 #ifdef DURIAN_CAMERA_SWITCH
1848         /* stooping to new low's in hackyness :( */
1849         oldmarkers= seq->scene->markers;
1850         seq->scene->markers.first= seq->scene->markers.last= NULL;
1851 #endif
1852         
1853         if(sequencer_view3d_cb && BLI_thread_is_main() && doseq_gl && (seq->scene == scene || have_seq==0) && seq->scene->camera) {
1854                 /* opengl offscreen render */
1855                 scene_update_for_newframe(G.main, seq->scene, seq->scene->lay);
1856                 ibuf= sequencer_view3d_cb(seq->scene, seqrectx, seqrecty, 
1857                                           scene->r.seq_prev_type);
1858         }
1859         else {
1860                 Render *re;
1861                 RenderResult rres;
1862                 
1863                 if(rendering)
1864                         re= RE_NewRender(" do_build_seq_ibuf");
1865                 else
1866                         re= RE_NewRender(sce->id.name);
1867                 
1868                 RE_BlenderFrame(re, G.main, sce, NULL, sce->lay, frame);
1869                 
1870                 RE_AcquireResultImage(re, &rres);
1871                 
1872                 if(rres.rectf) {
1873                         ibuf= IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rectfloat, 0);
1874                         memcpy(ibuf->rect_float, rres.rectf, 4*sizeof(float)*rres.rectx*rres.recty);
1875                         if(rres.rectz) {
1876                                 addzbuffloatImBuf(ibuf);
1877                                 memcpy(ibuf->zbuf_float, rres.rectz, sizeof(float)*rres.rectx*rres.recty);
1878                         }
1879
1880                         /* float buffers in the sequencer are not linear */
1881                         ibuf->profile= IB_PROFILE_LINEAR_RGB;
1882                         IMB_convert_profile(ibuf, IB_PROFILE_SRGB);                     
1883                 }
1884                 else if (rres.rect32) {
1885                         ibuf= IMB_allocImBuf(rres.rectx, rres.recty, 32, IB_rect, 0);
1886                         memcpy(ibuf->rect, rres.rect32, 4*rres.rectx*rres.recty);
1887                 }
1888                 
1889                 RE_ReleaseResultImage(re);
1890                 
1891                 // BIF_end_render_callbacks();
1892         }
1893         
1894         /* restore */
1895         scene->r.scemode |= doseq;
1896         
1897         seq->scene->r.cfra = oldcfra;
1898         seq->scene->camera= oldcamera;
1899         
1900 #ifdef DURIAN_CAMERA_SWITCH
1901         /* stooping to new low's in hackyness :( */
1902         seq->scene->markers= oldmarkers;
1903 #endif
1904
1905         return ibuf;
1906 }
1907
1908 static ImBuf * seq_render_strip(Scene *scene, Sequence * seq, float cfra,
1909                                 int render_size, 
1910                                 int seqrectx, int seqrecty)
1911 {
1912         char name[FILE_MAXDIR+FILE_MAXFILE];
1913         int use_preprocess = input_have_to_preprocess(
1914                 scene, seq, cfra, seqrectx, seqrecty);
1915         ImBuf * ibuf = seq_stripelem_cache_get(
1916                 seq, seqrectx, seqrecty, cfra, SEQ_STRIPELEM_IBUF);
1917         float nr = give_stripelem_index(seq, cfra);
1918
1919         /* currently, we cache preprocessed images */
1920         if (ibuf) {
1921                 use_preprocess = FALSE;
1922         }
1923
1924         if(seq->type == SEQ_META) {
1925                 ImBuf * meta_ibuf = 0;
1926
1927                 if (ibuf == 0) {
1928                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
1929                 }
1930
1931                 if(!ibuf && seq->seqbase.first) {
1932                         meta_ibuf = seq_render_strip_stack(
1933                                 scene,
1934                                 &seq->seqbase, seq->start + nr, 0,
1935                                 render_size, seqrectx, seqrecty);
1936                 }
1937
1938                 if(!ibuf && meta_ibuf) {
1939                         ibuf = meta_ibuf;
1940                         if(ibuf && use_preprocess) {
1941                                 struct ImBuf * i = IMB_dupImBuf(ibuf);
1942
1943                                 IMB_freeImBuf(ibuf);
1944
1945                                 ibuf = i;
1946                         }
1947                 }
1948         } else if(seq->type == SEQ_SPEED) {
1949                 ImBuf * child_ibuf = 0;
1950
1951                 if (ibuf == 0) {
1952                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
1953                 }
1954
1955                 if (ibuf == 0) {
1956                         float f_cfra;
1957                         SpeedControlVars * s 
1958                                 = (SpeedControlVars *)seq->effectdata;
1959
1960                         sequence_effect_speed_rebuild_map(scene, seq, 0);
1961
1962                         /* weeek! */
1963                         f_cfra = seq->start + s->frameMap[(int) nr];
1964
1965                         child_ibuf = seq_render_strip(scene, seq->seq1, f_cfra,
1966                                                       render_size, 
1967                                                       seqrectx, seqrecty);
1968                 }
1969
1970                 if (!ibuf && child_ibuf) {
1971                         ibuf = child_ibuf;
1972                         if(ibuf && use_preprocess) {
1973                                 struct ImBuf * i = IMB_dupImBuf(ibuf);
1974
1975                                 IMB_freeImBuf(ibuf);
1976
1977                                 ibuf = i;
1978                         }
1979                 }
1980         } else if(seq->type & SEQ_EFFECT) {
1981                 /* should the effect be recalculated? */
1982                 
1983                 if (ibuf == 0) {
1984                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
1985                 }
1986
1987                 if(ibuf == 0) {         
1988                         ibuf = seq_render_effect_strip_impl(
1989                                 scene, cfra, seq, render_size, 
1990                                 seqrectx, seqrecty);
1991                 }
1992         } else if(seq->type == SEQ_IMAGE) {
1993                 StripElem * s_elem = give_stripelem(seq, cfra);
1994
1995                 if(ibuf == 0) {
1996                         BLI_join_dirfile(name, seq->strip->dir, s_elem->name);
1997                         BLI_path_abs(name, G.sce);
1998
1999                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
2000                 }
2001
2002                 if (ibuf == 0) {
2003                         ibuf = copy_from_ibuf_still(seq,nr,seqrectx,seqrecty);
2004                 }
2005
2006                 if (ibuf == 0 && (ibuf=IMB_loadiffname(name, IB_rect))) {
2007                         /* we don't need both (speed reasons)! */
2008                         if (ibuf->rect_float && ibuf->rect)
2009                                 imb_freerectImBuf(ibuf);
2010
2011                         /* all sequencer color is done in SRGB space, linear gives odd crossfades */
2012                         if(ibuf->profile == IB_PROFILE_LINEAR_RGB)
2013                                 IMB_convert_profile(ibuf, IB_PROFILE_NONE);
2014
2015                         copy_to_ibuf_still(seq, nr, ibuf);
2016                 }
2017         } else if(seq->type == SEQ_MOVIE) {
2018                 if(ibuf == 0) {
2019                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
2020                         
2021                 }
2022                 
2023                 if (ibuf == 0) {
2024                         ibuf = copy_from_ibuf_still(seq, nr,seqrectx,seqrecty);
2025                 }
2026
2027                 if (ibuf == 0) {
2028                         if(seq->anim==0) {
2029                                 BLI_join_dirfile(name, 
2030                                                  seq->strip->dir, 
2031                                                  seq->strip->stripdata->name);
2032                                 BLI_path_abs(name, G.sce);
2033                                         
2034                                 seq->anim = openanim(
2035                                         name, IB_rect | 
2036                                         ((seq->flag & SEQ_FILTERY) 
2037                                          ? IB_animdeinterlace : 0));
2038                         }
2039                         if(seq->anim) {
2040                                 IMB_anim_set_preseek(seq->anim, 
2041                                                      seq->anim_preseek);
2042                                 ibuf = IMB_anim_absolute(seq->anim, 
2043                                                          nr 
2044                                                          + seq->anim_startofs);
2045                                 /* we don't need both (speed reasons)! */
2046                                 if (ibuf && ibuf->rect_float 
2047                                     && ibuf->rect) {
2048                                         imb_freerectImBuf(ibuf);
2049                                 }
2050
2051                         }
2052                         copy_to_ibuf_still(seq, nr, ibuf);
2053                 }
2054                         
2055         } else if(seq->type == SEQ_SCENE) {     // scene can be NULL after deletions
2056                 if (ibuf == 0) {
2057                         ibuf = seq_proxy_fetch(scene, seq, cfra, render_size);
2058                 }
2059                 if (ibuf == 0) {
2060                         ibuf = copy_from_ibuf_still(seq, nr,seqrectx,seqrecty);
2061                 }
2062                 
2063                 if (ibuf == 0) {
2064                         ibuf = seq_render_scene_strip_impl(scene, seq, nr,
2065                                                            seqrectx, seqrecty);
2066
2067                         copy_to_ibuf_still(seq, nr, ibuf);
2068                 }
2069         }
2070
2071         if (!ibuf) {
2072                 ibuf = IMB_allocImBuf(
2073                         (short)seqrectx, (short)seqrecty, 32, IB_rect, 0);
2074         }
2075
2076         if (ibuf->x != seqrectx || ibuf->y != seqrecty) {
2077                 use_preprocess = TRUE;
2078         }
2079
2080         if (use_preprocess) {
2081                 ibuf = input_preprocess(scene, seq, cfra, seqrectx,
2082                                         seqrecty, ibuf);
2083         }
2084
2085         seq_stripelem_cache_put(
2086                 seq, seqrectx, seqrecty, cfra, SEQ_STRIPELEM_IBUF, ibuf);
2087
2088         return ibuf;
2089 }
2090
2091 /* **********************************************************************
2092    strip stack rendering functions
2093    ********************************************************************** */
2094
2095 static int seq_must_swap_input_in_blend_mode(Sequence * seq)
2096 {
2097         int swap_input = FALSE;
2098
2099         /* bad hack, to fix crazy input ordering of 
2100            those two effects */
2101
2102         if (seq->blend_mode == SEQ_ALPHAOVER ||
2103                 seq->blend_mode == SEQ_ALPHAUNDER ||
2104                 seq->blend_mode == SEQ_OVERDROP) {
2105                 swap_input = TRUE;
2106         }
2107         
2108         return swap_input;
2109 }
2110
2111 static int seq_get_early_out_for_blend_mode(Sequence * seq)
2112 {
2113         struct SeqEffectHandle sh = get_sequence_blend(seq);
2114         float facf = seq->blend_opacity / 100.0;
2115         int early_out = sh.early_out(seq, facf, facf);
2116         
2117         if (early_out < 1) {
2118                 return early_out;
2119         }
2120
2121         if (seq_must_swap_input_in_blend_mode(seq)) {
2122                 if (early_out == 2) {
2123                         return 1;
2124                 } else if (early_out == 1) {
2125                         return 2;
2126                 }
2127         }
2128         return early_out;
2129 }
2130
2131 static ImBuf* seq_render_strip_stack(
2132         Scene *scene, ListBase *seqbasep, float cfra, int chanshown, 
2133         int render_size, int seqrectx, int seqrecty)
2134 {
2135         Sequence* seq_arr[MAXSEQ+1];
2136         int count;
2137         int i;
2138         ImBuf* out = 0;
2139
2140         count = get_shown_sequences(seqbasep, cfra, chanshown, 
2141                                     (Sequence **)&seq_arr);
2142
2143         if (!count) {
2144                 return 0;
2145         }
2146
2147 #if 0 /* commentind since this breaks keyframing, since it resets the value on draw */
2148         if(scene->r.cfra != cfra) {
2149                 // XXX for prefetch and overlay offset!..., very bad!!!
2150                 AnimData *adt= BKE_animdata_from_id(&scene->id);
2151                 BKE_animsys_evaluate_animdata(&scene->id, adt, cfra, ADT_RECALC_ANIM);
2152         }
2153 #endif
2154
2155         out = seq_stripelem_cache_get(
2156                 seq_arr[count - 1], 
2157                 seqrectx, seqrecty, cfra, SEQ_STRIPELEM_IBUF_COMP);
2158
2159         if (out) {
2160                 return out;
2161         }
2162         
2163         if(count == 1) {
2164                 out = seq_render_strip(scene, seq_arr[0],
2165                                         cfra, render_size,
2166                                         seqrectx, seqrecty);
2167                 seq_stripelem_cache_put(
2168                         seq_arr[0], 
2169                         seqrectx, seqrecty, cfra, 
2170                         SEQ_STRIPELEM_IBUF_COMP, out);
2171
2172                 return out;
2173         }
2174
2175
2176         for (i = count - 1; i >= 0; i--) {
2177                 int early_out;
2178                 Sequence * seq = seq_arr[i];
2179
2180                 out = seq_stripelem_cache_get(
2181                         seq, 
2182                         seqrectx, seqrecty, cfra, SEQ_STRIPELEM_IBUF_COMP);
2183
2184                 if (out) {
2185                         break;
2186                 }
2187                 if (seq->blend_mode == SEQ_BLEND_REPLACE) {
2188                         out = seq_render_strip(scene, seq, cfra,
2189                                                render_size,
2190                                                seqrectx, seqrecty);
2191                         break;
2192                 }
2193
2194                 early_out = seq_get_early_out_for_blend_mode(seq);
2195
2196                 switch (early_out) {
2197                 case -1:
2198                 case 2:
2199                         out = seq_render_strip(scene, seq, cfra,
2200                                                render_size,
2201                                                seqrectx, seqrecty);
2202                         break;
2203                 case 1:
2204                         if (i == 0) {
2205                                 out = IMB_allocImBuf(
2206                                         (short)seqrectx, (short)seqrecty, 
2207                                         32, IB_rect, 0);
2208                         }
2209                         break;
2210                 case 0:
2211                         if (i == 0) {
2212                                 out = seq_render_strip(scene, seq, cfra,
2213                                                        render_size,
2214                                                        seqrectx, seqrecty);
2215                         }
2216
2217                         break;
2218                 }
2219                 if (out) {
2220                         break;
2221                 }
2222         }
2223
2224         seq_stripelem_cache_put(
2225                 seq_arr[i], seqrectx, seqrecty, cfra, 
2226                 SEQ_STRIPELEM_IBUF_COMP, out);
2227
2228
2229         i++;
2230
2231         for (; i < count; i++) {
2232                 Sequence * seq = seq_arr[i];
2233
2234                 if (seq_get_early_out_for_blend_mode(seq) == 0) {
2235                         struct SeqEffectHandle sh = get_sequence_blend(seq);
2236                         ImBuf * ibuf1 = out;
2237                         ImBuf * ibuf2 = seq_render_strip(scene, seq, cfra,
2238                                                          render_size,
2239                                                          seqrectx, seqrecty);
2240
2241                         float facf = seq->blend_opacity / 100.0;
2242                         int swap_input 
2243                                 = seq_must_swap_input_in_blend_mode(seq);
2244
2245                         int x= seqrectx;
2246                         int y= seqrecty;
2247
2248                         if (swap_input) {
2249                                 out = sh.execute(scene, seq, cfra, 
2250                                                  facf, facf, x, y, render_size,
2251                                                  ibuf2, ibuf1, 0);
2252                         } else {
2253                                 out = sh.execute(scene, seq, cfra, 
2254                                                  facf, facf, x, y, render_size,
2255                                                  ibuf1, ibuf2, 0);
2256                         }
2257                 
2258                         IMB_freeImBuf(ibuf1);
2259                         IMB_freeImBuf(ibuf2);
2260                 }
2261
2262                 seq_stripelem_cache_put(
2263                         seq_arr[i], seqrectx, seqrecty, cfra, 
2264                         SEQ_STRIPELEM_IBUF_COMP, out);
2265         }
2266
2267         return out;
2268 }
2269
2270 /*
2271  * returned ImBuf is refed!
2272  * you have to free after usage!
2273  */
2274
2275 ImBuf *give_ibuf_seq(Scene *scene, int rectx, int recty, int cfra, int chanshown, int render_size)
2276 {
2277         Editing *ed= seq_give_editing(scene, FALSE);
2278         int count;
2279         ListBase *seqbasep;
2280         
2281         if(ed==NULL) return NULL;
2282
2283         count = BLI_countlist(&ed->metastack);
2284         if((chanshown < 0) && (count > 0)) {
2285                 count = MAX2(count + chanshown, 0);
2286                 seqbasep= ((MetaStack*)BLI_findlink(&ed->metastack, count))->oldbasep;
2287         } else {
2288                 seqbasep= ed->seqbasep;
2289         }
2290
2291         return seq_render_strip_stack(
2292                 scene, seqbasep, cfra, chanshown, render_size, rectx, recty);
2293 }
2294
2295 ImBuf *give_ibuf_seqbase(struct Scene *scene, int rectx, int recty, int cfra, int chanshown, int render_size, ListBase *seqbasep)
2296 {
2297         return seq_render_strip_stack(scene, seqbasep, cfra, chanshown, render_size, rectx, recty);
2298 }
2299
2300
2301 ImBuf *give_ibuf_seq_direct(Scene *scene, int rectx, int recty, int cfra, int render_size, Sequence *seq)
2302 {
2303         return seq_render_strip(scene, seq, cfra, render_size, rectx, recty);
2304 }
2305
2306 #if 0
2307 /* check used when we need to change seq->blend_mode but not to effect or audio strips */
2308 static int seq_can_blend(Sequence *seq)
2309 {
2310         if (ELEM4(seq->type, SEQ_IMAGE, SEQ_META, SEQ_SCENE, SEQ_MOVIE)) {
2311                 return 1;
2312         } else {
2313                 return 0;
2314         }
2315 }
2316 #endif
2317
2318 /* *********************** threading api ******************* */
2319
2320 static ListBase running_threads;
2321 static ListBase prefetch_wait;
2322 static ListBase prefetch_done;
2323
2324 static pthread_mutex_t queue_lock          = PTHREAD_MUTEX_INITIALIZER;
2325 static pthread_mutex_t wakeup_lock         = PTHREAD_MUTEX_INITIALIZER;
2326 static pthread_cond_t  wakeup_cond         = PTHREAD_COND_INITIALIZER;
2327
2328 //static pthread_mutex_t prefetch_ready_lock = PTHREAD_MUTEX_INITIALIZER;
2329 //static pthread_cond_t  prefetch_ready_cond = PTHREAD_COND_INITIALIZER;
2330
2331 static pthread_mutex_t frame_done_lock     = PTHREAD_MUTEX_INITIALIZER;
2332 static pthread_cond_t  frame_done_cond     = PTHREAD_COND_INITIALIZER;
2333
2334 static volatile int seq_thread_shutdown = TRUE; 
2335 static volatile int seq_last_given_monoton_cfra = 0;
2336 static int monoton_cfra = 0;
2337
2338 typedef struct PrefetchThread {
2339         struct PrefetchThread *next, *prev;
2340         
2341         Scene *scene;
2342         struct PrefetchQueueElem *current;
2343         pthread_t pthread;
2344         int running;
2345         
2346 } PrefetchThread;
2347
2348 typedef struct PrefetchQueueElem {
2349         struct PrefetchQueueElem *next, *prev;
2350         
2351         int rectx;
2352         int recty;
2353         int cfra;
2354         int chanshown;
2355         int render_size;
2356
2357         int monoton_cfra;
2358
2359         struct ImBuf * ibuf;
2360 } PrefetchQueueElem;
2361
2362 #if 0
2363 static void *seq_prefetch_thread(void * This_)
2364 {
2365         PrefetchThread * This = This_;
2366
2367         while (!seq_thread_shutdown) {
2368                 PrefetchQueueElem *e;
2369                 int s_last;
2370
2371                 pthread_mutex_lock(&queue_lock);
2372                 e = prefetch_wait.first;
2373                 if (e) {
2374                         BLI_remlink(&prefetch_wait, e);
2375                 }
2376                 s_last = seq_last_given_monoton_cfra;
2377
2378                 This->current = e;
2379
2380                 pthread_mutex_unlock(&queue_lock);
2381
2382                 if (!e) {
2383                         pthread_mutex_lock(&prefetch_ready_lock);
2384
2385                         This->running = FALSE;
2386
2387                         pthread_cond_signal(&prefetch_ready_cond);
2388                         pthread_mutex_unlock(&prefetch_ready_lock);
2389
2390                         pthread_mutex_lock(&wakeup_lock);
2391                         if (!seq_thread_shutdown) {
2392                                 pthread_cond_wait(&wakeup_cond, &wakeup_lock);
2393                         }
2394                         pthread_mutex_unlock(&wakeup_lock);
2395                         continue;
2396                 }
2397
2398                 This->running = TRUE;
2399                 
2400                 if (e->cfra >= s_last) { 
2401                         e->ibuf = give_ibuf_seq_impl(This->scene, 
2402                                 e->rectx, e->recty, e->cfra, e->chanshown,
2403                                 e->render_size);
2404                 }
2405
2406                 pthread_mutex_lock(&queue_lock);
2407
2408                 BLI_addtail(&prefetch_done, e);
2409
2410                 for (e = prefetch_wait.first; e; e = e->next) {
2411                         if (s_last > e->monoton_cfra) {
2412                                 BLI_remlink(&prefetch_wait, e);
2413                                 MEM_freeN(e);
2414                         }
2415                 }
2416
2417                 for (e = prefetch_done.first; e; e = e->next) {
2418                         if (s_last > e->monoton_cfra) {
2419                                 if (e->ibuf) {
2420                                         IMB_cache_limiter_unref(e->ibuf);
2421                                 }
2422                                 BLI_remlink(&prefetch_done, e);
2423                                 MEM_freeN(e);
2424                         }
2425                 }
2426
2427                 pthread_mutex_unlock(&queue_lock);
2428
2429                 pthread_mutex_lock(&frame_done_lock);
2430                 pthread_cond_signal(&frame_done_cond);
2431                 pthread_mutex_unlock(&frame_done_lock);
2432         }
2433         return 0;
2434 }
2435
2436 static void seq_start_threads(Scene *scene)
2437 {
2438         int i;
2439
2440         running_threads.first = running_threads.last = NULL;
2441         prefetch_wait.first = prefetch_wait.last = NULL;
2442         prefetch_done.first = prefetch_done.last = NULL;
2443
2444         seq_thread_shutdown = FALSE;
2445         seq_last_given_monoton_cfra = monoton_cfra = 0;
2446
2447         /* since global structures are modified during the processing
2448            of one frame, only one render thread is currently possible... 
2449
2450            (but we code, in the hope, that we can remove this restriction
2451            soon...)
2452         */
2453
2454         fprintf(stderr, "SEQ-THREAD: seq_start_threads\n");
2455
2456         for (i = 0; i < 1; i++) {
2457                 PrefetchThread *t = MEM_callocN(sizeof(PrefetchThread), "prefetch_thread");
2458                 t->scene= scene;
2459                 t->running = TRUE;
2460                 BLI_addtail(&running_threads, t);
2461
2462                 pthread_create(&t->pthread, NULL, seq_prefetch_thread, t);
2463         }
2464
2465         /* init malloc mutex */
2466         BLI_init_threads(0, 0, 0);
2467 }
2468
2469 static void seq_stop_threads()
2470 {
2471         PrefetchThread *tslot;
2472         PrefetchQueueElem *e;
2473
2474         fprintf(stderr, "SEQ-THREAD: seq_stop_threads()\n");
2475
2476         if (seq_thread_shutdown) {
2477                 fprintf(stderr, "SEQ-THREAD: ... already stopped\n");
2478                 return;
2479         }
2480         
2481         pthread_mutex_lock(&wakeup_lock);
2482
2483         seq_thread_shutdown = TRUE;
2484
2485                 pthread_cond_broadcast(&wakeup_cond);
2486                 pthread_mutex_unlock(&wakeup_lock);
2487
2488         for(tslot = running_threads.first; tslot; tslot= tslot->next) {
2489                 pthread_join(tslot->pthread, NULL);
2490         }
2491
2492
2493         for (e = prefetch_wait.first; e; e = e->next) {
2494                 BLI_remlink(&prefetch_wait, e);
2495                 MEM_freeN(e);
2496         }
2497
2498         for (e = prefetch_done.first; e; e = e->next) {
2499                 if (e->ibuf) {
2500                         IMB_cache_limiter_unref(e->ibuf);
2501                 }
2502                 BLI_remlink(&prefetch_done, e);
2503                 MEM_freeN(e);
2504         }
2505
2506         BLI_freelistN(&running_threads);
2507
2508         /* deinit malloc mutex */
2509         BLI_end_threads(0);
2510 }
2511 #endif
2512
2513 void give_ibuf_prefetch_request(int rectx, int recty, int cfra, int chanshown,
2514                                 int render_size)
2515 {
2516         PrefetchQueueElem *e;
2517         if (seq_thread_shutdown) {
2518                 return;
2519         }
2520
2521         e = MEM_callocN(sizeof(PrefetchQueueElem), "prefetch_queue_elem");
2522         e->rectx = rectx;
2523         e->recty = recty;
2524         e->cfra = cfra;
2525         e->chanshown = chanshown;
2526         e->render_size = render_size;
2527         e->monoton_cfra = monoton_cfra++;
2528
2529         pthread_mutex_lock(&queue_lock);
2530         BLI_addtail(&prefetch_wait, e);
2531         pthread_mutex_unlock(&queue_lock);
2532         
2533         pthread_mutex_lock(&wakeup_lock);
2534         pthread_cond_signal(&wakeup_cond);
2535         pthread_mutex_unlock(&wakeup_lock);
2536 }
2537
2538 #if 0
2539 static void seq_wait_for_prefetch_ready()
2540 {
2541         PrefetchThread *tslot;
2542
2543         if (seq_thread_shutdown) {
2544                 return;
2545         }
2546
2547         fprintf(stderr, "SEQ-THREAD: rendering prefetch frames...\n");
2548
2549         pthread_mutex_lock(&prefetch_ready_lock);
2550
2551         for(;;) {
2552                 for(tslot = running_threads.first; tslot; tslot= tslot->next) {
2553                         if (tslot->running) {
2554                                 break;
2555                         }
2556                 }
2557                 if (!tslot) {
2558                         break;
2559                 }
2560                 pthread_cond_wait(&prefetch_ready_cond, &prefetch_ready_lock);
2561         }
2562
2563         pthread_mutex_unlock(&prefetch_ready_lock);
2564
2565         fprintf(stderr, "SEQ-THREAD: prefetch done\n");
2566 }
2567 #endif
2568
2569 ImBuf *give_ibuf_seq_threaded(Scene *scene, int rectx, int recty, int cfra, int chanshown, int render_size)
2570 {
2571         PrefetchQueueElem *e = NULL;
2572         int found_something = FALSE;
2573
2574         if (seq_thread_shutdown) {
2575                 return give_ibuf_seq(scene, rectx, recty, cfra, chanshown, render_size);
2576         }
2577
2578         while (!e) {
2579                 int success = FALSE;
2580                 pthread_mutex_lock(&queue_lock);
2581
2582                 for (e = prefetch_done.first; e; e = e->next) {
2583                         if (cfra == e->cfra &&
2584                                 chanshown == e->chanshown &&
2585                                 rectx == e->rectx && 
2586                                 recty == e->recty &&
2587                                 render_size == e->render_size) {
2588                                 success = TRUE;
2589                                 found_something = TRUE;
2590                                 break;
2591                         }
2592                 }
2593
2594                 if (!e) {
2595                         for (e = prefetch_wait.first; e; e = e->next) {
2596                                 if (cfra == e->cfra &&
2597                                         chanshown == e->chanshown &&
2598                                         rectx == e->rectx && 
2599                                         recty == e->recty &&
2600                                         render_size == e->render_size) {
2601                                         found_something = TRUE;
2602                                         break;
2603                                 }
2604                         }
2605                 }
2606
2607                 if (!e) {
2608                         PrefetchThread *tslot;
2609
2610                         for(tslot = running_threads.first; 
2611                                 tslot; tslot= tslot->next) {
2612                                 if (tslot->current &&
2613                                         cfra == tslot->current->cfra &&
2614                                         chanshown == tslot->current->chanshown &&
2615                                         rectx == tslot->current->rectx && 
2616                                         recty == tslot->current->recty &&
2617                                         render_size== tslot->current->render_size){
2618                                         found_something = TRUE;
2619                                         break;
2620                                 }
2621                         }
2622                 }
2623
2624                 /* e->ibuf is unrefed by render thread on next round. */
2625
2626                 if (e) {
2627                         seq_last_given_monoton_cfra = e->monoton_cfra;
2628                 }
2629
2630                 pthread_mutex_unlock(&queue_lock);
2631
2632                 if (!success) {
2633                         e = NULL;
2634
2635                         if (!found_something) {
2636                                 fprintf(stderr, 
2637                                         "SEQ-THREAD: Requested frame "
2638                                         "not in queue ???\n");
2639                                 break;
2640                         }
2641                         pthread_mutex_lock(&frame_done_lock);
2642                         pthread_cond_wait(&frame_done_cond, &frame_done_lock);
2643                         pthread_mutex_unlock(&frame_done_lock);
2644                 }
2645         }
2646         
2647         return e ? e->ibuf : 0;
2648 }
2649
2650 /* Functions to free imbuf and anim data on changes */
2651
2652 static void free_anim_seq(Sequence *seq)
2653 {
2654         if(seq->anim) {
2655                 IMB_free_anim(seq->anim);
2656                 seq->anim = 0;
2657         }
2658 }
2659
2660 void free_imbuf_seq(Scene *scene, ListBase * seqbase, int check_mem_usage,
2661                     int keep_file_handles)
2662 {
2663         Sequence *seq;
2664
2665         if (check_mem_usage) {
2666                 /* Let the cache limitor take care of this (schlaile) */
2667                 /* While render let's keep all memory available for render 
2668                    (ton)
2669                    At least if free memory is tight...
2670                    This can make a big difference in encoding speed
2671                    (it is around 4 times(!) faster, if we do not waste time
2672                    on freeing _all_ buffers every time on long timelines...)
2673                    (schlaile)
2674                 */
2675         
2676                 uintptr_t mem_in_use;
2677                 uintptr_t mmap_in_use;
2678                 uintptr_t max;
2679         
2680                 mem_in_use= MEM_get_memory_in_use();
2681                 mmap_in_use= MEM_get_mapped_memory_in_use();
2682                 max = MEM_CacheLimiter_get_maximum();
2683         
2684                 if (max == 0 || mem_in_use + mmap_in_use <= max) {
2685                         return;
2686                 }
2687         }
2688
2689         seq_stripelem_cache_cleanup();
2690         
2691         for(seq= seqbase->first; seq; seq= seq->next) {
2692                 if(seq->strip) {
2693                         if(seq->type==SEQ_MOVIE && !keep_file_handles)
2694                                 free_anim_seq(seq);
2695                         if(seq->type==SEQ_SPEED) {
2696                                 sequence_effect_speed_rebuild_map(scene, seq, 1);
2697                         }
2698                 }
2699                 if(seq->type==SEQ_META) {
2700                         free_imbuf_seq(scene, &seq->seqbase, FALSE,
2701                                        keep_file_handles);
2702                 }
2703                 if(seq->type==SEQ_SCENE) {
2704                         /* FIXME: recurs downwards, 
2705                            but do recurs protection somehow! */
2706                 }
2707         }
2708         
2709 }
2710
2711 static int update_changed_seq_recurs(Scene *scene, Sequence *seq, Sequence *changed_seq, int len_change, int ibuf_change)
2712 {
2713         Sequence *subseq;
2714         int free_imbuf = 0;
2715         
2716         /* recurs downwards to see if this seq depends on the changed seq */
2717         
2718         if(seq == NULL)
2719                 return 0;
2720         
2721         if(seq == changed_seq)
2722                 free_imbuf = 1;
2723         
2724         for(subseq=seq->seqbase.first; subseq; subseq=subseq->next)
2725                 if(update_changed_seq_recurs(scene, subseq, changed_seq, len_change, ibuf_change))
2726                         free_imbuf = TRUE;
2727         
2728         if(seq->seq1)
2729                 if(update_changed_seq_recurs(scene, seq->seq1, changed_seq, len_change, ibuf_change))
2730                         free_imbuf = TRUE;
2731         if(seq->seq2 && (seq->seq2 != seq->seq1))
2732                 if(update_changed_seq_recurs(scene, seq->seq2, changed_seq, len_change, ibuf_change))
2733                         free_imbuf = TRUE;
2734         if(seq->seq3 && (seq->seq3 != seq->seq1) && (seq->seq3 != seq->seq2))
2735                 if(update_changed_seq_recurs(scene, seq->seq3, changed_seq, len_change, ibuf_change))
2736                         free_imbuf = TRUE;
2737         
2738         if(free_imbuf) {
2739                 if(ibuf_change) {
2740                         if(seq->type == SEQ_MOVIE)
2741                                 free_anim_seq(seq);
2742                         if(seq->type == SEQ_SPEED) {
2743                                 sequence_effect_speed_rebuild_map(scene, seq, 1);
2744                         }
2745                 }
2746                 
2747                 if(len_change)
2748                         calc_sequence(scene, seq);
2749         }
2750         
2751         return free_imbuf;
2752 }
2753
2754 void update_changed_seq_and_deps(Scene *scene, Sequence *changed_seq, int len_change, int ibuf_change)
2755 {
2756         Editing *ed= seq_give_editing(scene, FALSE);
2757         Sequence *seq;
2758         
2759         if (ed==NULL) return;
2760         
2761         for (seq=ed->seqbase.first; seq; seq=seq->next)
2762                 update_changed_seq_recurs(scene, seq, changed_seq, len_change, ibuf_change);
2763 }
2764
2765 /* seq funcs's for transforming internally
2766  notice the difference between start/end and left/right.
2767
2768  left and right are the bounds at which the sequence is rendered,
2769 start and end are from the start and fixed length of the sequence.
2770 */
2771 int seq_tx_get_start(Sequence *seq) {
2772         return seq->start;
2773 }
2774 int seq_tx_get_end(Sequence *seq)
2775 {
2776         return seq->start+seq->len;
2777 }
2778
2779 int seq_tx_get_final_left(Sequence *seq, int metaclip)
2780 {
2781         if (metaclip && seq->tmp) {
2782                 /* return the range clipped by the parents range */
2783                 return MAX2( seq_tx_get_final_left(seq, 0), seq_tx_get_final_left((Sequence *)seq->tmp, 1) );
2784         } else {
2785                 return (seq->start - seq->startstill) + seq->startofs;
2786         }
2787
2788 }
2789 int seq_tx_get_final_right(Sequence *seq, int metaclip)
2790 {
2791         if (metaclip && seq->tmp) {
2792                 /* return the range clipped by the parents range */
2793                 return MIN2( seq_tx_get_final_right(seq, 0), seq_tx_get_final_right((Sequence *)seq->tmp, 1) );
2794         } else {
2795                 return ((seq->start+seq->len) + seq->endstill) - seq->endofs;
2796         }
2797 }
2798
2799 void seq_tx_set_final_left(Sequence *seq, int val)
2800 {
2801         if (val < (seq)->start) {
2802                 seq->startstill = abs(val - (seq)->start);
2803                 seq->startofs = 0;
2804         } else {
2805                 seq->startofs = abs(val - (seq)->start);
2806                 seq->startstill = 0;
2807         }
2808 }
2809
2810 void seq_tx_set_final_right(Sequence *seq, int val)
2811 {
2812         if (val > (seq)->start + (seq)->len) {
2813                 seq->endstill = abs(val - (seq->start + (seq)->len));
2814                 seq->endofs = 0;
2815         } else {
2816                 seq->endofs = abs(val - ((seq)->start + (seq)->len));
2817                 seq->endstill = 0;
2818         }
2819 }
2820
2821 /* used so we can do a quick check for single image seq
2822    since they work a bit differently to normal image seq's (during transform) */
2823 int seq_single_check(Sequence *seq)
2824 {
2825         if ( seq->len==1 && (seq->type == SEQ_IMAGE || seq->type == SEQ_COLOR
2826                              || seq->type == SEQ_MULTICAM))
2827                 return 1;
2828         else
2829                 return 0;
2830 }
2831
2832 /* check if the selected seq's reference unselected seq's */
2833 int seqbase_isolated_sel_check(ListBase *seqbase)
2834 {
2835         Sequence *seq;
2836         /* is there more than 1 select */
2837         int ok= FALSE;
2838
2839         for(seq= seqbase->first; seq; seq= seq->next) {
2840                 if(seq->flag & SELECT) {
2841                         ok= TRUE;
2842                         break;
2843                 }
2844         }
2845
2846         if(ok == FALSE)
2847                 return FALSE;
2848
2849         /* test relationships */
2850         for(seq= seqbase->first; seq; seq= seq->next) {
2851                 if(seq->flag & SELECT) {
2852                         if(seq->type & SEQ_EFFECT) {
2853                                 if(seq->seq1 && (seq->seq1->flag & SELECT)==0) return FALSE;
2854                                 if(seq->seq2 && (seq->seq2->flag & SELECT)==0) return FALSE;
2855                                 if(seq->seq3 && (seq->seq3->flag & SELECT)==0) return FALSE;
2856                         }
2857                 }
2858                 else if(seq->type & SEQ_EFFECT) {
2859                         if(seq->seq1 && (seq->seq1->flag & SELECT)) return FALSE;
2860                         if(seq->seq2 && (seq->seq2->flag & SELECT)) return FALSE;
2861                         if(seq->seq3 && (seq->seq3->flag & SELECT)) return FALSE;
2862                 }
2863         }
2864
2865         return TRUE;
2866 }
2867
2868 /* use to impose limits when dragging/extending - so impossible situations dont happen
2869  * Cant use the SEQ_LEFTSEL and SEQ_LEFTSEL directly because the strip may be in a metastrip */
2870 void seq_tx_handle_xlimits(Sequence *seq, int leftflag, int rightflag)
2871 {
2872         if(leftflag) {
2873                 if (seq_tx_get_final_left(seq, 0) >= seq_tx_get_final_right(seq, 0)) {
2874                         seq_tx_set_final_left(seq, seq_tx_get_final_right(seq, 0)-1);
2875                 }
2876
2877                 if (seq_single_check(seq)==0) {
2878                         if (seq_tx_get_final_left(seq, 0) >= seq_tx_get_end(seq)) {
2879                                 seq_tx_set_final_left(seq, seq_tx_get_end(seq)-1);
2880                         }
2881
2882                         /* dosnt work now - TODO */
2883                         /*
2884                         if (seq_tx_get_start(seq) >= seq_tx_get_final_right(seq, 0)) {
2885                                 int ofs;
2886                                 ofs = seq_tx_get_start(seq) - seq_tx_get_final_right(seq, 0);
2887                                 seq->start -= ofs;
2888                                 seq_tx_set_final_left(seq, seq_tx_get_final_left(seq, 0) + ofs );
2889                         }*/
2890
2891                 }
2892         }
2893
2894         if(rightflag) {
2895                 if (seq_tx_get_final_right(seq, 0) <=  seq_tx_get_final_left(seq, 0)) {
2896                         seq_tx_set_final_right(seq, seq_tx_get_final_left(seq, 0)+1);
2897                 }
2898
2899                 if (seq_single_check(seq)==0) {
2900                         if (seq_tx_get_final_right(seq, 0) <= seq_tx_get_start(seq)) {
2901                                 seq_tx_set_final_right(seq, seq_tx_get_start(seq)+1);
2902                         }
2903                 }
2904         }
2905
2906         /* sounds cannot be extended past their endpoints */
2907         if (seq->type == SEQ_SOUND) {
2908                 seq->startstill= 0;
2909                 seq->endstill= 0;
2910         }
2911 }
2912
2913 void seq_single_fix(Sequence *seq)
2914 {
2915         int left, start, offset;
2916         if (!seq_single_check(seq))
2917                 return;
2918
2919         /* make sure the image is always at the start since there is only one,
2920            adjusting its start should be ok */
2921         left = seq_tx_get_final_left(seq, 0);
2922         start = seq->start;
2923         if (start != left) {
2924                 offset = left - start;
2925                 seq_tx_set_final_left( seq, seq_tx_get_final_left(seq, 0) - offset );
2926                 seq_tx_set_final_right( seq, seq_tx_get_final_right(seq, 0) - offset );
2927                 seq->start += offset;
2928         }
2929 }
2930
2931 int seq_tx_test(Sequence * seq)
2932 {
2933         return (seq->type < SEQ_EFFECT) || (get_sequence_effect_num_inputs(seq->type) == 0);
2934 }
2935
2936 static int seq_overlap(Sequence *seq1, Sequence *seq2)
2937 {
2938         if(seq1 != seq2)
2939                 if(seq1->machine==seq2->machine)
2940                         if(((seq1->enddisp <= seq2->startdisp) || (seq1->startdisp >= seq2->enddisp))==0)
2941                                 return 1;
2942
2943         return 0;
2944 }
2945
2946 int seq_test_overlap(ListBase * seqbasep, Sequence *test)
2947 {
2948         Sequence *seq;
2949
2950         seq= seqbasep->first;
2951         while(seq) {
2952                 if(seq_overlap(test, seq))
2953                         return 1;
2954
2955                 seq= seq->next;
2956         }
2957         return 0;
2958 }
2959
2960
2961 static void seq_translate(Scene *evil_scene, Sequence *seq, int delta)
2962 {
2963         seq_offset_animdata(evil_scene, seq, delta);
2964         seq->start += delta;
2965
2966         if(seq->type==SEQ_META) {
2967                 Sequence *seq_child;
2968                 for(seq_child= seq->seqbase.first; seq_child; seq_child= seq_child->next) {
2969                         seq_translate(evil_scene, seq_child, delta);
2970                 }
2971         }
2972
2973         calc_sequence_disp(evil_scene, seq);
2974 }
2975
2976 /* return 0 if there werent enough space */
2977 int shuffle_seq(ListBase * seqbasep, Sequence *test, Scene *evil_scene)
2978 {
2979         int orig_machine= test->machine;
2980         test->machine++;
2981         calc_sequence(evil_scene, test);
2982         while( seq_test_overlap(seqbasep, test) ) {
2983                 if(test->machine >= MAXSEQ) {
2984                         break;
2985                 }
2986                 test->machine++;
2987                 calc_sequence(evil_scene, test); // XXX - I dont think this is needed since were only moving vertically, Campbell.
2988         }
2989
2990         
2991         if(test->machine >= MAXSEQ) {
2992                 /* Blender 2.4x would remove the strip.
2993                  * nicer to move it to the end */
2994
2995                 Sequence *seq;
2996                 int new_frame= test->enddisp;
2997
2998                 for(seq= seqbasep->first; seq; seq= seq->next) {
2999                         if (seq->machine == orig_machine)
3000                                 new_frame = MAX2(new_frame, seq->enddisp);
3001                 }
3002
3003                 test->machine= orig_machine;
3004                 new_frame = new_frame + (test->start-test->startdisp); /* adjust by the startdisp */
3005                 seq_translate(evil_scene, test, new_frame - test->start);
3006
3007                 calc_sequence(evil_scene, test);
3008                 return 0;
3009         } else {
3010                 return 1;
3011         }
3012 }
3013
3014 static int shuffle_seq_time_offset_test(ListBase * seqbasep, char dir)
3015 {
3016         int offset= 0;
3017         Sequence *seq, *seq_other;
3018
3019         for(seq= seqbasep->first; seq; seq= seq->next) {
3020                 if(seq->tmp) {
3021                         for(seq_other= seqbasep->first; seq_other; seq_other= seq_other->next) {
3022                                 if(!seq_other->tmp && seq_overlap(seq, seq_other)) {
3023                                         if(dir=='L') {
3024                                                 offset= MIN2(offset, seq_other->startdisp - seq->enddisp);
3025                                         }
3026                                         else {
3027                                                 offset= MAX2(offset, seq_other->enddisp - seq->startdisp);
3028                                         }
3029                                 }
3030                         }
3031                 }
3032         }
3033         return offset;
3034 }
3035
3036 static int shuffle_seq_time_offset(Scene* scene, ListBase * seqbasep, char dir)
3037 {
3038         int ofs= 0;
3039         int tot_ofs= 0;
3040         Sequence *seq;
3041         while( (ofs= shuffle_seq_time_offset_test(seqbasep, dir)) ) {
3042                 for(seq= seqbasep->first; seq; seq= seq->next) {
3043                         if(seq->tmp) {
3044                                 /* seq_test_overlap only tests display values */
3045                                 seq->startdisp +=       ofs;
3046                                 seq->enddisp +=         ofs;
3047                         }
3048                 }
3049
3050                 tot_ofs+= ofs;
3051         }
3052
3053         for(seq= seqbasep->first; seq; seq= seq->next) {
3054                 if(seq->tmp)
3055                         calc_sequence_disp(scene, seq); /* corrects dummy startdisp/enddisp values */
3056         }
3057
3058         return tot_ofs;
3059 }
3060
3061 int shuffle_seq_time(ListBase * seqbasep, Scene *evil_scene)
3062 {
3063         /* note: seq->tmp is used to tag strips to move */
3064
3065         Sequence *seq;
3066
3067         int offset_l = shuffle_seq_time_offset(evil_scene, seqbasep, 'L');
3068         int offset_r = shuffle_seq_time_offset(evil_scene, seqbasep, 'R');
3069         int offset = (-offset_l < offset_r) ?  offset_l:offset_r;
3070
3071         if(offset) {
3072                 for(seq= seqbasep->first; seq; seq= seq->next) {
3073                         if(seq->tmp) {
3074                                 seq_translate(evil_scene, seq, offset);
3075                                 seq->flag &= ~SEQ_OVERLAP;
3076                         }
3077                 }
3078         }
3079
3080         return offset? 0:1;
3081 }
3082
3083 void seq_update_sound(Scene* scene, Sequence *seq)
3084 {
3085         if(seq->scene_sound)
3086         {
3087                 sound_move_scene_sound(scene, seq->scene_sound, seq->startdisp, seq->enddisp, seq->startofs + seq->anim_startofs);
3088                 /* mute is set in seq_update_muting_recursive */
3089         }
3090 }
3091
3092 static void seq_update_muting_recursive(Scene *scene, ListBase *seqbasep, Sequence *metaseq, int mute)
3093 {
3094         Sequence *seq;
3095         int seqmute;
3096
3097         /* for sound we go over full meta tree to update muted state,
3098            since sound is played outside of evaluating the imbufs, */
3099         for(seq=seqbasep->first; seq; seq=seq->next) {
3100                 seqmute= (mute || (seq->flag & SEQ_MUTE));
3101
3102                 if(seq->type == SEQ_META) {
3103                         /* if this is the current meta sequence, unmute because
3104                            all sequences above this were set to mute */
3105                         if(seq == metaseq)
3106                                 seqmute= 0;
3107
3108                         seq_update_muting_recursive(scene, &seq->seqbase, metaseq, seqmute);
3109                 }
3110                 else if((seq->type == SEQ_SOUND) || (seq->type == SEQ_SCENE)) {
3111                         if(seq->scene_sound) {
3112                                 sound_mute_scene_sound(scene, seq->scene_sound, seqmute);
3113                         }
3114                 }
3115         }
3116 }
3117
3118 void seq_update_muting(Scene *scene, Editing *ed)
3119 {
3120         if(ed) {
3121                 /* mute all sounds up to current metastack list */
3122                 MetaStack *ms= ed->metastack.last;
3123
3124                 if(ms)
3125                         seq_update_muting_recursive(scene, &ed->seqbase, ms->parseq, 1);
3126                 else
3127                         seq_update_muting_recursive(scene, &ed->seqbase, NULL, 0);
3128         }
3129 }
3130
3131 /* in cases where we done know the sequence's listbase */
3132 ListBase *seq_seqbase(ListBase *seqbase, Sequence *seq)
3133 {
3134         Sequence *iseq;
3135         ListBase *lb= NULL;
3136
3137         for(iseq= seqbase->first; iseq; iseq= iseq->next) {
3138                 if(seq==iseq) {
3139                         return seqbase;
3140                 }
3141                 else if(iseq->seqbase.first && (lb= seq_seqbase(&iseq->seqbase, seq))) {
3142                         return lb;
3143                 }
3144         }
3145
3146         return NULL;
3147 }
3148
3149 int seq_swap(Sequence *seq_a, Sequence *seq_b)
3150 {
3151         char name[sizeof(seq_a->name)];
3152
3153         if(seq_a->len != seq_b->len)
3154                 return 0;
3155
3156         /* type checking, could be more advanced but disalow sound vs non-sound copy */
3157         if(seq_a->type != seq_b->type) {
3158                 if(seq_a->type == SEQ_SOUND || seq_b->type == SEQ_SOUND) {
3159                         return 0;
3160                 }
3161
3162                 /* disallow effects to swap with non-effects strips */
3163                 if((seq_a->type & SEQ_EFFECT) != (seq_b->type & SEQ_EFFECT)) {
3164                         return 0;
3165                 }
3166
3167                 if((seq_a->type & SEQ_EFFECT) && (seq_b->type & SEQ_EFFECT)) {
3168                         if(get_sequence_effect_num_inputs(seq_a->type) != get_sequence_effect_num_inputs(seq_b->type)) {
3169                                 return 0;
3170                         }
3171                 }
3172         }
3173
3174         SWAP(Sequence, *seq_a, *seq_b);
3175
3176         /* swap back names so animation fcurves dont get swapped */
3177         strcpy(name, seq_a->name+2);
3178         strcpy(seq_a->name+2, seq_b->name+2);
3179         strcpy(seq_b->name+2, name);
3180
3181         /* swap back opacity, and overlay mode */
3182         SWAP(int, seq_a->blend_mode, seq_b->blend_mode);
3183         SWAP(float, seq_a->blend_opacity, seq_b->blend_opacity);
3184
3185
3186         SWAP(void *, seq_a->prev, seq_b->prev);
3187         SWAP(void *, seq_a->next, seq_b->next);
3188         SWAP(int, seq_a->start, seq_b->start);
3189         SWAP(int, seq_a->startofs, seq_b->startofs);
3190         SWAP(int, seq_a->endofs, seq_b->endofs);
3191         SWAP(int, seq_a->startstill, seq_b->startstill);
3192         SWAP(int, seq_a->endstill, seq_b->endstill);
3193         SWAP(int, seq_a->machine, seq_b->machine);
3194         SWAP(int, seq_a->startdisp, seq_b->startdisp);
3195         SWAP(int, seq_a->enddisp, seq_b->enddisp);
3196
3197         return 1;
3198 }
3199
3200 /* XXX - hackish function needed for transforming strips! TODO - have some better solution */
3201 void seq_offset_animdata(Scene *scene, Sequence *seq, int ofs)
3202 {
3203         char str[32];
3204         FCurve *fcu;
3205
3206         if(scene->adt==NULL || ofs==0 || scene->adt->action==NULL)
3207                 return;
3208
3209         sprintf(str, "[\"%s\"]", seq->name+2);
3210
3211         for (fcu= scene->adt->action->curves.first; fcu; fcu= fcu->next) {
3212                 if(strstr(fcu->rna_path, "sequence_editor.sequences_all[") && strstr(fcu->rna_path, str)) {
3213                         int i;
3214                         for (i = 0; i < fcu->totvert; i++) {
3215                                 BezTriple *bezt= &fcu->bezt[i];
3216                                 bezt->vec[0][0] += ofs;
3217                                 bezt->vec[1][0] += ofs;
3218                                 bezt->vec[2][0] += ofs;
3219                         }
3220                 }
3221         }
3222 }
3223
3224 void seq_dupe_animdata(Scene *scene, char *name_from, char *name_to)
3225 {
3226         char str_from[32];
3227         FCurve *fcu;
3228         FCurve *fcu_last;
3229         FCurve *fcu_cpy;
3230         ListBase lb= {NULL, NULL};
3231
3232         if(scene->adt==NULL || scene->adt->action==NULL)
3233                 return;
3234
3235         sprintf(str_from, "[\"%s\"]", name_from);
3236
3237         fcu_last= scene->adt->action->curves.last;
3238
3239         for (fcu= scene->adt->action->curves.first; fcu && fcu->prev != fcu_last; fcu= fcu->next) {
3240                 if(strstr(fcu->rna_path, "sequence_editor.sequences_all[") && strstr(fcu->rna_path, str_from)) {
3241                         fcu_cpy= copy_fcurve(fcu);
3242                         BLI_addtail(&lb, fcu_cpy);
3243                 }
3244         }
3245
3246         /* notice validate is 0, keep this because the seq may not be added to the scene yet */
3247         BKE_animdata_fix_paths_rename(&scene->id, scene->adt, "sequence_editor.sequences_all", name_from, name_to, 0, 0, 0);
3248
3249         /* add the original fcurves back */
3250         addlisttolist(&scene->adt->action->curves, &lb);
3251 }
3252
3253 /* XXX - hackish function needed to remove all fcurves belonging to a sequencer strip */
3254 static void seq_free_animdata(Scene *scene, Sequence *seq)
3255 {
3256         char str[32];
3257         FCurve *fcu;
3258
3259         if(scene->adt==NULL || scene->adt->action==NULL)
3260                 return;
3261
3262         sprintf(str, "[\"%s\"]", seq->name+2);
3263
3264         fcu= scene->adt->action->curves.first; 
3265
3266         while (fcu) {
3267                 if(strstr(fcu->rna_path, "sequence_editor.sequences_all[") && strstr(fcu->rna_path, str)) {
3268                         FCurve *next_fcu = fcu->next;
3269                         
3270                         BLI_remlink(&scene->adt->action->curves, fcu);
3271                         free_fcurve(fcu);
3272
3273                         fcu = next_fcu;
3274        &nbs