[英]Is there a way I can rotate one object and not both of them?
我正在從事一個具有 GUI 和移動坦克的項目。 雖然坦克移動得很好,但我無法弄清楚如何單獨移動/旋轉它們。 我還需要清理我的代碼,因為我覺得我有很多額外的事情要做。
這是一些代碼,這是我嘗試過的。
我有四個班級。 導彈、坦克和董事會。 我在Tank class 中調用 keylisteners。我應該在 doDrawing 方法中這樣做嗎? doDrawing方法在Board class中。
private void doDrawing(Graphics g)
{
final double rads = Math.toRadians(120);
final double sin = Math.abs(Math.sin(rads));
final double cos = Math.abs(Math.cos(rads));
final int w = (int) Math.floor(tank1.getX() * cos + tank1.getX() * sin);
final int h = (int) Math.floor(tank1.getY() * cos + tank1.getY() * sin);
Graphics2D g2d = (Graphics2D) g;
g2d.translate(w, h);
g2d.rotate(rot, tank1.getX(), tank1.getY());
AffineTransform backup = g2d.getTransform();
AffineTransform trans = new AffineTransform();
g2d.setTransform(backup);
//g2d.drawImage(tank1.getImage(), tank1.getX(), tank1.getY(), this);
trans.setToIdentity();
trans.rotate(rot, h, w);
trans.translate(h, w);
trans.setTransform(backup);
g2d.drawImage(tank1.getImage(), tank1.getX(), tank1.getY(), this);
//g2d.drawImage(tank1.getImage(), tank1.getX(), tank1.getY(), this);
g2d.drawImage(tank2.getImage(), tank2.getX(), tank2.getY(), this);
List<Missile> missiles = tank1.getMissiles();
for (Missile missile : missiles)
{
//trans.rotate(Math.toRadians(rads), w/2, h/2);
g2d.drawImage(missile.getImage(), missile.getX(), missile.getY() - 7, this);
//g2d.rotate(rot, missile.getX(), missile.getY() - 7);
}
}
所以,只是看着...
private void doDrawing(Graphics g)
{
//...
Graphics2D g2d = (Graphics2D) g;
g2d.translate(w, h);
g2d.rotate(rot, tank1.getX(), tank1.getY());
AffineTransform backup = g2d.getTransform();
AffineTransform trans = new AffineTransform();
g2d.setTransform(backup);
//g2d.drawImage(tank1.getImage(), tank1.getX(), tank1.getY(), this);
trans.setToIdentity();
trans.rotate(rot, h, w);
trans.translate(h,w);
trans.setTransform(backup);
g2d.drawImage(tank1.getImage(), tank1.getX(), tank1.getY(), this);
g2d.drawImage(tank2.getImage(), tank2.getX(), tank2.getY(), this);
//...
}
很明顯,您正在對Graphics
上下文應用一個永遠不會撤消的轉換,因此在它之后繪制的所有內容都將應用相同的轉換。
您需要做的第一件事是分解繪制邏輯,以便它可以繪制單個實體。
您需要做的第二件事是在對其進行任何修改之前創建Graphics
上下文的副本,這將防止父副本繼續進行這些修改,這些修改將與未來的修改混合在一起。
也許像...
private void doDrawing(Graphics g) {
// Because I don't trust anybody
Graphics2D g2d = (Graphics2D) g.create();
drawTank(tank1, g2d);
g2d.dispose();
g2d = (Graphics2D) g.create();
drawTank(tank2, g2d);
g2d.dispose();
}
private void drawTank(Tank tank, Graphics2D g) {
final double rads = Math.toRadians(120);
final double sin = Math.abs(Math.sin(rads));
final double cos = Math.abs(Math.cos(rads));
final int w = (int) Math.floor(tank.getX() * cos + tank.getX() * sin);
final int h = (int) Math.floor(tank.getY() * cos + tank.getY() * sin);
Graphics2D g2d = (Graphics2D) g.create();
g2d.translate(w, h);
// `rot` should be derived from the tank ... no idea where this is
g2d.translate(tank.getX(), tank.getY());
// Origin has now been translated to the tanks position
g2d.rotate(rot, 0, 0);
g2d.drawImage(tank.getImage(), 0, 0, this);
// We no longer to need to keep these resources
g2d.dispose();
// Create a new "clean" copy
g2d = (Graphics2D) g.create();
// I don't know if it's needed, but I would, personally, calculate
// any required rotation again, but that's me
List<Missile> missiles = tank1.getMissiles();
for (Missile missile : missiles) {
g2d.drawImage(missile.getImage(), missile.getX(), missile.getY() - 7, this);
}
}
例如,參見:
java.util.List<Tank>
保存在程序的 model 中。如果您的坦克同步移動/旋轉,我想原因是它們都收到相同的關鍵事件並以相同的方式做出反應。
將按鍵監聽器(或另一個答案中建議的更好的按鍵綁定)放入您的板 class。監聽器將檢查按下/釋放哪個鍵,並向正確的坦克發出移動或轉動或其他任何命令。 這樣你就可以讓一個坦克對 WASD 做出反應,而另一個坦克對上/下/左/右做出反應。
然而,坦克 class 中的方法不會對關鍵事件做出反應,但可以命名為前進、后退、左轉、右轉。
doDrawing 方法應該像它的名字所暗示的那樣做:只是執行繪圖。 這可能會發生任何次數以獲得良好的屏幕刷新率或在另一個 window 不再隱藏您的游戲后重新繪制棋盤。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.