📄 actor2d.java
字号:
package like.actor2D;
import like.graphics.*;
import java.awt.*;
import java.awt.geom.*;
import java.util.*;
/************************************************
*封装了移动和绘制一个2-D游戏对象所需要的一般信息
*必须指定一个Actor2DGroup对象
*请务必重写update()方法
************************************************/
public class Actor2D implements Moveable
{
//一个actor具有的一般状态
public static final int STATE_ALIVE = 1;
public static final int STATE_DYING = 2;
public static final int STATE_DEAD = 4;
//当前状态
protected int state;
//所属于的角色组
protected Actor2DGroup group;
//actor位置,速度,以及缓存的变换
protected Vector2D pos;
protected Vector2D excursion;
protected Vector2D vel;
protected AffineTransform xform;
//2d世界里的长和宽(注意跟图片帧的长宽的区别)
protected int posWidth;
protected int posHeight;
//动画模式(AnimateMode)
public final static int AnimateMode_WAIT = 0;
public final static int AnimateMode_AUTOPLAY = 1;
public final static int AnimateMode_BUFFER = 2;
public final static int AnimateMode_NOMPLAY = 3;
//.....
//动画辅助状态(AnimateHelpState)
protected boolean AnimateHelpState_Wait;
protected boolean AnimateHelpState_NoFazeMe;
protected boolean AnimateHelpState_Buffer;
protected int AnimateHelpState_BfferTimes;
//播放下一帧之前需要等待的帧数和一个帧数计数器
protected int animWait;
protected int animCount;
//冲突检测用的边界矩形
protected Rectangle2D bounds;
//和这个actor有冲突的actor列表
protected LinkedList collisionList;
//指向当前动画条的引用&&当前播放器
protected AnimationStrip currAnimation;
protected Animator currAnimator;
//创建一个属于给定Actor2DGroup的Actor2D对象
public Actor2D(Actor2DGroup group)
{
this.group = group;
bounds = new Rectangle2D.Double();
collisionList = new LinkedList();
state = 0;
pos = new Vector2D.Integer();
vel = new Vector2D.Integer();
excursion = new Vector2D.Integer();
xform = new AffineTransform();
currAnimation = null;
animWait = 0;
animCount = 0;
posWidth = 0;
posHeight = 0;
}
public AnimationStrip getCurrAnimationStrip()
{
return this.currAnimation;
}
//更新动画
public boolean animate()
{
boolean temp = false;
if(this.currAnimation != null)
{
if(++animCount >= animWait)
{
if(this.AnimateHelpState_Wait)
{
//是否需要静止一段时间后自动播放一个动画
//需要请添加代码
}
else
{
//如果正处在动画缓冲则检索一下是否缓冲结束
if(AnimateHelpState_Buffer && currAnimation.getCurrFrame(currAnimator)==currAnimation.getLastFrame())
{
this.moveBy(this.vel);
this.AnimateHelpState_BfferTimes--;
if(AnimateHelpState_BfferTimes<=0)
{
AnimateHelpState_BfferTimes = 0;
setAnimateMode(AnimateMode_WAIT);
}
else this.currAnimation.getNextFrame(currAnimator);
}
else
{
this.moveBy(this.vel);
this.currAnimation.getNextFrame(currAnimator);
}
temp=true;
}
animCount = 0;
}
}
return temp;
}
//设置动画模式
public void setAnimateMode(int AnimateMode)
{
switch(AnimateMode)
{
case AnimateMode_WAIT:
this.AnimateHelpState_Wait = true;
this.AnimateHelpState_NoFazeMe = false;
this.AnimateHelpState_Buffer = false;
break;
case AnimateMode_AUTOPLAY:
this.AnimateHelpState_Wait = false;
this.AnimateHelpState_NoFazeMe = true;
this.AnimateHelpState_Buffer = true;
break;
case AnimateMode_BUFFER:
this.AnimateHelpState_Wait = false;
this.AnimateHelpState_NoFazeMe = false;
this.AnimateHelpState_Buffer = true;
break;
case AnimateMode_NOMPLAY:
this.AnimateHelpState_Wait = false;
this.AnimateHelpState_NoFazeMe = false;
this.AnimateHelpState_Buffer = false;
break;
default:
break;
}
}
//缓冲次数,0表示缓冲完当前动画
public void setBufferTimes(int bufferTimes)
{
this.AnimateHelpState_BfferTimes = bufferTimes;
}
//设置贞播放间隔
public void setAnimWait(int animWait)
{
this.animWait = animWait;
}
//返回是否免打扰设置
public boolean getNotFazeMe()
{
return this.AnimateHelpState_NoFazeMe;
}
//根据当前的x,y位置更新边界盒
public void updateBounds()
{
//确保知道actor的正确宽度和高度以及偏移量
if(this.posWidth <= 0 && currAnimation != null)
{
this.posWidth = currAnimation.getPosWidth();
}
if(this.posHeight <= 0 && currAnimation != null)
{
posHeight = currAnimation.getPosHeight();
}
bounds.setRect(pos.getX(),pos.getY(),this.posWidth,this.posHeight);
if(currAnimation != null)
{
this.excursion.setX(currAnimation.getExcrusionx());
}
if(currAnimation != null)
{
this.excursion.setY(currAnimation.getExcrusiony());
}
}
//使用他自身的变换来绘制actor
public void paint(Graphics2D g2d)
{
if(currAnimation != null)
{
g2d.drawImage(this.currAnimation.getCurrFrame(currAnimator),
xform,AnimationStrip.observer);
}
}
//在(x,y)坐标处绘制actor
public void paint(Graphics2D g2d,double x,double y)
{
if(currAnimation != null)
{
g2d.drawImage(this.currAnimation.getCurrFrame(currAnimator),
AffineTransform.getTranslateInstance(x,y),AnimationStrip.observer);
}
}
//实现接口Moveable接口中的方法
public Rectangle2D getBounds()
{
return this.bounds;
}
public boolean collidesWith(Moveable other)
{
return (bounds.contains(other.getBounds()) ||
bounds.intersects(other.getBounds()));
}
public boolean collidesWith(Rectangle2D other)
{
return (bounds.contains(other) ||
bounds.intersects(other));
}
public static boolean collidesWith(Moveable m1,Moveable m2)
{
return (m1.getBounds().contains(m2.getBounds()) ||
m1.getBounds().intersects(m2.getBounds()));
}
public void addCollision(Moveable other)
{
if(collisionList == null)
{
collisionList = new LinkedList();
collisionList.add(other);
return;
}
if(!collisionList.contains(other))
{
collisionList.add(other);
}
}
//this method is left empty, but not abstract
public void processCollisions()
{
}
//请重写此方法
public void update()
{
if(animate())
{
updateBounds();
checkBounds();
//把当前位置写到变换里
xform.setToTranslation(pos.getX()+excursion.getX(),pos.getY()+excursion.getY());
}
}
/************************************************
*确保actor的边界没有超出actor2DGorup所限定的边界
*子类应该根据自己的需要来重写这个方法来检测冲突
************************************************/
public void checkBounds()
{
if(group == null) return;
if(bounds.getX() < group.MIN_X_POS)
pos.setX(group.MIN_X_POS);
else if(bounds.getX() + posWidth > group.MAX_X_POS)
pos.setX(group.MAX_X_POS - posWidth);
if(bounds.getY() < group.MIN_Y_POS)
pos.setY(group.MIN_Y_POS);
else if(bounds.getY() + posHeight > group.MAX_Y_POS)
pos.setY(group.MAX_Y_POS - posHeight);
}
//返回当前角色所属的组(Actor2DGroup)
public Actor2DGroup getGroup()
{
return this.group;
}
//当前动画的访问
public void setCurrAnimation(AnimationStrip curr)
{
this.currAnimation = curr;
this.currAnimator = this.currAnimation.createNewAnimator();
}
public AnimationStrip getCurrAnimation()
{
return currAnimation;
}
//把传入的值和当前的状态值进行位操作
//设置初始值
public final void setState(int attr)
{
state |= attr;
}
//去除指定状态
public final void resetState(int attr)
{
state &= ~attr;
}
public final int getState()
{
return state;
}
public final void clearState()
{
state = 0;
}
//判断所传入的状态属性是否被acror的属性所包含
public final boolean hasState(int attr)
{
return ((state & attr) != 0);
}
//actor的速度,位置和的访问方法
public final void setVel(int x,int y)
{
this.vel.setX(x);
this.vel.setY(y);
}
public final Vector2D getVel()
{
return this.vel;
}
public final void setX(double px)
{
pos.setX(px);
}
public final void setY(double py)
{
pos.setY(py);
}
public final int getX()
{
return (int)pos.getX();
}
public final int getY()
{
return (int)pos.getY();
}
public final void setPos(int x,int y)
{
pos.setX(x);
pos.setY(y);
}
public final void setPos(double x,double y)
{
pos.setX(x);
pos.setY(y);
}
public final void setPos(Vector2D v)
{
pos.setX(v.getX());
pos.setY(v.getY());
}
public final Vector2D getPos()
{
return pos;
}
//移动
public final void moveBy(int x,int y)
{
pos.translate(x,y);
}
public final void moveBy(Vector2D vel)
{
pos.translate(vel);
}
//简单边界盒,判断actor是否与传入的actor冲突
public boolean intersects(Actor2D other)
{
return bounds.intersects(other.getBounds());
}
}//Actor2D
/*****************************************************************
*****************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -