⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nokia3d.java

📁 怎样做一个手机游戏上面有很多经验之谈
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
import javax.microedition.lcdui.*;
import javax.microedition.midlet.*;
import javax.microedition.m3g.*;
import java.util.*;

public class Nokia3D extends Canvas
{
	// Debug output flag
	private static final boolean DEBUG = false;

	// Graphics3d context
    private Graphics3D		g3d;

	// Random generator
	private	Random			m_random = new Random();

	// Some flags
	private boolean			m_tunnelFadeOut = false;
	private boolean			m_fogOn = false;
	private float			m_lightIntensity = 1.0f;
	private GameMIDlet		m_midlet;

	// Nokia scene params
	private	static final int SCENE_NOKIA_LENGTH = 33000;
	private	static final int SCENE_NOKIA_HIDEBUG = 22000;

	// Snowflake count
	private static final int NUM_SNOWFLAKES = 20;
	private static final float SNOWFLAKE_SCALE = 6f;
	private static final float GROUND_LEVEL = 0f;

	// Bug scene length in ms
	private	static final int SCENE_BUG_LENGTH = 6700;

	// The tunnel scene length
	private	static final int SCENE_TUNNEL_LENGTH = 3000;

	// Current scene index
	private int				m_currentScene;

	// Number of scenes
	private static final int SCENE_COUNT = 5;

	// Scene indices
	private static final int SCENE_NOKIA = 0;
	private static final int SCENE_BUG = 1;
	private static final int SCENE_TUNNEL = 2;
	private static final int SCENE_POND = 3;
	private static final int SCENE_LOWPOLY = 4;

	// User IDs for the ant polygon image
	private static final int UID_NOKIA_ANTIMAGE = 47364324;

	// Items in the tunnel scene..
	private static final int UID_TUNNEL_MESH = 116237701;
	private static final int UID_TUNNEL_CAMERA = 457572229;
	private static final int UID_TUNNEL_LIGHT = 131143914;

	// For the pond scene
	private static final int UID_POND_CAMERA1 = 653251478;
	private static final int UID_POND_CAMERA2 = 124296655;
	private static final int UID_POND_CAMERA3 = 901844788;
	private static final int UID_POND_CAMERA4 = 468090727;
	private static final int UID_POND_ANTHEAD = 296699498;

	// Fov value for pond scenes
	private float[]		m_cameraFOVs = {35, 25, 30, 30};
	private int			m_currentCamera = 0;

	// Switches for the tunnel
	private static final int NO_TEXTURE = 0;
	private static final int ONE_TEXTURE = 1;
	private static final int DUAL_TEXTURE = 2;
	private static final int TOGGLE_FOG = 3;

	// We load .m3g scenes here
	private World[]		m_scenes;

	// Time counter
	private int 		m_currentTime;

	// Time in millisecs
	private long		m_lastFrame;
	private int			m_deltaTime;

	//
	public Nokia3D( GameMIDlet m )
	{
		m_midlet = m;
	}

	//
	public void startApp(boolean b)
	{
       	// Create a new 3D graphics context
        g3d = Graphics3D.getInstance();

		try
		{
			// Allocate some scenes
			m_scenes = new World[SCENE_COUNT];

			// Load the nokia scene
			m_scenes[SCENE_NOKIA] = loadScene("/nokia_on_ice.m3g");
			preInitNokiaScene();

			// Start from the first scene
			m_currentScene = SCENE_NOKIA;
			m_currentTime = 0;
		}
		catch (Exception e)
		{
			e.printStackTrace();
		}

		//
		if (DEBUG)
			System.out.println("Loaded");
	}

	// Loads a scene with given name
	private World loadScene(String name)
	{
		long mem = Runtime.getRuntime().freeMemory();
		Object3D[] o = null;
		try
		{
			o = Loader.load(name);
		} catch (java.lang.OutOfMemoryError e) {
			System.err.println("Not enough memory.\nUse '-heapsize 1M' to increse heap size.");
			m_midlet.destroyApp( true );
		} catch (Exception e) {
			e.printStackTrace();
		}

		long memNow = mem - Runtime.getRuntime().freeMemory();

		if (DEBUG)
		{
			System.out.println("Scene took " + memNow + " bytes..");
			// Show free mem
			showMemory();
		}

		return (World) o[0];
	}

	public void executeOnce()
	{
		Display display = Display.getDisplay( m_midlet );
		if ( display.getCurrent() == this )
		{
			long frm = System.currentTimeMillis();

			// make sure we don't do a huge skip on the first frame
			if (m_lastFrame == 0)
			{
				m_deltaTime = 0;
			}
			else
			{
				m_deltaTime = (int) (frm - m_lastFrame);
			}

			m_lastFrame = frm;
			repaint();
			serviceRepaints();
		}
	}

	//
	protected void keyPressed( int keyCode )
	{
		int gameAction = getGameAction( keyCode );

		if (m_currentScene == SCENE_TUNNEL)
		{
			if (keyCode == Canvas.KEY_NUM1)
			{
				switchTunnelMode(NO_TEXTURE);
			}
			else
			if (keyCode == Canvas.KEY_NUM2)
			{
				switchTunnelMode(ONE_TEXTURE);
			}
			else
			if (keyCode == Canvas.KEY_NUM3)
			{
				switchTunnelMode(DUAL_TEXTURE);
			}
			else
			if (keyCode == Canvas.KEY_NUM4)
			{
				switchTunnelMode(TOGGLE_FOG);
			}
			else
			if (keyCode == Canvas.KEY_NUM5)
			{
				m_tunnelFadeOut = true;
			}
		}

		if (m_currentScene == SCENE_POND)
		{
			// Find the pond scene..
			World pond = m_scenes[SCENE_POND];
	
			// Switch active cameras		
			if (keyCode == Canvas.KEY_NUM1)
			{
				Camera c = (Camera) pond.find(UID_POND_CAMERA1);
				pond.setActiveCamera(c);
				m_currentCamera = 0;
			}
			else
			if (keyCode == Canvas.KEY_NUM2)
			{
				Camera c = (Camera) pond.find(UID_POND_CAMERA2);
				pond.setActiveCamera(c);
				m_currentCamera = 1;
			}
			else
			if (keyCode == Canvas.KEY_NUM3)
			{
				Camera c = (Camera) pond.find(UID_POND_CAMERA3);
				pond.setActiveCamera(c);
				m_currentCamera = 2;
			}
			else
			if (keyCode == Canvas.KEY_NUM4)
			{
				Camera c = (Camera) pond.find(UID_POND_CAMERA4);
				pond.setActiveCamera(c);
				m_currentCamera = 3;
			}
			else
			// Adjust current FOV factor
			if (gameAction == Canvas.UP)
			{
				float fo = m_cameraFOVs[m_currentCamera];
				if (fo > 15)
					fo-=5;
				m_cameraFOVs[m_currentCamera] = fo;
				// Set the field-of-view
				Camera c = pond.getActiveCamera();
				c.setPerspective(fo, 1.0f, 0.1f,5);
			}
			else
			if (gameAction == Canvas.DOWN)
			{
				float fo = m_cameraFOVs[m_currentCamera];
				if (fo < 45)
					fo+=5;
				m_cameraFOVs[m_currentCamera] = fo;
				// Set the field-of-view
				Camera c = pond.getActiveCamera();
				c.setPerspective(fo, 1.0f, 0.1f,5);
			}
		}

		if (keyCode == Canvas.KEY_NUM0)
		{
			m_midlet.destroyApp( true );
		}
	}

	// Do something..
	public void paint( Graphics g )
	{
        int w = getWidth();
        int h = getHeight();

		// if we don't have a g3d context, fill screen with red color
        if (g3d == null)
		{
			g.setClip(0,0, w,h);
			g.setColor(100,10,15);
			g.fillRect(0,0, w,h);
            return;
        }

		//
		int delta = m_deltaTime * 3/4;

		// update demo
		updateDemo(m_currentTime, delta);

		// bind to graphics
		g3d.bindTarget(g);

		try
		{
			// get currently displayed scene
			World scn = m_scenes[m_currentScene];
			scn.animate(m_currentTime);
	
			// do something after animation
			postAnimate();
	
	        g3d.render(scn);
			scn = null;
		}
		finally
		{
			// release g3d
	        g3d.releaseTarget();
		}

		// update timer by delta value
        m_currentTime+=delta;
	}

	// updates the demo
	private void updateDemo(int time, int delta)
	{
		if (m_currentScene == SCENE_NOKIA)
		{
			updateNokiaScene(time);
		}
		else
		if (m_currentScene == SCENE_BUG)
		{
			updateBugScene(time);
		}
		else
		if (m_currentScene == SCENE_TUNNEL)
		{
			updateTunnelScene(time, delta);
		}
	}

	// does some post-animate() tasks
	private void postAnimate()
	{
		/** target the current camera's group to ant's head */
		if (m_currentScene == SCENE_POND)
		{
			World scn = m_scenes[m_currentScene];
			Node camGroup = scn.getActiveCamera().getParent();
			camGroup.align(null);
		}
	}

	// Frees the old scene (destroys it's references) and frees up mem
	private void freeOldScene()
	{
		// Get mem
		long mem = Runtime.getRuntime().freeMemory();

		// Null any references we stored when setting up the scene
		removeSnowFlakes();
		removeTunnelScene();

		// Null the current scene reference
		// This is now the only stored reference to a node in the scene,
		// so this should allow the whole scene (including all its childen)
		// to be garbage collected.
		m_scenes[m_currentScene] = null;

		// try to free some memory...
		System.gc();

		// Show how much we actually freed
		if (DEBUG)
		{
			long memNow = Runtime.getRuntime().freeMemory() - mem;
			System.out.println("Freed " + memNow + " bytes ...");
			// Show free mem
			showMemory();
		}
	}

	//
	private void showMemory()
	{
		if (DEBUG)
			System.out.println("Memory available : " + Runtime.getRuntime().freeMemory() + " / " + Runtime.getRuntime().totalMemory());
	}

	//
	private void preInitNokiaScene()
	{
		// Search the node with the 2d bug image and hide it for now..
		World nokia = m_scenes[SCENE_NOKIA];
		Mesh m = (Mesh) nokia.find(UID_NOKIA_ANTIMAGE);
		m.setRenderingEnable(false);

		// Add some snowflakes to the scene
		initSnowFlakes();
	}

	//
	private boolean showBug = false;
	private void updateNokiaScene(int time)
	{
		// Do not show the bug node before certain time has been reached..
		if (time > SCENE_NOKIA_HIDEBUG && !showBug)
		{
			// Search the image node & display it
			World nokia = m_scenes[SCENE_NOKIA];
			Mesh m = (Mesh) nokia.find(UID_NOKIA_ANTIMAGE);
			m.setRenderingEnable(true);
			// Show the lil' fellah :)
			showBug = true;
		}

		// Animate the snowflakes..
		animateSnowFlakes(time);

		// Switch to bug scene when
		if (time > SCENE_NOKIA_LENGTH)
		{
			//
			freeOldScene();

			// Load the bug scene
			m_scenes[SCENE_BUG] = loadScene("/otokka_jump2.m3g");

			//
			m_currentScene = SCENE_BUG;
			m_currentTime = 0;
		}
	}

	//
	private void updateBugScene(int time)
	{
		// Switch to bug scene when
		if (time > SCENE_BUG_LENGTH)
		{
			//
			freeOldScene();

			// Load the pond scene
			m_scenes[SCENE_TUNNEL] = loadScene("/tunnel.m3g");
			preInitTunnelScene();

			//
			m_currentScene = SCENE_TUNNEL;
			m_currentTime = 0;
		}
	}

	//
	private void preInitTunnelScene()
	{
		/** Select the world... */
		World w = m_scenes[SCENE_TUNNEL];

		// Find the tunnel mesh
		Mesh tnl = (Mesh) w.find(UID_TUNNEL_MESH);

		// Get the appearance from the mesh
		Appearance ap = tnl.getAppearance(0);

		// Get the vertex buffer for the tunnel mesh

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -