#include "autoconf.h"
#include "automation.h"
#include "awindowgui.inc"
+#include "bccmodels.h"
+#include "bchash.h"
#include "bcsignals.h"
#include "clip.h"
#include "cstrdup.h"
-#include "bccmodels.h"
-#include "bchash.h"
#include "clipedls.h"
#include "edits.h"
#include "edl.h"
#include "edlsession.h"
#include "filexml.h"
+#include "floatauto.h"
+#include "floatautos.h"
#include "guicast.h"
#include "indexstate.h"
#include "interlacemodes.h"
nested_edl->create_objects();
nested_edl->read_xml(file, LOAD_ALL);
if( (load_flags & LOAD_ALL) == LOAD_ALL )
- nested_edls.add_clip(nested_edl);
+ nested_edls.get_nested(nested_edl);
nested_edl->remove_user();
}
else
// The string is not terminated in this call.
int EDL::save_xml(FileXML *file, const char *output_path)
{
- copy(0, tracks->total_length(), 1, file, output_path, 0);
+ copy(1, file, output_path, 0);
return 0;
}
return copy(start, end, all,
"/EDL", file, output_path, rewind_it);
}
+int EDL::copy(int all, FileXML *file, const char *output_path, int rewind_it)
+{
+ return copy(0, tracks->total_length(), all, file, output_path, rewind_it);
+}
int EDL::copy_clip(double start, double end, int all,
FileXML *file, const char *output_path, int rewind_it)
return copy(start, end, all,
"/CLIP_EDL", file, output_path, rewind_it);
}
+int EDL::copy_clip(int all, FileXML *file, const char *output_path, int rewind_it)
+{
+ return copy_clip(0, tracks->total_length(), all, file, output_path, rewind_it);
+}
+
int EDL::copy_nested_edl(double start, double end, int all,
FileXML *file, const char *output_path, int rewind_it)
{
return copy(start, end, all,
"/NESTED_EDL", file, output_path, rewind_it);
}
+int EDL::copy_nested_edl(int all, FileXML *file, const char *output_path, int rewind_it)
+{
+ return copy_nested_edl(0, tracks->total_length(), all, file, output_path, rewind_it);
+}
+
int EDL::copy_vwindow_edl(double start, double end, int all,
FileXML *file, const char *output_path, int rewind_it)
{
return copy(start, end, all,
"/VWINDOW_EDL", file, output_path, rewind_it);
}
+int EDL::copy_vwindow_edl(int all, FileXML *file, const char *output_path, int rewind_it)
+{
+ return copy_vwindow_edl(0, tracks->total_length(), all, file, output_path, rewind_it);
+}
+
int EDL::copy(double start, double end, int all,
const char *closer, FileXML *file,
// Don't want this if using clipboard
if( all ) {
for( int i=0; i<total_vwindow_edls(); ++i )
- get_vwindow_edl(i)->copy_vwindow_edl(0, tracks->total_length(), 1,
- file, output_path, 0);
+ get_vwindow_edl(i)->copy_vwindow_edl(1, file, output_path, 0);
for( int i=0; i<clips.size(); ++i )
- clips[i]->copy_clip(0, tracks->total_length(), 1,
- file, output_path, 0);
+ clips[i]->copy_clip(1, file, output_path, 0);
mixers.save(file);
}
return 0;
}
-EDL *EDL::get_nested(EDL *nested_edl, const char *path)
+void EDL::copy_indexables(EDL *edl)
{
- for( int i=0; i<nested_edls.size(); ++i ) {
- EDL *dst = nested_edls[i];
- if( !strcmp(path, dst->path) ) return dst;
+ for( Track *track=edl->tracks->first; track; track=track->next ) {
+ for( Edit *edit=track->edits->first; edit; edit=edit->next ) {
+ if( edit->asset )
+ assets->update(edit->asset);
+ if( edit->nested_edl )
+ nested_edls.get_nested(edit->nested_edl);
+ }
}
- return new_nested(nested_edl, path);
}
-EDL *EDL::new_nested(EDL *nested_edl, const char *path)
+EDL *EDL::new_nested(EDL *edl, const char *path)
{
- EDL *new_edl = new EDL; // no parent for nested clip
+ EDL *nested = new EDL; // no parent for nested edl
+ nested->create_objects();
+ nested->copy_session(edl);
+ nested->set_path(path);
+ nested->update_index(edl);
+ nested->copy_indexables(edl);
+ nested->tracks->copy_from(edl->tracks);
+ nested_edls.append(nested);
+ return nested;
+}
+
+EDL *EDL::create_nested_clip(EDL *nested)
+{
+ EDL *new_edl = new EDL(this); // parent for clip edl
new_edl->create_objects();
- new_edl->copy_session(this);
- new_edl->create_nested(nested_edl, path);
+ new_edl->create_nested(nested);
return new_edl;
}
-void EDL::create_nested(EDL *nested_edl, const char *path)
+void EDL::create_nested(EDL *nested)
{
- set_path(path);
- strcpy(local_session->clip_title, path);
-// save a ref to nested edl for garbage delete
- EDL *nest = clips.get_copy(nested_edl);
// Keep frame rate, sample rate, and output size unchanged.
// Nest all video & audio outputs
session->video_tracks = 1;
- session->audio_tracks = nest->session->audio_channels;
+ session->audio_tracks = nested->session->audio_channels;
create_default_tracks();
- insert_asset(0, nest, 0, 0, 0);
+ insert_asset(0, nested, 0, 0, 0);
}
void EDL::retrack()
void EDL::set_path(const char *path)
{
+ if( &this->path[0] == path ) return;
strcpy(this->path, path);
}
EDL *new_nested_edl = 0;
if( asset ) new_asset = assets->update(asset);
- if( nested_edl ) new_nested_edl = nested_edls.get_copy(nested_edl);
+ if( nested_edl ) new_nested_edl = nested_edls.get_nested(nested_edl);
// Paste video
int vtrack = 0;
return new_position;
}
+void EDL::rescale_proxy(int orig_scale, int new_scale)
+{
+ if( orig_scale == new_scale ) return;
+// project size
+ float orig_w = (float)session->output_w * orig_scale;
+ float orig_h = (float)session->output_h * orig_scale;
+ if( !parent_edl ) {
+ session->output_w = Units::round(orig_w / new_scale);
+ session->output_h = Units::round(orig_h / new_scale);
+ }
+
+// track sizes
+ for( Track *track=tracks->first; track; track=track->next ) {
+ if( track->data_type != TRACK_VIDEO ) continue;
+ orig_w = (float)track->track_w * orig_scale;
+ orig_h = (float)track->track_h * orig_scale;
+ track->track_w = Units::round(orig_w / new_scale);
+ track->track_h = Units::round(orig_h / new_scale);
+ ((MaskAutos*)track->automation->autos[AUTOMATION_MASK])->
+ set_proxy(orig_scale, new_scale);
+ ((FloatAutos*)track->automation->autos[AUTOMATION_CAMERA_X])->
+ set_proxy(orig_scale, new_scale);
+ ((FloatAutos*)track->automation->autos[AUTOMATION_CAMERA_Y])->
+ set_proxy(orig_scale, new_scale);
+ ((FloatAutos*)track->automation->autos[AUTOMATION_PROJECTOR_X])->
+ set_proxy(orig_scale, new_scale);
+ ((FloatAutos*)track->automation->autos[AUTOMATION_PROJECTOR_Y])->
+ set_proxy(orig_scale, new_scale);
+ }
+}
+
+void EDL::set_proxy(int use_scaler, int new_scale, int auto_scale,
+ ArrayList<Indexable*> *orig_assets, ArrayList<Indexable*> *proxy_assets)
+{
+ int orig_use_scaler = session->proxy_use_scaler;
+ int orig_scale = session->proxy_scale;
+// rescale to full size asset in read_frame
+ session->proxy_use_scaler = use_scaler;
+ session->proxy_scale = new_scale;
+ session->proxy_auto_scale = auto_scale;
+
+ if( use_scaler ) {
+ for( int i=0; i<proxy_assets->size(); ++i ) {
+ Asset *proxy_asset = (Asset *)proxy_assets->get(i);
+ proxy_asset->width = orig_assets->get(i)->get_w();
+ proxy_asset->height = orig_assets->get(i)->get_h();
+ }
+ new_scale = 1;
+ }
+
+ if( !orig_use_scaler )
+ rescale_proxy(orig_scale, new_scale);
+
+// change original assets to proxy assets
+ int awindow_folder = use_scaler || new_scale != 1 ? AW_PROXY_FOLDER : AW_MEDIA_FOLDER;
+ for( int i=0,n=proxy_assets->size(); i<n; ++i ) {
+ const char *orig_path = orig_assets->get(i)->path;
+ Indexable *proxy_idxbl = proxy_assets->get(i);
+ proxy_idxbl->awindow_folder = awindow_folder;
+ Asset *proxy_asset = proxy_idxbl->is_asset ? assets->update((Asset *)proxy_idxbl) : 0;
+ EDL *proxy_edl = !proxy_idxbl->is_asset ? (EDL *)proxy_idxbl : 0;
+// replace track contents
+ for( Track *track=tracks->first; track; track=track->next ) {
+ if( track->data_type != TRACK_VIDEO ) continue;
+ for( Edit *edit=track->edits->first; edit; edit=edit->next ) {
+ Indexable *idxbl = (Indexable *)edit->asset;
+ if( !idxbl ) idxbl = (Indexable *)edit->nested_edl;
+ if( !idxbl ) continue;
+ if( strcmp(idxbl->path, orig_path) ) continue;
+ edit->asset = proxy_asset;
+ edit->nested_edl = proxy_edl;
+ }
+ }
+ for( int j=0,m=clips.size(); j<m; ++j ) {
+ EDL *clip = clips[j];
+ int has_proxy = 0;
+ for( Track *track=clip->tracks->first; track; track=track->next ) {
+ if( track->data_type != TRACK_VIDEO ) continue;
+ for( Edit *edit=track->edits->first; edit; edit=edit->next ) {
+ Indexable *idxbl = (Indexable *)edit->asset;
+ if( !idxbl ) idxbl = (Indexable *)edit->nested_edl;
+ if( !idxbl ) continue;
+ if( strcmp(idxbl->path, orig_path) ) continue;
+ edit->asset = proxy_asset;
+ edit->nested_edl = proxy_edl;
+ has_proxy = 1;
+ }
+ }
+ if( has_proxy && !orig_use_scaler )
+ clip->rescale_proxy(orig_scale, new_scale);
+ }
+ }
+}
+
+void EDL::add_proxy(int use_scaler,
+ ArrayList<Indexable*> *orig_assets, ArrayList<Indexable*> *proxy_assets)
+{
+ if( use_scaler ) {
+ for( int i=0,n=proxy_assets->size(); i<n; ++i ) {
+ Asset *proxy_asset = (Asset *)proxy_assets->get(i);
+ proxy_asset->width = orig_assets->get(i)->get_w();
+ proxy_asset->height = orig_assets->get(i)->get_h();
+ }
+ }
+
+// change original assets to proxy assets
+ for( int i=0,n=proxy_assets->size(); i<n; ++i ) {
+ Asset *proxy_asset = assets->update((Asset *)proxy_assets->get(i));
+ proxy_asset->awindow_folder = AW_PROXY_FOLDER;
+// replace track contents
+ for( Track *track=tracks->first; track; track=track->next ) {
+ if( track->data_type != TRACK_VIDEO ) continue;
+ for( Edit *edit=track->edits->first; edit; edit=edit->next ) {
+ if( !edit->asset ) continue;
+ if( !strcmp(edit->asset->path, orig_assets->get(i)->path) ) {
+ edit->asset = proxy_asset;
+ }
+ }
+ }
+ }
+}
+