cleared some warnings
[sw/motorsim] / src / com / billkuker / rocketry / motorsim / visual / workbench / SRFuelEditor.java
1 package com.billkuker.rocketry.motorsim.visual.workbench;
2
3 import java.awt.Dimension;
4 import java.awt.FlowLayout;
5 import java.awt.event.ActionEvent;
6 import java.awt.event.ActionListener;
7 import java.beans.PropertyChangeEvent;
8 import java.text.DecimalFormat;
9 import java.text.NumberFormat;
10 import java.util.Collections;
11 import java.util.Vector;
12
13 import javax.measure.quantity.Pressure;
14 import javax.measure.quantity.Velocity;
15 import javax.measure.quantity.VolumetricDensity;
16 import javax.measure.unit.SI;
17 import javax.swing.ButtonGroup;
18 import javax.swing.JButton;
19 import javax.swing.JFrame;
20 import javax.swing.JPanel;
21 import javax.swing.JRadioButton;
22 import javax.swing.JScrollPane;
23 import javax.swing.JSplitPane;
24 import javax.swing.JTable;
25 import javax.swing.SwingUtilities;
26 import javax.swing.event.ChangeEvent;
27 import javax.swing.event.ChangeListener;
28 import javax.swing.table.AbstractTableModel;
29
30 import org.jscience.physics.amount.Amount;
31
32 import com.billkuker.rocketry.motorsim.Fuel;
33 import com.billkuker.rocketry.motorsim.RocketScience;
34 import com.billkuker.rocketry.motorsim.fuel.EditableFuel.EditableCombustionProduct;
35 import com.billkuker.rocketry.motorsim.fuel.PiecewiseSaintRobertFuel;
36 import com.billkuker.rocketry.motorsim.fuel.SaintRobertFuel;
37 import com.billkuker.rocketry.motorsim.fuel.SaintRobertFuel.Type;
38 import com.billkuker.rocketry.motorsim.visual.Chart;
39 import com.billkuker.rocketry.motorsim.visual.Editor;
40
41 public class SRFuelEditor extends JSplitPane {
42         private static final NumberFormat nf = new DecimalFormat("##########.###");
43
44         Chart<Pressure, Velocity> burnRate;
45
46         private class Entry implements Comparable<Entry> {
47                 Amount<Pressure> p = Amount.valueOf(0, RocketScience.UnitPreference.getUnitPreference().getPreferredUnit(RocketScience.PSI));
48                 double a;
49                 double n;
50
51                 @Override
52                 public int compareTo(Entry o) {
53                         return p.compareTo(o.p);
54                 }
55         }
56
57         public static class EditablePSRFuel extends PiecewiseSaintRobertFuel {
58
59                 private Amount<VolumetricDensity> idealDensity = (Amount<VolumetricDensity>) Amount
60                                 .valueOf("1 g/mm^3");
61                 private double combustionEfficiency = 1;
62                 private double densityRatio = 1;
63                 private EditableCombustionProduct cp;
64                 private String name = "New Fuel";
65
66                 public EditablePSRFuel(Type t) {
67                         super(t);
68                         cp = new EditableCombustionProduct();
69                 }
70                 
71                 public void clear(){
72                         super.clear();
73                 }
74                 
75                 public void setType(Type t){
76                         super.setType(t);
77                 }
78
79                 public void add(Amount<Pressure> p, final double _a, final double _n) {
80                         super.add(p, _a, _n);
81
82                 }
83
84                 public Amount<VolumetricDensity> getIdealDensity() {
85                         return idealDensity;
86                 }
87
88                 public void setIdealDensity(Amount<VolumetricDensity> idealDensity) {
89                         this.idealDensity = idealDensity;
90                 }
91
92                 public double getCombustionEfficiency() {
93                         return combustionEfficiency;
94                 }
95
96                 public void setCombustionEfficiency(double combustionEfficiency) {
97                         this.combustionEfficiency = combustionEfficiency;
98                 }
99
100                 public double getDensityRatio() {
101                         return densityRatio;
102                 }
103
104                 public void setDensityRatio(double densityRatio) {
105                         this.densityRatio = densityRatio;
106                 }
107
108                 @Override
109                 public CombustionProduct getCombustionProduct() {
110                         return cp;
111                 }
112
113                 public String getName() {
114                         return name;
115                 }
116
117                 public void setName(String name) {
118                         this.name = name;
119                 }
120
121         }
122
123         final EditablePSRFuel f = new EditablePSRFuel(SaintRobertFuel.Type.SI);
124
125         private class TM extends AbstractTableModel {
126
127                 @Override
128                 public int getColumnCount() {
129                         return 3;
130                 }
131
132                 @Override
133                 public int getRowCount() {
134                         return entries.size();
135                 }
136
137                 @Override
138                 public String getColumnName(int col) {
139                         switch (col) {
140                         case 0:
141                                 return "Pressure";
142                         case 1:
143                                 return "Coefficient (a)";
144                         case 2:
145                                 return "Exponent (n)";
146                         }
147                         return null;
148                 }
149
150                 @Override
151                 public Object getValueAt(int rowIndex, int columnIndex) {
152                         Entry e = entries.get(rowIndex);
153                         switch (columnIndex) {
154                         case 0:
155                                 //Format like 100 psi or 4.8 Mpa
156                                 return nf.format(e.p.doubleValue(e.p.getUnit())) + " " + e.p.getUnit();
157                         case 1:
158                                 return e.a;
159                         case 2:
160                                 return e.n;
161                         }
162                         return null;
163                 }
164
165                 public boolean isCellEditable(int row, int col) {
166                         return true;
167                 }
168
169                 public void setValueAt(Object value, int row, int col) {
170                         Entry e = entries.get(row);
171                         try {
172                                 switch (col) {
173                                 case 0:
174                                         try {
175                                                 e.p = (Amount<Pressure>) Amount.valueOf((String) value);
176                                         } catch ( Exception ee ){
177                                                 double d = Double.parseDouble((String)value);
178                                                 e.p = (Amount<Pressure>)Amount.valueOf(d, e.p.getUnit());
179                                         }
180                                         break;
181                                 case 1:
182                                         e.a = Double.valueOf((String) value);
183                                         break;
184                                 case 2:
185                                         e.n = Double.valueOf((String) value);
186                                 }
187                         } catch (Exception ex) {
188                                 ex.printStackTrace();
189                         }
190                         Collections.sort(entries);
191                         fireTableDataChanged();
192                         //f = new EditablePSRFuel(SaintRobertFuel.Type.NONSI);
193                         f.clear();
194                         for (Entry en : entries) {
195                                 f.add(en.p, en.a, en.n);
196                         }
197                         f.firePropertyChange(new PropertyChangeEvent(f,"entries", null, null));
198
199                         update();
200
201                 }
202
203                 @Override
204                 public void fireTableDataChanged() {
205                         super.fireTableDataChanged();
206                 }
207
208         };
209         
210         public Fuel getFuel(){
211                 return f;
212         }
213
214         private void update() {
215                 SwingUtilities.invokeLater(new Runnable() {
216
217                         @Override
218                         public void run() {
219                                 editTop.setTopComponent(new Editor(f));
220                                 editTop.setBottomComponent(new Editor(f.getCombustionProduct()));
221                                 if (burnRate != null)
222                                         SRFuelEditor.this.remove(burnRate);
223                                 try {
224                                         burnRate = new Chart<Pressure, Velocity>(
225                                                         SI.MEGA(SI.PASCAL), SI.MILLIMETER.divide(SI.SECOND)
226                                                                         .asType(Velocity.class), f, "burnRate");
227                                 } catch (NoSuchMethodException e) {
228                                         throw new Error(e);
229                                 }
230                                 burnRate.setDomain(burnRate.new IntervalDomain(Amount.valueOf(
231                                                 0, SI.MEGA(SI.PASCAL)), Amount.valueOf(11, SI
232                                                 .MEGA(SI.PASCAL)), 50));
233                                 SRFuelEditor.this.setRightComponent(burnRate);
234                                 SRFuelEditor.this.revalidate();
235                         }
236                 });
237         }
238
239         private Vector<Entry> entries = new Vector<Entry>();
240
241         JSplitPane editParent;
242         JSplitPane editTop;
243         JSplitPane editBottom;
244         JPanel controls;
245
246         public SRFuelEditor() {
247                 super(HORIZONTAL_SPLIT);
248                 setResizeWeight(0);
249                 setDividerLocation(.3);
250                 
251                 final TM tm = new TM();
252
253                 editParent = new JSplitPane(JSplitPane.VERTICAL_SPLIT);
254                 editTop = new JSplitPane(JSplitPane.VERTICAL_SPLIT);
255                 editBottom = new JSplitPane(JSplitPane.VERTICAL_SPLIT);
256                 
257                 editParent.setTopComponent(editTop);
258                 editParent.setBottomComponent(editBottom);
259                 
260                 editTop.setTopComponent(new Editor(f));
261
262                 JTable table = new JTable(tm);
263                 JScrollPane scrollpane = new JScrollPane(table);
264                 scrollpane.setMinimumSize(new Dimension(200, 200));
265                 editBottom.setTopComponent(scrollpane);
266
267                 setLeftComponent(editParent);
268
269                 JButton add = new JButton("Add Data");
270                 add.addActionListener(new ActionListener() {
271                         @Override
272                         public void actionPerformed(ActionEvent e) {
273                                 entries.add(new Entry());
274                                 tm.fireTableDataChanged();
275                         }
276                 });
277                 controls = new JPanel();
278                 controls.setPreferredSize(new Dimension(200, 50));
279                 controls.setLayout(new FlowLayout());
280                         
281                 controls.add(add);
282
283                 
284                 final JRadioButton si, nonsi;
285                 ButtonGroup type = new ButtonGroup();
286                 JPanel radio = new JPanel();
287                 radio.add(si = new JRadioButton("SI"));
288                 radio.add(nonsi = new JRadioButton("NonSI"));
289                 controls.add(radio);
290                 type.add(si);
291                 type.add(nonsi);
292
293                 si.setSelected(true);
294                 
295                 si.addChangeListener(new ChangeListener(){
296                         @Override
297                         public void stateChanged(ChangeEvent e) {
298                                 if ( si.isSelected() ){
299                                         System.err.println("SI");
300                                         f.setType(Type.SI);
301                                 } else {
302                                         System.err.println("NONSI");
303                                         f.setType(Type.NONSI);
304                                 }
305                                 update();
306                         }});
307                 
308                 editBottom.setBottomComponent(controls);
309                 
310                 
311                 editParent.setDividerLocation(.5);
312                 editTop.setDividerLocation(.5);
313                 editBottom.setDividerLocation(.8);
314                 
315                 editParent.resetToPreferredSizes();
316                 revalidate();
317
318                 update();
319         }
320
321         public static void main(String args[]) {
322                 SRFuelEditor ed;
323                 JFrame f = new JFrame();
324                 f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
325                 f.setContentPane(ed = new SRFuelEditor());
326                 f.setSize(800, 600);
327                 f.setVisible(true);
328
329         }
330
331 }