r1053: Add Russian translation.
[cinelerra_cv.git] / cinelerra / batchrender.C
blob2355ff173ddd193fe0b4a770c4c0281cfd091cb9
1 #include "asset.h"
2 #include "batchrender.h"
3 #include "bcsignals.h"
4 #include "confirmsave.h"
5 #include "bchash.h"
6 #include "edl.h"
7 #include "edlsession.h"
8 #include "errorbox.h"
9 #include "filesystem.h"
10 #include "filexml.h"
11 #include "keys.h"
12 #include "language.h"
13 #include "mainsession.h"
14 #include "mutex.h"
15 #include "mwindow.h"
16 #include "mwindowgui.h"
17 #include "packagedispatcher.h"
18 #include "packagerenderer.h"
19 #include "preferences.h"
20 #include "render.h"
21 #include "theme.h"
22 #include "transportque.h"
23 #include "vframe.h"
29 static char *list_titles[] = 
31         N_("Enabled"), 
32         N_("Output"),
33         N_("EDL"),
34         N_("Elapsed")
37 static int list_widths[] =
39         50,
40         100,
41         200,
42         100
45 BatchRenderMenuItem::BatchRenderMenuItem(MWindow *mwindow)
46  : BC_MenuItem(_("Batch Render..."), "Shift-B", 'B')
48         set_shift(1); 
49         this->mwindow = mwindow;
52 int BatchRenderMenuItem::handle_event()
54         mwindow->batch_render->start();
55         return 1;
65 BatchRenderJob::BatchRenderJob(Preferences *preferences)
67         this->preferences = preferences;
68         asset = new Asset;
69         edl_path[0] = 0;
70         strategy = 0;
71         enabled = 1;
72         elapsed = 0;
75 BatchRenderJob::~BatchRenderJob()
77         Garbage::delete_object(asset);
80 void BatchRenderJob::copy_from(BatchRenderJob *src)
82         asset->copy_from(src->asset, 0);
83         strcpy(edl_path, src->edl_path);
84         strategy = src->strategy;
85         enabled = src->enabled;
86         elapsed = 0;
89 void BatchRenderJob::load(FileXML *file)
91         int result = 0;
93         edl_path[0] = 0;
94         file->tag.get_property("EDL_PATH", edl_path);
95         strategy = file->tag.get_property("STRATEGY", strategy);
96         enabled = file->tag.get_property("ENABLED", enabled);
97         elapsed = file->tag.get_property("ELAPSED", elapsed);
98         fix_strategy();
100         result = file->read_tag();
101         if(!result)
102         {
103                 if(file->tag.title_is("ASSET"))
104                 {
105                         file->tag.get_property("SRC", asset->path);
106                         asset->read(file, 0);
107 // The compression parameters are stored in the defaults to reduce
108 // coding maintenance.  The defaults must now be stuffed into the XML for
109 // unique storage.
110                         BC_Hash defaults;
111                         defaults.load_string(file->read_text());
112                         asset->load_defaults(&defaults,
113                                 "",
114                                 0,
115                                 1,
116                                 0,
117                                 0,
118                                 0);
119                 }
120         }
123 void BatchRenderJob::save(FileXML *file)
125 TRACE("BatchRenderJob::save 1");
126         file->tag.set_property("EDL_PATH", edl_path);
127 TRACE("BatchRenderJob::save 1");
128         file->tag.set_property("STRATEGY", strategy);
129 TRACE("BatchRenderJob::save 1");
130         file->tag.set_property("ENABLED", enabled);
131 TRACE("BatchRenderJob::save 1");
132         file->tag.set_property("ELAPSED", elapsed);
133 TRACE("BatchRenderJob::save 1");
134         file->append_tag();
135 TRACE("BatchRenderJob::save 1");
136         file->append_newline();
137 TRACE("BatchRenderJob::save 1");
138         asset->write(file,
139                 0,
140                 "");
142 // The compression parameters are stored in the defaults to reduce
143 // coding maintenance.  The defaults must now be stuffed into the XML for
144 // unique storage.
145         BC_Hash defaults;
146         asset->save_defaults(&defaults, 
147                 "",
148                 0,
149                 1,
150                 0,
151                 0,
152                 0);
153         char *string;
154         defaults.save_string(string);
155         file->append_text(string);
156         delete [] string;
157 TRACE("BatchRenderJob::save 1");
158         file->tag.set_title("/JOB");
159 TRACE("BatchRenderJob::save 1");
160         file->append_tag();
161 TRACE("BatchRenderJob::save 1");
162         file->append_newline();
163 TRACE("BatchRenderJob::save 10");
166 void BatchRenderJob::fix_strategy()
168         strategy = Render::fix_strategy(strategy, preferences->use_renderfarm);
180 BatchRenderThread::BatchRenderThread(MWindow *mwindow)
181  : BC_DialogThread()
183         this->mwindow = mwindow;
184         current_job = 0;
185         rendering_job = -1;
186         is_rendering = 0;
187         default_job = 0;
190 BatchRenderThread::BatchRenderThread()
191  : BC_DialogThread()
193         mwindow = 0;
194         current_job = 0;
195         rendering_job = -1;
196         is_rendering = 0;
197         default_job = 0;
200 void BatchRenderThread::handle_close_event(int result)
202 // Save settings
203 TRACE("BatchRenderThread::handle_close_event 1");
204         char path[BCTEXTLEN];
205 TRACE("BatchRenderThread::handle_close_event 1");
206         path[0] = 0;
207 TRACE("BatchRenderThread::handle_close_event 1");
208         save_jobs(path);
209 TRACE("BatchRenderThread::handle_close_event 1");
210         save_defaults(mwindow->defaults);
211 TRACE("BatchRenderThread::handle_close_event 1");
212         delete default_job;
213 TRACE("BatchRenderThread::handle_close_event 1");
214         default_job = 0;
215 TRACE("BatchRenderThread::handle_close_event 1");
216         jobs.remove_all_objects();
217 TRACE("BatchRenderThread::handle_close_event 100");
220 BC_Window* BatchRenderThread::new_gui()
222         current_start = 0.0;
223         current_end = 0.0;
224         default_job = new BatchRenderJob(mwindow->preferences);
226         char path[BCTEXTLEN];
227         path[0] = 0;
228         load_jobs(path, mwindow->preferences);
229         load_defaults(mwindow->defaults);
230         this->gui = new BatchRenderGUI(mwindow, 
231                 this,
232                 mwindow->session->batchrender_x,
233                 mwindow->session->batchrender_y,
234                 mwindow->session->batchrender_w,
235                 mwindow->session->batchrender_h);
236         this->gui->create_objects();
237         return this->gui;
241 void BatchRenderThread::load_jobs(char *path, Preferences *preferences)
243         FileXML file;
244         int result = 0;
246         jobs.remove_all_objects();
247         if(path[0])
248                 file.read_from_file(path);
249         else
250                 file.read_from_file(create_path(path));
252         while(!result)
253         {
254                 if(!(result = file.read_tag()))
255                 {
256                         if(file.tag.title_is("JOB"))
257                         {
258                                 BatchRenderJob *job;
259                                 jobs.append(job = new BatchRenderJob(preferences));
260                                 job->load(&file);
261                         }
262                 }
263         }
266 void BatchRenderThread::save_jobs(char *path)
268         FileXML file;
270         for(int i = 0; i < jobs.total; i++)
271         {
272                 file.tag.set_title("JOB");
273                 jobs.values[i]->save(&file);
274         }
276         if(path[0])
277                 file.write_to_file(path);
278         else
279                 file.write_to_file(create_path(path));
282 void BatchRenderThread::load_defaults(BC_Hash *defaults)
284         if(default_job)
285         {
286                 default_job->asset->load_defaults(defaults,
287                         "BATCHRENDER_",
288                         1,
289                         1,
290                         1,
291                         1,
292                         1);
293                 default_job->fix_strategy();
294         }
296         for(int i = 0; i < BATCHRENDER_COLUMNS; i++)
297         {
298                 char string[BCTEXTLEN];
299                 sprintf(string, "BATCHRENDER_COLUMN%d", i);
300                 column_width[i] = defaults->get(string, list_widths[i]);
301         }
304 void BatchRenderThread::save_defaults(BC_Hash *defaults)
306         if(default_job)
307         {
308                 default_job->asset->save_defaults(defaults,
309                         "BATCHRENDER_",
310                         1,
311                         1,
312                         1,
313                         1,
314                         1);
315                 defaults->update("BATCHRENDER_STRATEGY", default_job->strategy);
316         }
317         for(int i = 0; i < BATCHRENDER_COLUMNS; i++)
318         {
319                 char string[BCTEXTLEN];
320                 sprintf(string, "BATCHRENDER_COLUMN%d", i);
321                 defaults->update(string, column_width[i]);
322         }
323 //      defaults->update("BATCHRENDER_JOB", current_job);
324         if(mwindow)
325                 mwindow->save_defaults();
326         else
327                 defaults->save();
330 char* BatchRenderThread::create_path(char *string)
332         FileSystem fs;
333         sprintf(string, "%s", BCASTDIR);
334         fs.complete_path(string);
335         strcat(string, BATCH_PATH);
336         return string;
339 void BatchRenderThread::new_job()
341         BatchRenderJob *result = new BatchRenderJob(mwindow->preferences);
342         result->copy_from(get_current_job());
343         jobs.append(result);
344         current_job = jobs.total - 1;
345         gui->create_list(1);
346         gui->change_job();
349 void BatchRenderThread::delete_job()
351         if(current_job < jobs.total && current_job >= 0)
352         {
353                 jobs.remove_object_number(current_job);
354                 if(current_job > 0) current_job--;
355                 gui->create_list(1);
356                 gui->change_job();
357         }
360 BatchRenderJob* BatchRenderThread::get_current_job()
362         BatchRenderJob *result;
363         if(current_job >= jobs.total || current_job < 0)
364         {
365                 result = default_job;
366         }
367         else
368         {
369                 result = jobs.values[current_job];
370         }
371         return result;
375 Asset* BatchRenderThread::get_current_asset()
377         return get_current_job()->asset;
380 char* BatchRenderThread::get_current_edl()
382         return get_current_job()->edl_path;
386 // Test EDL files for existence
387 int BatchRenderThread::test_edl_files()
389         for(int i = 0; i < jobs.total; i++)
390         {
391                 if(jobs.values[i]->enabled)
392                 {
393                         FILE *fd = fopen(jobs.values[i]->edl_path, "r");
394                         if(!fd)
395                         {
396                                 char string[BCTEXTLEN];
397                                 sprintf(string, _("EDL %s not found.\n"), jobs.values[i]->edl_path);
398                                 if(mwindow)
399                                 {
400                                         ErrorBox error_box(PROGRAM_NAME ": Error",
401                                                 mwindow->gui->get_abs_cursor_x(1),
402                                                 mwindow->gui->get_abs_cursor_y(1));
403                                         error_box.create_objects(string);
404                                         error_box.run_window();
405                                         gui->new_batch->enable();
406                                         gui->delete_batch->enable();
407                                 }
408                                 else
409                                 {
410                                         fprintf(stderr, 
411                                                 "%s",
412                                                 string);
413                                 }
415                                 is_rendering = 0;
416                                 return 1;
417                         }
418                         else
419                         {
420                                 fclose(fd);
421                         }
422                 }
423         }
424         return 0;
427 void BatchRenderThread::calculate_dest_paths(ArrayList<char*> *paths,
428         Preferences *preferences,
429         ArrayList<PluginServer*> *plugindb)
431         for(int i = 0; i < jobs.total; i++)
432         {
433                 BatchRenderJob *job = jobs.values[i];
434                 if(job->enabled)
435                 {
436                         PackageDispatcher *packages = new PackageDispatcher;
438 // Load EDL
439                         TransportCommand *command = new TransportCommand;
440                         FileXML *file = new FileXML;
441                         file->read_from_file(job->edl_path);
443 // Use command to calculate range.
444                         command->command = NORMAL_FWD;
445                         command->get_edl()->load_xml(plugindb, 
446                                 file, 
447                                 LOAD_ALL);
448                         command->change_type = CHANGE_ALL;
449                         command->set_playback_range();
450                         command->playback_range_adjust_inout();
452 // Create test packages
453                         packages->create_packages(mwindow,
454                                 command->get_edl(),
455                                 preferences,
456                                 job->strategy, 
457                                 job->asset, 
458                                 command->start_position, 
459                                 command->end_position,
460                                 0);
462 // Append output paths allocated to total
463                         packages->get_package_paths(paths);
465 // Delete package harness
466                         delete packages;
467                         delete command;
468                         delete file;
469                 }
470         }
474 void BatchRenderThread::start_rendering(char *config_path,
475         char *batch_path)
477         BC_Hash *boot_defaults;
478         Preferences *preferences;
479         Render *render;
480         ArrayList<PluginServer*> *plugindb;
482 // Initialize stuff which MWindow does.
483         MWindow::init_defaults(boot_defaults, config_path);
484         load_defaults(boot_defaults);
485         preferences = new Preferences;
486         preferences->load_defaults(boot_defaults);
487         MWindow::init_plugins(preferences, plugindb, 0);
489         load_jobs(batch_path, preferences);
490         save_jobs(batch_path);
491         save_defaults(boot_defaults);
493 // Test EDL files for existence
494         if(test_edl_files()) return;
497 // Predict all destination paths
498         ArrayList<char*> paths;
499         calculate_dest_paths(&paths,
500                 preferences,
501                 plugindb);
503         int result = ConfirmSave::test_files(0, &paths);
504         paths.remove_all_objects();
506 // Abort on any existing file because it's so hard to set this up.
507         if(result) return;
509         render = new Render(0);
510         render->start_batches(&jobs, 
511                 boot_defaults,
512                 preferences,
513                 plugindb);
516 void BatchRenderThread::start_rendering()
518         if(is_rendering) return;
520         is_rendering = 1;
521         char path[BCTEXTLEN];
522         path[0] = 0;
523         save_jobs(path);
524         save_defaults(mwindow->defaults);
525         gui->new_batch->disable();
526         gui->delete_batch->disable();
528 // Test EDL files for existence
529         if(test_edl_files()) return;
531 // Predict all destination paths
532         ArrayList<char*> paths;
533         calculate_dest_paths(&paths,
534                 mwindow->preferences,
535                 mwindow->plugindb);
537 // Test destination files for overwrite
538         int result = ConfirmSave::test_files(mwindow, &paths);
539         paths.remove_all_objects();
541 // User cancelled
542         if(result)
543         {
544                 is_rendering = 0;
545                 gui->new_batch->enable();
546                 gui->delete_batch->enable();
547                 return;
548         }
550         mwindow->render->start_batches(&jobs);
553 void BatchRenderThread::stop_rendering()
555         if(!is_rendering) return;
556         mwindow->render->stop_operation();
557         is_rendering = 0;
560 void BatchRenderThread::update_active(int number)
562         gui->lock_window("BatchRenderThread::update_active");
563         if(number >= 0)
564         {
565                 current_job = number;
566                 rendering_job = number;
567         }
568         else
569         {
570                 rendering_job = -1;
571                 is_rendering = 0;
572         }
573         gui->create_list(1);
574         gui->unlock_window();
577 void BatchRenderThread::update_done(int number, 
578         int create_list, 
579         double elapsed_time)
581         gui->lock_window("BatchRenderThread::update_done");
582         if(number < 0)
583         {
584                 gui->new_batch->enable();
585                 gui->delete_batch->enable();
586         }
587         else
588         {
589                 jobs.values[number]->enabled = 0;
590                 jobs.values[number]->elapsed = elapsed_time;
591                 if(create_list) gui->create_list(1);
592         }
593         gui->unlock_window();
596 void BatchRenderThread::move_batch(int src, int dst)
598         BatchRenderJob *src_job = jobs.values[src];
599         if(dst < 0) dst = jobs.total - 1;
601         if(dst != src)
602         {
603                 for(int i = src; i < jobs.total - 1; i++)
604                         jobs.values[i] = jobs.values[i + 1];
605 //              if(dst > src) dst--;
606                 for(int i = jobs.total - 1; i > dst; i--)
607                         jobs.values[i] = jobs.values[i - 1];
608                 jobs.values[dst] = src_job;
609                 gui->create_list(1);
610         }
621 BatchRenderGUI::BatchRenderGUI(MWindow *mwindow, 
622         BatchRenderThread *thread,
623         int x,
624         int y,
625         int w,
626         int h)
627  : BC_Window(PROGRAM_NAME ": Batch Render", 
628         x,
629         y,
630         w, 
631         h, 
632         50, 
633         50, 
634         1,
635         0, 
636         1)
638         this->mwindow = mwindow;
639         this->thread = thread;
642 BatchRenderGUI::~BatchRenderGUI()
644         delete format_tools;
648 void BatchRenderGUI::create_objects()
650         mwindow->theme->get_batchrender_sizes(this, get_w(), get_h());
651         create_list(0);
653         int x = mwindow->theme->batchrender_x1;
654         int y = 5;
655         int x1 = mwindow->theme->batchrender_x1;
656         int x2 = mwindow->theme->batchrender_x2;
657         int x3 = mwindow->theme->batchrender_x3;
658         int y1 = y;
659         int y2;
661 // output file
662         add_subwindow(output_path_title = new BC_Title(x1, y, _("Output path:")));
663         y += 20;
664         format_tools = new BatchFormat(mwindow,
665                                         this, 
666                                         thread->get_current_asset());
667         format_tools->create_objects(x, 
668                                                 y, 
669                                                 1, 
670                                                 1, 
671                                                 1, 
672                                                 1, 
673                                                 0, 
674                                                 1, 
675                                                 0, 
676                                                 0, 
677                                                 &thread->get_current_job()->strategy, 
678                                                 0);
680         x2 = x;
681         y2 = y + 10;
682         x += format_tools->get_w();
683         y = y1;
684         x1 = x;
685         x3 = x + 80;
687 // input EDL
688         x = x1;
689         add_subwindow(edl_path_title = new BC_Title(x, y, _("EDL Path:")));
690         y += 20;
691         add_subwindow(edl_path_text = new BatchRenderEDLPath(
692                 thread, 
693                 x, 
694                 y, 
695                 get_w() - x - 40, 
696                 thread->get_current_edl()));
698         x += edl_path_text->get_w();
699         add_subwindow(edl_path_browse = new BrowseButton(
700                 mwindow,
701                 this,
702                 edl_path_text, 
703                 x, 
704                 y, 
705                 thread->get_current_edl(),
706                 _("Input EDL"),
707                 _("Select an EDL to load:"),
708                 0));
710         x = x1;
712         y += 45;
713         add_subwindow(new_batch = new BatchRenderNew(thread, 
714                 x, 
715                 y));
716         x += new_batch->get_w() + 10;
718         add_subwindow(delete_batch = new BatchRenderDelete(thread, 
719                 x, 
720                 y));
721         x += delete_batch->get_w() + 10;
723         add_subwindow(savelist_batch = new BatchRenderSaveList(thread, 
724                 x, 
725                 y));
726         x += savelist_batch->get_w() + 10;
728         add_subwindow(loadlist_batch = new BatchRenderLoadList(thread, 
729                 x, 
730                 y));
731         x += loadlist_batch->get_w() + 10;
734         x = x2;
735         y = y2;
736         add_subwindow(list_title = new BC_Title(x, y, _("Batches to render:")));
737         y += 20;
738         add_subwindow(batch_list = new BatchRenderList(thread, 
739                 x, 
740                 y,
741                 get_w() - x - 10,
742                 get_h() - y - BC_GenericButton::calculate_h() - 15));
744         y += batch_list->get_h() + 10;
745         add_subwindow(start_button = new BatchRenderStart(thread, 
746             x, 
747             y));
748         x = get_w() / 2 -
749                 BC_GenericButton::calculate_w(this, _("Stop")) / 2;
750         add_subwindow(stop_button = new BatchRenderStop(thread, 
751                 x, 
752                 y));
753         x = get_w() - 
754                 BC_GenericButton::calculate_w(this, _("Close")) - 
755                 10;
756         add_subwindow(cancel_button = new BatchRenderCancel(thread, 
757                 x, 
758                 y));
760         show_window();
763 int BatchRenderGUI::resize_event(int w, int h)
765         mwindow->session->batchrender_w = w;
766         mwindow->session->batchrender_h = h;
767         mwindow->theme->get_batchrender_sizes(this, w, h);
769         int x = mwindow->theme->batchrender_x1;
770         int y = 5;
771         int x1 = mwindow->theme->batchrender_x1;
772         int x2 = mwindow->theme->batchrender_x2;
773         int x3 = mwindow->theme->batchrender_x3;
774         int y1 = y;
775         int y2;
777         output_path_title->reposition_window(x1, y);
778         y += 20;
779         format_tools->reposition_window(x, y);
780         x2 = x;
781         y2 = y + 10;
782         y = y1;
783         x += format_tools->get_w();
784         x1 = x;
785         x3 = x + 80;
787         x = x1;
788         edl_path_title->reposition_window(x, y);
789         y += 20;
790         edl_path_text->reposition_window(x, y, w - x - 40);
791         x += edl_path_text->get_w();
792         edl_path_browse->reposition_window(x, y);
794         x = x1;
795 //      y += 30;
796 //      status_title->reposition_window(x, y);
797 //      x = x3;
798 //      status_text->reposition_window(x, y);
799 //      x = x1;
800 //      y += 30;
801 //      progress_bar->reposition_window(x, y, w - x - 10);
803         y += 30;
804         new_batch->reposition_window(x, y);
805         x += new_batch->get_w() + 10;
806         delete_batch->reposition_window(x, y);
807         x += delete_batch->get_w() + 10;
809         x = x2;
810         y = y2;
811         int y_margin = get_h() - batch_list->get_h();
812         list_title->reposition_window(x, y);
813         y += 20;
814         batch_list->reposition_window(x, y, w - x - 10, h - y_margin);
816         y += batch_list->get_h() + 10;
817         start_button->reposition_window(x, y);
818         x = w / 2 - 
819                 stop_button->get_w() / 2;
820         stop_button->reposition_window(x, y);
821         x = w -
822                 cancel_button->get_w() - 
823                 10;
824         cancel_button->reposition_window(x, y);
825         return 1;
828 int BatchRenderGUI::translation_event()
830         mwindow->session->batchrender_x = get_x();
831         mwindow->session->batchrender_y = get_y();
832         return 1;
835 int BatchRenderGUI::close_event()
837 // Stop batch rendering
838         unlock_window();
839         thread->stop_rendering();
840         lock_window("BatchRenderGUI::close_event");
841         set_done(1);
842         return 1;
845 void BatchRenderGUI::create_list(int update_widget)
847         for(int i = 0; i < BATCHRENDER_COLUMNS; i++)
848         {
849                 list_columns[i].remove_all_objects();
850         }
852         for(int i = 0; i < thread->jobs.total; i++)
853         {
854                 BatchRenderJob *job = thread->jobs.values[i];
855                 char string[BCTEXTLEN];
856                 BC_ListBoxItem *enabled = new BC_ListBoxItem(job->enabled ? 
857                         (char*)"X" : 
858                         (char*)" ");
859                 BC_ListBoxItem *item1 = new BC_ListBoxItem(job->asset->path);
860                 BC_ListBoxItem *item2 = new BC_ListBoxItem(job->edl_path);
861                 BC_ListBoxItem *item3;
862                 if(job->elapsed)
863                         item3 = new BC_ListBoxItem(
864                                 Units::totext(string,
865                                         job->elapsed,
866                                         TIME_HMS2));
867                 else
868                         item3 = new BC_ListBoxItem(_("Unknown"));
869                 list_columns[0].append(enabled);
870                 list_columns[1].append(item1);
871                 list_columns[2].append(item2);
872                 list_columns[3].append(item3);
873                 if(i == thread->current_job)
874                 {
875                         enabled->set_selected(1);
876                         item1->set_selected(1);
877                         item2->set_selected(1);
878                         item3->set_selected(1);
879                 }
880                 if(i == thread->rendering_job)
881                 {
882                         enabled->set_color(RED);
883                         item1->set_color(RED);
884                         item2->set_color(RED);
885                         item3->set_color(RED);
886                 }
887         }
889         if(update_widget)
890         {
891                 batch_list->update(list_columns,
892                                                 list_titles,
893                                                 thread->column_width,
894                                                 BATCHRENDER_COLUMNS,
895                                                 batch_list->get_xposition(),
896                                                 batch_list->get_yposition(), 
897                                                 batch_list->get_highlighted_item(),  // Flat index of item cursor is over
898                                                 1,     // set all autoplace flags to 1
899                                                 1);
900         }
903 void BatchRenderGUI::change_job()
905         BatchRenderJob *job = thread->get_current_job();
906         format_tools->update(job->asset, &job->strategy);
907         edl_path_text->update(job->edl_path);
917 BatchFormat::BatchFormat(MWindow *mwindow,
918                         BatchRenderGUI *gui,
919                         Asset *asset)
920  : FormatTools(mwindow, gui, asset)
922         this->gui = gui;
923         this->mwindow = mwindow;
926 BatchFormat::~BatchFormat()
931 int BatchFormat::handle_event()
933         gui->create_list(1);
934         return 1;
947 BatchRenderEDLPath::BatchRenderEDLPath(BatchRenderThread *thread, 
948         int x, 
949         int y, 
950         int w, 
951         char *text)
952  : BC_TextBox(x, 
953                 y, 
954                 w, 
955                 1,
956                 text)
958         this->thread = thread;
962 int BatchRenderEDLPath::handle_event()
964         strcpy(thread->get_current_edl(), get_text());
965         thread->gui->create_list(1);
966         return 1;
974 BatchRenderNew::BatchRenderNew(BatchRenderThread *thread, 
975         int x, 
976         int y)
977  : BC_GenericButton(x, y, _("New"))
979         this->thread = thread;
982 int BatchRenderNew::handle_event()
984         thread->new_job();
985         return 1;
988 BatchRenderDelete::BatchRenderDelete(BatchRenderThread *thread, 
989         int x, 
990         int y)
991  : BC_GenericButton(x, y, _("Delete"))
993         this->thread = thread;
996 int BatchRenderDelete::handle_event()
998         thread->delete_job();
999         return 1;
1004 BatchRenderSaveList::BatchRenderSaveList(BatchRenderThread *thread, 
1005         int x, 
1006         int y)
1007  : BC_GenericButton(x, y, _("Save List"))
1009         this->thread = thread;
1010         set_tooltip(_("Save a Batch Render List"));
1011         gui = 0;
1012         startup_lock = new Mutex("BatchRenderSaveList::startup_lock");
1015 BatchRenderSaveList::~BatchRenderSaveList()
1017         startup_lock->lock("BatchRenderSaveList::~BrowseButton");
1018         if(gui)
1019         {
1020                 gui->lock_window();
1021                 gui->set_done(1);
1022                 gui->unlock_window();
1023         }
1024         startup_lock->unlock();
1025         Thread::join();
1026         delete startup_lock;
1029 int BatchRenderSaveList::handle_event()
1031         if(Thread::running())
1032         {
1033                 if(gui)
1034                 {
1035                         gui->lock_window();
1036                         gui->raise_window();
1037                         gui->unlock_window();
1038                 }
1039                 return 1;
1040         }
1041         startup_lock->lock("BatchRenderSaveList::handle_event 1");
1042         Thread::start();
1043         startup_lock->lock("BatchRenderSaveList::handle_event 2");
1044         startup_lock->unlock();
1045         return 1;
1048 void BatchRenderSaveList::run()
1050         char default_path[BCTEXTLEN];
1051         sprintf(default_path, "~");
1052         BC_FileBox filewindow(100,
1053                               100,
1054                               this->thread->mwindow->defaults->get("DEFAULT_BATCHLOADPATH", default_path),
1055                               _("Save Batch Render List"),
1056                               _("Enter a Batch Render filename to save as:"),
1057                               0,
1058                               0,
1059                               0,
1060                               0);
1062         gui = &filewindow;
1064         startup_lock->unlock();
1065         filewindow.create_objects();
1067         int result2 = filewindow.run_window();
1069         if(!result2)
1070         {
1071                 this->thread->save_jobs(filewindow.get_submitted_path());
1072                 this->thread->mwindow->defaults->update("DEFAULT_BATCHLOADPATH", filewindow.get_submitted_path());
1073         }
1075         this->thread->gui->flush();
1076         startup_lock->lock("BatchRenderLoadList::run");
1077         gui = 0;
1078         startup_lock->unlock();
1081 int BatchRenderSaveList::keypress_event() {
1082         if (get_keypress() == 's' || 
1083             get_keypress() == 'S') return handle_event();
1084         return 0;
1090 BatchRenderLoadList::BatchRenderLoadList(BatchRenderThread *thread, 
1091         int x, 
1092         int y)
1093   : BC_GenericButton(x, y, _("Load List")),
1094     Thread()
1096         this->thread = thread;
1097         set_tooltip(_("Load a previously saved Batch Render List"));
1098         gui = 0;
1099         startup_lock = new Mutex("BatchRenderLoadList::startup_lock");
1102 BatchRenderLoadList::~BatchRenderLoadList()
1104         startup_lock->lock("BatchRenderLoadList::~BrowseButton");
1105         if(gui)
1106         {
1107                 gui->lock_window();
1108                 gui->set_done(1);
1109                 gui->unlock_window();
1110         }
1111         startup_lock->unlock();
1112         Thread::join();
1113         delete startup_lock;
1116 int BatchRenderLoadList::handle_event()
1118         if(Thread::running())
1119         {
1120                 if(gui)
1121                 {
1122                         gui->lock_window();
1123                         gui->raise_window();
1124                         gui->unlock_window();
1125                 }
1126                 return 1;
1127         }
1128         startup_lock->lock("BatchRenderLoadList::handle_event 1");
1129         Thread::start();
1130         startup_lock->lock("BatchRenderLoadList::handle_event 2");
1131         startup_lock->unlock();
1132         return 1;
1135 void BatchRenderLoadList::run()
1137         char default_path[BCTEXTLEN];
1138         sprintf(default_path, "~");
1139         BC_FileBox filewindow(100,
1140                               100,
1141                               this->thread->mwindow->defaults->get("DEFAULT_BATCHLOADPATH", default_path),
1142                               _("Load Batch Render List"),
1143                               _("Enter a Batch Render filename to load from:"),
1144                               0,
1145                               0,
1146                               0,
1147                               0);
1149         gui = &filewindow;
1151         startup_lock->unlock();
1152         filewindow.create_objects();
1154         int result2 = filewindow.run_window();
1156         if(!result2)
1157         {
1158                 this->thread->load_jobs(filewindow.get_submitted_path(),this->thread->mwindow->preferences);
1159                 this->thread->gui->create_list(1);
1160                 this->thread->mwindow->defaults->update("DEFAULT_BATCHLOADPATH", filewindow.get_submitted_path());
1161         }
1163         this->thread->gui->flush();
1164         startup_lock->lock("BatchRenderLoadList::run");
1165         gui = 0;
1166         startup_lock->unlock();
1169 int BatchRenderLoadList::keypress_event() {
1170         if (get_keypress() == 'o' || 
1171             get_keypress() == 'O') return handle_event();
1172         return 0;
1175 BatchRenderList::BatchRenderList(BatchRenderThread *thread, 
1176         int x, 
1177         int y,
1178         int w,
1179         int h)
1180  : BC_ListBox(x, 
1181         y, 
1182         w, 
1183         h, 
1184         LISTBOX_TEXT,
1185         thread->gui->list_columns,
1186         list_titles,
1187         thread->column_width,
1188         BATCHRENDER_COLUMNS,
1189         0,
1190         0,
1191         LISTBOX_SINGLE,
1192         ICON_LEFT,
1193         1)
1195         this->thread = thread;
1196         dragging_item = 0;
1197         set_process_drag(0);
1200 int BatchRenderList::handle_event()
1202         return 1;
1205 int BatchRenderList::selection_changed()
1207         thread->current_job = get_selection_number(0, 0);
1208         thread->gui->change_job();
1209         if(get_cursor_x() < thread->column_width[0])
1210         {
1211                 BatchRenderJob *job = thread->get_current_job();
1212                 job->enabled = !job->enabled;
1213                 thread->gui->create_list(1);
1214         }
1215         return 1;
1218 int BatchRenderList::column_resize_event()
1220         for(int i = 0; i < BATCHRENDER_COLUMNS; i++)
1221         {
1222                 thread->column_width[i] = get_column_width(i);
1223         }
1224         return 1;
1227 int BatchRenderList::drag_start_event()
1229         if(BC_ListBox::drag_start_event())
1230         {
1231                 dragging_item = 1;
1232                 return 1;
1233         }
1235         return 0;
1238 int BatchRenderList::drag_motion_event()
1240         if(BC_ListBox::drag_motion_event())
1241         {
1242                 return 1;
1243         }
1244         return 0;
1247 int BatchRenderList::drag_stop_event()
1249         if(dragging_item)
1250         {
1251                 int src = get_selection_number(0, 0);
1252                 int dst = get_highlighted_item();
1253                 if(src != dst)
1254                 {
1255                         thread->move_batch(src, dst);
1256                 }
1257                 BC_ListBox::drag_stop_event();
1258         }
1273 BatchRenderStart::BatchRenderStart(BatchRenderThread *thread, 
1274         int x, 
1275         int y)
1276  : BC_GenericButton(x, 
1277         y, 
1278         _("Start"))
1280         this->thread = thread;
1283 int BatchRenderStart::handle_event()
1285         thread->start_rendering();
1286         return 1;
1289 BatchRenderStop::BatchRenderStop(BatchRenderThread *thread, 
1290         int x, 
1291         int y)
1292  : BC_GenericButton(x, 
1293         y, 
1294         _("Stop"))
1296         this->thread = thread;
1299 int BatchRenderStop::handle_event()
1301         unlock_window();
1302         thread->stop_rendering();
1303         lock_window("BatchRenderStop::handle_event");
1304         return 1;
1308 BatchRenderCancel::BatchRenderCancel(BatchRenderThread *thread, 
1309         int x, 
1310         int y)
1311  : BC_GenericButton(x, 
1312         y, 
1313         _("Close"))
1315         this->thread = thread;
1318 int BatchRenderCancel::handle_event()
1320         unlock_window();
1321         thread->stop_rendering();
1322         lock_window("BatchRenderCancel::handle_event");
1323         thread->gui->set_done(1);
1324         return 1;
1327 int BatchRenderCancel::keypress_event()
1329         if(get_keypress() == ESC) 
1330         {
1331                 unlock_window();
1332                 thread->stop_rendering();
1333                 lock_window("BatchRenderCancel::keypress_event");
1334                 thread->gui->set_done(1);
1335                 return 1;
1336         }
1337         return 0;