3

谁能告诉我为什么这个程序说我缺少一个主要方法?我在这段代码的底部有一个。

import javax.swing.*;
import javax.swing.event.*;
import java.awt.*;
import java.awt.event.*;

public class Collision extends JFrame
{
    final int WIDTH = 900, HEIGHT = 650;

    double p1Speed = .5, p2Speed = .5;

    //these are the ints that represent directions
    final int UP = 0, RIGHT = 1, DOWN = 2, LEFT = 3;

    //these will keep track of the players directions(default = up)
    int p1Direction = UP;
    int p2Direction = UP;

    Rectangle left = new Rectangle(0,0,WIDTH/9,HEIGHT);
    Rectangle right = new Rectangle((WIDTH/9)*8,0,WIDTH/9,HEIGHT);
    Rectangle top = new Rectangle(0,0,WIDTH,HEIGHT/9);
    Rectangle bottom = new Rectangle(0,(HEIGHT/9)*8, WIDTH,HEIGHT/9);
    Rectangle center = new Rectangle((int)((WIDTH/9)* 2.5),(int)((HEIGHT/9)*2.5),(int) 
    ((WIDTH/9)*5),(HEIGHT/9)*4);

    Rectangle obstacle = new Rectangle(WIDTH/2,(int)((HEIGHT/9)*7),WIDTH/10,HEIGHT/9);
    Rectangle obstacle2 = new Rectangle(WIDTH/3,(int)((HEIGHT/9)*5),WIDTH/10,HEIGHT/4);
    Rectangle obstacle3 = new Rectangle(2*(WIDTH/3),(int)
    ((HEIGHT/9)*5),WIDTH/10,HEIGHT/4);
    Rectangle obstacle4 = new Rectangle(WIDTH/3,HEIGHT/9,WIDTH/30,HEIGHT/9);
    Rectangle obstacle5 = new Rectangle(WIDTH/2,(int)((HEIGHT/9)*1.5),WIDTH/30,HEIGHT/4);

    Rectangle finish = new Rectangle(WIDTH/9,(HEIGHT/2)-HEIGHT/9,(int) 
    ((WIDTH/9)*1.5),HEIGHT/70);

    Rectangle p1 = new Rectangle(WIDTH/9,HEIGHT/2, WIDTH/30,WIDTH/30);

    Rectangle p2 = new Rectangle(((WIDTH/9)+((int)((WIDTH/9)*1.5)/2)),(HEIGHT/2)+ 
    (HEIGHT/10),WIDTH/30,WIDTH/30);
    public Collision()
    {
        //the following code creates the JFrame
        super("Radical Racing");
        setSize(WIDTH,HEIGHT);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setVisible(true);

        //start the inner class (which works on it's own because it is a thread)
        Move1 m1 = new Move1();
        Move2 m2 = new Move2();
        m1.start();
        m2.start();

    }
    public void paint(Graphics g)
    {
        super.paint(g);

        //draw the bckround for the racetrack
        g.setColor(Color.DARK_GRAY);
        g.fillRect(0,0,WIDTH,HEIGHT);

        //When we drawthe border will be green
        g.setColor(Color.GREEN);

        //the following rectangle is the start line for the outer player
        Rectangle lineO = new
                Rectangle(WIDTH/9,HEIGHT/2,(int)((WIDTH/9)*1.5)/2,HEIGHT/140);

        //the following rctangle is the start line for the inner player
        Rectangle lineI = new
                Rectangle(((WIDTH/9)+((int)((WIDTH/9)*1.5)/2)),(HEIGHT/2)+(HEIGHT/10),
        (int)((WIDTH/9)*1.5)/2,HEIGHT/140);

        //now using the rectangles, draw it
        g.fillRect(left.x,left.y,left.width,left.height);
        g.fillRect(right.x,right.y,right.width,right.height);
        g.fillRect(top.x,top.y,top.width,top.height);
        g.fillRect(bottom.x,bottom.y,bottom.width,bottom.height);
        g.fillRect(center.x,center.y,center.width,center.height);
        g.fillRect(obstacle.x,obstacle.y,obstacle.width,obstacle.height);
        g.fillRect(obstacle2.x,obstacle2.y,obstacle2.width,obstacle2.height);
        g.fillRect(obstacle3.x,obstacle3.y,obstacle3.width,obstacle3.height);
        g.fillRect(obstacle4.x,obstacle4.y,obstacle4.width,obstacle4.height);
        g.fillRect(obstacle5.x,obstacle5.y,obstacle5.width,obstacle5.height);
    //set the starting line color
        g.setColor(Color.WHITE);
        //the draw the starting line
        g.fillRect(lineO.x,lineO.y,lineO.width,lineO.height);
        g.fillRect(lineI.x,lineI.y,lineI.width,lineI.height);
        //set the color of the finish line to yellow
        g.setColor(Color.YELLOW);
        g.fillRect(finish.x,finish.y,finish.width,finish.height);

        //set the color to blue for p1
        g.setColor(Color.BLUE);
        //now draw the actual player
        g.fill3DRect(p1.x,p1.y,p1.width,p1.height,true);

        //set the color to red for p2
        g.setColor(Color.red);
        //now draw the actual player
        g.fill3DRect(p2.x,p2.y,p2.width,p2.height,true);

    }
    private class Move1 extends Thread implements KeyListener
    {
        public void run()
        {
            //add the code to make the KeyListener "wake up"
            addKeyListener(this);

            //now, put the code should all be in an infinite loop, so the process repeats.
            while(true)
            {

            try
            {
                //first refresh the screen:
                repaint();

                //check to see if the car hits the outside of the walls.
                //If so make it slow it's speed by setting it's speed to .4.
                if(p1.intersects(left) ||  p1.intersects(right) ||
                p1.intersects(top) ||  p1.intersects(bottom) ||
                p1.intersects(obstacle) ||  p1.intersects(obstacle2) ||       
                p1.intersects(p2) ||  p1.intersects(obstacle3) ||
                p1.intersects(obstacle4) ||  p1.intersects(obstacle5))   
                {
                    p1Speed = -4;
                }

                if(p1.intersects(center))
                {
                    p1Speed = -2.5;
                }
                //increase speed a bit
                if(p1Speed<=5)
                    p1Speed+=.2;

                //these will move the player based on direction
                if(p1Direction == UP)
                {
                    p1.y-=(int)p1Speed;
                }
                if(p1Direction ==DOWN)
                {
                    p1.y+=(int)p1Speed;
                }
                if(p1Direction == LEFT)
                {
                    p1.x-=(int)p1Speed;
                } 
                if(p1Direction == RIGHT)
                {
                    p1.x+=(int)p1Speed;
                } 
                //This delays the refresh rate
                Thread.sleep(75);
            }
            catch(Exception e)

            {//if there is an exception (an error), exit the loop
                break;
            }
            }
        }
        //You must also implement this method from Key Listener
        public void keyPressed(KeyEvent event)
        {

        }
        //You must also implement this method from key listener
        public void keyReleased(KeyEvent event)
        {

        }
        //You must also implement this method from key listener

        public void keyTyped(KeyEvent event)
        {

            if(event.getKeyChar()=='a')
            {
                p1Direction = LEFT;
            }
            if(event.getKeyChar()=='s')
            {
                p1Direction = DOWN;
            }
            if(event.getKeyChar()=='d')
            {
                p1Direction = RIGHT;
            }
            if(event.getKeyChar()=='w')
            {
                p1Direction = UP;
            }
        }
    }

        private class Move2 extends Thread implements KeyListener
        {
            public void run()
            {
                //add the code to make the key listener wake up
                addKeyListener(this);

                //now this should all be in an infinite loop so that the process repeats
                while(true)
                {

                    try
                    {
                        //first refresh the screen
                        repaint();
                        //check to see if the car hits the outside walls.
                        //if so make it slow its speed by setting it's speed to -4.
                        if(p2.intersects(left) || p2.intersects(right) ||
                        p2.intersects(top) || p2.intersects(bottom) ||
                        p2.intersects(obstacle) || p2.intersects(obstacle2) ||  
                        p1.intersects(p2))
                        {
                            p2Speed = -4;
                        }

                        if(p2.intersects(center))
                        {
                            p2Speed = -2.5;
                        }
                        //increase speed a bit
                        if(p2Speed<=5)
                            p2Speed = .2;
                        //these will move the player based off direction
                        if(p2Direction == UP)
                {
                    p2.y-=(int)p2Speed;
                }
                if(p2Direction ==DOWN)
                {
                    p2.y+=(int)p2Speed;
                }
                if(p2Direction == LEFT)
                {
                    p2.x-=(int)p2Speed;
                } 
                if(p2Direction == LEFT)
                {
                    p2.x+=(int)p2Speed;
                } 
                //this delays the refresh rate:
                Thread.sleep(75);
                    }
                catch(Exception e)
                {
                    //if there is an exception, exit the loop.
                    break;

            }

          }
        }

        //you must also implement this method from key listener
        public void keyPressed(KeyEvent event)
        {

        }
        public void keyReleased(KeyEvent event)
        {

        }
        public void keyTyped(KeyEvent event)
        {
            if(event.getKeyChar()=='j')
            {
                p2Direction = LEFT;
            }
            if(event.getKeyChar()=='k')
            {
                p2Direction = DOWN;
            }
            if(event.getKeyChar()=='l')
            {
                p2Direction = RIGHT;
            }
            if(event.getKeyChar()=='i')
            {
                p2Direction = UP;
            }
        }


        //This starts the program by calling the constructor:        
        public static void main(String [] args)
        {
        new Collision();
        }
     }
4

1 回答 1

3

KeyListeners only work if the component listened to has the focus, and often KeyListeners fail because this is not so. So one thing to do is to test this, and if the component has lost the focus than do things to correct this.

But having said this, I have to ask what book you're using, since in general, you want to avoid using KeyListeners with Swing applications in favor of Key Bindings. Also, it is usually not recommended to draw directly in a JFrame, so you may wish to use a different book.

于 2012-05-26T02:34:38.377 回答