完成了LabVIEW上的2048之后。。最近学了几周的Android,所以就想用Android实现一下。。
百度了不少方案 ,有View,GridView,我就突发奇想……想用TextView实现一下,然后就有了大概的思路:用一个二维数组然后在运算的过程中实时更新TextView的属性,并加入了计分和最高分记录与回显。 上代码!
1.首先是布局文件
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center_horizontal" android:orientation="vertical" > <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="100dp" android:orientation="horizontal" > <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="40dp" android:text="Score:" android:textColor="#CCC0B3" /> <TextView android:id="@+id/score" android:layout_width="60dp" android:layout_height="wrap_content" android:text="0" android:textColor="#CCC0B3" /> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="40dp" android:text="BestScore:" android:textColor="#CCC0B3" /> <TextView android:id="@+id/bestscore" android:layout_width="60dp" android:layout_height="wrap_content" android:text="0" android:textColor="#CCC0B3" /> </LinearLayout> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginTop="20dp" android:orientation="horizontal" > <TextView android:id="@+id/textview00" android:layout_width="70dp" android:layout_height="70dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20dp" /> <TextView android:id="@+id/textview01" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20dp" /> <TextView android:id="@+id/textview02" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20dp" /> <TextView android:id="@+id/textview03" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20dp" /> </LinearLayout> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginTop="10dp" android:orientation="horizontal" > <TextView android:id="@+id/textview10" android:layout_width="70dp" android:layout_height="70dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview11" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview12" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview13" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> </LinearLayout> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginTop="10dp" android:orientation="horizontal" > <TextView android:id="@+id/textview20" android:layout_width="70dp" android:layout_height="70dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview21" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview22" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview23" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> </LinearLayout> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginTop="10dp" android:orientation="horizontal" > <TextView android:id="@+id/textview30" android:layout_width="70dp" android:layout_height="70dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview31" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview32" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> <TextView android:id="@+id/textview33" android:layout_width="70dp" android:layout_height="70dp" android:layout_marginLeft="10dp" android:background="#CCC0B3" android:gravity="center" android:textColor="#FFFFFF" android:textSize="20sp" /> </LinearLayout> </LinearLayout>2.MainActivity
package com.ldgforever.twozerofourdight; import java.util.Map; import com.ldgforever.action.Action; import com.ldgforever.savedata.savedata; import android.app.Activity; import android.app.AlertDialog; import android.content.DialogInterface; import android.content.DialogInterface.OnClickListener; import android.graphics.Color; import android.os.Bundle; import android.view.Menu; import android.view.MotionEvent; import android.widget.TextView; public class MainActivity extends Activity { private static TextView mtextview00; private static TextView mtextview01; private static TextView mtextview02; private static TextView mtextview03; private static TextView mtextview10; private static TextView mtextview11; private static TextView mtextview12; private static TextView mtextview13; private static TextView mtextview20; private static TextView mtextview21; private static TextView mtextview22; private static TextView mtextview23; private static TextView mtextview30; private static TextView mtextview31; private static TextView mtextview32; private static TextView mtextview33; private static TextView mScore; private static TextView mBestScore; public static int score = 0; public static int bestscore = 0; float startX = 0, startY = 0, endX, endY; private int[][] a = { { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 } }; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); score = 0; mtextview00 = (TextView) findViewById(R.id.textview00); mtextview01 = (TextView) findViewById(R.id.textview01); mtextview02 = (TextView) findViewById(R.id.textview02); mtextview03 = (TextView) findViewById(R.id.textview03); mtextview10 = (TextView) findViewById(R.id.textview10); mtextview11 = (TextView) findViewById(R.id.textview11); mtextview12 = (TextView) findViewById(R.id.textview12); mtextview13 = (TextView) findViewById(R.id.textview13); mtextview20 = (TextView) findViewById(R.id.textview20); mtextview21 = (TextView) findViewById(R.id.textview21); mtextview22 = (TextView) findViewById(R.id.textview22); mtextview23 = (TextView) findViewById(R.id.textview23); mtextview30 = (TextView) findViewById(R.id.textview30); mtextview31 = (TextView) findViewById(R.id.textview31); mtextview32 = (TextView) findViewById(R.id.textview32); mtextview33 = (TextView) findViewById(R.id.textview33); mScore = (TextView) findViewById(R.id.score); mBestScore = (TextView) findViewById(R.id.bestscore); } @Override public boolean dispatchTouchEvent(MotionEvent event) { int action = event.getAction(); if (action == MotionEvent.ACTION_DOWN) { startX = event.getX(); startY = event.getY(); } else if (action == MotionEvent.ACTION_UP) { endX = event.getX(); endY = event.getY(); int direction = GetSlideDirection(startX, startY, endX, endY); int winORlose = Action.Slide(direction, a); switch (winORlose) { case 0: dialog("您赢了!"); break; case 1: dialog("您输了"); default: break; } } return super.dispatchTouchEvent(event); } // 返回角度 private double GetSlideAngle(float dx, float dy) { return Math.atan2(dy, dx) * 180 / Math.PI; } private int GetSlideDirection(float startX, float startY, float endX, float endY) { float dy = startY - endY; float dx = endX - startX; int result = 0; // 没有滑动 // 如果滑动距离太短 if (Math.abs(dx) < 2 && Math.abs(dy) < 2) { return result; } double angle = GetSlideAngle(dx, dy); if (angle >= -45 && angle < 45) { return 1; // 向右滑动 } else if (angle >= 45 && angle < 135) { return 2; // 向上滑动 } else if (angle >= -135 && angle < -45) { return 4; // 向下滑动 } else if ((angle >= 135 && angle <= 180) || (angle >= -180 && angle < -135)) { return 3; // 向左滑动 } return result; } public void reset(int a[][]) { int i, j; for (i = 0; i < 4; i++) { for (j = 0; j < 4; j++) { a[i][j] = 0; } } score = 0; /** * 回显数据 */ Map<String, String> userInfoMap = savedata.getUserInfo(); if (userInfoMap != null) { mBestScore.setText(userInfoMap.get("BestScore")); } updateState(a, score, bestscore); } /** * 实时更新textview属性 * @param a * @param Score * @param BestScore */ public static void updateState(int[][] a, int Score, int BestScore) { updateTextViewState(a[0][0], mtextview00); updateTextViewState(a[0][1], mtextview01); updateTextViewState(a[0][2], mtextview02); updateTextViewState(a[0][3], mtextview03); updateTextViewState(a[1][0], mtextview10); updateTextViewState(a[1][1], mtextview11); updateTextViewState(a[1][2], mtextview12); updateTextViewState(a[1][3], mtextview13); updateTextViewState(a[2][1], mtextview21); updateTextViewState(a[2][2], mtextview22); updateTextViewState(a[2][3], mtextview23); updateTextViewState(a[2][0], mtextview20); updateTextViewState(a[3][0], mtextview30); updateTextViewState(a[3][1], mtextview31); updateTextViewState(a[3][2], mtextview32); updateTextViewState(a[3][3], mtextview33); mScore.setText(Score + ""); mBestScore.setText(BestScore + ""); } public static void updateTextViewState(int role, TextView textview) { switch (role) { case 2: textview.setText("2"); textview.setBackgroundColor(Color.parseColor("#EEE4DA")); break; case 4: textview.setText("4"); textview.setBackgroundColor(Color.parseColor("#EDE0C8")); break; case 8: textview.setText("8"); textview.setBackgroundColor(Color.parseColor("#F2B179")); break; case 16: textview.setText("16"); textview.setBackgroundColor(Color.parseColor("#F49563")); break; case 32: textview.setText("32"); textview.setBackgroundColor(Color.parseColor("#F5794D")); break; case 64: textview.setText("64"); textview.setBackgroundColor(Color.parseColor("#F55D37")); break; case 128: textview.setText("128"); textview.setBackgroundColor(Color.parseColor("#EEE863")); break; case 256: textview.setText("256"); textview.setBackgroundColor(Color.parseColor("#EDB04D")); break; case 512: textview.setText("512"); textview.setBackgroundColor(Color.parseColor("#ECB04D")); break; case 1024: textview.setText("1024"); textview.setBackgroundColor(Color.parseColor("#EB9437")); break; case 2048: textview.setText("2048"); textview.setBackgroundColor(Color.parseColor("#EA7821")); break; default: textview.setText(""); textview.setBackgroundColor(Color.parseColor("#CCC0B3")); break; } } /** * 对话框 * @param winorlose */ protected void dialog(String winorlose) { AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this); builder.setMessage(winorlose); builder.setTitle("提示"); builder.setPositiveButton("重新开始", new OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { reset(a); mScore.setText("0"); dialog.dismiss(); } }); builder.setNegativeButton("关闭游戏", new OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.dismiss(); finish(); } }); builder.create().show(); } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.main, menu); return true; } }3.行为动作相关
package com.ldgforever.action; import com.ldgforever.randomcreate.randomCreate; import com.ldgforever.savedata.savedata; import com.ldgforever.twozerofourdight.MainActivity; import android.content.SharedPreferences; import android.widget.TextView; public class Action { static int t; static void up_remove_blank(int[][] a) { int i, j, k; for (j = 0; j < 4; j++) { for (i = 1; i < 4; i++) { k = i; while (k - 1 >= 0 && a[k - 1][j] == 0) {// 上面的那个为空 t = a[k][j]; a[k][j] = a[k - 1][j]; a[k - 1][j] = t; k--; } } } } static void down_remove_blank(int a[][]) { int i, j, k; for (j = 0; j < 4; j++) { for (i = 2; i >= 0; i--) { k = i; while (k + 1 <= 3 && a[k + 1][j] == 0) {// 上面的那个为空 t = a[k][j]; a[k][j] = a[k + 1][j]; a[k + 1][j] = t; k++; } } } } static void left_remove_blank(int a[][]) { int i, j, k; for (i = 0; i < 4; i++) { for (j = 1; j < 4; j++) { k = j; while (k - 1 >= 0 && a[i][k - 1] == 0) {// 上面的那个为空 t = a[i][k]; a[i][k] = a[i][k - 1]; a[i][k - 1] = t; k--; } } } } static void right_remove_blank(int a[][]) { int i, j, k; for (i = 0; i < 4; i++) { for (j = 2; j >= 0; j--) { k = j; while (k + 1 <= 3 && a[i][k + 1] == 0) {// 上面的那个为空 t = a[i][k]; a[i][k] = a[i][k + 1]; a[i][k + 1] = t; k++; } } } } static void left(int a[][]) { int i, j; for (i = 0; i < 4; i++) { for (j = 0; j < 3; j++) { if (a[i][j] == a[i][j + 1]) { a[i][j] += a[i][j + 1]; if (a[i][j] != 0) { MainActivity.score += 2; updatecore(MainActivity.score, MainActivity.bestscore); } a[i][j + 1] = 0; left_remove_blank(a); } } } } static void up(int a[][]) { int i, j; for (j = 0; j < 4; j++) { for (i = 0; i < 3; i++) { if (a[i][j] == a[i + 1][j]) { a[i][j] += a[i + 1][j]; if (a[i][j] != 0) { MainActivity.score += 2; updatecore(MainActivity.score, MainActivity.bestscore); } a[i + 1][j] = 0; up_remove_blank(a); } } } } static void right(int a[][]) { int i, j; for (i = 0; i < 4; i++) { for (j = 3; j >= 1; j--) { if (a[i][j] == a[i][j - 1]) { a[i][j] += a[i][j - 1]; if (a[i][j] != 0) { MainActivity.score += 2; updatecore(MainActivity.score, MainActivity.bestscore); } a[i][j - 1] = 0; right_remove_blank(a); } } } } static void down(int a[][]) { int i, j; for (j = 0; j < 4; j++) { for (i = 3; i >= 1; i--) { if (a[i][j] == a[i - 1][j]) { a[i][j] += a[i - 1][j]; if (a[i][j] != 0) { MainActivity.score += 2; updatecore(MainActivity.score, MainActivity.bestscore); } a[i - 1][j] = 0; down_remove_blank(a); } } } } static boolean isFailure(int a[][]) { int i, j; for (i = 0; i < 4; i++) { for (j = 0; j < 4; j++) { if (a[i][j] == 0) { return false; } } } return true; } static boolean isWin(int a[][]) { int i, j; for (i = 0; i < 4; i++) { for (j = 0; j < 4; j++) { if (a[i][j] == 2048) { return true; } } } return false; } public static void updatecore(int score, int bestscore) { if (MainActivity.score > MainActivity.bestscore) { MainActivity.bestscore = MainActivity.score; savedata.saveUserInfo(MainActivity.bestscore); } } public static int Slide(int direction, int a[][]) { if (direction == 3) { left_remove_blank(a); left(a); MainActivity.updateState(a, MainActivity.score, MainActivity.bestscore); if (isWin(a)) return 0; else if (isFailure(a)) return 1; else { String index = randomCreate.searchforZERO(a); randomCreate.randomCreate(a, index); MainActivity.updateState(a, MainActivity.score, MainActivity.bestscore); } } else if (direction == 1) { right_remove_blank(a); right(a); if (isWin(a)) return 0; else if (isFailure(a)) return 1; else { String index = randomCreate.searchforZERO(a); randomCreate.randomCreate(a, index); MainActivity.updateState(a, MainActivity.score, MainActivity.bestscore); } } else if (direction == 2) { up_remove_blank(a); up(a); if (isWin(a)) return 0; else if (isFailure(a)) return 1; else { String index = randomCreate.searchforZERO(a); randomCreate.randomCreate(a, index); MainActivity.updateState(a, MainActivity.score, MainActivity.bestscore); } } else if (direction == 4) { down_remove_blank(a); down(a); if (isWin(a)) return 0; else if (isFailure(a)) return 1; else { String index = randomCreate.searchforZERO(a); randomCreate.randomCreate(a, index); MainActivity.updateState(a, MainActivity.score, MainActivity.bestscore); } } return 2; } }4.生成2,4的随机数 2与4之比约为9:1
package com.ldgforever.randomcreate; public class randomCreate { public static int[][] randomCreate(int a[][], String index) { String[] b = index.split("####"); int random = (int) (Math.random() * (b.length - 1)); String[] c = b[random].split("##"); if (Math.random() > 0.1) { a[Integer.parseInt(c[0])][Integer.parseInt(c[1])] = 2; } else { a[Integer.parseInt(c[0])][Integer.parseInt(c[1])] = 4; } return a; } public static String searchforZERO(int a[][]) { int i, j; String index = ""; for (i = 0; i < 4; i++) { for (j = 0; j < 4; j++) { if (a[i][j] == 0) { index = i + "##" + j + "####" + index; } } } return index; } }5.数据的存储与回显
package com.ldgforever.savedata; import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.InputStreamReader; import java.util.HashMap; import java.util.Map; import android.os.Environment; import android.text.TextUtils; public class savedata { /** * 保存Score * * @return */ public static boolean saveUserInfo(int BestScore) { File BSFile = Environment.getDataDirectory(); File file = new File(BSFile, "BestScore.txt"); // String path = // "/data/data/com.ldgforever.twozerofourdight/BestScore.txt"; try { FileOutputStream fos = new FileOutputStream(file); String data = "##" + BestScore; fos.write(data.getBytes()); fos.flush(); fos.close(); return true; } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } return false; } /** * 读取用户输入文件 * * @return */ public static Map<String, String> getUserInfo() { File BSFile = Environment.getDataDirectory(); File file = new File(BSFile, "BestScore.txt"); // String path = // "/data/data/com.ldgforever.twozerofourdight/BestScore.txt"; try { FileInputStream fis = new FileInputStream(file); BufferedReader reader = new BufferedReader(new InputStreamReader(fis)); // 构建字符流对象 String text = reader.readLine(); reader.close(); if (!TextUtils.isEmpty(text)) { String[] split = text.split("##"); Map<String, String> userInfoMap = new HashMap<String, String>(); userInfoMap.put("Score", split[0]); userInfoMap.put("BestScore", split[1]); return userInfoMap; } } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } return null; } } 最终效果: