pf2e-sage-stats 0.2.5 → 0.2.6
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/README.md +48 -34
- package/dist/app.js +55 -37
- package/dist/index.js +141 -19
- package/package.json +6 -2
- package/src/app.ts +92 -40
- package/src/index.ts +155 -14
package/README.md
CHANGED
|
@@ -4,104 +4,118 @@ sage! macro set name=flat dice="[{o:m} d20 >= {0} flat {...}]" cat=Misc tier=Ser
|
|
|
4
4
|
```
|
|
5
5
|
### Strikes
|
|
6
6
|
```
|
|
7
|
-
sage! macro set name="melee" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::melee.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::melee.{s:default}.desc:} {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {{p}::melee.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
7
|
+
sage! macro set name="melee" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::melee.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::melee.{s:default}.desc:} {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {{p}::melee.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
8
8
|
```
|
|
9
9
|
```
|
|
10
|
-
sage! macro set name="ranged" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::ranged.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::ranged.{s:default}.desc:} {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {{p}::ranged.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
10
|
+
sage! macro set name="ranged" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::ranged.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::ranged.{s:default}.desc:} {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {{p}::ranged.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
11
11
|
```
|
|
12
12
|
```
|
|
13
|
-
sage! macro set name="spell" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::spells:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) Spell Attack {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {...}]" cat=Strikes tier=Server -y
|
|
13
|
+
sage! macro set name="spell" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::spells:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) Spell Attack {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`({c:+0} AC) `} {ac} {utils::{t:known}:ac} {{t:none}::{r:ac}:} {c} {...}]" cat=Strikes tier=Server -y
|
|
14
14
|
```
|
|
15
15
|
### Saves
|
|
16
16
|
```
|
|
17
|
-
sage! macro set name="fort" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::fort:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::fort.info:} Fortitude Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
17
|
+
sage! macro set name="fort" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::fort:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::fort.info:} Fortitude Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
18
18
|
```
|
|
19
19
|
```
|
|
20
|
-
sage! macro set name="fortitude" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::fort:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::fort.info:} Fortitude Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
20
|
+
sage! macro set name="fortitude" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::fort:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::fort.info:} Fortitude Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
21
21
|
```
|
|
22
22
|
```
|
|
23
|
-
sage! macro set name="ref" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::reflex:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::reflex.info:} Reflex Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
23
|
+
sage! macro set name="ref" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::reflex:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::reflex.info:} Reflex Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
24
24
|
```
|
|
25
25
|
```
|
|
26
|
-
sage! macro set name="reflex" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::reflex:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::reflex.info:} Reflex Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
26
|
+
sage! macro set name="reflex" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::reflex:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::reflex.info:} Reflex Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
27
27
|
```
|
|
28
28
|
```
|
|
29
|
-
sage! macro set name="will" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::will:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::will.info:} Will Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
29
|
+
sage! macro set name="will" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::will:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::will.info:} Will Save {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Saves tier=Server -y
|
|
30
30
|
```
|
|
31
31
|
### Initiative
|
|
32
32
|
```
|
|
33
|
-
sage! macro set name="init" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::{s:Perception}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::initiative.info:} Initiative `({s:Perception}) `{...}]" cat=Initiative tier=Server -y
|
|
33
|
+
sage! macro set name="init" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::{s:Perception}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::initiative.info:} Initiative `({s:Perception}) `{...}]" cat=Initiative tier=Server -y
|
|
34
34
|
```
|
|
35
35
|
```
|
|
36
|
-
sage! macro set name="initiative" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::{s:Perception}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::initiative.info:} Initiative `({s:Perception}) `{...}]" cat=Initiative tier=Server -y
|
|
36
|
+
sage! macro set name="initiative" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::{s:Perception}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::initiative.info:} Initiative `({s:Perception}) `{...}]" cat=Initiative tier=Server -y
|
|
37
37
|
```
|
|
38
|
-
### Skills
|
|
38
|
+
### Skills 1
|
|
39
39
|
```
|
|
40
|
-
sage! macro set name="acrobatics" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::acrobatics:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::acrobatics.info:} Acrobatics Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
40
|
+
sage! macro set name="acrobatics" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::acrobatics:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::acrobatics.info:} Acrobatics Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
41
41
|
```
|
|
42
42
|
```
|
|
43
|
-
sage! macro set name="arcana" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::arcana:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::arcana.info:} Arcana Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
43
|
+
sage! macro set name="arcana" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::arcana:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::arcana.info:} Arcana Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
44
44
|
```
|
|
45
45
|
```
|
|
46
|
-
sage! macro set name="athletics" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::athletics:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::athletics.info:} Athletics Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
46
|
+
sage! macro set name="athletics" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::athletics:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::athletics.info:} Athletics Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
47
47
|
```
|
|
48
48
|
```
|
|
49
|
-
sage! macro set name="crafting" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::crafting:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::crafting.info:} Crafting Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
49
|
+
sage! macro set name="crafting" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::crafting:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::crafting.info:} Crafting Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
50
50
|
```
|
|
51
51
|
```
|
|
52
|
-
sage! macro set name="craft" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::crafting:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::crafting.info:} Crafting Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
52
|
+
sage! macro set name="craft" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::crafting:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::crafting.info:} Crafting Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
53
53
|
```
|
|
54
|
+
### Skills 2
|
|
54
55
|
```
|
|
55
|
-
sage! macro set name="deception" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::deception:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::deception.info:} Deception Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
56
|
+
sage! macro set name="deception" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::deception:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::deception.info:} Deception Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
56
57
|
```
|
|
57
58
|
```
|
|
58
|
-
sage! macro set name="diplomacy" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::diplomacy:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::diplomacy.info:} Diplomacy Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
59
|
+
sage! macro set name="diplomacy" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::diplomacy:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::diplomacy.info:} Diplomacy Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
59
60
|
```
|
|
60
61
|
```
|
|
61
|
-
sage! macro set name="intimidation" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::intimidation:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::intimidation.info:} Intimidation Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
62
|
+
sage! macro set name="intimidation" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::intimidation:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::intimidation.info:} Intimidation Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
62
63
|
```
|
|
63
64
|
```
|
|
64
|
-
sage! macro set name="medicine" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::medicine:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::medicine.info:} Medicine Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
65
|
+
sage! macro set name="medicine" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::medicine:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::medicine.info:} Medicine Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
65
66
|
```
|
|
66
67
|
```
|
|
67
|
-
sage! macro set name="nature" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::nature:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::nature.info:} Nature Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
68
|
+
sage! macro set name="nature" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::nature:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::nature.info:} Nature Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
68
69
|
```
|
|
70
|
+
### Skills 3
|
|
69
71
|
```
|
|
70
|
-
sage! macro set name="occultism" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::occultism:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::occultism.info:} Occultism Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
72
|
+
sage! macro set name="occultism" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::occultism:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::occultism.info:} Occultism Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
71
73
|
```
|
|
72
74
|
```
|
|
73
|
-
sage! macro set name="performance" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::performance:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::performance.info:} Performance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
75
|
+
sage! macro set name="performance" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::performance:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::performance.info:} Performance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
74
76
|
```
|
|
75
77
|
```
|
|
76
|
-
sage! macro set name="perfomance" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::performance:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::performance.info:} Performance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
78
|
+
sage! macro set name="perfomance" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::performance:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::performance.info:} Performance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
77
79
|
```
|
|
78
80
|
```
|
|
79
|
-
sage! macro set name="religion" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::religion:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::religion.info:} Religion Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
81
|
+
sage! macro set name="religion" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::religion:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::religion.info:} Religion Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
80
82
|
```
|
|
81
83
|
```
|
|
82
|
-
sage! macro set name="society" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::society:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::society.info:} Society Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
84
|
+
sage! macro set name="society" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::society:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::society.info:} Society Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
83
85
|
```
|
|
86
|
+
### Skills 4
|
|
84
87
|
```
|
|
85
|
-
sage! macro set name="stealth" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::stealth:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::stealth.info:} Stealth Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
88
|
+
sage! macro set name="stealth" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::stealth:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::stealth.info:} Stealth Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
86
89
|
```
|
|
87
90
|
```
|
|
88
|
-
sage! macro set name="survival" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::survival:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::survival.info:} Survival Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
91
|
+
sage! macro set name="survival" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::survival:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::survival.info:} Survival Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
89
92
|
```
|
|
90
93
|
```
|
|
91
|
-
sage! macro set name="thievery" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::thievery:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::thievery.info:} Thievery Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
94
|
+
sage! macro set name="thievery" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::thievery:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::thievery.info:} Thievery Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
92
95
|
```
|
|
93
96
|
```
|
|
94
|
-
sage! macro set name="perception" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::perception:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::perception.info:} Perception Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
97
|
+
sage! macro set name="perception" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::perception:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::perception.info:} Perception Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
95
98
|
```
|
|
96
99
|
```
|
|
97
|
-
sage! macro set name="lore" dice="[{{p}::out:m} {flat::{f:none}:} {d:1}d20+{{p}::lore.{0}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::lore.{0}.info:} {{p}::lore.{0}.name:} Lore Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
100
|
+
sage! macro set name="lore" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::lore.{0}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::lore.{0}.info:} {{p}::lore.{0}.name:} Lore Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
98
101
|
```
|
|
102
|
+
### Skills 5
|
|
99
103
|
```
|
|
100
|
-
sage! macro set name="assurance" dice="[{{p}::out:m} {flat::{f:none}:} (10)d20+{0:0}-10 {v} {{p}::name:} Assurance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
104
|
+
sage! macro set name="assurance" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} (10)d20+{0:0}-10 {v} {{p}::name:} Assurance Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
101
105
|
```
|
|
102
106
|
```
|
|
103
|
-
sage! macro set name="skill" dice="[{{p}::out:m} {flat::{f:none}:} d20+{0:0} {v} {{p}::name:} Skill Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
107
|
+
sage! macro set name="skill" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} d20+{0:0} {v} {{p}::name:} Skill Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
104
108
|
```
|
|
105
109
|
```
|
|
106
|
-
sage! macro set name="secret" dice="[{{p}::out:m} {flat::{f:none}:} d20+{{p}::{0}:{a:0}} {v} {{p}::name:} Secret {0} Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
110
|
+
sage! macro set name="secret" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} d20+{{p}::{0}:{a:0}} {v} {{p}::name:} Secret {0} Check {utils::{t:known}:vs} {{t:none}::name:} {utils::{t:known}:`{r:Spell} DC ({c:+0} DC) `} {dc} {utils::{t:known}:dc} {{t:none}::dc.{r:spells}:} {c} {...}]" cat=Skills tier=Server -y
|
|
111
|
+
```
|
|
112
|
+
### Legacy
|
|
113
|
+
```
|
|
114
|
+
sage! macro set name="mstrike" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::melee.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::melee.{s:default}.desc:} vs {{0}::name:} `({c:+0} AC) ` ac {{0}::{r:ac}:} {c} {{p}::melee.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
115
|
+
```
|
|
116
|
+
```
|
|
117
|
+
sage! macro set name="rstrike" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::ranged.{s:default}:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) {{p}::ranged.{s:default}.desc:} vs {{0}::name:} `({c:+0} AC) ` ac {{0}::{r:ac}:} {c} {{p}::ranged.{s:default}.damage:} {...}]" cat=Strikes tier=Server -y
|
|
118
|
+
```
|
|
119
|
+
```
|
|
120
|
+
sage! macro set name="sstrike" dice="[{{p}::{o:out}:{o:m}} {x} {flat::{f:none}:{f}} {dice::{d:none}:{d:1}}d20+{{p}::spells:{a:0}} {m} {v} {{p}::name:} (mod `{m:+0}`) Spell Attack vs {{0}::name:} `({c:+0} AC) ` ac {{0}::{r:ac}:} {c} {...}]" cat=Strikes tier=Server -y
|
|
107
121
|
```
|
package/dist/app.js
CHANGED
|
@@ -12,13 +12,14 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
12
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
13
|
};
|
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
-
exports.sortFolder = exports.formatTracker = exports.newtracker = exports.formatHP = exports.formatTable = exports.formatCommand = exports.formatTSV = exports.flatten = exports.parseStatblock = exports.parseTracker = exports.parseJSON = exports.formatJSON = exports.fromatMap = exports.
|
|
15
|
+
exports.screenPlay = exports.sortFolder = exports.formatTracker = exports.newtracker = exports.formatHP = exports.formatTable = exports.formatCommand = exports.formatTSV = exports.flatten = exports.parseStatblock = exports.parseTracker = exports.parseJSON = exports.formatJSON = exports.fromatMap = exports.diceMap = exports.flatMap = exports.stub = void 0;
|
|
16
16
|
const zod_1 = __importDefault(require("zod"));
|
|
17
17
|
const tsv_1 = require("tsv");
|
|
18
18
|
const lodash_1 = require("lodash");
|
|
19
19
|
const dedent_js_1 = __importDefault(require("dedent-js"));
|
|
20
20
|
const abbreviate_1 = __importDefault(require("abbreviate"));
|
|
21
21
|
const pluralize_1 = __importDefault(require("pluralize"));
|
|
22
|
+
const jsdom_1 = require("jsdom");
|
|
22
23
|
const promises_1 = require("fs/promises");
|
|
23
24
|
const schema = zod_1.default.object({
|
|
24
25
|
name: zod_1.default.string(),
|
|
@@ -201,16 +202,8 @@ const charSchema = zod_1.default.object({
|
|
|
201
202
|
conditions: zod_1.default.string().default(''),
|
|
202
203
|
children: zod_1.default.array(childSchema).default([]),
|
|
203
204
|
});
|
|
204
|
-
exports.
|
|
205
|
-
|
|
206
|
-
'incredibly-easy': '`(Incredibly Easy)`',
|
|
207
|
-
'very-easy': '`(Very Easy)`',
|
|
208
|
-
'easy': '`(Easy)`',
|
|
209
|
-
'hard': '`(Hard)`',
|
|
210
|
-
'very-hard': '`(Very Easy)`',
|
|
211
|
-
'incredibly-hard': '`(Incredibly Hard)`',
|
|
212
|
-
});
|
|
213
|
-
exports.adjustmentMap = adjustmentMap;
|
|
205
|
+
exports.flatMap = Object.assign(Object.assign({}, ([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20].map((v) => ([`${v}`, `d20 >= ${v} flat;`])).reduce((p, [k, v]) => { p[k] = v; return p; }, {}))), { c: 'd20 >= 5 flat;', concealed: 'd20 >= 5 flat;', h: 'd20 >= 11 flat;', hidden: 'd20 >= 11 flat;' });
|
|
206
|
+
exports.diceMap = Object.assign(Object.assign({}, ([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20].map((v) => ([`${v}`, `(${v})`])).reduce((p, [k, v]) => { p[k] = v; return p; }, {}))), { a: '+2', adv: '+2', advantage: '+2', d: '-2', dis: '-2', disadvantage: '-2', f: '+2', for: '+2', fort: '+2', fortune: '+2', m: '-2', mis: '-2', misfortune: '-2' });
|
|
214
207
|
const fromatMap = (name, map) => {
|
|
215
208
|
return tsv_1.TSV.stringify([Object.assign({ name }, map)]);
|
|
216
209
|
};
|
|
@@ -283,10 +276,7 @@ const locateStrikes = (statblock, alias) => {
|
|
|
283
276
|
.replace(/\+\d/g, '')
|
|
284
277
|
.replace(/Weapon\s+Striking(\s+\((Greater|Major)\))?/gi, '')
|
|
285
278
|
.replace(/((Greater|Major)\s+)?Striking/gi, '')
|
|
286
|
-
.replace(/\(
|
|
287
|
-
.replace(/\(Finesse\)/gi, '')
|
|
288
|
-
.replace(/\(\+\)/gi, '')
|
|
289
|
-
.replace(/\(\)/gi, '')
|
|
279
|
+
.replace(/\(.*\)/gi, '')
|
|
290
280
|
.replace(/\s+/g, ' ')
|
|
291
281
|
.trim();
|
|
292
282
|
const bps = /(?<=[^\w']|^)[BbPpSs](?=[^\w]|$)/g;
|
|
@@ -305,6 +295,8 @@ const locateStrikes = (statblock, alias) => {
|
|
|
305
295
|
.replace(/Electricity/, 'electricity')
|
|
306
296
|
.replace(/Sonic/, 'sonic')
|
|
307
297
|
.replace(/Spirit/, 'spirit')
|
|
298
|
+
.replace(/Acid/, 'acid')
|
|
299
|
+
.replace(/[pP]lus\s(\d+d)/, '+$1')
|
|
308
300
|
.trim();
|
|
309
301
|
const twoHand = _traits.match(/(two-hand|two-handed)\s+(d\d+)/);
|
|
310
302
|
if (twoHand && twoHand[2]) {
|
|
@@ -379,17 +371,7 @@ const toRanged = ([key, value]) => [
|
|
|
379
371
|
[`ranged.${key}.desc`, value.desc],
|
|
380
372
|
...(value.damage ? [[`ranged.${key}.damage`, value.damage]] : []),
|
|
381
373
|
];
|
|
382
|
-
const
|
|
383
|
-
['dc.recall.incredibly-easy', secret ? `||${value - 10}||` : `${value - 10}`],
|
|
384
|
-
['dc.recall.very-easy', secret ? `||${value - 5}||` : `${value - 5}`],
|
|
385
|
-
['dc.recall.easy', secret ? `||${value - 2}||` : `${value - 2}`],
|
|
386
|
-
['dc.recall.default', secret ? `||${value}||` : `${value}`],
|
|
387
|
-
['dc.recall', secret ? `||${value}||` : `${value}`],
|
|
388
|
-
['dc.recall.hard', secret ? `||${value + 2}||` : `${value + 2}`],
|
|
389
|
-
['dc.recall.very-hard', secret ? `||${value + 5}||` : `${value + 5}`],
|
|
390
|
-
['dc.recall.incredibly-hard', secret ? `||${value + 10}||` : `${value + 10}`],
|
|
391
|
-
])(dcByLevel[Math.max(Math.min(level + 1, dcByLevel.length - 1), 0)] + bump);
|
|
392
|
-
const flatten = (stats, secretDC = false, defaultSkills = false, recallDC = false) => {
|
|
374
|
+
const flatten = (stats, secretDC = false, defaultSkills = false) => {
|
|
393
375
|
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m;
|
|
394
376
|
const untrained = stats.untrained;
|
|
395
377
|
const skills = defaultSkills ? Object.assign({ acrobatics: untrained + stats.attributes.dexterity, arcana: untrained + stats.attributes.intelligence, athletics: untrained + stats.attributes.strength, crafting: untrained + stats.attributes.intelligence, deception: untrained + stats.attributes.charisma, diplomacy: untrained + stats.attributes.charisma, intimidation: untrained + stats.attributes.charisma, medicine: untrained + stats.attributes.wisdom, nature: untrained + stats.attributes.wisdom, occultism: untrained + stats.attributes.intelligence, performance: untrained + stats.attributes.charisma, religion: untrained + stats.attributes.wisdom, society: untrained + stats.attributes.intelligence, stealth: untrained + stats.attributes.dexterity, survival: untrained + stats.attributes.wisdom, thievery: untrained + stats.attributes.dexterity }, stats.skills) : stats.skills;
|
|
@@ -469,9 +451,6 @@ const flatten = (stats, secretDC = false, defaultSkills = false, recallDC = fals
|
|
|
469
451
|
...(0, lodash_1.entries)(skills).map(mod2DC(true, ((_m = stats.bump.skills) !== null && _m !== void 0 ? _m : stats.bump.default))),
|
|
470
452
|
...(0, lodash_1.entries)(stats.extra).map(mod2DC(true, stats.bump.default)),
|
|
471
453
|
] : []),
|
|
472
|
-
...(recallDC ? [
|
|
473
|
-
...recallDCs(stats.level, secretDC, stats.bump.default),
|
|
474
|
-
] : []),
|
|
475
454
|
...(stats.perceptionInfo.length > 0 ? [
|
|
476
455
|
[`perception.info`, `\`(${stats.perceptionInfo.join(', ')})\``]
|
|
477
456
|
] : []),
|
|
@@ -484,9 +463,9 @@ const flatten = (stats, secretDC = false, defaultSkills = false, recallDC = fals
|
|
|
484
463
|
].reduce((p, [key, value]) => { p[key] = value; return p; }, {});
|
|
485
464
|
};
|
|
486
465
|
exports.flatten = flatten;
|
|
487
|
-
const formatTSV = (stats, secretDC = false, defaultSkills = false
|
|
466
|
+
const formatTSV = (stats, secretDC = false, defaultSkills = false) => (tsv_1.TSV.stringify([(0, exports.flatten)(stats, secretDC, defaultSkills)]));
|
|
488
467
|
exports.formatTSV = formatTSV;
|
|
489
|
-
const formatCommand = (stats, secretDC = false, defaultSkills = false
|
|
468
|
+
const formatCommand = (stats, secretDC = false, defaultSkills = false) => (Object.entries((0, exports.flatten)(stats, secretDC, defaultSkills)).map(([k, v]) => `${k}="${v}"`).join(' '));
|
|
490
469
|
exports.formatCommand = formatCommand;
|
|
491
470
|
const formatTable = (table, season, scenario, _name, gm, players) => {
|
|
492
471
|
const name = _name.replace(/[\s-_]/g, ' ').replace(/[^a-zA-Z0-9 ]/g, '');
|
|
@@ -497,7 +476,7 @@ const formatTable = (table, season, scenario, _name, gm, players) => {
|
|
|
497
476
|
@TableBot create "${gameName}" --gm ${gm} --players ${players} --table-name ${tableName} --ooc-table-name ooc-${tableName} --category Game Tables
|
|
498
477
|
\`\`\`
|
|
499
478
|
\`\`\`
|
|
500
|
-
sage! game create name="${gameName}" gameSystem="pf2e" ic=" #${tableName} " ooc=" #ooc-${tableName} " gms=" ${gm} " players=" @${gameName} " dialogPost="post" diceSecret="gm" diceCrit="timestwo" diceOutput=M gmCharName="Хронист"
|
|
479
|
+
sage! game create name="${gameName}" gameSystem="pf2e" ic=" #${tableName} " ooc=" #ooc-${tableName} " gms=" ${gm} " players=" @${gameName} " dialogPost="post" diceSecret="gm" diceCrit="timestwo" diceOutput=M gmCharName="Хронист"
|
|
501
480
|
\`\`\`
|
|
502
481
|
`;
|
|
503
482
|
};
|
|
@@ -550,8 +529,10 @@ const newtracker = (status) => {
|
|
|
550
529
|
};
|
|
551
530
|
exports.newtracker = newtracker;
|
|
552
531
|
const formatTracker = (tracker) => {
|
|
532
|
+
const aliasSpace = (t) => (t.alias.length > 0 ? 0 : 5);
|
|
533
|
+
const nameLengthWithAlias = (t) => t.name.length - aliasSpace(t);
|
|
553
534
|
const nameLength = tracker.reduce((p, c) => {
|
|
554
|
-
const length = c.children.reduce((pp, cc) => pp > cc
|
|
535
|
+
const length = c.children.reduce((pp, cc) => pp > nameLengthWithAlias(cc) ? pp : nameLengthWithAlias(cc), nameLengthWithAlias(c));
|
|
555
536
|
return p > length ? p : length;
|
|
556
537
|
}, 0);
|
|
557
538
|
const hpLength = tracker.reduce((p, c) => {
|
|
@@ -580,15 +561,15 @@ const formatTracker = (tracker) => {
|
|
|
580
561
|
if (tracker[index - 1] && tracker[index - 1].foe !== char.foe) {
|
|
581
562
|
ls.push('');
|
|
582
563
|
}
|
|
583
|
-
const hp = char.foe ? (`-${char.maxhp - char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}`.padStart(hpLength)) : (`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}
|
|
564
|
+
const hp = !char.foe && char.hp > 0 ? (`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}/${char.maxhp}`.padStart(hpLength)) : char.hp > 0 ? (`-${char.maxhp - char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}`.padStart(hpLength)) : (`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}`.padStart(hpLength));
|
|
584
565
|
const hpBar = (value, max) => (value <= 0 ? (':crossed:') : value >= max ? (':healthy:') : (hpMap[Math.round((hpMap.length - 1) * value / max)]));
|
|
585
|
-
ls.push((`${stateMap[char.state]}**\` ${char.name.padEnd(nameLength)} ▏${char.alias.padEnd(3)} ▏${hp} \`** ${hpBar(char.hp, char.maxhp)} `));
|
|
566
|
+
ls.push((`${stateMap[char.hp > 0 ? char.state : 'cross']}**\` ${char.name.padEnd(nameLength + aliasSpace(char))}${char.alias.length > 0 ? ` ▏${char.alias.padEnd(3)}` : ''} ▏${hp} \`** ${hpBar(char.hp, char.maxhp)} `));
|
|
586
567
|
if (char.conditions.length > 0) {
|
|
587
568
|
ls.push(`-# ${char.conditions}`);
|
|
588
569
|
}
|
|
589
570
|
for (const child of char.children) {
|
|
590
|
-
const hhp = char.foe ? (`-${child.maxhp - child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}`.padStart(hpLength)) : (`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}
|
|
591
|
-
ls.push((`:smallnode:**\` ${child.name.padEnd(nameLength)} ▏${child.alias.padEnd(3)} ▏${hhp} \`** ${hpBar(child.hp, child.maxhp)} `));
|
|
571
|
+
const hhp = !char.foe && child.hp > 0 ? (`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}/${child.maxhp}`.padStart(hpLength)) : child.hp > 0 ? (`-${child.maxhp - child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}`.padStart(hpLength)) : (`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}`.padStart(hpLength));
|
|
572
|
+
ls.push((`:smallnode:**\` ${child.name.padEnd(nameLength + aliasSpace(child))}${child.alias.length > 0 ? ` ▏${child.alias.padEnd(3)}` : ''} ▏${hhp} \`** ${hpBar(child.hp, child.maxhp)} `));
|
|
592
573
|
if (child.conditions.length > 0) {
|
|
593
574
|
ls.push(`-# ${child.conditions}`);
|
|
594
575
|
}
|
|
@@ -615,3 +596,40 @@ const sortFolder = () => __awaiter(void 0, void 0, void 0, function* () {
|
|
|
615
596
|
return transformed;
|
|
616
597
|
});
|
|
617
598
|
exports.sortFolder = sortFolder;
|
|
599
|
+
const screenPlay = (htmlContent) => {
|
|
600
|
+
const dom = new jsdom_1.JSDOM(htmlContent);
|
|
601
|
+
const document = dom.window.document;
|
|
602
|
+
const outputLines = [];
|
|
603
|
+
const preambleEntry = document.querySelector('.preamble__entry');
|
|
604
|
+
if (preambleEntry) {
|
|
605
|
+
outputLines.push(`SCENE: ${preambleEntry.textContent}`);
|
|
606
|
+
outputLines.push('');
|
|
607
|
+
}
|
|
608
|
+
// Process all chatlog messages
|
|
609
|
+
const messages = document.querySelectorAll('.chatlog__message');
|
|
610
|
+
messages.forEach(message => {
|
|
611
|
+
var _a, _b, _c, _d;
|
|
612
|
+
const authorElement = message.querySelector('.chatlog__author');
|
|
613
|
+
const contentElement = message.querySelector('.chatlog__content');
|
|
614
|
+
if (!authorElement || !contentElement)
|
|
615
|
+
return;
|
|
616
|
+
const author = (_b = (_a = authorElement.textContent) === null || _a === void 0 ? void 0 : _a.trim()) !== null && _b !== void 0 ? _b : '';
|
|
617
|
+
const content = (_d = (_c = contentElement.textContent) === null || _c === void 0 ? void 0 : _c.trim()) !== null && _d !== void 0 ? _d : '';
|
|
618
|
+
// Skip bot tags in character names
|
|
619
|
+
const characterName = author.replace(/\s*BOT$/, '');
|
|
620
|
+
// Add character line
|
|
621
|
+
outputLines.push(`${characterName.toUpperCase()}`);
|
|
622
|
+
// Add dialogue/content (wrap long lines)
|
|
623
|
+
const lines = content.split('\n').map((c) => (c
|
|
624
|
+
.replace(/(—|--)/g, '-')
|
|
625
|
+
// eslint-disable-next-line no-irregular-whitespace
|
|
626
|
+
.replace(/(|)/g, '')
|
|
627
|
+
.trim())).filter((c) => c.length);
|
|
628
|
+
for (const line of lines) {
|
|
629
|
+
outputLines.push(` ${line}`);
|
|
630
|
+
}
|
|
631
|
+
outputLines.push('');
|
|
632
|
+
});
|
|
633
|
+
return outputLines.join('\n');
|
|
634
|
+
};
|
|
635
|
+
exports.screenPlay = screenPlay;
|
package/dist/index.js
CHANGED
|
@@ -24,6 +24,7 @@ const commander_1 = require("commander");
|
|
|
24
24
|
const promises_1 = __importDefault(require("fs/promises"));
|
|
25
25
|
const path_1 = __importDefault(require("path"));
|
|
26
26
|
const readline_1 = __importDefault(require("readline"));
|
|
27
|
+
const clipboardy_1 = __importDefault(require("clipboardy"));
|
|
27
28
|
const package_json_1 = __importDefault(require("../package.json"));
|
|
28
29
|
const app_1 = require("./app");
|
|
29
30
|
const program = new commander_1.Command(package_json_1.default.name);
|
|
@@ -71,6 +72,19 @@ program.command('sort')
|
|
|
71
72
|
.action(() => __awaiter(void 0, void 0, void 0, function* () {
|
|
72
73
|
console.log(yield (0, app_1.sortFolder)());
|
|
73
74
|
}));
|
|
75
|
+
program.command('convert')
|
|
76
|
+
.description('Convert a discord export file into a txt log')
|
|
77
|
+
.argument('<file>', 'input file')
|
|
78
|
+
.option('-o, --output <file>', 'output file')
|
|
79
|
+
.action((argument, option) => __awaiter(void 0, void 0, void 0, function* () {
|
|
80
|
+
const file = yield promises_1.default.readFile(argument, { encoding: 'utf-8' });
|
|
81
|
+
if (option.output) {
|
|
82
|
+
yield promises_1.default.writeFile(option.output, (0, app_1.screenPlay)(file), { encoding: 'utf-8' });
|
|
83
|
+
}
|
|
84
|
+
else {
|
|
85
|
+
console.log((0, app_1.screenPlay)(file));
|
|
86
|
+
}
|
|
87
|
+
}));
|
|
74
88
|
program.command('flat')
|
|
75
89
|
.description('Generte a special flat npc tsv')
|
|
76
90
|
.option('-n, --name <string>', 'npc name')
|
|
@@ -78,23 +92,23 @@ program.command('flat')
|
|
|
78
92
|
.action((option) => __awaiter(void 0, void 0, void 0, function* () {
|
|
79
93
|
var _a, _b;
|
|
80
94
|
if (option.output) {
|
|
81
|
-
yield promises_1.default.writeFile(option.output, (0, app_1.fromatMap)((_a = option.name) !== null && _a !== void 0 ? _a : 'flat', app_1.
|
|
95
|
+
yield promises_1.default.writeFile(option.output, (0, app_1.fromatMap)((_a = option.name) !== null && _a !== void 0 ? _a : 'flat', app_1.flatMap), { encoding: 'utf-8' });
|
|
82
96
|
}
|
|
83
97
|
else {
|
|
84
|
-
console.log((0, app_1.fromatMap)((_b = option.name) !== null && _b !== void 0 ? _b : 'flat', app_1.
|
|
98
|
+
console.log((0, app_1.fromatMap)((_b = option.name) !== null && _b !== void 0 ? _b : 'flat', app_1.flatMap));
|
|
85
99
|
}
|
|
86
100
|
}));
|
|
87
|
-
program.command('
|
|
88
|
-
.description('Generte a special
|
|
101
|
+
program.command('dice')
|
|
102
|
+
.description('Generte a special dice npc tsv')
|
|
89
103
|
.option('-n, --name <string>', 'npc name')
|
|
90
104
|
.option('-o, --output <file>', 'output json')
|
|
91
105
|
.action((option) => __awaiter(void 0, void 0, void 0, function* () {
|
|
92
106
|
var _a, _b;
|
|
93
107
|
if (option.output) {
|
|
94
|
-
yield promises_1.default.writeFile(option.output, (0, app_1.fromatMap)((_a = option.name) !== null && _a !== void 0 ? _a : '
|
|
108
|
+
yield promises_1.default.writeFile(option.output, (0, app_1.fromatMap)((_a = option.name) !== null && _a !== void 0 ? _a : 'dice', app_1.diceMap), { encoding: 'utf-8' });
|
|
95
109
|
}
|
|
96
110
|
else {
|
|
97
|
-
console.log((0, app_1.fromatMap)((_b = option.name) !== null && _b !== void 0 ? _b : '
|
|
111
|
+
console.log((0, app_1.fromatMap)((_b = option.name) !== null && _b !== void 0 ? _b : 'dice', app_1.diceMap));
|
|
98
112
|
}
|
|
99
113
|
}));
|
|
100
114
|
program.command('statblock')
|
|
@@ -131,26 +145,24 @@ program.command('tsv')
|
|
|
131
145
|
.argument('<file>', 'input json')
|
|
132
146
|
.option('-o, --output <file>', 'output tsv')
|
|
133
147
|
.option('-s, --secretDC', 'produce secret DCs')
|
|
134
|
-
.option('-r, --recallDC', 'produce recall DCs')
|
|
135
148
|
.option('-d, --defaultSkills', 'produce values for untrained skills')
|
|
136
149
|
.action((argument, option) => __awaiter(void 0, void 0, void 0, function* () {
|
|
137
150
|
const file = yield promises_1.default.readFile(argument, { encoding: 'utf-8' });
|
|
138
151
|
const stats = (0, app_1.parseJSON)(file);
|
|
139
152
|
const output = option.output ? option.output : path_1.default.join(path_1.default.parse(argument).dir, path_1.default.parse(argument).name + '.tsv');
|
|
140
|
-
yield promises_1.default.writeFile(output, (0, app_1.formatTSV)(stats, option.secretDC, option.defaultSkills
|
|
153
|
+
yield promises_1.default.writeFile(output, (0, app_1.formatTSV)(stats, option.secretDC, option.defaultSkills), { encoding: 'utf-8' });
|
|
141
154
|
}));
|
|
142
155
|
program.command('command')
|
|
143
156
|
.description('Generte a creation command file from JSON')
|
|
144
157
|
.argument('<file>', 'input json')
|
|
145
158
|
.option('-o, --output <file>', 'output txt')
|
|
146
159
|
.option('-s, --secretDC', 'produce secret DCs')
|
|
147
|
-
.option('-r, --recallDC', 'produce recall DCs')
|
|
148
160
|
.option('-d, --defaultSkills', 'produce values for untrained skills')
|
|
149
161
|
.action((argument, option) => __awaiter(void 0, void 0, void 0, function* () {
|
|
150
162
|
const file = yield promises_1.default.readFile(argument, { encoding: 'utf-8' });
|
|
151
163
|
const stats = (0, app_1.parseJSON)(file);
|
|
152
164
|
const output = option.output ? option.output : path_1.default.join(path_1.default.parse(argument).dir, path_1.default.parse(argument).name + '-command.txt');
|
|
153
|
-
yield promises_1.default.writeFile(output, (0, app_1.formatCommand)(stats, option.secretDC, option.defaultSkills
|
|
165
|
+
yield promises_1.default.writeFile(output, (0, app_1.formatCommand)(stats, option.secretDC, option.defaultSkills), { encoding: 'utf-8' });
|
|
154
166
|
}));
|
|
155
167
|
program.command('newtracker')
|
|
156
168
|
.argument('<file>', 'input text file')
|
|
@@ -191,7 +203,9 @@ program.command('track')
|
|
|
191
203
|
}
|
|
192
204
|
else {
|
|
193
205
|
console.clear();
|
|
194
|
-
|
|
206
|
+
const track = (0, app_1.formatTracker)(tracker);
|
|
207
|
+
clipboardy_1.default.writeSync(track);
|
|
208
|
+
console.log(track);
|
|
195
209
|
}
|
|
196
210
|
});
|
|
197
211
|
yield invoke(argument);
|
|
@@ -216,7 +230,7 @@ program.command('track')
|
|
|
216
230
|
}
|
|
217
231
|
}))(),
|
|
218
232
|
(() => __awaiter(void 0, void 0, void 0, function* () {
|
|
219
|
-
var _a, _b, _c, _d, _e;
|
|
233
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l;
|
|
220
234
|
const rl = readline_1.default.createInterface({
|
|
221
235
|
input: process.stdin,
|
|
222
236
|
output: process.stdout
|
|
@@ -267,19 +281,48 @@ program.command('track')
|
|
|
267
281
|
}
|
|
268
282
|
},
|
|
269
283
|
}, {
|
|
270
|
-
regex: /^\s*(\S+)\s+[sS]
|
|
284
|
+
regex: /^\s*(\S+)\s+[sS]?\s*=?"([^"]*)"/,
|
|
271
285
|
map: (match) => {
|
|
272
286
|
return { command: 'set-conditions', tag: match[1], value: match[2] };
|
|
273
287
|
},
|
|
288
|
+
}, {
|
|
289
|
+
regex: /^\s*(\S+)\s+[sS]?\s*\+"([^"]*)"/,
|
|
290
|
+
map: (match) => {
|
|
291
|
+
return { command: 'add-conditions', tag: match[1], value: match[2] };
|
|
292
|
+
},
|
|
293
|
+
}, {
|
|
294
|
+
regex: /^\s*(\S+)\s+[sS]?\s*-"([^"]*)"/,
|
|
295
|
+
map: (match) => {
|
|
296
|
+
return { command: 'rem-conditions', tag: match[1], value: match[2] };
|
|
297
|
+
},
|
|
298
|
+
}, {
|
|
299
|
+
regex: /^\s*(\S+)\s+[sS]?\s*\+\+"([^"]*)"/,
|
|
300
|
+
map: (match) => {
|
|
301
|
+
return { command: 'inc-conditions', tag: match[1], value: match[2] };
|
|
302
|
+
},
|
|
303
|
+
}, {
|
|
304
|
+
regex: /^\s*(\S+)\s+[sS]?\s*--"([^"]*)"/,
|
|
305
|
+
map: (match) => {
|
|
306
|
+
return { command: 'dec-conditions', tag: match[1], value: match[2] };
|
|
307
|
+
},
|
|
274
308
|
}, {
|
|
275
309
|
regex: /^\s*(\S+)\s+[cC]/,
|
|
276
310
|
map: (match) => ({ command: 'check', tag: match[1] }),
|
|
277
311
|
}, {
|
|
278
312
|
regex: /^\s*(\S+)\s+[aA]/,
|
|
279
313
|
map: (match) => ({ command: 'arrow', tag: match[1] }),
|
|
314
|
+
}, {
|
|
315
|
+
regex: /^\s*(\S+)\s+[eE]/,
|
|
316
|
+
map: (match) => ({ command: 'empty', tag: match[1] }),
|
|
317
|
+
}, {
|
|
318
|
+
regex: /^\s*(\S+)\s+[xX]/,
|
|
319
|
+
map: (match) => ({ command: 'cross', tag: match[1] }),
|
|
280
320
|
}, {
|
|
281
321
|
regex: /^\s*(\S+)\s+[dD]/,
|
|
282
322
|
map: (match) => ({ command: 'delete', tag: match[1] }),
|
|
323
|
+
}, {
|
|
324
|
+
regex: /^\s*(\S+)\s+[wW]/,
|
|
325
|
+
map: (match) => ({ command: 'wait', tag: match[1] }),
|
|
283
326
|
}];
|
|
284
327
|
const actions = [];
|
|
285
328
|
while (true) {
|
|
@@ -321,6 +364,24 @@ program.command('track')
|
|
|
321
364
|
}
|
|
322
365
|
}
|
|
323
366
|
}
|
|
367
|
+
else if (action.command === 'wait') {
|
|
368
|
+
const sorted = [...tracker].sort((a, b) => (a.init === b.init) ? (b.foe ? 1 : 0) - (a.foe ? 1 : 0) : b.init - a.init);
|
|
369
|
+
const blocks = [[sorted[0]]];
|
|
370
|
+
for (let i = 1; i < sorted.length; ++i) {
|
|
371
|
+
if (sorted[i].foe === blocks[blocks.length - 1][0].foe) {
|
|
372
|
+
blocks[blocks.length - 1].push(sorted[i]);
|
|
373
|
+
}
|
|
374
|
+
else {
|
|
375
|
+
blocks.push([sorted[i]]);
|
|
376
|
+
}
|
|
377
|
+
}
|
|
378
|
+
const blockIndex = blocks.findIndex((b) => b.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
379
|
+
const block = blocks[blockIndex + 1];
|
|
380
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag);
|
|
381
|
+
if (block && item) {
|
|
382
|
+
item.init = ((_b = (_a = block[block.length - 1]) === null || _a === void 0 ? void 0 : _a.init) !== null && _b !== void 0 ? _b : 0) - 1;
|
|
383
|
+
}
|
|
384
|
+
}
|
|
324
385
|
else if (action.command === 'check') {
|
|
325
386
|
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag);
|
|
326
387
|
if (item) {
|
|
@@ -333,6 +394,18 @@ program.command('track')
|
|
|
333
394
|
item.state = "arrow";
|
|
334
395
|
}
|
|
335
396
|
}
|
|
397
|
+
else if (action.command === 'empty') {
|
|
398
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag);
|
|
399
|
+
if (item) {
|
|
400
|
+
item.state = "empty";
|
|
401
|
+
}
|
|
402
|
+
}
|
|
403
|
+
else if (action.command === 'cross') {
|
|
404
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag);
|
|
405
|
+
if (item) {
|
|
406
|
+
item.state = "cross";
|
|
407
|
+
}
|
|
408
|
+
}
|
|
336
409
|
else if (action.command === 'delete') {
|
|
337
410
|
tracker = tracker.filter((c) => !(c.id === action.tag || c.alias === action.tag || c.name == action.tag)).map((p) => (Object.assign(Object.assign({}, p), { children: p.children.filter((c) => !(c.id === action.tag || c.alias === action.tag || c.name == action.tag)) })));
|
|
338
411
|
}
|
|
@@ -353,13 +426,13 @@ program.command('track')
|
|
|
353
426
|
});
|
|
354
427
|
}
|
|
355
428
|
else if (action.command === 'set-thp') {
|
|
356
|
-
const item = (
|
|
429
|
+
const item = (_c = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _c !== void 0 ? _c : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
357
430
|
if (item) {
|
|
358
431
|
item.temphp = Math.max(0, action.value);
|
|
359
432
|
}
|
|
360
433
|
}
|
|
361
434
|
else if (action.command === 'set-hp') {
|
|
362
|
-
const item = (
|
|
435
|
+
const item = (_d = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _d !== void 0 ? _d : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
363
436
|
if (item) {
|
|
364
437
|
item.hp = Math.min(item.maxhp, Math.max(0, action.value));
|
|
365
438
|
}
|
|
@@ -371,19 +444,68 @@ program.command('track')
|
|
|
371
444
|
}
|
|
372
445
|
}
|
|
373
446
|
else if (action.command === 'set-conditions') {
|
|
374
|
-
const item = (
|
|
447
|
+
const item = (_e = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _e !== void 0 ? _e : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
375
448
|
if (item) {
|
|
376
|
-
item.conditions = action.value;
|
|
449
|
+
item.conditions = action.value.trim();
|
|
450
|
+
}
|
|
451
|
+
}
|
|
452
|
+
else if (action.command === 'add-conditions') {
|
|
453
|
+
const item = (_f = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _f !== void 0 ? _f : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
454
|
+
if (item) {
|
|
455
|
+
const conditions = [...item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length), action.value.toLowerCase().trim()];
|
|
456
|
+
item.conditions = conditions.join(', ');
|
|
457
|
+
}
|
|
458
|
+
}
|
|
459
|
+
else if (action.command === 'rem-conditions') {
|
|
460
|
+
const item = (_g = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _g !== void 0 ? _g : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
461
|
+
if (item) {
|
|
462
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).filter((c) => !c.includes(action.value.toLowerCase().trim()));
|
|
463
|
+
item.conditions = conditions.join(', ');
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
else if (action.command === 'inc-conditions') {
|
|
467
|
+
const item = (_h = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _h !== void 0 ? _h : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
468
|
+
if (item) {
|
|
469
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).map((c) => {
|
|
470
|
+
if (c.includes(action.value.toLowerCase().trim())) {
|
|
471
|
+
const match = c.match(/(.*)\s+(\d+)/);
|
|
472
|
+
if (match && match[1] && match[2]) {
|
|
473
|
+
return `${match[1].trim()} ${parseInt(match[2]) + 1}`;
|
|
474
|
+
}
|
|
475
|
+
}
|
|
476
|
+
return c;
|
|
477
|
+
});
|
|
478
|
+
item.conditions = conditions.join(', ');
|
|
479
|
+
}
|
|
480
|
+
}
|
|
481
|
+
else if (action.command === 'dec-conditions') {
|
|
482
|
+
const item = (_j = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _j !== void 0 ? _j : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
483
|
+
if (item) {
|
|
484
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).map((c) => {
|
|
485
|
+
if (c.includes(action.value.toLowerCase().trim())) {
|
|
486
|
+
const match = c.match(/(.*)\s+(\d+)/);
|
|
487
|
+
if (match && match[1] && match[2]) {
|
|
488
|
+
if (parseInt(match[2]) > 1) {
|
|
489
|
+
return `${match[1].trim()} ${parseInt(match[2]) - 1}`;
|
|
490
|
+
}
|
|
491
|
+
else {
|
|
492
|
+
return match[1].trim();
|
|
493
|
+
}
|
|
494
|
+
}
|
|
495
|
+
}
|
|
496
|
+
return c;
|
|
497
|
+
});
|
|
498
|
+
item.conditions = conditions.join(', ');
|
|
377
499
|
}
|
|
378
500
|
}
|
|
379
501
|
else if (action.command === 'mod-thp') {
|
|
380
|
-
const item = (
|
|
502
|
+
const item = (_k = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _k !== void 0 ? _k : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
381
503
|
if (item) {
|
|
382
504
|
item.temphp = Math.max(0, item.temphp + action.value);
|
|
383
505
|
}
|
|
384
506
|
}
|
|
385
507
|
else if (action.command === 'mod-hp') {
|
|
386
|
-
const item = (
|
|
508
|
+
const item = (_l = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)) !== null && _l !== void 0 ? _l : (tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag));
|
|
387
509
|
if (item) {
|
|
388
510
|
let hp = item.hp;
|
|
389
511
|
let thp = item.temphp;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pf2e-sage-stats",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.6",
|
|
4
4
|
"description": "An RPG Sage's .tsv stat generation tool",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"author": "ikariott@gmail.com",
|
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
"devDependencies": {
|
|
18
18
|
"@eslint/js": "^9.17.0",
|
|
19
19
|
"@types/jest": "^29.5.14",
|
|
20
|
+
"@types/jsdom": "^27.0.0",
|
|
20
21
|
"@types/lodash": "^4.17.13",
|
|
21
22
|
"@types/pluralize": "^0.0.33",
|
|
22
23
|
"@types/tsv": "^0.2.4",
|
|
@@ -30,11 +31,14 @@
|
|
|
30
31
|
},
|
|
31
32
|
"dependencies": {
|
|
32
33
|
"abbreviate": "^0.0.3",
|
|
34
|
+
"clipboardy": "^5.1.0",
|
|
33
35
|
"commander": "^12.1.0",
|
|
34
36
|
"dedent-js": "^1.0.1",
|
|
37
|
+
"jsdom": "^28.0.0",
|
|
35
38
|
"lodash": "^4.17.21",
|
|
36
39
|
"pluralize": "^8.0.0",
|
|
37
40
|
"tsv": "^0.2.0",
|
|
38
41
|
"zod": "^3.24.1"
|
|
39
|
-
}
|
|
42
|
+
},
|
|
43
|
+
"packageManager": "yarn@1.22.21+sha1.1959a18351b811cdeedbd484a8f86c3cc3bbaf72"
|
|
40
44
|
}
|
package/src/app.ts
CHANGED
|
@@ -4,6 +4,7 @@ import { capitalize, entries, startCase, toLower, kebabCase, keys, difference, g
|
|
|
4
4
|
import dedent from 'dedent-js';
|
|
5
5
|
import abbreviate from 'abbreviate';
|
|
6
6
|
import pluralize from 'pluralize';
|
|
7
|
+
import { JSDOM } from 'jsdom';
|
|
7
8
|
import { readdir, rename, stat } from 'fs/promises';
|
|
8
9
|
|
|
9
10
|
const schema = zod.object({
|
|
@@ -197,7 +198,7 @@ const charSchema = zod.object({
|
|
|
197
198
|
|
|
198
199
|
export type CharSchema = zod.infer<typeof charSchema>;
|
|
199
200
|
|
|
200
|
-
export const
|
|
201
|
+
export const flatMap: Record<string, string> = {
|
|
201
202
|
...([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20].map((v): [string, string] => (
|
|
202
203
|
[`${v}`, `d20 >= ${v} flat;`]
|
|
203
204
|
)).reduce<Record<string, string>>((p, [k, v]) => { p[k] = v; return p }, {})),
|
|
@@ -207,14 +208,24 @@ export const prediceateMap: Record<string, string> = {
|
|
|
207
208
|
hidden: 'd20 >= 11 flat;',
|
|
208
209
|
};
|
|
209
210
|
|
|
210
|
-
export const
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
211
|
+
export const diceMap: Record<string, string> = {
|
|
212
|
+
...([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20].map((v): [string, string] => (
|
|
213
|
+
[`${v}`, `(${v})`]
|
|
214
|
+
)).reduce<Record<string, string>>((p, [k, v]) => { p[k] = v; return p }, {})),
|
|
215
|
+
a: '+2',
|
|
216
|
+
adv: '+2',
|
|
217
|
+
advantage: '+2',
|
|
218
|
+
d: '-2',
|
|
219
|
+
dis: '-2',
|
|
220
|
+
disadvantage: '-2',
|
|
221
|
+
f: '+2',
|
|
222
|
+
for: '+2',
|
|
223
|
+
fort: '+2',
|
|
224
|
+
fortune: '+2',
|
|
225
|
+
m: '-2',
|
|
226
|
+
mis: '-2',
|
|
227
|
+
misfortune: '-2',
|
|
228
|
+
};
|
|
218
229
|
|
|
219
230
|
export const fromatMap = (name: string, map: Record<string, string>) => {
|
|
220
231
|
return TSV.stringify([{
|
|
@@ -308,10 +319,7 @@ const locateStrikes = (statblock: string, alias: string): Record<string, Schema[
|
|
|
308
319
|
.replace(/\+\d/g, '')
|
|
309
320
|
.replace(/Weapon\s+Striking(\s+\((Greater|Major)\))?/gi, '')
|
|
310
321
|
.replace(/((Greater|Major)\s+)?Striking/gi, '')
|
|
311
|
-
.replace(/\(
|
|
312
|
-
.replace(/\(Finesse\)/gi, '')
|
|
313
|
-
.replace(/\(\+\)/gi, '')
|
|
314
|
-
.replace(/\(\)/gi, '')
|
|
322
|
+
.replace(/\(.*\)/gi, '')
|
|
315
323
|
.replace(/\s+/g, ' ')
|
|
316
324
|
.trim();
|
|
317
325
|
|
|
@@ -333,6 +341,8 @@ const locateStrikes = (statblock: string, alias: string): Record<string, Schema[
|
|
|
333
341
|
.replace(/Electricity/, 'electricity')
|
|
334
342
|
.replace(/Sonic/, 'sonic')
|
|
335
343
|
.replace(/Spirit/, 'spirit')
|
|
344
|
+
.replace(/Acid/, 'acid')
|
|
345
|
+
.replace(/[pP]lus\s(\d+d)/, '+$1')
|
|
336
346
|
.trim();
|
|
337
347
|
|
|
338
348
|
const twoHand = _traits.match(/(two-hand|two-handed)\s+(d\d+)/);
|
|
@@ -484,18 +494,7 @@ const toRanged = ([key, value]: [string, Schema['ranged'][string]]): [string, nu
|
|
|
484
494
|
...(value.damage ? [[`ranged.${key}.damage`, value.damage] as [string, string]] : []),
|
|
485
495
|
];
|
|
486
496
|
|
|
487
|
-
const
|
|
488
|
-
['dc.recall.incredibly-easy', secret ? `||${value - 10}||` : `${value - 10}`],
|
|
489
|
-
['dc.recall.very-easy', secret ? `||${value - 5}||` : `${value - 5}`],
|
|
490
|
-
['dc.recall.easy', secret ? `||${value - 2}||` : `${value - 2}`],
|
|
491
|
-
['dc.recall.default', secret ? `||${value}||` : `${value}`],
|
|
492
|
-
['dc.recall', secret ? `||${value}||` : `${value}`],
|
|
493
|
-
['dc.recall.hard', secret ? `||${value + 2}||` : `${value + 2}`],
|
|
494
|
-
['dc.recall.very-hard', secret ? `||${value + 5}||` : `${value + 5}`],
|
|
495
|
-
['dc.recall.incredibly-hard', secret ? `||${value + 10}||` : `${value + 10}`],
|
|
496
|
-
])(dcByLevel[Math.max(Math.min(level + 1, dcByLevel.length - 1), 0)] + bump);
|
|
497
|
-
|
|
498
|
-
export const flatten = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false, recallDC: boolean = false): Record<string, string | number> => {
|
|
497
|
+
export const flatten = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false): Record<string, string | number> => {
|
|
499
498
|
const untrained = stats.untrained;
|
|
500
499
|
const skills = defaultSkills ? {
|
|
501
500
|
acrobatics: untrained + stats.attributes.dexterity,
|
|
@@ -600,9 +599,6 @@ export const flatten = (stats: Schema, secretDC: boolean = false, defaultSkills:
|
|
|
600
599
|
...entries(skills).map(mod2DC(true, (stats.bump.skills ?? stats.bump.default))),
|
|
601
600
|
...entries(stats.extra).map(mod2DC(true, stats.bump.default)),
|
|
602
601
|
] : []),
|
|
603
|
-
...(recallDC ? [
|
|
604
|
-
...recallDCs(stats.level, secretDC, stats.bump.default),
|
|
605
|
-
] : []),
|
|
606
602
|
...(stats.perceptionInfo.length > 0 ? [
|
|
607
603
|
[`perception.info`, `\`(${stats.perceptionInfo.join(', ')})\``]
|
|
608
604
|
] : []),
|
|
@@ -615,12 +611,12 @@ export const flatten = (stats: Schema, secretDC: boolean = false, defaultSkills:
|
|
|
615
611
|
].reduce<Record<string | number, string | number>>((p, [key, value]) => { p[key] = value; return p }, {});
|
|
616
612
|
}
|
|
617
613
|
|
|
618
|
-
export const formatTSV = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false
|
|
619
|
-
TSV.stringify([flatten(stats, secretDC, defaultSkills
|
|
614
|
+
export const formatTSV = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false): string => (
|
|
615
|
+
TSV.stringify([flatten(stats, secretDC, defaultSkills)])
|
|
620
616
|
);
|
|
621
617
|
|
|
622
|
-
export const formatCommand = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false
|
|
623
|
-
Object.entries(flatten(stats, secretDC, defaultSkills
|
|
618
|
+
export const formatCommand = (stats: Schema, secretDC: boolean = false, defaultSkills: boolean = false): string => (
|
|
619
|
+
Object.entries(flatten(stats, secretDC, defaultSkills)).map(([k, v]) => `${k}="${v}"`).join(' ')
|
|
624
620
|
);
|
|
625
621
|
|
|
626
622
|
export const formatTable = (table: string, season: string, scenario: string, _name: string, gm: string, players: string) => {
|
|
@@ -634,7 +630,7 @@ export const formatTable = (table: string, season: string, scenario: string, _na
|
|
|
634
630
|
@TableBot create "${gameName}" --gm ${gm} --players ${players} --table-name ${tableName} --ooc-table-name ooc-${tableName} --category Game Tables
|
|
635
631
|
\`\`\`
|
|
636
632
|
\`\`\`
|
|
637
|
-
sage! game create name="${gameName}" gameSystem="pf2e" ic=" #${tableName} " ooc=" #ooc-${tableName} " gms=" ${gm} " players=" @${gameName} " dialogPost="post" diceSecret="gm" diceCrit="timestwo" diceOutput=M gmCharName="Хронист"
|
|
633
|
+
sage! game create name="${gameName}" gameSystem="pf2e" ic=" #${tableName} " ooc=" #ooc-${tableName} " gms=" ${gm} " players=" @${gameName} " dialogPost="post" diceSecret="gm" diceCrit="timestwo" diceOutput=M gmCharName="Хронист"
|
|
638
634
|
\`\`\`
|
|
639
635
|
`;
|
|
640
636
|
};
|
|
@@ -702,8 +698,11 @@ export const newtracker = (status: string) => {
|
|
|
702
698
|
};
|
|
703
699
|
|
|
704
700
|
export const formatTracker = (tracker: CharSchema[]) => {
|
|
701
|
+
const aliasSpace = (t: { alias: string }) => (t.alias.length > 0 ? 0 : 5);
|
|
702
|
+
const nameLengthWithAlias = (t: { name: string, alias: string }) => t.name.length - aliasSpace(t);
|
|
703
|
+
|
|
705
704
|
const nameLength = tracker.reduce((p, c) => {
|
|
706
|
-
const length = c.children.reduce((pp, cc) => pp > cc
|
|
705
|
+
const length = c.children.reduce((pp, cc) => pp > nameLengthWithAlias(cc) ? pp : nameLengthWithAlias(cc), nameLengthWithAlias(c));
|
|
707
706
|
|
|
708
707
|
return p > length ? p : length;
|
|
709
708
|
}, 0);
|
|
@@ -742,10 +741,12 @@ export const formatTracker = (tracker: CharSchema[]) => {
|
|
|
742
741
|
ls.push('')
|
|
743
742
|
}
|
|
744
743
|
|
|
745
|
-
const hp = char.foe ? (
|
|
744
|
+
const hp = !char.foe && char.hp > 0 ? (
|
|
745
|
+
`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}/${char.maxhp}`.padStart(hpLength)
|
|
746
|
+
) : char.hp > 0 ? (
|
|
746
747
|
`-${char.maxhp - char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}`.padStart(hpLength)
|
|
747
748
|
) : (
|
|
748
|
-
`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}
|
|
749
|
+
`${char.hp}${char.temphp > 0 ? `+${char.temphp}` : ''}`.padStart(hpLength)
|
|
749
750
|
);
|
|
750
751
|
|
|
751
752
|
const hpBar = (value: number, max: number) => (
|
|
@@ -759,7 +760,7 @@ export const formatTracker = (tracker: CharSchema[]) => {
|
|
|
759
760
|
);
|
|
760
761
|
|
|
761
762
|
ls.push((
|
|
762
|
-
`${stateMap[char.state]}**\` ${char.name.padEnd(nameLength)} ▏${char.alias.padEnd(3)} ▏${hp} \`** ${hpBar(char.hp, char.maxhp)} `
|
|
763
|
+
`${stateMap[char.hp > 0 ? char.state : 'cross']}**\` ${char.name.padEnd(nameLength + aliasSpace(char))}${char.alias.length > 0 ? ` ▏${char.alias.padEnd(3)}` : ''} ▏${hp} \`** ${hpBar(char.hp, char.maxhp)} `
|
|
763
764
|
))
|
|
764
765
|
|
|
765
766
|
if (char.conditions.length > 0) {
|
|
@@ -767,14 +768,16 @@ export const formatTracker = (tracker: CharSchema[]) => {
|
|
|
767
768
|
}
|
|
768
769
|
|
|
769
770
|
for (const child of char.children) {
|
|
770
|
-
const hhp = char.foe ? (
|
|
771
|
+
const hhp = !char.foe && child.hp > 0 ? (
|
|
772
|
+
`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}/${child.maxhp}`.padStart(hpLength)
|
|
773
|
+
) : child.hp > 0 ? (
|
|
771
774
|
`-${child.maxhp - child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}`.padStart(hpLength)
|
|
772
775
|
) : (
|
|
773
|
-
`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}
|
|
776
|
+
`${child.hp}${child.temphp > 0 ? `+${child.temphp}` : ''}`.padStart(hpLength)
|
|
774
777
|
);
|
|
775
778
|
|
|
776
779
|
ls.push((
|
|
777
|
-
`:smallnode:**\` ${child.name.padEnd(nameLength)} ▏${child.alias.padEnd(3)} ▏${hhp} \`** ${hpBar(child.hp, child.maxhp)} `
|
|
780
|
+
`:smallnode:**\` ${child.name.padEnd(nameLength + aliasSpace(child))}${child.alias.length > 0 ? ` ▏${child.alias.padEnd(3)}` : ''} ▏${hhp} \`** ${hpBar(child.hp, child.maxhp)} `
|
|
778
781
|
))
|
|
779
782
|
|
|
780
783
|
if (child.conditions.length > 0) {
|
|
@@ -813,3 +816,52 @@ export const sortFolder = async () => {
|
|
|
813
816
|
|
|
814
817
|
return transformed;
|
|
815
818
|
};
|
|
819
|
+
|
|
820
|
+
export const screenPlay = (htmlContent: string) => {
|
|
821
|
+
const dom = new JSDOM(htmlContent);
|
|
822
|
+
const document = dom.window.document;
|
|
823
|
+
|
|
824
|
+
const outputLines = [];
|
|
825
|
+
|
|
826
|
+
const preambleEntry = document.querySelector('.preamble__entry');
|
|
827
|
+
if (preambleEntry) {
|
|
828
|
+
outputLines.push(`SCENE: ${preambleEntry.textContent}`);
|
|
829
|
+
outputLines.push('');
|
|
830
|
+
}
|
|
831
|
+
|
|
832
|
+
// Process all chatlog messages
|
|
833
|
+
const messages = document.querySelectorAll('.chatlog__message');
|
|
834
|
+
|
|
835
|
+
messages.forEach(message => {
|
|
836
|
+
const authorElement = message.querySelector('.chatlog__author');
|
|
837
|
+
const contentElement = message.querySelector('.chatlog__content');
|
|
838
|
+
|
|
839
|
+
if (!authorElement || !contentElement) return;
|
|
840
|
+
|
|
841
|
+
const author = authorElement.textContent?.trim() ?? '';
|
|
842
|
+
const content = contentElement.textContent?.trim() ?? '';
|
|
843
|
+
|
|
844
|
+
// Skip bot tags in character names
|
|
845
|
+
const characterName = author.replace(/\s*BOT$/, '');
|
|
846
|
+
|
|
847
|
+
// Add character line
|
|
848
|
+
outputLines.push(`${characterName.toUpperCase()}`);
|
|
849
|
+
|
|
850
|
+
// Add dialogue/content (wrap long lines)
|
|
851
|
+
const lines = content.split('\n').map((c) => (
|
|
852
|
+
c
|
|
853
|
+
.replace(/(—|--)/g, '-')
|
|
854
|
+
// eslint-disable-next-line no-irregular-whitespace
|
|
855
|
+
.replace(/(|)/g, '')
|
|
856
|
+
.trim()
|
|
857
|
+
)).filter((c) => c.length);
|
|
858
|
+
|
|
859
|
+
for (const line of lines) {
|
|
860
|
+
outputLines.push(` ${line}`);
|
|
861
|
+
}
|
|
862
|
+
|
|
863
|
+
outputLines.push('');
|
|
864
|
+
});
|
|
865
|
+
|
|
866
|
+
return outputLines.join('\n');
|
|
867
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -4,10 +4,11 @@ import { Command } from 'commander';
|
|
|
4
4
|
import fs from 'fs/promises';
|
|
5
5
|
import path from 'path';
|
|
6
6
|
import readline from 'readline';
|
|
7
|
+
import clipboardy from 'clipboardy';
|
|
7
8
|
|
|
8
9
|
import pack from '../package.json';
|
|
9
10
|
|
|
10
|
-
import { sortFolder, formatCommand, formatJSON, formatTSV, fromatMap, parseJSON, parseStatblock, stub,
|
|
11
|
+
import { sortFolder, formatCommand, formatJSON, formatTSV, fromatMap, parseJSON, parseStatblock, stub, flatMap, formatTable, formatHP, newtracker, parseTracker, formatTracker, screenPlay, diceMap } from './app';
|
|
11
12
|
|
|
12
13
|
const program = new Command(pack.name);
|
|
13
14
|
|
|
@@ -57,27 +58,41 @@ program.command('sort')
|
|
|
57
58
|
console.log(await sortFolder());
|
|
58
59
|
});
|
|
59
60
|
|
|
61
|
+
program.command('convert')
|
|
62
|
+
.description('Convert a discord export file into a txt log')
|
|
63
|
+
.argument('<file>', 'input file')
|
|
64
|
+
.option('-o, --output <file>', 'output file')
|
|
65
|
+
.action(async (argument, option) => {
|
|
66
|
+
const file = await fs.readFile(argument, { encoding: 'utf-8' });
|
|
67
|
+
|
|
68
|
+
if (option.output) {
|
|
69
|
+
await fs.writeFile(option.output, screenPlay(file), { encoding: 'utf-8' })
|
|
70
|
+
} else {
|
|
71
|
+
console.log(screenPlay(file));
|
|
72
|
+
}
|
|
73
|
+
});
|
|
74
|
+
|
|
60
75
|
program.command('flat')
|
|
61
76
|
.description('Generte a special flat npc tsv')
|
|
62
77
|
.option('-n, --name <string>', 'npc name')
|
|
63
78
|
.option('-o, --output <file>', 'output json')
|
|
64
79
|
.action(async (option) => {
|
|
65
80
|
if (option.output) {
|
|
66
|
-
await fs.writeFile(option.output, fromatMap(option.name ?? 'flat',
|
|
81
|
+
await fs.writeFile(option.output, fromatMap(option.name ?? 'flat', flatMap), { encoding: 'utf-8' })
|
|
67
82
|
} else {
|
|
68
|
-
console.log(fromatMap(option.name ?? 'flat',
|
|
83
|
+
console.log(fromatMap(option.name ?? 'flat', flatMap));
|
|
69
84
|
}
|
|
70
85
|
});
|
|
71
86
|
|
|
72
|
-
program.command('
|
|
73
|
-
.description('Generte a special
|
|
87
|
+
program.command('dice')
|
|
88
|
+
.description('Generte a special dice npc tsv')
|
|
74
89
|
.option('-n, --name <string>', 'npc name')
|
|
75
90
|
.option('-o, --output <file>', 'output json')
|
|
76
91
|
.action(async (option) => {
|
|
77
92
|
if (option.output) {
|
|
78
|
-
await fs.writeFile(option.output, fromatMap(option.name ?? '
|
|
93
|
+
await fs.writeFile(option.output, fromatMap(option.name ?? 'dice', diceMap), { encoding: 'utf-8' })
|
|
79
94
|
} else {
|
|
80
|
-
console.log(fromatMap(option.name ?? '
|
|
95
|
+
console.log(fromatMap(option.name ?? 'dice', diceMap));
|
|
81
96
|
}
|
|
82
97
|
});
|
|
83
98
|
|
|
@@ -119,7 +134,6 @@ program.command('tsv')
|
|
|
119
134
|
.argument('<file>', 'input json')
|
|
120
135
|
.option('-o, --output <file>', 'output tsv')
|
|
121
136
|
.option('-s, --secretDC', 'produce secret DCs')
|
|
122
|
-
.option('-r, --recallDC', 'produce recall DCs')
|
|
123
137
|
.option('-d, --defaultSkills', 'produce values for untrained skills')
|
|
124
138
|
.action(async (argument, option) => {
|
|
125
139
|
const file = await fs.readFile(argument, { encoding: 'utf-8' });
|
|
@@ -128,7 +142,7 @@ program.command('tsv')
|
|
|
128
142
|
|
|
129
143
|
const output = option.output ? option.output : path.join(path.parse(argument).dir, path.parse(argument).name + '.tsv');
|
|
130
144
|
|
|
131
|
-
await fs.writeFile(output, formatTSV(stats, option.secretDC, option.defaultSkills
|
|
145
|
+
await fs.writeFile(output, formatTSV(stats, option.secretDC, option.defaultSkills), { encoding: 'utf-8' });
|
|
132
146
|
});
|
|
133
147
|
|
|
134
148
|
program.command('command')
|
|
@@ -136,7 +150,6 @@ program.command('command')
|
|
|
136
150
|
.argument('<file>', 'input json')
|
|
137
151
|
.option('-o, --output <file>', 'output txt')
|
|
138
152
|
.option('-s, --secretDC', 'produce secret DCs')
|
|
139
|
-
.option('-r, --recallDC', 'produce recall DCs')
|
|
140
153
|
.option('-d, --defaultSkills', 'produce values for untrained skills')
|
|
141
154
|
.action(async (argument, option) => {
|
|
142
155
|
const file = await fs.readFile(argument, { encoding: 'utf-8' });
|
|
@@ -145,7 +158,7 @@ program.command('command')
|
|
|
145
158
|
|
|
146
159
|
const output = option.output ? option.output : path.join(path.parse(argument).dir, path.parse(argument).name + '-command.txt');
|
|
147
160
|
|
|
148
|
-
await fs.writeFile(output, formatCommand(stats, option.secretDC, option.defaultSkills
|
|
161
|
+
await fs.writeFile(output, formatCommand(stats, option.secretDC, option.defaultSkills), { encoding: 'utf-8' });
|
|
149
162
|
});
|
|
150
163
|
|
|
151
164
|
program.command('newtracker')
|
|
@@ -193,7 +206,10 @@ program.command('track')
|
|
|
193
206
|
await fs.writeFile(option.output, formatTracker(tracker), { encoding: 'utf-8' })
|
|
194
207
|
} else {
|
|
195
208
|
console.clear();
|
|
196
|
-
|
|
209
|
+
|
|
210
|
+
const track = formatTracker(tracker);
|
|
211
|
+
clipboardy.writeSync(track)
|
|
212
|
+
console.log(track);
|
|
197
213
|
}
|
|
198
214
|
}
|
|
199
215
|
|
|
@@ -258,19 +274,48 @@ program.command('track')
|
|
|
258
274
|
}
|
|
259
275
|
},
|
|
260
276
|
}, {
|
|
261
|
-
regex: /^\s*(\S+)\s+[sS]
|
|
277
|
+
regex: /^\s*(\S+)\s+[sS]?\s*=?"([^"]*)"/,
|
|
262
278
|
map: (match: RegExpMatchArray) => {
|
|
263
279
|
return { command: 'set-conditions' as const, tag: match[1], value: match[2] };
|
|
264
280
|
},
|
|
281
|
+
}, {
|
|
282
|
+
regex: /^\s*(\S+)\s+[sS]?\s*\+"([^"]*)"/,
|
|
283
|
+
map: (match: RegExpMatchArray) => {
|
|
284
|
+
return { command: 'add-conditions' as const, tag: match[1], value: match[2] };
|
|
285
|
+
},
|
|
286
|
+
}, {
|
|
287
|
+
regex: /^\s*(\S+)\s+[sS]?\s*-"([^"]*)"/,
|
|
288
|
+
map: (match: RegExpMatchArray) => {
|
|
289
|
+
return { command: 'rem-conditions' as const, tag: match[1], value: match[2] };
|
|
290
|
+
},
|
|
291
|
+
}, {
|
|
292
|
+
regex: /^\s*(\S+)\s+[sS]?\s*\+\+"([^"]*)"/,
|
|
293
|
+
map: (match: RegExpMatchArray) => {
|
|
294
|
+
return { command: 'inc-conditions' as const, tag: match[1], value: match[2] };
|
|
295
|
+
},
|
|
296
|
+
}, {
|
|
297
|
+
regex: /^\s*(\S+)\s+[sS]?\s*--"([^"]*)"/,
|
|
298
|
+
map: (match: RegExpMatchArray) => {
|
|
299
|
+
return { command: 'dec-conditions' as const, tag: match[1], value: match[2] };
|
|
300
|
+
},
|
|
265
301
|
}, {
|
|
266
302
|
regex: /^\s*(\S+)\s+[cC]/,
|
|
267
303
|
map: (match: RegExpMatchArray) => ({ command: 'check' as const, tag: match[1] }),
|
|
268
304
|
}, {
|
|
269
305
|
regex: /^\s*(\S+)\s+[aA]/,
|
|
270
306
|
map: (match: RegExpMatchArray) => ({ command: 'arrow' as const, tag: match[1] }),
|
|
307
|
+
}, {
|
|
308
|
+
regex: /^\s*(\S+)\s+[eE]/,
|
|
309
|
+
map: (match: RegExpMatchArray) => ({ command: 'empty' as const, tag: match[1] }),
|
|
310
|
+
}, {
|
|
311
|
+
regex: /^\s*(\S+)\s+[xX]/,
|
|
312
|
+
map: (match: RegExpMatchArray) => ({ command: 'cross' as const, tag: match[1] }),
|
|
271
313
|
}, {
|
|
272
314
|
regex: /^\s*(\S+)\s+[dD]/,
|
|
273
315
|
map: (match: RegExpMatchArray) => ({ command: 'delete' as const, tag: match[1] }),
|
|
316
|
+
}, {
|
|
317
|
+
regex: /^\s*(\S+)\s+[wW]/,
|
|
318
|
+
map: (match: RegExpMatchArray) => ({ command: 'wait' as const, tag: match[1] }),
|
|
274
319
|
}];
|
|
275
320
|
|
|
276
321
|
const actions: ReturnType<typeof commands[number]['map']>[] = [];
|
|
@@ -322,6 +367,26 @@ program.command('track')
|
|
|
322
367
|
blocks[i].forEach((b) => b.state = 'empty')
|
|
323
368
|
}
|
|
324
369
|
}
|
|
370
|
+
} else if (action.command === 'wait') {
|
|
371
|
+
const sorted = [...tracker].sort((a, b) => (a.init === b.init) ? (b.foe ? 1 : 0) - (a.foe ? 1 : 0) : b.init - a.init);
|
|
372
|
+
|
|
373
|
+
const blocks = [[sorted[0]]];
|
|
374
|
+
|
|
375
|
+
for (let i=1; i < sorted.length; ++i) {
|
|
376
|
+
if (sorted[i].foe === blocks[blocks.length-1][0].foe) {
|
|
377
|
+
blocks[blocks.length-1].push(sorted[i])
|
|
378
|
+
} else {
|
|
379
|
+
blocks.push([sorted[i]])
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
const blockIndex = blocks.findIndex((b) => b.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag))
|
|
384
|
+
const block = blocks[blockIndex + 1]
|
|
385
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
386
|
+
|
|
387
|
+
if (block && item) {
|
|
388
|
+
item.init = (block[block.length - 1]?.init ?? 0) - 1;
|
|
389
|
+
}
|
|
325
390
|
} else if (action.command === 'check') {
|
|
326
391
|
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
327
392
|
|
|
@@ -334,6 +399,18 @@ program.command('track')
|
|
|
334
399
|
if (item) {
|
|
335
400
|
item.state = "arrow"
|
|
336
401
|
}
|
|
402
|
+
} else if (action.command === 'empty') {
|
|
403
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
404
|
+
|
|
405
|
+
if (item) {
|
|
406
|
+
item.state = "empty"
|
|
407
|
+
}
|
|
408
|
+
} else if (action.command === 'cross') {
|
|
409
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
410
|
+
|
|
411
|
+
if (item) {
|
|
412
|
+
item.state = "cross"
|
|
413
|
+
}
|
|
337
414
|
} else if (action.command === 'delete') {
|
|
338
415
|
tracker = tracker.filter((c) => !(c.id === action.tag || c.alias === action.tag || c.name == action.tag)).map((p) => ({
|
|
339
416
|
...p,
|
|
@@ -381,7 +458,71 @@ program.command('track')
|
|
|
381
458
|
)
|
|
382
459
|
|
|
383
460
|
if (item) {
|
|
384
|
-
item.conditions = action.value
|
|
461
|
+
item.conditions = action.value.trim()
|
|
462
|
+
}
|
|
463
|
+
} else if (action.command === 'add-conditions') {
|
|
464
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag) ?? (
|
|
465
|
+
tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
466
|
+
)
|
|
467
|
+
|
|
468
|
+
if (item) {
|
|
469
|
+
const conditions = [...item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length), action.value.toLowerCase().trim()];
|
|
470
|
+
|
|
471
|
+
item.conditions = conditions.join(', ')
|
|
472
|
+
}
|
|
473
|
+
} else if (action.command === 'rem-conditions') {
|
|
474
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag) ?? (
|
|
475
|
+
tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
476
|
+
)
|
|
477
|
+
|
|
478
|
+
if (item) {
|
|
479
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).filter((c) => !c.includes(action.value.toLowerCase().trim()));
|
|
480
|
+
|
|
481
|
+
item.conditions = conditions.join(', ')
|
|
482
|
+
}
|
|
483
|
+
} else if (action.command === 'inc-conditions') {
|
|
484
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag) ?? (
|
|
485
|
+
tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
486
|
+
)
|
|
487
|
+
|
|
488
|
+
if (item) {
|
|
489
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).map((c) => {
|
|
490
|
+
if (c.includes(action.value.toLowerCase().trim())) {
|
|
491
|
+
const match = c.match(/(.*)\s+(\d+)/);
|
|
492
|
+
|
|
493
|
+
if (match && match[1] && match[2]) {
|
|
494
|
+
return `${match[1].trim()} ${parseInt(match[2]) + 1}`
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
|
|
498
|
+
return c;
|
|
499
|
+
});
|
|
500
|
+
|
|
501
|
+
item.conditions = conditions.join(', ')
|
|
502
|
+
}
|
|
503
|
+
} else if (action.command === 'dec-conditions') {
|
|
504
|
+
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag) ?? (
|
|
505
|
+
tracker.flatMap((c) => c.children).find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag)
|
|
506
|
+
)
|
|
507
|
+
|
|
508
|
+
if (item) {
|
|
509
|
+
const conditions = item.conditions.split(',').map((c) => c.toLowerCase().trim()).filter((c) => c.length).map((c) => {
|
|
510
|
+
if (c.includes(action.value.toLowerCase().trim())) {
|
|
511
|
+
const match = c.match(/(.*)\s+(\d+)/);
|
|
512
|
+
|
|
513
|
+
if (match && match[1] && match[2]) {
|
|
514
|
+
if (parseInt(match[2]) > 1) {
|
|
515
|
+
return `${match[1].trim()} ${parseInt(match[2]) - 1}`
|
|
516
|
+
} else {
|
|
517
|
+
return match[1].trim()
|
|
518
|
+
}
|
|
519
|
+
}
|
|
520
|
+
}
|
|
521
|
+
|
|
522
|
+
return c;
|
|
523
|
+
});
|
|
524
|
+
|
|
525
|
+
item.conditions = conditions.join(', ')
|
|
385
526
|
}
|
|
386
527
|
} else if (action.command === 'mod-thp') {
|
|
387
528
|
const item = tracker.find((c) => c.id === action.tag || c.alias === action.tag || c.name == action.tag) ?? (
|