From 520529128c1dc589fc73ab724a3aec78cf8bcf20 Mon Sep 17 00:00:00 2001 From: kruland2607 Date: Thu, 29 Mar 2012 02:47:49 +0000 Subject: [PATCH] Initial work on BodyTube ComponentPresets. git-svn-id: https://openrocket.svn.sourceforge.net/svnroot/openrocket/trunk@491 180e2498-e6e9-4542-8430-84ac67f01cd8 --- core/.classpath | 1 + core/build.xml | 3 +- core/doc/techdoc/figures/motors/staged | 44 ++ core/lib/opencsv-2.3.jar | Bin 0 -> 14146 bytes core/resources/datafiles/bodytubepresets.csv | 384 ++++++++++++++++++ core/resources/l10n/messages.properties | 1 + .../database/BodyTubePresetDao.java | 50 +++ core/src/net/sf/openrocket/database/Daos.java | 7 + .../net/sf/openrocket/database/DaosImpl.java | 19 + .../gui/adaptors/BodyTubePresetModel.java | 105 +++++ .../openrocket/gui/adaptors/DoubleModel.java | 58 ++- .../gui/configdialog/BodyTubeConfig.java | 52 ++- .../sf/openrocket/preset/ComponentPreset.java | 34 +- .../openrocket/rocketcomponent/BodyTube.java | 13 +- .../rocketcomponent/ExternalComponent.java | 63 +-- .../sf/openrocket/startup/Application.java | 11 + .../net/sf/openrocket/startup/Startup.java | 3 + 17 files changed, 773 insertions(+), 75 deletions(-) create mode 100644 core/doc/techdoc/figures/motors/staged create mode 100644 core/lib/opencsv-2.3.jar create mode 100644 core/resources/datafiles/bodytubepresets.csv create mode 100644 core/src/net/sf/openrocket/database/BodyTubePresetDao.java create mode 100644 core/src/net/sf/openrocket/database/Daos.java create mode 100644 core/src/net/sf/openrocket/database/DaosImpl.java create mode 100644 core/src/net/sf/openrocket/gui/adaptors/BodyTubePresetModel.java diff --git a/core/.classpath b/core/.classpath index deeb71e4..275144a9 100644 --- a/core/.classpath +++ b/core/.classpath @@ -26,5 +26,6 @@ + diff --git a/core/build.xml b/core/build.xml index 0e57a6b0..a1c930c9 100644 --- a/core/build.xml +++ b/core/build.xml @@ -57,7 +57,7 @@ - + @@ -73,6 +73,7 @@ + diff --git a/core/doc/techdoc/figures/motors/staged b/core/doc/techdoc/figures/motors/staged new file mode 100644 index 00000000..b9b5e5c7 --- /dev/null +++ b/core/doc/techdoc/figures/motors/staged @@ -0,0 +1,44 @@ +#FIG 3.2 Produced by xfig version 3.2.5 +Landscape +Center +Metric +A4 +100.00 +Single +-2 +1200 2 +0 32 #696d69 +6 4275 -3915 5625 225 +1 2 0 1 0 0 48 -1 20 0.000 1 0.0000 4960 -224 170 87 4790 -224 5130 -224 +1 2 0 1 0 32 49 -1 20 0.000 1 0.0000 4951 -109 540 270 4411 -109 5491 -109 +1 2 0 1 0 7 50 -1 20 0.000 1 0.0000 4950 -112 675 337 4275 -112 5625 -112 +1 2 0 1 0 7 55 -1 -1 0.000 1 0.0000 4950 -292 675 337 4275 -292 5625 -292 +1 2 1 1 0 7 60 -1 -1 4.000 1 0.0000 4950 -3547 675 337 4275 -3547 5625 -3547 +2 1 0 1 0 7 51 -1 -1 0.000 0 0 -1 0 0 2 + 4275 -89 4275 -314 +2 2 0 0 -1 7 53 -1 20 0.000 0 0 -1 0 0 5 + 4275 -314 5625 -314 5625 -89 4275 -89 4275 -314 +2 1 0 1 0 7 51 -1 -1 0.000 0 0 -1 0 0 2 + 5625 -134 5625 -314 +2 1 1 1 0 32 60 -1 -1 4.000 0 0 -1 0 0 2 + 4275 -269 4275 -3554 +2 1 1 1 0 32 60 -1 -1 4.000 0 0 -1 0 0 2 + 5625 -269 5625 -3554 +2 1 0 1 0 7 51 -1 -1 0.000 0 0 -1 0 0 2 + 4590 -990 4590 -1170 +-6 +1 2 0 1 0 0 48 -1 20 0.000 1 0.0000 4960 4185 170 87 4790 4185 5130 4185 +1 2 0 1 0 32 49 -1 20 0.000 1 0.0000 4951 4300 540 270 4411 4300 5491 4300 +1 2 0 1 0 7 50 -1 20 0.000 1 0.0000 4950 4297 675 337 4275 4297 5625 4297 +1 2 0 1 0 7 55 -1 -1 0.000 1 0.0000 4950 4117 675 337 4275 4117 5625 4117 +1 2 1 1 0 7 55 -1 -1 4.000 1 0.0000 4950 862 675 337 4275 862 5625 862 +2 1 0 1 0 7 51 -1 -1 0.000 0 0 -1 0 0 2 + 4275 4320 4275 4095 +2 2 0 0 -1 7 53 -1 20 0.000 0 0 -1 0 0 5 + 4275 4095 5625 4095 5625 4320 4275 4320 4275 4095 +2 1 1 1 0 32 55 -1 -1 4.000 0 0 -1 0 0 2 + 4275 4140 4275 855 +2 1 1 1 0 32 55 -1 -1 4.000 0 0 -1 0 0 2 + 5625 4140 5625 855 +2 2 1 0 0 7 57 -1 20 2.000 0 0 -1 0 0 5 + 4275 1125 5625 1125 5625 4275 4275 4275 4275 1125 diff --git a/core/lib/opencsv-2.3.jar b/core/lib/opencsv-2.3.jar new file mode 100644 index 0000000000000000000000000000000000000000..32b00f927594a1854b371fe5bdeacc30f8aa75f8 GIT binary patch literal 14146 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
hi4iPC@6 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 templates = new ArrayList(); + + // Package scope constructor to control creation pattern. + BodyTubePresetDao() {} + + void initialize() throws IOException { + + InputStream is = BodyTubePresetDao.class.getResourceAsStream("/datafiles/bodytubepresets.csv"); + InputStreamReader r = new InputStreamReader(is); + // Create the CSV reader. Use comma separator and double-quote escaping. Skip first line. + CSVReader reader = new CSVReader(r,',','"',1); + String[] line; + while( (line = reader.readNext()) != null ) { + String manu = line[0]; + String prod = line[1]; + // inner diameter in centimeters + String idString = line[2]; + double innerRadius = Double.parseDouble(idString) /100.0/2.0; + // outer diameter in centimeters + String odString = line[3]; + double outerRadius = Double.parseDouble(odString) /100.0/2.0; + // length in centimeters + String maxLength = line[4]; + double length = Double.parseDouble(maxLength) /100.0; + BodyTube bt = new BodyTube(length, outerRadius, outerRadius - innerRadius ); + ComponentPreset preset = new ComponentPreset( manu, prod, "", bt ); + templates.add(preset); + } + + } + + public List listAll() { + return templates; + } + +} diff --git a/core/src/net/sf/openrocket/database/Daos.java b/core/src/net/sf/openrocket/database/Daos.java new file mode 100644 index 00000000..210a186a --- /dev/null +++ b/core/src/net/sf/openrocket/database/Daos.java @@ -0,0 +1,7 @@ +package net.sf.openrocket.database; + +public interface Daos { + + public BodyTubePresetDao getBodyTubePresetDao(); + +} diff --git a/core/src/net/sf/openrocket/database/DaosImpl.java b/core/src/net/sf/openrocket/database/DaosImpl.java new file mode 100644 index 00000000..c1fc44d8 --- /dev/null +++ b/core/src/net/sf/openrocket/database/DaosImpl.java @@ -0,0 +1,19 @@ +package net.sf.openrocket.database; + + +public class DaosImpl implements Daos { + + private BodyTubePresetDao bodyTubePresetDao; + + public DaosImpl() throws Exception { + bodyTubePresetDao = new BodyTubePresetDao(); + bodyTubePresetDao.initialize(); + + } + + @Override + public BodyTubePresetDao getBodyTubePresetDao() { + return bodyTubePresetDao; + } + +} diff --git a/core/src/net/sf/openrocket/gui/adaptors/BodyTubePresetModel.java b/core/src/net/sf/openrocket/gui/adaptors/BodyTubePresetModel.java new file mode 100644 index 00000000..ff73bf60 --- /dev/null +++ b/core/src/net/sf/openrocket/gui/adaptors/BodyTubePresetModel.java @@ -0,0 +1,105 @@ +package net.sf.openrocket.gui.adaptors; + +import java.util.List; + +import javax.swing.AbstractListModel; +import javax.swing.ComboBoxModel; +import javax.swing.event.ListDataListener; + +import net.sf.openrocket.preset.ComponentPreset; +import net.sf.openrocket.rocketcomponent.ComponentChangeEvent; +import net.sf.openrocket.rocketcomponent.ComponentChangeListener; +import net.sf.openrocket.rocketcomponent.RocketComponent; +import net.sf.openrocket.startup.Application; + +public class BodyTubePresetModel extends AbstractListModel implements + ComboBoxModel, ComponentChangeListener { + + private final RocketComponent component; + + private List presets; + + public BodyTubePresetModel(RocketComponent component) { + presets = Application.getDaos().getBodyTubePresetDao().listAll(); + this.component = component; + } + + public static class BodyTubePresetAdapter { + private ComponentPreset bt; + private BodyTubePresetAdapter( ComponentPreset bt ) { + this.bt = bt; + } + @Override + public String toString() { + return bt.getManufacturer() + " " + bt.getPartNo(); + } + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + ((bt == null) ? 0 : bt.hashCode()); + return result; + } + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + BodyTubePresetAdapter other = (BodyTubePresetAdapter) obj; + if (bt == null) { + if (other.bt != null) + return false; + } else if (!bt.equals(other.bt)) + return false; + return true; + } + } + + @Override + public int getSize() { + return presets.size(); + } + + @Override + public Object getElementAt(int index) { + return new BodyTubePresetAdapter(presets.get(index)); + } + + @Override + public void addListDataListener(ListDataListener l) { + // TODO Auto-generated method stub + + } + + @Override + public void removeListDataListener(ListDataListener l) { + // TODO Auto-generated method stub + + } + + @Override + public void componentChanged(ComponentChangeEvent e) { + // TODO Auto-generated method stub + + } + + @Override + public void setSelectedItem(Object anItem) { + BodyTubePresetAdapter selected = (BodyTubePresetAdapter) anItem; + component.loadPreset(selected.bt); + } + + @Override + public Object getSelectedItem() { + ComponentPreset preset = (ComponentPreset) component.getPresetComponent(); + if ( preset == null ) { + return null; + } else { + return new BodyTubePresetAdapter(preset); + } + } + +} diff --git a/core/src/net/sf/openrocket/gui/adaptors/DoubleModel.java b/core/src/net/sf/openrocket/gui/adaptors/DoubleModel.java index 820a54a6..cd7066f8 100644 --- a/core/src/net/sf/openrocket/gui/adaptors/DoubleModel.java +++ b/core/src/net/sf/openrocket/gui/adaptors/DoubleModel.java @@ -157,7 +157,8 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat * Use linear scale value = linear1 * x + linear0 when x < linearPosition * Use quadratic scale value = quad2 * x^2 + quad1 * x + quad0 otherwise */ - + private final boolean islinear; + // Linear in range x <= linearPosition private final double linearPosition; @@ -169,11 +170,10 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat //private final double linear0; // Non-linear multiplier, exponent and constant - private final double quad2, quad1, quad0; - - + private double quad2, quad1, quad0; public ValueSliderModel(DoubleModel min, DoubleModel max) { + this.islinear = true; linearPosition = 1.0; this.min = min; @@ -192,6 +192,7 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat * Generate a linear model from min to max. */ public ValueSliderModel(double min, double max) { + this.islinear = true; linearPosition = 1.0; this.min = new DoubleModel(min); @@ -205,6 +206,10 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat this(min, 0.5, mid, max); } + public ValueSliderModel(double min, double mid, DoubleModel max) { + this(min, 0.5, mid, max); + } + /* * v(x) = mul * x^exp + add * @@ -212,33 +217,46 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat * v(1) = mul + add = max * v'(pos) = mul*exp * pos^(exp-1) = linearMul */ - public ValueSliderModel(double min, double pos, double mid, double max) { + public ValueSliderModel(double min, double pos, double mid, double max ) { + this(min, pos, mid, new DoubleModel(max)); + } + public ValueSliderModel(double min, double pos, double mid, DoubleModel max) { this.min = new DoubleModel(min); this.mid = new DoubleModel(mid); - this.max = new DoubleModel(max); - + this.max = max; + this.islinear = false; + + max.addChangeListener(this); + linearPosition = pos; //linear0 = min; //linear1 = (mid-min)/pos; - if (!(min < mid && mid <= max && 0 < pos && pos < 1)) { + if (!(min < mid && mid <= max.getValue() && 0 < pos && pos < 1)) { throw new IllegalArgumentException("Bad arguments for ValueSliderModel " + "min=" + min + " mid=" + mid + " max=" + max + " pos=" + pos); } + updateExponentialParameters(); + + } + + private void updateExponentialParameters() { + double pos = this.linearPosition; + double minValue = this.min.getValue(); + double midValue = this.mid.getValue(); + double maxValue = this.max.getValue(); /* * quad2..0 are calculated such that * f(pos) = mid - continuity * f(1) = max - end point * f'(pos) = linear1 - continuity of derivative */ - - double delta = (mid - min) / pos; - quad2 = (max - mid - delta + delta * pos) / pow2(pos - 1); - quad1 = (delta + 2 * (mid - max) * pos - delta * pos * pos) / pow2(pos - 1); - quad0 = (mid - (2 * mid + delta) * pos + (max + delta) * pos * pos) / pow2(pos - 1); - + double delta = (midValue - minValue) / pos; + quad2 = (maxValue - midValue - delta + delta * pos) / pow2(pos - 1); + quad1 = (delta + 2 * (midValue - maxValue) * pos - delta * pos * pos) / pow2(pos - 1); + quad0 = (midValue - (2 * midValue + delta) * pos + (maxValue + delta) * pos * pos) / pow2(pos - 1); } private double pow2(double x) { @@ -366,6 +384,11 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat @Override public void stateChanged(EventObject e) { // Min or max range has changed. + if ( !islinear ) { + double midValue = (max.getValue() - min.getValue()) /3.0; + mid.setValue(midValue); + updateExponentialParameters(); + } // Fire if not already firing if (firing == 0) fireStateChanged(); @@ -385,6 +408,10 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat return new ValueSliderModel(min, mid, max); } + public BoundedRangeModel getSliderModel(double min, double mid, DoubleModel max) { + return new ValueSliderModel(min, mid, max); + } + public BoundedRangeModel getSliderModel(double min, double pos, double mid, double max) { return new ValueSliderModel(min, pos, mid, max); } @@ -516,7 +543,7 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat private Unit currentUnit; private final double minValue; - private final double maxValue; + private double maxValue; private String toString = null; @@ -725,7 +752,6 @@ public class DoubleModel implements StateChangeListener, ChangeSource, Invalidat } } - /** * Returns whether setting the value automatically is available. */ diff --git a/core/src/net/sf/openrocket/gui/configdialog/BodyTubeConfig.java b/core/src/net/sf/openrocket/gui/configdialog/BodyTubeConfig.java index af272a0d..ffed6e73 100644 --- a/core/src/net/sf/openrocket/gui/configdialog/BodyTubeConfig.java +++ b/core/src/net/sf/openrocket/gui/configdialog/BodyTubeConfig.java @@ -2,6 +2,7 @@ package net.sf.openrocket.gui.configdialog; import javax.swing.JCheckBox; +import javax.swing.JComboBox; import javax.swing.JLabel; import javax.swing.JPanel; import javax.swing.JSpinner; @@ -9,6 +10,7 @@ import javax.swing.JSpinner; import net.miginfocom.swing.MigLayout; import net.sf.openrocket.document.OpenRocketDocument; import net.sf.openrocket.gui.SpinnerEditor; +import net.sf.openrocket.gui.adaptors.BodyTubePresetModel; import net.sf.openrocket.gui.adaptors.BooleanModel; import net.sf.openrocket.gui.adaptors.DoubleModel; import net.sf.openrocket.gui.components.BasicSlider; @@ -16,12 +18,15 @@ import net.sf.openrocket.gui.components.UnitSelector; import net.sf.openrocket.l10n.Translator; import net.sf.openrocket.material.Material; import net.sf.openrocket.rocketcomponent.BodyTube; +import net.sf.openrocket.rocketcomponent.ComponentChangeEvent; +import net.sf.openrocket.rocketcomponent.ComponentChangeListener; import net.sf.openrocket.rocketcomponent.RocketComponent; import net.sf.openrocket.startup.Application; import net.sf.openrocket.unit.UnitGroup; public class BodyTubeConfig extends RocketComponentConfig { + private ComponentChangeListener listener; private MotorConfig motorConfigPane = null; private static final Translator trans = Application.getTranslator(); @@ -30,17 +35,25 @@ public class BodyTubeConfig extends RocketComponentConfig { JPanel panel = new JPanel(new MigLayout("gap rel unrel", "[][65lp::][30lp::][]", "")); + //// Body tube template + panel.add( new JLabel(trans.get("BodyTubecfg.lbl.Bodytubepreset")) ); + { + JComboBox combo = new JComboBox(new BodyTubePresetModel(component)); + panel.add(combo, "wrap"); + } + //// Body tube length panel.add(new JLabel(trans.get("BodyTubecfg.lbl.Bodytubelength"))); - DoubleModel m = new DoubleModel(component, "Length", UnitGroup.UNITS_LENGTH, 0); + final DoubleModel maxLength = new DoubleModel(2.0); + DoubleModel length = new DoubleModel(component, "Length", UnitGroup.UNITS_LENGTH, 0); - JSpinner spin = new JSpinner(m.getSpinnerModel()); + JSpinner spin = new JSpinner(length.getSpinnerModel()); spin.setEditor(new SpinnerEditor(spin)); panel.add(spin, "growx"); - panel.add(new UnitSelector(m), "growx"); - panel.add(new BasicSlider(m.getSliderModel(0, 0.5, 2.0)), "w 100lp, wrap"); + panel.add(new UnitSelector(length), "growx"); + panel.add(new BasicSlider(length.getSliderModel(0, 0.5, maxLength)), "w 100lp, wrap"); //// Body tube diameter @@ -66,7 +79,7 @@ public class BodyTubeConfig extends RocketComponentConfig { panel.add(new JLabel(trans.get("BodyTubecfg.lbl.Innerdiameter"))); // Diameter = 2*Radius - m = new DoubleModel(component, "InnerRadius", 2, UnitGroup.UNITS_LENGTH, 0); + DoubleModel m = new DoubleModel(component, "InnerRadius", 2, UnitGroup.UNITS_LENGTH, 0); spin = new JSpinner(m.getSpinnerModel()); @@ -107,6 +120,29 @@ public class BodyTubeConfig extends RocketComponentConfig { tabbedPane.insertTab(trans.get("BodyTubecfg.tab.Motor"), null, motorConfigPane, trans.get("BodyTubecfg.tab.Motormountconf"), 1); tabbedPane.setSelectedIndex(0); + + // need to work in the max length for body tubes based on presets... + BodyTube bt = (BodyTube) component; + if ( bt.getPresetComponent() != null ) { + BodyTube btPreset = (BodyTube) bt.getPresetComponent().getPrototype(); + maxLength.setValue( btPreset.getLength() ); + } + + listener = new ComponentChangeListener() { + + @Override + public void componentChanged(ComponentChangeEvent e) { + BodyTube bt = (BodyTube) component; + if ( bt.getPresetComponent() != null ) { + BodyTube btPreset = (BodyTube) bt.getPresetComponent().getPrototype(); + maxLength.setValue(btPreset.getLength()); + } + + } + + }; + component.addChangeListener(listener); + } @Override @@ -115,5 +151,11 @@ public class BodyTubeConfig extends RocketComponentConfig { if (motorConfigPane != null) motorConfigPane.updateFields(); } + + @Override + public void invalidateModels() { + super.invalidateModels(); + component.removeChangeListener(listener); + } } diff --git a/core/src/net/sf/openrocket/preset/ComponentPreset.java b/core/src/net/sf/openrocket/preset/ComponentPreset.java index 87343e93..cf24bb1b 100644 --- a/core/src/net/sf/openrocket/preset/ComponentPreset.java +++ b/core/src/net/sf/openrocket/preset/ComponentPreset.java @@ -1,8 +1,8 @@ package net.sf.openrocket.preset; -import net.sf.openrocket.motor.Manufacturer; import net.sf.openrocket.rocketcomponent.RocketComponent; + /** * A model for a preset component. *

@@ -11,63 +11,63 @@ import net.sf.openrocket.rocketcomponent.RocketComponent; * * @author Sampo Niskanen */ -public abstract class ComponentPreset { - - private final Manufacturer manufacturer; +public class ComponentPreset { + + + private final String manufacturer; private final String partNo; private final String partDescription; private final RocketComponent prototype; - - - public ComponentPreset(Manufacturer manufacturer, String partNo, String partDescription, - RocketComponent prototype) { + + + public ComponentPreset(String manufacturer, String partNo, String partDescription, RocketComponent prototype) { this.manufacturer = manufacturer; this.partNo = partNo; this.partDescription = partDescription; this.prototype = prototype.copy(); - + if (prototype.getParent() != null) { throw new IllegalArgumentException("Prototype component cannot have a parent"); } if (prototype.getChildCount() > 0) { throw new IllegalArgumentException("Prototype component cannot have children"); } + } - - + /** * Return the component class that this preset defines. */ public Class getComponentClass() { return prototype.getClass(); } - + /** * Return the manufacturer of this preset component. */ - public Manufacturer getManufacturer() { + public String getManufacturer() { return manufacturer; } - + /** * Return the part number. This is the part identifier (e.g. "BT-50"). */ public String getPartNo() { return partNo; } - + /** * Return the part description. This is a longer description of the component. */ public String getPartDescription() { return partDescription; } - + /** * Return a prototype component. This component may be modified freely. */ public RocketComponent getPrototype() { return prototype.copy(); } - + } diff --git a/core/src/net/sf/openrocket/rocketcomponent/BodyTube.java b/core/src/net/sf/openrocket/rocketcomponent/BodyTube.java index 64c1b4a9..fe8571eb 100644 --- a/core/src/net/sf/openrocket/rocketcomponent/BodyTube.java +++ b/core/src/net/sf/openrocket/rocketcomponent/BodyTube.java @@ -135,13 +135,16 @@ public class BodyTube extends SymmetricComponent implements MotorMount, Coaxial @Override protected void loadFromPreset(RocketComponent preset) { - BodyTube c = (BodyTube) preset; - this.setOuterRadius(c.getOuterRadius()); - super.loadFromPreset(preset); + BodyTube bt = (BodyTube) preset; + this.autoRadius = false; + this.outerRadius = bt.getOuterRadius(); + this.thickness = (bt.getOuterRadius() - bt.getInnerRadius()); + this.length = bt.getLength(); + + fireComponentChangeEvent(ComponentChangeEvent.MASS_CHANGE); + } - - @Override public double getAftRadius() { return getOuterRadius(); diff --git a/core/src/net/sf/openrocket/rocketcomponent/ExternalComponent.java b/core/src/net/sf/openrocket/rocketcomponent/ExternalComponent.java index 8d958da6..85bc39f1 100644 --- a/core/src/net/sf/openrocket/rocketcomponent/ExternalComponent.java +++ b/core/src/net/sf/openrocket/rocketcomponent/ExternalComponent.java @@ -17,7 +17,7 @@ import net.sf.openrocket.unit.UnitGroup; */ public abstract class ExternalComponent extends RocketComponent { - + public enum Finish { //// Rough ROUGH("ExternalComponent.Rough", 500e-6), @@ -29,35 +29,35 @@ public abstract class ExternalComponent extends RocketComponent { SMOOTH("ExternalComponent.Smoothpaint", 20e-6), //// Polished POLISHED("ExternalComponent.Polished", 2e-6); - + private static final Translator trans = Application.getTranslator(); private final String name; private final double roughnessSize; - + Finish(String name, double roughness) { this.name = name; this.roughnessSize = roughness; } - + public double getRoughnessSize() { return roughnessSize; } - + @Override public String toString() { return trans.get(name) + " (" + UnitGroup.UNITS_ROUGHNESS.toStringUnit(roughnessSize) + ")"; } } - - + + /** * The material of the component. */ protected Material material = null; - + protected Finish finish = Finish.NORMAL; - - + + /** * Constructor that sets the relative position of the component. @@ -66,13 +66,13 @@ public abstract class ExternalComponent extends RocketComponent { super(relativePosition); this.material = Application.getPreferences().getDefaultComponentMaterial(this.getClass(), Material.Type.BULK); } - + /** * Returns the volume of the component. This value is used in calculating the mass * of the object. */ public abstract double getComponentVolume(); - + /** * Calculates the mass of the component as the product of the volume and interior density. */ @@ -80,7 +80,7 @@ public abstract class ExternalComponent extends RocketComponent { public double getComponentMass() { return material.getDensity() * getComponentVolume(); } - + /** * ExternalComponent has aerodynamic effect, so return true. */ @@ -88,7 +88,7 @@ public abstract class ExternalComponent extends RocketComponent { public boolean isAerodynamic() { return true; } - + /** * ExternalComponent has effect on the mass, so return true. */ @@ -96,18 +96,18 @@ public abstract class ExternalComponent extends RocketComponent { public boolean isMassive() { return true; } - - + + public Material getMaterial() { return material; } - + public void setMaterial(Material mat) { if (mat.getType() != Material.Type.BULK) { throw new IllegalArgumentException("ExternalComponent requires a bulk material" + " type=" + mat.getType()); } - + if (material.equals(mat)) return; material = mat; @@ -115,29 +115,31 @@ public abstract class ExternalComponent extends RocketComponent { fireComponentChangeEvent(ComponentChangeEvent.MASS_CHANGE); clearPreset(); } - + public Finish getFinish() { return finish; } - + public void setFinish(Finish finish) { if (this.finish == finish) return; this.finish = finish; fireComponentChangeEvent(ComponentChangeEvent.AERODYNAMIC_CHANGE); } - - + + @Override protected void loadFromPreset(RocketComponent preset) { super.loadFromPreset(preset); - + // Surface finish is left unchanged - + ExternalComponent c = (ExternalComponent) preset; - + Material mat = c.getMaterial(); - if (c.isMassOverridden()) { + if ( mat != null ) { + setMaterial(mat); + } else if (c.isMassOverridden()) { double mass = c.getOverrideMass(); double volume = getComponentVolume(); double density; @@ -147,12 +149,11 @@ public abstract class ExternalComponent extends RocketComponent { density = 1000; } mat = Material.newMaterial(Type.BULK, mat.getName(), density, true); + setMaterial(mat); } - - setMaterial(mat); } - - + + @Override protected List copyFrom(RocketComponent c) { ExternalComponent src = (ExternalComponent) c; @@ -160,5 +161,5 @@ public abstract class ExternalComponent extends RocketComponent { this.material = src.material; return super.copyFrom(c); } - + } diff --git a/core/src/net/sf/openrocket/startup/Application.java b/core/src/net/sf/openrocket/startup/Application.java index 7718b67e..9f0f4321 100644 --- a/core/src/net/sf/openrocket/startup/Application.java +++ b/core/src/net/sf/openrocket/startup/Application.java @@ -1,5 +1,6 @@ package net.sf.openrocket.startup; +import net.sf.openrocket.database.Daos; import net.sf.openrocket.database.MotorDatabase; import net.sf.openrocket.l10n.ClassBasedTranslator; import net.sf.openrocket.l10n.DebugTranslator; @@ -23,6 +24,8 @@ public final class Application { private static Translator baseTranslator = new DebugTranslator(null); private static MotorDatabase motorSetDatabase; + + private static Daos daos; private static Preferences preferences; @@ -159,6 +162,14 @@ public final class Application { public static void setMotorSetDatabase(MotorDatabase motorSetDatabase) { Application.motorSetDatabase = motorSetDatabase; } + + public static Daos getDaos() { + return daos; + } + + public static void setDaos(Daos daos) { + Application.daos = daos; + } } diff --git a/core/src/net/sf/openrocket/startup/Startup.java b/core/src/net/sf/openrocket/startup/Startup.java index d288ea76..95b03c52 100644 --- a/core/src/net/sf/openrocket/startup/Startup.java +++ b/core/src/net/sf/openrocket/startup/Startup.java @@ -4,6 +4,7 @@ import java.io.PrintStream; import java.util.Locale; import java.util.prefs.Preferences; +import net.sf.openrocket.database.DaosImpl; import net.sf.openrocket.gui.util.SwingPreferences; import net.sf.openrocket.l10n.DebugTranslator; import net.sf.openrocket.l10n.L10N; @@ -52,6 +53,8 @@ public class Startup { Application.setPreferences( new SwingPreferences() ); + Application.setDaos( new DaosImpl() ); + // Setup the translations initializeL10n(); -- 2.47.2