天天看點

Java中2.5D遊戲(斜45度角)的設計與實作(2)

上次我已說過Java實作2.5D的關鍵在于斜視圖坐标的轉化,隻要“你的美工”或者“你——的美工”技術到位,2D到2.5D的圖形就簡單實作來說就已 經足夠了(暫不考慮日照及雲霧等特殊效果)。但反過來說,2.5D界面也确實對美工有了一定的要求,如果沒有好的原圖,2.5D程式實作起來将事倍功半, 枉費氣力不說,還達不到應有的效果。

而遺憾的是,對于我這種非遊戲開發人員來說,遊戲美工簡直不可求更不可遇,而我搜遍google,卻 也找不到多少2.5D地圖可供使用(我想找皇家騎士團或最終幻想戰略版那種地圖,居然沒有現成的……準備過兩天重下遊戲自己摳圖……)。于是我怒從胸中 起,惡向膽邊行,将一種更加極端的方法付諸于實踐……

我所謂更加極端的方法,就是利用看上去向2.5D的2D程式蒙混過關——也就是所謂的“僞2.5D實作”

我們可以看到,在此例中角色及建築始終由X,Y交織點确定,即采取通常的2D算法實作。

但我們都知道,3D或2D本質上差別隻是視覺上的,反映到螢幕上的無外是分辨率不等的象素罷了。如果我們直接将做好的2D地圖放入其中,能否起到想要的作用呢?

我們來試試看,首先,我載入一個做好的2.5D地圖(取材自幻想三國,原圖大小2675X930,我以800X600卷簾顯示)

我們可以看到,由于采用了2.5D的視覺圖,單就畫面而言,通常沒有人會懷疑所見到的是“斜45度立體視圖”。

這時候有兩種殊途同歸的方式可供選擇:一是利用ps等工具,在斜視圖上生成镂空圖,利用樓空圖生成map數組來演算此斜視圖。二是直接利用編輯器等工具在斜視圖上标注通行區域,以此生成數組。

我并沒有開發專用的編輯器,是以利用ps制作镂空圖如下(原圖于斜視圖大小一緻,為示範用縮小):

其中我将黑色設定為禁行區域,白色為通行區域,而生成一個二維的整形數組,代表map的所有x,y點

将字元列印成地圖如下(部分)

此時,我們就可以利用地圖數組在斜視圖上描繪出對應的x,y點。

于通常的2D地圖相同,坐标由左上x,y點開始,到右下x,y點結束,描繪出了整張地圖内容(圖中紅色為不可移動區域,黑色為可移動區域)

那麼我們現在要做的,就是将角色置身于當中了。

利用建構好的sprite類,我們能輕松的分解角色圖,我将一個ro中人物置身其中。

這時,由于地圖+人物俱為斜視圖,是以會形成斜45度視角的錯覺。

但新的問題來了,我們如何令角色移動呢?首先,我們顯示角色的移動路徑出來。

大 家可以看到,如果我們沿用原來2D的尋徑方式,那麼在移動過程中角色将按照2D路線行走。雖然對平面遊戲來說在正常不過,但對于已經是"2.5D"畫面的 我們來講,顯然是不能夠容忍的,這時候就需要我們摒棄原先的尋徑方式,将2.5D尋徑的A*方法引入其中,具體方式将在下次介紹。

最後,我們去除輔助線等,運作效果如下:

由于設定的關系,此時背景畫面随角色運動而卷簾移動,但就操作感受上講,與普通的2.5D遊戲是無異的。

上述操作代碼如下:

Java中2.5D遊戲(斜45度角)的設計與實作(2)

package org.loon.framework.game.image;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.Color;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.Frame;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.Graphics;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.Image;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.Panel;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.KeyEvent;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.KeyListener;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.MouseEvent;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.MouseListener;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.WindowAdapter;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import java.awt.event.WindowEvent;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

import org.loon.framework.game.script.map.BitmapToMap;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import org.loon.framework.game.sprite.Configure;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import org.loon.framework.game.sprite.Event;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import org.loon.framework.game.sprite.Sprite;

Java中2.5D遊戲(斜45度角)的設計與實作(2)

import org.loon.framework.game.sprite.SpriteGroup;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

/**

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * <p>

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * Title: LoonFramework

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * </p>

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * Description:Java純2D僞2.5D測試

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * Copyright: Copyright (c) 2007

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * Company: LoonFramework

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * 

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * @author chenpeng

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * @email:[email][email protected][/email]

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 * @version 0.1

Java中2.5D遊戲(斜45度角)的設計與實作(2)

 */

Java中2.5D遊戲(斜45度角)的設計與實作(2)

public class RpgTest extends Panel implements KeyListener, MouseListener {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

    /**

Java中2.5D遊戲(斜45度角)的設計與實作(2)

     * 

Java中2.5D遊戲(斜45度角)的設計與實作(2)

     */

Java中2.5D遊戲(斜45度角)的設計與實作(2)

    private static final long serialVersionUID = 1L;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    BitmapToMap btm = null;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    Sprite[] roleMain = new Sprite[2];

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    Configure config = null;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    //role圖行排列順序

Java中2.5D遊戲(斜45度角)的設計與實作(2)

    final String imgList = "0,1,2,3,4,6,5,7";

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    Image img = null;

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public RpgTest() {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        setSize(800, 600);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        setBackground(Color.BLACK);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //精靈組

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        SpriteGroup sgp = new SpriteGroup();

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //載入角色圖

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        Bitmap bit = new Bitmap("./imagerpg/ro.png");

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        try {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

            // 重新排列圖檔行列,超出索引則指定位置無圖

Java中2.5D遊戲(斜45度角)的設計與實作(2)

            img = bit.getScriptRegroup(70, 124, imgList);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        } catch (Exception e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

            e.printStackTrace();

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        }

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //建立精靈,寬70,高124

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[0] = new Sprite(img, 70, 124);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //定位

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[0].setXY(45,50);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[0].setVisible(true);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[1] = new Sprite(img, 70, 124);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[1].setXY(31,41);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[1].setVisible(true);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //變更角色方向

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        roleMain[1].setDirection(5);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 加載原始背景圖,背景镂空圖(行走區域标注圖)

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        btm = new BitmapToMap("./imagerpg/map_1.png", "./imagerpg/map_1_2.png",800,600);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //镂空色

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        btm.setFiltrateColor(new LColor(255, 255, 255));

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //列印字元地圖

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        System.out.println(btm.toStringMap());

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 允許顯示網格

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        btm.setReseau(false);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 加載角色

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        sgp.add(roleMain[0]);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        sgp.add(roleMain[1]);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 追蹤指定對象

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // roleMain[1].setPursueObject(roleMain[0]);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 以數組方式注入

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // config=new Configure(btm,roleMain);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 以spriteGroup方式注入Configure統一地圖與角色管理

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config = new Configure(btm, sgp);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //使用2.5d視角走法

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config.set25d(true);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        //顯示移動路徑

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config.setMovePath(false);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        setFocusable(true);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        addKeyListener(this);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        addMouseListener(this);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    }

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void update(Graphics g) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        paint(g);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void paint(Graphics g) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // g.drawImage(img, 0, 0, this);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config.draw(g);

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // g.drawImage(bit.getFleshKeepOut("./s.jpg"), 0, 0, this);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // g.dispose();

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void keyPressed(KeyEvent e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 控制指定角色移動

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config.go(roleMain[0], Event.select(e.getKeyCode()));

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        // 重新整理

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        repaint();

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void keyReleased(KeyEvent e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void keyTyped(KeyEvent e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void mouseClicked(MouseEvent e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        config.goMouse(roleMain[0], e.getPoint(), getGraphics());

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void mouseEntered(MouseEvent arg0) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void mouseExited(MouseEvent arg0) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void mousePressed(MouseEvent arg0) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public void mouseReleased(MouseEvent arg0) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

    public static void main(String[] args) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

        java.awt.EventQueue.invokeLater(new Runnable() {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

            public void run() {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                Frame frm = new Frame("Java純2D僞2.5D測試");

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.add(new RpgTest());

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.setResizable(false);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.setSize(800, 600);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.addWindowListener(new WindowAdapter() {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                    public void windowClosing(WindowEvent e) {

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                        System.exit(0);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                    }

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                });

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.setLocationRelativeTo(null);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

                frm.setVisible(true);

Java中2.5D遊戲(斜45度角)的設計與實作(2)

            }

Java中2.5D遊戲(斜45度角)的設計與實作(2)

        });

Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)
Java中2.5D遊戲(斜45度角)的設計與實作(2)

}

Java中2.5D遊戲(斜45度角)的設計與實作(2)

本文轉自 cping 51CTO部落格,原文連結:http://blog.51cto.com/cping1982/130065