From Gossip@caterpillar

Computer Graphics: 迷宮(斜角地圖實例)

 

 


這個程式就不多作解釋了,所有的觀念前面都講過了,繪圖時使用迴圈走訪陣列,所以深度問題也自然獲得解決,連結 看看效果。
  • Map45Rotate.java
package onlyfun.caterpillar.graphics.animation;

import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JApplet;

public class Map45Rotate extends JApplet
implements KeyListener {
private Image offScreen, lawnImage;
private Image block, floor, character2;

// 1: Wall 2: Penguin
private int[][]
maze = {{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},
{0,0,0,0,0,1,0,0,1,0,0,1,1,0,0,1},
{1,0,1,0,1,0,0,0,1,0,1,0,0,0,1,1},
{1,0,0,0,0,1,0,1,1,0,1,0,1,0,0,1},
{1,1,0,0,0,0,0,0,0,0,0,0,1,1,1,1},
{1,1,0,1,0,1,1,0,1,1,0,0,1,0,1,1},
{1,1,0,0,0,0,1,0,0,1,0,0,0,0,1,1},
{1,1,0,0,1,0,1,1,1,1,0,1,0,0,1,1},
{1,1,1,1,1,0,0,0,1,1,0,0,0,0,1,1},
{1,0,0,0,0,0,0,0,1,0,0,1,1,0,1,1},
{1,0,1,0,1,0,0,0,1,0,1,0,0,0,1,1},
{1,1,1,0,0,0,1,1,1,0,1,0,1,1,1,1},
{1,0,0,0,1,0,0,0,1,1,0,0,0,0,0,1},
{1,0,0,0,1,0,0,0,1,1,0,0,0,0,0,1},
{1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0},
{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};

private SpriteAndMaze spriteAndMaze;

private int halfWidth, halfHeight;
private int startX, startY;
private int characterImageX;

private Graphics offScreenGraphics;

public void init() {
addKeyListener(this);

setBackground(Color.white);

//取得影像
MediaTracker mediaTracker = new MediaTracker(this);
floor = getImage(getDocumentBase(),"floor.gif");
block = getImage(getDocumentBase(),"block3.gif");
character2 =
getImage(getDocumentBase(),"character2.gif");
mediaTracker.addImage(floor,0);
mediaTracker.addImage(block,0);
mediaTracker.addImage(character2,0);

try {
showStatus("影像載入中(Loading Images)...");
mediaTracker.waitForAll();
}
catch(InterruptedException e){
e.printStackTrace();
}

int appletWidth = getSize().width;
int appletHeight = getSize().height;

//建立次畫面
lawnImage = createImage(appletWidth, appletHeight);
Graphics lawnGraphics = lawnImage.getGraphics();

offScreen = createImage(appletWidth, appletHeight);
offScreenGraphics = offScreen.getGraphics();

halfWidth = floor.getWidth(this) / 2;
halfHeight = floor.getHeight(this) / 2;

startX = appletWidth / 2;
startY = appletHeight / 8;

// 繪製地板
for(int j = 0; j < maze.length; j++) {
for(int i = 0; i < maze[0].length; i++) {
int x = startX - i*halfWidth + j*halfWidth;
int y = startY + i*halfHeight + j*halfHeight;
lawnGraphics.drawImage(floor, x, y,this);
}
}

spriteAndMaze = new SpriteAndMaze(0, 1, maze);

Thread thread = new Thread(new Runnable() {
public void run() {
while(true) {
repaint();
// 人物走動動畫
characterImageX += 50;
if(characterImageX >= 300)
characterImageX = 0;
try {
Thread.sleep(250);
}
catch(InterruptedException e) {
e.printStackTrace();
}
}
}
});
thread.start();
}

public void update(Graphics g) {
paint(g);
}

public void paint(Graphics g) {
offScreenGraphics.drawImage(lawnImage, 0, 0, this);

// 繪製牆與人物
for(int j = 0; j < maze.length; j++) {
for(int i = 0; i < maze[0].length; i++) {
int x = startX - i*halfWidth + j*halfWidth;
int y = startY - 10 + i*halfHeight +
j*halfHeight;

if(maze[i][j] == 1) {
offScreenGraphics.drawImage(block, x,
y,this);
}

if(spriteAndMaze.getLocationX() == j &&
spriteAndMaze.getLocationY() == i) {
offScreenGraphics.drawImage(character2,
x, y, x + 25, y + 25,
characterImageX, 0,
characterImageX + 50, 50, this);
}
}
}
//將次畫面貼到主畫面中
g.drawImage(offScreen,0,0,this);
}

//=====實作KeyListener介面 =====

public void keyTyped(KeyEvent e) { }

public void keyPressed(KeyEvent e) {
int key = e.getKeyCode();

switch(key) {
case KeyEvent.VK_RIGHT:
spriteAndMaze.moveUp();
break;
case KeyEvent.VK_LEFT:
spriteAndMaze.moveDown();
break;
case KeyEvent.VK_UP:
spriteAndMaze.moveLeft();
break;
case KeyEvent.VK_DOWN:
spriteAndMaze.moveRight();
break;
}

repaint();
}

public void keyReleased(KeyEvent e) {}
}

class SpriteAndMaze {
private int i, j;
private int maze[][];

public SpriteAndMaze() {}

public SpriteAndMaze(int x, int y) {
this.i = y;
this.j = x;
}

public SpriteAndMaze(int x, int y, int[][] maze) {
this(x, y);
this.maze = maze;
}

public void moveUp() {
if(isMovable(i-1, j)) {
i--;
}
}

public void moveDown() {
if(isMovable(i+1, j)) {
i++;
}
}

public void moveRight() {
if(isMovable(i, j+1)) {
j++;
}
}

public void moveLeft() {
if(isMovable(i, j-1)) {
j--;
}
}

private boolean isMovable(int i, int j) {
if(i < 0 || j < 0 || j >= maze[0].length ||
i >=maze.length)
return false;

if(maze[i][j] == 0)
return true;
else
return false;
}

public int getLocationX() {
return j;
}
public int getLocationY() {
return i;
}
public void setLocationX(int locationX) {
this.j = locationX;
}
public void setLocationY(int locationY) {
this.i= locationY;
}
public int[][] getMaze() {
return maze;
}
public void setMaze(int[][] maze) {
this.maze = maze;
}
}