@logic-pad/core 0.24.0 → 0.25.1

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 (268) hide show
  1. package/assets/logic-core.global.d.ts +22 -0
  2. package/dist/benchmark/helper.d.ts +21 -0
  3. package/dist/benchmark/helper.js +34 -0
  4. package/dist/benchmark/prepareBench.js +140 -0
  5. package/dist/benchmark/runBench.js +206 -0
  6. package/dist/{data → src/data}/dataHelper.js +4 -18
  7. package/dist/{data → src/data}/grid.js +15 -68
  8. package/dist/{data → src/data}/gridZones.js +1 -6
  9. package/dist/{data → src/data}/rules/banPatternRule.js +19 -50
  10. package/dist/{data → src/data}/rules/cellCountPerZoneRule.js +2 -6
  11. package/dist/{data → src/data}/rules/cellCountRule.js +62 -96
  12. package/dist/{data → src/data}/rules/completePatternRule.js +6 -22
  13. package/dist/{data → src/data}/rules/connectAllRule.js +20 -50
  14. package/dist/{data → src/data}/rules/connectZonesRule.js +28 -58
  15. package/dist/{data → src/data}/rules/containsShapeRule.js +29 -65
  16. package/dist/{data → src/data}/rules/customRule.js +28 -57
  17. package/dist/{data → src/data}/rules/differentCountPerZoneRule.js +33 -68
  18. package/dist/{data → src/data}/rules/exactCountPerZoneRule.js +43 -82
  19. package/dist/{data → src/data}/rules/foresightRule.js +50 -87
  20. package/dist/{data → src/data}/rules/lyingSymbolRule.js +37 -88
  21. package/dist/{data → src/data}/rules/musicControlLine.js +69 -131
  22. package/dist/{data → src/data}/rules/musicGridRule.js +43 -76
  23. package/dist/{data → src/data}/rules/mysteryRule.js +29 -58
  24. package/dist/src/data/rules/noLoopsRule.d.ts +29 -0
  25. package/dist/src/data/rules/noLoopsRule.js +111 -0
  26. package/dist/{data → src/data}/rules/offByXRule.js +49 -74
  27. package/dist/{data → src/data}/rules/perfectionRule.js +8 -28
  28. package/dist/{data → src/data}/rules/regionAreaRule.js +47 -86
  29. package/dist/{data → src/data}/rules/regionShapeRule.js +2 -6
  30. package/dist/{data → src/data}/rules/rules.gen.d.ts +1 -0
  31. package/dist/{data → src/data}/rules/rules.gen.js +1 -0
  32. package/dist/{data → src/data}/rules/sameCountPerZoneRule.js +33 -68
  33. package/dist/{data → src/data}/rules/sameShapeRule.js +18 -44
  34. package/dist/{data → src/data}/rules/symbolsPerRegionRule.js +52 -90
  35. package/dist/{data → src/data}/rules/undercluedRule.js +11 -27
  36. package/dist/{data → src/data}/rules/uniqueShapeRule.js +18 -44
  37. package/dist/{data → src/data}/rules/wrapAroundRule.js +99 -138
  38. package/dist/{data → src/data}/serializer/serializer_checksum.js +1 -9
  39. package/dist/{data → src/data}/serializer/serializer_v0.js +1 -9
  40. package/dist/{data → src/data}/solver/auto/autoSolver.js +11 -40
  41. package/dist/{data → src/data}/solver/backtrack/backtrackSolver.js +15 -39
  42. package/dist/{data → src/data}/solver/backtrack/backtrackWorker.js +1 -1
  43. package/dist/{data → src/data}/solver/backtrack/data.js +16 -48
  44. package/dist/{data → src/data}/solver/backtrack/rules/banPattern.js +1 -6
  45. package/dist/{data → src/data}/solver/backtrack/rules/cellCount.js +1 -6
  46. package/dist/{data → src/data}/solver/backtrack/rules/connectAll.js +1 -6
  47. package/dist/{data → src/data}/solver/backtrack/rules/regionArea.js +1 -6
  48. package/dist/{data → src/data}/solver/backtrack/rules/regionShape.js +1 -6
  49. package/dist/{data → src/data}/solver/backtrack/rules/sameShape.js +1 -6
  50. package/dist/{data → src/data}/solver/backtrack/rules/symbolsPerRegion.js +2 -12
  51. package/dist/{data → src/data}/solver/backtrack/rules/uniqueShape.js +1 -6
  52. package/dist/{data → src/data}/solver/backtrack/symbols/areaNumber.js +1 -6
  53. package/dist/{data → src/data}/solver/backtrack/symbols/dart.js +1 -6
  54. package/dist/{data → src/data}/solver/backtrack/symbols/directionLinker.js +3 -13
  55. package/dist/{data → src/data}/solver/backtrack/symbols/focus.js +3 -13
  56. package/dist/{data → src/data}/solver/backtrack/symbols/galaxy.js +1 -6
  57. package/dist/{data → src/data}/solver/backtrack/symbols/letter.js +2 -12
  58. package/dist/{data → src/data}/solver/backtrack/symbols/lotus.js +1 -6
  59. package/dist/{data → src/data}/solver/backtrack/symbols/minesweeper.js +3 -13
  60. package/dist/{data → src/data}/solver/backtrack/symbols/myopia.js +1 -6
  61. package/dist/{data → src/data}/solver/backtrack/symbols/viewpoint.js +1 -6
  62. package/dist/{data → src/data}/solver/cspuz/cspuzSolver.js +22 -46
  63. package/dist/{data → src/data}/solver/eventIteratingSolver.js +9 -12
  64. package/dist/{data → src/data}/solver/solver.js +1 -8
  65. package/dist/src/data/solver/universal/universalSolver.js +20 -0
  66. package/dist/src/data/solver/universal/universalWorker.d.ts +1 -0
  67. package/dist/{data → src/data}/solver/z3/modules/areaNumberModule.js +1 -9
  68. package/dist/{data → src/data}/solver/z3/modules/cellCountModule.js +1 -9
  69. package/dist/{data → src/data}/solver/z3/modules/connectAllModule.js +1 -9
  70. package/dist/{data → src/data}/solver/z3/modules/dartModule.js +1 -9
  71. package/dist/{data → src/data}/solver/z3/modules/letterModule.js +1 -9
  72. package/dist/{data → src/data}/solver/z3/modules/myopiaModule.js +1 -9
  73. package/dist/{data → src/data}/solver/z3/modules/regionAreaModule.js +1 -9
  74. package/dist/{data → src/data}/solver/z3/modules/viewpointModule.js +1 -9
  75. package/dist/{data → src/data}/solver/z3/z3Solver.js +4 -27
  76. package/dist/{data → src/data}/solver/z3/z3SolverContext.js +3 -12
  77. package/dist/{data → src/data}/symbols/areaNumberSymbol.js +28 -44
  78. package/dist/{data → src/data}/symbols/customIconSymbol.js +40 -64
  79. package/dist/{data → src/data}/symbols/customSymbol.js +4 -12
  80. package/dist/{data → src/data}/symbols/customTextSymbol.js +40 -64
  81. package/dist/{data → src/data}/symbols/dartSymbol.js +39 -59
  82. package/dist/{data → src/data}/symbols/directionLinkerSymbol.js +34 -63
  83. package/dist/{data → src/data}/symbols/everyLetterSymbol.js +37 -65
  84. package/dist/{data → src/data}/symbols/focusSymbol.js +49 -69
  85. package/dist/{data → src/data}/symbols/galaxySymbol.js +12 -31
  86. package/dist/{data → src/data}/symbols/hiddenSymbol.js +34 -62
  87. package/dist/{data → src/data}/symbols/houseSymbol.js +39 -67
  88. package/dist/{data → src/data}/symbols/letterSymbol.js +40 -68
  89. package/dist/{data → src/data}/symbols/lotusSymbol.js +58 -81
  90. package/dist/{data → src/data}/symbols/minesweeperSymbol.js +30 -46
  91. package/dist/{data → src/data}/symbols/myopiaSymbol.js +45 -69
  92. package/dist/{data → src/data}/symbols/numberSymbol.js +6 -18
  93. package/dist/{data → src/data}/symbols/symbol.js +4 -12
  94. package/dist/{data → src/data}/symbols/viewpointSymbol.js +26 -42
  95. package/dist/{data → src/data}/tile.js +6 -18
  96. package/dist/src/data/validateAsync.js +71 -0
  97. package/dist/src/data/validateAsyncWorker.d.ts +1 -0
  98. package/dist/{index.d.ts → src/index.d.ts} +2 -1
  99. package/dist/{index.js → src/index.js} +2 -1
  100. package/package.json +13 -10
  101. package/dist/data/solver/universal/universalSolver.js +0 -38
  102. package/dist/data/validateAsync.js +0 -128
  103. /package/dist/{data/solver/backtrack/backtrackWorker.d.ts → benchmark/prepareBench.d.ts} +0 -0
  104. /package/dist/{data/solver/cspuz/cspuzWorker.d.ts → benchmark/runBench.d.ts} +0 -0
  105. /package/dist/{data → src/data}/config.d.ts +0 -0
  106. /package/dist/{data → src/data}/config.js +0 -0
  107. /package/dist/{data → src/data}/configurable.d.ts +0 -0
  108. /package/dist/{data → src/data}/configurable.js +0 -0
  109. /package/dist/{data → src/data}/dataHelper.d.ts +0 -0
  110. /package/dist/{data → src/data}/events/eventHelper.d.ts +0 -0
  111. /package/dist/{data → src/data}/events/eventHelper.js +0 -0
  112. /package/dist/{data → src/data}/events/onFinalValidation.d.ts +0 -0
  113. /package/dist/{data → src/data}/events/onFinalValidation.js +0 -0
  114. /package/dist/{data → src/data}/events/onGetTile.d.ts +0 -0
  115. /package/dist/{data → src/data}/events/onGetTile.js +0 -0
  116. /package/dist/{data → src/data}/events/onGridChange.d.ts +0 -0
  117. /package/dist/{data → src/data}/events/onGridChange.js +0 -0
  118. /package/dist/{data → src/data}/events/onGridResize.d.ts +0 -0
  119. /package/dist/{data → src/data}/events/onGridResize.js +0 -0
  120. /package/dist/{data → src/data}/events/onSetGrid.d.ts +0 -0
  121. /package/dist/{data → src/data}/events/onSetGrid.js +0 -0
  122. /package/dist/{data → src/data}/events/onSymbolDisplay.d.ts +0 -0
  123. /package/dist/{data → src/data}/events/onSymbolDisplay.js +0 -0
  124. /package/dist/{data → src/data}/events/onSymbolMerge.d.ts +0 -0
  125. /package/dist/{data → src/data}/events/onSymbolMerge.js +0 -0
  126. /package/dist/{data → src/data}/events/onSymbolValidation.d.ts +0 -0
  127. /package/dist/{data → src/data}/events/onSymbolValidation.js +0 -0
  128. /package/dist/{data → src/data}/grid.d.ts +0 -0
  129. /package/dist/{data → src/data}/gridConnections.d.ts +0 -0
  130. /package/dist/{data → src/data}/gridConnections.js +0 -0
  131. /package/dist/{data → src/data}/gridZones.d.ts +0 -0
  132. /package/dist/{data → src/data}/instruction.d.ts +0 -0
  133. /package/dist/{data → src/data}/instruction.js +0 -0
  134. /package/dist/{data → src/data}/primitives.d.ts +0 -0
  135. /package/dist/{data → src/data}/primitives.js +0 -0
  136. /package/dist/{data → src/data}/puzzle.d.ts +0 -0
  137. /package/dist/{data → src/data}/puzzle.js +0 -0
  138. /package/dist/{data → src/data}/rules/banPatternRule.d.ts +0 -0
  139. /package/dist/{data → src/data}/rules/cellCountPerZoneRule.d.ts +0 -0
  140. /package/dist/{data → src/data}/rules/cellCountRule.d.ts +0 -0
  141. /package/dist/{data → src/data}/rules/completePatternRule.d.ts +0 -0
  142. /package/dist/{data → src/data}/rules/connectAllRule.d.ts +0 -0
  143. /package/dist/{data → src/data}/rules/connectZonesRule.d.ts +0 -0
  144. /package/dist/{data → src/data}/rules/containsShapeRule.d.ts +0 -0
  145. /package/dist/{data → src/data}/rules/customRule.d.ts +0 -0
  146. /package/dist/{data → src/data}/rules/differentCountPerZoneRule.d.ts +0 -0
  147. /package/dist/{data → src/data}/rules/exactCountPerZoneRule.d.ts +0 -0
  148. /package/dist/{data → src/data}/rules/foresightRule.d.ts +0 -0
  149. /package/dist/{data → src/data}/rules/index.d.ts +0 -0
  150. /package/dist/{data → src/data}/rules/index.js +0 -0
  151. /package/dist/{data → src/data}/rules/lyingSymbolRule.d.ts +0 -0
  152. /package/dist/{data → src/data}/rules/musicControlLine.d.ts +0 -0
  153. /package/dist/{data → src/data}/rules/musicGridRule.d.ts +0 -0
  154. /package/dist/{data → src/data}/rules/mysteryRule.d.ts +0 -0
  155. /package/dist/{data → src/data}/rules/offByXRule.d.ts +0 -0
  156. /package/dist/{data → src/data}/rules/perfectionRule.d.ts +0 -0
  157. /package/dist/{data → src/data}/rules/regionAreaRule.d.ts +0 -0
  158. /package/dist/{data → src/data}/rules/regionShapeRule.d.ts +0 -0
  159. /package/dist/{data → src/data}/rules/rule.d.ts +0 -0
  160. /package/dist/{data → src/data}/rules/rule.js +0 -0
  161. /package/dist/{data → src/data}/rules/sameCountPerZoneRule.d.ts +0 -0
  162. /package/dist/{data → src/data}/rules/sameShapeRule.d.ts +0 -0
  163. /package/dist/{data → src/data}/rules/symbolsPerRegionRule.d.ts +0 -0
  164. /package/dist/{data → src/data}/rules/undercluedRule.d.ts +0 -0
  165. /package/dist/{data → src/data}/rules/uniqueShapeRule.d.ts +0 -0
  166. /package/dist/{data → src/data}/rules/wrapAroundRule.d.ts +0 -0
  167. /package/dist/{data → src/data}/serializer/allSerializers.d.ts +0 -0
  168. /package/dist/{data → src/data}/serializer/allSerializers.js +0 -0
  169. /package/dist/{data → src/data}/serializer/compressor/allCompressors.d.ts +0 -0
  170. /package/dist/{data → src/data}/serializer/compressor/allCompressors.js +0 -0
  171. /package/dist/{data → src/data}/serializer/compressor/checksumCompressor.d.ts +0 -0
  172. /package/dist/{data → src/data}/serializer/compressor/checksumCompressor.js +0 -0
  173. /package/dist/{data → src/data}/serializer/compressor/compressorBase.d.ts +0 -0
  174. /package/dist/{data → src/data}/serializer/compressor/compressorBase.js +0 -0
  175. /package/dist/{data → src/data}/serializer/compressor/deflateCompressor.d.ts +0 -0
  176. /package/dist/{data → src/data}/serializer/compressor/deflateCompressor.js +0 -0
  177. /package/dist/{data → src/data}/serializer/compressor/gzipCompressor.d.ts +0 -0
  178. /package/dist/{data → src/data}/serializer/compressor/gzipCompressor.js +0 -0
  179. /package/dist/{data → src/data}/serializer/compressor/streamCompressor.d.ts +0 -0
  180. /package/dist/{data → src/data}/serializer/compressor/streamCompressor.js +0 -0
  181. /package/dist/{data → src/data}/serializer/serializerBase.d.ts +0 -0
  182. /package/dist/{data → src/data}/serializer/serializerBase.js +0 -0
  183. /package/dist/{data → src/data}/serializer/serializer_checksum.d.ts +0 -0
  184. /package/dist/{data → src/data}/serializer/serializer_v0.d.ts +0 -0
  185. /package/dist/{data → src/data}/shapes.d.ts +0 -0
  186. /package/dist/{data → src/data}/shapes.js +0 -0
  187. /package/dist/{data → src/data}/solver/allSolvers.d.ts +0 -0
  188. /package/dist/{data → src/data}/solver/allSolvers.js +0 -0
  189. /package/dist/{data → src/data}/solver/auto/autoSolver.d.ts +0 -0
  190. /package/dist/{data → src/data}/solver/backtrack/backtrackSolver.d.ts +0 -0
  191. /package/dist/{data/solver/universal/universalWorker.d.ts → src/data/solver/backtrack/backtrackWorker.d.ts} +0 -0
  192. /package/dist/{data → src/data}/solver/backtrack/data.d.ts +0 -0
  193. /package/dist/{data → src/data}/solver/backtrack/rules/banPattern.d.ts +0 -0
  194. /package/dist/{data → src/data}/solver/backtrack/rules/cellCount.d.ts +0 -0
  195. /package/dist/{data → src/data}/solver/backtrack/rules/connectAll.d.ts +0 -0
  196. /package/dist/{data → src/data}/solver/backtrack/rules/regionArea.d.ts +0 -0
  197. /package/dist/{data → src/data}/solver/backtrack/rules/regionShape.d.ts +0 -0
  198. /package/dist/{data → src/data}/solver/backtrack/rules/sameShape.d.ts +0 -0
  199. /package/dist/{data → src/data}/solver/backtrack/rules/symbolsPerRegion.d.ts +0 -0
  200. /package/dist/{data → src/data}/solver/backtrack/rules/uniqueShape.d.ts +0 -0
  201. /package/dist/{data → src/data}/solver/backtrack/symbols/areaNumber.d.ts +0 -0
  202. /package/dist/{data → src/data}/solver/backtrack/symbols/dart.d.ts +0 -0
  203. /package/dist/{data → src/data}/solver/backtrack/symbols/directionLinker.d.ts +0 -0
  204. /package/dist/{data → src/data}/solver/backtrack/symbols/focus.d.ts +0 -0
  205. /package/dist/{data → src/data}/solver/backtrack/symbols/galaxy.d.ts +0 -0
  206. /package/dist/{data → src/data}/solver/backtrack/symbols/letter.d.ts +0 -0
  207. /package/dist/{data → src/data}/solver/backtrack/symbols/lotus.d.ts +0 -0
  208. /package/dist/{data → src/data}/solver/backtrack/symbols/minesweeper.d.ts +0 -0
  209. /package/dist/{data → src/data}/solver/backtrack/symbols/myopia.d.ts +0 -0
  210. /package/dist/{data → src/data}/solver/backtrack/symbols/viewpoint.d.ts +0 -0
  211. /package/dist/{data → src/data}/solver/cspuz/cspuzSolver.d.ts +0 -0
  212. /package/dist/{data/validateAsyncWorker.d.ts → src/data/solver/cspuz/cspuzWorker.d.ts} +0 -0
  213. /package/dist/{data → src/data}/solver/cspuz/cspuzWorker.js +0 -0
  214. /package/dist/{data → src/data}/solver/cspuz/jsonify.d.ts +0 -0
  215. /package/dist/{data → src/data}/solver/cspuz/jsonify.js +0 -0
  216. /package/dist/{data → src/data}/solver/eventIteratingSolver.d.ts +0 -0
  217. /package/dist/{data → src/data}/solver/solver.d.ts +0 -0
  218. /package/dist/{data → src/data}/solver/universal/universalSolver.d.ts +0 -0
  219. /package/dist/{data → src/data}/solver/universal/universalWorker.js +0 -0
  220. /package/dist/{data → src/data}/solver/z3/modules/areaNumberModule.d.ts +0 -0
  221. /package/dist/{data → src/data}/solver/z3/modules/cellCountModule.d.ts +0 -0
  222. /package/dist/{data → src/data}/solver/z3/modules/connectAllModule.d.ts +0 -0
  223. /package/dist/{data → src/data}/solver/z3/modules/dartModule.d.ts +0 -0
  224. /package/dist/{data → src/data}/solver/z3/modules/index.d.ts +0 -0
  225. /package/dist/{data → src/data}/solver/z3/modules/index.js +0 -0
  226. /package/dist/{data → src/data}/solver/z3/modules/letterModule.d.ts +0 -0
  227. /package/dist/{data → src/data}/solver/z3/modules/modules.gen.d.ts +0 -0
  228. /package/dist/{data → src/data}/solver/z3/modules/modules.gen.js +0 -0
  229. /package/dist/{data → src/data}/solver/z3/modules/myopiaModule.d.ts +0 -0
  230. /package/dist/{data → src/data}/solver/z3/modules/regionAreaModule.d.ts +0 -0
  231. /package/dist/{data → src/data}/solver/z3/modules/viewpointModule.d.ts +0 -0
  232. /package/dist/{data → src/data}/solver/z3/modules/z3Module.d.ts +0 -0
  233. /package/dist/{data → src/data}/solver/z3/modules/z3Module.js +0 -0
  234. /package/dist/{data → src/data}/solver/z3/utils.d.ts +0 -0
  235. /package/dist/{data → src/data}/solver/z3/utils.js +0 -0
  236. /package/dist/{data → src/data}/solver/z3/z3Solver.d.ts +0 -0
  237. /package/dist/{data → src/data}/solver/z3/z3SolverContext.d.ts +0 -0
  238. /package/dist/{data → src/data}/symbols/areaNumberSymbol.d.ts +0 -0
  239. /package/dist/{data → src/data}/symbols/customIconSymbol.d.ts +0 -0
  240. /package/dist/{data → src/data}/symbols/customSymbol.d.ts +0 -0
  241. /package/dist/{data → src/data}/symbols/customTextSymbol.d.ts +0 -0
  242. /package/dist/{data → src/data}/symbols/dartSymbol.d.ts +0 -0
  243. /package/dist/{data → src/data}/symbols/directionLinkerSymbol.d.ts +0 -0
  244. /package/dist/{data → src/data}/symbols/everyLetterSymbol.d.ts +0 -0
  245. /package/dist/{data → src/data}/symbols/focusSymbol.d.ts +0 -0
  246. /package/dist/{data → src/data}/symbols/galaxySymbol.d.ts +0 -0
  247. /package/dist/{data → src/data}/symbols/hiddenSymbol.d.ts +0 -0
  248. /package/dist/{data → src/data}/symbols/houseSymbol.d.ts +0 -0
  249. /package/dist/{data → src/data}/symbols/index.d.ts +0 -0
  250. /package/dist/{data → src/data}/symbols/index.js +0 -0
  251. /package/dist/{data → src/data}/symbols/letterSymbol.d.ts +0 -0
  252. /package/dist/{data → src/data}/symbols/lotusSymbol.d.ts +0 -0
  253. /package/dist/{data → src/data}/symbols/minesweeperSymbol.d.ts +0 -0
  254. /package/dist/{data → src/data}/symbols/myopiaSymbol.d.ts +0 -0
  255. /package/dist/{data → src/data}/symbols/numberSymbol.d.ts +0 -0
  256. /package/dist/{data → src/data}/symbols/symbol.d.ts +0 -0
  257. /package/dist/{data → src/data}/symbols/symbols.gen.d.ts +0 -0
  258. /package/dist/{data → src/data}/symbols/symbols.gen.js +0 -0
  259. /package/dist/{data → src/data}/symbols/viewpointSymbol.d.ts +0 -0
  260. /package/dist/{data → src/data}/tile.d.ts +0 -0
  261. /package/dist/{data → src/data}/tileConnections.d.ts +0 -0
  262. /package/dist/{data → src/data}/tileConnections.js +0 -0
  263. /package/dist/{data → src/data}/validate.d.ts +0 -0
  264. /package/dist/{data → src/data}/validate.js +0 -0
  265. /package/dist/{data → src/data}/validateAsync.d.ts +0 -0
  266. /package/dist/{data → src/data}/validateAsyncWorker.js +0 -0
  267. /package/dist/{polyfill → src/polyfill}/streamPolyfill.d.ts +0 -0
  268. /package/dist/{polyfill → src/polyfill}/streamPolyfill.js +0 -0
@@ -1929,6 +1929,28 @@ declare global {
1929
1929
  withVisible(visible: boolean): this;
1930
1930
  static cleanSolution(solution: GridData, baseGrid?: GridData): GridData;
1931
1931
  }
1932
+ export declare class NoLoopsRule extends Rule {
1933
+ readonly color: Color;
1934
+ readonly title = 'No Loops';
1935
+ private static readonly CONFIGS;
1936
+ private static readonly EXAMPLE_GRID_LIGHT;
1937
+ private static readonly EXAMPLE_GRID_DARK;
1938
+ private static readonly SEARCH_VARIANTS;
1939
+ /**
1940
+ * **No loops in <color> cells**
1941
+ *
1942
+ * @param color - The color of the cells to check.
1943
+ */
1944
+ constructor(color: Color);
1945
+ get id(): string;
1946
+ get explanation(): string;
1947
+ get configs(): readonly AnyConfig[] | null;
1948
+ createExampleGrid(): GridData;
1949
+ get searchVariants(): SearchVariant[];
1950
+ validateGrid(grid: GridData): RuleState;
1951
+ copyWith({ color }: { color?: Color }): this;
1952
+ withColor(color: Color): this;
1953
+ }
1932
1954
  export declare class OffByXRule
1933
1955
  extends Rule
1934
1956
  implements SymbolValidationHandler
@@ -0,0 +1,21 @@
1
+ import { Puzzle } from '../src/data/puzzle.js';
2
+ import CompressorBase from '../src/data/serializer/compressor/compressorBase.js';
3
+ declare class BunCompressor extends CompressorBase {
4
+ get id(): string;
5
+ compress(input: string): Promise<string>;
6
+ decompress(input: string): Promise<string>;
7
+ }
8
+ export declare const bunCompressor: BunCompressor;
9
+ export interface PuzzleEntry {
10
+ pid: number;
11
+ difficulty: number;
12
+ puzzleLink: string;
13
+ }
14
+ export interface BenchmarkEntry {
15
+ pid: number;
16
+ supported: boolean;
17
+ solveTime: number;
18
+ solveCorrect: boolean;
19
+ }
20
+ export declare function parseLink(link: string): Promise<Puzzle>;
21
+ export {};
@@ -0,0 +1,34 @@
1
+ import { Serializer } from '../src/data/serializer/allSerializers.js';
2
+ import { encode, decode } from 'uint8-to-base64';
3
+ import CompressorBase from '../src/data/serializer/compressor/compressorBase.js';
4
+ const decoder = new TextDecoder();
5
+ const encoder = new TextEncoder();
6
+ class BunCompressor extends CompressorBase {
7
+ get id() {
8
+ return 'dfl';
9
+ }
10
+ compress(input) {
11
+ const data = Bun.deflateSync(encoder.encode(input), {
12
+ library: 'libdeflate',
13
+ level: 12,
14
+ });
15
+ return Promise.resolve(`${this.id}_${encode(data).replace(/\+/g, '-').replace(/\//g, '_')}`);
16
+ }
17
+ decompress(input) {
18
+ const data = decode(input.replace(`${this.id}_`, '').replace(/-/g, '+').replace(/_/g, '/'));
19
+ const result = Bun.inflateSync(data, {
20
+ library: 'libdeflate',
21
+ level: 12,
22
+ });
23
+ return Promise.resolve(decoder.decode(result));
24
+ }
25
+ }
26
+ export const bunCompressor = new BunCompressor();
27
+ export async function parseLink(link) {
28
+ const url = new URL(link);
29
+ const data = url.searchParams.get('d');
30
+ if (data === null) {
31
+ throw new Error('Missing data parameter');
32
+ }
33
+ return Serializer.parsePuzzle(await bunCompressor.decompress(data));
34
+ }
@@ -0,0 +1,140 @@
1
+ import { parseArgs } from 'util';
2
+ import { allSolvers } from '../src/data/solver/allSolvers.js';
3
+ import { parseLink } from './helper.js';
4
+ import PQueue from 'p-queue';
5
+ const allPuzzlesPath = 'benchmark/data/all_puzzles_logic_pad.json';
6
+ const { values, positionals } = parseArgs({
7
+ args: Bun.argv,
8
+ options: {
9
+ maxTime: {
10
+ type: 'string',
11
+ default: '10',
12
+ short: 't',
13
+ },
14
+ maxCount: {
15
+ type: 'string',
16
+ default: '99999',
17
+ short: 'c',
18
+ },
19
+ concurrency: {
20
+ type: 'string',
21
+ default: '4',
22
+ short: 'n',
23
+ },
24
+ help: {
25
+ type: 'boolean',
26
+ short: 'h',
27
+ },
28
+ },
29
+ strict: true,
30
+ allowPositionals: true,
31
+ });
32
+ positionals.splice(0, 2); // Remove "bun" and script name
33
+ if (values.help || positionals.length !== 1) {
34
+ console.log(`
35
+ Usage: bun bench:prepare <solver> [options]
36
+
37
+ Options:
38
+ -t, --maxTime <number> Maximum seconds allowed for each solve (default: 10)
39
+ -c, --maxCount <number> Maximum number of puzzles included (default: 100)
40
+ -n, --concurrency <number> Number of solves to run concurrently (default: 4)
41
+ -h, --help Show this help message
42
+
43
+ Solver:
44
+ Name of the solver to benchmark. Available solvers are:
45
+ ${[...allSolvers.keys()].map(s => ` - ${s}`).join('\n')}
46
+ `);
47
+ process.exit(0);
48
+ }
49
+ const maxTime = parseFloat(values.maxTime) * 1000;
50
+ const maxCount = parseInt(values.maxCount);
51
+ const solverName = positionals[0];
52
+ const solver = allSolvers.get(solverName);
53
+ if (!solver) {
54
+ console.error(`Error: Solver "${solverName}" not found.`);
55
+ process.exit(1);
56
+ }
57
+ const allPuzzles = (await Bun.file(allPuzzlesPath).json());
58
+ allPuzzles.sort(() => Math.random() - 0.5);
59
+ const results = [];
60
+ const pqueue = new PQueue({ concurrency: 4 });
61
+ function printEntry(benchmarkEntry, entryId, solverId, pid) {
62
+ if (benchmarkEntry.supported) {
63
+ console.log(`${solverId}\t| ${entryId} / ${allPuzzles.length}\t| ${pid}\t| ${Number.isNaN(benchmarkEntry.solveTime)
64
+ ? 'timeout'
65
+ : `${benchmarkEntry.solveTime.toFixed(0)}ms`} ${benchmarkEntry.solveCorrect ? '✓' : '✗'}`);
66
+ }
67
+ else {
68
+ console.log(`${solverId}\t| ${entryId} / ${allPuzzles.length}\t| ${pid}\t| unsupported`);
69
+ }
70
+ }
71
+ console.log('Available\t| Selected\t| PID\t| Result');
72
+ for (const entry of allPuzzles) {
73
+ if (results.filter(r => r.result.solveCorrect && r.result.supported).length >=
74
+ maxCount) {
75
+ break;
76
+ }
77
+ const puzzle = await parseLink(entry.puzzleLink);
78
+ void pqueue.add(async () => {
79
+ if (!solver.isGridSupported(puzzle.grid)) {
80
+ results.push({
81
+ puzzle: entry,
82
+ result: {
83
+ pid: entry.pid,
84
+ supported: false,
85
+ solveTime: Number.NaN,
86
+ solveCorrect: false,
87
+ },
88
+ });
89
+ printEntry(results[results.length - 1].result, results.length, solverName, entry.pid);
90
+ return;
91
+ }
92
+ const startTime = performance.now();
93
+ const abortController = new AbortController();
94
+ const benchmarkEntry = {
95
+ pid: entry.pid,
96
+ supported: true,
97
+ solveTime: Number.NaN,
98
+ solveCorrect: false,
99
+ };
100
+ let step = 0;
101
+ const handle = setTimeout(() => {
102
+ abortController.abort();
103
+ }, maxTime);
104
+ try {
105
+ for await (const solution of solver.solve(puzzle.grid, abortController.signal)) {
106
+ if (step === 0) {
107
+ const solveCorrect = solution?.colorEquals(puzzle.solution) ?? false;
108
+ if (!solveCorrect)
109
+ break;
110
+ }
111
+ else {
112
+ benchmarkEntry.solveCorrect = solution === null;
113
+ if (benchmarkEntry.solveCorrect)
114
+ benchmarkEntry.solveTime = performance.now() - startTime;
115
+ break;
116
+ }
117
+ step++;
118
+ }
119
+ }
120
+ catch {
121
+ benchmarkEntry.solveCorrect = false;
122
+ }
123
+ clearTimeout(handle);
124
+ results.push({ puzzle: entry, result: benchmarkEntry });
125
+ printEntry(results[results.length - 1].result, results.length, solverName, entry.pid);
126
+ });
127
+ }
128
+ await pqueue.onIdle();
129
+ const selectedPuzzles = results.filter(r => r.result.solveCorrect && r.result.supported);
130
+ const benchmarkEntries = selectedPuzzles.map(r => r.result);
131
+ await Bun.write(`benchmark/data/bench_${solverName}_puzzles.json`, JSON.stringify(selectedPuzzles.map(r => r.puzzle), null, 2));
132
+ await Bun.write(`benchmark/data/bench_${solverName}_results.json`, JSON.stringify(benchmarkEntries, null, 2));
133
+ console.log(`
134
+ Benchmark preparation completed. Selected ${selectedPuzzles.length} puzzles.
135
+
136
+ - Solver: ${solverName} Max Time: ${maxTime}ms Max Count: ${maxCount}
137
+ - Average time: ${benchmarkEntries.filter(e => !Number.isNaN(e.solveTime)).reduce((a, b) => a + b.solveTime, 0) / benchmarkEntries.filter(e => !Number.isNaN(e.solveTime)).length}ms
138
+ - Number of timeouts: ${benchmarkEntries.filter(e => Number.isNaN(e.solveTime)).length}
139
+ - Solve correctness: ${benchmarkEntries.filter(e => e.solveCorrect).length} / ${benchmarkEntries.length}
140
+ `);
@@ -0,0 +1,206 @@
1
+ import { parseArgs } from 'util';
2
+ import { allSolvers } from '../src/data/solver/allSolvers.js';
3
+ import { parseLink } from './helper.js';
4
+ import PQueue from 'p-queue';
5
+ const { values, positionals } = parseArgs({
6
+ args: Bun.argv,
7
+ options: {
8
+ maxTime: {
9
+ type: 'string',
10
+ default: '10',
11
+ short: 't',
12
+ },
13
+ maxCount: {
14
+ type: 'string',
15
+ default: '99999',
16
+ short: 'c',
17
+ },
18
+ concurrency: {
19
+ type: 'string',
20
+ default: '4',
21
+ short: 'n',
22
+ },
23
+ help: {
24
+ type: 'boolean',
25
+ short: 'h',
26
+ },
27
+ },
28
+ strict: true,
29
+ allowPositionals: true,
30
+ });
31
+ positionals.splice(0, 2); // Remove "bun" and script name
32
+ if (values.help || positionals.length === 0) {
33
+ console.log(`
34
+ Usage: bun bench:run <solver> [options]
35
+
36
+ Options:
37
+ -t, --maxTime <number> Maximum seconds allowed for each solve (default: 10)
38
+ -c, --maxCount <number> Maximum number of puzzles included (default: 100)
39
+ -n, --concurrency <number> Number of solves to run concurrently (default: 4)
40
+ -h, --help Show this help message
41
+
42
+ Solvers available for benchmarking:
43
+ ${[...allSolvers.keys()].map(s => ` - ${s}`).join('\n')}
44
+ `);
45
+ process.exit(0);
46
+ }
47
+ const maxTime = parseFloat(values.maxTime) * 1000;
48
+ const maxCount = parseInt(values.maxCount);
49
+ const concurrency = parseInt(values.concurrency);
50
+ for (const name of positionals) {
51
+ if (!allSolvers.has(name)) {
52
+ console.error(`Error: Solver "${name}" not found.`);
53
+ process.exit(1);
54
+ }
55
+ }
56
+ const allPuzzles = (await Bun.file(`benchmark/data/bench_${positionals[0]}_puzzles.json`).json());
57
+ allPuzzles.sort(() => Math.random() - 0.5);
58
+ allPuzzles.splice(maxCount);
59
+ const benchmarkEntries = Object.fromEntries(positionals.map(name => [
60
+ name,
61
+ allPuzzles.map(p => ({
62
+ pid: p.pid,
63
+ supported: false,
64
+ solveTime: Number.NaN,
65
+ solveCorrect: false,
66
+ })),
67
+ ]));
68
+ const pqueue = new PQueue({ concurrency });
69
+ function printEntry(benchmarkEntry, entryId, solverId, pid) {
70
+ if (benchmarkEntry.supported) {
71
+ console.log(`${solverId}\t| ${entryId} / ${allPuzzles.length}\t| ${pid}\t| ${Number.isNaN(benchmarkEntry.solveTime)
72
+ ? 'timeout'
73
+ : `${benchmarkEntry.solveTime.toFixed(0)}ms`} ${benchmarkEntry.solveCorrect ? '✓' : '✗'}`);
74
+ }
75
+ else {
76
+ console.log(`${solverId}\t| ${entryId} / ${allPuzzles.length}\t| ${pid}\t| unsupported`);
77
+ }
78
+ }
79
+ console.log('Solver \t| Trial \t| PID\t| Result');
80
+ console.log();
81
+ for (let i = 0; i < allPuzzles.length; i++) {
82
+ const entry = allPuzzles[i];
83
+ const solvers = positionals.slice().sort(() => Math.random() - 0.5);
84
+ const puzzle = await parseLink(entry.puzzleLink);
85
+ for (const solverId of solvers) {
86
+ const solver = allSolvers.get(solverId);
87
+ void pqueue.add(async () => {
88
+ if (!solver.isGridSupported(puzzle.grid)) {
89
+ benchmarkEntries[solverId][i] = {
90
+ pid: entry.pid,
91
+ supported: false,
92
+ solveTime: Number.NaN,
93
+ solveCorrect: false,
94
+ };
95
+ printEntry(benchmarkEntries[solverId][i], i + 1, solverId, entry.pid);
96
+ return;
97
+ }
98
+ const startTime = performance.now();
99
+ const abortController = new AbortController();
100
+ const benchmarkEntry = {
101
+ pid: entry.pid,
102
+ supported: true,
103
+ solveTime: Number.NaN,
104
+ solveCorrect: false,
105
+ };
106
+ let step = 0;
107
+ const handle = setTimeout(() => {
108
+ abortController.abort();
109
+ }, maxTime);
110
+ try {
111
+ for await (const solution of solver.solve(puzzle.grid, abortController.signal)) {
112
+ if (step === 0) {
113
+ const solveCorrect = solution?.colorEquals(puzzle.solution) ?? false;
114
+ if (!solveCorrect)
115
+ break;
116
+ }
117
+ else {
118
+ benchmarkEntry.solveCorrect = solution === null;
119
+ if (benchmarkEntry.solveCorrect)
120
+ benchmarkEntry.solveTime = performance.now() - startTime;
121
+ break;
122
+ }
123
+ step++;
124
+ }
125
+ }
126
+ catch {
127
+ benchmarkEntry.solveCorrect = false;
128
+ }
129
+ clearTimeout(handle);
130
+ benchmarkEntries[solverId][i] = benchmarkEntry;
131
+ printEntry(benchmarkEntry, i + 1, solverId, entry.pid);
132
+ });
133
+ }
134
+ }
135
+ await pqueue.onIdle();
136
+ const results = positionals.map(name => ({
137
+ solver: name,
138
+ fastestCount: 0,
139
+ solve25: 0,
140
+ solve50: 0,
141
+ solve75: 0,
142
+ solveSD: 0,
143
+ unsupportedCount: 0,
144
+ incorrectCount: 0,
145
+ }));
146
+ for (let i = 0; i < benchmarkEntries[positionals[0]].length; i++) {
147
+ let fastestSolveTime = Number.POSITIVE_INFINITY;
148
+ let fastestSolverIndex = null;
149
+ for (let j = 0; j < positionals.length; j++) {
150
+ const entry = benchmarkEntries[positionals[j]][i];
151
+ if (!entry.supported) {
152
+ results[j].unsupportedCount++;
153
+ continue;
154
+ }
155
+ if (entry.solveCorrect && !Number.isNaN(entry.solveTime)) {
156
+ if (entry.solveTime < fastestSolveTime) {
157
+ fastestSolveTime = entry.solveTime;
158
+ fastestSolverIndex = j;
159
+ }
160
+ }
161
+ else {
162
+ results[j].incorrectCount++;
163
+ }
164
+ }
165
+ if (fastestSolverIndex !== null) {
166
+ results[fastestSolverIndex].fastestCount++;
167
+ }
168
+ }
169
+ for (let j = 0; j < positionals.length; j++) {
170
+ const entries = benchmarkEntries[positionals[j]].filter(e => e.supported && e.solveCorrect && !Number.isNaN(e.solveTime));
171
+ // 25th percentile
172
+ const times = entries.map(e => e.solveTime).sort((a, b) => a - b);
173
+ results[j].solve25 =
174
+ times.length === 0
175
+ ? Number.NaN
176
+ : times[Math.floor((times.length - 1) * 0.25)];
177
+ // 50th percentile (median)
178
+ results[j].solve50 =
179
+ times.length === 0
180
+ ? Number.NaN
181
+ : times[Math.floor((times.length - 1) * 0.5)];
182
+ // 75th percentile
183
+ results[j].solve75 =
184
+ times.length === 0
185
+ ? Number.NaN
186
+ : times[Math.floor((times.length - 1) * 0.75)];
187
+ // Standard deviation
188
+ const mean = times.reduce((sum, time) => sum + time, 0) / (times.length || 1);
189
+ const variance = times.reduce((sum, time) => sum + (time - mean) ** 2, 0) /
190
+ (times.length || 1);
191
+ results[j].solveSD = Math.sqrt(variance);
192
+ }
193
+ console.log('\nBenchmark Results:');
194
+ for (const result of results) {
195
+ console.log(`
196
+ ${result.solver}:
197
+ Fastest Solves: ${result.fastestCount}
198
+ Solve time:
199
+ P25: ${Number.isNaN(result.solve25) ? 'N/A' : `${result.solve25.toFixed(2)}ms`}
200
+ P50: ${Number.isNaN(result.solve50) ? 'N/A' : `${result.solve50.toFixed(2)}ms`}
201
+ P75: ${Number.isNaN(result.solve75) ? 'N/A' : `${result.solve75.toFixed(2)}ms`}
202
+ SD: ${Number.isNaN(result.solveSD) ? 'N/A' : `${result.solveSD.toFixed(2)}ms`}
203
+ Unsupported Puzzles: ${result.unsupportedCount}
204
+ Incorrect Solutions: ${result.incorrectCount}
205
+ `);
206
+ }
@@ -199,19 +199,11 @@ export function unescape(text, escapeCharacters = '=,:|') {
199
199
  return result + text.substring(index);
200
200
  }
201
201
  export class CachedAccess {
202
+ getter;
203
+ static UNCACHED = Symbol('uncached');
204
+ cache = CachedAccess.UNCACHED;
202
205
  constructor(getter) {
203
- Object.defineProperty(this, "getter", {
204
- enumerable: true,
205
- configurable: true,
206
- writable: true,
207
- value: getter
208
- });
209
- Object.defineProperty(this, "cache", {
210
- enumerable: true,
211
- configurable: true,
212
- writable: true,
213
- value: CachedAccess.UNCACHED
214
- });
206
+ this.getter = getter;
215
207
  }
216
208
  static of(getter) {
217
209
  return new CachedAccess(getter);
@@ -223,9 +215,3 @@ export class CachedAccess {
223
215
  return this.cache;
224
216
  }
225
217
  }
226
- Object.defineProperty(CachedAccess, "UNCACHED", {
227
- enumerable: true,
228
- configurable: true,
229
- writable: true,
230
- value: Symbol('uncached')
231
- });
@@ -13,6 +13,19 @@ export const NEIGHBOR_OFFSETS = [
13
13
  { x: 0, y: 1 },
14
14
  ];
15
15
  export default class GridData {
16
+ width;
17
+ height;
18
+ tiles;
19
+ connections;
20
+ zones;
21
+ symbols;
22
+ rules;
23
+ // Important rules are cached for quick access
24
+ /* eslint-disable @typescript-eslint/no-unsafe-enum-comparison */
25
+ musicGrid = CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.MusicGrid));
26
+ completePattern = CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.CompletePattern));
27
+ underclued = CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.Underclued));
28
+ wrapAround = CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.WrapAround));
16
29
  /* eslint-enable @typescript-eslint/no-unsafe-enum-comparison */
17
30
  /**
18
31
  * Create a new grid with tiles, connections, symbols and rules.
@@ -26,74 +39,8 @@ export default class GridData {
26
39
  * @param rules The rules of the grid.
27
40
  */
28
41
  constructor(width, height, tiles, connections, zones, symbols, rules) {
29
- Object.defineProperty(this, "width", {
30
- enumerable: true,
31
- configurable: true,
32
- writable: true,
33
- value: width
34
- });
35
- Object.defineProperty(this, "height", {
36
- enumerable: true,
37
- configurable: true,
38
- writable: true,
39
- value: height
40
- });
41
- Object.defineProperty(this, "tiles", {
42
- enumerable: true,
43
- configurable: true,
44
- writable: true,
45
- value: void 0
46
- });
47
- Object.defineProperty(this, "connections", {
48
- enumerable: true,
49
- configurable: true,
50
- writable: true,
51
- value: void 0
52
- });
53
- Object.defineProperty(this, "zones", {
54
- enumerable: true,
55
- configurable: true,
56
- writable: true,
57
- value: void 0
58
- });
59
- Object.defineProperty(this, "symbols", {
60
- enumerable: true,
61
- configurable: true,
62
- writable: true,
63
- value: void 0
64
- });
65
- Object.defineProperty(this, "rules", {
66
- enumerable: true,
67
- configurable: true,
68
- writable: true,
69
- value: void 0
70
- });
71
- // Important rules are cached for quick access
72
- /* eslint-disable @typescript-eslint/no-unsafe-enum-comparison */
73
- Object.defineProperty(this, "musicGrid", {
74
- enumerable: true,
75
- configurable: true,
76
- writable: true,
77
- value: CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.MusicGrid))
78
- });
79
- Object.defineProperty(this, "completePattern", {
80
- enumerable: true,
81
- configurable: true,
82
- writable: true,
83
- value: CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.CompletePattern))
84
- });
85
- Object.defineProperty(this, "underclued", {
86
- enumerable: true,
87
- configurable: true,
88
- writable: true,
89
- value: CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.Underclued))
90
- });
91
- Object.defineProperty(this, "wrapAround", {
92
- enumerable: true,
93
- configurable: true,
94
- writable: true,
95
- value: CachedAccess.of(() => this.findRule(rule => rule.id === MajorRule.WrapAround))
96
- });
42
+ this.width = width;
43
+ this.height = height;
97
44
  this.width = width;
98
45
  this.height = height;
99
46
  this.tiles = tiles ?? array(width, height, () => TileData.empty());
@@ -1,12 +1,7 @@
1
1
  import { isSameEdge } from './dataHelper.js';
2
2
  export default class GridZones {
3
+ edges;
3
4
  constructor(edges) {
4
- Object.defineProperty(this, "edges", {
5
- enumerable: true,
6
- configurable: true,
7
- writable: true,
8
- value: void 0
9
- });
10
5
  this.edges = GridZones.deduplicateEdges(edges ?? []);
11
6
  }
12
7
  addEdge(edge) {
@@ -4,7 +4,25 @@ import { array } from '../dataHelper.js';
4
4
  import { Color, State } from '../primitives.js';
5
5
  import { getShapeVariants, sanitizePatternGrid, tilesToShape, } from '../shapes.js';
6
6
  import Rule from './rule.js';
7
- class BanPatternRule extends Rule {
7
+ export default class BanPatternRule extends Rule {
8
+ title = 'Ban Pattern';
9
+ static EXAMPLE_GRID = Object.freeze(GridData.create(['nnnnn', 'nnnnn', 'wwwwn', 'nnnnn', 'nnnnn']));
10
+ static CONFIGS = Object.freeze([
11
+ {
12
+ type: ConfigType.Shape,
13
+ default: BanPatternRule.EXAMPLE_GRID,
14
+ resizable: true,
15
+ field: 'pattern',
16
+ description: 'Pattern',
17
+ explanation: 'The pattern to be banned. Can be a mix of dark and light tiles.',
18
+ configurable: true,
19
+ },
20
+ ]);
21
+ static SEARCH_VARIANTS = [
22
+ new BanPatternRule(BanPatternRule.EXAMPLE_GRID).searchVariant(),
23
+ ];
24
+ pattern;
25
+ cache;
8
26
  /**
9
27
  * **Don't make this pattern**
10
28
  *
@@ -12,24 +30,6 @@ class BanPatternRule extends Rule {
12
30
  */
13
31
  constructor(pattern) {
14
32
  super();
15
- Object.defineProperty(this, "title", {
16
- enumerable: true,
17
- configurable: true,
18
- writable: true,
19
- value: 'Ban Pattern'
20
- });
21
- Object.defineProperty(this, "pattern", {
22
- enumerable: true,
23
- configurable: true,
24
- writable: true,
25
- value: void 0
26
- });
27
- Object.defineProperty(this, "cache", {
28
- enumerable: true,
29
- configurable: true,
30
- writable: true,
31
- value: void 0
32
- });
33
33
  this.pattern = sanitizePatternGrid(pattern);
34
34
  this.cache = getShapeVariants(tilesToShape(this.pattern.tiles));
35
35
  }
@@ -122,35 +122,4 @@ class BanPatternRule extends Rule {
122
122
  return this.copyWith({ pattern });
123
123
  }
124
124
  }
125
- Object.defineProperty(BanPatternRule, "EXAMPLE_GRID", {
126
- enumerable: true,
127
- configurable: true,
128
- writable: true,
129
- value: Object.freeze(GridData.create(['nnnnn', 'nnnnn', 'wwwwn', 'nnnnn', 'nnnnn']))
130
- });
131
- Object.defineProperty(BanPatternRule, "CONFIGS", {
132
- enumerable: true,
133
- configurable: true,
134
- writable: true,
135
- value: Object.freeze([
136
- {
137
- type: ConfigType.Shape,
138
- default: BanPatternRule.EXAMPLE_GRID,
139
- resizable: true,
140
- field: 'pattern',
141
- description: 'Pattern',
142
- explanation: 'The pattern to be banned. Can be a mix of dark and light tiles.',
143
- configurable: true,
144
- },
145
- ])
146
- });
147
- Object.defineProperty(BanPatternRule, "SEARCH_VARIANTS", {
148
- enumerable: true,
149
- configurable: true,
150
- writable: true,
151
- value: [
152
- new BanPatternRule(BanPatternRule.EXAMPLE_GRID).searchVariant(),
153
- ]
154
- });
155
- export default BanPatternRule;
156
125
  export const instance = new BanPatternRule(GridData.create([]));
@@ -1,6 +1,7 @@
1
1
  import { Color } from '../primitives.js';
2
2
  import Rule from './rule.js';
3
3
  export default class CellCountPerZoneRule extends Rule {
4
+ color;
4
5
  get configExplanation() {
5
6
  return 'Use the zone tool to define areas on the grid.';
6
7
  }
@@ -9,12 +10,7 @@ export default class CellCountPerZoneRule extends Rule {
9
10
  */
10
11
  constructor(color) {
11
12
  super();
12
- Object.defineProperty(this, "color", {
13
- enumerable: true,
14
- configurable: true,
15
- writable: true,
16
- value: color
17
- });
13
+ this.color = color;
18
14
  this.color = color;
19
15
  }
20
16
  getZoneCounts(grid) {