annotate sv/document/Document.h @ 282:d9319859a4cf tip

(none)
author benoitrigolleau
date Fri, 31 Oct 2008 11:00:24 +0000
parents 8bdd4752c2b2
children
rev   line source
lbajardsilogic@0 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
lbajardsilogic@0 2
lbajardsilogic@0 3 /*
lbajardsilogic@0 4 Sonic Visualiser
lbajardsilogic@0 5 An audio file viewer and annotation editor.
lbajardsilogic@0 6 Centre for Digital Music, Queen Mary, University of London.
lbajardsilogic@0 7 This file copyright 2006 Chris Cannam and QMUL.
lbajardsilogic@0 8
lbajardsilogic@0 9 This program is free software; you can redistribute it and/or
lbajardsilogic@0 10 modify it under the terms of the GNU General Public License as
lbajardsilogic@0 11 published by the Free Software Foundation; either version 2 of the
lbajardsilogic@0 12 License, or (at your option) any later version. See the file
lbajardsilogic@0 13 COPYING included with this distribution for more information.
lbajardsilogic@0 14 */
lbajardsilogic@0 15
lbajardsilogic@0 16 #ifndef _DOCUMENT_H_
lbajardsilogic@0 17 #define _DOCUMENT_H_
lbajardsilogic@0 18
lbajardsilogic@0 19 #include "layer/LayerFactory.h"
lbajardsilogic@0 20 #include "transform/Transform.h"
lbajardsilogic@0 21 #include "transform/PluginTransform.h"
lbajardsilogic@0 22 #include "base/Command.h"
lbajardsilogic@19 23 #include "data/model/AudioSourceInfoModel.h"
lbajardsilogic@79 24 #include "filter/RealTimeFilterFactory.h"
lbajardsilogic@79 25 #include "filter/FilterStack.h"
lbajardsilogic@0 26
lbajardsilogic@0 27 #include <map>
lbajardsilogic@0 28 #include <set>
lbajardsilogic@0 29
lbajardsilogic@0 30 class Model;
lbajardsilogic@0 31 class Layer;
lbajardsilogic@0 32 class View;
lbajardsilogic@0 33 class WaveFileModel;
lbajardsilogic@0 34
lbajardsilogic@0 35 /**
lbajardsilogic@0 36 * A Sonic Visualiser document consists of a set of data models, and
lbajardsilogic@0 37 * also the visualisation layers used to display them. Changes to the
lbajardsilogic@0 38 * layers and their layout need to be stored and managed in much the
lbajardsilogic@0 39 * same way as changes to the underlying data.
lbajardsilogic@0 40 *
lbajardsilogic@0 41 * The document manages:
lbajardsilogic@0 42 *
lbajardsilogic@0 43 * - A main data Model, which provides the underlying sample rate and
lbajardsilogic@0 44 * such like. This must be a WaveFileModel.
lbajardsilogic@0 45 *
lbajardsilogic@0 46 * - Any number of imported Model objects, which contain data without any
lbajardsilogic@0 47 * requirement to remember where the data came from or how to
lbajardsilogic@0 48 * regenerate it.
lbajardsilogic@0 49 *
lbajardsilogic@0 50 * - Any number of Model objects that were generated by a Transform
lbajardsilogic@0 51 * such as FeatureExtractionPluginTransform. For these, we also
lbajardsilogic@0 52 * record the source model and the name of the transform used to
lbajardsilogic@0 53 * generate the model so that we can regenerate it (potentially
lbajardsilogic@0 54 * from a different source) on demand.
lbajardsilogic@0 55 *
lbajardsilogic@0 56 * - A flat list of Layer objects. Elsewhere, the GUI may distribute these
lbajardsilogic@0 57 * across any number of View widgets. A layer may be viewable on more
lbajardsilogic@0 58 * than one view at once, in principle. A layer refers to one model,
lbajardsilogic@0 59 * but the same model can be in use in more than one layer.
lbajardsilogic@0 60 *
lbajardsilogic@0 61 * The document does *not* manage the existence or structure of Pane
lbajardsilogic@0 62 * and other view widgets. However, it does provide convenience
lbajardsilogic@0 63 * methods for reference-counted command-based management of the
lbajardsilogic@0 64 * association between layers and views (addLayerToView,
lbajardsilogic@0 65 * removeLayerFromView).
lbajardsilogic@0 66 */
lbajardsilogic@0 67
lbajardsilogic@0 68 class Document : public QObject,
lbajardsilogic@0 69 public XmlExportable
lbajardsilogic@0 70 {
lbajardsilogic@0 71 Q_OBJECT
lbajardsilogic@0 72
lbajardsilogic@0 73 public:
lbajardsilogic@0 74 Document();
lbajardsilogic@0 75 virtual ~Document();
lbajardsilogic@0 76
lbajardsilogic@175 77 void reset();
lbajardsilogic@175 78
lbajardsilogic@0 79 /**
lbajardsilogic@0 80 * Create and return a new layer of the given type, associated
lbajardsilogic@0 81 * with no model. The caller may set any model on this layer, but
lbajardsilogic@0 82 * the model must also be registered with the document via the
lbajardsilogic@0 83 * add-model methods below.
lbajardsilogic@0 84 */
lbajardsilogic@0 85 Layer *createLayer(LayerFactory::LayerType);
lbajardsilogic@0 86
lbajardsilogic@0 87 /**
lbajardsilogic@0 88 * Create and return a new layer of the given type, associated
lbajardsilogic@0 89 * with the current main model (if appropriate to the layer type).
lbajardsilogic@0 90 */
lbajardsilogic@0 91 Layer *createMainModelLayer(LayerFactory::LayerType);
lbajardsilogic@0 92
lbajardsilogic@0 93 /**
lbajardsilogic@0 94 * Create and return a new layer associated with the given model,
lbajardsilogic@0 95 * and register the model as an imported model.
lbajardsilogic@0 96 */
lbajardsilogic@0 97 Layer *createImportedLayer(Model *);
lbajardsilogic@0 98
lbajardsilogic@0 99 /**
lbajardsilogic@0 100 * Create and return a new layer of the given type, with an
lbajardsilogic@0 101 * appropriate empty model. If the given type is not one for
lbajardsilogic@0 102 * which an empty model can meaningfully be created, return 0.
lbajardsilogic@0 103 */
lbajardsilogic@0 104 Layer *createEmptyLayer(LayerFactory::LayerType);
lbajardsilogic@0 105
lbajardsilogic@0 106 /**
lbajardsilogic@0 107 * Create and return a new layer of the given type, associated
lbajardsilogic@0 108 * with the given transform name. This method does not run the
lbajardsilogic@0 109 * transform itself, nor create a model. The caller can safely
lbajardsilogic@0 110 * add a model to the layer later, but note that all models used
lbajardsilogic@0 111 * by a transform layer _must_ be registered with the document
lbajardsilogic@0 112 * using addDerivedModel below.
lbajardsilogic@0 113 */
lbajardsilogic@0 114 Layer *createDerivedLayer(LayerFactory::LayerType, TransformId);
lbajardsilogic@0 115
lbajardsilogic@0 116 /**
lbajardsilogic@0 117 * Create and return a suitable layer for the given transform,
lbajardsilogic@0 118 * running the transform and associating the resulting model with
lbajardsilogic@0 119 * the new layer.
lbajardsilogic@0 120 */
lbajardsilogic@0 121 Layer *createDerivedLayer(TransformId,
lbajardsilogic@0 122 Model *inputModel,
lbajardsilogic@0 123 const PluginTransform::ExecutionContext &context,
lbajardsilogic@0 124 QString configurationXml);
lbajardsilogic@0 125
lbajardsilogic@0 126 /**
lbajardsilogic@0 127 * Set the main model (the source for playback sample rate, etc)
lbajardsilogic@0 128 * to the given wave file model. This will regenerate any derived
lbajardsilogic@0 129 * models that were based on the previous main model.
lbajardsilogic@0 130 */
lbajardsilogic@0 131 void setMainModel(WaveFileModel *);
lbajardsilogic@0 132
lbajardsilogic@0 133 /**
lbajardsilogic@0 134 * Get the main model (the source for playback sample rate, etc).
lbajardsilogic@0 135 */
lbajardsilogic@0 136 WaveFileModel *getMainModel() { return m_mainModel; }
lbajardsilogic@0 137
lbajardsilogic@0 138 /**
lbajardsilogic@0 139 * Get the main model (the source for playback sample rate, etc).
lbajardsilogic@0 140 */
lbajardsilogic@0 141 const WaveFileModel *getMainModel() const { return m_mainModel; }
lbajardsilogic@0 142
lbajardsilogic@0 143 std::vector<Model *> getTransformInputModels();
lbajardsilogic@0 144
lbajardsilogic@19 145 inline void setAudioSourceInfoFileName(const QString& name){m_audioSourceInfoFileName = name;}
lbajardsilogic@19 146 inline QString getAudioSourceInfoFileName() const { return m_audioSourceInfoFileName;}
lbajardsilogic@19 147
lbajardsilogic@19 148 void setAudioSourceInfoModel(AudioSourceInfoModel *infoModel);
lbajardsilogic@19 149
lbajardsilogic@0 150 /**
lbajardsilogic@0 151 * Add a derived model associated with the given transform,
lbajardsilogic@0 152 * running the transform and returning the resulting model.
lbajardsilogic@0 153 */
lbajardsilogic@0 154 Model *addDerivedModel(TransformId transform,
lbajardsilogic@0 155 Model *inputModel,
lbajardsilogic@0 156 const PluginTransform::ExecutionContext &context,
lbajardsilogic@0 157 QString configurationXml);
lbajardsilogic@0 158
lbajardsilogic@0 159 /**
lbajardsilogic@0 160 * Add a derived model associated with the given transform. This
lbajardsilogic@0 161 * is necessary to register any derived model that was not created
lbajardsilogic@0 162 * by the document using createDerivedModel or createDerivedLayer.
lbajardsilogic@0 163 */
lbajardsilogic@0 164 void addDerivedModel(TransformId,
lbajardsilogic@0 165 Model *inputModel,
lbajardsilogic@0 166 const PluginTransform::ExecutionContext &context,
lbajardsilogic@0 167 Model *outputModelToAdd,
lbajardsilogic@0 168 QString configurationXml);
lbajardsilogic@0 169
lbajardsilogic@0 170 /**
lbajardsilogic@0 171 * Add an imported (non-derived, non-main) model. This is
lbajardsilogic@0 172 * necessary to register any imported model that is associated
lbajardsilogic@0 173 * with a layer.
lbajardsilogic@0 174 */
lbajardsilogic@0 175 void addImportedModel(Model *);
lbajardsilogic@0 176
lbajardsilogic@0 177 /**
lbajardsilogic@0 178 * Associate the given model with the given layer. The model must
lbajardsilogic@0 179 * have already been registered using one of the addXXModel
lbajardsilogic@0 180 * methods above.
lbajardsilogic@0 181 */
lbajardsilogic@0 182 void setModel(Layer *, Model *);
lbajardsilogic@0 183
lbajardsilogic@0 184 /**
lbajardsilogic@0 185 * Set the given layer to use the given channel of its model (-1
lbajardsilogic@0 186 * means all available channels).
lbajardsilogic@0 187 */
lbajardsilogic@0 188 void setChannel(Layer *, int);
lbajardsilogic@0 189
lbajardsilogic@0 190 /**
lbajardsilogic@0 191 * Add the given layer to the given view. If the layer is
lbajardsilogic@0 192 * intended to show a particular model, the model should normally
lbajardsilogic@0 193 * be set using setModel before this method is called.
lbajardsilogic@0 194 */
lbajardsilogic@0 195 void addLayerToView(View *, Layer *);
lbajardsilogic@0 196
lbajardsilogic@254 197 void addLayerToViewWithoutCommand(View *, Layer *);
lbajardsilogic@254 198
lbajardsilogic@254 199 /**
lbajardsilogic@0 200 * Remove the given layer from the given view.
lbajardsilogic@0 201 */
lbajardsilogic@0 202 void removeLayerFromView(View *, Layer *);
lbajardsilogic@254 203 void removeLayerFromViewWithoutCommand(View *, Layer *);
lbajardsilogic@0 204
lbajardsilogic@19 205 inline std::set<Layer *>& getLayers(){return m_layers;}
lbajardsilogic@19 206
lbajardsilogic@0 207 void toXml(QTextStream &, QString indent, QString extraAttributes) const;
lbajardsilogic@0 208 QString toXmlString(QString indent, QString extraAttributes) const;
lbajardsilogic@0 209
lbajardsilogic@19 210 QString toEasaierXmlString(QString indent, QString extraAttributes) const;
lbajardsilogic@19 211
lbajardsilogic@79 212 Filter *createFilter(RealTimeFilterFactory::FilterType);
lbajardsilogic@79 213
lbajardsilogic@79 214 FilterStack *getRealTimeFilterStack(){return m_filterStack;}
lbajardsilogic@79 215
lbajardsilogic@79 216 void removeFilter(QString &name);
lbajardsilogic@79 217 void removeAllFilters();
lbajardsilogic@79 218
lbajardsilogic@0 219 signals:
lbajardsilogic@0 220 void layerAdded(Layer *);
lbajardsilogic@0 221 void layerRemoved(Layer *);
lbajardsilogic@0 222 void layerAboutToBeDeleted(Layer *);
lbajardsilogic@0 223
lbajardsilogic@0 224 // Emitted when a layer is first added to a view, or when it is
lbajardsilogic@0 225 // last removed from a view
lbajardsilogic@0 226 void layerInAView(Layer *, bool);
lbajardsilogic@0 227
lbajardsilogic@0 228 void modelAdded(Model *);
lbajardsilogic@0 229 void mainModelChanged(WaveFileModel *); // emitted after modelAdded
lbajardsilogic@0 230 void modelAboutToBeDeleted(Model *);
lbajardsilogic@0 231
lbajardsilogic@0 232 void modelGenerationFailed(QString transformName);
lbajardsilogic@0 233 void modelRegenerationFailed(QString layerName, QString transformName);
lbajardsilogic@0 234
lbajardsilogic@19 235 void audioSourceInfoAdded(AudioSourceInfoModel *);
lbajardsilogic@19 236
lbajardsilogic@223 237 void newFilterAdded(PropertyContainer *);
lbajardsilogic@79 238 void filterRemoved(QString);
lbajardsilogic@79 239
lbajardsilogic@0 240 protected:
lbajardsilogic@0 241 void releaseModel(Model *model);
lbajardsilogic@0 242
lbajardsilogic@0 243 /**
lbajardsilogic@0 244 * Delete the given layer, and also its associated model if no
lbajardsilogic@0 245 * longer used by any other layer. In general, this should be the
lbajardsilogic@0 246 * only method used to delete layers -- doing so directly is a bit
lbajardsilogic@0 247 * of a social gaffe.
lbajardsilogic@0 248 */
lbajardsilogic@0 249 void deleteLayer(Layer *, bool force = false);
lbajardsilogic@0 250
lbajardsilogic@0 251 /*
lbajardsilogic@0 252 * Every model that is in use by a layer in the document must be
lbajardsilogic@0 253 * found in either m_mainModel, m_derivedModels or
lbajardsilogic@0 254 * m_importedModels. We own and control the lifespan of all of
lbajardsilogic@0 255 * these models.
lbajardsilogic@0 256 */
lbajardsilogic@0 257
lbajardsilogic@0 258 /**
lbajardsilogic@0 259 * The model that provides the underlying sample rate, etc. This
lbajardsilogic@0 260 * model is not reference counted for layers, and is not freed
lbajardsilogic@0 261 * unless it is replaced or the document is deleted.
lbajardsilogic@0 262 */
lbajardsilogic@0 263 WaveFileModel *m_mainModel;
lbajardsilogic@0 264
lbajardsilogic@19 265 /**
lbajardsilogic@19 266 * The name of the file on the easaier server that provides info on title, author...etc
lbajardsilogic@19 267 */
lbajardsilogic@19 268 QString m_audioSourceInfoFileName;
lbajardsilogic@19 269
lbajardsilogic@19 270 /**
lbajardsilogic@19 271 * The model that provides info on title, author...etc
lbajardsilogic@19 272 */
lbajardsilogic@19 273 AudioSourceInfoModel *m_audioSourceInfoModel;
lbajardsilogic@19 274
lbajardsilogic@0 275 struct ModelRecord
lbajardsilogic@0 276 {
lbajardsilogic@0 277 // Information associated with a non-main model. If this
lbajardsilogic@0 278 // model is derived from another, then source will be non-NULL
lbajardsilogic@0 279 // and the transform name will be set appropriately. If the
lbajardsilogic@0 280 // transform name is set but source is NULL, then there was a
lbajardsilogic@0 281 // transform involved but the (target) model has been modified
lbajardsilogic@0 282 // since being generated from it.
lbajardsilogic@0 283 const Model *source;
lbajardsilogic@0 284 TransformId transform;
lbajardsilogic@0 285 PluginTransform::ExecutionContext context;
lbajardsilogic@0 286 QString configurationXml;
lbajardsilogic@0 287
lbajardsilogic@0 288 // Count of the number of layers using this model.
lbajardsilogic@0 289 int refcount;
lbajardsilogic@0 290 };
lbajardsilogic@0 291
lbajardsilogic@0 292 typedef std::map<Model *, ModelRecord> ModelMap;
lbajardsilogic@0 293 ModelMap m_models;
lbajardsilogic@0 294
lbajardsilogic@0 295 class AddLayerCommand : public Command
lbajardsilogic@0 296 {
lbajardsilogic@0 297 public:
lbajardsilogic@0 298 AddLayerCommand(Document *d, View *view, Layer *layer);
lbajardsilogic@0 299 virtual ~AddLayerCommand();
lbajardsilogic@0 300
lbajardsilogic@0 301 virtual void execute();
lbajardsilogic@0 302 virtual void unexecute();
lbajardsilogic@0 303 virtual QString getName() const { return m_name; }
lbajardsilogic@0 304
lbajardsilogic@0 305 protected:
lbajardsilogic@0 306 Document *m_d;
lbajardsilogic@0 307 View *m_view; // I don't own this
lbajardsilogic@0 308 Layer *m_layer; // Document owns this, but I determine its lifespans
lbajardsilogic@0 309 QString m_name;
lbajardsilogic@0 310 bool m_added;
lbajardsilogic@0 311 };
lbajardsilogic@0 312
lbajardsilogic@0 313 class RemoveLayerCommand : public Command
lbajardsilogic@0 314 {
lbajardsilogic@0 315 public:
lbajardsilogic@0 316 RemoveLayerCommand(Document *d, View *view, Layer *layer);
lbajardsilogic@0 317 virtual ~RemoveLayerCommand();
lbajardsilogic@0 318
lbajardsilogic@0 319 virtual void execute();
lbajardsilogic@0 320 virtual void unexecute();
lbajardsilogic@0 321 virtual QString getName() const { return m_name; }
lbajardsilogic@0 322
lbajardsilogic@0 323 protected:
lbajardsilogic@0 324 Document *m_d;
lbajardsilogic@0 325 View *m_view; // I don't own this
lbajardsilogic@0 326 Layer *m_layer; // Document owns this, but I determine its lifespan
lbajardsilogic@0 327 QString m_name;
lbajardsilogic@0 328 bool m_added;
lbajardsilogic@0 329 };
lbajardsilogic@0 330
lbajardsilogic@0 331 typedef std::map<Layer *, std::set<View *> > LayerViewMap;
lbajardsilogic@0 332 LayerViewMap m_layerViewMap;
lbajardsilogic@0 333
lbajardsilogic@0 334 void addToLayerViewMap(Layer *, View *);
lbajardsilogic@0 335 void removeFromLayerViewMap(Layer *, View *);
lbajardsilogic@0 336
lbajardsilogic@0 337 QString getUniqueLayerName(QString candidate);
lbajardsilogic@0 338
lbajardsilogic@0 339 /**
lbajardsilogic@0 340 * And these are the layers. We also control the lifespans of
lbajardsilogic@0 341 * these (usually through the commands used to add and remove them).
lbajardsilogic@0 342 */
lbajardsilogic@0 343 typedef std::set<Layer *> LayerSet;
lbajardsilogic@0 344 LayerSet m_layers;
lbajardsilogic@79 345
lbajardsilogic@79 346 FilterStack *m_filterStack;
lbajardsilogic@0 347 };
lbajardsilogic@0 348
lbajardsilogic@0 349 #endif