Chris@498: /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */ Chris@498: Chris@498: /* Chris@498: Sonic Visualiser Chris@498: An audio file viewer and annotation editor. Chris@498: Chris@498: Sonic Annotator Chris@498: A utility for batch feature extraction from audio files. Chris@498: Chris@498: Mark Levy, Chris Sutton and Chris Cannam, Queen Mary, University of London. Chris@498: Copyright 2007-2008 QMUL. Chris@498: Chris@498: This program is free software; you can redistribute it and/or Chris@498: modify it under the terms of the GNU General Public License as Chris@498: published by the Free Software Foundation; either version 2 of the Chris@498: License, or (at your option) any later version. See the file Chris@498: COPYING included with this distribution for more information. Chris@498: */ Chris@498: Chris@498: #include "CSVFeatureWriter.h" Chris@498: Chris@498: #include Chris@498: Chris@498: #include Chris@498: #include Chris@498: Chris@498: using namespace std; Chris@498: using namespace Vamp; Chris@498: Chris@498: CSVFeatureWriter::CSVFeatureWriter() : Chris@498: FileFeatureWriter(SupportOneFilePerTrackTransform | Chris@498: SupportOneFileTotal, Chris@498: "csv"), Chris@669: m_separator(","), Chris@669: m_sampleTiming(false) Chris@498: { Chris@498: } Chris@498: Chris@498: CSVFeatureWriter::~CSVFeatureWriter() Chris@498: { Chris@498: } Chris@498: Chris@498: CSVFeatureWriter::ParameterList Chris@498: CSVFeatureWriter::getSupportedParameters() const Chris@498: { Chris@498: ParameterList pl = FileFeatureWriter::getSupportedParameters(); Chris@498: Parameter p; Chris@498: Chris@498: p.name = "separator"; Chris@498: p.description = "Column separator for output. Default is \",\" (comma)."; Chris@498: p.hasArg = true; Chris@498: pl.push_back(p); Chris@669: Chris@669: p.name = "sample-timing"; Chris@669: p.description = "Show timings as sample frame counts instead of in seconds."; Chris@669: p.hasArg = false; Chris@669: pl.push_back(p); Chris@498: Chris@498: return pl; Chris@498: } Chris@498: Chris@498: void Chris@498: CSVFeatureWriter::setParameters(map ¶ms) Chris@498: { Chris@498: FileFeatureWriter::setParameters(params); Chris@498: Chris@690: SVDEBUG << "CSVFeatureWriter::setParameters" << endl; Chris@498: for (map::iterator i = params.begin(); Chris@498: i != params.end(); ++i) { Chris@498: cerr << i->first << " -> " << i->second << endl; Chris@498: if (i->first == "separator") { Chris@498: m_separator = i->second.c_str(); Chris@669: } else if (i->first == "sample-timing") { Chris@669: m_sampleTiming = true; Chris@498: } Chris@498: } Chris@498: } Chris@498: Chris@498: void Chris@498: CSVFeatureWriter::write(QString trackId, Chris@498: const Transform &transform, Chris@930: const Plugin::OutputDescriptor& , Chris@498: const Plugin::FeatureList& features, Chris@498: std::string summaryType) Chris@498: { Chris@498: // Select appropriate output file for our track/transform Chris@498: // combination Chris@498: Chris@498: QTextStream *sptr = getOutputStream(trackId, transform.getIdentifier()); Chris@604: if (!sptr) { Chris@604: throw FailedToOpenOutputStream(trackId, transform.getIdentifier()); Chris@604: } Chris@498: Chris@498: QTextStream &stream = *sptr; Chris@498: Chris@498: for (unsigned int i = 0; i < features.size(); ++i) { Chris@498: Chris@514: if (m_stdout || m_singleFileName != "") { Chris@514: if (trackId != m_prevPrintedTrackId) { Chris@514: stream << "\"" << trackId << "\"" << m_separator; Chris@514: m_prevPrintedTrackId = trackId; Chris@514: } else { Chris@514: stream << m_separator; Chris@514: } Chris@514: } Chris@514: Chris@669: if (m_sampleTiming) { Chris@498: Chris@669: stream << Vamp::RealTime::realTime2Frame Chris@669: (features[i].timestamp, transform.getSampleRate()); Chris@669: Chris@669: if (features[i].hasDuration) { Chris@669: stream << m_separator; Chris@669: stream << Vamp::RealTime::realTime2Frame Chris@669: (features[i].duration, transform.getSampleRate()); Chris@669: } Chris@669: Chris@669: } else { Chris@669: Chris@669: QString timestamp = features[i].timestamp.toString().c_str(); Chris@669: timestamp.replace(QRegExp("^ +"), ""); Chris@669: stream << timestamp; Chris@669: Chris@669: if (features[i].hasDuration) { Chris@669: QString duration = features[i].duration.toString().c_str(); Chris@669: duration.replace(QRegExp("^ +"), ""); Chris@669: stream << m_separator << duration; Chris@669: } Chris@669: } Chris@498: Chris@498: if (summaryType != "") { Chris@498: stream << m_separator << summaryType.c_str(); Chris@498: } Chris@498: Chris@498: for (unsigned int j = 0; j < features[i].values.size(); ++j) { Chris@498: stream << m_separator << features[i].values[j]; Chris@498: } Chris@498: Chris@514: if (features[i].label != "") { Chris@514: stream << m_separator << "\"" << features[i].label.c_str() << "\""; Chris@514: } Chris@514: Chris@498: stream << "\n"; Chris@498: } Chris@498: } Chris@498: Chris@498: