From cc1d8e595e5149ba7f824b2a18a58b1df9bfcc0c Mon Sep 17 00:00:00 2001 From: Nicolas Pope <nwpope@utu.fi> Date: Thu, 30 Jul 2020 10:08:27 +0300 Subject: [PATCH] Add GUI audio mixer --- applications/gui2/src/modules/camera.cpp | 13 +++++++ applications/gui2/src/modules/camera.hpp | 3 ++ applications/gui2/src/views/camera.cpp | 2 +- applications/gui2/src/widgets/soundctrl.cpp | 40 +++++++++++++++++++-- applications/gui2/src/widgets/soundctrl.hpp | 5 ++- components/audio/src/speaker.cpp | 2 +- 6 files changed, 60 insertions(+), 5 deletions(-) diff --git a/applications/gui2/src/modules/camera.cpp b/applications/gui2/src/modules/camera.cpp index a47d35f1a..c362d6a48 100644 --- a/applications/gui2/src/modules/camera.cpp +++ b/applications/gui2/src/modules/camera.cpp @@ -3,6 +3,7 @@ #include "../views/camera3d.hpp" #include <ftl/rgbd/capabilities.hpp> +#include <ftl/streams/renderer.hpp> #include <chrono> #include <opencv2/imgproc.hpp> @@ -330,6 +331,18 @@ std::string Camera::getActiveSourceURI() { return ""; } +ftl::audio::StereoMixerF<100> *Camera::mixer() { + if (mixer_) return mixer_; + if (movable_) { + auto *rend = io->feed()->getRenderer(frame_id_); + if (rend) { + mixer_ = &(rend->mixer()); + return mixer_; + } + } + return nullptr; +} + bool Camera::isRecording() { return io->feed()->isRecording(); } diff --git a/applications/gui2/src/modules/camera.hpp b/applications/gui2/src/modules/camera.hpp index d4da36f3b..bdcb6dcaa 100644 --- a/applications/gui2/src/modules/camera.hpp +++ b/applications/gui2/src/modules/camera.hpp @@ -7,6 +7,7 @@ #include <ftl/render/colouriser.hpp> #include <ftl/render/overlay.hpp> #include <ftl/codecs/touch.hpp> +#include <ftl/audio/mixer.hpp> namespace ftl { namespace gui2 { @@ -49,6 +50,7 @@ public: ftl::render::Colouriser* colouriser() { return colouriser_.get(); }; ftl::overlay::Overlay* overlay() { return overlay_.get(); } + ftl::audio::StereoMixerF<100> *mixer(); void drawOverlay(NVGcontext *ctx); @@ -90,6 +92,7 @@ private: std::map<ftl::data::Message,std::string> messages_; CameraView* view = nullptr; + ftl::audio::StereoMixerF<100> *mixer_ = nullptr; MUTEX mtx_; diff --git a/applications/gui2/src/views/camera.cpp b/applications/gui2/src/views/camera.cpp index 565381ebc..76ff8efab 100644 --- a/applications/gui2/src/views/camera.cpp +++ b/applications/gui2/src/views/camera.cpp @@ -204,7 +204,7 @@ MediaPanel::MediaPanel(nanogui::Widget *parent, ftl::gui2::Camera* ctrl) : this->setTheme(theme); // Volume control - button_volume = new ftl::gui2::VolumeButton(this); + button_volume = new ftl::gui2::VolumeButton(this, ctrl_->mixer()); button_volume->setValue(ctrl_->volume()); button_volume->setCallback([ctrl = ctrl_](float v){ ctrl->setVolume(v); }); diff --git a/applications/gui2/src/widgets/soundctrl.cpp b/applications/gui2/src/widgets/soundctrl.cpp index 87ca183a5..4a8d6a08d 100644 --- a/applications/gui2/src/widgets/soundctrl.cpp +++ b/applications/gui2/src/widgets/soundctrl.cpp @@ -9,8 +9,8 @@ using ftl::gui2::PopupButton; using ftl::gui2::VolumeButton; using ftl::gui2::Screen; -VolumeButton::VolumeButton(nanogui::Widget *parent) : - ftl::gui2::PopupButton(parent, "", ENTYPO_ICON_SOUND) { +VolumeButton::VolumeButton(nanogui::Widget *parent, ftl::audio::StereoMixerF<100> *mixer) : + ftl::gui2::PopupButton(parent, "", ENTYPO_ICON_SOUND), mixer_(mixer) { setChevronIcon(-1); muted_ = false; @@ -27,6 +27,42 @@ VolumeButton::VolumeButton(nanogui::Widget *parent) : setValue(value); if (cb_) { cb_(value); } }); + + if (mixer) { + auto *mixbut = new nanogui::Button(mPopup, "Mixer", ENTYPO_ICON_SOUND_MIX); + mPopup->setAnchorHeight(70); + + auto *mixer_widget = new nanogui::Widget(mPopup); + mixer_widget->setLayout(new nanogui::GroupLayout(0, 6, 14, 0)); + mixer_widget->setVisible(false); + + // Add mixer slider for each track in mixer. + for (int t=0; t<mixer->tracks(); ++t) { + auto *label = new nanogui::Label(mixer_widget, mixer->name(t)); + label->setFontSize(12); + auto *mixslider = new nanogui::Slider(mixer_widget); + mixslider->setHighlightColor(dynamic_cast<Screen*>(screen())->getColor("highlight1")); + mixslider->setHeight(20); + mixslider->setValue(mixer->gain(t)); + mixslider->setHighlightedRange({0.0f, mixer->gain(t)}); + + mixslider->setCallback([this,t,mixslider](float value) { + mixslider->setValue(value); + mixslider->setHighlightedRange({0.0f, value}); + mixer_->setGain(t, value); + }); + } + + mixbut->setCallback([this,mixer_widget]() { + mixer_widget->setVisible(!mixer_widget->visible()); + if (mixer_widget->visible()) { + mPopup->setAnchorHeight(70+mixer_widget->childCount()*20); + } else { + mPopup->setAnchorHeight(70); + } + screen()->performLayout(); + }); + } } VolumeButton::~VolumeButton() { diff --git a/applications/gui2/src/widgets/soundctrl.hpp b/applications/gui2/src/widgets/soundctrl.hpp index 1db40ec5c..5495edd5c 100644 --- a/applications/gui2/src/widgets/soundctrl.hpp +++ b/applications/gui2/src/widgets/soundctrl.hpp @@ -1,6 +1,7 @@ #pragma once #include <nanogui/entypo.h> +#include <ftl/audio/mixer.hpp> #include "popupbutton.hpp" @@ -9,7 +10,7 @@ namespace gui2 { class VolumeButton : public ftl::gui2::PopupButton { public: - VolumeButton(nanogui::Widget *parent); + VolumeButton(nanogui::Widget *parent, ftl::audio::StereoMixerF<100> *mixer); virtual ~VolumeButton(); // callback, new value passed in argument @@ -38,6 +39,8 @@ private: nanogui::Slider* slider_; std::function<void(float)> cb_; + ftl::audio::StereoMixerF<100> *mixer_; + float scroll_step_ = 0.02f; float value_; bool muted_; diff --git a/components/audio/src/speaker.cpp b/components/audio/src/speaker.cpp index 89f865454..7db2e8426 100644 --- a/components/audio/src/speaker.cpp +++ b/components/audio/src/speaker.cpp @@ -155,7 +155,7 @@ void Speaker::setDelay(int64_t ms) { void Speaker::setVolume(float value) { // TODO: adjust volume using system mixer volume_ = std::max(0.0f, std::min(1.0f, value)); - buffer_->setGain(volume_); + if (buffer_) buffer_->setGain(volume_); } float Speaker::volume() { -- GitLab