您的位置:首页 > 移动开发 > Android开发

g2048游戏2-android

2016-09-11 23:35 211 查看

g2048游戏2-android

接着上一篇g2048游戏1-android

g2048主界面

主界面(MainView)其实就是需要绘制表格,首要考虑android自带的ShapeDrawable资源。

MainView需要绘制:

1:整个表格背景background_rectangle.xml

2:每一小格背景

小格无数字背景cell_rectangle.xml

小格有数字x背景cell_rectangle_x.xml

绘制背景上的数字canvas.drawText

主界面MainView

j\i0123
042
14
22
32
MainView需要自定义,在该类中只负责绘制,而数据逻辑交给辅助MainGame .java

背景使用ShapeDrawable

整个表格背景background_rectangle.xml

小格无数字背景cell_rectangle.xml

小格有数字x背景cell_rectangle_x.xml

这个三个背景是一样的,都使用ShapeDrawable,只是颜色背景不一样

如background_rectangle.xml

<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" android:padding = "10dp">
<solid android:color="#bbada0"/>
<corners
android:bottomRightRadius="10dp"
android:bottomLeftRadius="10dp"
android:topLeftRadius="10dp"
android:topRightRadius="10dp"/>
</shape>


其他背景颜色

color=”#d6cdc4”

color=”#eee4da”

color=”#ede0c8”

color=”#f2b179”

color=”#f59563”

color=”#f67c5f”

color=”#f65e3b”

color=”#edcf72”

color=”#edcc61”

color=”#edc850”

color=”#edc53f”

color=”#edc22e”

自定义MainView

其中MainGame 对象负责数据逻辑,GestureDetector手势对象负责监听上下左右滑动

public class MainView extends View {

public MainGame game;
private GestureDetector gesture;
private int numCellTypes = 13;

// Layout
private Paint paint = new Paint();
private int cellSize;
private int gridWidth;
private float textSize;
private float cellTextSize;
private int startX;
private int endX;
private int startY;
private int endY;

// Text
private int TEXT_WHITE;
private int TEXT_BLACK;

// asssets drawable
private Drawable backgroundRectangle;
private BitmapDrawable[] bitmapCell = new BitmapDrawable[numCellTypes];
private Bitmap background = null;

public MainView(Context context) {
super(context);

game = new MainGame(this);
//Loading resources
Resources resources = context.getResources();
try {
//Getting assets
backgroundRectangle = resources.getDrawable(R.drawable.background_rectangle);
TEXT_WHITE = resources.getColor(R.color.text_white);
TEXT_BLACK = resources.getColor(R.color.text_black);
this.setBackgroundColor(resources.getColor(R.color.background));
Typeface font = Typeface.createFromAsset(resources.getAssets(), "ClearSans-Bold.ttf");
paint.setTypeface(font);
paint.setAntiAlias(true);
} catch (Exception e) {
System.out.println("Error getting assets?");
}

gesture = new GestureDetector(context, new InputListener(this));
game.newGame();
}

@Override
protected void onDraw(Canvas canvas) {
canvas.drawBitmap(background, 0, 0, paint);
drawCells(canvas);
}

@Override
protected void onSizeChanged(int width, int height, int oldw, int oldh) {
super.onSizeChanged(width, height, oldw, oldh);
getLayout(width, height);
createBitmapCells();
createBackgroundBitmap(width, height);
}

@Override
public boolean onTouchEvent(MotionEvent event) {
return gesture.onTouchEvent(event);
}

private void drawCells(Canvas canvas) {
paint.setTextSize(textSize);
paint.setTextAlign(Paint.Align.CENTER);

for (int i = 0; i < game.numSquaresX; i++) {
for (int j = 0; j < game.numSquaresY; j++) {
int sX = startX + gridWidth + (cellSize + gridWidth) * i;
int eX = sX + cellSize;
int sY = startY + gridWidth + (cellSize + gridWidth) * j;
int eY = sY + cellSize;

CellData currentCellData = game.grid.getCellContent(i, j);
if (currentCellData != null) {
int value = currentCellData.getValue();
int index = Utils.log2(value) >= numCellTypes ? numCellTypes - 1 : Utils.log2(value);

bitmapCell[index].setBounds(sX, sY, eX, eY);
bitmapCell[index].draw(canvas);
}
}
}
}

private void getLayout(int width, int height) {
cellSize = Math.min(width / (game.numSquaresX + 1), height / (game.numSquaresY + 3));
gridWidth = cellSize / 7;
int screenMiddleX = width / 2;
int screenMiddleY = height / 2;

paint.setTextAlign(Paint.Align.CENTER);
paint.setTextSize(cellSize);
textSize = cellSize * cellSize / Math.max(cellSize, paint.measureText("0000"));
cellTextSize = textSize;

//Grid Dimensions
double halfNumSquaresX = game.numSquaresX / 2d;
double halfNumSquaresY = game.numSquaresY / 2d;

startX = (int) (screenMiddleX - (cellSize + gridWidth) * halfNumSquaresX - gridWidth / 2);
endX = (int) (screenMiddleX + (cellSize + gridWidth) * halfNumSquaresX + gridWidth / 2);
startY = (int) (screenMiddleY - (cellSize + gridWidth) * halfNumSquaresY - gridWidth / 2);
endY = (int) (screenMiddleY + (cellSize + gridWidth) * halfNumSquaresY + gridWidth / 2);
}

private void createBitmapCells() {
Resources resources = getResources();
int[] cellRectangleIds = getCellRectangleIds();
paint.setTextAlign(Paint.Align.CENTER);
for (int i = 1; i < bitmapCell.length; i++) {
int value = (int) Math.pow(2, i);
paint.setTextSize(cellTextSize);
float tempTextSize = cellTextSize * cellSize * 0.9f / Math.max(cellSize * 0.9f, paint.measureText(String.valueOf(value)));
paint.setTextSize(tempTextSize);
Bitmap bitmap = Bitmap.createBitmap(cellSize, cellSize, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
drawDrawable(canvas, resources.getDrawable(cellRectangleIds[i]), 0, 0, cellSize, cellSize);
drawCellText(canvas, value, 0, 0);
bitmapCell[i] = new BitmapDrawable(resources, bitmap);
}
}

private int[] getCellRectangleIds() {
int[] cellRectangleIds = new int[numCellTypes];
cellRectangleIds[0] = R.drawable.cell_rectangle;
cellRectangleIds[1] = R.drawable.cell_rectangle_2;
cellRectangleIds[2] = R.drawable.cell_rectangle_4;
cellRectangleIds[3] = R.drawable.cell_rectangle_8;
cellRectangleIds[4] = R.drawable.cell_rectangle_16;
cellRectangleIds[5] = R.drawable.cell_rectangle_32;
cellRectangleIds[6] = R.drawable.cell_rectangle_64;
cellRectangleIds[7] = R.drawable.cell_rectangle_128;
cellRectangleIds[8] = R.drawable.cell_rectangle_256;
cellRectangleIds[9] = R.drawable.cell_rectangle_512;
cellRectangleIds[10] = R.drawable.cell_rectangle_1024;
cellRectangleIds[11] = R.drawable.cell_rectangle_2048;
cellRectangleIds[12] = R.drawable.cell_rectangle_4096;
return cellRectangleIds;
}

private void createBackgroundBitmap(int width, int height) {
background = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(background);
drawBackground(canvas);
drawBackgroundGrid(canvas);
}

private void drawBackground(Canvas canvas) {
drawDrawable(canvas, backgroundRectangle, startX, startY, endX, endY);
}

private void drawBackgroundGrid(Canvas canvas) {
Resources resources = getResources();
Drawable backgroundCell = resources.getDrawable(R.drawable.cell_rectangle);

for (int i = 0; i < game.numSquaresX; i++) {
for (int j = 0; j < game.numSquaresY; j++) {
int sX = startX + gridWidth + (cellSize + gridWidth) * i;
int eX = sX + cellSize;
int sY = startY + gridWidth + (cellSize + gridWidth) * j;
int eY = sY + cellSize;

drawDrawable(canvas, backgroundCell, sX, sY, eX, eY);
}
}
}

private void drawDrawable(Canvas canvas, Drawable draw, int startX, int startY, int endX, int endY) {
draw.setBounds(startX, startY, endX, endY);
draw.draw(canvas);
}

private void drawCellText(Canvas canvas, int value, int sX, int sY) {
int textShiftY = Utils.centerText(paint);
if (value >= 8) {
paint.setColor(TEXT_WHITE);
} else {
paint.setColor(TEXT_BLACK);
}
canvas.drawText("" + value, sX + cellSize / 2, sY + cellSize / 2 - textShiftY, paint);
}

}


添加工具类Utils

工具类一般添加固定通用的方法,便于以后快速开发调用。

下面Utils中是对自定义MainView增加两种方法:一种是计算绘画字符串的基准线;一种是计算一个数是2的几次方

public class Utils {

public static int centerText(Paint paint) {
return (int) ((paint.descent() + paint.ascent()) / 2);
}

public static int log2(int n) {
if (n <= 0) throw new IllegalArgumentException();
return 31 - Integer.numberOfLeadingZeros(n);
}
}


上面“计算一个数是2的几次方”还有其他方法:

(int) (Math.log10(n) / Math.log10(2))

下一篇g2048游戏3-android
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  android 游戏