From: Good Guy Date: Thu, 17 Dec 2015 16:37:25 +0000 (-0700) Subject: add refresh rate to vicons + a bunch of bug fixes X-Git-Url: https://git.cinelerra-gg.org/git/?a=commitdiff_plain;h=9d843688067273fd869c55a418962c64814b12ae;p=goodguy%2Fhistory.git add refresh rate to vicons + a bunch of bug fixes --- diff --git a/cinelerra-5.0/cinelerra/awindowgui.C b/cinelerra-5.0/cinelerra/awindowgui.C index f340bb0e..3e351957 100644 --- a/cinelerra-5.0/cinelerra/awindowgui.C +++ b/cinelerra-5.0/cinelerra/awindowgui.C @@ -91,7 +91,8 @@ VFrame *AssetVIcon::frame() if( !temp ) temp = new VFrame(asset->width, asset->height, BC_RGB888); file->set_layer(0); - file->set_video_position(images.size(),0); + int64_t pos = seq_no / picon->gui->vicon_thread->refresh_rate * frame_rate; + file->set_video_position(pos,0); int ww = picon->gui->vicon_thread->view_w; int hh = picon->gui->vicon_thread->view_h; while( seq_no >= images.size() ) { @@ -103,11 +104,10 @@ VFrame *AssetVIcon::frame() return *images[seq_no]; } -int64_t AssetVIcon::next_frame(int n) +int64_t AssetVIcon::set_seq_no(int64_t no) { - age += n * period; - if( (seq_no+=n) >= length ) seq_no = 0; - return seq_no; + if( no >= length ) no = 0; + return seq_no = no; } int AssetVIcon::get_vx() diff --git a/cinelerra-5.0/cinelerra/awindowgui.h b/cinelerra-5.0/cinelerra/awindowgui.h index f80cbca1..d1c2455b 100644 --- a/cinelerra-5.0/cinelerra/awindowgui.h +++ b/cinelerra-5.0/cinelerra/awindowgui.h @@ -99,7 +99,7 @@ public: int64_t length; VFrame *frame(); - int64_t next_frame(int n); + int64_t set_seq_no(int64_t no); int get_vx(); int get_vy(); diff --git a/cinelerra-5.0/cinelerra/dbwindow.C b/cinelerra-5.0/cinelerra/dbwindow.C index 6d479b37..2a6395cf 100644 --- a/cinelerra-5.0/cinelerra/dbwindow.C +++ b/cinelerra-5.0/cinelerra/dbwindow.C @@ -338,7 +338,7 @@ move_column_event() } DbWindowVIcon::DbWindowVIcon() - : VIcon(SWIDTH, SHEIGHT, 24) + : VIcon(SWIDTH, SHEIGHT, VICON_RATE) { lbox = 0; item = 0; @@ -392,11 +392,10 @@ VFrame *DbWindowVIcon::frame() return *images[seq_no]; } -int64_t DbWindowVIcon::next_frame(int n) +int64_t DbWindowVIcon::set_seq_no(int64_t no) { - age += n * period; - if( (seq_no+=n) >= clip_size ) seq_no = 0; - return seq_no; + if( no >= clip_size ) no = 0; + return seq_no = no; } @@ -449,7 +448,7 @@ update_image(DbWindowGUI *gui, int clip_id) this->prefix_size = mdb->clip_prefix_size(); this->suffix_offset = mdb->clip_frames() - clip_size; double framerate = mdb->clip_framerate(); - this->period = 1000. / (framerate > 0 ? framerate : 24); + this->frame_rate = framerate > 0 ? framerate : VICON_RATE; gui->vicon_thread->add_vicon(this); } mdb->detach(); diff --git a/cinelerra-5.0/cinelerra/dbwindow.h b/cinelerra-5.0/cinelerra/dbwindow.h index 4fcd2f0a..f36644f5 100644 --- a/cinelerra-5.0/cinelerra/dbwindow.h +++ b/cinelerra-5.0/cinelerra/dbwindow.h @@ -249,7 +249,7 @@ public: int prefix_size, suffix_offset; VFrame *frame(); - int64_t next_frame(int n); + int64_t set_seq_no(int64_t no); void load_frames(DbWindow::MDb *mdb); void read_frames(DbWindow::MDb *mdb); diff --git a/cinelerra-5.0/cinelerra/ffmpeg.C b/cinelerra-5.0/cinelerra/ffmpeg.C index a6bbabc1..4b585eaa 100644 --- a/cinelerra-5.0/cinelerra/ffmpeg.C +++ b/cinelerra-5.0/cinelerra/ffmpeg.C @@ -1887,7 +1887,6 @@ int FFMPEG::audio_seek(int stream, int64_t pos) { int aidx = astrm_index[stream].st_idx; FFAudioStream *aud = ffaudio[aidx]; - pos = pos * aud->sample_rate / file_base->asset->sample_rate + 0.5; aud->audio_seek(pos); return 0; } @@ -1896,7 +1895,6 @@ int FFMPEG::video_seek(int stream, int64_t pos) { int vidx = vstrm_index[stream].st_idx; FFVideoStream *vid = ffvideo[vidx]; - pos = pos * vid->frame_rate / file_base->asset->frame_rate + 0.5; vid->video_seek(pos); return 0; } @@ -1907,7 +1905,6 @@ int FFMPEG::decode(int chn, int64_t pos, double *samples, int len) if( !has_audio || chn >= astrm_index.size() ) return -1; int aidx = astrm_index[chn].st_idx; FFAudioStream *aud = ffaudio[aidx]; - pos = pos * aud->sample_rate / file_base->asset->sample_rate + 0.5; if( aud->load(pos, len) < len ) return -1; int ch = astrm_index[chn].st_ch; int ret = aud->read(samples,len,ch); @@ -1919,7 +1916,6 @@ int FFMPEG::decode(int layer, int64_t pos, VFrame *vframe) if( !has_video || layer >= vstrm_index.size() ) return -1; int vidx = vstrm_index[layer].st_idx; FFVideoStream *vid = ffvideo[vidx]; - pos = pos * vid->frame_rate / file_base->asset->frame_rate + 0.5; return vid->load(vframe, pos); } diff --git a/cinelerra-5.0/cinelerra/fileffmpeg.C b/cinelerra-5.0/cinelerra/fileffmpeg.C index 66fda8c1..b5b459ef 100644 --- a/cinelerra-5.0/cinelerra/fileffmpeg.C +++ b/cinelerra-5.0/cinelerra/fileffmpeg.C @@ -303,7 +303,7 @@ int FileFFMPEG::read_frame(VFrame *frame) int64_t pos = file->current_frame; int ret = ff->decode(layer, pos, frame); frame->set_status(ret); - if( ret > 0 ) return 0; + if( ret >= 0 ) return 0; frame->clear_frame(); return -1; } diff --git a/cinelerra-5.0/cinelerra/resourcethread.C b/cinelerra-5.0/cinelerra/resourcethread.C index ba6729c3..c14bf27b 100644 --- a/cinelerra-5.0/cinelerra/resourcethread.C +++ b/cinelerra-5.0/cinelerra/resourcethread.C @@ -195,6 +195,8 @@ ResourceThread::~ResourceThread() delete temp_buffer[i]; delete timer; delete render_engine; + if( audio_asset ) audio_asset->remove_user(); + if( video_asset ) video_asset->remove_user(); } void ResourceThread::create_objects() @@ -377,12 +379,14 @@ File *ResourceThread::get_audio_source(Asset *asset) { mwindow->audio_cache->check_in(audio_asset); audio_source = 0; + audio_asset->remove_user(); audio_asset = 0; } if( !audio_asset && asset ) { audio_asset = asset; + audio_asset->add_user(); audio_source = mwindow->audio_cache->check_out(asset, mwindow->edl); } return audio_source; @@ -395,12 +399,14 @@ File *ResourceThread::get_video_source(Asset *asset) { mwindow->video_cache->check_in(video_asset); video_source = 0; + video_asset->remove_user(); video_asset = 0; } if( !video_asset && asset ) { video_asset = asset; + video_asset->add_user(); video_source = mwindow->video_cache->check_out(asset, mwindow->edl); } return video_source; diff --git a/cinelerra-5.0/cinelerra/vwindowgui.C b/cinelerra-5.0/cinelerra/vwindowgui.C index 7fa2f4be..3c9ad5e6 100644 --- a/cinelerra-5.0/cinelerra/vwindowgui.C +++ b/cinelerra-5.0/cinelerra/vwindowgui.C @@ -806,6 +806,9 @@ void VWindowCanvas::zoom_resize_window(float percentage) void VWindowCanvas::close_source() { + gui->unlock_window(); + gui->vwindow->playback_engine->interrupt_playback(1); + gui->lock_window("VWindowCanvas::close_source"); gui->vwindow->delete_source(1, 1); } diff --git a/cinelerra-5.0/global_config b/cinelerra-5.0/global_config index 4fbe48b3..623a0e33 100644 --- a/cinelerra-5.0/global_config +++ b/cinelerra-5.0/global_config @@ -5,7 +5,7 @@ HAVE_XFT := y HAVE_ESOUND := y HAVE_FIREWIRE := y HAVE_OSS := y -STATIC_LIBRARIES := n +STATIC_LIBRARIES := y OBJDIR := $(shell uname --machine) @@ -105,4 +105,3 @@ LOOP_BEGIN = @ for i in $(DIRS) ; \ LOOP_END = done -EXTRA_LIBS += -lnuma diff --git a/cinelerra-5.0/guicast/vicon.C b/cinelerra-5.0/guicast/vicon.C index 269c96a2..428ed4c7 100644 --- a/cinelerra-5.0/guicast/vicon.C +++ b/cinelerra-5.0/guicast/vicon.C @@ -12,9 +12,10 @@ VIcon(int vw, int vh, double rate) { this->vw = vw; this->vh = vh; - this->period = 1000./rate; + this->frame_rate = rate; + this->cycle_start = 0; this->age = 0; - this->seq_no = 0; + this->seq_no = 0; this->in_use = 1; } @@ -73,6 +74,7 @@ VIconThread(BC_WindowBase *wdw, int vw, int vh) this->viewing = 0; draw_lock = new Condition(0, "VIconThread::draw_lock", 1); timer = new Timer(); + this->refresh_rate = VICON_RATE; done = 0; interrupted = 1; } @@ -175,14 +177,14 @@ ViewPopup *VIconThread::new_view_window(VFrame *frame) void VIconThread:: reset_images() { - for( int i=t_heap.size(); --i>=0; ) t_heap[i]->age = 0; + for( int i=t_heap.size(); --i>=0; ) t_heap[i]->reset(); timer->update(); img_dirty = win_dirty = 0; } -void VIconThread::add_vicon(VIcon *vip, double age) +void VIconThread::add_vicon(VIcon *vip) { - vip->age = age; + double age = vip->age; int i = t_heap.size(); t_heap.append(vip); for( int k; i>0 && ageage; i=k ) t_heap[i] = t_heap[k]; @@ -272,7 +274,7 @@ run() if( !next ) break; int64_t now = timer->get_difference(); if( next == first || (draw_flash && now >= draw_flash) ) { - add_vicon(next, next->age); + add_vicon(next); if( !draw_flash ) draw_flash = now + 100; else if( now >= draw_flash ) draw_flash = now + 1; wdw->unlock_window(); @@ -295,12 +297,14 @@ run() if( draw(next) && !draw_flash ) draw_flash = next->age; now = timer->get_difference(); - int64_t late = now - next->age; - int count = late / next->period; - int nfrms = count > 0 ? count : 1; - if( !next->next_frame(nfrms) ) + if( !next->seq_no ) next->cycle_start = now; + int64_t ref_no = (now - next->cycle_start) / 1000 * refresh_rate; + int count = ref_no - next->seq_no; + if( count < 1 ) count = 1; + next->age += count * 1000 / refresh_rate; + if( !next->set_seq_no(next->seq_no + count) ) next->age = now + 1000; - add_vicon(next, next->age); + add_vicon(next); } if( viewing != vicon ) update_view(); diff --git a/cinelerra-5.0/guicast/vicon.h b/cinelerra-5.0/guicast/vicon.h index da194c41..6ae0119e 100644 --- a/cinelerra-5.0/guicast/vicon.h +++ b/cinelerra-5.0/guicast/vicon.h @@ -37,22 +37,17 @@ public: class VIcon { public: - int vw, vh, vcmdl, in_use; + int vw, vh, in_use; ArrayList images; int64_t seq_no; - double age, period; + double cycle_start, age, frame_rate; - double frame_rate() { return 1000/period; } - void frame_rate(double r) { period = 1000/r; } int64_t vframes() { return images.size(); } + void reset() { seq_no = 0; cycle_start = 0; age = 0; } void clear_images() { images.remove_all_objects(); } + virtual int64_t set_seq_no(int64_t no) { return seq_no = no; } virtual VFrame *frame() { return *images[seq_no]; } - virtual int64_t next_frame(int n) { - age += n * period; - if( (seq_no+=n) >= images.size() ) seq_no = 0; - return seq_no; - } virtual int get_vx() { return 0; } virtual int get_vy() { return 0; } @@ -60,7 +55,7 @@ public: void draw_vframe(BC_WindowBase *wdw, int x, int y); void dump(const char *dir); - VIcon(int vw=VICON_WIDTH, int vh=VICON_HEIGHT, double rate=24); + VIcon(int vw=VICON_WIDTH, int vh=VICON_HEIGHT, double rate=VICON_RATE); virtual ~VIcon(); }; @@ -75,10 +70,11 @@ public: VIcon *viewing, *vicon; int view_w, view_h; int img_dirty, win_dirty; + double refresh_rate; ArrayListt_heap; VIcon *low_vicon(); - void add_vicon(VIcon *vicon, double age=0); + void add_vicon(VIcon *vicon); int del_vicon(VIcon *&vicon); void run(); void flash(); diff --git a/cinelerra-5.0/guicast/vicon.inc b/cinelerra-5.0/guicast/vicon.inc index 77b9ca87..f105e480 100644 --- a/cinelerra-5.0/guicast/vicon.inc +++ b/cinelerra-5.0/guicast/vicon.inc @@ -3,6 +3,7 @@ #define VICON_WIDTH 80 #define VICON_HEIGHT 45 +#define VICON_RATE 24 class ViewWindow; class VIconThread;