From 84ca3b1f82b4e6f530dcea90fcd1260e0aad33bb Mon Sep 17 00:00:00 2001 From: brunoherbelin Date: Sat, 23 May 2020 14:46:01 +0200 Subject: [PATCH] Cleanup creation of sources --- ImGuiVisitor.cpp | 2 +- Mixer.cpp | 97 ++++++++++++++++++++----------------- Mixer.h | 12 ++--- RenderingManager.cpp | 2 +- Scene.h | 2 +- Session.cpp | 18 +++++-- Session.h | 4 +- SessionSource.cpp | 4 ++ UserInterfaceManager.cpp | 102 ++++++++++++++++++++++++++++----------- UserInterfaceManager.h | 4 ++ main.cpp | 49 +++++-------------- 11 files changed, 171 insertions(+), 125 deletions(-) diff --git a/ImGuiVisitor.cpp b/ImGuiVisitor.cpp index 44b91a9..731f0b6 100644 --- a/ImGuiVisitor.cpp +++ b/ImGuiVisitor.cpp @@ -300,6 +300,6 @@ void ImGuiVisitor::visit (RenderSource& s) void ImGuiVisitor::visit (CloneSource& s) { // ImGui::Button("Expand", ImVec2(IMGUI_RIGHT_ALIGN, 0)); - ImGui::Text("Clone of %s", s.origin()->name()); + ImGui::Text("Clone of %s", s.origin()->name().c_str()); } diff --git a/Mixer.cpp b/Mixer.cpp index d32e7db..8f8e691 100644 --- a/Mixer.cpp +++ b/Mixer.cpp @@ -159,12 +159,16 @@ void Mixer::update() // update session and associated sources session_->update(dt); + if (session()->failedSource() != nullptr) + deleteSource(session()->failedSource()); + // update views mixing_.update(dt); geometry_.update(dt); layer_.update(dt); // optimize the reordering in depth for views + // deep updates shall be performed only 1 frame View::need_deep_update_ = false; } @@ -175,44 +179,45 @@ void Mixer::draw() } // manangement of sources -void Mixer::createSourceFile(std::string path) +Source * Mixer::createSourceFile(std::string path) { - // sanity check - if ( !SystemToolkit::file_exists( path ) ) { - Log::Notify("File %s does not exist.", path.c_str()); - return; - } // ready to create a source Source *s = nullptr; - // test type of file by extension - std::string ext = SystemToolkit::extension_filename(path); - if ( ext == "vmx" ) - { - // create a session source - SessionSource *ss = new SessionSource(); - ss->load(path); - s = ss; - } - else { - // (try to) create media source by default - MediaSource *ms = new MediaSource; - ms->setPath(path); - s = ms; + // sanity check + if ( SystemToolkit::file_exists( path ) ) { + + // test type of file by extension + std::string ext = SystemToolkit::extension_filename(path); + if ( ext == "vmx" ) + { + // create a session source + SessionSource *ss = new SessionSource(); + ss->load(path); + s = ss; + } + else { + // (try to) create media source by default + MediaSource *ms = new MediaSource; + ms->setPath(path); + s = ms; + } + + // remember in recent media + Settings::application.recentImport.push(path); + Settings::application.recentImport.path = SystemToolkit::path_filename(path); + + // propose a new name based on uri + renameSource(s, SystemToolkit::base_filename(path)); + } + else + Log::Notify("File %s does not exist.", path.c_str()); - // remember in recent media - Settings::application.recentImport.push(path); - Settings::application.recentImport.path = SystemToolkit::path_filename(path); - - // propose a new name based on uri - renameSource(s, SystemToolkit::base_filename(path)); - - // add to mixer - insertSource(s); + return s; } -void Mixer::createSourceRender() +Source * Mixer::createSourceRender() { // ready to create a source RenderSource *s = new RenderSource; @@ -220,37 +225,41 @@ void Mixer::createSourceRender() // propose a new name based on session name renameSource(s, SystemToolkit::base_filename(session_->filename())); - // add to mixer - insertSource(s); + return s; } -void Mixer::createSourceClone(std::string namesource) +Source * Mixer::createSourceClone(std::string namesource) { + // ready to create a source + Source *s = nullptr; + SourceList::iterator origin = session_->find(namesource); if (origin != session_->end()) { // create a source - CloneSource *s = (*origin)->clone(); + s = (*origin)->clone(); // get new name renameSource(s, (*origin)->name()); - - // add to mixer - insertSource(s); } + + return s; } void Mixer::insertSource(Source *s) { - // Add source to Session and set it as current - setCurrentSource( session_->addSource(s) ); + if ( s != nullptr ) + { + // Add source to Session and set it as current + setCurrentSource( session_->addSource(s) ); - // add sources Nodes to all views - mixing_.scene.ws()->attach(s->group(View::MIXING)); - geometry_.scene.ws()->attach(s->group(View::GEOMETRY)); - layer_.scene.ws()->attach(s->group(View::LAYER)); + // add sources Nodes to all views + mixing_.scene.ws()->attach(s->group(View::MIXING)); + geometry_.scene.ws()->attach(s->group(View::GEOMETRY)); + layer_.scene.ws()->attach(s->group(View::LAYER)); - layer_.setDepth(s); + layer_.setDepth(s); + } } void Mixer::deleteCurrentSource() diff --git a/Mixer.h b/Mixer.h index 2fba41c..4b8a71e 100644 --- a/Mixer.h +++ b/Mixer.h @@ -34,13 +34,14 @@ public: void draw(); // manangement of sources - void createSourceFile(std::string path); - void createSourceRender(); - void createSourceClone(std::string namesource); + Source * createSourceFile(std::string path); + Source * createSourceClone(std::string namesource); + Source * createSourceRender(); // operations on sources - void renameSource(Source *s, const std::string &newname); + void insertSource(Source *s); void deleteSource(Source *s); + void renameSource(Source *s, const std::string &newname); // current source void setCurrentSource(std::string namesource); @@ -49,7 +50,7 @@ public: void setCurrentSource(Source *s); void unsetCurrentSource(); void deleteCurrentSource(); - Source *currentSource(); + Source * currentSource(); int indexCurrentSource(); // management of view @@ -73,7 +74,6 @@ protected: Session *back_session_; void swap(); - void insertSource(Source *s); void setCurrentSource(SourceList::iterator it); SourceList::iterator current_source_; int current_source_index_; diff --git a/RenderingManager.cpp b/RenderingManager.cpp index 5df197e..9a21225 100644 --- a/RenderingManager.cpp +++ b/RenderingManager.cpp @@ -446,7 +446,7 @@ void Rendering::FileDropped(GLFWwindow *, int path_count, const char* paths[]) if (filename.empty()) break; // try to create a source - Mixer::manager().createSourceFile( filename ); + Mixer::manager().insertSource ( Mixer::manager().createSourceFile( filename ) ); } } diff --git a/Scene.h b/Scene.h index 58c4e1c..e90f7d1 100644 --- a/Scene.h +++ b/Scene.h @@ -67,7 +67,7 @@ public: // public members, to manipulate with care bool visible_; - uint refcount_; + uint refcount_; glm::mat4 transform_; glm::vec3 scale_, rotation_, translation_; diff --git a/Session.cpp b/Session.cpp index 67a2e96..1ece749 100644 --- a/Session.cpp +++ b/Session.cpp @@ -8,7 +8,7 @@ #include "Log.h" -Session::Session() : filename_("") +Session::Session() : filename_(""), failedSource_(nullptr) { config_[View::RENDERING] = new Group; config_[View::RENDERING]->scale_ = render_.resolution(); @@ -40,12 +40,20 @@ Session::~Session() // update all sources void Session::update(float dt) { + failedSource_ = nullptr; + // pre-render of all sources for( SourceList::iterator it = sources_.begin(); it != sources_.end(); it++){ - // render the source - (*it)->render(); - // update the source - (*it)->update(dt); + + if ( (*it)->failed() ) { + failedSource_ = (*it); + } + else { + // render the source + (*it)->render(); + // update the source + (*it)->update(dt); + } } // update the scene tree diff --git a/Session.h b/Session.h index 7b1293a..df6b9c1 100644 --- a/Session.h +++ b/Session.h @@ -25,8 +25,9 @@ public: SourceList::iterator find (Node *node); uint numSource() const; - // update all sources + // update all sources and return the list of source which failed void update (float dt); + Source *failedSource() { return failedSource_; } // result of render inline FrameBuffer *frame () const { return render_.frame(); } @@ -41,6 +42,7 @@ public: protected: RenderView render_; + Source *failedSource_; SourceList sources_; std::string filename_; std::map config_; diff --git a/SessionSource.cpp b/SessionSource.cpp index d5c25b2..d9b1f27 100644 --- a/SessionSource.cpp +++ b/SessionSource.cpp @@ -136,6 +136,10 @@ void SessionSource::render() // update session session_->update(dt_); + // delete a source which failed + if (session()->failedSource() != nullptr) + session()->deleteSource(session()->failedSource()); + // render the sesion into frame buffer static glm::mat4 projection = glm::ortho(-1.f, 1.f, -1.f, 1.f, -1.f, 1.f); renderbuffer_->begin(); diff --git a/UserInterfaceManager.cpp b/UserInterfaceManager.cpp index 039bd55..b5fb5bd 100644 --- a/UserInterfaceManager.cpp +++ b/UserInterfaceManager.cpp @@ -854,6 +854,9 @@ Navigator::Navigator() pannel_width = 5.f * width; height = 100; padding_width = 100; + new_source_type_ = 0; + new_source_to_create_ = ""; + sprintf(new_source_filename_, " "); } void Navigator::toggle(int index) @@ -871,6 +874,8 @@ void Navigator::clearSelection() { for(int i=0; ibegin(); iter != Mixer::manager().session()->end(); iter++, index++) { // draw an indicator for current source @@ -946,13 +950,7 @@ void Navigator::Render() if (selected_button[index]) Mixer::manager().setCurrentSource(selected_source_index); } - // delete sources which failed - if ( (*iter)->failed() ) - source_to_delete = *iter; } - // TODO : general (mixer?) paradigm to delete failed sources (here it looks like a hack) - if (source_to_delete != nullptr) - Mixer::manager().deleteSource(source_to_delete); // the "+" icon for action of creating new source if (ImGui::Selectable( ICON_FA_PLUS, &selected_button[NAV_NEW], 0, iconsize)) @@ -1078,62 +1076,108 @@ void Navigator::RenderNewPannel() ImGui::PopFont(); ImGui::SetNextItemWidth(IMGUI_RIGHT_ALIGN); - static int new_source_type = 0; - ImGui::Combo("Origin", &new_source_type, "File\0Software\0Hardware\0"); + ImGui::Combo("Origin", &new_source_type_, "File\0Software\0Hardware\0"); // Media Source creation - if (new_source_type == 0) { + if (new_source_type_ == 0) { // helper ImGui::SetCursorPosX(pannel_width - 30 + IMGUI_RIGHT_ALIGN); ImGuiToolkit::HelpMarker("Create a source from a file:\n- Video (*.mpg, *mov, *.avi, etc.)\n- Image (*.jpg, *.png, etc.)\n- Vector graphics (*.svg)\n- vimix session (*.vmx)\n\nEquivalent to dropping the file in the workspace."); - // filename of the media to open - static char filename[2048]; - // browse for a filename if (ImGuiToolkit::ButtonIcon(2, 5)) { - std::thread (ImportFileDialogOpen, filename, Settings::application.recentImport.path).detach(); + std::thread (ImportFileDialogOpen, new_source_filename_, Settings::application.recentImport.path).detach(); } // combo of recent media filenames ImGui::SameLine(0, 10); ImGui::SetNextItemWidth(IMGUI_RIGHT_ALIGN); if (ImGui::BeginCombo("##RecentImport", "Select recent")) { - std::for_each(Settings::application.recentImport.filenames.begin(), - Settings::application.recentImport.filenames.end(), [](std::string& path) { - int right = MIN( 40, path.size()); - if (ImGui::Selectable( path.substr( path.size() - right ).c_str() )) { - sprintf(filename, "%s", path.c_str()); + for (auto path = Settings::application.recentImport.filenames.begin(); + path != Settings::application.recentImport.filenames.end(); path++ ) + { + int right = MIN( 40, path->size()); + if (ImGui::Selectable( path->substr( path->size() - right ).c_str() )) { + sprintf(new_source_filename_, "%s", path->c_str()); } - }); + } ImGui::EndCombo(); } // filename text entry - [Return] to validate ImGui::SetNextItemWidth(IMGUI_RIGHT_ALIGN); - if (ImGui::InputText("Path", filename, IM_ARRAYSIZE(filename), ImGuiInputTextFlags_EnterReturnsTrue) ) { - Mixer::manager().createSourceFile( std::string(filename) ); + Source *s = nullptr; + if (ImGui::InputText("Path", new_source_filename_, IM_ARRAYSIZE(new_source_filename_), ImGuiInputTextFlags_EnterReturnsTrue) ) { + s = Mixer::manager().createSourceFile( std::string(new_source_filename_) ); selected_button[NAV_NEW] = false; } // or press Validate button ImGui::Text(" "); if ( ImGui::Button("Create !", ImVec2(pannel_width - padding_width, 0)) ) { - Mixer::manager().createSourceFile( std::string(filename) ); + s = Mixer::manager().createSourceFile( std::string(new_source_filename_) ); selected_button[NAV_NEW] = false; } + Mixer::manager().insertSource(s); } // Render Source creator - else if (new_source_type == 1){ + else if (new_source_type_ == 1){ // helper ImGui::SetCursorPosX(pannel_width - 30 + IMGUI_RIGHT_ALIGN); ImGuiToolkit::HelpMarker("Create a source from a software algorithm or from vimix objects."); - ImGui::Text(" "); - if ( ImGui::Button("Create !", ImVec2(pannel_width - padding_width, 0)) ) { + // Selection of a source to create + static uint texture = 0; + static ImVec2 preview_size; + static ImVec2 preview_uv1, preview_uv2; + static float preview_width = ImGui::GetContentRegionAvail().x IMGUI_RIGHT_ALIGN; - Mixer::manager().createSourceClone("toto"); -// Mixer::manager().createSourceRender(); - selected_button[NAV_NEW] = false; + ImGui::SetNextItemWidth(IMGUI_RIGHT_ALIGN); + if (ImGui::BeginCombo("##Source", "Select source")) + { + if (ImGui::Selectable( "Render" )) { + new_source_to_create_ = "Render"; + texture = Mixer::manager().session()->frame()->texture(); + preview_size = ImVec2( preview_width, preview_width / Mixer::manager().session()->frame()->aspectRatio()); + preview_uv1 = ImVec2(0.f, 1.f); + preview_uv2 = ImVec2(1.f, 0.f); + } + SourceList::iterator iter; + for (iter = Mixer::manager().session()->begin(); iter != Mixer::manager().session()->end(); iter++) + { + if (ImGui::Selectable( (*iter)->name().c_str() )) { + new_source_to_create_ = (*iter)->name(); + texture = (*iter)->texture(); + preview_size = ImVec2( preview_width, preview_width / (*iter)->frame()->aspectRatio()); + preview_uv1 = ImVec2(0.f, 0.f); + preview_uv2 = ImVec2(1.f, 1.f); + } + } + ImGui::EndCombo(); + } + + if (!new_source_to_create_.empty()) { + + // preview + if (texture != 0) { + ImGui::Image((void*)(uintptr_t) texture, preview_size, preview_uv1, preview_uv2); + } + + ImGui::Text("%s ", new_source_to_create_.c_str()); + if ( ImGui::Button("Create !", ImVec2(pannel_width - padding_width, 0)) ) { + + Source *s = nullptr; + if (new_source_to_create_ == "Render") + s = Mixer::manager().createSourceRender(); + else + s = Mixer::manager().createSourceClone(new_source_to_create_); + + Mixer::manager().insertSource(s); + + // reset for next time + new_source_to_create_ = ""; + texture = 0; + selected_button[NAV_NEW] = false; + } } } diff --git a/UserInterfaceManager.h b/UserInterfaceManager.h index 84205d7..398861a 100644 --- a/UserInterfaceManager.h +++ b/UserInterfaceManager.h @@ -33,6 +33,10 @@ class Navigator void RenderNewPannel(); void RenderMainPannel(); + int new_source_type_; + std::string new_source_to_create_; + char new_source_filename_[2048]; + public: Navigator(); diff --git a/main.cpp b/main.cpp index 68252aa..4c26a21 100644 --- a/main.cpp +++ b/main.cpp @@ -24,25 +24,10 @@ #include "ImGuiVisitor.h" // vmix -#include "defines.h" #include "Settings.h" - -// mixing #include "Mixer.h" -#include "Source.h" #include "RenderingManager.h" #include "UserInterfaceManager.h" -#include "FrameBuffer.h" -#include "Resource.h" -#include "ImageProcessingShader.h" - -#include "MediaPlayer.h" -#include "Scene.h" -#include "Primitives.h" -#include "Mesh.h" -#include "SessionVisitor.h" - -#define PI 3.14159265358979323846 void drawScene() @@ -83,31 +68,11 @@ int main(int, char**) #endif // test text editor - UserInterface::manager().fillShaderEditor( Resource::getText("shaders/image.fs") ); +// UserInterface::manager().fillShaderEditor( Resource::getText("shaders/image.fs") ); // draw the scene Rendering::manager().PushFrontDrawCallback(drawScene); - // init elements to the scene -// if ( !Mixer::manager().open("./testsession.vmx") ) -// { -// Mixer::manager().createSourceMedia("file:///home/bhbn/Videos/iss.mov"); -// Mixer::manager().createSourceMedia("file:///home/bhbn/Videos/fish.mp4"); -// } - -// Animation A; -// A.translation_ = glm::vec3(0.f, 0.f, 3.f); -// A.speed_ = 0.1f; -// A.axis_ = glm::vec3(1.f, 1.f, 1.f); -// Mesh P("mesh/point.ply"); -// P.scale_ = glm::vec3(0.15f); -// A.addChild(&P); -// Mixer::manager().currentView()->scene.root()->addChild(&A); - - // custom test window -// Rendering::manager().PushBackDrawCallback(drawCustomGui); - - /// /// Main LOOP /// @@ -118,11 +83,21 @@ int main(int, char**) Rendering::manager().Draw(); } + /// + /// UI TERMINATE + /// UserInterface::manager().Terminate(); + + /// + /// RENDERING TERMINATE + /// Rendering::manager().Terminate(); + /// + /// Settings + /// Settings::Save(); - + /// ok return 0; }