annotate main/OSCHandler.cpp @ 289:ee96e37a3cbb

* Make it possible to import an entire session from an RDF document. However, at the moment the timings of events appear to be constrained by how far the audio decoder has got through its audio file at the time the event is queried -- need to investigate.
author Chris Cannam
date Fri, 21 Nov 2008 18:03:14 +0000
parents 9d772bee2095
children 3f0c98204636
rev   line source
Chris@224 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
Chris@224 2
Chris@224 3 /*
Chris@224 4 Sonic Visualiser
Chris@224 5 An audio file viewer and annotation editor.
Chris@224 6 Centre for Digital Music, Queen Mary, University of London.
Chris@224 7 This file copyright 2006-2007 Chris Cannam and QMUL.
Chris@224 8
Chris@224 9 This program is free software; you can redistribute it and/or
Chris@224 10 modify it under the terms of the GNU General Public License as
Chris@224 11 published by the Free Software Foundation; either version 2 of the
Chris@224 12 License, or (at your option) any later version. See the file
Chris@224 13 COPYING included with this distribution for more information.
Chris@224 14 */
Chris@216 15
Chris@216 16 #include "MainWindow.h"
Chris@216 17 #include "data/osc/OSCQueue.h"
Chris@216 18
Chris@216 19 #include "layer/WaveformLayer.h"
Chris@216 20 #include "view/ViewManager.h"
Chris@216 21 #include "view/Pane.h"
Chris@216 22 #include "view/PaneStack.h"
Chris@216 23 #include "data/model/WaveFileModel.h"
Chris@248 24 #include "widgets/CommandHistory.h"
Chris@216 25 #include "audioio/AudioCallbackPlaySource.h"
Chris@216 26 #include "audioio/AudioCallbackPlayTarget.h"
Chris@216 27 #include "framework/Document.h"
Chris@216 28 #include "data/fileio/WavFileWriter.h"
Chris@249 29 #include "transform/TransformFactory.h"
Chris@216 30 #include "widgets/Fader.h"
Chris@216 31 #include "widgets/AudioDial.h"
Chris@216 32
Chris@216 33 #include <QFileInfo>
Chris@216 34
Chris@216 35 void
Chris@216 36 MainWindow::handleOSCMessage(const OSCMessage &message)
Chris@216 37 {
Chris@216 38 std::cerr << "MainWindow::handleOSCMessage: thread id = "
Chris@216 39 << QThread::currentThreadId() << std::endl;
Chris@216 40
Chris@216 41 // This large function should really be abstracted out.
Chris@216 42
Chris@216 43 if (message.getMethod() == "open") {
Chris@216 44
Chris@216 45 if (message.getArgCount() == 1 &&
Chris@216 46 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 47 QString path = message.getArg(0).toString();
Chris@216 48 if (open(path, ReplaceMainModel) != FileOpenSucceeded) {
Chris@216 49 std::cerr << "MainWindow::handleOSCMessage: File open failed for path \""
Chris@216 50 << path.toStdString() << "\"" << std::endl;
Chris@216 51 }
Chris@216 52 //!!! we really need to spin here and not return until the
Chris@216 53 // file has been completely decoded...
Chris@216 54 }
Chris@216 55
Chris@216 56 } else if (message.getMethod() == "openadditional") {
Chris@216 57
Chris@216 58 if (message.getArgCount() == 1 &&
Chris@216 59 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 60 QString path = message.getArg(0).toString();
Chris@216 61 if (open(path, CreateAdditionalModel) != FileOpenSucceeded) {
Chris@216 62 std::cerr << "MainWindow::handleOSCMessage: File open failed for path \""
Chris@216 63 << path.toStdString() << "\"" << std::endl;
Chris@216 64 }
Chris@216 65 }
Chris@216 66
Chris@216 67 } else if (message.getMethod() == "recent" ||
Chris@216 68 message.getMethod() == "last") {
Chris@216 69
Chris@216 70 int n = 0;
Chris@216 71 if (message.getMethod() == "recent" &&
Chris@216 72 message.getArgCount() == 1 &&
Chris@216 73 message.getArg(0).canConvert(QVariant::Int)) {
Chris@216 74 n = message.getArg(0).toInt() - 1;
Chris@216 75 }
Chris@216 76 std::vector<QString> recent = m_recentFiles.getRecent();
Chris@216 77 if (n >= 0 && n < int(recent.size())) {
Chris@216 78 if (open(recent[n], ReplaceMainModel) != FileOpenSucceeded) {
Chris@216 79 std::cerr << "MainWindow::handleOSCMessage: File open failed for path \""
Chris@216 80 << recent[n].toStdString() << "\"" << std::endl;
Chris@216 81 }
Chris@216 82 }
Chris@216 83
Chris@216 84 } else if (message.getMethod() == "save") {
Chris@216 85
Chris@216 86 QString path;
Chris@216 87 if (message.getArgCount() == 1 &&
Chris@216 88 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 89 path = message.getArg(0).toString();
Chris@216 90 if (QFileInfo(path).exists()) {
Chris@216 91 std::cerr << "MainWindow::handleOSCMessage: Refusing to overwrite existing file in save" << std::endl;
Chris@216 92 } else {
Chris@216 93 saveSessionFile(path);
Chris@216 94 }
Chris@216 95 }
Chris@216 96
Chris@216 97 } else if (message.getMethod() == "export") {
Chris@216 98
Chris@216 99 QString path;
Chris@216 100 if (getMainModel()) {
Chris@216 101 if (message.getArgCount() == 1 &&
Chris@216 102 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 103 path = message.getArg(0).toString();
Chris@216 104 if (QFileInfo(path).exists()) {
Chris@216 105 std::cerr << "MainWindow::handleOSCMessage: Refusing to overwrite existing file in export" << std::endl;
Chris@216 106 } else {
Chris@216 107 WavFileWriter writer(path,
Chris@216 108 getMainModel()->getSampleRate(),
Chris@216 109 getMainModel()->getChannelCount());
Chris@216 110 MultiSelection ms = m_viewManager->getSelection();
Chris@216 111 if (!ms.getSelections().empty()) {
Chris@216 112 writer.writeModel(getMainModel(), &ms);
Chris@216 113 } else {
Chris@216 114 writer.writeModel(getMainModel());
Chris@216 115 }
Chris@216 116 }
Chris@216 117 }
Chris@216 118 }
Chris@216 119
Chris@216 120 } else if (message.getMethod() == "jump" ||
Chris@216 121 message.getMethod() == "play") {
Chris@216 122
Chris@216 123 if (getMainModel()) {
Chris@216 124
Chris@216 125 unsigned long frame = m_viewManager->getPlaybackFrame();
Chris@216 126 bool selection = false;
Chris@216 127 bool play = (message.getMethod() == "play");
Chris@216 128
Chris@216 129 if (message.getArgCount() == 1) {
Chris@216 130
Chris@216 131 if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 132 message.getArg(0).toString() == "selection") {
Chris@216 133
Chris@216 134 selection = true;
Chris@216 135
Chris@216 136 } else if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 137 message.getArg(0).toString() == "end") {
Chris@216 138
Chris@216 139 frame = getMainModel()->getEndFrame();
Chris@216 140
Chris@216 141 } else if (message.getArg(0).canConvert(QVariant::Double)) {
Chris@216 142
Chris@216 143 double time = message.getArg(0).toDouble();
Chris@216 144 if (time < 0.0) time = 0.0;
Chris@216 145
Chris@216 146 frame = lrint(time * getMainModel()->getSampleRate());
Chris@216 147 }
Chris@216 148 }
Chris@216 149
Chris@216 150 if (frame > getMainModel()->getEndFrame()) {
Chris@216 151 frame = getMainModel()->getEndFrame();
Chris@216 152 }
Chris@216 153
Chris@216 154 if (play) {
Chris@216 155 m_viewManager->setPlaySelectionMode(selection);
Chris@216 156 }
Chris@216 157
Chris@216 158 if (selection) {
Chris@216 159 MultiSelection::SelectionList sl = m_viewManager->getSelections();
Chris@216 160 if (!sl.empty()) {
Chris@216 161 frame = sl.begin()->getStartFrame();
Chris@216 162 }
Chris@216 163 }
Chris@216 164
Chris@216 165 m_viewManager->setPlaybackFrame(frame);
Chris@216 166
Chris@216 167 if (play && !m_playSource->isPlaying()) {
Chris@216 168 m_playSource->play(frame);
Chris@216 169 }
Chris@216 170 }
Chris@216 171
Chris@216 172 } else if (message.getMethod() == "stop") {
Chris@216 173
Chris@216 174 if (m_playSource->isPlaying()) m_playSource->stop();
Chris@216 175
Chris@216 176 } else if (message.getMethod() == "loop") {
Chris@216 177
Chris@216 178 if (message.getArgCount() == 1 &&
Chris@216 179 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 180
Chris@216 181 QString str = message.getArg(0).toString();
Chris@216 182 if (str == "on") {
Chris@216 183 m_viewManager->setPlayLoopMode(true);
Chris@216 184 } else if (str == "off") {
Chris@216 185 m_viewManager->setPlayLoopMode(false);
Chris@216 186 }
Chris@216 187 }
Chris@216 188
Chris@216 189 } else if (message.getMethod() == "solo") {
Chris@216 190
Chris@216 191 if (message.getArgCount() == 1 &&
Chris@216 192 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 193
Chris@216 194 QString str = message.getArg(0).toString();
Chris@216 195 if (str == "on") {
Chris@216 196 m_viewManager->setPlaySoloMode(true);
Chris@216 197 } else if (str == "off") {
Chris@216 198 m_viewManager->setPlaySoloMode(false);
Chris@216 199 }
Chris@216 200 }
Chris@216 201
Chris@216 202 } else if (message.getMethod() == "select" ||
Chris@216 203 message.getMethod() == "addselect") {
Chris@216 204
Chris@216 205 if (getMainModel()) {
Chris@216 206
Chris@216 207 int f0 = getMainModel()->getStartFrame();
Chris@216 208 int f1 = getMainModel()->getEndFrame();
Chris@216 209
Chris@216 210 bool done = false;
Chris@216 211
Chris@216 212 if (message.getArgCount() == 2 &&
Chris@216 213 message.getArg(0).canConvert(QVariant::Double) &&
Chris@216 214 message.getArg(1).canConvert(QVariant::Double)) {
Chris@216 215
Chris@216 216 double t0 = message.getArg(0).toDouble();
Chris@216 217 double t1 = message.getArg(1).toDouble();
Chris@216 218 if (t1 < t0) { double temp = t0; t0 = t1; t1 = temp; }
Chris@216 219 if (t0 < 0.0) t0 = 0.0;
Chris@216 220 if (t1 < 0.0) t1 = 0.0;
Chris@216 221
Chris@216 222 f0 = lrint(t0 * getMainModel()->getSampleRate());
Chris@216 223 f1 = lrint(t1 * getMainModel()->getSampleRate());
Chris@216 224
Chris@216 225 Pane *pane = m_paneStack->getCurrentPane();
Chris@216 226 Layer *layer = 0;
Chris@216 227 if (pane) layer = pane->getSelectedLayer();
Chris@216 228 if (layer) {
Chris@216 229 size_t resolution;
Chris@216 230 layer->snapToFeatureFrame(pane, f0, resolution,
Chris@216 231 Layer::SnapLeft);
Chris@216 232 layer->snapToFeatureFrame(pane, f1, resolution,
Chris@216 233 Layer::SnapRight);
Chris@216 234 }
Chris@216 235
Chris@216 236 } else if (message.getArgCount() == 1 &&
Chris@216 237 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 238
Chris@216 239 QString str = message.getArg(0).toString();
Chris@216 240 if (str == "none") {
Chris@216 241 m_viewManager->clearSelections();
Chris@216 242 done = true;
Chris@216 243 }
Chris@216 244 }
Chris@216 245
Chris@216 246 if (!done) {
Chris@216 247 if (message.getMethod() == "select") {
Chris@216 248 m_viewManager->setSelection(Selection(f0, f1));
Chris@216 249 } else {
Chris@216 250 m_viewManager->addSelection(Selection(f0, f1));
Chris@216 251 }
Chris@216 252 }
Chris@216 253 }
Chris@216 254
Chris@216 255 } else if (message.getMethod() == "add") {
Chris@216 256
Chris@216 257 if (getMainModel()) {
Chris@216 258
Chris@216 259 if (message.getArgCount() >= 1 &&
Chris@216 260 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 261
Chris@216 262 int channel = -1;
Chris@216 263 if (message.getArgCount() == 2 &&
Chris@216 264 message.getArg(0).canConvert(QVariant::Int)) {
Chris@216 265 channel = message.getArg(0).toInt();
Chris@216 266 if (channel < -1 ||
Chris@216 267 channel > int(getMainModel()->getChannelCount())) {
Chris@216 268 std::cerr << "WARNING: MainWindow::handleOSCMessage: channel "
Chris@216 269 << channel << " out of range" << std::endl;
Chris@216 270 channel = -1;
Chris@216 271 }
Chris@216 272 }
Chris@216 273
Chris@216 274 QString str = message.getArg(0).toString();
Chris@216 275
Chris@216 276 LayerFactory::LayerType type =
Chris@216 277 LayerFactory::getInstance()->getLayerTypeForName(str);
Chris@216 278
Chris@216 279 if (type == LayerFactory::UnknownLayer) {
Chris@216 280 std::cerr << "WARNING: MainWindow::handleOSCMessage: unknown layer "
Chris@216 281 << "type " << str.toStdString() << std::endl;
Chris@216 282 } else {
Chris@216 283
Chris@232 284 LayerConfiguration configuration(type,
Chris@232 285 getMainModel(),
Chris@232 286 channel);
Chris@216 287
Chris@216 288 addPane(configuration,
Chris@216 289 tr("Add %1 Pane")
Chris@216 290 .arg(LayerFactory::getInstance()->
Chris@216 291 getLayerPresentationName(type)));
Chris@216 292 }
Chris@216 293 }
Chris@216 294 }
Chris@216 295
Chris@216 296 } else if (message.getMethod() == "undo") {
Chris@216 297
Chris@216 298 CommandHistory::getInstance()->undo();
Chris@216 299
Chris@216 300 } else if (message.getMethod() == "redo") {
Chris@216 301
Chris@216 302 CommandHistory::getInstance()->redo();
Chris@216 303
Chris@216 304 } else if (message.getMethod() == "set") {
Chris@216 305
Chris@216 306 if (message.getArgCount() == 2 &&
Chris@216 307 message.getArg(0).canConvert(QVariant::String) &&
Chris@216 308 message.getArg(1).canConvert(QVariant::Double)) {
Chris@216 309
Chris@216 310 QString property = message.getArg(0).toString();
Chris@216 311 float value = (float)message.getArg(1).toDouble();
Chris@216 312
Chris@216 313 if (property == "gain") {
Chris@216 314 if (value < 0.0) value = 0.0;
Chris@216 315 m_fader->setValue(value);
Chris@216 316 if (m_playTarget) m_playTarget->setOutputGain(value);
Chris@216 317 } else if (property == "speedup") {
Chris@216 318 m_playSpeed->setMappedValue(value);
Chris@216 319 } else if (property == "overlays") {
Chris@216 320 if (value < 0.5) {
Chris@216 321 m_viewManager->setOverlayMode(ViewManager::NoOverlays);
Chris@216 322 } else if (value < 1.5) {
Chris@216 323 m_viewManager->setOverlayMode(ViewManager::MinimalOverlays);
Chris@216 324 } else if (value < 2.5) {
Chris@216 325 m_viewManager->setOverlayMode(ViewManager::StandardOverlays);
Chris@216 326 } else {
Chris@216 327 m_viewManager->setOverlayMode(ViewManager::AllOverlays);
Chris@216 328 }
Chris@216 329 } else if (property == "zoomwheels") {
Chris@216 330 m_viewManager->setZoomWheelsEnabled(value > 0.5);
Chris@216 331 } else if (property == "propertyboxes") {
Chris@216 332 bool toggle = ((value < 0.5) !=
Chris@216 333 (m_paneStack->getLayoutStyle() == PaneStack::NoPropertyStacks));
Chris@216 334 if (toggle) togglePropertyBoxes();
Chris@216 335 }
Chris@216 336
Chris@216 337 } else {
Chris@216 338 PropertyContainer *container = 0;
Chris@216 339 Pane *pane = m_paneStack->getCurrentPane();
Chris@216 340 if (pane &&
Chris@216 341 message.getArgCount() == 3 &&
Chris@216 342 message.getArg(0).canConvert(QVariant::String) &&
Chris@216 343 message.getArg(1).canConvert(QVariant::String) &&
Chris@216 344 message.getArg(2).canConvert(QVariant::String)) {
Chris@216 345 if (message.getArg(0).toString() == "pane") {
Chris@216 346 container = pane->getPropertyContainer(0);
Chris@216 347 } else if (message.getArg(0).toString() == "layer") {
Chris@216 348 container = pane->getSelectedLayer();
Chris@216 349 }
Chris@216 350 }
Chris@216 351 if (container) {
Chris@216 352 QString nameString = message.getArg(1).toString();
Chris@216 353 QString valueString = message.getArg(2).toString();
Chris@248 354 Command *c = container->getSetPropertyCommand
Chris@248 355 (nameString, valueString);
Chris@248 356 if (c) CommandHistory::getInstance()->addCommand(c, true, true);
Chris@216 357 }
Chris@216 358 }
Chris@216 359
Chris@216 360 } else if (message.getMethod() == "setcurrent") {
Chris@216 361
Chris@216 362 int paneIndex = -1, layerIndex = -1;
Chris@216 363 bool wantLayer = false;
Chris@216 364
Chris@216 365 if (message.getArgCount() >= 1 &&
Chris@216 366 message.getArg(0).canConvert(QVariant::Int)) {
Chris@216 367
Chris@216 368 paneIndex = message.getArg(0).toInt() - 1;
Chris@216 369
Chris@216 370 if (message.getArgCount() >= 2 &&
Chris@216 371 message.getArg(1).canConvert(QVariant::Int)) {
Chris@216 372 wantLayer = true;
Chris@216 373 layerIndex = message.getArg(1).toInt() - 1;
Chris@216 374 }
Chris@216 375 }
Chris@216 376
Chris@216 377 if (paneIndex >= 0 && paneIndex < m_paneStack->getPaneCount()) {
Chris@216 378 Pane *pane = m_paneStack->getPane(paneIndex);
Chris@216 379 m_paneStack->setCurrentPane(pane);
Chris@216 380 if (layerIndex >= 0 && layerIndex < pane->getLayerCount()) {
Chris@216 381 Layer *layer = pane->getLayer(layerIndex);
Chris@216 382 m_paneStack->setCurrentLayer(pane, layer);
Chris@216 383 } else if (wantLayer && layerIndex == -1) {
Chris@216 384 m_paneStack->setCurrentLayer(pane, 0);
Chris@216 385 }
Chris@216 386 }
Chris@216 387
Chris@216 388 } else if (message.getMethod() == "delete") {
Chris@216 389
Chris@216 390 if (message.getArgCount() == 1 &&
Chris@216 391 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 392
Chris@216 393 QString target = message.getArg(0).toString();
Chris@216 394
Chris@216 395 if (target == "pane") {
Chris@216 396
Chris@216 397 deleteCurrentPane();
Chris@216 398
Chris@216 399 } else if (target == "layer") {
Chris@216 400
Chris@216 401 deleteCurrentLayer();
Chris@216 402
Chris@216 403 } else {
Chris@216 404
Chris@216 405 std::cerr << "WARNING: MainWindow::handleOSCMessage: Unknown delete target " << target.toStdString() << std::endl;
Chris@216 406 }
Chris@216 407 }
Chris@216 408
Chris@216 409 } else if (message.getMethod() == "zoom") {
Chris@216 410
Chris@216 411 if (message.getArgCount() == 1) {
Chris@216 412 if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 413 message.getArg(0).toString() == "in") {
Chris@216 414 zoomIn();
Chris@216 415 } else if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 416 message.getArg(0).toString() == "out") {
Chris@216 417 zoomOut();
Chris@216 418 } else if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 419 message.getArg(0).toString() == "default") {
Chris@216 420 zoomDefault();
Chris@216 421 } else if (message.getArg(0).canConvert(QVariant::Double)) {
Chris@216 422 double level = message.getArg(0).toDouble();
Chris@216 423 Pane *currentPane = m_paneStack->getCurrentPane();
Chris@216 424 if (level < 1.0) level = 1.0;
Chris@216 425 if (currentPane) currentPane->setZoomLevel(lrint(level));
Chris@216 426 }
Chris@216 427 }
Chris@216 428
Chris@216 429 } else if (message.getMethod() == "zoomvertical") {
Chris@216 430
Chris@216 431 Pane *pane = m_paneStack->getCurrentPane();
Chris@216 432 Layer *layer = 0;
Chris@216 433 if (pane && pane->getLayerCount() > 0) {
Chris@216 434 layer = pane->getLayer(pane->getLayerCount() - 1);
Chris@216 435 }
Chris@216 436 int defaultStep = 0;
Chris@216 437 int steps = 0;
Chris@216 438 if (layer) {
Chris@216 439 steps = layer->getVerticalZoomSteps(defaultStep);
Chris@216 440 if (message.getArgCount() == 1 && steps > 0) {
Chris@216 441 if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 442 message.getArg(0).toString() == "in") {
Chris@216 443 int step = layer->getCurrentVerticalZoomStep() + 1;
Chris@216 444 if (step < steps) layer->setVerticalZoomStep(step);
Chris@216 445 } else if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 446 message.getArg(0).toString() == "out") {
Chris@216 447 int step = layer->getCurrentVerticalZoomStep() - 1;
Chris@216 448 if (step >= 0) layer->setVerticalZoomStep(step);
Chris@216 449 } else if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 450 message.getArg(0).toString() == "default") {
Chris@216 451 layer->setVerticalZoomStep(defaultStep);
Chris@216 452 }
Chris@216 453 } else if (message.getArgCount() == 2) {
Chris@216 454 if (message.getArg(0).canConvert(QVariant::Double) &&
Chris@216 455 message.getArg(1).canConvert(QVariant::Double)) {
Chris@216 456 double min = message.getArg(0).toDouble();
Chris@216 457 double max = message.getArg(1).toDouble();
Chris@216 458 layer->setDisplayExtents(min, max);
Chris@216 459 }
Chris@216 460 }
Chris@216 461 }
Chris@216 462
Chris@216 463 } else if (message.getMethod() == "quit") {
Chris@216 464
Chris@216 465 m_abandoning = true;
Chris@216 466 close();
Chris@216 467
Chris@216 468 } else if (message.getMethod() == "resize") {
Chris@216 469
Chris@216 470 if (message.getArgCount() == 2) {
Chris@216 471
Chris@216 472 int width = 0, height = 0;
Chris@216 473
Chris@216 474 if (message.getArg(1).canConvert(QVariant::Int)) {
Chris@216 475
Chris@216 476 height = message.getArg(1).toInt();
Chris@216 477
Chris@216 478 if (message.getArg(0).canConvert(QVariant::String) &&
Chris@216 479 message.getArg(0).toString() == "pane") {
Chris@216 480
Chris@216 481 Pane *pane = m_paneStack->getCurrentPane();
Chris@216 482 if (pane) pane->resize(pane->width(), height);
Chris@216 483
Chris@216 484 } else if (message.getArg(0).canConvert(QVariant::Int)) {
Chris@216 485
Chris@216 486 width = message.getArg(0).toInt();
Chris@216 487 resize(width, height);
Chris@216 488 }
Chris@216 489 }
Chris@216 490 }
Chris@216 491
Chris@216 492 } else if (message.getMethod() == "transform") {
Chris@216 493
Chris@216 494 Pane *pane = m_paneStack->getCurrentPane();
Chris@216 495
Chris@216 496 if (getMainModel() &&
Chris@216 497 pane &&
Chris@216 498 message.getArgCount() == 1 &&
Chris@216 499 message.getArg(0).canConvert(QVariant::String)) {
Chris@216 500
Chris@224 501 TransformId transformId = message.getArg(0).toString();
Chris@216 502
Chris@224 503 Transform transform = TransformFactory::getInstance()->
Chris@224 504 getDefaultTransformFor(transformId);
Chris@224 505
Chris@216 506 Layer *newLayer = m_document->createDerivedLayer
Chris@224 507 (transform, getMainModel());
Chris@216 508
Chris@216 509 if (newLayer) {
Chris@216 510 m_document->addLayerToView(pane, newLayer);
Chris@224 511 m_recentTransforms.add(transformId);
Chris@216 512 m_paneStack->setCurrentLayer(pane, newLayer);
Chris@216 513 }
Chris@216 514 }
Chris@216 515
Chris@216 516 } else {
Chris@216 517 std::cerr << "WARNING: MainWindow::handleOSCMessage: Unknown or unsupported "
Chris@216 518 << "method \"" << message.getMethod().toStdString()
Chris@216 519 << "\"" << std::endl;
Chris@216 520 }
Chris@216 521
Chris@216 522 }