// Form package org.javamoney.examples.ez.money.gui.view.register; import static org.javamoney.examples.ez.common.CommonConstants.IS_MAC; import static org.javamoney.examples.ez.common.utility.ButtonHelper.buildButton; import static org.javamoney.examples.ez.common.utility.I18NHelper.getSharedProperty; import static org.javamoney.examples.ez.money.KeywordKeys.NOT_CATEGORIZED; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.CANCEL; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.DATE_PICKER; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.EDIT; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.ENTER; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.NEW; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.NEXT; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.PENDING; import static org.javamoney.examples.ez.money.gui.view.register.FormButtonKeys.SPLIT; import static org.javamoney.examples.ez.money.gui.view.register.FormFieldKeys.AMOUNT; import static org.javamoney.examples.ez.money.gui.view.register.FormFieldKeys.CHECK_NUMBER; import static org.javamoney.examples.ez.money.gui.view.register.FormFieldKeys.DATE; import static org.javamoney.examples.ez.money.gui.view.register.FormFieldKeys.NOTES; import static org.javamoney.examples.ez.money.model.DataManager.getAccounts; import static org.javamoney.examples.ez.money.model.DataManager.getExpenses; import static org.javamoney.examples.ez.money.model.DataManager.getIncome; import static org.javamoney.examples.ez.money.model.DataManager.getPayees; import static org.javamoney.examples.ez.money.model.dynamic.transaction.TransactionTypeKeys.EXPENSE; import static org.javamoney.examples.ez.money.model.dynamic.transaction.TransactionTypeKeys.INCOME; import static org.javamoney.examples.ez.money.model.dynamic.transaction.TransactionTypeKeys.TRANSFER; import static org.javamoney.examples.ez.money.model.persisted.transaction.Transaction.MAX_PAYEE_LENGTH; import static org.javamoney.examples.ez.money.utility.EditorHelper.createAmountFieldEditor; import static org.javamoney.examples.ez.money.utility.EditorHelper.createCheckNumberFieldEditor; import static org.javamoney.examples.ez.money.utility.EditorHelper.createDateFieldEditor; import static org.javamoney.examples.ez.money.utility.EditorHelper.createNotesFieldEditor; import java.awt.GridBagConstraints; import java.awt.event.ActionListener; import javax.swing.AbstractButton; import javax.swing.JButton; import javax.swing.JCheckBox; import javax.swing.JTextField; import org.javamoney.examples.ez.money.IconKeys; import org.javamoney.examples.ez.money.gui.chooser.ElementComboBoxChooser; import org.javamoney.examples.ez.money.model.DataCollection; import org.javamoney.examples.ez.money.model.dynamic.transaction.TransactionTypeKeys; import org.javamoney.examples.ez.common.gui.Link; import org.javamoney.examples.ez.common.gui.Panel; import org.javamoney.examples.ez.common.utility.ClipboardMenuController; import org.javamoney.examples.ez.common.utility.I18NHelper; import org.javamoney.examples.ez.common.utility.TextConstrainer; /** * This class facilitates management of all the elements that make up the * transaction form. */ final class Form extends Panel { /** * Constructs a new form customized for the specified transaction type. * * @param type The transaction type. * @param handler The listener to be notified when action events occur. */ protected Form(TransactionTypeKeys type, ActionListener handler) { setType(type); setPayFromChooser(new ElementComboBoxChooser(getPayFromCollection())); setPayToChooser(new ElementComboBoxChooser(getPayToCollection())); createButtons(handler); createFields(); buildPanel(); if(getType() != TRANSFER) { getPayFromChooser().setEditable(true); getPayFromChooser().getTextField().setDocument(new TextConstrainer(MAX_PAYEE_LENGTH)); // Add listeners. new AutoCompleteHandler(this); new ClipboardMenuController(getPayFromChooser().getTextField()); } // Add listeners. for(JTextField field : getFields()) { new ClipboardMenuController(field); } new FormDateHandler(this); new FormTraversalHandler(this); } /** * This method clears all the editable fields in the form. */ protected void clearFields() { for(JTextField field : getFields()) { field.setText(""); } if(getType() != TRANSFER) { getPayFromChooser().clearSelection(); setPayToIsSplit(false); } } /** * This method enables or disables the elements of the from depending of the * specified value. * * @param value true or false. */ protected void enableForm(boolean value) { // Enable buttons. for(AbstractButton button : getButtons()) { button.setEnabled(value); } // Enable fields. for(JTextField field : getFields()) { field.setEnabled(value); } // Enable choosers. getPayToChooser().setEnabled(value); getPayFromChooser().setEnabled(value); // Set defaults. getButton(NEW).setEnabled(true); // Splits are only for non-transfers. if(value == true && getType() == TRANSFER) { getButton(SPLIT).setEnabled(false); } } /** * This method returns the form button for the specified key. * * @param key The button's key. * * @return The form button for the specified key. */ protected AbstractButton getButton(FormButtonKeys key) { return getButtons()[key.ordinal()]; } /** * This method returns the form field for the specified key. * * @param key The field's key. * * @return The form field for the specified key. */ protected JTextField getField(FormFieldKeys key) { return getFields()[key.ordinal()]; } /** * This method returns where the money is being paid from, either an account * or payee. * * @return Where the money is being paid from, either an account or payee. */ protected String getPayFrom() { return getPayFromChooser().getSelectedItem(); } /** * This method returns the chooser for selecting where the money is being paid * from, either an account or payee. * * @return The chooser for selecting where the money is being paid from. */ protected ElementComboBoxChooser getPayFromChooser() { return itsPayFromChooser; } /** * This method returns the where the money is being paid to, either an account * or category. * * @return Where the money is being paid to, either an account or category. */ protected String getPayTo() { String payTo = getPayToChooser().getSelectedItem(); if(payTo.equals(NOT_CATEGORIZED.toString()) == true) { payTo = ""; } return payTo; } /** * This method returns the chooser for selecting where the money is being paid * to, either an account or category. * * @return The chooser for selecting where the money is being paid to. */ protected ElementComboBoxChooser getPayToChooser() { return itsPayToChooser; } /** * This method returns the transaction type. * * @return The transaction type. */ protected TransactionTypeKeys getType() { return itsType; } /** * This method sets whether or not the transaction is being paid out to * multiple categories. * <p> * <b>Note:</b> This should only apply to categories and not accounts. * * @param isSplit true or false. */ protected void setPayToIsSplit(boolean isSplit) { if(isSplit == true) { getPayToChooser().removeAllItems(); getPayToChooser().addItem(getProperty("split")); } else { getPayToChooser().displayElements(getPayToCollection()); getPayToChooser().addNotCategorizedOption(); getPayToChooser().setSelectedIndex(0); } } ////////////////////////////////////////////////////////////////////////////// // Start of private methods. ////////////////////////////////////////////////////////////////////////////// private void buildPanel() { String category = null; String gap = ": "; String payee = null; // Get correct category text. if(getType() == TRANSFER) { category = getSharedProperty("to") + gap; } else { category = getSharedProperty("category") + gap; } // Get correct payee text. if(getType() == EXPENSE) { payee = getSharedProperty("to") + gap; } else { payee = getSharedProperty("from") + gap; } // Build panel. setFill(GridBagConstraints.HORIZONTAL); add(getButton(NEXT), 6, 0, 1, 1, 0, 20); add(getButton(NEW), 0, 1, 1, 1, 0, 0); add(getField(DATE), 5, 1, 1, 1, 0, 20); add(getButton(DATE_PICKER), 6, 1, 1, 1, 0, 0); add(getButton(EDIT), 7, 2, 1, 1, 0, 20); add(getButton(SPLIT), 3, 3, 1, 1, 0, 20); add(getButton(ENTER), 7, 3, 1, 1, 0, 0); add(getButton(CANCEL), 7, 5, 1, 1, 0, 20); setAnchor(GridBagConstraints.EAST); setFill(GridBagConstraints.NONE); add(payee, 1, 2, 1, 1, 0, 0); add(category, 1, 3, 1, 1, 0, 0); add(getSharedProperty("notes") + gap, 1, 5, 1, 1, 0, 0); add(getSharedProperty("check_number") + gap, 4, 0, 1, 1, 0, 0); add(getSharedProperty("date") + gap, 4, 1, 1, 1, 0, 0); add(getSharedProperty("amount") + gap, 4, 2, 1, 1, 0, 0); setFill(GridBagConstraints.HORIZONTAL); add(getPayFromChooser(), 2, 2, 2, 1, 0, 0); add(getPayToChooser(), 2, 3, 1, 1, 100, 0); add(getField(NOTES), 2, 5, 2, 1, 0, 0); add(getField(CHECK_NUMBER), 5, 0, 1, 1, 0, 0); add(getField(AMOUNT), 5, 2, 1, 1, 0, 0); add(getButton(PENDING), 5, 3, 1, 1, 0, 0); // Aesthetic spacers. addEmptyCellAt(1, 6, 10); addEmptyCellAt(4, 4, 12); addEmptyCellAt(5, 5, 17); } private JButton createButton(FormButtonKeys key, String tip, ActionListener listener) { JButton button = new JButton(); // Build Button. buildButton(button, key.getText(), listener, "", tip); if(IS_MAC == false) { button.setMnemonic(key.getText().charAt(0)); } return button; } private void createButtons(ActionListener handler) { itsButtons = new AbstractButton[8]; getButtons()[CANCEL.ordinal()] = createButton(CANCEL, null, handler); getButtons()[EDIT.ordinal()] = createButton(EDIT, null, handler); getButtons()[ENTER.ordinal()] = createButton(ENTER, null, handler); getButtons()[DATE_PICKER.ordinal()] = createLink(IconKeys.DATE, getSharedProperty("date_tip"), handler); getButtons()[NEW.ordinal()] = createButton(NEW, null, handler); getButtons()[NEXT.ordinal()] = createLink(IconKeys.FORM_NEXT_CHECK, getProperty("next_tip"), handler); getButtons()[PENDING.ordinal()] = new JCheckBox(PENDING.getText()); getButtons()[SPLIT.ordinal()] = createButton(SPLIT, null, handler); } private void createFields() { itsFields = new JTextField[4]; getFields()[AMOUNT.ordinal()] = createAmountFieldEditor(); getFields()[CHECK_NUMBER.ordinal()] = createCheckNumberFieldEditor(); getFields()[DATE.ordinal()] = createDateFieldEditor(); getFields()[NOTES.ordinal()] = createNotesFieldEditor(); } private Link createLink(IconKeys icon, String tip, ActionListener listener) { Link link = new Link(); // Build link. buildButton(link, "", icon.getIcon(), listener, "", tip); return link; } private AbstractButton[] getButtons() { return itsButtons; } private JTextField[] getFields() { return itsFields; } private DataCollection getPayFromCollection() { return (getType() == TRANSFER) ? getAccounts() : getPayees(); } private DataCollection getPayToCollection() { DataCollection collection = getExpenses(); if(getType() == INCOME) { collection = getIncome(); } else if(getType() == TRANSFER) { collection = getAccounts(); } return collection; } private static String getProperty(String key) { return I18NHelper.getProperty("Form." + key); } private void setPayFromChooser(ElementComboBoxChooser chooser) { itsPayFromChooser = chooser; } private void setPayToChooser(ElementComboBoxChooser chooser) { itsPayToChooser = chooser; } private void setType(TransactionTypeKeys type) { itsType = type; } ////////////////////////////////////////////////////////////////////////////// // Start of class members. ////////////////////////////////////////////////////////////////////////////// private AbstractButton[] itsButtons; private JTextField[] itsFields; private ElementComboBoxChooser itsPayFromChooser; private ElementComboBoxChooser itsPayToChooser; private TransactionTypeKeys itsType; }