package org.ourunix.android.jpctmd2demo;
import java.io.IOException;
import java.io.InputStream;
import javax.microedition.khronos.egl.EGLConfig;
import javax.microedition.khronos.opengles.GL10;
import org.ourunix.android.R;
import org.ourunix.android.RenderBase;
import android.content.Context;
import android.content.res.AssetManager;
import android.content.res.Resources;
import android.graphics.BitmapFactory;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import com.threed.jpct.Camera;
import com.threed.jpct.FrameBuffer;
import com.threed.jpct.Loader;
import com.threed.jpct.Object3D;
import com.threed.jpct.RGBColor;
import com.threed.jpct.Texture;
import com.threed.jpct.TextureManager;
import com.threed.jpct.World;
public class GLRenderer extends RenderBase {
public Context context;
// jpct需要准备下述对象实例,虚拟世界、Framebuffer、3D对象、纹理等
private World world;
private FrameBuffer fb;
private Object3D soilder;
private String[] texturesName = {"snork"};
private float scale = 0.8f;
// 行走动画 相关参数
private int an = 2;
private float ind = 0;
public GLRenderer(Context ctx){
super(ctx);
context = ctx;
}
@Override
public void onDrawFrame(GL10 gl) {
// TODO Auto-generated method stub
doAnim();
// 用颜色清除FrameBuffer
fb.clear(RGBColor.BLACK);
// 变换和灯光所有多边形
world.renderScene(fb);
// 绘制
world.draw(fb);
//显示
fb.display();
}
/**
* 实现动画的代码
* */
private void doAnim() {
// TODO Auto-generated method stub
//每一帧加0.018f
ind += 0.018f;
if (ind > 1f) {
ind -= 1f;
}
// 关于此处的两个变量,ind的值为0-1(jpct-ae规定),0表示第一帧,1为最后一帧;
//至于an这个变量,它的意思是sub-sequence如果在keyframe(3ds中),因为在一个
//完整的动画包含了seq和sub-sequence,所以设置为2表示执行sub-sequence的动画,
//但这里设置为2我就不太明白了,不过如果不填,效果会不自然,所以我就先暂时把它
//设置为2
soilder.animate(ind, an);
}
float downX = 0;
float downY = 0;
float upX = 0;
float upY = 0;
@Override
public boolean onTouch(View v, MotionEvent event) {
return super.onTouch(v, event);
}
@Override
public void rightSwipe() {
soilder.rotateY(-5);
super.rightSwipe();
}
@Override
public void leftSwipe() {
soilder.rotateY(5);
super.leftSwipe();
}
@Override
public boolean handleTouchEvent(MotionEvent event) {
int action = event.getAction();
switch (action) {
case MotionEvent.ACTION_DOWN:
downX = event.getX();
downY = event.getY();
break;
case MotionEvent.ACTION_MOVE:
upX = event.getX();
upY = event.getY();
float deltaX = downX - upX;
float deltaY = downY - upY;
// swipe horizontal?
if(Math.abs(deltaX) > SWIPE_MIN_DISTANCE){
// left or right
if(deltaX < 0) { rightSwipe(); }
if(deltaX > 0) { leftSwipe(); }
}
else {
Log.i("", "Swipe was only " + Math.abs(deltaX) + " long, need at least " + SWIPE_MIN_DISTANCE);
return false; // We don't consume the event
}
// swipe vertical?
if(Math.abs(deltaY) > SWIPE_MIN_DISTANCE){
// top or down
if(deltaY < 0) { downSwipe(); }
if(deltaY > 0) { upSwipe();}
}
else {
Log.i("", "Swipe was only " + Math.abs(deltaX) + " long, need at least " + SWIPE_MIN_DISTANCE);
return false; // We don't consume the event
}
break;
case MotionEvent.ACTION_UP:break;
case MotionEvent.ACTION_CANCEL:break;
}
return super.handleTouchEvent(event);
}
@Override
public void onSurfaceChanged(GL10 gl, int width, int height) {
// TODO Auto-generated method stub
// 如果FrameBuffer不为NULL,释放fb所占资源
if (fb != null){
fb.dispose();
}
fb = new FrameBuffer(gl, width, height);
}
@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
//载入Assets文件夹下的文件
new LoadAssets(context.getResources());
// TODO Auto-generated method stub
//实例化虚拟世界
world = new World();
//设置了环境光源强度。负:整个场景会变暗;正:将照亮了一切。
world.setAmbientLight(150, 150, 150);
TextureManager tm = TextureManager.getInstance();
Texture texture2 = new Texture(BitmapFactory.decodeResource(context.getResources(), R.raw.soilder));
tm.addTexture(texturesName[0], texture2);
// 从assets文件夹中读取soilder.md2文件来实例化Object3D snork
soilder = Loader.loadMD2(LoadAssets.loadf("soilder.md2"), scale);
// 旋转soilder对象到"适当位置"
soilder.translate(0, 0, -50);
//这才是将纹理添加进去
soilder.setTexture(texturesName[0]);
// 释放部分资源
soilder.strip();
// 编译
soilder.build();
// 将snork添加到World对象中
world.addObject(soilder);
//获得Camera
Camera cam = world.getCamera();
cam.setPosition(0, 0, -100);
cam.lookAt(soilder.getTransformedCenter());
}
}
//加载assets类
class LoadAssets {
public static Resources res;
public LoadAssets(Resources resources) {
res = resources;
}
public static InputStream loadf(String fileName) {
AssetManager am = res.getAssets();
try {
return am.open(fileName, AssetManager.ACCESS_UNKNOWN);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
return null;
}
}
}