Commit | Line | Data |
---|---|---|
7379efc5 BA |
1 | import ChessRules from "/base_rules.js"; |
2 | ||
3 | export default class CwdaRules extends ChessRules { | |
4 | ||
5 | static get Options() { | |
6 | return { | |
7 | select: ChessRules.Options.select.concat([ | |
8 | { | |
9 | label: "Army 1", | |
10 | variable: "army1", | |
11 | defaut: 'C', | |
12 | options: [ | |
13 | { label: "Colorbound Clobberers", value: 'C' }, | |
14 | { label: "Nutty Knights", value: 'N' }, | |
15 | { label: "Remarkable Rookies", value: 'R' }, | |
16 | { label: "Fide", value: 'F' } | |
17 | ] | |
18 | }, | |
19 | { | |
20 | label: "Army 2", | |
21 | variable: "army2", | |
22 | defaut: 'C', | |
23 | options: [ | |
24 | { label: "Colorbound Clobberers", value: 'C' }, | |
25 | { label: "Nutty Knights", value: 'N' }, | |
26 | { label: "Remarkable Rookies", value: 'R' }, | |
27 | { label: "Fide", value: 'F' } | |
28 | ] | |
29 | } | |
30 | ]), | |
31 | input: ChessRules.Options.input, | |
32 | styles: ChessRules.Options.styles | |
33 | }; | |
34 | } | |
35 | ||
36 | static get PiecesMap() { | |
37 | return { | |
38 | // Colorbound Clobberers | |
39 | 'C': { | |
40 | 'r': 'd', | |
41 | 'n': 'w', | |
42 | 'b': 'f', | |
43 | 'q': 'c', | |
44 | 'k': 'm', | |
45 | 'p': 'z' | |
46 | }, | |
47 | // Nutty Knights | |
48 | 'N': { | |
49 | 'r': 'g', | |
50 | 'n': 'i', | |
51 | 'b': 't', | |
52 | 'q': 'l', | |
53 | 'k': 'e', | |
54 | 'p': 'v' | |
55 | }, | |
56 | // Remarkable Rookies | |
57 | 'R': { | |
58 | 'r': 's', | |
59 | 'n': 'y', | |
60 | 'b': 'h', | |
61 | 'q': 'o', | |
62 | 'k': 'a', | |
63 | 'p': 'u' | |
64 | } | |
65 | }; | |
66 | } | |
67 | ||
68 | genRandInitBaseFen() { | |
69 | let s = FenUtil.setupPieces( | |
70 | ['r', 'n', 'b', 'q', 'k', 'b', 'n', 'r'], | |
71 | { | |
72 | randomness: this.options["randomness"], | |
73 | between: [{p1: 'k', p2: 'r'}], | |
74 | diffCol: ['b'], | |
75 | flags: ['r', 'k'] | |
76 | } | |
77 | ); | |
78 | let pawnLines = { | |
79 | w: "pppppppp", | |
80 | b: "pppppppp" | |
81 | }; | |
82 | for (const c of ['w', 'b']) { | |
83 | const army = "army" + (c == 'w' ? "1" : "2"); | |
84 | if (this.options[army] != 'F') { | |
85 | for (let obj of [s, pawnLines]) { | |
86 | obj[c] = obj[c].split("") | |
87 | .map(p => V.PiecesMap[this.options[army]][p]).join(""); | |
88 | } | |
89 | } | |
90 | } | |
91 | return { | |
92 | fen: s.b.join("") + "/" + | |
93 | pawnLines['b'] + "/8/8/8/8/" + pawnLines['w'].toUpperCase() + | |
94 | "/" + s.w.join("").toUpperCase(), | |
95 | o: {flags: s.flags} | |
96 | }; | |
97 | } | |
98 | ||
99 | getPartFen(o) { | |
100 | return Object.assign( | |
101 | { "armies": this.options["army1"] + this.options["army2"] }, | |
102 | super.getPartFen(o) | |
103 | ); | |
104 | } | |
105 | ||
106 | setOtherVariables(fenParsed) { | |
107 | super.setOtherVariables(fenParsed); | |
108 | this.army1 = fenParsed.armies.charAt(0); | |
109 | this.army2 = fenParsed.armies.charAt(1); | |
110 | } | |
111 | ||
112 | isKing(x, y, p) { | |
113 | if (!p) | |
114 | p = this.getPiece(x, y); | |
115 | return (super.isKing(x, y, p) || ['a', 'e', 'm'].includes(p)); | |
116 | } | |
117 | ||
118 | // Helper to describe pieces movements | |
119 | static get steps() { | |
120 | return { | |
121 | // Dabbabah | |
122 | 'd': [ | |
123 | [-2, 0], | |
124 | [0, -2], | |
125 | [2, 0], | |
126 | [0, 2] | |
127 | ], | |
128 | // Alfil | |
129 | 'a': [ | |
130 | [2, 2], | |
131 | [2, -2], | |
132 | [-2, 2], | |
133 | [-2, -2] | |
134 | ], | |
135 | // Ferz | |
136 | 'f': [ | |
137 | [1, 1], | |
138 | [1, -1], | |
139 | [-1, 1], | |
140 | [-1, -1] | |
141 | ], | |
142 | // Wazir | |
143 | 'w': [ | |
144 | [-1, 0], | |
145 | [0, -1], | |
146 | [1, 0], | |
147 | [0, 1] | |
148 | ], | |
149 | // Threeleaper | |
150 | '$3': [ | |
151 | [-3, 0], | |
152 | [0, -3], | |
153 | [3, 0], | |
154 | [0, 3] | |
155 | ], | |
156 | // Narrow knight | |
157 | '$n': [ | |
158 | [-2, -1], | |
159 | [-2, 1], | |
160 | [2, -1], | |
161 | [2, 1] | |
162 | ] | |
163 | }; | |
164 | } | |
165 | ||
166 | pieces(color, x, y) { | |
167 | const res = super.pieces(color, x, y); | |
168 | return Object.assign( | |
169 | { | |
170 | 'd': { | |
171 | "class": "c_rook", | |
172 | both: [ | |
173 | {steps: V.steps.b}, | |
174 | {steps: V.steps.d, range: 1} | |
175 | ] | |
176 | }, | |
177 | 'w': { | |
178 | "class": "c_knight", | |
179 | both: [ | |
180 | {steps: V.steps.a, range: 1}, | |
181 | {steps: V.steps.r, range: 1} | |
182 | ] | |
183 | }, | |
184 | 'f': { | |
185 | "class": "c_bishop", | |
186 | both: [ | |
187 | {steps: V.steps.d, range: 1}, | |
188 | {steps: V.steps.a, range: 1}, | |
189 | {steps: V.steps.b, range: 1} | |
190 | ] | |
191 | }, | |
192 | 'c': { | |
193 | "class": "c_queen", | |
194 | both: [ | |
195 | {steps: V.steps.b}, | |
196 | {steps: V.steps.n, range: 1} | |
197 | ] | |
198 | }, | |
199 | 'm': { moveas: 'k' }, | |
200 | 'z': { moveas: 'p' }, | |
201 | 'g': { | |
202 | ||
203 | }, | |
204 | 'i': { | |
205 | ||
206 | }, | |
207 | 't': { | |
208 | ||
209 | }, | |
210 | 'l': { | |
211 | ||
212 | }, | |
213 | 'e': { moveas: 'k' }, | |
214 | 'v': { moveas: 'p' }, | |
215 | 's': { | |
216 | ||
217 | }, | |
218 | 'y': { | |
219 | ||
220 | }, | |
221 | 'h': { | |
222 | ||
223 | }, | |
224 | 'o': { | |
225 | ||
226 | }, | |
227 | 'a': { moveas: 'k' }, | |
228 | 'u': { moveas: 'p' } | |
229 | }, | |
230 | res | |
231 | ); | |
232 | ||
233 | ||
234 | ||
235 | ||
236 | ||
237 | getPotentialN_rookMoves(sq) { | |
238 | const c = this.turn; | |
239 | const rookSteps = [ [0, -1], [0, 1], [c == 'w' ? -1 : 1, 0] ]; | |
240 | const backward = (c == 'w' ? 1 : -1); | |
241 | const kingSteps = [ [backward, -1], [backward, 0], [backward, 1] ]; | |
242 | return ( | |
243 | this.getSlideNJumpMoves(sq, rookSteps).concat( | |
244 | this.getSlideNJumpMoves(sq, kingSteps, 1)) | |
245 | ); | |
246 | } | |
247 | ||
248 | getPotentialN_knightMoves(sq) { | |
249 | return ( | |
250 | this.getSlideNJumpMoves(sq, V.steps.$n, 1).concat( | |
251 | this.getSlideNJumpMoves(sq, V.steps.f, 1)) | |
252 | ); | |
253 | } | |
254 | ||
255 | getPotentialN_bishopMoves(sq) { | |
256 | const backward = (this.turn == 'w' ? 1 : -1); | |
257 | const kingSteps = [ | |
258 | [0, -1], [0, 1], [backward, -1], [backward, 0], [backward, 1] | |
259 | ]; | |
260 | const forward = -backward; | |
261 | const knightSteps = [ | |
262 | [2*forward, -1], [2*forward, 1], [forward, -2], [forward, 2] | |
263 | ]; | |
264 | return ( | |
265 | this.getSlideNJumpMoves(sq, knightSteps, 1).concat( | |
266 | this.getSlideNJumpMoves(sq, kingSteps, 1)) | |
267 | ); | |
268 | } | |
269 | ||
270 | getPotentialN_queenMoves(sq) { | |
271 | const backward = (this.turn == 'w' ? 1 : -1); | |
272 | const forward = -backward; | |
273 | const kingSteps = [ | |
274 | [forward, -1], [forward, 1], | |
275 | [backward, -1], [backward, 0], [backward, 1] | |
276 | ]; | |
277 | const knightSteps = [ | |
278 | [2*forward, -1], [2*forward, 1], [forward, -2], [forward, 2] | |
279 | ]; | |
280 | const rookSteps = [ [0, -1], [0, 1], [forward, 0] ]; | |
281 | return ( | |
282 | this.getSlideNJumpMoves(sq, rookSteps).concat( | |
283 | this.getSlideNJumpMoves(sq, kingSteps, 1)).concat( | |
284 | this.getSlideNJumpMoves(sq, knightSteps, 1)) | |
285 | ); | |
286 | } | |
287 | ||
288 | getPotentialR_rookMoves(sq) { | |
289 | return this.getSlideNJumpMoves(sq, V.steps.r, 4); | |
290 | } | |
291 | ||
292 | getPotentialR_knightMoves(sq) { | |
293 | return ( | |
294 | this.getSlideNJumpMoves(sq, V.steps.d, 1).concat( | |
295 | this.getSlideNJumpMoves(sq, V.steps.w, 1)) | |
296 | ); | |
297 | } | |
298 | ||
299 | getPotentialR_bishopMoves(sq) { | |
300 | return ( | |
301 | this.getSlideNJumpMoves(sq, V.steps.d, 1).concat( | |
302 | this.getSlideNJumpMoves(sq, V.steps.f, 1)).concat( | |
303 | this.getSlideNJumpMoves(sq, V.steps.$3, 1)) | |
304 | ); | |
305 | } | |
306 | ||
307 | getPotentialR_queenMoves(sq) { | |
308 | return ( | |
309 | this.getSlideNJumpMoves(sq, V.steps.r).concat( | |
310 | this.getSlideNJumpMoves(sq, V.steps.n, 1)) | |
311 | ); | |
312 | } | |
313 | ||
314 | case V.PAWN: { | |
315 | // Can promote in anything from the two current armies | |
316 | let promotions = []; | |
317 | for (let army of ["army1", "army2"]) { | |
318 | if (army == "army2" && this.army2 == this.army1) break; | |
319 | switch (this[army]) { | |
320 | case 'C': { | |
321 | Array.prototype.push.apply(promotions, | |
322 | [V.C_ROOK, V.C_KNIGHT, V.C_BISHOP, V.C_QUEEN]); | |
323 | break; | |
324 | } | |
325 | case 'N': { | |
326 | Array.prototype.push.apply(promotions, | |
327 | [V.N_ROOK, V.N_KNIGHT, V.N_BISHOP, V.N_QUEEN]); | |
328 | break; | |
329 | } | |
330 | case 'R': { | |
331 | Array.prototype.push.apply(promotions, | |
332 | [V.R_ROOK, V.R_KNIGHT, V.R_BISHOP, V.R_QUEEN]); | |
333 | break; | |
334 | } | |
335 | case 'F': { | |
336 | Array.prototype.push.apply(promotions, | |
337 | [V.ROOK, V.KNIGHT, V.BISHOP, V.QUEEN]); | |
338 | break; | |
339 | } | |
340 | } | |
341 | } | |
342 | return super.getPotentialPawnMoves(sq, promotions); | |
343 | } | |
344 | default: return super.getPotentialMovesFrom(sq); | |
345 | } | |
346 | ||
347 | getCastleMoves([x, y]) { | |
348 | const color = this.getColor(x, y); | |
349 | let finalSquares = [ [2, 3], [V.size.y - 2, V.size.y - 3] ]; | |
350 | if ( | |
351 | (color == 'w' && this.army1 == 'C') || | |
352 | (color == 'b' && this.army2 == 'C') | |
353 | ) { | |
354 | // Colorbound castle long in an unusual way: | |
355 | finalSquares[0] = [1, 2]; | |
356 | } | |
357 | return super.getCastleMoves([x, y], finalSquares); | |
358 | } | |
359 | ||
360 | }; |