diff --git a/3rdparty/libossia b/3rdparty/libossia index e8d84aaa46..52e6f47cc4 160000 --- a/3rdparty/libossia +++ b/3rdparty/libossia @@ -1 +1 @@ -Subproject commit e8d84aaa46e859599cc8cb15cd3c25a5004c0657 +Subproject commit 52e6f47cc45fea713e599bcee88d7815321abb9f diff --git a/src/lib/score/tools/IdentifierGeneration.cpp b/src/lib/score/tools/IdentifierGeneration.cpp index 118a56440a..c063cb9a4e 100644 --- a/src/lib/score/tools/IdentifierGeneration.cpp +++ b/src/lib/score/tools/IdentifierGeneration.cpp @@ -31,15 +31,15 @@ struct IdGen { } - auto make() noexcept { return dist(gen); } + int32_t make() noexcept { return dist(gen); } }; +static IdGen g_idgen; int32_t random_id_generator::getRandomId() { using namespace std; - static IdGen idgen; - return idgen.make(); + return g_idgen.make(); } #endif diff --git a/src/plugins/score-plugin-protocols/Protocols/Mapper/MapperDevice.cpp b/src/plugins/score-plugin-protocols/Protocols/Mapper/MapperDevice.cpp index 3d0be591a2..f0c21bc6c2 100644 --- a/src/plugins/score-plugin-protocols/Protocols/Mapper/MapperDevice.cpp +++ b/src/plugins/score-plugin-protocols/Protocols/Mapper/MapperDevice.cpp @@ -27,6 +27,7 @@ #include #include +#include #include #include @@ -98,6 +99,7 @@ class observable_device_roots final : public QObject r.push_back(&d->get_root_node()); return r; } + const auto& devices() const noexcept { return m_devices; } private: std::vector m_devices; @@ -334,16 +336,65 @@ class mapper_protocol final , m_code{code} , m_devices{roots} , m_roots{m_devices.roots()} + { + this->moveToThread(&m_thread); + m_thread.start(); + QMetaObject::invokeMethod(this, &mapper_protocol::init_engine, Qt::QueuedConnection); + } + + ~mapper_protocol() override + { + if(m_engine) + { + stop(); + } + } + + void stop() override + { + QMetaObject::invokeMethod( + this, &mapper_protocol::teardown_engine, Qt::QueuedConnection); + m_thread.wait(); + } + + void teardown_engine() + { + delete m_component; + delete m_engine; + m_thread.exit(); + m_component = nullptr; + m_engine = nullptr; + } + + void init_engine() { m_engine = new QQmlEngine{this}; m_component = new QQmlComponent{m_engine}; + auto obj = new ossia::qt::qml_device_engine_functions{ + {}, [](ossia::net::parameter_base& param, const ossia::value_port& v) { + if(v.get_data().empty()) + return; + auto& last = v.get_data().back().value; + param.push_value(last); + }, m_engine}; + obj->setDevice(m_device); + for(auto dev : m_devices.devices()) + obj->devices.push_back(dev); + + m_engine->rootContext()->setContextProperty("Device", obj); + QObject::connect( this, &mapper_protocol::sig_push, this, &mapper_protocol::slot_push); QObject::connect( this, &mapper_protocol::sig_recv, this, &mapper_protocol::slot_recv); con(m_devices, &observable_device_roots::rootsChanged, this, - [this](std::vector r) { + [this, obj](std::vector r) { + ossia::qt::qml_device_cache cache; + for(auto node : r) + cache.push_back(&node->get_device()); + ossia::remove_duplicates(cache); + obj->devices = cache; m_roots = std::move(r); reset_tree(); }); @@ -351,22 +402,27 @@ class mapper_protocol final QObject::connect( m_component, &QQmlComponent::statusChanged, this, [this](QQmlComponent::Status status) { - qDebug() << status; - qDebug() << m_component->errorString(); if(!m_device) return; switch(status) { case QQmlComponent::Status::Ready: { - m_object = m_component->create(); - m_object->setParent(m_engine->rootContext()); - - QVariant ret; - QMetaObject::invokeMethod(m_object, "createTree", Q_RETURN_ARG(QVariant, ret)); - qt::create_device( - *m_device, ret.value()); - reset_tree(); + if((m_object = m_component->create())) + { + m_object->setParent(m_engine->rootContext()); + + QVariant ret; + QMetaObject::invokeMethod( + m_object, "createTree", Q_RETURN_ARG(QVariant, ret)); + qt::create_device( + *m_device, ret.value()); + reset_tree(); + } + else + { + qDebug() << "Mapper: could not create object"; + } return; } case QQmlComponent::Status::Loading: @@ -376,19 +432,7 @@ class mapper_protocol final qDebug() << m_component->errorString(); return; } - }); - - this->moveToThread(&m_thread); - m_thread.start(); - } - - ~mapper_protocol() override - { - m_thread.exit(); - m_thread.wait(); - - delete m_component; - delete m_engine; + }); } void sig_push(mapper_parameter* p, const ossia::value& v) W_SIGNAL(sig_push, p, v); @@ -688,9 +732,11 @@ class MapperDevice final : public Device::OwningDeviceInterface const auto& stgs = settings().deviceSpecificSettings.value(); + auto proto + = std::make_unique(stgs.text.toUtf8(), *devlist); + auto nm = settings().name.toStdString(); m_dev = std::make_unique( - std::make_unique(stgs.text.toUtf8(), *devlist), - settings().name.toStdString()); + static_cast&&>(proto), nm); deviceChanged(nullptr, m_dev.get());