我有一个程序,我必须做的,我必须采取单独的形状对象,并将它们组合起来,以创建最终的汽车形状。我们给予预制的形状,如前轮胎,后轮胎,车身,挡风玻璃和车顶,并应将它们组合成一个车型。已经提供给我的代码如下:
CompositeShape shape = new CompositeShape();
final double WIDTH = 60;
Rectangle2D.Double body
= new Rectangle2D.Double(0, WIDTH / 6,
WIDTH, WIDTH / 6);
Ellipse2D.Double frontTire
= new Ellipse2D.Double(WIDTH / 6, WIDTH / 3,
WIDTH / 6, WIDTH / 6);
Ellipse2D.Double rearTire
= new Ellipse2D.Double(WIDTH * 2 / 3, WIDTH / 3,
WIDTH / 6, WIDTH / 6);
shape.add(body);
shape.add(frontTire);
shape.add(rearTire);
现在,我必须创建compositeShape类,它是组合发生的地方,但我不知道在add(Shape)方法中该怎么做。我们还被告知我们应该使用路径导师方法,但我们并没有真正讲过路径导师或我们应该用它做什么。我不是要求某人告诉我究竟要编码什么,只是一些有用的起点。
我想到的第一件事就是这样:
public class CompositeShape implements Shape {
Graphics2D g2;
public void add(Shape shape){
g2.draw(shape);
}
但它不起作用,因为我无法实例化一个新的图形对象,我得到一个空指针异常。在那之后,我非常难过该做什么。任何帮助将不胜感激。谢谢!
答案 0 :(得分:1)
可能不是在add()方法中绘制Shape,而是应该存储添加的Shape以便稍后绘制。你可以通过赋予CompositeShape某种集合来保存添加的Shapes,这就是我在add()方法中所做的全部。除此之外,它将取决于CompositeShape应该具有的其他行为。如果你必须能够绘制一个CompositeShape,那么你可能会得到一个Graphics对象来绘制。您不必创建自己的。然后绘制CompositeShape将绘制它包含的所有形状。
答案 1 :(得分:1)
java.awt.geom.Area可以将多个形状与方法add,subtract,exclusiveOr和intersect组合在一起。这是CompositeShape的现成课程。
你被要求重新创建为“CompositeShape”似乎非常奇怪,因为Area已经做了你想做的事。
解决方案可以像
一样简单class CompositeShape扩展了java.awt.geom.Area {}
你已经完成了。
或,您已经获得了有关PathIterator的提示,可能是您被鼓励手动管理列表中添加的形状,然后实现所有方法在迭代其他形状方面的Shape接口。
例如,getBounds()需要返回形状的矩形边界,因此得到第一个的矩形边界,然后使用Rectangle.union将其与其他边界连接起来。
对于getPathIterator(),返回一个实现PathIterator的新内部类,它将迭代集合中的所有形状,并迭代每个getPathIterator方法的路径段,返回每个路径段。
在实践中听起来都是不必要的,因为所需的类已经存在。我想你应该澄清想要什么。祝你好运。
为了澄清我对getPathIterator的实现所说的内容,返回类似这样的内容。我没试过这个。这假设您的列表名为shapes
。
public PathIterator getPathIterator(final AffineTransform at, final double flatness) {
return new PathIterator() {
private PathIterator currentPathIterator;
private Iterator<Shape> shapeIterator = shapes.iterator();
{ nextShape(); }
private void nextShape() {
if (shapeIterator.hasNext()) {
currentPathIterator = shapeIterator.next().getPathIterator(at, flatness);
} else {
currentPathIterator = null;
}
}
public int getWindingRule() {
return WIND_NON_ZERO;
}
public boolean isDone() {
for (;;) {
if (currentPathIterator == null) return true;
if (!currentPathIterator.isDone()) return false;
nextShape();
}
}
public void next() {
currentPathIterator.next();
}
public int currentSegment(float[] coords) {
return currentPathIterator.currentSegment(coords);
}
public int currentSegment(double[] coords) {
return currentPathIterator.currentSegment(coords);
}
};
}