Как я могу переместить форму вперед под определенным углом в Java? - PullRequest
0 голосов
/ 17 марта 2019

Я пытаюсь создать игру, в которой я могу повернуть прямоугольник и переместить его вперед в определенном направлении или назад, когда я нажимаю вправо, он вращается по часовой стрелке, а если я нажимаю влево, он идет против часовой стрелки, но я У меня проблема в том, что если я двигаюсь вверх или вниз, он вращается одинаково только тогда, когда я нажимаю вправо и влево, но я ожидал, что они будут двигаться вверх или вниз, я посмотрел на другие программы и попытался скопировать их методы, но все еще отсутствует что-то, кто-то, пожалуйста, помогите, заранее спасибо

Вот мой точный код ниже:

 public class Rotate extends JPanel implements ActionListener,KeyListener{
 Timer t = new Timer(20,this); 
 boolean right=false;
 boolean left=false;
 boolean up=false;
 boolean down=false;
 Rectangle tank;
 int tankx=30;
 int tanky=50;
 double a;
 int angle;

 Rotate()
 {

  JFrame f = new JFrame();
  f.add(this);
  f.addKeyListener(this);
  f.setSize(1000,1000);
  f.setVisible(true);
  f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);


      tank = new Rectangle(400,400,30,50);

}
public static void main(String[] args) {
new Rotate();
}
int i;
 public void paint(Graphics g) {

   super.paint(g);
   Graphics2D g2d =(Graphics2D)g;


   g2d.rotate(a,tank.getWidth()+tankx/2,tank.getHeight()+tanky/2);
   g.setColor(Color.red);
   g.fillRect(tankx,tanky,tank.width,tank.height);

   if(angle>360)
   {
       angle=0;

   }
   else if(angle<0)
   {
       angle=360;

   }
    a= Math.toRadians(angle);   

    System.out.println("x");
         t.start();
}





@Override
public void actionPerformed(ActionEvent e) {

 if(right==true)
 {

       angle+=4;

 }
 else if(left==true)
 {


      angle-=4; 

 }   
 else if(down==true)
 {
  angle-=4;
  tank.x-=Math.cos(a);
  tank.y-=Math.sin(a);   

 }
 else if(up==true)
 {
  angle+=4;
  tank.x+=Math.cos(a);
  tank.y+=Math.sin(a);   

 }
    repaint();
     }



@Override
public void keyTyped(KeyEvent e) {

}

@Override
public void keyPressed(KeyEvent e) {
  if(e.getKeyCode()==KeyEvent.VK_RIGHT)
  {
      right=true;
  }
  else if(e.getKeyCode()==KeyEvent.VK_LEFT)
  {
      left=true;
  }
  else if(e.getKeyCode()==KeyEvent.VK_UP)
  {
     up=true;
  }
  else if(e.getKeyCode()==KeyEvent.VK_DOWN)
  {
      down=true;
  }
}

@Override
public void keyReleased(KeyEvent e) {
  right=false;
  left=false;
  up=false;
  down=false;
}

}

1 Ответ

0 голосов
/ 17 марта 2019

g.fillRect(tankx, tanky, tank.width, tank.height); ? Когда tankx или tanky действительно изменяется?

Поскольку вы изменяете нижележащий контекст Graphics в каждом цикле рисования, вы рискуете сложить вращение,Лучше использовать Graphics#create, чтобы создать снимок текущего состояния, а затем изменить его.Просто не забудьте вызвать Graphics#dispose для копии

Помните, что когда вы вращаете контекст Graphics, вы также поворачиваете исходную точку (0x0), поэтому движение больше не будет "вверх" или "вниз ", но будет относительно угла поворота.

Итак, это модификация вашего кода.Я обновил метод paint (вы действительно должны использовать paintComponent), чтобы начало координат переводилось в положение танка (это делает 0x0 положение танка), тогда стало намного легчеповерните.

import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.Timer;

public class Rotate extends JPanel implements ActionListener, KeyListener {

    Timer t = new Timer(20, this);
    boolean right = false;
    boolean left = false;
    boolean up = false;
    boolean down = false;
    Rectangle tank;
    int angle;

    Rotate() {

        JFrame f = new JFrame();
        f.add(this);
        f.addKeyListener(this);
        f.setSize(1000, 1000);
        f.setVisible(true);
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        tank = new Rectangle(400, 400, 30, 50);
        t.start();
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                new Rotate();
            }
        });
    }

    @Override
    protected void paintComponent(Graphics g) {

        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g.create();

        double radian = Math.toRadians(angle);
        g2d.translate(tank.x, tank.y);
        g2d.rotate(radian, tank.getWidth() / 2, tank.getHeight() / 2);
        g2d.setColor(Color.red);
        g2d.fillRect(0, 0, tank.width, tank.height);
        g2d.dispose();
    }

    @Override
    public void actionPerformed(ActionEvent e) {

        if (right == true) {

            angle += 4;
            System.out.println("Right");

        } else if (left == true) {

            angle -= 4;
            System.out.println("Left");

        } else if (down == true) {
            angle -= 4;
            double radian = Math.toRadians(angle);
            tank.x -= Math.cos(radian);
            tank.y -= Math.sin(radian);
            System.out.println("Down: " + tank.x + "x" + tank.y);

        } else if (up == true) {
            angle += 4;
            double radian = Math.toRadians(angle);
            tank.x += Math.cos(radian);
            tank.y += Math.sin(radian);
            System.out.println("Up: " + tank.x + "x" + tank.y);

        }
        repaint();
    }

    @Override
    public void keyTyped(KeyEvent e) {

    }

    @Override
    public void keyPressed(KeyEvent e) {
        if (e.getKeyCode() == KeyEvent.VK_RIGHT) {
            right = true;
        } else if (e.getKeyCode() == KeyEvent.VK_LEFT) {
            left = true;
        } else if (e.getKeyCode() == KeyEvent.VK_UP) {
            up = true;
        } else if (e.getKeyCode() == KeyEvent.VK_DOWN) {
            down = true;
        }
    }

    @Override
    public void keyReleased(KeyEvent e) {
        right = false;
        left = false;
        up = false;
        down = false;
    }
}

Я также думаю, что вы cos / sin повернули не в ту сторону, и вы должны вычесть вверх, а если добавить - вниз, но это исключительно на основе наблюдений.

Возможно, вы захотите взглянуть на:

для получения дополнительных идей

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...