From 6064b2029ec71fafa688694a61ebc945279c9881 Mon Sep 17 00:00:00 2001 From: Christian Muehlhaeuser Date: Wed, 14 Dec 2011 11:16:09 +0100 Subject: [PATCH] * New sidebar style. Also, first steps towards reorganizing it. --- src/CMakeLists.txt | 8 +- src/libtomahawk/playlistinterface.h | 7 +- src/libtomahawk/utils/proxystyle.cpp | 6 +- src/libtomahawk/viewmanager.cpp | 11 + src/libtomahawk/viewmanager.h | 3 + src/sourcetree/items/categoryitems.cpp | 7 +- src/sourcetree/items/categoryitems.h | 3 + src/sourcetree/items/groupitem.cpp | 55 +++ src/sourcetree/items/groupitem.h | 53 ++ src/sourcetree/items/historyitem.cpp | 96 ++++ src/sourcetree/items/historyitem.h | 57 +++ src/sourcetree/items/playlistitems.cpp | 6 +- .../{collectionitem.cpp => sourceitem.cpp} | 213 ++++---- .../items/{collectionitem.h => sourceitem.h} | 17 +- src/sourcetree/items/sourcetreeitem.cpp | 10 +- src/sourcetree/items/sourcetreeitem.h | 3 + src/sourcetree/sourcedelegate.cpp | 459 +++++++++++------- src/sourcetree/sourcedelegate.h | 6 + src/sourcetree/sourcesmodel.cpp | 124 +++-- src/sourcetree/sourcesmodel.h | 45 +- src/sourcetree/sourcesproxymodel.cpp | 33 +- src/sourcetree/sourcesproxymodel.h | 5 + src/sourcetree/sourcetreeview.cpp | 30 +- src/sourcetree/sourcetreeview.h | 3 +- 24 files changed, 873 insertions(+), 387 deletions(-) create mode 100644 src/sourcetree/items/groupitem.cpp create mode 100644 src/sourcetree/items/groupitem.h create mode 100644 src/sourcetree/items/historyitem.cpp create mode 100644 src/sourcetree/items/historyitem.h rename src/sourcetree/items/{collectionitem.cpp => sourceitem.cpp} (65%) rename src/sourcetree/items/{collectionitem.h => sourceitem.h} (89%) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 984150128..75cade522 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -58,11 +58,13 @@ SET( tomahawkSourcesGui ${tomahawkSourcesGui} sourcetree/sourcedelegate.cpp sourcetree/animationhelper.cpp sourcetree/items/sourcetreeitem.cpp - sourcetree/items/collectionitem.cpp + sourcetree/items/sourceitem.cpp sourcetree/items/playlistitems.cpp sourcetree/items/categoryitems.cpp sourcetree/items/genericpageitems.cpp sourcetree/items/temporarypageitem.cpp + sourcetree/items/groupitem.cpp + sourcetree/items/historyitem.cpp breakpad/BreakPad.cpp @@ -110,11 +112,13 @@ SET( tomahawkHeadersGui ${tomahawkHeadersGui} sourcetree/sourcedelegate.h sourcetree/animationhelper.h sourcetree/items/sourcetreeitem.h - sourcetree/items/collectionitem.h + sourcetree/items/sourceitem.h sourcetree/items/playlistitems.h sourcetree/items/categoryitems.h sourcetree/items/genericpageitems.h sourcetree/items/temporarypageitem.h + sourcetree/items/groupitem.h + sourcetree/items/historyitem.h tomahawktrayicon.h audiocontrols.h diff --git a/src/libtomahawk/playlistinterface.h b/src/libtomahawk/playlistinterface.h index 4ef652137..991a84275 100644 --- a/src/libtomahawk/playlistinterface.h +++ b/src/libtomahawk/playlistinterface.h @@ -73,11 +73,16 @@ public: QObject* object() const { return m_object; } + static void dontDelete( Tomahawk::PlaylistInterface* obj ) + { + tDebug() << Q_FUNC_INFO << obj; + } + virtual Tomahawk::playlistinterface_ptr getSharedPointer() { if ( m_sharedPtr.isNull() ) { - m_sharedPtr = Tomahawk::playlistinterface_ptr( this ); + m_sharedPtr = Tomahawk::playlistinterface_ptr( this, dontDelete ); } return m_sharedPtr; diff --git a/src/libtomahawk/utils/proxystyle.cpp b/src/libtomahawk/utils/proxystyle.cpp index 1e906f0f6..99bd5f69c 100644 --- a/src/libtomahawk/utils/proxystyle.cpp +++ b/src/libtomahawk/utils/proxystyle.cpp @@ -34,14 +34,12 @@ ProxyStyle::drawPrimitive( PrimitiveElement pe, const QStyleOption* opt, QPainte { if ( pe == PE_IndicatorBranch ) { - if ( opt->state & QStyle::State_Children ) + if ( opt->state & QStyle::State_Children && !w->property( "flattenBranches" ).toBool() ) { - QRect r = opt->rect; - int hd = ( opt->rect.height() - ARROW_HEIGHT ) / 2; int wd = ( opt->rect.width() - ARROW_WIDTH ) / 2; - r.adjust( wd, hd, 0, 0 ); + QRect r = opt->rect.adjusted( wd, hd, 0, 0 ); QPointF pointsOpened[3] = { QPointF( r.x(), r.y() ), QPointF( r.x() + ARROW_WIDTH, r.y() ), QPointF( r.x() + ARROW_WIDTH / 2, r.y() + ARROW_HEIGHT ) }; QPointF pointsClosed[3] = { QPointF( r.x(), r.y() ), QPointF( r.x() + ARROW_WIDTH, r.y() + ARROW_HEIGHT / 2 ), QPointF( r.x(), r.y() + ARROW_HEIGHT ) }; diff --git a/src/libtomahawk/viewmanager.cpp b/src/libtomahawk/viewmanager.cpp index 2841f39a1..b33804d02 100644 --- a/src/libtomahawk/viewmanager.cpp +++ b/src/libtomahawk/viewmanager.cpp @@ -40,6 +40,7 @@ #include "sourcelist.h" #include "tomahawksettings.h" +#include "customplaylistview.h" #include "dynamic/widgets/DynamicWidget.h" #include "widgets/welcomewidget.h" @@ -71,6 +72,7 @@ ViewManager::ViewManager( QObject* parent ) , m_widget( new QWidget() ) , m_welcomeWidget( new WelcomeWidget() ) , m_whatsHotWidget( new WhatsHotWidget() ) + , m_topLovedWidget( 0 ) , m_currentMode( PlaylistInterface::Tree ) { s_instance = this; @@ -418,6 +420,15 @@ ViewManager::showWhatsHotPage() } +Tomahawk::ViewPage* +ViewManager::showTopLovedPage() +{ + if ( !m_topLovedWidget ) + m_topLovedWidget = new CustomPlaylistView( CustomPlaylistView::AllLovedTracks, source_ptr(), m_widget ); + + return show( m_topLovedWidget ); +} + void ViewManager::setTableMode() diff --git a/src/libtomahawk/viewmanager.h b/src/libtomahawk/viewmanager.h index 3c2bed9a6..1a9b698b8 100644 --- a/src/libtomahawk/viewmanager.h +++ b/src/libtomahawk/viewmanager.h @@ -90,6 +90,7 @@ public: Tomahawk::ViewPage* welcomeWidget() const { return m_welcomeWidget; } Tomahawk::ViewPage* whatsHotWidget() const { return m_whatsHotWidget; } + Tomahawk::ViewPage* topLovedWidget() const { return m_topLovedWidget; } ArtistView* superCollectionView() const { return m_superCollectionView; } /// Get the view page for the given item. Not pretty... @@ -133,6 +134,7 @@ public slots: Tomahawk::ViewPage* showSuperCollection(); Tomahawk::ViewPage* showWelcomePage(); Tomahawk::ViewPage* showWhatsHotPage(); + Tomahawk::ViewPage* showTopLovedPage(); void showCurrentTrack(); // Returns the shown viewpage @@ -194,6 +196,7 @@ private: QueueView* m_queue; WelcomeWidget* m_welcomeWidget; WhatsHotWidget* m_whatsHotWidget; + Tomahawk::ViewPage* m_topLovedWidget; QList< Tomahawk::collection_ptr > m_superCollections; diff --git a/src/sourcetree/items/categoryitems.cpp b/src/sourcetree/items/categoryitems.cpp index cd0461f25..3cd74f326 100644 --- a/src/sourcetree/items/categoryitems.cpp +++ b/src/sourcetree/items/categoryitems.cpp @@ -365,6 +365,8 @@ CategoryItem::CategoryItem( SourcesModel* model, SourceTreeItem* parent, Sources m_addItem = new CategoryAddItem( model, this, m_category ); } // endRowsAdded(); + + connect( this, SIGNAL( toggleExpandRequest( SourceTreeItem* ) ), model, SLOT( itemToggleExpandRequest( SourceTreeItem* ) ) ); } @@ -405,8 +407,5 @@ CategoryItem::peerSortValue() const void CategoryItem::activate() { - if( m_category == SourcesModel::StationsCategory ) { - // TODO activate stations page - } - + emit toggleExpandRequest( this ); } diff --git a/src/sourcetree/items/categoryitems.h b/src/sourcetree/items/categoryitems.h index 0b9697955..c1e3dcadd 100644 --- a/src/sourcetree/items/categoryitems.h +++ b/src/sourcetree/items/categoryitems.h @@ -75,6 +75,9 @@ public: SourcesModel::CategoryType categoryType() { return m_category; } +signals: + void toggleExpandRequest( SourceTreeItem* ); + private: SourcesModel::CategoryType m_category; CategoryAddItem* m_addItem; diff --git a/src/sourcetree/items/groupitem.cpp b/src/sourcetree/items/groupitem.cpp new file mode 100644 index 000000000..57e8b56cd --- /dev/null +++ b/src/sourcetree/items/groupitem.cpp @@ -0,0 +1,55 @@ +/* === This file is part of Tomahawk Player - === + * + * Copyright 2010-2011, Christian Muehlhaeuser + * Copyright 2010-2011, Leo Franchi + * + * Tomahawk is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tomahawk is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tomahawk. If not, see . + */ + +#include "groupitem.h" + +#include "utils/tomahawkutils.h" +#include "utils/logger.h" +#include "viewmanager.h" +#include "audio/audioengine.h" + +using namespace Tomahawk; + + +GroupItem::GroupItem( SourcesModel* model, SourceTreeItem* parent, const QString& text, int peerSortValue ) + : SourceTreeItem( model, parent, SourcesModel::Group ) + , m_text( text ) + , m_peerSortValue( peerSortValue ) +{ + connect( this, SIGNAL( toggleExpandRequest( SourceTreeItem* ) ), model, SLOT( itemToggleExpandRequest( SourceTreeItem* ) ) ); +} + + +GroupItem::~GroupItem() +{ +} + + +void +GroupItem::activate() +{ + emit toggleExpandRequest( this ); +} + + +QString +GroupItem::text() const +{ + return m_text; +} diff --git a/src/sourcetree/items/groupitem.h b/src/sourcetree/items/groupitem.h new file mode 100644 index 000000000..ae129b773 --- /dev/null +++ b/src/sourcetree/items/groupitem.h @@ -0,0 +1,53 @@ +/* === This file is part of Tomahawk Player - === + * + * Copyright 2010-2011, Christian Muehlhaeuser + * Copyright 2010-2011, Leo Franchi + * + * Tomahawk is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tomahawk is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tomahawk. If not, see . + */ + +#ifndef GROUP_ITEM_H +#define GROUP_ITEM_H + +#include "sourcetreeitem.h" + +#include "boost/function.hpp" +#include "boost/bind.hpp" + +// generic item that has some name, some text, and calls a certain slot when activated. badabing! +class GroupItem : public SourceTreeItem +{ + Q_OBJECT +public: + // takes 2 function pointers: show: called when wanting to show the desired view page. get: called to get the view page from ViewManager if it exists + GroupItem( SourcesModel* model, SourceTreeItem* parent, const QString& text, int peerSortValue = 0 ); + virtual ~GroupItem(); + + virtual QString text() const; + virtual void activate(); + virtual bool willAcceptDrag( const QMimeData* data ) const { Q_UNUSED( data ); return false; } + virtual QIcon icon() const { return QIcon(); } + virtual int peerSortValue() const { return m_peerSortValue; } + virtual bool isBeingPlayed() const { return false; } + +signals: + void activated(); + void toggleExpandRequest( SourceTreeItem* ); + +private: + QString m_text; + int m_peerSortValue; +}; + +#endif diff --git a/src/sourcetree/items/historyitem.cpp b/src/sourcetree/items/historyitem.cpp new file mode 100644 index 000000000..09aaa2b6a --- /dev/null +++ b/src/sourcetree/items/historyitem.cpp @@ -0,0 +1,96 @@ +/* === This file is part of Tomahawk Player - === + * + * Copyright 2010-2011, Christian Muehlhaeuser + * Copyright 2010-2011, Leo Franchi + * + * Tomahawk is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tomahawk is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tomahawk. If not, see . + */ + +#include "historyitem.h" + +#include "viewmanager.h" +#include "genericpageitems.h" +#include "utils/tomahawkutilsgui.h" +#include "utils/logger.h" +#include "playlist/customplaylistview.h" +#include "temporarypageitem.h" +#include "sourcelist.h" + +using namespace Tomahawk; + + +HistoryItem::HistoryItem( SourcesModel* model, SourceTreeItem* parent, const QString& text, int peerSortValue ) + : GroupItem( model, parent, text, peerSortValue ) +{ + connect( this, SIGNAL( toggleExpandRequest( SourceTreeItem* ) ), model, SLOT( itemToggleExpandRequest( SourceTreeItem* ) ) ); + connect( ViewManager::instance(), SIGNAL( tempPageActivated( Tomahawk::ViewPage* ) ), SLOT( tempPageActivated( Tomahawk::ViewPage* ) ) ); +} + + +HistoryItem::~HistoryItem() +{ +} + + +void +HistoryItem::activate() +{ + emit toggleExpandRequest( this ); +} + + +void +HistoryItem::tempPageActivated( Tomahawk::ViewPage* v ) +{ + const int idx = children().count(); + int latest = idx; + if ( idx ) + { + latest = children().last()->IDValue(); + + foreach ( TemporaryPageItem* page, m_tempItems ) + { + if ( page->page() == v ) + { + emit selectRequest( page ); + return; + } + } + } + + // Only keep 5 temporary pages at once + while ( m_tempItems.size() > 4 ) + { + TemporaryPageItem* item = m_tempItems.takeFirst(); + QTimer::singleShot( 0, item, SLOT( removeFromList() ) ); + } + + emit beginRowsAdded( idx, idx ); + + TemporaryPageItem* tempPage = new TemporaryPageItem( model(), this, v, latest + 1 ); + connect( tempPage, SIGNAL( removed() ), this, SLOT( temporaryPageDestroyed() ) ); + m_tempItems << tempPage; + endRowsAdded(); + + emit selectRequest( tempPage ); +} + + +void +HistoryItem::temporaryPageDestroyed() +{ + TemporaryPageItem* tempPage = qobject_cast< TemporaryPageItem* >( sender() ); + Q_ASSERT( tempPage ); + m_tempItems.removeAll( tempPage ); +} diff --git a/src/sourcetree/items/historyitem.h b/src/sourcetree/items/historyitem.h new file mode 100644 index 000000000..d3dd23449 --- /dev/null +++ b/src/sourcetree/items/historyitem.h @@ -0,0 +1,57 @@ +/* === This file is part of Tomahawk Player - === + * + * Copyright 2010-2011, Christian Muehlhaeuser + * Copyright 2010-2011, Leo Franchi + * + * Tomahawk is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tomahawk is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tomahawk. If not, see . + */ + +#ifndef HISTORY_ITEM_H +#define HISTORY_ITEM_H + +#include "groupitem.h" + +class TemporaryPageItem; +class GenericPageItem; +class CategoryItem; + +namespace Tomahawk +{ + class ViewPage; +} + +class HistoryItem : public GroupItem +{ + Q_OBJECT +public: + HistoryItem( SourcesModel* model, SourceTreeItem* parent, const QString& text, int peerSortValue = 0 ); + virtual ~HistoryItem(); + + virtual void activate(); + +signals: + void activated(); + void toggleExpandRequest( SourceTreeItem* ); + +private slots: + void tempPageActivated( Tomahawk::ViewPage* ); + void temporaryPageDestroyed(); + +private: + QList< TemporaryPageItem* > m_tempItems; + +private: +}; + +#endif diff --git a/src/sourcetree/items/playlistitems.cpp b/src/sourcetree/items/playlistitems.cpp index 7785eceef..1df14c381 100644 --- a/src/sourcetree/items/playlistitems.cpp +++ b/src/sourcetree/items/playlistitems.cpp @@ -25,7 +25,7 @@ #include "viewmanager.h" #include "playlist/dynamic/GeneratorInterface.h" #include "categoryitems.h" -#include "collectionitem.h" +#include "sourceitem.h" #include "utils/tomahawkutils.h" #include "utils/logger.h" #include "dropjob.h" @@ -337,7 +337,7 @@ DynamicPlaylistItem::checkReparentHackNeeded( const DynamicPlaylistRevision& rev CategoryItem* from = cat; CategoryItem* to = 0; if( cat->categoryType() == SourcesModel::PlaylistsCategory && revision.mode == OnDemand ) { // WRONG - CollectionItem* col = qobject_cast< CollectionItem* >( cat->parent() ); + SourceItem* col = qobject_cast< SourceItem* >( cat->parent() ); to = col->stationsCategory(); if( !to ) { // you have got to be fucking kidding me int fme = col->children().count(); @@ -348,7 +348,7 @@ DynamicPlaylistItem::checkReparentHackNeeded( const DynamicPlaylistRevision& rev col->setStationsCategory( to ); } } else if( cat->categoryType() == SourcesModel::StationsCategory && revision.mode == Static ) { // WRONG - CollectionItem* col = qobject_cast< CollectionItem* >( cat->parent() ); + SourceItem* col = qobject_cast< SourceItem* >( cat->parent() ); to = col->playlistsCategory(); // qDebug() << "TRYING TO HACK TO:" << to; if( !to ) { // you have got to be fucking kidding me diff --git a/src/sourcetree/items/collectionitem.cpp b/src/sourcetree/items/sourceitem.cpp similarity index 65% rename from src/sourcetree/items/collectionitem.cpp rename to src/sourcetree/items/sourceitem.cpp index 4307d5dbb..5a78379ff 100644 --- a/src/sourcetree/items/collectionitem.cpp +++ b/src/sourcetree/items/sourceitem.cpp @@ -16,7 +16,7 @@ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. */ -#include "collectionitem.h" +#include "sourceitem.h" #include "categoryitems.h" #include "playlistitems.h" @@ -28,14 +28,13 @@ #include "widgets/SocialPlaylistWidget.h" #include "playlist/customplaylistview.h" #include "source.h" -#include "temporarypageitem.h" -#include +#include "sourcelist.h" -/// CollectionItem +/// SourceItem using namespace Tomahawk; -CollectionItem::CollectionItem( SourcesModel* mdl, SourceTreeItem* parent, const Tomahawk::source_ptr& source ) +SourceItem::SourceItem( SourcesModel* mdl, SourceTreeItem* parent, const Tomahawk::source_ptr& source ) : SourceTreeItem( mdl, parent, SourcesModel::Collection ) , m_source( source ) , m_playlists( 0 ) @@ -43,51 +42,31 @@ CollectionItem::CollectionItem( SourcesModel* mdl, SourceTreeItem* parent, cons , m_latchedOn( false ) , m_sourceInfoItem( 0 ) , m_coolPlaylistsItem( 0 ) - , m_lovedTracksItem() + , m_collectionPage( 0 ) , m_sourceInfoPage( 0 ) , m_coolPlaylistsPage( 0 ) , m_lovedTracksPage( 0 ) , m_whatsHotPage( 0 ) { - m_lovedTracksItem = new GenericPageItem( model(), this, ( m_source.isNull() ? tr( "Top Loved Tracks" ) : tr( "Loved Tracks" ) ), QIcon( RESPATH "images/loved_playlist.png" ), - boost::bind( &CollectionItem::lovedTracksClicked, this ), - boost::bind( &CollectionItem::getLovedTracksPage, this ) ); - m_lovedTracksItem->setSortValue( -250 ); - if ( m_source.isNull() ) { - // super collection - connect( ViewManager::instance(), SIGNAL( tempPageActivated( Tomahawk::ViewPage*) ), this, SLOT( tempPageActivated( Tomahawk::ViewPage* ) ) ); - - // add misc children of root node - GenericPageItem* recent = new GenericPageItem( model(), this, tr( "Dashboard" ), QIcon( RESPATH "images/dashboard.png" ), - boost::bind( &ViewManager::showWelcomePage, ViewManager::instance() ), - boost::bind( &ViewManager::welcomeWidget, ViewManager::instance() ) - ); - recent->setSortValue( -300 ); - - GenericPageItem* hot = new GenericPageItem( model(), this, tr( "Charts" ), QIcon( RESPATH "images/charts.png" ), - boost::bind( &ViewManager::showWhatsHotPage, ViewManager::instance() ), - boost::bind( &ViewManager::whatsHotWidget, ViewManager::instance() ) - ); - hot->setSortValue( -300 ); - - - // TODO finish implementing and making pretty -// m_coolPlaylistsItem = new GenericPageItem( model(), this, tr( "Cool Stuff" ), QIcon( RESPATH "images/new-additions.png" ), -// boost::bind( &CollectionItem::coolPlaylistsClicked, this ), -// boost::bind( &CollectionItem::getCoolPlaylistsPage, this ) -// ); -// m_coolPlaylistsItem->setSortValue( 200 ); - m_superCol = TomahawkUtils::createAvatarFrame( QPixmap( RESPATH "images/supercollection.png" ) ); - return; } + m_lovedTracksItem = new GenericPageItem( model(), this, tr( "Loved Tracks" ), QIcon( RESPATH "images/loved_playlist.png" ), + boost::bind( &SourceItem::lovedTracksClicked, this ), + boost::bind( &SourceItem::getLovedTracksPage, this ) ); + m_lovedTracksItem->setSortValue( -250 ); + + m_collectionItem = new GenericPageItem( model(), this, tr( "Collection" ), QIcon( RESPATH "images/drop-song.png" ), //FIXME different icon + boost::bind( &SourceItem::collectionClicked, this ), + boost::bind( &SourceItem::getCollectionPage, this ) ); + m_collectionItem->setSortValue( -350 ); + m_sourceInfoItem = new GenericPageItem( model(), this, tr( "New Additions" ), QIcon( RESPATH "images/new-additions.png" ), - boost::bind( &CollectionItem::sourceInfoClicked, this ), - boost::bind( &CollectionItem::getSourceInfoPage, this ) ); + boost::bind( &SourceItem::sourceInfoClicked, this ), + boost::bind( &SourceItem::getSourceInfoPage, this ) ); m_sourceInfoItem->setSortValue( -300 ); // create category items if there are playlists to show, or stations to show @@ -114,14 +93,14 @@ CollectionItem::CollectionItem( SourcesModel* mdl, SourceTreeItem* parent, cons // load auto playlists and stations! - connect( source.data(), SIGNAL( stats( QVariantMap ) ), this, SIGNAL( updated() ) ); - connect( source.data(), SIGNAL( syncedWithDatabase() ), this, SIGNAL( updated() ) ); - connect( source.data(), SIGNAL( playbackStarted( Tomahawk::query_ptr ) ), this, SIGNAL( updated() ) ); - connect( source.data(), SIGNAL( stateChanged() ), this, SIGNAL( updated() ) ); - connect( source.data(), SIGNAL( offline() ), this, SIGNAL( updated() ) ); - connect( source.data(), SIGNAL( online() ), this, SIGNAL( updated() ) ); - connect( SourceList::instance(), SIGNAL( sourceLatchedOn( Tomahawk::source_ptr, Tomahawk::source_ptr ) ), this, SLOT( latchedOn( Tomahawk::source_ptr, Tomahawk::source_ptr ) ) ); - connect( SourceList::instance(), SIGNAL( sourceLatchedOff( Tomahawk::source_ptr, Tomahawk::source_ptr ) ), this, SLOT( latchedOff( Tomahawk::source_ptr, Tomahawk::source_ptr ) ) ); + connect( source.data(), SIGNAL( stats( QVariantMap ) ), SIGNAL( updated() ) ); + connect( source.data(), SIGNAL( syncedWithDatabase() ), SIGNAL( updated() ) ); + connect( source.data(), SIGNAL( playbackStarted( Tomahawk::query_ptr ) ), SIGNAL( updated() ) ); + connect( source.data(), SIGNAL( stateChanged() ), SIGNAL( updated() ) ); + connect( source.data(), SIGNAL( offline() ), SIGNAL( updated() ) ); + connect( source.data(), SIGNAL( online() ), SIGNAL( updated() ) ); + connect( SourceList::instance(), SIGNAL( sourceLatchedOn( Tomahawk::source_ptr, Tomahawk::source_ptr ) ), SLOT( latchedOn( Tomahawk::source_ptr, Tomahawk::source_ptr ) ) ); + connect( SourceList::instance(), SIGNAL( sourceLatchedOff( Tomahawk::source_ptr, Tomahawk::source_ptr ) ), SLOT( latchedOff( Tomahawk::source_ptr, Tomahawk::source_ptr ) ) ); connect( source->collection().data(), SIGNAL( playlistsAdded( QList ) ), SLOT( onPlaylistsAdded( QList ) ), Qt::QueuedConnection ); @@ -131,30 +110,30 @@ CollectionItem::CollectionItem( SourcesModel* mdl, SourceTreeItem* parent, cons SLOT( onStationsAdded( QList ) ), Qt::QueuedConnection ); if ( m_source->isLocal() ) - QTimer::singleShot(0, this, SLOT(requestExpanding())); + QTimer::singleShot( 0, this, SLOT( requestExpanding() ) ); } Tomahawk::source_ptr -CollectionItem::source() const +SourceItem::source() const { return m_source; } QString -CollectionItem::text() const +SourceItem::text() const { return m_source.isNull() ? tr( "Super Collection" ) : m_source->friendlyName(); } int -CollectionItem::IDValue() const +SourceItem::IDValue() const { - if( m_source.isNull() ) + if ( m_source.isNull() ) return -1; - if( m_source->isLocal() ) + if ( m_source->isLocal() ) return 0; return m_source->id(); @@ -162,46 +141,46 @@ CollectionItem::IDValue() const int -CollectionItem::peerSortValue() const +SourceItem::peerSortValue() const { - if( m_source.isNull() ) + if ( m_source.isNull() || m_source->isLocal() ) return -1; - if( m_source->isLocal() ) - return 0; return 1; } void -CollectionItem::activate() +SourceItem::activate() { ViewPage* p = 0; if ( source().isNull() ) p = ViewManager::instance()->showSuperCollection(); else - p = ViewManager::instance()->show( source()->collection() ); + emit toggleExpandRequest( this ); +// p = ViewManager::instance()->show( source()->collection() ); model()->linkSourceItemToPage( this, p ); } QIcon -CollectionItem::icon() const +SourceItem::icon() const { if ( m_source.isNull() ) return m_superCol; else { - if( m_source->avatar().isNull() ) + if ( m_source->avatar().isNull() ) return m_defaultAvatar; else return m_source->avatar( Source::FancyStyle ); } } + bool -CollectionItem::localLatchedOn() const +SourceItem::localLatchedOn() const { // Don't show a listen icon if this is the local collection and we are latched on to someone who went offline // we are technically still latched on (if they come back online we'll be still listening along) but it's not visible @@ -216,7 +195,7 @@ CollectionItem::localLatchedOn() const void -CollectionItem::latchedOff( const source_ptr& from, const source_ptr& to ) +SourceItem::latchedOff( const source_ptr& from, const source_ptr& to ) { if ( from->isLocal() && ( m_source == to || m_source == from ) ) { @@ -226,8 +205,9 @@ CollectionItem::latchedOff( const source_ptr& from, const source_ptr& to ) } } + void -CollectionItem::latchedOn( const source_ptr& from, const source_ptr& to ) +SourceItem::latchedOn( const source_ptr& from, const source_ptr& to ) { if ( from->isLocal() && ( m_source == to || m_source == from ) ) { @@ -239,29 +219,32 @@ CollectionItem::latchedOn( const source_ptr& from, const source_ptr& to ) void -CollectionItem::playlistsAddedInternal( SourceTreeItem* parent, const QList< dynplaylist_ptr >& playlists ) +SourceItem::playlistsAddedInternal( SourceTreeItem* parent, const QList< dynplaylist_ptr >& playlists ) { QList< SourceTreeItem* > items; int addOffset = playlists.first()->author()->isLocal() ? 1 : 0; int from = parent->children().count() - addOffset; parent->beginRowsAdded( from, from + playlists.count() - 1 ); - foreach( const dynplaylist_ptr& p, playlists ) + foreach ( const dynplaylist_ptr& p, playlists ) { DynamicPlaylistItem* plItem = new DynamicPlaylistItem( model(), parent, p, parent->children().count() - addOffset ); // qDebug() << "Dynamic Playlist added:" << p->title() << p->creator() << p->info(); p->loadRevision(); items << plItem; - if( p->mode() == Static ) { - if( m_source->isLocal() ) + if ( p->mode() == Static ) + { + if ( m_source->isLocal() ) connect( p.data(), SIGNAL( aboutToBeDeleted( Tomahawk::dynplaylist_ptr ) ), SLOT( onAutoPlaylistDeleted( Tomahawk::dynplaylist_ptr ) ), Qt::QueuedConnection ); else connect( p.data(), SIGNAL( deleted( Tomahawk::dynplaylist_ptr ) ), SLOT( onAutoPlaylistDeleted( Tomahawk::dynplaylist_ptr ) ), Qt::QueuedConnection ); - } else { - if( m_source->isLocal() ) + } + else + { + if ( m_source->isLocal() ) connect( p.data(), SIGNAL( aboutToBeDeleted( Tomahawk::dynplaylist_ptr ) ), SLOT( onStationDeleted( Tomahawk::dynplaylist_ptr ) ), Qt::QueuedConnection ); else @@ -275,7 +258,7 @@ CollectionItem::playlistsAddedInternal( SourceTreeItem* parent, const QList< dyn template< typename T > void -CollectionItem::playlistDeletedInternal( SourceTreeItem* parent, const T& p ) +SourceItem::playlistDeletedInternal( SourceTreeItem* parent, const T& p ) { Q_ASSERT( parent ); // How can we delete playlists if we have none? int curCount = parent->children().count(); @@ -314,7 +297,7 @@ CollectionItem::playlistDeletedInternal( SourceTreeItem* parent, const T& p ) void -CollectionItem::onPlaylistsAdded( const QList< playlist_ptr >& playlists ) +SourceItem::onPlaylistsAdded( const QList< playlist_ptr >& playlists ) { // qDebug() << Q_FUNC_INFO << m_source->friendlyName() << playlists.count(); @@ -355,14 +338,14 @@ CollectionItem::onPlaylistsAdded( const QList< playlist_ptr >& playlists ) void -CollectionItem::onPlaylistDeleted( const playlist_ptr& playlist ) +SourceItem::onPlaylistDeleted( const playlist_ptr& playlist ) { playlistDeletedInternal( m_playlists, playlist ); } void -CollectionItem::onAutoPlaylistsAdded( const QList< dynplaylist_ptr >& playlists ) +SourceItem::onAutoPlaylistsAdded( const QList< dynplaylist_ptr >& playlists ) { if( playlists.isEmpty() ) return; @@ -381,7 +364,7 @@ CollectionItem::onAutoPlaylistsAdded( const QList< dynplaylist_ptr >& playlists void -CollectionItem::onAutoPlaylistDeleted( const dynplaylist_ptr& playlist ) +SourceItem::onAutoPlaylistDeleted( const dynplaylist_ptr& playlist ) { if( !m_playlists ) qDebug() << "NO playlist category item for a deleting playlist.."; @@ -391,7 +374,7 @@ CollectionItem::onAutoPlaylistDeleted( const dynplaylist_ptr& playlist ) void -CollectionItem::onStationsAdded( const QList< dynplaylist_ptr >& stations ) +SourceItem::onStationsAdded( const QList< dynplaylist_ptr >& stations ) { if( stations.isEmpty() ) return; @@ -410,59 +393,21 @@ CollectionItem::onStationsAdded( const QList< dynplaylist_ptr >& stations ) void -CollectionItem::onStationDeleted( const dynplaylist_ptr& station ) +SourceItem::onStationDeleted( const dynplaylist_ptr& station ) { playlistDeletedInternal( m_stations, station ); } void -CollectionItem::requestExpanding() +SourceItem::requestExpanding() { - emit expandRequest(this); -} - - -void -CollectionItem::tempPageActivated( Tomahawk::ViewPage* v ) -{ - const int idx = children().count(); - const int latest = children().last()->IDValue(); - - foreach ( TemporaryPageItem* page, m_tempItems ) - { - if ( page->page() == v ) - { - emit selectRequest( page ); - return; - } - } - - // Only keep 5 temporary pages at once - while ( m_tempItems.size() > 4 ) - { - TemporaryPageItem* item = m_tempItems.takeFirst(); - QTimer::singleShot( 0, item, SLOT( removeFromList() ) ); - } - emit beginRowsAdded( idx, idx ); - TemporaryPageItem* tempPage = new TemporaryPageItem( model(), this, v, latest + 1 ); - connect( tempPage, SIGNAL( removed() ), this, SLOT( temporaryPageDestroyed() ) ); - m_tempItems << tempPage; - endRowsAdded(); - emit selectRequest( tempPage ); -} - -void -CollectionItem::temporaryPageDestroyed() -{ - TemporaryPageItem* tempPage = qobject_cast< TemporaryPageItem* >( sender() ); - Q_ASSERT( tempPage ); - m_tempItems.removeAll( tempPage ); + emit expandRequest( this ); } ViewPage* -CollectionItem::sourceInfoClicked() +SourceItem::sourceInfoClicked() { if( m_source.isNull() ) return 0; @@ -473,19 +418,37 @@ CollectionItem::sourceInfoClicked() ViewPage* -CollectionItem::getSourceInfoPage() const +SourceItem::getSourceInfoPage() const { return m_sourceInfoPage; } ViewPage* -CollectionItem::coolPlaylistsClicked() +SourceItem::collectionClicked() { - if( !m_source.isNull() ) + if( m_source.isNull() ) return 0; - if( !m_coolPlaylistsPage ) + m_collectionPage = ViewManager::instance()->show( m_source->collection() ); + return m_collectionPage; +} + + +ViewPage* +SourceItem::getCollectionPage() const +{ + return m_collectionPage;; +} + + +ViewPage* +SourceItem::coolPlaylistsClicked() +{ + if ( !m_source.isNull() ) + return 0; + + if ( !m_coolPlaylistsPage ) m_coolPlaylistsPage = new SocialPlaylistWidget( ViewManager::instance()->widget() ); ViewManager::instance()->show( m_coolPlaylistsPage ); @@ -494,16 +457,16 @@ CollectionItem::coolPlaylistsClicked() ViewPage* -CollectionItem::getCoolPlaylistsPage() const +SourceItem::getCoolPlaylistsPage() const { return m_coolPlaylistsPage; } ViewPage* -CollectionItem::lovedTracksClicked() +SourceItem::lovedTracksClicked() { - if( !m_lovedTracksPage ) + if ( !m_lovedTracksPage ) m_lovedTracksPage = new CustomPlaylistView( m_source.isNull() ? CustomPlaylistView::AllLovedTracks : CustomPlaylistView::SourceLovedTracks, m_source, ViewManager::instance()->widget() ); ViewManager::instance()->show( m_lovedTracksPage ); @@ -512,7 +475,7 @@ CollectionItem::lovedTracksClicked() ViewPage* -CollectionItem::getLovedTracksPage() const +SourceItem::getLovedTracksPage() const { return m_lovedTracksPage; } diff --git a/src/sourcetree/items/collectionitem.h b/src/sourcetree/items/sourceitem.h similarity index 89% rename from src/sourcetree/items/collectionitem.h rename to src/sourcetree/items/sourceitem.h index 41409032c..7827721e3 100644 --- a/src/sourcetree/items/collectionitem.h +++ b/src/sourcetree/items/sourceitem.h @@ -16,8 +16,8 @@ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. */ -#ifndef COLLECTION_ITEM_H -#define COLLECTION_ITEM_H +#ifndef SOURCE_ITEM_H +#define SOURCE_ITEM_H #include "sourcetreeitem.h" @@ -30,11 +30,11 @@ namespace Tomahawk class ViewPage; } -class CollectionItem : public SourceTreeItem +class SourceItem : public SourceTreeItem { Q_OBJECT public: - CollectionItem( SourcesModel* model, SourceTreeItem* parent, const Tomahawk::source_ptr& source ); + SourceItem( SourcesModel* model, SourceTreeItem* parent, const Tomahawk::source_ptr& source ); virtual QString text() const; virtual void activate(); @@ -64,12 +64,12 @@ private slots: void requestExpanding(); - void tempPageActivated( Tomahawk::ViewPage* ); - void temporaryPageDestroyed(); - Tomahawk::ViewPage* sourceInfoClicked(); Tomahawk::ViewPage* getSourceInfoPage() const; + Tomahawk::ViewPage* collectionClicked(); + Tomahawk::ViewPage* getCollectionPage() const; + Tomahawk::ViewPage* coolPlaylistsClicked(); Tomahawk::ViewPage* getCoolPlaylistsPage() const; @@ -89,11 +89,12 @@ private: bool m_latchedOn; Tomahawk::source_ptr m_latchedOnTo; - QList< TemporaryPageItem* > m_tempItems; + GenericPageItem* m_collectionItem; GenericPageItem* m_sourceInfoItem; GenericPageItem* m_coolPlaylistsItem; GenericPageItem* m_lovedTracksItem; + Tomahawk::ViewPage* m_collectionPage; Tomahawk::ViewPage* m_sourceInfoPage; Tomahawk::ViewPage* m_coolPlaylistsPage; Tomahawk::ViewPage* m_lovedTracksPage; diff --git a/src/sourcetree/items/sourcetreeitem.cpp b/src/sourcetree/items/sourcetreeitem.cpp index 5f82833c3..01a0224f8 100644 --- a/src/sourcetree/items/sourcetreeitem.cpp +++ b/src/sourcetree/items/sourcetreeitem.cpp @@ -29,18 +29,20 @@ SourceTreeItem::SourceTreeItem( SourcesModel* model, SourceTreeItem* parent, Sou , m_parent( parent ) , m_model( model ) { - connect( this, SIGNAL( beginChildRowsAdded( int,int ) ), m_model, SLOT( onItemRowsAddedBegin( int,int ) ) ); - connect( this, SIGNAL( beginChildRowsRemoved( int,int ) ), m_model, SLOT( onItemRowsRemovedBegin( int,int ) ) ); + connect( this, SIGNAL( beginChildRowsAdded( int, int ) ), m_model, SLOT( onItemRowsAddedBegin( int, int ) ) ); + connect( this, SIGNAL( beginChildRowsRemoved( int, int ) ), m_model, SLOT( onItemRowsRemovedBegin( int, int ) ) ); connect( this, SIGNAL( childRowsAdded() ), m_model, SLOT( onItemRowsAddedDone() ) ); connect( this, SIGNAL( childRowsRemoved() ), m_model, SLOT( onItemRowsRemovedDone() ) ); connect( this, SIGNAL( updated() ), m_model, SLOT( itemUpdated() ) ); connect( this, SIGNAL( selectRequest( SourceTreeItem* ) ), m_model, SLOT( itemSelectRequest( SourceTreeItem* ) ) ); connect( this, SIGNAL( expandRequest( SourceTreeItem* ) ), m_model, SLOT( itemExpandRequest( SourceTreeItem* ) ) ); - if( !m_parent ) + connect( this, SIGNAL( toggleExpandRequest( SourceTreeItem* ) ), m_model, SLOT( itemToggleExpandRequest( SourceTreeItem* ) ) ); + + if ( !m_parent ) return; // caller must call begin/endInsertRows - if( index < 0 ) + if ( index < 0 ) m_parent->appendChild( this ); else m_parent->insertChild( index, this ); diff --git a/src/sourcetree/items/sourcetreeitem.h b/src/sourcetree/items/sourcetreeitem.h index 814cc0f2d..4e17f7e35 100644 --- a/src/sourcetree/items/sourcetreeitem.h +++ b/src/sourcetree/items/sourcetreeitem.h @@ -25,6 +25,7 @@ #include "sourcesmodel.h" class QMimeData; + class SourceTreeItem : public QObject { Q_OBJECT @@ -80,6 +81,7 @@ signals: void updated(); void selectRequest( SourceTreeItem* ); void expandRequest( SourceTreeItem* ); + void toggleExpandRequest( SourceTreeItem* ); void beginChildRowsAdded( int fromRow, int toRow ); void childRowsAdded(); @@ -90,6 +92,7 @@ signals: protected: void setRowType( SourcesModel::RowType t ) { m_type = t; } void setParentItem( SourceTreeItem* item ) { m_parent = item; } + private: SourcesModel::RowType m_type; diff --git a/src/sourcetree/sourcedelegate.cpp b/src/sourcetree/sourcedelegate.cpp index 13c538c95..331df0243 100644 --- a/src/sourcetree/sourcedelegate.cpp +++ b/src/sourcetree/sourcedelegate.cpp @@ -21,7 +21,7 @@ #include "sourcedelegate.h" #include "items/sourcetreeitem.h" -#include "items/collectionitem.h" +#include "items/sourceitem.h" #include "items/playlistitems.h" #include "items/categoryitems.h" #include "items/temporarypageitem.h" @@ -37,7 +37,7 @@ #include