mirror of
https://github.com/tomahawk-player/tomahawk.git
synced 2025-08-14 10:05:32 +02:00
* Advanced random mode keeps track of playback history and prevents songs from being played too often. This is a statistically correct random, not a natural random. This should also find a random track while huge amounts of a playlist are still about to be resolved.
This commit is contained in:
@@ -103,20 +103,54 @@ PlayableProxyModelPlaylistInterface::siblingItem( int itemsAway, bool readOnly )
|
|||||||
|
|
||||||
PlayableProxyModel* proxyModel = m_proxyModel.data();
|
PlayableProxyModel* proxyModel = m_proxyModel.data();
|
||||||
|
|
||||||
|
while ( m_shuffleHistory.count() >= proxyModel->rowCount() )
|
||||||
|
{
|
||||||
|
m_shuffleHistory.removeFirst();
|
||||||
|
}
|
||||||
|
|
||||||
QModelIndex idx = proxyModel->index( 0, 0 );
|
QModelIndex idx = proxyModel->index( 0, 0 );
|
||||||
if ( proxyModel->rowCount() )
|
if ( proxyModel->rowCount() )
|
||||||
{
|
{
|
||||||
if ( m_shuffled )
|
if ( m_shuffled )
|
||||||
{
|
{
|
||||||
// random mode is enabled
|
// random mode is enabled
|
||||||
// TODO come up with a clever random logic, that keeps track of previously played items
|
if ( m_shuffleCache.isValid() )
|
||||||
|
{
|
||||||
|
idx = m_shuffleCache;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
int safetyCounter = 0;
|
||||||
|
PlayableItem* item = 0;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
safetyCounter++;
|
||||||
idx = proxyModel->index( qrand() % proxyModel->rowCount(), 0 );
|
idx = proxyModel->index( qrand() % proxyModel->rowCount(), 0 );
|
||||||
|
item = proxyModel->itemFromIndex( proxyModel->mapToSource( idx ) );
|
||||||
|
}
|
||||||
|
while ( safetyCounter < proxyModel->rowCount() &&
|
||||||
|
( !item || !item->query()->playable() || m_shuffleHistory.contains( item->query() ) ) );
|
||||||
|
|
||||||
|
if ( item && item->query()->playable() )
|
||||||
|
{
|
||||||
|
if ( readOnly )
|
||||||
|
{
|
||||||
|
m_shuffleCache = idx;
|
||||||
|
tDebug( LOGVERBOSE ) << "Next shuffled PlaylistItem cached:" << item->query()->toString() << item->query()->results().at( 0 )->url()
|
||||||
|
<< "- after" << safetyCounter << "tries to find a track";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
tDebug() << Q_FUNC_INFO << "Error finding next shuffled playable track";
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else if ( proxyModel->currentIndex().isValid() )
|
else if ( proxyModel->currentIndex().isValid() )
|
||||||
{
|
{
|
||||||
|
// random mode is disabled
|
||||||
idx = proxyModel->currentIndex();
|
idx = proxyModel->currentIndex();
|
||||||
|
|
||||||
// random mode is disabled
|
|
||||||
if ( m_repeatMode != PlaylistModes::RepeatOne )
|
if ( m_repeatMode != PlaylistModes::RepeatOne )
|
||||||
{
|
{
|
||||||
// keep progressing through the playlist normally
|
// keep progressing through the playlist normally
|
||||||
@@ -146,9 +180,14 @@ PlayableProxyModelPlaylistInterface::siblingItem( int itemsAway, bool readOnly )
|
|||||||
PlayableItem* item = proxyModel->itemFromIndex( proxyModel->mapToSource( idx ) );
|
PlayableItem* item = proxyModel->itemFromIndex( proxyModel->mapToSource( idx ) );
|
||||||
if ( item && item->query()->playable() )
|
if ( item && item->query()->playable() )
|
||||||
{
|
{
|
||||||
qDebug() << "Next PlaylistItem found:" << item->query()->toString() << item->query()->results().at( 0 )->url();
|
tDebug( LOGVERBOSE ) << "Next PlaylistItem found:" << item->query()->toString() << item->query()->results().at( 0 )->url();
|
||||||
if ( !readOnly )
|
if ( !readOnly )
|
||||||
|
{
|
||||||
proxyModel->setCurrentIndex( idx );
|
proxyModel->setCurrentIndex( idx );
|
||||||
|
m_shuffleHistory << item->query();
|
||||||
|
m_shuffleCache = QPersistentModelIndex();
|
||||||
|
}
|
||||||
|
|
||||||
return item->query()->results().at( 0 );
|
return item->query()->results().at( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -172,6 +211,7 @@ PlayableProxyModelPlaylistInterface::currentItem() const
|
|||||||
PlayableItem* item = proxyModel->itemFromIndex( proxyModel->mapToSource( proxyModel->currentIndex() ) );
|
PlayableItem* item = proxyModel->itemFromIndex( proxyModel->mapToSource( proxyModel->currentIndex() ) );
|
||||||
if ( item && !item->query().isNull() && item->query()->playable() )
|
if ( item && !item->query().isNull() && item->query()->playable() )
|
||||||
return item->query()->results().at( 0 );
|
return item->query()->results().at( 0 );
|
||||||
|
|
||||||
return Tomahawk::result_ptr();
|
return Tomahawk::result_ptr();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -59,8 +59,11 @@ public slots:
|
|||||||
|
|
||||||
protected:
|
protected:
|
||||||
QWeakPointer< PlayableProxyModel > m_proxyModel;
|
QWeakPointer< PlayableProxyModel > m_proxyModel;
|
||||||
|
|
||||||
PlaylistModes::RepeatMode m_repeatMode;
|
PlaylistModes::RepeatMode m_repeatMode;
|
||||||
bool m_shuffled;
|
bool m_shuffled;
|
||||||
|
QList< Tomahawk::query_ptr > m_shuffleHistory;
|
||||||
|
QPersistentModelIndex m_shuffleCache;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //ns
|
} //ns
|
||||||
|
Reference in New Issue
Block a user