From d563ee14a9cada6153acaef3a978f5d3ce6afef5 Mon Sep 17 00:00:00 2001 From: brunoherbelin Date: Sat, 3 Oct 2020 17:54:34 +0200 Subject: [PATCH] Cleanup source id management, and improved session merging and source renaming. --- Mixer.cpp | 22 ++++++++------ Mixer.h | 6 ++-- Session.cpp | 33 +++++++++++--------- Session.h | 4 ++- SessionCreator.cpp | 65 ++++++++++++++++++++++------------------ SessionVisitor.cpp | 2 ++ Source.h | 10 +++++++ UserInterfaceManager.cpp | 2 +- 8 files changed, 88 insertions(+), 56 deletions(-) diff --git a/Mixer.cpp b/Mixer.cpp index 4c2fa0c..3e62efc 100644 --- a/Mixer.cpp +++ b/Mixer.cpp @@ -474,15 +474,12 @@ void Mixer::renameSource(Source *s, const std::string &newname) if ( newname.empty() ) tentativename = "source"; - // trivial case : same name as current - if ( tentativename == s->name() ) - return; - // search for a source of the name 'tentativename' std::string basename = tentativename; int count = 1; - while ( std::find_if(session_->begin(), session_->end(), Source::hasName(tentativename)) != session_->end() ) { - tentativename = basename + std::to_string(++count); + for( auto it = session_->begin(); it != session_->end(); it++){ + if ( s->id() != (*it)->id() && (*it)->name() == tentativename ) + tentativename = basename + std::to_string( ++count ); } // ok to rename @@ -533,6 +530,11 @@ Source * Mixer::findSource (std::string namesource) return nullptr; } +void Mixer::setCurrentSource(int id) +{ + setCurrentSource( session_->find(id) ); +} + void Mixer::setCurrentSource(Node *node) { setCurrentSource( session_->find(node) ); @@ -548,9 +550,9 @@ void Mixer::setCurrentSource(Source *s) setCurrentSource( session_->find(s) ); } -void Mixer::setCurrentSource(int index) +void Mixer::setCurrentIndex(int index) { - setCurrentSource( session_->find(index) ); + setCurrentSource( session_->at(index) ); } void Mixer::setCurrentNext() @@ -728,8 +730,10 @@ void Mixer::merge(Session *session) } // import every sources - for ( Source *s = session->popSource(); s != nullptr; s = session->popSource()) + for ( Source *s = session->popSource(); s != nullptr; s = session->popSource()) { + renameSource(s, s->name()); insertSource(s); + } } void Mixer::swap() diff --git a/Mixer.h b/Mixer.h index 4824010..33ae8d7 100644 --- a/Mixer.h +++ b/Mixer.h @@ -50,14 +50,16 @@ public: void deleteSelection(); // current source + Source * currentSource (); void setCurrentSource (Source *s); void setCurrentSource (std::string namesource); void setCurrentSource (Node *node); - void setCurrentSource (int index); + void setCurrentSource (int id); void setCurrentNext (); void unsetCurrentSource (); + + void setCurrentIndex (int index); int indexCurrentSource (); - Source * currentSource (); // browsing into sources Source * findSource (Node *node); diff --git a/Session.cpp b/Session.cpp index 1c0108d..bc71d20 100644 --- a/Session.cpp +++ b/Session.cpp @@ -225,25 +225,16 @@ SourceList::iterator Session::end() return sources_.end(); } -SourceList::iterator Session::find(int index) -{ - if (index<0) - return sources_.end(); - - int i = 0; - SourceList::iterator it = sources_.begin(); - while ( i < index && it != sources_.end() ){ - i++; - it++; - } - return it; -} - SourceList::iterator Session::find(Source *s) { return std::find(sources_.begin(), sources_.end(), s); } +SourceList::iterator Session::find(int id) +{ + return std::find_if(sources_.begin(), sources_.end(), Source::hasId(id)); +} + SourceList::iterator Session::find(std::string namesource) { return std::find_if(sources_.begin(), sources_.end(), Source::hasName(namesource)); @@ -264,6 +255,20 @@ bool Session::empty() const return sources_.empty(); } +SourceList::iterator Session::at(int index) +{ + if (index<0) + return sources_.end(); + + int i = 0; + SourceList::iterator it = sources_.begin(); + while ( i < index && it != sources_.end() ){ + i++; + it++; + } + return it; +} + int Session::index(SourceList::iterator it) const { int index = -1; diff --git a/Session.h b/Session.h index e47a946..ccd22e5 100644 --- a/Session.h +++ b/Session.h @@ -33,10 +33,12 @@ public: uint numSource() const; SourceList::iterator begin (); SourceList::iterator end (); - SourceList::iterator find (int index); SourceList::iterator find (Source *s); SourceList::iterator find (std::string name); SourceList::iterator find (Node *node); + SourceList::iterator find (int id); + + SourceList::iterator at (int index); int index (SourceList::iterator it) const; // update all sources and mark sources which failed diff --git a/SessionCreator.cpp b/SessionCreator.cpp index 8229781..9298bc0 100644 --- a/SessionCreator.cpp +++ b/SessionCreator.cpp @@ -95,36 +95,43 @@ void SessionCreator::loadSession(XMLElement *sessionNode) xmlCurrent_ = sourceNode; counter++; - const char *pType = xmlCurrent_->Attribute("type"); - if (!pType) - continue; - if ( std::string(pType) == "MediaSource") { - MediaSource *new_media_source = new MediaSource; - new_media_source->accept(*this); - session_->addSource(new_media_source); - } - else if ( std::string(pType) == "SessionSource") { - SessionSource *new_session_source = new SessionSource; - new_session_source->accept(*this); - session_->addSource(new_session_source); - } - else if ( std::string(pType) == "RenderSource") { - RenderSource *new_render_source = new RenderSource(session_); - new_render_source->accept(*this); - session_->addSource(new_render_source); - } - else if ( std::string(pType) == "PatternSource") { - PatternSource *new_pattern_source = new PatternSource; - new_pattern_source->accept(*this); - session_->addSource(new_pattern_source); - } - else if ( std::string(pType) == "DeviceSource") { - DeviceSource *new_pattern_source = new DeviceSource; - new_pattern_source->accept(*this); - session_->addSource(new_pattern_source); - } - // TODO : create other types of source + // source to load + Source *load_source = nullptr; + // check if a source with same id exists + int id__ = -1; + xmlCurrent_->QueryIntAttribute("id", &id__); + SourceList::iterator sit = session_->find(id__); + + // no source with this id exists + if ( sit == session_->end() ) { + // create a new source depending on type + const char *pType = xmlCurrent_->Attribute("type"); + if (!pType) + continue; + if ( std::string(pType) == "MediaSource") { + load_source = new MediaSource; + } + else if ( std::string(pType) == "SessionSource") { + load_source = new SessionSource; + } + else if ( std::string(pType) == "RenderSource") { + load_source = new RenderSource(session_); + } + else if ( std::string(pType) == "PatternSource") { + load_source = new PatternSource; + } + else if ( std::string(pType) == "DeviceSource") { + load_source = new DeviceSource; + } + // add source to session + session_->addSource(load_source); + } + else + load_source = *sit; + + // apply config to source + load_source->accept(*this); } // create clones after all sources to potentially clone have been created diff --git a/SessionVisitor.cpp b/SessionVisitor.cpp index c0de35b..3bc8a9b 100644 --- a/SessionVisitor.cpp +++ b/SessionVisitor.cpp @@ -194,6 +194,7 @@ void SessionVisitor::visit(ImageShader &n) { // Shader of a textured type xmlCurrent_->SetAttribute("type", "ImageShader"); + xmlCurrent_->SetAttribute("id", n.id()); XMLElement *uniforms = xmlDoc_->NewElement("uniforms"); uniforms->SetAttribute("stipple", n.stipple); @@ -206,6 +207,7 @@ void SessionVisitor::visit(ImageProcessingShader &n) { // Shader of a textured type xmlCurrent_->SetAttribute("type", "ImageProcessingShader"); + xmlCurrent_->SetAttribute("id", n.id()); XMLElement *filter = xmlDoc_->NewElement("uniforms"); filter->SetAttribute("brightness", n.brightness); diff --git a/Source.h b/Source.h index c1fd4b9..7fb9983 100644 --- a/Source.h +++ b/Source.h @@ -122,6 +122,16 @@ public: std::string _n; }; + struct hasId: public std::unary_function + { + inline bool operator()(const Source* elem) const { + return (elem && elem->id() == _id); + } + hasId(int id) : _id(id) { } + private: + int _id; + }; + virtual glm::ivec2 icon() const { return glm::ivec2(12, 11); } protected: diff --git a/UserInterfaceManager.cpp b/UserInterfaceManager.cpp index a77fd0c..0eecbd3 100644 --- a/UserInterfaceManager.cpp +++ b/UserInterfaceManager.cpp @@ -1669,7 +1669,7 @@ void Navigator::Render() { applyButtonSelection(index); if (selected_button[index]) - Mixer::manager().setCurrentSource(index); + Mixer::manager().setCurrentIndex(index); } ImGui::PopID(); }