comparison widgets/CSVFormatDialog.cpp @ 1323:8068a0bee550

Merge from branch import-audio-data
author Chris Cannam
date Wed, 12 Sep 2018 15:58:11 +0100
parents fbda05431ce0
children 0930a27ebea2
comparison
equal deleted inserted replaced
1316:c0d8356e274f 1323:8068a0bee550
2 2
3 /* 3 /*
4 Sonic Visualiser 4 Sonic Visualiser
5 An audio file viewer and annotation editor. 5 An audio file viewer and annotation editor.
6 Centre for Digital Music, Queen Mary, University of London. 6 Centre for Digital Music, Queen Mary, University of London.
7 This file copyright 2006 Chris Cannam. 7 This file copyright 2006-2018 Chris Cannam and QMUL.
8 8
9 This program is free software; you can redistribute it and/or 9 This program is free software; you can redistribute it and/or
10 modify it under the terms of the GNU General Public License as 10 modify it under the terms of the GNU General Public License as
11 published by the Free Software Foundation; either version 2 of the 11 published by the Free Software Foundation; either version 2 of the
12 License, or (at your option) any later version. See the file 12 License, or (at your option) any later version. See the file
46 46
47 QGridLayout *layout = new QGridLayout; 47 QGridLayout *layout = new QGridLayout;
48 48
49 int row = 0; 49 int row = 0;
50 50
51 layout->addWidget(new QLabel(tr("Please select the correct data format for this file.")), 51 layout->addWidget
52 row++, 0, 1, 4); 52 (new QLabel(tr("Please select the correct data format for this file.")),
53 row++, 0, 1, 4);
53 54
54 QFrame *exampleFrame = new QFrame; 55 QFrame *exampleFrame = new QFrame;
55 exampleFrame->setFrameStyle(QFrame::StyledPanel | QFrame::Sunken); 56 exampleFrame->setFrameStyle(QFrame::StyledPanel | QFrame::Sunken);
56 exampleFrame->setLineWidth(2); 57 exampleFrame->setLineWidth(2);
57 QGridLayout *exampleLayout = new QGridLayout; 58 QGridLayout *exampleLayout = new QGridLayout;
62 palette.setColor(QPalette::Window, palette.color(QPalette::Base)); 63 palette.setColor(QPalette::Window, palette.color(QPalette::Base));
63 exampleFrame->setPalette(palette); 64 exampleFrame->setPalette(palette);
64 65
65 QFont fp; 66 QFont fp;
66 fp.setPointSize(int(floor(fp.pointSize() * 0.9))); 67 fp.setPointSize(int(floor(fp.pointSize() * 0.9)));
67 // fp.setFixedPitch(true);
68 // fp.setStyleHint(QFont::TypeWriter);
69 // fp.setFamily("Monospaced");
70 68
71 int columns = format.getColumnCount(); 69 int columns = format.getColumnCount();
72 QList<QStringList> example = m_format.getExample(); 70 QList<QStringList> example = m_format.getExample();
73 71
74 for (int i = 0; i < columns; ++i) { 72 for (int i = 0; i < columns; ++i) {
75 73
76 QComboBox *cpc = new QComboBox; 74 QComboBox *cpc = new QComboBox;
77 m_columnPurposeCombos.push_back(cpc); 75 m_columnPurposeCombos.push_back(cpc);
78 exampleLayout->addWidget(cpc, 0, i); 76 exampleLayout->addWidget(cpc, 0, i);
79 connect(cpc, SIGNAL(activated(int)), this, SLOT(columnPurposeChanged(int))); 77 connect(cpc, SIGNAL(activated(int)), this, SLOT(columnPurposeChanged(int)));
80 78
81 if (i == m_maxDisplayCols && columns > i + 2) { 79 if (i == m_maxDisplayCols && columns > i + 2) {
82 m_fuzzyColumn = i; 80 m_fuzzyColumn = i;
81
83 cpc->addItem(tr("<ignore>")); 82 cpc->addItem(tr("<ignore>"));
84 cpc->addItem(tr("Values")); 83 cpc->addItem(tr("Values"));
85 cpc->setCurrentIndex 84 cpc->setCurrentIndex
86 (m_format.getColumnPurpose(i-1) == CSVFormat::ColumnUnknown ? 0 : 1); 85 (m_format.getColumnPurpose(i-1) ==
87 exampleLayout->addWidget(new QLabel(tr("(%1 more)").arg(columns - i)), 86 CSVFormat::ColumnUnknown ? 0 : 1);
88 1, i); 87
88 exampleLayout->addWidget
89 (new QLabel(tr("(%1 more)").arg(columns - i)), 1, i);
89 break; 90 break;
90 } 91 }
91 92
92 // NB must be in the same order as the CSVFormat::ColumnPurpose enum 93 // NB must be in the same order as the CSVFormat::ColumnPurpose enum
93 cpc->addItem(tr("<ignore>")); // ColumnUnknown 94 cpc->addItem(tr("<ignore>")); // ColumnUnknown
96 cpc->addItem(tr("Duration")); // ColumnDuration 97 cpc->addItem(tr("Duration")); // ColumnDuration
97 cpc->addItem(tr("Value")); // ColumnValue 98 cpc->addItem(tr("Value")); // ColumnValue
98 cpc->addItem(tr("Pitch")); // ColumnPitch 99 cpc->addItem(tr("Pitch")); // ColumnPitch
99 cpc->addItem(tr("Label")); // ColumnLabel 100 cpc->addItem(tr("Label")); // ColumnLabel
100 cpc->setCurrentIndex(int(m_format.getColumnPurpose(i))); 101 cpc->setCurrentIndex(int(m_format.getColumnPurpose(i)));
101 102
102 for (int j = 0; j < example.size() && j < 6; ++j) { 103 for (int j = 0; j < example.size() && j < 6; ++j) {
103 if (i >= example[j].size()) { 104 if (i >= example[j].size()) {
104 continue; 105 continue;
105 } 106 }
106 QLabel *label = new QLabel; 107 QLabel *label = new QLabel;
130 }; 131 };
131 132
132 for (auto &l: m_timingLabels) { 133 for (auto &l: m_timingLabels) {
133 m_timingTypeCombo->addItem(l.second); 134 m_timingTypeCombo->addItem(l.second);
134 } 135 }
135 136
136 layout->addWidget(m_timingTypeCombo, row++, 1, 1, 2); 137 layout->addWidget(m_timingTypeCombo, row++, 1, 1, 2);
137 138
138 connect(m_timingTypeCombo, SIGNAL(activated(int)), 139 connect(m_timingTypeCombo, SIGNAL(activated(int)),
139 this, SLOT(timingTypeChanged(int))); 140 this, SLOT(timingTypeChanged(int)));
140 141
141 m_initialTimingOption = TimingImplicit; 142 m_initialTimingOption = TimingImplicit;
142 if (m_format.getTimingType() == CSVFormat::ExplicitTiming) { 143 if (m_format.getTimingType() == CSVFormat::ExplicitTiming) {
143 switch (m_format.getTimeUnits()) { 144 switch (m_format.getTimeUnits()) {
144 case CSVFormat::TimeSeconds: 145 case CSVFormat::TimeSeconds:
145 m_initialTimingOption = TimingExplicitSeconds; break; 146 m_initialTimingOption = TimingExplicitSeconds; break;
150 case CSVFormat::TimeWindows: 151 case CSVFormat::TimeWindows:
151 m_initialTimingOption = TimingImplicit; break; 152 m_initialTimingOption = TimingImplicit; break;
152 } 153 }
153 } 154 }
154 m_timingTypeCombo->setCurrentIndex(int(m_initialTimingOption)); 155 m_timingTypeCombo->setCurrentIndex(int(m_initialTimingOption));
155 156
156 m_sampleRateLabel = new QLabel(tr("Audio sample rate (Hz):")); 157 m_sampleRateLabel = new QLabel(tr("Audio sample rate (Hz):"));
157 layout->addWidget(m_sampleRateLabel, row, 0); 158 layout->addWidget(m_sampleRateLabel, row, 0);
158 159
159 int sampleRates[] = { 160 int sampleRates[] = {
160 8000, 11025, 12000, 22050, 24000, 32000, 161 8000, 11025, 12000, 22050, 24000, 32000,
176 connect(m_sampleRateCombo, SIGNAL(editTextChanged(QString)), 177 connect(m_sampleRateCombo, SIGNAL(editTextChanged(QString)),
177 this, SLOT(sampleRateChanged(QString))); 178 this, SLOT(sampleRateChanged(QString)));
178 179
179 m_windowSizeLabel = new QLabel(tr("Frame increment between rows:")); 180 m_windowSizeLabel = new QLabel(tr("Frame increment between rows:"));
180 layout->addWidget(m_windowSizeLabel, row, 0); 181 layout->addWidget(m_windowSizeLabel, row, 0);
181 182
182 m_windowSizeCombo = new QComboBox; 183 m_windowSizeCombo = new QComboBox;
183 for (int i = 0; i <= 16; ++i) { 184 for (int i = 0; i <= 16; ++i) {
184 int value = 1 << i; 185 int value = 1 << i;
185 m_windowSizeCombo->addItem(QString("%1").arg(value)); 186 m_windowSizeCombo->addItem(QString("%1").arg(value));
186 if (value == int(m_format.getWindowSize())) { 187 if (value == int(m_format.getWindowSize())) {
187 m_windowSizeCombo->setCurrentIndex(i); 188 m_windowSizeCombo->setCurrentIndex(i);
188 } 189 }
189 } 190 }
190 m_windowSizeCombo->setEditable(true); 191 m_windowSizeCombo->setEditable(true);
191 192
192 layout->addWidget(m_windowSizeCombo, row++, 1); 193 layout->addWidget(m_windowSizeCombo, row++, 1);
193 connect(m_windowSizeCombo, SIGNAL(activated(QString)), 194 connect(m_windowSizeCombo, SIGNAL(activated(QString)),
194 this, SLOT(windowSizeChanged(QString))); 195 this, SLOT(windowSizeChanged(QString)));
195 connect(m_windowSizeCombo, SIGNAL(editTextChanged(QString)), 196 connect(m_windowSizeCombo, SIGNAL(editTextChanged(QString)),
196 this, SLOT(windowSizeChanged(QString))); 197 this, SLOT(windowSizeChanged(QString)));
223 } 224 }
224 225
225 void 226 void
226 CSVFormatDialog::updateModelLabel() 227 CSVFormatDialog::updateModelLabel()
227 { 228 {
229 if (!m_modelLabel) {
230 return;
231 }
232
228 LayerFactory *f = LayerFactory::getInstance(); 233 LayerFactory *f = LayerFactory::getInstance();
229 234
230 QString s; 235 QString s;
231 switch (m_format.getModelType()) { 236 switch (m_format.getModelType()) {
232 case CSVFormat::OneDimensionalModel: 237 case CSVFormat::OneDimensionalModel:
242 s = f->getLayerPresentationName(LayerFactory::Notes); 247 s = f->getLayerPresentationName(LayerFactory::Notes);
243 break; 248 break;
244 case CSVFormat::ThreeDimensionalModel: 249 case CSVFormat::ThreeDimensionalModel:
245 s = f->getLayerPresentationName(LayerFactory::Colour3DPlot); 250 s = f->getLayerPresentationName(LayerFactory::Colour3DPlot);
246 break; 251 break;
252 case CSVFormat::WaveFileModel:
253 s = f->getLayerPresentationName(LayerFactory::Waveform);
254 break;
247 } 255 }
248 256
249 m_modelLabel->setText("\n" + tr("Data will be displayed in a %1 layer.").arg(s)); 257 m_modelLabel->setText("\n" + tr("Data will be displayed in a %1 layer.")
258 .arg(s));
250 } 259 }
251 260
252 void 261 void
253 CSVFormatDialog::applyStartTimePurpose() 262 CSVFormatDialog::applyStartTimePurpose()
254 { 263 {
339 { 348 {
340 QObject *o = sender(); 349 QObject *o = sender();
341 QComboBox *cb = qobject_cast<QComboBox *>(o); 350 QComboBox *cb = qobject_cast<QComboBox *>(o);
342 if (!cb) return; 351 if (!cb) return;
343 352
353 // Ensure a consistent set of column purposes, in case of a
354 // situation where some combinations are contradictory. Only
355 // updates the UI, does not update the stored format record from
356 // the UI - that's the job of updateFormatFromDialog
357
344 CSVFormat::ColumnPurpose purpose = (CSVFormat::ColumnPurpose)p; 358 CSVFormat::ColumnPurpose purpose = (CSVFormat::ColumnPurpose)p;
345 359
346 bool haveStartTime = false; // so as to update timing type combo appropriately 360 bool haveStartTime = false; // so as to update timing type combo appropriately
347 361
348 // Ensure the column purpose combos are consistent with one 362 // Ensure the column purpose combos are consistent with one
410 } 424 }
411 425
412 updateFormatFromDialog(); 426 updateFormatFromDialog();
413 updateComboVisibility(); 427 updateComboVisibility();
414 } 428 }
415 429
416 void 430 void
417 CSVFormatDialog::updateFormatFromDialog() 431 CSVFormatDialog::updateFormatFromDialog()
418 { 432 {
419 switch (TimingOption(m_timingTypeCombo->currentIndex())) { 433 switch (TimingOption(m_timingTypeCombo->currentIndex())) {
420 434
421 case TimingExplicitSeconds: 435 case TimingExplicitSeconds:
422 m_format.setTimingType(CSVFormat::ExplicitTiming); 436 m_format.setTimingType(CSVFormat::ExplicitTiming);
423 m_format.setTimeUnits(CSVFormat::TimeSeconds); 437 m_format.setTimeUnits(CSVFormat::TimeSeconds);
424 break; 438 break;
425 439
426 case TimingExplicitMsec: 440 case TimingExplicitMsec:
427 m_format.setTimingType(CSVFormat::ExplicitTiming); 441 m_format.setTimingType(CSVFormat::ExplicitTiming);
428 m_format.setTimeUnits(CSVFormat::TimeMilliseconds); 442 m_format.setTimeUnits(CSVFormat::TimeMilliseconds);
429 break; 443 break;
430 444
431 case TimingExplicitSamples: 445 case TimingExplicitSamples:
432 m_format.setTimingType(CSVFormat::ExplicitTiming); 446 m_format.setTimingType(CSVFormat::ExplicitTiming);
433 m_format.setTimeUnits(CSVFormat::TimeAudioFrames); 447 m_format.setTimeUnits(CSVFormat::TimeAudioFrames);
434 break; 448 break;
435 449
436 case TimingImplicit: 450 case TimingImplicit:
437 m_format.setTimingType(CSVFormat::ImplicitTiming); 451 m_format.setTimingType(CSVFormat::ImplicitTiming);
438 m_format.setTimeUnits(CSVFormat::TimeWindows); 452 m_format.setTimeUnits(CSVFormat::TimeWindows);
439 break; 453 break;
440 } 454 }
441 455
442 bool haveStartTime = false; 456 bool haveStartTime = false;
443 bool haveDuration = false; 457 bool haveDuration = false;
444 bool havePitch = false; 458 bool havePitch = false;
445 int valueCount = 0; 459 int valueCount = 0;
446 460
447 for (int i = 0; i < m_columnPurposeCombos.size(); ++i) { 461 for (int i = 0; i < m_columnPurposeCombos.size(); ++i) {
448 462
449 QComboBox *thisCombo = m_columnPurposeCombos[i]; 463 QComboBox *thisCombo = m_columnPurposeCombos[i];
450 464
451 CSVFormat::ColumnPurpose purpose = (CSVFormat::ColumnPurpose) 465 CSVFormat::ColumnPurpose purpose =
452 (thisCombo->currentIndex()); 466 (CSVFormat::ColumnPurpose) (thisCombo->currentIndex());
453 467
454 if (i == m_fuzzyColumn) { 468 if (i == m_fuzzyColumn) {
455 for (int j = i; j < m_format.getColumnCount(); ++j) { 469 for (int j = i; j < m_format.getColumnCount(); ++j) {
456 if (purpose == CSVFormat::ColumnUnknown) { 470 if (purpose == CSVFormat::ColumnUnknown) {
457 m_format.setColumnPurpose(j, CSVFormat::ColumnUnknown); 471 m_format.setColumnPurpose(j, CSVFormat::ColumnUnknown);
458 } else { // Value 472 } else { // Value