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 {
43 private final List<String> columnNames;
46 * A ContactWrapper instance
48 private final ContactWrapper contactDatabase;
51 * A list of all contacts
53 private final List<Contact> contacts;
56 * Constructor which accepts maxContacts for maximum (initial) contacts and
59 * @param maxContacts Maximum allowed contacts
60 * @param client Client instance to use
62 public ContactManager (final int maxContacts, final Client client) {
63 // Always call super constructor first
66 // Set client instance
67 this.setClient(client);
70 this.contacts = new ArrayList<>(maxContacts);
72 // Init database connection
73 this.contactDatabase = new ContactDatabaseFrontend(this);
76 this.columnNames = new ArrayList<>(15);
79 this.fillColumnNamesFromBundle();
82 this.contactDatabase.readAllContacts();
85 //* NOISY-DEBUG: */ this.getLogger().debug("client=" + client);
89 * Adds given Contact instance to list
91 * @param contact Contact instance to add
94 public void addContact (final Contact contact) {
95 assert (this.contacts instanceof List) : "this.contacts is not initialized";
97 this.contacts.add(contact);
101 * Let the user add a new other address
104 public void doAddOtherAddress () {
105 throw new UnsupportedOperationException("Not supported yet.");
109 * Let the user change address data
111 * @param contact Instance to change data
112 * @param client Client instance to call back
115 public void doChangeAddressData (final Contact contact, final Client client) {
116 // First display it again
117 client.displayAddressBox(contact);
120 if (contact.isOwnContact()) {
121 // Deligate to client
122 this.getClient().doChangeOwnAddressData(contact);
124 // Other contact's address data to change
125 throw new UnsupportedOperationException("Changing contact entries not finished.");
133 * Let the user change "name data"
135 * @param contact Instance to change data
136 * @param client Client instance to call back
139 public void doChangeNameData (final Contact contact, final Client client) {
140 // First display them again
141 client.displayNameBox(contact);
144 if (contact.isOwnContact()) {
146 this.getClient().doChangeOwnNameData(contact);
148 // Then re-ask them ...
149 throw new UnsupportedOperationException("Changing contact entries not finished.");
157 * Let the user change other address
160 public void doChangeOtherAddress () {
161 throw new UnsupportedOperationException("Not supported yet.");
165 * Let the user change other data
167 * @param contact Instance to change data
168 * @param client Client instance to call back
169 * @todo Didn't handle birthday
172 public void doChangeOtherData (final Contact contact, final Client client) {
173 // First display them again
174 this.getClient().displayOtherDataBox(contact);
177 if (contact.isOwnContact()) {
179 this.getClient().doChangeOwnOtherData(contact);
181 // Then re-ask them ...
182 throw new UnsupportedOperationException("Changing contact entries not finished.");
190 * Allows the user to change his/her own data
193 public void doChangeOwnData () {
195 * First check if the user has registered own contact, before that
196 * nothing can be changed.
198 if (!this.isOwnContactAdded()) {
200 this.getClient().outputMessage("Sie haben noch nicht Ihre Daten eingegeben.");
202 // Skip any below code
207 Contact contact = this.getOwnContact();
210 assert (contact instanceof Contact);
213 contact.show(this.getClient());
216 // Ask user what to change
217 this.getClient().userChooseChangeContactData(contact);
218 } catch (final UnhandledUserChoiceException ex) {
219 this.getLogger().catching(ex);
224 * Let the user delete other address
227 public void doDeleteOtherAddress () {
228 throw new UnsupportedOperationException("Not supported yet.");
232 * Asks user for own data
235 public void doEnterOwnData () {
236 // Deligate this call to the client
237 Contact contact = this.getClient().doEnterOwnData();
239 // Add it to contact "book"
240 this.registerContact(contact);
244 public void doListContacts () {
245 throw new UnsupportedOperationException("Not supported yet.");
249 public void doSearchContacts () {
250 throw new UnsupportedOperationException("Not supported yet.");
254 * Shuts down this contact manager
257 public void doShutdown () {
258 // Shut down the database layer
259 this.getContactDatabase().doShutdown();
263 * Asks the user for his/her cellphone number
265 * @return User's cellphone number
268 public String enterOwnCellNumber () {
269 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Handynummer an: ", true);
273 * Asks the user for his/her city's name
275 * @return City's name of the user
278 public String enterOwnCity () {
279 return this.getClient().enterString(3, 50, "Bitte geben Sie Ihre Wohnort ein: ", false);
283 * Asks the user for his/her city's name
285 * @return City's name of the user
288 public String enterOwnComment () {
289 return this.getClient().enterString(0, 100, "Kommentar zu Ihrem Eintrag: ", true);
293 * Asks the user for his/her company name
295 * @return User's company name
298 public String enterOwnCompanyName () {
299 return this.getClient().enterString(5, 50, "Bitte geben Sie Ihre Firmenbezeichnung ein: ", true);
303 * Asks user for his/her own country code
305 * @return User's own country code
308 public String enterOwnCountryCode () {
309 return this.getClient().enterString(2, 2, "Bitte geben Sie den zweistelligen Ländercode von Ihrem Land ein: ", false).toUpperCase();
313 * Asks user for his/her own country code
315 * @return User's own country code
318 public String enterOwnEmailAddress () {
319 return this.getClient().enterString(10, 50, "Bitte geben Sie Ihre Email-Adresse ein: ", true);
323 * Asks the user for family name
325 * @return Family name of the user
328 public String enterOwnFamilyName () {
329 return this.getClient().enterString(2, 50, "Bitte geben Sie Ihren Nachnamen ein: ", false);
333 * Asks the user for family name
335 * @return Family name of the user
338 public String enterOwnFaxNumber () {
339 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Faxnummer an: ", true);
343 * Asks the user for gender, until a valid has been entered
345 * @return Gender of the user
348 public char enterOwnGender () {
349 return this.getClient().enterChar(new char[] {'M', 'F', 'C'}, "Bitte geben Sie die Anrede ein: (M=Herr, F=Frau, C=Firma): ");
353 * Asks the user for phone number
355 * @return Phone number of the user
358 public String enterOwnPhoneNumber () {
359 return this.getClient().enterString(5, 30, "Bitte geben Sie Ihre Telefonnummer an: ", true);
363 * Asks the user for own street (including number)
365 * @return Own street an number
368 public String enterOwnStreet () {
369 return this.getClient().enterString(5, 50, "Bitte geben Sie Ihre Strasse und Hausnummer ein: ", false);
373 * Asks the user for surname
375 * @return Surname of the user
378 public String enterOwnSurname () {
379 return this.getClient().enterString(2, 50, "Bitte geben Sie Ihren Vornamen ein: ", false);
383 * Asks the user for own ZIP code
388 public int enterOwnZipCode () {
389 return this.getClient().enterInt(0, 99_999, "Bitte geben Sie Ihre Postleitzahl ein: ");
393 public final int getColumnCount () {
394 assert (this.columnNames instanceof List) : "this.columnNames is not initialized";
396 return this.columnNames.size();
400 * Getter for column name at given index.
402 * @param columnIndex Column index
403 * @return Human-readable column name
406 public String getColumnName (final int columnIndex) {
407 assert (this.columnNames instanceof List) : "this.columnNames is not initialized";
409 // Get column name at index
410 return this.columnNames.get(columnIndex);
414 * Getter for whole contact list
416 * @return List of all contacts
419 public List<Contact> getList () {
420 assert (this.contacts instanceof List) : "this.contacts is not initialized";
421 return Collections.unmodifiableList(this.contacts);
425 * Checks whether own contact is already added by checking all entries for
428 * @return Whether own contact is already added
431 public boolean isOwnContactAdded () {
433 this.getLogger().trace("CALLED!");
435 assert (this.contacts instanceof List) : "this.contacts is not initialized";
437 // Default is not added
438 boolean isAdded = false;
440 // Now get it back from address book, first get an iterator
441 Iterator<Contact> iterator = this.contacts.iterator();
444 while (iterator.hasNext()) {
446 Contact contact = iterator.next();
449 if (contact instanceof Contact) {
451 isAdded = contact.isOwnContact();
453 // Is this own contact?
462 this.getLogger().trace(MessageFormat.format("isAdded={0} : EXIT!", isAdded));
469 * Adds given contact to address book and flushes all entries to database
471 * @param contact Contact being added
472 * @todo Add check for book size
475 public void registerContact (final Contact contact) {
476 // Check if contact is found
477 if (this.isContactAlreadyAdded(contact)) {
478 // Contact already added
479 // @todo Do something here
480 } else if ((contact.isOwnContact()) && (this.isOwnContactAdded())) {
481 // Own contact already added
482 // @todo Do something
488 */ this.getLogger().debug(MessageFormat.format("Adding '{0}' '{1}' at pos '{2}' ...", contact.getSurname(), contact.getFamilyName(), this.size()));
490 // Add contact to internal list
491 this.addContact(contact);
500 * @return size of contact "book"
503 public final int size () {
504 assert (this.contacts instanceof List) : "this.contacts is not initialized";
505 return this.contacts.size();
509 * Fills the column names array with strings from bundle
511 private void fillColumnNamesFromBundle () {
512 assert (this.columnNames instanceof List) : "this.columnNames is not initialized";
515 this.getLogger().trace("CALLED!");
517 // First get an iterator from key set to iterate over
518 Iterator<String> iterator = this.getBundle().keySet().iterator();
520 // Then iterate over all
521 while (iterator.hasNext()) {
523 String key = iterator.next();
525 // Does the key start with ContactManager.columnName ?
526 if (key.startsWith("ContactManager.columnName")) {
527 // This is the wanted entry.
528 this.getLogger().debug(MessageFormat.format("key={0}", key));
531 this.columnNames.add(this.getBundle().getString(key));
536 this.getLogger().trace(MessageFormat.format("getColumnCount()={0}: EXIT!", this.getColumnCount()));
540 * Flushes all entries by calling database backend
542 private void flush () {
544 this.getContactDatabase().flushAllContacts();
548 * A ContactWrapper instance
550 * @return the database
552 private ContactWrapper getContactDatabase () {
553 return this.contactDatabase;
557 * "Getter" for own contact instance or null if not found
559 * @return Contact instance or null
561 private Contact getOwnContact () {
562 assert (this.contacts instanceof List) : "this.contacts is not initialized";
564 // Now get it back from address book, first get an iterator
565 Iterator<Contact> iterator = this.contacts.iterator();
568 Contact contact = null;
570 // Search all contact
571 while (iterator.hasNext()) {
573 Contact next = iterator.next();
575 // Is this own contact?
576 if (next.isOwnContact()) {
584 // Return instance or null
589 * Checks whether given contact was found in "address book"
591 * @param checkContact Contact to be checked
592 * @return TRUE if found, FALSE if not found
594 private boolean isContactAlreadyAdded (final Contact checkContact) throws NullPointerException {
595 assert (this.contacts instanceof List) : "this.contacts is not initialized";
597 // Default is not found
598 boolean isFound = false;
601 //* NOISY-DEBUG: */ this.getLogger().debug("Checking '" + this.contacts.length + "' entries...");
602 // Now get it back from address book, first get an iterator
603 Iterator<Contact> iterator = this.contacts.iterator();
606 while (iterator.hasNext()) {
608 Contact contact = iterator.next();
611 //* NOISY-DEBUG: */ this.getLogger().debug("contact=" + contact + ",checkContent=" + checkContact);
613 if ((contact instanceof Contact) && ((contact.equals(checkContact)))) {
614 // Found matching entry