@pkmn/engine 0.1.0-dev.b01cb48c → 0.1.0-dev.b14f2221

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.
Files changed (81) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +21 -11
  3. package/build/pkg/addon/browser.d.ts +3 -0
  4. package/build/pkg/addon/browser.js +47 -0
  5. package/build/pkg/addon/browser.js.map +1 -0
  6. package/build/pkg/addon/node.d.ts +3 -0
  7. package/build/pkg/addon/node.js +110 -0
  8. package/build/pkg/addon/node.js.map +1 -0
  9. package/build/pkg/addon/wasm.d.ts +2 -0
  10. package/build/pkg/addon/wasm.js +53 -0
  11. package/build/pkg/addon/wasm.js.map +1 -0
  12. package/build/pkg/addon.d.ts +26 -4
  13. package/build/pkg/addon.js +34 -65
  14. package/build/pkg/addon.js.map +1 -1
  15. package/build/pkg/data/layout.json +15 -2
  16. package/build/pkg/data/protocol.json +23 -9
  17. package/build/pkg/data.d.ts +23 -1
  18. package/build/pkg/data.js.map +1 -1
  19. package/build/pkg/gen1.d.ts +15 -18
  20. package/build/pkg/gen1.js +28 -19
  21. package/build/pkg/gen1.js.map +1 -1
  22. package/build/pkg/index.d.ts +40 -90
  23. package/build/pkg/index.js +23 -70
  24. package/build/pkg/index.js.map +1 -1
  25. package/build/pkg/protocol.d.ts +20 -1
  26. package/build/pkg/protocol.js +105 -103
  27. package/build/pkg/protocol.js.map +1 -1
  28. package/build/tools/debug.js +68 -74
  29. package/build/tools/debug.js.map +1 -1
  30. package/build/tools/display/debug.jsx +152 -0
  31. package/build/tools/display/debug.jsx.map +1 -0
  32. package/build/tools/display/index.js +152 -0
  33. package/build/tools/display/index.js.map +1 -0
  34. package/build/tools/display/ui.jsx +359 -0
  35. package/build/tools/display/ui.jsx.map +1 -0
  36. package/build/tools/display/util.js +33 -0
  37. package/build/tools/display/util.js.map +1 -0
  38. package/build.zig +255 -102
  39. package/package.json +59 -138
  40. package/src/bin/install-pkmn-engine +25 -7
  41. package/src/bin/pkmn-debug +1 -1
  42. package/src/lib/bindings/c.zig +200 -0
  43. package/src/lib/bindings/node.zig +117 -0
  44. package/src/lib/bindings/wasm.zig +50 -0
  45. package/src/lib/common/array.zig +70 -0
  46. package/src/lib/common/data.zig +8 -8
  47. package/src/lib/common/debug.zig +30 -9
  48. package/src/lib/common/js.zig +3 -7
  49. package/src/lib/common/optional.zig +11 -17
  50. package/src/lib/common/options.zig +4 -0
  51. package/src/lib/common/protocol.zig +195 -159
  52. package/src/lib/common/rational.zig +303 -310
  53. package/src/lib/common/rng.zig +5 -7
  54. package/src/lib/common/util.zig +33 -1
  55. package/src/lib/gen1/calc.zig +324 -180
  56. package/src/lib/gen1/chance.zig +536 -140
  57. package/src/lib/gen1/data/moves.zig +2 -4
  58. package/src/lib/gen1/data/species.zig +1 -3
  59. package/src/lib/gen1/data/types.zig +3 -4
  60. package/src/lib/gen1/data.zig +40 -43
  61. package/src/lib/gen1/helpers.zig +17 -29
  62. package/src/lib/gen1/mechanics.zig +240 -187
  63. package/src/lib/gen2/calc.zig +35 -28
  64. package/src/lib/gen2/chance.zig +88 -74
  65. package/src/lib/gen2/data/items.zig +1 -3
  66. package/src/lib/gen2/data/moves.zig +2 -4
  67. package/src/lib/gen2/data/species.zig +1 -3
  68. package/src/lib/gen2/data/types.zig +7 -5
  69. package/src/lib/gen2/data.zig +33 -35
  70. package/src/lib/gen2/generated.zig +18 -23
  71. package/src/lib/gen2/helpers.zig +9 -20
  72. package/src/lib/gen2/mechanics.zig +98 -98
  73. package/src/lib/napi.h +2 -0
  74. package/src/lib/node.zig +4 -121
  75. package/src/lib/pkmn.zig +103 -22
  76. package/src/lib/wasm.zig +9 -9
  77. package/src/tools/display/dom.ts +93 -0
  78. package/src/tools/display/ui.css +354 -0
  79. package/build/test/display.js +0 -405
  80. package/build/test/display.js.map +0 -1
  81. package/src/test/display/pkmn.html.tmpl +0 -368
@@ -1,24 +1,20 @@
1
- const std = @import("std");
2
- const builtin = @import("builtin");
3
-
4
- const pkmn = @import("../pkmn.zig");
5
-
6
- const data = @import("../common/data.zig");
7
1
  const DEBUG = @import("../common/debug.zig").print;
8
- const protocol = @import("../common/protocol.zig");
9
- const rng = @import("../common/rng.zig");
10
- const util = @import("../common/util.zig");
11
2
 
3
+ const builtin = @import("builtin");
4
+ const calc = @import("calc.zig");
5
+ const chance = @import("chance.zig");
6
+ const data = @import("../common/data.zig");
7
+ const gen1 = @import("../gen1/data.zig");
12
8
  const items = @import("data/items.zig");
9
+ const mechanics = @import("mechanics.zig");
13
10
  const moves = @import("data/moves.zig");
11
+ const pkmn = @import("../pkmn.zig");
12
+ const protocol = @import("../common/protocol.zig");
13
+ const rng = @import("../common/rng.zig");
14
14
  const species = @import("data/species.zig");
15
+ const std = @import("std");
15
16
  const types = @import("data/types.zig");
16
-
17
- const gen1 = @import("../gen1/data.zig");
18
-
19
- const calc = @import("calc.zig");
20
- const chance = @import("chance.zig");
21
- const mechanics = @import("mechanics.zig");
17
+ const util = @import("../common/util.zig");
22
18
 
23
19
  const assert = std.debug.assert;
24
20
  const expectEqual = std.testing.expectEqual;
@@ -45,6 +41,7 @@ const Player = data.Player;
45
41
  const Result = data.Result;
46
42
 
47
43
  const PointerType = util.PointerType;
44
+ const isPointerTo = util.isPointerTo;
48
45
 
49
46
  const showdown = pkmn.options.showdown;
50
47
 
@@ -60,15 +57,15 @@ pub fn Battle(comptime RNG: anytype) type {
60
57
  turn: u16 = 0,
61
58
  field: Field = .{},
62
59
 
63
- _: [padding]u8 = .{0} ** padding,
60
+ _: [padding]u8 = @splat(0),
64
61
 
65
62
  pub fn side(self: anytype, player: Player) PointerType(@TypeOf(self), Side) {
66
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Self);
63
+ assert(isPointerTo(self, Self));
67
64
  return &self.sides[@intFromEnum(player)];
68
65
  }
69
66
 
70
67
  pub fn foe(self: anytype, player: Player) PointerType(@TypeOf(self), Side) {
71
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Self);
68
+ assert(isPointerTo(self, Self));
72
69
  return &self.sides[@intFromEnum(player.foe())];
73
70
  }
74
71
 
@@ -103,13 +100,13 @@ pub const Weather = enum(u4) {
103
100
  };
104
101
 
105
102
  pub const Side = extern struct {
106
- pokemon: [6]Pokemon = [_]Pokemon{.{}} ** 6,
103
+ pokemon: [6]Pokemon = @splat(.{}),
107
104
  active: ActivePokemon align(8) = .{},
108
105
  conditions: Conditions = .{},
109
106
  // NB: wLastPlayerCounterMove / wLastEnemyCounterMove (wLastPlayerMove / wLastEnemyMove)
110
107
  last_used_move: Move = .None,
111
108
 
112
- _: [7]u8 = .{0} ** 7,
109
+ _: [7]u8 = @splat(0),
113
110
 
114
111
  const Conditions = packed struct(u32) {
115
112
  Spikes: bool = false,
@@ -134,7 +131,7 @@ pub const Side = extern struct {
134
131
  }
135
132
 
136
133
  pub fn get(self: anytype, slot: u8) PointerType(@TypeOf(self), Pokemon) {
137
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Side);
134
+ assert(isPointerTo(self, Side));
138
135
  assert(slot > 0 and slot <= 6);
139
136
  const id = self.pokemon[slot - 1].position;
140
137
  assert(id > 0 and id <= 6);
@@ -142,7 +139,7 @@ pub const Side = extern struct {
142
139
  }
143
140
 
144
141
  pub fn stored(self: anytype) PointerType(@TypeOf(self), Pokemon) {
145
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Side);
142
+ assert(isPointerTo(self, Side));
146
143
  return self.get(1);
147
144
  }
148
145
 
@@ -164,7 +161,7 @@ pub const Side = extern struct {
164
161
  pub const ActivePokemon = extern struct {
165
162
  volatiles: Volatiles align(4) = .{},
166
163
  stats: Stats(u16) = .{},
167
- moves: [4]MoveSlot = [_]MoveSlot{.{}} ** 4,
164
+ moves: [4]MoveSlot = @splat(.{}),
168
165
  boosts: Boosts = .{},
169
166
  types: Types = .{},
170
167
  species: Species = .None,
@@ -176,7 +173,7 @@ pub const ActivePokemon = extern struct {
176
173
  }
177
174
 
178
175
  pub fn move(self: anytype, mslot: u8) PointerType(@TypeOf(self), MoveSlot) {
179
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Pokemon);
176
+ assert(isPointerTo(self, Pokemon));
180
177
  assert(mslot > 0 and mslot <= 4);
181
178
  assert(self.moves[mslot - 1].id != .None);
182
179
  return &self.moves[mslot - 1];
@@ -185,7 +182,7 @@ pub const ActivePokemon = extern struct {
185
182
 
186
183
  pub const Pokemon = extern struct {
187
184
  stats: Stats(u16) = .{},
188
- moves: [4]MoveSlot = [_]MoveSlot{.{}} ** 4,
185
+ moves: [4]MoveSlot = @splat(.{}),
189
186
  types: Types = .{},
190
187
  dvs: DVs = .{},
191
188
  hp: u16 = 0,
@@ -201,7 +198,7 @@ pub const Pokemon = extern struct {
201
198
  }
202
199
 
203
200
  pub fn move(self: anytype, mslot: u8) PointerType(@TypeOf(self), MoveSlot) {
204
- assert(@typeInfo(@TypeOf(self)).Pointer.child == Pokemon);
201
+ assert(isPointerTo(self, Pokemon));
205
202
  assert(mslot > 0 and mslot <= 4);
206
203
  assert(self.moves[mslot - 1].id != .None);
207
204
  return &self.moves[mslot - 1];
@@ -248,12 +245,12 @@ test DVs {
248
245
  var dvs = DVs.from(.Mewtwo, .{ .def = 13 });
249
246
  try expectEqual(Gender.Unknown, dvs.gender);
250
247
  try expectEqual(Type.Ice, dvs.type);
251
- try expectEqual(70, dvs.power());
248
+ try expectEqual(@as(u8, 70), dvs.power());
252
249
 
253
250
  dvs = DVs.from(.Pikachu, .{ .spc = 14 });
254
251
  try expectEqual(Gender.Male, dvs.gender);
255
252
  try expectEqual(Type.Dark, dvs.type);
256
- try expectEqual(69, dvs.power());
253
+ try expectEqual(@as(u8, 69), dvs.power());
257
254
 
258
255
  dvs = DVs.from(.Cyndaquil, .{ .atk = 1, .def = 3, .spe = 10, .spc = 9 });
259
256
  try expectEqual(Gender.Female, dvs.gender);
@@ -380,9 +377,9 @@ test Stats {
380
377
  try expectEqual(0, stats.def);
381
378
 
382
379
  var base = Species.get(.Gyarados).stats;
383
- try expectEqual(127, Stats(u16).calc("hp", base.hp, 0, 5120, 38));
380
+ try expectEqual(@as(u16, 127), Stats(u16).calc("hp", base.hp, 0, 5120, 38));
384
381
  base = Species.get(.Pidgeot).stats;
385
- try expectEqual(279, Stats(u16).calc("spe", base.spe, 15, 63001, 100));
382
+ try expectEqual(@as(u16, 279), Stats(u16).calc("spe", base.spe, 15, 63001, 100));
386
383
  }
387
384
 
388
385
  pub const Boosts = packed struct(u32) {
@@ -428,8 +425,8 @@ test Move {
428
425
  try expectEqual(Move.Effect.ConfusionChance, move.effect);
429
426
  try expectEqual(rng.Gen12.percent(50), move.accuracy);
430
427
  try expectEqual(rng.Gen12.percent(100), move.chance);
431
- try expectEqual(5, Move.pp(.DynamicPunch));
432
- try expectEqual(-1, Move.get(.Counter).priority);
428
+ try expectEqual(@as(u8, 5), Move.pp(.DynamicPunch));
429
+ try expectEqual(@as(i8, -1), Move.get(.Counter).priority);
433
430
  try expect(!move.effect.isHighCritical());
434
431
  try expect(Move.get(.KarateChop).effect.isHighCritical());
435
432
  try expect(Move.get(.RazorWind).effect.isHighCritical());
@@ -439,7 +436,7 @@ pub const Species = species.Species;
439
436
 
440
437
  test Species {
441
438
  try expectEqual(152, @intFromEnum(Species.Chikorita));
442
- try expectEqual(100, Species.get(.Celebi).stats.spd);
439
+ try expectEqual(@as(u8, 100), Species.get(.Celebi).stats.spd);
443
440
  }
444
441
 
445
442
  pub const Type = types.Type;
@@ -452,8 +449,9 @@ test Types {
452
449
  try expect(!Type.Steel.special());
453
450
  try expect(Type.Dark.special());
454
451
 
455
- try expectEqual(3, Type.Water.precedence());
456
- try expect(Type.Bug.precedence() > Type.Poison.precedence());
452
+ try expectEqual(@as(u8, 3), Type.precedence(.Water, .Water));
453
+ try expect(Type.precedence(.Poison, .Bug) > Type.precedence(.Poison, .Poison));
454
+ try expect(Type.precedence(.Ice, .Fire) > Type.precedence(.Ice, .Water));
457
455
 
458
456
  try expectEqual(Effectiveness.Super, Type.effectiveness(.Ghost, .Psychic));
459
457
  try expectEqual(Effectiveness.Super, Type.effectiveness(.Water, .Fire));
@@ -1,37 +1,32 @@
1
1
  //! Code generated by `tools/generate` - manual edits will be overwritten.
2
2
 
3
- const std = @import("std");
4
-
5
3
  const common = @import("../common/data.zig");
6
-
7
4
  const data = @import("data.zig");
8
5
  const mechanics = @import("mechanics.zig");
6
+ const std = @import("std");
9
7
 
10
- const Player = common.Player;
11
- const Result = common.Result;
12
-
13
- const Effectiveness = data.Effectiveness;
14
- const Move = data.Move;
15
-
16
- const Effects = mechanics.Effects;
17
- const State = mechanics.State;
18
-
19
- const canMove = mechanics.canMove;
8
+ const adjustDamage = mechanics.adjustDamage;
9
+ const afterMove = mechanics.afterMove;
10
+ const applyDamage = mechanics.applyDamage;
11
+ const buildRage = mechanics.buildRage;
12
+ const calcDamage = mechanics.calcDamage;
20
13
  const canCharge = mechanics.canCharge;
14
+ const canMove = mechanics.canMove;
15
+ const checkCriticalHit = mechanics.checkCriticalHit;
16
+ const checkHit = mechanics.checkHit;
21
17
  const decrementPP = mechanics.decrementPP;
18
+ const destinyBond = mechanics.destinyBond;
22
19
  const doMove = mechanics.doMove;
23
- const checkHit = mechanics.checkHit;
24
- const checkCriticalHit = mechanics.checkCriticalHit;
25
- const calcDamage = mechanics.calcDamage;
26
- const adjustDamage = mechanics.adjustDamage;
27
- const randomizeDamage = mechanics.randomizeDamage;
28
- const applyDamage = mechanics.applyDamage;
29
- const reportOutcome = mechanics.reportOutcome;
30
20
  const effectChance = mechanics.effectChance;
31
- const afterMove = mechanics.afterMove;
32
- const buildRage = mechanics.buildRage;
21
+ const Effectiveness = data.Effectiveness;
22
+ const Effects = mechanics.Effects;
33
23
  const kingsRock = mechanics.kingsRock;
34
- const destinyBond = mechanics.destinyBond;
24
+ const Move = data.Move;
25
+ const Player = common.Player;
26
+ const randomizeDamage = mechanics.randomizeDamage;
27
+ const reportOutcome = mechanics.reportOutcome;
28
+ const Result = common.Result;
29
+ const State = mechanics.State;
35
30
 
36
31
  const SECONDARY = true;
37
32
  const KINGS = true;
@@ -1,31 +1,20 @@
1
- const std = @import("std");
2
-
3
1
  const common = @import("../common/data.zig");
2
+ const data = @import("data.zig");
3
+ const gen1 = @import("../gen1/data.zig");
4
4
  const options = @import("../common/options.zig");
5
- const protocol = @import("../common/protocol.zig");
6
5
  const rng = @import("../common/rng.zig");
7
-
8
- const gen1 = @import("../gen1/data.zig");
9
-
10
- const data = @import("data.zig");
6
+ const std = @import("std");
11
7
 
12
8
  const assert = std.debug.assert;
13
-
14
- const expectEqual = std.testing.expectEqual;
15
-
16
9
  const Choice = common.Choice;
17
-
18
- const showdown = options.showdown;
19
-
20
- const PSRNG = rng.PSRNG;
21
-
22
10
  const DVs = data.DVs;
23
11
  const Item = data.Item;
24
12
  const Move = data.Move;
25
13
  const MoveSlot = data.MoveSlot;
14
+ const PSRNG = rng.PSRNG;
15
+ const showdown = options.showdown;
26
16
  const Species = data.Species;
27
17
  const Stats = data.Stats;
28
- const Status = data.Status;
29
18
 
30
19
  pub const Options = struct {
31
20
  cleric: bool = showdown,
@@ -83,7 +72,7 @@ pub fn prng(rand: *PSRNG) data.PRNG {
83
72
  var carry: u8 = 0;
84
73
  var div: u8 = 0;
85
74
 
86
- var i: u8 = 0;
75
+ var i: usize = 0;
87
76
  while (i < seed.len) {
88
77
  div = @intCast(timer >> 8);
89
78
  // This is effectively @addWithOverflow but with three operands
@@ -151,7 +140,7 @@ pub const Pokemon = struct {
151
140
  var pokemon = data.Pokemon{};
152
141
  pokemon.species = p.species;
153
142
  const species = Species.get(p.species);
154
- inline for (@typeInfo(@TypeOf(pokemon.stats)).Struct.fields) |field| {
143
+ inline for (@typeInfo(@TypeOf(pokemon.stats)).@"struct".fields) |field| {
155
144
  const hp = comptime std.mem.eql(u8, field.name, "hp");
156
145
  const spc =
157
146
  comptime std.mem.eql(u8, field.name, "spa") or std.mem.eql(u8, field.name, "spd");
@@ -192,7 +181,7 @@ pub const Pokemon = struct {
192
181
 
193
182
  var stats: Stats(u16) = .{};
194
183
  const dvs = gen1.DVs.random(rand);
195
- inline for (@typeInfo(@TypeOf(stats)).Struct.fields) |field| {
184
+ inline for (@typeInfo(@TypeOf(stats)).@"struct".fields) |field| {
196
185
  const hp = std.mem.eql(u8, field.name, "hp");
197
186
  const spc = std.mem.eql(u8, field.name, "spa") or std.mem.eql(u8, field.name, "spd");
198
187
  @field(stats, field.name) = Stats(u16).calc(
@@ -204,7 +193,7 @@ pub const Pokemon = struct {
204
193
  );
205
194
  }
206
195
 
207
- var ms = [_]MoveSlot{.{}} ** 4;
196
+ var ms: [4]MoveSlot = @splat(.{});
208
197
  const n = if (rand.chance(u8, 1, 100)) rand.range(u4, 1, 3 + 1) else 4;
209
198
  for (0..n) |i| {
210
199
  var m: Move = .None;