@pompidup/kingdomino-engine 3.2.0 → 3.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +200 -11
- package/dist/index.js +1514 -151
- package/dist/index.js.map +1 -1
- package/dist/index.universal.js +5169 -0
- package/dist/wasm-bridge.js +4287 -0
- package/package.json +3 -2
package/dist/index.js
CHANGED
|
@@ -168,6 +168,25 @@ var wrapWithDebug = (engine, options) => {
|
|
|
168
168
|
engine.getDynastyResults,
|
|
169
169
|
logger,
|
|
170
170
|
level
|
|
171
|
+
),
|
|
172
|
+
placeKnight: wrapMethod(
|
|
173
|
+
"placeKnight",
|
|
174
|
+
engine.placeKnight,
|
|
175
|
+
logger,
|
|
176
|
+
level
|
|
177
|
+
),
|
|
178
|
+
constructBuilding: wrapMethod(
|
|
179
|
+
"constructBuilding",
|
|
180
|
+
engine.constructBuilding,
|
|
181
|
+
logger,
|
|
182
|
+
level
|
|
183
|
+
),
|
|
184
|
+
useDragon: wrapMethod("useDragon", engine.useDragon, logger, level),
|
|
185
|
+
skipOptionalAction: wrapMethod(
|
|
186
|
+
"skipOptionalAction",
|
|
187
|
+
engine.skipOptionalAction,
|
|
188
|
+
logger,
|
|
189
|
+
level
|
|
171
190
|
)
|
|
172
191
|
};
|
|
173
192
|
};
|
|
@@ -232,7 +251,12 @@ var wrapWithEvents = (engine, callbacks) => ({
|
|
|
232
251
|
callbacks.onGameEnd?.({ game });
|
|
233
252
|
}
|
|
234
253
|
return game;
|
|
235
|
-
}
|
|
254
|
+
},
|
|
255
|
+
// Queendomino methods — pass through (no specific events yet)
|
|
256
|
+
placeKnight: (cmd) => engine.placeKnight(cmd),
|
|
257
|
+
constructBuilding: (cmd) => engine.constructBuilding(cmd),
|
|
258
|
+
useDragon: (cmd) => engine.useDragon(cmd),
|
|
259
|
+
skipOptionalAction: (cmd) => engine.skipOptionalAction(cmd)
|
|
236
260
|
});
|
|
237
261
|
|
|
238
262
|
// src/adapterServerside/consoleLogger.ts
|
|
@@ -261,6 +285,61 @@ var silentLogger = {
|
|
|
261
285
|
}
|
|
262
286
|
};
|
|
263
287
|
|
|
288
|
+
// src/datasources/buildings.json
|
|
289
|
+
var buildings_default = [
|
|
290
|
+
{ id: 1, name: "The Bakery", cost: 1, immediateBonus: { type: "coins", amount: 2 }, crowns: 0, towers: 0 },
|
|
291
|
+
{ id: 2, name: "The Bakery", cost: 1, immediateBonus: { type: "coins", amount: 2 }, crowns: 0, towers: 0 },
|
|
292
|
+
{ id: 3, name: "The Sawmill", cost: 2, crowns: 0, towers: 0, endGameScoring: { type: "perTerrain", terrain: "forest", points: 1 } },
|
|
293
|
+
{ id: 4, name: "The Fishmonger's", cost: 2, immediateBonus: { type: "coins", amount: 1 }, crowns: 0, towers: 0, endGameScoring: { type: "perTerrain", terrain: "sea", points: 1 } },
|
|
294
|
+
{ id: 5, name: "The Fishmonger's", cost: 2, immediateBonus: { type: "coins", amount: 1 }, crowns: 0, towers: 0, endGameScoring: { type: "perTerrain", terrain: "sea", points: 1 } },
|
|
295
|
+
{ id: 6, name: "The Weaving Shop", cost: 3, crowns: 1, towers: 0, endGameScoring: { type: "perTerrain", terrain: "wheat", points: 1 } },
|
|
296
|
+
{ id: 7, name: "The Magic School", cost: 4, crowns: 1, towers: 0, endGameScoring: { type: "perCrown", points: 1 } },
|
|
297
|
+
{ id: 8, name: "The Fountain", cost: 3, crowns: 0, towers: 1, endGameScoring: { type: "perTower", points: 2 } },
|
|
298
|
+
{ id: 9, name: "The Church", cost: 4, crowns: 1, towers: 0, endGameScoring: { type: "perBuilding", points: 2 } },
|
|
299
|
+
{ id: 10, name: "The Bath", cost: 2, immediateBonus: { type: "coins", amount: 1 }, crowns: 0, towers: 0, endGameScoring: { type: "flat", points: 4 } },
|
|
300
|
+
{ id: 11, name: "The Guard Tower", cost: 1, crowns: 0, towers: 1, endGameScoring: { type: "flat", points: 2 } },
|
|
301
|
+
{ id: 12, name: "The Guard Tower", cost: 1, crowns: 0, towers: 1, endGameScoring: { type: "flat", points: 2 } },
|
|
302
|
+
{ id: 13, name: "The Big Tower", cost: 3, crowns: 0, towers: 2, endGameScoring: { type: "flat", points: 4 } },
|
|
303
|
+
{ id: 14, name: "The Guardhouse", cost: 2, crowns: 0, towers: 1, endGameScoring: { type: "perBuilding", points: 1 } },
|
|
304
|
+
{ id: 15, name: "The Fortified Castle", cost: 5, crowns: 2, towers: 1, endGameScoring: { type: "flat", points: 6 } },
|
|
305
|
+
{ id: 16, name: "The Travelling Castle", cost: 3, crowns: 1, towers: 1, endGameScoring: { type: "perTower", points: 1 } },
|
|
306
|
+
{ id: 17, name: "The Travelling Group", cost: 2, immediateBonus: { type: "coins", amount: 1 }, crowns: 0, towers: 0, endGameScoring: { type: "perBuilding", points: 1 } },
|
|
307
|
+
{ id: 18, name: "The Harbour", cost: 3, crowns: 0, towers: 0, endGameScoring: { type: "perTerrain", terrain: "sea", points: 2 } }
|
|
308
|
+
];
|
|
309
|
+
|
|
310
|
+
// src/adapterServerside/jsonBuildings.ts
|
|
311
|
+
var jsonBuildings = () => {
|
|
312
|
+
const buildings = buildings_default.map((b) => {
|
|
313
|
+
const tile = {
|
|
314
|
+
id: b.id,
|
|
315
|
+
name: b.name,
|
|
316
|
+
cost: b.cost,
|
|
317
|
+
crowns: b.crowns,
|
|
318
|
+
towers: b.towers
|
|
319
|
+
};
|
|
320
|
+
if (b.immediateBonus) {
|
|
321
|
+
tile.immediateBonus = {
|
|
322
|
+
type: b.immediateBonus.type,
|
|
323
|
+
amount: b.immediateBonus.amount
|
|
324
|
+
};
|
|
325
|
+
}
|
|
326
|
+
if ("endGameScoring" in b && b.endGameScoring) {
|
|
327
|
+
tile.endGameScoring = {
|
|
328
|
+
type: b.endGameScoring.type,
|
|
329
|
+
points: b.endGameScoring.points,
|
|
330
|
+
..."terrain" in b.endGameScoring && {
|
|
331
|
+
terrain: b.endGameScoring.terrain
|
|
332
|
+
}
|
|
333
|
+
};
|
|
334
|
+
}
|
|
335
|
+
return tile;
|
|
336
|
+
});
|
|
337
|
+
return {
|
|
338
|
+
getAll: () => buildings
|
|
339
|
+
};
|
|
340
|
+
};
|
|
341
|
+
var jsonBuildings_default = jsonBuildings;
|
|
342
|
+
|
|
264
343
|
// src/datasources/dominoes.json
|
|
265
344
|
var dominoes_default = {
|
|
266
345
|
Classic: [
|
|
@@ -314,84 +393,614 @@ var dominoes_default = {
|
|
|
314
393
|
crowns: 0
|
|
315
394
|
},
|
|
316
395
|
right: {
|
|
317
|
-
type: "forest",
|
|
396
|
+
type: "forest",
|
|
397
|
+
crowns: 0
|
|
398
|
+
},
|
|
399
|
+
number: 5
|
|
400
|
+
},
|
|
401
|
+
{
|
|
402
|
+
left: {
|
|
403
|
+
type: "forest",
|
|
404
|
+
crowns: 0
|
|
405
|
+
},
|
|
406
|
+
right: {
|
|
407
|
+
type: "forest",
|
|
408
|
+
crowns: 0
|
|
409
|
+
},
|
|
410
|
+
number: 6
|
|
411
|
+
},
|
|
412
|
+
{
|
|
413
|
+
left: {
|
|
414
|
+
type: "sea",
|
|
415
|
+
crowns: 0
|
|
416
|
+
},
|
|
417
|
+
right: {
|
|
418
|
+
type: "sea",
|
|
419
|
+
crowns: 0
|
|
420
|
+
},
|
|
421
|
+
number: 7
|
|
422
|
+
},
|
|
423
|
+
{
|
|
424
|
+
left: {
|
|
425
|
+
type: "sea",
|
|
426
|
+
crowns: 0
|
|
427
|
+
},
|
|
428
|
+
right: {
|
|
429
|
+
type: "sea",
|
|
430
|
+
crowns: 0
|
|
431
|
+
},
|
|
432
|
+
number: 8
|
|
433
|
+
},
|
|
434
|
+
{
|
|
435
|
+
left: {
|
|
436
|
+
type: "sea",
|
|
437
|
+
crowns: 0
|
|
438
|
+
},
|
|
439
|
+
right: {
|
|
440
|
+
type: "sea",
|
|
441
|
+
crowns: 0
|
|
442
|
+
},
|
|
443
|
+
number: 9
|
|
444
|
+
},
|
|
445
|
+
{
|
|
446
|
+
left: {
|
|
447
|
+
type: "plain",
|
|
448
|
+
crowns: 0
|
|
449
|
+
},
|
|
450
|
+
right: {
|
|
451
|
+
type: "plain",
|
|
452
|
+
crowns: 0
|
|
453
|
+
},
|
|
454
|
+
number: 10
|
|
455
|
+
},
|
|
456
|
+
{
|
|
457
|
+
left: {
|
|
458
|
+
type: "plain",
|
|
459
|
+
crowns: 0
|
|
460
|
+
},
|
|
461
|
+
right: {
|
|
462
|
+
type: "plain",
|
|
463
|
+
crowns: 0
|
|
464
|
+
},
|
|
465
|
+
number: 11
|
|
466
|
+
},
|
|
467
|
+
{
|
|
468
|
+
left: {
|
|
469
|
+
type: "swamp",
|
|
470
|
+
crowns: 0
|
|
471
|
+
},
|
|
472
|
+
right: {
|
|
473
|
+
type: "swamp",
|
|
474
|
+
crowns: 0
|
|
475
|
+
},
|
|
476
|
+
number: 12
|
|
477
|
+
},
|
|
478
|
+
{
|
|
479
|
+
left: {
|
|
480
|
+
type: "wheat",
|
|
481
|
+
crowns: 0
|
|
482
|
+
},
|
|
483
|
+
right: {
|
|
484
|
+
type: "forest",
|
|
485
|
+
crowns: 0
|
|
486
|
+
},
|
|
487
|
+
number: 13
|
|
488
|
+
},
|
|
489
|
+
{
|
|
490
|
+
left: {
|
|
491
|
+
type: "wheat",
|
|
492
|
+
crowns: 0
|
|
493
|
+
},
|
|
494
|
+
right: {
|
|
495
|
+
type: "sea",
|
|
496
|
+
crowns: 0
|
|
497
|
+
},
|
|
498
|
+
number: 14
|
|
499
|
+
},
|
|
500
|
+
{
|
|
501
|
+
left: {
|
|
502
|
+
type: "wheat",
|
|
503
|
+
crowns: 0
|
|
504
|
+
},
|
|
505
|
+
right: {
|
|
506
|
+
type: "plain",
|
|
507
|
+
crowns: 0
|
|
508
|
+
},
|
|
509
|
+
number: 15
|
|
510
|
+
},
|
|
511
|
+
{
|
|
512
|
+
left: {
|
|
513
|
+
type: "wheat",
|
|
514
|
+
crowns: 0
|
|
515
|
+
},
|
|
516
|
+
right: {
|
|
517
|
+
type: "swamp",
|
|
518
|
+
crowns: 0
|
|
519
|
+
},
|
|
520
|
+
number: 16
|
|
521
|
+
},
|
|
522
|
+
{
|
|
523
|
+
left: {
|
|
524
|
+
type: "forest",
|
|
525
|
+
crowns: 0
|
|
526
|
+
},
|
|
527
|
+
right: {
|
|
528
|
+
type: "sea",
|
|
529
|
+
crowns: 0
|
|
530
|
+
},
|
|
531
|
+
number: 17
|
|
532
|
+
},
|
|
533
|
+
{
|
|
534
|
+
left: {
|
|
535
|
+
type: "forest",
|
|
536
|
+
crowns: 0
|
|
537
|
+
},
|
|
538
|
+
right: {
|
|
539
|
+
type: "plain",
|
|
540
|
+
crowns: 0
|
|
541
|
+
},
|
|
542
|
+
number: 18
|
|
543
|
+
},
|
|
544
|
+
{
|
|
545
|
+
left: {
|
|
546
|
+
type: "wheat",
|
|
547
|
+
crowns: 1
|
|
548
|
+
},
|
|
549
|
+
right: {
|
|
550
|
+
type: "forest",
|
|
551
|
+
crowns: 0
|
|
552
|
+
},
|
|
553
|
+
number: 19
|
|
554
|
+
},
|
|
555
|
+
{
|
|
556
|
+
left: {
|
|
557
|
+
type: "wheat",
|
|
558
|
+
crowns: 1
|
|
559
|
+
},
|
|
560
|
+
right: {
|
|
561
|
+
type: "sea",
|
|
562
|
+
crowns: 0
|
|
563
|
+
},
|
|
564
|
+
number: 20
|
|
565
|
+
},
|
|
566
|
+
{
|
|
567
|
+
left: {
|
|
568
|
+
type: "wheat",
|
|
569
|
+
crowns: 1
|
|
570
|
+
},
|
|
571
|
+
right: {
|
|
572
|
+
type: "plain",
|
|
573
|
+
crowns: 0
|
|
574
|
+
},
|
|
575
|
+
number: 21
|
|
576
|
+
},
|
|
577
|
+
{
|
|
578
|
+
left: {
|
|
579
|
+
type: "wheat",
|
|
580
|
+
crowns: 1
|
|
581
|
+
},
|
|
582
|
+
right: {
|
|
583
|
+
type: "swamp",
|
|
584
|
+
crowns: 0
|
|
585
|
+
},
|
|
586
|
+
number: 22
|
|
587
|
+
},
|
|
588
|
+
{
|
|
589
|
+
left: {
|
|
590
|
+
type: "wheat",
|
|
591
|
+
crowns: 1
|
|
592
|
+
},
|
|
593
|
+
right: {
|
|
594
|
+
type: "mine",
|
|
595
|
+
crowns: 0
|
|
596
|
+
},
|
|
597
|
+
number: 23
|
|
598
|
+
},
|
|
599
|
+
{
|
|
600
|
+
left: {
|
|
601
|
+
type: "forest",
|
|
602
|
+
crowns: 1
|
|
603
|
+
},
|
|
604
|
+
right: {
|
|
605
|
+
type: "wheat",
|
|
606
|
+
crowns: 0
|
|
607
|
+
},
|
|
608
|
+
number: 24
|
|
609
|
+
},
|
|
610
|
+
{
|
|
611
|
+
left: {
|
|
612
|
+
type: "forest",
|
|
613
|
+
crowns: 1
|
|
614
|
+
},
|
|
615
|
+
right: {
|
|
616
|
+
type: "wheat",
|
|
617
|
+
crowns: 0
|
|
618
|
+
},
|
|
619
|
+
number: 25
|
|
620
|
+
},
|
|
621
|
+
{
|
|
622
|
+
left: {
|
|
623
|
+
type: "forest",
|
|
624
|
+
crowns: 1
|
|
625
|
+
},
|
|
626
|
+
right: {
|
|
627
|
+
type: "wheat",
|
|
628
|
+
crowns: 0
|
|
629
|
+
},
|
|
630
|
+
number: 26
|
|
631
|
+
},
|
|
632
|
+
{
|
|
633
|
+
left: {
|
|
634
|
+
type: "forest",
|
|
635
|
+
crowns: 1
|
|
636
|
+
},
|
|
637
|
+
right: {
|
|
638
|
+
type: "wheat",
|
|
639
|
+
crowns: 0
|
|
640
|
+
},
|
|
641
|
+
number: 27
|
|
642
|
+
},
|
|
643
|
+
{
|
|
644
|
+
left: {
|
|
645
|
+
type: "forest",
|
|
646
|
+
crowns: 1
|
|
647
|
+
},
|
|
648
|
+
right: {
|
|
649
|
+
type: "sea",
|
|
650
|
+
crowns: 0
|
|
651
|
+
},
|
|
652
|
+
number: 28
|
|
653
|
+
},
|
|
654
|
+
{
|
|
655
|
+
left: {
|
|
656
|
+
type: "forest",
|
|
657
|
+
crowns: 1
|
|
658
|
+
},
|
|
659
|
+
right: {
|
|
660
|
+
type: "plain",
|
|
661
|
+
crowns: 0
|
|
662
|
+
},
|
|
663
|
+
number: 29
|
|
664
|
+
},
|
|
665
|
+
{
|
|
666
|
+
left: {
|
|
667
|
+
type: "sea",
|
|
668
|
+
crowns: 1
|
|
669
|
+
},
|
|
670
|
+
right: {
|
|
671
|
+
type: "wheat",
|
|
672
|
+
crowns: 0
|
|
673
|
+
},
|
|
674
|
+
number: 30
|
|
675
|
+
},
|
|
676
|
+
{
|
|
677
|
+
left: {
|
|
678
|
+
type: "sea",
|
|
679
|
+
crowns: 1
|
|
680
|
+
},
|
|
681
|
+
right: {
|
|
682
|
+
type: "wheat",
|
|
683
|
+
crowns: 0
|
|
684
|
+
},
|
|
685
|
+
number: 31
|
|
686
|
+
},
|
|
687
|
+
{
|
|
688
|
+
left: {
|
|
689
|
+
type: "sea",
|
|
690
|
+
crowns: 1
|
|
691
|
+
},
|
|
692
|
+
right: {
|
|
693
|
+
type: "forest",
|
|
694
|
+
crowns: 0
|
|
695
|
+
},
|
|
696
|
+
number: 32
|
|
697
|
+
},
|
|
698
|
+
{
|
|
699
|
+
left: {
|
|
700
|
+
type: "sea",
|
|
701
|
+
crowns: 1
|
|
702
|
+
},
|
|
703
|
+
right: {
|
|
704
|
+
type: "forest",
|
|
705
|
+
crowns: 0
|
|
706
|
+
},
|
|
707
|
+
number: 33
|
|
708
|
+
},
|
|
709
|
+
{
|
|
710
|
+
left: {
|
|
711
|
+
type: "sea",
|
|
712
|
+
crowns: 1
|
|
713
|
+
},
|
|
714
|
+
right: {
|
|
715
|
+
type: "forest",
|
|
716
|
+
crowns: 0
|
|
717
|
+
},
|
|
718
|
+
number: 34
|
|
719
|
+
},
|
|
720
|
+
{
|
|
721
|
+
left: {
|
|
722
|
+
type: "sea",
|
|
723
|
+
crowns: 1
|
|
724
|
+
},
|
|
725
|
+
right: {
|
|
726
|
+
type: "forest",
|
|
727
|
+
crowns: 0
|
|
728
|
+
},
|
|
729
|
+
number: 35
|
|
730
|
+
},
|
|
731
|
+
{
|
|
732
|
+
left: {
|
|
733
|
+
type: "wheat",
|
|
734
|
+
crowns: 0
|
|
735
|
+
},
|
|
736
|
+
right: {
|
|
737
|
+
type: "plain",
|
|
738
|
+
crowns: 1
|
|
739
|
+
},
|
|
740
|
+
number: 36
|
|
741
|
+
},
|
|
742
|
+
{
|
|
743
|
+
left: {
|
|
744
|
+
type: "sea",
|
|
745
|
+
crowns: 0
|
|
746
|
+
},
|
|
747
|
+
right: {
|
|
748
|
+
type: "plain",
|
|
749
|
+
crowns: 1
|
|
750
|
+
},
|
|
751
|
+
number: 37
|
|
752
|
+
},
|
|
753
|
+
{
|
|
754
|
+
left: {
|
|
755
|
+
type: "wheat",
|
|
756
|
+
crowns: 0
|
|
757
|
+
},
|
|
758
|
+
right: {
|
|
759
|
+
type: "swamp",
|
|
760
|
+
crowns: 1
|
|
761
|
+
},
|
|
762
|
+
number: 38
|
|
763
|
+
},
|
|
764
|
+
{
|
|
765
|
+
left: {
|
|
766
|
+
type: "plain",
|
|
767
|
+
crowns: 0
|
|
768
|
+
},
|
|
769
|
+
right: {
|
|
770
|
+
type: "swamp",
|
|
771
|
+
crowns: 0
|
|
772
|
+
},
|
|
773
|
+
number: 39
|
|
774
|
+
},
|
|
775
|
+
{
|
|
776
|
+
left: {
|
|
777
|
+
type: "mine",
|
|
778
|
+
crowns: 1
|
|
779
|
+
},
|
|
780
|
+
right: {
|
|
781
|
+
type: "wheat",
|
|
782
|
+
crowns: 0
|
|
783
|
+
},
|
|
784
|
+
number: 40
|
|
785
|
+
},
|
|
786
|
+
{
|
|
787
|
+
left: {
|
|
788
|
+
type: "wheat",
|
|
789
|
+
crowns: 0
|
|
790
|
+
},
|
|
791
|
+
right: {
|
|
792
|
+
type: "plain",
|
|
793
|
+
crowns: 2
|
|
794
|
+
},
|
|
795
|
+
number: 41
|
|
796
|
+
},
|
|
797
|
+
{
|
|
798
|
+
left: {
|
|
799
|
+
type: "sea",
|
|
800
|
+
crowns: 0
|
|
801
|
+
},
|
|
802
|
+
right: {
|
|
803
|
+
type: "plain",
|
|
804
|
+
crowns: 2
|
|
805
|
+
},
|
|
806
|
+
number: 42
|
|
807
|
+
},
|
|
808
|
+
{
|
|
809
|
+
left: {
|
|
810
|
+
type: "wheat",
|
|
811
|
+
crowns: 0
|
|
812
|
+
},
|
|
813
|
+
right: {
|
|
814
|
+
type: "swamp",
|
|
815
|
+
crowns: 2
|
|
816
|
+
},
|
|
817
|
+
number: 43
|
|
818
|
+
},
|
|
819
|
+
{
|
|
820
|
+
left: {
|
|
821
|
+
type: "plain",
|
|
822
|
+
crowns: 0
|
|
823
|
+
},
|
|
824
|
+
right: {
|
|
825
|
+
type: "swamp",
|
|
826
|
+
crowns: 2
|
|
827
|
+
},
|
|
828
|
+
number: 44
|
|
829
|
+
},
|
|
830
|
+
{
|
|
831
|
+
left: {
|
|
832
|
+
type: "mine",
|
|
833
|
+
crowns: 2
|
|
834
|
+
},
|
|
835
|
+
right: {
|
|
836
|
+
type: "wheat",
|
|
837
|
+
crowns: 0
|
|
838
|
+
},
|
|
839
|
+
number: 45
|
|
840
|
+
},
|
|
841
|
+
{
|
|
842
|
+
left: {
|
|
843
|
+
type: "swamp",
|
|
844
|
+
crowns: 0
|
|
845
|
+
},
|
|
846
|
+
right: {
|
|
847
|
+
type: "mine",
|
|
848
|
+
crowns: 2
|
|
849
|
+
},
|
|
850
|
+
number: 46
|
|
851
|
+
},
|
|
852
|
+
{
|
|
853
|
+
left: {
|
|
854
|
+
type: "swamp",
|
|
855
|
+
crowns: 0
|
|
856
|
+
},
|
|
857
|
+
right: {
|
|
858
|
+
type: "mine",
|
|
859
|
+
crowns: 2
|
|
860
|
+
},
|
|
861
|
+
number: 47
|
|
862
|
+
},
|
|
863
|
+
{
|
|
864
|
+
left: {
|
|
865
|
+
type: "wheat",
|
|
866
|
+
crowns: 0
|
|
867
|
+
},
|
|
868
|
+
right: {
|
|
869
|
+
type: "mine",
|
|
870
|
+
crowns: 3
|
|
871
|
+
},
|
|
872
|
+
number: 48
|
|
873
|
+
}
|
|
874
|
+
],
|
|
875
|
+
QueenDomino: [
|
|
876
|
+
{
|
|
877
|
+
left: {
|
|
878
|
+
type: "wheat",
|
|
879
|
+
crowns: 0
|
|
880
|
+
},
|
|
881
|
+
right: {
|
|
882
|
+
type: "wheat",
|
|
883
|
+
crowns: 0
|
|
884
|
+
},
|
|
885
|
+
number: 1
|
|
886
|
+
},
|
|
887
|
+
{
|
|
888
|
+
left: {
|
|
889
|
+
type: "wheat",
|
|
890
|
+
crowns: 0
|
|
891
|
+
},
|
|
892
|
+
right: {
|
|
893
|
+
type: "wheat",
|
|
894
|
+
crowns: 0
|
|
895
|
+
},
|
|
896
|
+
number: 2
|
|
897
|
+
},
|
|
898
|
+
{
|
|
899
|
+
left: {
|
|
900
|
+
type: "forest",
|
|
901
|
+
crowns: 0
|
|
902
|
+
},
|
|
903
|
+
right: {
|
|
904
|
+
type: "forest",
|
|
905
|
+
crowns: 0
|
|
906
|
+
},
|
|
907
|
+
number: 3
|
|
908
|
+
},
|
|
909
|
+
{
|
|
910
|
+
left: {
|
|
911
|
+
type: "forest",
|
|
912
|
+
crowns: 0
|
|
913
|
+
},
|
|
914
|
+
right: {
|
|
915
|
+
type: "forest",
|
|
916
|
+
crowns: 0
|
|
917
|
+
},
|
|
918
|
+
number: 4
|
|
919
|
+
},
|
|
920
|
+
{
|
|
921
|
+
left: {
|
|
922
|
+
type: "sea",
|
|
923
|
+
crowns: 0
|
|
924
|
+
},
|
|
925
|
+
right: {
|
|
926
|
+
type: "sea",
|
|
318
927
|
crowns: 0
|
|
319
928
|
},
|
|
320
929
|
number: 5
|
|
321
930
|
},
|
|
322
931
|
{
|
|
323
932
|
left: {
|
|
324
|
-
type: "
|
|
933
|
+
type: "sea",
|
|
325
934
|
crowns: 0
|
|
326
935
|
},
|
|
327
936
|
right: {
|
|
328
|
-
type: "
|
|
937
|
+
type: "sea",
|
|
329
938
|
crowns: 0
|
|
330
939
|
},
|
|
331
940
|
number: 6
|
|
332
941
|
},
|
|
333
942
|
{
|
|
334
943
|
left: {
|
|
335
|
-
type: "
|
|
944
|
+
type: "plain",
|
|
336
945
|
crowns: 0
|
|
337
946
|
},
|
|
338
947
|
right: {
|
|
339
|
-
type: "
|
|
948
|
+
type: "plain",
|
|
340
949
|
crowns: 0
|
|
341
950
|
},
|
|
342
951
|
number: 7
|
|
343
952
|
},
|
|
344
953
|
{
|
|
345
954
|
left: {
|
|
346
|
-
type: "
|
|
955
|
+
type: "plain",
|
|
347
956
|
crowns: 0
|
|
348
957
|
},
|
|
349
958
|
right: {
|
|
350
|
-
type: "
|
|
959
|
+
type: "plain",
|
|
351
960
|
crowns: 0
|
|
352
961
|
},
|
|
353
962
|
number: 8
|
|
354
963
|
},
|
|
355
964
|
{
|
|
356
965
|
left: {
|
|
357
|
-
type: "
|
|
966
|
+
type: "swamp",
|
|
358
967
|
crowns: 0
|
|
359
968
|
},
|
|
360
969
|
right: {
|
|
361
|
-
type: "
|
|
970
|
+
type: "swamp",
|
|
362
971
|
crowns: 0
|
|
363
972
|
},
|
|
364
973
|
number: 9
|
|
365
974
|
},
|
|
366
975
|
{
|
|
367
976
|
left: {
|
|
368
|
-
type: "
|
|
977
|
+
type: "swamp",
|
|
369
978
|
crowns: 0
|
|
370
979
|
},
|
|
371
980
|
right: {
|
|
372
|
-
type: "
|
|
981
|
+
type: "swamp",
|
|
373
982
|
crowns: 0
|
|
374
983
|
},
|
|
375
984
|
number: 10
|
|
376
985
|
},
|
|
377
986
|
{
|
|
378
987
|
left: {
|
|
379
|
-
type: "
|
|
988
|
+
type: "mine",
|
|
380
989
|
crowns: 0
|
|
381
990
|
},
|
|
382
991
|
right: {
|
|
383
|
-
type: "
|
|
992
|
+
type: "mine",
|
|
384
993
|
crowns: 0
|
|
385
994
|
},
|
|
386
995
|
number: 11
|
|
387
996
|
},
|
|
388
997
|
{
|
|
389
998
|
left: {
|
|
390
|
-
type: "
|
|
999
|
+
type: "wheat",
|
|
391
1000
|
crowns: 0
|
|
392
1001
|
},
|
|
393
1002
|
right: {
|
|
394
|
-
type: "
|
|
1003
|
+
type: "forest",
|
|
395
1004
|
crowns: 0
|
|
396
1005
|
},
|
|
397
1006
|
number: 12
|
|
@@ -399,10 +1008,11 @@ var dominoes_default = {
|
|
|
399
1008
|
{
|
|
400
1009
|
left: {
|
|
401
1010
|
type: "wheat",
|
|
402
|
-
crowns: 0
|
|
1011
|
+
crowns: 0,
|
|
1012
|
+
hasConstructionSquare: true
|
|
403
1013
|
},
|
|
404
1014
|
right: {
|
|
405
|
-
type: "
|
|
1015
|
+
type: "sea",
|
|
406
1016
|
crowns: 0
|
|
407
1017
|
},
|
|
408
1018
|
number: 13
|
|
@@ -413,51 +1023,54 @@ var dominoes_default = {
|
|
|
413
1023
|
crowns: 0
|
|
414
1024
|
},
|
|
415
1025
|
right: {
|
|
416
|
-
type: "
|
|
417
|
-
crowns: 0
|
|
1026
|
+
type: "plain",
|
|
1027
|
+
crowns: 0,
|
|
1028
|
+
hasConstructionSquare: true
|
|
418
1029
|
},
|
|
419
1030
|
number: 14
|
|
420
1031
|
},
|
|
421
1032
|
{
|
|
422
1033
|
left: {
|
|
423
|
-
type: "
|
|
424
|
-
crowns: 0
|
|
1034
|
+
type: "forest",
|
|
1035
|
+
crowns: 0,
|
|
1036
|
+
hasConstructionSquare: true
|
|
425
1037
|
},
|
|
426
1038
|
right: {
|
|
427
|
-
type: "
|
|
1039
|
+
type: "sea",
|
|
428
1040
|
crowns: 0
|
|
429
1041
|
},
|
|
430
1042
|
number: 15
|
|
431
1043
|
},
|
|
432
1044
|
{
|
|
433
1045
|
left: {
|
|
434
|
-
type: "
|
|
1046
|
+
type: "forest",
|
|
435
1047
|
crowns: 0
|
|
436
1048
|
},
|
|
437
1049
|
right: {
|
|
438
|
-
type: "
|
|
1050
|
+
type: "plain",
|
|
439
1051
|
crowns: 0
|
|
440
1052
|
},
|
|
441
1053
|
number: 16
|
|
442
1054
|
},
|
|
443
1055
|
{
|
|
444
1056
|
left: {
|
|
445
|
-
type: "
|
|
1057
|
+
type: "sea",
|
|
446
1058
|
crowns: 0
|
|
447
1059
|
},
|
|
448
1060
|
right: {
|
|
449
|
-
type: "
|
|
450
|
-
crowns: 0
|
|
1061
|
+
type: "plain",
|
|
1062
|
+
crowns: 0,
|
|
1063
|
+
hasConstructionSquare: true
|
|
451
1064
|
},
|
|
452
1065
|
number: 17
|
|
453
1066
|
},
|
|
454
1067
|
{
|
|
455
1068
|
left: {
|
|
456
|
-
type: "
|
|
1069
|
+
type: "wheat",
|
|
457
1070
|
crowns: 0
|
|
458
1071
|
},
|
|
459
1072
|
right: {
|
|
460
|
-
type: "
|
|
1073
|
+
type: "swamp",
|
|
461
1074
|
crowns: 0
|
|
462
1075
|
},
|
|
463
1076
|
number: 18
|
|
@@ -465,7 +1078,8 @@ var dominoes_default = {
|
|
|
465
1078
|
{
|
|
466
1079
|
left: {
|
|
467
1080
|
type: "wheat",
|
|
468
|
-
crowns: 1
|
|
1081
|
+
crowns: 1,
|
|
1082
|
+
hasConstructionSquare: true
|
|
469
1083
|
},
|
|
470
1084
|
right: {
|
|
471
1085
|
type: "forest",
|
|
@@ -491,28 +1105,30 @@ var dominoes_default = {
|
|
|
491
1105
|
},
|
|
492
1106
|
right: {
|
|
493
1107
|
type: "plain",
|
|
494
|
-
crowns: 0
|
|
1108
|
+
crowns: 0,
|
|
1109
|
+
hasConstructionSquare: true
|
|
495
1110
|
},
|
|
496
1111
|
number: 21
|
|
497
1112
|
},
|
|
498
1113
|
{
|
|
499
1114
|
left: {
|
|
500
|
-
type: "
|
|
1115
|
+
type: "forest",
|
|
501
1116
|
crowns: 1
|
|
502
1117
|
},
|
|
503
1118
|
right: {
|
|
504
|
-
type: "
|
|
505
|
-
crowns: 0
|
|
1119
|
+
type: "wheat",
|
|
1120
|
+
crowns: 0,
|
|
1121
|
+
hasConstructionSquare: true
|
|
506
1122
|
},
|
|
507
1123
|
number: 22
|
|
508
1124
|
},
|
|
509
1125
|
{
|
|
510
1126
|
left: {
|
|
511
|
-
type: "
|
|
1127
|
+
type: "forest",
|
|
512
1128
|
crowns: 1
|
|
513
1129
|
},
|
|
514
1130
|
right: {
|
|
515
|
-
type: "
|
|
1131
|
+
type: "sea",
|
|
516
1132
|
crowns: 0
|
|
517
1133
|
},
|
|
518
1134
|
number: 23
|
|
@@ -520,17 +1136,18 @@ var dominoes_default = {
|
|
|
520
1136
|
{
|
|
521
1137
|
left: {
|
|
522
1138
|
type: "forest",
|
|
523
|
-
crowns: 1
|
|
1139
|
+
crowns: 1,
|
|
1140
|
+
hasConstructionSquare: true
|
|
524
1141
|
},
|
|
525
1142
|
right: {
|
|
526
|
-
type: "
|
|
1143
|
+
type: "plain",
|
|
527
1144
|
crowns: 0
|
|
528
1145
|
},
|
|
529
1146
|
number: 24
|
|
530
1147
|
},
|
|
531
1148
|
{
|
|
532
1149
|
left: {
|
|
533
|
-
type: "
|
|
1150
|
+
type: "sea",
|
|
534
1151
|
crowns: 1
|
|
535
1152
|
},
|
|
536
1153
|
right: {
|
|
@@ -541,18 +1158,19 @@ var dominoes_default = {
|
|
|
541
1158
|
},
|
|
542
1159
|
{
|
|
543
1160
|
left: {
|
|
544
|
-
type: "
|
|
1161
|
+
type: "sea",
|
|
545
1162
|
crowns: 1
|
|
546
1163
|
},
|
|
547
1164
|
right: {
|
|
548
|
-
type: "
|
|
549
|
-
crowns: 0
|
|
1165
|
+
type: "forest",
|
|
1166
|
+
crowns: 0,
|
|
1167
|
+
hasConstructionSquare: true
|
|
550
1168
|
},
|
|
551
1169
|
number: 26
|
|
552
1170
|
},
|
|
553
1171
|
{
|
|
554
1172
|
left: {
|
|
555
|
-
type: "
|
|
1173
|
+
type: "plain",
|
|
556
1174
|
crowns: 1
|
|
557
1175
|
},
|
|
558
1176
|
right: {
|
|
@@ -563,22 +1181,23 @@ var dominoes_default = {
|
|
|
563
1181
|
},
|
|
564
1182
|
{
|
|
565
1183
|
left: {
|
|
566
|
-
type: "
|
|
567
|
-
crowns: 1
|
|
1184
|
+
type: "plain",
|
|
1185
|
+
crowns: 1,
|
|
1186
|
+
hasConstructionSquare: true
|
|
568
1187
|
},
|
|
569
1188
|
right: {
|
|
570
|
-
type: "
|
|
1189
|
+
type: "forest",
|
|
571
1190
|
crowns: 0
|
|
572
1191
|
},
|
|
573
1192
|
number: 28
|
|
574
1193
|
},
|
|
575
1194
|
{
|
|
576
1195
|
left: {
|
|
577
|
-
type: "
|
|
1196
|
+
type: "wheat",
|
|
578
1197
|
crowns: 1
|
|
579
1198
|
},
|
|
580
1199
|
right: {
|
|
581
|
-
type: "
|
|
1200
|
+
type: "mine",
|
|
582
1201
|
crowns: 0
|
|
583
1202
|
},
|
|
584
1203
|
number: 29
|
|
@@ -589,30 +1208,33 @@ var dominoes_default = {
|
|
|
589
1208
|
crowns: 1
|
|
590
1209
|
},
|
|
591
1210
|
right: {
|
|
592
|
-
type: "
|
|
593
|
-
crowns: 0
|
|
1211
|
+
type: "plain",
|
|
1212
|
+
crowns: 0,
|
|
1213
|
+
hasConstructionSquare: true
|
|
594
1214
|
},
|
|
595
1215
|
number: 30
|
|
596
1216
|
},
|
|
597
1217
|
{
|
|
598
1218
|
left: {
|
|
599
|
-
type: "
|
|
600
|
-
crowns: 1
|
|
1219
|
+
type: "wheat",
|
|
1220
|
+
crowns: 1,
|
|
1221
|
+
hasConstructionSquare: true
|
|
601
1222
|
},
|
|
602
1223
|
right: {
|
|
603
|
-
type: "
|
|
604
|
-
crowns:
|
|
1224
|
+
type: "swamp",
|
|
1225
|
+
crowns: 1
|
|
605
1226
|
},
|
|
606
1227
|
number: 31
|
|
607
1228
|
},
|
|
608
1229
|
{
|
|
609
1230
|
left: {
|
|
610
|
-
type: "
|
|
1231
|
+
type: "forest",
|
|
611
1232
|
crowns: 1
|
|
612
1233
|
},
|
|
613
1234
|
right: {
|
|
614
|
-
type: "
|
|
615
|
-
crowns:
|
|
1235
|
+
type: "sea",
|
|
1236
|
+
crowns: 1,
|
|
1237
|
+
hasConstructionSquare: true
|
|
616
1238
|
},
|
|
617
1239
|
number: 32
|
|
618
1240
|
},
|
|
@@ -622,73 +1244,77 @@ var dominoes_default = {
|
|
|
622
1244
|
crowns: 1
|
|
623
1245
|
},
|
|
624
1246
|
right: {
|
|
625
|
-
type: "
|
|
626
|
-
crowns:
|
|
1247
|
+
type: "plain",
|
|
1248
|
+
crowns: 1
|
|
627
1249
|
},
|
|
628
1250
|
number: 33
|
|
629
1251
|
},
|
|
630
1252
|
{
|
|
631
1253
|
left: {
|
|
632
|
-
type: "
|
|
633
|
-
crowns: 1
|
|
1254
|
+
type: "plain",
|
|
1255
|
+
crowns: 1,
|
|
1256
|
+
hasConstructionSquare: true
|
|
634
1257
|
},
|
|
635
1258
|
right: {
|
|
636
|
-
type: "
|
|
637
|
-
crowns:
|
|
1259
|
+
type: "swamp",
|
|
1260
|
+
crowns: 1
|
|
638
1261
|
},
|
|
639
1262
|
number: 34
|
|
640
1263
|
},
|
|
641
1264
|
{
|
|
642
1265
|
left: {
|
|
643
|
-
type: "
|
|
644
|
-
crowns: 1
|
|
1266
|
+
type: "forest",
|
|
1267
|
+
crowns: 1,
|
|
1268
|
+
hasConstructionSquare: true
|
|
645
1269
|
},
|
|
646
1270
|
right: {
|
|
647
|
-
type: "
|
|
648
|
-
crowns:
|
|
1271
|
+
type: "mine",
|
|
1272
|
+
crowns: 1
|
|
649
1273
|
},
|
|
650
1274
|
number: 35
|
|
651
1275
|
},
|
|
652
1276
|
{
|
|
653
1277
|
left: {
|
|
654
1278
|
type: "wheat",
|
|
655
|
-
crowns:
|
|
1279
|
+
crowns: 2,
|
|
1280
|
+
hasConstructionSquare: true
|
|
656
1281
|
},
|
|
657
1282
|
right: {
|
|
658
|
-
type: "
|
|
659
|
-
crowns:
|
|
1283
|
+
type: "forest",
|
|
1284
|
+
crowns: 0
|
|
660
1285
|
},
|
|
661
1286
|
number: 36
|
|
662
1287
|
},
|
|
663
1288
|
{
|
|
664
1289
|
left: {
|
|
665
1290
|
type: "sea",
|
|
666
|
-
crowns:
|
|
1291
|
+
crowns: 2
|
|
667
1292
|
},
|
|
668
1293
|
right: {
|
|
669
|
-
type: "
|
|
670
|
-
crowns:
|
|
1294
|
+
type: "wheat",
|
|
1295
|
+
crowns: 0,
|
|
1296
|
+
hasConstructionSquare: true
|
|
671
1297
|
},
|
|
672
1298
|
number: 37
|
|
673
1299
|
},
|
|
674
1300
|
{
|
|
675
1301
|
left: {
|
|
676
|
-
type: "
|
|
677
|
-
crowns:
|
|
1302
|
+
type: "plain",
|
|
1303
|
+
crowns: 2
|
|
678
1304
|
},
|
|
679
1305
|
right: {
|
|
680
|
-
type: "
|
|
681
|
-
crowns:
|
|
1306
|
+
type: "forest",
|
|
1307
|
+
crowns: 0
|
|
682
1308
|
},
|
|
683
1309
|
number: 38
|
|
684
1310
|
},
|
|
685
1311
|
{
|
|
686
1312
|
left: {
|
|
687
|
-
type: "
|
|
688
|
-
crowns:
|
|
1313
|
+
type: "swamp",
|
|
1314
|
+
crowns: 2
|
|
689
1315
|
},
|
|
690
1316
|
right: {
|
|
691
|
-
type: "
|
|
1317
|
+
type: "wheat",
|
|
692
1318
|
crowns: 0
|
|
693
1319
|
},
|
|
694
1320
|
number: 39
|
|
@@ -696,7 +1322,8 @@ var dominoes_default = {
|
|
|
696
1322
|
{
|
|
697
1323
|
left: {
|
|
698
1324
|
type: "mine",
|
|
699
|
-
crowns:
|
|
1325
|
+
crowns: 2,
|
|
1326
|
+
hasConstructionSquare: true
|
|
700
1327
|
},
|
|
701
1328
|
right: {
|
|
702
1329
|
type: "wheat",
|
|
@@ -707,7 +1334,7 @@ var dominoes_default = {
|
|
|
707
1334
|
{
|
|
708
1335
|
left: {
|
|
709
1336
|
type: "wheat",
|
|
710
|
-
crowns:
|
|
1337
|
+
crowns: 2
|
|
711
1338
|
},
|
|
712
1339
|
right: {
|
|
713
1340
|
type: "plain",
|
|
@@ -718,73 +1345,75 @@ var dominoes_default = {
|
|
|
718
1345
|
{
|
|
719
1346
|
left: {
|
|
720
1347
|
type: "sea",
|
|
721
|
-
crowns:
|
|
1348
|
+
crowns: 2
|
|
722
1349
|
},
|
|
723
1350
|
right: {
|
|
724
|
-
type: "
|
|
725
|
-
crowns:
|
|
1351
|
+
type: "forest",
|
|
1352
|
+
crowns: 1,
|
|
1353
|
+
hasConstructionSquare: true
|
|
726
1354
|
},
|
|
727
1355
|
number: 42
|
|
728
1356
|
},
|
|
729
1357
|
{
|
|
730
1358
|
left: {
|
|
731
|
-
type: "wheat",
|
|
732
|
-
crowns: 0
|
|
733
|
-
},
|
|
734
|
-
right: {
|
|
735
1359
|
type: "swamp",
|
|
736
1360
|
crowns: 2
|
|
737
1361
|
},
|
|
1362
|
+
right: {
|
|
1363
|
+
type: "plain",
|
|
1364
|
+
crowns: 1
|
|
1365
|
+
},
|
|
738
1366
|
number: 43
|
|
739
1367
|
},
|
|
740
1368
|
{
|
|
741
1369
|
left: {
|
|
742
|
-
type: "
|
|
743
|
-
crowns:
|
|
1370
|
+
type: "mine",
|
|
1371
|
+
crowns: 2
|
|
744
1372
|
},
|
|
745
1373
|
right: {
|
|
746
1374
|
type: "swamp",
|
|
747
|
-
crowns:
|
|
1375
|
+
crowns: 1
|
|
748
1376
|
},
|
|
749
1377
|
number: 44
|
|
750
1378
|
},
|
|
751
1379
|
{
|
|
752
1380
|
left: {
|
|
753
|
-
type: "
|
|
1381
|
+
type: "wheat",
|
|
754
1382
|
crowns: 2
|
|
755
1383
|
},
|
|
756
1384
|
right: {
|
|
757
|
-
type: "
|
|
758
|
-
crowns:
|
|
1385
|
+
type: "mine",
|
|
1386
|
+
crowns: 2
|
|
759
1387
|
},
|
|
760
1388
|
number: 45
|
|
761
1389
|
},
|
|
762
1390
|
{
|
|
763
1391
|
left: {
|
|
764
|
-
type: "
|
|
765
|
-
crowns:
|
|
1392
|
+
type: "forest",
|
|
1393
|
+
crowns: 2
|
|
766
1394
|
},
|
|
767
1395
|
right: {
|
|
768
1396
|
type: "mine",
|
|
769
|
-
crowns: 2
|
|
1397
|
+
crowns: 2,
|
|
1398
|
+
hasConstructionSquare: true
|
|
770
1399
|
},
|
|
771
1400
|
number: 46
|
|
772
1401
|
},
|
|
773
1402
|
{
|
|
774
1403
|
left: {
|
|
775
1404
|
type: "swamp",
|
|
776
|
-
crowns:
|
|
1405
|
+
crowns: 2
|
|
777
1406
|
},
|
|
778
1407
|
right: {
|
|
779
1408
|
type: "mine",
|
|
780
|
-
crowns:
|
|
1409
|
+
crowns: 3
|
|
781
1410
|
},
|
|
782
1411
|
number: 47
|
|
783
1412
|
},
|
|
784
1413
|
{
|
|
785
1414
|
left: {
|
|
786
|
-
type: "
|
|
787
|
-
crowns:
|
|
1415
|
+
type: "plain",
|
|
1416
|
+
crowns: 2
|
|
788
1417
|
},
|
|
789
1418
|
right: {
|
|
790
1419
|
type: "mine",
|
|
@@ -796,20 +1425,24 @@ var dominoes_default = {
|
|
|
796
1425
|
};
|
|
797
1426
|
|
|
798
1427
|
// src/adapterServerside/jsonDominoes.ts
|
|
1428
|
+
var mapTile = (raw) => {
|
|
1429
|
+
const tile = {
|
|
1430
|
+
type: raw.type,
|
|
1431
|
+
crowns: raw.crowns
|
|
1432
|
+
};
|
|
1433
|
+
if (raw.hasConstructionSquare) {
|
|
1434
|
+
tile.hasConstructionSquare = true;
|
|
1435
|
+
}
|
|
1436
|
+
return tile;
|
|
1437
|
+
};
|
|
799
1438
|
var jsonDominoes = () => {
|
|
800
1439
|
const dominoes = {};
|
|
801
1440
|
for (const [key, value] of Object.entries(dominoes_default)) {
|
|
802
1441
|
const currentDominoes = [];
|
|
803
1442
|
value.forEach((domino) => {
|
|
804
1443
|
currentDominoes.push({
|
|
805
|
-
left:
|
|
806
|
-
|
|
807
|
-
crowns: domino.left.crowns
|
|
808
|
-
},
|
|
809
|
-
right: {
|
|
810
|
-
type: domino.right.type,
|
|
811
|
-
crowns: domino.right.crowns
|
|
812
|
-
},
|
|
1444
|
+
left: mapTile(domino.left),
|
|
1445
|
+
right: mapTile(domino.right),
|
|
813
1446
|
number: domino.number
|
|
814
1447
|
});
|
|
815
1448
|
});
|
|
@@ -828,6 +1461,10 @@ var modes_default = [
|
|
|
828
1461
|
{
|
|
829
1462
|
name: "Classic",
|
|
830
1463
|
description: "Original KingDomino rules"
|
|
1464
|
+
},
|
|
1465
|
+
{
|
|
1466
|
+
name: "QueenDomino",
|
|
1467
|
+
description: "Queendomino expansion with buildings, knights, coins, the Queen and the Dragon"
|
|
831
1468
|
}
|
|
832
1469
|
];
|
|
833
1470
|
|
|
@@ -888,23 +1525,35 @@ var rules_default = {
|
|
|
888
1525
|
{
|
|
889
1526
|
name: "The middle Kingdom",
|
|
890
1527
|
description: "Gain 10 additional points if your castle is in the middle of the kingdom.",
|
|
891
|
-
mode: [
|
|
1528
|
+
mode: [
|
|
1529
|
+
{ name: "Classic", description: "King Domino classic mode" },
|
|
1530
|
+
{ name: "QueenDomino", description: "Queendomino expansion with buildings, knights, coins, the Queen and the Dragon" }
|
|
1531
|
+
]
|
|
892
1532
|
},
|
|
893
1533
|
{
|
|
894
1534
|
name: "Harmony",
|
|
895
1535
|
description: "Gain 5 additional points if your kingdom is complete (no discarded dominoes).",
|
|
896
|
-
mode: [
|
|
1536
|
+
mode: [
|
|
1537
|
+
{ name: "Classic", description: "King Domino classic mode" },
|
|
1538
|
+
{ name: "QueenDomino", description: "Queendomino expansion with buildings, knights, coins, the Queen and the Dragon" }
|
|
1539
|
+
]
|
|
897
1540
|
},
|
|
898
1541
|
{
|
|
899
1542
|
name: "The Mighty Duel",
|
|
900
1543
|
description: "Use all 48 dominoes and build a 7x7 kingdom. For 2 players only.",
|
|
901
|
-
mode: [
|
|
1544
|
+
mode: [
|
|
1545
|
+
{ name: "Classic", description: "King Domino classic mode" },
|
|
1546
|
+
{ name: "QueenDomino", description: "Queendomino expansion with buildings, knights, coins, the Queen and the Dragon" }
|
|
1547
|
+
],
|
|
902
1548
|
playersLimit: 2
|
|
903
1549
|
},
|
|
904
1550
|
{
|
|
905
1551
|
name: "Dynasty",
|
|
906
1552
|
description: "Play 3 games in a row. The player with the highest total points wins.",
|
|
907
|
-
mode: [
|
|
1553
|
+
mode: [
|
|
1554
|
+
{ name: "Classic", description: "King Domino classic mode" },
|
|
1555
|
+
{ name: "QueenDomino", description: "Queendomino expansion with buildings, knights, coins, the Queen and the Dragon" }
|
|
1556
|
+
]
|
|
908
1557
|
}
|
|
909
1558
|
]
|
|
910
1559
|
};
|
|
@@ -955,9 +1604,8 @@ var shuffleMethod = (array) => {
|
|
|
955
1604
|
};
|
|
956
1605
|
|
|
957
1606
|
// src/adapterServerside/uuid.ts
|
|
958
|
-
import { randomUUID } from "crypto";
|
|
959
1607
|
var uuidMethod = () => {
|
|
960
|
-
return randomUUID();
|
|
1608
|
+
return globalThis.crypto.randomUUID();
|
|
961
1609
|
};
|
|
962
1610
|
|
|
963
1611
|
// src/core/domain/errors/domainErrors.ts
|
|
@@ -987,7 +1635,17 @@ var ErrorCode = {
|
|
|
987
1635
|
DOMINO_ALREADY_PICKED: "DOMINO_ALREADY_PICKED",
|
|
988
1636
|
// History errors
|
|
989
1637
|
UNDO_UNAVAILABLE: "UNDO_UNAVAILABLE",
|
|
990
|
-
REDO_UNAVAILABLE: "REDO_UNAVAILABLE"
|
|
1638
|
+
REDO_UNAVAILABLE: "REDO_UNAVAILABLE",
|
|
1639
|
+
// Queendomino errors
|
|
1640
|
+
CANNOT_PLACE_KNIGHT: "CANNOT_PLACE_KNIGHT",
|
|
1641
|
+
MAX_KNIGHTS_REACHED: "MAX_KNIGHTS_REACHED",
|
|
1642
|
+
KNIGHT_TERRITORY_OCCUPIED: "KNIGHT_TERRITORY_OCCUPIED",
|
|
1643
|
+
CANNOT_AFFORD_BUILDING: "CANNOT_AFFORD_BUILDING",
|
|
1644
|
+
NO_CONSTRUCTION_SQUARE: "NO_CONSTRUCTION_SQUARE",
|
|
1645
|
+
DRAGON_UNAVAILABLE: "DRAGON_UNAVAILABLE",
|
|
1646
|
+
QUEEN_HOLDER_CANNOT_USE_DRAGON: "QUEEN_HOLDER_CANNOT_USE_DRAGON",
|
|
1647
|
+
BUILDING_NOT_FOUND: "BUILDING_NOT_FOUND",
|
|
1648
|
+
INVALID_OPTIONAL_ACTION: "INVALID_OPTIONAL_ACTION"
|
|
991
1649
|
};
|
|
992
1650
|
var createDomainError = (code, message, context) => ({
|
|
993
1651
|
code,
|
|
@@ -1120,7 +1778,17 @@ var TranslationKey = {
|
|
|
1120
1778
|
// Actions
|
|
1121
1779
|
ACTION_PICK_DOMINO: "action.pickDomino",
|
|
1122
1780
|
ACTION_PLACE_DOMINO: "action.placeDomino",
|
|
1123
|
-
ACTION_PASS: "action.pass"
|
|
1781
|
+
ACTION_PASS: "action.pass",
|
|
1782
|
+
// Queendomino errors
|
|
1783
|
+
ERROR_CANNOT_PLACE_KNIGHT: "error.cannotPlaceKnight",
|
|
1784
|
+
ERROR_MAX_KNIGHTS_REACHED: "error.maxKnightsReached",
|
|
1785
|
+
ERROR_KNIGHT_TERRITORY_OCCUPIED: "error.knightTerritoryOccupied",
|
|
1786
|
+
ERROR_CANNOT_AFFORD_BUILDING: "error.cannotAffordBuilding",
|
|
1787
|
+
ERROR_NO_CONSTRUCTION_SQUARE: "error.noConstructionSquare",
|
|
1788
|
+
ERROR_DRAGON_UNAVAILABLE: "error.dragonUnavailable",
|
|
1789
|
+
ERROR_QUEEN_HOLDER_CANNOT_USE_DRAGON: "error.queenHolderCannotUseDragon",
|
|
1790
|
+
ERROR_BUILDING_NOT_FOUND: "error.buildingNotFound",
|
|
1791
|
+
ERROR_INVALID_OPTIONAL_ACTION: "error.invalidOptionalAction"
|
|
1124
1792
|
};
|
|
1125
1793
|
var defaultTranslations = {
|
|
1126
1794
|
// Error messages
|
|
@@ -1166,7 +1834,17 @@ var defaultTranslations = {
|
|
|
1166
1834
|
// Actions
|
|
1167
1835
|
[TranslationKey.ACTION_PICK_DOMINO]: "Pick Domino",
|
|
1168
1836
|
[TranslationKey.ACTION_PLACE_DOMINO]: "Place Domino",
|
|
1169
|
-
[TranslationKey.ACTION_PASS]: "Pass"
|
|
1837
|
+
[TranslationKey.ACTION_PASS]: "Pass",
|
|
1838
|
+
// Queendomino errors
|
|
1839
|
+
[TranslationKey.ERROR_CANNOT_PLACE_KNIGHT]: "Cannot place knight here",
|
|
1840
|
+
[TranslationKey.ERROR_MAX_KNIGHTS_REACHED]: "Maximum number of knights reached (3)",
|
|
1841
|
+
[TranslationKey.ERROR_KNIGHT_TERRITORY_OCCUPIED]: "This territory already has a knight",
|
|
1842
|
+
[TranslationKey.ERROR_CANNOT_AFFORD_BUILDING]: "Not enough coins to purchase this building",
|
|
1843
|
+
[TranslationKey.ERROR_NO_CONSTRUCTION_SQUARE]: "No open construction square available",
|
|
1844
|
+
[TranslationKey.ERROR_DRAGON_UNAVAILABLE]: "The Dragon is not available this round",
|
|
1845
|
+
[TranslationKey.ERROR_QUEEN_HOLDER_CANNOT_USE_DRAGON]: "The Queen holder cannot use the Dragon",
|
|
1846
|
+
[TranslationKey.ERROR_BUILDING_NOT_FOUND]: "Building not found on the Builders Board",
|
|
1847
|
+
[TranslationKey.ERROR_INVALID_OPTIONAL_ACTION]: "Invalid optional action for this game state"
|
|
1170
1848
|
};
|
|
1171
1849
|
var errorCodeToTranslationKey = {
|
|
1172
1850
|
[ErrorCode.INVALID_STEP]: TranslationKey.ERROR_INVALID_STEP,
|
|
@@ -1189,7 +1867,16 @@ var errorCodeToTranslationKey = {
|
|
|
1189
1867
|
[ErrorCode.CANNOT_PLACE]: TranslationKey.ERROR_CANNOT_PLACE,
|
|
1190
1868
|
[ErrorCode.DOMINO_ALREADY_PICKED]: TranslationKey.ERROR_DOMINO_ALREADY_PICKED,
|
|
1191
1869
|
[ErrorCode.UNDO_UNAVAILABLE]: TranslationKey.ERROR_UNDO_UNAVAILABLE,
|
|
1192
|
-
[ErrorCode.REDO_UNAVAILABLE]: TranslationKey.ERROR_REDO_UNAVAILABLE
|
|
1870
|
+
[ErrorCode.REDO_UNAVAILABLE]: TranslationKey.ERROR_REDO_UNAVAILABLE,
|
|
1871
|
+
[ErrorCode.CANNOT_PLACE_KNIGHT]: TranslationKey.ERROR_CANNOT_PLACE_KNIGHT,
|
|
1872
|
+
[ErrorCode.MAX_KNIGHTS_REACHED]: TranslationKey.ERROR_MAX_KNIGHTS_REACHED,
|
|
1873
|
+
[ErrorCode.KNIGHT_TERRITORY_OCCUPIED]: TranslationKey.ERROR_KNIGHT_TERRITORY_OCCUPIED,
|
|
1874
|
+
[ErrorCode.CANNOT_AFFORD_BUILDING]: TranslationKey.ERROR_CANNOT_AFFORD_BUILDING,
|
|
1875
|
+
[ErrorCode.NO_CONSTRUCTION_SQUARE]: TranslationKey.ERROR_NO_CONSTRUCTION_SQUARE,
|
|
1876
|
+
[ErrorCode.DRAGON_UNAVAILABLE]: TranslationKey.ERROR_DRAGON_UNAVAILABLE,
|
|
1877
|
+
[ErrorCode.QUEEN_HOLDER_CANNOT_USE_DRAGON]: TranslationKey.ERROR_QUEEN_HOLDER_CANNOT_USE_DRAGON,
|
|
1878
|
+
[ErrorCode.BUILDING_NOT_FOUND]: TranslationKey.ERROR_BUILDING_NOT_FOUND,
|
|
1879
|
+
[ErrorCode.INVALID_OPTIONAL_ACTION]: TranslationKey.ERROR_INVALID_OPTIONAL_ACTION
|
|
1193
1880
|
};
|
|
1194
1881
|
var translateErrorCode = (translator, code, params) => {
|
|
1195
1882
|
const key = errorCodeToTranslationKey[code];
|
|
@@ -1679,47 +2366,191 @@ var deserializeGameHandler = (logger, translator) => {
|
|
|
1679
2366
|
};
|
|
1680
2367
|
};
|
|
1681
2368
|
|
|
1682
|
-
// src/application/handlers/startGameHandler.ts
|
|
1683
|
-
var startGameHandler = (logger, translator, useCase) => (command) => {
|
|
1684
|
-
const { game } = command;
|
|
1685
|
-
logger.info(`Starting game: ${game.id}`);
|
|
1686
|
-
if (!isGameWithNextStep(game)) {
|
|
2369
|
+
// src/application/handlers/startGameHandler.ts
|
|
2370
|
+
var startGameHandler = (logger, translator, useCase) => (command) => {
|
|
2371
|
+
const { game } = command;
|
|
2372
|
+
logger.info(`Starting game: ${game.id}`);
|
|
2373
|
+
if (!isGameWithNextStep(game)) {
|
|
2374
|
+
logger.error(
|
|
2375
|
+
`Invalid game, required nextAction type: 'step' but got: ${game.nextAction.type}`
|
|
2376
|
+
);
|
|
2377
|
+
throw new InvalidStepError(
|
|
2378
|
+
translateErrorCode(translator, ErrorCode.INVALID_STEP),
|
|
2379
|
+
{ expected: "step", actual: game.nextAction.type, gameId: game.id }
|
|
2380
|
+
);
|
|
2381
|
+
}
|
|
2382
|
+
if (game.nextAction.step !== "start" && game.nextAction.step !== "options") {
|
|
2383
|
+
logger.error(
|
|
2384
|
+
`Required game with start step or options step but got: ${game.nextAction.step}`
|
|
2385
|
+
);
|
|
2386
|
+
throw new InvalidStepError(
|
|
2387
|
+
translateErrorCode(translator, ErrorCode.INVALID_STEP),
|
|
2388
|
+
{
|
|
2389
|
+
expected: "start|options",
|
|
2390
|
+
actual: game.nextAction.step,
|
|
2391
|
+
gameId: game.id
|
|
2392
|
+
}
|
|
2393
|
+
);
|
|
2394
|
+
}
|
|
2395
|
+
const result = useCase(game);
|
|
2396
|
+
if (isErr(result)) {
|
|
2397
|
+
logger.error(`Error starting game: ${result.error}`);
|
|
2398
|
+
const code = result.error;
|
|
2399
|
+
throw new StepExecutionError(translateErrorCode(translator, code), code, {
|
|
2400
|
+
gameId: game.id
|
|
2401
|
+
});
|
|
2402
|
+
}
|
|
2403
|
+
logger.info(`Game started: ${game.id}`);
|
|
2404
|
+
return result.value;
|
|
2405
|
+
};
|
|
2406
|
+
|
|
2407
|
+
// src/application/handlers/placeKnightHandler.ts
|
|
2408
|
+
var placeKnightHandler = (logger, translator, useCase) => (command) => {
|
|
2409
|
+
const { game, lordId, position } = command;
|
|
2410
|
+
logger.info(
|
|
2411
|
+
`Placing knight for lord: ${lordId} at position: ${JSON.stringify(
|
|
2412
|
+
position
|
|
2413
|
+
)} in game: ${game.id}`
|
|
2414
|
+
);
|
|
2415
|
+
if (game.nextAction.nextAction !== "placeKnight") {
|
|
2416
|
+
logger.error(
|
|
2417
|
+
`Required game with placeKnight action but got: ${game.nextAction.nextAction}`
|
|
2418
|
+
);
|
|
2419
|
+
throw new InvalidStepError(
|
|
2420
|
+
translateErrorCode(translator, ErrorCode.INVALID_STEP),
|
|
2421
|
+
{
|
|
2422
|
+
expected: "placeKnight",
|
|
2423
|
+
actual: game.nextAction.nextAction,
|
|
2424
|
+
gameId: game.id
|
|
2425
|
+
}
|
|
2426
|
+
);
|
|
2427
|
+
}
|
|
2428
|
+
const result = useCase(game, lordId, position);
|
|
2429
|
+
if (isErr(result)) {
|
|
2430
|
+
logger.error(`Error placing knight: ${result.error}`);
|
|
2431
|
+
const code = result.error;
|
|
2432
|
+
throw new ActionExecutionError(
|
|
2433
|
+
translateErrorCode(translator, code),
|
|
2434
|
+
code,
|
|
2435
|
+
{
|
|
2436
|
+
gameId: game.id,
|
|
2437
|
+
lordId: command.lordId,
|
|
2438
|
+
position: command.position
|
|
2439
|
+
}
|
|
2440
|
+
);
|
|
2441
|
+
}
|
|
2442
|
+
logger.info(
|
|
2443
|
+
`Knight placed for lord: ${lordId} at position: ${JSON.stringify(
|
|
2444
|
+
position
|
|
2445
|
+
)} in game: ${game.id}`
|
|
2446
|
+
);
|
|
2447
|
+
return result.value;
|
|
2448
|
+
};
|
|
2449
|
+
|
|
2450
|
+
// src/application/handlers/constructBuildingHandler.ts
|
|
2451
|
+
var constructBuildingHandler = (logger, translator, useCase) => (command) => {
|
|
2452
|
+
const { game, lordId, buildingId, position } = command;
|
|
2453
|
+
logger.info(
|
|
2454
|
+
`Constructing building: ${buildingId} for lord: ${lordId} at position: ${JSON.stringify(
|
|
2455
|
+
position
|
|
2456
|
+
)} in game: ${game.id}`
|
|
2457
|
+
);
|
|
2458
|
+
if (game.nextAction.nextAction !== "constructBuilding") {
|
|
1687
2459
|
logger.error(
|
|
1688
|
-
`
|
|
2460
|
+
`Required game with constructBuilding action but got: ${game.nextAction.nextAction}`
|
|
1689
2461
|
);
|
|
1690
2462
|
throw new InvalidStepError(
|
|
1691
2463
|
translateErrorCode(translator, ErrorCode.INVALID_STEP),
|
|
1692
|
-
{
|
|
2464
|
+
{
|
|
2465
|
+
expected: "constructBuilding",
|
|
2466
|
+
actual: game.nextAction.nextAction,
|
|
2467
|
+
gameId: game.id
|
|
2468
|
+
}
|
|
1693
2469
|
);
|
|
1694
2470
|
}
|
|
1695
|
-
|
|
2471
|
+
const result = useCase(game, lordId, buildingId, position);
|
|
2472
|
+
if (isErr(result)) {
|
|
2473
|
+
logger.error(`Error constructing building: ${result.error}`);
|
|
2474
|
+
const code = result.error;
|
|
2475
|
+
throw new ActionExecutionError(
|
|
2476
|
+
translateErrorCode(translator, code),
|
|
2477
|
+
code,
|
|
2478
|
+
{
|
|
2479
|
+
gameId: game.id,
|
|
2480
|
+
lordId: command.lordId,
|
|
2481
|
+
buildingId: command.buildingId,
|
|
2482
|
+
position: command.position
|
|
2483
|
+
}
|
|
2484
|
+
);
|
|
2485
|
+
}
|
|
2486
|
+
logger.info(
|
|
2487
|
+
`Building constructed: ${buildingId} for lord: ${lordId} at position: ${JSON.stringify(
|
|
2488
|
+
position
|
|
2489
|
+
)} in game: ${game.id}`
|
|
2490
|
+
);
|
|
2491
|
+
return result.value;
|
|
2492
|
+
};
|
|
2493
|
+
|
|
2494
|
+
// src/application/handlers/useDragonHandler.ts
|
|
2495
|
+
var useDragonHandler = (logger, translator, useCase) => (command) => {
|
|
2496
|
+
const { game, lordId, buildingId } = command;
|
|
2497
|
+
logger.info(
|
|
2498
|
+
`Using dragon on building: ${buildingId} for lord: ${lordId} in game: ${game.id}`
|
|
2499
|
+
);
|
|
2500
|
+
if (game.nextAction.nextAction !== "useDragon") {
|
|
1696
2501
|
logger.error(
|
|
1697
|
-
`Required game with
|
|
2502
|
+
`Required game with useDragon action but got: ${game.nextAction.nextAction}`
|
|
1698
2503
|
);
|
|
1699
2504
|
throw new InvalidStepError(
|
|
1700
2505
|
translateErrorCode(translator, ErrorCode.INVALID_STEP),
|
|
1701
2506
|
{
|
|
1702
|
-
expected: "
|
|
1703
|
-
actual: game.nextAction.
|
|
2507
|
+
expected: "useDragon",
|
|
2508
|
+
actual: game.nextAction.nextAction,
|
|
1704
2509
|
gameId: game.id
|
|
1705
2510
|
}
|
|
1706
2511
|
);
|
|
1707
2512
|
}
|
|
1708
|
-
const result = useCase(game);
|
|
2513
|
+
const result = useCase(game, lordId, buildingId);
|
|
1709
2514
|
if (isErr(result)) {
|
|
1710
|
-
logger.error(`Error
|
|
2515
|
+
logger.error(`Error using dragon: ${result.error}`);
|
|
1711
2516
|
const code = result.error;
|
|
1712
|
-
throw new
|
|
1713
|
-
|
|
1714
|
-
|
|
2517
|
+
throw new ActionExecutionError(
|
|
2518
|
+
translateErrorCode(translator, code),
|
|
2519
|
+
code,
|
|
2520
|
+
{
|
|
2521
|
+
gameId: game.id,
|
|
2522
|
+
lordId: command.lordId,
|
|
2523
|
+
buildingId: command.buildingId
|
|
2524
|
+
}
|
|
2525
|
+
);
|
|
1715
2526
|
}
|
|
1716
|
-
logger.info(
|
|
2527
|
+
logger.info(
|
|
2528
|
+
`Dragon used on building: ${buildingId} for lord: ${lordId} in game: ${game.id}`
|
|
2529
|
+
);
|
|
1717
2530
|
return result.value;
|
|
1718
2531
|
};
|
|
1719
2532
|
|
|
1720
|
-
// src/
|
|
1721
|
-
var
|
|
1722
|
-
|
|
2533
|
+
// src/application/handlers/skipOptionalActionHandler.ts
|
|
2534
|
+
var skipOptionalActionHandler = (logger, translator, useCase) => (command) => {
|
|
2535
|
+
const { game, lordId } = command;
|
|
2536
|
+
logger.info(
|
|
2537
|
+
`Skipping optional action for lord: ${lordId} in game: ${game.id}`
|
|
2538
|
+
);
|
|
2539
|
+
const result = useCase(game, lordId);
|
|
2540
|
+
if (isErr(result)) {
|
|
2541
|
+
logger.error(`Error skipping optional action: ${result.error}`);
|
|
2542
|
+
const code = result.error;
|
|
2543
|
+
throw new ActionExecutionError(
|
|
2544
|
+
translateErrorCode(translator, code),
|
|
2545
|
+
code,
|
|
2546
|
+
{ gameId: game.id, lordId: command.lordId }
|
|
2547
|
+
);
|
|
2548
|
+
}
|
|
2549
|
+
logger.info(
|
|
2550
|
+
`Optional action skipped for lord: ${lordId} in game: ${game.id}`
|
|
2551
|
+
);
|
|
2552
|
+
return result.value;
|
|
2553
|
+
};
|
|
1723
2554
|
|
|
1724
2555
|
// src/core/domain/types/domino.ts
|
|
1725
2556
|
var GROUND = [
|
|
@@ -1732,6 +2563,10 @@ var GROUND = [
|
|
|
1732
2563
|
"mine"
|
|
1733
2564
|
];
|
|
1734
2565
|
|
|
2566
|
+
// src/core/domain/types/kingdom.ts
|
|
2567
|
+
var GRIDSIZE = 9;
|
|
2568
|
+
var MAX_KINGDOM_SIZE = 5;
|
|
2569
|
+
|
|
1735
2570
|
// src/core/domain/types/player.ts
|
|
1736
2571
|
var playerActions = {
|
|
1737
2572
|
/** Place a previously picked domino on the kingdom */
|
|
@@ -1739,7 +2574,15 @@ var playerActions = {
|
|
|
1739
2574
|
/** Pick a domino from the revealed set */
|
|
1740
2575
|
pickDomino: "pickDomino",
|
|
1741
2576
|
/** Pass/discard when no valid placement exists */
|
|
1742
|
-
pass: "pass"
|
|
2577
|
+
pass: "pass",
|
|
2578
|
+
/** Place a knight on the just-placed domino (Queendomino, optional) */
|
|
2579
|
+
placeKnight: "placeKnight",
|
|
2580
|
+
/** Construct a building on a construction square (Queendomino, optional) */
|
|
2581
|
+
constructBuilding: "constructBuilding",
|
|
2582
|
+
/** Use the Dragon to burn a building tile (Queendomino, optional) */
|
|
2583
|
+
useDragon: "useDragon",
|
|
2584
|
+
/** Skip the current optional action (Queendomino) */
|
|
2585
|
+
skipOptionalAction: "skipOptionalAction"
|
|
1743
2586
|
};
|
|
1744
2587
|
|
|
1745
2588
|
// src/core/domain/entities/rule.ts
|
|
@@ -1837,6 +2680,24 @@ var addExtraRulesUseCase = (deps) => (game, rules) => {
|
|
|
1837
2680
|
return ok(updatedGame);
|
|
1838
2681
|
};
|
|
1839
2682
|
|
|
2683
|
+
// src/core/domain/entities/economy.ts
|
|
2684
|
+
var STARTING_COINS = 7;
|
|
2685
|
+
var MAX_KNIGHTS = 3;
|
|
2686
|
+
var addCoins = (player, amount) => ({
|
|
2687
|
+
...player,
|
|
2688
|
+
coins: (player.coins ?? 0) + amount
|
|
2689
|
+
});
|
|
2690
|
+
var removeCoins = (player, amount) => ({
|
|
2691
|
+
...player,
|
|
2692
|
+
coins: (player.coins ?? 0) - amount
|
|
2693
|
+
});
|
|
2694
|
+
var canAfford = (player, cost) => (player.coins ?? 0) >= cost;
|
|
2695
|
+
var addTowers = (player, amount) => ({
|
|
2696
|
+
...player,
|
|
2697
|
+
towers: (player.towers ?? 0) + amount
|
|
2698
|
+
});
|
|
2699
|
+
var getTowerCount = (player) => player.towers ?? 0;
|
|
2700
|
+
|
|
1840
2701
|
// src/core/domain/entities/domino.ts
|
|
1841
2702
|
var isGround = (ground) => {
|
|
1842
2703
|
return GROUND.includes(ground);
|
|
@@ -2132,6 +2993,12 @@ var addPlayersUseCase = (deps) => (game, players) => {
|
|
|
2132
2993
|
if (isErr(newPlayer)) {
|
|
2133
2994
|
return newPlayer;
|
|
2134
2995
|
}
|
|
2996
|
+
if (game.mode.name === "QueenDomino") {
|
|
2997
|
+
newPlayer.value.coins = STARTING_COINS;
|
|
2998
|
+
newPlayer.value.towers = 0;
|
|
2999
|
+
newPlayer.value.knights = [];
|
|
3000
|
+
newPlayer.value.buildings = [];
|
|
3001
|
+
}
|
|
2135
3002
|
newPlayers.push(newPlayer.value);
|
|
2136
3003
|
}
|
|
2137
3004
|
const rules = ruleRepository.getAll();
|
|
@@ -2278,6 +3145,19 @@ var findNextLord = (lords) => {
|
|
|
2278
3145
|
var allLordsHavePlayed = (lords) => {
|
|
2279
3146
|
return lords.every((lord) => lord.turnEnded);
|
|
2280
3147
|
};
|
|
3148
|
+
var QUEENDOMINO_ACTION_SEQUENCE = [
|
|
3149
|
+
playerActions.placeKnight,
|
|
3150
|
+
playerActions.constructBuilding,
|
|
3151
|
+
playerActions.useDragon,
|
|
3152
|
+
playerActions.pickDomino
|
|
3153
|
+
];
|
|
3154
|
+
var nextQueenDominoAction = (currentAction) => {
|
|
3155
|
+
const index = QUEENDOMINO_ACTION_SEQUENCE.indexOf(currentAction);
|
|
3156
|
+
if (index === -1 || index >= QUEENDOMINO_ACTION_SEQUENCE.length - 1) {
|
|
3157
|
+
return playerActions.pickDomino;
|
|
3158
|
+
}
|
|
3159
|
+
return QUEENDOMINO_ACTION_SEQUENCE[index + 1];
|
|
3160
|
+
};
|
|
2281
3161
|
|
|
2282
3162
|
// src/core/useCases/chooseDomino.ts
|
|
2283
3163
|
var chooseDominoUseCase = (game, lordId, dominoPick) => {
|
|
@@ -2348,7 +3228,19 @@ var chooseDominoUseCase = (game, lordId, dominoPick) => {
|
|
|
2348
3228
|
|
|
2349
3229
|
// src/core/domain/entities/game.ts
|
|
2350
3230
|
var create = (payload) => {
|
|
2351
|
-
const { id, mode, dominoes, seed } = payload;
|
|
3231
|
+
const { id, mode, dominoes, seed, buildings } = payload;
|
|
3232
|
+
let queendomino;
|
|
3233
|
+
if (mode.name === "QueenDomino" && buildings) {
|
|
3234
|
+
queendomino = {
|
|
3235
|
+
buildersBoard: {
|
|
3236
|
+
slots: [],
|
|
3237
|
+
drawPile: buildings
|
|
3238
|
+
},
|
|
3239
|
+
queenHolderId: null,
|
|
3240
|
+
dragonAvailable: true,
|
|
3241
|
+
dragonUsedThisRound: false
|
|
3242
|
+
};
|
|
3243
|
+
}
|
|
2352
3244
|
return {
|
|
2353
3245
|
id,
|
|
2354
3246
|
dominoes,
|
|
@@ -2371,7 +3263,8 @@ var create = (payload) => {
|
|
|
2371
3263
|
extra: []
|
|
2372
3264
|
},
|
|
2373
3265
|
mode,
|
|
2374
|
-
...seed !== void 0 && { seed }
|
|
3266
|
+
...seed !== void 0 && { seed },
|
|
3267
|
+
...queendomino !== void 0 && { queendomino }
|
|
2375
3268
|
};
|
|
2376
3269
|
};
|
|
2377
3270
|
|
|
@@ -2389,7 +3282,7 @@ var createMode = (mode, availableMode) => {
|
|
|
2389
3282
|
|
|
2390
3283
|
// src/core/useCases/createGame.ts
|
|
2391
3284
|
var createGameUseCase = (deps) => (mode, seed) => {
|
|
2392
|
-
const { modeRepository, dominoesRepository, uuidMethod: uuidMethod2 } = deps;
|
|
3285
|
+
const { modeRepository, dominoesRepository, uuidMethod: uuidMethod2, buildingsRepository } = deps;
|
|
2393
3286
|
const id = uuidMethod2();
|
|
2394
3287
|
const gameSeed = seed ?? uuidMethod2();
|
|
2395
3288
|
const availableMode = modeRepository.getAvailables();
|
|
@@ -2401,11 +3294,17 @@ var createGameUseCase = (deps) => (mode, seed) => {
|
|
|
2401
3294
|
if (!dominoes || dominoes.length === 0) {
|
|
2402
3295
|
return err(ErrorCode.DOMINO_NOT_FOUND);
|
|
2403
3296
|
}
|
|
3297
|
+
const isQueenDomino = newMode.value.name === "QueenDomino";
|
|
3298
|
+
let buildings;
|
|
3299
|
+
if (isQueenDomino && buildingsRepository) {
|
|
3300
|
+
buildings = buildingsRepository.getAll();
|
|
3301
|
+
}
|
|
2404
3302
|
const payload = {
|
|
2405
3303
|
id,
|
|
2406
3304
|
mode: newMode.value,
|
|
2407
3305
|
dominoes,
|
|
2408
|
-
seed: gameSeed
|
|
3306
|
+
seed: gameSeed,
|
|
3307
|
+
buildings
|
|
2409
3308
|
};
|
|
2410
3309
|
const newGame = create(payload);
|
|
2411
3310
|
return ok(newGame);
|
|
@@ -2698,6 +3597,7 @@ var placeDominoUseCase = (game, lordId, position, rotation) => {
|
|
|
2698
3597
|
type: "step",
|
|
2699
3598
|
step: gameSteps.result
|
|
2700
3599
|
};
|
|
3600
|
+
const isQueenDomino = game.mode.name === "QueenDomino";
|
|
2701
3601
|
if (isLastTurn && allLordsHavePlayed(updatedLords)) {
|
|
2702
3602
|
updatedGame = {
|
|
2703
3603
|
...game,
|
|
@@ -2705,6 +3605,29 @@ var placeDominoUseCase = (game, lordId, position, rotation) => {
|
|
|
2705
3605
|
nextAction: resultStep,
|
|
2706
3606
|
players: updatedPlayers
|
|
2707
3607
|
};
|
|
3608
|
+
} else if (isQueenDomino && !isLastTurn) {
|
|
3609
|
+
updatedGame = {
|
|
3610
|
+
...game,
|
|
3611
|
+
lords: updatedLords,
|
|
3612
|
+
nextAction: {
|
|
3613
|
+
type: "action",
|
|
3614
|
+
nextLord: currentLord.id,
|
|
3615
|
+
nextAction: playerActions.placeKnight
|
|
3616
|
+
},
|
|
3617
|
+
players: updatedPlayers
|
|
3618
|
+
};
|
|
3619
|
+
} else if (isQueenDomino && isLastTurn) {
|
|
3620
|
+
const queenDominoAction = {
|
|
3621
|
+
type: "action",
|
|
3622
|
+
nextLord: currentLord.id,
|
|
3623
|
+
nextAction: playerActions.placeKnight
|
|
3624
|
+
};
|
|
3625
|
+
updatedGame = {
|
|
3626
|
+
...game,
|
|
3627
|
+
lords: updatedLords,
|
|
3628
|
+
nextAction: queenDominoAction,
|
|
3629
|
+
players: updatedPlayers
|
|
3630
|
+
};
|
|
2708
3631
|
} else {
|
|
2709
3632
|
updatedGame = {
|
|
2710
3633
|
...game,
|
|
@@ -2716,6 +3639,401 @@ var placeDominoUseCase = (game, lordId, position, rotation) => {
|
|
|
2716
3639
|
return ok(updatedGame);
|
|
2717
3640
|
};
|
|
2718
3641
|
|
|
3642
|
+
// src/core/domain/entities/knight.ts
|
|
3643
|
+
var countConstructionSquaresInTerritory = (kingdom, position) => {
|
|
3644
|
+
const rows = kingdom.length;
|
|
3645
|
+
const cols = kingdom[0]?.length ?? 0;
|
|
3646
|
+
const startTile = kingdom[position.y]?.[position.x];
|
|
3647
|
+
if (!startTile || startTile.type === "empty" || startTile.type === "castle") {
|
|
3648
|
+
return 0;
|
|
3649
|
+
}
|
|
3650
|
+
const terrainType = startTile.type;
|
|
3651
|
+
const visited = kingdom.map((row) => row.map(() => false));
|
|
3652
|
+
const queue = [[position.x, position.y]];
|
|
3653
|
+
visited[position.y][position.x] = true;
|
|
3654
|
+
let count = 0;
|
|
3655
|
+
const directions = [
|
|
3656
|
+
[-1, 0],
|
|
3657
|
+
[1, 0],
|
|
3658
|
+
[0, -1],
|
|
3659
|
+
[0, 1]
|
|
3660
|
+
];
|
|
3661
|
+
while (queue.length > 0) {
|
|
3662
|
+
const [cx, cy] = queue.pop();
|
|
3663
|
+
const tile = kingdom[cy][cx];
|
|
3664
|
+
if (tile.type !== "empty" && tile.type !== "castle" && "hasConstructionSquare" in tile && tile.hasConstructionSquare) {
|
|
3665
|
+
count++;
|
|
3666
|
+
}
|
|
3667
|
+
for (const [dx, dy] of directions) {
|
|
3668
|
+
const nx = cx + dx;
|
|
3669
|
+
const ny = cy + dy;
|
|
3670
|
+
if (nx >= 0 && ny >= 0 && nx < cols && ny < rows && !visited[ny][nx] && kingdom[ny][nx].type === terrainType) {
|
|
3671
|
+
visited[ny][nx] = true;
|
|
3672
|
+
queue.push([nx, ny]);
|
|
3673
|
+
}
|
|
3674
|
+
}
|
|
3675
|
+
}
|
|
3676
|
+
return count;
|
|
3677
|
+
};
|
|
3678
|
+
var getTerritoryTerrain = (kingdom, position) => {
|
|
3679
|
+
const tile = kingdom[position.y]?.[position.x];
|
|
3680
|
+
if (!tile || tile.type === "empty" || tile.type === "castle") return null;
|
|
3681
|
+
return tile.type;
|
|
3682
|
+
};
|
|
3683
|
+
var territoryHasKnight = (kingdom, position, knights) => {
|
|
3684
|
+
const terrain = getTerritoryTerrain(kingdom, position);
|
|
3685
|
+
if (!terrain) return false;
|
|
3686
|
+
const rows = kingdom.length;
|
|
3687
|
+
const cols = kingdom[0]?.length ?? 0;
|
|
3688
|
+
const visited = kingdom.map((row) => row.map(() => false));
|
|
3689
|
+
const queue = [[position.x, position.y]];
|
|
3690
|
+
visited[position.y][position.x] = true;
|
|
3691
|
+
const territoryPositions = /* @__PURE__ */ new Set();
|
|
3692
|
+
const directions = [
|
|
3693
|
+
[-1, 0],
|
|
3694
|
+
[1, 0],
|
|
3695
|
+
[0, -1],
|
|
3696
|
+
[0, 1]
|
|
3697
|
+
];
|
|
3698
|
+
while (queue.length > 0) {
|
|
3699
|
+
const [cx, cy] = queue.pop();
|
|
3700
|
+
territoryPositions.add(`${cx},${cy}`);
|
|
3701
|
+
for (const [dx, dy] of directions) {
|
|
3702
|
+
const nx = cx + dx;
|
|
3703
|
+
const ny = cy + dy;
|
|
3704
|
+
if (nx >= 0 && ny >= 0 && nx < cols && ny < rows && !visited[ny][nx] && kingdom[ny][nx].type === terrain) {
|
|
3705
|
+
visited[ny][nx] = true;
|
|
3706
|
+
queue.push([nx, ny]);
|
|
3707
|
+
}
|
|
3708
|
+
}
|
|
3709
|
+
}
|
|
3710
|
+
return knights.some(
|
|
3711
|
+
(k) => territoryPositions.has(`${k.position.x},${k.position.y}`)
|
|
3712
|
+
);
|
|
3713
|
+
};
|
|
3714
|
+
var canPlaceKnight = (player, kingdom, position) => {
|
|
3715
|
+
const knights = player.knights ?? [];
|
|
3716
|
+
if (knights.length >= MAX_KNIGHTS) return false;
|
|
3717
|
+
const tile = kingdom[position.y]?.[position.x];
|
|
3718
|
+
if (!tile || tile.type === "empty" || tile.type === "castle") return false;
|
|
3719
|
+
if (territoryHasKnight(kingdom, position, knights)) return false;
|
|
3720
|
+
return true;
|
|
3721
|
+
};
|
|
3722
|
+
var placeKnight = (player, kingdom, position) => {
|
|
3723
|
+
const knight = { playerId: player.id, position };
|
|
3724
|
+
const knights = [...player.knights ?? [], knight];
|
|
3725
|
+
const taxAmount = countConstructionSquaresInTerritory(kingdom, position);
|
|
3726
|
+
const updatedPlayer = addCoins({ ...player, knights }, taxAmount);
|
|
3727
|
+
return updatedPlayer;
|
|
3728
|
+
};
|
|
3729
|
+
|
|
3730
|
+
// src/core/useCases/placeKnight.ts
|
|
3731
|
+
var placeKnightUseCase = (game, lordId, position) => {
|
|
3732
|
+
const currentAction = game.nextAction;
|
|
3733
|
+
if (currentAction.nextLord !== lordId) {
|
|
3734
|
+
return err(ErrorCode.NOT_YOUR_TURN);
|
|
3735
|
+
}
|
|
3736
|
+
if (currentAction.nextAction !== playerActions.placeKnight) {
|
|
3737
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
3738
|
+
}
|
|
3739
|
+
const currentLord = game.lords.find((l) => l.id === lordId);
|
|
3740
|
+
if (!currentLord) return err(ErrorCode.LORD_NOT_FOUND);
|
|
3741
|
+
const currentPlayer = game.players.find(
|
|
3742
|
+
(p) => p.id === currentLord.playerId
|
|
3743
|
+
);
|
|
3744
|
+
if (!currentPlayer) return err(ErrorCode.PLAYER_NOT_FOUND);
|
|
3745
|
+
if (!canPlaceKnight(currentPlayer, currentPlayer.kingdom, position)) {
|
|
3746
|
+
return err(ErrorCode.CANNOT_PLACE_KNIGHT);
|
|
3747
|
+
}
|
|
3748
|
+
const updatedPlayer = placeKnight(
|
|
3749
|
+
currentPlayer,
|
|
3750
|
+
currentPlayer.kingdom,
|
|
3751
|
+
position
|
|
3752
|
+
);
|
|
3753
|
+
const updatedPlayers = game.players.map(
|
|
3754
|
+
(p) => p.id === currentPlayer.id ? updatedPlayer : p
|
|
3755
|
+
);
|
|
3756
|
+
const nextAction = nextQueenDominoAction(playerActions.placeKnight);
|
|
3757
|
+
return ok({
|
|
3758
|
+
...game,
|
|
3759
|
+
players: updatedPlayers,
|
|
3760
|
+
nextAction: {
|
|
3761
|
+
type: "action",
|
|
3762
|
+
nextLord: lordId,
|
|
3763
|
+
nextAction
|
|
3764
|
+
}
|
|
3765
|
+
});
|
|
3766
|
+
};
|
|
3767
|
+
|
|
3768
|
+
// src/core/domain/entities/building.ts
|
|
3769
|
+
var BOARD_SLOTS = 4;
|
|
3770
|
+
var createBuildersBoard = (tiles, shuffle) => {
|
|
3771
|
+
const shuffled = shuffle([...tiles]);
|
|
3772
|
+
const slots = shuffled.slice(0, BOARD_SLOTS);
|
|
3773
|
+
const drawPile = shuffled.slice(BOARD_SLOTS);
|
|
3774
|
+
return {
|
|
3775
|
+
slots,
|
|
3776
|
+
drawPile
|
|
3777
|
+
};
|
|
3778
|
+
};
|
|
3779
|
+
var findBuildingOnBoard = (board, buildingId) => {
|
|
3780
|
+
for (let i = 0; i < board.slots.length; i++) {
|
|
3781
|
+
const slot = board.slots[i];
|
|
3782
|
+
if (slot && slot.id === buildingId) {
|
|
3783
|
+
return { building: slot, slotIndex: i };
|
|
3784
|
+
}
|
|
3785
|
+
}
|
|
3786
|
+
return null;
|
|
3787
|
+
};
|
|
3788
|
+
var removeBuildingFromBoard = (board, slotIndex) => {
|
|
3789
|
+
const newSlots = [...board.slots];
|
|
3790
|
+
newSlots[slotIndex] = null;
|
|
3791
|
+
return { ...board, slots: newSlots };
|
|
3792
|
+
};
|
|
3793
|
+
var purchaseBuilding = (board, player, buildingId) => {
|
|
3794
|
+
const found = findBuildingOnBoard(board, buildingId);
|
|
3795
|
+
if (!found) return null;
|
|
3796
|
+
const { building, slotIndex } = found;
|
|
3797
|
+
if (!canAfford(player, building.cost)) return null;
|
|
3798
|
+
let updatedPlayer = removeCoins(player, building.cost);
|
|
3799
|
+
if (building.immediateBonus) {
|
|
3800
|
+
switch (building.immediateBonus.type) {
|
|
3801
|
+
case "coins":
|
|
3802
|
+
updatedPlayer = addCoins(updatedPlayer, building.immediateBonus.amount);
|
|
3803
|
+
break;
|
|
3804
|
+
case "tower":
|
|
3805
|
+
updatedPlayer = addTowers(
|
|
3806
|
+
updatedPlayer,
|
|
3807
|
+
building.immediateBonus.amount
|
|
3808
|
+
);
|
|
3809
|
+
break;
|
|
3810
|
+
}
|
|
3811
|
+
}
|
|
3812
|
+
if (building.towers > 0) {
|
|
3813
|
+
updatedPlayer = addTowers(updatedPlayer, building.towers);
|
|
3814
|
+
}
|
|
3815
|
+
const updatedBoard = removeBuildingFromBoard(board, slotIndex);
|
|
3816
|
+
return { updatedBoard, updatedPlayer, building };
|
|
3817
|
+
};
|
|
3818
|
+
var isValidConstructionPosition = (kingdom, placedBuildings, position) => {
|
|
3819
|
+
const tile = kingdom[position.y]?.[position.x];
|
|
3820
|
+
if (!tile || tile.type === "empty" || tile.type === "castle") return false;
|
|
3821
|
+
if (!("hasConstructionSquare" in tile) || !tile.hasConstructionSquare)
|
|
3822
|
+
return false;
|
|
3823
|
+
const occupied = placedBuildings.some(
|
|
3824
|
+
(b) => b.position.x === position.x && b.position.y === position.y
|
|
3825
|
+
);
|
|
3826
|
+
return !occupied;
|
|
3827
|
+
};
|
|
3828
|
+
var placeBuildingOnKingdom = (kingdom, building, position) => {
|
|
3829
|
+
const newKingdom = kingdom.map((row) => [...row]);
|
|
3830
|
+
const tile = newKingdom[position.y][position.x];
|
|
3831
|
+
if (tile.type !== "empty" && tile.type !== "castle") {
|
|
3832
|
+
newKingdom[position.y][position.x] = {
|
|
3833
|
+
...tile,
|
|
3834
|
+
crowns: tile.crowns + building.crowns
|
|
3835
|
+
};
|
|
3836
|
+
}
|
|
3837
|
+
return newKingdom;
|
|
3838
|
+
};
|
|
3839
|
+
var destroyWithDragon = (board, buildingId, player) => {
|
|
3840
|
+
const found = findBuildingOnBoard(board, buildingId);
|
|
3841
|
+
if (!found) return null;
|
|
3842
|
+
const { building, slotIndex } = found;
|
|
3843
|
+
if (!canAfford(player, building.cost)) return null;
|
|
3844
|
+
const updatedPlayer = removeCoins(player, building.cost);
|
|
3845
|
+
const updatedBoard = removeBuildingFromBoard(board, slotIndex);
|
|
3846
|
+
return { updatedBoard, updatedPlayer };
|
|
3847
|
+
};
|
|
3848
|
+
|
|
3849
|
+
// src/core/domain/entities/queen.ts
|
|
3850
|
+
var determineQueenHolder = (players, currentHolderId) => {
|
|
3851
|
+
let maxTowers = 0;
|
|
3852
|
+
let leaderId = null;
|
|
3853
|
+
let isTied = false;
|
|
3854
|
+
for (const player of players) {
|
|
3855
|
+
const towers = getTowerCount(player);
|
|
3856
|
+
if (towers > maxTowers) {
|
|
3857
|
+
maxTowers = towers;
|
|
3858
|
+
leaderId = player.id;
|
|
3859
|
+
isTied = false;
|
|
3860
|
+
} else if (towers === maxTowers && towers > 0 && leaderId !== null) {
|
|
3861
|
+
isTied = true;
|
|
3862
|
+
}
|
|
3863
|
+
}
|
|
3864
|
+
if (isTied || maxTowers === 0) {
|
|
3865
|
+
return currentHolderId;
|
|
3866
|
+
}
|
|
3867
|
+
return leaderId;
|
|
3868
|
+
};
|
|
3869
|
+
|
|
3870
|
+
// src/core/useCases/constructBuilding.ts
|
|
3871
|
+
var constructBuildingUseCase = (game, lordId, buildingId, position) => {
|
|
3872
|
+
const currentAction = game.nextAction;
|
|
3873
|
+
if (currentAction.nextLord !== lordId) {
|
|
3874
|
+
return err(ErrorCode.NOT_YOUR_TURN);
|
|
3875
|
+
}
|
|
3876
|
+
if (currentAction.nextAction !== playerActions.constructBuilding) {
|
|
3877
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
3878
|
+
}
|
|
3879
|
+
if (!game.queendomino) {
|
|
3880
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
3881
|
+
}
|
|
3882
|
+
const currentLord = game.lords.find((l) => l.id === lordId);
|
|
3883
|
+
if (!currentLord) return err(ErrorCode.LORD_NOT_FOUND);
|
|
3884
|
+
const currentPlayer = game.players.find(
|
|
3885
|
+
(p) => p.id === currentLord.playerId
|
|
3886
|
+
);
|
|
3887
|
+
if (!currentPlayer) return err(ErrorCode.PLAYER_NOT_FOUND);
|
|
3888
|
+
if (!isValidConstructionPosition(
|
|
3889
|
+
currentPlayer.kingdom,
|
|
3890
|
+
currentPlayer.buildings ?? [],
|
|
3891
|
+
position
|
|
3892
|
+
)) {
|
|
3893
|
+
return err(ErrorCode.NO_CONSTRUCTION_SQUARE);
|
|
3894
|
+
}
|
|
3895
|
+
const purchaseResult = purchaseBuilding(
|
|
3896
|
+
game.queendomino.buildersBoard,
|
|
3897
|
+
currentPlayer,
|
|
3898
|
+
buildingId
|
|
3899
|
+
);
|
|
3900
|
+
if (!purchaseResult) {
|
|
3901
|
+
return err(ErrorCode.CANNOT_AFFORD_BUILDING);
|
|
3902
|
+
}
|
|
3903
|
+
const { updatedBoard, updatedPlayer, building } = purchaseResult;
|
|
3904
|
+
const updatedKingdom = placeBuildingOnKingdom(
|
|
3905
|
+
updatedPlayer.kingdom,
|
|
3906
|
+
building,
|
|
3907
|
+
position
|
|
3908
|
+
);
|
|
3909
|
+
const placedBuilding = { building, position };
|
|
3910
|
+
const finalPlayer = {
|
|
3911
|
+
...updatedPlayer,
|
|
3912
|
+
kingdom: updatedKingdom,
|
|
3913
|
+
buildings: [...updatedPlayer.buildings ?? [], placedBuilding]
|
|
3914
|
+
};
|
|
3915
|
+
const updatedPlayers = game.players.map(
|
|
3916
|
+
(p) => p.id === currentPlayer.id ? finalPlayer : p
|
|
3917
|
+
);
|
|
3918
|
+
const newQueenHolder = determineQueenHolder(
|
|
3919
|
+
updatedPlayers,
|
|
3920
|
+
game.queendomino.queenHolderId
|
|
3921
|
+
);
|
|
3922
|
+
const nextAction = nextQueenDominoAction(playerActions.constructBuilding);
|
|
3923
|
+
return ok({
|
|
3924
|
+
...game,
|
|
3925
|
+
players: updatedPlayers,
|
|
3926
|
+
queendomino: {
|
|
3927
|
+
...game.queendomino,
|
|
3928
|
+
buildersBoard: updatedBoard,
|
|
3929
|
+
queenHolderId: newQueenHolder
|
|
3930
|
+
},
|
|
3931
|
+
nextAction: {
|
|
3932
|
+
type: "action",
|
|
3933
|
+
nextLord: lordId,
|
|
3934
|
+
nextAction
|
|
3935
|
+
}
|
|
3936
|
+
});
|
|
3937
|
+
};
|
|
3938
|
+
|
|
3939
|
+
// src/core/useCases/useDragon.ts
|
|
3940
|
+
var useDragonUseCase = (game, lordId, buildingId) => {
|
|
3941
|
+
const currentAction = game.nextAction;
|
|
3942
|
+
if (currentAction.nextLord !== lordId) {
|
|
3943
|
+
return err(ErrorCode.NOT_YOUR_TURN);
|
|
3944
|
+
}
|
|
3945
|
+
if (currentAction.nextAction !== playerActions.useDragon) {
|
|
3946
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
3947
|
+
}
|
|
3948
|
+
if (!game.queendomino) {
|
|
3949
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
3950
|
+
}
|
|
3951
|
+
if (!game.queendomino.dragonAvailable || game.queendomino.dragonUsedThisRound) {
|
|
3952
|
+
return err(ErrorCode.DRAGON_UNAVAILABLE);
|
|
3953
|
+
}
|
|
3954
|
+
const currentLord = game.lords.find((l) => l.id === lordId);
|
|
3955
|
+
if (!currentLord) return err(ErrorCode.LORD_NOT_FOUND);
|
|
3956
|
+
const currentPlayer = game.players.find(
|
|
3957
|
+
(p) => p.id === currentLord.playerId
|
|
3958
|
+
);
|
|
3959
|
+
if (!currentPlayer) return err(ErrorCode.PLAYER_NOT_FOUND);
|
|
3960
|
+
if (game.queendomino.queenHolderId === currentPlayer.id) {
|
|
3961
|
+
return err(ErrorCode.QUEEN_HOLDER_CANNOT_USE_DRAGON);
|
|
3962
|
+
}
|
|
3963
|
+
const result = destroyWithDragon(
|
|
3964
|
+
game.queendomino.buildersBoard,
|
|
3965
|
+
buildingId,
|
|
3966
|
+
currentPlayer
|
|
3967
|
+
);
|
|
3968
|
+
if (!result) {
|
|
3969
|
+
return err(ErrorCode.BUILDING_NOT_FOUND);
|
|
3970
|
+
}
|
|
3971
|
+
const { updatedBoard, updatedPlayer } = result;
|
|
3972
|
+
const updatedPlayers = game.players.map(
|
|
3973
|
+
(p) => p.id === currentPlayer.id ? updatedPlayer : p
|
|
3974
|
+
);
|
|
3975
|
+
const maxTurns = game.rules.basic.maxTurns;
|
|
3976
|
+
const isLastTurn = game.turn === maxTurns;
|
|
3977
|
+
if (isLastTurn && allLordsHavePlayed(game.lords)) {
|
|
3978
|
+
return ok({
|
|
3979
|
+
...game,
|
|
3980
|
+
players: updatedPlayers,
|
|
3981
|
+
queendomino: {
|
|
3982
|
+
...game.queendomino,
|
|
3983
|
+
buildersBoard: updatedBoard,
|
|
3984
|
+
dragonUsedThisRound: true
|
|
3985
|
+
},
|
|
3986
|
+
nextAction: { type: "step", step: gameSteps.result }
|
|
3987
|
+
});
|
|
3988
|
+
}
|
|
3989
|
+
return ok({
|
|
3990
|
+
...game,
|
|
3991
|
+
players: updatedPlayers,
|
|
3992
|
+
queendomino: {
|
|
3993
|
+
...game.queendomino,
|
|
3994
|
+
buildersBoard: updatedBoard,
|
|
3995
|
+
dragonUsedThisRound: true
|
|
3996
|
+
},
|
|
3997
|
+
nextAction: nextLordWithAction(game.lords)
|
|
3998
|
+
});
|
|
3999
|
+
};
|
|
4000
|
+
|
|
4001
|
+
// src/core/useCases/skipOptionalAction.ts
|
|
4002
|
+
var skipOptionalActionUseCase = (game, lordId) => {
|
|
4003
|
+
const currentAction = game.nextAction;
|
|
4004
|
+
if (currentAction.nextLord !== lordId) {
|
|
4005
|
+
return err(ErrorCode.NOT_YOUR_TURN);
|
|
4006
|
+
}
|
|
4007
|
+
const action = currentAction.nextAction;
|
|
4008
|
+
const isOptional = action === playerActions.placeKnight || action === playerActions.constructBuilding || action === playerActions.useDragon;
|
|
4009
|
+
if (!isOptional) {
|
|
4010
|
+
return err(ErrorCode.INVALID_OPTIONAL_ACTION);
|
|
4011
|
+
}
|
|
4012
|
+
const nextAction = nextQueenDominoAction(action);
|
|
4013
|
+
if (nextAction === playerActions.pickDomino) {
|
|
4014
|
+
const maxTurns = game.rules.basic.maxTurns;
|
|
4015
|
+
const isLastTurn = game.turn === maxTurns;
|
|
4016
|
+
if (isLastTurn && allLordsHavePlayed(game.lords)) {
|
|
4017
|
+
return ok({
|
|
4018
|
+
...game,
|
|
4019
|
+
nextAction: { type: "step", step: gameSteps.result }
|
|
4020
|
+
});
|
|
4021
|
+
}
|
|
4022
|
+
return ok({
|
|
4023
|
+
...game,
|
|
4024
|
+
nextAction: nextLordWithAction(game.lords)
|
|
4025
|
+
});
|
|
4026
|
+
}
|
|
4027
|
+
return ok({
|
|
4028
|
+
...game,
|
|
4029
|
+
nextAction: {
|
|
4030
|
+
type: "action",
|
|
4031
|
+
nextLord: lordId,
|
|
4032
|
+
nextAction
|
|
4033
|
+
}
|
|
4034
|
+
});
|
|
4035
|
+
};
|
|
4036
|
+
|
|
2719
4037
|
// src/core/useCases/startGame.ts
|
|
2720
4038
|
var startGameUseCase = (deps) => (game) => {
|
|
2721
4039
|
const { uuidMethod: uuidMethod2, shuffleMethod: shuffleMethod2 } = deps;
|
|
@@ -2744,6 +4062,15 @@ var startGameUseCase = (deps) => (game) => {
|
|
|
2744
4062
|
nextLord: shuffledLords[0].id,
|
|
2745
4063
|
nextAction: playerActions.pickDomino
|
|
2746
4064
|
};
|
|
4065
|
+
let queendomino = game.queendomino;
|
|
4066
|
+
if (queendomino && game.mode.name === "QueenDomino") {
|
|
4067
|
+
const buildingShuffle = game.seed ? createSeededShuffle(game.seed, "buildings") : shuffleMethod2;
|
|
4068
|
+
const board = createBuildersBoard(
|
|
4069
|
+
queendomino.buildersBoard.drawPile,
|
|
4070
|
+
buildingShuffle
|
|
4071
|
+
);
|
|
4072
|
+
queendomino = { ...queendomino, buildersBoard: board };
|
|
4073
|
+
}
|
|
2747
4074
|
const newState = {
|
|
2748
4075
|
...game,
|
|
2749
4076
|
lords: shuffledLords,
|
|
@@ -2756,7 +4083,8 @@ var startGameUseCase = (deps) => (game) => {
|
|
|
2756
4083
|
lordId: null,
|
|
2757
4084
|
position: index + 1
|
|
2758
4085
|
};
|
|
2759
|
-
})
|
|
4086
|
+
}),
|
|
4087
|
+
...queendomino !== void 0 && { queendomino }
|
|
2760
4088
|
};
|
|
2761
4089
|
return ok(newState);
|
|
2762
4090
|
};
|
|
@@ -2765,6 +4093,7 @@ var startGameUseCase = (deps) => (game) => {
|
|
|
2765
4093
|
var configureEngine = (config) => {
|
|
2766
4094
|
const modeRepository = jsonModes_default();
|
|
2767
4095
|
const dominoesRepository = jsonDominoes_default();
|
|
4096
|
+
const buildingsRepository = jsonBuildings_default();
|
|
2768
4097
|
const ruleRepository = jsonRules_default();
|
|
2769
4098
|
const uuid = config.uuidMethod || uuidMethod;
|
|
2770
4099
|
const shuffle = config.shuffleMethod || shuffleMethod;
|
|
@@ -2777,7 +4106,8 @@ var configureEngine = (config) => {
|
|
|
2777
4106
|
createGameUseCase({
|
|
2778
4107
|
modeRepository,
|
|
2779
4108
|
dominoesRepository,
|
|
2780
|
-
uuidMethod: uuid
|
|
4109
|
+
uuidMethod: uuid,
|
|
4110
|
+
buildingsRepository
|
|
2781
4111
|
})
|
|
2782
4112
|
),
|
|
2783
4113
|
getModesHandler: getModesHandler(
|
|
@@ -2853,6 +4183,26 @@ var configureEngine = (config) => {
|
|
|
2853
4183
|
logger,
|
|
2854
4184
|
translator,
|
|
2855
4185
|
getDynastyResultUseCase
|
|
4186
|
+
),
|
|
4187
|
+
placeKnightHandler: placeKnightHandler(
|
|
4188
|
+
logger,
|
|
4189
|
+
translator,
|
|
4190
|
+
placeKnightUseCase
|
|
4191
|
+
),
|
|
4192
|
+
constructBuildingHandler: constructBuildingHandler(
|
|
4193
|
+
logger,
|
|
4194
|
+
translator,
|
|
4195
|
+
constructBuildingUseCase
|
|
4196
|
+
),
|
|
4197
|
+
useDragonHandler: useDragonHandler(
|
|
4198
|
+
logger,
|
|
4199
|
+
translator,
|
|
4200
|
+
useDragonUseCase
|
|
4201
|
+
),
|
|
4202
|
+
skipOptionalActionHandler: skipOptionalActionHandler(
|
|
4203
|
+
logger,
|
|
4204
|
+
translator,
|
|
4205
|
+
skipOptionalActionUseCase
|
|
2856
4206
|
)
|
|
2857
4207
|
};
|
|
2858
4208
|
};
|
|
@@ -3576,7 +4926,12 @@ var wrapWithActionLog = (engine) => {
|
|
|
3576
4926
|
const game = engine.discardDomino(cmd);
|
|
3577
4927
|
record("discardDomino", { lordId: cmd.lordId }, game.turn);
|
|
3578
4928
|
return game;
|
|
3579
|
-
}
|
|
4929
|
+
},
|
|
4930
|
+
// Queendomino methods — pass through (no action log recording yet)
|
|
4931
|
+
placeKnight: (cmd) => engine.placeKnight(cmd),
|
|
4932
|
+
constructBuilding: (cmd) => engine.constructBuilding(cmd),
|
|
4933
|
+
useDragon: (cmd) => engine.useDragon(cmd),
|
|
4934
|
+
skipOptionalAction: (cmd) => engine.skipOptionalAction(cmd)
|
|
3580
4935
|
};
|
|
3581
4936
|
return {
|
|
3582
4937
|
engine: wrappedEngine,
|
|
@@ -3717,7 +5072,11 @@ var createGameEngine = (config) => {
|
|
|
3717
5072
|
canPlaceDominoHandler: canPlaceDominoHandler2,
|
|
3718
5073
|
serializeGameHandler: serializeGameHandler2,
|
|
3719
5074
|
deserializeGameHandler: deserializeGameHandler2,
|
|
3720
|
-
getDynastyResultHandler: getDynastyResultHandler2
|
|
5075
|
+
getDynastyResultHandler: getDynastyResultHandler2,
|
|
5076
|
+
placeKnightHandler: placeKnightHandler2,
|
|
5077
|
+
constructBuildingHandler: constructBuildingHandler2,
|
|
5078
|
+
useDragonHandler: useDragonHandler2,
|
|
5079
|
+
skipOptionalActionHandler: skipOptionalActionHandler2
|
|
3721
5080
|
} = configureEngine(config);
|
|
3722
5081
|
let engine = {
|
|
3723
5082
|
getModes: (command) => getModesHandler2(command),
|
|
@@ -3735,7 +5094,11 @@ var createGameEngine = (config) => {
|
|
|
3735
5094
|
canPlaceDomino: (command) => canPlaceDominoHandler2(command),
|
|
3736
5095
|
serialize: (command) => serializeGameHandler2(command),
|
|
3737
5096
|
deserialize: (command) => deserializeGameHandler2(command),
|
|
3738
|
-
getDynastyResults: (command) => getDynastyResultHandler2(command)
|
|
5097
|
+
getDynastyResults: (command) => getDynastyResultHandler2(command),
|
|
5098
|
+
placeKnight: (command) => placeKnightHandler2(command),
|
|
5099
|
+
constructBuilding: (command) => constructBuildingHandler2(command),
|
|
5100
|
+
useDragon: (command) => useDragonHandler2(command),
|
|
5101
|
+
skipOptionalAction: (command) => skipOptionalActionHandler2(command)
|
|
3739
5102
|
};
|
|
3740
5103
|
if (config.events) {
|
|
3741
5104
|
engine = wrapWithEvents(engine, config.events);
|