├── .classpath
├── .gitignore
├── .project
├── .settings
└── org.eclipse.jdt.core.prefs
├── AndroidManifest.xml
├── LICENSE.txt
├── README.md
├── libs
├── domob_android_sdk.jar
└── umeng_sdk.jar
├── proguard-project.txt
├── project.properties
├── res
├── drawable-hdpi
│ └── icon.png
├── drawable-mdpi
│ └── icon.png
├── drawable
│ ├── bg.png
│ ├── kill.png
│ ├── menubg.jpg
│ ├── qp1.jpg
│ ├── qz.png
│ └── sel.png
├── layout
│ ├── dialog.xml
│ └── main.xml
├── menu
│ └── option_menu.xml
├── values-zh-rCN
│ └── strings.xml
└── values
│ └── strings.xml
└── src
└── com
└── onezeros
└── chinesechess
├── AI.java
├── ChessboardView.java
└── ChineseChessActivity.java
/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # built application files
2 | *.apk
3 | *.ap_
4 |
5 | # files for the dex VM
6 | *.dex
7 |
8 | # Java class files
9 | *.class
10 |
11 | # generated files
12 | bin/
13 | gen/
14 |
15 | # Local configuration file (sdk path, etc)
16 | local.properties
17 |
--------------------------------------------------------------------------------
/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | ChineseChess
4 |
5 |
6 |
7 |
8 |
9 | com.android.ide.eclipse.adt.ResourceManagerBuilder
10 |
11 |
12 |
13 |
14 | com.android.ide.eclipse.adt.PreCompilerBuilder
15 |
16 |
17 |
18 |
19 | org.eclipse.jdt.core.javabuilder
20 |
21 |
22 |
23 |
24 | com.android.ide.eclipse.adt.ApkBuilder
25 |
26 |
27 |
28 |
29 |
30 | com.android.ide.eclipse.adt.AndroidNature
31 | org.eclipse.jdt.core.javanature
32 |
33 |
34 |
--------------------------------------------------------------------------------
/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5
4 | org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
5 | org.eclipse.jdt.core.compiler.compliance=1.5
6 | org.eclipse.jdt.core.compiler.debug.lineNumber=generate
7 | org.eclipse.jdt.core.compiler.debug.localVariable=generate
8 | org.eclipse.jdt.core.compiler.debug.sourceFile=generate
9 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
10 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
11 | org.eclipse.jdt.core.compiler.source=1.5
12 |
--------------------------------------------------------------------------------
/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
19 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
30 |
31 |
32 |
33 |
34 |
--------------------------------------------------------------------------------
/LICENSE.txt:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2012 Zhijie Lee
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy of
6 | this software and associated documentation files (the "Software"), to deal in
7 | the Software without restriction, including without limitation the rights to
8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
9 | the Software, and to permit persons to whom the Software is furnished to do so,
10 | subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | ChineseChess4Android
2 | ====================
3 |
4 | a android version of the Chinese Chess game, which is not very difficult to defeat
--------------------------------------------------------------------------------
/libs/domob_android_sdk.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/libs/domob_android_sdk.jar
--------------------------------------------------------------------------------
/libs/umeng_sdk.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/libs/umeng_sdk.jar
--------------------------------------------------------------------------------
/proguard-project.txt:
--------------------------------------------------------------------------------
1 | # To enable ProGuard in your project, edit project.properties
2 | # to define the proguard.config property as described in that file.
3 | #
4 | # Add project specific ProGuard rules here.
5 | # By default, the flags in this file are appended to flags specified
6 | # in ${sdk.dir}/tools/proguard/proguard-android.txt
7 | # You can edit the include path and order by changing the ProGuard
8 | # include property in project.properties.
9 | #
10 | # For more details, see
11 | # http://developer.android.com/guide/developing/tools/proguard.html
12 |
13 | # Add any project specific keep options here:
14 |
15 | # If your project uses WebView with JS, uncomment the following
16 | # and specify the fully qualified class name to the JavaScript interface
17 | # class:
18 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
19 | # public *;
20 | #}
21 |
--------------------------------------------------------------------------------
/project.properties:
--------------------------------------------------------------------------------
1 | # This file is automatically generated by Android Tools.
2 | # Do not modify this file -- YOUR CHANGES WILL BE ERASED!
3 | #
4 | # This file must be checked in Version Control Systems.
5 | #
6 | # To customize properties used by the Ant build system edit
7 | # "ant.properties", and override values to adapt the script to your
8 | # project structure.
9 | #
10 | # To enable ProGuard to shrink and obfuscate your code, uncomment this (available properties: sdk.dir, user.home):
11 | #proguard.config=${sdk.dir}/tools/proguard/proguard-android.txt:proguard-project.txt
12 |
13 | # Project target.
14 | target=android-15
15 |
--------------------------------------------------------------------------------
/res/drawable-hdpi/icon.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable-hdpi/icon.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/icon.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable-mdpi/icon.png
--------------------------------------------------------------------------------
/res/drawable/bg.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/bg.png
--------------------------------------------------------------------------------
/res/drawable/kill.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/kill.png
--------------------------------------------------------------------------------
/res/drawable/menubg.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/menubg.jpg
--------------------------------------------------------------------------------
/res/drawable/qp1.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/qp1.jpg
--------------------------------------------------------------------------------
/res/drawable/qz.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/qz.png
--------------------------------------------------------------------------------
/res/drawable/sel.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zhijie/ChineseChess4Android/2bf9d10115353e17a1e87885a0c7231326b78bf2/res/drawable/sel.png
--------------------------------------------------------------------------------
/res/layout/dialog.xml:
--------------------------------------------------------------------------------
1 |
7 |
13 |
19 |
--------------------------------------------------------------------------------
/res/layout/main.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
6 |
7 |
8 |
13 |
14 |
19 |
20 |
28 |
29 |
34 |
35 |
36 |
37 |
42 |
49 |
55 |
56 |
57 |
--------------------------------------------------------------------------------
/res/menu/option_menu.xml:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/res/values-zh-rCN/strings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | 中国象棋
5 | 哈哈,我赢了。还敢再玩儿吗?
6 | 算你运气好,下次就不一定了。敢再来一局吗?
7 | 新游戏
8 | 继续游戏
9 | 亲,终于回来了,想死我了
10 | 该你动手啦~~~
11 | 给点儿时间让我想想。。。
12 | 初级
13 | 中级
14 | 高级
15 | 中国象棋是一款简洁的益智游戏,程序界面简洁,人机对战,电脑智力水平分为三个等级,等级越高,运行时耗费的时间会稍长些。各个阶段的象棋爱好者都可以把玩儿哦.程序开源地址:https://github.com/zhijie/ChineseChess4Android。版本:1.1.0
16 | 关于
17 |
--------------------------------------------------------------------------------
/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | ChineseChess
4 | Hiahia, I win. dare to try again ?
5 | You are really lucky, dare to try again ?
6 | New Game
7 | Continue
8 | Hello
9 | Your turn.
10 | Let me have a look.
11 | level LOW
12 | level MIDDLE
13 | level HIGH
14 |
--------------------------------------------------------------------------------
/src/com/onezeros/chinesechess/AI.java:
--------------------------------------------------------------------------------
1 | /*
2 | * ChineseChess4Android
3 | *
4 | * Copyright (c) 2012 Zhijie Lee
5 | *
6 | * The MIT License (MIT)
7 | *
8 | * Permission is hereby granted, free of charge, to any person obtaining a copy of
9 | * this software and associated documentation files (the "Software"), to deal in
10 | * the Software without restriction, including without limitation the rights to
11 | * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
12 | * the Software, and to permit persons to whom the Software is furnished to do so,
13 | * subject to the following conditions:
14 | *
15 | * The above copyright notice and this permission notice shall be included in all
16 | * copies or substantial portions of the Software.
17 | *
18 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
20 | * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
21 | * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
22 | * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
23 | * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 | */
25 | package com.onezeros.chinesechess;
26 |
27 | import java.io.DataInputStream;
28 | import java.io.DataOutputStream;
29 | import java.io.IOException;
30 | import java.io.Serializable;
31 |
32 | import android.R.integer;
33 | import android.bluetooth.BluetoothA2dp;
34 | import android.os.Bundle;
35 | import android.os.Parcel;
36 | import android.os.Parcelable;
37 |
38 | /**
39 | * algorithm from feiyan
40 | * @author onezeros
41 | *
42 | */
43 |
44 | public class AI {
45 | private int MAX_PLY = 4;
46 | public static final int SIZE_X = 9;
47 | public static final int SIZE_Y = 10;
48 | public static final int BOARD_SIZE = SIZE_X*SIZE_Y;
49 |
50 | public static final int MOVE_STACK = 4096;
51 | public static final int HIST_STACK = 50;
52 |
53 | public static final int EMPTY = 7;
54 | public static final int DARK = 0;
55 | public static final int LIGHT = 1;
56 |
57 | public static final int PAWN = 0 ;
58 | public static final int BISHOP = 1;
59 | public static final int ELEPHANT = 2;
60 | public static final int KNIGHT = 3;
61 | public static final int CANNON = 4;
62 | public static final int ROOK = 5;
63 | public static final int KING = 6;
64 |
65 | public static final int INFINITY = 20000;
66 | public static final int NORMAL = 0;
67 | public static final int SELECT = 1;
68 |
69 | // result of a move
70 | public static final int MOVE_WIN = 1;
71 | public static final int MOVE_INVALID = 2;
72 | public static final int MOVE_OK = 3;
73 |
74 |
75 |
76 |
77 |
78 | /* the board representation && the initial board state */
79 | // 0, 1,represent for both sides
80 | public int[] color = new int[BOARD_SIZE];
81 |
82 | public int[] piece = new int[BOARD_SIZE];
83 |
84 | /* For getting information */
85 | int nodecount, brandtotal = 0, gencount = 0;
86 | int ply, side, xside, computerside;
87 | Move newmove = new Move();
88 | Recorder[] gen_dat ;//record moved steps
89 | //store possible moves indexs in gen_data for current situation
90 | int[] gen_begin = new int[HIST_STACK];
91 | int[] gen_end = new int[HIST_STACK];
92 | History[] hist_dat ;//history data
93 | int hdp;
94 |
95 | public void setSearchDepth(int depth) {
96 | MAX_PLY = depth > 4 ? 4:(depth < 2 ? 2 :depth);
97 | }
98 |
99 | public void saveStatus(DataOutputStream dos) throws IOException {
100 | for (int i = 0; i < color.length; i++) {
101 | dos.writeInt(color[i]);
102 | }
103 | for (int i = 0; i < piece.length; i++) {
104 | dos.writeInt(piece[i]);
105 | }
106 | dos.writeInt(MAX_PLY);
107 | dos.writeInt(nodecount);
108 | dos.writeInt(brandtotal);
109 | dos.writeInt(gencount);
110 | dos.writeInt(ply);
111 | dos.writeInt(side);
112 | dos.writeInt(xside);
113 | dos.writeInt(computerside);
114 |
115 | dos.writeInt(newmove.from);
116 | dos.writeInt(newmove.dest);
117 |
118 | for (int i = 0; i < gen_dat.length; i++) {
119 | dos.writeInt(gen_dat[i].m.from);
120 | dos.writeInt(gen_dat[i].m.dest);
121 | }
122 | for (int i = 0; i < gen_begin.length; i++) {
123 | dos.writeInt(gen_begin[i]);
124 | }
125 | for (int i = 0; i < gen_end.length; i++) {
126 | dos.writeInt(gen_end[i]);
127 | }
128 | for (int i = 0; i < hist_dat.length; i++) {
129 | dos.writeInt(hist_dat[i].m.from);
130 | dos.writeInt(hist_dat[i].m.dest);
131 | dos.writeInt(hist_dat[i].capture);
132 | }
133 |
134 | dos.writeInt(hdp);
135 | }
136 |
137 | public void restoreStatus(DataInputStream dis) throws IOException {
138 | for (int i = 0; i < color.length; i++) {
139 | color[i] = dis.readInt();
140 | }
141 | for (int i = 0; i < piece.length; i++) {
142 | piece[i] = dis.readInt();
143 | }
144 | MAX_PLY = dis.readInt();
145 | nodecount = dis.readInt();
146 | brandtotal = dis.readInt();
147 | gencount = dis.readInt();
148 | ply = dis.readInt();
149 | side = dis.readInt();
150 | xside = dis.readInt();
151 | computerside = dis.readInt();
152 |
153 | newmove.from = dis.readInt();
154 | newmove.dest = dis.readInt();
155 |
156 | for (int i = 0; i < gen_dat.length; i++) {
157 | gen_dat[i].m.from = dis.readInt();
158 | gen_dat[i].m.dest = dis.readInt();
159 | }
160 | for (int i = 0; i < gen_begin.length; i++) {
161 | gen_begin[i] = dis.readInt();
162 | }
163 | for (int i = 0; i < gen_end.length; i++) {
164 | gen_end[i] = dis.readInt();
165 | }
166 | for (int i = 0; i < hist_dat.length; i++) {
167 | hist_dat[i].m.from = dis.readInt();
168 | hist_dat[i].m.dest = dis.readInt();
169 | hist_dat[i].capture = dis.readInt();
170 | }
171 |
172 | hdp = dis.readInt();
173 | }
174 | /**** MOVE GENERATE ****/
175 | //[7][8] possible positions offset
176 | final int[][] offset = {
177 | {-1, 1,13, 0, 0, 0, 0, 0}, /* PAWN {for DARK side} */
178 | {-12,-14,12,14,0,0,0,0}, /* BISHOP */
179 | {-28,-24,24,28, 0, 0, 0, 0 }, /* ELEPHAN */
180 | {-11,-15,-25,-27,11,15,25,27}, /* KNIGHT */
181 | {-1, 1,-13,13, 0, 0, 0, 0}, /* CANNON */
182 | {-1, 1,-13,13, 0, 0, 0, 0}, /* ROOK */
183 | {-1, 1,-13,13, 0, 0, 0, 0}/* KING */
184 | };
185 |
186 | //14*13,10*9
187 | final int[] mailbox182 = {
188 | -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
189 | -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
190 | -1,-1, 0, 1, 2, 3, 4, 5, 6, 7, 8,-1,-1,
191 | -1,-1, 9,10,11,12,13,14,15,16,17,-1,-1,
192 | -1,-1,18,19,20,21,22,23,24,25,26,-1,-1,
193 | -1,-1,27,28,29,30,31,32,33,34,35,-1,-1,
194 | -1,-1,36,37,38,39,40,41,42,43,44,-1,-1,
195 | -1,-1,45,46,47,48,49,50,51,52,53,-1,-1,
196 | -1,-1,54,55,56,57,58,59,60,61,62,-1,-1,
197 | -1,-1,63,64,65,66,67,68,69,70,71,-1,-1,
198 | -1,-1,72,73,74,75,76,77,78,79,80,-1,-1,
199 | -1,-1,81,82,83,84,85,86,87,88,89,-1,-1,
200 | -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
201 | -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1
202 | };
203 |
204 | //positions in mailbox182 10*9
205 | final int[] mailbox90 = {
206 | 28, 29, 30, 31, 32, 33, 34, 35, 36,//+5
207 | 41, 42, 43, 44, 45, 46, 47, 48, 49,
208 | 54, 55, 56, 57, 58, 59, 60, 61, 62,
209 | 67, 68, 69, 70, 71, 72, 73, 74, 75,
210 | 80, 81, 82, 83, 84, 85, 86, 87, 88,
211 | 93, 94, 95, 96, 97, 98, 99,100,101,
212 | 106, 107,108,109,110,111,112,113,114,
213 | 119, 120,121,122,123,124,125,126,127,
214 | 132, 133,134,135,136,137,138,139,140,
215 | 145, 146,147,148,149,150,151,152,153
216 | };
217 |
218 | final int[] legalposition = {
219 | 1, 1, 5, 3, 3, 3, 5, 1, 1,
220 | 1, 1, 1, 3, 3, 3, 1, 1, 1,
221 | 5, 1, 1, 3, 7, 3, 1, 1, 5,
222 | 1, 1, 1, 1, 1, 1, 1, 1, 1,
223 | 9, 1,13, 1, 9, 1,13, 1, 9,
224 | 9, 9, 9, 9, 9, 9, 9, 9, 9,
225 | 9, 9, 9, 9, 9, 9, 9, 9, 9,
226 | 9, 9, 9, 9, 9, 9, 9, 9, 9,
227 | 9, 9, 9, 9, 9, 9, 9, 9, 9,
228 | 9, 9, 9, 9, 9, 9, 9, 9, 9
229 | };
230 |
231 | final int[] maskpiece = {8, 2, 4, 1, 1, 1, 2};
232 | final int[] knightcheck = {1,-1,-9,-9,-1,1,9,9};
233 | final int[] elephancheck = {-10,-8,8,10,0,0,0,0};
234 | final int[] kingpalace = {3,4,5,12,13,14,21,22,23};//possible positions for computer side
235 |
236 |
237 | public AI() {
238 | gen_dat = new Recorder[MOVE_STACK];
239 | for (int i = 0; i < gen_dat.length; i++) {
240 | gen_dat[i] = new Recorder();
241 | }
242 | hist_dat = new History[HIST_STACK];
243 | for (int i = 0; i < hist_dat.length; i++) {
244 | hist_dat[i] = new History();
245 | }
246 | }
247 | public void init() {
248 | gen_begin[0] = 0;
249 | ply = 0;
250 | hdp = 0;
251 | side = LIGHT;
252 | xside = DARK;
253 | computerside = DARK;
254 |
255 | int[] clr = {
256 | 0, 0, 0, 0, 0, 0, 0, 0, 0,
257 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
258 | 7, 0, 7, 7, 7, 7, 7, 0, 7,
259 | 0, 7, 0, 7, 0, 7, 0, 7, 0,
260 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
261 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
262 | 1, 7, 1, 7, 1, 7, 1, 7, 1,
263 | 7, 1, 7, 7, 7, 7, 7, 1, 7,
264 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
265 | 1, 1, 1, 1, 1, 1, 1, 1, 1
266 | };
267 | int[] pc = {
268 | 5, 3, 2, 1, 6, 1, 2, 3, 5,
269 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
270 | 7, 4, 7, 7, 7, 7, 7, 4, 7,
271 | 0, 7, 0, 7, 0, 7, 0, 7, 0,
272 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
273 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
274 | 0, 7, 0, 7, 0, 7, 0, 7, 0,
275 | 7, 4, 7, 7, 7, 7, 7, 4, 7,
276 | 7, 7, 7, 7, 7, 7, 7, 7, 7,
277 | 5, 3, 2, 1, 6, 1, 2, 3, 5
278 | };
279 | System.arraycopy(clr, 0, color, 0, clr.length);
280 | System.arraycopy(pc, 0, piece, 0, pc.length);
281 | }
282 | //check whether computer's King will be killed by opponent's King directly
283 | // after computer moves King,
284 | int kingFace(int from, int dest)
285 | {
286 | int i, k, t, r = 0;
287 | i = from % SIZE_X;
288 | if (i>=3 && i<=5 && piece[dest]!=KING)
289 | {
290 | t = piece[dest]; piece[dest] = piece[from]; piece[from] = EMPTY;//make the move
291 | i = 0;
292 | for (k=kingpalace[i]; piece[k]!=KING; k++) ;
293 | for (k += SIZE_X; k alpha) alpha = best;
422 |
423 | if (move(gen_dat[i].m)) value = 1000-ply;
424 | else value = -alphabeta(-beta, -alpha, depth-1);
425 | unmove();
426 |
427 | if (value > best)
428 | {
429 | best = value;
430 | if (ply == 0) {
431 | newmove.from = gen_dat[i].m.from;
432 | newmove.dest = gen_dat[i].m.dest;
433 | }
434 | }
435 | }
436 |
437 | return best;
438 | }
439 | //real move
440 | public boolean updateNewMove()
441 | {
442 | int from, dest, p;
443 | from = newmove.from; dest = newmove.dest; p = piece[dest];
444 | piece[dest] = piece[from]; piece[from] = EMPTY;
445 | color[dest] = color[from]; color[from] = EMPTY;
446 | return p == KING;
447 | }
448 |
449 | //
450 | public int takeAMove(int from , int to) {
451 | generateMoves();
452 | newmove.from = from;
453 | newmove.dest = to;
454 | int ret = MOVE_INVALID;
455 | for (int i=gen_begin[ply]; i= AI.BOARD_SIZE || index < 0) {
120 | return -1;
121 | }
122 | return index;
123 | }
124 | private PointF chessIndex2CanvasCoord(int i) {
125 | PointF point = new PointF(chessIndex2LogicPoint(i));
126 | point.x *= mLaticeLen ;
127 | point.x += mStartBoardX;
128 | point.y *= mLaticeLen ;
129 | point.y += mStartBoardY;
130 | return point;
131 | }
132 | private Point chessIndex2LogicPoint(int i) {
133 | return new Point(i%9,i/9);
134 | }
135 |
136 | @Override
137 | protected void onDraw(Canvas canvas) {
138 | if (mLaticeLen <0) {
139 | // load chess images
140 | Bitmap chessBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.qz);
141 |
142 | mLaticeLen = getWidth() * 35 /320.0f;
143 | mChesslen = mLaticeLen * 19.0f / 20;
144 | mLaticeLen2 = mLaticeLen/2.0f;
145 | mChessLen2 = mChesslen /2.0f;
146 |
147 | mStartBoardX = getWidth() * 20.0f / 320;
148 | mStartBoardY = getHeight() * 20.0f /354;
149 |
150 | int stepH = chessBitmap.getHeight() / 3;
151 | int stepW = chessBitmap.getWidth() / 14;
152 | for (int i = 0; i < 7; i++) {
153 | mChessBitmaps[AI.LIGHT][i] = Bitmap.createBitmap(chessBitmap, i * stepW, 0, stepW, stepH);
154 | mChessBitmaps[AI.DARK][i] = Bitmap.createBitmap(chessBitmap, (i+7) * stepW, 0, stepW, stepH);
155 | }
156 | chessBitmap = mChessBitmaps[0][0];
157 | mChessBitmaps[0][0] = mChessBitmaps[0][6];
158 | mChessBitmaps[0][6] = chessBitmap;
159 | chessBitmap = mChessBitmaps[1][0];
160 | mChessBitmaps[1][0] = mChessBitmaps[1][6];
161 | mChessBitmaps[1][6] = chessBitmap;
162 | chessBitmap = mChessBitmaps[0][4];
163 | mChessBitmaps[0][4] = mChessBitmaps[0][5];
164 | mChessBitmaps[0][5] = chessBitmap;
165 | chessBitmap = mChessBitmaps[1][4];
166 | mChessBitmaps[1][4] = mChessBitmaps[1][5];
167 | mChessBitmaps[1][5] = chessBitmap;
168 |
169 | mSelectBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.sel);
170 | }
171 |
172 | // draw each chess
173 | for(int i =0 ; i < AI.BOARD_SIZE ; i++) {
174 | if (mPieces[i] != AI.EMPTY) {
175 | PointF point = chessIndex2CanvasCoord(i);
176 | Bitmap bmp = mChessBitmaps[mColors[i]][mPieces[i]];
177 | canvas.drawBitmap(bmp, null,new RectF(point.x - mChessLen2, point.y - mChessLen2, point.x + mChessLen2, point.y + mChessLen2), null);
178 | }
179 | }
180 |
181 | // draw selected positions
182 | if (mChessFrom >=0 ) {
183 | PointF point = chessIndex2CanvasCoord(mChessFrom);
184 | canvas.drawBitmap(mSelectBitmap, null,new RectF(point.x - mChessLen2, point.y - mChessLen2, point.x + mChessLen2, point.y + mChessLen2), null);
185 | }
186 | if (mChessTo >=0 ) {
187 | PointF point = chessIndex2CanvasCoord(mChessTo);
188 | canvas.drawBitmap(mSelectBitmap, null,new RectF(point.x - mChessLen2, point.y - mChessLen2, point.x + mChessLen2, point.y + mChessLen2), null);
189 | }
190 | super.onDraw(canvas);
191 | }
192 |
193 | public void setAILevel(int depth) {
194 | mAi.setSearchDepth(depth);
195 | }
196 | void newGame() {
197 | mAi.init();
198 | mChessFrom = -1;
199 | mChessTo = -1;
200 | mIsComputerThinking = false;
201 |
202 | System.arraycopy(mAi.piece, 0, mPieces, 0, mPieces.length);
203 | System.arraycopy(mAi.color, 0, mColors, 0, mColors.length);
204 | mInfoTextView.setText(getResources().getString(R.string.welcome));
205 | postInvalidate();
206 | }
207 |
208 | void saveGameStatus() {
209 | try {
210 |
211 | // File file = new File(SAVE_STATE_FILE_NAME);
212 | // FileOutputStream fos = new FileOutputStream(file);
213 | FileOutputStream fos = mContext.openFileOutput(SAVE_STATE_FILE_NAME, Context.MODE_PRIVATE);
214 | DataOutputStream dos = new DataOutputStream(fos);
215 |
216 | dos.writeInt(mChessFrom);
217 | dos.writeInt(mChessTo);
218 |
219 | mAi.saveStatus(dos);
220 |
221 | dos.close();
222 | fos.close();
223 | } catch (FileNotFoundException e) {
224 | // TODO Auto-generated catch block
225 | e.printStackTrace();
226 | } catch (IOException e) {
227 | // TODO Auto-generated catch block
228 | e.printStackTrace();
229 | }
230 |
231 | }
232 |
233 | void restoreGameStatus() {
234 | try {
235 | // File file = new File(SAVE_STATE_FILE_NAME);
236 | // FileInputStream fis = new FileInputStream(file);
237 | FileInputStream fis = mContext.openFileInput(SAVE_STATE_FILE_NAME);
238 | DataInputStream dis = new DataInputStream(fis);
239 |
240 | mChessFrom = dis.readInt();
241 | mChessTo = dis.readInt();
242 |
243 | mAi.restoreStatus(dis);
244 |
245 | System.arraycopy(mAi.piece, 0, mPieces, 0, mPieces.length);
246 | System.arraycopy(mAi.color, 0, mColors, 0, mColors.length);
247 | mIsComputerThinking = false;
248 | } catch (FileNotFoundException e) {
249 | newGame();
250 | e.printStackTrace();
251 | } catch (IOException e) {
252 | newGame();
253 | e.printStackTrace();
254 | }
255 | }
256 |
257 | @Override
258 | public boolean onTouchEvent(MotionEvent event) {
259 | if (!mIsComputerThinking && event.getAction() == MotionEvent.ACTION_DOWN) {
260 | final int chess = canvasCoord2ChessIndex(new PointF(event.getX(),event.getY()));
261 | Log.d("lzj", "chess index clicked : "+ chess);
262 | if (chess >0 ) {
263 | if (mChessFrom >= 0 && mChessTo >= 0 || mChessFrom < 0) {
264 | if (mAi.color[chess] == USER_COLOR) {
265 | mChessFrom = chess;
266 | mChessTo = -1;
267 | invalidate();
268 | }
269 | }else if( mChessFrom >= 0 && mChessTo < 0 && mAi.color[chess] == USER_COLOR){
270 | mChessFrom = chess;
271 | invalidate();
272 | }else if (mChessTo < 0) {
273 | Log.d("lzj", "second click, from: " + mChessFrom + ", to: "+chess);
274 | //human move
275 | int ret = mAi.takeAMove(mChessFrom, chess);
276 | if (ret == AI.MOVE_OK) {
277 | Log.d("lzj", "human move ok");
278 | mChessTo = chess;
279 | System.arraycopy(mAi.piece, 0, mPieces, 0, mPieces.length);
280 | System.arraycopy(mAi.color, 0, mColors, 0, mColors.length);
281 | invalidate();
282 |
283 | mIsComputerThinking = true;
284 | mInfoTextView.setText(getResources().getString(R.string.computer_move));
285 | new Thread(new Runnable() {
286 |
287 | public void run() {
288 | // computer move
289 | int ret = mAi.computerMove();
290 | Move move = mAi.getComputerMove();
291 | mChessFrom = move.from;
292 | mChessTo = move.dest;
293 | System.arraycopy(mAi.piece, 0, mPieces, 0, mPieces.length);
294 | System.arraycopy(mAi.color, 0, mColors, 0, mColors.length);
295 | postInvalidate();
296 | mIsComputerThinking = false;
297 |
298 | Message msg = mMessageHandler.obtainMessage(MSG_COMPUTER_MOVE_DONE);
299 | mMessageHandler.sendMessage(msg);
300 |
301 | if (ret == AI.MOVE_WIN) {
302 | msg = mMessageHandler.obtainMessage(MSG_COMPUTER_WIN);
303 | mMessageHandler.sendMessage(msg);
304 | }
305 | }
306 | }).start();
307 | } else if (ret == AI.MOVE_WIN) {
308 | Message msg = mMessageHandler.obtainMessage(MSG_USER_WIN);
309 | mMessageHandler.sendMessage(msg);
310 | }
311 | Log.d("lzj", "takeAMove ret : " + ret);
312 | }
313 | }
314 | }
315 | return super.onTouchEvent(event);
316 | }
317 | class MessageHandler extends Handler {
318 | public void handleMessage(Message msg){
319 | Log.d("lzj", "message hander : msg.what = " + msg.what);
320 | switch (msg.what) {
321 | case MSG_USER_MOVE_DONE:
322 | break;
323 | case MSG_COMPUTER_MOVE_DONE:
324 | invalidate();
325 | mInfoTextView.setText(getResources().getString(R.string.user_move));
326 | break;
327 | case MSG_COMPUTER_WIN:
328 | mAlertDialogBuilder.setMessage(getResources().getString(R.string.computer_win));
329 | mAlertDialogBuilder.create().show();
330 | break;
331 | case MSG_USER_WIN:
332 | mAlertDialogBuilder.setMessage(getResources()
333 | .getString(R.string.user_win));
334 | mAlertDialogBuilder.create().show();
335 | break;
336 | default:
337 | break;
338 | }
339 | }
340 | }
341 | }
342 |
--------------------------------------------------------------------------------
/src/com/onezeros/chinesechess/ChineseChessActivity.java:
--------------------------------------------------------------------------------
1 | /*
2 | * ChineseChess4Android
3 | *
4 | * Copyright (c) 2012 Zhijie Lee
5 | *
6 | * The MIT License (MIT)
7 | *
8 | * Permission is hereby granted, free of charge, to any person obtaining a copy of
9 | * this software and associated documentation files (the "Software"), to deal in
10 | * the Software without restriction, including without limitation the rights to
11 | * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
12 | * the Software, and to permit persons to whom the Software is furnished to do so,
13 | * subject to the following conditions:
14 | *
15 | * The above copyright notice and this permission notice shall be included in all
16 | * copies or substantial portions of the Software.
17 | *
18 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
20 | * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
21 | * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
22 | * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
23 | * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 | */
25 | package com.onezeros.chinesechess;
26 |
27 | import cn.domob.android.ads.DomobAdView;
28 | import cn.domob.android.ads.DomobUpdater;
29 |
30 | import com.android.chinesechess.R;
31 | import com.umeng.analytics.MobclickAgent;
32 |
33 | import android.app.Activity;
34 | import android.app.Dialog;
35 | import android.os.Bundle;
36 | import android.view.Menu;
37 | import android.view.MenuInflater;
38 | import android.view.MenuItem;
39 | import android.view.View;
40 | import android.view.View.OnClickListener;
41 | import android.widget.Button;
42 | import android.widget.LinearLayout;
43 | import android.widget.RelativeLayout;
44 | import android.widget.TextView;
45 |
46 | public class ChineseChessActivity extends Activity {
47 | public static final String DOMOB_PUBLISHER_ID_STRING = "56OJyOeouMzH2P6sIM";
48 |
49 | ChessboardView mChessboardView;
50 | RelativeLayout mMainLayout;
51 | LinearLayout mMenuLayout;
52 | Button mNewGameButton;
53 | Button mContinueButton;
54 | TextView mInfoTextView;
55 | boolean mIsUIStart = true;
56 |
57 | @Override
58 | public void onCreate(Bundle savedInstanceState) {
59 | super.onCreate(savedInstanceState);
60 | setContentView(R.layout.main);
61 |
62 | mMainLayout = (RelativeLayout)findViewById(R.id.mainview);
63 | mMenuLayout = (LinearLayout)findViewById(R.id.menu_view);
64 | mNewGameButton = (Button)findViewById(R.id.new_game_btn);
65 | mContinueButton = (Button)findViewById(R.id.restore_game_btn);
66 |
67 | mChessboardView = (ChessboardView)findViewById(R.id.chessboard);
68 |
69 | mInfoTextView = (TextView)findViewById(R.id.info_tv);
70 | mChessboardView.setInfoTextview(mInfoTextView);
71 |
72 | mNewGameButton.setOnClickListener(new OnClickListener() {
73 |
74 | public void onClick(View v) {
75 | mChessboardView.newGame();
76 | switchViewTo(mMainLayout);
77 | mIsUIStart = false;
78 | }
79 | });
80 | mContinueButton.setOnClickListener(new OnClickListener() {
81 |
82 | public void onClick(View v) {
83 | if (mIsUIStart) {
84 | mChessboardView.restoreGameStatus();
85 | }
86 | switchViewTo(mMainLayout);
87 | mIsUIStart = false;
88 | }
89 | });
90 |
91 | // domob ad
92 | LinearLayout layout = (LinearLayout)findViewById(R.id.AdLinearLayout);
93 | DomobAdView adView = new DomobAdView(this,DOMOB_PUBLISHER_ID_STRING,DomobAdView.INLINE_SIZE_320X50);
94 | layout.addView(adView);
95 |
96 | DomobUpdater.checkUpdate(this, DOMOB_PUBLISHER_ID_STRING);
97 | }
98 |
99 | void switchViewTo(View v) {
100 | if (v == mMainLayout) {
101 | mMenuLayout.setVisibility(View.INVISIBLE);
102 | mMainLayout.setVisibility(View.VISIBLE);
103 | }else if (v == mMenuLayout) {
104 | mMenuLayout.setVisibility(View.VISIBLE);
105 | mMainLayout.setVisibility(View.INVISIBLE);
106 | }
107 | }
108 | @Override
109 | public void onBackPressed() {
110 | if (mMainLayout.getVisibility() == View.VISIBLE) {
111 | switchViewTo(mMenuLayout);
112 | }else {
113 | super.onBackPressed();
114 | }
115 | }
116 |
117 | @Override
118 | protected void onPause() {
119 | super.onPause();
120 | MobclickAgent.onPause(this);
121 | mChessboardView.saveGameStatus();
122 | }
123 |
124 | @Override
125 | protected void onResume() {
126 | super.onResume();
127 | MobclickAgent.onResume(this);
128 | }
129 | @Override
130 | public boolean onCreateOptionsMenu(Menu menu) {
131 | MenuInflater inflater = new MenuInflater(this);
132 | inflater.inflate(R.menu.option_menu, menu);
133 | return true;
134 | }
135 |
136 | @Override
137 | public boolean onOptionsItemSelected(MenuItem item) {
138 |
139 | switch (item.getItemId()) {
140 | case R.id.level1_menu:
141 | mChessboardView.setAILevel(3);
142 | mChessboardView.newGame();
143 | break;
144 | case R.id.level2_menu:
145 | mChessboardView.setAILevel(4);
146 | mChessboardView.newGame();
147 | break;
148 | case R.id.level3_menu:
149 | mChessboardView.setAILevel(5);
150 | mChessboardView.newGame();
151 | break;
152 | case R.id.about_menu:
153 | Dialog dialog = new Dialog(this);
154 | dialog.setContentView(R.layout.dialog);
155 | dialog.setTitle(R.string.about_title);
156 | dialog.show();
157 | break;
158 | default:
159 | break;
160 | }
161 | return super.onOptionsItemSelected(item);
162 | }
163 | }
--------------------------------------------------------------------------------