annotate data/model/NoteModel.h @ 316:3a6725f285d6

* Make RemoteFile far more pervasive, and use it for local files as well so that we can handle both transparently. Make it shallow copy with reference counting, so it can be used by value without having to worry about the cache file lifetime. Use RemoteFile for MainWindow file-open functions, etc
author Chris Cannam
date Thu, 18 Oct 2007 15:31:20 +0000
parents 70a232b1f12a
children 7a4bd2c8585c
rev   line source
Chris@147 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
Chris@147 2
Chris@147 3 /*
Chris@147 4 Sonic Visualiser
Chris@147 5 An audio file viewer and annotation editor.
Chris@147 6 Centre for Digital Music, Queen Mary, University of London.
Chris@147 7 This file copyright 2006 Chris Cannam.
Chris@147 8
Chris@147 9 This program is free software; you can redistribute it and/or
Chris@147 10 modify it under the terms of the GNU General Public License as
Chris@147 11 published by the Free Software Foundation; either version 2 of the
Chris@147 12 License, or (at your option) any later version. See the file
Chris@147 13 COPYING included with this distribution for more information.
Chris@147 14 */
Chris@147 15
Chris@147 16 #ifndef _NOTE_MODEL_H_
Chris@147 17 #define _NOTE_MODEL_H_
Chris@147 18
Chris@147 19 #include "SparseValueModel.h"
Chris@150 20 #include "base/PlayParameterRepository.h"
Chris@147 21 #include "base/RealTime.h"
Chris@147 22
Chris@147 23 /**
Chris@147 24 * Note type for use in a SparseModel or SparseValueModel. All we
Chris@147 25 * mean by a "note" is something that has an onset time, a single
Chris@147 26 * value, and a duration. Like other points, it can also have a
Chris@147 27 * label. With this point type, the model can be thought of as
Chris@147 28 * representing a simple MIDI-type piano roll, except that the y
Chris@147 29 * coordinates (values) do not have to be discrete integers.
Chris@147 30 */
Chris@147 31
Chris@147 32 struct Note
Chris@147 33 {
Chris@147 34 public:
Chris@147 35 Note(long _frame) : frame(_frame), value(0.0f), duration(0) { }
Chris@147 36 Note(long _frame, float _value, size_t _duration, QString _label) :
Chris@147 37 frame(_frame), value(_value), duration(_duration), label(_label) { }
Chris@147 38
Chris@147 39 int getDimensions() const { return 3; }
Chris@147 40
Chris@147 41 long frame;
Chris@147 42 float value;
Chris@147 43 size_t duration;
Chris@147 44 QString label;
Chris@147 45
Chris@314 46 void toXml(QTextStream &stream,
Chris@314 47 QString indent = "",
Chris@314 48 QString extraAttributes = "") const
Chris@147 49 {
Chris@314 50 stream <<
Chris@314 51 QString("%1<point frame=\"%2\" value=\"%3\" duration=\"%4\" label=\"%5\" %6/>\n")
Chris@147 52 .arg(indent).arg(frame).arg(value).arg(duration).arg(label).arg(extraAttributes);
Chris@147 53 }
Chris@147 54
Chris@147 55 QString toDelimitedDataString(QString delimiter, size_t sampleRate) const
Chris@147 56 {
Chris@147 57 QStringList list;
Chris@147 58 list << RealTime::frame2RealTime(frame, sampleRate).toString().c_str();
Chris@147 59 list << QString("%1").arg(value);
Chris@147 60 list << QString("%1").arg(duration);
Chris@147 61 list << label;
Chris@147 62 return list.join(delimiter);
Chris@147 63 }
Chris@147 64
Chris@147 65 struct Comparator {
Chris@147 66 bool operator()(const Note &p1,
Chris@147 67 const Note &p2) const {
Chris@147 68 if (p1.frame != p2.frame) return p1.frame < p2.frame;
Chris@147 69 if (p1.value != p2.value) return p1.value < p2.value;
Chris@147 70 if (p1.duration != p2.duration) return p1.duration < p2.duration;
Chris@147 71 return p1.label < p2.label;
Chris@147 72 }
Chris@147 73 };
Chris@147 74
Chris@147 75 struct OrderComparator {
Chris@147 76 bool operator()(const Note &p1,
Chris@147 77 const Note &p2) const {
Chris@147 78 return p1.frame < p2.frame;
Chris@147 79 }
Chris@147 80 };
Chris@147 81 };
Chris@147 82
Chris@147 83
Chris@147 84 class NoteModel : public SparseValueModel<Note>
Chris@147 85 {
Chris@147 86 public:
Chris@147 87 NoteModel(size_t sampleRate, size_t resolution,
Chris@256 88 bool notifyOnAdd = true) :
Chris@256 89 SparseValueModel<Note>(sampleRate, resolution,
Chris@256 90 notifyOnAdd),
Chris@256 91 m_valueQuantization(0)
Chris@256 92 {
Chris@256 93 PlayParameterRepository::getInstance()->addModel(this);
Chris@256 94 }
Chris@256 95
Chris@256 96 NoteModel(size_t sampleRate, size_t resolution,
Chris@147 97 float valueMinimum, float valueMaximum,
Chris@147 98 bool notifyOnAdd = true) :
Chris@147 99 SparseValueModel<Note>(sampleRate, resolution,
Chris@147 100 valueMinimum, valueMaximum,
Chris@147 101 notifyOnAdd),
Chris@147 102 m_valueQuantization(0)
Chris@147 103 {
Chris@147 104 PlayParameterRepository::getInstance()->addModel(this);
Chris@147 105 }
Chris@147 106
Chris@147 107 float getValueQuantization() const { return m_valueQuantization; }
Chris@147 108 void setValueQuantization(float q) { m_valueQuantization = q; }
Chris@147 109
Chris@147 110 /**
Chris@147 111 * Notes have a duration, so this returns all points that span any
Chris@147 112 * of the given range (as well as the usual additional few before
Chris@147 113 * and after). Consequently this can be very slow (optimised data
Chris@147 114 * structures still to be done!).
Chris@147 115 */
Chris@147 116 virtual PointList getPoints(long start, long end) const;
Chris@147 117
Chris@147 118 /**
Chris@147 119 * Notes have a duration, so this returns all points that span the
Chris@147 120 * given frame. Consequently this can be very slow (optimised
Chris@147 121 * data structures still to be done!).
Chris@147 122 */
Chris@147 123 virtual PointList getPoints(long frame) const;
Chris@147 124
Chris@288 125 virtual void toXml(QTextStream &out,
Chris@288 126 QString indent = "",
Chris@288 127 QString extraAttributes = "") const
Chris@147 128 {
Chris@314 129 SparseValueModel<Note>::toXml
Chris@288 130 (out,
Chris@288 131 indent,
Chris@147 132 QString("%1 valueQuantization=\"%2\"")
Chris@147 133 .arg(extraAttributes).arg(m_valueQuantization));
Chris@147 134 }
Chris@147 135
Chris@147 136 protected:
Chris@147 137 float m_valueQuantization;
Chris@147 138 };
Chris@147 139
Chris@147 140 #endif