SR-JRC | ein Framework für Java-Richclient-Anwendungen |
| Entitätsübersicht erstellen Genaugenommen ist die Übersichtsklasse kein View, sondern ein Viewcontroller, aber wir wollen ja nicht päpstlicher sein, als der Papst - schließlich bleiben die "großen" Benutzeraktionen der Kontrollerklasse (der Anwendung) vorbehalten. Grundlage für eine Übersichtsanzeige ist die Klasse public class AddressTableView extends AbstractTableView<Addresses> { protected static final String PREFIX = AddressesTableView.class.getSimpleName(); protected static RendererFactory rf; public AddressTableView(List<Addresses> list, int selectionMode, List<Addresses> initialSelection) { super(list, selectionMode, initialSelection); setTableFormat(new AddressTableFormat()); setSelectionMode(selectionMode); } @Override protected JComponent buildPanel() { return createTable(); } } Für eine einfache Übersicht reicht es, bei Wer weiterführende Beispiele sucht, möge sich bitte das Projekt VdrAssistant anschauen. Dort gibt es weitere Übersichten und komplexerer Filter (z.B. EpgManager). Wie der obige Konstruktor schon andeutete, braucht selbst die einfachste Variante einer Übersicht zumindest ein Tabellenformat. Mit dem Format werden die Spalten der Übersicht konfiguriert. Erweiterte Übersichten können noch Filter und vieles mehr enthalten. Doch dazu später. Eine solche Formatklasse könnte wie folgt aussehen: protected class AddressTableFormat extends AbstractTableFormat { private final String[] columnNames = { "type", "city", "street", "zip", "state", "country" }; private final int[] width = { 20, 200, 200, 90, 150, 150 }; public AddressTableFormat() { super(PREFIX); } @Override protected String[] getColumnNames() { return columnNames; } @Override protected int getColumnWidth(int idx) { if (idx < width.length) return width[idx]; return 0; } @Override protected int getMaxColWidth(int idx) { if (idx < width.length) return width[idx]; return 0; } @Override protected void setColumnRenderer(TableColumn tc, int colIndex) { if (colIndex == 0) tc.setCellRenderer(rf.getEnumRenderer(JLabel.RIGHT)); } @Override protected void setTypeRenderers(JTable table) { // ask for factory service here rf = (RendererFactory) ApplicationServiceProvider.getService(RendererFactory.class); } @Override public Object getColumnValue(Addresses instance, int idx) { switch (idx) { case 0: return instance.getType(); case 1: return instance.getCity(); case 2: return instance.getStreet(); case 3: return instance.getZip(); case 4: return instance.getState(); case 5: return instance.getCountry(); } return null; } }
Filter dienen dazu, die angezeigten Sätze der Übersicht zu reduzieren, ohne dafür auf die Datenbank zuzugreifen. Glazedlists bringt diese Funktionalität von Haus aus mit, d.h. der entsprechende Aufwand ist vernachlässigbar. Ein Filter besteht aus einem Eingabe-Element, über das der Anwender die Filterkriterien verändern kann (selbstverständlich setzen wir hier wieder auf JGoodies). Dann natürlich aus der Klasse, die den Filter auf die Datensätze der Liste anwendet - zu guter Letzt muss alles noch aktiviert werden. Fangen wir mit dem Eingabe-Element an: public class AddressesFilter implements ListFilterComponent<Addresses> { private JTextField filter; private TextComponentMatcherEditor<Addresses> me; public RecordingFilter() { filter = new JTextField(20); me = new TextComponentMatcherEditor<Addresses>( filter, new AddressesFilterator()); } public JComponent getFilterPane() { FormLayout layout = new FormLayout("right:max(25dlu;pref), 3dlu, default:grow"); DefaultFormBuilder builder = new DefaultFormBuilder(layout); MessageSource msgSource = (MessageSource) ApplicationServiceProvider.getService(MessageSource.class); builder.setDefaultDialogBorder(); builder.append(msgSource.getMessage(PREFIX + "filter", null, PREFIX + "filter", null), filter, true); return builder.getPanel(); } public MatcherEditor<Addresses> getMatcherEditor() { return me; } } Fehlt noch die Klasse, die den Filter auf die Liste der Übersicht anwendet. Bei der Funktion protected class AddressesFilterator implements TextFilterator<Addresses> { public void getFilterStrings(List Um den Filter zu verwenden, müssen wir die Übersichtsklasse etwas erweitern: public class AddressTableView extends AbstractTableView<Addresses> { protected static final String PREFIX = AddressesTableView.class.getSimpleName(); protected static RendererFactory rf; private AddressesFilter filter; public AddressTableView(List Hier nochmal die gesamte Übersichtklasse komplett: public class AddressTableView extends AbstractTableView<Addresses> { public class AddressesFilter implements ListFilterComponent<Addresses> { private JTextField filter; private TextComponentMatcherEditor<Addresses> me; public RecordingFilter() { filter = new JTextField(20); me = new TextComponentMatcherEditor<Addresses>( filter, new AddressesFilterator()); } public JComponent getFilterPane() { FormLayout layout = new FormLayout("right:max(25dlu;pref), 3dlu, default:grow"); DefaultFormBuilder builder = new DefaultFormBuilder(layout); MessageSource msgSource = (MessageSource) ApplicationServiceProvider.getService(MessageSource.class); builder.setDefaultDialogBorder(); builder.append(msgSource.getMessage(PREFIX + "filter", null, PREFIX + "filter", null), filter, true); return builder.getPanel(); } public MatcherEditor<Addresses> getMatcherEditor() { return me; } } protected class AddressesFilterator implements TextFilterator<Addresses> { public void getFilterStrings(List |