您的位置:首页 > 编程语言 > Java开发

Java[伪]寻径追踪实现(由Loonframework提供)

2007-10-19 09:52 211 查看
我们都知道,在诸如魔兽的很多战略游戏中,会出现要求某A角色接近某B角色的情况(攻击或是怎么着咱不考虑……),玩家很简单的一步操作,却会引发开发者“怎么走过去”这个“复杂”的算法问题,也就是所谓的“Path-finding”——寻径。

好的寻径算法,不但能避免不必要的资源损耗,而且能令游戏友好度增加。反之则会严重影响游戏的可玩性或诸如GIS等系统的可靠性。

在本次,我以Java为例,演示一个最简单的寻径系统——甚至可以说是伪寻径系统的实现。 (^^)

首先,我们建立一个追踪者(一说到这里我就想起了生化里的掠食者……)


package org.test.tracker;




import java.awt.Color;


import java.awt.Graphics;






/** *//**


* <p>


* Title: LoonFramework


* </p>


* <p>


* Description:追踪者。


* </p>


* <p>


* Copyright: Copyright (c) 2007


* </p>


* <p>


* Company: LoonFramework


* </p>


*


* @author chenpeng


* @email:ceponline@yahoo.com.cn


* @version 0.1


*/




public class Tracker ...{




private static final int SIZE = TrackerPanel.SIZE;




public int x;




public int y;






/** *//**


* 析构函数,默认坐标为0,0


*


*/




public Tracker() ...{


this(0, 0);


}






/** *//**


* 析构函数,设定x,y坐标


*


* @param x


* @param y


*/




public Tracker(int x, int y) ...{


this.x = x;


this.y = y;


}






/** *//**


* 设定追踪对象


*


* @param prey


*/




public void chase(Objective objective) ...{


//始终以目标坐标矫正追踪者坐标。




if (x > objective.x) ...{


x--;




} else if (x < objective.x) ...{


x++;


}






if (y > objective.y) ...{


y--;




} else if (y < objective.y) ...{


y++;


}


}






/** *//**


* 绘制追踪者


*


* @param g


*/




public void draw(Graphics g) ...{


g.setColor(Color.RED);


g.fillRect(x * SIZE, y * SIZE, SIZE, SIZE);


}


}



而后,我们建立一个被追踪的目标。


package org.test.tracker;




import java.awt.Color;


import java.awt.Graphics;






/** *//**


* <p>


* Title: LoonFramework


* </p>


* <p>


* Description:被跟踪的目标对象。


* </p>


* <p>


* Copyright: Copyright (c) 2007


* </p>


* <p>


* Company: LoonFramework


* </p>


*


* @author chenpeng


* @email:ceponline@yahoo.com.cn


* @version 0.1


*/




public class Objective ...{




private static final int SIZE = TrackerPanel.SIZE;




private static final int UP = 0;




private static final int DOWN = 1;




private static final int LEFT = 2;




private static final int RIGHT = 3;




public int x;




public int y;






/** *//**


* 析构函数,内部转换x,y坐标。


*


*/




public Objective() ...{


x = TrackerPanel.COL / 2;


y = TrackerPanel.ROW / 2;


}







/** *//**


* 析构函数,设定x,y坐标。


*


*/




public Objective(int x, int y) ...{


this.x = x;


this.y = y;


}






/** *//**


* 移动目标


*


* @param dir


*/




public void move(int dir) ...{




switch (dir) ...{


case UP:


y--;


break;


case DOWN:


y++;


break;


case LEFT:


x--;


break;


case RIGHT:


x++;


break;


}


}






/** *//**


* 绘制目标


*


* @param g


*/




public void draw(Graphics g) ...{


g.setColor(Color.BLUE);


g.fillOval(x * SIZE, y * SIZE, SIZE, SIZE);


}


}



最后,我们建立一个面板,用以绘制图形。


package org.test.tracker;




import java.awt.Color;


import java.awt.Dimension;


import java.awt.Frame;


import java.awt.Graphics;


import java.awt.Image;


import java.awt.Panel;


import java.awt.event.KeyEvent;


import java.awt.event.KeyListener;


import java.awt.image.BufferedImage;






/** *//**


* <p>


* Title: LoonFramework


* </p>


* <p>


* Description:追踪演示面板。


* </p>


* <p>


* Copyright: Copyright (c) 2007


* </p>


* <p>


* Company: LoonFramework


* </p>


*


* @author chenpeng


* @email:ceponline@yahoo.com.cn


* @version 0.1


*/




public class TrackerPanel extends Panel implements Runnable, KeyListener ...{




/** *//**


*


*/


private static final long serialVersionUID = 1L;




// 设定窗体宽与高


private static final int WIDTH = 480;




private static final int HEIGHT = 480;




// 描绘的正方体大小


static final int SIZE = 8;




// 获得对应列数,即将frame转化为类数组的存在。


public static final int ROW = HEIGHT / SIZE;




public static final int COL = WIDTH / SIZE;




// 获得对应行数


private static final int UP = 0;




private static final int DOWN = 1;




private static final int LEFT = 2;




private static final int RIGHT = 3;




// 追踪者


private Tracker tracker;




// 目标


private Objective objective;




private Thread thread;




private Image screen = null;




private Graphics bg = null;






public TrackerPanel() ...{


setPreferredSize(new Dimension(WIDTH, HEIGHT));


setFocusable(true);


addKeyListener(this);


screen = new BufferedImage(WIDTH, HEIGHT, 1);


bg = screen.getGraphics();


// 追踪者初始位置,0行,0列


tracker = new Tracker(0, 0);


// 目标初始位置,50行,50列


objective = new Objective(50, 50);


thread = new Thread(this);


thread.start();


}






public void paint(Graphics g) ...{


// 设定底色为白色,并清屏


bg.setColor(Color.white);


bg.fillRect(0, 0, WIDTH, HEIGHT);


// 绘制追踪者


tracker.draw(bg);


// 绘制目标


objective.draw(bg);


g.drawImage(screen, 0, 0, this);


g.dispose();


}






public void update(Graphics g) ...{


paint(g);


}






public void run() ...{




while (true) ...{


// 设定追击的目标。


tracker.chase(objective);


repaint();




try ...{


Thread.sleep(110);




} catch (InterruptedException e) ...{


e.printStackTrace();


}


}


}






public void keyTyped(KeyEvent e) ...{


}






public void keyPressed(KeyEvent e) ...{


int key = e.getKeyCode();




switch (key) ...{


case KeyEvent.VK_UP:


objective.move(UP);


break;


case KeyEvent.VK_DOWN:


objective.move(DOWN);


break;


case KeyEvent.VK_LEFT:


objective.move(LEFT);


break;


case KeyEvent.VK_RIGHT:


objective.move(RIGHT);


break;


}


repaint();


}






public void keyReleased(KeyEvent e) ...{


}






public static void main(String[] args) ...{


Frame frm = new Frame();


frm.setTitle("简单的Java图形寻径追踪实现(由Loonframework提供)");


frm.setSize(WIDTH, HEIGHT);


frm.setResizable(false);


frm.add(new TrackerPanel());


frm.setVisible(true);


}




}



这时,画面上显示的红色正方体为追踪者,蓝色圆球为被追踪目标,而无论篮球如何移动,红色正方体都将始终向篮球靠拢。

实际上,通过代码我们就可以知道,这时两者间的移动路径,被没有经过复杂的方法演算,而是以目标的坐标来决定的,颇有独孤九剑那种,敌人若是只有一招,我也只有一招,他若是有千招万招,我也自是千招万招。但是,这种方法在实际的寻径处理中,并不能很好的解决如障碍物,区域转换等问题,所以只是一种[伪]寻径,
或者说是在无障碍情况下的简单解决方案。

如果关注寻径算法在Java中的进一步实现,还请继续关注我的blog……

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: