@airmark/quiver 0.16.0 → 0.18.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@airmark/quiver",
3
- "version": "0.16.0",
3
+ "version": "0.18.0",
4
4
  "description": "Airmark Quiver — Air Force and DAF document Quills for Quillmark.",
5
5
  "type": "module",
6
6
  "exports": {
@@ -17,7 +17,7 @@
17
17
  },
18
18
  "devDependencies": {
19
19
  "@quillmark/quiver": "^0.7.0",
20
- "@quillmark/wasm": "0.77.0"
20
+ "@quillmark/wasm": "^0.78.0"
21
21
  },
22
22
  "scripts": {
23
23
  "test": "node --test quiver.test.js",
@@ -35,6 +35,6 @@
35
35
  "license": "Apache-2.0",
36
36
  "repository": {
37
37
  "type": "git",
38
- "url": "https://github.com/nibsbin/airmark-quiver"
38
+ "url": "https://github.com/tonguetoquill/airmark-quiver"
39
39
  }
40
40
  }
@@ -28,7 +28,7 @@ main:
28
28
  type: string
29
29
  description: Commander's authentication entry on page 1.
30
30
 
31
- card_types:
31
+ leaf_kinds:
32
32
  experience:
33
33
  description: Each card represents one row in the Record of Experience table. Rows fill page 1 (up to 16 rows) then page 2 (up to 21 rows), for a maximum of 37 rows.
34
34
  ui:
@@ -11,7 +11,7 @@ commanders_auth: ""
11
11
  ---
12
12
 
13
13
  <!-- ═══════════════════════════════════════════════════════════════
14
- RECORD OF EXPERIENCE CARDS
14
+ RECORD OF EXPERIENCE LEAVES
15
15
  Each card below becomes one row in the experience table.
16
16
  Page 1 holds up to 16 rows; Page 2 holds up to 21 rows (37 max).
17
17
 
@@ -29,7 +29,7 @@ commanders_auth: ""
29
29
 
30
30
  <!-- Example 1: Initial assignment to a unit -->
31
31
  ---
32
- CARD: experience
32
+ KIND: experience
33
33
  date: 2025-01-15
34
34
  action: "Assigned to 1 ACCS/DOT as Weapons Director"
35
35
  written_grade: ""
@@ -41,7 +41,7 @@ auth_or_remarks: "Initial assignment"
41
41
 
42
42
  <!-- Example 2: Written upgrade evaluation -->
43
43
  ---
44
- CARD: experience
44
+ KIND: experience
45
45
  date: 2025-03-15
46
46
  action: "Completed written upgrade evaluation for 3-Level"
47
47
  written_grade: "3"
@@ -53,7 +53,7 @@ auth_or_remarks: "Per AFMAN 13-1CRCV1"
53
53
 
54
54
  <!-- Example 3: Positional (live-environment) upgrade / certification -->
55
55
  ---
56
- CARD: experience
56
+ KIND: experience
57
57
  date: 2025-06-20
58
58
  action: "Certified Mission Ready — positional upgrade"
59
59
  written_grade: ""
@@ -65,7 +65,7 @@ auth_or_remarks: "SSgt Jones, T.R."
65
65
 
66
66
  <!-- Example 4: Combined written + positional upgrade (both columns filled) -->
67
67
  ---
68
- CARD: experience
68
+ KIND: experience
69
69
  date: 2025-08-01
70
70
  action: "Upgrade evaluation — written and positional"
71
71
  written_grade: "4"
@@ -77,7 +77,7 @@ auth_or_remarks: "Verified by unit commander"
77
77
 
78
78
  <!-- Example 5: PCS departure — no written/positional grade; omit grade dates (or use "") -->
79
79
  ---
80
- CARD: experience
80
+ KIND: experience
81
81
  date: 2025-09-01
82
82
  action: "PCS to 726 ACS/MOC, Tinker AFB OK"
83
83
  written_grade: ""
@@ -35,14 +35,14 @@
35
35
  #if "grade" in data { vals.insert("commonforms_text_p1_3", data.grade) }
36
36
  #if "commanders_auth" in data { vals.insert("commonforms_text_p1_116", data.commanders_auth) }
37
37
 
38
- // --- Experience table rows from cards ---
38
+ // --- Experience table rows from LEAVES ---
39
39
  // The form supports 16 rows on page 1 and 21 rows on page 2 (37 total).
40
40
  // Overflow rows are silently ignored.
41
41
  #let max-rows = 37
42
42
  #{
43
43
  let row = 0
44
- for card in data.CARDS {
45
- if card.CARD == "experience" {
44
+ for card in data.LEAVES {
45
+ if card.KIND == "experience" {
46
46
  if row < max-rows {
47
47
  for (col, key) in col-keys.enumerate() {
48
48
  let value = form-cell(card.at(key, default: none))
@@ -39,7 +39,7 @@ main:
39
39
  unit_commander_rank_name_and_telephone:
40
40
  type: string
41
41
 
42
- card_types:
42
+ leaf_kinds:
43
43
  accomplishments_continued:
44
44
  description: Optional. Add this card only when page 2 overflow is required. Use the card body for continued bullets. Rank/name on page 2 matches the main nominee line automatically.
45
45
  ui:
@@ -16,7 +16,7 @@ Use this main body for page 1 accomplishments.
16
16
  - Replace all placeholder values.
17
17
 
18
18
  ---
19
- CARD: accomplishments_continued
19
+ KIND: accomplishments_continued
20
20
  ---
21
21
 
22
22
  Use this card body only if page 2 overflow is needed.
@@ -38,8 +38,8 @@
38
38
  }
39
39
 
40
40
  #let continued-key = "SPECIFIC_ACCOMPLISHMENTS_Use_Performance_Statements_IAW_DAFMAN_362806_Continued"
41
- #for card in data.CARDS {
42
- if card.CARD == "accomplishments_continued" and continued-key not in vals and "BODY" in card {
41
+ #for card in data.LEAVES {
42
+ if card.KIND == "accomplishments_continued" and continued-key not in vals and "BODY" in card {
43
43
  vals.insert(continued-key, card.BODY)
44
44
  }
45
45
  }
@@ -81,7 +81,7 @@ main:
81
81
  type: string
82
82
  description: "Put in your Emergency Contact's Phone Number."
83
83
 
84
- card_types:
84
+ leaf_kinds:
85
85
  itinerary:
86
86
  description: "Each card represents one row in the travel itinerary table. Up to 10 rows are supported."
87
87
  ui:
@@ -16,7 +16,7 @@ emergency_contact_phone: "999-999-9999"
16
16
  ---
17
17
 
18
18
  ---
19
- CARD: itinerary
19
+ KIND: itinerary
20
20
  date: 2026-03-26
21
21
  departure_point: "Biloxi, MS"
22
22
  arrival_point: "Fake City, MS"
@@ -25,7 +25,7 @@ mileage: "250"
25
25
  ---
26
26
 
27
27
  ---
28
- CARD: itinerary
28
+ KIND: itinerary
29
29
  date: 2026-03-29
30
30
  departure_point: "Fake City, MS"
31
31
  arrival_point: "Biloxi, MS"
@@ -29,14 +29,14 @@
29
29
  #tf(40pt, 100pt)[#show-date(data.at("departure_date", default: none))]
30
30
  #tf(123pt, 100pt)[#data.at("final_destination", default: "")]
31
31
 
32
- // Itinerary Rows (via CARDS)
32
+ // Itinerary Rows (via LEAVES)
33
33
  #{
34
34
  let row = 0
35
35
  let dy-start = 160pt
36
36
  let dy-step = 40pt
37
- if "CARDS" in data {
38
- for card in data.CARDS {
39
- if card.CARD == "itinerary" and row < 10 {
37
+ if "LEAVES" in data {
38
+ for card in data.LEAVES {
39
+ if card.KIND == "itinerary" and row < 10 {
40
40
  let dy = dy-start + (row * dy-step)
41
41
  tf(80pt, dy)[#show-date(card.at("date", default: none))]
42
42
  tf(135pt, dy)[#card.at("departure_point", default: "")]
@@ -182,7 +182,7 @@ main:
182
182
  compact: true
183
183
  description: "Optional marking appended after double slash (e.g. NF with classification CUI renders as CUI//NF). Leave blank to show only the classification with no //."
184
184
 
185
- card_types:
185
+ leaf_kinds:
186
186
  indorsement:
187
187
  description: Chain of routing endorsements. Each endorsement block adds an official response or forwarding action to the original memo.
188
188
  ui:
@@ -43,7 +43,7 @@ The `usaf_memo` Quill package takes care of all 33-337 formatting details. Focus
43
43
  Do not include a complimentary close (e.g. "Respectfully,") in official memorandums.
44
44
 
45
45
  ---
46
- CARD: indorsement
46
+ KIND: indorsement
47
47
  for: ORG/SYMBOL
48
48
  format: standard
49
49
  from: ORG/SYMBOL
@@ -53,4 +53,4 @@ signature_block:
53
53
  - Duty Title
54
54
  ---
55
55
 
56
- This body and the metdata above are an indorsement card. Multiple or no indorsements cards can be used.
56
+ This body and the metdata above are an indorsement card. Multiple or no indorsements leaves can be used.
@@ -200,7 +200,7 @@
200
200
  context {
201
201
  let heading_buffer = none
202
202
  // Filter out zero-width paragraphs so that an empty body (e.g. empty
203
- // string from a CARD with no text) emits nothing and collapses to zero
203
+ // string from a KIND with no text) emits nothing and collapses to zero
204
204
  // vertical space. Tables are always kept regardless of measured width.
205
205
  let items = PAR_BUFFER.get().filter(item =>
206
206
  item.kind == "table" or measure(item.content).width > 0pt
@@ -46,7 +46,7 @@
46
46
  let ind_from = first-or-value(from)
47
47
  let ind_for = to
48
48
 
49
- // An empty body (e.g. a CARD with only an action selected and no markdown
49
+ // An empty body (e.g. a KIND with only an action selected and no markdown
50
50
  // body) collapses to zero rendered layout via render-body's filter. To
51
51
  // make the "empty body takes no layout space" guarantee end-to-end, also
52
52
  // suppress the spacing the surrounding code reserves *for* the body:
@@ -69,9 +69,9 @@
69
69
  ..if "attachments" in data { (attachments: data.attachments) },
70
70
  )
71
71
 
72
- // Indorsements - iterate through CARDS array and filter by CARD type
73
- #for (i, card) in data.CARDS.enumerate() {
74
- if card.CARD == "indorsement" {
72
+ // Indorsements - iterate through LEAVES array and filter by KIND type
73
+ #for (i, card) in data.LEAVES.enumerate() {
74
+ if card.KIND == "indorsement" {
75
75
  // The quillmark helper leaves an unset/whitespace-only markdown body as
76
76
  // the empty string `""`; only non-empty bodies are eval'd into content.
77
77
  // Pass truly empty content (`[]`) in the empty case so indorsement can