Mercurial > hg > easaier-soundaccess
view sv/document/ESFileReader.cpp @ 225:3200ed3fc957
allow to save/restore filter settings in a session
author | lbajardsilogic |
---|---|
date | Wed, 13 Feb 2008 13:44:28 +0000 |
parents | 74d1b3bda5a3 |
children |
line wrap: on
line source
/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */ /* Sound Access EASAIER client application. Silogic 2007. Laure Bajard. 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 <QString> #include <QMessageBox> #include <QFileDialog> #include <QUrl> #include <iostream> #include "ESFileReader.h" #include "layer/Layer.h" #include "view/View.h" #include "base/PlayParameters.h" #include "base/PlayParameterRepository.h" #include "base/TempDirectory.h" #include "data/fileio/AudioFileReaderFactory.h" #include "data/model/WaveFileModel.h" #include "data/model/DenseThreeDimensionalModel.h" #include "data/model/SparseOneDimensionalModel.h" #include "data/model/SparseTimeValueModel.h" #include "data/model/NoteModel.h" #include "data/model/TextModel.h" #include "view/Pane.h" #include "document/Document.h" ESFileReader::ESFileReader(Document *document, ESFileReaderPaneCallback &callback) : QXmlDefaultHandler(), m_document(document), m_paneCallback(callback), m_currentPane(0), m_inView(false), m_inData(false), m_ok(false) {} void ESFileReader::parse(const QString &xmlData) { QXmlInputSource inputSource; inputSource.setData(xmlData); parse(inputSource); } void ESFileReader::parse(QXmlInputSource &inputSource) { QXmlSimpleReader reader; reader.setContentHandler(this); reader.setErrorHandler(this); m_ok = reader.parse(inputSource); } bool ESFileReader::isOK() { return m_ok; } ESFileReader::~ESFileReader() {} bool ESFileReader::startElement(const QString &, const QString &, const QString &qName, const QXmlAttributes &attributes) { QString name = qName.toLower(); bool ok = false; // Valid element names: // // easaiersession // data // easaierresources // audio // display // window // view // layer if (name == "easaiersession") { // nothing needed ok = true; } else if (name == "data") { // nothing needed m_inData = true; ok = true; } else if (name == "easaierresources") { // nothing needed ok = true; } else if (name == "audio") { QString filename = attributes.value("value"); m_document->setAudioSourceInfoFileName(filename); } else if (name == "filters") { // nothing needed ok = true; } else if (name == "filter") { // nothing needed ok = readFilter(attributes);; } else if (name == "display") { // nothing needed ok = true; } else if (name == "window") { ok = readWindow(attributes); } else if (name == "view") { m_inView = true; ok = readView(attributes); } else if (name == "layer") { ok = readLayer(attributes); } if (!ok) { std::cerr << "WARNING: Easaier Session-XML: Failed to completely process element \"" << name.toLocal8Bit().data() << "\"" << std::endl; } return true; } bool ESFileReader::characters(const QString &text) { return true; } bool ESFileReader::endElement(const QString &, const QString &, const QString &qName) { QString name = qName.toLower(); if (name == "data") { m_inData = false; } else if (name == "view") { m_inView = false; } return true; } bool ESFileReader::error(const QXmlParseException &exception) { m_errorString = QString("ERROR: Easaier Session-XML: %1 at line %2, column %3") .arg(exception.message()) .arg(exception.lineNumber()) .arg(exception.columnNumber()); std::cerr << m_errorString.toLocal8Bit().data() << std::endl; return QXmlDefaultHandler::error(exception); } bool ESFileReader::fatalError(const QXmlParseException &exception) { m_errorString = QString("FATAL ERROR: Easaier Session-XML: %1 at line %2, column %3") .arg(exception.message()) .arg(exception.lineNumber()) .arg(exception.columnNumber()); std::cerr << m_errorString.toLocal8Bit().data() << std::endl; return QXmlDefaultHandler::fatalError(exception); } #define READ_MANDATORY(TYPE, NAME, CONVERSION) \ TYPE NAME = attributes.value(#NAME).trimmed().CONVERSION(&ok); \ if (!ok) { \ std::cerr << "WARNING: Easaier Session-XML: Missing or invalid mandatory " #TYPE " attribute \"" #NAME "\"" << std::endl; \ return false; \ } bool ESFileReader::readWindow(const QXmlAttributes &attributes) { bool ok = false; READ_MANDATORY(int, width, toInt); READ_MANDATORY(int, height, toInt); m_paneCallback.setWindowSize(width, height); return true; } bool ESFileReader::readView(const QXmlAttributes &attributes) { QString type = attributes.value("type"); m_currentPane = 0; if (type != "pane") { std::cerr << "WARNING: Easaier session-XML: Unexpected view type \"" << type.toLocal8Bit().data() << "\"" << std::endl; return false; } m_currentPane = m_paneCallback.addPane(); if (!m_currentPane) { std::cerr << "WARNING: Easaier session-XML: Internal error: Failed to add pane!" << std::endl; return false; } bool ok = false; View *view = m_currentPane; // The view properties first READ_MANDATORY(size_t, centre, toUInt); READ_MANDATORY(size_t, zoom, toUInt); READ_MANDATORY(int, followPan, toInt); READ_MANDATORY(int, followZoom, toInt); QString tracking = attributes.value("tracking"); // Specify the follow modes before we set the actual values view->setFollowGlobalPan(followPan); view->setFollowGlobalZoom(followZoom); view->setPlaybackFollow(tracking == "scroll" ? PlaybackScrollContinuous : tracking == "page" ? PlaybackScrollPage : PlaybackIgnore); // Then set these values view->setCentreFrame(centre); view->setZoomLevel(zoom); // And pane properties READ_MANDATORY(int, centreLineVisible, toInt); m_currentPane->setCentreLineVisible(centreLineVisible); int height = attributes.value("height").toInt(&ok); if (ok) { m_currentPane->resize(m_currentPane->width(), height); } return true; } bool ESFileReader::readLayer(const QXmlAttributes &attributes) { QString type = attributes.value("type"); int id; bool ok = false; id = attributes.value("id").trimmed().toInt(&ok); if (!ok) { std::cerr << "WARNING: Easaier session-XML: No layer id for layer of type \"" << type.toLocal8Bit().data() << "\"" << std::endl; return false; } Layer *layer = 0; bool isNewLayer = false; // Layers are expected to be defined in layer elements in the data // section, and referred to in layer elements in the view // sections. So if we're in the data section, we expect this // layer not to exist already; if we're in the view section, we // expect it to exist. if (m_inData) { if (m_layers.find(id) != m_layers.end()) { std::cerr << "WARNING: Easaier session-XML: Ignoring duplicate layer id " << id << " in data section" << std::endl; return false; } layer = m_layers[id] = m_document->createLayer (LayerFactory::getInstance()->getLayerTypeForName(type)); if (layer) { m_layers[id] = layer; isNewLayer = true; } } else { if (!m_currentPane) { std::cerr << "WARNING: Easaier session-XML: No current pane for layer " << id << " in view section" << std::endl; return false; } if (m_layers.find(id) != m_layers.end()) { layer = m_layers[id]; } else { layer = m_document->createLayer(LayerFactory::getInstance()->getLayerTypeForName(type)); if (layer) { m_layers[id] = layer; isNewLayer = true; } } } if (!layer) { std::cerr << "WARNING: Easaier session-XML: Failed to add layer of type \"" << type.toLocal8Bit().data() << "\"" << std::endl; return false; } if (isNewLayer) { QString name = attributes.value("name"); layer->setObjectName(name); QString modelName = attributes.value("model"); int modelId = attributes.value("modelId").toInt(); layer->setModelName(modelName); layer->setModelId(modelId); layer->setProperties(attributes); } if (!m_inData && m_currentPane) { m_document->addLayerToView(m_currentPane, layer); } return true; } bool ESFileReader::readFilter(const QXmlAttributes &attributes) { QString name = attributes.value("groupname"); FilterStack *filterStack = m_document->getRealTimeFilterStack(); if (!filterStack) { std::cerr << "WARNING: Easaier session-XML: Failed to get filterStack \"" << name.toLocal8Bit().data() << "\"" << std::endl; return false; } Filter *curFilter = filterStack->findFilter(name); if (!curFilter) { std::cerr << "WARNING: Easaier session-XML: Failed to get filter \"" << name.toLocal8Bit().data() << "\"" << std::endl; return false; } curFilter->setProperties(attributes); return true; }