注:本系列教程全部翻译完之后可能会以PDF的形式发布。
如果有什么错误可以到http://blog.csdn.net/kakashi8841留言或EMAIL:[email protected]给我。
jME版本 :jME_2.0.1_Stable
开发工具:MyEclipse8.5
操作系统:Window7/Vista
在这个向导,我将首次为玩家增加夺取flag数目的统计。那么我们将移除flag的计时随机位置,取代的是,我们将增加检查去看看玩家的vehicle是否“夺取”了Flag。
首先,增加一个新的字段给Vehicle
private int flagsGrabbed;
增加getter和setter方法
public int getFlagsGrabbed() {
return flagsGrabbed;
}
public void setFlagsGrabbed(int flagsGrabbed) {
this.flagsGrabbed = flagsGrabbed;
}
为了移除Flag计时,我们停止更新,注释Flag的update。
// flag.update(interpolation);
我们首先通过增加一个新字段决定了玩家能在多远获取一面flag。
//获取距离
private float grabDistanceSquared = 64f;
我们这里使用的方法将在每次游戏update时检查Flag和Vehicle的距离。直接在游戏的update中加入:
//首先获取Flag和player的距离
float distanceSquared =
player.getLocalTranslation().distanceSquared(
flag.getLocalTranslation()
);
如果vehicle和flag足够接近,我们将获取它并重设flag位置。
//检查能否获取flag
if(distanceSquared <= grabDistanceSquared){
//重设flag,如果reset不能使用
//请到Flag.java里面将reset方法改为public
flag.reset();
player.setFlagsGrabbed(player.getFlagsGrabbed()+1);
}
import com.jme.math.FastMath;
import com.jme.math.Quaternion;
import com.jme.math.Vector3f;
import com.jme.scene.Node;
import com.jme.scene.Spatial;
/**
* Vehicle将会是一个node,处理了vehicle在游戏中的移动。
* 它拥有定义它的加速度acceleration、速度velocity
* 和减速度barking的参数。
* 转向速度turnSpeed定义了它有怎样的处理。
* 而重量weight定义了漂移时的摩擦力,它下降多快等等。
* @author Mark Powell
*/
public class Vehicle extends Node {
private Spatial model;
private float velocity;
private float maxSpeed = 30;
private float minSpeed = 10;
private float acceleration;
private float braking;
private float turnSpeed;
private float weight;
private Vector3f tempVa;
private int lean;
private float leanAngle;
private static final float LEAN_BUFFER = 0.05f;
private Vector3f leanAxis = new Vector3f(0,0,1);
private Quaternion q = new Quaternion();
private int flagsGrabbed;
public int getFlagsGrabbed() {
return flagsGrabbed;
}
public void setFlagsGrabbed(int flagsGrabbed) {
this.flagsGrabbed = flagsGrabbed;
}
private Spatial backwheel,frontwheel;
public Spatial getFrontwheel() {
return frontwheel;
}
public void setFrontwheel(Spatial frontwheel) {
this.frontwheel = frontwheel;
}
public Spatial getBackwheel() {
return backwheel;
}
public void setBackwheel(Spatial backwheel) {
this.backwheel = backwheel;
}
private float angle;
private Quaternion rotQuat = new Quaternion();
private Vector3f wheelAxis = new Vector3f(0, 1, 0);
/**
* 基础构造方法,获取模型作为vehicle的外观
* @param id vehicle的id
* @param model 表达vehicle绘图外观的模型
*/
public Vehicle(String id, Spatial model){
super(id);
setModel(model);
}
/**
* 构造方法,获取模型作为vehicle的外观
* @param id vehicle的id
* @param model 表达vehicle绘图外观的模型
* @param maxSpeed vehicle能达到的最大速度(Unit/Sec)
* @param minSpeed vehicle的反向最大速度(Unit/Sec)
* @param accerlation vehicle多快能达到最大速度
* @param braking vehicle减速的速度以及按多久反向
* @param weight vehicle的重量
* @param turnSpeed vehicle转向转得多块
*/
public Vehicle(String id,Spatial model,
float maxSpeed, float minSpeed,
float accerlation, float braking,
float weight, float turnSpeed){
super(id);
setModel(model);
this.maxSpeed = maxSpeed;
this.minSpeed = minSpeed;
this.acceleration = acceleration;
this.braking = braking;
this.weight = weight;
this.turnSpeed = turnSpeed;
}
public Spatial getModel() {
return model;
}
public void setModel(Spatial model) {
this.detachChild(this.model);
this.model = model;
this.attachChild(this.model);
//获取前轮和后轮的引用
backwheel = ((Node)model).getChild("backwheel");
frontwheel = ((Node)model).getChild("frontwheel");
}
public float getVelocity() {
return velocity;
}
public void setVelocity(float velocity) {
this.velocity = velocity;
}
public float getMaxSpeed() {
return maxSpeed;
}
public void setMaxSpeed(float maxSpeed) {
this.maxSpeed = maxSpeed;
}
public float getMinSpeed() {
return minSpeed;
}
public void setMinSpeed(float minSpeed) {
this.minSpeed = minSpeed;
}
public float getAcceleration() {
return acceleration;
}
public void setAcceleration(float acceleration) {
this.acceleration = acceleration;
}
public float getBraking() {
return braking;
}
public void setBraking(float braking) {
this.braking = braking;
}
public float getTurnSpeed() {
return turnSpeed;
}
public void setTurnSpeed(float turnSpeed) {
this.turnSpeed = turnSpeed;
}
public float getWeight() {
return weight;
}
public void setWeight(float weight) {
this.weight = weight;
}
public void accerate(float time){
velocity = (velocity+=acceleration*time)
> maxSpeed ? maxSpeed : velocity;
}
public void brake(float time){
velocity = (velocity-=braking*time)
< -minSpeed ? -minSpeed : velocity;
}
public void drift(float time) {
if(velocity < -FastMath.FLT_EPSILON) {
velocity += ((weight/5) * time);
//我们将漂移到停止,所以不能超过0
velocity = velocity > 0 ? 0 : velocity;
} else if(velocity > FastMath.FLT_EPSILON){
velocity -= ((weight/5) * time);
//我们将漂移到停止,所以不能低于0
velocity = velocity < 0 ? 0 : velocity;
}
}
public void update(float time){
this.localTranslation.addLocal(
this.localRotation.getRotationColumn(2, tempVa)
.mult(velocity*time)
);
rotateWheels(time);
processLean(time);
}
public void setRotateOn(int modifier) {
lean = modifier;
}
/**
* processlean将基于一个lean因素调整bike模型的角度。
* 我们调整bike而不是Vehicle,
* 因为Vehicle关心的是bike在terrain上的位置
* @param time the time between frames
*/
private void processLean(float time) {
//查查我们是否需要倾斜
if(lean != 0) {
if(lean == -1 && leanAngle < 0) {
leanAngle += -lean * 4 * time;
} else if(lean == 1 && leanAngle > 0) {
leanAngle += -lean * 4 * time;
} else {
leanAngle += -lean * 2 * time;
}
//最大倾斜为-1到1
if(leanAngle > 1) {
leanAngle = 1;
} else if(leanAngle < -1) {
leanAngle = -1;
}
} else { //我们不需要倾斜,让它正直
if(leanAngle < LEAN_BUFFER && leanAngle > -LEAN_BUFFER) {
leanAngle = 0;
}
else if(leanAngle < -FastMath.FLT_EPSILON) {
leanAngle += time * 4;
} else if(leanAngle > FastMath.FLT_EPSILON) {
leanAngle -= time * 4;
} else {
leanAngle = 0;
}
}
q.fromAngleAxis(leanAngle, leanAxis);
model.setLocalRotation(q);
lean = 0;
}
private void rotateWheels(float time){
//当vehicle移动的时候旋转轮子
if(vehicleIsMoving()){
//前进
if(velocity > FastMath.FLT_EPSILON){
angle = angle - ((time) * velocity * 0.5f);
if (angle < -360) {
angle += 360;
}
}else{
angle = angle + ((time) * velocity * .5f);
if(angle > 360){
angle -= 360;
}
}
rotQuat.fromAngleAxis(angle, wheelAxis);
frontwheel.getLocalRotation().multLocal(rotQuat);
backwheel.setLocalRotation(frontwheel.getLocalRotation());
}
}
/**
* 用于判断vehicle是否移动的便利方法。
* 当速度velocity接近0时为真。
* @return true 当vehicle正在移动,否则为false
*/
private boolean vehicleIsMoving() {
return velocity > FastMath.FLT_EPSILON ||
velocity < -FastMath.FLT_EPSILON;
}
}