From b55798fc64eee00c6fab3b4763e791befb7275f9 Mon Sep 17 00:00:00 2001 From: Good Guy Date: Sun, 25 Feb 2018 17:31:30 -0700 Subject: [PATCH] clip picons as clip_icon.png, vwindow hang, fix for drop target test --- cinelerra-5.1/cinelerra/awindowgui.C | 148 ++++++++++++++++++++++++- cinelerra-5.1/cinelerra/awindowgui.h | 7 ++ cinelerra-5.1/cinelerra/clippopup.C | 4 + cinelerra-5.1/cinelerra/localsession.C | 16 +++ cinelerra-5.1/cinelerra/localsession.h | 2 + cinelerra-5.1/cinelerra/mwindowedit.C | 11 +- cinelerra-5.1/cinelerra/vwindow.C | 3 +- cinelerra-5.1/guicast/bcwindowbase.C | 4 +- 8 files changed, 185 insertions(+), 10 deletions(-) diff --git a/cinelerra-5.1/cinelerra/awindowgui.C b/cinelerra-5.1/cinelerra/awindowgui.C index fc087f56..094ef19b 100644 --- a/cinelerra-5.1/cinelerra/awindowgui.C +++ b/cinelerra-5.1/cinelerra/awindowgui.C @@ -19,6 +19,7 @@ * */ +#include "arender.h" #include "asset.h" #include "assetedit.h" #include "assetpopup.h" @@ -55,10 +56,14 @@ #include "mwindow.h" #include "newfolder.h" #include "preferences.h" +#include "renderengine.h" #include "samples.h" #include "theme.h" +#include "tracks.h" +#include "transportque.h" #include "vframe.h" #include "vicon.h" +#include "vrender.h" #include "vwindowgui.h" #include "vwindow.h" @@ -416,6 +421,33 @@ void AssetPicon::reset() persistent = 0; } +void AssetPicon::open_render_engine(EDL *edl, int is_audio) +{ + TransportCommand command; + command.command = is_audio ? NORMAL_FWD : CURRENT_FRAME; + command.get_edl()->copy_all(edl); + command.change_type = CHANGE_ALL; + command.realtime = 0; + render_engine = new RenderEngine(0, mwindow->preferences, 0, 0); + render_engine->set_vcache(mwindow->video_cache); + render_engine->set_acache(mwindow->audio_cache); + render_engine->arm_command(&command); +} +void AssetPicon::close_render_engine() +{ + delete render_engine; render_engine = 0; +} +void AssetPicon::render_video(int64_t pos, VFrame *vfrm) +{ + if( !render_engine || !render_engine->vrender ) return; + render_engine->vrender->process_buffer(vfrm, pos, 0); +} +void AssetPicon::render_audio(int64_t pos, Samples **samples, int len) +{ + if( !render_engine || !render_engine->arender ) return; + render_engine->arender->process_buffer(samples, len, pos); +} + void AssetPicon::create_objects() { FileSystem fs; @@ -428,6 +460,10 @@ void AssetPicon::create_objects() fs.extract_name(name, indexable->path); set_text(name); } + else if( edl ) { + set_text(strcpy(name, edl->local_session->clip_title)); + set_text(name); + } if( indexable && indexable->is_asset ) { Asset *asset = (Asset*)indexable; @@ -575,9 +611,115 @@ void AssetPicon::create_objects() } else if( edl ) { - set_text(strcpy(name, edl->local_session->clip_title)); - icon = gui->clip_icon; - icon_vframe = gui->clip_vframe; + if( edl->tracks->playable_video_tracks() ) { + if( mwindow->preferences->use_thumbnails ) { + gui->unlock_window(); + char clip_icon_path[BCTEXTLEN]; + char *clip_icon = edl->local_session->clip_icon; + if( clip_icon[0] ) { + snprintf(clip_icon_path, sizeof(clip_icon_path), + "%s/%s", File::get_config_path(), clip_icon); + icon_vframe = VFramePng::vframe_png(clip_icon_path); + } + if( !icon_vframe ) { + int edl_h = edl->get_h(), edl_w = edl->get_w(); + int height = edl_h > 0 ? edl_h : 1; + int width = edl_w > 0 ? edl_w : 1; + pixmap_w = pixmap_h * width / height; + + if( gui->temp_picon && + (gui->temp_picon->get_w() != width || + gui->temp_picon->get_h() != height) ) { + delete gui->temp_picon; gui->temp_picon = 0; + } + + if( !gui->temp_picon ) { + gui->temp_picon = new VFrame(0, -1, + width, height, BC_RGB888, -1); + } + char string[BCTEXTLEN]; + sprintf(string, _("Rendering %s"), name); + mwindow->gui->lock_window("AssetPicon::create_objects"); + mwindow->gui->show_message(string); + mwindow->gui->unlock_window(); + open_render_engine(edl, 0); + render_video(0, gui->temp_picon); + close_render_engine(); + gui->lock_window("AssetPicon::create_objects 0"); + icon_vframe = new VFrame(0, + -1, pixmap_w, pixmap_h, BC_RGB888, -1); + icon_vframe->transfer_from(gui->temp_picon); + if( clip_icon[0] ) icon_vframe->write_png(clip_icon_path); + } + else { + pixmap_w = icon_vframe->get_w(); + pixmap_h = icon_vframe->get_h(); + } + icon = new BC_Pixmap(gui, pixmap_w, pixmap_h); + icon->draw_vframe(icon_vframe, + 0, 0, pixmap_w, pixmap_h, 0, 0); + } + else { + icon = gui->clip_icon; + icon_vframe = gui->clip_vframe; + } + } + else + if( edl->tracks->playable_audio_tracks() ) { + if( mwindow->preferences->use_thumbnails ) { + gui->unlock_window(); + char clip_icon_path[BCTEXTLEN]; + char *clip_icon = edl->local_session->clip_icon; + if( clip_icon[0] ) { + snprintf(clip_icon_path, sizeof(clip_icon_path), + "%s/%s", File::get_config_path(), clip_icon); + icon_vframe = VFramePng::vframe_png(clip_icon_path); + } + if( !icon_vframe ) { + pixmap_w = pixmap_h * 16/9; + icon_vframe = new VFrame(0, + -1, pixmap_w, pixmap_h, BC_RGB888, -1); + char string[BCTEXTLEN]; + sprintf(string, _("Rendering %s"), name); + mwindow->gui->lock_window("AssetPicon::create_objects 3"); + mwindow->gui->show_message(string); + mwindow->gui->unlock_window(); + int sample_rate = edl->get_sample_rate(); + int channels = edl->get_audio_channels(); + if( channels > 2 ) channels = 2; + int64_t audio_samples = edl->get_audio_samples(); + double duration = (double)audio_samples / sample_rate; + draw_hue_bar(icon_vframe, duration); + Samples *samples[MAX_CHANNELS]; + int bfrsz = sample_rate; + for( int i=0; ilock_window("AssetPicon::create_objects 4"); + static int line_colors[2] = { GREEN, YELLOW }; + static int base_colors[2] = { RED, PINK }; + for( int i=channels; --i>=0; ) { + draw_wave(icon_vframe, samples[i]->get_data(), bfrsz, + base_colors[i], line_colors[i]); + } + for( int i=0; iwrite_png(clip_icon_path); + } + else { + pixmap_w = icon_vframe->get_w(); + pixmap_h = icon_vframe->get_h(); + } + icon = new BC_Pixmap(gui, pixmap_w, pixmap_h); + icon->draw_vframe(icon_vframe, + 0, 0, pixmap_w, pixmap_h, 0, 0); + } + else { + icon = gui->clip_icon; + icon_vframe = gui->clip_vframe; + } + } } else if( plugin ) { diff --git a/cinelerra-5.1/cinelerra/awindowgui.h b/cinelerra-5.1/cinelerra/awindowgui.h index 703c9764..04d83460 100644 --- a/cinelerra-5.1/cinelerra/awindowgui.h +++ b/cinelerra-5.1/cinelerra/awindowgui.h @@ -42,6 +42,8 @@ #include "mwindow.inc" #include "newfolder.inc" #include "pluginserver.inc" +#include "renderengine.inc" +#include "samples.inc" #include "vicon.h" class AssetPicon : public BC_ListBoxItem @@ -59,6 +61,10 @@ public: static void draw_hue_bar(VFrame *frame, double t); static void draw_wave(VFrame *frame, double *dp, int len, int base_color, int line_color); + void open_render_engine(EDL *edl, int is_audio); + void close_render_engine(); + void render_video(int64_t pos, VFrame *vfrm); + void render_audio(int64_t pos, Samples **samples, int len); MWindow *mwindow; AWindowGUI *gui; @@ -81,6 +87,7 @@ public: PluginServer *plugin; Label *label; VIcon *vicon; + RenderEngine *render_engine; }; typedef int16_t vicon_audio_t; diff --git a/cinelerra-5.1/cinelerra/clippopup.C b/cinelerra-5.1/cinelerra/clippopup.C index ac432d33..a364947a 100644 --- a/cinelerra-5.1/cinelerra/clippopup.C +++ b/cinelerra-5.1/cinelerra/clippopup.C @@ -449,6 +449,10 @@ int ClipPopupNest::handle_event() dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday, dtm.tm_hour, dtm.tm_min, dtm.tm_sec); clip_edl->set_path(path); + sprintf(new_clip->local_session->clip_icon, + "clip_%02d%02d%02d-%02d%02d%02d.png", + dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday, + dtm.tm_hour, dtm.tm_min, dtm.tm_sec); new_clip->set_path(path); new_clip->to_nested(clip_edl); int idx = edl->clips.number_of(clip); diff --git a/cinelerra-5.1/cinelerra/localsession.C b/cinelerra-5.1/cinelerra/localsession.C index 771f7f5e..19f8d62a 100644 --- a/cinelerra-5.1/cinelerra/localsession.C +++ b/cinelerra-5.1/cinelerra/localsession.C @@ -63,6 +63,7 @@ LocalSession::LocalSession(EDL *edl) awindow_folder = AW_CLIP_FOLDER; sprintf(clip_title, _("Program")); strcpy(clip_notes, _("Hello world")); + strcpy(clip_icon, ""); clipboard_length = 0; loop_playback = 0; loop_start = loop_end = 0; @@ -117,6 +118,7 @@ void LocalSession::copy_from(LocalSession *that) { strcpy(clip_title, that->clip_title); strcpy(clip_notes, that->clip_notes); + strcpy(clip_icon, that->clip_icon); awindow_folder = that->awindow_folder; in_point = that->in_point; loop_playback = that->loop_playback; @@ -167,6 +169,7 @@ void LocalSession::save_xml(FileXML *file, double start) file->tag.set_property("SELECTION_END", selectionend - start); file->tag.set_property("CLIP_TITLE", clip_title); file->tag.set_property("CLIP_NOTES", clip_notes); + file->tag.set_property("CLIP_ICON", clip_icon); file->tag.set_property("AWINDOW_FOLDER", awindow_folder); file->tag.set_property("X_PANE", x_pane); file->tag.set_property("Y_PANE", y_pane); @@ -242,6 +245,19 @@ void LocalSession::load_xml(FileXML *file, unsigned long load_flags) // Overwritten by MWindow::load_filenames file->tag.get_property("CLIP_TITLE", clip_title); file->tag.get_property("CLIP_NOTES", clip_notes); + clip_icon[0] = 0; + file->tag.get_property("CLIP_ICON", clip_icon); +// kludge if possible + if( !clip_icon[0] ) { + char *cp = clip_notes; + int year, mon, mday, hour, min, sec; + while( *cp && *cp++ != ':' ); + if( *cp && sscanf(cp, "%d/%02d/%02d %02d:%02d:%02d,", + &year, &mon, &mday, &hour, &min, &sec) == 6 ) { + sprintf(clip_icon, "clip_%02d%02d%02d-%02d%02d%02d.png", + year, mon, mday, hour, min, sec); + } + } const char *folder = file->tag.get_property("FOLDER"); if( folder ) { awindow_folder = AWindowGUI::folder_number(folder); diff --git a/cinelerra-5.1/cinelerra/localsession.h b/cinelerra-5.1/cinelerra/localsession.h index 7c987937..bf1ddeeb 100644 --- a/cinelerra-5.1/cinelerra/localsession.h +++ b/cinelerra-5.1/cinelerra/localsession.h @@ -78,6 +78,8 @@ public: // Title if clip char clip_title[BCTEXTLEN]; char clip_notes[BCTEXTLEN]; + char clip_icon[BCSTRLEN]; + // Folder in parent EDL of clip int awindow_folder; diff --git a/cinelerra-5.1/cinelerra/mwindowedit.C b/cinelerra-5.1/cinelerra/mwindowedit.C index 7b06f5ef..2d417dbd 100644 --- a/cinelerra-5.1/cinelerra/mwindowedit.C +++ b/cinelerra-5.1/cinelerra/mwindowedit.C @@ -2043,7 +2043,7 @@ void MWindow::save_clip(EDL *new_edl, const char *txt) } time_t now; time(&now); - struct tm *tm = localtime(&now); + struct tm dtm; localtime_r(&now, &dtm); char *cp = new_edl->local_session->clip_notes; int n, sz = sizeof(new_edl->local_session->clip_notes)-1; if( txt && *txt ) { @@ -2052,8 +2052,8 @@ void MWindow::save_clip(EDL *new_edl, const char *txt) } n = snprintf(cp, sz, "%02d/%02d/%02d %02d:%02d:%02d, +%s\n", - tm->tm_year+1900, tm->tm_mon+1, tm->tm_mday, - tm->tm_hour, tm->tm_min, tm->tm_sec, duration); + dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday, + dtm.tm_hour, dtm.tm_min, dtm.tm_sec, duration); cp += n; sz -= n; if( path && *path ) { FileSystem fs; @@ -2063,7 +2063,10 @@ void MWindow::save_clip(EDL *new_edl, const char *txt) cp += n; sz -= n; } cp[n] = 0; - + sprintf(new_edl->local_session->clip_icon, + "clip_%02d%02d%02d-%02d%02d%02d.png", + dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday, + dtm.tm_hour, dtm.tm_min, dtm.tm_sec); edl->update_assets(new_edl); int cur_x, cur_y; gui->get_abs_cursor(cur_x, cur_y, 0); diff --git a/cinelerra-5.1/cinelerra/vwindow.C b/cinelerra-5.1/cinelerra/vwindow.C index 7a24e1bc..d1ea6b03 100644 --- a/cinelerra-5.1/cinelerra/vwindow.C +++ b/cinelerra-5.1/cinelerra/vwindow.C @@ -273,13 +273,14 @@ void VWindow::change_source(EDL *edl) if( playback_engine->is_playing_back ) stop_playback(1); - gui->lock_window("VWindow::change_source 3"); //printf("VWindow::change_source %d %p\n", __LINE__, edl); // EDLs are identical // if(edl && mwindow->edl->vwindow_edl && // edl->id == mwindow->edl->vwindow_edl->id) return; if(edl && get_edl() && edl->id == get_edl()->id) return; + gui->lock_window("VWindow::change_source 3"); + delete_source(1, 0); if(edl) diff --git a/cinelerra-5.1/guicast/bcwindowbase.C b/cinelerra-5.1/guicast/bcwindowbase.C index 6f45933f..2ab508f2 100644 --- a/cinelerra-5.1/guicast/bcwindowbase.C +++ b/cinelerra-5.1/guicast/bcwindowbase.C @@ -3848,8 +3848,8 @@ int BC_WindowBase::get_cursor_over_window() int ret = XQueryPointer(display, win, &root_return, &child_return, &abs_x, &abs_y, &win_x, &win_y, &temp_mask); - if( ret && win != root_return && child_return != None ) - ret = match_window(child_return); + if( ret && child_return == None && win != root_return ) ret = 0; + if( ret && child_return != None ) ret = match_window(child_return); return ret; } -- 2.26.2