Java来做马里奥 0 —让精灵再次舞动

                记得在红白机(FC)年代,还刚刚上小学的我对马里奥、冒险岛、洛克人、魂斗罗等游戏几乎可说是痴迷,每天放学回家就是想去游戏,就是要通关,就是想和关底论个胜负高低。

许多年过去了,沧海桑田,FC曾经的荣耀早已不再,只留下我们对曾经少年时的点点记忆。即使当时在FC上看上去多么复杂,多么高不可攀的游戏,在当今,即使最普通的程序员都可以轻易实现。

本着向经典学习、向经典致敬的心情,我也准备用Java在PC机再现当年马里奥的风采。

下面我在代码中所演示的,是一个简单的ACT游戏动作及地图构成原型。

Map.java
package  org.test.mario;

import  java.awt.Color;
import  java.awt.Graphics;
import  java.awt.Point;

/** */ /**
 * <p>
 * Title: LoonFramework
 * </p>
 * <p>
 * Description:地图绘制及描述用类
 * </p>
 * <p>
 * Copyright: Copyright (c) 2008
 * </p>
 * <p>
 * Company: LoonFramework
 * </p>
 * 
 * @author chenpeng
 * @email:ceponline@yahoo.com.cn
 * @version 0.1
 */

public   class  Map  ... {

    // 在以前的blog文章中我介绍过,游戏开发中通常以数组描述地图
    // 此处1描绘为一个障碍物,0描绘为一个可通行空间
    final static private int[][] map = ...{
            ...{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
            ...{ 1, 0, 0, 0, 0, 0, 0, 0, 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, 1, 1, 1, 1, 1 } }
;

    // 地面瓦片的宽度
    final static private int TILE_SIZE = 32;

    // 行
    final static private int ROW = 15;

    // 列
    final static private int COL = 20;

    /** *//**
     * 构造函数
     * 
     */

    public Map() ...{
    }


    public void draw(Graphics g) ...{
         g.setColor(Color.ORANGE);
        for (int i = 0; i < ROW; i++) ...{
            for (int j = 0; j < COL; j++) ...{
                switch (map[i][j]) ...{
                case 1:
                    g.fillRect(tilesToPixels(j), tilesToPixels(i), TILE_SIZE,
                            TILE_SIZE);
                    break;
                }

            }

        }

    }


    /** *//**
     * 换算角色与地板的撞击,并返回Point用以描述新的x,y
     * 
     * @param player
     * @param newX
     * @param newY
     * @return
     */

    public Point getTileHit(Role player, double newX, double newY) ...{
        // 取最小的整数但不能小于自身,用以换算坐标
        newX = Math.ceil(newX);
        newY = Math.ceil(newY);

        double fromX = Math.min(player.getX(), newX);
        double fromY = Math.min(player.getY(), newY);
        double toX = Math.max(player.getX(), newX);
        double toY = Math.max(player.getY(), newY);

        int fromTileX = pixelsToTiles(fromX);
        int fromTileY = pixelsToTiles(fromY);
        int toTileX = pixelsToTiles(toX + Role.WIDTH - 1);
        int toTileY = pixelsToTiles(toY + Role.HEIGHT - 1);

        // 返回Point,用以描述x,y坐标点
        for (int x = fromTileX; x <= toTileX; x++) ...{
            for (int y = fromTileY; y <= toTileY; y++) ...{
                if (x < 0 || x >= COL) ...{
                    return new Point(x, y);
                }

                if (y < 0 || y >= ROW) ...{
                    return new Point(x, y);
                }

                if (map[y][x] == 1) ...{
                    return new Point(x, y);
                }

            }

        }


        return null;
    }


    /** *//**
     * 将Tiles转为Pixels
     * 
     * @param pixels
     * @return
     */

    public static int pixelsToTiles(double pixels) ...{
        return (int) Math.floor(pixels / TILE_SIZE);
    }


    /** *//**
     * 将Pixels转为Tiles
     * 
     * @param pixels
     * @return
     */

    public static int tilesToPixels(int tiles) ...{
        return tiles * TILE_SIZE;
    }

}


Role.java
package  org.test.mario;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值