|
这节其实是将自定义渲染的。
不过我额外的补充一些内容。
平面行走图是RPG等类型游戏常用的图片资源。
类似这种
问题是这个库貌似不支持多个动作集成在一个图片中,其实这种情况下怎么办、最好当然是提供想对象的资源,但这也不好
因为这个库里面AI是主要的对渲染这部分基本上没什么特殊的功能。不方便。
所以我们要自己动手写一下怎么支持这个功能。
其实在本库中
[size=+2][size=1em]Constructor Summary | | | [size=11.199999809265137px] [size=+2][size=1em]Method Summary | [size=-1][size=1em] void | draw( BaseEntity owner, float posX, float posY, float velX, float velY, float headX, float headY)
绘制 | [size=-1][size=1em] int | | [size=-1][size=1em] void | | [size=-1][size=1em] int | | [size=-1][size=1em] int | | [size=11.199999809265137px] 这个也能看明白。
本库的bitmap中根本没有类似的功能。根据源码的分析解读,此类写的甚是简单。
[pre lang="java" line="1"]package game2dai.entityshapes.ps;
import game2dai.entities.BaseEntity;
import processing.core.PApplet;
import processing.core.PImage;
/**
* The entity graphic comes from an image file.
*
* @author Peter Lager
*
*/
public class BitmapPic extends PicturePS {
PImage[] img;
int lastTime = 0, elapsedTime = 0;
int interval = 0;
int frameNo = 0;
/**
* Single image for all frames
* @param papp
* @param fname the name of the bitmap image file
*/
public BitmapPic(PApplet papp, String fname){
super(papp);
img = ImageBank.getImage(papp, fname);
}
/**
* An animated image. <br>
* The image frames are stored as tiles within a single image
*
* @param papp
* @param fname the name of the bitmap image file
* @param nCols number of tiles horizontally
* @param nRows number of rows vertically
* @param interval the time (milliseconds) between image frames
*/
public BitmapPic(PApplet papp, String fname, int nCols, int nRows, int interval){
super(papp);
img = ImageBank.getImage(papp, fname, nCols, nRows);
lastTime = app.millis();
elapsedTime = 0;
this.interval = (nCols* nRows > 1) ? interval : 0;
}
@Override
public void draw(BaseEntity owner, float posX, float posY, float velX,
float velY, float headX, float headY) {
// Draw and hints that are specified and relevant
if(hints != 0){
Hints.hintFlags = hints;
Hints.draw(app, owner, velX, velY, headX, headY);
}
// Determine the angle the entity is facing
float angle = PApplet.atan2(headY, headX);
// If this an animated image then update the animation
if(interval > 0){
int ctime = app.millis();
while(ctime > lastTime + interval){
lastTime += interval;
frameNo++;
}
frameNo %= img.length;
}
// Prepare to draw the entity
app.pushStyle();
app.imageMode(PApplet.CENTER);
app.pushMatrix();
app.translate(posX, posY);
app.rotate(angle);
// Draw the entity
app.image(img[frameNo],0,0);
// Finished drawing
app.popMatrix();
app.popStyle();
}
/**
* Set the number of milliseconds between frames. <br>
* Negative values will be treated as zero which will cause the animation to pause.
*
* @param interval
*/
public void interval(int interval){
if(interval <= 0)
this.interval = 0;
else
this.interval = interval;
}
public int interval(){
return interval;
}
/**
* Use next frame in the animation
* @return this renderer
*/
public int nextFrame(){
frameNo++;
frameNo %= img.length;
return frameNo;
}
/**
* Use previous frame in the animation
* @return this renderer
*/
public int prevFrame(){
frameNo += img.length - 1;
frameNo %= img.length;
return frameNo;
}
}
[/code]
好吧,逼上梁山了,很多时候都是这样的。
所以自己写吧
写有两种方法,一种就是集成此类然后从写函数。
另一种就是直接根据此类中提供的一些方法,进行方法级别的修改。
在此我们先搞定方法级别的。
我们主要要实现的上下左右四个方向的行走。当然了就是给力。按一下方向键,人物做一下向这个方向行走的动画
[pre lang="processing" line="1"]import game2dai.entities.*;
import game2dai.entityshapes.ps.*;
import game2dai.maths.*;
import game2dai.*;
import game2dai.entityshapes.*;
import game2dai.fsm.*;
import game2dai.steering.*;
import game2dai.utils.*;
import game2dai.graph.*;
// AnimRenderer_01
World world;
StopWatch sw;
Vehicle tank;
Vector2D target = new Vector2D();
BitmapPic view;
BitmapPic viewshang;
BitmapPic viewxia;
BitmapPic viewzuo;
BitmapPic viewyou;
Vector2D origin;
int movei=0;;
public void setup() {
size(600, 320);
world = new World(width, height);
sw = new StopWatch();
// Create the mover
tank = new Vehicle(new Vector2D(width/2, height/2), // position
40, // collision radius
new Vector2D(0, 0), // velocity
40, // maximum speed
new Vector2D(0, 0), // headinga
15, // mass
90f, // turning rate
1000 // max force
);
// What does this mover look like
view = new BitmapPic(this, "nvzhujiao.png", 4,4,0);
tank.renderer(view);
// Finally we want to add this to our game domain
world.add(tank);
sw.reset();
}
public void draw() {
double elapsedTime = sw.getElapsedTime();
tank.AP().arriveOn(target);
origin=tank.AP().getFeelers()[1];
float speed = (float) tank.speed();
float maxSpeed = (float) tank.maxSpeed();
if (speed > 1) {
int newInterval = (int) map(speed, 0, maxSpeed, 600, 40);
// view.interval(newInterval);
}
else {
//view.interval(0);
}
world.update(elapsedTime);
background(218, 140, 54);
world.draw();
}
void keyPressed()
{
switch (keyCode)
{
case 87 :
{
if(movei>=12&&movei<15)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(12);
}
println(movei);
target.set(origin.x, 0);
break;
}
case 83 :
{
if(movei>=0&&movei<3)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(0);
}
println(movei);
target.set(origin.x, height);
break;
}
case 65 :
{
if(movei>=4&&movei<7)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(4);
}
target.set(0, origin.y);
break;
}
case 68 :
{
if(movei>=8&&movei<11)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(8);
}
target.set(width, origin.y);
break;
}
default :
println("keyCode: "+keyCode);
break;
}
}
void changeMovei(int needto)
{
int moveitemp=movei;
if(needto>=0&&needto<=15)
{
if(moveitemp==needto)
{
}
else
{
if(moveitemp>needto)
{//movei>needto
for(int i=0;i<moveitemp-needto;i++)
{
view.prevFrame();
movei--;
}
}
else
{//movei<needto
for(int i=0;i<needto-moveitemp;i++)
{
view.nextFrame();
movei++;
}
}
}
}
}[/code]
当然这个程序还有一给问题,就是我们用的是车类进行的修改,而类会自动前进
这时候怎么让我们的主人公的步伐和前进速度一直
这时候有两种方法
一种是记录行走的方向,然后做一个方法进行动画分析
另一种是让动画不动的时候,速度为零,就可以了。
[pre lang="processing" line="1"]import game2dai.entities.*;
import game2dai.entityshapes.ps.*;
import game2dai.maths.*;
import game2dai.*;
import game2dai.entityshapes.*;
import game2dai.fsm.*;
import game2dai.steering.*;
import game2dai.utils.*;
import game2dai.graph.*;
// AnimRenderer_01
World world;
StopWatch sw;
Vehicle tank;
Vector2D target = new Vector2D();
BitmapPic view;
BitmapPic viewshang;
BitmapPic viewxia;
BitmapPic viewzuo;
BitmapPic viewyou;
Vector2D origin;
int movei=0;;
int fangxiang=0;//0下1上2左3右
public void setup() {
size(600, 320);
world = new World(width, height);
sw = new StopWatch();
// Create the mover
tank = new Vehicle(new Vector2D(width/2, height/2), // position
40, // collision radius
new Vector2D(0, 0), // velocity
40, // maximum speed
new Vector2D(0, 0), // headinga
15, // mass
90f, // turning rate
1000 // max force
);
// What does this mover look like
view = new BitmapPic(this, "nvzhujiao.png", 4,4,0);
tank.renderer(view);
// Finally we want to add this to our game domain
world.add(tank);
sw.reset();
}
public void draw() {
double elapsedTime = sw.getElapsedTime();
tank.AP().arriveOn(target);
origin=tank.AP().getFeelers()[1];
float speed = (float) tank.speed();
float maxSpeed = (float) tank.maxSpeed();
if (speed > 1) {
int newInterval = (int) map(speed, 0, maxSpeed, 600, 40);
//view.interval(newInterval);
DonghuaFenxi();
}
else {
//view.interval(0);
}
world.update(elapsedTime);
background(218, 140, 54);
world.draw();
}
void keyPressed()
{
switch (keyCode)
{
case 87 :
{
fangxiang=1;
break;
}
case 83 :
{
fangxiang=0;
break;
}
case 65 :
{
fangxiang=2;
break;
}
case 68 :
{
fangxiang=3;
break;
}
default :
println("keyCode: "+keyCode);
break;
}
}
void DonghuaFenxi()
{
switch (fangxiang)
{
case 1 :
{
if(movei>=12&&movei<15)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(12);
}
println(movei);
target.set(origin.x, 0);
break;
}
case 0 :
{
if(movei>=0&&movei<3)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(0);
}
println(movei);
target.set(origin.x, height);
break;
}
case 2 :
{
if(movei>=4&&movei<7)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(4);
}
target.set(0, origin.y);
break;
}
case 3 :
{
if(movei>=8&&movei<11)
{
view.nextFrame();
movei++;
}
else
{
changeMovei(8);
}
target.set(width, origin.y);
break;
}
default :
println("keyCode: "+keyCode);
break;
}
}
void changeMovei(int needto)
{
int moveitemp=movei;
if(needto>=0&&needto<=15)
{
if(moveitemp==needto)
{
}
else
{
if(moveitemp>needto)
{//movei>needto
for(int i=0;i<moveitemp-needto;i++)
{
view.prevFrame();
movei--;
}
}
else
{//movei<needto
for(int i=0;i<needto-moveitemp;i++)
{
view.nextFrame();
movei++;
}
}
}
}
}[/code]
效果是动态的,截图开不出来。
|
本帖子中包含更多资源
您需要 登录 才可以下载或查看,没有帐号?注册
x
|