Mercurial > hg > svapp
changeset 205:a3fbd52031a5
* Provide callback for use when configuring a plugin with GUI
author | Chris Cannam |
---|---|
date | Fri, 08 Oct 2010 11:20:10 +0100 |
parents | 5ee9e6bc21eb |
children | 58e41f580714 |
files | framework/TransformUserConfigurator.cpp framework/TransformUserConfigurator.h svapp.pro |
diffstat | 3 files changed, 267 insertions(+), 0 deletions(-) [+] |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/framework/TransformUserConfigurator.cpp Fri Oct 08 11:20:10 2010 +0100 @@ -0,0 +1,223 @@ +/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */ + +/* + Sonic Visualiser + An audio file viewer and annotation editor. + Centre for Digital Music, Queen Mary, University of London. + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. See the file + COPYING included with this distribution for more information. +*/ + +#include "TransformUserConfigurator.h" + +#include "transform/TransformFactory.h" + +#include "widgets/PluginParameterDialog.h" + +#include "plugin/FeatureExtractionPluginFactory.h" +#include "plugin/RealTimePluginFactory.h" +#include "plugin/RealTimePluginInstance.h" + +#include "data/model/DenseTimeValueModel.h" + +#include <vamp-hostsdk/Plugin.h> + +#include <QStringList> + +#include <typeinfo> + +bool +TransformUserConfigurator::getChannelRange(TransformId identifier, + Vamp::PluginBase *plugin, + int &minChannels, int &maxChannels) +{ + if (plugin && plugin->getType() == "Feature Extraction Plugin") { + Vamp::Plugin *vp = static_cast<Vamp::Plugin *>(plugin); + std::cerr << "TransformUserConfigurator::getChannelRange: is a VP" << std::endl; + minChannels = vp->getMinChannelCount(); + maxChannels = vp->getMaxChannelCount(); + return true; + } else { + std::cerr << "TransformUserConfigurator::getChannelRange: is not a VP" << std::endl; + return TransformFactory::getInstance()-> + getTransformChannelRange(identifier, minChannels, maxChannels); + } +} + +bool +TransformUserConfigurator::configure(ModelTransformer::Input &input, + Transform &transform, + Vamp::PluginBase *plugin, + Model *inputModel, + AudioPlaySource *source, + size_t startFrame, + size_t duration, + const QMap<QString, Model *> &modelMap, + QStringList candidateModelNames, + QString defaultModelName) +{ + bool ok = false; + QString id = transform.getPluginIdentifier(); + QString output = transform.getOutput(); + QString outputLabel = ""; + QString outputDescription = ""; + + bool frequency = false; + bool effect = false; + bool generator = false; + + if (!plugin) return false; + + if (FeatureExtractionPluginFactory::instanceFor(id)) { + + Vamp::Plugin *vp = static_cast<Vamp::Plugin *>(plugin); + + frequency = (vp->getInputDomain() == Vamp::Plugin::FrequencyDomain); + + std::vector<Vamp::Plugin::OutputDescriptor> od = + vp->getOutputDescriptors(); + + std::cerr << "configure: looking for output: " << output.toStdString() << std::endl; + + if (od.size() > 1) { + for (size_t i = 0; i < od.size(); ++i) { + if (od[i].identifier == output.toStdString()) { + outputLabel = od[i].name.c_str(); + outputDescription = od[i].description.c_str(); + break; + } + } + } + + } else if (RealTimePluginFactory::instanceFor(id)) { + + RealTimePluginFactory *factory = RealTimePluginFactory::instanceFor(id); + const RealTimePluginDescriptor *desc = factory->getPluginDescriptor(id); + + if (desc->audioInputPortCount > 0 && + desc->audioOutputPortCount > 0 && + !desc->isSynth) { + effect = true; + } + + if (desc->audioInputPortCount == 0) { + generator = true; + } + + if (output != "A") { + int outputNo = output.toInt(); + if (outputNo >= 0 && outputNo < int(desc->controlOutputPortCount)) { + outputLabel = desc->controlOutputPortNames[outputNo].c_str(); + } + } + + RealTimePluginInstance *rtp = + static_cast<RealTimePluginInstance *>(plugin); + + if (effect && source) { + std::cerr << "Setting auditioning effect" << std::endl; + source->setAuditioningEffect(rtp); + } + } + + int sourceChannels = 1; + if (dynamic_cast<DenseTimeValueModel *>(inputModel)) { + sourceChannels = dynamic_cast<DenseTimeValueModel *>(inputModel) + ->getChannelCount(); + } + + int minChannels = 1, maxChannels = sourceChannels; + getChannelRange(transform.getIdentifier(), plugin, + minChannels, maxChannels); + + int targetChannels = sourceChannels; + if (!effect) { + if (sourceChannels < minChannels) targetChannels = minChannels; + if (sourceChannels > maxChannels) targetChannels = maxChannels; + } + + int defaultChannel = -1; //!!! no longer saved! [was context.channel] + + PluginParameterDialog *dialog = new PluginParameterDialog(plugin); + + dialog->setMoreInfoUrl(TransformFactory::getInstance()-> + getTransformInfoUrl(transform.getIdentifier())); + + if (candidateModelNames.size() > 1 && !generator) { + dialog->setCandidateInputModels(candidateModelNames, + defaultModelName); + } + + if (startFrame != 0 || duration != 0) { + dialog->setShowSelectionOnlyOption(true); + } + + if (targetChannels > 0) { + dialog->setChannelArrangement(sourceChannels, targetChannels, + defaultChannel); + } + + dialog->setOutputLabel(outputLabel, outputDescription); + + dialog->setShowProcessingOptions(true, frequency); + + if (dialog->exec() == QDialog::Accepted) { + ok = true; + } + + QString selectedInput = dialog->getInputModel(); + if (selectedInput != "") { + if (modelMap.contains(selectedInput)) { + inputModel = modelMap.value(selectedInput); + std::cerr << "Found selected input \"" << selectedInput.toStdString() << "\" in model map, result is " << inputModel << std::endl; + } else { + std::cerr << "Failed to find selected input \"" << selectedInput.toStdString() << "\" in model map" << std::endl; + } + } else { + std::cerr << "Selected input empty: \"" << selectedInput.toStdString() << "\"" << std::endl; + } + + // Write parameters back to transform object + TransformFactory::getInstance()-> + setParametersFromPlugin(transform, plugin); + + input.setChannel(dialog->getChannel()); + + //!!! The dialog ought to be taking & returning transform + //objects and input objects and stuff rather than passing + //around all this misc stuff, but that's for tomorrow + //(whenever that may be) + + if (startFrame != 0 || duration != 0) { + if (dialog->getSelectionOnly()) { + transform.setStartTime(RealTime::frame2RealTime + (startFrame, inputModel->getSampleRate())); + transform.setDuration(RealTime::frame2RealTime + (duration, inputModel->getSampleRate())); + } + } + + size_t stepSize = 0, blockSize = 0; + WindowType windowType = HanningWindow; + + dialog->getProcessingParameters(stepSize, + blockSize, + windowType); + + transform.setStepSize(stepSize); + transform.setBlockSize(blockSize); + transform.setWindowType(windowType); + + delete dialog; + + if (effect && source) { + source->setAuditioningEffect(0); + } + + return ok; +} +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/framework/TransformUserConfigurator.h Fri Oct 08 11:20:10 2010 +0100 @@ -0,0 +1,42 @@ +/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */ + +/* + Sonic Visualiser + An audio file viewer and annotation editor. + Centre for Digital Music, Queen Mary, University of London. + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. See the file + COPYING included with this distribution for more information. +*/ + +#ifndef _TRANSFORM_USER_CONFIGURATOR_H_ +#define _TRANSFORM_USER_CONFIGURATOR_H_ + +#include "transform/ModelTransformerFactory.h" + +class TransformUserConfigurator : public ModelTransformerFactory::UserConfigurator +{ +public: + // This is of course absolutely gross + + virtual bool configure(ModelTransformer::Input &input, + Transform &transform, + Vamp::PluginBase *plugin, + Model *inputModel, + AudioPlaySource *source, + size_t startFrame, + size_t duration, + const QMap<QString, Model *> &modelMap, + QStringList candidateModelNames, + QString defaultModelName); + +private: + bool getChannelRange(TransformId identifier, + Vamp::PluginBase *plugin, int &min, int &max); + +}; + +#endif
--- a/svapp.pro Fri Oct 08 11:19:57 2010 +0100 +++ b/svapp.pro Fri Oct 08 11:20:10 2010 +0100 @@ -35,10 +35,12 @@ HEADERS += framework/Document.h \ framework/MainWindowBase.h \ framework/SVFileReader.h \ + framework/TransformUserConfigurator.h \ framework/VersionTester.h SOURCES += framework/Document.cpp \ framework/MainWindowBase.cpp \ framework/SVFileReader.cpp \ + framework/TransformUserConfigurator.cpp \ framework/VersionTester.cpp