r373: Merged the official release 1.2.1.
[cinelerra_cv.git] / cinelerra / recordmonitor.C
blobc94d8612520b441348a356d0c30232ccefb50c35
1 #include "asset.h"
2 #include "channelpicker.h"
3 #include "condition.h"
4 #include "cursors.h"
5 #include "libdv.h"
6 #include "edl.h"
7 #include "edlsession.h"
8 #include "keys.h"
9 #include "language.h"
10 #include "meterpanel.h"
11 #include "mwindow.h"
12 #include "playbackconfig.h"
13 #include "preferences.h"
14 #include "record.h"
15 #include "recordconfig.h"
16 #include "recordgui.h"
17 #include "recordtransport.h"
18 #include "recordmonitor.h"
19 #include "mainsession.h"
20 #include "theme.h"
21 #include "videodevice.inc"
22 #include "vframe.h"
23 #include "videodevice.h"
26 RecordMonitor::RecordMonitor(MWindow *mwindow, Record *record)
27  : Thread(1)
29         this->mwindow = mwindow;
30         this->record = record;
31         device = 0;
32         thread = 0;
36 RecordMonitor::~RecordMonitor()
38         if(thread)
39         {
40                 thread->stop_playback();
41                 delete thread;
42         }
43         window->set_done(0);
44         Thread::join();
45         if(device) 
46         {
47                 device->close_all();
48                 delete device;
49         }
50         delete window;
53 int RecordMonitor::create_objects()
55         window = new RecordMonitorGUI(mwindow,
56                 record, 
57                 this);
58         window->create_objects();
60         if(record->default_asset->video_data)
61         {
62 // Configure the output for record monitoring
63                 VideoOutConfig config;
64                 device = new VideoDevice;
68 // Override default device for X11 drivers
69                 if(mwindow->edl->session->playback_config->vconfig->driver ==
70                         PLAYBACK_X11_XV) config.driver = PLAYBACK_X11_XV;
71                 config.x11_use_fields = 0;
74                 device->open_output(&config, 
75                                                 record->default_asset->frame_rate, 
76                                                 record->default_asset->width, 
77                                                 record->default_asset->height,
78                                                 window->canvas,
79                                                 0);
81                 thread = new RecordMonitorThread(mwindow, record, this);
82                 thread->start_playback();
83         }
85         Thread::start();
86         return 0;
90 void RecordMonitor::run()
92         window->run_window();
93         close_threads();
96 int RecordMonitor::close_threads()
98         if(window->channel_picker) window->channel_picker->close_threads();
101 int RecordMonitor::update(VFrame *vframe)
103         return thread->write_frame(vframe);
106 void RecordMonitor::update_channel(char *text)
108         if(window->channel_picker)
109                 window->channel_picker->channel_text->update(text);
112 int RecordMonitor::get_mbuttons_height()
114         return RECBUTTON_HEIGHT;
117 int RecordMonitor::fix_size(int &w, int &h, int width_given, float aspect_ratio)
119         w = width_given;
120         h = (int)((float)width_given / aspect_ratio);
123 float RecordMonitor::get_scale(int w)
125         if(mwindow->edl->get_aspect_ratio() > 
126                 (float)record->frame_w / record->frame_h)
127         {
128                 return (float)w / 
129                         ((float)record->frame_h * 
130                         mwindow->edl->get_aspect_ratio());
131         }
132         else
133         {
134                 return (float)w / record->frame_w;
135         }
138 int RecordMonitor::get_canvas_height()
140         return window->get_h() - get_mbuttons_height();
143 int RecordMonitor::get_channel_x()
145 //      return 240;
146         return 5;
149 int RecordMonitor::get_channel_y()
151         return 2;
163 RecordMonitorGUI::RecordMonitorGUI(MWindow *mwindow,
164         Record *record, 
165         RecordMonitor *thread)
166  : BC_Window(PROGRAM_NAME ": Video in", 
167                         mwindow->session->rmonitor_x,
168                         mwindow->session->rmonitor_y,
169                         mwindow->session->rmonitor_w, 
170                         mwindow->session->rmonitor_h, 
171                         150, 
172                         50, 
173                         1, 
174                         1,
175                         1)
177         this->mwindow = mwindow;
178         this->thread = thread;
179         this->record = record;
180         avc = 0;
181         avc1394_transport = 0;
182         avc1394transport_title = 0;
183         avc1394transport_timecode = 0;
184         avc1394transport_thread = 0;
185         bitmap = 0;
186         channel_picker = 0;
187         reverse_interlace = 0;
188         meters = 0;
189         canvas = 0;
190         current_operation = MONITOR_NONE;
193 RecordMonitorGUI::~RecordMonitorGUI()
195         if(bitmap) delete bitmap;
196         if(channel_picker) delete channel_picker;
197         if(avc1394transport_thread)
198                 delete avc1394transport_thread;
199         if(avc)
200         {
201                 delete avc;
202         }
203         if(avc1394_transport)
204         {
205                 delete avc1394_transport;
206         }
207         if(avc1394transport_title)
208                 delete avc1394transport_title;
211 int RecordMonitorGUI::create_objects()
213 // y offset for video canvas if we have the transport controls
214         int do_channel = (mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX ||
215                         mwindow->edl->session->vconfig_in->driver == CAPTURE_BUZ ||
216                         mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2 ||
217                         mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2JPEG);
218         int do_interlace = (mwindow->edl->session->vconfig_in->driver == CAPTURE_BUZ ||
219                 mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2JPEG);
220         int background_done = 0;
222         mwindow->theme->get_rmonitor_sizes(record->default_asset->audio_data, 
223                 record->default_asset->video_data,
224                 do_channel,
225                 do_interlace,
226                 0);
233         if(record->default_asset->video_data)
234         {
235                 int driver = mwindow->edl->session->vconfig_in->driver;
237                 if(driver == CAPTURE_FIREWIRE)
238                 {
239                         avc = new AVC1394Control;
240                         if(avc->device > -1)
241                         {
242                                 mwindow->theme->get_rmonitor_sizes(record->default_asset->audio_data, 
243                                         record->default_asset->video_data,
244                                         do_channel,
245                                         do_interlace,
246                                         1);
247                                 mwindow->theme->draw_rmonitor_bg(this);
248                                 background_done = 1;
250 printf("RecordMonitorGUI::create_objects %d %d\n", mwindow->theme->rmonitor_tx_x, mwindow->theme->rmonitor_tx_y);
251                                 avc1394_transport = new AVC1394Transport(mwindow,
252                                         avc,
253                                         this,
254                                         mwindow->theme->rmonitor_tx_x,
255                                         mwindow->theme->rmonitor_tx_y);
256                                 avc1394_transport->create_objects();
258                                 add_subwindow(avc1394transport_timecode =
259                                         new BC_Title(avc1394_transport->x_end,
260                                                 mwindow->theme->rmonitor_tx_y + 10,
261                                                 _("00:00:00:00"),
262                                                 MEDIUM_7SEGMENT,
263                                                 BLACK));
265                                 avc1394transport_thread =
266                                         new AVC1394TransportThread(avc1394transport_timecode,
267                                                 avc);
269                                 avc1394transport_thread->start();
271                         }
272                 }
275                 if(!background_done)
276                 {
277                         mwindow->theme->draw_rmonitor_bg(this);
278                         background_done = 1;
279                 }
281                 canvas = new RecordMonitorCanvas(mwindow, 
282                         this,
283                         record, 
284                         mwindow->theme->rmonitor_canvas_x, 
285                         mwindow->theme->rmonitor_canvas_y, 
286                         mwindow->theme->rmonitor_canvas_w, 
287                         mwindow->theme->rmonitor_canvas_h);
288                 canvas->create_objects(0);
290                 if(driver == VIDEO4LINUX ||
291                         driver == CAPTURE_BUZ ||
292                         driver == VIDEO4LINUX2 ||
293                         driver == VIDEO4LINUX2JPEG)
294                 {
295                         channel_picker = new ChannelPicker(mwindow,
296                                 record,
297                                 thread,
298                                 record->channeldb,
299                                 mwindow->theme->rmonitor_channel_x, 
300                                 mwindow->theme->rmonitor_channel_y);
301                         channel_picker->create_objects();
302                 }
304                 if(driver == CAPTURE_BUZ ||
305                         driver == VIDEO4LINUX2JPEG)
306                 {
307                         add_subwindow(reverse_interlace = new ReverseInterlace(record,
308                                 mwindow->theme->rmonitor_interlace_x, 
309                                 mwindow->theme->rmonitor_interlace_y));
310                 }
311                 
312                 add_subwindow(monitor_menu = new BC_PopupMenu(0, 
313                         0, 
314                         0, 
315                         "", 
316                         0));
317                 monitor_menu->add_item(new RecordMonitorFullsize(mwindow, 
318                         this));
319         }
322         if(!background_done)
323         {
324                 mwindow->theme->draw_rmonitor_bg(this);
325                 background_done = 1;
326         }
328         if(record->default_asset->audio_data)
329         {
330                 meters = new MeterPanel(mwindow, 
331                         this,
332                         mwindow->theme->rmonitor_meter_x,
333                         mwindow->theme->rmonitor_meter_y,
334                         mwindow->theme->rmonitor_meter_h,
335                         record->default_asset->channels,
336                         1,
337                         1);
338                 meters->create_objects();
339         }
340         return 0;
343 int RecordMonitorGUI::button_press()
345         if(get_buttonpress() == 2)
346         {
347                 return 0;
348         }
349         else
350 // Right button
351         if(get_button_down() == 3)
352         {
353                 monitor_menu->activate_menu();
354                 return 1;
355         }
356         return 0;
359 int RecordMonitorGUI::button_release()
361         return 0;
364 int RecordMonitorGUI::get_virtual_center()
368 int RecordMonitorGUI::cursor_motion()
370         return 0;
373 int RecordMonitorGUI::keypress_event()
375         int result = 0;
376         switch(get_keypress())
377         {
378                 case LEFT:
379                         if(!ctrl_down()) 
380                         { 
381                                 record->record_gui->set_translation(--(record->video_x), record->video_y, record->video_zoom);
382                         }
383                         else
384                         {
385                                 record->video_zoom -= 0.1;
386                                 record->record_gui->set_translation(record->video_x, record->video_y, record->video_zoom);
387                         }
388                         result = 1;
389                         break;
390                 case RIGHT:
391                         if(!ctrl_down()) 
392                         { 
393                                 record->record_gui->set_translation(++(record->video_x), record->video_y, record->video_zoom);
394                         }
395                         else
396                         {
397                                 record->video_zoom += 0.1;
398                                 record->record_gui->set_translation(record->video_x, record->video_y, record->video_zoom);
399                         }
400                         result = 1;
401                         break;
402                 case UP:
403                         if(!ctrl_down()) 
404                         { 
405                                 record->record_gui->set_translation(record->video_x, --(record->video_y), record->video_zoom);
406                         }
407                         else
408                         {
409                                 record->video_zoom -= 0.1;
410                                 record->record_gui->set_translation(record->video_x, record->video_y, record->video_zoom);
411                         }
412                         result = 1;
413                         break;
414                 case DOWN:
415                         if(!ctrl_down()) 
416                         { 
417                                 record->record_gui->set_translation(record->video_x, ++(record->video_y), record->video_zoom);
418                         }
419                         else
420                         {
421                                 record->video_zoom += 0.1;
422                                 record->record_gui->set_translation(record->video_x, record->video_y, record->video_zoom);
423                         }
424                         result = 1;
425                         break;
426                 case 'w':
427                         close_event();
428                         break;
429                 default:
430                         if(avc1394_transport)
431                                 result = avc1394_transport->keypress_event(get_keypress());
432                         break;
433         }
434         return result;
438 int RecordMonitorGUI::translation_event()
440 //printf("MWindowGUI::translation_event 1 %d %d\n", get_x(), get_y());
441         mwindow->session->rmonitor_x = get_x();
442         mwindow->session->rmonitor_y = get_y();
443         return 0;
446 int RecordMonitorGUI::resize_event(int w, int h)
448         int do_channel = (mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX ||
449                         mwindow->edl->session->vconfig_in->driver == CAPTURE_BUZ ||
450                         mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2 ||
451                         mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2JPEG);
452         int do_interlace = (mwindow->edl->session->vconfig_in->driver == CAPTURE_BUZ ||
453                 mwindow->edl->session->vconfig_in->driver == VIDEO4LINUX2JPEG);
454         int do_avc = avc1394_transport ? 1 : 0;
456         mwindow->session->rmonitor_x = get_x();
457         mwindow->session->rmonitor_y = get_y();
458         mwindow->session->rmonitor_w = w;
459         mwindow->session->rmonitor_h = h;
461         mwindow->theme->get_rmonitor_sizes(record->default_asset->audio_data, 
462                 record->default_asset->video_data,
463                 do_channel,
464                 do_interlace,
465                 do_avc);
466         mwindow->theme->draw_rmonitor_bg(this);
467         flash();
470 //      record_transport->reposition_window(mwindow->theme->rmonitor_tx_x,
471 //              mwindow->theme->rmonitor_tx_y);
472         if(avc1394_transport)
473         {
474                 avc1394_transport->reposition_window(mwindow->theme->rmonitor_tx_x,
475                         mwindow->theme->rmonitor_tx_y);
476         }
477         
478         if(channel_picker) channel_picker->reposition();
479         if(reverse_interlace) reverse_interlace->reposition_window(reverse_interlace->get_x(),
480                 reverse_interlace->get_y());
481         if(record->default_asset->video_data)
482         {
483                 canvas->reposition_window(0,
484                         mwindow->theme->rmonitor_canvas_x, 
485                         mwindow->theme->rmonitor_canvas_y, 
486                         mwindow->theme->rmonitor_canvas_w, 
487                         mwindow->theme->rmonitor_canvas_h);
488         }
490         if(record->default_asset->audio_data)
491         {
492                 meters->reposition_window(mwindow->theme->rmonitor_meter_x, 
493                         mwindow->theme->rmonitor_meter_y, 
494                         mwindow->theme->rmonitor_meter_h);
495         }
497         set_title();
498         BC_WindowBase::resize_event(w, h);
499         flash();
500         flush();
501         return 1;
504 int RecordMonitorGUI::set_title()
506 return 0;
507         char string[1024];
508         int scale;
510         scale = (int)(thread->get_scale(thread->record->video_window_w) * 100 + 0.5);
512         sprintf(string, PROGRAM_NAME ": Video in %d%%", scale);
513         BC_Window::set_title(string);
514         return 0;
517 int RecordMonitorGUI::close_event()
519         thread->record->monitor_video = 0;
520         thread->record->monitor_audio = 0;
521         thread->record->video_window_open = 0;
522         if(record->record_gui->monitor_video) record->record_gui->monitor_video->update(0);
523         if(record->record_gui->monitor_audio) record->record_gui->monitor_audio->update(0);
524         hide_window();
525         record->record_gui->flush();
526         return 0;
529 int RecordMonitorGUI::create_bitmap()
531         if(bitmap && 
532                 (bitmap->get_w() != get_w() || 
533                         bitmap->get_h() != thread->get_canvas_height()))
534         {
535                 delete bitmap;
536                 bitmap = 0;
537         }
539         if(!bitmap)
540         {
541 //              bitmap = canvas->new_bitmap(get_w(), thread->get_canvas_height());
542         }
543         return 0;
546 ReverseInterlace::ReverseInterlace(Record *record, int x, int y)
547  : BC_CheckBox(x, y, record->reverse_interlace, _("Swap fields"))
549         this->record = record;
552 ReverseInterlace::~ReverseInterlace()
556 int ReverseInterlace::handle_event()
558         record->reverse_interlace = get_value();
559         return 0;
562 RecordMonitorCanvas::RecordMonitorCanvas(MWindow *mwindow, 
563         RecordMonitorGUI *window, 
564         Record *record, 
565         int x, 
566         int y, 
567         int w, 
568         int h)
569  : Canvas(window, 
570         x, 
571         y, 
572         w, 
573         h, 
574         record->default_asset->width,
575         record->default_asset->height,
576         0,
577         0,
578         1)
580         this->window = window;
581         this->mwindow = mwindow;
582         this->record = record;
583 //printf("RecordMonitorCanvas::RecordMonitorCanvas 1 %d\n", mwindow->edl->session->vconfig_in->driver);
584 //printf("RecordMonitorCanvas::RecordMonitorCanvas 2\n");
587 RecordMonitorCanvas::~RecordMonitorCanvas()
591 int RecordMonitorCanvas::get_output_w()
593         return record->default_asset->width;
596 int RecordMonitorCanvas::get_output_h()
598         return record->default_asset->height;
602 int RecordMonitorCanvas::button_press_event()
604         if(Canvas::button_press_event()) return 1;
605         
606         if(mwindow->edl->session->vconfig_in->driver == SCREENCAPTURE)
607         {
608                 window->current_operation = MONITOR_TRANSLATE;
609                 window->translate_x_origin = record->video_x;
610                 window->translate_y_origin = record->video_y;
611                 window->cursor_x_origin = get_cursor_x();
612                 window->cursor_y_origin = get_cursor_y();
613         }
615         return 0;
618 void RecordMonitorCanvas::zoom_resize_window(float percentage)
620         int canvas_w, canvas_h;
621         calculate_sizes(mwindow->edl->get_aspect_ratio(), 
622                 record->default_asset->width, 
623                 record->default_asset->height, 
624                 percentage,
625                 canvas_w,
626                 canvas_h);
627         int new_w, new_h;
628         new_w = canvas_w + (window->get_w() - mwindow->theme->rmonitor_canvas_w);
629         new_h = canvas_h + (window->get_h() - mwindow->theme->rmonitor_canvas_h);
630         window->resize_window(new_w, new_h);
631         window->resize_event(new_w, new_h);
634 int RecordMonitorCanvas::button_release_event()
636         window->current_operation = MONITOR_NONE;
637         return 0;
640 int RecordMonitorCanvas::cursor_motion_event()
642         if(window->current_operation == MONITOR_TRANSLATE)
643         {
644                 record->set_translation(
645                         get_cursor_x() - window->cursor_x_origin + window->translate_x_origin,
646                         get_cursor_y() - window->cursor_y_origin + window->translate_y_origin);
647         }
649         return 0;
652 int RecordMonitorCanvas::cursor_enter_event()
654         if(mwindow->edl->session->vconfig_in->driver == SCREENCAPTURE)
655                 set_cursor(MOVE_CURSOR);
656         return 0;
659 void RecordMonitorCanvas::reset_translation()
661         record->set_translation(0, 0);
664 int RecordMonitorCanvas::keypress_event()
666         int result = 0;
667         switch(canvas->get_keypress())
668         {
669                 case LEFT:
670                         record->set_translation(--record->video_x, record->video_y);
671                         break;
672                 case RIGHT:
673                         record->set_translation(++record->video_x, record->video_y);
674                         break;
675                 case UP:
676                         record->set_translation(record->video_x, --record->video_y);
677                         break;
678                 case DOWN:
679                         record->set_translation(record->video_x, ++record->video_y);
680                         break;
681         }
682         return result;
686 RecordMonitorFullsize::RecordMonitorFullsize(MWindow *mwindow, 
687         RecordMonitorGUI *window)
688  : BC_MenuItem(_("Zoom 100%"))
690         this->mwindow = mwindow;
691         this->window = window;
693 int RecordMonitorFullsize::handle_event()
695         return 1;
705 // ================================== slippery playback ============================
708 RecordMonitorThread::RecordMonitorThread(MWindow *mwindow, 
709         Record *record, 
710         RecordMonitor *record_monitor)
711  : Thread(1, 0, 0)
713         this->mwindow = mwindow;
714         this->record_monitor = record_monitor;
715         this->record = record;
716         reset_parameters();
717         output_lock = new Condition(1, "RecordMonitor::output_lock");
718         input_lock = new Condition(1, "RecordMonitor::input_lock");
722 void RecordMonitorThread::reset_parameters()
724         input_frame = 0;
725         output_frame[0] = 0;
726         shared_data = 0;
727         jpeg_engine = 0;
728         dv_engine = 0;
729         ready = 0;
733 RecordMonitorThread::~RecordMonitorThread()
735         if(input_frame && !shared_data) delete input_frame;
736         delete output_lock;
737         delete input_lock;
740 void RecordMonitorThread::init_output_format()
742         long offset;
744 //printf("RecordMonitorThread::init_output_format 1\n");
745         switch(mwindow->edl->session->vconfig_in->driver)
746         {
747                 case SCREENCAPTURE:
748                         output_colormodel = record->vdevice->get_best_colormodel(record->default_asset);
749                         break;
750         
751         
752                 case CAPTURE_BUZ:
753                 case VIDEO4LINUX2JPEG:
754                         jpeg_engine = new RecVideoMJPGThread(record, this);
755                         jpeg_engine->start_rendering();
756                         output_colormodel = BC_YUV422P;
757                         break;
759                 case CAPTURE_FIREWIRE:
760                         dv_engine = new RecVideoDVThread(record, this);
761                         dv_engine->start_rendering();
762                         output_colormodel = BC_YUV422P;
763                         break;
765                 case VIDEO4LINUX:
766                 case VIDEO4LINUX2:
767                         output_colormodel = record->vdevice->get_best_colormodel(record->default_asset);
768 //printf("RecordMonitorThread::init_output_format 2 %d\n", output_colormodel);
769                         break;
770         }
773 int RecordMonitorThread::start_playback()
775         ready = 1;
776         done = 0;
777         output_lock->lock("RecordMonitorThread::start_playback");
778         Thread::start();
779         return 0;
782 int RecordMonitorThread::stop_playback()
784         done = 1;
785         output_lock->unlock();
786         Thread::join();
787 //printf("RecordMonitorThread::stop_playback 1\n");
789         switch(mwindow->edl->session->vconfig_in->driver)
790         {
791                 case CAPTURE_BUZ:
792                 case VIDEO4LINUX2JPEG:
793                         if(jpeg_engine) 
794                         {
795                                 jpeg_engine->stop_rendering();
796                                 delete jpeg_engine;
797                         }
798                         break;
800                 case CAPTURE_FIREWIRE:
801                         if(dv_engine)
802                         {
803                                 dv_engine->stop_rendering();
804                                 delete dv_engine;
805                         }
806                         break;
807         }
808 //printf("RecordMonitorThread::stop_playback 4\n");
810         return 0;
813 int RecordMonitorThread::write_frame(VFrame *new_frame)
815         if(ready)
816         {
817                 ready = 0;
818                 shared_data = (new_frame->get_color_model() != BC_COMPRESSED);
821 // Need to wait until after Record creates the input device before starting monitor
822 // because the input device deterimes the output format.
823 // First time
824                 if(!output_frame[0]) init_output_format();
825                 if(!shared_data)
826                 {
827                         if(!input_frame) input_frame = new VFrame;
828                         input_frame->allocate_compressed_data(new_frame->get_compressed_size());
829                         memcpy(input_frame->get_data(), 
830                                 new_frame->get_data(), 
831                                 new_frame->get_compressed_size());
832                         input_frame->set_compressed_size(new_frame->get_compressed_size());
833                         input_frame->set_field2_offset(new_frame->get_field2_offset());
834                 }
835                 else
836                 {
837                         input_lock->lock("RecordMonitorThread::write_frame");
838                         input_frame = new_frame;
839                 }
840                 output_lock->unlock();
841         }
842         return 0;
845 int RecordMonitorThread::render_jpeg()
847 //printf("RecordMonitorThread::render_jpeg 1\n");
848         jpeg_engine->render_frame(input_frame, input_frame->get_compressed_size());
849 //printf("RecordMonitorThread::render_jpeg 2\n");
850         return 0;
853 int RecordMonitorThread::render_dv()
855         dv_engine->render_frame(input_frame, input_frame->get_compressed_size());
856         return 0;
859 void RecordMonitorThread::render_uncompressed()
861 // printf("RecordMonitorThread::render_uncompressed 1 %p %p %p %p %p %p %p\n", 
862 //      output_frame[0],
863 //      output_frame[0]->get_y(), 
864 //      output_frame[0]->get_u(), 
865 //      output_frame[0]->get_v(),
866 //      input_frame->get_y(),
867 //      input_frame->get_u(),
868 //      input_frame->get_v());
870         output_frame[0]->copy_from(input_frame);
872 //printf("RecordMonitorThread::render_uncompressed 2\n");
875 void RecordMonitorThread::show_output_frame()
877         record_monitor->device->write_buffer(output_frame, record->edl);
880 void RecordMonitorThread::unlock_input()
882         if(shared_data) input_lock->unlock();
885 int RecordMonitorThread::render_frame()
887         switch(mwindow->edl->session->vconfig_in->driver)
888         {
889                 case CAPTURE_BUZ:
890                 case VIDEO4LINUX2JPEG:
891                         render_jpeg();
892                         break;
894                 case CAPTURE_FIREWIRE:
895                         render_dv();
896                         break;
898                 default:
899                         render_uncompressed();
900                         break;
901         }
903         return 0;
906 void RecordMonitorThread::new_output_frame()
908         long offset;
909 //printf("RecordMonitorThread::new_output_frame %d %p %p\n", output_colormodel, record_monitor, record_monitor->device);
910         record_monitor->device->new_output_buffers(output_frame, output_colormodel);
911 //printf("RecordMonitorThread::new_output_frame 2\n");
914 void RecordMonitorThread::run()
916 //printf("RecordMonitorThread::run 1 %d\n", getpid());
917         while(!done)
918         {
919 // Wait for next frame
920                 output_lock->lock("RecordMonitorThread::run");
921                 if(done)
922                 {
923                         unlock_input();
924                         return;
925                 }
926 //printf("RecordMonitorThread::run 1\n");
927                 new_output_frame();
928 //printf("RecordMonitorThread::run 2\n");
929                 render_frame();
930 //printf("RecordMonitorThread::run 3\n");
931                 show_output_frame();
932 //printf("RecordMonitorThread::run 4\n");
933                 unlock_input();
934 // Get next frame
935                 ready = 1;
936         }
941 RecVideoMJPGThread::RecVideoMJPGThread(Record *record, RecordMonitorThread *thread)
943         this->record = record;
944         this->thread = thread;
945         mjpeg = 0;
948 RecVideoMJPGThread::~RecVideoMJPGThread()
952 int RecVideoMJPGThread::start_rendering()
954         mjpeg = mjpeg_new(record->default_asset->width, 
955                 record->default_asset->height, 
956                 2);
957 //printf("RecVideoMJPGThread::start_rendering 1 %p\n", mjpeg);
958         return 0;
961 int RecVideoMJPGThread::stop_rendering()
963 //printf("RecVideoMJPGThread::stop_rendering 1 %p\n", mjpeg);
964         if(mjpeg) mjpeg_delete(mjpeg);
965 //printf("RecVideoMJPGThread::stop_rendering 2\n");
966         return 0;
969 int RecVideoMJPGThread::render_frame(VFrame *frame, long size)
971 // printf("RecVideoMJPGThread::render_frame %d %02x%02x %02x%02x\n", 
972 // frame->get_field2_offset(), 
973 // frame->get_data()[0], 
974 // frame->get_data()[1], 
975 // frame->get_data()[frame->get_field2_offset()], 
976 // frame->get_data()[frame->get_field2_offset() + 1]);
977 //frame->set_field2_offset(0);
978         mjpeg_decompress(mjpeg, 
979                 frame->get_data(), 
980                 frame->get_compressed_size(), 
981                 frame->get_field2_offset(), 
982                 thread->output_frame[0]->get_rows(), 
983                 thread->output_frame[0]->get_y(), 
984                 thread->output_frame[0]->get_u(), 
985                 thread->output_frame[0]->get_v(),
986                 thread->output_frame[0]->get_color_model(),
987                 record->mwindow->preferences->processors);
988         return 0;
994 RecVideoDVThread::RecVideoDVThread(Record *record, RecordMonitorThread *thread)
996         this->record = record;
997         this->thread = thread;
998         dv = 0;
1001 RecVideoDVThread::~RecVideoDVThread()
1006 int RecVideoDVThread::start_rendering()
1008         dv = (void*)dv_new();
1009         return 0;
1012 int RecVideoDVThread::stop_rendering()
1014         if(dv) dv_delete(((dv_t*)dv));
1015         return 0;
1018 int RecVideoDVThread::render_frame(VFrame *frame, long size)
1020         unsigned char *yuv_planes[3];
1021         yuv_planes[0] = thread->output_frame[0]->get_y();
1022         yuv_planes[1] = thread->output_frame[0]->get_u();
1023         yuv_planes[2] = thread->output_frame[0]->get_v();
1024         dv_read_video(((dv_t*)dv), 
1025                 yuv_planes, 
1026                 frame->get_data(), 
1027                 frame->get_compressed_size(),
1028                 thread->output_frame[0]->get_color_model());
1029         return 0;