@doan-labs/peek 0.1.0 → 1.1.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/src/svg.ts CHANGED
@@ -13,7 +13,7 @@ import {
13
13
  restPose,
14
14
  } from './draw'
15
15
  import { type Axes, fnv1a, type Identity, identify } from './identity'
16
- import type { Expression } from './tables'
16
+ import { ACCESSORIES, type AccessorySlot, type Expression } from './tables'
17
17
 
18
18
  export type PeekOptions = Partial<Axes> & {
19
19
  /** px. Drives the stroke ramp (thicker below 96) and the riso print. */
@@ -35,6 +35,12 @@ export type PeekOptions = Partial<Axes> & {
35
35
  id?: string
36
36
  }
37
37
 
38
+ // an unknown item from untyped callers keeps what the name picked
39
+ const wear = <S extends AccessorySlot>(o: PeekOptions, base: Identity, s: S) =>
40
+ (ACCESSORIES[s] as readonly string[]).includes(o[s] as string)
41
+ ? (o[s] as Identity[S])
42
+ : base[s]
43
+
38
44
  /**
39
45
  * A name decides identity unless the caller overrides an axis: an explicit
40
46
  * face, color or part wins over the hash, and every other axis stays put.
@@ -54,6 +60,9 @@ export function settle(
54
60
  mouth: o.mouth ?? base.mouth,
55
61
  cheeks: o.cheeks ?? base.cheeks,
56
62
  trait: o.trait ?? base.trait,
63
+ eyewear: wear(o, base, 'eyewear'),
64
+ headwear: wear(o, base, 'headwear'),
65
+ neckwear: wear(o, base, 'neckwear'),
57
66
  }
58
67
  const pose = restPose(who, o.expression ?? 'normal', o.gaze)
59
68
  const look = {
@@ -63,8 +72,13 @@ export function settle(
63
72
  riso: o.riso ?? false,
64
73
  live,
65
74
  }
75
+ // Keep the byte-level peek@1 contract for faces without accessories.
76
+ const { eyewear, headwear, neckwear, ...legacy } = who
77
+ const wardrobe =
78
+ eyewear !== 'none' || headwear !== 'none' || neckwear !== 'none'
66
79
  const id =
67
- o.id ?? `peek-${fnv1a(JSON.stringify([who, pose, look])).toString(36)}`
80
+ o.id ??
81
+ `peek-${fnv1a(JSON.stringify([wardrobe ? who : legacy, pose, look])).toString(36)}`
68
82
  return { who, pose, opts: { ...look, id, title: o.title ?? name } }
69
83
  }
70
84
 
package/src/tables.ts CHANGED
@@ -184,6 +184,20 @@ export const PARTS = {
184
184
  trait: ['square', 'fin', 'ring', 'dot', 'peak'],
185
185
  } as const
186
186
 
187
+ // The bow's single warm accent, transcribed from the accessory sheet.
188
+ export const ACCESSORY_INK = { knot: '#E5412D' } as const
189
+
190
+ /** Independent wardrobe slots. peek@1 picks none; callers can dress it. */
191
+ export const ACCESSORIES = {
192
+ eyewear: ['none', 'glasses', 'sunglasses'],
193
+ headwear: ['none', 'bow', 'cap', 'sprout'],
194
+ neckwear: ['none', 'tie'],
195
+ } as const
196
+ export type Eyewear = (typeof ACCESSORIES.eyewear)[number]
197
+ export type Headwear = (typeof ACCESSORIES.headwear)[number]
198
+ export type Neckwear = (typeof ACCESSORIES.neckwear)[number]
199
+ export type AccessorySlot = keyof typeof ACCESSORIES
200
+
187
201
  export type Face = keyof typeof FACES
188
202
  export type Color = keyof typeof COLORS
189
203
  export type Part = keyof typeof PARTS
@@ -192,11 +206,22 @@ export type Brows = (typeof PARTS.brows)[number]
192
206
  export type Mouth = (typeof PARTS.mouth)[number]
193
207
  export type Cheeks = (typeof PARTS.cheeks)[number]
194
208
  export type Trait = (typeof PARTS.trait)[number]
195
- export type Axis = 'face' | 'color' | Part
209
+ export type Axis = 'face' | 'color' | Part | AccessorySlot
196
210
 
197
211
  /** How much of each list a version may pick from. Append-only too. */
198
212
  export const VERSIONS: Record<number, Record<Axis, number>> = {
199
- 1: { face: 4, color: 7, eyes: 3, brows: 4, mouth: 4, cheeks: 3, trait: 5 },
213
+ 1: {
214
+ face: 4,
215
+ color: 7,
216
+ eyes: 3,
217
+ brows: 4,
218
+ mouth: 4,
219
+ cheeks: 3,
220
+ trait: 5,
221
+ eyewear: 1,
222
+ headwear: 1,
223
+ neckwear: 1,
224
+ },
200
225
  }
201
226
  export const LATEST = 1
202
227