@tungstenstudio/outschart-generator 1.0.0-rc.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/LICENSE +15 -0
- package/README.md +184 -0
- package/dist/index.cjs +1194 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +107 -0
- package/dist/index.d.ts +107 -0
- package/dist/index.js +1155 -0
- package/dist/index.js.map +1 -0
- package/package.json +60 -0
- package/src/dartboard.ts +122 -0
- package/src/data/dartboard-dimensions.json +77 -0
- package/src/data/dartboard-layout.json +66 -0
- package/src/data/double-out-checkouts.ts +168 -0
- package/src/data/single-out-checkouts.ts +177 -0
- package/src/filter.ts +35 -0
- package/src/generate.ts +91 -0
- package/src/index.ts +37 -0
- package/src/lookup.ts +47 -0
- package/src/miss-analysis.ts +90 -0
- package/src/notation.ts +69 -0
- package/src/recommend.ts +434 -0
- package/src/types.ts +141 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
ISC License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026, Tungsten Studio
|
|
4
|
+
|
|
5
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
6
|
+
purpose with or without fee is hereby granted, provided that the above
|
|
7
|
+
copyright notice and this permission notice appear in all copies.
|
|
8
|
+
|
|
9
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
10
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
11
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
12
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
13
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
14
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
15
|
+
PERFORMANCE OF THIS SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
# @tungstenstudio/outschart-generator
|
|
2
|
+
|
|
3
|
+
Darts outs/checkout chart generator with pre-computed lookups and a miss-aware recommendation engine.
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
- **Instant lookups** — pre-computed double-out and single-out charts, zero computation
|
|
8
|
+
- **Generation engine** — brute-force enumerate all possible checkouts (82K double-out, 242K single-out)
|
|
9
|
+
- **Miss-aware recommendations** — scoring algorithm using physical dartboard layout, segment areas, and bust risk
|
|
10
|
+
- **Preferred targets** — filter checkouts to your favorite finishing doubles/targets
|
|
11
|
+
- **Notation presets** — format charts for different regional conventions (british, american, or custom)
|
|
12
|
+
- **Zero dependencies** — pure TypeScript, works in Node.js and browsers
|
|
13
|
+
|
|
14
|
+
## Install
|
|
15
|
+
|
|
16
|
+
```
|
|
17
|
+
npm install @tungstenstudio/outschart-generator
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## Quick Start
|
|
21
|
+
|
|
22
|
+
```ts
|
|
23
|
+
import { getCheckout, getCheckoutChart, getBogeyNumbers } from '@tungstenstudio/outschart-generator';
|
|
24
|
+
|
|
25
|
+
// Instant lookup
|
|
26
|
+
getCheckout(170, 'double');
|
|
27
|
+
// { darts: ['T20', 'T20', 'Bull'], numDarts: 3 }
|
|
28
|
+
|
|
29
|
+
getCheckout(40, 'double');
|
|
30
|
+
// { darts: ['D20'], numDarts: 1 }
|
|
31
|
+
|
|
32
|
+
// Full chart
|
|
33
|
+
const chart = getCheckoutChart('double');
|
|
34
|
+
|
|
35
|
+
// Bogey numbers (no checkout possible)
|
|
36
|
+
getBogeyNumbers('double');
|
|
37
|
+
// [159, 162, 163, 165, 166, 168, 169]
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
## API
|
|
41
|
+
|
|
42
|
+
### Lookup Functions (pre-computed, instant)
|
|
43
|
+
|
|
44
|
+
#### `getCheckout(score, outMode?)`
|
|
45
|
+
Returns the recommended checkout for a single score, or `null` if not checkable.
|
|
46
|
+
|
|
47
|
+
```ts
|
|
48
|
+
getCheckout(92, 'double')
|
|
49
|
+
// { darts: ['T20', 'D16'], numDarts: 2 }
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
#### `getCheckoutChart(outMode?, range?)`
|
|
53
|
+
Returns the full checkout chart, optionally filtered by score range.
|
|
54
|
+
|
|
55
|
+
```ts
|
|
56
|
+
getCheckoutChart('single', { min: 1, max: 60 })
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
#### `getBogeyNumbers(outMode?)`
|
|
60
|
+
Returns scores that cannot be finished in 3 darts.
|
|
61
|
+
|
|
62
|
+
#### `isCheckable(score, outMode?)`
|
|
63
|
+
Returns `true` if the score has a checkout in the pre-computed chart.
|
|
64
|
+
|
|
65
|
+
### Generation Engine (computational)
|
|
66
|
+
|
|
67
|
+
#### `generateAllCheckouts(options)`
|
|
68
|
+
Brute-force enumerates ALL possible checkouts.
|
|
69
|
+
|
|
70
|
+
```ts
|
|
71
|
+
const result = generateAllCheckouts({ outMode: 'double' });
|
|
72
|
+
// result.totalOptions === 82047
|
|
73
|
+
// result.checkouts[170].options === [['T20', 'T20', 'Bull']]
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
#### `generateRecommended(options)`
|
|
77
|
+
Generates a miss-aware recommended chart using the scoring algorithm.
|
|
78
|
+
|
|
79
|
+
```ts
|
|
80
|
+
const result = generateRecommended({
|
|
81
|
+
outMode: 'single',
|
|
82
|
+
includeAlternates: true,
|
|
83
|
+
altThreshold: 1.0,
|
|
84
|
+
overrides: { 100: { darts: ['T20', '20', '20'] } },
|
|
85
|
+
});
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
#### `filterByPreferredTargets(checkouts, preferredTargets)`
|
|
89
|
+
Filters enumerated checkouts to only those finishing on preferred targets.
|
|
90
|
+
|
|
91
|
+
```ts
|
|
92
|
+
const all = generateAllCheckouts({ outMode: 'double' });
|
|
93
|
+
const filtered = filterByPreferredTargets(all.checkouts, ['D20', 'D16']);
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
### Notation / Internationalization
|
|
97
|
+
|
|
98
|
+
#### `formatDart(dart, notation)`
|
|
99
|
+
Formats a single dart label using a notation preset or custom map.
|
|
100
|
+
|
|
101
|
+
```ts
|
|
102
|
+
import { formatDart, NOTATIONS } from '@tungstenstudio/outschart-generator';
|
|
103
|
+
|
|
104
|
+
formatDart('T20', NOTATIONS.british) // 'T20'
|
|
105
|
+
formatDart('Bull', NOTATIONS.british) // 'DB'
|
|
106
|
+
formatDart('25', NOTATIONS.american) // 'SB'
|
|
107
|
+
formatDart('20', NOTATIONS.explicit) // 'S20'
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
#### `formatCheckoutChart(chart, notation)`
|
|
111
|
+
Formats an entire checkout chart. Accepts a preset name string or a `NotationMap` object.
|
|
112
|
+
|
|
113
|
+
```ts
|
|
114
|
+
import { getCheckoutChart, formatCheckoutChart } from '@tungstenstudio/outschart-generator';
|
|
115
|
+
|
|
116
|
+
const chart = getCheckoutChart('double');
|
|
117
|
+
|
|
118
|
+
// Use a built-in preset by name
|
|
119
|
+
const british = formatCheckoutChart(chart, 'british');
|
|
120
|
+
british[170].darts // ['T20', 'T20', 'DB']
|
|
121
|
+
|
|
122
|
+
// Use a fully custom notation
|
|
123
|
+
const custom = formatCheckoutChart(chart, {
|
|
124
|
+
treble: 'Triple ',
|
|
125
|
+
double: 'Double ',
|
|
126
|
+
single: '',
|
|
127
|
+
bull: 'Bullseye',
|
|
128
|
+
outerBull: 'Outer Bull',
|
|
129
|
+
});
|
|
130
|
+
custom[170].darts // ['Triple 20', 'Triple 20', 'Bullseye']
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
#### `NOTATIONS`
|
|
134
|
+
Built-in notation presets:
|
|
135
|
+
|
|
136
|
+
| Preset | Treble | Double | Single | Bull | 25 |
|
|
137
|
+
|--------|--------|--------|--------|------|------|
|
|
138
|
+
| `default` | `T20` | `D20` | `20` | `Bull` | `25` |
|
|
139
|
+
| `british` | `T20` | `D20` | `S20` | `DB` | `SB` |
|
|
140
|
+
| `american` | `T20` | `D20` | `20` | `DB` | `SB` |
|
|
141
|
+
| `explicit` | `T20` | `D20` | `S20` | `Bull` | `25` |
|
|
142
|
+
|
|
143
|
+
### Utilities
|
|
144
|
+
|
|
145
|
+
#### `parseTarget(str)`
|
|
146
|
+
Parses dart notation into components.
|
|
147
|
+
|
|
148
|
+
```ts
|
|
149
|
+
parseTarget('D16') // { bed: 'double', number: 16, value: 32 }
|
|
150
|
+
parseTarget('T20') // { bed: 'treble', number: 20, value: 60 }
|
|
151
|
+
parseTarget('Bull') // { bed: 'Bull', number: null, value: 50 }
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
#### `formatTarget(bed, number)`
|
|
155
|
+
Inverse of `parseTarget` — formats a bed/number pair into label and value.
|
|
156
|
+
|
|
157
|
+
### Types
|
|
158
|
+
|
|
159
|
+
- `OutMode` — `'double' | 'single'`
|
|
160
|
+
- `CheckoutEntry` — `{ darts: string[]; numDarts: number; alternates?: string[][] }`
|
|
161
|
+
- `CheckoutChart` — `Record<number, CheckoutEntry>`
|
|
162
|
+
- `ParsedTarget` — `{ bed: BedType; number: number | null; value: number }`
|
|
163
|
+
- `NotationMap` — `{ treble: string; double: string; single: string; bull: string; outerBull: string }`
|
|
164
|
+
- `OutsChartError` — Custom error class with semantic codes
|
|
165
|
+
|
|
166
|
+
## Demo
|
|
167
|
+
|
|
168
|
+
See the [live demo](https://tungstenstudio.gitlab.io/libs/outschart-generator/) for an interactive chart with preferred targets and export.
|
|
169
|
+
|
|
170
|
+
## Development
|
|
171
|
+
|
|
172
|
+
```bash
|
|
173
|
+
npm install
|
|
174
|
+
npm run test # Run tests
|
|
175
|
+
npm run typecheck # Type-check
|
|
176
|
+
npm run build # Build ESM + CJS + DTS
|
|
177
|
+
npm run build:demo # Build demo IIFE bundle
|
|
178
|
+
npm run dev # Build demo and serve locally
|
|
179
|
+
npm run verify # Run all checks
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
## License
|
|
183
|
+
|
|
184
|
+
ISC
|