00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include <opie2/odebug.h>
00023 #include <opie2/opimrecordlist.h>
00024 #include <opie2/oresource.h>
00025
00026 #include <qpe/timestring.h>
00027
00028 #include "abtable.h"
00029
00030 #include <errno.h>
00031 #include <fcntl.h>
00032 #include <unistd.h>
00033 #include <stdlib.h>
00034
00035 #include <ctype.h>
00036
00037 #if 0
00038
00045 AbTableItem::AbTableItem( QTable *t, EditType et, const QString &s,
00046 const QString &secondSortKey)
00047 : QTableItem( t, et, s )
00048 {
00049
00050 sortKey = Qtopia::buildSortKey( s, secondSortKey );
00051 }
00052
00053 int AbTableItem::alignment() const
00054 {
00055 return AlignLeft|AlignVCenter;
00056 }
00057
00058 QString AbTableItem::key() const
00059 {
00060 return sortKey;
00061 }
00062
00063
00064 void AbTableItem::setItem( const QString &txt, const QString &secondKey )
00065 {
00066 setText( txt );
00067 sortKey = Qtopia::buildSortKey( txt, secondKey );
00068
00069
00070 }
00071
00078 AbPickItem::AbPickItem( QTable *t ) :
00079 QTableItem(t, WhenCurrent, "?")
00080 {
00081 }
00082
00083 QWidget *AbPickItem::createEditor() const
00084 {
00085 QComboBox* combo = new QComboBox( table()->viewport() );
00086 ( (AbPickItem*)this )->cb = combo;
00087 AbTable* t = static_cast<AbTable*>(table());
00088 QStringList c = t->choiceNames();
00089 int cur = 0;
00090 for (QStringList::ConstIterator it = c.begin(); it!=c.end(); ++it) {
00091 if ( *it == text() )
00092 cur = combo->count();
00093 combo->insertItem(*it);
00094 }
00095 combo->setCurrentItem(cur);
00096 return combo;
00097 }
00098
00099 void AbPickItem::setContentFromEditor( QWidget *w )
00100 {
00101 if ( w->inherits("QComboBox") )
00102 setText( ( (QComboBox*)w )->currentText() );
00103 else
00104 QTableItem::setContentFromEditor( w );
00105 }
00106
00107 #endif
00108
00115 AbTable::AbTable( const QValueList<int> order, QWidget *parent, const char *name )
00116 : QTable( parent, name ),
00117 lastSortCol( -1 ),
00118 asc( TRUE ),
00119 intFields( order ),
00120 enablePainting( true ),
00121 columnVisible( true ),
00122 countNested( 0 )
00123 {
00124
00125 setSelectionMode( NoSelection );
00126 init();
00127 setSorting( false );
00128
00129 connect( this, SIGNAL(clicked(int,int,int,const QPoint&)),
00130 this, SLOT(itemClicked(int,int)) );
00131
00132
00133
00134 }
00135
00136 AbTable::~AbTable()
00137 {
00138 }
00139
00140 void AbTable::init()
00141 {
00142
00143 setNumRows( 0 );
00144 setNumCols( 2 );
00145
00146 horizontalHeader()->setLabel( 0, tr( "Full Name" ));
00147 horizontalHeader()->setLabel( 1, tr( "Contact" ));
00148 setLeftMargin( 0 );
00149 verticalHeader()->hide();
00150 columnVisible = true;
00151 }
00152
00153 void AbTable::setContacts( const Opie::OPimContactAccess::List& viewList )
00154 {
00155 odebug << "AbTable::setContacts()" << oendl;
00156
00157 clear();
00158 m_viewList = viewList;
00159
00160 setPaintingEnabled( FALSE );
00161
00162 setNumRows( m_viewList.count() );
00163
00164
00165 updateVisible();
00166
00167 setPaintingEnabled( TRUE );
00168
00169 }
00170
00171 void AbTable::setOrderedList( const QValueList<int> ordered )
00172 {
00173 intFields = ordered;
00174 }
00175
00176
00177 bool AbTable::selectContact( int UID )
00178 {
00179 odebug << "AbTable::selectContact( " << UID << " )" << oendl;
00180 int rows = numRows();
00181 bool found = false;
00182
00183 setPaintingEnabled( FALSE );
00184 odebug << "Search start" << oendl;
00185 for ( int r = 0; r < rows; ++r ) {
00186 if ( m_viewList.uidAt( r ) == UID ){
00187 ensureCellVisible( r, 0 );
00188 setCurrentCell( r, 0 );
00189 found = true;
00190 break;
00191 }
00192 }
00193 odebug << "Search end" << oendl;
00194
00195 if ( !found ){
00196 ensureCellVisible( 0,0 );
00197 setCurrentCell( 0, 0 );
00198 }
00199
00200 setPaintingEnabled( TRUE );
00201
00202 return true;
00203 }
00204
00205
00206 void AbTable::columnClicked( int col )
00207 {
00208 odebug << "columClicked(" << col << ")" << oendl;
00209
00210 if ( col == 0 ){
00211 odebug << "Change sort order: " << asc << oendl;
00212 asc = !asc;
00213 emit signalSortOrderChanged( asc );
00214 }
00215 }
00216
00217 void AbTable::resort()
00218 {
00219 owarn << "void AbTable::resort() NOT POSSIBLE !!" << oendl;
00220
00221 }
00222
00223 Opie::OPimContact AbTable::currentEntry()
00224 {
00225 return m_viewList[currentRow()];
00226 }
00227
00228 int AbTable::currentEntry_UID()
00229 {
00230 return ( currentEntry().uid() );
00231 }
00232
00233 void AbTable::clear()
00234 {
00235 odebug << "void AbTable::clear()" << oendl;
00236
00237
00238 setPaintingEnabled( FALSE );
00239 for ( int r = 0; r < numRows(); ++r ) {
00240 for ( int c = 0; c < numCols(); ++c ) {
00241 if ( cellWidget( r, c ) )
00242 clearCellWidget( r, c );
00243 clearCell( r, c );
00244 }
00245 }
00246 setNumRows( 0 );
00247 setPaintingEnabled( TRUE );
00248 }
00249
00250
00251 void AbTable::refresh()
00252 {
00253 owarn << "void AbTable::refresh() NOT IMPLEMENTED !!" << oendl;
00254
00255 #if 0
00256 int rows = numRows();
00257 AbTableItem *abi;
00258 ContactItem contactItem;
00259
00260 setPaintingEnabled( FALSE );
00261 for ( int r = 0; r < rows; ++r ) {
00262 abi = static_cast<AbTableItem*>( item(r, 0) );
00263 contactItem = findContactContact( contactList[abi], r );
00264 static_cast<AbTableItem*>( item(r, 1) )->setItem( contactItem.value, abi->text() );
00265 if ( !contactItem.icon.isNull() ){
00266 static_cast<AbTableItem*>( item(r, 1) )->
00267 setPixmap( contactItem.icon );
00268 }else{
00269 static_cast<AbTableItem*>( item(r, 1) )->
00270 setPixmap( QPixmap() );
00271 }
00272 }
00273 resort();
00274 setPaintingEnabled( TRUE );
00275
00276 #endif
00277 }
00278
00279 void AbTable::keyPressEvent( QKeyEvent *e )
00280 {
00281 char key = toupper( e->ascii() );
00282
00283 if ( key >= 'A' && key <= 'Z' )
00284 moveTo( key );
00285
00286
00287 switch( e->key() ) {
00288 case Qt::Key_Space:
00289 case Qt::Key_Return:
00290 case Qt::Key_Enter:
00291 emit signalSwitch();
00292 break;
00293
00294
00295
00296
00297
00298
00299
00300
00301 default:
00302 QTable::keyPressEvent( e );
00303 }
00304
00305 }
00306
00307 void AbTable::moveTo( char )
00308 {
00309 odebug << "void AbTable::moveTo( char c ) NOT IMPLEMENTED !!" << oendl;
00310
00311 }
00312
00313 #if 0
00314
00315 QString AbTable::findContactName( const Opie::OPimContact &entry )
00316 {
00317
00318 QString str;
00319 str = entry.fileAs();
00320 if ( str.isEmpty() ) {
00321 str = entry.company();
00322 if ( str.isEmpty() ) {
00323 str = entry.defaultEmail();
00324 }
00325 }
00326 return str;
00327 }
00328 #endif
00329
00330
00331 void AbTable::resizeRows() {
00332
00333
00334
00335
00336
00337
00338
00339
00340 }
00341
00342
00343 void AbTable::realignTable()
00344 {
00345
00346
00347 setPaintingEnabled( FALSE );
00348
00349 resizeRows();
00350 fitColumns();
00351
00352 setPaintingEnabled( TRUE );
00353
00354 }
00355
00356
00357
00358
00359 #if QT_VERSION <= 230
00360 #ifndef SINGLE_APP
00361 void QTable::paintEmptyArea( QPainter *p, int cx, int cy, int cw, int ch )
00362 {
00363
00364 QRegion reg( QRect( cx, cy, cw, ch ) );
00365
00366 reg = reg.subtract( QRect( QPoint( 0, 0 ), tableSize() ) );
00367
00368 QArray<QRect> r = reg.rects();
00369 for (unsigned int i=0; i<r.count(); i++)
00370 p->fillRect( r[i], colorGroup().brush( QColorGroup::Base ) );
00371 }
00372 #endif
00373 #endif
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393 void AbTable::fitColumns()
00394 {
00395 odebug << "void AbTable::fitColumns()" << oendl;
00396 int contentsWidth = visibleWidth() / 2;
00397
00398
00399
00400 setPaintingEnabled( FALSE );
00401
00402 if ( columnVisible == false ){
00403 showColumn(0);
00404 columnVisible = true;
00405 }
00406
00407
00408
00409 setColumnWidth( 0, contentsWidth );
00410 adjustColumn(1);
00411 if ( columnWidth(1) < contentsWidth )
00412 setColumnWidth( 1, contentsWidth );
00413
00414 setPaintingEnabled( TRUE );
00415 }
00416
00417 void AbTable::show()
00418 {
00419
00420 realignTable();
00421 QTable::show();
00422 }
00423
00424 #if 0
00425 void AbTable::setChoiceNames( const QStringList& list)
00426 {
00427 choicenames = list;
00428 if ( choicenames.isEmpty() ) {
00429
00430 setNumCols( 2 );
00431 } else {
00432
00433 setNumCols( 3 );
00434 setColumnWidth( 2, fontMetrics().width(tr( "Pick" ))+8 );
00435 horizontalHeader()->setLabel( 2, tr( "Pick" ));
00436 }
00437 fitColumns();
00438 }
00439 #endif
00440
00441 void AbTable::itemClicked(int,int col)
00442 {
00443
00444 if ( col == 2 ) {
00445 return;
00446 } else {
00447
00448 emit signalSwitch();
00449 }
00450 }
00451
00452 #if 0
00453 QStringList AbTable::choiceNames() const
00454 {
00455 return choicenames;
00456 }
00457
00458 #endif
00459 void AbTable::setChoiceSelection( const QValueList<int>& list )
00460 {
00461 intFields = list;
00462 }
00463
00464 QStringList AbTable::choiceSelection(int ) const
00465 {
00466 QStringList r;
00467
00468
00469
00470
00471
00472
00473
00474
00475
00476
00477
00478 return r;
00479 }
00480
00481
00482 void AbTable::updateVisible()
00483 {
00484
00485
00486 int visible,
00487 totalRows,
00488 row,
00489 selectedRow = 0;
00490
00491 visible = 0;
00492
00493 setPaintingEnabled( FALSE );
00494
00495 realignTable();
00496
00497 totalRows = numRows();
00498 for ( row = 0; row < totalRows; row++ ) {
00499 if ( rowHeight(row) == 0 ) {
00500 showRow( row );
00501 adjustRow( row );
00502 if ( isSelected( row,0 ) || isSelected( row,1 ) )
00503 selectedRow = row;
00504 }
00505 visible++;
00506 }
00507
00508 if ( selectedRow )
00509 setCurrentCell( selectedRow, 0 );
00510
00511 if ( !visible )
00512 setCurrentCell( -1, 0 );
00513
00514 setPaintingEnabled( TRUE );
00515 }
00516
00517
00518 void AbTable::setPaintingEnabled( bool e )
00519 {
00520
00521
00522
00523 if ( e ) {
00524 if ( countNested > 0 )
00525 --countNested;
00526 if ( ! countNested ){
00527 setUpdatesEnabled( true );
00528 enablePainting = true;
00529 rowHeightChanged( 0 );
00530 viewport()->update();
00531 }
00532 } else {
00533 ++countNested;
00534 enablePainting = false;
00535 setUpdatesEnabled( false );
00536 }
00537
00538
00539 }
00540
00541 void AbTable::viewportPaintEvent( QPaintEvent* e ) {
00542
00543
00544 if ( enablePainting )
00545 QTable::viewportPaintEvent( e );
00546 }
00547
00548 void AbTable::paintCell(QPainter* p, int row, int col, const QRect& cr, bool ) {
00549 const QColorGroup &cg = colorGroup();
00550
00551 p->save();
00552
00553
00554
00555 Opie::OPimContact act_contact = m_viewList[row];
00556
00557
00558 if ( (row % 2 ) == 0 ) {
00559 p->fillRect( 0, 0, cr.width(), cr.height(), cg.brush( QColorGroup::Base ) );
00560 p->setPen( QPen( cg.text() ) );
00561 }
00562 else {
00563 p->fillRect( 0, 0, cr.width(), cr.height(), cg.brush( QColorGroup::Background ) );
00564 p->setPen( QPen( cg.buttonText() ) );
00565 }
00566
00567 QFont f = p->font();
00568 QFontMetrics fm(f);
00569
00570 int marg = 2;
00571 int x = 0;
00572 int y = ( cr.height() - 14 ) / 2;
00573
00574 QString nameText = act_contact.fileAs();
00575
00576 switch( col ){
00577 case 0:
00578 p->drawText( x + marg,2 + fm.ascent(), nameText );
00579 break;
00580 case 1:{
00581
00582 ContactItem contactItem = findContactContact( act_contact, 0 );
00583 QPixmap contactPic = contactItem.icon;
00584 QString contactText = contactItem.value;
00585
00586 if ( !contactPic.isNull() )
00587 {
00588 p->drawPixmap( x + marg, y, contactPic );
00589 p->drawText( x + marg + contactPic.width()
00590 + 4,2 + fm.ascent(), contactText );
00591 }
00592 else
00593 {
00594 p->drawText( x + marg,2 + fm.ascent(), contactText );
00595 }
00596 }
00597 break;
00598
00599 }
00600 p->restore();
00601 }
00602
00603 void AbTable::rowHeightChanged( int row )
00604 {
00605 if ( enablePainting )
00606 QTable::rowHeightChanged( row );
00607 }
00608 ContactItem AbTable::findContactContact( const Opie::OPimContact &entry, int )
00609 {
00610
00611 int iconsize = fontMetrics().height();
00612 QImage icon;
00613
00614 ContactItem item;
00615 item.value = "";
00616
00617 for ( QValueList<int>::ConstIterator it = intFields.begin();
00618 it != intFields.end(); ++it ) {
00619 icon.reset();
00620
00621 switch ( *it ) {
00622 default:
00623 break;
00624 case Qtopia::Title:
00625 item.value = entry.title();
00626 break;
00627 case Qtopia::Suffix:
00628 item.value = entry.suffix();
00629 break;
00630 case Qtopia::FileAs:
00631 item.value = entry.fileAs();
00632 break;
00633 case Qtopia::DefaultEmail:
00634 item.value = entry.defaultEmail();
00635 if ( !item.value.isEmpty() )
00636 icon = Opie::Core::OResource::loadPixmap( "addressbook/email" );
00637 break;
00638 case Qtopia::Emails:
00639 item.value = entry.emails();
00640 if ( !item.value.isEmpty() )
00641 icon = Opie::Core::OResource::loadPixmap( "addressbook/email" );
00642 break;
00643 case Qtopia::HomeStreet:
00644 item.value = entry.homeStreet();
00645 break;
00646 case Qtopia::HomeCity:
00647 item.value = entry.homeCity();
00648 break;
00649 case Qtopia::HomeState:
00650 item.value = entry.homeState();
00651 break;
00652 case Qtopia::HomeZip:
00653 item.value = entry.homeZip();
00654 break;
00655 case Qtopia::HomeCountry:
00656 item.value = entry.homeCountry();
00657 break;
00658 case Qtopia::HomePhone:
00659 item.value = entry.homePhone();
00660 if ( !item.value.isEmpty() )
00661 icon = Opie::Core::OResource::loadPixmap( "addressbook/phonehome" );
00662 break;
00663 case Qtopia::HomeFax:
00664 item.value = entry.homeFax();
00665 if ( !item.value.isEmpty() )
00666 icon = Opie::Core::OResource::loadPixmap( "addressbook/faxhome" );
00667 break;
00668 case Qtopia::HomeMobile:
00669 item.value = entry.homeMobile();
00670 if ( !item.value.isEmpty() )
00671 icon = Opie::Core::OResource::loadPixmap( "addressbook/mobilehome" );
00672 break;
00673 case Qtopia::HomeWebPage:
00674 item.value = entry.homeWebpage();
00675 if ( !item.value.isEmpty() )
00676 icon = Opie::Core::OResource::loadPixmap( "addressbook/webpagehome" );
00677 break;
00678 case Qtopia::Company:
00679 item.value = entry.company();
00680 break;
00681 case Qtopia::BusinessCity:
00682 item.value = entry.businessCity();
00683 break;
00684 case Qtopia::BusinessStreet:
00685 item.value = entry.businessStreet();
00686 break;
00687 case Qtopia::BusinessZip:
00688 item.value = entry.businessZip();
00689 break;
00690 case Qtopia::BusinessCountry:
00691 item.value = entry.businessCountry();
00692 break;
00693 case Qtopia::BusinessWebPage:
00694 item.value = entry.businessWebpage();
00695 if ( !item.value.isEmpty() )
00696 icon = Opie::Core::OResource::loadPixmap( "addressbook/webpagework" );
00697 break;
00698 case Qtopia::JobTitle:
00699 item.value = entry.jobTitle();
00700 break;
00701 case Qtopia::Department:
00702 item.value = entry.department();
00703 break;
00704 case Qtopia::Office:
00705 item.value = entry.office();
00706 break;
00707 case Qtopia::BusinessPhone:
00708 item.value = entry.businessPhone();
00709 if ( !item.value.isEmpty() )
00710 icon = Opie::Core::OResource::loadPixmap( "addressbook/phonework" );
00711 break;
00712 case Qtopia::BusinessFax:
00713 item.value = entry.businessFax();
00714 if ( !item.value.isEmpty() )
00715 icon = Opie::Core::OResource::loadPixmap( "addressbook/faxwork" );
00716 break;
00717 case Qtopia::BusinessMobile:
00718 item.value = entry.businessMobile();
00719 if ( !item.value.isEmpty() )
00720 icon = Opie::Core::OResource::loadPixmap( "addressbook/mobilework" );
00721 break;
00722 case Qtopia::BusinessPager:
00723 item.value = entry.businessPager();
00724 break;
00725 case Qtopia::Profession:
00726 item.value = entry.profession();
00727 break;
00728 case Qtopia::Assistant:
00729 item.value = entry.assistant();
00730 break;
00731 case Qtopia::Manager:
00732 item.value = entry.manager();
00733 break;
00734 case Qtopia::Spouse:
00735 item.value = entry.spouse();
00736 break;
00737 case Qtopia::Gender:
00738 item.value = entry.gender();
00739 break;
00740 case Qtopia::Birthday:
00741 if ( ! entry.birthday().isNull() ){
00742 item.value = TimeString::numberDateString( entry.birthday() );
00743 }
00744 break;
00745 case Qtopia::Anniversary:
00746 if ( ! entry.anniversary().isNull() ){
00747 item.value = TimeString::numberDateString( entry.anniversary() );
00748 }
00749 break;
00750 case Qtopia::Nickname:
00751 item.value = entry.nickname();
00752 break;
00753 case Qtopia::Children:
00754 item.value = entry.children();
00755 break;
00756 case Qtopia::Notes:
00757 item.value = entry.notes();
00758 break;
00759 }
00760
00761 if ( !icon.isNull() ) {
00762 item.icon = icon.smoothScale( iconsize, iconsize );
00763 }
00764
00765 if ( !item.value.isEmpty() )
00766 break;
00767 }
00768 return item;
00769 }