updates for 0.9.3

This commit is contained in:
Sampo Niskanen 2009-08-30 15:46:18 +00:00
parent ab156438b5
commit 7a4e0a8bc3
54 changed files with 1058 additions and 367 deletions

View File

@ -2,10 +2,12 @@
<classpath>
<classpathentry kind="src" path="src"/>
<classpathentry kind="src" path="extra-src"/>
<classpathentry kind="src" path="test"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
<classpathentry kind="lib" path="/home/sampo/Projects/OpenRocket/lib/miglayout15-swing.jar"/>
<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/JCommon 1.0.16"/>
<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/JFreeChart 1.0.13"/>
<classpathentry kind="lib" path="/home/sampo/Projects/OpenRocket/extra-lib/RXTXcomm.jar"/>
<classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>
<classpathentry kind="output" path="bin"/>
</classpath>

View File

@ -1,3 +1,13 @@
2009-08-29 Sampo Niskanen
* Extracted motor manufacturer into separate class
* Started writing unit tests
2009-08-28 Sampo Niskanen
* Added icon and source info to About dialog
* Finalized flight event plot icons
2009-08-27 Sampo Niskanen
* Allow clicking on label to toggle checkbox in two tables

7
TODO
View File

@ -4,15 +4,11 @@ Feature roadmap for OpenRocket 1.0
Must-have:
- Draw remaining event icons (for 0.9.3)
- Change automatic exception reporting success code to 202 (for 0.9.3)
- Test automatic exception reporting (for 0.9.3)
- Allow editing user-defined materials
- Go through thrust curves and correct errors
- Add styrofoam and depron materials
- Through-the-wall fins
- Update "About" dialog with icon and source info
Bugs:
@ -56,4 +52,7 @@ Done:
- Read more thrust curve formats
- Showing events in plots
- Table boolean selecting by clicking label
- Test automatic exception reporting (for 0.9.3)
- Draw remaining event icons (for 0.9.3)
- Update "About" dialog with icon and source info

View File

@ -1,8 +1,12 @@
# The OpenRocket build version
build.version=0.9.3pre
# The source of the package. When building a package for a specific
# distribution (Debian, Fedora etc.), this should be changed appropriately!
# This is displayed in the About dialog and included in bug reports.
build.source=default

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -1,5 +1,6 @@
event-simulation-end.png from famfamfam Silk icon set
(http://www.famfamfam.com/lab/icons/silk/)
event-simulation-end.png from famfamfam icon set
All others custom-drawn.
All others custom-drawn by Sampo Niskanen.

Binary file not shown.

After

Width:  |  Height:  |  Size: 466 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 305 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 623 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 636 B

BIN
pix/icon/icon-about.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 39 KiB

View File

@ -5,8 +5,8 @@ import static net.sf.openrocket.util.MathUtil.pow2;
import java.util.Iterator;
import java.util.Map;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.Configuration;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.Rocket;
import net.sf.openrocket.rocketcomponent.RocketComponent;

View File

@ -8,7 +8,7 @@ import java.util.ArrayList;
import net.sf.openrocket.file.GeneralMotorLoader;
import net.sf.openrocket.material.Material;
import net.sf.openrocket.material.MaterialStorage;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.util.JarUtil;
import net.sf.openrocket.util.MathUtil;
import net.sf.openrocket.util.Prefs;
@ -229,7 +229,7 @@ public class Databases {
boolean match = true;
if (type != null && type != m.getMotorType())
match = false;
else if (manufacturer != null && !manufacturer.equalsIgnoreCase(m.getManufacturer()))
else if (manufacturer != null && !m.getManufacturer().matches(manufacturer))
match = false;
else if (designation != null && !designation.equalsIgnoreCase(m.getDesignation()))
match = false;

View File

@ -6,7 +6,7 @@ import java.io.Reader;
import java.nio.charset.Charset;
import java.util.List;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.motor.Motor;
/**
* A motor loader class that detects the file type based on the file name extension.

View File

@ -8,174 +8,15 @@ import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.util.MathUtil;
public abstract class MotorLoader implements Loader<Motor> {
/**
* Manufacturer codes to expand. These are general translations that are used
* both in RASP and RockSim engine files.
*/
private static final Map<String,String> MANUFACTURER_CODES =
new HashMap<String,String>();
static {
/*
* TODO: CRITICAL: Should names have Inc. LLC. etc?
*/
// AeroTech has many name combinations...
for (String s: new String[] { "A", "AT", "AERO", "AEROT", "AEROTECH" }) {
MANUFACTURER_CODES.put(s, "AeroTech");
MANUFACTURER_CODES.put(s+"-RMS", "AeroTech");
MANUFACTURER_CODES.put(s+"/RMS", "AeroTech");
MANUFACTURER_CODES.put(s+"-RCS", "AeroTech");
MANUFACTURER_CODES.put(s+"/RCS", "AeroTech");
MANUFACTURER_CODES.put("RCS-" + s, "AeroTech");
MANUFACTURER_CODES.put("RCS/" + s, "AeroTech");
MANUFACTURER_CODES.put(s+"-APOGEE", "AeroTech");
MANUFACTURER_CODES.put(s+"/APOGEE", "AeroTech");
}
MANUFACTURER_CODES.put("ISP", "AeroTech");
MANUFACTURER_CODES.put("AHR", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRID", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRIDS", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRID ROCKETRY", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRIDS ROCKETRY", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRID ROCKETRY LLC", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("ALPHA HYBRID ROCKETRY, LLC", "Alpha Hybrid Rocketry LLC");
MANUFACTURER_CODES.put("AMW", "Animal Motor Works");
MANUFACTURER_CODES.put("AW", "Animal Motor Works");
MANUFACTURER_CODES.put("ANIMAL", "Animal Motor Works");
MANUFACTURER_CODES.put("ANIMAL MOTOR WORKS", "Animal Motor Works");
MANUFACTURER_CODES.put("AP", "Apogee");
MANUFACTURER_CODES.put("APOG", "Apogee");
MANUFACTURER_CODES.put("APOGEE", "Apogee");
MANUFACTURER_CODES.put("P", "Apogee");
MANUFACTURER_CODES.put("CES", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CESARONI", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CESARONI TECHNOLOGY", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CESARONI TECHNOLOGY INC", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CESARONI TECHNOLOGY INC.", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CESARONI TECHNOLOGY INCORPORATED", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CTI", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CS", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CSR", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("PRO38", "Cesaroni Technology Inc.");
MANUFACTURER_CODES.put("CR", "Contrail Rockets");
MANUFACTURER_CODES.put("CONTR", "Contrail Rockets");
MANUFACTURER_CODES.put("CONTRAIL", "Contrail Rockets");
MANUFACTURER_CODES.put("CONTRAIL ROCKET", "Contrail Rockets");
MANUFACTURER_CODES.put("CONTRAIL ROCKETS", "Contrail Rockets");
MANUFACTURER_CODES.put("E", "Estes");
MANUFACTURER_CODES.put("ES", "Estes");
MANUFACTURER_CODES.put("ESTES", "Estes");
MANUFACTURER_CODES.put("EM", "Ellis Mountain");
MANUFACTURER_CODES.put("ELLIS", "Ellis Mountain");
MANUFACTURER_CODES.put("ELLIS MOUNTAIN", "Ellis Mountain");
MANUFACTURER_CODES.put("ELLIS MOUNTAIN ROCKET", "Ellis Mountain");
MANUFACTURER_CODES.put("ELLIS MOUNTAIN ROCKETS", "Ellis Mountain");
MANUFACTURER_CODES.put("GR", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA ROCKET", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA ROCKETS", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA MOTOR", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA MOTORS", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA ROCKET MOTOR", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("GORILLA ROCKET MOTORS", "Gorilla Rocket Motors");
MANUFACTURER_CODES.put("H", "HyperTEK");
MANUFACTURER_CODES.put("HT", "HyperTEK");
MANUFACTURER_CODES.put("HYPER", "HyperTEK");
MANUFACTURER_CODES.put("HYPERTEK", "HyperTEK");
MANUFACTURER_CODES.put("K", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KBA", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("K/AT", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("K-AT", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOS", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON/AT", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON-AT", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON/AEROTECH", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON-AEROTECH", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON-BY-AEROTECH", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("KOSDON BY AEROTECH", "Kosdon by AeroTech");
MANUFACTURER_CODES.put("LOKI", "Loki Research");
MANUFACTURER_CODES.put("LOKI RESEARCH", "Loki Research");
MANUFACTURER_CODES.put("LR", "Loki Research");
MANUFACTURER_CODES.put("PM", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PML", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES LTD", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES, LTD", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES LTD.", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES, LTD.", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES LIMITED", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PUBLIC MISSILES, LIMITED", "Public Missiles, Ltd.");
MANUFACTURER_CODES.put("PP", "Propulsion Polymers");
MANUFACTURER_CODES.put("PROP", "Propulsion Polymers");
MANUFACTURER_CODES.put("PROPULSION", "Propulsion Polymers");
MANUFACTURER_CODES.put("PROPULSION-POLYMERS", "Propulsion Polymers");
MANUFACTURER_CODES.put("PROPULSION POLYMERS", "Propulsion Polymers");
MANUFACTURER_CODES.put("Q", "Quest");
MANUFACTURER_CODES.put("QU", "Quest");
MANUFACTURER_CODES.put("QUEST", "Quest");
MANUFACTURER_CODES.put("RATT", "RATT Works");
MANUFACTURER_CODES.put("RATT WORKS", "RATT Works");
MANUFACTURER_CODES.put("RT", "RATT Works");
MANUFACTURER_CODES.put("RTW", "RATT Works");
MANUFACTURER_CODES.put("RR", "Roadrunner Rocketry");
MANUFACTURER_CODES.put("ROADRUNNER", "Roadrunner Rocketry");
MANUFACTURER_CODES.put("ROADRUNNER ROCKETRY", "Roadrunner Rocketry");
MANUFACTURER_CODES.put("RV", "Rocketvision");
MANUFACTURER_CODES.put("ROCKETVISION", "Rocketvision");
MANUFACTURER_CODES.put("SR", "Sky Ripper Systems");
MANUFACTURER_CODES.put("SRS", "Sky Ripper Systems");
MANUFACTURER_CODES.put("SKYR", "Sky Ripper Systems");
MANUFACTURER_CODES.put("SKYRIPPER", "Sky Ripper Systems");
MANUFACTURER_CODES.put("SKYRIPPER SYSTEMS", "Sky Ripper Systems");
MANUFACTURER_CODES.put("SKY RIPPER SYSTEMS", "Sky Ripper Systems");
MANUFACTURER_CODES.put("WCH", "West Coast Hybrids");
MANUFACTURER_CODES.put("WCR", "West Coast Hybrids");
MANUFACTURER_CODES.put("WEST COAST HYBRIDS", "West Coast Hybrids");
MANUFACTURER_CODES.put("SF", "WECO Feuerwerk"); // Previously Sachsen Feuerwerks
MANUFACTURER_CODES.put("SACHSEN FEUERWERK", "WECO Feuerwerk");
MANUFACTURER_CODES.put("SACHSEN FEUERWERKS", "WECO Feuerwerk");
MANUFACTURER_CODES.put("WECO", "WECO Feuerwerk");
MANUFACTURER_CODES.put("WECO FEUERWERK", "WECO Feuerwerk");
MANUFACTURER_CODES.put("WECO FEUERWERKS", "WECO Feuerwerk");
}
/**
* Load motors from the specified <code>InputStream</code>. The file is read using
* the default charset returned by {@link #getDefaultCharset()}.
@ -330,28 +171,7 @@ public abstract class MotorLoader implements Loader<Motor> {
} while (index < primary.size()-1);
}
/**
* Convert a manufacturer string. This should be done for all manufacturers
* for overall consistency. This includes both RASP name expansions and some
* general renaming. This should also be performed when loading designs in order
* to identify manufacturers correctly.
*
* @param mfg the original manufacturer / manufacturer code.
* @return the manufacturer name.
*/
public static String convertManufacturer(String mfg) {
// Replace underscore and trim
mfg = mfg.replace('_', ' ').trim();
// Check for conversion
String conv = MANUFACTURER_CODES.get(mfg.toUpperCase());
if (conv != null)
return conv;
else
return mfg;
}
@SuppressWarnings("unchecked")
protected static void finalizeThrustCurve(List<Double> time, List<Double> thrust,

View File

@ -20,6 +20,7 @@ import net.sf.openrocket.file.simplesax.ElementHandler;
import net.sf.openrocket.file.simplesax.PlainTextHandler;
import net.sf.openrocket.file.simplesax.SimpleSAX;
import net.sf.openrocket.material.Material;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.BodyComponent;
import net.sf.openrocket.rocketcomponent.BodyTube;
import net.sf.openrocket.rocketcomponent.Bulkhead;
@ -37,7 +38,6 @@ import net.sf.openrocket.rocketcomponent.InternalComponent;
import net.sf.openrocket.rocketcomponent.LaunchLug;
import net.sf.openrocket.rocketcomponent.MassComponent;
import net.sf.openrocket.rocketcomponent.MassObject;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.NoseCone;
import net.sf.openrocket.rocketcomponent.Parachute;
@ -1030,7 +1030,7 @@ class MotorHandler extends ElementHandler {
} else if (element.equals("manufacturer")) {
// Manufacturer
manufacturer = MotorLoader.convertManufacturer(content);
manufacturer = content;
} else if (element.equals("designation")) {

View File

@ -8,8 +8,9 @@ import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.ThrustCurveMotor;
import net.sf.openrocket.motor.Manufacturer;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.motor.ThrustCurveMotor;
import net.sf.openrocket.util.Coordinate;
public class RASPMotorLoader extends MotorLoader {
@ -118,7 +119,7 @@ public class RASPMotorLoader extends MotorLoader {
propW = Double.parseDouble(pieces[4]);
totalW = Double.parseDouble(pieces[5]);
manufacturer = convertManufacturer(pieces[6]);
manufacturer = pieces[6];
if (propW > totalW) {
throw new IOException("Propellant weight exceeds total weight in " +
@ -196,7 +197,8 @@ public class RASPMotorLoader extends MotorLoader {
try {
return new ThrustCurveMotor(manufacturer, designation, comment, Motor.Type.UNKNOWN,
return new ThrustCurveMotor(Manufacturer.getManufacturer(manufacturer),
designation, comment, Motor.Type.UNKNOWN,
delays, diameter, length, timeArray, thrustArray, cgArray);
} catch (IllegalArgumentException e) {

View File

@ -12,8 +12,9 @@ import net.sf.openrocket.file.simplesax.ElementHandler;
import net.sf.openrocket.file.simplesax.NullElementHandler;
import net.sf.openrocket.file.simplesax.PlainTextHandler;
import net.sf.openrocket.file.simplesax.SimpleSAX;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.ThrustCurveMotor;
import net.sf.openrocket.motor.Manufacturer;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.motor.ThrustCurveMotor;
import net.sf.openrocket.util.Coordinate;
import org.xml.sax.InputSource;
@ -147,7 +148,7 @@ public class RockSimMotorLoader extends MotorLoader {
str = attributes.get("mfg");
if (str == null)
throw new SAXException("Manufacturer missing");
manufacturer = convertManufacturer(str);
manufacturer = str;
// Designation
str = attributes.get("code");
@ -339,7 +340,8 @@ public class RockSimMotorLoader extends MotorLoader {
}
try {
return new ThrustCurveMotor(manufacturer, designation, description, type,
return new ThrustCurveMotor(Manufacturer.getManufacturer(manufacturer),
designation, description, type,
delays, diameter, length, timeArray, thrustArray, cgArray);
} catch (IllegalArgumentException e) {
throw new SAXException("Illegal motor data", e);

View File

@ -7,8 +7,8 @@ import java.util.List;
import net.sf.openrocket.file.RocketSaver;
import net.sf.openrocket.material.Material;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.ComponentAssembly;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.Rocket;
import net.sf.openrocket.rocketcomponent.RocketComponent;
@ -121,7 +121,7 @@ public class RocketComponentSaver {
if (motor.getMotorType() != Motor.Type.UNKNOWN) {
elements.add(" <type>" + motor.getMotorType().name().toLowerCase() + "</type>");
}
elements.add(" <manufacturer>" + RocketSaver.escapeXML(motor.getManufacturer()) + "</manufacturer>");
elements.add(" <manufacturer>" + RocketSaver.escapeXML(motor.getManufacturer().getSimpleName()) + "</manufacturer>");
elements.add(" <designation>" + RocketSaver.escapeXML(motor.getDesignation()) + "</designation>");
elements.add(" <diameter>" + motor.getDiameter() + "</diameter>");
elements.add(" <length>" + motor.getLength() + "</length>");

View File

@ -25,8 +25,8 @@ import net.sf.openrocket.gui.adaptors.MotorConfigurationModel;
import net.sf.openrocket.gui.components.BasicSlider;
import net.sf.openrocket.gui.components.UnitSelector;
import net.sf.openrocket.gui.dialogs.MotorChooserDialog;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.Configuration;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.Rocket;
import net.sf.openrocket.rocketcomponent.RocketComponent;
@ -186,7 +186,7 @@ public class MotorConfig extends JPanel {
if (m == null)
motorLabel.setText("None");
else
motorLabel.setText(m.getManufacturer() + " " +
motorLabel.setText(m.getManufacturer().getDisplayName() + " " +
m.getDesignation(mount.getMotorDelay(id)));
}

View File

@ -6,12 +6,14 @@ import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import net.miginfocom.swing.MigLayout;
import net.sf.openrocket.gui.components.ResizeLabel;
import net.sf.openrocket.gui.components.URLLabel;
import net.sf.openrocket.util.GUIUtil;
import net.sf.openrocket.util.Icons;
import net.sf.openrocket.util.Prefs;
public class AboutDialog extends JDialog {
@ -26,12 +28,24 @@ public class AboutDialog extends JDialog {
JPanel panel = new JPanel(new MigLayout("fill"));
panel.add(new ResizeLabel("OpenRocket", 20), "ax 50%, wrap para");
panel.add(new ResizeLabel("Version " + version, 3), "ax 50%, wrap 30lp");
panel.add(new JLabel(Icons.loadImageIcon("pix/icon/icon-about.png", "OpenRocket")),
"spany 5, top");
panel.add(new ResizeLabel("Copyright \u00A9 2007-2009 Sampo Niskanen"), "ax 50%, wrap para");
panel.add(new ResizeLabel("OpenRocket", 20), "ax 50%, growy, wrap para");
panel.add(new ResizeLabel("Version " + version, 3), "ax 50%, growy, wrap rel");
panel.add(new URLLabel(OPENROCKET_URL), "ax 50%, wrap para");
String source = Prefs.getBuildSource();
if (!Prefs.DEFAULT_BUILD_SOURCE.equalsIgnoreCase(source)) {
panel.add(new ResizeLabel("Distributed by " + source, -1),
"ax 50%, growy, wrap para");
} else {
panel.add(new ResizeLabel(" ", -1), "ax 50%, growy, wrap para");
}
panel.add(new ResizeLabel("Copyright \u00A9 2007-2009 Sampo Niskanen"),
"ax 50%, growy, wrap para");
panel.add(new URLLabel(OPENROCKET_URL), "ax 50%, growy, wrap para");
JButton close = new JButton("Close");
@ -41,7 +55,7 @@ public class AboutDialog extends JDialog {
AboutDialog.this.dispose();
}
});
panel.add(close, "right");
panel.add(close, "spanx, right");
this.add(panel);
this.setTitle("OpenRocket " + version);

View File

@ -143,7 +143,7 @@ public class BugReportDialog extends JDialog {
this.pack();
this.setLocationRelativeTo(parent);
GUIUtil.installEscapeCloseOperation(this);
// GUIUtil.setDefaultButton(close);
GUIUtil.setDefaultButton(send);
}

View File

@ -27,7 +27,7 @@ import javax.swing.table.TableColumnModel;
import net.miginfocom.swing.MigLayout;
import net.sf.openrocket.document.OpenRocketDocument;
import net.sf.openrocket.gui.main.BasicFrame;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.Rocket;
import net.sf.openrocket.rocketcomponent.RocketComponent;

View File

@ -38,7 +38,7 @@ import javax.swing.table.TableRowSorter;
import net.miginfocom.swing.MigLayout;
import net.sf.openrocket.database.Databases;
import net.sf.openrocket.gui.components.ResizeLabel;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.unit.UnitGroup;
import net.sf.openrocket.util.GUIUtil;
import net.sf.openrocket.util.Prefs;
@ -382,7 +382,7 @@ public class MotorChooserDialog extends JDialog {
MANUFACTURER("Manufacturer",100) {
@Override
public String getValue(Motor m) {
return m.getManufacturer();
return m.getManufacturer().getDisplayName();
}
// @Override
// public String getToolTipText(Motor m) {

View File

@ -81,16 +81,18 @@ public class PlotDialog extends JDialog {
private static final Map<FlightEvent.Type, Image> EVENT_IMAGES =
new HashMap<FlightEvent.Type, Image>();
static {
loadImage(FlightEvent.Type.LAUNCH, "pix/spheres/red-16x16.png");
loadImage(FlightEvent.Type.LAUNCH, "pix/eventicons/event-launch.png");
loadImage(FlightEvent.Type.LIFTOFF, "pix/eventicons/event-liftoff.png");
loadImage(FlightEvent.Type.LAUNCHROD, "pix/eventicons/event-launchrod.png");
loadImage(FlightEvent.Type.IGNITION, "pix/eventicons/event-ignition.png");
loadImage(FlightEvent.Type.BURNOUT, "pix/eventicons/event-burnout.png");
loadImage(FlightEvent.Type.EJECTION_CHARGE, "pix/spheres/green-16x16.png");
loadImage(FlightEvent.Type.STAGE_SEPARATION, "pix/eventicons/event-stage-separation.png");
loadImage(FlightEvent.Type.EJECTION_CHARGE,"pix/eventicons/event-ejection-charge.png");
loadImage(FlightEvent.Type.STAGE_SEPARATION,
"pix/eventicons/event-stage-separation.png");
loadImage(FlightEvent.Type.APOGEE, "pix/eventicons/event-apogee.png");
loadImage(FlightEvent.Type.RECOVERY_DEVICE_DEPLOYMENT, "pix/spheres/blue-16x16.png");
loadImage(FlightEvent.Type.GROUND_HIT, "pix/spheres/gray-16x16.png");
loadImage(FlightEvent.Type.RECOVERY_DEVICE_DEPLOYMENT,
"pix/eventicons/event-recovery-device-deployment.png");
loadImage(FlightEvent.Type.GROUND_HIT, "pix/eventicons/event-ground-hit.png");
loadImage(FlightEvent.Type.SIMULATION_END, "pix/eventicons/event-simulation-end.png");
}

View File

@ -20,8 +20,8 @@ import java.util.Iterator;
import java.util.LinkedHashSet;
import net.sf.openrocket.gui.figureelements.FigureElement;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.Configuration;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.RocketComponent;
import net.sf.openrocket.util.Coordinate;

View File

@ -0,0 +1,226 @@
package net.sf.openrocket.motor;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
public class Manufacturer {
private static Set<Manufacturer> manufacturers = new HashSet<Manufacturer>();
static {
// AeroTech has many name combinations...
List<String> names = new ArrayList<String>();
for (String s: new String[] { "A", "AT", "AERO", "AEROT", "AEROTECH" }) {
names.add(s);
names.add(s+"-RMS");
names.add(s+"-RCS");
names.add("RCS-" + s);
names.add(s+"-APOGEE");
}
names.add("ISP");
manufacturers.add(new Manufacturer("AeroTech", "AeroTech",
names.toArray(new String[0])));
manufacturers.add(new Manufacturer("Alpha Hybrid Rocketry LLC",
"Alpha Hybrid Rocketry",
"AHR", "ALPHA", "ALPHA HYBRID", "ALPHA HYBRIDS", "ALPHA HYBRIDS ROCKETRY"));
manufacturers.add(new Manufacturer("Animal Motor Works","Animal Motor Works",
"AMW", "AW", "ANIMAL"));
manufacturers.add(new Manufacturer("Apogee","Apogee",
"AP", "APOG", "P"));
manufacturers.add(new Manufacturer("Cesaroni Technology Inc.",
"Cesaroni Technology",
"CES", "CESARONI", "CESARONI TECHNOLOGY INCORPORATED", "CTI",
"CS", "CSR", "PRO38"));
manufacturers.add(new Manufacturer("Contrail Rockets","Contrail Rockets",
"CR", "CONTR", "CONTRAIL", "CONTRAIL ROCKET"));
manufacturers.add(new Manufacturer("Estes","Estes",
"E", "ES"));
manufacturers.add(new Manufacturer("Ellis Mountain","Ellis Mountain",
"EM", "ELLIS", "ELLIS MOUNTAIN ROCKET", "ELLIS MOUNTAIN ROCKETS"));
manufacturers.add(new Manufacturer("Gorilla Rocket Motors",
"Gorilla Rocket Motors",
"GR", "GORILLA", "GORILLA ROCKET", "GORILLA ROCKETS", "GORILLA MOTOR",
"GORILLA MOTORS", "GORILLA ROCKET MOTOR"));
manufacturers.add(new Manufacturer("HyperTEK", "HyperTEK",
"H", "HT", "HYPER"));
manufacturers.add(new Manufacturer("Kosdon by AeroTech", "Kosdon by AeroTech",
"K", "KBA", "K-AT", "KOS", "KOSDON", "KOSDON/AT", "KOSDON/AEROTECH"));
manufacturers.add(new Manufacturer("Loki Research", "Loki Research",
"LOKI", "LR"));
manufacturers.add(new Manufacturer("Public Missiles, Ltd.", "Public Missiles",
"PM", "PML", "PUBLIC MISSILES LIMITED"));
manufacturers.add(new Manufacturer("Propulsion Polymers", "Propulsion Polymers",
"PP", "PROP", "PROPULSION"));
manufacturers.add(new Manufacturer("Quest", "Quest",
"Q", "QU"));
manufacturers.add(new Manufacturer("RATT Works", "RATT Works",
"RATT", "RT", "RTW"));
manufacturers.add(new Manufacturer("Roadrunner Rocketry","Roadrunner Rocketry",
"RR", "ROADRUNNER"));
manufacturers.add(new Manufacturer("Rocketvision", "Rocketvision",
"RV", "ROCKET VISION"));
manufacturers.add(new Manufacturer("Sky Ripper Systems","Sky Ripper Systems",
"SR", "SRS", "SKYR", "SKYRIPPER", "SKY RIPPER", "SKYRIPPER SYSTEMS"));
manufacturers.add(new Manufacturer("West Coast Hybrids", "West Coast Hybrids",
"WCH", "WCR", "WEST COAST", "WEST COAST HYBRID"));
// German WECO Feuerwerk, previously Sachsen Feuerwerk
manufacturers.add(new Manufacturer("WECO Feuerwerk", "WECO Feuerwerk",
"WECO", "WECO FEUERWERKS", "SF", "SACHSEN", "SACHSEN FEUERWERK",
"SACHSEN FEUERWERKS"));
// Check that no duplicates have appeared
for (Manufacturer m1: manufacturers) {
for (Manufacturer m2: manufacturers) {
if (m1 == m2)
continue;
for (String name: m1.getAllNames()) {
if (m2.matches(name)) {
throw new IllegalStateException("Manufacturer name clash between " +
"manufacturers " + m1 + " and " + m2 + " name " + name);
}
}
}
}
}
private final String displayName;
private final String simpleName;
private final Set<String> allNames;
private final Set<String> searchNames;
private Manufacturer(String displayName, String simpleName, String... alternateNames) {
this.displayName = displayName;
this.simpleName = simpleName;
Set<String> all = new HashSet<String>();
Set<String> search = new HashSet<String>();
all.add(displayName);
all.add(simpleName);
search.add(generateSearchString(displayName));
search.add(generateSearchString(simpleName));
for (String name: alternateNames) {
all.add(name);
search.add(generateSearchString(name));
}
this.allNames = Collections.unmodifiableSet(all);
this.searchNames = Collections.unmodifiableSet(search);
}
/**
* Returns the display name of the manufacturer. This is the value that
* should be presented in the UI to the user.
*
* @return the display name
*/
public String getDisplayName() {
return displayName;
}
/**
* Returns the simple name of the manufacturer. This should be used for example
* when saving the manufacturer for compatibility.
*
* @return the simple name.
*/
public String getSimpleName() {
return simpleName;
}
/**
* Return all names of the manufacturer. This includes all kinds of
* codes that correspond to the manufacturer (for example "A" for AeroTech).
*
* @return an unmodifiable set of the alternative names.
*/
public Set<String> getAllNames() {
return allNames;
}
/**
* Check whether the display, simple or any of the alternative names matches the
* specified name. Matching is performed case insensitively and ignoring any
* non-letter and non-number characters.
*
* @param name the name to search for.
* @return whether this manufacturer matches the request.
*/
public boolean matches(String name) {
if (name == null)
return false;
return this.searchNames.contains(generateSearchString(name));
}
/**
* Return the display name of the manufacturer.
*/
@Override
public String toString() {
return displayName;
}
/**
* Returns a manufacturer for the given name. The manufacturer is searched for
* within the manufacturers and if a match is found the corresponding
* object is returned. If not, a new manufacturer is returned with display and
* simple name the name specified. Subsequent requests for the same (or corresponding)
* manufacturer name will return the same object.
*
* @param name the manufacturer name to search for.
* @return the Manufacturer object corresponding the name.
*/
public static synchronized Manufacturer getManufacturer(String name) {
for (Manufacturer m: manufacturers) {
if (m.matches(name))
return m;
}
Manufacturer m = new Manufacturer(name.trim(), name.trim());
manufacturers.add(m);
return m;
}
private String generateSearchString(String str) {
return str.toLowerCase().replaceAll("[^a-zA-Z0-9]+", " ").trim();
}
}

View File

@ -1,4 +1,4 @@
package net.sf.openrocket.rocketcomponent;
package net.sf.openrocket.motor;
import java.text.Collator;
import java.util.Comparator;
@ -94,7 +94,7 @@ public abstract class Motor implements Comparable<Motor> {
private final String manufacturer;
private final Manufacturer manufacturer;
private final String designation;
private final String description;
private final Type motorType;
@ -125,7 +125,7 @@ public abstract class Motor implements Comparable<Motor> {
* @param diameter maximum diameter of the motor
* @param length length of the motor
*/
protected Motor(String manufacturer, String designation, String description,
protected Motor(Manufacturer manufacturer, String designation, String description,
Type type, double[] delays, double diameter, double length) {
if (manufacturer == null || designation == null || description == null ||
@ -355,7 +355,7 @@ public abstract class Motor implements Comparable<Motor> {
*
* @return the manufacturer
*/
public String getManufacturer() {
public Manufacturer getManufacturer() {
return manufacturer;
}
@ -539,7 +539,8 @@ public abstract class Motor implements Comparable<Motor> {
int value;
// 1. Manufacturer
value = COLLATOR.compare(this.manufacturer, other.manufacturer);
value = COLLATOR.compare(this.manufacturer.getDisplayName(),
other.manufacturer.getDisplayName());
if (value != 0)
return value;

View File

@ -1,4 +1,4 @@
package net.sf.openrocket.rocketcomponent;
package net.sf.openrocket.motor;
import net.sf.openrocket.util.Coordinate;
import net.sf.openrocket.util.MathUtil;
@ -33,7 +33,7 @@ public class ThrustCurveMotor extends Motor {
* @param thrust thrust at the time points.
* @param cg cg at the time points.
*/
public ThrustCurveMotor(String manufacturer, String designation, String description,
public ThrustCurveMotor(Manufacturer manufacturer, String designation, String description,
Motor.Type type, double[] delays, double diameter, double length,
double[] time, double[] thrust, Coordinate[] cg) {
super(manufacturer, designation, description, type, delays, diameter, length);

View File

@ -4,6 +4,7 @@ import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.util.Coordinate;
import net.sf.openrocket.util.MathUtil;

View File

@ -4,6 +4,7 @@ import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.util.Coordinate;
import net.sf.openrocket.util.MathUtil;

View File

@ -1,5 +1,6 @@
package net.sf.openrocket.rocketcomponent;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.simulation.FlightEvent;
import net.sf.openrocket.util.ChangeSource;

View File

@ -12,6 +12,7 @@ import java.util.UUID;
import javax.swing.event.ChangeListener;
import javax.swing.event.EventListenerList;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.util.Coordinate;
import net.sf.openrocket.util.MathUtil;

View File

@ -11,9 +11,9 @@ import net.sf.openrocket.aerodynamics.AtmosphericConditions;
import net.sf.openrocket.aerodynamics.AtmosphericModel;
import net.sf.openrocket.aerodynamics.Warning;
import net.sf.openrocket.aerodynamics.WarningSet;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.Clusterable;
import net.sf.openrocket.rocketcomponent.Configuration;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.MotorMount;
import net.sf.openrocket.rocketcomponent.RecoveryDevice;
import net.sf.openrocket.rocketcomponent.RocketComponent;

View File

@ -10,10 +10,51 @@ import java.io.Serializable;
* @author Sampo Niskanen <sampo.niskanen@iki.fi>
*/
public final class Coordinate implements Serializable {
//////// Debug section
/*
* Debugging info. If openrocket.debug.coordinatecount is defined, a line is
* printed every 1000000 instantiations (or as many as defined).
*/
private static final boolean COUNT_DEBUG;
private static final int COUNT_DIFF;
static {
String str = System.getProperty("openrocket.debug.coordinatecount", null);
int diff = 0;
if (str == null) {
COUNT_DEBUG = false;
COUNT_DIFF = 0;
} else {
COUNT_DEBUG = true;
try {
diff = Integer.parseInt(str);
} catch (NumberFormatException ignore) { }
if (diff < 1000)
diff = 1000000;
COUNT_DIFF = diff;
}
}
private static int count = 0;
{
// Debug count
if (COUNT_DEBUG) {
count++;
if ((count % COUNT_DIFF) == 0) {
System.out.println("Coordinate instantiated " + count + " times.");
}
}
}
//////// End debug section
public static final Coordinate NUL = new Coordinate(0,0,0,0);
public static final Coordinate NaN = new Coordinate(Double.NaN,Double.NaN,
Double.NaN,Double.NaN);
public static final double COMPARISON_DELTA = 0.000001;
public final double x,y,z;
public final double weight;
@ -21,15 +62,6 @@ public final class Coordinate implements Serializable {
private double length = -1; /* Cached when calculated */
/* Count and report the number of times a Coordinate is constructed: */
// private static int count=0;
// {
// count++;
// if ((count % 1000) == 0) {
// System.err.println("Coordinate instantiated "+count+" times");
// }
// }
public Coordinate() {
@ -52,6 +84,7 @@ public final class Coordinate implements Serializable {
this.y = y;
this.z = z;
this.weight=w;
}
@ -261,31 +294,4 @@ public final class Coordinate implements Serializable {
}
public static void main(String[] arg) {
double a=1.2;
double x;
Coordinate c;
long t1, t2;
x = 0;
t1 = System.nanoTime();
for (int i=0; i < 100000000; i++) {
x = x + a;
}
t2 = System.nanoTime();
System.out.println("Value: "+x);
System.out.println("Plain addition: "+ ((t2-t1+500000)/1000000) + " ms");
c = Coordinate.NUL;
t1 = System.nanoTime();
for (int i=0; i < 100000000; i++) {
c = c.add(a,0,0);
}
t2 = System.nanoTime();
System.out.println("Value: "+c.x);
System.out.println("Coordinate addition: "+ ((t2-t1+500000)/1000000) + " ms");
}
}

View File

@ -57,7 +57,9 @@ public class Icons {
public static final Icon DELETE = loadImageIcon("pix/icons/delete.png", "Delete");
private static ImageIcon loadImageIcon(String file, String name) {
public static ImageIcon loadImageIcon(String file, String name) {
URL url = ClassLoader.getSystemResource(file);
if (url == null) {
System.err.println("Resource "+file+" not found! Ignoring...");

View File

@ -73,7 +73,7 @@ public class MathUtil {
if (equals(toMin, toMax))
return toMin;
if (equals(fromMin, fromMax)) {
throw new IllegalArgumentException("from range is singular an to range is not.");
throw new IllegalArgumentException("from range is singular and to range is not.");
}
return (value - fromMin)/(fromMax-fromMin) * (toMax - toMin) + toMin;
}
@ -168,6 +168,16 @@ public class MathUtil {
return Math.abs(a-b) < EPSILON*absb;
}
/**
* Return the sign of the number. This corresponds to Math.signum, but ignores
* the special cases of zero and NaN. The value returned for those is arbitrary.
* <p>
* This method is about 4 times faster than Math.signum().
*
* @param x the checked value.
* @return -1.0 if x<0; 1.0 if x>0; otherwise either -1.0 or 1.0.
*/
public static double sign(double x) {
return (x<0) ? -1.0 : 1.0;
}
@ -180,38 +190,4 @@ public class MathUtil {
*/
public static void main(String[] arg) {
double nan = Double.NaN;
System.out.println("min(5,6) = " + min(5, 6));
System.out.println("min(5,nan) = " + min(5, nan));
System.out.println("min(nan,6) = " + min(nan, 6));
System.out.println("min(nan,nan) = " + min(nan, nan));
System.out.println();
System.out.println("max(5,6) = " + max(5, 6));
System.out.println("max(5,nan) = " + max(5, nan));
System.out.println("max(nan,6) = " + max(nan, 6));
System.out.println("max(nan,nan) = " + max(nan, nan));
System.out.println();
System.out.println("min(5,6,7) = " + min(5, 6, 7));
System.out.println("min(5,6,nan) = " + min(5, 6, nan));
System.out.println("min(5,nan,7) = " + min(5, nan, 7));
System.out.println("min(5,nan,nan) = " + min(5, nan, nan));
System.out.println("min(nan,6,7) = " + min(nan, 6, 7));
System.out.println("min(nan,6,nan) = " + min(nan, 6, nan));
System.out.println("min(nan,nan,7) = " + min(nan, nan, 7));
System.out.println("min(nan,nan,nan) = " + min(nan, nan, nan));
System.out.println();
System.out.println("max(5,6,7) = " + max(5, 6, 7));
System.out.println("max(5,6,nan) = " + max(5, 6, nan));
System.out.println("max(5,nan,7) = " + max(5, nan, 7));
System.out.println("max(5,nan,nan) = " + max(5, nan, nan));
System.out.println("max(nan,6,7) = " + max(nan, 6, 7));
System.out.println("max(nan,6,nan) = " + max(nan, 6, nan));
System.out.println("max(nan,nan,7) = " + max(nan, nan, 7));
System.out.println("max(nan,nan,nan) = " + max(nan, nan, nan));
System.out.println();
}
}

View File

@ -55,6 +55,7 @@ public class Prefs {
private static final String BUILD_VERSION;
private static final String BUILD_SOURCE;
public static final String DEFAULT_BUILD_SOURCE = "default";
static {
try {

View File

@ -41,18 +41,4 @@ public class Rotation2D {
return new Coordinate(cos*c.x + sin*c.y, cos*c.y - sin*c.x, c.z, c.weight);
}
public static void main(String arg[]) {
Coordinate c = new Coordinate(1,1,1,2.5);
Rotation2D rot = new Rotation2D(Math.PI/4);
System.out.println("X: "+rot.rotateX(c));
System.out.println("Y: "+rot.rotateY(c));
System.out.println("Z: "+rot.rotateZ(c));
System.out.println("invX: "+rot.invRotateX(c));
System.out.println("invY: "+rot.invRotateY(c));
System.out.println("invZ: "+rot.invRotateZ(c));
}
}

View File

@ -2,6 +2,7 @@ package net.sf.openrocket.util;
import net.sf.openrocket.database.Databases;
import net.sf.openrocket.material.Material;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.rocketcomponent.BodyTube;
import net.sf.openrocket.rocketcomponent.Bulkhead;
import net.sf.openrocket.rocketcomponent.CenteringRing;
@ -10,7 +11,6 @@ import net.sf.openrocket.rocketcomponent.IllegalFinPointException;
import net.sf.openrocket.rocketcomponent.InnerTube;
import net.sf.openrocket.rocketcomponent.LaunchLug;
import net.sf.openrocket.rocketcomponent.MassComponent;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.NoseCone;
import net.sf.openrocket.rocketcomponent.Rocket;
import net.sf.openrocket.rocketcomponent.Stage;

View File

@ -1,16 +1,13 @@
package net.sf.openrocket.util;
import java.util.Locale;
public class TextUtil {
/**
* Return a string of the double value with suitable precision.
* Return a string of the double value with suitable precision (5 digits).
* The string is the shortest representation of the value including the
* required precision.
*
* TODO: MEDIUM: Extra zeros are added unnecessarily to the end of the string.
*
* @param d the value to present.
* @return a representation with suitable precision.
*/
@ -31,46 +28,106 @@ public class TextUtil {
}
final String sign = (d < 0) ? "-" : "";
double abs = Math.abs(d);
if (abs < 0.001) {
// Compact exponential notation
int exp = 0;
while (abs < 1.0) {
abs *= 10;
exp++;
}
String sign = (d < 0) ? "-" : "";
return sign + String.format((Locale)null, "%.4fe-%d", abs, exp);
// Small and large values always in exponential notation
if (abs < 0.001 || abs >= 100000000) {
return sign + exponentialFormat(abs);
}
if (abs < 0.01)
return String.format((Locale)null, "%.7f", d);
if (abs < 0.1)
return String.format((Locale)null, "%.6f", d);
if (abs < 1)
return String.format((Locale)null, "%.5f", d);
if (abs < 10)
return String.format((Locale)null, "%.4f", d);
if (abs < 100)
return String.format((Locale)null, "%.3f", d);
if (abs < 1000)
return String.format((Locale)null, "%.2f", d);
if (abs < 10000)
return String.format((Locale)null, "%.1f", d);
if (abs < 100000000.0)
return String.format((Locale)null, "%.0f", d);
// Compact exponential notation
int exp = 0;
while (abs >= 10.0) {
abs /= 10;
// Check whether decimal or exponential notation is shorter
String exp = exponentialFormat(abs);
String dec = decimalFormat(abs);
if (dec.length() <= exp.length())
return sign + dec;
else
return sign + exp;
}
/*
* value must be positive and not zero!
*/
private static String exponentialFormat(double value) {
int exp;
exp = 0;
while (value < 1.0) {
value *= 10;
exp--;
}
while (value >= 10.0) {
value /= 10;
exp++;
}
String sign = (d < 0) ? "-" : "";
return sign + String.format((Locale)null, "%.4fe%d", abs, exp);
return shortDecimal(value, 4) + "e" + exp;
}
/*
* value must be positive and not zero!
*/
private static String decimalFormat(double value) {
if (value >= 10000)
return "" + (int)(value + 0.5);
int decimals = 1;
double v = value;
while (v < 1000) {
v *= 10;
decimals++;
}
return shortDecimal(value, decimals);
}
/*
* value must be positive!
*/
private static String shortDecimal(double value, int decimals) {
int whole = (int)value;
value -= whole;
// Calculate limit, return when remaining value less than this
double limit;
limit = 0.5;
for (int i=0; i<decimals; i++)
limit /= 10;
if (value < limit)
return "" + whole;
limit *= 10;
StringBuilder sb = new StringBuilder();
sb.append("" + whole);
sb.append('.');
for (int i = 0; i<decimals; i++) {
value *= 10;
if (i == decimals-1)
value += 0.5;
whole = (int)value;
value -= whole;
sb.append((char)('0' + whole));
if (value < limit)
return sb.toString();
limit *= 10;
}
return sb.toString();
}
}

View File

@ -1,4 +1,4 @@
package net.sf.openrocket.util;
package net.sf.openrocket.utils;
import static net.sf.openrocket.aerodynamics.AtmosphericConditions.GAMMA;
import static net.sf.openrocket.aerodynamics.AtmosphericConditions.R;
@ -18,6 +18,7 @@ import net.sf.openrocket.file.GeneralRocketLoader;
import net.sf.openrocket.file.RocketLoadException;
import net.sf.openrocket.file.RocketLoader;
import net.sf.openrocket.rocketcomponent.Configuration;
import net.sf.openrocket.util.MathUtil;
public class Analysis {

View File

@ -7,8 +7,9 @@ import java.util.List;
import net.sf.openrocket.file.GeneralMotorLoader;
import net.sf.openrocket.file.MotorLoader;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.ThrustCurveMotor;
import net.sf.openrocket.motor.Manufacturer;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.motor.ThrustCurveMotor;
public class MotorCheck {
@ -38,7 +39,7 @@ public class MotorCheck {
}
String base = file.split("_")[0];
String mfg = MotorLoader.convertManufacturer(base);
Manufacturer mfg = Manufacturer.getManufacturer(base);
if (motors != null) {
if (motors.size() == 0) {
@ -63,7 +64,7 @@ public class MotorCheck {
ok = false;
}
if (!m.getManufacturer().equals(mfg)) {
if (m.getManufacturer() != mfg) {
System.out.println("ERROR: Inconsistent manufacturer " +
m.getManufacturer() + " (file name indicates " + mfg
+ ")");

View File

@ -8,8 +8,9 @@ import java.util.List;
import net.sf.openrocket.file.GeneralMotorLoader;
import net.sf.openrocket.file.MotorLoader;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.ThrustCurveMotor;
import net.sf.openrocket.motor.Manufacturer;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.motor.ThrustCurveMotor;
public class MotorCompare {
@ -83,10 +84,10 @@ public class MotorCompare {
// Manufacturers
System.out.printf("Manufacture:");
String mfg = motors.get(0).getManufacturer();
Manufacturer mfg = motors.get(0).getManufacturer();
for (Motor m: motors) {
System.out.printf("\t%s", m.getManufacturer());
if (!m.getManufacturer().equals(mfg)) {
if (m.getManufacturer() != mfg) {
cause.add("Manufacturer");
bad = true;
}

View File

@ -8,8 +8,8 @@ import java.util.List;
import net.sf.openrocket.file.GeneralMotorLoader;
import net.sf.openrocket.file.MotorLoader;
import net.sf.openrocket.rocketcomponent.Motor;
import net.sf.openrocket.rocketcomponent.ThrustCurveMotor;
import net.sf.openrocket.motor.Motor;
import net.sf.openrocket.motor.ThrustCurveMotor;
public class MotorPrinter {

32
test/Test.java Normal file
View File

@ -0,0 +1,32 @@
import net.sf.openrocket.util.Coordinate;
public class Test {
public static int COUNT = 10000000;
public static void main(String[] args) {
for (int i=1; ; i++) {
long t1 = System.currentTimeMillis();
run();
long t2 = System.currentTimeMillis();
System.out.println("Run " + i + " took " + (t2-t1) + " ms");
}
}
private static void run() {
Coordinate a = new Coordinate(1,1,1,1);
Coordinate b = new Coordinate(1,1,1,1);
for (int i=0; i < COUNT; i++) {
a = a.add(b);
}
System.out.println("value:"+a);
return;
}
}

View File

@ -0,0 +1,88 @@
package net.sf.openrocket.motor;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
public class ManufacturerTest {
@Test
public void testExisting() {
Manufacturer m1, m2, m3, m4, m5;
m1 = Manufacturer.getManufacturer("aerotech");
m2 = Manufacturer.getManufacturer("a ");
m3 = Manufacturer.getManufacturer("-isp-");
m4 = Manufacturer.getManufacturer("at/rcs");
m5 = Manufacturer.getManufacturer("e");
assertEquals(m1, m2);
assertEquals(m1, m3);
assertEquals(m1, m4);
assertNotSame(m1, m5);
}
@Test
public void testNew() {
Manufacturer m1, m2, m3;
m1 = Manufacturer.getManufacturer("Unknown");
m2 = Manufacturer.getManufacturer(" Unknown/ ");
m3 = Manufacturer.getManufacturer("Unknown/a");
assertEquals(m1.getDisplayName(), "Unknown");
assertEquals(m2.getDisplayName(), "Unknown");
assertEquals(m1, m2);
assertEquals(m3.getDisplayName(), "Unknown/a");
assertNotSame(m1, m3);
}
@Test
public void simpleNameTest() {
Manufacturer m1, m2, m3, m4;
m1 = Manufacturer.getManufacturer("cs");
m2 = Manufacturer.getManufacturer("Cesaroni Technology");
m3 = Manufacturer.getManufacturer("Cesaroni Technology Inc");
m4 = Manufacturer.getManufacturer("Cesaroni Technology Inc.");
assertEquals(m1.getDisplayName(), "Cesaroni Technology Inc.");
assertEquals(m1.toString(), "Cesaroni Technology Inc.");
assertEquals(m1.getSimpleName(), "Cesaroni Technology");
assertEquals(m1, m2);
assertEquals(m1, m3);
assertEquals(m1, m4);
}
@Test
public void matchesTest() {
Manufacturer m1;
m1 = Manufacturer.getManufacturer("aerotech");
assertTrue(m1.matches("a"));
assertTrue(m1.matches("a/"));
assertTrue(m1.matches("a/rcs"));
assertTrue(m1.matches("a/rms"));
assertTrue(m1.matches("aerotech ...-/%¤#_!"));
assertTrue(m1.matches(" .isp/"));
assertFalse(m1.matches("aero/tech"));
assertFalse(m1.matches("aero.tech"));
assertFalse(m1.matches("aero_tech"));
assertFalse(m1.matches("aero tech"));
}
}

View File

@ -0,0 +1,64 @@
package net.sf.openrocket.util;
import static org.junit.Assert.*;
import org.junit.Test;
public class CoordinateTest {
private static final double EPS = 0.0000000001;
@Test
public void coordinateTest() {
Coordinate x = new Coordinate(1,1,1,1);
Coordinate y = new Coordinate(1,2,3,4);
assertCoordinateEquals(new Coordinate(2,1,1,1), x.setX(2));
assertCoordinateEquals(new Coordinate(1,2,1,1), x.setY(2));
assertCoordinateEquals(new Coordinate(1,1,2,1), x.setZ(2));
assertCoordinateEquals(new Coordinate(1,1,1,2), x.setWeight(2));
assertCoordinateEquals(new Coordinate(2,3,4,1), x.setXYZ(y).add(1,1,1));
assertFalse(x.isNaN());
assertTrue(x.setX(Double.NaN).isNaN());
assertTrue(Coordinate.NaN.isNaN());
assertTrue(x.isWeighted());
assertFalse(x.setWeight(0).isWeighted());
assertCoordinateEquals(x, x.add(Coordinate.NUL));
assertCoordinateEquals(new Coordinate(2,3,4,5), x.add(y));
assertCoordinateEquals(new Coordinate(2,3,4,1), x.add(1,2,3));
assertCoordinateEquals(new Coordinate(2,3,4,5), x.add(1,2,3,4));
assertCoordinateEquals(new Coordinate(0,-1,-2,1), x.sub(y));
assertCoordinateEquals(new Coordinate(0,-1,-2,1), x.sub(1,2,3));
assertCoordinateEquals(new Coordinate(2,4,6,8), y.multiply(2));
assertEquals(1+2+3, y.dot(x));
assertEquals(1+2+3, x.dot(y));
assertEquals(1+2+3, Coordinate.dot(x,y));
assertEquals(x.dot(x), x.length2());
assertEquals(y.dot(y), y.length2());
assertEquals(Math.sqrt(1+4+9), y.length(), EPS);
assertEquals(1, y.normalize().length(), EPS);
assertCoordinateEquals(new Coordinate(1.75,1.75,1.75,4),
new Coordinate(1,1,1,1).average(new Coordinate(2,2,2,3)));
assertCoordinateEquals(new Coordinate(1,1,1,1),
new Coordinate(1,1,1,1).average(new Coordinate(2,2,2,0)));
assertCoordinateEquals(new Coordinate(1.5,1.5,1.5,0),
new Coordinate(1,1,1,0).average(new Coordinate(2,2,2,0)));
}
private void assertCoordinateEquals(Coordinate a, Coordinate b) {
assertEquals(a, b);
assertEquals(a.weight, b.weight, EPS);
}
}

View File

@ -0,0 +1,148 @@
package net.sf.openrocket.util;
import static java.lang.Double.NaN;
import static java.lang.Math.PI;
import static org.junit.Assert.*;
import org.junit.Test;
public class MathUtilTest {
public static final double EPS = 0.00000000001;
@Test
public void miscMathTest() {
assertEquals(PI*PI, MathUtil.pow2(PI), EPS);
assertEquals(PI*PI*PI, MathUtil.pow3(PI), EPS);
assertEquals(PI*PI*PI*PI, MathUtil.pow4(PI), EPS);
assertEquals(1.0, MathUtil.clamp(0.9999, 1.0, 2.0));
assertEquals(1.23, MathUtil.clamp(1.23, 1.0, 2.0));
assertEquals(2.0, MathUtil.clamp(2 + EPS/100, 1.0, 2.0));
assertEquals(1.0f, MathUtil.clamp(0.9999f, 1.0f, 2.0f));
assertEquals(1.23f, MathUtil.clamp(1.23f, 1.0f, 2.0f));
assertEquals(2.0f, MathUtil.clamp(2.0001f, 1.0f, 2.0f));
assertEquals(1, MathUtil.clamp(-3, 1, 5));
assertEquals(3, MathUtil.clamp(3, 1, 5));
assertEquals(5, MathUtil.clamp(6, 1, 5));
assertEquals(-1.0, MathUtil.sign(Double.NEGATIVE_INFINITY));
assertEquals(-1.0, MathUtil.sign(-100));
assertEquals(-1.0, MathUtil.sign(Math.nextAfter(0.0, -1.0)));
assertEquals( 1.0, MathUtil.sign(Math.nextUp(0.0)));
assertEquals( 1.0, MathUtil.sign(100));
assertEquals( 1.0, MathUtil.sign(Double.POSITIVE_INFINITY));
}
@Test
public void hypotTest() {
for (int i=0; i<10000; i++) {
double x = Math.random()*100 - 50;
double y = Math.random()*i - i/2;
double z = Math.hypot(x, y);
assertEquals(z, MathUtil.hypot(x, y), EPS);
}
}
@Test
public void reduceTest() {
for (int i=-1000; i<1000; i++) {
double angle = Math.random() * 2*PI;
double shift = angle + i*2*PI;
assertEquals(angle, MathUtil.reduce360(shift), EPS);
}
for (int i=-1000; i<1000; i++) {
double angle = Math.random() * 2*PI - PI;
double shift = angle + i*2*PI;
assertEquals(angle, MathUtil.reduce180(shift), EPS);
}
}
@Test
public void minmaxTest() {
assertEquals(1.0, MathUtil.min(1.0, Math.nextUp(1.0)));
assertEquals(1.0, MathUtil.min(1.0, Double.POSITIVE_INFINITY));
assertEquals(1.0, MathUtil.min(NaN, 1.0));
assertEquals(1.0, MathUtil.min(1.0, NaN));
assertEquals(NaN, MathUtil.min(NaN, NaN));
assertEquals(Math.nextUp(1.0), MathUtil.max(1.0, Math.nextUp(1.0)));
assertEquals(Double.POSITIVE_INFINITY, MathUtil.max(1.0, Double.POSITIVE_INFINITY));
assertEquals(1.0, MathUtil.max(NaN, 1.0));
assertEquals(1.0, MathUtil.max(1.0, NaN));
assertEquals(NaN, MathUtil.max(NaN, NaN));
assertEquals(1.0, MathUtil.min(1.0, 2.0, 3.0));
assertEquals(1.0, MathUtil.min(1.0, NaN, NaN));
assertEquals(1.0, MathUtil.min(NaN, 1.0, NaN));
assertEquals(1.0, MathUtil.min(NaN, NaN, 1.0));
assertEquals(1.0, MathUtil.min(2.0, NaN, 1.0));
assertEquals(1.0, MathUtil.min(1.0, 2.0, NaN));
assertEquals(1.0, MathUtil.min(NaN, 2.0, 1.0));
assertEquals(3.0, MathUtil.max(1.0, 3.0, 2.0));
assertEquals(1.0, MathUtil.max(1.0, NaN, NaN));
assertEquals(1.0, MathUtil.max(NaN, 1.0, NaN));
assertEquals(1.0, MathUtil.max(NaN, NaN, 1.0));
assertEquals(2.0, MathUtil.max(2.0, NaN, 1.0));
assertEquals(2.0, MathUtil.max(1.0, 2.0, NaN));
assertEquals(2.0, MathUtil.max(NaN, 2.0, 1.0));
}
@Test
public void mapTest() {
assertEquals(1.0, MathUtil.map(1.0, 0.0, 5.0, -1.0, 9.0), EPS);
assertEquals(7.0, MathUtil.map(1.0, 5.0, 0.0, -1.0, 9.0), EPS);
assertEquals(7.0, MathUtil.map(1.0, 0.0, 5.0, 9.0, -1.0), EPS);
assertEquals(6.0, MathUtil.map(6.0, 0.0, 5.0, Math.nextUp(6.0), 6.0), EPS);
assertEquals(6.0, MathUtil.map(6.0, 0.0, 0.0, Math.nextUp(6.0), 6.0), EPS);
try {
MathUtil.map(6.0, 1.0, Math.nextUp(1.0), 1.0, 2.0);
fail("Should not be reached.");
} catch (IllegalArgumentException normal) { }
assertEquals(7.0, MathUtil.map(Math.nextUp(1.0), 0.0, 5.0, 9.0, -1.0), EPS);
}
@Test
public void equalsTest() {
assertTrue(MathUtil.equals(1.0, 1.0 + MathUtil.EPSILON/3));
assertFalse(MathUtil.equals(1.0, 1.0 + MathUtil.EPSILON*2));
assertTrue(MathUtil.equals(-1.0, -1.0 + MathUtil.EPSILON/3));
assertFalse(MathUtil.equals(-1.0, -1.0 + MathUtil.EPSILON*2));
for (double zero: new double[] { 0.0, MathUtil.EPSILON/10, -MathUtil.EPSILON/10 }) {
assertTrue(MathUtil.equals(zero, MathUtil.EPSILON/3));
assertTrue(MathUtil.equals(zero, -MathUtil.EPSILON/3));
assertFalse(MathUtil.equals(zero, MathUtil.EPSILON*2));
assertFalse(MathUtil.equals(zero, -MathUtil.EPSILON*2));
assertTrue(MathUtil.equals(MathUtil.EPSILON/3, zero));
assertTrue(MathUtil.equals(-MathUtil.EPSILON/3, zero));
assertFalse(MathUtil.equals(MathUtil.EPSILON*2, zero));
assertFalse(MathUtil.equals(-MathUtil.EPSILON*2, zero));
}
for (double value: new double[] { PI*1e20, -PI*1e20 }) {
assertTrue("value=" + value, MathUtil.equals(value, value + 1));
assertTrue("value=" + value, MathUtil.equals(value, Math.nextUp(value)));
assertTrue("value=" + value, MathUtil.equals(value, value * (1+MathUtil.EPSILON)));
}
assertFalse(MathUtil.equals(NaN, 0.0));
assertFalse(MathUtil.equals(0.0, NaN));
assertFalse(MathUtil.equals(NaN, NaN));
}
}

View File

@ -0,0 +1,31 @@
package net.sf.openrocket.util;
import static org.junit.Assert.assertEquals;
import org.junit.Test;
public class Rotation2DTest {
@Test
public void rotationTest() {
double rot60 = 0.5;
double rot30 = Math.sqrt(3)/2;
Coordinate x = new Coordinate(1,1,0);
Coordinate y = new Coordinate(0,1,1);
Rotation2D rot = new Rotation2D(Math.PI/3); // 60 deg
assertEquals(new Coordinate(rot60, 1, -rot30), rot.rotateY(x));
assertEquals(new Coordinate(rot60, 1, rot30), rot.invRotateY(x));
assertEquals(new Coordinate(1, rot60, rot30), rot.rotateX(x));
assertEquals(new Coordinate(1, rot60, -rot30), rot.invRotateX(x));
assertEquals(new Coordinate(-rot30, rot60, 1), rot.rotateZ(y));
assertEquals(new Coordinate(rot30, rot60, 1), rot.invRotateZ(y));
}
}

View File

@ -0,0 +1,210 @@
package net.sf.openrocket.util;
import static java.lang.Math.PI;
import static org.junit.Assert.assertEquals;
import org.junit.Test;
public class TextUtilTest {
@Test
public void specialCaseTest() {
assertEquals("NaN",TextUtil.doubleToString(Double.NaN));
assertEquals("Inf",TextUtil.doubleToString(Double.POSITIVE_INFINITY));
assertEquals("-Inf",TextUtil.doubleToString(Double.NEGATIVE_INFINITY));
assertEquals("0",TextUtil.doubleToString(0.0));
assertEquals("0",TextUtil.doubleToString(MathUtil.EPSILON/3));
assertEquals("0",TextUtil.doubleToString(-MathUtil.EPSILON/3));
}
@Test
public void longTest() {
assertEquals("3.1416e-5", TextUtil.doubleToString(PI*1e-5));
assertEquals("3.1416e-4", TextUtil.doubleToString(PI*1e-4));
assertEquals("0.0031416", TextUtil.doubleToString(PI*1e-3));
assertEquals("0.031416", TextUtil.doubleToString(PI*1e-2));
assertEquals("0.31416", TextUtil.doubleToString(PI*1e-1));
assertEquals("3.1416", TextUtil.doubleToString(PI));
assertEquals("31.416", TextUtil.doubleToString(PI*1e1));
assertEquals("314.16", TextUtil.doubleToString(PI*1e2));
assertEquals("3141.6", TextUtil.doubleToString(PI*1e3));
assertEquals("31416", TextUtil.doubleToString(PI*1e4));
assertEquals("314159", TextUtil.doubleToString(PI*1e5));
assertEquals("3141593", TextUtil.doubleToString(PI*1e6));
assertEquals("31415927", TextUtil.doubleToString(PI*1e7));
assertEquals("3.1416e8", TextUtil.doubleToString(PI*1e8));
assertEquals("3.1416e9", TextUtil.doubleToString(PI*1e9));
assertEquals("3.1416e10", TextUtil.doubleToString(PI*1e10));
assertEquals("-3.1416e-5", TextUtil.doubleToString(-PI*1e-5));
assertEquals("-3.1416e-4", TextUtil.doubleToString(-PI*1e-4));
assertEquals("-0.0031416", TextUtil.doubleToString(-PI*1e-3));
assertEquals("-0.031416", TextUtil.doubleToString(-PI*1e-2));
assertEquals("-0.31416", TextUtil.doubleToString(-PI*1e-1));
assertEquals("-3.1416", TextUtil.doubleToString(-PI));
assertEquals("-31.416", TextUtil.doubleToString(-PI*1e1));
assertEquals("-314.16", TextUtil.doubleToString(-PI*1e2));
assertEquals("-3141.6", TextUtil.doubleToString(-PI*1e3));
assertEquals("-31416", TextUtil.doubleToString(-PI*1e4));
assertEquals("-314159", TextUtil.doubleToString(-PI*1e5));
assertEquals("-3141593", TextUtil.doubleToString(-PI*1e6));
assertEquals("-31415927", TextUtil.doubleToString(-PI*1e7));
assertEquals("-3.1416e8", TextUtil.doubleToString(-PI*1e8));
assertEquals("-3.1416e9", TextUtil.doubleToString(-PI*1e9));
assertEquals("-3.1416e10", TextUtil.doubleToString(-PI*1e10));
}
@Test
public void shortTest() {
double p = 3.1;
assertEquals("3.1e-5", TextUtil.doubleToString(p*1e-5));
assertEquals("3.1e-4", TextUtil.doubleToString(p*1e-4));
assertEquals("0.0031", TextUtil.doubleToString(p*1e-3));
assertEquals("0.031", TextUtil.doubleToString(p*1e-2));
assertEquals("0.31", TextUtil.doubleToString(p*1e-1));
assertEquals("3.1", TextUtil.doubleToString(p));
assertEquals("31", TextUtil.doubleToString(p*1e1));
assertEquals("310", TextUtil.doubleToString(p*1e2));
assertEquals("3100", TextUtil.doubleToString(p*1e3));
assertEquals("31000", TextUtil.doubleToString(p*1e4));
assertEquals("3.1e5", TextUtil.doubleToString(p*1e5));
assertEquals("3.1e6", TextUtil.doubleToString(p*1e6));
assertEquals("3.1e7", TextUtil.doubleToString(p*1e7));
assertEquals("3.1e8", TextUtil.doubleToString(p*1e8));
assertEquals("3.1e9", TextUtil.doubleToString(p*1e9));
assertEquals("3.1e10", TextUtil.doubleToString(p*1e10));
assertEquals("-3.1e-5", TextUtil.doubleToString(-p*1e-5));
assertEquals("-3.1e-4", TextUtil.doubleToString(-p*1e-4));
assertEquals("-0.0031", TextUtil.doubleToString(-p*1e-3));
assertEquals("-0.031", TextUtil.doubleToString(-p*1e-2));
assertEquals("-0.31", TextUtil.doubleToString(-p*1e-1));
assertEquals("-3.1", TextUtil.doubleToString(-p));
assertEquals("-31", TextUtil.doubleToString(-p*1e1));
assertEquals("-310", TextUtil.doubleToString(-p*1e2));
assertEquals("-3100", TextUtil.doubleToString(-p*1e3));
assertEquals("-31000", TextUtil.doubleToString(-p*1e4));
assertEquals("-3.1e5", TextUtil.doubleToString(-p*1e5));
assertEquals("-3.1e6", TextUtil.doubleToString(-p*1e6));
assertEquals("-3.1e7", TextUtil.doubleToString(-p*1e7));
assertEquals("-3.1e8", TextUtil.doubleToString(-p*1e8));
assertEquals("-3.1e9", TextUtil.doubleToString(-p*1e9));
assertEquals("-3.1e10", TextUtil.doubleToString(-p*1e10));
p = 3;
assertEquals("3e-5", TextUtil.doubleToString(p*1e-5));
assertEquals("3e-4", TextUtil.doubleToString(p*1e-4));
assertEquals("3e-3", TextUtil.doubleToString(p*1e-3));
assertEquals("0.03", TextUtil.doubleToString(p*1e-2));
assertEquals("0.3", TextUtil.doubleToString(p*1e-1));
assertEquals("3", TextUtil.doubleToString(p));
assertEquals("30", TextUtil.doubleToString(p*1e1));
assertEquals("300", TextUtil.doubleToString(p*1e2));
assertEquals("3e3", TextUtil.doubleToString(p*1e3));
assertEquals("3e4", TextUtil.doubleToString(p*1e4));
assertEquals("3e5", TextUtil.doubleToString(p*1e5));
assertEquals("3e6", TextUtil.doubleToString(p*1e6));
assertEquals("3e7", TextUtil.doubleToString(p*1e7));
assertEquals("3e8", TextUtil.doubleToString(p*1e8));
assertEquals("3e9", TextUtil.doubleToString(p*1e9));
assertEquals("3e10", TextUtil.doubleToString(p*1e10));
assertEquals("-3e-5", TextUtil.doubleToString(-p*1e-5));
assertEquals("-3e-4", TextUtil.doubleToString(-p*1e-4));
assertEquals("-3e-3", TextUtil.doubleToString(-p*1e-3));
assertEquals("-0.03", TextUtil.doubleToString(-p*1e-2));
assertEquals("-0.3", TextUtil.doubleToString(-p*1e-1));
assertEquals("-3", TextUtil.doubleToString(-p));
assertEquals("-30", TextUtil.doubleToString(-p*1e1));
assertEquals("-300", TextUtil.doubleToString(-p*1e2));
assertEquals("-3e3", TextUtil.doubleToString(-p*1e3));
assertEquals("-3e4", TextUtil.doubleToString(-p*1e4));
assertEquals("-3e5", TextUtil.doubleToString(-p*1e5));
assertEquals("-3e6", TextUtil.doubleToString(-p*1e6));
assertEquals("-3e7", TextUtil.doubleToString(-p*1e7));
assertEquals("-3e8", TextUtil.doubleToString(-p*1e8));
assertEquals("-3e9", TextUtil.doubleToString(-p*1e9));
assertEquals("-3e10", TextUtil.doubleToString(-p*1e10));
}
@Test
public void roundingTest() {
/*
* Not testing with 1.00015 because it might be changed during number formatting
* calculations. Its rounding is basically arbitrary anyway.
*/
assertEquals("1.0002e-5", TextUtil.doubleToString(1.0001500001e-5));
assertEquals("1.0001e-5", TextUtil.doubleToString(1.0001499999e-5));
assertEquals("1.0002e-4", TextUtil.doubleToString(1.0001500001e-4));
assertEquals("1.0001e-4", TextUtil.doubleToString(1.0001499999e-4));
assertEquals("0.0010002", TextUtil.doubleToString(1.0001500001e-3));
assertEquals("0.0010001", TextUtil.doubleToString(1.0001499999e-3));
assertEquals("0.010002", TextUtil.doubleToString(1.0001500001e-2));
assertEquals("0.010001", TextUtil.doubleToString(1.0001499999e-2));
assertEquals("0.10002", TextUtil.doubleToString(1.0001500001e-1));
assertEquals("0.10001", TextUtil.doubleToString(1.0001499999e-1));
assertEquals("1.0002", TextUtil.doubleToString(1.0001500001));
assertEquals("1.0001", TextUtil.doubleToString(1.0001499999));
assertEquals("10.002", TextUtil.doubleToString(1.0001500001e1));
assertEquals("10.001", TextUtil.doubleToString(1.0001499999e1));
assertEquals("100.02", TextUtil.doubleToString(1.0001500001e2));
assertEquals("100.01", TextUtil.doubleToString(1.0001499999e2));
assertEquals("1000.2", TextUtil.doubleToString(1.0001500001e3));
assertEquals("1000.1", TextUtil.doubleToString(1.0001499999e3));
assertEquals("10002", TextUtil.doubleToString(1.0001500001e4));
assertEquals("10001", TextUtil.doubleToString(1.0001499999e4));
assertEquals("100012", TextUtil.doubleToString(1.00011500001e5));
assertEquals("100011", TextUtil.doubleToString(1.00011499999e5));
assertEquals("1000112", TextUtil.doubleToString(1.000111500001e6));
assertEquals("1000111", TextUtil.doubleToString(1.000111499999e6));
assertEquals("10001112", TextUtil.doubleToString(1.0001111500001e7));
assertEquals("10001111", TextUtil.doubleToString(1.0001111499999e7));
assertEquals("1.0002e8", TextUtil.doubleToString(1.0001500001e8));
assertEquals("1.0001e8", TextUtil.doubleToString(1.0001499999e8));
assertEquals("1.0002e9", TextUtil.doubleToString(1.0001500001e9));
assertEquals("1.0001e9", TextUtil.doubleToString(1.0001499999e9));
assertEquals("1.0002e10", TextUtil.doubleToString(1.0001500001e10));
assertEquals("1.0001e10", TextUtil.doubleToString(1.0001499999e10));
assertEquals("-1.0002e-5", TextUtil.doubleToString(-1.0001500001e-5));
assertEquals("-1.0001e-5", TextUtil.doubleToString(-1.0001499999e-5));
assertEquals("-1.0002e-4", TextUtil.doubleToString(-1.0001500001e-4));
assertEquals("-1.0001e-4", TextUtil.doubleToString(-1.0001499999e-4));
assertEquals("-0.0010002", TextUtil.doubleToString(-1.0001500001e-3));
assertEquals("-0.0010001", TextUtil.doubleToString(-1.0001499999e-3));
assertEquals("-0.010002", TextUtil.doubleToString(-1.0001500001e-2));
assertEquals("-0.010001", TextUtil.doubleToString(-1.0001499999e-2));
assertEquals("-0.10002", TextUtil.doubleToString(-1.0001500001e-1));
assertEquals("-0.10001", TextUtil.doubleToString(-1.0001499999e-1));
assertEquals("-1.0002", TextUtil.doubleToString(-1.0001500001));
assertEquals("-1.0001", TextUtil.doubleToString(-1.0001499999));
assertEquals("-10.002", TextUtil.doubleToString(-1.0001500001e1));
assertEquals("-10.001", TextUtil.doubleToString(-1.0001499999e1));
assertEquals("-100.02", TextUtil.doubleToString(-1.0001500001e2));
assertEquals("-100.01", TextUtil.doubleToString(-1.0001499999e2));
assertEquals("-1000.2", TextUtil.doubleToString(-1.0001500001e3));
assertEquals("-1000.1", TextUtil.doubleToString(-1.0001499999e3));
assertEquals("-10002", TextUtil.doubleToString(-1.0001500001e4));
assertEquals("-10001", TextUtil.doubleToString(-1.0001499999e4));
assertEquals("-100012", TextUtil.doubleToString(-1.00011500001e5));
assertEquals("-100011", TextUtil.doubleToString(-1.00011499999e5));
assertEquals("-1000112", TextUtil.doubleToString(-1.000111500001e6));
assertEquals("-1000111", TextUtil.doubleToString(-1.000111499999e6));
assertEquals("-10001112", TextUtil.doubleToString(-1.0001111500001e7));
assertEquals("-10001111", TextUtil.doubleToString(-1.0001111499999e7));
assertEquals("-1.0002e8", TextUtil.doubleToString(-1.0001500001e8));
assertEquals("-1.0001e8", TextUtil.doubleToString(-1.0001499999e8));
assertEquals("-1.0002e9", TextUtil.doubleToString(-1.0001500001e9));
assertEquals("-1.0001e9", TextUtil.doubleToString(-1.0001499999e9));
assertEquals("-1.0002e10", TextUtil.doubleToString(-1.0001500001e10));
assertEquals("-1.0001e10", TextUtil.doubleToString(-1.0001499999e10));
}
}