kdeui Library API Documentation

klistviewsearchline.cpp

00001 /* This file is part of the KDE libraries 00002 Copyright (c) 2003 Scott Wheeler <wheeler@kde.org> 00003 00004 This library is free software; you can redistribute it and/or 00005 modify it under the terms of the GNU Library General Public 00006 License version 2 as published by the Free Software Foundation. 00007 00008 This library is distributed in the hope that it will be useful, 00009 but WITHOUT ANY WARRANTY; without even the implied warranty of 00010 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00011 Library General Public License for more details. 00012 00013 You should have received a copy of the GNU Library General Public License 00014 along with this library; see the file COPYING.LIB. If not, write to 00015 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, 00016 Boston, MA 02111-1307, USA. 00017 */ 00018 00019 #include "klistviewsearchline.h" 00020 00021 #include <klistview.h> 00022 #include <kdebug.h> 00023 #include <klocale.h> 00024 00025 #include <qtimer.h> 00026 #include <qpopupmenu.h> 00027 00028 #define KLISTVIEWSEARCHLINE_ALLCOLUMNS_ID 2004 00029 00030 class KListViewSearchLine::KListViewSearchLinePrivate 00031 { 00032 public: 00033 KListViewSearchLinePrivate() : 00034 listView(0), 00035 caseSensitive(false), 00036 activeSearch(false), 00037 keepParentsVisible(true), 00038 queuedSearches(0) {} 00039 00040 KListView *listView; 00041 bool caseSensitive; 00042 bool activeSearch; 00043 bool keepParentsVisible; 00044 QString search; 00045 int queuedSearches; 00046 QValueList<int> searchColumns; 00047 }; 00048 00050 // public methods 00052 00053 KListViewSearchLine::KListViewSearchLine(QWidget *parent, KListView *listView, const char *name) : 00054 KLineEdit(parent, name) 00055 { 00056 d = new KListViewSearchLinePrivate; 00057 00058 d->listView = listView; 00059 00060 connect(this, SIGNAL(textChanged(const QString &)), 00061 this, SLOT(queueSearch(const QString &))); 00062 00063 if(listView) { 00064 connect(listView, SIGNAL(destroyed()), 00065 this, SLOT(listViewDeleted())); 00066 00067 connect(listView, SIGNAL(itemAdded(QListViewItem *)), 00068 this, SLOT(itemAdded(QListViewItem *))); 00069 } 00070 else 00071 setEnabled(false); 00072 } 00073 00074 KListViewSearchLine::KListViewSearchLine(QWidget *parent, const char *name) : 00075 KLineEdit(parent, name) 00076 { 00077 d = new KListViewSearchLinePrivate; 00078 00079 d->listView = 0L; 00080 00081 connect(this, SIGNAL(textChanged(const QString &)), 00082 this, SLOT(queueSearch(const QString &))); 00083 00084 setEnabled(false); 00085 } 00086 00087 KListViewSearchLine::~KListViewSearchLine() 00088 { 00089 delete d; 00090 } 00091 00092 bool KListViewSearchLine::caseSensitive() const 00093 { 00094 return d->caseSensitive; 00095 } 00096 00097 QValueList<int> KListViewSearchLine::searchColumns() const 00098 { 00099 return d->searchColumns; 00100 } 00101 00102 bool KListViewSearchLine::keepParentsVisible() const 00103 { 00104 return d->keepParentsVisible; 00105 } 00106 00107 KListView *KListViewSearchLine::listView() const 00108 { 00109 return d->listView; 00110 } 00111 00113 // public slots 00115 00116 void KListViewSearchLine::updateSearch(const QString &s) 00117 { 00118 if(!d->listView) 00119 return; 00120 00121 d->search = s.isNull() ? text() : s; 00122 00123 // If there's a selected item that is visible, make sure that it's visible 00124 // when the search changes too (assuming that it still matches). 00125 00126 QListViewItem *currentItem = 0; 00127 00128 switch(d->listView->selectionMode()) 00129 { 00130 case KListView::NoSelection: 00131 break; 00132 case KListView::Single: 00133 currentItem = d->listView->selectedItem(); 00134 break; 00135 default: 00136 { 00137 int flags = QListViewItemIterator::Selected | QListViewItemIterator::Visible; 00138 for(QListViewItemIterator it(d->listView, flags); 00139 it.current() && !currentItem; 00140 ++it) 00141 { 00142 if(d->listView->itemRect(it.current()).isValid()) 00143 currentItem = it.current(); 00144 } 00145 } 00146 } 00147 00148 if(d->keepParentsVisible) 00149 checkItemParentsVisible(d->listView->firstChild()); 00150 else 00151 checkItemParentsNotVisible(); 00152 00153 if(currentItem) 00154 d->listView->ensureItemVisible(currentItem); 00155 } 00156 00157 void KListViewSearchLine::setCaseSensitive(bool cs) 00158 { 00159 d->caseSensitive = cs; 00160 } 00161 00162 void KListViewSearchLine::setKeepParentsVisible(bool v) 00163 { 00164 d->keepParentsVisible = v; 00165 } 00166 00167 void KListViewSearchLine::setSearchColumns(const QValueList<int> &columns) 00168 { 00169 d->searchColumns = columns; 00170 } 00171 00172 void KListViewSearchLine::setListView(KListView *lv) 00173 { 00174 if(d->listView) { 00175 disconnect(d->listView, SIGNAL(destroyed()), 00176 this, SLOT(listViewDeleted())); 00177 00178 disconnect(d->listView, SIGNAL(itemAdded(QListViewItem *)), 00179 this, SLOT(itemAdded(QListViewItem *))); 00180 } 00181 00182 d->listView = lv; 00183 00184 if(lv) { 00185 connect(d->listView, SIGNAL(destroyed()), 00186 this, SLOT(listViewDeleted())); 00187 00188 connect(d->listView, SIGNAL(itemAdded(QListViewItem *)), 00189 this, SLOT(itemAdded(QListViewItem *))); 00190 } 00191 00192 setEnabled(bool(lv)); 00193 } 00194 00196 // protected members 00198 00199 bool KListViewSearchLine::itemMatches(const QListViewItem *item, const QString &s) const 00200 { 00201 if(s.isEmpty()) 00202 return true; 00203 00204 // If the search column list is populated, search just the columns 00205 // specifified. If it is empty default to searching all of the columns. 00206 00207 if(!d->searchColumns.isEmpty()) { 00208 QValueList<int>::ConstIterator it = d->searchColumns.begin(); 00209 for(; it != d->searchColumns.end(); ++it) { 00210 if(*it < item->listView()->columns() && 00211 item->text(*it).find(s, 0, d->caseSensitive) >= 0) 00212 return true; 00213 } 00214 } 00215 else { 00216 for(int i = 0; i < item->listView()->columns(); i++) { 00217 if(item->text(i).find(s, 0, d->caseSensitive) >= 0) 00218 return true; 00219 } 00220 } 00221 00222 return false; 00223 } 00224 00225 QPopupMenu *KListViewSearchLine::createPopupMenu() 00226 { 00227 QPopupMenu *popup = KLineEdit::createPopupMenu(); 00228 00229 QPopupMenu *subMenu = new QPopupMenu( popup ); 00230 connect( subMenu, SIGNAL( activated(int) ), this, SLOT( searchColumnsMenuActivated(int) ) ); 00231 00232 popup->insertSeparator(); 00233 popup->insertItem( i18n("Search Columns"), subMenu ); 00234 00235 subMenu->insertItem(i18n("All Columns"), KLISTVIEWSEARCHLINE_ALLCOLUMNS_ID); 00236 subMenu->insertSeparator(); 00237 00238 bool allColumnsAreSearchColumns = true; 00239 for(int i = 0; i < d->listView->columns(); i++) { 00240 subMenu->insertItem(d->listView->columnText(i), i); 00241 if (d->searchColumns.isEmpty() || d->searchColumns.find(i) != d->searchColumns.end()) 00242 subMenu->setItemChecked(i, true); 00243 else 00244 allColumnsAreSearchColumns = false; 00245 } 00246 subMenu->setItemChecked(KLISTVIEWSEARCHLINE_ALLCOLUMNS_ID, allColumnsAreSearchColumns); 00247 00248 // searchColumnsMenuActivated() relies on one possible "all" representation 00249 if (allColumnsAreSearchColumns && !d->searchColumns.isEmpty()) 00250 d->searchColumns.clear(); 00251 00252 return popup; 00253 } 00254 00256 // protected slots 00258 00259 void KListViewSearchLine::queueSearch(const QString &search) 00260 { 00261 d->queuedSearches++; 00262 d->search = search; 00263 QTimer::singleShot(200, this, SLOT(activateSearch())); 00264 } 00265 00266 void KListViewSearchLine::activateSearch() 00267 { 00268 d->queuedSearches--; 00269 00270 if(d->queuedSearches == 0) 00271 updateSearch(d->search); 00272 } 00273 00275 // private slots 00277 00278 void KListViewSearchLine::itemAdded(QListViewItem *item) const 00279 { 00280 item->setVisible(itemMatches(item, text())); 00281 } 00282 00283 void KListViewSearchLine::listViewDeleted() 00284 { 00285 d->listView = 0; 00286 setEnabled(false); 00287 } 00288 00289 void KListViewSearchLine::searchColumnsMenuActivated(int id) 00290 { 00291 if (id==KLISTVIEWSEARCHLINE_ALLCOLUMNS_ID) { 00292 if (d->searchColumns.isEmpty()) 00293 d->searchColumns.append(0); 00294 else 00295 d->searchColumns.clear(); 00296 } 00297 else { 00298 if (d->searchColumns.find(id) != d->searchColumns.end()) 00299 d->searchColumns.remove(id); 00300 else { 00301 if (d->searchColumns.isEmpty()) 00302 for(int i = 0; i < d->listView->columns(); i++) { 00303 if (i!=id) 00304 d->searchColumns.append(i); 00305 } 00306 else 00307 d->searchColumns.append(id); 00308 } 00309 } 00310 updateSearch(); 00311 } 00312 00314 // private methods 00316 00317 void KListViewSearchLine::checkItemParentsNotVisible() 00318 { 00319 QListViewItemIterator it(d->listView); 00320 for(; it.current(); ++it) 00321 { 00322 QListViewItem *item = it.current(); 00323 if(itemMatches(item, d->search)) 00324 item->setVisible(true); 00325 else 00326 item->setVisible(false); 00327 } 00328 } 00329 00330 bool KListViewSearchLine::checkItemParentsVisible(QListViewItem *item) 00331 { 00332 bool visible = false; 00333 for(; item; item = item->nextSibling()) { 00334 if((item->firstChild() && checkItemParentsVisible(item->firstChild())) || 00335 itemMatches(item, d->search)) 00336 { 00337 item->setVisible( true ); 00338 visible = true; 00339 } 00340 else 00341 item->setVisible(false); 00342 } 00343 return visible; 00344 } 00345 00346 #include "klistviewsearchline.moc"
KDE Logo
This file is part of the documentation for kdeui Library Version 3.3.0.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Wed Sep 29 09:40:33 2004 by doxygen 1.3.8 written by Dimitri van Heesch, © 1997-2003