author | kergoth <kergoth> | 2002-01-25 22:14:26 (UTC) |
---|---|---|
committer | kergoth <kergoth> | 2002-01-25 22:14:26 (UTC) |
commit | 15318cad33835e4e2dc620d033e43cd930676cdd (patch) (unidiff) | |
tree | c2fa0399a2c47fda8e2cd0092c73a809d17f68eb /core/pim/addressbook | |
download | opie-15318cad33835e4e2dc620d033e43cd930676cdd.zip opie-15318cad33835e4e2dc620d033e43cd930676cdd.tar.gz opie-15318cad33835e4e2dc620d033e43cd930676cdd.tar.bz2 |
Initial revision
-rw-r--r-- | core/pim/addressbook/.cvsignore | 16 | ||||
-rw-r--r-- | core/pim/addressbook/Makefile.in | 244 | ||||
-rw-r--r-- | core/pim/addressbook/abeditor.cpp | 619 | ||||
-rw-r--r-- | core/pim/addressbook/abeditor.h | 79 | ||||
-rw-r--r-- | core/pim/addressbook/ablabel.cpp | 53 | ||||
-rw-r--r-- | core/pim/addressbook/ablabel.h | 50 | ||||
-rw-r--r-- | core/pim/addressbook/abtable.cpp | 1091 | ||||
-rw-r--r-- | core/pim/addressbook/abtable.h | 140 | ||||
-rw-r--r-- | core/pim/addressbook/addressbook.cpp | 829 | ||||
-rw-r--r-- | core/pim/addressbook/addressbook.cw | 26 | ||||
-rw-r--r-- | core/pim/addressbook/addressbook.h | 99 | ||||
-rw-r--r-- | core/pim/addressbook/addressbook.pro | 22 | ||||
-rw-r--r-- | core/pim/addressbook/addresspicker.cpp | 52 | ||||
-rw-r--r-- | core/pim/addressbook/addresspicker.h | 39 | ||||
-rw-r--r-- | core/pim/addressbook/addresssettings.cpp | 136 | ||||
-rw-r--r-- | core/pim/addressbook/addresssettings.h | 47 | ||||
-rw-r--r-- | core/pim/addressbook/addresssettingsbase.ui | 170 | ||||
-rw-r--r-- | core/pim/addressbook/main.cpp | 41 | ||||
-rw-r--r-- | core/pim/addressbook/qpe-addressbook.control | 9 |
19 files changed, 3762 insertions, 0 deletions
diff --git a/core/pim/addressbook/.cvsignore b/core/pim/addressbook/.cvsignore new file mode 100644 index 0000000..28d87f2 --- a/dev/null +++ b/core/pim/addressbook/.cvsignore | |||
@@ -0,0 +1,16 @@ | |||
1 | moc_* | ||
2 | Makefile | ||
3 | abeditorbase.h | ||
4 | abaddress.h | ||
5 | abcompanybase.h | ||
6 | abnamebase.h | ||
7 | abeditorbase.cpp | ||
8 | abaddress.cpp | ||
9 | abcompanybase.cpp | ||
10 | abnamebase.cpp | ||
11 | abeditorpage2base.ui | ||
12 | abeditorpage2base.h | ||
13 | abeditorpage2base.cpp | ||
14 | addresssettingsbase.h | ||
15 | addresssettingsbase.cpp | ||
16 | |||
diff --git a/core/pim/addressbook/Makefile.in b/core/pim/addressbook/Makefile.in new file mode 100644 index 0000000..93c73c3 --- a/dev/null +++ b/core/pim/addressbook/Makefile.in | |||
@@ -0,0 +1,244 @@ | |||
1 | ############################################################################# | ||
2 | |||
3 | ####### Compiler, tools and options | ||
4 | |||
5 | CXX =$(SYSCONF_CXX) $(QT_CXX_MT) | ||
6 | CXXFLAGS=$(SYSCONF_CXXFLAGS_QT) $(SYSCONF_CXXFLAGS) | ||
7 | CC =$(SYSCONF_CC) $(QT_C_MT) | ||
8 | CFLAGS =$(SYSCONF_CFLAGS) | ||
9 | INCPATH =-I$(QPEDIR)/include | ||
10 | LFLAGS =$(SYSCONF_LFLAGS_QT) $(SYSCONF_RPATH_QT) $(SYSCONF_LFLAGS) $(QT_LFLAGS_MT) | ||
11 | LIBS =$(SUBLIBS) -lqpe $(SYSCONF_LIBS_QT) $(SYSCONF_LIBS) $(SYSCONF_LIBS_QTAPP) | ||
12 | MOC =$(SYSCONF_MOC) | ||
13 | UIC =$(SYSCONF_UIC) | ||
14 | |||
15 | ####### Target | ||
16 | |||
17 | DESTDIR = $(QPEDIR)/bin/ | ||
18 | VER_MAJ = 1 | ||
19 | VER_MIN = 0 | ||
20 | VER_PATCH = 0 | ||
21 | TARGET= addressbook | ||
22 | TARGET1 = lib$(TARGET).so.$(VER_MAJ) | ||
23 | |||
24 | ####### Files | ||
25 | |||
26 | HEADERS =addressbook.h \ | ||
27 | abeditor.h \ | ||
28 | ablabel.h \ | ||
29 | abtable.h \ | ||
30 | addresssettings.h | ||
31 | SOURCES =main.cpp \ | ||
32 | addressbook.cpp \ | ||
33 | abeditor.cpp \ | ||
34 | ablabel.cpp \ | ||
35 | abtable.cpp \ | ||
36 | addresssettings.cpp | ||
37 | OBJECTS =main.o \ | ||
38 | addressbook.o \ | ||
39 | abeditor.o \ | ||
40 | ablabel.o \ | ||
41 | abtable.o \ | ||
42 | addresssettings.o \ | ||
43 | addresssettingsbase.o | ||
44 | INTERFACES = addresssettingsbase.ui | ||
45 | UICDECLS = addresssettingsbase.h | ||
46 | UICIMPLS = addresssettingsbase.cpp | ||
47 | SRCMOC =moc_addressbook.cpp \ | ||
48 | moc_abeditor.cpp \ | ||
49 | moc_ablabel.cpp \ | ||
50 | moc_abtable.cpp \ | ||
51 | moc_addresssettings.cpp \ | ||
52 | moc_addresssettingsbase.cpp | ||
53 | OBJMOC =moc_addressbook.o \ | ||
54 | moc_abeditor.o \ | ||
55 | moc_ablabel.o \ | ||
56 | moc_abtable.o \ | ||
57 | moc_addresssettings.o \ | ||
58 | moc_addresssettingsbase.o | ||
59 | |||
60 | |||
61 | ####### Implicit rules | ||
62 | |||
63 | .SUFFIXES: .cpp .cxx .cc .C .c | ||
64 | |||
65 | .cpp.o: | ||
66 | $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< | ||
67 | |||
68 | .cxx.o: | ||
69 | $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< | ||
70 | |||
71 | .cc.o: | ||
72 | $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< | ||
73 | |||
74 | .C.o: | ||
75 | $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< | ||
76 | |||
77 | .c.o: | ||
78 | $(CC) -c $(CFLAGS) $(INCPATH) -o $@ $< | ||
79 | |||
80 | ####### Build rules | ||
81 | |||
82 | |||
83 | all: $(DESTDIR)$(TARGET) | ||
84 | |||
85 | $(DESTDIR)$(TARGET): $(UICDECLS) $(OBJECTS) $(OBJMOC) $(SUBLIBS) | ||
86 | $(SYSCONF_LINK) $(LFLAGS) -o $(DESTDIR)$(TARGET) $(OBJECTS) $(OBJMOC) $(LIBS) | ||
87 | |||
88 | moc: $(SRCMOC) | ||
89 | |||
90 | tmake: | ||
91 | tmake p4addressbook.pro | ||
92 | |||
93 | clean: | ||
94 | -rm -f $(OBJECTS) $(OBJMOC) $(SRCMOC) $(UICIMPLS) $(UICDECLS) | ||
95 | -rm -f *~ core | ||
96 | -rm -f allmoc.cpp | ||
97 | |||
98 | ####### Extension Modules | ||
99 | |||
100 | listpromodules: | ||
101 | @echo | ||
102 | |||
103 | listallmodules: | ||
104 | @echo | ||
105 | |||
106 | listaddonpromodules: | ||
107 | @echo | ||
108 | |||
109 | listaddonentmodules: | ||
110 | @echo | ||
111 | |||
112 | |||
113 | REQUIRES= | ||
114 | |||
115 | ####### Sub-libraries | ||
116 | |||
117 | |||
118 | ###### Combined headers | ||
119 | |||
120 | |||
121 | |||
122 | ####### Compile | ||
123 | |||
124 | main.o: main.cpp \ | ||
125 | addressbook.h \ | ||
126 | $(QPEDIR)/include/qpe/qpeapplication.h \ | ||
127 | $(QPEDIR)/include/qpe/qcopenvelope_qws.h | ||
128 | |||
129 | addressbook.o: addressbook.cpp \ | ||
130 | abeditor.h \ | ||
131 | $(QPEDIR)/include/qpe/contact.h \ | ||
132 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
133 | $(QPEDIR)/include/qpe/recordfields.h \ | ||
134 | ablabel.h \ | ||
135 | abtable.h \ | ||
136 | $(QPEDIR)/include/qpe/categories.h \ | ||
137 | addresssettings.h \ | ||
138 | addresssettingsbase.h \ | ||
139 | addressbook.h \ | ||
140 | $(QPEDIR)/include/qpe/qpeapplication.h \ | ||
141 | $(QPEDIR)/include/qpe/config.h \ | ||
142 | $(QPEDIR)/include/qpe/finddialog.h \ | ||
143 | $(QPEDIR)/include/qpe/global.h \ | ||
144 | $(QPEDIR)/include/qpe/resource.h \ | ||
145 | $(QPEDIR)/include/qpe/ir.h \ | ||
146 | $(QPEDIR)/include/qpe/qpemessagebox.h \ | ||
147 | $(QPEDIR)/include/qpe/qcopenvelope_qws.h \ | ||
148 | $(QPEDIR)/include/qpe/qpemenubar.h \ | ||
149 | $(QPEDIR)/include/qpe/qpetoolbar.h | ||
150 | |||
151 | abeditor.o: abeditor.cpp \ | ||
152 | abeditor.h \ | ||
153 | $(QPEDIR)/include/qpe/contact.h \ | ||
154 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
155 | $(QPEDIR)/include/qpe/recordfields.h \ | ||
156 | addresspicker.h \ | ||
157 | $(QPEDIR)/include/qpe/categoryselect.h \ | ||
158 | $(QPEDIR)/include/qpe/qpeapplication.h \ | ||
159 | $(QPEDIR)/include/qpe/qpedialog.h | ||
160 | |||
161 | ablabel.o: ablabel.cpp \ | ||
162 | ablabel.h \ | ||
163 | $(QPEDIR)/include/qpe/contact.h \ | ||
164 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
165 | $(QPEDIR)/include/qpe/recordfields.h \ | ||
166 | $(QPEDIR)/include/qpe/stringutil.h | ||
167 | |||
168 | abtable.o: abtable.cpp \ | ||
169 | $(QPEDIR)/include/qpe/categoryselect.h \ | ||
170 | $(QPEDIR)/include/qpe/config.h \ | ||
171 | $(QPEDIR)/include/qpe/stringutil.h \ | ||
172 | $(QPEDIR)/include/qpe/qcopenvelope_qws.h \ | ||
173 | abtable.h \ | ||
174 | $(QPEDIR)/include/qpe/categories.h \ | ||
175 | $(QPEDIR)/include/qpe/contact.h \ | ||
176 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
177 | $(QPEDIR)/include/qpe/recordfields.h | ||
178 | |||
179 | addresssettings.o: addresssettings.cpp \ | ||
180 | addresssettings.h \ | ||
181 | addresssettingsbase.h \ | ||
182 | $(QPEDIR)/include/qpe/config.h \ | ||
183 | $(QPEDIR)/include/qpe/contact.h \ | ||
184 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
185 | $(QPEDIR)/include/qpe/recordfields.h | ||
186 | |||
187 | addresssettingsbase.h: addresssettingsbase.ui | ||
188 | $(UIC) addresssettingsbase.ui -o $(INTERFACE_DECL_PATH)/addresssettingsbase.h | ||
189 | |||
190 | addresssettingsbase.cpp: addresssettingsbase.ui | ||
191 | $(UIC) addresssettingsbase.ui -i addresssettingsbase.h -o addresssettingsbase.cpp | ||
192 | |||
193 | addresssettingsbase.o: addresssettingsbase.cpp \ | ||
194 | addresssettingsbase.h \ | ||
195 | addresssettingsbase.ui | ||
196 | |||
197 | moc_addressbook.o: moc_addressbook.cpp \ | ||
198 | addressbook.h | ||
199 | |||
200 | moc_abeditor.o: moc_abeditor.cpp \ | ||
201 | abeditor.h \ | ||
202 | $(QPEDIR)/include/qpe/contact.h \ | ||
203 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
204 | $(QPEDIR)/include/qpe/recordfields.h | ||
205 | |||
206 | moc_ablabel.o: moc_ablabel.cpp \ | ||
207 | ablabel.h \ | ||
208 | $(QPEDIR)/include/qpe/contact.h \ | ||
209 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
210 | $(QPEDIR)/include/qpe/recordfields.h | ||
211 | |||
212 | moc_abtable.o: moc_abtable.cpp \ | ||
213 | abtable.h \ | ||
214 | $(QPEDIR)/include/qpe/categories.h \ | ||
215 | $(QPEDIR)/include/qpe/contact.h \ | ||
216 | $(QPEDIR)/include/qpe/palmtoprecord.h \ | ||
217 | $(QPEDIR)/include/qpe/recordfields.h | ||
218 | |||
219 | moc_addresssettings.o: moc_addresssettings.cpp \ | ||
220 | addresssettings.h \ | ||
221 | addresssettingsbase.h | ||
222 | |||
223 | moc_addresssettingsbase.o: moc_addresssettingsbase.cpp \ | ||
224 | addresssettingsbase.h | ||
225 | |||
226 | moc_addressbook.cpp: addressbook.h | ||
227 | $(MOC) addressbook.h -o moc_addressbook.cpp | ||
228 | |||
229 | moc_abeditor.cpp: abeditor.h | ||
230 | $(MOC) abeditor.h -o moc_abeditor.cpp | ||
231 | |||
232 | moc_ablabel.cpp: ablabel.h | ||
233 | $(MOC) ablabel.h -o moc_ablabel.cpp | ||
234 | |||
235 | moc_abtable.cpp: abtable.h | ||
236 | $(MOC) abtable.h -o moc_abtable.cpp | ||
237 | |||
238 | moc_addresssettings.cpp: addresssettings.h | ||
239 | $(MOC) addresssettings.h -o moc_addresssettings.cpp | ||
240 | |||
241 | moc_addresssettingsbase.cpp: addresssettingsbase.h | ||
242 | $(MOC) addresssettingsbase.h -o moc_addresssettingsbase.cpp | ||
243 | |||
244 | |||
diff --git a/core/pim/addressbook/abeditor.cpp b/core/pim/addressbook/abeditor.cpp new file mode 100644 index 0000000..6354db9 --- a/dev/null +++ b/core/pim/addressbook/abeditor.cpp | |||
@@ -0,0 +1,619 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include "abeditor.h" | ||
22 | #include "addresspicker.h" | ||
23 | |||
24 | #include <qpe/categoryselect.h> | ||
25 | #include <qpe/qpeapplication.h> | ||
26 | #include <qpe/qpedialog.h> | ||
27 | |||
28 | #include <qcombobox.h> | ||
29 | #include <qlabel.h> | ||
30 | #include <qlayout.h> | ||
31 | #include <qlineedit.h> | ||
32 | #include <qmultilineedit.h> | ||
33 | #include <qscrollview.h> | ||
34 | #include <qtoolbutton.h> | ||
35 | #include <qpushbutton.h> | ||
36 | #include <qmainwindow.h> | ||
37 | |||
38 | |||
39 | static inline bool containsAlphaNum( const QString &str ); | ||
40 | static inline bool constainsWhiteSpace( const QString &str ); | ||
41 | |||
42 | |||
43 | // helper functions, convert our comma delimited list to proper | ||
44 | // file format... | ||
45 | void parseEmailFrom( const QString &txt, QString &strDefaultEmail, | ||
46 | QString &strAll ); | ||
47 | |||
48 | // helper convert from file format to comma delimited... | ||
49 | void parseEmailTo( const QString &strDefaultEmail, | ||
50 | const QString &strOtherEmail, QString &strBack ); | ||
51 | |||
52 | |||
53 | |||
54 | AbEditor::AbEditor( const Contact &entry, const QValueList<int> *newOrdered, | ||
55 | QStringList *slNewOrdered, | ||
56 | QWidget *parent = 0, const char *name = 0, WFlags fl = 0 ) | ||
57 | : QDialog( parent, name, TRUE, fl ), | ||
58 | orderedValues( newOrdered ), | ||
59 | slOrdered( slNewOrdered ) | ||
60 | { | ||
61 | init(); | ||
62 | initMap(); | ||
63 | setEntry( entry ); | ||
64 | } | ||
65 | |||
66 | AbEditor::~AbEditor() | ||
67 | { | ||
68 | } | ||
69 | |||
70 | void AbEditor::init() | ||
71 | { | ||
72 | middleEdit = 0; | ||
73 | QVBoxLayout *vb = new QVBoxLayout( this ); | ||
74 | svPage = new QScrollView( this ); | ||
75 | svPage->setHScrollBarMode( QScrollView::AlwaysOff ); | ||
76 | vb->addWidget( svPage ); | ||
77 | svPage->setResizePolicy( QScrollView::AutoOneFit ); | ||
78 | svPage->setFrameStyle( QFrame::NoFrame ); | ||
79 | |||
80 | QWidget *container = new QWidget( svPage->viewport() ); | ||
81 | svPage->addChild( container ); | ||
82 | |||
83 | QGridLayout *gl = new QGridLayout( container, 20, 2, 4, 2 ); | ||
84 | |||
85 | QLabel *l = new QLabel( tr("First Name"), container ); | ||
86 | gl->addWidget( l, 0, 0 ); | ||
87 | firstEdit = new QLineEdit( container ); | ||
88 | gl->addWidget( firstEdit, 0, 1 ); | ||
89 | |||
90 | l = new QLabel( tr("Last Name"), container ); | ||
91 | gl->addWidget( l, 1, 0 ); | ||
92 | lastEdit = new QLineEdit( container ); | ||
93 | gl->addWidget( lastEdit, 1, 1 ); | ||
94 | |||
95 | l = new QLabel( tr("Categories"), container ); | ||
96 | gl->addWidget( l, 2, 0 ); | ||
97 | |||
98 | cmbCat = new CategorySelect( container ); | ||
99 | gl->addWidget( cmbCat, 2, 1 ); | ||
100 | |||
101 | int i; | ||
102 | bool foundGender, | ||
103 | foundNotes; | ||
104 | foundGender = foundNotes = false; | ||
105 | QStringList::ConstIterator it = slOrdered->begin(); | ||
106 | for ( i = 0; it != slOrdered->end(); i++, ++it ) { | ||
107 | if ( !foundGender && *it == tr("Gender") ) { | ||
108 | foundGender = true; | ||
109 | } else if ( !foundNotes && *it == tr("Notes") ) { | ||
110 | foundNotes = true; | ||
111 | } else { | ||
112 | l = new QLabel( *it, container ); | ||
113 | listName.append( l ); | ||
114 | gl->addWidget( l, i + 3, 0 ); | ||
115 | QLineEdit *e = new QLineEdit( container ); | ||
116 | listValue.append( e ); | ||
117 | gl->addWidget( e, i + 3, 1 ); | ||
118 | if ( *it == tr( "Middle Name" ) ) | ||
119 | middleEdit = e; | ||
120 | } | ||
121 | } | ||
122 | l = new QLabel( tr("Gender"), container ); | ||
123 | gl->addWidget( l, slOrdered->count() + 3, 0 ); | ||
124 | genderCombo = new QComboBox( container ); | ||
125 | genderCombo->insertItem( "", 0 ); | ||
126 | genderCombo->insertItem( tr( "Male" ), 1 ); | ||
127 | genderCombo->insertItem( tr( "Female" ), 2 ); | ||
128 | gl->addWidget( genderCombo, slOrdered->count() + 3, 1 ); | ||
129 | |||
130 | dlgNote = new QDialog( this, "Note Dialog", TRUE ); | ||
131 | dlgNote->setCaption( tr("Enter Note") ); | ||
132 | QVBoxLayout *vbNote = new QVBoxLayout( dlgNote ); | ||
133 | // lblNote = new QLabel( dlgNote ); | ||
134 | // lblNote->setMinimumSize( lblNote->sizeHint() + QSize( 0, 4 ) ); | ||
135 | // vbNote->addWidget( lblNote ); | ||
136 | txtNote = new QMultiLineEdit( dlgNote ); | ||
137 | vbNote->addWidget( txtNote ); | ||
138 | |||
139 | QHBoxLayout *hb = new QHBoxLayout( vb ); | ||
140 | hb->addStretch( 2 ); | ||
141 | QPushButton *pb = new QPushButton( tr("Notes..."), this ); | ||
142 | hb->addWidget( pb ); | ||
143 | connect( pb, SIGNAL(clicked()), this, SLOT(slotNote()) ); | ||
144 | |||
145 | new QPEDialogListener(this); | ||
146 | } | ||
147 | |||
148 | void AbEditor::initMap() | ||
149 | { | ||
150 | /* | ||
151 | // since the fields and the XML fields exist, create a map | ||
152 | // between them... | ||
153 | Config cfg1( "AddressBook" ); | ||
154 | Config cfg2( "AddressBook" ); | ||
155 | QString strCfg1, | ||
156 | strCfg2; | ||
157 | int i; | ||
158 | |||
159 | // This stuff better exist... | ||
160 | cfg1.setGroup( "AddressFields" ); | ||
161 | cfg2.setGroup( "XMLFields" ); | ||
162 | i = 0; | ||
163 | strCfg1 = cfg1.readEntry( "Field" + QString::number(i), QString::null ); | ||
164 | strCfg2 = cfg2.readEntry( "XMLField" + QString::number(i++), | ||
165 | QString::null ); | ||
166 | while ( !strCfg1.isNull() && !strCfg2.isNull() ) { | ||
167 | mapField.insert( strCfg1, strCfg2 ); | ||
168 | strCfg1 = cfg1.readEntry( "Field" + QString::number(i), | ||
169 | QString::null ); | ||
170 | strCfg2 = cfg2.readEntry( "XMLField" + QString::number(i++), | ||
171 | QString::null ); | ||
172 | } | ||
173 | */ | ||
174 | } | ||
175 | |||
176 | void AbEditor::loadFields() | ||
177 | { | ||
178 | QStringList::ConstIterator it; | ||
179 | QListIterator<QLabel> lit( listName ); | ||
180 | for ( it = slOrdered->begin(); *lit; ++lit, ++it ) { | ||
181 | (*lit)->setText( *it ); | ||
182 | } | ||
183 | } | ||
184 | |||
185 | void AbEditor::setEntry( const Contact &entry ) | ||
186 | { | ||
187 | ent = entry; | ||
188 | QListIterator<QLineEdit> it( listValue ); | ||
189 | firstEdit->setText( ent.firstName() ); | ||
190 | lastEdit->setText( ent.lastName() ); | ||
191 | cmbCat->setCategories( ent.categories(), "Contacts", tr("Contacts") ); | ||
192 | |||
193 | // ### Fix... | ||
194 | QValueList<int>::ConstIterator itVl; | ||
195 | for ( itVl = orderedValues->begin(); *it && itVl != orderedValues->end(); | ||
196 | ++itVl, ++it ) { | ||
197 | switch( *itVl ) { | ||
198 | case Qtopia::Title: | ||
199 | (*it)->setText(ent.title()); | ||
200 | break; | ||
201 | case Qtopia::MiddleName: | ||
202 | (*it)->setText( ent.middleName() ); | ||
203 | break; | ||
204 | case Qtopia::Suffix: | ||
205 | (*it)->setText( ent.suffix() ); | ||
206 | break; | ||
207 | |||
208 | |||
209 | case Qtopia::DefaultEmail: | ||
210 | case Qtopia::Emails: | ||
211 | { | ||
212 | QString strDefEmail = ent.defaultEmail(); | ||
213 | QString strAllEmail = ent.emails(); | ||
214 | QString strFinal; | ||
215 | parseEmailTo( strDefEmail, strAllEmail, strFinal ); | ||
216 | (*it)->setText( strFinal ); | ||
217 | // make sure we see the "default" | ||
218 | (*it)->home( false ); | ||
219 | break; | ||
220 | } | ||
221 | |||
222 | // home | ||
223 | case Qtopia::HomeStreet: | ||
224 | (*it)->setText(ent.homeStreet() ); | ||
225 | break; | ||
226 | case Qtopia::HomeCity: | ||
227 | (*it)->setText( ent.homeCity() ); | ||
228 | break; | ||
229 | case Qtopia::HomeState: | ||
230 | (*it)->setText( ent.homeState() ); | ||
231 | break; | ||
232 | case Qtopia::HomeZip: | ||
233 | (*it)->setText( ent.homeZip() ); | ||
234 | break; | ||
235 | case Qtopia::HomeCountry: | ||
236 | (*it)->setText( ent.homeCountry() ); | ||
237 | break; | ||
238 | case Qtopia::HomePhone: | ||
239 | (*it)->setText( ent.homePhone() ); | ||
240 | break; | ||
241 | case Qtopia::HomeFax: | ||
242 | (*it)->setText( ent.homeFax() ); | ||
243 | break; | ||
244 | case Qtopia::HomeMobile: | ||
245 | (*it)->setText( ent.homeMobile() ); | ||
246 | break; | ||
247 | case Qtopia::HomeWebPage: | ||
248 | (*it)->setText( ent.homeWebpage() ); | ||
249 | break; | ||
250 | |||
251 | // business | ||
252 | case Qtopia::Company: | ||
253 | (*it)->setText( ent.company() ); | ||
254 | break; | ||
255 | case Qtopia::BusinessStreet: | ||
256 | (*it)->setText( ent.businessStreet() ); | ||
257 | break; | ||
258 | case Qtopia::BusinessCity: | ||
259 | (*it)->setText( ent.businessCity() ); | ||
260 | break; | ||
261 | case Qtopia::BusinessState: | ||
262 | (*it)->setText( ent.businessState() ); | ||
263 | break; | ||
264 | case Qtopia::BusinessZip: | ||
265 | (*it)->setText( ent.businessZip() ); | ||
266 | break; | ||
267 | case Qtopia::BusinessCountry: | ||
268 | (*it)->setText( ent.businessCountry() ); | ||
269 | break; | ||
270 | case Qtopia::BusinessWebPage: | ||
271 | (*it)->setText( ent.businessWebpage() ); | ||
272 | break; | ||
273 | case Qtopia::JobTitle: | ||
274 | (*it)->setText( ent.jobTitle() ); | ||
275 | break; | ||
276 | case Qtopia::Department: | ||
277 | (*it)->setText( ent.department() ); | ||
278 | break; | ||
279 | case Qtopia::Office: | ||
280 | (*it)->setText( ent.office() ); | ||
281 | break; | ||
282 | case Qtopia::BusinessPhone: | ||
283 | (*it)->setText( ent.businessPhone() ); | ||
284 | break; | ||
285 | case Qtopia::BusinessFax: | ||
286 | (*it)->setText( ent.businessFax() ); | ||
287 | break; | ||
288 | case Qtopia::BusinessMobile: | ||
289 | (*it)->setText( ent.businessMobile() ); | ||
290 | break; | ||
291 | case Qtopia::BusinessPager: | ||
292 | (*it)->setText( ent.businessPager() ); | ||
293 | break; | ||
294 | case Qtopia::Profession: | ||
295 | (*it)->setText( ent.profession() ); | ||
296 | break; | ||
297 | case Qtopia::Assistant: | ||
298 | (*it)->setText( ent.assistant() ); | ||
299 | break; | ||
300 | case Qtopia::Manager: | ||
301 | (*it)->setText( ent.manager() ); | ||
302 | break; | ||
303 | |||
304 | // personal | ||
305 | case Qtopia::Spouse: | ||
306 | (*it)->setText( ent.spouse() ); | ||
307 | break; | ||
308 | case Qtopia::Children: | ||
309 | (*it)->setText( ent.children() ); | ||
310 | break; | ||
311 | case Qtopia::Birthday: | ||
312 | (*it)->setText( ent.birthday() ); | ||
313 | break; | ||
314 | case Qtopia::Anniversary: | ||
315 | (*it)->setText( ent.anniversary() ); | ||
316 | break; | ||
317 | case Qtopia::Nickname: | ||
318 | (*it)->setText( ent.nickname() ); | ||
319 | break; | ||
320 | |||
321 | } | ||
322 | } | ||
323 | |||
324 | QString gender = ent.gender(); | ||
325 | genderCombo->setCurrentItem( gender.toInt() ); | ||
326 | |||
327 | txtNote->setText( ent.notes() ); | ||
328 | } | ||
329 | |||
330 | void AbEditor::accept() | ||
331 | { | ||
332 | if ( isEmpty() ) | ||
333 | reject(); | ||
334 | else { | ||
335 | saveEntry(); | ||
336 | QDialog::accept(); | ||
337 | } | ||
338 | } | ||
339 | |||
340 | bool AbEditor::isEmpty() | ||
341 | { | ||
342 | // analyze all the fields and make sure there is _something_ there | ||
343 | // that warrants saving... | ||
344 | QString t = firstEdit->text(); | ||
345 | if ( !t.isEmpty() && containsAlphaNum( t ) ) | ||
346 | return false; | ||
347 | |||
348 | t = lastEdit->text(); | ||
349 | if ( !t.isEmpty() && containsAlphaNum( t ) ) | ||
350 | return false; | ||
351 | |||
352 | QListIterator<QLineEdit> it( listValue ); | ||
353 | for ( ; it.current(); ++it ) { | ||
354 | t = it.current()->text(); | ||
355 | if ( !t.isEmpty() && containsAlphaNum( t ) ) | ||
356 | return false; | ||
357 | } | ||
358 | |||
359 | t = txtNote->text(); | ||
360 | if ( !t.isEmpty() && containsAlphaNum( t ) ) | ||
361 | return false; | ||
362 | |||
363 | return true; | ||
364 | } | ||
365 | |||
366 | void AbEditor::saveEntry() | ||
367 | { | ||
368 | QString strDefaultEmail, strOtherEmail; | ||
369 | |||
370 | // determine if there has been a change in names | ||
371 | if ( ent.firstName() != firstEdit->text() || | ||
372 | ent.lastName() != lastEdit->text() | ||
373 | || (middleEdit && ent.middleName() != middleEdit->text()) ) { | ||
374 | // set the names | ||
375 | ent.setFirstName( firstEdit->text() ); | ||
376 | ent.setLastName( lastEdit->text() ); | ||
377 | if ( middleEdit ) | ||
378 | ent.setMiddleName( middleEdit->text() ); | ||
379 | ent.setFileAs(); | ||
380 | } | ||
381 | |||
382 | ent.setCategories( cmbCat->currentCategories() ); | ||
383 | |||
384 | QListIterator<QLineEdit> it( listValue ); | ||
385 | int i; | ||
386 | QValueList<int>::ConstIterator<int> vlIt; | ||
387 | for ( i = 0, vlIt = orderedValues->begin(); | ||
388 | it.current(); ++it, ++vlIt, i++ ) { | ||
389 | switch( *vlIt ) { | ||
390 | case Qtopia::Title: | ||
391 | ent.setTitle( it.current()->text() ); | ||
392 | break; | ||
393 | case Qtopia::MiddleName: | ||
394 | ent.setMiddleName( it.current()->text() ); | ||
395 | break; | ||
396 | case Qtopia::Suffix: | ||
397 | ent.setSuffix( it.current()->text() ); | ||
398 | break; | ||
399 | // case Qtopia::Category: | ||
400 | // { | ||
401 | // // QStringList slCat = QStringList::split( ";", value ); | ||
402 | // // QValueList<int> cat; | ||
403 | // // for ( QStringList::ConstIterator it = slCat.begin(); | ||
404 | // // it != slCat.end(); ++it ) | ||
405 | // // cat.append( (*it).toInt() ); | ||
406 | // // ent.setCategories( cat ); | ||
407 | // } | ||
408 | // break; | ||
409 | |||
410 | |||
411 | case Qtopia::DefaultEmail: | ||
412 | case Qtopia::Emails: | ||
413 | parseEmailFrom( it.current()->text(), strDefaultEmail, | ||
414 | strOtherEmail ); | ||
415 | ent.setDefaultEmail( strDefaultEmail ); | ||
416 | ent.setEmails( strOtherEmail ); | ||
417 | break; | ||
418 | |||
419 | // home | ||
420 | case Qtopia::HomeStreet: | ||
421 | ent.setHomeStreet( it.current()->text() ); | ||
422 | break; | ||
423 | case Qtopia::HomeCity: | ||
424 | ent.setHomeCity( it.current()->text() ); | ||
425 | break; | ||
426 | case Qtopia::HomeState: | ||
427 | ent.setHomeState( it.current()->text() ); | ||
428 | break; | ||
429 | case Qtopia::HomeZip: | ||
430 | ent.setHomeZip( it.current()->text() ); | ||
431 | break; | ||
432 | case Qtopia::HomeCountry: | ||
433 | ent.setHomeCountry( it.current()->text() ); | ||
434 | break; | ||
435 | case Qtopia::HomePhone: | ||
436 | ent.setHomePhone( it.current()->text() ); | ||
437 | break; | ||
438 | case Qtopia::HomeFax: | ||
439 | ent.setHomeFax( it.current()->text() ); | ||
440 | break; | ||
441 | case Qtopia::HomeMobile: | ||
442 | ent.setHomeMobile( it.current()->text() ); | ||
443 | break; | ||
444 | case Qtopia::HomeWebPage: | ||
445 | ent.setHomeWebpage( it.current()->text() ); | ||
446 | break; | ||
447 | |||
448 | // business | ||
449 | case Qtopia::Company: | ||
450 | ent.setCompany( it.current()->text() ); | ||
451 | break; | ||
452 | case Qtopia::BusinessStreet: | ||
453 | ent.setBusinessStreet( it.current()->text() ); | ||
454 | break; | ||
455 | case Qtopia::BusinessCity: | ||
456 | ent.setBusinessCity( it.current()->text() ); | ||
457 | break; | ||
458 | case Qtopia::BusinessState: | ||
459 | ent.setBusinessState( it.current()->text() ); | ||
460 | break; | ||
461 | case Qtopia::BusinessZip: | ||
462 | ent.setBusinessZip( it.current()->text() ); | ||
463 | break; | ||
464 | case Qtopia::BusinessCountry: | ||
465 | ent.setBusinessCountry( it.current()->text() ); | ||
466 | break; | ||
467 | case Qtopia::BusinessWebPage: | ||
468 | ent.setBusinessWebpage( it.current()->text() ); | ||
469 | break; | ||
470 | case Qtopia::JobTitle: | ||
471 | ent.setJobTitle( it.current()->text() ); | ||
472 | break; | ||
473 | case Qtopia::Department: | ||
474 | ent.setDepartment( it.current()->text() ); | ||
475 | break; | ||
476 | case Qtopia::Office: | ||
477 | ent.setOffice( it.current()->text() ); | ||
478 | break; | ||
479 | case Qtopia::BusinessPhone: | ||
480 | ent.setBusinessPhone( it.current()->text() ); | ||
481 | break; | ||
482 | case Qtopia::BusinessFax: | ||
483 | ent.setBusinessFax( it.current()->text() ); | ||
484 | break; | ||
485 | case Qtopia::BusinessMobile: | ||
486 | ent.setBusinessMobile( it.current()->text() ); | ||
487 | break; | ||
488 | case Qtopia::BusinessPager: | ||
489 | ent.setBusinessPager( it.current()->text() ); | ||
490 | break; | ||
491 | case Qtopia::Profession: | ||
492 | ent.setProfession( it.current()->text() ); | ||
493 | break; | ||
494 | case Qtopia::Assistant: | ||
495 | ent.setAssistant( it.current()->text() ); | ||
496 | break; | ||
497 | case Qtopia::Manager: | ||
498 | ent.setManager( it.current()->text() ); | ||
499 | break; | ||
500 | |||
501 | // personal | ||
502 | case Qtopia::Spouse: | ||
503 | ent.setSpouse( it.current()->text() ); | ||
504 | break; | ||
505 | case Qtopia::Children: | ||
506 | ent.setChildren( it.current()->text() ); | ||
507 | break; | ||
508 | case Qtopia::Birthday: | ||
509 | ent.setBirthday( it.current()->text() ); | ||
510 | break; | ||
511 | case Qtopia::Anniversary: | ||
512 | ent.setAnniversary( it.current()->text() ); | ||
513 | break; | ||
514 | case Qtopia::Nickname: | ||
515 | ent.setNickname( it.current()->text() ); | ||
516 | break; | ||
517 | default: | ||
518 | break; | ||
519 | |||
520 | } | ||
521 | } | ||
522 | |||
523 | int gender = genderCombo->currentItem(); | ||
524 | ent.setGender( QString::number( gender ) ); | ||
525 | |||
526 | QString str = txtNote->text(); | ||
527 | if ( !str.isNull() ) | ||
528 | ent.setNotes( str ); | ||
529 | } | ||
530 | |||
531 | void AbEditor::slotNote() | ||
532 | { | ||
533 | dlgNote->showMaximized(); | ||
534 | if ( !dlgNote->exec() ) { | ||
535 | // reset the note... | ||
536 | txtNote->setText( ent.notes() ); | ||
537 | } | ||
538 | } | ||
539 | |||
540 | void AbEditor::setNameFocus() | ||
541 | { | ||
542 | firstEdit->setFocus(); | ||
543 | } | ||
544 | |||
545 | void parseEmailFrom( const QString &txt, QString &strDefaultEmail, | ||
546 | QString &strAll ) | ||
547 | { | ||
548 | int where, | ||
549 | start; | ||
550 | if ( txt.isEmpty() ) | ||
551 | return; | ||
552 | // find the first | ||
553 | where = txt.find( ',' ); | ||
554 | if ( where < 0 ) { | ||
555 | strDefaultEmail = txt; | ||
556 | strAll = txt; | ||
557 | } else { | ||
558 | strDefaultEmail = txt.left( where ).stripWhiteSpace(); | ||
559 | strAll = strDefaultEmail; | ||
560 | while ( where > -1 ) { | ||
561 | strAll.append(" "); | ||
562 | start = where; | ||
563 | where = txt.find( ',', where + 1 ); | ||
564 | if ( where > - 1 ) | ||
565 | strAll.append( txt.mid(start + 1, where - start - 1).stripWhiteSpace() ); | ||
566 | else // grab until the end... | ||
567 | strAll.append( txt.right(txt.length() - start - 1).stripWhiteSpace() ); | ||
568 | } | ||
569 | } | ||
570 | } | ||
571 | |||
572 | void parseEmailTo( const QString &strDefaultEmail, | ||
573 | const QString &strOtherEmail, QString &strBack ) | ||
574 | { | ||
575 | // create a comma dilimeted set of emails... | ||
576 | // use the power of short circuiting... | ||
577 | bool foundDefault = false; | ||
578 | QString strTmp; | ||
579 | int start = 0; | ||
580 | int where; | ||
581 | // start at the beginng. | ||
582 | strBack = strDefaultEmail; | ||
583 | where = 0; | ||
584 | while ( where > -1 ) { | ||
585 | start = where; | ||
586 | where = strOtherEmail.find( ' ', where + 1 ); | ||
587 | if ( where > 0 ) { | ||
588 | strTmp = strOtherEmail.mid( start, where - start ).stripWhiteSpace(); | ||
589 | } else | ||
590 | strTmp = strOtherEmail.right( strOtherEmail.length() - start ).stripWhiteSpace(); | ||
591 | if ( foundDefault || strTmp != strDefaultEmail ) { | ||
592 | strBack.append( ", " ); | ||
593 | strBack.append( strTmp ); | ||
594 | } else | ||
595 | foundDefault = true; | ||
596 | } | ||
597 | } | ||
598 | |||
599 | |||
600 | static inline bool containsAlphaNum( const QString &str ) | ||
601 | { | ||
602 | int i, | ||
603 | count = str.length(); | ||
604 | for ( i = 0; i < count; i++ ) | ||
605 | if ( !str[i].isSpace() ) | ||
606 | return TRUE; | ||
607 | return FALSE; | ||
608 | } | ||
609 | |||
610 | static inline bool constainsWhiteSpace( const QString &str ) | ||
611 | { | ||
612 | int i, | ||
613 | count = str.length(); | ||
614 | for (i = 0; i < count; i++ ) | ||
615 | if ( str[i].isSpace() ) | ||
616 | return TRUE; | ||
617 | return FALSE; | ||
618 | } | ||
619 | |||
diff --git a/core/pim/addressbook/abeditor.h b/core/pim/addressbook/abeditor.h new file mode 100644 index 0000000..9ce6704 --- a/dev/null +++ b/core/pim/addressbook/abeditor.h | |||
@@ -0,0 +1,79 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | #ifndef ABEDITOR_H | ||
21 | #define ABEDITOR_H | ||
22 | |||
23 | #include <qpe/contact.h> | ||
24 | |||
25 | #include <qdialog.h> | ||
26 | #include <qlist.h> | ||
27 | #include <qmap.h> | ||
28 | #include <qstringlist.h> | ||
29 | |||
30 | class QScrollView; | ||
31 | class QMultiLineEdit; | ||
32 | class QLineEdit; | ||
33 | class QLabel; | ||
34 | class QComboBox; | ||
35 | class CategorySelect; | ||
36 | |||
37 | class AbEditor : public QDialog | ||
38 | { | ||
39 | Q_OBJECT | ||
40 | public: | ||
41 | AbEditor( const Contact &entry, const QValueList<int> *newOrdedValues, | ||
42 | QStringList *slNewOrdered, | ||
43 | QWidget* parent = 0, const char* name = 0, WFlags fl = 0 ); | ||
44 | ~AbEditor(); | ||
45 | void loadFields(); | ||
46 | void setNameFocus(); | ||
47 | Contact entry() const { return ent; } | ||
48 | |||
49 | public slots: | ||
50 | void slotNote(); | ||
51 | void setEntry( const Contact &entry ); | ||
52 | |||
53 | protected slots: | ||
54 | void accept(); | ||
55 | |||
56 | private: | ||
57 | void init(); | ||
58 | void initMap(); | ||
59 | void saveEntry(); | ||
60 | bool isEmpty(); | ||
61 | |||
62 | private: | ||
63 | QDialog *dlgNote; | ||
64 | QLabel *lblNote; | ||
65 | QMultiLineEdit *txtNote; | ||
66 | Contact ent; | ||
67 | QScrollView *svPage; | ||
68 | QLineEdit *firstEdit; | ||
69 | QLineEdit *lastEdit; | ||
70 | QLineEdit *middleEdit; | ||
71 | QComboBox *genderCombo; | ||
72 | QList<QLineEdit> listValue; | ||
73 | QList<QLabel> listName; | ||
74 | const QValueList<int> *orderedValues; | ||
75 | QStringList *slOrdered; | ||
76 | CategorySelect *cmbCat; | ||
77 | }; | ||
78 | |||
79 | #endif | ||
diff --git a/core/pim/addressbook/ablabel.cpp b/core/pim/addressbook/ablabel.cpp new file mode 100644 index 0000000..3bf3e12 --- a/dev/null +++ b/core/pim/addressbook/ablabel.cpp | |||
@@ -0,0 +1,53 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include "ablabel.h" | ||
22 | |||
23 | #include <qpe/stringutil.h> | ||
24 | |||
25 | #include <qregexp.h> | ||
26 | #include <qstylesheet.h> | ||
27 | |||
28 | AbLabel::AbLabel( QWidget *parent, const char *name ) | ||
29 | : QTextView( parent, name ) | ||
30 | { | ||
31 | } | ||
32 | |||
33 | AbLabel::~AbLabel() | ||
34 | { | ||
35 | } | ||
36 | |||
37 | void AbLabel::init( const Contact &entry ) | ||
38 | { | ||
39 | ent = entry; | ||
40 | } | ||
41 | |||
42 | void AbLabel::sync() | ||
43 | { | ||
44 | QString text = ent.toRichText(); | ||
45 | setText( text ); | ||
46 | } | ||
47 | |||
48 | void AbLabel::keyPressEvent( QKeyEvent *e ) | ||
49 | { | ||
50 | if ( e->key() == Qt::Key_F33 ) { | ||
51 | emit okPressed(); | ||
52 | } | ||
53 | } | ||
diff --git a/core/pim/addressbook/ablabel.h b/core/pim/addressbook/ablabel.h new file mode 100644 index 0000000..cfbd999 --- a/dev/null +++ b/core/pim/addressbook/ablabel.h | |||
@@ -0,0 +1,50 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | #ifndef ABLABEL_H | ||
21 | #define ABLABEL_H | ||
22 | |||
23 | #include <qpe/contact.h> | ||
24 | #include <qtextview.h> | ||
25 | |||
26 | class AbLabel : public QTextView | ||
27 | { | ||
28 | Q_OBJECT | ||
29 | |||
30 | public: | ||
31 | AbLabel( QWidget *parent, const char *name = 0 ); | ||
32 | ~AbLabel(); | ||
33 | |||
34 | public slots: | ||
35 | void init( const Contact &entry ); | ||
36 | void sync(); | ||
37 | |||
38 | signals: | ||
39 | void okPressed(); | ||
40 | |||
41 | protected: | ||
42 | void keyPressEvent( QKeyEvent * ); | ||
43 | |||
44 | private: | ||
45 | Contact ent; | ||
46 | |||
47 | }; | ||
48 | |||
49 | #endif // ABLABEL_H | ||
50 | |||
diff --git a/core/pim/addressbook/abtable.cpp b/core/pim/addressbook/abtable.cpp new file mode 100644 index 0000000..0911edf --- a/dev/null +++ b/core/pim/addressbook/abtable.cpp | |||
@@ -0,0 +1,1091 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include <qpe/categoryselect.h> | ||
22 | #include <qpe/config.h> | ||
23 | #include <qpe/stringutil.h> | ||
24 | #include <qpe/qcopenvelope_qws.h> | ||
25 | |||
26 | #include <qasciidict.h> | ||
27 | #include <qdatetime.h> | ||
28 | #include <qfile.h> | ||
29 | |||
30 | #include "abtable.h" | ||
31 | |||
32 | #include <errno.h> | ||
33 | #include <fcntl.h> | ||
34 | #include <unistd.h> | ||
35 | #include <stdlib.h> | ||
36 | |||
37 | #include <ctype.h> //toupper() for key hack | ||
38 | |||
39 | static bool contactCompare( const Contact &cnt, const QRegExp &r, int category ); | ||
40 | |||
41 | //### qtmail/addresslist.cpp hardcodes this filename as well | ||
42 | static QString journalFileName() | ||
43 | { | ||
44 | QString str = getenv("HOME"); | ||
45 | str +="/.abjournal"; | ||
46 | return str; | ||
47 | } | ||
48 | |||
49 | |||
50 | |||
51 | /*! | ||
52 | \class AbTableItem abtable.h | ||
53 | |||
54 | \brief QTableItem based class for showing a field of an entry | ||
55 | */ | ||
56 | |||
57 | AbTableItem::AbTableItem( QTable *t, EditType et, const QString &s, | ||
58 | const QString &secondSortKey) | ||
59 | : QTableItem( t, et, s ) | ||
60 | { | ||
61 | // sortKey = s.lower() + QChar( '\0' ) + secondSortKey.lower(); | ||
62 | sortKey = Qtopia::buildSortKey( s, secondSortKey ); | ||
63 | } | ||
64 | |||
65 | int AbTableItem::alignment() const | ||
66 | { | ||
67 | return AlignLeft|AlignVCenter; | ||
68 | } | ||
69 | |||
70 | QString AbTableItem::key() const | ||
71 | { | ||
72 | return sortKey; | ||
73 | } | ||
74 | |||
75 | // A way to reset the item, without out doing a delete or a new... | ||
76 | void AbTableItem::setItem( const QString &txt, const QString &secondKey ) | ||
77 | { | ||
78 | setText( txt ); | ||
79 | sortKey = Qtopia::buildSortKey( txt, secondKey ); | ||
80 | |||
81 | // sortKey = txt.lower() + QChar( '\0' ) + secondKey.lower(); | ||
82 | } | ||
83 | |||
84 | /*! | ||
85 | \class AbPickItem abtable.h | ||
86 | |||
87 | \brief QTableItem based class for showing slection of an entry | ||
88 | */ | ||
89 | |||
90 | AbPickItem::AbPickItem( QTable *t ) : | ||
91 | QTableItem(t, WhenCurrent, "?") | ||
92 | { | ||
93 | } | ||
94 | |||
95 | QWidget *AbPickItem::createEditor() const | ||
96 | { | ||
97 | QComboBox* combo = new QComboBox( table()->viewport() ); | ||
98 | ( (AbPickItem*)this )->cb = combo; | ||
99 | AbTable* t = static_cast<AbTable*>(table()); | ||
100 | QStringList c = t->choiceNames(); | ||
101 | int cur = 0; | ||
102 | for (QStringList::ConstIterator it = c.begin(); it!=c.end(); ++it) { | ||
103 | if ( *it == text() ) | ||
104 | cur = combo->count(); | ||
105 | combo->insertItem(*it); | ||
106 | } | ||
107 | combo->setCurrentItem(cur); | ||
108 | return combo; | ||
109 | } | ||
110 | |||
111 | void AbPickItem::setContentFromEditor( QWidget *w ) | ||
112 | { | ||
113 | if ( w->inherits("QComboBox") ) | ||
114 | setText( ( (QComboBox*)w )->currentText() ); | ||
115 | else | ||
116 | QTableItem::setContentFromEditor( w ); | ||
117 | } | ||
118 | |||
119 | /*! | ||
120 | \class AbTable abtable.h | ||
121 | |||
122 | \brief QTable based class for showing a list of entries | ||
123 | */ | ||
124 | |||
125 | AbTable::AbTable( const QValueList<int> *order, QWidget *parent, const char *name ) | ||
126 | // #ifdef QT_QTABLE_NOHEADER_CONSTRUCTOR | ||
127 | // : QTable( 0, 0, parent, name, TRUE ), | ||
128 | // #else | ||
129 | : QTable( parent, name ), | ||
130 | // #endif | ||
131 | lastSortCol( -1 ), | ||
132 | asc( TRUE ), | ||
133 | intFields( order ), | ||
134 | currFindRow( -2 ), | ||
135 | mCat( 0 ) | ||
136 | { | ||
137 | mCat.load( categoryFileName() ); | ||
138 | setSelectionMode( NoSelection ); | ||
139 | init(); | ||
140 | setSorting( TRUE ); | ||
141 | connect( this, SIGNAL(clicked(int,int,int,const QPoint &)), | ||
142 | this, SLOT(itemClicked(int,int)) ); | ||
143 | } | ||
144 | |||
145 | AbTable::~AbTable() | ||
146 | { | ||
147 | } | ||
148 | |||
149 | void AbTable::init() | ||
150 | { | ||
151 | setNumRows( 0 ); | ||
152 | setNumCols( 2 ); | ||
153 | |||
154 | horizontalHeader()->setLabel( 0, tr( "Full Name" )); | ||
155 | horizontalHeader()->setLabel( 1, tr( "Contact" )); | ||
156 | setLeftMargin( 0 ); | ||
157 | verticalHeader()->hide(); | ||
158 | } | ||
159 | |||
160 | void AbTable::columnClicked( int col ) | ||
161 | { | ||
162 | if ( !sorting() ) | ||
163 | return; | ||
164 | |||
165 | if ( lastSortCol == -1 ) | ||
166 | lastSortCol = col; | ||
167 | |||
168 | if ( col == lastSortCol ) { | ||
169 | asc = !asc; | ||
170 | } else { | ||
171 | lastSortCol = col; | ||
172 | asc = TRUE; | ||
173 | } | ||
174 | resort(); | ||
175 | } | ||
176 | |||
177 | void AbTable::resort() | ||
178 | { | ||
179 | if ( sorting() ) { | ||
180 | if ( lastSortCol == -1 ) | ||
181 | lastSortCol = 0; | ||
182 | sortColumn( lastSortCol, asc, TRUE ); | ||
183 | updateVisible(); | ||
184 | } | ||
185 | } | ||
186 | |||
187 | Contact AbTable::currentEntry() | ||
188 | { | ||
189 | Contact cnt; | ||
190 | AbTableItem *abItem; | ||
191 | abItem = static_cast<AbTableItem*>(item( currentRow(), 0 )); | ||
192 | if ( abItem ) { | ||
193 | cnt = contactList[abItem]; | ||
194 | } | ||
195 | return cnt; | ||
196 | } | ||
197 | |||
198 | void AbTable::replaceCurrentEntry( const Contact &newContact ) | ||
199 | { | ||
200 | int row = currentRow(); | ||
201 | updateJournal( newContact, Contact::ACTION_REPLACE, row ); | ||
202 | updateVisible(); | ||
203 | |||
204 | journalFreeReplace( newContact, row ); | ||
205 | } | ||
206 | |||
207 | void AbTable::deleteCurrentEntry() | ||
208 | { | ||
209 | int row = currentRow(); | ||
210 | AbTableItem *abItem; | ||
211 | abItem = static_cast<AbTableItem*>(item( row, 0 )); | ||
212 | Contact oldContact; | ||
213 | oldContact = contactList[abItem]; | ||
214 | updateJournal( oldContact, Contact::ACTION_REMOVE, row ); | ||
215 | |||
216 | // a little wasteful, but it ensure's there is only one place | ||
217 | // where we delete. | ||
218 | journalFreeRemove( row ); | ||
219 | updateVisible(); | ||
220 | |||
221 | if ( numRows() == 0 ) | ||
222 | emit empty( TRUE ); | ||
223 | } | ||
224 | |||
225 | void AbTable::clear() | ||
226 | { | ||
227 | contactList.clear(); | ||
228 | for ( int r = 0; r < numRows(); ++r ) { | ||
229 | for ( int c = 0; c < numCols(); ++c ) { | ||
230 | if ( cellWidget( r, c ) ) | ||
231 | clearCellWidget( r, c ); | ||
232 | clearCell( r, c ); | ||
233 | } | ||
234 | } | ||
235 | setNumRows( 0 ); | ||
236 | } | ||
237 | |||
238 | void AbTable::refresh() | ||
239 | { | ||
240 | int rows = numRows(); | ||
241 | QString value; | ||
242 | AbTableItem *abi; | ||
243 | for ( int r = 0; r < rows; ++r ) { | ||
244 | abi = static_cast<AbTableItem*>( item(r, 0) ); | ||
245 | value = findContactContact( contactList[abi] ); | ||
246 | static_cast<AbTableItem*>( item(r, 1) )->setItem( value, abi->text() ); | ||
247 | } | ||
248 | resort(); | ||
249 | } | ||
250 | |||
251 | void AbTable::keyPressEvent( QKeyEvent *e ) | ||
252 | { | ||
253 | char key = toupper( e->ascii() ); | ||
254 | |||
255 | if ( key >= 'A' && key <= 'Z' ) | ||
256 | moveTo( key ); | ||
257 | |||
258 | switch( e->key() ) { | ||
259 | case Qt::Key_Space: | ||
260 | case Qt::Key_Return: | ||
261 | case Qt::Key_Enter: | ||
262 | emit details(); | ||
263 | break; | ||
264 | default: | ||
265 | QTable::keyPressEvent( e ); | ||
266 | } | ||
267 | } | ||
268 | |||
269 | void AbTable::moveTo( char c ) | ||
270 | { | ||
271 | |||
272 | int rows = numRows(); | ||
273 | QString value; | ||
274 | AbTableItem *abi; | ||
275 | int r; | ||
276 | if ( asc ) { | ||
277 | r = 0; | ||
278 | while ( r < rows-1) { | ||
279 | abi = static_cast<AbTableItem*>( item(r, 0) ); | ||
280 | QChar first = abi->key()[0]; | ||
281 | //### is there a bug in QChar to char comparison??? | ||
282 | if ( first.row() || first.cell() >= c ) | ||
283 | break; | ||
284 | r++; | ||
285 | } | ||
286 | } else { | ||
287 | //### should probably disable reverse sorting instead | ||
288 | r = rows - 1; | ||
289 | while ( r > 0 ) { | ||
290 | abi = static_cast<AbTableItem*>( item(r, 0) ); | ||
291 | QChar first = abi->key()[0]; | ||
292 | //### is there a bug in QChar to char comparison??? | ||
293 | if ( first.row() || first.cell() >= c ) | ||
294 | break; | ||
295 | r--; | ||
296 | } | ||
297 | } | ||
298 | setCurrentCell( r, currentColumn() ); | ||
299 | } | ||
300 | |||
301 | |||
302 | QString AbTable::findContactName( const Contact &entry ) | ||
303 | { | ||
304 | // We use the fileAs, then company, defaultEmail | ||
305 | QString str; | ||
306 | str = entry.fileAs(); | ||
307 | if ( str.isEmpty() ) { | ||
308 | str = entry.company(); | ||
309 | if ( str.isEmpty() ) { | ||
310 | str = entry.defaultEmail(); | ||
311 | } | ||
312 | } | ||
313 | return str; | ||
314 | } | ||
315 | |||
316 | QString AbTable::findContactContact( const Contact &entry ) | ||
317 | { | ||
318 | QString value; | ||
319 | value = ""; | ||
320 | for ( QValueList<int>::ConstIterator it = intFields->begin(); | ||
321 | it != intFields->end(); ++it ) { | ||
322 | switch ( *it ) { | ||
323 | default: | ||
324 | break; | ||
325 | case Qtopia::Title: | ||
326 | value = entry.title(); | ||
327 | break; | ||
328 | case Qtopia::Suffix: | ||
329 | value = entry.suffix(); | ||
330 | break; | ||
331 | case Qtopia::FileAs: | ||
332 | value = entry.fileAs(); | ||
333 | break; | ||
334 | case Qtopia::DefaultEmail: | ||
335 | value = entry.defaultEmail(); | ||
336 | case Qtopia::Emails: | ||
337 | value = entry.emails(); | ||
338 | break; | ||
339 | case Qtopia::HomeStreet: | ||
340 | value = entry.homeStreet(); | ||
341 | break; | ||
342 | case Qtopia::HomeCity: | ||
343 | value = entry.homeCity(); | ||
344 | break; | ||
345 | case Qtopia::HomeState: | ||
346 | value = entry.homeState(); | ||
347 | break; | ||
348 | case Qtopia::HomeZip: | ||
349 | value = entry.homeZip(); | ||
350 | break; | ||
351 | case Qtopia::HomeCountry: | ||
352 | value = entry.homeCountry(); | ||
353 | break; | ||
354 | case Qtopia::HomePhone: | ||
355 | value = entry.homePhone(); | ||
356 | break; | ||
357 | case Qtopia::HomeFax: | ||
358 | value = entry.homeFax(); | ||
359 | break; | ||
360 | case Qtopia::HomeMobile: | ||
361 | value = entry.homeMobile(); | ||
362 | break; | ||
363 | case Qtopia::HomeWebPage: | ||
364 | value = entry.homeWebpage(); | ||
365 | break; | ||
366 | case Qtopia::Company: | ||
367 | value = entry.company(); | ||
368 | break; | ||
369 | case Qtopia::BusinessCity: | ||
370 | value = entry.businessCity(); | ||
371 | break; | ||
372 | case Qtopia::BusinessStreet: | ||
373 | value = entry.businessStreet(); | ||
374 | break; | ||
375 | case Qtopia::BusinessZip: | ||
376 | value = entry.businessZip(); | ||
377 | break; | ||
378 | case Qtopia::BusinessCountry: | ||
379 | value = entry.businessCountry(); | ||
380 | break; | ||
381 | case Qtopia::BusinessWebPage: | ||
382 | value = entry.businessWebpage(); | ||
383 | break; | ||
384 | case Qtopia::JobTitle: | ||
385 | value = entry.jobTitle(); | ||
386 | break; | ||
387 | case Qtopia::Department: | ||
388 | value = entry.department(); | ||
389 | break; | ||
390 | case Qtopia::Office: | ||
391 | value = entry.office(); | ||
392 | break; | ||
393 | case Qtopia::BusinessPhone: | ||
394 | value = entry.businessPhone(); | ||
395 | break; | ||
396 | case Qtopia::BusinessFax: | ||
397 | value = entry.businessFax(); | ||
398 | break; | ||
399 | case Qtopia::BusinessMobile: | ||
400 | value = entry.businessMobile(); | ||
401 | break; | ||
402 | case Qtopia::BusinessPager: | ||
403 | value = entry.businessPager(); | ||
404 | break; | ||
405 | case Qtopia::Profession: | ||
406 | value = entry.profession(); | ||
407 | break; | ||
408 | case Qtopia::Assistant: | ||
409 | value = entry.assistant(); | ||
410 | break; | ||
411 | case Qtopia::Manager: | ||
412 | value = entry.manager(); | ||
413 | break; | ||
414 | case Qtopia::Spouse: | ||
415 | value = entry.spouse(); | ||
416 | break; | ||
417 | case Qtopia::Gender: | ||
418 | value = entry.gender(); | ||
419 | break; | ||
420 | case Qtopia::Birthday: | ||
421 | value = entry.birthday(); | ||
422 | break; | ||
423 | case Qtopia::Anniversary: | ||
424 | value = entry.anniversary(); | ||
425 | break; | ||
426 | case Qtopia::Nickname: | ||
427 | value = entry.nickname(); | ||
428 | break; | ||
429 | case Qtopia::Children: | ||
430 | value = entry.children(); | ||
431 | break; | ||
432 | case Qtopia::Notes: | ||
433 | value = entry.notes(); | ||
434 | break; | ||
435 | } | ||
436 | if ( !value.isEmpty() ) | ||
437 | break; | ||
438 | } | ||
439 | return value; | ||
440 | } | ||
441 | |||
442 | void AbTable::addEntry( const Contact &newCnt ) | ||
443 | { | ||
444 | int row = numRows(); | ||
445 | setNumRows( row + 1 ); | ||
446 | updateJournal( newCnt, Contact::ACTION_ADD ); | ||
447 | insertIntoTable( newCnt, row ); | ||
448 | setCurrentCell( row, 0 ); | ||
449 | updateVisible(); | ||
450 | } | ||
451 | |||
452 | void AbTable::updateJournal( const Contact &cnt, | ||
453 | Contact::journal_action action, int row ) | ||
454 | { | ||
455 | QFile f( journalFileName() ); | ||
456 | if ( !f.open(IO_WriteOnly|IO_Append) ) | ||
457 | return; | ||
458 | QString buf; | ||
459 | QCString str; | ||
460 | buf = "<Contact "; | ||
461 | cnt.save( buf ); | ||
462 | buf += " action=\"" + QString::number( (int)action ) + "\" "; | ||
463 | if ( action == Contact::ACTION_REMOVE || action == Contact::ACTION_REPLACE) | ||
464 | buf += " actionrow=\"" + QString::number(row) + "\" "; | ||
465 | buf += "/>\n"; | ||
466 | QCString cstr = buf.utf8(); | ||
467 | f.writeBlock( cstr.data(), cstr.length() ); | ||
468 | QCopEnvelope( "QPE/PIM", "addressbookUpdated()" ); | ||
469 | } | ||
470 | |||
471 | bool AbTable::save( const QString &fn ) | ||
472 | { | ||
473 | // QTime t; | ||
474 | // t.start(); | ||
475 | |||
476 | QString strNewFile = fn + ".new"; | ||
477 | QFile f( strNewFile ); | ||
478 | if ( !f.open( IO_WriteOnly|IO_Raw ) ) | ||
479 | return false; | ||
480 | |||
481 | int total_written; | ||
482 | QString out; | ||
483 | out = "<?xml version=\"1.0\" encoding=\"UTF-8\"?><!DOCTYPE Addressbook ><AddressBook>\n" | ||
484 | " <Groups>\n" | ||
485 | " </Groups>\n" | ||
486 | " <Contacts>\n"; | ||
487 | QMapIterator<AbTableItem*, Contact> it; | ||
488 | for ( it = contactList.begin(); it != contactList.end(); ++it ) { | ||
489 | out += "<Contact "; | ||
490 | it.data().save( out ); | ||
491 | out += "/>\n"; | ||
492 | QCString cstr = out.utf8(); | ||
493 | total_written = f.writeBlock( cstr.data(), cstr.length() ); | ||
494 | if ( total_written != int(cstr.length()) ) { | ||
495 | f.close(); | ||
496 | QFile::remove( strNewFile ); | ||
497 | return false; | ||
498 | } | ||
499 | out = ""; | ||
500 | } | ||
501 | out += " </Contacts>\n</AddressBook>\n"; | ||
502 | |||
503 | QCString cstr = out.utf8(); | ||
504 | total_written = f.writeBlock( cstr.data(), cstr.length() ); | ||
505 | if ( total_written != int(cstr.length()) ) { | ||
506 | f.close(); | ||
507 | QFile::remove( strNewFile ); | ||
508 | return false; | ||
509 | } | ||
510 | f.close(); | ||
511 | |||
512 | // qDebug("saving: %d", t.elapsed() ); | ||
513 | |||
514 | // move the file over, I'm just going to use the system call | ||
515 | // because, I don't feel like using QDir. | ||
516 | if ( ::rename( strNewFile.latin1(), fn.latin1() ) < 0 ) { | ||
517 | qWarning( "problem renaming file %s to %s, errno: %d", | ||
518 | strNewFile.latin1(), fn.latin1(), errno ); | ||
519 | // remove the tmp file... | ||
520 | QFile::remove( strNewFile ); | ||
521 | } | ||
522 | // remove the journal... | ||
523 | QFile::remove( journalFileName() ); | ||
524 | return true; | ||
525 | } | ||
526 | |||
527 | void AbTable::load( const QString &fn ) | ||
528 | { | ||
529 | setSorting( false ); | ||
530 | loadFile( fn, false ); | ||
531 | // merge in the journal | ||
532 | if ( QFile::exists( journalFileName() ) ) { | ||
533 | loadFile( journalFileName(), true ); | ||
534 | save( fn ); | ||
535 | } | ||
536 | setSorting( true ); | ||
537 | resort(); | ||
538 | } | ||
539 | |||
540 | void AbTable::loadFile( const QString &strFile, bool journalFile ) | ||
541 | { | ||
542 | // QTime t; | ||
543 | // t.start(); | ||
544 | QFile f( strFile ); | ||
545 | if ( !f.open(IO_ReadOnly) ) | ||
546 | return; | ||
547 | QList<Contact> list; | ||
548 | list.setAutoDelete( TRUE ); | ||
549 | QByteArray ba = f.readAll(); | ||
550 | f.close(); | ||
551 | char *uc = ba.data();//(QChar *)data.unicode(); | ||
552 | int len = ba.size();//data.length(); | ||
553 | bool foundAction = false; | ||
554 | Contact::journal_action action; | ||
555 | bool foundKey = false; | ||
556 | int journalKey = 0; | ||
557 | |||
558 | const int JOURNALACTION = Qtopia::Notes + 1; | ||
559 | const int JOURNALROW = JOURNALACTION + 1; | ||
560 | |||
561 | // ********************************** | ||
562 | // CHANGE THE SIZE OF THE DICT IF YOU ADD ANY MORE FIELDS!!!! | ||
563 | // ********************************** | ||
564 | QAsciiDict<int> dict( 47 ); | ||
565 | dict.setAutoDelete( TRUE ); | ||
566 | dict.insert( "Uid", new int(Qtopia::AddressUid) ); | ||
567 | dict.insert( "Title", new int(Qtopia::Title) ); | ||
568 | dict.insert( "FirstName", new int(Qtopia::FirstName) ); | ||
569 | dict.insert( "MiddleName", new int(Qtopia::MiddleName) ); | ||
570 | dict.insert( "LastName", new int(Qtopia::LastName) ); | ||
571 | dict.insert( "Suffix", new int(Qtopia::Suffix) ); | ||
572 | dict.insert( "FileAs", new int(Qtopia::FileAs) ); | ||
573 | dict.insert( "Categories", new int(Qtopia::AddressCategory) ); | ||
574 | dict.insert( "DefaultEmail", new int(Qtopia::DefaultEmail) ); | ||
575 | dict.insert( "Emails", new int(Qtopia::Emails) ); | ||
576 | dict.insert( "HomeStreet", new int(Qtopia::HomeStreet) ); | ||
577 | dict.insert( "HomeCity", new int(Qtopia::HomeCity) ); | ||
578 | dict.insert( "HomeState", new int(Qtopia::HomeState) ); | ||
579 | dict.insert( "HomeZip", new int(Qtopia::HomeZip) ); | ||
580 | dict.insert( "HomeCountry", new int(Qtopia::HomeCountry) ); | ||
581 | dict.insert( "HomePhone", new int(Qtopia::HomePhone) ); | ||
582 | dict.insert( "HomeFax", new int(Qtopia::HomeFax) ); | ||
583 | dict.insert( "HomeMobile", new int(Qtopia::HomeMobile) ); | ||
584 | dict.insert( "HomeWebPage", new int(Qtopia::HomeWebPage) ); | ||
585 | dict.insert( "Company", new int(Qtopia::Company) ); | ||
586 | dict.insert( "BusinessStreet", new int(Qtopia::BusinessStreet) ); | ||
587 | dict.insert( "BusinessCity", new int(Qtopia::BusinessCity) ); | ||
588 | dict.insert( "BusinessState", new int(Qtopia::BusinessState) ); | ||
589 | dict.insert( "BusinessZip", new int(Qtopia::BusinessZip) ); | ||
590 | dict.insert( "BusinessCountry", new int(Qtopia::BusinessCountry) ); | ||
591 | dict.insert( "BusinessWebPage", new int(Qtopia::BusinessWebPage) ); | ||
592 | dict.insert( "JobTitle", new int(Qtopia::JobTitle) ); | ||
593 | dict.insert( "Department", new int(Qtopia::Department) ); | ||
594 | dict.insert( "Office", new int(Qtopia::Office) ); | ||
595 | dict.insert( "BusinessPhone", new int(Qtopia::BusinessPhone) ); | ||
596 | dict.insert( "BusinessFax", new int(Qtopia::BusinessFax) ); | ||
597 | dict.insert( "BusinessMobile", new int(Qtopia::BusinessMobile) ); | ||
598 | dict.insert( "BusinessPager", new int(Qtopia::BusinessPager) ); | ||
599 | dict.insert( "Profession", new int(Qtopia::Profession) ); | ||
600 | dict.insert( "Assistant", new int(Qtopia::Assistant) ); | ||
601 | dict.insert( "Manager", new int(Qtopia::Manager) ); | ||
602 | dict.insert( "Spouse", new int(Qtopia::Spouse) ); | ||
603 | dict.insert( "Children", new int(Qtopia::Children) ); | ||
604 | dict.insert( "Gender", new int(Qtopia::Gender) ); | ||
605 | dict.insert( "Birthday", new int(Qtopia::Birthday) ); | ||
606 | dict.insert( "Anniversary", new int(Qtopia::Anniversary) ); | ||
607 | dict.insert( "Nickname", new int(Qtopia::Nickname) ); | ||
608 | dict.insert( "Notes", new int(Qtopia::Notes) ); | ||
609 | dict.insert( "action", new int(JOURNALACTION) ); | ||
610 | dict.insert( "actionrow", new int(JOURNALROW) ); | ||
611 | |||
612 | int i = 0; | ||
613 | int num = 0; | ||
614 | char *point; | ||
615 | while ( (point = strstr( uc+i, "<Contact " ) ) != NULL ) { | ||
616 | i = point - uc; | ||
617 | // if we are reading the standard file, we just need to | ||
618 | // insert info, so just say we'll do an insert... | ||
619 | action = Contact::ACTION_ADD; | ||
620 | // new Contact | ||
621 | Contact *cnt = new Contact; | ||
622 | i += 9; | ||
623 | while ( 1 ) { | ||
624 | while ( i < len && (uc[i] == ' ' || uc[i] == '\n' || uc[i] == '\r') ) | ||
625 | i++; | ||
626 | if ( i >= len-2 || (uc[i] == '/' && uc[i+1] == '>') ) | ||
627 | break; | ||
628 | // we have another attribute read it. | ||
629 | int j = i; | ||
630 | while ( j < len && uc[j] != '=' ) | ||
631 | j++; | ||
632 | char *attr = uc+i; | ||
633 | uc[j] = '\0'; | ||
634 | //qDebug("attr=%s", attr.latin1() ); | ||
635 | i = ++j; // skip = | ||
636 | while ( i < len && uc[i] != '"' ) | ||
637 | i++; | ||
638 | j = ++i; | ||
639 | bool haveEnt = FALSE; | ||
640 | bool haveUtf = FALSE; | ||
641 | while ( j < len && uc[j] != '"' ) { | ||
642 | if ( uc[j] == '&' ) | ||
643 | haveEnt = TRUE; | ||
644 | if ( ((unsigned char)uc[j]) > 0x7f ) | ||
645 | haveUtf = TRUE; | ||
646 | j++; | ||
647 | } | ||
648 | |||
649 | if ( j == i ) { | ||
650 | // empty value | ||
651 | i = j + 1; | ||
652 | continue; | ||
653 | } | ||
654 | |||
655 | QString value = haveUtf ? QString::fromUtf8( uc+i, j-i ) | ||
656 | : QString::fromLatin1( uc+i, j-i ); | ||
657 | if ( haveEnt ) | ||
658 | value = Qtopia::plainString( value ); | ||
659 | i = j + 1; | ||
660 | |||
661 | int *find = dict[ attr ]; | ||
662 | if ( !find ) { | ||
663 | cnt->setCustomField(attr, value); | ||
664 | continue; | ||
665 | } | ||
666 | #if 1 | ||
667 | switch( *find ) { | ||
668 | case Qtopia::AddressUid: | ||
669 | cnt->setUid( value.toInt() ); | ||
670 | break; | ||
671 | case Qtopia::AddressCategory: | ||
672 | cnt->setCategories( Qtopia::Record::idsFromString( value )); | ||
673 | break; | ||
674 | case JOURNALACTION: | ||
675 | action = Contact::journal_action(value.toInt()); | ||
676 | break; | ||
677 | case JOURNALROW: | ||
678 | journalKey = value.toInt(); | ||
679 | break; | ||
680 | |||
681 | default: | ||
682 | cnt->insert( *find, value ); | ||
683 | break; | ||
684 | } | ||
685 | #endif | ||
686 | } | ||
687 | |||
688 | // sadly we can't delay adding of items from the journal to get | ||
689 | // the proper effect, but then, the journal should _never_ be | ||
690 | // that huge, and recovering from a crash is not necessarily | ||
691 | // a *fast* thing. | ||
692 | switch ( action ) { | ||
693 | case Contact::ACTION_ADD: | ||
694 | if ( journalFile ) { | ||
695 | int myrows = numRows(); | ||
696 | setNumRows( myrows + 1 ); | ||
697 | insertIntoTable( *cnt, myrows ); | ||
698 | delete cnt; | ||
699 | } | ||
700 | else | ||
701 | list.append( cnt ); | ||
702 | break; | ||
703 | case Contact::ACTION_REMOVE: | ||
704 | // yup, we don't use the entry to remove the object... | ||
705 | journalFreeRemove( journalKey ); | ||
706 | delete cnt; | ||
707 | break; | ||
708 | case Contact::ACTION_REPLACE: | ||
709 | journalFreeReplace( *cnt, journalKey ); | ||
710 | delete cnt; | ||
711 | break; | ||
712 | default: | ||
713 | break; | ||
714 | } | ||
715 | num++; | ||
716 | foundAction = false; | ||
717 | foundKey = false; | ||
718 | // if ( num % 100 == 0 ) { | ||
719 | // qDebug("loading file, num=%d, t=%d", num, t.elapsed() ); | ||
720 | // } | ||
721 | } | ||
722 | if ( list.count() > 0 ) { | ||
723 | internalAddEntries( list ); | ||
724 | } | ||
725 | // qDebug("done loading %d, t=%d", num, t.elapsed() ); | ||
726 | |||
727 | } | ||
728 | |||
729 | void AbTable::realignTable( int row ) | ||
730 | { | ||
731 | QTableItem *ti1, | ||
732 | *ti2; | ||
733 | int totalRows = numRows(); | ||
734 | for ( int curr = row; curr < totalRows - 1; curr++ ) { | ||
735 | // the same info from the todo list still applies, but I | ||
736 | // don't think it is _too_ bad. | ||
737 | ti1 = item( curr + 1, 0 ); | ||
738 | ti2 = item( curr + 1, 1 ); | ||
739 | takeItem( ti1 ); | ||
740 | takeItem( ti2 ); | ||
741 | setItem( curr, 0, ti1 ); | ||
742 | setItem( curr, 1, ti2 ); | ||
743 | } | ||
744 | setNumRows( totalRows - 1 ); | ||
745 | resort(); | ||
746 | } | ||
747 | |||
748 | void AbTable::insertIntoTable( const Contact &cnt, int row ) | ||
749 | { | ||
750 | QString strName, | ||
751 | strContact; | ||
752 | |||
753 | strName = findContactName( cnt ); | ||
754 | strContact = findContactContact( cnt ); | ||
755 | |||
756 | AbTableItem *ati; | ||
757 | ati = new AbTableItem( this, QTableItem::Never, strName, strContact); | ||
758 | contactList.insert( ati, cnt ); | ||
759 | setItem( row, 0, ati ); | ||
760 | ati = new AbTableItem( this, QTableItem::Never, strContact, strName); | ||
761 | setItem( row, 1, ati ); | ||
762 | |||
763 | //### cannot do this; table only has two columns at this point | ||
764 | // setItem( row, 2, new AbPickItem( this ) ); | ||
765 | |||
766 | // resort at some point? | ||
767 | } | ||
768 | |||
769 | void AbTable::internalAddEntries( QList<Contact> &list ) | ||
770 | { | ||
771 | setUpdatesEnabled( FALSE ); | ||
772 | setNumRows( list.count() ); | ||
773 | int row = 0; | ||
774 | Contact *it; | ||
775 | for ( it = list.first(); it; it = list.next() ) | ||
776 | insertIntoTable( *it, row++ ); | ||
777 | resort(); | ||
778 | setUpdatesEnabled( TRUE ); | ||
779 | } | ||
780 | |||
781 | |||
782 | void AbTable::journalFreeReplace( const Contact &cnt, int row ) | ||
783 | { | ||
784 | QString strName, | ||
785 | strContact; | ||
786 | AbTableItem *ati; | ||
787 | |||
788 | strName = findContactName( cnt ); | ||
789 | strContact = findContactContact( cnt ); | ||
790 | ati = static_cast<AbTableItem*>(item(row, 0)); | ||
791 | contactList.remove( ati ); | ||
792 | ati->setItem( strName, strContact ); | ||
793 | contactList.insert( ati, cnt ); | ||
794 | |||
795 | ati = static_cast<AbTableItem*>(item(row, 1)); | ||
796 | ati->setItem( strContact, strName ); | ||
797 | } | ||
798 | |||
799 | void AbTable::journalFreeRemove( int row ) | ||
800 | { | ||
801 | AbTableItem *ati; | ||
802 | ati = static_cast<AbTableItem*>(item(row, 0)); | ||
803 | if ( !ati ) | ||
804 | return; | ||
805 | contactList.remove( ati ); | ||
806 | realignTable( row ); | ||
807 | } | ||
808 | |||
809 | #if QT_VERSION <= 230 | ||
810 | #ifndef SINGLE_APP | ||
811 | void QTable::paintEmptyArea( QPainter *p, int cx, int cy, int cw, int ch ) | ||
812 | { | ||
813 | // Region of the rect we should draw | ||
814 | QRegion reg( QRect( cx, cy, cw, ch ) ); | ||
815 | // Subtract the table from it | ||
816 | reg = reg.subtract( QRect( QPoint( 0, 0 ), tableSize() ) ); | ||
817 | // And draw the rectangles (transformed as needed) | ||
818 | QArray<QRect> r = reg.rects(); | ||
819 | for (unsigned int i=0; i<r.count(); i++) | ||
820 | p->fillRect( r[i], colorGroup().brush( QColorGroup::Base ) ); | ||
821 | } | ||
822 | #endif | ||
823 | #endif | ||
824 | |||
825 | |||
826 | // int AbTable::rowHeight( int ) const | ||
827 | // { | ||
828 | // return 18; | ||
829 | // } | ||
830 | |||
831 | // int AbTable::rowPos( int row ) const | ||
832 | // { | ||
833 | // return 18*row; | ||
834 | // } | ||
835 | |||
836 | // int AbTable::rowAt( int pos ) const | ||
837 | // { | ||
838 | // return QMIN( pos/18, numRows()-1 ); | ||
839 | // } | ||
840 | |||
841 | void AbTable::slotDoFind( const QString &findString, bool caseSensitive, | ||
842 | bool backwards, int category ) | ||
843 | { | ||
844 | if ( currFindRow < -1 ) | ||
845 | currFindRow = currentRow() - 1; | ||
846 | clearSelection( TRUE ); | ||
847 | int rows, | ||
848 | row; | ||
849 | AbTableItem *ati; | ||
850 | QRegExp r( findString ); | ||
851 | r.setCaseSensitive( caseSensitive ); | ||
852 | rows = numRows(); | ||
853 | static bool wrapAround = true; | ||
854 | |||
855 | if ( !backwards ) { | ||
856 | for ( row = currFindRow + 1; row < rows; row++ ) { | ||
857 | ati = static_cast<AbTableItem*>( item(row, 0) ); | ||
858 | if ( contactCompare( contactList[ati], r, category ) ) | ||
859 | break; | ||
860 | |||
861 | } | ||
862 | } else { | ||
863 | for ( row = currFindRow - 1; row > -1; row-- ) { | ||
864 | ati = static_cast<AbTableItem*>( item(row, 0) ); | ||
865 | if ( contactCompare( contactList[ati], r, category ) ) | ||
866 | break; | ||
867 | } | ||
868 | } | ||
869 | if ( row >= rows || row < 0 ) { | ||
870 | if ( row < 0 ) | ||
871 | currFindRow = rows; | ||
872 | else | ||
873 | currFindRow = -1; | ||
874 | |||
875 | if ( wrapAround ) | ||
876 | emit signalWrapAround(); | ||
877 | else | ||
878 | emit signalNotFound(); | ||
879 | |||
880 | wrapAround = !wrapAround; | ||
881 | } else { | ||
882 | currFindRow = row; | ||
883 | QTableSelection foundSelection; | ||
884 | foundSelection.init( currFindRow, 0 ); | ||
885 | foundSelection.expandTo( currFindRow, numCols() - 1 ); | ||
886 | addSelection( foundSelection ); | ||
887 | setCurrentCell( currFindRow, numCols() - 1 ); | ||
888 | wrapAround = true; | ||
889 | } | ||
890 | } | ||
891 | |||
892 | static bool contactCompare( const Contact &cnt, const QRegExp &r, int category ) | ||
893 | { | ||
894 | bool returnMe; | ||
895 | QArray<int> cats; | ||
896 | cats = cnt.categories(); | ||
897 | |||
898 | returnMe = false; | ||
899 | if ( (category == -1 && cats.count() == 0) || category == -2 ) | ||
900 | returnMe = cnt.match( r ); | ||
901 | else { | ||
902 | int i; | ||
903 | for ( i = 0; i < int(cats.count()); i++ ) { | ||
904 | if ( cats[i] == category ) { | ||
905 | returnMe = cnt.match( r ); | ||
906 | break; | ||
907 | } | ||
908 | } | ||
909 | } | ||
910 | return returnMe; | ||
911 | } | ||
912 | |||
913 | void AbTable::fitColumns() | ||
914 | { | ||
915 | int contentsWidth = visibleWidth(); | ||
916 | int n = numCols(); | ||
917 | int pw = n == 3 ? columnWidth(2) : 0; | ||
918 | setColumnWidth( 0, contentsWidth - contentsWidth / 2 ); | ||
919 | setColumnWidth( 1, contentsWidth / 2 - pw ); | ||
920 | } | ||
921 | |||
922 | void AbTable::show() | ||
923 | { | ||
924 | fitColumns(); | ||
925 | QTable::show(); | ||
926 | } | ||
927 | |||
928 | void AbTable::setChoiceNames( const QStringList& list) | ||
929 | { | ||
930 | choicenames = list; | ||
931 | if ( choicenames.isEmpty() ) { | ||
932 | // hide pick column | ||
933 | setNumCols( 2 ); | ||
934 | } else { | ||
935 | // show pick column | ||
936 | setNumCols( 3 ); | ||
937 | setColumnWidth( 2, fontMetrics().width(tr( "Pick" ))+8 ); | ||
938 | horizontalHeader()->setLabel( 2, tr( "Pick" )); | ||
939 | } | ||
940 | fitColumns(); | ||
941 | } | ||
942 | |||
943 | void AbTable::itemClicked(int,int col) | ||
944 | { | ||
945 | if ( col == 2 ) { | ||
946 | return; | ||
947 | } else { | ||
948 | emit details(); | ||
949 | } | ||
950 | } | ||
951 | |||
952 | QStringList AbTable::choiceNames() const | ||
953 | { | ||
954 | return choicenames; | ||
955 | } | ||
956 | |||
957 | void AbTable::setChoiceSelection(int /*index*/, const QStringList& /*list*/) | ||
958 | { | ||
959 | /* ###### | ||
960 | |||
961 | QString selname = choicenames.at(index); | ||
962 | for (each row) { | ||
963 | Contact *c = contactForRow(row); | ||
964 | if ( list.contains(c->email) ) { | ||
965 | list.remove(c->email); | ||
966 | setText(row, 2, selname); | ||
967 | } | ||
968 | } | ||
969 | for (remaining list items) { | ||
970 | Contact *c = new contact(item); | ||
971 | setText(newrow, 2, selname); | ||
972 | } | ||
973 | |||
974 | */ | ||
975 | } | ||
976 | |||
977 | QStringList AbTable::choiceSelection(int /*index*/) const | ||
978 | { | ||
979 | QStringList r; | ||
980 | /* ###### | ||
981 | |||
982 | QString selname = choicenames.at(index); | ||
983 | for (each row) { | ||
984 | Contact *c = contactForRow(row); | ||
985 | if ( text(row,2) == selname ) { | ||
986 | r.append(c->email); | ||
987 | } | ||
988 | } | ||
989 | |||
990 | */ | ||
991 | return r; | ||
992 | } | ||
993 | |||
994 | void AbTable::setShowCategory( const QString &c ) | ||
995 | { | ||
996 | showCat = c; | ||
997 | updateVisible(); | ||
998 | } | ||
999 | |||
1000 | QString AbTable::showCategory() const | ||
1001 | { | ||
1002 | return showCat; | ||
1003 | } | ||
1004 | |||
1005 | |||
1006 | QStringList AbTable::categories() | ||
1007 | { | ||
1008 | mCat.load( categoryFileName() ); | ||
1009 | QStringList categoryList = mCat.labels( "Contacts" ); | ||
1010 | return categoryList; | ||
1011 | } | ||
1012 | |||
1013 | void AbTable::updateVisible() | ||
1014 | { | ||
1015 | int visible, | ||
1016 | totalRows, | ||
1017 | id, | ||
1018 | totalCats, | ||
1019 | it, | ||
1020 | row; | ||
1021 | bool hide; | ||
1022 | AbTableItem *ati; | ||
1023 | Contact *cnt; | ||
1024 | visible = 0; | ||
1025 | |||
1026 | setPaintingEnabled( FALSE ); | ||
1027 | |||
1028 | totalRows = numRows(); | ||
1029 | id = mCat.id( "Contacts", showCat ); | ||
1030 | QArray<int> cats; | ||
1031 | for ( row = 0; row < totalRows; row++ ) { | ||
1032 | ati = static_cast<AbTableItem*>( item(row, 0) ); | ||
1033 | cnt = &contactList[ati]; | ||
1034 | cats = cnt->categories(); | ||
1035 | hide = false; | ||
1036 | if ( !showCat.isEmpty() ) { | ||
1037 | if ( showCat == tr( "Unfiled" ) ) { | ||
1038 | if ( cats.count() > 0 ) | ||
1039 | hide = true; | ||
1040 | } else { | ||
1041 | // do some comparing | ||
1042 | if ( !hide ) { | ||
1043 | hide = true; | ||
1044 | totalCats = int(cats.count()); | ||
1045 | for ( it = 0; it < totalCats; it++ ) { | ||
1046 | if ( cats[it] == id ) { | ||
1047 | hide = false; | ||
1048 | break; | ||
1049 | } | ||
1050 | } | ||
1051 | } | ||
1052 | } | ||
1053 | } | ||
1054 | if ( hide ) { | ||
1055 | if ( currentRow() == row ) | ||
1056 | setCurrentCell( -1, 0 ); | ||
1057 | if ( rowHeight(row) > 0 ) | ||
1058 | hideRow( row ); | ||
1059 | } else { | ||
1060 | if ( rowHeight(row) == 0 ) { | ||
1061 | showRow( row ); | ||
1062 | adjustRow( row ); | ||
1063 | } | ||
1064 | visible++; | ||
1065 | } | ||
1066 | } | ||
1067 | if ( !visible ) | ||
1068 | setCurrentCell( -1, 0 ); | ||
1069 | |||
1070 | setPaintingEnabled( TRUE ); | ||
1071 | } | ||
1072 | |||
1073 | |||
1074 | void AbTable::setPaintingEnabled( bool e ) | ||
1075 | { | ||
1076 | if ( e != enablePainting ) { | ||
1077 | if ( !enablePainting ) { | ||
1078 | enablePainting = true; | ||
1079 | rowHeightChanged( 0 ); | ||
1080 | viewport()->update(); | ||
1081 | } else { | ||
1082 | enablePainting = false; | ||
1083 | } | ||
1084 | } | ||
1085 | } | ||
1086 | |||
1087 | void AbTable::rowHeightChanged( int row ) | ||
1088 | { | ||
1089 | if ( enablePainting ) | ||
1090 | QTable::rowHeightChanged( row ); | ||
1091 | } | ||
diff --git a/core/pim/addressbook/abtable.h b/core/pim/addressbook/abtable.h new file mode 100644 index 0000000..9b96997 --- a/dev/null +++ b/core/pim/addressbook/abtable.h | |||
@@ -0,0 +1,140 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #ifndef ABTABLE_H | ||
22 | #define ABTABLE_H | ||
23 | |||
24 | #include <qpe/categories.h> | ||
25 | #include <qpe/contact.h> | ||
26 | |||
27 | #include <qmap.h> | ||
28 | #include <qtable.h> | ||
29 | #include <qstringlist.h> | ||
30 | #include <qcombobox.h> | ||
31 | |||
32 | class AbTableItem : public QTableItem | ||
33 | { | ||
34 | public: | ||
35 | AbTableItem( QTable *t, EditType et, const QString &s, | ||
36 | const QString &secondSortKey); | ||
37 | QString entryKey() const; | ||
38 | void setEntryKey( const QString & k ); | ||
39 | virtual int alignment() const; | ||
40 | virtual QString key() const; | ||
41 | void setItem( const QString &txt, const QString &secondKey ); | ||
42 | |||
43 | private: | ||
44 | QString sortKey; | ||
45 | }; | ||
46 | |||
47 | class AbPickItem : public QTableItem | ||
48 | { | ||
49 | public: | ||
50 | AbPickItem( QTable *t ); | ||
51 | |||
52 | QWidget *createEditor() const; | ||
53 | void setContentFromEditor( QWidget *w ); | ||
54 | |||
55 | private: | ||
56 | QGuardedPtr<QComboBox> cb; | ||
57 | }; | ||
58 | |||
59 | class AbTable : public QTable | ||
60 | { | ||
61 | Q_OBJECT | ||
62 | |||
63 | public: | ||
64 | AbTable( const QValueList<int> *ordered, QWidget *parent, const char *name=0 ); | ||
65 | ~AbTable(); | ||
66 | // NEW | ||
67 | void addEntry( const Contact &newContact ); | ||
68 | Contact currentEntry(); | ||
69 | void replaceCurrentEntry( const Contact &newContact ); | ||
70 | |||
71 | void init(); | ||
72 | |||
73 | void deleteCurrentEntry(); | ||
74 | void clear(); | ||
75 | void clearFindRow() { currFindRow = -2; } | ||
76 | void loadFields(); | ||
77 | void refresh(); | ||
78 | bool save( const QString &fn ); | ||
79 | void load( const QString &fn ); | ||
80 | |||
81 | // addresspicker mode | ||
82 | void setChoiceNames( const QStringList& list); | ||
83 | QStringList choiceNames() const; | ||
84 | void setChoiceSelection(int index, const QStringList& list); | ||
85 | QStringList choiceSelection(int index) const; | ||
86 | void setShowCategory( const QString &c ); | ||
87 | QString showCategory() const; | ||
88 | QStringList categories(); | ||
89 | |||
90 | void show(); | ||
91 | void setPaintingEnabled( bool e ); | ||
92 | |||
93 | public slots: | ||
94 | void slotDoFind( const QString &str, bool caseSensitive, bool backwards, | ||
95 | int category ); | ||
96 | signals: | ||
97 | void empty( bool ); | ||
98 | void details(); | ||
99 | void signalNotFound(); | ||
100 | void signalWrapAround(); | ||
101 | |||
102 | protected: | ||
103 | virtual void keyPressEvent( QKeyEvent *e ); | ||
104 | |||
105 | // int rowHeight( int ) const; | ||
106 | // int rowPos( int row ) const; | ||
107 | // virtual int rowAt( int pos ) const; | ||
108 | |||
109 | |||
110 | protected slots: | ||
111 | void moveTo( char ); | ||
112 | virtual void columnClicked( int col ); | ||
113 | void itemClicked(int,int col); | ||
114 | void rowHeightChanged( int row ); | ||
115 | |||
116 | private: | ||
117 | void loadFile( const QString &strFile, bool journalFile ); | ||
118 | void fitColumns(); | ||
119 | void resort(); | ||
120 | void updateJournal( const Contact &contact, Contact::journal_action action, | ||
121 | int row = -1 ); | ||
122 | void insertIntoTable( const Contact &contact, int row ); | ||
123 | void internalAddEntries( QList<Contact> &list ); | ||
124 | QString findContactName( const Contact &entry ); | ||
125 | QString findContactContact( const Contact &entry ); | ||
126 | void journalFreeReplace( const Contact &cnt, int row ); | ||
127 | void journalFreeRemove( int row ); | ||
128 | void realignTable( int ); | ||
129 | void updateVisible(); | ||
130 | int lastSortCol; | ||
131 | bool asc; | ||
132 | QMap<AbTableItem*, Contact> contactList; | ||
133 | const QValueList<int> *intFields; | ||
134 | int currFindRow; | ||
135 | QString showCat; | ||
136 | QStringList choicenames; | ||
137 | bool enablePainting; | ||
138 | Categories mCat; | ||
139 | }; | ||
140 | #endif // ABTABLE_H | ||
diff --git a/core/pim/addressbook/addressbook.cpp b/core/pim/addressbook/addressbook.cpp new file mode 100644 index 0000000..b694e4f --- a/dev/null +++ b/core/pim/addressbook/addressbook.cpp | |||
@@ -0,0 +1,829 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include "abeditor.h" | ||
22 | #include "ablabel.h" | ||
23 | #include "abtable.h" | ||
24 | #include "addresssettings.h" | ||
25 | #include "addressbook.h" | ||
26 | |||
27 | #include <qpe/qpeapplication.h> | ||
28 | #include <qpe/config.h> | ||
29 | #include <qpe/contact.h> | ||
30 | #include <qpe/finddialog.h> | ||
31 | #include <qpe/global.h> | ||
32 | #include <qpe/resource.h> | ||
33 | #include <qpe/ir.h> | ||
34 | #include <qpe/qpemessagebox.h> | ||
35 | #include <qpe/qcopenvelope_qws.h> | ||
36 | |||
37 | #include <qaction.h> | ||
38 | #include <qdialog.h> | ||
39 | #include <qdir.h> | ||
40 | #include <qfile.h> | ||
41 | #include <qimage.h> | ||
42 | #include <qlayout.h> | ||
43 | #include <qpe/qpemenubar.h> | ||
44 | #include <qmessagebox.h> | ||
45 | #include <qpixmap.h> | ||
46 | #include <qpopupmenu.h> | ||
47 | #include <qpe/qpetoolbar.h> | ||
48 | #include <qstringlist.h> | ||
49 | #include <qtoolbutton.h> | ||
50 | #include <qwhatsthis.h> | ||
51 | |||
52 | #include <stdlib.h> | ||
53 | #include <sys/stat.h> | ||
54 | #include <sys/types.h> | ||
55 | #include <fcntl.h> | ||
56 | #include <unistd.h> | ||
57 | |||
58 | #include <qdatetime.h> | ||
59 | |||
60 | static QString addressbookOldXMLFilename() | ||
61 | { | ||
62 | QString filename = QPEApplication::documentDir() + "addressbook.xml"; | ||
63 | return filename; | ||
64 | } | ||
65 | |||
66 | static QString addressbookXMLFilename() | ||
67 | { | ||
68 | QString filename = Global::applicationFileName("addressbook", | ||
69 | "addressbook.xml"); | ||
70 | return filename; | ||
71 | } | ||
72 | |||
73 | static QString addressbookPersonalVCardName() | ||
74 | { | ||
75 | QString filename = Global::applicationFileName("addressbook", | ||
76 | "businesscard.vcf"); | ||
77 | return filename; | ||
78 | } | ||
79 | |||
80 | |||
81 | AddressbookWindow::AddressbookWindow( QWidget *parent, const char *name, | ||
82 | WFlags f ) | ||
83 | : QMainWindow( parent, name, f ), | ||
84 | abEditor(0), | ||
85 | bAbEditFirstTime(TRUE), | ||
86 | syncing(FALSE) | ||
87 | { | ||
88 | initFields(); | ||
89 | |||
90 | setCaption( tr("Contacts") ); | ||
91 | setIcon( Resource::loadPixmap( "AddressBook" ) ); | ||
92 | |||
93 | setToolBarsMovable( FALSE ); | ||
94 | |||
95 | // Create Toolbars | ||
96 | |||
97 | QPEToolBar *bar = new QPEToolBar( this ); | ||
98 | bar->setHorizontalStretchable( TRUE ); | ||
99 | |||
100 | QPEMenuBar *mbList = new QPEMenuBar( bar ); | ||
101 | mbList->setMargin( 0 ); | ||
102 | |||
103 | QPopupMenu *edit = new QPopupMenu( this ); | ||
104 | mbList->insertItem( tr( "Contact" ), edit ); | ||
105 | |||
106 | listTools = new QPEToolBar( this, "list operations" ); | ||
107 | |||
108 | |||
109 | QAction *a = new QAction( tr( "New" ), Resource::loadPixmap( "new" ), QString::null, | ||
110 | 0, this, 0 ); | ||
111 | actionNew = a; | ||
112 | connect( a, SIGNAL( activated() ), this, SLOT( slotListNew() ) ); | ||
113 | a->addTo( edit ); | ||
114 | a->addTo( listTools ); | ||
115 | |||
116 | a = new QAction( tr( "Edit" ), Resource::loadPixmap( "edit" ), QString::null, | ||
117 | 0, this, 0 ); | ||
118 | actionEdit = a; | ||
119 | connect( a, SIGNAL( activated() ), this, SLOT( slotViewEdit() ) ); | ||
120 | a->addTo( edit ); | ||
121 | a->addTo( listTools ); | ||
122 | |||
123 | a = new QAction( tr( "Delete" ), Resource::loadPixmap( "trash" ), QString::null, | ||
124 | 0, this, 0 ); | ||
125 | actionTrash = a; | ||
126 | connect( a, SIGNAL( activated() ), this, SLOT( slotListDelete() ) ); | ||
127 | a->addTo( edit ); | ||
128 | a->addTo( listTools ); | ||
129 | |||
130 | a = new QAction( tr( "Find" ), Resource::loadPixmap( "mag" ), | ||
131 | QString::null, 0, this, 0 ); | ||
132 | actionFind = a; | ||
133 | connect( a, SIGNAL(activated()), this, SLOT(slotFind()) ); | ||
134 | a->addTo( edit ); | ||
135 | a->addTo( listTools ); | ||
136 | |||
137 | |||
138 | a = new QAction( tr( "Write Mail To" ), Resource::loadPixmap( "qtmail/reply" ), | ||
139 | QString::null, 0, this, 0 ); | ||
140 | a->setEnabled( FALSE ); | ||
141 | actionMail = a; | ||
142 | connect( a, SIGNAL( activated() ), this, SLOT( writeMail() ) ); | ||
143 | a->addTo( edit ); | ||
144 | a->addTo( listTools ); | ||
145 | |||
146 | |||
147 | |||
148 | if ( Ir::supported() ) { | ||
149 | a = new QAction( tr ("Beam Entry" ), Resource::loadPixmap( "beam" ), QString::null, | ||
150 | 0, this, 0 ); | ||
151 | actionBeam = a; | ||
152 | connect( a, SIGNAL( activated() ), this, SLOT( slotBeam() ) ); | ||
153 | a->addTo( edit ); | ||
154 | a->addTo( listTools ); | ||
155 | } | ||
156 | |||
157 | edit->insertSeparator(); | ||
158 | |||
159 | a = new QAction( tr("My Personal Details"), QString::null, 0, 0, 0, TRUE ); | ||
160 | actionPersonal = a; | ||
161 | connect( a, SIGNAL( activated() ), this, SLOT( slotPersonalView() ) ); | ||
162 | a->addTo( edit ); | ||
163 | |||
164 | |||
165 | a = new QAction( tr( "Arrange Edit Fields"), QString::null, 0, 0 ); | ||
166 | connect( a, SIGNAL( activated() ), this, SLOT( slotSettings() ) ); | ||
167 | a->addTo( edit ); | ||
168 | |||
169 | // Create Views | ||
170 | |||
171 | // This is safe to call without checking to see if it exists... | ||
172 | // not to mention it also does the necessary stuff for the | ||
173 | // journaling... | ||
174 | QString str = addressbookXMLFilename(); | ||
175 | if ( str.isNull() ) { | ||
176 | QMessageBox::warning( this, tr("Out of Space"), | ||
177 | tr("There is not enough space to create\n" | ||
178 | "neccessary startup files.\n" | ||
179 | "\nFree up some space before\nentering data!") | ||
180 | ); | ||
181 | } | ||
182 | |||
183 | abList = new AbTable( &orderedFields, this, "table" ); | ||
184 | abList->setHScrollBarMode( QScrollView::AlwaysOff ); | ||
185 | connect( abList, SIGNAL( empty( bool ) ), | ||
186 | this, SLOT( listIsEmpty( bool ) ) ); | ||
187 | connect( abList, SIGNAL( details() ), | ||
188 | this, SLOT( slotListView() ) ); | ||
189 | connect( abList, SIGNAL(currentChanged(int,int)), | ||
190 | this, SLOT(slotUpdateToolbar()) ); | ||
191 | |||
192 | mView = 0; | ||
193 | |||
194 | abList->load( addressbookXMLFilename() ); | ||
195 | if ( QFile::exists(addressbookOldXMLFilename()) ) { | ||
196 | abList->load( addressbookOldXMLFilename() ); | ||
197 | QFile::remove(addressbookOldXMLFilename()); | ||
198 | } | ||
199 | |||
200 | catMenu = new QPopupMenu( this ); | ||
201 | catMenu->setCheckable( TRUE ); | ||
202 | connect( catMenu, SIGNAL(activated(int)), this, SLOT(slotSetCategory(int)) ); | ||
203 | populateCategories(); | ||
204 | |||
205 | mbList->insertItem( tr("View"), catMenu ); | ||
206 | setCentralWidget( abList ); | ||
207 | |||
208 | // qDebug("adressbook contrsuction: t=%d", t.elapsed() ); | ||
209 | } | ||
210 | |||
211 | void AddressbookWindow::setDocument( const QString &filename ) | ||
212 | { | ||
213 | if ( filename.find(".vcf") != int(filename.length()) - 4 ) return; | ||
214 | |||
215 | QValueList<Contact> cl = Contact::readVCard( filename ); | ||
216 | for( QValueList<Contact>::Iterator it = cl.begin(); it != cl.end(); ++it ) { | ||
217 | // QString msg = tr("You received a vCard for\n%1.\nDo You want to add it to your\naddressbook?") | ||
218 | // .arg( (*it).fullName() ); | ||
219 | // if ( QMessageBox::information( this, tr("received contact"), msg, QMessageBox::Ok, QMessageBox::Cancel ) == | ||
220 | // QMessageBox::Ok ) { | ||
221 | abList->addEntry( *it ); | ||
222 | // } | ||
223 | } | ||
224 | |||
225 | } | ||
226 | |||
227 | void AddressbookWindow::resizeEvent( QResizeEvent *e ) | ||
228 | { | ||
229 | QMainWindow::resizeEvent( e ); | ||
230 | |||
231 | if ( centralWidget() == abList ) | ||
232 | showList(); | ||
233 | else if ( centralWidget() == mView ) | ||
234 | showView(); | ||
235 | } | ||
236 | |||
237 | AddressbookWindow::~AddressbookWindow() | ||
238 | { | ||
239 | } | ||
240 | |||
241 | void AddressbookWindow::slotUpdateToolbar() | ||
242 | { | ||
243 | Contact ce = abList->currentEntry(); | ||
244 | actionMail->setEnabled( !ce.defaultEmail().isEmpty() ); | ||
245 | } | ||
246 | |||
247 | void AddressbookWindow::showList() | ||
248 | { | ||
249 | if ( mView ) mView->hide(); | ||
250 | setCentralWidget( abList ); | ||
251 | abList->show(); | ||
252 | // update our focues... (or use a stack widget!); | ||
253 | abList->setFocus(); | ||
254 | } | ||
255 | |||
256 | void AddressbookWindow::showView() | ||
257 | { | ||
258 | if ( abList->numRows() > 0 ) { | ||
259 | abList->hide(); | ||
260 | setCentralWidget( abView() ); | ||
261 | mView->show(); | ||
262 | mView->setFocus(); | ||
263 | } | ||
264 | } | ||
265 | |||
266 | void AddressbookWindow::slotListNew() | ||
267 | { | ||
268 | Contact cnt; | ||
269 | if( !syncing ) { | ||
270 | if ( abEditor ) | ||
271 | abEditor->setEntry( cnt ); | ||
272 | abView()->init( cnt ); | ||
273 | editEntry( NewEntry ); | ||
274 | } else { | ||
275 | QMessageBox::warning(this, tr("Contacts"), | ||
276 | tr("Can not edit data, currently syncing")); | ||
277 | } | ||
278 | } | ||
279 | |||
280 | void AddressbookWindow::slotListView() | ||
281 | { | ||
282 | abView()->init( abList->currentEntry() ); | ||
283 | mView->sync(); | ||
284 | showView(); | ||
285 | } | ||
286 | |||
287 | void AddressbookWindow::slotListDelete() | ||
288 | { | ||
289 | if(!syncing) { | ||
290 | Contact tmpEntry = abList->currentEntry(); | ||
291 | |||
292 | // get a name, do the best we can... | ||
293 | QString strName = tmpEntry.fullName(); | ||
294 | if ( strName.isEmpty() ) { | ||
295 | strName = tmpEntry.company(); | ||
296 | if ( strName.isEmpty() ) | ||
297 | strName = "No Name"; | ||
298 | } | ||
299 | |||
300 | |||
301 | if ( QPEMessageBox::confirmDelete( this, tr( "Contacts" ), | ||
302 | strName ) ) { | ||
303 | abList->deleteCurrentEntry(); | ||
304 | showList(); | ||
305 | } | ||
306 | } else { | ||
307 | QMessageBox::warning( this, tr("Contacts"), | ||
308 | tr("Can not edit data, currently syncing") ); | ||
309 | } | ||
310 | } | ||
311 | |||
312 | void AddressbookWindow::slotViewBack() | ||
313 | { | ||
314 | showList(); | ||
315 | } | ||
316 | |||
317 | void AddressbookWindow::slotViewEdit() | ||
318 | { | ||
319 | if(!syncing) { | ||
320 | if (actionPersonal->isOn()) { | ||
321 | editPersonal(); | ||
322 | } else { | ||
323 | if ( !bAbEditFirstTime ) | ||
324 | abEditor->setEntry( abList->currentEntry() ); | ||
325 | editEntry( EditEntry ); | ||
326 | } | ||
327 | } else { | ||
328 | QMessageBox::warning( this, tr("Contacts"), | ||
329 | tr("Can not edit data, currently syncing") ); | ||
330 | } | ||
331 | } | ||
332 | |||
333 | |||
334 | |||
335 | void AddressbookWindow::writeMail() | ||
336 | { | ||
337 | Contact c = abList->currentEntry(); | ||
338 | QString name = c.fileAs(); | ||
339 | QString email = c.defaultEmail(); | ||
340 | QCopEnvelope e("QPE/Application/qtmail", "writeMail(QString,QString)"); | ||
341 | e << name << email; | ||
342 | } | ||
343 | |||
344 | |||
345 | |||
346 | |||
347 | static const char * beamfile = "/tmp/obex/contact.vcf"; | ||
348 | |||
349 | void AddressbookWindow::slotBeam() | ||
350 | { | ||
351 | QString filename; | ||
352 | Contact c; | ||
353 | if ( actionPersonal->isOn() ) { | ||
354 | filename = addressbookPersonalVCardName(); | ||
355 | if (!QFile::exists(filename)) | ||
356 | return; // can't beam a non-existent file | ||
357 | c = Contact::readVCard( filename )[0]; | ||
358 | } else { | ||
359 | unlink( beamfile ); // delete if exists | ||
360 | c = abList->currentEntry(); | ||
361 | mkdir("/tmp/obex/", 0755); | ||
362 | Contact::writeVCard( beamfile, c ); | ||
363 | filename = beamfile; | ||
364 | } | ||
365 | Ir *ir = new Ir( this ); | ||
366 | connect( ir, SIGNAL( done( Ir * ) ), this, SLOT( beamDone( Ir * ) ) ); | ||
367 | QString description = c.fullName(); | ||
368 | ir->send( filename, description, "text/x-vCard" ); | ||
369 | } | ||
370 | |||
371 | void AddressbookWindow::beamDone( Ir *ir ) | ||
372 | { | ||
373 | delete ir; | ||
374 | unlink( beamfile ); | ||
375 | } | ||
376 | |||
377 | |||
378 | static void parseName( const QString& name, QString *first, QString *middle, | ||
379 | QString * last ) | ||
380 | { | ||
381 | |||
382 | int comma = name.find ( "," ); | ||
383 | QString rest; | ||
384 | if ( comma > 0 ) { | ||
385 | *last = name.left( comma ); | ||
386 | comma++; | ||
387 | while ( comma < int(name.length()) && name[comma] == ' ' ) | ||
388 | comma++; | ||
389 | rest = name.mid( comma ); | ||
390 | } else { | ||
391 | int space = name.findRev( ' ' ); | ||
392 | *last = name.mid( space+1 ); | ||
393 | rest = name.left( space ); | ||
394 | } | ||
395 | int space = rest.find( ' ' ); | ||
396 | if ( space <= 0 ) { | ||
397 | *first = rest; | ||
398 | } else { | ||
399 | *first = rest.left( space ); | ||
400 | *middle = rest.mid( space+1 ); | ||
401 | } | ||
402 | |||
403 | } | ||
404 | |||
405 | |||
406 | void AddressbookWindow::appMessage(const QCString &msg, const QByteArray &data) | ||
407 | { | ||
408 | if (msg == "editPersonal()") { | ||
409 | editPersonal(); | ||
410 | } else if (msg == "editPersonalAndClose()") { | ||
411 | editPersonal(); | ||
412 | close(); | ||
413 | } else if ( msg == "addContact(QString,QString)" ) { | ||
414 | QDataStream stream(data,IO_ReadOnly); | ||
415 | QString name, email; | ||
416 | stream >> name >> email; | ||
417 | |||
418 | Contact cnt; | ||
419 | QString fn, mn, ln; | ||
420 | parseName( name, &fn, &mn, &ln ); | ||
421 | //qDebug( " %s - %s - %s", fn.latin1(), mn.latin1(), ln.latin1() ); | ||
422 | cnt.setFirstName( fn ); | ||
423 | cnt.setMiddleName( mn ); | ||
424 | cnt.setLastName( ln ); | ||
425 | cnt.setEmails( email ); | ||
426 | cnt.setDefaultEmail( email ); | ||
427 | cnt.setFileAs(); | ||
428 | |||
429 | if ( bAbEditFirstTime ) { | ||
430 | abEditor = new AbEditor( cnt, &orderedFields, &slOrderedFields, | ||
431 | this, "editor" ); | ||
432 | bAbEditFirstTime = FALSE; | ||
433 | } else { | ||
434 | abEditor->setEntry( cnt ); | ||
435 | } | ||
436 | abView()->init( cnt ); | ||
437 | editEntry( NewEntry ); | ||
438 | |||
439 | |||
440 | |||
441 | } | ||
442 | #if 0 | ||
443 | else if (msg == "pickAddresses(QCString,QCString,QStringList,...)" ) { | ||
444 | QDataStream stream(data,IO_ReadOnly); | ||
445 | QCString ch,m; | ||
446 | QStringList types; | ||
447 | stream >> ch >> m >> types; | ||
448 | AddressPicker picker(abList,this,0,TRUE); | ||
449 | picker.showMaximized(); | ||
450 | picker.setChoiceNames(types); | ||
451 | int i=0; | ||
452 | for (QStringList::ConstIterator it = types.begin(); it!=types.end(); ++it) { | ||
453 | QStringList sel; | ||
454 | stream >> sel; | ||
455 | picker.setSelection(i++,sel); | ||
456 | } | ||
457 | picker.showMaximized(); | ||
458 | picker.exec(); | ||
459 | |||
460 | // ###### note: contacts may have been added - save here! | ||
461 | |||
462 | setCentralWidget(abList); | ||
463 | QCopEnvelope e(ch,m); | ||
464 | i=0; | ||
465 | for (QStringList::ConstIterator it = types.begin(); it!=types.end(); ++it) { | ||
466 | QStringList sel = picker.selection(i++); | ||
467 | e << sel; | ||
468 | } | ||
469 | } | ||
470 | #endif | ||
471 | |||
472 | } | ||
473 | |||
474 | void AddressbookWindow::editPersonal() | ||
475 | { | ||
476 | QString filename = addressbookPersonalVCardName(); | ||
477 | Contact me; | ||
478 | if (QFile::exists(filename)) | ||
479 | me = Contact::readVCard( filename )[0]; | ||
480 | if (bAbEditFirstTime) { | ||
481 | abEditor = new AbEditor( me, &orderedFields, &slOrderedFields, | ||
482 | this, "editor" ); | ||
483 | // don't create a new editor every time | ||
484 | bAbEditFirstTime = FALSE; | ||
485 | } else | ||
486 | abEditor->setEntry( me ); | ||
487 | |||
488 | abEditor->setCaption(tr("Edit My Personal Details")); | ||
489 | abEditor->showMaximized(); | ||
490 | |||
491 | // fix the foxus... | ||
492 | abEditor->setNameFocus(); | ||
493 | if ( abEditor->exec() ) { | ||
494 | setFocus(); | ||
495 | Contact new_personal = abEditor->entry(); | ||
496 | QString fname = addressbookPersonalVCardName(); | ||
497 | Contact::writeVCard( fname, new_personal ); | ||
498 | abView()->init(new_personal); | ||
499 | abView()->sync(); | ||
500 | } | ||
501 | abEditor->setCaption( tr("Edit Address") ); | ||
502 | } | ||
503 | |||
504 | void AddressbookWindow::slotPersonalView() | ||
505 | { | ||
506 | if (!actionPersonal->isOn()) { | ||
507 | // we just turned it off | ||
508 | setCaption( tr("Contacts") ); | ||
509 | actionNew->setEnabled(TRUE); | ||
510 | actionTrash->setEnabled(TRUE); | ||
511 | actionFind->setEnabled(TRUE); | ||
512 | slotUpdateToolbar(); // maybe some of the above could be moved there | ||
513 | showList(); | ||
514 | return; | ||
515 | } | ||
516 | |||
517 | // XXX need to disable some QActions. | ||
518 | actionNew->setEnabled(FALSE); | ||
519 | actionTrash->setEnabled(FALSE); | ||
520 | actionFind->setEnabled(FALSE); | ||
521 | actionMail->setEnabled(FALSE); | ||
522 | |||
523 | setCaption( tr("Contacts - My Personal Details") ); | ||
524 | QString filename = addressbookPersonalVCardName(); | ||
525 | Contact me; | ||
526 | if (QFile::exists(filename)) | ||
527 | me = Contact::readVCard( filename )[0]; | ||
528 | |||
529 | abView()->init( me ); | ||
530 | abView()->sync(); | ||
531 | abList->hide(); | ||
532 | setCentralWidget( abView() ); | ||
533 | mView->show(); | ||
534 | mView->setFocus(); | ||
535 | } | ||
536 | |||
537 | void AddressbookWindow::editEntry( EntryMode entryMode ) | ||
538 | { | ||
539 | Contact entry; | ||
540 | if ( bAbEditFirstTime ) { | ||
541 | abEditor = new AbEditor( entry, &orderedFields, &slOrderedFields, | ||
542 | this, "editor" ); | ||
543 | bAbEditFirstTime = FALSE; | ||
544 | if ( entryMode == EditEntry ) | ||
545 | abEditor->setEntry( abList->currentEntry() ); | ||
546 | } | ||
547 | // other things may chane the caption. | ||
548 | abEditor->setCaption( tr("Edit Address") ); | ||
549 | |||
550 | #if defined(Q_WS_QWS) || defined(_WS_QWS_) | ||
551 | abEditor->showMaximized(); | ||
552 | #endif | ||
553 | // fix the foxus... | ||
554 | abEditor->setNameFocus(); | ||
555 | if ( abEditor->exec() ) { | ||
556 | setFocus(); | ||
557 | if ( entryMode == NewEntry ) { | ||
558 | Contact insertEntry = abEditor->entry(); | ||
559 | insertEntry.assignUid(); | ||
560 | abList->addEntry( insertEntry ); | ||
561 | } else { | ||
562 | Contact replaceEntry = abEditor->entry(); | ||
563 | if ( !replaceEntry.isValidUid() ) | ||
564 | replaceEntry.assignUid(); | ||
565 | abList->replaceCurrentEntry( replaceEntry ); | ||
566 | } | ||
567 | } | ||
568 | populateCategories(); | ||
569 | showList(); | ||
570 | } | ||
571 | |||
572 | void AddressbookWindow::listIsEmpty( bool empty ) | ||
573 | { | ||
574 | if ( !empty ) { | ||
575 | deleteButton->setEnabled( TRUE ); | ||
576 | } | ||
577 | } | ||
578 | |||
579 | void AddressbookWindow::reload() | ||
580 | { | ||
581 | syncing = FALSE; | ||
582 | abList->clear(); | ||
583 | abList->load( addressbookXMLFilename() ); | ||
584 | } | ||
585 | |||
586 | void AddressbookWindow::flush() | ||
587 | { | ||
588 | syncing = TRUE; | ||
589 | abList->save( addressbookXMLFilename() ); | ||
590 | } | ||
591 | |||
592 | |||
593 | void AddressbookWindow::closeEvent( QCloseEvent *e ) | ||
594 | { | ||
595 | if ( centralWidget() == mView ) { | ||
596 | if (actionPersonal->isOn()) { | ||
597 | // pretend we clicked it off | ||
598 | actionPersonal->setOn(FALSE); | ||
599 | slotPersonalView(); | ||
600 | } else { | ||
601 | showList(); | ||
602 | } | ||
603 | e->ignore(); | ||
604 | return; | ||
605 | } | ||
606 | |||
607 | if(syncing) { | ||
608 | /* shouldn't we save, I hear you say? well its already been set | ||
609 | so that an edit can not occur during a sync, and we flushed | ||
610 | at the start of the sync, so there is no need to save | ||
611 | Saving however itself would cause problems. */ | ||
612 | e->accept(); | ||
613 | return; | ||
614 | } | ||
615 | //################## shouldn't always save | ||
616 | if ( save() ) | ||
617 | e->accept(); | ||
618 | else | ||
619 | e->ignore(); | ||
620 | } | ||
621 | |||
622 | /* | ||
623 | Returns TRUE if it is OK to exit | ||
624 | */ | ||
625 | |||
626 | bool AddressbookWindow::save() | ||
627 | { | ||
628 | QString str = addressbookXMLFilename(); | ||
629 | if ( str.isNull() ) { | ||
630 | if ( QMessageBox::critical( 0, tr("Out of space"), | ||
631 | tr("Unable to save information.\n" | ||
632 | "Free up some space\n" | ||
633 | "and try again.\n" | ||
634 | "\nQuit anyway?"), | ||
635 | QMessageBox::Yes|QMessageBox::Escape, | ||
636 | QMessageBox::No|QMessageBox::Default ) | ||
637 | != QMessageBox::No ) | ||
638 | return TRUE; | ||
639 | else | ||
640 | return FALSE; | ||
641 | } else { | ||
642 | if ( !abList->save( str ) ) { | ||
643 | if ( QMessageBox::critical( 0, tr( "Out of space" ), | ||
644 | tr("Unable to save information.\n" | ||
645 | "Free up some space\n" | ||
646 | "and try again.\n" | ||
647 | "\nQuit anyway?"), | ||
648 | QMessageBox::Yes|QMessageBox::Escape, | ||
649 | QMessageBox::No|QMessageBox::Default ) | ||
650 | != QMessageBox::No ) | ||
651 | return TRUE; | ||
652 | else | ||
653 | return FALSE; | ||
654 | } | ||
655 | } | ||
656 | return TRUE; | ||
657 | } | ||
658 | |||
659 | void AddressbookWindow::slotSettings() | ||
660 | { | ||
661 | AddressSettings frmSettings( this ); | ||
662 | #if defined(Q_WS_QWS) || defined(_WS_QWS_) | ||
663 | frmSettings.showMaximized(); | ||
664 | #endif | ||
665 | |||
666 | if ( frmSettings.exec() ) { | ||
667 | allFields.clear(); | ||
668 | orderedFields.clear(); | ||
669 | slOrderedFields.clear(); | ||
670 | initFields(); | ||
671 | if ( abEditor ) | ||
672 | abEditor->loadFields(); | ||
673 | abList->refresh(); | ||
674 | } | ||
675 | } | ||
676 | |||
677 | |||
678 | void AddressbookWindow::initFields() | ||
679 | { | ||
680 | // we really don't need the things from the configuration, anymore | ||
681 | // only thing that is important are the important categories. So, | ||
682 | // Call the contact functions that correspond to these old functions... | ||
683 | |||
684 | QStringList xmlFields = Contact::fields(); | ||
685 | QStringList visibleFields = Contact::trfields(); | ||
686 | xmlFields.remove( "Title" ); | ||
687 | visibleFields.remove( tr("Name Title") ); | ||
688 | visibleFields.remove( tr("Notes") ); | ||
689 | |||
690 | int i, | ||
691 | version; | ||
692 | Config cfg( "AddressBook" ); | ||
693 | QString zn; | ||
694 | |||
695 | // ### Write a function to keep this from happening again... | ||
696 | QStringList::ConstIterator it; | ||
697 | for ( i = 0, it = xmlFields.begin(); it != xmlFields.end(); ++it, i++ ) { | ||
698 | allFields.append( i + 3 ); | ||
699 | } | ||
700 | |||
701 | cfg.setGroup( "Version" ); | ||
702 | version = cfg.readNumEntry( "version" ); | ||
703 | i = 0; | ||
704 | if ( version >= ADDRESSVERSION ) { | ||
705 | |||
706 | cfg.setGroup( "ImportantCategory" ); | ||
707 | |||
708 | zn = cfg.readEntry( "Category" + QString::number(i), QString::null ); | ||
709 | while ( !zn.isNull() ) { | ||
710 | if ( zn.contains( tr("Work") ) || zn.contains( tr("Mb") ) ) { | ||
711 | slOrderedFields.clear(); | ||
712 | break; | ||
713 | } | ||
714 | slOrderedFields.append( zn ); | ||
715 | zn = cfg.readEntry( "Category" + QString::number(++i), QString::null ); | ||
716 | } | ||
717 | } else { | ||
718 | QString str; | ||
719 | str = getenv("HOME"); | ||
720 | str += "/Settings/AddressBook.conf"; | ||
721 | QFile::remove( str ); | ||
722 | } | ||
723 | if ( slOrderedFields.count() > 0 ) { | ||
724 | for( QStringList::ConstIterator it = slOrderedFields.begin(); | ||
725 | it != slOrderedFields.end(); ++it ) { | ||
726 | QValueList<int>::ConstIterator itVl; | ||
727 | QStringList::ConstIterator itVis; | ||
728 | itVl = allFields.begin(); | ||
729 | for ( itVis = visibleFields.begin(); | ||
730 | itVis != visibleFields.end() && itVl != allFields.end(); | ||
731 | ++itVis, ++itVl ) { | ||
732 | if ( *it == *itVis && itVl != allFields.end() ) { | ||
733 | orderedFields.append( *itVl ); | ||
734 | } | ||
735 | } | ||
736 | } | ||
737 | } else { | ||
738 | QValueList<int>::ConstIterator it; | ||
739 | for ( it = allFields.begin(); it != allFields.end(); ++it ) | ||
740 | orderedFields.append( *it ); | ||
741 | |||
742 | slOrderedFields = visibleFields; | ||
743 | orderedFields.remove( Qtopia::AddressUid ); | ||
744 | orderedFields.remove( Qtopia::Title ); | ||
745 | orderedFields.remove( Qtopia::Groups ); | ||
746 | orderedFields.remove( Qtopia::AddressCategory ); | ||
747 | orderedFields.remove( Qtopia::FirstName ); | ||
748 | orderedFields.remove( Qtopia::LastName ); | ||
749 | orderedFields.remove( Qtopia::DefaultEmail ); | ||
750 | orderedFields.remove( Qtopia::FileAs ); | ||
751 | orderedFields.remove( Qtopia::Notes ); | ||
752 | orderedFields.remove( Qtopia::Gender ); | ||
753 | slOrderedFields.remove( tr("Name Title") ); | ||
754 | slOrderedFields.remove( tr("First Name") ); | ||
755 | slOrderedFields.remove( tr("Last Name") ); | ||
756 | slOrderedFields.remove( tr("File As") ); | ||
757 | slOrderedFields.remove( tr("Default Email") ); | ||
758 | slOrderedFields.remove( tr("Notes") ); | ||
759 | slOrderedFields.remove( tr("Gender") ); | ||
760 | |||
761 | } | ||
762 | } | ||
763 | |||
764 | |||
765 | AbLabel *AddressbookWindow::abView() | ||
766 | { | ||
767 | if ( !mView ) { | ||
768 | mView = new AbLabel( this, "viewer" ); | ||
769 | mView->init( Contact() ); | ||
770 | connect( mView, SIGNAL( okPressed() ), this, SLOT( slotListView() ) ); | ||
771 | } | ||
772 | return mView; | ||
773 | } | ||
774 | |||
775 | void AddressbookWindow::slotFind() | ||
776 | { | ||
777 | if ( centralWidget() == abView() ) | ||
778 | showList(); | ||
779 | FindDialog frmFind( "Contacts", this ); | ||
780 | QObject::connect( &frmFind, SIGNAL(signalFindClicked(const QString &, bool, bool, int)), abList, SLOT(slotDoFind( const QString&,bool,bool,int))); | ||
781 | QObject::connect( abList, SIGNAL(signalNotFound()), &frmFind, SLOT(slotNotFound()) ); | ||
782 | QObject::connect( abList, SIGNAL(signalWrapAround()), &frmFind, SLOT(slotWrapAround()) ); | ||
783 | frmFind.exec(); | ||
784 | if ( abList->numSelections() ) | ||
785 | abList->clearSelection(); | ||
786 | abList->clearFindRow(); | ||
787 | } | ||
788 | |||
789 | void AddressbookWindow::slotSetCategory( int c ) | ||
790 | { | ||
791 | if ( c <= 0 ) | ||
792 | return; | ||
793 | for ( unsigned int i = 1; i < catMenu->count(); i++ ) | ||
794 | catMenu->setItemChecked( i, c == (int)i ); | ||
795 | if ( c == 1 ) { | ||
796 | abList->setShowCategory( QString::null ); | ||
797 | setCaption( tr("Contacts") + " - " + tr ( "All" ) ); | ||
798 | } else if ( c == (int)catMenu->count() ) { | ||
799 | abList->setShowCategory( tr( "Unfiled" ) ); | ||
800 | setCaption( tr("Contacts") + " - " + tr( "Unfiled" ) ); | ||
801 | } else { | ||
802 | QString cat = abList->categories()[c - 2]; | ||
803 | abList->setShowCategory( cat ); | ||
804 | setCaption( tr("Contacts") + " - " + cat ); | ||
805 | } | ||
806 | } | ||
807 | |||
808 | void AddressbookWindow::populateCategories() | ||
809 | { | ||
810 | catMenu->clear(); | ||
811 | |||
812 | int id, | ||
813 | rememberId; | ||
814 | id = 1; | ||
815 | catMenu->insertItem( tr( "All" ), id++ ); | ||
816 | QStringList categories = abList->categories(); | ||
817 | categories.append( tr( "Unfiled" ) ); | ||
818 | for ( QStringList::Iterator it = categories.begin(); | ||
819 | it != categories.end(); ++it ) { | ||
820 | catMenu->insertItem( *it, id ); | ||
821 | if ( *it == abList->showCategory() ) | ||
822 | rememberId = id; | ||
823 | ++id; | ||
824 | } | ||
825 | if ( abList->showCategory().isEmpty() ) | ||
826 | slotSetCategory( 1 ); | ||
827 | else | ||
828 | slotSetCategory( rememberId ); | ||
829 | } | ||
diff --git a/core/pim/addressbook/addressbook.cw b/core/pim/addressbook/addressbook.cw new file mode 100644 index 0000000..452df36 --- a/dev/null +++ b/core/pim/addressbook/addressbook.cw | |||
@@ -0,0 +1,26 @@ | |||
1 | <!DOCTYPE CW><CW> | ||
2 | <customwidgets> | ||
3 | <customwidget> | ||
4 | <class>AbLineEdit</class> | ||
5 | <header location="local">ablineedit.h</header> | ||
6 | <sizehint> | ||
7 | <width>-1</width> | ||
8 | <height>-1</height> | ||
9 | </sizehint> | ||
10 | <pixmap> | ||
11 | <data format="XPM.GZ" length="646">789c6dd2c10ac2300c00d07bbf2234b7229d1be245fc04c5a3201e4615f430059d0711ff5ddb2e6bb236ec90eed134cb5a19d8ef36602af5ecdbfeeac05dda0798d3abebde87e3faa374d3807fa0d633a52d38d8de6f679fe33fc776e196f53cd010188256a3600a292882096246517815ca99884606e18044a3a40d91824820924265a7923a2e8bcd05f33db1173e002913175f2a6be6d3294871a2d95fa00e8a94ee017b69d339d90df1e77c57ea072ede6758</data> | ||
12 | </pixmap> | ||
13 | </customwidget> | ||
14 | <customwidget> | ||
15 | <class>AbMultiLineEdit</class> | ||
16 | <header location="local">abmultilineedit.h</header> | ||
17 | <sizehint> | ||
18 | <width>-1</width> | ||
19 | <height>-1</height> | ||
20 | </sizehint> | ||
21 | <pixmap> | ||
22 | <data format="XPM.GZ" length="646">789c6dd2c10ac2300c00d07bbf2234b7229d1be245fc04c5a3201e4615f430059d0711ff5ddb2e6bb236ec90eed134cb5a19d8ef36602af5ecdbfeeac05dda0798d3abebde87e3faa374d3807fa0d633a52d38d8de6f679fe33fc776e196f53cd010188256a3600a292882096246517815ca99884606e18044a3a40d91824820924265a7923a2e8bcd05f33db1173e002913175f2a6be6d3294871a2d95fa00e8a94ee017b69d339d90df1e77c57ea072ede6758</data> | ||
23 | </pixmap> | ||
24 | </customwidget> | ||
25 | </customwidgets> | ||
26 | </CW> | ||
diff --git a/core/pim/addressbook/addressbook.h b/core/pim/addressbook/addressbook.h new file mode 100644 index 0000000..9694465 --- a/dev/null +++ b/core/pim/addressbook/addressbook.h | |||
@@ -0,0 +1,99 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | #ifndef Addressbook_H | ||
21 | #define Addressbook_H | ||
22 | |||
23 | #include <qmainwindow.h> | ||
24 | |||
25 | class AbEditor; | ||
26 | class AbLabel; | ||
27 | class AbTable; | ||
28 | class QPEToolBar; | ||
29 | class QPopupMenu; | ||
30 | class QToolButton; | ||
31 | class QDialog; | ||
32 | class Ir; | ||
33 | class QAction; | ||
34 | |||
35 | class AddressbookWindow: public QMainWindow | ||
36 | { | ||
37 | Q_OBJECT | ||
38 | public: | ||
39 | AddressbookWindow( QWidget *parent = 0, const char *name = 0, WFlags f = 0 ); | ||
40 | ~AddressbookWindow(); | ||
41 | |||
42 | protected: | ||
43 | void resizeEvent( QResizeEvent * e ); | ||
44 | void showList(); | ||
45 | void showView(); | ||
46 | enum EntryMode { NewEntry=0, EditEntry }; | ||
47 | void editPersonal(); | ||
48 | void editEntry( EntryMode ); | ||
49 | void closeEvent( QCloseEvent *e ); | ||
50 | bool save(); | ||
51 | |||
52 | public slots: | ||
53 | void flush(); | ||
54 | void reload(); | ||
55 | void appMessage(const QCString &, const QByteArray &); | ||
56 | void setDocument( const QString & ); | ||
57 | |||
58 | private slots: | ||
59 | void slotListNew(); | ||
60 | void slotListView(); | ||
61 | void slotListDelete(); | ||
62 | void slotViewBack(); | ||
63 | void slotViewEdit(); | ||
64 | void slotPersonalView(); | ||
65 | void listIsEmpty( bool ); | ||
66 | void slotSettings(); | ||
67 | void writeMail(); | ||
68 | void slotBeam(); | ||
69 | void beamDone( Ir * ); | ||
70 | void slotFind(); | ||
71 | void slotSetCategory( int ); | ||
72 | void slotUpdateToolbar(); | ||
73 | |||
74 | private: | ||
75 | void initFields();// inititialize our fields... | ||
76 | AbLabel *abView(); | ||
77 | void populateCategories(); | ||
78 | |||
79 | QPopupMenu *catMenu; | ||
80 | QPEToolBar *listTools; | ||
81 | QToolButton *deleteButton; | ||
82 | QValueList<int> allFields, | ||
83 | orderedFields; | ||
84 | QStringList slOrderedFields; | ||
85 | enum Panes { paneList=0, paneView, paneEdit }; | ||
86 | AbEditor *abEditor; | ||
87 | AbLabel *mView; | ||
88 | AbTable *abList; | ||
89 | |||
90 | QAction *actionNew, *actionEdit, *actionTrash, *actionFind, *actionBeam, | ||
91 | *actionPersonal, *actionMail; | ||
92 | |||
93 | bool bAbEditFirstTime; | ||
94 | int viewMargin; | ||
95 | |||
96 | bool syncing; | ||
97 | }; | ||
98 | |||
99 | #endif | ||
diff --git a/core/pim/addressbook/addressbook.pro b/core/pim/addressbook/addressbook.pro new file mode 100644 index 0000000..8d3401d --- a/dev/null +++ b/core/pim/addressbook/addressbook.pro | |||
@@ -0,0 +1,22 @@ | |||
1 | TEMPLATE= app | ||
2 | CONFIG = qt warn_on release | ||
3 | DESTDIR = $(QPEDIR)/bin | ||
4 | HEADERS= addressbook.h \ | ||
5 | abeditor.h \ | ||
6 | ablabel.h \ | ||
7 | abtable.h \ | ||
8 | addresssettings.h | ||
9 | SOURCES= main.cpp \ | ||
10 | addressbook.cpp \ | ||
11 | abeditor.cpp \ | ||
12 | ablabel.cpp \ | ||
13 | abtable.cpp \ | ||
14 | addresssettings.cpp | ||
15 | INTERFACES= addresssettingsbase.ui | ||
16 | |||
17 | TARGET = addressbook | ||
18 | INCLUDEPATH += $(QPEDIR)/include | ||
19 | DEPENDPATH+= $(QPEDIR)/include | ||
20 | LIBS += -lqpe | ||
21 | |||
22 | TRANSLATIONS = ../i18n/de/addressbook.ts | ||
diff --git a/core/pim/addressbook/addresspicker.cpp b/core/pim/addressbook/addresspicker.cpp new file mode 100644 index 0000000..79c4d43 --- a/dev/null +++ b/core/pim/addressbook/addresspicker.cpp | |||
@@ -0,0 +1,52 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include "addresspicker.h" | ||
22 | #include "abtable.h" | ||
23 | |||
24 | #include <qlayout.h> | ||
25 | |||
26 | /*! | ||
27 | \a tab is reparented for use in the picker. Take it back out if you want | ||
28 | to regain ownership. | ||
29 | */ | ||
30 | AddressPicker::AddressPicker(AbTable* tab, QWidget* parent, const char* name, bool modal) : | ||
31 | QDialog(parent,name,modal) | ||
32 | { | ||
33 | QVBoxLayout* vb = new QVBoxLayout(this); | ||
34 | tab->reparent(this,QPoint(0,0)); | ||
35 | table = tab; | ||
36 | vb->addWidget(table); | ||
37 | } | ||
38 | |||
39 | void AddressPicker::setChoiceNames(const QStringList& list) | ||
40 | { | ||
41 | table->setChoiceNames(list); | ||
42 | } | ||
43 | |||
44 | void AddressPicker::setSelection(int index, const QStringList& list) | ||
45 | { | ||
46 | table->setChoiceSelection(index,list); | ||
47 | } | ||
48 | |||
49 | QStringList AddressPicker::selection(int index) const | ||
50 | { | ||
51 | return table->choiceSelection(index); | ||
52 | } | ||
diff --git a/core/pim/addressbook/addresspicker.h b/core/pim/addressbook/addresspicker.h new file mode 100644 index 0000000..8a57479 --- a/dev/null +++ b/core/pim/addressbook/addresspicker.h | |||
@@ -0,0 +1,39 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | #ifndef AddressPicker_H | ||
21 | #define AddressPicker_H | ||
22 | |||
23 | #include <qdialog.h> | ||
24 | |||
25 | class AbTable; | ||
26 | |||
27 | class AddressPicker : public QDialog { | ||
28 | public: | ||
29 | AddressPicker(AbTable* table, QWidget* parent, const char* name=0, bool modal=FALSE); | ||
30 | |||
31 | void setChoiceNames(const QStringList&); | ||
32 | void setSelection(int index, const QStringList&); | ||
33 | QStringList selection(int index) const; | ||
34 | |||
35 | private: | ||
36 | AbTable* table; | ||
37 | }; | ||
38 | |||
39 | #endif | ||
diff --git a/core/pim/addressbook/addresssettings.cpp b/core/pim/addressbook/addresssettings.cpp new file mode 100644 index 0000000..e7c2210 --- a/dev/null +++ b/core/pim/addressbook/addresssettings.cpp | |||
@@ -0,0 +1,136 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | |||
22 | #include "addresssettings.h" | ||
23 | |||
24 | #include <qpe/config.h> | ||
25 | #include <qpe/contact.h> | ||
26 | |||
27 | #include <qfile.h> | ||
28 | #include <qlistbox.h> | ||
29 | |||
30 | #include <stdlib.h> | ||
31 | |||
32 | AddressSettings::AddressSettings( QWidget *parent, const char *name ) | ||
33 | : AddressSettingsBase( parent, name, TRUE ) | ||
34 | { | ||
35 | init(); | ||
36 | } | ||
37 | |||
38 | AddressSettings::~AddressSettings() | ||
39 | { | ||
40 | } | ||
41 | |||
42 | void AddressSettings::init() | ||
43 | { | ||
44 | QStringList slFields = Contact::trfields(); | ||
45 | // Make this match what is in initFields | ||
46 | slFields.remove( tr("Name Title") ); | ||
47 | slFields.remove( tr("First Name") ); | ||
48 | slFields.remove( tr("Last Name") ); | ||
49 | slFields.remove( tr("File As") ); | ||
50 | slFields.remove( tr("Default Email") ); | ||
51 | slFields.remove( tr("Notes") ); | ||
52 | slFields.remove( tr("Gender") ); | ||
53 | |||
54 | |||
55 | for( QStringList::Iterator it = slFields.begin(); | ||
56 | it != slFields.end(); ++it ) { | ||
57 | fieldListBox->insertItem( *it ); | ||
58 | } | ||
59 | |||
60 | Config cfg( "AddressBook" ); | ||
61 | |||
62 | cfg.setGroup( "Version" ); | ||
63 | int version; | ||
64 | version = cfg.readNumEntry( "version" ); | ||
65 | if ( version >= ADDRESSVERSION ) { | ||
66 | int i = 0; | ||
67 | int p = 0; | ||
68 | cfg.setGroup( "ImportantCategory" ); | ||
69 | QString zn = cfg.readEntry( "Category" + QString::number(i), | ||
70 | QString::null ); | ||
71 | while ( !zn.isNull() ) { | ||
72 | for ( int m = i; m < (int)fieldListBox->count(); m++ ) { | ||
73 | if ( fieldListBox->text( m ) == zn ) { | ||
74 | if ( m != p ) { | ||
75 | fieldListBox->removeItem( m ); | ||
76 | fieldListBox->insertItem( zn, p ); | ||
77 | } | ||
78 | p++; | ||
79 | break; | ||
80 | } | ||
81 | } | ||
82 | zn = cfg.readEntry( "Category" + QString::number(++i), | ||
83 | QString::null ); | ||
84 | } | ||
85 | |||
86 | fieldListBox->setCurrentItem( 0 ); | ||
87 | } else { | ||
88 | QString str; | ||
89 | str = getenv("HOME"); | ||
90 | |||
91 | str += "/Settings/AddressBook.conf"; | ||
92 | QFile::remove( str ); | ||
93 | } | ||
94 | } | ||
95 | |||
96 | void AddressSettings::itemUp() | ||
97 | { | ||
98 | int i = fieldListBox->currentItem(); | ||
99 | if ( i > 0 ) { | ||
100 | QString item = fieldListBox->currentText(); | ||
101 | fieldListBox->removeItem( i ); | ||
102 | fieldListBox->insertItem( item, i-1 ); | ||
103 | fieldListBox->setCurrentItem( i-1 ); | ||
104 | } | ||
105 | } | ||
106 | |||
107 | void AddressSettings::itemDown() | ||
108 | { | ||
109 | int i = fieldListBox->currentItem(); | ||
110 | if ( i < (int)fieldListBox->count() - 1 ) { | ||
111 | QString item = fieldListBox->currentText(); | ||
112 | fieldListBox->removeItem( i ); | ||
113 | fieldListBox->insertItem( item, i+1 ); | ||
114 | fieldListBox->setCurrentItem( i+1 ); | ||
115 | } | ||
116 | } | ||
117 | |||
118 | void AddressSettings::accept() | ||
119 | { | ||
120 | save(); | ||
121 | QDialog::accept(); | ||
122 | } | ||
123 | |||
124 | |||
125 | void AddressSettings::save() | ||
126 | { | ||
127 | Config cfg( "AddressBook" ); | ||
128 | cfg.setGroup( "Version" ); | ||
129 | // *** To change the version change it here... | ||
130 | cfg.writeEntry( "version", QString::number(ADDRESSVERSION) ); | ||
131 | cfg.setGroup( "ImportantCategory" ); | ||
132 | |||
133 | for ( int i = 0; i < (int)fieldListBox->count(); i++ ) { | ||
134 | cfg.writeEntry( "Category"+QString::number(i), fieldListBox->text(i) ); | ||
135 | } | ||
136 | } | ||
diff --git a/core/pim/addressbook/addresssettings.h b/core/pim/addressbook/addresssettings.h new file mode 100644 index 0000000..0fdfa77 --- a/dev/null +++ b/core/pim/addressbook/addresssettings.h | |||
@@ -0,0 +1,47 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #ifndef _ADDRESSSETTINGS_H_ | ||
22 | #define _ADDRESSSETTINGS_H_ | ||
23 | |||
24 | #include <qlist.h> | ||
25 | #include <qstringlist.h> | ||
26 | #include "addresssettingsbase.h" | ||
27 | |||
28 | const int ADDRESSVERSION = 3; | ||
29 | |||
30 | class AddressSettings : public AddressSettingsBase | ||
31 | { | ||
32 | Q_OBJECT | ||
33 | public: | ||
34 | AddressSettings( QWidget *parent = 0, const char *name = 0 ); | ||
35 | ~AddressSettings(); | ||
36 | |||
37 | protected: | ||
38 | void accept(); | ||
39 | virtual void itemUp(); | ||
40 | virtual void itemDown(); | ||
41 | |||
42 | private: | ||
43 | void init(); | ||
44 | void save(); | ||
45 | }; | ||
46 | |||
47 | #endif // _ADDRESSSETTINGS_H_ | ||
diff --git a/core/pim/addressbook/addresssettingsbase.ui b/core/pim/addressbook/addresssettingsbase.ui new file mode 100644 index 0000000..bd3b85b --- a/dev/null +++ b/core/pim/addressbook/addresssettingsbase.ui | |||
@@ -0,0 +1,170 @@ | |||
1 | <!DOCTYPE UI><UI> | ||
2 | <class>AddressSettingsBase</class> | ||
3 | <comment>/********************************************************************** | ||
4 | ** Copyright (C) 2001 Trolltech AS. All rights reserved. | ||
5 | ** | ||
6 | ** This file is part of Qt Palmtop Environment. | ||
7 | ** | ||
8 | ** This file may be distributed and/or modified under the terms of the | ||
9 | ** GNU General Public License version 2 as published by the Free Software | ||
10 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
11 | ** packaging of this file. | ||
12 | ** | ||
13 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
14 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
15 | ** | ||
16 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
17 | ** | ||
18 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
19 | ** not clear to you. | ||
20 | ** | ||
21 | ** $Id$ | ||
22 | ** | ||
23 | **********************************************************************/</comment> | ||
24 | <widget> | ||
25 | <class>QDialog</class> | ||
26 | <property stdset="1"> | ||
27 | <name>name</name> | ||
28 | <cstring>AddressSettingsBase</cstring> | ||
29 | </property> | ||
30 | <property stdset="1"> | ||
31 | <name>geometry</name> | ||
32 | <rect> | ||
33 | <x>0</x> | ||
34 | <y>0</y> | ||
35 | <width>244</width> | ||
36 | <height>207</height> | ||
37 | </rect> | ||
38 | </property> | ||
39 | <property stdset="1"> | ||
40 | <name>caption</name> | ||
41 | <string>Arrange Edit Fields</string> | ||
42 | </property> | ||
43 | <property> | ||
44 | <name>layoutMargin</name> | ||
45 | </property> | ||
46 | <property> | ||
47 | <name>layoutSpacing</name> | ||
48 | </property> | ||
49 | <grid> | ||
50 | <property stdset="1"> | ||
51 | <name>margin</name> | ||
52 | <number>6</number> | ||
53 | </property> | ||
54 | <property stdset="1"> | ||
55 | <name>spacing</name> | ||
56 | <number>6</number> | ||
57 | </property> | ||
58 | <widget row="1" column="0" rowspan="3" colspan="1" > | ||
59 | <class>QListBox</class> | ||
60 | <property stdset="1"> | ||
61 | <name>name</name> | ||
62 | <cstring>fieldListBox</cstring> | ||
63 | </property> | ||
64 | </widget> | ||
65 | <widget row="0" column="0" rowspan="1" colspan="2" > | ||
66 | <class>QLabel</class> | ||
67 | <property stdset="1"> | ||
68 | <name>name</name> | ||
69 | <cstring>lblExplain</cstring> | ||
70 | </property> | ||
71 | <property stdset="1"> | ||
72 | <name>sizePolicy</name> | ||
73 | <sizepolicy> | ||
74 | <hsizetype>1</hsizetype> | ||
75 | <vsizetype>1</vsizetype> | ||
76 | </sizepolicy> | ||
77 | </property> | ||
78 | <property stdset="1"> | ||
79 | <name>frameShape</name> | ||
80 | <enum>MShape</enum> | ||
81 | </property> | ||
82 | <property stdset="1"> | ||
83 | <name>frameShadow</name> | ||
84 | <enum>MShadow</enum> | ||
85 | </property> | ||
86 | <property stdset="1"> | ||
87 | <name>text</name> | ||
88 | <string>Select the field order:</string> | ||
89 | </property> | ||
90 | <property stdset="1"> | ||
91 | <name>alignment</name> | ||
92 | <set>AlignTop|AlignLeft</set> | ||
93 | </property> | ||
94 | <property> | ||
95 | <name>hAlign</name> | ||
96 | </property> | ||
97 | <property> | ||
98 | <name>vAlign</name> | ||
99 | </property> | ||
100 | </widget> | ||
101 | <widget row="1" column="1" > | ||
102 | <class>QPushButton</class> | ||
103 | <property stdset="1"> | ||
104 | <name>name</name> | ||
105 | <cstring>upButton</cstring> | ||
106 | </property> | ||
107 | <property stdset="1"> | ||
108 | <name>text</name> | ||
109 | <string>Up</string> | ||
110 | </property> | ||
111 | <property stdset="1"> | ||
112 | <name>autoRepeat</name> | ||
113 | <bool>true</bool> | ||
114 | </property> | ||
115 | </widget> | ||
116 | <widget row="2" column="1" > | ||
117 | <class>QPushButton</class> | ||
118 | <property stdset="1"> | ||
119 | <name>name</name> | ||
120 | <cstring>downButton</cstring> | ||
121 | </property> | ||
122 | <property stdset="1"> | ||
123 | <name>text</name> | ||
124 | <string>Down</string> | ||
125 | </property> | ||
126 | <property stdset="1"> | ||
127 | <name>autoRepeat</name> | ||
128 | <bool>true</bool> | ||
129 | </property> | ||
130 | </widget> | ||
131 | <spacer row="3" column="1" > | ||
132 | <property> | ||
133 | <name>name</name> | ||
134 | <cstring>Spacer2</cstring> | ||
135 | </property> | ||
136 | <property stdset="1"> | ||
137 | <name>orientation</name> | ||
138 | <enum>Vertical</enum> | ||
139 | </property> | ||
140 | <property stdset="1"> | ||
141 | <name>sizeType</name> | ||
142 | <enum>Expanding</enum> | ||
143 | </property> | ||
144 | <property> | ||
145 | <name>sizeHint</name> | ||
146 | <size> | ||
147 | <width>20</width> | ||
148 | <height>20</height> | ||
149 | </size> | ||
150 | </property> | ||
151 | </spacer> | ||
152 | </grid> | ||
153 | </widget> | ||
154 | <connections> | ||
155 | <connection> | ||
156 | <sender>upButton</sender> | ||
157 | <signal>clicked()</signal> | ||
158 | <receiver>AddressSettingsBase</receiver> | ||
159 | <slot>itemUp()</slot> | ||
160 | </connection> | ||
161 | <connection> | ||
162 | <sender>downButton</sender> | ||
163 | <signal>clicked()</signal> | ||
164 | <receiver>AddressSettingsBase</receiver> | ||
165 | <slot>itemDown()</slot> | ||
166 | </connection> | ||
167 | <slot access="protected">itemUp()</slot> | ||
168 | <slot access="protected">itemDown()</slot> | ||
169 | </connections> | ||
170 | </UI> | ||
diff --git a/core/pim/addressbook/main.cpp b/core/pim/addressbook/main.cpp new file mode 100644 index 0000000..2ea1819 --- a/dev/null +++ b/core/pim/addressbook/main.cpp | |||
@@ -0,0 +1,41 @@ | |||
1 | /********************************************************************** | ||
2 | ** Copyright (C) 2000 Trolltech AS. All rights reserved. | ||
3 | ** | ||
4 | ** This file is part of Qt Palmtop Environment. | ||
5 | ** | ||
6 | ** This file may be distributed and/or modified under the terms of the | ||
7 | ** GNU General Public License version 2 as published by the Free Software | ||
8 | ** Foundation and appearing in the file LICENSE.GPL included in the | ||
9 | ** packaging of this file. | ||
10 | ** | ||
11 | ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE | ||
12 | ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. | ||
13 | ** | ||
14 | ** See http://www.trolltech.com/gpl/ for GPL licensing information. | ||
15 | ** | ||
16 | ** Contact info@trolltech.com if any conditions of this licensing are | ||
17 | ** not clear to you. | ||
18 | ** | ||
19 | **********************************************************************/ | ||
20 | |||
21 | #include "addressbook.h" | ||
22 | |||
23 | #include <qpe/qpeapplication.h> | ||
24 | #include <qpe/qcopenvelope_qws.h> | ||
25 | #include <qstring.h> | ||
26 | |||
27 | int main( int argc, char ** argv ) | ||
28 | { | ||
29 | QPEApplication a( argc, argv ); | ||
30 | |||
31 | AddressbookWindow mw; | ||
32 | QObject::connect( &a, SIGNAL( flush() ), &mw, SLOT( flush() ) ); | ||
33 | QObject::connect( &a, SIGNAL( reload() ), &mw, SLOT( reload() ) ); | ||
34 | QObject::connect( &a, SIGNAL( appMessage(const QCString &, const QByteArray &) ), | ||
35 | &mw, SLOT( appMessage(const QCString &, const QByteArray &) ) ); | ||
36 | |||
37 | mw.setCaption( AddressbookWindow::tr("Contacts") ); | ||
38 | a.showMainDocumentWidget(&mw); | ||
39 | |||
40 | return a.exec(); | ||
41 | } | ||
diff --git a/core/pim/addressbook/qpe-addressbook.control b/core/pim/addressbook/qpe-addressbook.control new file mode 100644 index 0000000..cca98f3 --- a/dev/null +++ b/core/pim/addressbook/qpe-addressbook.control | |||
@@ -0,0 +1,9 @@ | |||
1 | Files: bin/addressbook apps/Applications/addressbook.desktop | ||
2 | Priority: optional | ||
3 | Section: qpe/applications | ||
4 | Maintainer: Warwick Allison <warwick@trolltech.com> | ||
5 | Architecture: arm | ||
6 | Version: $QPE_VERSION-3 | ||
7 | Depends: qpe-base ($QPE_VERSION) | ||
8 | Description: Contacts | ||
9 | A simple addressbook for the Qtopia environment. | ||