categoryview.cpp
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "categoryview.h"
00021 #include "categoryview.moc"
00022
00023 #include "../blokkalaccount.h"
00024 #include "../blokkalblog.h"
00025 #include "../blokkalentry.h"
00026 #include "../blokkalio/categorymanager.h"
00027
00028 #include "blogdelegate.h"
00029
00030 #include <kdebug.h>
00031
00032 #include <QSortFilterProxyModel>
00033
00034 class Blokkal::Ui::CategoryModel::Private {
00035 public:
00036 Private( const Blog * blog ):
00037 blog( blog ) {}
00038 const Blog * const blog;
00039 };
00040
00041 Blokkal::Ui::CategoryModel::CategoryModel( Blokkal::Blog * blog, QObject * parent ):
00042 TreeModel( new TreeModel::TreeItemNode( 0, blog ), parent ),
00043 d( new Private( blog ) )
00044 {
00045 Blokkal::Account * account = d->blog->account();
00046 Blokkal::Io::CategoryManager * manager = account->categoryManager();
00047 Blokkal::Io::CategoryList categories = manager->categories( blog->id() );
00048 for( Blokkal::Io::CategoryList::ConstIterator it = categories.begin();
00049 it != categories.end();
00050 ++it )
00051 {
00052 addCategory( d->blog->id(), *it );
00053 }
00054
00055 connect( manager,
00056 SIGNAL( categoryAdded( const QString &, Blokkal::Io::Category * ) ),
00057 SLOT( addCategory( const QString &, Blokkal::Io::Category * ) ) );
00058 connect( manager,
00059 SIGNAL( categoryRemoved( const QString &, Blokkal::Io::Category * ) ),
00060 SLOT( removeCategory( const QString &, Blokkal::Io::Category * ) ) );
00061 }
00062
00063 Blokkal::Ui::CategoryModel::~CategoryModel( void )
00064 {
00065 }
00066
00067
00068 void Blokkal::Ui::CategoryModel::addCategory( const QString & blogId, Blokkal::Io::Category * category )
00069 {
00070 if( blogId != d->blog->id() ) {
00071 return;
00072 }
00073
00074 beginInsertRows( QModelIndex(),
00075 root()->children.size(),
00076 root()->children.size() );
00077 new TreeItemNode( root(), category );
00078 endInsertRows();
00079
00080 connect( category,
00081 SIGNAL( updated( Blokkal::Io::Category* ) ),
00082 SLOT( emitDataChanged( Blokkal::Io::Category* ) ) );
00083 }
00084
00085 void Blokkal::Ui::CategoryModel::removeCategory( const QString & blogId, Blokkal::Io::Category * category )
00086 {
00087 if( blogId != d->blog->id() ) {
00088 return;
00089 }
00090
00091 TreeItemNode * categoryNode;
00092 for( int i = 0; i != root()->children.size(); ++i ) {
00093 categoryNode = root()->children.at(i);
00094 if( ((Blokkal::Io::Category*)categoryNode->data.toULongLong() ) == category ) {
00095 break;
00096 }
00097 categoryNode = 0;
00098 }
00099
00100 if( !categoryNode ) {
00101 return;
00102 }
00103
00104 int index = root()->children.indexOf( categoryNode );
00105 beginRemoveRows( QModelIndex(),
00106 index,
00107 index );
00108 delete root()->children.takeAt( index );
00109 endRemoveRows();
00110 }
00111
00112
00113 void Blokkal::Ui::CategoryModel::emitDataChanged( Blokkal::Io::Category * category )
00114 {
00115 TreeItemNode * node;
00116 for( int i = 0; i != root()->children.size(); ++i ) {
00117 node = root()->children.at(i);
00118 if( ((Blokkal::Io::Category*)node->data.toULongLong() ) == category ) {
00119 QModelIndex index = createIndex( node->parent->children.indexOf( node ),
00120 0,
00121 node );
00122 emit dataChanged( index, index );
00123 return;
00124 }
00125 }
00126 }
00127
00128 QVariant Blokkal::Ui::CategoryModel::data( const QModelIndex & index, int role ) const
00129 {
00130 if( role != SortRole ) {
00131 return TreeModel::data( index, role );
00132 }
00133
00134 if( !index.isValid() ) {
00135 return QVariant();
00136 }
00137
00138 Io::Category * const category = dynamic_cast<Io::Category*>( (QObject*) index.data().toULongLong() );
00139 if( !category ) {
00140 kError() << "invalid data type encountered" << endl;
00141 return QVariant();
00142 }
00143
00144 return category->name();
00145 }
00146
00147
00148
00149
00150 class Blokkal::Ui::CategoryView::Private {
00151 public:
00152 Private( Blokkal::Entry * entry, bool exclusive ) :
00153 entry( entry ),
00154 exclusive( exclusive ){}
00155
00156 Blokkal::Entry * entry;
00157 bool exclusive;
00158 };
00159
00160 Blokkal::Ui::CategoryView::CategoryView( Blokkal::Entry * entry, bool exclusive, QWidget * parent ) :
00161 BlogView( parent, BlogDelegate::DisplayCheckBoxes ),
00162 d( new Private( entry, exclusive ) )
00163 {
00164 setSelectionMode( NoSelection );
00165 QSortFilterProxyModel * sortModel = new QSortFilterProxyModel( this );
00166 sortModel->setSourceModel( new CategoryModel( entry->blog() ) );
00167 sortModel->setSortRole( CategoryModel::SortRole );
00168 setModel( sortModel );
00169
00170 model()->sort( 0 );
00171 setRootIsDecorated( FALSE );
00172 }
00173
00174 Blokkal::Ui::CategoryView::~CategoryView( void )
00175 {
00176 delete d;
00177 }
00178
00179 void Blokkal::Ui::CategoryView::selectCategories( const QStringList & ids )
00180 {
00181 for( int i = 0; i < model()->rowCount(); ++i ) {
00182 QModelIndex index = model()->index( i, 0 );
00183 Blokkal::Io::Category * category = dynamic_cast<Blokkal::Io::Category*>( (QObject*) index.data().toULongLong() );
00184 if( !category ) {
00185 kDebug() << "model contains data types other than categories" << endl;
00186 continue;
00187 }
00188
00189 setChecked( index, ids.contains( category->id() ) );
00190
00191 if( d->exclusive && isChecked( index ) ) {
00192 return;
00193 }
00194 }
00195 }
00196
00197 QStringList Blokkal::Ui::CategoryView::selectedCategories( void ) const
00198 {
00199 QStringList ids;
00200
00201 for( int i = 0; i < model()->rowCount(); ++i ) {
00202 QModelIndex index = model()->index( i, 0 );
00203 Blokkal::Io::Category * category = dynamic_cast<Blokkal::Io::Category*>( (QObject*) index.data().toULongLong() );
00204 if( !category ) {
00205 kDebug() << "model contains data types other than categories" << endl;
00206 continue;
00207 }
00208
00209 if( isChecked( index ) ) {
00210 ids.append( category->id() );
00211 }
00212 }
00213
00214 return ids;
00215 }