1 package net.sf.openrocket.gui.adaptors;
4 import java.awt.Component;
6 import javax.swing.AbstractListModel;
7 import javax.swing.ComboBoxModel;
8 import javax.swing.SwingUtilities;
10 import net.sf.openrocket.database.Database;
11 import net.sf.openrocket.database.DatabaseListener;
12 import net.sf.openrocket.database.Databases;
13 import net.sf.openrocket.gui.dialogs.CustomMaterialDialog;
14 import net.sf.openrocket.l10n.Translator;
15 import net.sf.openrocket.material.Material;
16 import net.sf.openrocket.rocketcomponent.ComponentChangeEvent;
17 import net.sf.openrocket.rocketcomponent.ComponentChangeListener;
18 import net.sf.openrocket.rocketcomponent.RocketComponent;
19 import net.sf.openrocket.startup.Application;
20 import net.sf.openrocket.util.Reflection;
22 public class MaterialModel extends AbstractListModel implements
23 ComboBoxModel, ComponentChangeListener, DatabaseListener<Material> {
25 private static final String CUSTOM = "Custom";
28 private final Component parentComponent;
30 private final RocketComponent component;
31 private final Material.Type type;
32 private final Database<Material> database;
34 private final Reflection.Method getMethod;
35 private final Reflection.Method setMethod;
36 private static final Translator trans = Application.getTranslator();
39 public MaterialModel(Component parent, RocketComponent component, Material.Type type) {
41 //this(parent, component, type, trans.get("MaterialModel.title.Material"));
42 this(parent, component, type, "Material");
45 public MaterialModel(Component parent, RocketComponent component, Material.Type type,
47 this.parentComponent = parent;
48 this.component = component;
53 this.database = Databases.LINE_MATERIAL;
57 this.database = Databases.BULK_MATERIAL;
61 this.database = Databases.SURFACE_MATERIAL;
65 throw new IllegalArgumentException("Unknown material type:"+type);
69 getMethod = new Reflection.Method(component.getClass().getMethod("get"+name));
70 setMethod = new Reflection.Method(component.getClass().getMethod("set"+name,
72 } catch (NoSuchMethodException e) {
73 throw new IllegalArgumentException("get/is methods for material " +
74 "not present in class "+component.getClass().getCanonicalName());
77 component.addComponentChangeListener(this);
78 database.addDatabaseListener(this);
82 public Object getSelectedItem() {
83 return getMethod.invoke(component);
87 public void setSelectedItem(Object item) {
89 // Clear selection - huh?
95 // Open custom material dialog in the future, after combo box has closed
96 SwingUtilities.invokeLater(new Runnable() {
99 CustomMaterialDialog dialog = new CustomMaterialDialog(
100 SwingUtilities.getWindowAncestor(parentComponent),
101 (Material) getSelectedItem(), true,
102 //// Define custom material
103 trans.get("MaterialModel.title.Defcustmat"));
105 dialog.setVisible(true);
107 if (!dialog.getOkClicked())
110 Material material = dialog.getMaterial();
111 setMethod.invoke(component, material);
113 if (dialog.isAddSelected()) {
114 database.add(material);
119 } else if (item instanceof Material) {
121 setMethod.invoke(component, item);
124 throw new IllegalArgumentException("Illegal item class " + item.getClass() +
130 public Object getElementAt(int index) {
131 if (index == database.size()) {
133 } else if (index >= database.size()+1) {
136 return database.get(index);
140 public int getSize() {
141 return database.size() + 1;
146 //////// Change listeners
149 public void componentChanged(ComponentChangeEvent e) {
150 if (((ComponentChangeEvent)e).isMassChange()) {
151 this.fireContentsChanged(this, 0, 0);
156 public void elementAdded(Material element, Database<Material> source) {
157 this.fireContentsChanged(this, 0, database.size());
161 public void elementRemoved(Material element, Database<Material> source) {
162 this.fireContentsChanged(this, 0, database.size());