`
乱世群英
  • 浏览: 18711 次
  • 性别: Icon_minigender_1
  • 来自: 济南
社区版块
存档分类
最新评论

java 游戏编程 (六)

阅读更多
现在来让Fly移动。上一节已经能够监听键盘。现在对监听键盘事件做进一步封装。
首先设计一个类:GameAction.主要处理所有的键盘与鼠标事件,能够保存事件,在需要的时候调出。并能够设置键贴图,键贴图在另一个类InputManager中实现。所谓键贴图就是将按下的键具备什么功能做一个映射。先来看GameAction:引用Brackeen。
package com.jsheng.game.util;

/**
 * function: company: jsheng
 * 
 * @author wanghn wanghaining9999@sina.com
 */
public class GameAction {
	//标识一个正常行为
	public static final int NORMAL = 0;
	//按下键后返回值为1,放开喝再次按下也为1.
	public static final int DETECT_INITAL_PRESS_ONLY = 1;
	
	private static final int STATE_RELEASED = 0;
	private static final int STATE_PRESSED = 1;
	private static final int STATE_WAITING_FOR_RELEASE = 2;

	private String name;   	//动作名
	private int behavior;	//行为
	private int count;		//按下的次数
	private int state;		//状态

	public GameAction(String name) {
		this(name, NORMAL);
	}

	public GameAction(String name, int behavior) {
		this.name = name;
		this.behavior = behavior;
		reset();
	}

	public String getName() {
		return name;
	}

	public void reset() {
		state = STATE_RELEASED;
		count = 0;
	}

	
	public void tap() {
		press();
		release();
	}

	//表示键被按下
	public void press() {
		press(1);
	}

	public void press(int amount) {
		if (state != STATE_WAITING_FOR_RELEASE) {
			this.count += amount;
			state = STATE_PRESSED;
		}
	}

	public void release() {
		state = STATE_RELEASED;
	}

	public boolean isPressed() {
		return (getCount() != 0);
	}

	//检查按下的次数
	public int getCount() {
		int s = count;
		if (s != 0) {
			if (state == STATE_RELEASED) {
				count = 0;
			} else if (behavior == DETECT_INITAL_PRESS_ONLY) {
				state = STATE_WAITING_FOR_RELEASE;
				count = 0;
			}
		}
		return s;
	}
}


然后创建输入管理器这个类,代码比较长,但很简单:
package com.jsheng.game.util;

import java.awt.*;
import java.awt.event.*;
import java.util.List;
import java.util.ArrayList;
import javax.swing.SwingUtilities;

/** function:
 * company: jsheng
 * @author wanghn      wanghaining9999@sina.com
 */
public class InputManager implements KeyListener, MouseListener,
    MouseMotionListener, MouseWheelListener
{
    public static final Cursor INVISIBLE_CURSOR =
        Toolkit.getDefaultToolkit().createCustomCursor(
            Toolkit.getDefaultToolkit().getImage(""),
            new Point(0,0),
            "invisible");

    public static final int MOUSE_MOVE_LEFT = 0;
    public static final int MOUSE_MOVE_RIGHT = 1;
    public static final int MOUSE_MOVE_UP = 2;
    public static final int MOUSE_MOVE_DOWN = 3;
    public static final int MOUSE_WHEEL_UP = 4;
    public static final int MOUSE_WHEEL_DOWN = 5;
    public static final int MOUSE_BUTTON_1 = 6;
    public static final int MOUSE_BUTTON_2 = 7;
    public static final int MOUSE_BUTTON_3 = 8;

    private static final int NUM_MOUSE_CODES = 9;

    private static final int NUM_KEY_CODES = 600;

    private GameAction[] keyActions =
        new GameAction[NUM_KEY_CODES];
    private GameAction[] mouseActions =
        new GameAction[NUM_MOUSE_CODES];

    private Point mouseLocation;
    private Point centerLocation;
    private Component comp;
    private Robot robot;
    private boolean isRecentering;

    public InputManager(Component comp) {
        this.comp = comp;
        mouseLocation = new Point();
        centerLocation = new Point();

        comp.addKeyListener(this);
        comp.addMouseListener(this);
        comp.addMouseMotionListener(this);
        comp.addMouseWheelListener(this);
        comp.setFocusTraversalKeysEnabled(false);
    }

    public void setCursor(Cursor cursor) {
        comp.setCursor(cursor);
    }


    public void setRelativeMouseMode(boolean mode) {
        if (mode == isRelativeMouseMode()) {
            return;
        }

        if (mode) {
            try {
                robot = new Robot();
                recenterMouse();
            }
            catch (AWTException ex) {
                // couldn't create robot!
                robot = null;
            }
        }
        else {
            robot = null;
        }
    }


    public boolean isRelativeMouseMode() {
        return (robot != null);
    }


    public void mapToKey(GameAction gameAction, int keyCode) {
        keyActions[keyCode] = gameAction;
    }


    public void mapToMouse(GameAction gameAction,
        int mouseCode)
    {
        mouseActions[mouseCode] = gameAction;
    }

    public void clearMap(GameAction gameAction) {
        for (int i=0; i<keyActions.length; i++) {
            if (keyActions[i] == gameAction) {
                keyActions[i] = null;
            }
        }

        for (int i=0; i<mouseActions.length; i++) {
            if (mouseActions[i] == gameAction) {
                mouseActions[i] = null;
            }
        }

        gameAction.reset();
    }

    public List<String> getMaps(GameAction gameCode) {
        ArrayList<String> list = new ArrayList<String>();

        for (int i=0; i<keyActions.length; i++) {
            if (keyActions[i] == gameCode) {
                list.add(getKeyName(i));
            }
        }

        for (int i=0; i<mouseActions.length; i++) {
            if (mouseActions[i] == gameCode) {
                list.add(getMouseName(i));
            }
        }
        return list;
    }

    public void resetAllGameActions() {
        for (int i=0; i<keyActions.length; i++) {
            if (keyActions[i] != null) {
                keyActions[i].reset();
            }
        }

        for (int i=0; i<mouseActions.length; i++) {
            if (mouseActions[i] != null) {
                mouseActions[i].reset();
            }
        }
    }

    public static String getKeyName(int keyCode) {
        return KeyEvent.getKeyText(keyCode);
    }


    public static String getMouseName(int mouseCode) {
        switch (mouseCode) {
            case MOUSE_MOVE_LEFT: return "Mouse Left";
            case MOUSE_MOVE_RIGHT: return "Mouse Right";
            case MOUSE_MOVE_UP: return "Mouse Up";
            case MOUSE_MOVE_DOWN: return "Mouse Down";
            case MOUSE_WHEEL_UP: return "Mouse Wheel Up";
            case MOUSE_WHEEL_DOWN: return "Mouse Wheel Down";
            case MOUSE_BUTTON_1: return "Mouse Button 1";
            case MOUSE_BUTTON_2: return "Mouse Button 2";
            case MOUSE_BUTTON_3: return "Mouse Button 3";
            default: return "Unknown mouse code " + mouseCode;
        }
    }

    public int getMouseX() {
        return mouseLocation.x;
    }

    public int getMouseY() {
        return mouseLocation.y;
    }

    private synchronized void recenterMouse() {
        if (robot != null && comp.isShowing()) {
            centerLocation.x = comp.getWidth() / 2;
            centerLocation.y = comp.getHeight() / 2;
            SwingUtilities.convertPointToScreen(centerLocation,
                comp);
            isRecentering = true;
            robot.mouseMove(centerLocation.x, centerLocation.y);
        }
    }


    private GameAction getKeyAction(KeyEvent e) {
        int keyCode = e.getKeyCode();
        if (keyCode < keyActions.length) {
            return keyActions[keyCode];
        }
        else {
            return null;
        }
    }

    public static int getMouseButtonCode(MouseEvent e) {
         switch (e.getButton()) {
            case MouseEvent.BUTTON1:
                return MOUSE_BUTTON_1;
            case MouseEvent.BUTTON2:
                return MOUSE_BUTTON_2;
            case MouseEvent.BUTTON3:
                return MOUSE_BUTTON_3;
            default:
                return -1;
        }
    }


    private GameAction getMouseButtonAction(MouseEvent e) {
        int mouseCode = getMouseButtonCode(e);
        if (mouseCode != -1) {
             return mouseActions[mouseCode];
        }
        else {
             return null;
        }
    }


    public void keyPressed(KeyEvent e) {
        GameAction gameAction = getKeyAction(e);
        if (gameAction != null) {
            gameAction.press();
        }
        e.consume();
    }


    public void keyReleased(KeyEvent e) {
        GameAction gameAction = getKeyAction(e);
        if (gameAction != null) {
            gameAction.release();
        }
        e.consume();
    }


    public void keyTyped(KeyEvent e) {
        e.consume();
    }


    public void mousePressed(MouseEvent e) {
        GameAction gameAction = getMouseButtonAction(e);
        if (gameAction != null) {
            gameAction.press();
        }
    }


    public void mouseReleased(MouseEvent e) {
        GameAction gameAction = getMouseButtonAction(e);
        if (gameAction != null) {
            gameAction.release();
        }
    }


    public void mouseClicked(MouseEvent e) {
    }


    public void mouseEntered(MouseEvent e) {
        mouseMoved(e);
    }


    public void mouseExited(MouseEvent e) {
        mouseMoved(e);
    }


    public void mouseDragged(MouseEvent e) {
        mouseMoved(e);
    }


    public synchronized void mouseMoved(MouseEvent e) {
        if (isRecentering &&
            centerLocation.x == e.getX() &&
            centerLocation.y == e.getY())
        {
            isRecentering = false;
        }
        else {
            int dx = e.getX() - mouseLocation.x;
            int dy = e.getY() - mouseLocation.y;
            mouseHelper(MOUSE_MOVE_LEFT, MOUSE_MOVE_RIGHT, dx);
            mouseHelper(MOUSE_MOVE_UP, MOUSE_MOVE_DOWN, dy);

            if (isRelativeMouseMode()) {
                recenterMouse();
            }
        }

        mouseLocation.x = e.getX();
        mouseLocation.y = e.getY();

    }


    public void mouseWheelMoved(MouseWheelEvent e) {
        mouseHelper(MOUSE_WHEEL_UP, MOUSE_WHEEL_DOWN,
            e.getWheelRotation());
    }

    private void mouseHelper(int codeNeg, int codePos,
        int amount)
    {
        GameAction gameAction;
        if (amount < 0) {
            gameAction = mouseActions[codeNeg];
        }
        else {
            gameAction = mouseActions[codePos];
        }
        if (gameAction != null) {
            gameAction.press(Math.abs(amount));
            gameAction.release();
        }
    }

}



有了这些还不够,我们还需要为我们的主角增加重力,保证跳跃后能回到地球上,呵呵。
我们在来一个类Player,直接继承Fly,给它增加重力。
package com.jsheng.game.util;

/** function:
 * company: jsheng
 * @author wanghn      wanghaining9999@sina.com
 */
public class Player extends Fly {
	 public static final int STATE_NORMAL = 0;
	 public static final int STATE_JUMPING = 1;

	 public static final float SPEED = .3f;
	 public static final float GRAVITY = .002f;

	 private int floorY;
	 private int state;
	 public Player(Animation anim) {
	        super(anim);
	        state = STATE_NORMAL;
	    }
	    public int getState() {
	        return state;
	    }

	    public void setState(int state) {
	        this.state = state;
	    }

	    public void setFloorY(int floorY) {
	        this.floorY = floorY;
	        setY(floorY);
	    }

	    public void jump() {
	        setDy(-1);
	        state = STATE_JUMPING;
	    }

	    public void update(long elapsedTime) {
	        if (getState() == STATE_JUMPING) {
	            setDy(getDy() + GRAVITY * elapsedTime);
	        }
	        super.update(elapsedTime);
	        if (getState() == STATE_JUMPING && getY() >= floorY) {
	            setDy(0);
	            setY(floorY);
	            setState(STATE_NORMAL);
	        }

	    }
	}

有了这些,我们来做一个测试类:
package com.jsheng.game.test1;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Window;
import java.awt.event.KeyEvent;

import com.jsheng.game.util.Animation;
import com.jsheng.game.util.GameAction;
import com.jsheng.game.util.GameCore;
import com.jsheng.game.util.InputManager;
import com.jsheng.game.util.Player;

/** function:
 * company: jsheng
 * @author wanghn      wanghaining9999@sina.com
 */
public class InputManagerTest extends GameCore {

    public static void main(String[] args) {
        new InputManagerTest().run();
    }

    protected GameAction jump;
    protected GameAction exit;
    protected GameAction moveLeft;
    protected GameAction moveRight;
    protected GameAction pause;
    protected InputManager inputManager;
    private Player player;
    private Image bgImage;
    private boolean paused;

    public void init() {
        super.init();
        Window window = screen.getFullScreenWindow();
        inputManager = new InputManager(window);
        createGameActions();
        createFly();
        paused = false;
    }
    public boolean isPaused() {
        return paused;
    }
    public void setPaused(boolean p) {
        if (paused != p) {
            this.paused = p;
            inputManager.resetAllGameActions();
        }
    }


    public void update(long elapsedTime) {
        checkSystemInput();

        if (!isPaused()) {
            checkGameInput();
            player.update(elapsedTime);
        }
    }

    public void checkSystemInput() {
        if (pause.isPressed()) {
            setPaused(!isPaused());
        }
        if (exit.isPressed()) {
            stop();
        }
    }
    public void checkGameInput() {
        float x = 0;
        if (moveLeft.isPressed()) {
            x-=Player.SPEED;
        }
        if (moveRight.isPressed()) {
            x+=Player.SPEED;
        }
        player.setDx(x);

        if (jump.isPressed() &&
            player.getState() != Player.STATE_JUMPING)
        {
            player.jump();
        }
    }


    public void draw(Graphics2D g) {
        g.drawImage(bgImage, 0, 0, null);
        g.drawImage(player.getImage(),
            Math.round(player.getX()),
            Math.round(player.getY()),
            null);
    }

    public void createGameActions() {
        jump = new GameAction("jump",
            GameAction.DETECT_INITAL_PRESS_ONLY);
        exit = new GameAction("exit",
            GameAction.DETECT_INITAL_PRESS_ONLY);
        moveLeft = new GameAction("moveLeft");
        moveRight = new GameAction("moveRight");
        pause = new GameAction("pause",
            GameAction.DETECT_INITAL_PRESS_ONLY);

        inputManager.mapToKey(exit, KeyEvent.VK_ESCAPE);
        inputManager.mapToKey(pause, KeyEvent.VK_P);

        inputManager.mapToKey(jump, KeyEvent.VK_SPACE);
        inputManager.mapToMouse(jump,
            InputManager.MOUSE_BUTTON_1);

        inputManager.mapToKey(moveLeft, KeyEvent.VK_LEFT);
        inputManager.mapToKey(moveRight, KeyEvent.VK_RIGHT);

        inputManager.mapToKey(moveLeft, KeyEvent.VK_A);
        inputManager.mapToKey(moveRight, KeyEvent.VK_D);

        inputManager.mapToMouse(moveLeft,
          InputManager.MOUSE_MOVE_LEFT);
        inputManager.mapToMouse(moveRight,
          InputManager.MOUSE_MOVE_RIGHT);

    }
    private void createFly() {
        bgImage = loadImage("images/bg.jpg");
        Image player1 = loadImage("images/1.jpg");
        Image player2 = loadImage("images/2.jpg");
        Image player3 = loadImage("images/3.jpg");
        Animation anim = new Animation();
        anim.addFrame(player1, 250);
        anim.addFrame(player2, 150);
        anim.addFrame(player1, 150);
        anim.addFrame(player2, 150);
        anim.addFrame(player3, 200);
        anim.addFrame(player2, 150);
        player = new Player(anim);
        player.setFloorY(screen.getHeight() - player.getHeight());
    }

}


wasd或箭头控制方向,空格为跳跃,P是暂停。也可以用鼠标控制跳跃与方向。
在暂停游戏后,控制动作的类GameAction要复位,保证暂停后按下的键失效。
分享到:
评论
1 楼 scx0237 2010-02-02  
GameCore 这个类在哪里呀

相关推荐

    JAVA游戏编程

    JAVA游戏编程 JAVA入门 JAVA游戏编程 JAVA入门 JAVA游戏编程 JAVA入门 JAVA游戏编程 JAVA入门 JAVA游戏编程 JAVA入门 JAVA游戏编程 JAVA入门

    游戏编程游戏编程java游戏编程java

    总的来说,Java游戏编程涵盖了广泛的编程知识,从基础到高级,从理论到实践,都需要深入理解和掌握。通过不断的学习和实践,开发者可以利用Java创造出丰富多样的游戏世界。在"JavaGames"这个压缩包中,可能包含了...

    Java游戏编程(游戏开发与编程序列).rar

    Java游戏编程是软件开发领域中的一个分支,它利用Java编程语言来创建各种类型的游戏,从简单的2D小游戏到复杂的3D大作。本资源“Java游戏编程(游戏开发与编程序列).rar”可能包含一系列教程、源代码示例或者相关...

    Java游戏编程原理与实践教程+随书原代码

    Java游戏编程原理与实践教程是一本深入探讨如何使用Java语言进行游戏开发的专业书籍。它涵盖了游戏编程的基础概念、核心技术以及实战技巧,旨在帮助读者从零基础到熟练掌握Java游戏开发。书中结合了大量的实例和源...

    《Java 2游戏编程》

    《Java 2游戏编程》是一本专为游戏开发爱好者和专业人士设计的教程,由美国作者Thomas Petchel撰写,并由晏利斌、孙淑敏、邵荣等人翻译成中文。这本书深入浅出地介绍了如何使用Java 2平台进行游戏开发,涵盖了从基础...

    java游戏编程导学

    Java游戏编程导学 在Java游戏开发领域,Java以其跨平台、高效稳定的特点,成为许多开发者的选择。本导学将深入探讨如何利用Java语言来创建引人入胜的游戏。Java游戏编程不仅涉及到基本的编程概念,还涵盖了图形渲染...

    Java游戏编程原理与实践教程源码

    Java游戏编程原理与实践是计算机科学中的一个重要领域,它结合了Java编程语言的特性与游戏设计的技巧。在这个教程源码包中,包含了多种经典游戏的实现,如推箱子、俄罗斯方块、超级玛丽等,这些都是游戏开发初学者和...

    java游戏编程原理与实践教程pdf+源代码

    Java游戏编程原理与实践教程是一本深入探讨如何使用Java语言进行游戏开发的专业书籍,由陈锐、夏敏捷、葛丽萍三位专家共同编著。这本书不仅涵盖了基础的编程概念,还详细介绍了游戏开发中的关键技术和实战技巧。通过...

    JAVA游戏编程.

    在JAVA游戏编程的世界里,开发者可以利用JAVA的强大功能和丰富的库来创造引人入胜的游戏体验。本课程资料集合了从基础知识到高级技术的全面学习路径,帮助你深入理解JAVA在游戏开发中的应用。 首先,从第二章的...

    Java游戏编程读书笔记

    在深入探讨Java游戏编程的世界之前,我们先要理解Java作为一种编程语言的基础特性。Java是由Sun Microsystems(现为Oracle公司)于1995年推出的,它是一种面向对象、跨平台的语言,具有“一次编写,到处运行”的特性...

    Java游戏编程入门

    想学JAVA游戏编程吗?快来了解下吧!这个资源是Java初学者的极品教程,讲的简单透彻。

    Java游戏编程

    Java游戏编程是一个涵盖广泛的主题,它涉及到使用Java编程语言来创建各种类型的游戏,从简单的2D小游戏到复杂的3D大作。在这个领域中,开发者需要掌握基础的编程概念,以及特定于游戏开发的技术。 首先,Java是一种...

    java游戏编程光盘源代码

    java游戏编程光盘源代码!~

    Java游戏编程源码教程

    Java游戏编程源码教程是一门深入浅出的学习资源,适合对Java编程有兴趣并希望进入游戏开发领域的初学者。本教程通过实例源码讲解,旨在帮助读者掌握Java在游戏开发中的应用,逐步提升编程技巧和游戏设计能力。 首先...

    Java游戏编程开发教程

    Java游戏编程开发教程是针对那些想要利用Java语言创建游戏的开发者设计的一套全面学习资源。Java作为一种跨平台、面向对象的编程语言,因其强大的性能和灵活性,在游戏开发领域有着广泛的应用。本教程将深入探讨如何...

    JAVA游戏编程源代码

    以下将详细介绍与"JAVA游戏编程源代码"相关的技术要点。 1. **Java基础知识**:Java是面向对象的语言,理解类、对象、封装、继承和多态等核心概念至关重要。同时,熟悉Java语法,如控制流(if-else,switch,循环)...

    Java游戏编程小手册

    "Java游戏编程小手册" 本资源是一个Java游戏编程的小手册,涵盖了Java游戏开发的基本概念、技术和框架。下面是从该资源中提炼出的知识点: 一、Java游戏开发概述 Java游戏开发是使用Java语言创建游戏的过程。...

    《Java游戏编程》源代码

    在百科里搜索“Java游戏编程” (http://baike.baidu.com/view/647813.htm),就能发现一部好书——《Java游戏编程》,是深入学习java可望而不可求(难买)的好书

    Java 游戏编程入门

    在《Java游戏编程入门》这本书中,作者向我们揭示了使用Java语言开发游戏的基本概念和技术。这是一本适合初学者的教程,旨在帮助那些对编程和游戏开发感兴趣的人快速掌握必要的技能。书中不仅包含了Java语言的基础...

    Java2游戏编程.pdf

    本书的出版标志着Java游戏编程技术的深入探索和应用,是对游戏开发人员和爱好者来说一本非常实用的参考书籍。 从书的内容来看,涵盖了Java游戏编程的众多方面,主要包括以下几点: 1. Java 2D游戏编程基础:书中从...

Global site tag (gtag.js) - Google Analytics