0

I have a problem in my code. I tried to do the game snake but i stopped at the continuous movement into an ActionMap of the drawpanel. I tried to use drawPanel.repaint in a loop but it show me only when it arrived at the end, but i want that all the movement give in the ActionMap. How i can do it? Or anyone have another solution for doing this?

    DrawPanel drawPanel = new DrawPanel();

    public Snake(){           
        InputMap inputMap = drawPanel.getInputMap();//JPanel.WHEN_IN_FOCUSED_WINDOW);
        ActionMap actionMap = drawPanel.getActionMap();                       
        inputMap.put(KeyStroke.getKeyStroke("RIGHT"), "rightAction");
        actionMap.put("rightAction", rightAction);            
        inputMap.put(KeyStroke.getKeyStroke("LEFT"), "leftAction");
        actionMap.put("leftAction", leftAction);            
        inputMap.put(KeyStroke.getKeyStroke("UP"), "upAction");
        actionMap.put("upAction", upAction);            
        inputMap.put(KeyStroke.getKeyStroke("DOWN"), "downAction");
        actionMap.put("downAction", downAction);

        add(drawPanel);            
        pack();
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setLocationRelativeTo(null);
        setVisible(true);
    }

    private class DrawPanel extends JPanel {

        protected void paintComponent(Graphics g) {                
            super.paintComponent(g);
            g.setColor(Color.GRAY);
                    g.fillRect(0, 0, getWidth(), getHeight());
            g.setColor(Color.GREEN);
            g.fillRect(x, y, 10, 10);    
        }
        public Dimension getPreferredSize() {
            return new Dimension(400, 400);
        }             
    }

    Action downAction = new AbstractAction(){
        public void actionPerformed(ActionEvent e) { 
            while (y<390)
            {              
                y +=+10;             
                drawPanel.repaint(); 
            }                
          /*  if (y<390)
                y +=+10; 
            else
                y = 390; 
            drawPanel.repaint();   
            */     
          }
    };

    Action upAction = new AbstractAction(){
        public void actionPerformed(ActionEvent e) {
            if (y>0)
                y -=10;
            else
                y = 0;
            drawPanel.repaint();
        }
    };

      Action leftAction = new AbstractAction(){
        public void actionPerformed(ActionEvent e) {
            if (x>0)
                x -=10;
            else
                x = 0;
            drawPanel.repaint();
        }
    };

    Action rightAction = new AbstractAction(){
        public void actionPerformed(ActionEvent e) {
            if (x<390)
                x +=10;
            else
                x = 390;
            drawPanel.repaint();
        }
    };    

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable(){
            public void run(){
                new Snake();
            }
        });
    }
}
mKorbel
  • 109,525
  • 20
  • 134
  • 319
Chris
  • 1
  • For my standard response check out [Motion Using the Keyboard](http://tips4java.wordpress.com/2013/06/09/motion-using-the-keyboard/) for examples with and without Timers. – camickr Dec 17 '14 at 15:50

2 Answers2

2

As shown here and here, you can evoke the actionPerformed() method of your own Action instances in the ActionListener of a javax.swing.Timer. You can adjust the timer's delay to pace the animation.

Community
  • 1
  • 1
trashgod
  • 203,806
  • 29
  • 246
  • 1,045
0

you should use a game loop that repaint screen always, not when you press the button. and, you should keep the stat of button. something like , "isDownPressing". and, you should make calculations in "paintComponent" function. btw, you need a callback for pressing a button, and releasing button.

Adem
  • 9,402
  • 9
  • 43
  • 58