annotate data/model/EditableDenseThreeDimensionalModel.cpp @ 282:d9319859a4cf tip

(none)
author benoitrigolleau
date Fri, 31 Oct 2008 11:00:24 +0000
parents fc9323a41f5a
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 #include "EditableDenseThreeDimensionalModel.h"
lbajardsilogic@0 17 #include "system/System.h"
lbajardsilogic@0 18
lbajardsilogic@0 19 #include <QTextStream>
lbajardsilogic@0 20
lbajardsilogic@0 21 #include <iostream>
lbajardsilogic@0 22
lbajardsilogic@0 23 #include <cmath>
lbajardsilogic@0 24
lbajardsilogic@0 25 EditableDenseThreeDimensionalModel::EditableDenseThreeDimensionalModel(size_t sampleRate,
lbajardsilogic@0 26 size_t resolution,
lbajardsilogic@0 27 size_t yBinCount,
lbajardsilogic@0 28 bool notifyOnAdd) :
lbajardsilogic@0 29 m_sampleRate(sampleRate),
lbajardsilogic@0 30 m_resolution(resolution),
lbajardsilogic@0 31 m_yBinCount(yBinCount),
lbajardsilogic@0 32 m_minimum(0.0),
lbajardsilogic@0 33 m_maximum(0.0),
lbajardsilogic@0 34 m_haveExtents(false),
lbajardsilogic@0 35 m_notifyOnAdd(notifyOnAdd),
lbajardsilogic@0 36 m_sinceLastNotifyMin(-1),
lbajardsilogic@0 37 m_sinceLastNotifyMax(-1),
lbajardsilogic@0 38 m_completion(100)
lbajardsilogic@0 39 {
lbajardsilogic@0 40 }
lbajardsilogic@0 41
lbajardsilogic@0 42 bool
lbajardsilogic@0 43 EditableDenseThreeDimensionalModel::isOK() const
lbajardsilogic@0 44 {
lbajardsilogic@0 45 return true;
lbajardsilogic@0 46 }
lbajardsilogic@0 47
lbajardsilogic@0 48 size_t
lbajardsilogic@0 49 EditableDenseThreeDimensionalModel::getSampleRate() const
lbajardsilogic@0 50 {
lbajardsilogic@0 51 return m_sampleRate;
lbajardsilogic@0 52 }
lbajardsilogic@0 53
lbajardsilogic@0 54 size_t
lbajardsilogic@0 55 EditableDenseThreeDimensionalModel::getStartFrame() const
lbajardsilogic@0 56 {
lbajardsilogic@0 57 return 0;
lbajardsilogic@0 58 }
lbajardsilogic@0 59
lbajardsilogic@0 60 size_t
lbajardsilogic@0 61 EditableDenseThreeDimensionalModel::getEndFrame() const
lbajardsilogic@0 62 {
lbajardsilogic@0 63 return m_resolution * m_data.size() + (m_resolution - 1);
lbajardsilogic@0 64 }
lbajardsilogic@0 65
lbajardsilogic@0 66 Model *
lbajardsilogic@0 67 EditableDenseThreeDimensionalModel::clone() const
lbajardsilogic@0 68 {
lbajardsilogic@0 69 EditableDenseThreeDimensionalModel *model =
lbajardsilogic@0 70 new EditableDenseThreeDimensionalModel
lbajardsilogic@0 71 (m_sampleRate, m_resolution, m_yBinCount);
lbajardsilogic@0 72
lbajardsilogic@0 73 model->m_minimum = m_minimum;
lbajardsilogic@0 74 model->m_maximum = m_maximum;
lbajardsilogic@0 75 model->m_haveExtents = m_haveExtents;
lbajardsilogic@0 76
lbajardsilogic@0 77 for (size_t i = 0; i < m_data.size(); ++i) {
lbajardsilogic@0 78 model->setColumn(i, m_data[i]);
lbajardsilogic@0 79 }
lbajardsilogic@0 80
lbajardsilogic@0 81 return model;
lbajardsilogic@0 82 }
lbajardsilogic@0 83
lbajardsilogic@0 84 size_t
lbajardsilogic@0 85 EditableDenseThreeDimensionalModel::getResolution() const
lbajardsilogic@0 86 {
lbajardsilogic@0 87 return m_resolution;
lbajardsilogic@0 88 }
lbajardsilogic@0 89
lbajardsilogic@0 90 void
lbajardsilogic@0 91 EditableDenseThreeDimensionalModel::setResolution(size_t sz)
lbajardsilogic@0 92 {
lbajardsilogic@0 93 m_resolution = sz;
lbajardsilogic@0 94 }
lbajardsilogic@0 95
lbajardsilogic@0 96 size_t
lbajardsilogic@0 97 EditableDenseThreeDimensionalModel::getWidth() const
lbajardsilogic@0 98 {
lbajardsilogic@0 99 return m_data.size();
lbajardsilogic@0 100 }
lbajardsilogic@0 101
lbajardsilogic@0 102 size_t
lbajardsilogic@0 103 EditableDenseThreeDimensionalModel::getHeight() const
lbajardsilogic@0 104 {
lbajardsilogic@0 105 return m_yBinCount;
lbajardsilogic@0 106 }
lbajardsilogic@0 107
lbajardsilogic@0 108 void
lbajardsilogic@0 109 EditableDenseThreeDimensionalModel::setHeight(size_t sz)
lbajardsilogic@0 110 {
lbajardsilogic@0 111 m_yBinCount = sz;
lbajardsilogic@0 112 }
lbajardsilogic@0 113
lbajardsilogic@0 114 float
lbajardsilogic@0 115 EditableDenseThreeDimensionalModel::getMinimumLevel() const
lbajardsilogic@0 116 {
lbajardsilogic@0 117 return m_minimum;
lbajardsilogic@0 118 }
lbajardsilogic@0 119
lbajardsilogic@0 120 void
lbajardsilogic@0 121 EditableDenseThreeDimensionalModel::setMinimumLevel(float level)
lbajardsilogic@0 122 {
lbajardsilogic@0 123 m_minimum = level;
lbajardsilogic@0 124 }
lbajardsilogic@0 125
lbajardsilogic@0 126 float
lbajardsilogic@0 127 EditableDenseThreeDimensionalModel::getMaximumLevel() const
lbajardsilogic@0 128 {
lbajardsilogic@0 129 return m_maximum;
lbajardsilogic@0 130 }
lbajardsilogic@0 131
lbajardsilogic@0 132 void
lbajardsilogic@0 133 EditableDenseThreeDimensionalModel::setMaximumLevel(float level)
lbajardsilogic@0 134 {
lbajardsilogic@0 135 m_maximum = level;
lbajardsilogic@0 136 }
lbajardsilogic@0 137
lbajardsilogic@0 138 void
lbajardsilogic@0 139 EditableDenseThreeDimensionalModel::getColumn(size_t index,
lbajardsilogic@0 140 Column &result) const
lbajardsilogic@0 141 {
lbajardsilogic@0 142 QMutexLocker locker(&m_mutex);
lbajardsilogic@0 143
lbajardsilogic@0 144 if (index < m_data.size()) {
lbajardsilogic@0 145 result = m_data[index];
lbajardsilogic@0 146 } else {
lbajardsilogic@0 147 result.clear();
lbajardsilogic@0 148 }
lbajardsilogic@0 149
lbajardsilogic@0 150 while (result.size() < m_yBinCount) result.push_back(m_minimum);
lbajardsilogic@0 151 }
lbajardsilogic@0 152
lbajardsilogic@0 153 float
lbajardsilogic@0 154 EditableDenseThreeDimensionalModel::getValueAt(size_t index, size_t n) const
lbajardsilogic@0 155 {
lbajardsilogic@0 156 QMutexLocker locker(&m_mutex);
lbajardsilogic@0 157
lbajardsilogic@0 158 if (index < m_data.size()) {
lbajardsilogic@0 159 const Column &s = m_data[index];
lbajardsilogic@0 160 // std::cerr << "index " << index << ", n " << n << ", res " << m_resolution << ", size " << s.size()
lbajardsilogic@0 161 // << std::endl;
lbajardsilogic@0 162 if (n < s.size()) return s[n];
lbajardsilogic@0 163 }
lbajardsilogic@0 164
lbajardsilogic@0 165 return m_minimum;
lbajardsilogic@0 166 }
lbajardsilogic@0 167
lbajardsilogic@0 168 void
lbajardsilogic@0 169 EditableDenseThreeDimensionalModel::setColumn(size_t index,
lbajardsilogic@0 170 const Column &values)
lbajardsilogic@0 171 {
lbajardsilogic@0 172 QMutexLocker locker(&m_mutex);
lbajardsilogic@0 173
lbajardsilogic@0 174 while (index >= m_data.size()) {
lbajardsilogic@0 175 m_data.push_back(Column());
lbajardsilogic@0 176 }
lbajardsilogic@0 177
lbajardsilogic@0 178 bool allChange = false;
lbajardsilogic@0 179
lbajardsilogic@0 180 for (size_t i = 0; i < values.size(); ++i) {
lbajardsilogic@0 181 float value = values[i];
lbajardsilogic@0 182 if (isnan(value) || isinf(value)) {
lbajardsilogic@0 183 continue;
lbajardsilogic@0 184 }
lbajardsilogic@0 185 if (!m_haveExtents || value < m_minimum) {
lbajardsilogic@0 186 m_minimum = value;
lbajardsilogic@0 187 allChange = true;
lbajardsilogic@0 188 }
lbajardsilogic@0 189 if (!m_haveExtents || value > m_maximum) {
lbajardsilogic@0 190 m_maximum = value;
lbajardsilogic@0 191 allChange = true;
lbajardsilogic@0 192 }
lbajardsilogic@0 193 m_haveExtents = true;
lbajardsilogic@0 194 }
lbajardsilogic@0 195
lbajardsilogic@0 196 m_data[index] = values;
lbajardsilogic@0 197
lbajardsilogic@0 198 long windowStart = index;
lbajardsilogic@0 199 windowStart *= m_resolution;
lbajardsilogic@0 200
lbajardsilogic@0 201 if (m_notifyOnAdd) {
lbajardsilogic@0 202 if (allChange) {
lbajardsilogic@0 203 emit modelChanged();
lbajardsilogic@0 204 } else {
lbajardsilogic@0 205 emit modelChanged(windowStart, windowStart + m_resolution);
lbajardsilogic@0 206 }
lbajardsilogic@0 207 } else {
lbajardsilogic@0 208 if (allChange) {
lbajardsilogic@0 209 m_sinceLastNotifyMin = -1;
lbajardsilogic@0 210 m_sinceLastNotifyMax = -1;
lbajardsilogic@0 211 emit modelChanged();
lbajardsilogic@0 212 } else {
lbajardsilogic@0 213 if (m_sinceLastNotifyMin == -1 ||
lbajardsilogic@0 214 windowStart < m_sinceLastNotifyMin) {
lbajardsilogic@0 215 m_sinceLastNotifyMin = windowStart;
lbajardsilogic@0 216 }
lbajardsilogic@0 217 if (m_sinceLastNotifyMax == -1 ||
lbajardsilogic@0 218 windowStart > m_sinceLastNotifyMax) {
lbajardsilogic@0 219 m_sinceLastNotifyMax = windowStart;
lbajardsilogic@0 220 }
lbajardsilogic@0 221 }
lbajardsilogic@0 222 }
lbajardsilogic@0 223 }
lbajardsilogic@0 224
lbajardsilogic@0 225 QString
lbajardsilogic@0 226 EditableDenseThreeDimensionalModel::getBinName(size_t n) const
lbajardsilogic@0 227 {
lbajardsilogic@0 228 if (m_binNames.size() > n) return m_binNames[n];
lbajardsilogic@0 229 else return "";
lbajardsilogic@0 230 }
lbajardsilogic@0 231
lbajardsilogic@0 232 void
lbajardsilogic@0 233 EditableDenseThreeDimensionalModel::setBinName(size_t n, QString name)
lbajardsilogic@0 234 {
lbajardsilogic@0 235 while (m_binNames.size() <= n) m_binNames.push_back("");
lbajardsilogic@0 236 m_binNames[n] = name;
lbajardsilogic@0 237 emit modelChanged();
lbajardsilogic@0 238 }
lbajardsilogic@0 239
lbajardsilogic@0 240 void
lbajardsilogic@0 241 EditableDenseThreeDimensionalModel::setBinNames(std::vector<QString> names)
lbajardsilogic@0 242 {
lbajardsilogic@0 243 m_binNames = names;
lbajardsilogic@0 244 emit modelChanged();
lbajardsilogic@0 245 }
lbajardsilogic@0 246
lbajardsilogic@0 247 void
lbajardsilogic@0 248 EditableDenseThreeDimensionalModel::setCompletion(int completion)
lbajardsilogic@0 249 {
lbajardsilogic@0 250 if (m_completion != completion) {
lbajardsilogic@0 251 m_completion = completion;
lbajardsilogic@0 252
lbajardsilogic@0 253 if (completion == 100) {
lbajardsilogic@0 254
lbajardsilogic@0 255 m_notifyOnAdd = true; // henceforth
lbajardsilogic@0 256 emit modelChanged();
lbajardsilogic@0 257
lbajardsilogic@0 258 } else if (!m_notifyOnAdd) {
lbajardsilogic@0 259
lbajardsilogic@0 260 if (m_sinceLastNotifyMin >= 0 &&
lbajardsilogic@0 261 m_sinceLastNotifyMax >= 0) {
lbajardsilogic@0 262 emit modelChanged(m_sinceLastNotifyMin,
lbajardsilogic@0 263 m_sinceLastNotifyMax + m_resolution);
lbajardsilogic@0 264 m_sinceLastNotifyMin = m_sinceLastNotifyMax = -1;
lbajardsilogic@0 265 } else {
lbajardsilogic@0 266 emit completionChanged();
lbajardsilogic@0 267 }
lbajardsilogic@0 268 } else {
lbajardsilogic@0 269 emit completionChanged();
lbajardsilogic@0 270 }
lbajardsilogic@0 271 }
lbajardsilogic@0 272 }
lbajardsilogic@0 273
lbajardsilogic@0 274 void
lbajardsilogic@0 275 EditableDenseThreeDimensionalModel::toXml(QTextStream &out,
lbajardsilogic@0 276 QString indent,
lbajardsilogic@0 277 QString extraAttributes) const
lbajardsilogic@0 278 {
lbajardsilogic@0 279 // For historical reasons we read and write "resolution" as "windowSize"
lbajardsilogic@0 280
lbajardsilogic@0 281 out << Model::toXmlString
lbajardsilogic@0 282 (indent, QString("type=\"dense\" dimensions=\"3\" windowSize=\"%1\" yBinCount=\"%2\" minimum=\"%3\" maximum=\"%4\" dataset=\"%5\" %6")
lbajardsilogic@0 283 .arg(m_resolution)
lbajardsilogic@0 284 .arg(m_yBinCount)
lbajardsilogic@0 285 .arg(m_minimum)
lbajardsilogic@0 286 .arg(m_maximum)
lbajardsilogic@0 287 .arg(getObjectExportId(&m_data))
lbajardsilogic@0 288 .arg(extraAttributes));
lbajardsilogic@0 289
lbajardsilogic@0 290 out << indent;
lbajardsilogic@0 291 out << QString("<dataset id=\"%1\" dimensions=\"3\" separator=\" \">\n")
lbajardsilogic@0 292 .arg(getObjectExportId(&m_data));
lbajardsilogic@0 293
lbajardsilogic@0 294 for (size_t i = 0; i < m_binNames.size(); ++i) {
lbajardsilogic@0 295 if (m_binNames[i] != "") {
lbajardsilogic@0 296 out << indent + " ";
lbajardsilogic@0 297 out << QString("<bin number=\"%1\" name=\"%2\"/>\n")
lbajardsilogic@0 298 .arg(i).arg(m_binNames[i]);
lbajardsilogic@0 299 }
lbajardsilogic@0 300 }
lbajardsilogic@0 301
lbajardsilogic@0 302 for (size_t i = 0; i < m_data.size(); ++i) {
lbajardsilogic@0 303 out << indent + " ";
lbajardsilogic@0 304 out << QString("<row n=\"%1\">").arg(i);
lbajardsilogic@0 305 for (size_t j = 0; j < m_data[i].size(); ++j) {
lbajardsilogic@0 306 if (j > 0) out << " ";
lbajardsilogic@0 307 out << m_data[i][j];
lbajardsilogic@0 308 }
lbajardsilogic@0 309 out << QString("</row>\n");
lbajardsilogic@0 310 }
lbajardsilogic@0 311
lbajardsilogic@0 312 out << indent + "</dataset>\n";
lbajardsilogic@0 313 }
lbajardsilogic@0 314
lbajardsilogic@0 315 QString
lbajardsilogic@0 316 EditableDenseThreeDimensionalModel::toXmlString(QString indent,
lbajardsilogic@0 317 QString extraAttributes) const
lbajardsilogic@0 318 {
lbajardsilogic@0 319 QString s;
lbajardsilogic@0 320
lbajardsilogic@0 321 {
lbajardsilogic@0 322 QTextStream out(&s);
lbajardsilogic@0 323 toXml(out, indent, extraAttributes);
lbajardsilogic@0 324 }
lbajardsilogic@0 325
lbajardsilogic@0 326 return s;
lbajardsilogic@0 327 }
lbajardsilogic@0 328