Exemplo n.º 1
0
BaseSqlTableModel::BaseSqlTableModel(QObject* pParent,
                                     TrackCollection* pTrackCollection,
                                     const char* settingsNamespace)
        : QAbstractTableModel(pParent),
          TrackModel(pTrackCollection->getDatabase(), settingsNamespace),
          m_pTrackCollection(pTrackCollection),
          m_trackDAO(pTrackCollection->getTrackDAO()),
          m_database(pTrackCollection->getDatabase()),
          m_previewDeckGroup(PlayerManager::groupForPreviewDeck(0)),
          m_bInitialized(false),
          m_currentSearch("") {
    connect(&PlayerInfo::instance(), SIGNAL(trackLoaded(QString, TrackPointer)),
            this, SLOT(trackLoaded(QString, TrackPointer)));
    connect(&m_trackDAO, SIGNAL(forceModelUpdate()),
            this, SLOT(select()));
    trackLoaded(m_previewDeckGroup, PlayerInfo::instance().getTrackInfo(m_previewDeckGroup));
}
Exemplo n.º 2
0
void CachingReaderWorker::loadTrack(const TrackPointer& pTrack) {
    //qDebug() << m_group << "CachingReaderWorker::loadTrack() lock acquired for load.";

    // Emit that a new track is loading, stops the current track
    emit(trackLoading());

    ReaderStatusUpdate status;
    status.status = TRACK_NOT_LOADED;

    QString filename = pTrack->getLocation();
    if (filename.isEmpty() || !pTrack->exists()) {
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_group << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", unlocked reader lock";
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be found.").arg(filename)));
        return;
    }

    Mixxx::AudioSourceConfig audioSrcCfg;
    audioSrcCfg.setChannelCount(CachingReaderChunk::kChannels);
    m_pAudioSource = openAudioSourceForReading(pTrack, audioSrcCfg);
    if (m_pAudioSource.isNull()) {
        m_maxReadableFrameIndex = Mixxx::AudioSource::getMinFrameIndex();
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_group << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", file invalid, unlocked reader lock";
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be loaded.").arg(filename)));
        return;
    }

    // Initially assume that the complete content offered by audio source
    // is available for reading. Later if read errors occur this value will
    // be decreased to avoid repeated reading of corrupt audio data.
    m_maxReadableFrameIndex = m_pAudioSource->getMaxFrameIndex();

    status.maxReadableFrameIndex = m_maxReadableFrameIndex;
    status.status = TRACK_LOADED;
    m_pReaderStatusFIFO->writeBlocking(&status, 1);

    // Clear the chunks to read list.
    CachingReaderChunkReadRequest request;
    while (m_pChunkReadRequestFIFO->read(&request, 1) == 1) {
        qDebug() << "Skipping read request for " << request.chunk->getIndex();
        status.status = CHUNK_READ_INVALID;
        status.chunk = request.chunk;
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
    }

    // Emit that the track is loaded.
    const SINT sampleCount =
            CachingReaderChunk::frames2samples(
                    m_pAudioSource->getFrameCount());
    emit(trackLoaded(pTrack, m_pAudioSource->getSamplingRate(), sampleCount));
}
Exemplo n.º 3
0
BaseSqlTableModel::BaseSqlTableModel(QObject* pParent,
                                     TrackCollection* pTrackCollection,
                                     const char* settingsNamespace)
        : QAbstractTableModel(pParent),
          TrackModel(pTrackCollection->getDatabase(), settingsNamespace),
          m_pTrackCollection(pTrackCollection),
          m_trackDAO(pTrackCollection->getTrackDAO()),
          m_database(pTrackCollection->getDatabase()),
          m_previewDeckGroup(PlayerManager::groupForPreviewDeck(0)),
          m_iPreviewDeckTrackId(-1),
          m_currentSearch("") {
    m_bInitialized = false;
    m_iSortColumn = 0;
    m_eSortOrder = Qt::AscendingOrder;
    connect(&PlayerInfo::instance(), SIGNAL(trackLoaded(QString, TrackPointer)),
            this, SLOT(trackLoaded(QString, TrackPointer)));
    trackLoaded(m_previewDeckGroup, PlayerInfo::instance().getTrackInfo(m_previewDeckGroup));
}
Exemplo n.º 4
0
void PlayerInfo::setTrackInfo(const QString& group, const TrackPointer& track) {
    QMutexLocker locker(&m_mutex);
    TrackPointer pOld = m_loadedTrackMap.value(group);
    if (pOld) {
        emit(trackUnloaded(group, pOld));
    }
    m_loadedTrackMap.insert(group, track);
    emit(trackLoaded(group, track));
}
Exemplo n.º 5
0
void CachingReaderWorker::loadTrack(const TrackPointer& pTrack) {
    //qDebug() << m_group << "CachingReaderWorker::loadTrack() lock acquired for load.";

    // Emit that a new track is loading, stops the current track
    emit(trackLoading());

    ReaderStatusUpdate status;
    status.status = TRACK_NOT_LOADED;
    status.chunk = NULL;
    status.trackFrameCount = 0;

    QString filename = pTrack->getLocation();

    if (filename.isEmpty() || !pTrack->exists()) {
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_group << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", unlocked reader lock";
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be found.").arg(filename)));
        return;
    }

    Mixxx::AudioSourceConfig audioSrcCfg;
    audioSrcCfg.channelCountHint = kChunkChannels;
    m_pAudioSource = openAudioSourceForReading(pTrack, audioSrcCfg);
    if (m_pAudioSource.isNull()) {
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_group << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", file invalid, unlocked reader lock";
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be loaded.").arg(filename)));
        return;
    }

    status.trackFrameCount = m_pAudioSource->getFrameCount();
    status.status = TRACK_LOADED;
    m_pReaderStatusFIFO->writeBlocking(&status, 1);

    // Clear the chunks to read list.
    ChunkReadRequest request;
    while (m_pChunkReadRequestFIFO->read(&request, 1) == 1) {
        qDebug() << "Skipping read request for " << request.chunk->chunk_number;
        status.status = CHUNK_READ_INVALID;
        status.chunk = request.chunk;
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
    }

    // Emit that the track is loaded.
    const SINT sampleCount =
            m_pAudioSource->getFrameCount() * kChunkChannels;
    emit(trackLoaded(pTrack, m_pAudioSource->getFrameRate(), sampleCount));
}
Exemplo n.º 6
0
void CachingReaderWorker::loadTrack(TrackPointer pTrack) {
    //qDebug() << m_pGroup << "CachingReaderWorker::loadTrack() lock acquired for load.";

    // Emit that a new track is loading, stops the current track
    emit(trackLoading());

    ReaderStatusUpdate status;
    status.status = TRACK_LOADED;
    status.chunk = NULL;
    status.trackNumSamples = 0;

    if (m_pCurrentSoundSource != NULL) {
        delete m_pCurrentSoundSource;
        m_pCurrentSoundSource = NULL;
    }
    m_iTrackNumSamples = 0;

    QString filename = pTrack->getLocation();

    if (filename.isEmpty() || !pTrack->exists()) {
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_pGroup << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", unlocked reader lock";
        status.status = TRACK_NOT_LOADED;
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be found.").arg(filename)));
        return;
    }

    m_pCurrentSoundSource = new SoundSourceProxy(pTrack);
    bool openSucceeded = (m_pCurrentSoundSource->open() == OK); //Open the song for reading
    unsigned int trackSampleRate = m_pCurrentSoundSource->getSampleRate();
    m_iTrackNumSamples = status.trackNumSamples =
            m_pCurrentSoundSource->length();

    if (!openSucceeded || m_iTrackNumSamples == 0 || trackSampleRate == 0) {
        // Must unlock before emitting to avoid deadlock
        qDebug() << m_pGroup << "CachingReaderWorker::loadTrack() load failed for\""
                 << filename << "\", file invalid, unlocked reader lock";
        status.status = TRACK_NOT_LOADED;
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
        emit(trackLoadFailed(
            pTrack, QString("The file '%1' could not be loaded.").arg(filename)));
        return;
    }

    m_pReaderStatusFIFO->writeBlocking(&status, 1);

    // Clear the chunks to read list.
    ChunkReadRequest request;
    while (m_pChunkReadRequestFIFO->read(&request, 1) == 1) {
        qDebug() << "Skipping read request for " << request.chunk->chunk_number;
        status.status = CHUNK_READ_INVALID;
        status.chunk = request.chunk;
        m_pReaderStatusFIFO->writeBlocking(&status, 1);
    }

    // Emit that the track is loaded.
    emit(trackLoaded(pTrack, trackSampleRate, m_iTrackNumSamples));
}
Exemplo n.º 7
0
// Create the temporary auto-DJ-crates table.
// Done the first time it's used, since the user might not even make
// use of this feature.
void AutoDJCratesDAO::createAutoDjCratesDatabase() {
    // If the use of tracks that haven't been played in a while has changed,
    // then the active-tracks view must be recreated.
    bool bUseIgnoreTime = (bool) m_pConfig->getValueString(
                              ConfigKey("[Auto DJ]", "UseIgnoreTime"), "0").toInt();
    if (m_bAutoDjCratesDbCreated) {
        if (m_bUseIgnoreTime != bUseIgnoreTime) {
            // Do all this in a single transaction.
            ScopedTransaction oTransaction(m_rDatabase);

            // Get rid of the old active-tracks view.
            QSqlQuery oQuery(m_rDatabase);
            oQuery.exec ("DROP VIEW IF EXISTS " AUTODJACTIVETRACKS_TABLE);
            if (!oQuery.exec()) {
                LOG_FAILED_QUERY(oQuery);
                return;
            }

            // Create the new active-tracks view.
            if (!createActiveTracksView (bUseIgnoreTime)) {
                return;
            }

            // Remember the new setting.
            m_bUseIgnoreTime = bUseIgnoreTime;

            // Commit these changes.
            oTransaction.commit();
        }
    } else {
        m_bUseIgnoreTime = bUseIgnoreTime;
    }

    // If this database has already been created, skip this.
    if (m_bAutoDjCratesDbCreated) {
        return;
    }

    // Do all of this in a single transaction.
    ScopedTransaction oTransaction(m_rDatabase);

    // The auto-DJ-crates table contains the track ID, the number of references
    // to that track ID in all of the auto-DJ crates, the number of times that
    // track has been played, and the number of references to the track in the
    // auto-DJ playlist (or in loaded decks).  It filters out tracks that have
    // been deleted from the database (i.e. "hidden" tracks).

    // Create an empty table.
    QSqlQuery oQuery(m_rDatabase);
    // CREATE TEMP TABLE temp_autodj_crates (track_id INTEGER UNIQUE, craterefs INTEGER, timesplayed INTEGER, autodjrefs INTEGER, lastplayed DATETIME);
    //oQuery.exec ("DROP TABLE IF EXISTS " AUTODJCRATES_TABLE);
    QString strQuery("CREATE TEMP TABLE " AUTODJCRATES_TABLE
                     " (" AUTODJCRATESTABLE_TRACKID " INTEGER UNIQUE, "
                     AUTODJCRATESTABLE_CRATEREFS " INTEGER, "
                     AUTODJCRATESTABLE_TIMESPLAYED " INTEGER, "
                     AUTODJCRATESTABLE_AUTODJREFS " INTEGER, "
                     AUTODJCRATESTABLE_LASTPLAYED " DATETIME)");
    oQuery.prepare(strQuery);
    if (!oQuery.exec()) {
        LOG_FAILED_QUERY(oQuery);
        return;
    }

    // Fill out the first three columns.
    // Supply default values for the last two.
    // INSERT INTO temp_autodj_crates (track_id, craterefs, timesplayed, autodjrefs, lastplayed) SELECT crate_tracks.track_id, COUNT (*), library.timesplayed, 0, "" FROM crate_tracks, library WHERE crate_tracks.crate_id IN (SELECT id FROM crates WHERE autodj = 1) AND crate_tracks.track_id = library.id AND library.mixxx_deleted = 0 GROUP BY crate_tracks.track_id, library.timesplayed;
    strQuery = QString("INSERT INTO " AUTODJCRATES_TABLE
                       " (" AUTODJCRATESTABLE_TRACKID ", " AUTODJCRATESTABLE_CRATEREFS ", "
                       AUTODJCRATESTABLE_TIMESPLAYED ", " AUTODJCRATESTABLE_AUTODJREFS ", "
                       AUTODJCRATESTABLE_LASTPLAYED ") SELECT " CRATE_TRACKS_TABLE
                       ".%1 , COUNT (*), " LIBRARY_TABLE ".%2, 0, \"\" FROM "
                       CRATE_TRACKS_TABLE ", " LIBRARY_TABLE " WHERE " CRATE_TRACKS_TABLE
                       ".%4 IN (SELECT %5 FROM " CRATE_TABLE " WHERE %6 = 1) AND "
                       CRATE_TRACKS_TABLE ".%1 = " LIBRARY_TABLE ".%7 AND " LIBRARY_TABLE
                       ".%3 == 0 GROUP BY " CRATE_TRACKS_TABLE ".%1, " LIBRARY_TABLE ".%2")
               .arg(CRATETRACKSTABLE_TRACKID, // %1
                    LIBRARYTABLE_TIMESPLAYED, // %2
                    LIBRARYTABLE_MIXXXDELETED, // %3
                    CRATETRACKSTABLE_CRATEID, // %4
                    CRATETABLE_ID, // %5
                    CRATETABLE_AUTODJ_SOURCE, // %6
                    LIBRARYTABLE_ID); // %7
    oQuery.prepare(strQuery);
    if (!oQuery.exec()) {
        LOG_FAILED_QUERY(oQuery);
        return;
    }

    // Fill out the number of auto-DJ-playlist references.
    if (!updateAutoDjPlaylistReferences()) {
        return;
    }

    // Fill out the last-played date/time.
    if (!updateLastPlayedDateTime()) {
        return;
    }

    // Create the active-tracks view.
    //oQuery.exec ("DROP VIEW IF EXISTS " AUTODJACTIVETRACKS_TABLE);
    if (!createActiveTracksView (m_bUseIgnoreTime)) {
        return;
    }

    // Make a list of the IDs of every set-log playlist.
    // SELECT id FROM Playlists WHERE hidden = 2;
    oQuery.prepare(QString("SELECT %1 FROM " PLAYLIST_TABLE " WHERE %2 = %3")
                   .arg(PLAYLISTTABLE_ID, // %1
                        PLAYLISTTABLE_HIDDEN, // %2
                        QString::number(PlaylistDAO::PLHT_SET_LOG))); // %3
    if (oQuery.exec()) {
        while (oQuery.next())
            m_lstSetLogPlaylistIds.append(oQuery.value(0).toInt());
    } else {
        LOG_FAILED_QUERY(oQuery);
        return;
    }

    // Now the auto-DJ crates database is initialized.
    // Externally-driven updates to the database from now on are driven by
    // signals.
    oTransaction.commit();

    // Be notified when a track is modified.
    // We only care when the number of times it's been played changes.
    connect(&m_rTrackDAO, SIGNAL(trackDirty(int)),
            this, SLOT(slotTrackDirty(int)));

    // Be notified when the status of crates changes.
    // We only care about the crates labeled as auto-DJ, and tracks added to,
    // and removed from, such crates.
    connect(&m_rCrateDAO, SIGNAL(added(int)),
            this, SLOT(slotCrateAdded(int)));
    connect(&m_rCrateDAO, SIGNAL(deleted(int)),
            this, SLOT(slotCrateDeleted(int)));
    connect(&m_rCrateDAO, SIGNAL(autoDjChanged(int,bool)),
            this, SLOT(slotCrateAutoDjChanged(int,bool)));
    connect(&m_rCrateDAO, SIGNAL(trackAdded(int,int)),
            this, SLOT(slotCrateTrackAdded(int,int)));
    connect(&m_rCrateDAO, SIGNAL(trackRemoved(int,int)),
            this, SLOT(slotCrateTrackRemoved(int,int)));

    // Be notified when playlists are added/removed.
    // We only care about set-log playlists.
    connect(&m_rPlaylistDAO, SIGNAL(added(int)),
            this, SLOT(slotPlaylistAdded(int)));
    connect(&m_rPlaylistDAO, SIGNAL(deleted(int)),
            this, SLOT(slotPlaylistDeleted(int)));

    // Be notified when tracks are added/removed from playlists.
    // We only care about the auto-DJ playlist and the set-log playlists.
    connect(&m_rPlaylistDAO, SIGNAL(trackAdded(int,int,int)),
            this, SLOT(slotPlaylistTrackAdded(int,int,int)));
    connect(&m_rPlaylistDAO, SIGNAL(trackRemoved(int,int,int)),
            this, SLOT(slotPlaylistTrackRemoved(int,int,int)));

    // Be notified when tracks are loaded to, or unloaded from, a deck.
    // These count as auto-DJ references, i.e. prevent the track from being
    // selected randomly.
    connect(&PlayerInfo::Instance(), SIGNAL(trackLoaded(QString,TrackPointer)),
            this, SLOT(slotPlayerInfoTrackLoaded(QString,TrackPointer)));
    connect(&PlayerInfo::Instance(),
            SIGNAL(trackUnloaded(QString,TrackPointer)),
            this, SLOT(slotPlayerInfoTrackUnloaded(QString,TrackPointer)));

    // Remember that the auto-DJ-crates database has been created.
    m_bAutoDjCratesDbCreated = true;
}
Exemplo n.º 8
0
BrowseTableModel::BrowseTableModel(QObject* parent,
                                   TrackCollection* pTrackCollection,
                                   RecordingManager* pRecordingManager)
        : TrackModel(pTrackCollection->database(),
                     "mixxx.db.model.browse"),
          QStandardItemModel(parent),
          m_pTrackCollection(pTrackCollection),
          m_pRecordingManager(pRecordingManager),
          m_previewDeckGroup(PlayerManager::groupForPreviewDeck(0)) {
    QStringList header_data;
    header_data.insert(COLUMN_PREVIEW, tr("Preview"));
    header_data.insert(COLUMN_FILENAME, tr("Filename"));
    header_data.insert(COLUMN_ARTIST, tr("Artist"));
    header_data.insert(COLUMN_TITLE, tr("Title"));
    header_data.insert(COLUMN_ALBUM, tr("Album"));
    header_data.insert(COLUMN_TRACK_NUMBER, tr("Track #"));
    header_data.insert(COLUMN_YEAR, tr("Year"));
    header_data.insert(COLUMN_GENRE, tr("Genre"));
    header_data.insert(COLUMN_COMPOSER, tr("Composer"));
    header_data.insert(COLUMN_COMMENT, tr("Comment"));
    header_data.insert(COLUMN_DURATION, tr("Duration"));
    header_data.insert(COLUMN_BPM, tr("BPM"));
    header_data.insert(COLUMN_KEY, tr("Key"));
    header_data.insert(COLUMN_TYPE, tr("Type"));
    header_data.insert(COLUMN_BITRATE, tr("Bitrate"));
    header_data.insert(COLUMN_REPLAYGAIN, tr("ReplayGain"));
    header_data.insert(COLUMN_LOCATION, tr("Location"));
    header_data.insert(COLUMN_ALBUMARTIST, tr("Album Artist"));
    header_data.insert(COLUMN_GROUPING, tr("Grouping"));
    header_data.insert(COLUMN_FILE_MODIFIED_TIME, tr("File Modified"));
    header_data.insert(COLUMN_FILE_CREATION_TIME, tr("File Created"));

    addSearchColumn(COLUMN_FILENAME);
    addSearchColumn(COLUMN_ARTIST);
    addSearchColumn(COLUMN_ALBUM);
    addSearchColumn(COLUMN_TITLE);
    addSearchColumn(COLUMN_GENRE);
    addSearchColumn(COLUMN_COMPOSER);
    addSearchColumn(COLUMN_KEY);
    addSearchColumn(COLUMN_COMMENT);
    addSearchColumn(COLUMN_ALBUMARTIST);
    addSearchColumn(COLUMN_GROUPING);
    addSearchColumn(COLUMN_FILE_MODIFIED_TIME);
    addSearchColumn(COLUMN_FILE_CREATION_TIME);

    setDefaultSort(COLUMN_FILENAME, Qt::AscendingOrder);

    setHorizontalHeaderLabels(header_data);
    // register the QList<T> as a metatype since we use QueuedConnection below
    qRegisterMetaType< QList< QList<QStandardItem*> > >(
        "QList< QList<QStandardItem*> >");
    qRegisterMetaType<BrowseTableModel*>("BrowseTableModel*");

    m_pBrowseThread = BrowseThread::getInstanceRef();
    connect(m_pBrowseThread.data(), SIGNAL(clearModel(BrowseTableModel*)),
            this, SLOT(slotClear(BrowseTableModel*)),
            Qt::QueuedConnection);

    connect(m_pBrowseThread.data(),
            SIGNAL(rowsAppended(const QList< QList<QStandardItem*> >&, BrowseTableModel*)),
            this,
            SLOT(slotInsert(const QList< QList<QStandardItem*> >&, BrowseTableModel*)),
            Qt::QueuedConnection);

    connect(&PlayerInfo::instance(), SIGNAL(trackLoaded(QString, TrackPointer)),
            this, SLOT(trackLoaded(QString, TrackPointer)));
    trackLoaded(m_previewDeckGroup, PlayerInfo::instance().getTrackInfo(m_previewDeckGroup));
}
Exemplo n.º 9
0
BaseTrackPlayer::BaseTrackPlayer(QObject* pParent,
                                 ConfigObject<ConfigValue>* pConfig,
                                 EngineMaster* pMixingEngine,
                                 EffectsManager* pEffectsManager,
                                 EngineChannel::ChannelOrientation defaultOrientation,
                                 QString group,
                                 bool defaultMaster,
                                 bool defaultHeadphones)
        : BasePlayer(pParent, group),
          m_pConfig(pConfig),
          m_pLoadedTrack(),
          m_pLowFilter(NULL),
          m_pMidFilter(NULL),
          m_pHighFilter(NULL),
          m_pLowFilterKill(NULL),
          m_pMidFilterKill(NULL),
          m_pHighFilterKill(NULL),
          m_replaygainPending(false) {
    m_pChannel = new EngineDeck(getGroup(), pConfig, pMixingEngine,
                                pEffectsManager, defaultOrientation);

    EngineBuffer* pEngineBuffer = m_pChannel->getEngineBuffer();
    pMixingEngine->addChannel(m_pChannel);

    // Set the routing option defaults for the master and headphone mixes.
    {
        ControlObject::set(ConfigKey(getGroup(), "master"), (double)defaultMaster);
        ControlObject::set(ConfigKey(getGroup(), "pfl"), (double)defaultHeadphones);
    }

    // Connect our signals and slots with the EngineBuffer's signals and
    // slots. This will let us know when the reader is done loading a track, and
    // let us request that the reader load a track.
    connect(this, SIGNAL(loadTrack(TrackPointer, bool)),
            pEngineBuffer, SLOT(slotLoadTrack(TrackPointer, bool)));
    connect(pEngineBuffer, SIGNAL(trackLoaded(TrackPointer)),
            this, SLOT(slotFinishLoading(TrackPointer)));
    connect(pEngineBuffer, SIGNAL(trackLoadFailed(TrackPointer, QString)),
            this, SLOT(slotLoadFailed(TrackPointer, QString)));
    connect(pEngineBuffer, SIGNAL(trackUnloaded(TrackPointer)),
            this, SLOT(slotUnloadTrack(TrackPointer)));

    // Get loop point control objects
    m_pLoopInPoint = new ControlObjectThread(
            getGroup(),"loop_start_position");
    m_pLoopOutPoint = new ControlObjectThread(
            getGroup(),"loop_end_position");

    // Duration of the current song, we create this one because nothing else does.
    m_pDuration = new ControlObject(ConfigKey(getGroup(), "duration"));

    // Waveform controls
    m_pWaveformZoom = new ControlPotmeter(ConfigKey(group, "waveform_zoom"),
                                          WaveformWidgetRenderer::s_waveformMinZoom,
                                          WaveformWidgetRenderer::s_waveformMaxZoom);
    m_pWaveformZoom->set(1.0);
    m_pWaveformZoom->setStepCount(WaveformWidgetRenderer::s_waveformMaxZoom -
            WaveformWidgetRenderer::s_waveformMinZoom);
    m_pWaveformZoom->setSmallStepCount(WaveformWidgetRenderer::s_waveformMaxZoom -
            WaveformWidgetRenderer::s_waveformMinZoom);

    m_pEndOfTrack = new ControlObject(ConfigKey(group, "end_of_track"));
    m_pEndOfTrack->set(0.);

    m_pPreGain = new ControlObjectSlave(ConfigKey(group, "pregain"));
    //BPM of the current song
    m_pBPM = new ControlObjectThread(group, "file_bpm");
    m_pKey = new ControlObjectThread(group, "file_key");
    m_pReplayGain = new ControlObjectThread(group, "replaygain");
    m_pPlay = new ControlObjectThread(group, "play");
    connect(m_pPlay, SIGNAL(valueChanged(double)),
            this, SLOT(slotPlayToggled(double)));
}
Exemplo n.º 10
0
void ClockControl::trackUnloaded(TrackPointer pTrack) {
    Q_UNUSED(pTrack)
    trackLoaded(TrackPointer());
}
Exemplo n.º 11
0
BaseTrackPlayer::BaseTrackPlayer(QObject* pParent,
                                 ConfigObject<ConfigValue>* pConfig,
                                 EngineMaster* pMixingEngine,
                                 EngineChannel::ChannelOrientation defaultOrientation,
                                 QString group,
                                 bool defaultMaster,
                                 bool defaultHeadphones) :
        BasePlayer(pParent, group),
        m_pConfig(pConfig),
        m_pLoadedTrack() {

    // Need to strdup the string because EngineChannel will save the pointer,
    // but we might get deleted before the EngineChannel. TODO(XXX)
    // pSafeGroupName is leaked. It's like 5 bytes so whatever.
    const char* pSafeGroupName = strdup(getGroup().toAscii().constData());

    m_pChannel = new EngineDeck(pSafeGroupName,
                                pConfig, defaultOrientation);

    EngineBuffer* pEngineBuffer = m_pChannel->getEngineBuffer();
    pMixingEngine->addChannel(m_pChannel);

    // Set the routing option defaults for the master and headphone mixes.
    {
        ControlObjectThreadMain* pMaster = new ControlObjectThreadMain(
                getGroup(), "master");
        pMaster->slotSet(defaultMaster);
        delete pMaster;

        ControlObjectThreadMain* pHeadphones = new ControlObjectThreadMain(
                getGroup(), "pfl");
        pHeadphones->slotSet(defaultHeadphones);
        delete pHeadphones;
    }

    // Connect our signals and slots with the EngineBuffer's signals and
    // slots. This will let us know when the reader is done loading a track, and
    // let us request that the reader load a track.
    connect(this, SIGNAL(loadTrack(TrackPointer, bool)),
            pEngineBuffer, SLOT(slotLoadTrack(TrackPointer, bool)));
    connect(pEngineBuffer, SIGNAL(trackLoaded(TrackPointer)),
            this, SLOT(slotFinishLoading(TrackPointer)));
    connect(pEngineBuffer, SIGNAL(trackLoadFailed(TrackPointer, QString)),
            this, SLOT(slotLoadFailed(TrackPointer, QString)));
    connect(pEngineBuffer, SIGNAL(trackUnloaded(TrackPointer)),
            this, SLOT(slotUnloadTrack(TrackPointer)));

    //Get cue point control object
    m_pCuePoint = new ControlObjectThreadMain(
            getGroup(),"cue_point");
    // Get loop point control objects
    m_pLoopInPoint = new ControlObjectThreadMain(
            getGroup(),"loop_start_position");
    m_pLoopOutPoint = new ControlObjectThreadMain(
            getGroup(),"loop_end_position");
    //Playback position within the currently loaded track (in this player).
    m_pPlayPosition = new ControlObjectThreadMain(
            getGroup(), "playposition");

    // Duration of the current song, we create this one because nothing else does.
    m_pDuration = new ControlObject(ConfigKey(getGroup(), "duration"));

    // Waveform controls
    m_pWaveformZoom = new ControlPotmeter(ConfigKey(group, "waveform_zoom"),
                                          WaveformWidgetRenderer::s_waveformMinZoom,
                                          WaveformWidgetRenderer::s_waveformMaxZoom);
    m_pWaveformZoom->set(1.0);
    m_pWaveformZoom->setStep(1.0);
    m_pWaveformZoom->setSmallStep(1.0);

    m_pEndOfTrack = new ControlObject(ConfigKey(group, "end_of_track"));
    m_pEndOfTrack->set(0.);

    //BPM of the current song
    m_pBPM = new ControlObjectThreadMain(group, "file_bpm");
    m_pReplayGain = new ControlObjectThreadMain(group, "replaygain");
    m_pPlay = new ControlObjectThreadMain(group, "play");
}
Exemplo n.º 12
0
BaseTrackPlayerImpl::BaseTrackPlayerImpl(QObject* pParent,
                                         UserSettingsPointer pConfig,
                                         EngineMaster* pMixingEngine,
                                         EffectsManager* pEffectsManager,
                                         VisualsManager* pVisualsManager,
                                         EngineChannel::ChannelOrientation defaultOrientation,
                                         const QString& group,
                                         bool defaultMaster,
                                         bool defaultHeadphones)
        : BaseTrackPlayer(pParent, group),
          m_pConfig(pConfig),
          m_pEngineMaster(pMixingEngine),
          m_pLoadedTrack(),
          m_replaygainPending(false) {
    ChannelHandleAndGroup channelGroup =
            pMixingEngine->registerChannelGroup(group);
    m_pChannel = new EngineDeck(channelGroup, pConfig, pMixingEngine,
                                pEffectsManager, defaultOrientation);

    m_pInputConfigured = std::make_unique<ControlProxy>(group, "input_configured", this);
    m_pPassthroughEnabled = std::make_unique<ControlProxy>(group, "passthrough", this);
    m_pPassthroughEnabled->connectValueChanged(this, &BaseTrackPlayerImpl::slotPassthroughEnabled);
#ifdef __VINYLCONTROL__
    m_pVinylControlEnabled = std::make_unique<ControlProxy>(group, "vinylcontrol_enabled", this);
    m_pVinylControlEnabled->connectValueChanged(this, &BaseTrackPlayerImpl::slotVinylControlEnabled);
    m_pVinylControlStatus = std::make_unique<ControlProxy>(group, "vinylcontrol_status", this);
#endif

    EngineBuffer* pEngineBuffer = m_pChannel->getEngineBuffer();
    pMixingEngine->addChannel(m_pChannel);

    // Set the routing option defaults for the master and headphone mixes.
    m_pChannel->setMaster(defaultMaster);
    m_pChannel->setPfl(defaultHeadphones);

    // Connect our signals and slots with the EngineBuffer's signals and
    // slots. This will let us know when the reader is done loading a track, and
    // let us request that the reader load a track.
    connect(pEngineBuffer, SIGNAL(trackLoaded(TrackPointer, TrackPointer)),
            this, SLOT(slotTrackLoaded(TrackPointer, TrackPointer)));
    connect(pEngineBuffer, SIGNAL(trackLoadFailed(TrackPointer, QString)),
            this, SLOT(slotLoadFailed(TrackPointer, QString)));

    // Get loop point control objects
    m_pLoopInPoint = std::make_unique<ControlProxy>(
            getGroup(), "loop_start_position", this);
    m_pLoopOutPoint = std::make_unique<ControlProxy>(
            getGroup(), "loop_end_position", this);

    // Duration of the current song, we create this one because nothing else does.
    m_pDuration = std::make_unique<ControlObject>(
        ConfigKey(getGroup(), "duration"));

    // Waveform controls
    // This acts somewhat like a ControlPotmeter, but the normal _up/_down methods
    // do not work properly with this CO.
    m_pWaveformZoom = std::make_unique<ControlObject>(
        ConfigKey(group, "waveform_zoom"));
    m_pWaveformZoom->connectValueChangeRequest(
        this, &BaseTrackPlayerImpl::slotWaveformZoomValueChangeRequest,
        Qt::DirectConnection);
    m_pWaveformZoom->set(1.0);
    m_pWaveformZoomUp = std::make_unique<ControlPushButton>(
        ConfigKey(group, "waveform_zoom_up"));
    connect(m_pWaveformZoomUp.get(), SIGNAL(valueChanged(double)),
            this, SLOT(slotWaveformZoomUp(double)));
    m_pWaveformZoomDown = std::make_unique<ControlPushButton>(
        ConfigKey(group, "waveform_zoom_down"));
    connect(m_pWaveformZoomDown.get(), SIGNAL(valueChanged(double)),
            this, SLOT(slotWaveformZoomDown(double)));
    m_pWaveformZoomSetDefault = std::make_unique<ControlPushButton>(
        ConfigKey(group, "waveform_zoom_set_default"));
    connect(m_pWaveformZoomSetDefault.get(), SIGNAL(valueChanged(double)),
            this, SLOT(slotWaveformZoomSetDefault(double)));

    m_pPreGain = std::make_unique<ControlProxy>(group, "pregain", this);
    // BPM of the current song
    m_pFileBPM = std::make_unique<ControlProxy>(group, "file_bpm", this);
    m_pKey = std::make_unique<ControlProxy>(group, "file_key", this);

    m_pReplayGain = std::make_unique<ControlProxy>(group, "replaygain", this);
    m_pPlay = std::make_unique<ControlProxy>(group, "play", this);
    m_pPlay->connectValueChanged(this, &BaseTrackPlayerImpl::slotPlayToggled);

    pVisualsManager->addDeck(group);
}