[prev in list] [next in list] [prev in thread] [next in thread] 

List:       kde-commits
Subject:    [Amarok] 599e1e9: Make MusicBrainz tagger return multiple results in
From:       Sergey Ivanov <123kash () gmail ! com>
Date:       2010-10-31 22:48:02
Message-ID: 20101031224802.7186CA60A4 () git ! kde ! org
[Download RAW message or body]

commit 599e1e972b5e61da9741b23e46afa61589aa46e6
branch master
Author: Sergey Ivanov <123kash@gmail.com>
Date:   Mon Nov 1 01:48:31 2010 +0300

    Make MusicBrainz tagger return multiple results in single-track search mode to \
let  user choose the right one.

diff --git a/src/dialogs/MusicBrainzTagger.cpp b/src/dialogs/MusicBrainzTagger.cpp
index d1e5d67..d327ea6 100644
--- a/src/dialogs/MusicBrainzTagger.cpp
+++ b/src/dialogs/MusicBrainzTagger.cpp
@@ -83,7 +83,7 @@ MusicBrainzTagger::init()
              SLOT( trackFound( const Meta::TrackPtr, const QVariantMap ) ) );
     connect( mb_finder, SIGNAL( done() ), SLOT( searchDone() ) );
     connect( mb_finder, SIGNAL( trackFound( const Meta::TrackPtr, const QVariantMap \
                ) ),
-             q_resultsModel, SLOT( trackFound( const Meta::TrackPtr, const \
QVariantMap ) ) ); +             q_resultsModel, SLOT( addTrack( const \
                Meta::TrackPtr, const QVariantMap ) ) );
     connect( mb_finder, SIGNAL( progressStep() ), SLOT( progressStep() ) );
     connect( ui->treeView_Result->header(), SIGNAL( sectionClicked( int ) ),
              q_resultsModel, SLOT( selectAll( int ) ) );
diff --git a/src/musicbrainz/MusicBrainzFinder.cpp \
b/src/musicbrainz/MusicBrainzFinder.cpp index bfe001c..82d31bd 100644
--- a/src/musicbrainz/MusicBrainzFinder.cpp
+++ b/src/musicbrainz/MusicBrainzFinder.cpp
@@ -127,6 +127,8 @@ MusicBrainzFinder::run( const Meta::TrackList &tracks )
             }
         m_requests.append( qMakePair( track, compileRequest( track ) ) );
     }
+
+    m_singleTrackSearch = tracks.count() == 1;
     _timer->start();
 }
 
@@ -290,7 +292,17 @@ MusicBrainzFinder::parsingDone( ThreadWeaver::Job *_parser )
                     }
 
                     float sim = float( s ) / maxPossibleScore;
-                    if( ( sim > maxSimilarity ) && ( sim > 0.6 ) )
+
+                    if( sim < 0.6 )
+                        continue;
+
+                    if( m_singleTrackSearch )
+                    {
+                        sendTrack( trackPtr, track );
+                        continue;
+                    }
+
+                    if( sim > maxSimilarity )
                     {
                         maxSimilarity = sim;
                         chosenTrack = track;
@@ -298,7 +310,7 @@ MusicBrainzFinder::parsingDone( ThreadWeaver::Job *_parser )
                 }
 
                 m_parsedMetaData.remove( trackPtr );
-                if( chosenTrack.isEmpty() )
+                if( chosenTrack.isEmpty() || m_singleTrackSearch )
                 {
                     parser->deleteLater();
                     checkDone();
@@ -307,7 +319,28 @@ MusicBrainzFinder::parsingDone( ThreadWeaver::Job *_parser )
                 curTrack = chosenTrack;
             }
             else
-                curTrack = parser->grabTrackByLength( trackPtr->length() );
+            {
+                if( m_singleTrackSearch )
+                {
+                    foreach( QString trackID, parser->tracks.keys() )
+                    {
+                        QVariantMap track = parser->grabTrackByID( trackID );
+                        if( track.contains( Meta::Field::SCORE ) )
+                        {
+                            if( track.value( Meta::Field::SCORE ).toInt() >= 50 )
+                                sendTrack( trackPtr, track );
+                        }
+                        else
+                            sendTrack( trackPtr, track );
+                    }
+
+                    parser->deleteLater();
+                    checkDone();
+                    return;
+                }
+                else
+                    curTrack = parser->grabTrackByLength( trackPtr->length() );
+            }
 
             sendTrack( trackPtr, curTrack );
         }
@@ -395,6 +428,9 @@ MusicBrainzFinder::guessMetadata( const Meta::TrackPtr &track )
 void
 MusicBrainzFinder::sendTrack( const Meta::TrackPtr track, const QVariantMap &info )
 {
+    if( info.isEmpty() )
+        return;
+
     QVariantMap tags = info;
     if( tags.contains( MusicBrainz::RELEASEID ) )
     {
diff --git a/src/musicbrainz/MusicBrainzFinder.h \
b/src/musicbrainz/MusicBrainzFinder.h index fdd44db..49c8f6b 100644
--- a/src/musicbrainz/MusicBrainzFinder.h
+++ b/src/musicbrainz/MusicBrainzFinder.h
@@ -48,7 +48,6 @@ class MusicBrainzFinder : public QObject
         void lookUpByPUID( const Meta::TrackPtr &track, const QString &puid );
 
     private slots:
-
         void sendNewRequest();
         void gotReply( QNetworkReply *reply );
         void authenticationRequest( QNetworkReply *reply, QAuthenticator \
*authenticator ); @@ -74,6 +73,8 @@ class MusicBrainzFinder : public QObject
         QString mb_username;
         QString mb_password;
 
+        bool m_singleTrackSearch;
+
         QMap < Meta::TrackPtr, QVariantMap > m_parsedMetaData;
 
         QNetworkAccessManager *net;
diff --git a/src/musicbrainz/MusicBrainzTagsModel.cpp \
b/src/musicbrainz/MusicBrainzTagsModel.cpp index 4b388b4..1bf7389 100644
--- a/src/musicbrainz/MusicBrainzTagsModel.cpp
+++ b/src/musicbrainz/MusicBrainzTagsModel.cpp
@@ -23,12 +23,92 @@
 #include "core/meta/support/MetaConstants.h"
 #include "core/meta/support/MetaUtility.h"
 
+MusciBrainzTagsItem::MusciBrainzTagsItem( Meta::TrackPtr track, const QVariantMap \
tags ) +                   : m_track( track )
+                   , m_data( tags )
+                   , m_checked( false )
+{
+}
+
+Qt::ItemFlags
+MusciBrainzTagsItem::flags()
+{
+    if( m_data.isEmpty() )
+        return Qt::NoItemFlags;
+
+    return Qt::ItemIsUserCheckable;
+}
+
+QVariant
+MusciBrainzTagsItem::data( int column )
+{
+    if( m_data.isEmpty() )
+        return QVariant();
+
+    switch( column )
+    {
+        case 1: return m_data.contains( Meta::Field::TITLE )
+                              ? m_data.value( Meta::Field::TITLE )
+                              : QVariant();
+        case 2: return m_data.contains( Meta::Field::ARTIST )
+                              ? m_data.value( Meta::Field::ARTIST )
+                              : QVariant();
+        case 3: return m_data.contains( Meta::Field::ALBUM )
+                              ? m_data.value( Meta::Field::ALBUM )
+                              : QVariant();
+        case 4: return m_data.contains( Meta::Field::ALBUMARTIST )
+                              ? m_data.value( Meta::Field::ALBUMARTIST )
+                              : QVariant();
+    }
+
+    return QVariant();
+}
+
+QVariantMap
+MusciBrainzTagsItem::data()
+{
+    return m_data;
+}
+
+void
+MusciBrainzTagsItem::setData( QVariantMap tags )
+{
+    m_data = tags;
+}
+
+bool
+MusciBrainzTagsItem::checked()
+{
+    return m_checked;
+}
+
+void
+MusciBrainzTagsItem::setChecked( bool checked )
+{
+    if( m_data.isEmpty() )
+        return;
+    m_checked = checked;
+}
+
+Meta::TrackPtr
+MusciBrainzTagsItem::track()
+{
+    return m_track;
+}
+
+
 MusicBrainzTagsModel::MusicBrainzTagsModel( Meta::TrackList tracks, QObject* parent)
-                    : QAbstractItemModel(parent)
-                    , m_tracks( tracks )
+                    : QAbstractItemModel( parent )
 {
-    for( int i = 0; i < m_tracks.count(); i++ )
-        m_tracksToSave.append( Qt::Unchecked );
+    if( tracks.count() == 1 )
+    {
+        m_singleTrackMode = true;
+        return;
+    }
+
+    m_singleTrackMode = false;
+    foreach( Meta::TrackPtr track, tracks )
+        m_items.append( MusciBrainzTagsItem( track ) );
 }
 
 MusicBrainzTagsModel::~MusicBrainzTagsModel()
@@ -55,25 +135,11 @@ MusicBrainzTagsModel::data( const QModelIndex &index, int role ) \
const  return QVariant();
 
     if( role == Qt::DisplayRole )
-    {
-        if( m_tags.contains( m_tracks.value( index.row() ) ) )
-        {
-            QVariantMap tags = m_tags.value( m_tracks.value( index.row() ) );
-            switch( index.column() )
-            {
-                case 1: return tags.value( Meta::Field::TITLE );
-                case 2: return tags.contains( Meta::Field::ALBUM )? tags.value( \
                Meta::Field::ARTIST ) : "";
-                case 3: return tags.contains( Meta::Field::ALBUM )? tags.value( \
                Meta::Field::ALBUM ) : "";
-                default: return QVariant();
-            }
-        }
-    }
+        return m_items.value( index.row() ).data( index.column() );
     else if( role == Qt::CheckStateRole &&
-             m_tags.contains( m_tracks.value( index.row() ) ) &&
-             index.column() == 0 )
-    {
-        return m_tracksToSave.value( index.row() );
-    }
+             index.column() == 0 &&
+             m_items.value( index.row() ).flags() == Qt::ItemIsUserCheckable )
+        return m_items.value( index.row() ).checked() ? Qt::Checked : Qt::Unchecked;
     else if( role == Qt::SizeHintRole && index.column() == 0 )
         return QSize( 0, 21 );
     return QVariant();
@@ -85,13 +151,13 @@ MusicBrainzTagsModel::setData( const QModelIndex &index, const \
                QVariant &value,
     if( !index.isValid() || role != Qt::CheckStateRole  || index.column() != 0 )
         return false;
 
-    if( m_tags.contains( m_tracks.value( index.row() ) ) && index.column() == 0 )
-    {
-        m_tracksToSave[ index.row() ] = static_cast< Qt::CheckState >( value.toInt() \
                );
-        return true;
-    }
-    else
-        return false;
+    if( m_singleTrackMode )
+        for( int i = 0; i < m_items.count(); i++ )
+            m_items[ i ].setChecked( false );
+
+    m_items[ index.row() ].setChecked( value.toBool() );
+    emit dataChanged( createIndex( 0, 0 ), createIndex( m_items.count() - 1, 0 ) );
+    return true;
 }
 
 QVariant
@@ -115,16 +181,13 @@ MusicBrainzTagsModel::flags( const QModelIndex &index ) const
     if( !index.isValid() )
         return QAbstractItemModel::flags( index );
 
-    if( m_tags.contains( m_tracks.value( index.row() ) ) && index.column() == 0 )
-        return Qt::ItemIsUserCheckable | QAbstractItemModel::flags( index );
-
-    return QAbstractItemModel::flags( index );
+    return m_items.value( index.row() ).flags() | QAbstractItemModel::flags( index \
);  }
 
 int
 MusicBrainzTagsModel::rowCount( const QModelIndex &parent ) const
 {
-    return parent.isValid()? -1 : m_tracks.count();
+    return parent.isValid()? -1 : m_items.count();
 }
 
 int
@@ -134,39 +197,43 @@ MusicBrainzTagsModel::columnCount( const QModelIndex & ) const
 }
 
 void
-MusicBrainzTagsModel::trackFound( const Meta::TrackPtr track, const QVariantMap tags \
) +MusicBrainzTagsModel::addTrack( const Meta::TrackPtr track, const QVariantMap tags \
)  {
-    if( !m_tracks.contains( track ) )
-        return;
-
-    m_tags.insert( track, tags );
+    if( m_singleTrackMode )
+    {
+        m_items.append( MusciBrainzTagsItem( track, tags ) );
+        emit layoutChanged();
+    }
+    else
+        for( int i = 0; i < m_items.count(); i++ )
+            if( m_items.value( i ).track() == track )
+            {
+                m_items[ i ].setData( tags );
+                break;
+            }
 
-    emit dataChanged( createIndex( 0, 0 ), createIndex( m_tracks.count() - 1, 4) );
+    emit dataChanged( createIndex( 0, 0 ), createIndex( m_items.count() - 1, 4 ) );
 }
 
 void
 MusicBrainzTagsModel::selectAll( int section )
 {
-    if( section != 0 )
+    if( section != 0 || m_singleTrackMode )
         return;
 
-    for( int i = 0; i < m_tracks.count(); i++ )
-        if( m_tags.contains( m_tracks.value( i ) ) )
-            m_tracksToSave[i] = Qt::Checked;
+    for( int i = 0; i < m_items.count(); i++ )
+        m_items[ i ].setChecked( true );
 
-    emit dataChanged( createIndex( 0, 0), createIndex( m_tracks.count() - 1, 0 ) );
+    emit dataChanged( createIndex( 0, 0), createIndex( m_items.count() - 1, 0 ) );
 }
 
 QMap < Meta::TrackPtr, QVariantMap >
 MusicBrainzTagsModel::getAllChecked()
 {
     QMap < Meta::TrackPtr, QVariantMap > result;
-    for( int i = 0; i < m_tracks.count(); i++ )
-        if( m_tags.contains( m_tracks.value( i ) ) &&
-            m_tracksToSave.value( i ) == Qt::Checked )
-        {
-            result.insert( m_tracks.value( i ), m_tags.value( m_tracks.value( i ) ) \
                );
-        }
+    foreach( MusciBrainzTagsItem item, m_items )
+        if( item.checked() )
+            result.insert( item.track(), item.data() );
 
     return result;
 }
diff --git a/src/musicbrainz/MusicBrainzTagsModel.h \
b/src/musicbrainz/MusicBrainzTagsModel.h index e79373c..a93929a 100644
--- a/src/musicbrainz/MusicBrainzTagsModel.h
+++ b/src/musicbrainz/MusicBrainzTagsModel.h
@@ -21,6 +21,30 @@
 #include <core/meta/Meta.h>
 #include <QAbstractItemModel>
 
+class MusciBrainzTagsItem
+{
+    public:
+        MusciBrainzTagsItem( Meta::TrackPtr track,  const QVariantMap tags = \
QVariantMap() ); +        MusciBrainzTagsItem() {}
+
+        Meta::TrackPtr track();
+
+        Qt::ItemFlags flags();
+
+        QVariant data( int column );
+        QVariantMap data();
+        void setData( QVariantMap tags );
+
+        bool checked();
+        void setChecked( bool checked );
+
+    private:
+        Meta::TrackPtr m_track;
+        QVariantMap m_data;
+
+        bool m_checked;
+};
+
 class MusicBrainzTagsModel : public QAbstractItemModel
 {
     Q_OBJECT
@@ -32,7 +56,7 @@ class MusicBrainzTagsModel : public QAbstractItemModel
         QModelIndex index( int row, int column, const QModelIndex &parent = \
QModelIndex() ) const;  QModelIndex parent( const QModelIndex &index ) const;
 
-        Qt::ItemFlags flags ( const QModelIndex &index ) const;
+        Qt::ItemFlags flags( const QModelIndex &index ) const;
         QVariant data( const QModelIndex &index, int role = Qt::DisplayRole ) const;
         bool setData( const QModelIndex &index, const QVariant &value, int role );
         QVariant headerData( int section, Qt::Orientation orientation, int role = \
Qt::DisplayRole ) const; @@ -43,13 +67,13 @@ class MusicBrainzTagsModel : public \
QAbstractItemModel  QMap < Meta::TrackPtr, QVariantMap > getAllChecked(); 
 
     public slots:
-        void trackFound( const Meta::TrackPtr track, const QVariantMap tags );
+        void addTrack( const Meta::TrackPtr track, const QVariantMap tags );
         void selectAll( int section );
 
     private:
-        Meta::TrackList m_tracks;
-        QMap < Meta::TrackPtr, QVariantMap > m_tags;
-        QList < Qt::CheckState > m_tracksToSave;
+        QList < MusciBrainzTagsItem > m_items;
+
+        bool m_singleTrackMode;
 };
 
 #endif // MUSICBRAINZTAGSMODEL_H
diff --git a/src/musicbrainz/MusicBrainzXmlParser.cpp \
b/src/musicbrainz/MusicBrainzXmlParser.cpp index 732bd8f..7043bea 100644
--- a/src/musicbrainz/MusicBrainzXmlParser.cpp
+++ b/src/musicbrainz/MusicBrainzXmlParser.cpp
@@ -353,3 +353,21 @@ MusicBrainzXmlParser::grabTrackByLength( const quint64 length )
     track.remove( MusicBrainz::TRACKOFFSET );
     return track;
 }
+
+QVariantMap
+MusicBrainzXmlParser::grabTrackByID( const QString &ID )
+{
+    if( !tracks.contains( ID ) )
+        return QVariantMap();
+
+    QVariantMap track = tracks.value( ID );
+    QString release = track.value( MusicBrainz::RELEASELIST \
).toStringList().first(); +    track.insert( MusicBrainz::RELEASEID, release );
+    track.insert( Meta::Field::ALBUM,
+                  releases.value( release ).value( Meta::Field::TITLE ).toString() \
); +    track.insert( Meta::Field::TRACKNUMBER,
+                  track.value( MusicBrainz::TRACKOFFSET ).toMap().value( release \
).toInt() ); +    track.remove( MusicBrainz::RELEASELIST );
+    track.remove( MusicBrainz::TRACKOFFSET );
+    return track;
+}
diff --git a/src/musicbrainz/MusicBrainzXmlParser.h \
b/src/musicbrainz/MusicBrainzXmlParser.h index 2218fa4..37f1fcd 100644
--- a/src/musicbrainz/MusicBrainzXmlParser.h
+++ b/src/musicbrainz/MusicBrainzXmlParser.h
@@ -40,6 +40,7 @@ class MusicBrainzXmlParser : public ThreadWeaver::Job
         int type();
 
         QVariantMap grabTrackByLength( const quint64 length );
+        QVariantMap grabTrackByID( const QString &ID );
 
         QMap< QString, QVariantMap > tracks;
         QMap< QString, QString > artists;


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic