2 * Copyright (C) 2015 Roland Haeder
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 package org.mxchange.addressbook.manager.contact;
19 import java.text.MessageFormat;
20 import java.util.ArrayList;
21 import java.util.Collections;
22 import java.util.Iterator;
23 import java.util.List;
24 import org.mxchange.addressbook.client.Client;
25 import org.mxchange.addressbook.contact.Contact;
26 import org.mxchange.addressbook.database.frontend.contact.ContactDatabaseFrontend;
27 import org.mxchange.addressbook.database.frontend.contact.ContactWrapper;
28 import org.mxchange.addressbook.exceptions.UnhandledUserChoiceException;
29 import org.mxchange.addressbook.manager.BaseManager;
32 * A manager for contacts, please note that this implementation loads the whole
35 * @author Roland Haeder
38 public class ContactManager extends BaseManager implements ManageableContact {
42 private final List<String> columnNames;
45 * A ContactWrapper instance
47 private final ContactWrapper contactDatabase;
50 * A list of all contacts
52 private final List<Contact> contacts;
55 * Constructor which accepts maxContacts for maximum (initial) contacts and
58 * @param maxContacts Maximum allowed contacts
59 * @param client Client instance to use
61 public ContactManager (final int maxContacts, final Client client) {
62 // Always call super constructor first
65 // Set client instance
66 this.setClient(client);
69 this.contacts = new ArrayList<>(maxContacts);
71 // Init database connection
72 this.contactDatabase = new ContactDatabaseFrontend(this);
75 this.columnNames = new ArrayList<>(15);
78 this.fillColumnNamesFromBundle();
81 this.contactDatabase.readAllContacts();
84 //* NOISY-DEBUG: */ this.getLogger().debug("client=" + client);
88 * Adds given Contact instance to list
90 * @param contact Contact instance to add
93 public void addContact (final Contact contact) {
94 assert(this.contacts instanceof List) : "this.contacts is not initialized";
96 this.contacts.add(contact);
100 * Let the user add a new other address
103 public void doAddOtherAddress () {
104 throw new UnsupportedOperationException("Not supported yet.");
108 * Let the user change address data
110 * @param contact Instance to change data
111 * @param client Client instance to call back
114 public void doChangeAddressData (final Contact contact, final Client client) {
115 // First display it again
116 client.displayAddressBox(contact);
119 if (contact.isOwnContact()) {
120 // Deligate to client
121 this.getClient().doChangeOwnAddressData(contact);
123 // Other contact's address data to change
124 throw new UnsupportedOperationException("Changing contact entries not finished.");
132 * Let the user change "name data"
134 * @param contact Instance to change data
135 * @param client Client instance to call back
138 public void doChangeNameData (final Contact contact, final Client client) {
139 // First display them again
140 client.displayNameBox(contact);
143 if (contact.isOwnContact()) {
145 this.getClient().doChangeOwnNameData(contact);
147 // Then re-ask them ...
148 throw new UnsupportedOperationException("Changing contact entries not finished.");
156 * Let the user change other address
159 public void doChangeOtherAddress () {
160 throw new UnsupportedOperationException("Not supported yet.");
164 * Let the user change other data
166 * @param contact Instance to change data
167 * @param client Client instance to call back
168 * @todo Didn't handle birthday
171 public void doChangeOtherData (final Contact contact, final Client client) {
172 // First display them again
173 this.getClient().displayOtherDataBox(contact);
176 if (contact.isOwnContact()) {
178 this.getClient().doChangeOwnOtherData(contact);
180 // Then re-ask them ...
181 throw new UnsupportedOperationException("Changing contact entries not finished.");
189 * Allows the user to change his/her own data
192 public void doChangeOwnData () {
194 * First check if the user has registered own contact, before that
195 * nothing can be changed.
197 if (!this.isOwnContactAdded()) {
199 this.getClient().outputMessage("Sie haben noch nicht Ihre Daten eingegeben.");
201 // Skip any below code
206 Contact contact = this.getOwnContact();
209 assert(contact instanceof Contact);
212 contact.show(this.getClient());
215 // Ask user what to change
216 this.getClient().userChooseChangeContactData(contact);
217 } catch (final UnhandledUserChoiceException ex) {
218 this.getLogger().catching(ex);
223 * Let the user delete other address
226 public void doDeleteOtherAddress () {
227 throw new UnsupportedOperationException("Not supported yet.");
231 * Asks user for own data
234 public void doEnterOwnData () {
235 // Deligate this call to the client
236 Contact contact = this.getClient().doEnterOwnData();
238 // Add it to contact "book"
239 this.registerContact(contact);
243 public void doListContacts () {
244 throw new UnsupportedOperationException("Not supported yet.");
248 public void doSearchContacts () {
249 throw new UnsupportedOperationException("Not supported yet.");
253 * Shuts down this contact manager
256 public void doShutdown () {
257 // Shut down the database layer
258 this.getContactDatabase().doShutdown();
262 * Asks the user for his/her cellphone number
264 * @return User's cellphone number
267 public String enterOwnCellNumber () {
268 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Handynummer an: ", true);
272 * Asks the user for his/her city's name
274 * @return City's name of the user
277 public String enterOwnCity () {
278 return this.getClient().enterString(3, 50, "Bitte geben Sie Ihre Wohnort ein: ", false);
282 * Asks the user for his/her city's name
284 * @return City's name of the user
287 public String enterOwnComment () {
288 return this.getClient().enterString(0, 100, "Kommentar zu Ihrem Eintrag: ", true);
292 * Asks the user for his/her company name
294 * @return User's company name
297 public String enterOwnCompanyName () {
298 return this.getClient().enterString(5, 50, "Bitte geben Sie Ihre Firmenbezeichnung ein: ", true);
302 * Asks user for his/her own country code
304 * @return User's own country code
307 public String enterOwnCountryCode () {
308 return this.getClient().enterString(2, 2, "Bitte geben Sie den zweistelligen Ländercode von Ihrem Land ein: ", false).toUpperCase();
312 * Asks user for his/her own country code
314 * @return User's own country code
317 public String enterOwnEmailAddress () {
318 return this.getClient().enterString(10, 50, "Bitte geben Sie Ihre Email-Adresse ein: ", true);
322 * Asks the user for family name
324 * @return Family name of the user
327 public String enterOwnFamilyName () {
328 return this.getClient().enterString(2, 50, "Bitte geben Sie Ihren Nachnamen ein: ", false);
332 * Asks the user for family name
334 * @return Family name of the user
337 public String enterOwnFaxNumber () {
338 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Faxnummer an: ", true);
342 * Asks the user for gender, until a valid has been entered
344 * @return Gender of the user
347 public char enterOwnGender () {
348 return this.getClient().enterChar(new char[] {'M', 'F', 'C'}, "Bitte geben Sie die Anrede ein: (M=Herr, F=Frau, C=Firma): ");
352 * Asks the user for phone number
354 * @return Phone number of the user
357 public String enterOwnPhoneNumber () {
358 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Telefonnummer an: ", true);
362 * Asks the user for own street (including number)
363 * @return Own street an number
366 public String enterOwnStreet () {
367 return this.getClient().enterString(5, 50, "Bitte geben Sie Ihre Strasse und Hausnummer ein: ", false);
371 * Asks the user for surname
372 * @return Surname of the user
375 public String enterOwnSurname () {
376 return this.getClient().enterString(2, 50, "Bitte geben Sie Ihren Vornamen ein: ", false);
380 * Asks the user for own ZIP code
385 public int enterOwnZipCode () {
386 return this.getClient().enterInt(0, 99_999, "Bitte geben Sie Ihre Postleitzahl ein: ");
390 public final int getColumnCount () {
391 assert(this.columnNames instanceof List) : "this.columnNames is not initialized";
393 return this.columnNames.size();
397 * Getter for column name at given index.
399 * @param columnIndex Column index
400 * @return Human-readable column name
403 public String getColumnName (final int columnIndex) {
404 assert(this.columnNames instanceof List) : "this.columnNames is not initialized";
406 // Get column name at index
407 return this.columnNames.get(columnIndex);
411 * Getter for whole contact list
413 * @return List of all contacts
416 public List<Contact> getList () {
417 assert(this.contacts instanceof List) : "this.contacts is not initialized";
418 return Collections.unmodifiableList(this.contacts);
422 * Checks whether own contact is already added by checking all entries for
425 * @return Whether own contact is already added
428 public boolean isOwnContactAdded () {
430 this.getLogger().trace("CALLED!");
432 assert(this.contacts instanceof List) : "this.contacts is not initialized";
434 // Default is not added
435 boolean isAdded = false;
437 // Now get it back from address book, first get an iterator
438 Iterator<Contact> iterator = this.contacts.iterator();
441 while (iterator.hasNext()) {
443 Contact contact = iterator.next();
446 if (contact instanceof Contact) {
448 isAdded = contact.isOwnContact();
450 // Is this own contact?
459 this.getLogger().trace(MessageFormat.format("isAdded={0} : EXIT!", isAdded));
466 * Adds given contact to address book and flushes all entries to database
468 * @param contact Contact being added
469 * @todo Add check for book size
472 public void registerContact (final Contact contact) {
473 // Check if contact is found
474 if (this.isContactAlreadyAdded(contact)) {
475 // Contact already added
476 // @todo Do something here
477 } else if ((contact.isOwnContact()) && (this.isOwnContactAdded())) {
478 // Own contact already added
479 // @todo Do something
483 /* NOISY-DEBUG: */ this.getLogger().debug(MessageFormat.format("Adding '{0}' '{1}' at pos '{2}' ...", contact.getSurname(), contact.getFamilyName(), this.size()));
485 // Add contact to internal list
486 this.addContact(contact);
495 * @return size of contact "book"
498 public final int size () {
499 assert(this.contacts instanceof List) : "this.contacts is not initialized";
500 return this.contacts.size();
504 * Fills the column names array with strings from bundle
506 private void fillColumnNamesFromBundle () {
507 assert(this.columnNames instanceof List) : "this.columnNames is not initialized";
510 this.getLogger().trace("CALLED!");
512 // First get an iterator from key set to iterate over
513 Iterator<String> iterator = this.getBundle().keySet().iterator();
515 // Then iterate over all
516 while (iterator.hasNext()) {
518 String key = iterator.next();
520 // Does the key start with ContactManager.columnName ?
521 if (key.startsWith("ContactManager.columnName")) {
522 // This is the wanted entry.
523 this.getLogger().debug(MessageFormat.format("key={0}", key));
526 this.columnNames.add(this.getBundle().getString(key));
531 this.getLogger().trace(MessageFormat.format("getColumnCount()={0}: EXIT!", this.getColumnCount()));
535 * Flushes all entries by calling database backend
537 private void flush () {
539 this.getContactDatabase().flushAllContacts();
543 * A ContactWrapper instance
545 * @return the database
547 private ContactWrapper getContactDatabase () {
548 return this.contactDatabase;
552 * "Getter" for own contact instance or null if not found
554 * @return Contact instance or null
556 private Contact getOwnContact () {
557 assert(this.contacts instanceof List) : "this.contacts is not initialized";
559 // Now get it back from address book, first get an iterator
560 Iterator<Contact> iterator = this.contacts.iterator();
563 Contact contact = null;
565 // Search all contact
566 while (iterator.hasNext()) {
568 Contact next = iterator.next();
570 // Is this own contact?
571 if (next.isOwnContact()) {
579 // Return instance or null
584 * Checks whether given contact was found in "address book"
586 * @param checkContact Contact to be checked
587 * @return TRUE if found, FALSE if not found
589 private boolean isContactAlreadyAdded (final Contact checkContact) throws NullPointerException {
590 assert(this.contacts instanceof List) : "this.contacts is not initialized";
592 // Default is not found
593 boolean isFound = false;
596 //* NOISY-DEBUG: */ this.getLogger().debug("Checking '" + this.contacts.length + "' entries...");
598 // Now get it back from address book, first get an iterator
599 Iterator<Contact> iterator = this.contacts.iterator();
602 while (iterator.hasNext()) {
604 Contact contact = iterator.next();
607 //* NOISY-DEBUG: */ this.getLogger().debug("contact=" + contact + ",checkContent=" + checkContact);
610 if ((contact instanceof Contact) && ((contact.equals(checkContact)))) {
611 // Found matching entry