Skip to content

Commit

Permalink
Get rid of Track object dependency (WIP)
Browse files Browse the repository at this point in the history
  • Loading branch information
Holzhaus committed Feb 16, 2020
1 parent 7f4f0ca commit 752d276
Show file tree
Hide file tree
Showing 5 changed files with 93 additions and 104 deletions.
69 changes: 17 additions & 52 deletions src/track/serato/markers.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -266,19 +266,29 @@ QByteArray SeratoMarkers::dump() const {
return data;
}

void SeratoMarkers::syncToTrackObject(Track* track, bool clearOtherValues) const {
qDebug() << "Syncing 'Serato Markers_' tag data to Track object..."
<< "(other values will be"
<< (clearOtherValues ? "cleared)" : "kept)");
QList<CuePointer> SeratoMarkers::getCues(int sampleRate) const {
qDebug() << "Reading cues from 'Serato Markers_' tag data..."

QMap<int, mixxx::SeratoMarkersEntryPointer> cueMap;
const double sampleRateKhz = sampleRate / 1000.0;
const double samples = sampleRateKhz * mixxx::kEngineChannelCount;
VERIFY_OR_DEBUG_ASSERT(samples != 0) {
qWarning() << "Failed to calculate samples factor, cannot read cues!";
return;
}

QList<CuePointer> cues;
int cueIndex = 0;
for (const auto& pEntry : m_entries) {
DEBUG_ASSERT(pEntry);
switch (pEntry->typeId()) {
case SeratoMarkersEntry::TypeId::Cue: {
cueMap.insert(cueIndex, pEntry);
CuePointer pCue(new Cue())

pCue->setType(Cue::Type::HotCue);
pCue->setHotCue(cueIndex);
pCue->setStartPosition(static_cast<double>(pEntry->getStartPosition()) * samples);
// TODO: Add support for hotcue colors

cueIndex++;
break;
}
Expand All @@ -288,52 +298,7 @@ void SeratoMarkers::syncToTrackObject(Track* track, bool clearOtherValues) const
}
}

const double sampleRateKhz = track->getSampleRate() / 1000.0;
const double samples = sampleRateKhz * mixxx::kEngineChannelCount;
VERIFY_OR_DEBUG_ASSERT(samples != 0) {
qWarning() << "Failed to calculate samples factor, cannot import cues!";
return;
}

// Update existing hotcues
for (const CuePointer& pCue : track->getCuePoints()) {
if (pCue->getType() != Cue::Type::HotCue) {
continue;
}

const mixxx::SeratoMarkersEntryPointer cueEntry = cueMap.take(pCue->getHotCue());
if (!cueEntry || !cueEntry->hasStartPosition()) {
if ((cueEntry && !cueEntry->hasStartPosition()) || clearOtherValues) {
// Delete cue if
// a) entry is present but has no position, or
// b) entry is not present and clearOtherValues is true
qDebug() << "Removed existing hotcue" << pCue->getHotCue() << pCue->getLabel() << "at" << pCue->getPosition();
track->removeCue(pCue);
}
continue;
}

pCue->setType(Cue::Type::HotCue);
pCue->setStartPosition(static_cast<double>(cueEntry->getStartPosition()) * samples);
if (clearOtherValues) {
// Reset label if clearOtherValues is set
pCue->setLabel("");
}
// TODO: Add support for hotcue colors
qDebug() << "Updated existing hotcue" << pCue->getHotCue() << pCue->getLabel() << "at" << pCue->getPosition();
}

// Add new cues
for (auto i = cueMap.constBegin(); i != cueMap.constEnd(); i++) {
CuePointer pCue = CuePointer(track->createAndAddCue());

pCue->setType(Cue::Type::HotCue);
pCue->setHotCue(i.key());
pCue->setStartPosition(static_cast<double>(i.value()->getStartPosition()) * samples);
// TODO: Add support for hotcue colors
qDebug() << "Added new hotcue" << pCue->getHotCue() << "at" << pCue->getPosition();
}
qDebug() << "Syncing 'Serato Markers_' tag data to Track object completed";
return cues;
}

} //namespace mixxx
6 changes: 2 additions & 4 deletions src/track/serato/markers.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,10 @@
#include <QList>
#include <memory>

#include "track/cue.h"
#include "util/color/rgbcolor.h"
#include "util/types.h"

// Forward declaration
class Track;

namespace mixxx {

class SeratoMarkersEntry;
Expand Down Expand Up @@ -158,7 +156,7 @@ class SeratoMarkers final {
m_trackColor = color;
}

void syncToTrackObject(Track* track, bool clearOtherValues = true) const;
QList<CuePointer> getCues(int sampleRate) const;

private:
QList<SeratoMarkersEntryPointer> m_entries;
Expand Down
83 changes: 42 additions & 41 deletions src/track/serato/markers2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -430,21 +430,31 @@ QByteArray SeratoMarkers2::dump() const {
return outerData.leftJustified(size, '\0');
}

void SeratoMarkers2::syncToTrackObject(Track* track) const {
qDebug() << "Syncing 'Serato Markers2' tag data to Track object...";
QList<CuePointer> SeratoMarkers2::getCues(int sampleRate) const {
qDebug() << "Reading cues from 'Serato Markers2' tag data...";

QMap<int, const mixxx::SeratoMarkers2CueEntry*> cueMap;
const double sampleRateKhz = sampleRate / 1000.0;
const double samples = sampleRateKhz * mixxx::kEngineChannelCount;
VERIFY_OR_DEBUG_ASSERT(samples != 0) {
qWarning() << "Failed to calculate samples factor, cannot read cues!";
return;
}

QList<CuePointer> cues;
for (auto& pEntry : m_entries) {
DEBUG_ASSERT(pEntry);
switch (pEntry->typeId()) {
case SeratoMarkers2Entry::TypeId::Cue: {
const mixxx::SeratoMarkers2CueEntry* pCueEntry = static_cast<mixxx::SeratoMarkers2CueEntry*>(pEntry.get());
cueMap.insert(pCueEntry->getIndex(), pCueEntry);
break;
}
case SeratoMarkers2Entry::TypeId::Bpmlock: {
const mixxx::SeratoMarkers2BpmlockEntry* pBpmlockEntry = static_cast<mixxx::SeratoMarkers2BpmlockEntry*>(pEntry.get());
track->setBpmLocked(pBpmlockEntry->isLocked());

CuePointer pCue = CuePointer(new Cue());
pCue->setType(Cue::Type::HotCue);
pCue->setHotCue(cueEntry->getIndex());
pCue->setStartPosition(static_cast<double>(cueEntry->getPosition()) * samples);
pCue->setLabel(cueEntry->getLabel());
// TODO: Add support for hotcue colors
cues.push_back(pCue);

break;
}
// TODO: Add support for COLOR/LOOP/FLIP
Expand All @@ -453,46 +463,37 @@ void SeratoMarkers2::syncToTrackObject(Track* track) const {
}
}

const double sampleRateKhz = track->getSampleRate() / 1000.0;
const double samples = sampleRateKhz * mixxx::kEngineChannelCount;
VERIFY_OR_DEBUG_ASSERT(samples != 0) {
qWarning() << "Failed to calculate samples factor, cannot import cues!";
return;
}
return cues;
}

RgbColor::optional_t SeratoMarkers2::getTrackColor() const {
qDebug() << "Reading track color from 'Serato Markers2' tag data...";

// Update existing hotcues
for (const CuePointer& pCue : track->getCuePoints()) {
if (pCue->getType() != Cue::Type::HotCue) {
for (auto& pEntry : m_entries) {
DEBUG_ASSERT(pEntry);
if (pEntry->typeId() != SeratoMarkers2Entry::TypeId::Color) {
continue;
}
const mixxx::SeratoMarkers2ColorEntry* pColorEntry = static_cast<mixxx::SeratoMarkers2ColorEntry*>(pEntry.get());
return RgbColor::optional(pColorEntry->getTrackColor());
}

return std::nullopt;
}

bool SeratoMarkers2::isBpmLocked() const {
qDebug() << "Reading bpmlock state from 'Serato Markers2' tag data...";

const mixxx::SeratoMarkers2CueEntry* cueEntry = cueMap.take(pCue->getHotCue());
if (!cueEntry) {
qWarning() << "Removed existing hotcue" << pCue->getHotCue() << pCue->getLabel() << "at" << pCue->getPosition();
track->removeCue(pCue);
for (auto& pEntry : m_entries) {
DEBUG_ASSERT(pEntry);
if (pEntry->typeId() != SeratoMarkers2Entry::TypeId::Bpmlock) {
continue;
}

pCue->setType(Cue::Type::HotCue);
pCue->setStartPosition(static_cast<double>(cueEntry->getPosition()) * samples);
pCue->setLabel(cueEntry->getLabel());
// TODO: Add support for hotcue colors
qWarning() << "Updated existing hotcue" << pCue->getHotCue() << pCue->getLabel() << "at" << pCue->getPosition();
const mixxx::SeratoMarkers2BpmlockEntry* pBpmlockEntry = static_cast<mixxx::SeratoMarkers2BpmlockEntry*>(pEntry.get());
return pBpmlockEntry->isLocked();
}

// Add new cues
for (auto cueEntry : cueMap.values()) {
DEBUG_ASSERT(cueEntry);
CuePointer pCue = CuePointer(track->createAndAddCue());

pCue->setType(Cue::Type::HotCue);
pCue->setHotCue(cueEntry->getIndex());
pCue->setStartPosition(static_cast<double>(cueEntry->getPosition()) * samples);
pCue->setLabel(cueEntry->getLabel());
// TODO: Add support for hotcue colors
qWarning() << "Added new hotcue" << pCue->getHotCue() << pCue->getLabel() << "at" << pCue->getPosition();
}
qDebug() << "Syncing 'Serato Markers2' tag data to Track object completed";
return false;
}

} //namespace mixxx
7 changes: 3 additions & 4 deletions src/track/serato/markers2.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,6 @@
#include "util/color/rgbcolor.h"
#include "util/types.h"

// forward declaration(s)
class Track;

namespace {
constexpr mixxx::RgbColor kDefaultTrackColor = mixxx::RgbColor(0xFF9999);
constexpr mixxx::RgbColor kDefaultCueColor = mixxx::RgbColor(0xCC0000);
Expand Down Expand Up @@ -422,7 +419,9 @@ class SeratoMarkers2 final {
m_entries = std::move(entries);
}

void syncToTrackObject(Track* track) const;
QList<CuePointer> getCues(int sampleRate) const;
RgbColor::optional_t getTrackColor() const;
bool isBpmLocked() const;

private:
int m_allocatedSize;
Expand Down
32 changes: 29 additions & 3 deletions src/track/serato/tags.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,39 @@

namespace mixxx {

void SeratoTags::syncToTrackObject(Track* track) const {
void SeratoTags::getCues(int sampleRate) const {
// Import "Serato Markers2" first, then overwrite values with those
// from "Serato Markers_". This is what Serato does too (i.e. if
// "Serato Markers_" and "Serato Markers2" contradict each other,
// Serato will use the values from "Serato Markers_").
m_seratoMarkers2.syncToTrackObject(track);
m_seratoMarkers.syncToTrackObject(track);

QMap<int, CuePointer> cueMap;
for (const CuePointer& pCue : m_seratoMarkers2.getCues(int sampleRate)) {
DEBUG_ASSERT(pCue);
int number = pCue->getHotCue()
DEBUG_ASSERT(number >= 0);
cueMap.insert(index, pCue);
};

for (const CuePointer& pCue : m_seratoMarkers.getCues(int sampleRate)) {
DEBUG_ASSERT(pCue);
int number = pCue->getHotCue()
DEBUG_ASSERT(number >= 0);

CuePoiner pUpdateCue = cueMap.value(number);
if (!pUpdateCue) {
cueMap.insert(index, pCue);
continue;
}

pUpdateCue->setType(pCue->getType());
pUpdateCue->setStartPosition(pCue->getStartPosition());
pUpdateCue->setEndPosition(pCue->getEndPosition());
pUpdateCue->setLabel(pCue->getLabel());
// TODO: Add support for cue colors
}

return cueMap.values();
}

#if 0
Expand Down

0 comments on commit 752d276

Please sign in to comment.