Make TubeFinSet RingInstanceable
Make the TubeFinSet RingInstanceable. This change updates the rendering of both the 2D and 3D views to handle the RingInstanceable shapes. This also updates the DocumentConfig to parse the new XML formats properly. Signed-off-by: Billy Olsen <billy.olsen@gmail.com>
This commit is contained in:
parent
1bb64d45d3
commit
74ec0be340
@ -294,6 +294,10 @@ class DocumentConfig {
|
||||
Reflection.findMethod(TubeFinSet.class, "setOuterRadius", double.class),
|
||||
"auto",
|
||||
Reflection.findMethod(TubeFinSet.class, "setOuterRadiusAutomatic", boolean.class)));
|
||||
setters.put("TubeFinSet:instancecount", new IntSetter(
|
||||
Reflection.findMethod(TubeFinSet.class, "setInstanceCount", int.class)));
|
||||
setters.put("TubeFinSet:angleoffset", new AnglePositionSetter() );
|
||||
setters.put("TubeFinSet:radiusoffset", new RadiusPositionSetter() );
|
||||
|
||||
// InternalComponent - nothing
|
||||
|
||||
|
@ -7,14 +7,16 @@ import java.util.List;
|
||||
import net.sf.openrocket.l10n.Translator;
|
||||
import net.sf.openrocket.preset.ComponentPreset;
|
||||
import net.sf.openrocket.preset.ComponentPreset.Type;
|
||||
import net.sf.openrocket.rocketcomponent.position.AngleMethod;
|
||||
import net.sf.openrocket.rocketcomponent.position.AxialMethod;
|
||||
import net.sf.openrocket.rocketcomponent.position.AxialPositionable;
|
||||
import net.sf.openrocket.rocketcomponent.position.RadiusMethod;
|
||||
import net.sf.openrocket.startup.Application;
|
||||
import net.sf.openrocket.util.Coordinate;
|
||||
import net.sf.openrocket.util.MathUtil;
|
||||
import net.sf.openrocket.util.Transformation;
|
||||
|
||||
public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
public class TubeFinSet extends ExternalComponent implements RingInstanceable, AxialPositionable {
|
||||
private static final Translator trans = Application.getTranslator();
|
||||
|
||||
private final static double DEFAULT_RADIUS = 0.025;
|
||||
@ -22,18 +24,20 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
private boolean autoRadius = true; // Radius chosen automatically based on parent component
|
||||
private double outerRadius = DEFAULT_RADIUS;
|
||||
protected double thickness = 0.002;
|
||||
|
||||
protected int fins = 6;
|
||||
private AngleMethod angleMethod = AngleMethod.FIXED;
|
||||
protected RadiusMethod radiusMethod = RadiusMethod.RELATIVE;
|
||||
|
||||
/**
|
||||
* Rotation angle of the first fin. Zero corresponds to the positive y-axis.
|
||||
*/
|
||||
protected double rotation = 0;
|
||||
private double firstFinOffsetRadians = 0;
|
||||
|
||||
protected int fins = 6;
|
||||
|
||||
/**
|
||||
* Rotation about the x-axis by angle this.rotation.
|
||||
*/
|
||||
protected Transformation baseRotation = Transformation.rotate_x(rotation);
|
||||
protected Transformation baseRotation = Transformation.IDENTITY; // initially, rotate by 0 radians.
|
||||
|
||||
/**
|
||||
* Rotation about the x-axis by 2*PI/fins.
|
||||
@ -167,7 +171,6 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
public int getFinCount() {
|
||||
return fins;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isAfter(){
|
||||
@ -195,7 +198,7 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
* @return The base rotation amount.
|
||||
*/
|
||||
public double getBaseRotation() {
|
||||
return rotation;
|
||||
return getAngleOffset();
|
||||
}
|
||||
|
||||
public double getFinRotation() {
|
||||
@ -207,12 +210,7 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
* @param r The base rotation amount.
|
||||
*/
|
||||
public void setBaseRotation(double r) {
|
||||
r = MathUtil.reduce180(r);
|
||||
if (MathUtil.equals(r, rotation))
|
||||
return;
|
||||
rotation = r;
|
||||
baseRotation = Transformation.rotate_x(rotation);
|
||||
fireComponentChangeEvent(ComponentChangeEvent.BOTH_CHANGE);
|
||||
setAngleOffset(r);
|
||||
}
|
||||
|
||||
public Transformation getBaseRotationTransformation() {
|
||||
@ -327,9 +325,9 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
RocketComponent s;
|
||||
|
||||
s = this.getParent();
|
||||
double x = this.getPosition().x;
|
||||
while (s != null) {
|
||||
if (s instanceof SymmetricComponent) {
|
||||
double x = this.getPosition().x;
|
||||
return ((SymmetricComponent) s).getRadius(x);
|
||||
}
|
||||
s = s.getParent();
|
||||
@ -337,4 +335,113 @@ public class TubeFinSet extends ExternalComponent implements AxialPositionable {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getInstanceCount() {
|
||||
return getFinCount();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setInstanceCount(int newCount) {
|
||||
setFinCount(newCount);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPatternName() {
|
||||
return (this.getInstanceCount() + "-tubefin-ring");
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getBoundingRadius() {
|
||||
// TODO Auto-generated method stub
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRadius(RadiusMethod method, double radius) {
|
||||
// TODO Auto-generated method stub
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAngleOffset(double angleRadians) {
|
||||
final double reducedAngle = MathUtil.reducePI(angleRadians);
|
||||
if (MathUtil.equals(reducedAngle, firstFinOffsetRadians))
|
||||
return;
|
||||
firstFinOffsetRadians = reducedAngle;
|
||||
|
||||
if (MathUtil.equals(this.firstFinOffsetRadians, 0)) {
|
||||
baseRotation = Transformation.IDENTITY;
|
||||
} else {
|
||||
baseRotation = Transformation.rotate_x(firstFinOffsetRadians);
|
||||
}
|
||||
|
||||
fireComponentChangeEvent(ComponentChangeEvent.BOTH_CHANGE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AngleMethod getAngleMethod() {
|
||||
return this.angleMethod;
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getAngleOffset() {
|
||||
return this.firstFinOffsetRadians;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAngleMethod(AngleMethod newAngleMethod) {
|
||||
mutex.verify();
|
||||
this.angleMethod = newAngleMethod;
|
||||
fireComponentChangeEvent(ComponentChangeEvent.BOTH_CHANGE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getInstanceAngleIncrement() {
|
||||
return ( 2*Math.PI / getFinCount());
|
||||
}
|
||||
|
||||
@Override
|
||||
public double[] getInstanceAngles() {
|
||||
final double angleIncrementRadians = getInstanceAngleIncrement();
|
||||
|
||||
double[] result = new double[getFinCount()];
|
||||
for (int finNumber=0; finNumber < getFinCount(); ++finNumber) {
|
||||
double additionalOffset = angleIncrementRadians * finNumber;
|
||||
result[finNumber] = MathUtil.reduce2PI(firstFinOffsetRadians + additionalOffset);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Coordinate[] getInstanceOffsets() {
|
||||
checkState();
|
||||
|
||||
final double bodyRadius = this.getBodyRadius();
|
||||
|
||||
// already includes the base rotation
|
||||
final double[] angles = getInstanceAngles();
|
||||
|
||||
Coordinate[] toReturn = new Coordinate[this.fins];
|
||||
for (int instanceNumber = 0; instanceNumber < this.fins; instanceNumber++) {
|
||||
final Coordinate raw = new Coordinate( 0, bodyRadius, 0);
|
||||
final Coordinate rotated = Transformation.getAxialRotation(angles[instanceNumber]).transform(raw);
|
||||
toReturn[instanceNumber] = rotated;
|
||||
}
|
||||
|
||||
return toReturn;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRadiusOffset(double radius) {
|
||||
// TODO Auto-generated method stub
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRadiusMethod(RadiusMethod method) {
|
||||
// TODO Auto-generated method stub
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -318,13 +318,8 @@ public class ComponentRenderer {
|
||||
gl.glPushMatrix();
|
||||
gl.glMatrixMode(GLMatrixFunc.GL_MODELVIEW);
|
||||
gl.glRotated(fs.getBaseRotation() * (180.0 / Math.PI), 1, 0, 0);
|
||||
for( int i = 0; i< fs.getFinCount(); i++ ) {
|
||||
gl.glPushMatrix();
|
||||
gl.glTranslated(0, fs.getOuterRadius() + fs.getBodyRadius(), 0);
|
||||
renderTube(gl, which, fs.getOuterRadius(), fs.getInnerRadius(), fs.getLength());
|
||||
gl.glPopMatrix();
|
||||
gl.glRotated(360.0 / fs.getFinCount(), 1, 0, 0);
|
||||
}
|
||||
gl.glTranslated(0, fs.getOuterRadius(), 0);
|
||||
renderTube(gl, which, fs.getOuterRadius(), fs.getInnerRadius(), fs.getLength());
|
||||
gl.glPopMatrix();
|
||||
}
|
||||
|
||||
|
@ -35,13 +35,10 @@ public class TubeFinSetShapes extends RocketComponentShape {
|
||||
final double outerRadius = finSet.getOuterRadius();
|
||||
final double length = finSet.getLength();
|
||||
Coordinate[] locations = transformLocations(finSet, transformation);
|
||||
Transformation finRotation = finSet.getFinRotationTransformation();
|
||||
|
||||
Shape[] shapes = new Shape[finSet.getFinCount()];
|
||||
for (int i=0; i < shapes.length; i++) {
|
||||
shapes[i] = new Rectangle2D.Double(locations[0].x, (locations[0].y-outerRadius), length, 2*outerRadius);
|
||||
locations = finRotation.transform(locations);
|
||||
}
|
||||
Shape[] shapes = new Shape[] {
|
||||
new Rectangle2D.Double(locations[0].x, (locations[0].y-outerRadius), length, 2*outerRadius)
|
||||
};
|
||||
|
||||
return RocketComponentShape.toArray(shapes, component);
|
||||
}
|
||||
@ -62,13 +59,10 @@ public class TubeFinSetShapes extends RocketComponentShape {
|
||||
|
||||
final double outerRadius = finSet.getOuterRadius();
|
||||
Coordinate[] locations = transformLocations(finSet, transformation);
|
||||
Transformation finRotation = finSet.getFinRotationTransformation();
|
||||
|
||||
Shape[] shapes = new Shape[finSet.getFinCount()];
|
||||
for (int i=0; i < shapes.length; i++) {
|
||||
shapes[i] = new Ellipse2D.Double((locations[0].z - outerRadius), (locations[0].y - outerRadius), (2 * outerRadius), (2 * outerRadius));
|
||||
locations = finRotation.transform(locations);
|
||||
}
|
||||
Shape[] shapes = new Shape[] {
|
||||
new Ellipse2D.Double((locations[0].z - outerRadius), (locations[0].y - outerRadius), (2 * outerRadius), (2 * outerRadius))
|
||||
};
|
||||
|
||||
return RocketComponentShape.toArray(shapes, component);
|
||||
}
|
||||
@ -95,13 +89,12 @@ public class TubeFinSetShapes extends RocketComponentShape {
|
||||
private static Coordinate[] transformLocations(final TubeFinSet finSet, final Transformation transformation) {
|
||||
final double outerRadius = finSet.getOuterRadius();
|
||||
final double bodyRadius = finSet.getBodyRadius();
|
||||
Coordinate[] locations = finSet.getComponentLocations();
|
||||
Transformation baseRotation = finSet.getBaseRotationTransformation();
|
||||
Coordinate[] locations = finSet.getInstanceLocations();
|
||||
|
||||
for (int i=0; i < locations.length; i++) {
|
||||
Coordinate c = locations[i].add(0, (bodyRadius + outerRadius), 0);
|
||||
c = transformation.linearTransform(c);
|
||||
c = baseRotation.transform(c);
|
||||
Coordinate c = locations[i].setX(0.);
|
||||
c = c.sub(0, (bodyRadius - outerRadius), 0);
|
||||
c = transformation.transform(c);
|
||||
locations[i] = c;
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user