Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
acf2c8ef07 | ||
|
|
b931d0634b | ||
|
|
99d6702fe1 | ||
|
|
96896ba92f | ||
|
|
6557ef82ad | ||
|
|
17c64ec0de | ||
|
|
64bef08fe0 | ||
|
|
d81034f6f4 | ||
|
|
f66ac84c0b | ||
|
|
24f513baf8 | ||
|
|
9269348bf4 | ||
|
|
2758be6096 | ||
|
|
b1cfb636df | ||
|
|
0d77741a41 | ||
|
|
6508a7e883 | ||
|
|
8cbea7c237 | ||
|
|
d89671e707 | ||
|
|
d0d907bd98 | ||
|
|
f3264d60e2 | ||
|
|
63da87f372 | ||
|
|
4a5561a82f | ||
|
|
9fb7867069 | ||
|
|
b64125e637 | ||
|
|
c728f7bb6d | ||
|
|
19b472de00 | ||
|
|
bf4e98a780 | ||
|
|
3d21b8e466 |
@@ -0,0 +1,12 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Badge shape -->
|
||||
<path d="M6,2 H26 L30,6 V30 H2 V6 Z" fill="none" stroke="currentColor" stroke-width="2" stroke-linejoin="round"/>
|
||||
<!-- Notch at top (lanyard hole) -->
|
||||
<rect x="13" y="0" width="6" height="4" rx="1" fill="currentColor"/>
|
||||
<!-- Head -->
|
||||
<circle cx="16" cy="12" r="4" fill="currentColor"/>
|
||||
<!-- Shoulders -->
|
||||
<path d="M8,26 C8,20 24,20 24,26" fill="currentColor"/>
|
||||
<!-- ID stripe at bottom -->
|
||||
<rect x="5" y="26" width="22" height="2" fill="currentColor" opacity="0.5"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 575 B |
@@ -0,0 +1,8 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Hexagonal speech bubble -->
|
||||
<polygon points="4,4 28,4 28,22 20,22 16,28 12,22 4,22" fill="currentColor" stroke="currentColor" stroke-width="2" stroke-linejoin="round" fill-rule="evenodd"/>
|
||||
<!-- Signal bars inside -->
|
||||
<rect x="8" y="14" width="3" height="5" fill="currentColor"/>
|
||||
<rect x="13" y="11" width="3" height="8" fill="currentColor"/>
|
||||
<rect x="18" y="8" width="3" height="11" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 489 B |
@@ -0,0 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Outer ring -->
|
||||
<circle cx="16" cy="16" r="13" fill="none" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Inner ring -->
|
||||
<circle cx="16" cy="16" r="5" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Crosshairs -->
|
||||
<line x1="16" y1="3" x2="16" y2="9" stroke="currentColor" stroke-width="2"/>
|
||||
<line x1="16" y1="23" x2="16" y2="29" stroke="currentColor" stroke-width="2"/>
|
||||
<line x1="3" y1="16" x2="9" y2="16" stroke="currentColor" stroke-width="2"/>
|
||||
<line x1="23" y1="16" x2="29" y2="16" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Corner tick marks -->
|
||||
<line x1="11" y1="5" x2="12.5" y2="5" stroke="currentColor" stroke-width="1.5"/>
|
||||
<line x1="21" y1="5" x2="19.5" y2="5" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Center dot -->
|
||||
<circle cx="16" cy="16" r="2" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 897 B |
@@ -0,0 +1,14 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Cylinder top ellipse -->
|
||||
<ellipse cx="16" cy="6" rx="12" ry="4" fill="none" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Cylinder body -->
|
||||
<line x1="4" y1="6" x2="4" y2="24" stroke="currentColor" stroke-width="2"/>
|
||||
<line x1="28" y1="6" x2="28" y2="24" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Cylinder bottom ellipse -->
|
||||
<ellipse cx="16" cy="24" rx="12" ry="4" fill="currentColor" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Data bands -->
|
||||
<ellipse cx="16" cy="12" rx="12" ry="4" fill="none" stroke="currentColor" stroke-width="1" stroke-dasharray="3 2"/>
|
||||
<ellipse cx="16" cy="18" rx="12" ry="4" fill="none" stroke="currentColor" stroke-width="1" stroke-dasharray="3 2"/>
|
||||
<!-- Access port -->
|
||||
<rect x="13" y="4" width="6" height="4" rx="1" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 866 B |
@@ -0,0 +1,10 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Stylus body -->
|
||||
<polygon points="8,4 24,4 28,8 16,30 4,8" fill="none" stroke="currentColor" stroke-width="2" stroke-linejoin="round"/>
|
||||
<!-- Stylus grip band -->
|
||||
<line x1="6" y1="10" x2="26" y2="10" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Tip -->
|
||||
<polygon points="16,25 13,29 19,29" fill="currentColor"/>
|
||||
<!-- SLA insignia on stylus face -->
|
||||
<text x="16" y="19" text-anchor="middle" font-family="sans-serif" font-size="7" font-weight="bold" fill="currentColor">SLA</text>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 567 B |
@@ -0,0 +1,15 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Main crate -->
|
||||
<rect x="3" y="8" width="26" height="20" fill="none" stroke="currentColor" stroke-width="2" rx="1"/>
|
||||
<!-- Lid -->
|
||||
<rect x="3" y="4" width="26" height="6" fill="currentColor" rx="1"/>
|
||||
<!-- Center clasp -->
|
||||
<rect x="13" y="6" width="6" height="4" rx="1" fill="currentColor" opacity="0.6"/>
|
||||
<!-- Horizontal divider on crate -->
|
||||
<line x1="3" y1="18" x2="29" y2="18" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Corner brackets -->
|
||||
<path d="M3,13 L3,10 L6,10" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
<path d="M29,13 L29,10 L26,10" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
<path d="M3,23 L3,26 L6,26" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
<path d="M29,23 L29,26 L26,26" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 881 B |
@@ -0,0 +1,13 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- File/tablet body -->
|
||||
<path d="M5,2 H22 L28,8 V30 H5 Z" fill="none" stroke="currentColor" stroke-width="2" stroke-linejoin="round"/>
|
||||
<!-- Folded corner -->
|
||||
<path d="M22,2 L22,8 L28,8" fill="none" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Text lines -->
|
||||
<line x1="9" y1="13" x2="24" y2="13" stroke="currentColor" stroke-width="1.5"/>
|
||||
<line x1="9" y1="17" x2="24" y2="17" stroke="currentColor" stroke-width="1.5"/>
|
||||
<line x1="9" y1="21" x2="20" y2="21" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Classified stamp -->
|
||||
<rect x="7" y="24" width="10" height="4" rx="0.5" fill="none" stroke="currentColor" stroke-width="1.2" transform="rotate(-8 12 26)"/>
|
||||
<line x1="8" y1="26" x2="16" y2="26" stroke="currentColor" stroke-width="1" transform="rotate(-8 12 26)"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 859 B |
@@ -0,0 +1,14 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Emitter housing -->
|
||||
<polygon points="12,6 20,6 22,12 10,12" fill="currentColor" stroke="currentColor" stroke-width="1.5" stroke-linejoin="round"/>
|
||||
<!-- Lens circle -->
|
||||
<circle cx="16" cy="9" r="3" fill="none" stroke="currentColor" stroke-width="1.5" opacity="0.7"/>
|
||||
<!-- Beam spread (lower trapezoid) -->
|
||||
<polygon points="10,12 22,12 28,28 4,28" fill="currentColor" stroke="currentColor" stroke-width="1.5" stroke-linejoin="round"/>
|
||||
<!-- Beam rays -->
|
||||
<line x1="16" y1="12" x2="16" y2="28" stroke="currentColor" stroke-width="1" opacity="0.5"/>
|
||||
<line x1="13" y1="12" x2="8" y2="28" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="19" y1="12" x2="24" y2="28" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Mounting bracket -->
|
||||
<rect x="14" y="2" width="4" height="5" rx="1" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 894 B |
@@ -0,0 +1,17 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Ruler body -->
|
||||
<rect x="2" y="12" width="28" height="8" rx="1" fill="none" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Major tick marks -->
|
||||
<line x1="9" y1="12" x2="9" y2="17" stroke="currentColor" stroke-width="1.5"/>
|
||||
<line x1="16" y1="12" x2="16" y2="20" stroke="currentColor" stroke-width="2"/>
|
||||
<line x1="23" y1="12" x2="23" y2="17" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Minor ticks -->
|
||||
<line x1="5" y1="12" x2="5" y2="15" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="12" y1="12" x2="12" y2="15" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="19" y1="12" x2="19" y2="15" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="26" y1="12" x2="26" y2="15" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Arrow / range indicator above -->
|
||||
<line x1="4" y1="8" x2="28" y2="8" stroke="currentColor" stroke-width="1.5"/>
|
||||
<polygon points="4,8 8,6 8,10" fill="currentColor"/>
|
||||
<polygon points="28,8 24,6 24,10" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.0 KiB |
@@ -0,0 +1,11 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Map pin shape -->
|
||||
<path d="M16,2 C10,2 6,7 6,12 C6,19 16,30 16,30 C16,30 26,19 26,12 C26,7 22,2 16,2 Z" fill="currentColor" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Inner ring -->
|
||||
<circle cx="16" cy="12" r="5" fill="none" stroke="currentColor" stroke-width="2"/>
|
||||
<!-- Center dot -->
|
||||
<circle cx="16" cy="12" r="2.5" fill="currentColor"/>
|
||||
<!-- Angular bracket decorations -->
|
||||
<path d="M10,5 L8,7" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/>
|
||||
<path d="M22,5 L24,7" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 644 B |
@@ -0,0 +1,5 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<rect x="14" y="12" width="36" height="40" rx="6" stroke="#F4F7FA" stroke-width="4"/>
|
||||
<circle cx="24" cy="27" r="5" stroke="#F4F7FA" stroke-width="4"/>
|
||||
<path d="M19 40c2-4 5-6 9-6s7 2 9 6M36 24h8M36 32h8M36 40h8" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 358 B |
@@ -0,0 +1,5 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M20 50V18l12-8 12 8v32" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<path d="M26 24h3M35 24h3M26 31h3M35 31h3M26 38h3M35 38h3" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
<path d="M16 50h32" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 376 B |
@@ -0,0 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M39 10c-8 4-13 12-13 22 0 10 5 18 13 22-13-1.5-24-11.8-24-27S26 11.5 39 10Z" fill="#F4F7FA"/>
|
||||
<path d="m40 21 8 11-8 11" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 297 B |
@@ -0,0 +1,5 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M10 32c5.7-9 13.1-13.5 22-13.5S48.3 23 54 32c-5.7 9-13.1 13.5-22 13.5S15.7 41 10 32Z" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<circle cx="32" cy="32" r="7" stroke="#F4F7FA" stroke-width="4"/>
|
||||
<circle cx="32" cy="32" r="2.5" fill="#F4F7FA"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 356 B |
@@ -0,0 +1,6 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M23 18h18l5 8-3 15H21l-3-15 5-8Z" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<circle cx="26" cy="29" r="2.5" fill="#F4F7FA"/>
|
||||
<circle cx="38" cy="29" r="2.5" fill="#F4F7FA"/>
|
||||
<path d="M26 37c2 2 4 3 6 3s4-1 6-3" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 385 B |
@@ -0,0 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M18 12h20l8 8v28a4 4 0 0 1-4 4H18a4 4 0 0 1-4-4V16a4 4 0 0 1 4-4Z" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<path d="M38 12v10h10M24 30h12M24 38h16" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 320 B |
@@ -0,0 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M32 16v28M24 44h16" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
<path d="M22 22c2.5-3.5 6-5 10-5s7.5 1.5 10 5M16 16c4.3-5.3 9.6-8 16-8s11.7 2.7 16 8M16 28c4.3 5.3 9.6 8 16 8s11.7-2.7 16-8" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 356 B |
@@ -0,0 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M18 48 28 16M30 50l8-26M42 48l6-18" stroke="#F4F7FA" stroke-width="5" stroke-linecap="round"/>
|
||||
<path d="M18 48c2-4 6-7 10-8M30 50c2-4 5-7 8-8M42 48c1.5-3 4-5.5 7-6.5" stroke="#F4F7FA" stroke-width="3.5" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 321 B |
@@ -0,0 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M32 8 48 14v14c0 11-6.4 20.8-16 28-9.6-7.2-16-17-16-28V14L32 8Z" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<path d="M32 18v24M22 30h20" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 306 B |
@@ -0,0 +1,5 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none">
|
||||
<path d="M24 10h16l8 14-8 14H24l-8-14 8-14Z" stroke="#F4F7FA" stroke-width="4" stroke-linejoin="round"/>
|
||||
<circle cx="32" cy="24" r="4" fill="#F4F7FA"/>
|
||||
<path d="M32 28v18M32 38h10M32 46H22" stroke="#F4F7FA" stroke-width="4" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 335 B |
@@ -0,0 +1,11 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Waveform bars -->
|
||||
<rect x="2" y="12" width="3" height="8" rx="1" fill="currentColor"/>
|
||||
<rect x="7" y="7" width="3" height="18" rx="1" fill="currentColor"/>
|
||||
<rect x="12" y="4" width="3" height="24" rx="1" fill="currentColor"/>
|
||||
<rect x="17" y="9" width="3" height="14" rx="1" fill="currentColor"/>
|
||||
<rect x="22" y="6" width="3" height="20" rx="1" fill="currentColor"/>
|
||||
<rect x="27" y="13" width="3" height="6" rx="1" fill="currentColor"/>
|
||||
<!-- Base line -->
|
||||
<line x1="2" y1="29" x2="30" y2="29" stroke="currentColor" stroke-width="1"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 631 B |
@@ -0,0 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Outer border -->
|
||||
<rect x="2" y="2" width="28" height="28" fill="none" stroke="currentColor" stroke-width="2" rx="1"/>
|
||||
<!-- Grid lines -->
|
||||
<line x1="11" y1="2" x2="11" y2="30" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="21" y1="2" x2="21" y2="30" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="2" y1="11" x2="30" y2="11" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="2" y1="21" x2="30" y2="21" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Sector fills — industrial blocks -->
|
||||
<rect x="3" y="3" width="7" height="7" fill="currentColor"/>
|
||||
<rect x="13" y="13" width="7" height="7" fill="currentColor" opacity="0.6"/>
|
||||
<rect x="22" y="22" width="7" height="7" fill="currentColor"/>
|
||||
<rect x="22" y="3" width="7" height="7" fill="currentColor"/>
|
||||
<!-- Location marker -->
|
||||
<polygon points="16,17 14,21 18,21" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 940 B |
@@ -0,0 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Hex gear outer -->
|
||||
<polygon points="16,2 27,8 27,20 16,26 5,20 5,8" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linejoin="round"/>
|
||||
<!-- Gear teeth on hex edges -->
|
||||
<polygon points="16,1 18,4 14,4" fill="currentColor"/>
|
||||
<polygon points="27.5,7.5 27,11 24.5,9.5" fill="currentColor"/>
|
||||
<polygon points="27.5,20.5 24.5,22.5 27,19" fill="currentColor"/>
|
||||
<polygon points="16,27 14,24 18,24" fill="currentColor"/>
|
||||
<polygon points="4.5,20.5 5,19 7.5,22.5" fill="currentColor"/>
|
||||
<polygon points="4.5,7.5 7.5,9.5 5,11" fill="currentColor"/>
|
||||
<!-- Inner hex cutout -->
|
||||
<polygon points="16,9 21,12 21,18 16,21 11,18 11,12" fill="currentColor"/>
|
||||
<!-- Center circle -->
|
||||
<circle cx="16" cy="15" r="3.5" fill="none" stroke="currentColor" stroke-width="2"/>
|
||||
<circle cx="16" cy="15" r="1.5" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 910 B |
@@ -0,0 +1,9 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Speaker cone -->
|
||||
<polygon points="4,11 12,11 20,5 20,27 12,21 4,21" fill="currentColor" stroke="currentColor" stroke-width="1.5" stroke-linejoin="round"/>
|
||||
<!-- Sound wave arcs -->
|
||||
<path d="M23,10 C26,12 26,20 23,22" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"/>
|
||||
<path d="M25,7 C30,11 30,21 25,25" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" opacity="0.6"/>
|
||||
<!-- Base line -->
|
||||
<rect x="4" y="21" width="8" height="5" rx="0.5" fill="currentColor" opacity="0.5"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 609 B |
@@ -0,0 +1,15 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Outer frame -->
|
||||
<rect x="2" y="3" width="28" height="26" fill="none" stroke="currentColor" stroke-width="2" rx="1"/>
|
||||
<!-- Header row -->
|
||||
<rect x="2" y="3" width="28" height="6" fill="currentColor" rx="1"/>
|
||||
<!-- Row dividers -->
|
||||
<line x1="2" y1="15" x2="30" y2="15" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="2" y1="21" x2="30" y2="21" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Column dividers -->
|
||||
<line x1="10" y1="9" x2="10" y2="29" stroke="currentColor" stroke-width="1"/>
|
||||
<line x1="21" y1="9" x2="21" y2="29" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Die symbol in first col -->
|
||||
<rect x="4" y="11" width="4" height="4" rx="0.5" fill="none" stroke="currentColor" stroke-width="1"/>
|
||||
<circle cx="6" cy="13" r="0.8" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 851 B |
@@ -0,0 +1,14 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- 2x2 tile grid with isometric feel -->
|
||||
<!-- Top-left tile -->
|
||||
<rect x="2" y="2" width="13" height="13" rx="1" fill="currentColor" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Top-right tile -->
|
||||
<rect x="17" y="2" width="13" height="13" rx="1" fill="currentColor" opacity="0.5" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Bottom-left tile -->
|
||||
<rect x="2" y="17" width="13" height="13" rx="1" fill="currentColor" opacity="0.5" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Bottom-right tile -->
|
||||
<rect x="17" y="17" width="13" height="13" rx="1" fill="currentColor" stroke="currentColor" stroke-width="1.5"/>
|
||||
<!-- Corner brackets on tiles -->
|
||||
<path d="M4,7 L4,4 L7,4" fill="none" stroke="currentColor" stroke-width="1.2"/>
|
||||
<path d="M19,7 L19,4 L22,4" fill="none" stroke="currentColor" stroke-width="1.2"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 907 B |
@@ -0,0 +1,10 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Hex base -->
|
||||
<polygon points="16,3 28,10 28,22 16,29 4,22 4,10" fill="none" stroke="currentColor" stroke-width="2" stroke-linejoin="round"/>
|
||||
<!-- Inner ring -->
|
||||
<polygon points="16,8 23,12 23,20 16,24 9,20 9,12" fill="none" stroke="currentColor" stroke-width="1"/>
|
||||
<!-- Head silhouette -->
|
||||
<circle cx="16" cy="14" r="3.5" fill="currentColor"/>
|
||||
<!-- Shoulders -->
|
||||
<path d="M10,23 C10,19 22,19 22,23" fill="currentColor"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 509 B |
@@ -0,0 +1,14 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
|
||||
<!-- Main wall line heavy -->
|
||||
<line x1="4" y1="16" x2="28" y2="16" stroke="currentColor" stroke-width="4"/>
|
||||
<!-- Wall battlements (top) -->
|
||||
<rect x="5" y="10" width="4" height="6" fill="currentColor"/>
|
||||
<rect x="13" y="10" width="4" height="6" fill="currentColor"/>
|
||||
<rect x="21" y="10" width="4" height="6" fill="currentColor"/>
|
||||
<!-- Wall base foundation -->
|
||||
<rect x="3" y="20" width="26" height="4" rx="1" fill="currentColor" opacity="0.5"/>
|
||||
<!-- Door gap indicator -->
|
||||
<rect x="14" y="16" width="4" height="4" fill="currentColor" opacity="0"/>
|
||||
<line x1="14" y1="16" x2="14" y2="24" stroke="currentColor" stroke-width="1" stroke-dasharray="2 2" opacity="0.7"/>
|
||||
<line x1="18" y1="16" x2="18" y2="24" stroke="currentColor" stroke-width="1" stroke-dasharray="2 2" opacity="0.7"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 869 B |
@@ -214,8 +214,8 @@
|
||||
},
|
||||
"hits": {
|
||||
"increase": {
|
||||
"android": "@UUID[Compendium.mosh.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Make a Wound Check}",
|
||||
"human": "@UUID[Compendium.mosh.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Make a Wound Check}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Make a Wound Check}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Make a Wound Check}"
|
||||
},
|
||||
"increaseHeader": {
|
||||
"android": "Damaged",
|
||||
@@ -226,12 +226,12 @@
|
||||
"human": "systems/sla-mothership/images/icons/ui/attributes/health.png"
|
||||
},
|
||||
"hitCeiling": {
|
||||
"android": "The end draws near . . .<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}",
|
||||
"human": "The end draws near . . .<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}"
|
||||
"android": "The end draws near . . .<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}",
|
||||
"human": "The end draws near . . .<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}"
|
||||
},
|
||||
"pastCeiling": {
|
||||
"android": "The end draws near . . .<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}",
|
||||
"human": "The end draws near . . .<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}"
|
||||
"android": "The end draws near . . .<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}",
|
||||
"human": "The end draws near . . .<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Make a Death Save}"
|
||||
},
|
||||
"decrease": {
|
||||
"android": "System resources free up and you feel energized.",
|
||||
@@ -823,64 +823,64 @@
|
||||
"macro": {
|
||||
"wound": {
|
||||
"bleeding": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Bleeding}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Bleeding}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Bleeding}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Bleeding}"
|
||||
},
|
||||
"bleeding_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Bleeding [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Bleeding [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Bleeding [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Bleeding [-]}"
|
||||
},
|
||||
"bleeding_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.tFcWNddtZvlv7tsg]{Bleeding [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.tFcWNddtZvlv7tsg]{Bleeding [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.tFcWNddtZvlv7tsg]{Bleeding [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.tFcWNddtZvlv7tsg]{Bleeding [+]}"
|
||||
},
|
||||
"blunt_force": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Blunt Force}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Blunt Force}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Blunt Force}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Blunt Force}"
|
||||
},
|
||||
"blunt_force_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.k0zf8ZGivRguc0wb]{Blunt Force [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.k0zf8ZGivRguc0wb]{Blunt Force [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.k0zf8ZGivRguc0wb]{Blunt Force [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.k0zf8ZGivRguc0wb]{Blunt Force [-]}"
|
||||
},
|
||||
"blunt_force_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Blunt Force [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Blunt Force [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Blunt Force [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Blunt Force [+]}"
|
||||
},
|
||||
"fire_explosives": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fire & Explosives}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fire & Explosives}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fire & Explosives}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fire & Explosives}"
|
||||
},
|
||||
"fire_explosives_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fire & Explosives [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fire & Explosives [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fire & Explosives [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fire & Explosives [-]}"
|
||||
},
|
||||
"fire_explosives_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fire & Explosives [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fire & Explosives [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fire & Explosives [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fire & Explosives [+]}"
|
||||
},
|
||||
"gore_massive": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Gore}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Gore}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Gore}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Gore}"
|
||||
},
|
||||
"gore_massive_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.eQPuDgwv8evetFIk]{Gore [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.eQPuDgwv8evetFIk]{Gore [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.eQPuDgwv8evetFIk]{Gore [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.eQPuDgwv8evetFIk]{Gore [-]}"
|
||||
},
|
||||
"gore_massive_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Gore [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Gore [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Gore [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Gore [+]}"
|
||||
},
|
||||
"gunshot": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.XgCOLv9UunBddUyW]{Gunshot}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.XgCOLv9UunBddUyW]{Gunshot}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.XgCOLv9UunBddUyW]{Gunshot}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.XgCOLv9UunBddUyW]{Gunshot}"
|
||||
},
|
||||
"gunshot_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Gunshot [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Gunshot [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Gunshot [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Gunshot [-]}"
|
||||
},
|
||||
"gunshot_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.fnVATRHYJEUlS3pR]{Gunshot [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.fnVATRHYJEUlS3pR]{Gunshot [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.fnVATRHYJEUlS3pR]{Gunshot [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.fnVATRHYJEUlS3pR]{Gunshot [+]}"
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@@ -214,8 +214,8 @@
|
||||
},
|
||||
"hits": {
|
||||
"increase": {
|
||||
"android": "@UUID[Compendium.mosh.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Faça um Teste de Ferimento}",
|
||||
"human": "@UUID[Compendium.mosh.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Faça um Teste de Ferimento}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Faça um Teste de Ferimento}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_hotbar_1e.ZzKgfEmRdvDfyBMS]{Faça um Teste de Ferimento}"
|
||||
},
|
||||
"increaseHeader": {
|
||||
"android": "Dano",
|
||||
@@ -226,12 +226,12 @@
|
||||
"human": "systems/sla-mothership/images/icons/ui/attributes/health.png"
|
||||
},
|
||||
"hitCeiling": {
|
||||
"android": "O fim está próximo...<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}",
|
||||
"human": "O fim está próximo...<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}"
|
||||
"android": "O fim está próximo...<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}",
|
||||
"human": "O fim está próximo...<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}"
|
||||
},
|
||||
"pastCeiling": {
|
||||
"android": "O fim está próximo...<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}",
|
||||
"human": "O fim está próximo...<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}"
|
||||
"android": "O fim está próximo...<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}",
|
||||
"human": "O fim está próximo...<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.NsRHfRuuNGPfkYVf]{Faça uma Salvaguarda de Morte}"
|
||||
},
|
||||
"decrease": {
|
||||
"android": "Os recursos do sistema se estabilizam e você se sente energizado.",
|
||||
@@ -823,64 +823,64 @@
|
||||
"macro": {
|
||||
"wound": {
|
||||
"bleeding": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Sangramento}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Sangramento}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Sangramento}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.1DD8i6eCS6nx2Ip0]{Sangramento}"
|
||||
},
|
||||
"bleeding_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Sangramento [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Sangramento [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Sangramento [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.xr2o2PU5vdrR6fxQ]{Sangramento [-]}"
|
||||
},
|
||||
"bleeding_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.tFcWNddtZvlv7tsg]{Sangramento [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.tFcWNddtZvlv7tsg]{Sangramento [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.tFcWNddtZvlv7tsg]{Sangramento [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.tFcWNddtZvlv7tsg]{Sangramento [+]}"
|
||||
},
|
||||
"blunt_force": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Força Contundente}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Força Contundente}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Força Contundente}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.TAjlQjA5AAy3qYL3]{Força Contundente}"
|
||||
},
|
||||
"blunt_force_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.k0zf8ZGivRguc0wb]{Força Contundente [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.k0zf8ZGivRguc0wb]{Força Contundente [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.k0zf8ZGivRguc0wb]{Força Contundente [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.k0zf8ZGivRguc0wb]{Força Contundente [-]}"
|
||||
},
|
||||
"blunt_force_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Força Contundente [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Força Contundente [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Força Contundente [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.oL3GH0HoEPlP8vzG]{Força Contundente [+]}"
|
||||
},
|
||||
"fire_explosives": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fogo & Explosivos}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fogo & Explosivos}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fogo & Explosivos}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.bZi1qKmcKLFvnhZ2]{Fogo & Explosivos}"
|
||||
},
|
||||
"fire_explosives_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fogo & Explosivos [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fogo & Explosivos [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fogo & Explosivos [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.7rYhbDAaFeok1Daq]{Fogo & Explosivos [-]}"
|
||||
},
|
||||
"fire_explosives_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fogo & Explosivos [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fogo & Explosivos [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fogo & Explosivos [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.dJnQKDf0AlwK27QD]{Fogo & Explosivos [+]}"
|
||||
},
|
||||
"gore_massive": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Carniça}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Carniça}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Carniça}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.S9nnHKWYGSQmjQdp]{Carniça}"
|
||||
},
|
||||
"gore_massive_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.eQPuDgwv8evetFIk]{Carniça [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.eQPuDgwv8evetFIk]{Carniça [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.eQPuDgwv8evetFIk]{Carniça [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.eQPuDgwv8evetFIk]{Carniça [-]}"
|
||||
},
|
||||
"gore_massive_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Carniça [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Carniça [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Carniça [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.DuVjNlE4lsnR7Emc]{Carniça [+]}"
|
||||
},
|
||||
"gunshot": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.XgCOLv9UunBddUyW]{Disparo de Arma}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.XgCOLv9UunBddUyW]{Disparo de Arma}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.XgCOLv9UunBddUyW]{Disparo de Arma}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.XgCOLv9UunBddUyW]{Disparo de Arma}"
|
||||
},
|
||||
"gunshot_dis": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Disparo de Arma [-]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Disparo de Arma [-]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Disparo de Arma [-]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.LTpa1ZYVZl4m9k6z]{Disparo de Arma [-]}"
|
||||
},
|
||||
"gunshot_adv": {
|
||||
"android": "@UUID[Compendium.mosh.macros_triggered_1e.fnVATRHYJEUlS3pR]{Disparo de Arma [+]}",
|
||||
"human": "@UUID[Compendium.mosh.macros_triggered_1e.fnVATRHYJEUlS3pR]{Disparo de Arma [+]}"
|
||||
"android": "@UUID[Compendium.sla-mothership.macros_triggered_1e.fnVATRHYJEUlS3pR]{Disparo de Arma [+]}",
|
||||
"human": "@UUID[Compendium.sla-mothership.macros_triggered_1e.fnVATRHYJEUlS3pR]{Disparo de Arma [+]}"
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@@ -141,6 +141,30 @@ function decorateSkillWithTraitPreview(skill, traitRows = []) {
|
||||
return skill;
|
||||
}
|
||||
|
||||
function getPurchasableItemTotalCost(itemData = {}) {
|
||||
const system = itemData?.system ?? itemData?.data ?? {};
|
||||
const unitCost = Number(system.cost ?? 0) || 0;
|
||||
const quantity = Math.max(1, Number(system.quantity ?? 1) || 1);
|
||||
return Math.round(unitCost * quantity * 100) / 100;
|
||||
}
|
||||
|
||||
function isAmmoPurchaseItem(itemData = {}) {
|
||||
const system = itemData?.system ?? itemData?.data ?? {};
|
||||
const sla = system?.sla ?? {};
|
||||
const name = String(itemData?.name ?? "").trim().toLowerCase();
|
||||
const category = String(sla.category ?? "").trim().toLowerCase();
|
||||
const calibre = String(sla.calibre ?? "").trim();
|
||||
const ammoTag = String(sla.ammoTag ?? "").trim();
|
||||
return category === "ammunition" || Boolean((calibre && ammoTag) || name.startsWith("ammo:"));
|
||||
}
|
||||
|
||||
function formatSlaTimestamp() {
|
||||
return new Intl.DateTimeFormat(undefined, {
|
||||
dateStyle: "short",
|
||||
timeStyle: "short"
|
||||
}).format(new Date());
|
||||
}
|
||||
|
||||
const SLA_SPECIES_RULES = {
|
||||
Human: [
|
||||
{ key: "adaptable", label: "Adaptable", summary: "Once per session, reroll one Stat check and take the better result.", optional: false, default: true }
|
||||
@@ -258,6 +282,9 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
superData.sla.fluxNotes ??= { value: "" };
|
||||
superData.sla.ebbNotes ??= { value: "" };
|
||||
superData.sla.speciesRules ??= {};
|
||||
superData.sla.sessionAbilityUsed ??= false;
|
||||
superData.sla.contacts ??= [];
|
||||
superData.sla.activityLog ??= { value: "" };
|
||||
const activeTheme = this.actor.getFlag("sla-mothership", "sheetTheme") || "modern";
|
||||
data.slaSheetTheme = activeTheme;
|
||||
data.data.slaSheetTheme = activeTheme;
|
||||
@@ -279,6 +306,19 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
data.data.vevaphonInstabilityElevated = instab >= 6;
|
||||
data.data.vevaphonInstabilityCritical = instab >= 10;
|
||||
data.data.vevaphonInstabilityClass = instab >= 10 ? "instability-critical" : instab >= 6 ? "instability-elevated" : "instability-nominal";
|
||||
data.data.vevaphonInstabilityDesc = instab >= 10
|
||||
? "Instability critical. Full reversion risk on every shift."
|
||||
: instab >= 6
|
||||
? "Instability elevated. Sanity saves required when morphing mid-scene."
|
||||
: "Instability nominal. Morphing is available without additional risk.";
|
||||
data.data.vevaphonMorphPanic = [
|
||||
{ roll: 1, label: "Cascade Shift", desc: "Random morph form, +1 Instability." },
|
||||
{ roll: 2, label: "Identity Bleed", desc: "Forgets name and callsign until end of scene." },
|
||||
{ roll: 3, label: "Partial Lock", desc: "One limb freezes. −10 physical rolls using that limb." },
|
||||
{ roll: 4, label: "Tissue Rejection", desc: "1d5 damage, armour does not apply." },
|
||||
{ roll: 5, label: "Threat Imprint", desc: "Locked on nearest visible target." },
|
||||
{ roll: 6, label: "Full Reversion", desc: "Base form, lose morph bonuses, −1 Instability." }
|
||||
];
|
||||
}
|
||||
data.data.slaSpeciesTraitList = String(superData.sla.speciesNotes?.value ?? "").split(/\n+/).map((entry) => entry.trim()).filter(Boolean);
|
||||
data.data.slaPackageSkillList = String(superData.sla.packageSkills?.value ?? "").split(/\s*,\s*/).map((entry) => entry.trim()).filter(Boolean);
|
||||
@@ -292,6 +332,17 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
disadvantage: String(this._slaTraitPickerSelection?.disadvantage ?? "").trim()
|
||||
};
|
||||
data.data.slaPrometheusStatus = this.actor.getSlaPrometheusStatus?.() ?? { enabled: false, inCombat: false, currentRound: 0, roundsUntilPulse: null, pulseThisRound: false };
|
||||
|
||||
// Contacts
|
||||
const rawContacts = Array.isArray(superData.sla.contacts) ? superData.sla.contacts : [];
|
||||
data.data.slaContacts = rawContacts.map((c) => ({
|
||||
id: String(c.id ?? foundry.utils.randomID()),
|
||||
name: String(c.name ?? "Unknown"),
|
||||
role: String(c.role ?? ""),
|
||||
notes: String(c.notes ?? ""),
|
||||
disposition: ["ally", "neutral", "hostile", "unknown"].includes(c.disposition) ? c.disposition : "neutral"
|
||||
}));
|
||||
data.data.slaContactCount = data.data.slaContacts.length;
|
||||
const traitRows = buildSlaTraitRows(data.data.persTraits ?? []);
|
||||
data.data.persTraitsEnhanced = traitRows;
|
||||
data.data.traitCount = traitRows.length;
|
||||
@@ -406,6 +457,7 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
const armors = [];
|
||||
const conditions = [];
|
||||
const abilities = [];
|
||||
const morphForms = [];
|
||||
const persTraits = [];
|
||||
|
||||
let curWeight = 0;
|
||||
@@ -512,7 +564,11 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
|
||||
conditions.push(i);
|
||||
} else if (i.type === 'ability') {
|
||||
abilities.push(i);
|
||||
if (i.system?.sla?.morphForm) {
|
||||
morphForms.push(i);
|
||||
} else {
|
||||
abilities.push(i);
|
||||
}
|
||||
} else if (i.type === 'persTrait') {
|
||||
persTraits.push(i);
|
||||
}
|
||||
@@ -549,6 +605,9 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
actorData.weapons = weapons;
|
||||
actorData.conditions = conditions;
|
||||
actorData.abilities = abilities;
|
||||
const activeMorphFormName = String(actorData.system?.sla?.morphForm?.value ?? "").trim();
|
||||
morphForms.forEach(f => { f.slaIsActiveMorphForm = f.name === activeMorphFormName; });
|
||||
actorData.slaMorphForms = morphForms;
|
||||
actorData.persTraits = persTraits.sort((left, right) => String(left?.name ?? "").localeCompare(String(right?.name ?? "")));
|
||||
|
||||
}
|
||||
@@ -663,19 +722,26 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
//Quantity adjuster
|
||||
html.on('mousedown', '.item-quantity', ev => {
|
||||
const li = ev.currentTarget.closest(".item");
|
||||
//const item = duplicate(this.actor.getEmbeddedDocument("Item", li.dataset.itemId))
|
||||
var item;
|
||||
item = foundry.utils.duplicate(this.actor.getEmbeddedDocument("Item", li.dataset.itemId));
|
||||
|
||||
let amount = item.system.quantity;
|
||||
const sourceItem = this.actor.getEmbeddedDocument("Item", li.dataset.itemId);
|
||||
if (!sourceItem) return;
|
||||
const item = foundry.utils.duplicate(sourceItem);
|
||||
const amount = Math.max(0, Number(item.system?.quantity ?? 0) || 0);
|
||||
let delta = 0;
|
||||
|
||||
if (event.button == 0) {
|
||||
item.system.quantity = Number(amount) + 1;
|
||||
} else if (event.button == 2) {
|
||||
item.system.quantity = Number(amount) - 1;
|
||||
if (ev.button === 0) {
|
||||
delta = 1;
|
||||
} else if (ev.button === 2) {
|
||||
delta = -1;
|
||||
}
|
||||
|
||||
this.actor.updateEmbeddedDocuments('Item', [item]);
|
||||
if (!delta) return;
|
||||
item.system.quantity = Math.max(0, amount + delta);
|
||||
|
||||
this.actor.updateEmbeddedDocuments('Item', [item]).then(async () => {
|
||||
if (delta > 0) {
|
||||
await this._applySlaQuantityIncreaseDebit(sourceItem, delta);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
//Severity adjuster
|
||||
@@ -760,7 +826,7 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
var item;
|
||||
item = foundry.utils.duplicate(this.actor.getEmbeddedDocument("Item", li.dataset.itemId));
|
||||
|
||||
this.actor.rollCheck(null, null, null, item.name, item.system.bonus, null);
|
||||
this.actor.rollCheck(null, null, null, item.name, item.system.bonus, null, null, { promptModifier: true });
|
||||
});
|
||||
|
||||
html.find('.sla-ebb-skill-roll').click(ev => {
|
||||
@@ -792,7 +858,7 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
//const item = duplicate(this.actor.getEmbeddedDocument("Item", li.dataset.itemId));
|
||||
var item;
|
||||
item = foundry.utils.duplicate(this.actor.getEmbeddedDocument("Item", li.dataset.itemId));
|
||||
this.actor.rollWeaponAttack(item);
|
||||
this.actor.rollWeaponAttack(item, { promptModifier: true });
|
||||
});
|
||||
|
||||
// Rollable Damage
|
||||
@@ -933,8 +999,123 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
this.render(false);
|
||||
});
|
||||
|
||||
html.find('.sla-panic-button').click(ev => {
|
||||
this.actor.rollTable("panicCheck", null, null, null, null, null, null);
|
||||
// SCL fractional adjustment buttons
|
||||
html.find('.sla-scl-adjust').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
const delta = parseFloat(ev.currentTarget.dataset.delta ?? 0);
|
||||
if (!delta) return;
|
||||
const current = parseFloat(String(this.actor.system?.sla?.scl?.value ?? "0").replace(",", ".")) || 0;
|
||||
const next = Math.max(0, Math.round((current + delta) * 10) / 10);
|
||||
const formatted = Number.isInteger(next) ? String(next) : next.toFixed(1);
|
||||
await this.actor.update({ "system.sla.scl.value": formatted });
|
||||
this.render(false);
|
||||
});
|
||||
|
||||
// Session ability tracking — checkbox
|
||||
html.find('.sla-session-ability-used').on('change', async (ev) => {
|
||||
ev.stopPropagation();
|
||||
await this.actor.update({ "system.sla.sessionAbilityUsed": ev.currentTarget.checked });
|
||||
});
|
||||
|
||||
// New Session reset button
|
||||
html.find('.sla-new-session').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
const confirmed = await Dialog.confirm({
|
||||
title: "New Session",
|
||||
content: "<p>Start a new session? This will reset the trauma response session ability for this operative.</p>",
|
||||
defaultYes: true
|
||||
});
|
||||
if (!confirmed) return;
|
||||
await this.actor.update({ "system.sla.sessionAbilityUsed": false });
|
||||
ui.notifications.info(`${this.actor.name}: session ability reset for new session.`);
|
||||
this.render(false);
|
||||
});
|
||||
|
||||
// Rest button — short or long rest dialog
|
||||
html.find('.sla-rest-button').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
const restType = await new Promise((resolve) => {
|
||||
new Dialog({
|
||||
title: "Take a Rest",
|
||||
content: `
|
||||
<p>What kind of rest is <strong>${this.actor.name}</strong> taking?</p>
|
||||
<p><strong>Short Rest:</strong> Removes non-permanent conditions. No stat recovery.</p>
|
||||
<p><strong>Long Rest:</strong> Removes non-permanent conditions and fully restores Flux (if Ebb user).</p>
|
||||
`,
|
||||
buttons: {
|
||||
short: { icon: '<i class="fas fa-moon"></i>', label: "Short Rest", callback: () => resolve("short") },
|
||||
long: { icon: '<i class="fas fa-bed"></i>', label: "Long Rest", callback: () => resolve("long") },
|
||||
cancel: { icon: '<i class="fas fa-times"></i>', label: "Cancel", callback: () => resolve(null) }
|
||||
},
|
||||
default: "short"
|
||||
}).render(true);
|
||||
});
|
||||
if (!restType) return;
|
||||
|
||||
const updates = {};
|
||||
// Remove temporary conditions (items of type "condition")
|
||||
const conditionIds = this.actor.items
|
||||
.filter((item) => item.type === "condition")
|
||||
.map((item) => item.id);
|
||||
if (conditionIds.length > 0) {
|
||||
await this.actor.deleteEmbeddedDocuments("Item", conditionIds);
|
||||
}
|
||||
|
||||
if (restType === "long") {
|
||||
// Restore Flux to max for Ebb users
|
||||
const isEbb = this.actor.isSlaEbbUser?.() ?? false;
|
||||
if (isEbb) {
|
||||
const fluxMax = Math.max(0, Number(this.actor.system?.sla?.flux?.max ?? 0));
|
||||
updates["system.sla.flux.value"] = fluxMax;
|
||||
await this.actor.updateSlaFluxState?.(fluxMax, { save: true });
|
||||
}
|
||||
}
|
||||
|
||||
if (Object.keys(updates).length > 0) {
|
||||
await this.actor.update(updates);
|
||||
}
|
||||
|
||||
const condMsg = conditionIds.length > 0 ? ` Cleared ${conditionIds.length} condition(s).` : "";
|
||||
const fluxMsg = restType === "long" && (this.actor.isSlaEbbUser?.() ?? false) ? " Flux restored." : "";
|
||||
ui.notifications.info(`${this.actor.name}: ${restType === "long" ? "Long" : "Short"} rest complete.${condMsg}${fluxMsg}`);
|
||||
await this.actor.addSlaActivityLog?.(`${restType === "long" ? "Long" : "Short"} rest.${condMsg}${fluxMsg}`);
|
||||
this.render(false);
|
||||
});
|
||||
|
||||
// Contact add button
|
||||
html.find('.sla-contact-add').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
await this._slaContactDialog(null);
|
||||
});
|
||||
|
||||
// Contact edit button
|
||||
html.find('.sla-contact-edit').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
const contactId = String(ev.currentTarget.dataset.contactId ?? "").trim();
|
||||
if (!contactId) return;
|
||||
await this._slaContactDialog(contactId);
|
||||
});
|
||||
|
||||
// Contact delete button
|
||||
html.find('.sla-contact-delete').click(async (ev) => {
|
||||
ev.preventDefault();
|
||||
const contactId = String(ev.currentTarget.dataset.contactId ?? "").trim();
|
||||
if (!contactId) return;
|
||||
const confirmed = await Dialog.confirm({
|
||||
title: "Delete Contact",
|
||||
content: "<p>Remove this contact from the operative's network?</p>",
|
||||
defaultYes: false
|
||||
});
|
||||
if (!confirmed) return;
|
||||
const contacts = Array.isArray(this.actor.system?.sla?.contacts) ? [...this.actor.system.sla.contacts] : [];
|
||||
const updated = contacts.filter((c) => c.id !== contactId);
|
||||
await this.actor.update({ "system.sla.contacts": updated });
|
||||
this.render(false);
|
||||
});
|
||||
|
||||
html.find('.sla-panic-button').click(async ev => {
|
||||
await this.actor.rollTable("panicCheck", null, null, null, null, null, null);
|
||||
await this.actor.addSlaActivityLog?.("Panic check triggered.");
|
||||
});
|
||||
|
||||
html.find('.sla-wound-button').click(ev => {
|
||||
@@ -1068,6 +1249,91 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
|
||||
async _onDrop(event) {
|
||||
const data = TextEditor.getDragEventData(event);
|
||||
if (data?.type !== "Item") return super._onDrop(event);
|
||||
|
||||
const droppedItem = await Item.implementation.fromDropData(data).catch(() => null);
|
||||
if (!droppedItem) return super._onDrop(event);
|
||||
|
||||
if (droppedItem.parent?.uuid === this.actor.uuid) {
|
||||
return super._onDrop(event);
|
||||
}
|
||||
|
||||
const shouldDebitPurchase = !droppedItem.parent || droppedItem.parent.documentName !== "Actor";
|
||||
const itemData = droppedItem.toObject();
|
||||
delete itemData._id;
|
||||
delete itemData.folder;
|
||||
const created = await this.actor.createEmbeddedDocuments("Item", [itemData], {
|
||||
slaPurchaseDebit: true,
|
||||
slaPurchaseSource: data.uuid ?? droppedItem.uuid ?? ""
|
||||
});
|
||||
if (shouldDebitPurchase) {
|
||||
await this._applySlaPurchaseDebit(created);
|
||||
}
|
||||
return created;
|
||||
}
|
||||
|
||||
async _applySlaPurchaseDebit(createdDocs = []) {
|
||||
const documents = Array.isArray(createdDocs) ? createdDocs : [createdDocs];
|
||||
const total = Math.round(documents.reduce((sum, doc) => sum + getPurchasableItemTotalCost(doc?.toObject?.() ?? doc), 0) * 100) / 100;
|
||||
if (!total) return;
|
||||
|
||||
const currentCredits = Number(this.actor.system?.credits?.value ?? 0) || 0;
|
||||
const newCredits = Math.round((currentCredits - total) * 100) / 100;
|
||||
const updateData = { "system.credits.value": newCredits };
|
||||
|
||||
const itemNames = documents.map((doc) => doc?.name).filter(Boolean).join(", ");
|
||||
const ammoDocs = documents
|
||||
.map((doc) => doc?.toObject?.() ?? doc)
|
||||
.filter((doc) => isAmmoPurchaseItem(doc));
|
||||
if (ammoDocs.length) {
|
||||
const stamp = formatSlaTimestamp();
|
||||
const currentLedger = String(this.actor.system?.sla?.ammoLedger?.value ?? "").trim();
|
||||
const purchaseEntries = ammoDocs.map((doc) => {
|
||||
const system = doc?.system ?? doc?.data ?? {};
|
||||
const quantity = Math.max(1, Number(system.quantity ?? 1) || 1);
|
||||
const unitCost = Number(system.cost ?? 0) || 0;
|
||||
const lineCost = Math.round(unitCost * quantity * 100) / 100;
|
||||
return `[${stamp}] PURCHASE | ${doc?.name ?? "Ammo"} | ${quantity} round${quantity === 1 ? "" : "s"} | -${lineCost} cR | balance ${newCredits} cR`;
|
||||
});
|
||||
const ledgerLines = [...purchaseEntries, ...currentLedger.split("\n").filter(Boolean)].slice(0, 60);
|
||||
updateData["system.sla.ammoLedger.value"] = ledgerLines.join("\n");
|
||||
}
|
||||
|
||||
await this.actor.update(updateData);
|
||||
|
||||
ui.notifications.info(`${this.actor.name}: deducted ${total} cR for ${itemNames || "purchased item"}. Credits now ${newCredits} cR.`);
|
||||
await this.actor.addSlaActivityLog?.(`Purchased ${itemNames || "item"} for ${total} cR. Credits now ${newCredits} cR.`);
|
||||
}
|
||||
|
||||
async _applySlaQuantityIncreaseDebit(itemDoc, increase = 0) {
|
||||
const added = Math.max(0, Number(increase ?? 0) || 0);
|
||||
if (!added || !itemDoc) return;
|
||||
|
||||
const unitCost = Number(itemDoc.system?.cost ?? 0) || 0;
|
||||
const total = Math.round(unitCost * added * 100) / 100;
|
||||
if (!total) return;
|
||||
|
||||
const currentCredits = Number(this.actor.system?.credits?.value ?? 0) || 0;
|
||||
const newCredits = Math.round((currentCredits - total) * 100) / 100;
|
||||
const updateData = { "system.credits.value": newCredits };
|
||||
|
||||
if (isAmmoPurchaseItem(itemDoc)) {
|
||||
const stamp = formatSlaTimestamp();
|
||||
const currentLedger = String(this.actor.system?.sla?.ammoLedger?.value ?? "").trim();
|
||||
const entry = `[${stamp}] PURCHASE | ${itemDoc.name ?? "Ammo"} | ${added} round${added === 1 ? "" : "s"} | -${total} cR | balance ${newCredits} cR`;
|
||||
const ledgerLines = [entry, ...currentLedger.split("\n").filter(Boolean)].slice(0, 60);
|
||||
updateData["system.sla.ammoLedger.value"] = ledgerLines.join("\n");
|
||||
}
|
||||
|
||||
await this.actor.update(updateData);
|
||||
ui.notifications.info(`${this.actor.name}: deducted ${total} cR for ${added} more ${itemDoc.name ?? "item"}. Credits now ${newCredits} cR.`);
|
||||
await this.actor.addSlaActivityLog?.(`Purchased +${added} ${itemDoc.name ?? "item"} for ${total} cR. Credits now ${newCredits} cR.`);
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
|
||||
/**
|
||||
* Handle creating a new Owned Item for the actor using initial data defined in the HTML dataset
|
||||
* @param {Event} event The originating click event
|
||||
@@ -1210,6 +1476,76 @@ export class MothershipActorSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Show a dialog for adding or editing a contact
|
||||
* @param {string|null} contactId null = add new, string = edit existing
|
||||
*/
|
||||
async _slaContactDialog(contactId) {
|
||||
const contacts = Array.isArray(this.actor.system?.sla?.contacts) ? [...this.actor.system.sla.contacts] : [];
|
||||
const existing = contactId ? contacts.find((c) => c.id === contactId) : null;
|
||||
const isNew = !existing;
|
||||
|
||||
const name = existing?.name ?? "";
|
||||
const role = existing?.role ?? "";
|
||||
const notes = existing?.notes ?? "";
|
||||
const disposition = existing?.disposition ?? "neutral";
|
||||
|
||||
const content = `
|
||||
<div style="display:grid; gap:8px; padding:8px 0;">
|
||||
<div>
|
||||
<label style="font-size:0.8rem; font-weight:600; display:block; margin-bottom:4px;">Name</label>
|
||||
<input type="text" id="sla-contact-name" value="${name}" placeholder="Contact name" style="width:100%;" />
|
||||
</div>
|
||||
<div>
|
||||
<label style="font-size:0.8rem; font-weight:600; display:block; margin-bottom:4px;">Role / Occupation</label>
|
||||
<input type="text" id="sla-contact-role" value="${role}" placeholder="e.g. Fixer, Fence, Squad medic" style="width:100%;" />
|
||||
</div>
|
||||
<div>
|
||||
<label style="font-size:0.8rem; font-weight:600; display:block; margin-bottom:4px;">Disposition</label>
|
||||
<select id="sla-contact-disposition" style="width:100%;">
|
||||
<option value="ally" ${disposition === "ally" ? "selected" : ""}>Ally</option>
|
||||
<option value="neutral" ${disposition === "neutral" ? "selected" : ""}>Neutral</option>
|
||||
<option value="hostile" ${disposition === "hostile" ? "selected" : ""}>Hostile</option>
|
||||
<option value="unknown" ${disposition === "unknown" ? "selected" : ""}>Unknown</option>
|
||||
</select>
|
||||
</div>
|
||||
<div>
|
||||
<label style="font-size:0.8rem; font-weight:600; display:block; margin-bottom:4px;">Notes</label>
|
||||
<textarea id="sla-contact-notes" rows="3" placeholder="Sector, history, how they know the operative..." style="width:100%;">${notes}</textarea>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
const result = await Dialog.prompt({
|
||||
title: isNew ? "Add Contact" : "Edit Contact",
|
||||
content,
|
||||
label: isNew ? "Add" : "Save",
|
||||
callback: (html) => {
|
||||
const nameVal = String(html.find("#sla-contact-name").val() ?? "").trim();
|
||||
if (!nameVal) return null;
|
||||
return {
|
||||
id: existing?.id ?? foundry.utils.randomID(),
|
||||
name: nameVal,
|
||||
role: String(html.find("#sla-contact-role").val() ?? "").trim(),
|
||||
disposition: String(html.find("#sla-contact-disposition").val() ?? "neutral"),
|
||||
notes: String(html.find("#sla-contact-notes").val() ?? "").trim()
|
||||
};
|
||||
},
|
||||
rejectClose: false
|
||||
});
|
||||
|
||||
if (!result) return;
|
||||
|
||||
let updated;
|
||||
if (isNew) {
|
||||
updated = [...contacts, result];
|
||||
} else {
|
||||
updated = contacts.map((c) => c.id === contactId ? result : c);
|
||||
}
|
||||
await this.actor.update({ "system.sla.contacts": updated });
|
||||
this.render(false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Extend and override the sheet header buttons
|
||||
* @override
|
||||
|
||||
@@ -4,6 +4,21 @@ import { SLADrugSystem } from "../sla-drug-system.js";
|
||||
import { SLA_SPECIES_BALANCE_VERSION, getSlaSpeciesStatAdjustments } from "../sla-species-balance.js";
|
||||
import { buildSlaTraumaResponseText } from "../sla-trauma.js";
|
||||
|
||||
// Global event delegation to handle interactive range slider value updates
|
||||
// in a way that is fully compatible with Foundry VTT's HTML sanitization.
|
||||
if (typeof document !== "undefined") {
|
||||
document.addEventListener("input", (event) => {
|
||||
const target = event.target;
|
||||
if (target && target.tagName === "INPUT" && target.name === "rollModifier") {
|
||||
const value = Number(target.value) || 0;
|
||||
const label = target.closest(".resource")?.querySelector(".slider-value");
|
||||
if (label) {
|
||||
label.innerText = (value >= 0 ? "+" : "") + value;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
const SLA_AMMO_TYPES = {
|
||||
STD: { label: "Standard", multiplier: 1, damageBonus: "", woundEffect: "", summary: "Standard ammunition." },
|
||||
AP: { label: "AP", multiplier: 2, damageBonus: "-1", woundEffect: "Gunshot [-]", summary: "Armour-piercing ammunition. Treat target armour as halved and reduce damage by 1." },
|
||||
@@ -402,14 +417,6 @@ export class MothershipActor extends Actor {
|
||||
// Prepare Character type specific data
|
||||
_deriveCharacter() {
|
||||
const system = this.system;
|
||||
//clamp stress.value to stress.min so stale stored values never show below the floor
|
||||
if (system.other?.stress) {
|
||||
const stressMin = Number(system.other.stress.min ?? 0);
|
||||
const stressVal = Number(system.other.stress.value ?? 0);
|
||||
if (Number.isFinite(stressMin) && Number.isFinite(stressVal) && stressVal < stressMin) {
|
||||
system.other.stress.value = stressMin;
|
||||
}
|
||||
}
|
||||
//armor points + damage reduction
|
||||
//init vars
|
||||
let armorPoints = 0;
|
||||
@@ -607,9 +614,123 @@ export class MothershipActor extends Actor {
|
||||
return rollStringParsed;
|
||||
}
|
||||
|
||||
clampSlaRollTarget(rollTarget, rollString = "") {
|
||||
const numericTarget = Number(rollTarget);
|
||||
if (!Number.isFinite(numericTarget)) return rollTarget;
|
||||
const usesD100 = String(rollString ?? "").includes("1d100");
|
||||
if (!usesD100) return numericTarget;
|
||||
return Math.min(98, numericTarget);
|
||||
}
|
||||
|
||||
isSlaAutomaticFailure(total, rollString = "") {
|
||||
const numericTotal = Number(total);
|
||||
if (!Number.isFinite(numericTotal)) return false;
|
||||
const usesD100 = String(rollString ?? "").includes("1d100");
|
||||
return usesD100 && numericTotal === 99;
|
||||
}
|
||||
|
||||
getSlaChatVariant(context = {}) {
|
||||
const actorClass = String(this.system?.class?.value ?? "").trim();
|
||||
const employer = String(this.system?.sla?.employer?.value ?? "").trim();
|
||||
const sector = String(this.system?.sla?.sector?.value ?? "").trim();
|
||||
const skill = String(context?.skill ?? "").trim();
|
||||
const skillCategory = String(context?.skillCategory ?? "").trim();
|
||||
const tableName = String(context?.tableName ?? "").trim();
|
||||
const header = String(context?.msgHeader ?? "").trim();
|
||||
const weaponName = String(context?.weapon?.name ?? "").trim();
|
||||
const itemName = String(context?.item?.name ?? "").trim();
|
||||
const extra = String(context?.extra ?? "").trim();
|
||||
|
||||
const haystack = [
|
||||
actorClass,
|
||||
employer,
|
||||
sector,
|
||||
skill,
|
||||
skillCategory,
|
||||
tableName,
|
||||
header,
|
||||
weaponName,
|
||||
itemName,
|
||||
extra
|
||||
].join(" ").toLowerCase();
|
||||
|
||||
if (context?.isSlaEbbSkill || /\bebb\b|ebon|brain\swaste|flux|telekinesis|blast|awareness/.test(haystack)) {
|
||||
return { key: "ebb", label: "Ebb", emblem: "EBB" };
|
||||
}
|
||||
if (/\bdark\s?night\b/.test(haystack)) {
|
||||
return { key: "darknight", label: "DarkNight", emblem: "DN" };
|
||||
}
|
||||
if (/\bshiver\b/.test(haystack)) {
|
||||
return { key: "shiver", label: "Shiver", emblem: "SV" };
|
||||
}
|
||||
if (/\bmort\b|mortuary|undertaker|corpse|cadaver/.test(haystack)) {
|
||||
return { key: "mort", label: "Mort", emblem: "MT" };
|
||||
}
|
||||
if (/\btek\b|technical|engineer|engineering|medic|medical|science|research/.test(haystack)) {
|
||||
return { key: "tek", label: "Tek", emblem: "TK" };
|
||||
}
|
||||
if (/\bops\b|operations|opscon|ops\scon|operative|squad/.test(haystack)) {
|
||||
return { key: "ops", label: "Ops", emblem: "OP" };
|
||||
}
|
||||
return { key: "sla", label: "SLA", emblem: "SLA" };
|
||||
}
|
||||
|
||||
getSlaSeverityMeta({ severity = null, tableName = "", specialRoll = "", tableResultNumber = null } = {}) {
|
||||
const rawSeverity = Number(severity);
|
||||
if (Number.isFinite(rawSeverity)) {
|
||||
if (rawSeverity >= 5) return { key: "critical", label: "Critical", cssClass: "sla-severity-critical" };
|
||||
if (rawSeverity >= 3) return { key: "severe", label: "Severe", cssClass: "sla-severity-severe" };
|
||||
return { key: "minor", label: "Minor", cssClass: "sla-severity-minor" };
|
||||
}
|
||||
|
||||
const name = String(tableName ?? "").toLowerCase();
|
||||
const special = String(specialRoll ?? "").toLowerCase();
|
||||
const numericResult = Number(tableResultNumber);
|
||||
|
||||
if (!Number.isFinite(numericResult)) {
|
||||
return { key: "minor", label: "Minor", cssClass: "sla-severity-minor" };
|
||||
}
|
||||
|
||||
const isPanic = special === "paniccheck" || name.includes("panic");
|
||||
const isWound = name.includes("wound");
|
||||
|
||||
if (isPanic) {
|
||||
if (numericResult >= 16) return { key: "critical", label: "Catastrophic", cssClass: "sla-severity-critical" };
|
||||
if (numericResult >= 9) return { key: "severe", label: "Severe", cssClass: "sla-severity-severe" };
|
||||
return { key: "minor", label: "Minor", cssClass: "sla-severity-minor" };
|
||||
}
|
||||
|
||||
if (isWound) {
|
||||
if (numericResult >= 8) return { key: "critical", label: "Critical", cssClass: "sla-severity-critical" };
|
||||
if (numericResult >= 4) return { key: "severe", label: "Severe", cssClass: "sla-severity-severe" };
|
||||
return { key: "minor", label: "Minor", cssClass: "sla-severity-minor" };
|
||||
}
|
||||
|
||||
return { key: "minor", label: "Minor", cssClass: "sla-severity-minor" };
|
||||
}
|
||||
|
||||
async addSlaActivityLog(entry, { maxEntries = 40 } = {}) {
|
||||
const text = String(entry ?? "").trim();
|
||||
if (!text || this.type !== "character") return null;
|
||||
|
||||
const timestamp = new Date().toLocaleString("en-GB", {
|
||||
day: "2-digit",
|
||||
month: "2-digit",
|
||||
year: "2-digit",
|
||||
hour: "2-digit",
|
||||
minute: "2-digit"
|
||||
});
|
||||
const currentLog = String(this.system?.sla?.activityLog?.value ?? "").trim();
|
||||
const existingLines = currentLog ? currentLog.split("\n").filter(Boolean) : [];
|
||||
const nextLines = [`[${timestamp}] ${text}`, ...existingLines].slice(0, Math.max(1, maxEntries));
|
||||
await this.update({ "system.sla.activityLog.value": nextLines.join("\n") });
|
||||
return nextLines[0];
|
||||
}
|
||||
|
||||
//central roll parsing function | TAKES '1d100',[Foundry roll object],true,true,41,'<' | RETURNS enriched Foundry roll object
|
||||
parseRollResult(rollString, rollResult, zeroBased, checkCrit, rollTarget, comparison, specialRoll) {
|
||||
//init vars
|
||||
rollTarget = this.clampSlaRollTarget(rollTarget, rollString);
|
||||
let doubles = new Set([0, 11, 22, 33, 44, 55, 66, 77, 88, 99]);
|
||||
let enrichedRollResult = rollResult;
|
||||
let rollFormula = enrichedRollResult.formula;
|
||||
@@ -678,29 +799,29 @@ export class MothershipActor extends Actor {
|
||||
if (rollString.includes("[")) {
|
||||
//set whether each die succeeded
|
||||
//die 0
|
||||
if (comparison === '<' && die0value < rollTarget && die0value < 90) {
|
||||
if (comparison === '<' && die0value < rollTarget && !this.isSlaAutomaticFailure(die0value, rollString)) {
|
||||
die0success = true;
|
||||
}
|
||||
if (comparison === '<=' && die0value <= rollTarget && die0value < 90) {
|
||||
if (comparison === '<=' && die0value <= rollTarget && !this.isSlaAutomaticFailure(die0value, rollString)) {
|
||||
die0success = true;
|
||||
}
|
||||
if (comparison === '>' && die0value > rollTarget && die0value < 90) {
|
||||
if (comparison === '>' && die0value > rollTarget && !this.isSlaAutomaticFailure(die0value, rollString)) {
|
||||
die0success = true;
|
||||
}
|
||||
if (comparison === '>=' && die0value >= rollTarget && die0value < 90) {
|
||||
if (comparison === '>=' && die0value >= rollTarget && !this.isSlaAutomaticFailure(die0value, rollString)) {
|
||||
die0success = true;
|
||||
}
|
||||
//die 1
|
||||
if (comparison === '<' && die1value < rollTarget && die1value < 90) {
|
||||
if (comparison === '<' && die1value < rollTarget && !this.isSlaAutomaticFailure(die1value, rollString)) {
|
||||
die1success = true;
|
||||
}
|
||||
if (comparison === '<=' && die1value <= rollTarget && die1value < 90) {
|
||||
if (comparison === '<=' && die1value <= rollTarget && !this.isSlaAutomaticFailure(die1value, rollString)) {
|
||||
die1success = true;
|
||||
}
|
||||
if (comparison === '>' && die1value > rollTarget && die1value < 90) {
|
||||
if (comparison === '>' && die1value > rollTarget && !this.isSlaAutomaticFailure(die1value, rollString)) {
|
||||
die1success = true;
|
||||
}
|
||||
if (comparison === '>=' && die1value >= rollTarget && die1value < 90) {
|
||||
if (comparison === '>=' && die1value >= rollTarget && !this.isSlaAutomaticFailure(die1value, rollString)) {
|
||||
die1success = true;
|
||||
}
|
||||
//set whether each die are a crit
|
||||
@@ -842,8 +963,8 @@ export class MothershipActor extends Actor {
|
||||
//add data point: detect success/failure
|
||||
if (rollTarget || rollTarget === 0) {
|
||||
//check for auto failure
|
||||
if (enrichedRollResult.total >= 90) {
|
||||
//result >= 90 is a failure
|
||||
if (this.isSlaAutomaticFailure(enrichedRollResult.total, rollString)) {
|
||||
// result 99 on d100 is always a failure
|
||||
enrichedRollResult.success = false;
|
||||
} else {
|
||||
//compare values based on compararison setting
|
||||
@@ -918,7 +1039,7 @@ export class MothershipActor extends Actor {
|
||||
compareIcon = '<i class="fas fa-greater-than-equal"></i>';
|
||||
}
|
||||
//prepare formula
|
||||
if (rollTarget) {
|
||||
if (rollTarget || rollTarget === 0) {
|
||||
//show dice against target
|
||||
diceFormula = rollString + ' ' + compareIcon + ' ' + rollTarget;
|
||||
} else {
|
||||
@@ -1311,27 +1432,27 @@ export class MothershipActor extends Actor {
|
||||
}
|
||||
//append Calm effects for Critical Panic Failure
|
||||
if (useCalm && !parsedRollResult.success && parsedRollResult.critical) {
|
||||
tableResultFooter = `<br><br>You lose 1d10 Calm because you critically failed.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}`;
|
||||
tableResultFooter = `<br><br>You lose 1d10 Calm because you critically failed.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}`;
|
||||
}
|
||||
//append effects for Stress + Maintenance Check Failure
|
||||
if (specialRoll === 'maintenanceCheck' && !useCalm && !parsedRollResult.success && !parsedRollResult.critical) {
|
||||
tableResultFooter = `<br><br>Everyone on board the ship takes 1 Stress.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.dvJR9DYXI2kV0BbR]{+1 Stress}`;
|
||||
tableResultFooter = `<br><br>Everyone on board the ship takes 1 Stress.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.dvJR9DYXI2kV0BbR]{+1 Stress}`;
|
||||
}
|
||||
//append effects for Stress + Critical Maintenance Check Failure
|
||||
if (specialRoll === 'maintenanceCheck' && !useCalm && !parsedRollResult.success && parsedRollResult.critical) {
|
||||
tableResultFooter = `<br><br>Everyone on board the ship takes 1 Stress. You must roll for another maintenance issue because you critically failed.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.dvJR9DYXI2kV0BbR]{+1 Stress}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.hRapiXGVW8WZQH12]{Roll for Maintenance Issue}`;
|
||||
tableResultFooter = `<br><br>Everyone on board the ship takes 1 Stress. You must roll for another maintenance issue because you critically failed.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.dvJR9DYXI2kV0BbR]{+1 Stress}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.hRapiXGVW8WZQH12]{Roll for Maintenance Issue}`;
|
||||
}
|
||||
//append effects for Calm + Maintenance Check Failure
|
||||
if (specialRoll === 'maintenanceCheck' && useCalm && !parsedRollResult.success && !parsedRollResult.critical) {
|
||||
tableResultFooter = `<br><br>Everyone on board the ship loses 1d10 Calm.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}`;
|
||||
tableResultFooter = `<br><br>Everyone on board the ship loses 1d10 Calm.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}`;
|
||||
}
|
||||
//append effects for Calm + Critical Maintenance Check Failure
|
||||
if (specialRoll === 'maintenanceCheck' && useCalm && !parsedRollResult.success && parsedRollResult.critical) {
|
||||
tableResultFooter = `<br><br>Everyone on board the ship loses 1d10 Calm. You must roll for another maintenance issue because you critically failed.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.hRapiXGVW8WZQH12]{Roll for Maintenance Issue}`;
|
||||
tableResultFooter = `<br><br>Everyone on board the ship loses 1d10 Calm. You must roll for another maintenance issue because you critically failed.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.jHyqXb2yDFTNWxpy]{-1d10 Calm}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.hRapiXGVW8WZQH12]{Roll for Maintenance Issue}`;
|
||||
}
|
||||
//append effects for Calm + Critical Maintenance Check Success
|
||||
if (specialRoll === 'maintenanceCheck' && useCalm && parsedRollResult.success && parsedRollResult.critical) {
|
||||
flavorText = flavorText + ` Gain 1d10 Calm.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.k2TtLFOG9mGaWVx3]{+1d10 Calm}`;
|
||||
flavorText = flavorText + ` Gain 1d10 Calm.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.k2TtLFOG9mGaWVx3]{+1d10 Calm}`;
|
||||
}
|
||||
//set table result type (using first value)
|
||||
if (tableResult[0].type === 0 || tableResult[0].type === 'text') {
|
||||
@@ -1343,6 +1464,12 @@ export class MothershipActor extends Actor {
|
||||
}
|
||||
//generate chat message
|
||||
//prepare data
|
||||
const severityMeta = this.getSlaSeverityMeta({
|
||||
tableName,
|
||||
specialRoll,
|
||||
tableResultNumber
|
||||
});
|
||||
|
||||
let messageData = {
|
||||
actor: this,
|
||||
tableResult: tableResult,
|
||||
@@ -1357,7 +1484,14 @@ export class MothershipActor extends Actor {
|
||||
woundText: woundText,
|
||||
secondRoll: secondRoll,
|
||||
parsedRollResult2: parsedRollResult2,
|
||||
specialRoll: specialRoll
|
||||
specialRoll: specialRoll,
|
||||
severityMeta: severityMeta,
|
||||
chatStyle: this.getSlaChatVariant({
|
||||
tableName,
|
||||
msgHeader: tableName,
|
||||
isSlaEbbSkill: false,
|
||||
extra: specialRoll
|
||||
})
|
||||
};
|
||||
//prepare template
|
||||
messageTemplate = 'systems/sla-mothership/templates/chat/rollTable.html';
|
||||
@@ -1376,6 +1510,7 @@ export class MothershipActor extends Actor {
|
||||
}, {
|
||||
keepId: true
|
||||
});
|
||||
await this.addSlaActivityLog?.(`${tableName}: ${parsedRollResult.success ? "success" : "failure"} on ${rollString}${tableResultNumber !== null ? ` -> ${tableResultNumber}` : ""}.`);
|
||||
if (game.modules.get("dice-so-nice") && game.modules.get("dice-so-nice").active) {
|
||||
//log what was done
|
||||
slaDebug(`Rolled on table ID: ${tableId}, with: rollString:${rollString}, aimFor:${aimFor}, zeroBased:${zeroBased}, checkCrit:${checkCrit}, rollAgainst:${rollAgainst}, comparison:${comparison}`);
|
||||
@@ -1609,8 +1744,6 @@ export class MothershipActor extends Actor {
|
||||
let skillList = ``;
|
||||
//create skill counter
|
||||
let skillCount = 0;
|
||||
//create dialog pixel counter
|
||||
let dialogHeight = 232;
|
||||
//loop through and create skill rows
|
||||
const filteredSkills = playerItems.filter((item) => item.type === "skill" && this.isSkillRelevantForContext(item, context));
|
||||
const skillSource = filteredSkills.length
|
||||
@@ -1638,13 +1771,9 @@ export class MothershipActor extends Actor {
|
||||
skillList = skillList + tempRow;
|
||||
//increment skill count
|
||||
skillCount++;
|
||||
//increment pixel counter
|
||||
dialogHeight = dialogHeight + 77;
|
||||
}
|
||||
//check if there are no skills, and adjust prompt height accordingly
|
||||
//check if there are no skills
|
||||
if (skillCount === 0) {
|
||||
//set window height
|
||||
dialogHeight = 170;
|
||||
skillList = `<div class="macro_window"><div class="macro_desc" style="padding: 12px 14px;">${requiresCombatSkills ? "No combat-tagged skills are available for this action." : "No matching skills are available for this action."}</div></div>`;
|
||||
}
|
||||
//create button header if needed
|
||||
@@ -1653,12 +1782,24 @@ export class MothershipActor extends Actor {
|
||||
} else {
|
||||
buttonDesc = ``;
|
||||
}
|
||||
//wrap skill list in a scrollable container so long lists don't push buttons off-screen
|
||||
const scrollableSkillList = `<div class="sla-skill-scroll-list" style="max-height: 340px; overflow-y: auto; padding-right: 4px; margin-bottom: 4px;">${skillList}</div>`;
|
||||
//create final dialog data
|
||||
const showModifier = !foundry.utils.hasProperty(context.attackContext ?? {}, "rollModifier");
|
||||
const modifierHtml = showModifier ? `
|
||||
<div class="resource" style="margin-top: 15px; margin-bottom: 10px; border-top: 1px dashed rgba(255,255,255,0.15); padding-top: 10px; padding-left: 10px; padding-right: 10px;">
|
||||
<label class="resource-label" style="display: flex; justify-content: space-between; font-weight: bold; margin-bottom: 8px;">
|
||||
<span>Roll Modifier</span>
|
||||
<span class="slider-value" style="font-weight: bold; color: #cc2828;">0</span>
|
||||
</label>
|
||||
<input type="range" name="rollModifier" min="-30" max="30" step="10" value="0" style="width: 100%; cursor: pointer; accent-color: #cc2828;" oninput="this.previousElementSibling.querySelector('.slider-value').innerText = (this.value >= 0 ? '+' : '') + this.value">
|
||||
</div>
|
||||
` : "";
|
||||
const dialogData = {
|
||||
window: {title: dlgTitle},
|
||||
classes: ["macro-popup-dialog"],
|
||||
position: {width: 600},
|
||||
content: skillHeader + `<div class="skill-dialog-scroll">${skillList}</div>` + buttonDesc,
|
||||
content: skillHeader + scrollableSkillList + modifierHtml + buttonDesc,
|
||||
buttons: []
|
||||
};
|
||||
//add adv/normal/dis buttons if we need a rollString
|
||||
@@ -1672,8 +1813,9 @@ export class MothershipActor extends Actor {
|
||||
rollString = `1d100 [+]`;
|
||||
skill = button.form.querySelector("input[name='skill']:checked")?.getAttribute("id");
|
||||
skillValue = button.form.querySelector("input[name='skill']:checked")?.getAttribute("value");
|
||||
resolve([rollString, skill, skillValue]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}`);
|
||||
const rollModifier = showModifier ? (Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0) : (Number(context.attackContext?.rollModifier ?? 0) || 0);
|
||||
resolve([rollString, skill, skillValue, rollModifier]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-angle-double-up`
|
||||
},
|
||||
@@ -1684,8 +1826,9 @@ export class MothershipActor extends Actor {
|
||||
rollString = `1d100`;
|
||||
skill = button.form.querySelector("input[name='skill']:checked")?.getAttribute("id");
|
||||
skillValue = button.form.querySelector("input[name='skill']:checked")?.getAttribute("value");
|
||||
resolve([rollString, skill, skillValue]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}`);
|
||||
const rollModifier = showModifier ? (Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0) : (Number(context.attackContext?.rollModifier ?? 0) || 0);
|
||||
resolve([rollString, skill, skillValue, rollModifier]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-minus`
|
||||
},
|
||||
@@ -1696,8 +1839,9 @@ export class MothershipActor extends Actor {
|
||||
rollString = `1d100 [-]`;
|
||||
skill = button.form.querySelector("input[name='skill']:checked")?.getAttribute("id");
|
||||
skillValue = button.form.querySelector("input[name='skill']:checked")?.getAttribute("value");
|
||||
resolve([rollString, skill, skillValue]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}`);
|
||||
const rollModifier = showModifier ? (Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0) : (Number(context.attackContext?.rollModifier ?? 0) || 0);
|
||||
resolve([rollString, skill, skillValue, rollModifier]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-angle-double-down`
|
||||
}
|
||||
@@ -1711,8 +1855,9 @@ export class MothershipActor extends Actor {
|
||||
callback: (event, button, dialog) => {
|
||||
skill = button.form.querySelector("input[name='skill']:checked")?.getAttribute("id");
|
||||
skillValue = button.form.querySelector("input[name='skill']:checked")?.getAttribute("value");
|
||||
resolve([rollString, skill, skillValue]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}`);
|
||||
const rollModifier = showModifier ? (Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0) : (Number(context.attackContext?.rollModifier ?? 0) || 0);
|
||||
resolve([rollString, skill, skillValue, rollModifier]);
|
||||
slaDebug(`User left the chooseSkill dialog with: rollString:${rollString}, skill:${skill}, skillValue:${skillValue}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-chevron-circle-right`
|
||||
}
|
||||
@@ -1733,19 +1878,29 @@ export class MothershipActor extends Actor {
|
||||
let dieAdv = die + ` [+]`;
|
||||
let dieDis = die + ` [-]`;
|
||||
//create final dialog data
|
||||
const modifierHtml = `
|
||||
<div class="resource" style="margin-top: 15px; margin-bottom: 10px; border-top: 1px dashed rgba(255,255,255,0.15); padding-top: 10px; padding-left: 10px; padding-right: 10px;">
|
||||
<label class="resource-label" style="display: flex; justify-content: space-between; font-weight: bold; margin-bottom: 8px;">
|
||||
<span>Roll Modifier</span>
|
||||
<span class="slider-value" style="font-weight: bold; color: #cc2828;">0</span>
|
||||
</label>
|
||||
<input type="range" name="rollModifier" min="-30" max="30" step="10" value="0" style="width: 100%; cursor: pointer; accent-color: #cc2828;" oninput="this.previousElementSibling.querySelector('.slider-value').innerText = (this.value >= 0 ? '+' : '') + this.value">
|
||||
</div>
|
||||
`;
|
||||
const dialogData = {
|
||||
window: {title: dlgTitle},
|
||||
classes: ["macro-popup-dialog"],
|
||||
position: {width: 600},
|
||||
content: `<div class="macro_prompt">` + game.i18n.localize("Mosh.SelectYourRollType") + `:</div>`,
|
||||
content: `<form style="padding: 5px 10px;"><div class="macro_prompt" style="margin-bottom:10px;">` + game.i18n.localize("Mosh.SelectYourRollType") + `:</div>` + modifierHtml + `</form>`,
|
||||
buttons: [
|
||||
{
|
||||
label: game.i18n.localize("Mosh.Advantage"),
|
||||
action: `action_advantage`,
|
||||
callback: (event, button, dialog) => {
|
||||
rollString = dieAdv;
|
||||
resolve([rollString]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}`);
|
||||
const rollModifier = Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0;
|
||||
resolve([rollString, rollModifier]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-angle-double-up`
|
||||
},
|
||||
@@ -1754,8 +1909,9 @@ export class MothershipActor extends Actor {
|
||||
action: `action_normal`,
|
||||
callback: (event, button, dialog) => {
|
||||
rollString = die;
|
||||
resolve([rollString]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}`);
|
||||
const rollModifier = Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0;
|
||||
resolve([rollString, rollModifier]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-minus`
|
||||
},
|
||||
@@ -1764,8 +1920,9 @@ export class MothershipActor extends Actor {
|
||||
action: `action_disadvantage`,
|
||||
callback: (event, button, dialog) => {
|
||||
rollString = dieDis;
|
||||
resolve([rollString]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}`);
|
||||
const rollModifier = Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0;
|
||||
resolve([rollString, rollModifier]);
|
||||
slaDebug(`User left the chooseAdvantage dialog with: rollString:${rollString}, modifier:${rollModifier}`);
|
||||
},
|
||||
icon: `fas fa-angle-double-down`
|
||||
}
|
||||
@@ -1874,19 +2031,29 @@ export class MothershipActor extends Actor {
|
||||
if (rawFormula === "Str/10") {
|
||||
rawFormula = `floor((${this.system.stats.strength.value} + ${(Number(this.system.stats.strength.mod) || 0)}) / 10)`;
|
||||
}
|
||||
const mult = Number(weapon?.system?.sla?.damageMultiplier ?? weapon?.system?.damageMultiplier ?? 1) || 1;
|
||||
if (mult > 1) {
|
||||
if (/^\d+d\d+/i.test(rawFormula)) {
|
||||
rawFormula = rawFormula.replace(/^(\d+)(d\d+)/i, (match, dice, rest) => {
|
||||
return `${Number(dice) * mult}${rest}`;
|
||||
});
|
||||
} else {
|
||||
rawFormula = `(${rawFormula}) * ${mult}`;
|
||||
}
|
||||
}
|
||||
const critDamageMode = game.settings.get('sla-mothership', 'critDamage');
|
||||
|
||||
if (isCritical) {
|
||||
if (critDamageMode === 'advantage') {
|
||||
rawFormula = `{${parsedDamageString},${parsedDamageString}}kh`;
|
||||
rawFormula = `{${rawFormula},${rawFormula}}kh`;
|
||||
} else if (critDamageMode === 'doubleDamage') {
|
||||
rawFormula = `(${parsedDamageString}) * 2`;
|
||||
rawFormula = `(${rawFormula}) * 2`;
|
||||
} else if (critDamageMode === 'doubleDice') {
|
||||
rawFormula = `${parsedDamageString} + ${parsedDamageString}`;
|
||||
rawFormula = `${rawFormula} + ${rawFormula}`;
|
||||
} else if (critDamageMode === 'maxDamage') {
|
||||
rawFormula = parsedDamageString.replaceAll('d', ' * ');
|
||||
rawFormula = rawFormula.replaceAll('d', ' * ');
|
||||
} else if (critDamageMode === 'weaponValue') {
|
||||
rawFormula = `${parsedDamageString} + ${weapon?.system?.critDmg || 0}`;
|
||||
rawFormula = `${rawFormula} + ${weapon?.system?.critDmg || 0}`;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2358,6 +2525,9 @@ export class MothershipActor extends Actor {
|
||||
rollString = chosenSkills[0];
|
||||
skill = chosenSkills[1];
|
||||
skillValue = chosenSkills[2];
|
||||
if (chosenSkills[3] !== undefined) {
|
||||
attackContext.rollModifier = chosenSkills[3];
|
||||
}
|
||||
}
|
||||
//if rollString is STILL blank, redirect player to choose the roll
|
||||
if (!rollString) {
|
||||
@@ -2365,6 +2535,9 @@ export class MothershipActor extends Actor {
|
||||
let chosenRollType = await this.chooseAdvantage(this.system.stats[attribute].rollLabel, '1d100');
|
||||
//set variables
|
||||
rollString = chosenRollType[0];
|
||||
if (chosenRollType[1] !== undefined) {
|
||||
attackContext.rollModifier = chosenRollType[1];
|
||||
}
|
||||
}
|
||||
//if this is a weapon roll
|
||||
if (weapon) {
|
||||
@@ -2424,7 +2597,15 @@ export class MothershipActor extends Actor {
|
||||
//if this is a damage roll
|
||||
if (specialRoll === 'damage') {
|
||||
//parse the roll string
|
||||
let damageRollString = weapon.system.damage
|
||||
let damageRollString = weapon.system.damage;
|
||||
if (weapon && !overrideDamagaRollString) {
|
||||
const mult = Number(weapon.system?.sla?.damageMultiplier ?? weapon.system?.damageMultiplier ?? 1) || 1;
|
||||
if (mult > 1) {
|
||||
damageRollString = damageRollString.replace(/^(\d+)(d\d+)/i, (match, dice, rest) => {
|
||||
return `${Number(dice) * mult}${rest}`;
|
||||
});
|
||||
}
|
||||
}
|
||||
if(overrideDamagaRollString){
|
||||
damageRollString = overrideDamagaRollString;
|
||||
}
|
||||
@@ -2443,8 +2624,10 @@ export class MothershipActor extends Actor {
|
||||
}
|
||||
//prepare flavortext
|
||||
if (weapon.system.damage === "Str/10" && this.type === 'character') {
|
||||
const mult = Number(weapon.system?.sla?.damageMultiplier ?? weapon.system?.damageMultiplier ?? 1) || 1;
|
||||
const multStr = mult > 1 ? `${mult} * ` : '';
|
||||
//determine the damage string
|
||||
flavorText = 'You strike your target for <strong>[[floor((' + this.system.stats.strength.value + ' + ' + (Number(this.system.stats.strength.mod) || 0) + ')/10)]] damage</strong>.';
|
||||
flavorText = 'You strike your target for <strong>[[' + multStr + 'floor((' + this.system.stats.strength.value + ' + ' + (Number(this.system.stats.strength.mod) || 0) + ')/10)]] damage</strong>.';
|
||||
} else {
|
||||
flavorText = 'You inflict [[' + parsedDamageString + '[' + dsnTheme + ']' + critMod + ']] points of damage.';
|
||||
}
|
||||
@@ -2480,7 +2663,13 @@ export class MothershipActor extends Actor {
|
||||
targetingResult: targetingResult,
|
||||
needsDesc: needsDesc,
|
||||
woundEffect: woundEffect,
|
||||
specialRoll: specialRoll
|
||||
specialRoll: specialRoll,
|
||||
chatStyle: this.getSlaChatVariant({
|
||||
weapon,
|
||||
msgHeader,
|
||||
isSlaEbbSkill: false,
|
||||
extra: ammoContext?.label ?? ""
|
||||
})
|
||||
};
|
||||
let chatData = {
|
||||
user: game.user.id,
|
||||
@@ -2495,6 +2684,7 @@ export class MothershipActor extends Actor {
|
||||
const content = await foundry.applications.handlebars.renderTemplate(template, messageData);
|
||||
chatData.content = content;
|
||||
await ChatMessage.create(chatData);
|
||||
await this.addSlaActivityLog?.(`${weapon.name}: damage roll resolved.${targetingResult ? ` ${targetingResult.targetName} took ${targetingResult.finalDamage} damage.` : ""}`);
|
||||
//log what was done
|
||||
console.log(`Rolled damage on:${weapon.name}`);
|
||||
//return messageData
|
||||
@@ -2512,6 +2702,25 @@ export class MothershipActor extends Actor {
|
||||
} else {
|
||||
rollTarget = rollTargetOverride;
|
||||
}
|
||||
const modifier = Number(attackContext?.rollModifier ?? 0) || 0;
|
||||
if (modifier) {
|
||||
rollTarget += modifier;
|
||||
if (effectiveRollBreakdown) {
|
||||
effectiveRollBreakdown.parts.push({
|
||||
label: "Roll Modifier",
|
||||
value: modifier
|
||||
});
|
||||
effectiveRollBreakdown.total += modifier;
|
||||
effectiveRollBreakdown.formulaText += ` ${modifier >= 0 ? "+" : ""}${modifier}`;
|
||||
}
|
||||
}
|
||||
rollTarget = this.clampSlaRollTarget(rollTarget, rollString);
|
||||
if (effectiveRollBreakdown && (String(rollString ?? "").includes("1d100"))) {
|
||||
effectiveRollBreakdown = {
|
||||
...effectiveRollBreakdown,
|
||||
total: rollTarget
|
||||
};
|
||||
}
|
||||
//roll the dice
|
||||
//parse the roll string
|
||||
let parsedRollString = this.parseRollString(rollString, aimFor);
|
||||
@@ -2674,9 +2883,9 @@ export class MothershipActor extends Actor {
|
||||
}
|
||||
if (ammoUsage) {
|
||||
const roundLabel = ammoUsage.shots === 1 ? 'round' : 'rounds';
|
||||
const ammoPrefix = `<strong>${ammoUsage.label}</strong> fire with <strong>${ammoUsage.ammoLabel}</strong> spent <strong>${ammoUsage.shots}</strong> ${roundLabel}. Magazine <strong>${ammoUsage.loaded}/${weapon.system.shots}</strong>. Reserve <strong>${ammoUsage.reserve}</strong>. Ammo cost <strong>${ammoUsage.totalCost}</strong> cR. ${ammoUsage.ammoRule}`;
|
||||
const ammoPrefix = `<strong>${ammoUsage.label}</strong> fire with <strong>${ammoUsage.ammoLabel}</strong> spent <strong>${ammoUsage.shots}</strong> ${roundLabel}. Magazine <strong>${ammoUsage.loaded}/${weapon.system.shots}</strong>. Reserve <strong>${ammoUsage.reserve}</strong>. Firing spend <strong>${ammoUsage.totalCost}</strong> cR. ${ammoUsage.ammoRule}`;
|
||||
const accountingText = ammoAccounting
|
||||
? ` Credits now <strong>${ammoAccounting.newCredits}</strong> cR. Running ammo spend <strong>${ammoAccounting.spendTotal}</strong> cR.`
|
||||
? ` Credits now <strong>${ammoAccounting.newCredits}</strong> cR. Running firing spend <strong>${ammoAccounting.spendTotal}</strong> cR.`
|
||||
: "";
|
||||
flavorText = flavorText ? `${ammoPrefix}${accountingText}<br>${flavorText}` : `${ammoPrefix}${accountingText}`;
|
||||
}
|
||||
@@ -2966,7 +3175,14 @@ export class MothershipActor extends Actor {
|
||||
targetingResult: targetingResult,
|
||||
firstEdition: game.settings.get('sla-mothership', 'firstEdition'),
|
||||
useCalm: game.settings.get('sla-mothership', 'useCalm'),
|
||||
androidPanic: game.settings.get('sla-mothership', 'androidPanic')
|
||||
androidPanic: game.settings.get('sla-mothership', 'androidPanic'),
|
||||
chatStyle: this.getSlaChatVariant({
|
||||
weapon,
|
||||
skill,
|
||||
skillCategory: String(attackContext?.skillCategory ?? "").trim(),
|
||||
msgHeader,
|
||||
isSlaEbbSkill
|
||||
})
|
||||
};
|
||||
//prepare template
|
||||
messageTemplate = 'systems/sla-mothership/templates/chat/rollCheck.html';
|
||||
@@ -2985,6 +3201,11 @@ export class MothershipActor extends Actor {
|
||||
}, {
|
||||
keepId: true
|
||||
});
|
||||
const skillLabel = String(skill ?? "").trim();
|
||||
const actionLabel = weapon
|
||||
? weapon.name
|
||||
: (skillLabel ? `${attributeLabel} / ${skillLabel}` : attributeLabel);
|
||||
await this.addSlaActivityLog?.(`${actionLabel}: ${parsedRollResult.success ? "success" : "failure"} (${parsedRollResult.total} vs ${rollTarget}).`);
|
||||
//is DSN active?
|
||||
if (game.modules.get("dice-so-nice") && game.modules.get("dice-so-nice").active) {
|
||||
//log what was done
|
||||
@@ -3863,10 +4084,58 @@ export class MothershipActor extends Actor {
|
||||
return { total, parts };
|
||||
}
|
||||
|
||||
async chooseWeaponAttackOptions(weapon) {
|
||||
async promptRollModifier(title = "Roll Modifier") {
|
||||
return new Promise((resolve) => {
|
||||
const dialogData = {
|
||||
window: { title },
|
||||
content: `
|
||||
<form style="padding: 5px 10px;">
|
||||
<div class="resource" style="margin-bottom: 15px;">
|
||||
<label class="resource-label" style="display: flex; justify-content: space-between; font-weight: bold; margin-bottom: 8px;">
|
||||
<span>Modifier Value</span>
|
||||
<span class="slider-value" style="font-weight: bold; color: #cc2828;">0</span>
|
||||
</label>
|
||||
<input type="range" name="rollModifier" min="-30" max="30" step="10" value="0" style="width: 100%; cursor: pointer; accent-color: #cc2828;">
|
||||
<div class="slider-ticks" style="display: flex; justify-content: space-between; margin-top: 5px; font-size: 0.85em; color: rgba(255,255,255,0.6); padding: 0 8px;">
|
||||
<span>-30</span>
|
||||
<span>-20</span>
|
||||
<span>-10</span>
|
||||
<span style="color: #cc2828; font-weight: bold;">0</span>
|
||||
<span>+10</span>
|
||||
<span>+20</span>
|
||||
<span>+30</span>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
`,
|
||||
buttons: [
|
||||
{
|
||||
label: "Roll",
|
||||
action: "roll",
|
||||
icon: "fas fa-dice-d20",
|
||||
callback: (_event, button) => {
|
||||
const modifier = Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0;
|
||||
resolve(modifier);
|
||||
}
|
||||
},
|
||||
{
|
||||
label: "Cancel",
|
||||
action: "cancel",
|
||||
icon: "fas fa-times",
|
||||
callback: () => resolve(null)
|
||||
}
|
||||
],
|
||||
close: () => resolve(null)
|
||||
};
|
||||
new foundry.applications.api.DialogV2(dialogData).render({ force: true });
|
||||
});
|
||||
}
|
||||
|
||||
async chooseWeaponAttackOptions(weapon, attackContext = {}) {
|
||||
const fireModes = this.getWeaponFireModes(weapon);
|
||||
const activeFireMode = this.getActiveWeaponFireMode(weapon);
|
||||
const ammoChoices = this.getWeaponAmmoChoices(weapon);
|
||||
const showModifier = Boolean(attackContext?.promptModifier);
|
||||
|
||||
return new Promise((resolve) => {
|
||||
const fireOptions = fireModes.map((mode) => `
|
||||
@@ -3876,20 +4145,40 @@ export class MothershipActor extends Actor {
|
||||
<option value="${choice.tag}" ${choice.selected ? "selected" : ""}>${choice.label}</option>
|
||||
`).join("");
|
||||
|
||||
const modifierHtml = showModifier ? `
|
||||
<div class="resource" style="margin-top: 15px; margin-bottom: 10px; border-top: 1px dashed rgba(255,255,255,0.15); padding-top: 10px;">
|
||||
<label class="resource-label" style="display: flex; justify-content: space-between; font-weight: bold; margin-bottom: 8px;">
|
||||
<span>Roll Modifier</span>
|
||||
<span class="slider-value" style="font-weight: bold; color: #cc2828;">0</span>
|
||||
</label>
|
||||
<input type="range" name="rollModifier" min="-30" max="30" step="10" value="0" style="width: 100%; cursor: pointer; accent-color: #cc2828;">
|
||||
<div class="slider-ticks" style="display: flex; justify-content: space-between; margin-top: 5px; font-size: 0.85em; color: rgba(255,255,255,0.6); padding: 0 8px;">
|
||||
<span>-30</span>
|
||||
<span>-20</span>
|
||||
<span>-10</span>
|
||||
<span style="color: #cc2828; font-weight: bold;">0</span>
|
||||
<span>+10</span>
|
||||
<span>+20</span>
|
||||
<span>+30</span>
|
||||
</div>
|
||||
</div>
|
||||
` : "";
|
||||
|
||||
const dialogData = {
|
||||
window: {
|
||||
title: `${weapon.name} Attack Setup`
|
||||
},
|
||||
content: `
|
||||
<form>
|
||||
<form style="padding: 5px 10px;">
|
||||
<div class="resource" style="margin-bottom: 10px;">
|
||||
<label class="resource-label">Fire Mode</label>
|
||||
<select name="fireMode">${fireOptions}</select>
|
||||
<label class="resource-label" style="font-weight: bold; margin-bottom: 5px; display: block;">Fire Mode</label>
|
||||
<select name="fireMode" style="width: 100%;">${fireOptions}</select>
|
||||
</div>
|
||||
<div class="resource" style="margin-bottom: 10px;">
|
||||
<label class="resource-label">Ammo Type</label>
|
||||
<select name="ammoTag">${ammoOptions}</select>
|
||||
<label class="resource-label" style="font-weight: bold; margin-bottom: 5px; display: block;">Ammo Type</label>
|
||||
<select name="ammoTag" style="width: 100%;">${ammoOptions}</select>
|
||||
</div>
|
||||
${modifierHtml}
|
||||
</form>
|
||||
`,
|
||||
buttons: [
|
||||
@@ -3901,10 +4190,12 @@ export class MothershipActor extends Actor {
|
||||
const fireLabel = button.form.querySelector("select[name='fireMode']")?.value ?? activeFireMode.label;
|
||||
const fireMode = fireModes.find((mode) => mode.label === fireLabel) ?? activeFireMode;
|
||||
const ammoTag = button.form.querySelector("select[name='ammoTag']")?.value ?? ammoChoices[0]?.tag ?? "STD";
|
||||
const rollModifier = showModifier ? (Number(button.form.querySelector("input[name='rollModifier']")?.value ?? 0) || 0) : 0;
|
||||
resolve({
|
||||
fireMode: fireMode.label,
|
||||
shotsPerFire: fireMode.shots,
|
||||
ammoTag
|
||||
ammoTag,
|
||||
rollModifier
|
||||
});
|
||||
}
|
||||
},
|
||||
@@ -3921,10 +4212,20 @@ export class MothershipActor extends Actor {
|
||||
});
|
||||
}
|
||||
|
||||
async rollWeaponAttack(weapon) {
|
||||
const attackContext = weapon?.system?.useAmmo ? await this.chooseWeaponAttackOptions(weapon) : {};
|
||||
if (weapon?.system?.useAmmo && !attackContext) return;
|
||||
return this.rollCheck(null, 'low', 'combat', null, null, weapon, null, attackContext ?? {});
|
||||
async rollWeaponAttack(weapon, attackContext = {}) {
|
||||
let context = { ...attackContext };
|
||||
if (weapon?.system?.useAmmo) {
|
||||
const ammoContext = await this.chooseWeaponAttackOptions(weapon, context);
|
||||
if (!ammoContext) return null;
|
||||
context = { ...context, ...ammoContext };
|
||||
} else {
|
||||
if (context.promptModifier) {
|
||||
const rollMod = await this.promptRollModifier(`${weapon.name} Attack Roll`);
|
||||
if (rollMod === null) return null;
|
||||
context.rollModifier = rollMod;
|
||||
}
|
||||
}
|
||||
return this.rollCheck(null, 'low', 'combat', null, null, weapon, null, context);
|
||||
}
|
||||
|
||||
async cycleWeaponFireMode(itemId, direction = 1) {
|
||||
@@ -4767,57 +5068,12 @@ export class MothershipActor extends Actor {
|
||||
|
||||
getSlaSpeciesMinimumWounds() {
|
||||
const species = String(this.system?.sla?.species?.value ?? "").trim();
|
||||
if (["Frother", "Shaktar", "Stormer 313 Malice", "Stormer 711 Xeno", "Stormer Vevaphon"].includes(species)) {
|
||||
if (["Frother", "Shaktar", "Stormer 313 Malice", "Stormer 711 Xeno"].includes(species)) {
|
||||
return 3;
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
|
||||
isSlaVevaphon() {
|
||||
const species = String(this.system?.sla?.species?.value ?? "").trim();
|
||||
return species === "Stormer Vevaphon";
|
||||
}
|
||||
|
||||
getSlaVevaphonInstability() {
|
||||
return Math.max(0, Math.min(12, Number(this.system?.sla?.vevaphonInstability?.value ?? 0) || 0));
|
||||
}
|
||||
|
||||
getSlaVevaphonMorphForm() {
|
||||
return String(this.system?.sla?.morphForm?.value ?? "").trim() || "Brute Form";
|
||||
}
|
||||
|
||||
async setSlaVevaphonMorphForm(formName) {
|
||||
if (!this.isSlaVevaphon()) return null;
|
||||
const validForms = ["Brute Form", "Stalker Form", "Raptor Form"];
|
||||
const resolved = validForms.find((entry) => entry === formName) ?? formName;
|
||||
const currentInstability = this.getSlaVevaphonInstability();
|
||||
const newInstability = Math.min(12, currentInstability + 1);
|
||||
await this.update({
|
||||
"system.sla.morphForm.value": resolved,
|
||||
"system.sla.vevaphonInstability.value": newInstability
|
||||
});
|
||||
const instabilityWarning = newInstability >= 10
|
||||
? " ⚠ Instability critical — Morph Panic risk on failed Sanity save."
|
||||
: newInstability >= 6
|
||||
? " Instability elevated — minor morph effects active."
|
||||
: "";
|
||||
ui.notifications.info(`${this.name} shifts to ${resolved}. Instability: ${newInstability}/12.${instabilityWarning}`);
|
||||
return { morphForm: resolved, instability: newInstability };
|
||||
}
|
||||
|
||||
async adjustSlaVevaphonInstability(delta = 1) {
|
||||
if (!this.isSlaVevaphon()) return null;
|
||||
const current = this.getSlaVevaphonInstability();
|
||||
const next = Math.max(0, Math.min(12, current + delta));
|
||||
await this.update({ "system.sla.vevaphonInstability.value": next });
|
||||
if (next >= 12) {
|
||||
ui.notifications.warn(`${this.name} has reached maximum Instability (12). The Vevaphon is lost — immediate retirement or death.`);
|
||||
} else if (next >= 10) {
|
||||
ui.notifications.warn(`${this.name} — Instability ${next}/12. Morph Panic risk: failed Sanity save triggers a Morph Panic event.`);
|
||||
}
|
||||
return next;
|
||||
}
|
||||
|
||||
async enforceSlaSpeciesWounds() {
|
||||
if (this.type !== "character") return null;
|
||||
const minimumWounds = this.getSlaSpeciesMinimumWounds();
|
||||
@@ -4912,16 +5168,31 @@ export class MothershipActor extends Actor {
|
||||
return ["Ebon", "Brain Waster"].includes(species);
|
||||
}
|
||||
|
||||
isSlaVevaphon() {
|
||||
return String(this.system?.sla?.species?.value ?? "").trim() === "Stormer Vevaphon";
|
||||
}
|
||||
|
||||
async setSlaVevaphonMorphForm(formName) {
|
||||
if (!formName) return;
|
||||
await this.update({ "system.sla.morphForm.value": String(formName) });
|
||||
}
|
||||
|
||||
async adjustSlaVevaphonInstability(delta) {
|
||||
const current = Math.max(0, Math.min(12, Number(this.system?.sla?.vevaphonInstability?.value ?? 0) || 0));
|
||||
const next = Math.max(0, Math.min(12, current + (Number(delta) || 0)));
|
||||
await this.update({ "system.sla.vevaphonInstability.value": next });
|
||||
}
|
||||
|
||||
getSlaRestrictedEbbItemIds() {
|
||||
return this.items
|
||||
.filter((item) => {
|
||||
const name = String(item.name ?? "").trim();
|
||||
const sla = item.system?.sla ?? {};
|
||||
if (item.type === "ability") {
|
||||
// Vevaphon morph form abilities are NOT Ebb items — exclude them
|
||||
if (item.system?.sla?.morphForm === true) return false;
|
||||
// Also exclude by name so hand-placed morph abilities are safe even without the flag
|
||||
const morphNames = ["Brute Form", "Stalker Form", "Raptor Form"];
|
||||
if (morphNames.includes(name)) return false;
|
||||
// Only flag abilities that are explicitly Ebb abilities.
|
||||
// Morph forms (Vevaphon) get abilityType "morph" from the generator and are never removed.
|
||||
// morphForm flag is a belt-and-suspenders guard in case abilityType is missing.
|
||||
if (sla.morphForm || String(sla.abilityType ?? "ebb").trim() !== "ebb") return false;
|
||||
return true;
|
||||
}
|
||||
if (item.type !== "skill") return false;
|
||||
@@ -4942,13 +5213,20 @@ export class MothershipActor extends Actor {
|
||||
"system.sla.ebbRating.value": 0
|
||||
};
|
||||
await this.update(updateData);
|
||||
if (restrictedIds.length) {
|
||||
await this.deleteEmbeddedDocuments("Item", restrictedIds);
|
||||
const validIds = restrictedIds.filter(id => this.items.get(id) !== undefined);
|
||||
let removed = 0;
|
||||
if (validIds.length) {
|
||||
try {
|
||||
await this.deleteEmbeddedDocuments("Item", validIds);
|
||||
removed = validIds.length;
|
||||
} catch (err) {
|
||||
// Concurrent enforcement calls may have already deleted these items — safe to ignore
|
||||
}
|
||||
}
|
||||
if (notify && restrictedIds.length) {
|
||||
if (notify && removed) {
|
||||
ui.notifications.warn(`${this.name} is not an Ebb user. Restricted Ebb skills and abilities were removed.`);
|
||||
}
|
||||
return { removed: restrictedIds.length };
|
||||
return { removed };
|
||||
}
|
||||
|
||||
const currentMax = Math.max(0, Number(this.system?.sla?.flux?.max ?? 0) || 0);
|
||||
@@ -5484,7 +5762,8 @@ export class MothershipActor extends Actor {
|
||||
insert: rollInsert,
|
||||
onlyDesc: true,
|
||||
swapNameDesc,
|
||||
swapName
|
||||
swapName,
|
||||
severityMeta: this.getSlaSeverityMeta({ severity: item?.system?.severity })
|
||||
};
|
||||
|
||||
const chatData = {
|
||||
|
||||
@@ -79,6 +79,9 @@ export class MothershipCreatureSheet extends foundry.appv1.sheets.ActorSheet {
|
||||
if (data.data.system.settings == null) {
|
||||
data.data.system.settings = {};
|
||||
}
|
||||
if (data.data.system.slaNpc == null) {
|
||||
data.data.system.slaNpc = {};
|
||||
}
|
||||
data.data.system.settings.useCalm = game.settings.get("sla-mothership", "useCalm");
|
||||
data.data.system.settings.hideWeight = game.settings.get("sla-mothership", "hideWeight");
|
||||
data.data.system.settings.firstEdition = game.settings.get("sla-mothership", "firstEdition");
|
||||
|
||||
@@ -0,0 +1,57 @@
|
||||
import { MothershipCreatureSheet } from "./creature-sheet.js";
|
||||
|
||||
/**
|
||||
* Extend MothershipCreatureSheet for the streamlined NPC (creature) actor sheet.
|
||||
* Displays a single-page, tab-free dashboard with core stats and equipment.
|
||||
* @extends {MothershipCreatureSheet}
|
||||
*/
|
||||
export class MothershipNpcSheet extends MothershipCreatureSheet {
|
||||
|
||||
/** @override */
|
||||
static get defaultOptions() {
|
||||
const options = {
|
||||
classes: ["mosh", "sheet", "actor", "creature", "npc-sheet"],
|
||||
template: "systems/sla-mothership/templates/actor/npc-sheet.html",
|
||||
width: 720,
|
||||
height: 680,
|
||||
tabs: [], // Disable tabs
|
||||
submitOnChange: true
|
||||
};
|
||||
|
||||
return foundry.utils.mergeObject(super.defaultOptions, options);
|
||||
}
|
||||
|
||||
/** @override */
|
||||
async getData() {
|
||||
const data = await super.getData();
|
||||
|
||||
// Limit the displayed skills to a maximum of 5
|
||||
if (data.skills) {
|
||||
data.skills = data.skills.slice(0, 5);
|
||||
}
|
||||
|
||||
// Flag to show/hide the "Add Skill" button based on 5-skill constraint
|
||||
data.showAddSkill = (!data.skills || data.skills.length < 5);
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
/** @override */
|
||||
activateListeners(html) {
|
||||
super.activateListeners(html);
|
||||
|
||||
if (!this.options.editable) return;
|
||||
|
||||
// Custom Wound Roll Button Click
|
||||
html.find('.npc-wound-roll').click(async ev => {
|
||||
ev.preventDefault();
|
||||
await this.actor.chooseSlaWoundTable();
|
||||
});
|
||||
|
||||
// Custom Panic Roll Button Click
|
||||
html.find('.npc-panic-roll').click(async ev => {
|
||||
ev.preventDefault();
|
||||
await this.actor.rollTable("panicCheck", null, null, null, null, null, null);
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,22 @@
|
||||
import { SLADrugSystem } from "../sla-drug-system.js";
|
||||
|
||||
function isAmmoPurchaseItem(itemData = {}) {
|
||||
const system = itemData?.system ?? {};
|
||||
const sla = system?.sla ?? {};
|
||||
const name = String(itemData?.name ?? "").trim().toLowerCase();
|
||||
const category = String(sla.category ?? "").trim().toLowerCase();
|
||||
const calibre = String(sla.calibre ?? "").trim();
|
||||
const ammoTag = String(sla.ammoTag ?? "").trim();
|
||||
return category === "ammunition" || Boolean((calibre && ammoTag) || name.startsWith("ammo:"));
|
||||
}
|
||||
|
||||
function formatSlaTimestamp() {
|
||||
return new Intl.DateTimeFormat(undefined, {
|
||||
dateStyle: "short",
|
||||
timeStyle: "short"
|
||||
}).format(new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Extend the basic ItemSheet with some very simple modifications
|
||||
* @extends {ItemSheet}
|
||||
@@ -128,11 +145,38 @@ export class MothershipItemSheet extends foundry.appv1.sheets.ItemSheet {
|
||||
|
||||
async _updateObject(event, formData) {
|
||||
const updateData = foundry.utils.expandObject(formData);
|
||||
const currentQty = Math.max(0, Number(this.item.system?.quantity ?? 0) || 0);
|
||||
if (Object.prototype.hasOwnProperty.call(updateData?.system ?? {}, "weight")) {
|
||||
const parsed = Number(updateData.system.weight ?? 0) || 0;
|
||||
updateData.system.weight = Math.round(parsed * 10) / 10;
|
||||
}
|
||||
await this.item.update(updateData, { diff: false });
|
||||
|
||||
const nextQtyRaw = updateData?.system?.quantity;
|
||||
const nextQty = nextQtyRaw === undefined ? currentQty : Math.max(0, Number(nextQtyRaw ?? 0) || 0);
|
||||
const increase = Math.max(0, nextQty - currentQty);
|
||||
const actor = this.item.parent;
|
||||
if (!increase || actor?.documentName !== "Actor") return;
|
||||
|
||||
const unitCost = Number(updateData?.system?.cost ?? this.item.system?.cost ?? 0) || 0;
|
||||
const total = Math.round(unitCost * increase * 100) / 100;
|
||||
if (!total) return;
|
||||
|
||||
const currentCredits = Number(actor.system?.credits?.value ?? 0) || 0;
|
||||
const newCredits = Math.round((currentCredits - total) * 100) / 100;
|
||||
const updateActorData = { "system.credits.value": newCredits };
|
||||
|
||||
if (isAmmoPurchaseItem(this.item.toObject())) {
|
||||
const stamp = formatSlaTimestamp();
|
||||
const currentLedger = String(actor.system?.sla?.ammoLedger?.value ?? "").trim();
|
||||
const entry = `[${stamp}] PURCHASE | ${this.item.name ?? "Ammo"} | ${increase} round${increase === 1 ? "" : "s"} | -${total} cR | balance ${newCredits} cR`;
|
||||
const ledgerLines = [entry, ...currentLedger.split("\n").filter(Boolean)].slice(0, 60);
|
||||
updateActorData["system.sla.ammoLedger.value"] = ledgerLines.join("\n");
|
||||
}
|
||||
|
||||
await actor.update(updateActorData);
|
||||
ui.notifications.info(`${actor.name}: deducted ${total} cR for ${increase} more ${this.item.name ?? "item"}. Credits now ${newCredits} cR.`);
|
||||
await actor.addSlaActivityLog?.(`Purchased +${increase} ${this.item.name ?? "item"} for ${total} cR. Credits now ${newCredits} cR.`);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
import { MothershipActor } from "./actor/actor.js";
|
||||
import { MothershipActorSheet, MothershipActorSheetDossier } from "./actor/actor-sheet.js";
|
||||
import { MothershipCreatureSheet } from "./actor/creature-sheet.js";
|
||||
import { MothershipNpcSheet } from "./actor/npc-sheet.js";
|
||||
import { MothershipShipSheet } from "./actor/ship-sheet.js";
|
||||
import { MothershipShipSheetSBT } from "./actor/ship-sheet-sbt.js";
|
||||
|
||||
@@ -12,6 +13,7 @@ import { MothershipSkillSheet } from "./item/skill-sheet.js";
|
||||
import { SLADrugSystem } from "./sla-drug-system.js";
|
||||
import { slaDebug } from "./logger.js";
|
||||
import { SLAMothershipGenerator } from "./windows/sla-character-generator.js";
|
||||
import { SLANpcGeneratorApp, generateSlaNpc } from "./windows/sla-npc-generator.js";
|
||||
import { SLAWorldToolsApp, installSlaSidebarButtons } from "./windows/sla-world-tools.js";
|
||||
|
||||
import {
|
||||
@@ -50,6 +52,8 @@ Hooks.once('init', async function () {
|
||||
closeDrug: (actor, itemId, drug = "") => SLADrugSystem.closeDrug({ actor, itemId, drug }),
|
||||
restartDrugReminders: () => SLADrugSystem.startReminderLoop(),
|
||||
openGenerator: (actor = null, options = {}) => SLAMothershipGenerator.open(actor, options),
|
||||
openNpcDesk: (options = {}) => SLANpcGeneratorApp.open(options),
|
||||
createNpc: (state = {}) => generateSlaNpc(state),
|
||||
createRandomOperative: (options = {}) => SLAMothershipGenerator.createRandomOperative(options),
|
||||
createStarterSquad: (options = {}) => SLAMothershipGenerator.createStarterSquad(options),
|
||||
openTools: () => SLAWorldToolsApp.open(),
|
||||
@@ -78,7 +82,8 @@ Hooks.once('init', async function () {
|
||||
foundry.documents.collections.Actors.unregisterSheet("core", foundry.appv1.sheets.ActorSheet);
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipActorSheet, {types: ['character'], makeDefault: true});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipActorSheetDossier, {types: ['character'], makeDefault: false, label: "SLA Dossier"});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipCreatureSheet, {types: ['creature'], makeDefault: false});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipNpcSheet, {types: ['creature'], makeDefault: true, label: "SLA Streamlined NPC Sheet"});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipCreatureSheet, {types: ['creature'], makeDefault: false, label: "SLA Standard Creature Sheet"});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipShipSheetSBT, {types: ['ship'], makeDefault: true});
|
||||
foundry.documents.collections.Actors.registerSheet("sla-mothership", MothershipShipSheet, {types: ['ship'], makeDefault: false});
|
||||
foundry.documents.collections.Items.unregisterSheet("core", foundry.appv1.sheets.ItemSheet);
|
||||
@@ -144,11 +149,38 @@ Hooks.once('init', async function () {
|
||||
await SLADrugSystem.handleEffectDeleted(effect, options);
|
||||
});
|
||||
|
||||
Hooks.on("createItem", async (item) => {
|
||||
// Debounce map: actorId → pending timeout handle.
|
||||
// Prevents enforceSlaEbbEligibility from being called once per item when the
|
||||
// character generator creates many items in rapid succession (each createItem
|
||||
// hook call would otherwise race to delete the same Ebb items concurrently).
|
||||
const _pendingEbbEnforcement = new Map();
|
||||
Hooks.on("createItem", async (item, options, userId) => {
|
||||
// ── Unarmed Combat Auto-Skill Drop ──
|
||||
const actor = item.parent;
|
||||
if (actor && actor.documentName === "Actor" && item.type === "weapon" && String(item.name).trim().toLowerCase() === "unarmed combat") {
|
||||
const hasSkill = actor.items.some(i => i.type === "skill" && String(i.name).trim().toLowerCase() === "unarmed combat");
|
||||
if (!hasSkill) {
|
||||
await actor.createEmbeddedDocuments("Item", [{
|
||||
name: "Unarmed Combat",
|
||||
type: "skill",
|
||||
img: "icons/svg/fist.svg",
|
||||
system: {
|
||||
rank: "Trained",
|
||||
bonus: 10,
|
||||
sla: { category: "combat", skillFamily: "", source: "Unarmed Item Drop" }
|
||||
}
|
||||
}]);
|
||||
ui.notifications.info(`Added 'Unarmed Combat' skill to ${actor.name}.`);
|
||||
}
|
||||
}
|
||||
|
||||
if (!actor || actor.type !== "character" || typeof actor.enforceSlaEbbEligibility !== "function") return;
|
||||
if (actor.isSlaEbbUser?.()) return;
|
||||
await actor.enforceSlaEbbEligibility({ notify: true, refillFlux: false });
|
||||
if (_pendingEbbEnforcement.has(actor.id)) clearTimeout(_pendingEbbEnforcement.get(actor.id));
|
||||
_pendingEbbEnforcement.set(actor.id, setTimeout(async () => {
|
||||
_pendingEbbEnforcement.delete(actor.id);
|
||||
await actor.enforceSlaEbbEligibility({ notify: true, refillFlux: false });
|
||||
}, 300));
|
||||
});
|
||||
|
||||
Hooks.on("updateActor", async (actor, changes, options) => {
|
||||
@@ -175,16 +207,37 @@ Hooks.once('init', async function () {
|
||||
|
||||
Hooks.on("renderActorDirectory", (app, html) => {
|
||||
installSlaSidebarButtons(app, html);
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("actors", html);
|
||||
});
|
||||
|
||||
Hooks.on("renderSidebarTab", (app, html) => {
|
||||
const isActorsTab = app?.tabName === "actors" || app?.options?.id === "actors";
|
||||
if (!isActorsTab) return;
|
||||
installSlaSidebarButtons(app, html);
|
||||
if (isActorsTab) installSlaSidebarButtons(app, html);
|
||||
if (!game.user?.isGM) {
|
||||
hideSlaRestrictedSidebarTabs();
|
||||
enforceSlaPlayerSidebarTabRestrictions(app, html);
|
||||
}
|
||||
});
|
||||
|
||||
Hooks.on("renderSceneDirectory", (_app, html) => {
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("scenes", html);
|
||||
});
|
||||
|
||||
Hooks.on("renderJournalDirectory", (_app, html) => {
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("journal", html);
|
||||
});
|
||||
|
||||
Hooks.on("renderRollTableDirectory", (_app, html) => {
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("tables", html);
|
||||
});
|
||||
|
||||
Hooks.on("renderCompendiumDirectory", (_app, html) => {
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("compendium", html);
|
||||
});
|
||||
|
||||
Hooks.on("renderCombatTracker", (app, html) => {
|
||||
installSlaCombatTrackerControls(app, html);
|
||||
if (!game.user?.isGM) enforceSlaPlayerDirectoryRestrictions("combat", html);
|
||||
});
|
||||
|
||||
Hooks.on("updateCombat", async (combat, changed) => {
|
||||
@@ -247,9 +300,62 @@ Hooks.once("ready", async function () {
|
||||
}
|
||||
|
||||
patchSlaInitiativeSystem();
|
||||
if (!game.user?.isGM) hideSlaRestrictedSidebarTabs();
|
||||
|
||||
// GM Conditions Summary — whisper to all GMs every 30 minutes
|
||||
if (game.user?.isGM) {
|
||||
setInterval(_sendGMConditionsSummary, 30 * 60 * 1000);
|
||||
console.log("SLA MOTHERSHIP | GM conditions summary timer started (every 30 minutes).");
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
/**
|
||||
* Scans all actors for active condition items and whispers a summary to GM(s).
|
||||
* Fires every 30 minutes when logged in as GM.
|
||||
*/
|
||||
function _sendGMConditionsSummary() {
|
||||
if (!game.user?.isGM) return;
|
||||
|
||||
const rows = [];
|
||||
for (const actor of game.actors) {
|
||||
const conditions = actor.items?.filter(i => i.type === "condition") ?? [];
|
||||
if (conditions.length === 0) continue;
|
||||
const conditionList = conditions.map(c => {
|
||||
const sev = c.system?.severity ?? "";
|
||||
return `<span style="color:#ff4444;font-weight:bold;">${c.name}${sev ? ` (${sev})` : ""}</span>`;
|
||||
}).join(", ");
|
||||
rows.push(`<tr><td style="padding:2px 8px;font-weight:bold;color:#eee;">${actor.name}</td><td style="padding:2px 8px;">${conditionList}</td></tr>`);
|
||||
}
|
||||
|
||||
let content;
|
||||
if (rows.length === 0) {
|
||||
content = `<div style="font-family:monospace;color:#888;padding:4px 8px;">
|
||||
<strong style="color:#ff4444;">⚕ CONDITIONS REPORT</strong> — No active conditions.
|
||||
</div>`;
|
||||
} else {
|
||||
content = `<div style="font-family:monospace;padding:4px 0;">
|
||||
<div style="background:#1a0000;border:1px solid #8b0000;border-radius:4px;padding:4px 8px;margin-bottom:6px;">
|
||||
<strong style="color:#ff4444;font-size:1em;">⚕ CONDITIONS REPORT</strong>
|
||||
<span style="color:#888;font-size:0.8em;margin-left:8px;">${new Date().toLocaleTimeString()}</span>
|
||||
</div>
|
||||
<table style="width:100%;border-collapse:collapse;">
|
||||
<thead><tr style="border-bottom:1px solid #8b0000;">
|
||||
<th style="padding:2px 8px;color:#aaa;text-align:left;font-size:0.8em;">ACTOR</th>
|
||||
<th style="padding:2px 8px;color:#aaa;text-align:left;font-size:0.8em;">CONDITIONS</th>
|
||||
</tr></thead>
|
||||
<tbody>${rows.join("")}</tbody>
|
||||
</table>
|
||||
</div>`;
|
||||
}
|
||||
|
||||
ChatMessage.create({
|
||||
content,
|
||||
whisper: ChatMessage.getWhisperRecipients("GM"),
|
||||
speaker: { alias: "SLA System" }
|
||||
});
|
||||
}
|
||||
|
||||
Hooks.on("renderChatMessageHTML", (app, html) => {
|
||||
const root = html?.[0] ?? html;
|
||||
if (!root?.querySelectorAll) return;
|
||||
@@ -272,6 +378,129 @@ Hooks.on("renderChatMessageHTML", (app, html) => {
|
||||
await actor.rollSlaWoundEffect(effectKey, modifier);
|
||||
});
|
||||
});
|
||||
|
||||
// ── Critical Hit? Button Handler ──
|
||||
root.querySelectorAll(".sla-crit-hit-btn").forEach((button) => {
|
||||
button.addEventListener("click", async (event) => {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
|
||||
const actorId = button.dataset.actorId;
|
||||
const itemId = button.dataset.itemId;
|
||||
const actor = actorId ? game.actors?.get(actorId) : null;
|
||||
if (!actor) {
|
||||
ui.notifications.warn("The actor for this critical hit could not be found.");
|
||||
return;
|
||||
}
|
||||
|
||||
const weapon = itemId ? actor.items.get(itemId) : null;
|
||||
|
||||
// Determine wound setting key based on weapon and damage type
|
||||
let settingKey = 'table1eWoundBluntForce';
|
||||
let tableLabel = 'Blunt Force';
|
||||
|
||||
if (weapon) {
|
||||
const name = String(weapon.name ?? "").toLowerCase();
|
||||
const damageType = String(weapon.system?.sla?.damageType ?? "").toLowerCase();
|
||||
|
||||
if (damageType.includes("blunt") || damageType.includes("impact")) {
|
||||
settingKey = 'table1eWoundBluntForce';
|
||||
tableLabel = 'Blunt Force';
|
||||
} else if (damageType.includes("penetrating") || damageType.includes("pierce") || damageType.includes("stab") || damageType.includes("bullet") || damageType.includes("shot")) {
|
||||
settingKey = 'table1eWoundGunshot';
|
||||
tableLabel = 'Gunshot';
|
||||
} else if (damageType.includes("slash") || damageType.includes("rend") || damageType.includes("bleed") || damageType.includes("cut")) {
|
||||
settingKey = 'table1eWoundBleeding';
|
||||
tableLabel = 'Bleeding';
|
||||
} else if (damageType.includes("fire") || damageType.includes("explos") || damageType.includes("acid") || damageType.includes("burn")) {
|
||||
settingKey = 'table1eWoundFireExplosives';
|
||||
tableLabel = 'Fire & Explosives';
|
||||
} else if (name.includes("pistol") || name.includes("smg") || name.includes("rifle") || name.includes("shotgun") || name.includes("blunderbuss") || name.includes("gun") || name.includes("harpoon") || name.includes("bullet") || name.includes("projectile") || name.includes("crossbow")) {
|
||||
settingKey = 'table1eWoundGunshot';
|
||||
tableLabel = 'Gunshot';
|
||||
} else if (name.includes("machete") || name.includes("cleaver") || name.includes("whip") || name.includes("blade") || name.includes("knife") || name.includes("sword") || name.includes("claws") || name.includes("bite") || name.includes("razor") || name.includes("teeth")) {
|
||||
settingKey = 'table1eWoundBleeding';
|
||||
tableLabel = 'Bleeding';
|
||||
} else if (name.includes("club") || name.includes("pipe") || name.includes("hammer") || name.includes("prod") || name.includes("unarmed") || name.includes("fist") || name.includes("strike") || name.includes("blunt") || name.includes("brawl") || name.includes("cuff")) {
|
||||
settingKey = 'table1eWoundBluntForce';
|
||||
tableLabel = 'Blunt Force';
|
||||
} else if (name.includes("bomb") || name.includes("acid") || name.includes("spit") || name.includes("fire") || name.includes("flame") || name.includes("grenade") || name.includes("explosive")) {
|
||||
settingKey = 'table1eWoundFireExplosives';
|
||||
tableLabel = 'Fire & Explosives';
|
||||
}
|
||||
}
|
||||
|
||||
const tableId = game.settings.get('sla-mothership', settingKey);
|
||||
if (!tableId) {
|
||||
ui.notifications.warn(`No wound table is configured for ${tableLabel}.`);
|
||||
return;
|
||||
}
|
||||
|
||||
// Resolve the table
|
||||
let resolved = game.tables.get(tableId) || game.tables.getName(tableId);
|
||||
if (!resolved) {
|
||||
for (const pack of game.packs) {
|
||||
if (pack.metadata.type === "RollTable") {
|
||||
const index = await pack.getIndex();
|
||||
const entry = index.find(e => e.id === tableId || e.name === tableId || e.name === `${tableLabel} Wound` || e.name === tableLabel.replace(/&/g, "and"));
|
||||
if (entry) {
|
||||
resolved = await pack.getDocument(entry._id);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!resolved) {
|
||||
ui.notifications.warn(`The ${tableLabel} wound table could not be found.`);
|
||||
return;
|
||||
}
|
||||
|
||||
await actor.rollTable(resolved.uuid ?? resolved.id ?? tableId, resolved.formula ?? "1d10", "low", true, false, null, null);
|
||||
});
|
||||
});
|
||||
|
||||
// ── Critical Success Option Button Handler ──
|
||||
root.querySelectorAll(".sla-crit-option-btn").forEach((button) => {
|
||||
button.addEventListener("click", async (event) => {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
|
||||
const actorId = button.dataset.actorId;
|
||||
const optionText = button.dataset.optionText;
|
||||
const actor = actorId ? game.actors?.get(actorId) : null;
|
||||
const actorName = actor ? actor.name : "An operative";
|
||||
|
||||
const chatContent = await foundry.applications.handlebars.renderTemplate(
|
||||
'systems/sla-mothership/templates/chat/sla-critical-selection.html',
|
||||
{
|
||||
actorName: actorName,
|
||||
img: actor?.img ?? 'icons/svg/mystery-man.svg',
|
||||
optionText: optionText
|
||||
}
|
||||
);
|
||||
|
||||
await ChatMessage.create({
|
||||
user: game.user.id,
|
||||
content: chatContent,
|
||||
speaker: ChatMessage.getSpeaker({ actor: actor })
|
||||
});
|
||||
|
||||
// Disable all options in the card
|
||||
const container = button.closest(".sla-crit-success-options");
|
||||
if (container) {
|
||||
container.querySelectorAll(".sla-crit-option-btn").forEach(btn => {
|
||||
btn.disabled = true;
|
||||
btn.style.opacity = 0.6;
|
||||
btn.style.cursor = "default";
|
||||
if (btn === button) {
|
||||
btn.style.background = "#0f300f";
|
||||
btn.style.border = "1px solid #1ebd1e";
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
//add custom damage dice for MOSH
|
||||
@@ -1249,3 +1478,366 @@ export function formatCreditsNumber(num) {
|
||||
return num.toString() + 'cr';
|
||||
}
|
||||
}
|
||||
|
||||
// ─────────────────────────────────────────────────────────────────────────────
|
||||
// SLA Industries Pause Screen Animation
|
||||
// ─────────────────────────────────────────────────────────────────────────────
|
||||
|
||||
let slaPauseRefreshHandle = null;
|
||||
|
||||
function injectSlaPauseAnimation() {
|
||||
document.body?.classList.add("sla-pause-active");
|
||||
if (document.querySelector('.sla-pause-root')) {
|
||||
return;
|
||||
}
|
||||
|
||||
const svgHTML = `
|
||||
<div class="sla-pause-root" aria-label="SLA Industries – Game Paused">
|
||||
<div class="sla-pause-stage">
|
||||
<svg class="sla-pause-svg" viewBox="-120 -120 240 260" xmlns="http://www.w3.org/2000/svg" role="img">
|
||||
<defs>
|
||||
<filter id="sla-glow-red" x="-50%" y="-50%" width="200%" height="200%">
|
||||
<feGaussianBlur stdDeviation="3.5" result="blur"/>
|
||||
<feMerge>
|
||||
<feMergeNode in="blur"/>
|
||||
<feMergeNode in="SourceGraphic"/>
|
||||
</feMerge>
|
||||
</filter>
|
||||
<filter id="sla-glow-ring" x="-30%" y="-30%" width="160%" height="160%">
|
||||
<feGaussianBlur stdDeviation="1.5" result="blur"/>
|
||||
<feMerge>
|
||||
<feMergeNode in="blur"/>
|
||||
<feMergeNode in="SourceGraphic"/>
|
||||
</feMerge>
|
||||
</filter>
|
||||
<radialGradient id="sla-bg-grad" cx="50%" cy="50%" r="50%">
|
||||
<stop offset="0%" stop-color="#1a0000" stop-opacity="0.95"/>
|
||||
<stop offset="100%" stop-color="#000000" stop-opacity="0.0"/>
|
||||
</radialGradient>
|
||||
<clipPath id="sla-clip-outer">
|
||||
<circle cx="0" cy="0" r="108"/>
|
||||
</clipPath>
|
||||
</defs>
|
||||
<circle cx="0" cy="0" r="108" fill="url(#sla-bg-grad)" class="sla-pause-core-glow"/>
|
||||
<g class="sla-ring-outer">
|
||||
<animateTransform attributeName="transform" type="rotate" from="0 0 0" to="360 0 0" dur="18s" repeatCount="indefinite"/>
|
||||
<circle cx="0" cy="0" r="90"
|
||||
fill="none"
|
||||
stroke="#8b1a1a"
|
||||
stroke-width="0.8"
|
||||
stroke-dasharray="6 4"
|
||||
opacity="0.7"
|
||||
filter="url(#sla-glow-ring)"
|
||||
/>
|
||||
<circle cx="0" cy="-90" r="5" fill="#cc2222" filter="url(#sla-glow-red)" class="sla-sat"/>
|
||||
<circle cx="77.9" cy="45" r="5" fill="#cc2222" filter="url(#sla-glow-red)" class="sla-sat"/>
|
||||
<circle cx="-77.9" cy="45" r="5" fill="#cc2222" filter="url(#sla-glow-red)" class="sla-sat"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(0)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(30)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(60)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(90)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(120)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(150)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(180)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(210)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(240)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(270)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(300)"/>
|
||||
<line x1="0" y1="-86" x2="0" y2="-94" stroke="#8b1a1a" stroke-width="1" transform="rotate(330)"/>
|
||||
</g>
|
||||
<g class="sla-ring-inner">
|
||||
<animateTransform attributeName="transform" type="rotate" from="360 0 0" to="0 0 0" dur="13s" repeatCount="indefinite"/>
|
||||
<circle cx="0" cy="0" r="62"
|
||||
fill="none"
|
||||
stroke="#6b1010"
|
||||
stroke-width="0.6"
|
||||
stroke-dasharray="4 6"
|
||||
opacity="0.6"
|
||||
filter="url(#sla-glow-ring)"
|
||||
/>
|
||||
<circle cx="53.7" cy="-31" r="3.5" fill="#dd4422" filter="url(#sla-glow-red)" class="sla-sat-inner"/>
|
||||
<circle cx="-53.7" cy="-31" r="3.5" fill="#dd4422" filter="url(#sla-glow-red)" class="sla-sat-inner"/>
|
||||
<circle cx="0" cy="62" r="3.5" fill="#dd4422" filter="url(#sla-glow-red)" class="sla-sat-inner"/>
|
||||
</g>
|
||||
<g filter="url(#sla-glow-red)" class="sla-pause-logo-core">
|
||||
<polygon
|
||||
points="0,-38 33,-19 33,19 0,38 -33,19 -33,-19"
|
||||
fill="#1a0000"
|
||||
stroke="#cc2222"
|
||||
stroke-width="1.2"
|
||||
opacity="0.9"
|
||||
/>
|
||||
<text
|
||||
x="0" y="14"
|
||||
text-anchor="middle"
|
||||
font-family="'Oswald', 'Impact', 'Arial Narrow', sans-serif"
|
||||
font-size="38"
|
||||
font-weight="700"
|
||||
letter-spacing="3"
|
||||
fill="#ff2222"
|
||||
class="sla-pause-logo-text"
|
||||
>SLA</text>
|
||||
</g>
|
||||
<line x1="-70" y1="48" x2="70" y2="48" stroke="#8b1a1a" stroke-width="0.5" opacity="0.7"/>
|
||||
<text
|
||||
x="0" y="68"
|
||||
text-anchor="middle"
|
||||
font-family="'Oswald', 'Courier New', monospace"
|
||||
font-size="11.5"
|
||||
font-weight="500"
|
||||
letter-spacing="3.2"
|
||||
fill="#ff7b7b"
|
||||
class="sla-pause-standby"
|
||||
>PLEASE STAND BY</text>
|
||||
<text
|
||||
x="0" y="94"
|
||||
text-anchor="middle"
|
||||
font-family="'Oswald', 'Arial Narrow', sans-serif"
|
||||
font-size="8"
|
||||
font-weight="300"
|
||||
letter-spacing="3"
|
||||
fill="#b13b3b"
|
||||
opacity="0.92"
|
||||
>SLA INDUSTRIES</text>
|
||||
<line
|
||||
x1="0" y1="-90" x2="0" y2="0"
|
||||
stroke="#ff2222"
|
||||
stroke-width="0.8"
|
||||
opacity="0.18"
|
||||
class="sla-pause-scan"
|
||||
/>
|
||||
</svg>
|
||||
</div>
|
||||
</div>`;
|
||||
document.body?.insertAdjacentHTML('beforeend', svgHTML);
|
||||
}
|
||||
|
||||
function removeSlaPauseAnimation() {
|
||||
document.querySelector(".sla-pause-root")?.remove();
|
||||
document.body?.classList.remove("sla-pause-active");
|
||||
}
|
||||
|
||||
function queueSlaPauseRefresh(delay = 0) {
|
||||
window.clearTimeout(slaPauseRefreshHandle);
|
||||
slaPauseRefreshHandle = window.setTimeout(() => {
|
||||
if (!game?.paused) return;
|
||||
injectSlaPauseAnimation();
|
||||
}, delay);
|
||||
}
|
||||
|
||||
Hooks.once('ready', () => {
|
||||
if (game.paused) {
|
||||
queueSlaPauseRefresh(0);
|
||||
queueSlaPauseRefresh(60);
|
||||
queueSlaPauseRefresh(180);
|
||||
}
|
||||
});
|
||||
|
||||
Hooks.on('pauseGame', (paused) => {
|
||||
if (paused) {
|
||||
requestAnimationFrame(() => requestAnimationFrame(() => injectSlaPauseAnimation()));
|
||||
queueSlaPauseRefresh(0);
|
||||
queueSlaPauseRefresh(60);
|
||||
queueSlaPauseRefresh(180);
|
||||
queueSlaPauseRefresh(360);
|
||||
} else {
|
||||
removeSlaPauseAnimation();
|
||||
}
|
||||
});
|
||||
|
||||
function getSlaHtmlRoot(html) {
|
||||
return html instanceof HTMLElement ? html : html?.[0] ?? null;
|
||||
}
|
||||
|
||||
function hideSlaRestrictedSidebarTabs() {
|
||||
[
|
||||
"#sidebar-tabs [data-tab='tables']",
|
||||
"#sidebar-tabs [aria-controls='tables']",
|
||||
"#sidebar-tabs [data-tab='compendium']",
|
||||
"#sidebar-tabs [aria-controls='compendium']"
|
||||
].forEach((selector) => {
|
||||
document.querySelectorAll(selector).forEach((el) => {
|
||||
el.closest("li")?.remove();
|
||||
if (el instanceof HTMLElement) el.remove();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function removeSlaElements(root, selectors = []) {
|
||||
selectors.forEach((selector) => {
|
||||
root.querySelectorAll(selector).forEach((el) => el.remove());
|
||||
});
|
||||
}
|
||||
|
||||
function pruneEmptySlaFolders(root) {
|
||||
const folders = Array.from(root.querySelectorAll(".directory-item.folder"));
|
||||
folders.reverse().forEach((folder) => {
|
||||
const visibleDocuments = Array.from(folder.querySelectorAll(".directory-item.document, li.document")).filter((node) => node.offsetParent !== null);
|
||||
const visibleFolders = Array.from(folder.querySelectorAll(":scope > .directory-list > .directory-item.folder, :scope > ol > li.folder")).filter((node) => node.offsetParent !== null);
|
||||
if (!visibleDocuments.length && !visibleFolders.length) folder.remove();
|
||||
});
|
||||
}
|
||||
|
||||
function shouldShowSlaPlayerJournal(entry) {
|
||||
if (!entry) return false;
|
||||
const name = String(entry.name ?? "").trim();
|
||||
if (/^operative handbook$/i.test(name)) return true;
|
||||
if (entry.getFlag?.("sla-mothership", "playerVisible") === true) return true;
|
||||
return entry.testUserPermission?.(game.user, CONST.DOCUMENT_OWNERSHIP_LEVELS.OWNER) ?? false;
|
||||
}
|
||||
|
||||
function filterSlaJournalDirectory(root) {
|
||||
const rows = Array.from(root.querySelectorAll("[data-entry-id], [data-document-id]"));
|
||||
rows.forEach((row) => {
|
||||
const id = row.dataset.entryId ?? row.dataset.documentId;
|
||||
if (!id) return;
|
||||
const entry = game.journal?.get?.(id);
|
||||
if (!shouldShowSlaPlayerJournal(entry)) row.remove();
|
||||
});
|
||||
pruneEmptySlaFolders(root);
|
||||
}
|
||||
|
||||
function enforceSlaPlayerDirectoryRestrictions(kind, html) {
|
||||
const root = getSlaHtmlRoot(html);
|
||||
if (!root || game.user?.isGM) return;
|
||||
|
||||
removeSlaElements(root, [
|
||||
".directory-header .header-actions",
|
||||
".directory-header .action-buttons",
|
||||
".sla-sidebar-actions",
|
||||
".qbm-scene-directory-actions",
|
||||
".qbm-launch",
|
||||
".sla-world-tools-launch",
|
||||
".sla-create-operative",
|
||||
".sla-create-random-operative",
|
||||
".sla-refresh-content",
|
||||
".sla-gear-cache-open",
|
||||
".sla-briefing-desk-open",
|
||||
".sla-bpn-dispatch-open",
|
||||
".sla-npc-director-open",
|
||||
".sla-npc-director-actor-open",
|
||||
".sla-ops-clock-open",
|
||||
".npp-generate-sidebar-btn"
|
||||
]);
|
||||
|
||||
if (kind === "journal") {
|
||||
filterSlaJournalDirectory(root);
|
||||
}
|
||||
|
||||
if (kind === "tables" || kind === "compendium") {
|
||||
root.innerHTML = "";
|
||||
}
|
||||
}
|
||||
|
||||
function enforceSlaPlayerSidebarTabRestrictions(app, html) {
|
||||
const tabName = app?.tabName ?? app?.options?.id ?? "";
|
||||
if (tabName === "actors") return enforceSlaPlayerDirectoryRestrictions("actors", html);
|
||||
if (tabName === "scenes") return enforceSlaPlayerDirectoryRestrictions("scenes", html);
|
||||
if (tabName === "journal") return enforceSlaPlayerDirectoryRestrictions("journal", html);
|
||||
if (tabName === "tables") return enforceSlaPlayerDirectoryRestrictions("tables", html);
|
||||
if (tabName === "compendium") return enforceSlaPlayerDirectoryRestrictions("compendium", html);
|
||||
if (tabName === "combat") return enforceSlaPlayerDirectoryRestrictions("combat", html);
|
||||
}
|
||||
|
||||
// ─────────────────────────────────────────────────────────────────────────────
|
||||
// SLA Industries — UI Icon Injection
|
||||
// Replaces Foundry's Font Awesome icons in the sidebar and scene controls
|
||||
// by walking the live DOM and applying inline CSS mask-image styles.
|
||||
// ─────────────────────────────────────────────────────────────────────────────
|
||||
|
||||
const SLA_ICON_BASE = "systems/sla-mothership/icons/ui/";
|
||||
|
||||
const SLA_SIDEBAR_ICONS = {
|
||||
chat: "chat",
|
||||
combat: "combat",
|
||||
scenes: "scenes",
|
||||
actors: "actors",
|
||||
items: "items",
|
||||
journal: "journal",
|
||||
tables: "tables",
|
||||
playlists: "playlists",
|
||||
compendium: "compendium",
|
||||
settings: "settings",
|
||||
};
|
||||
|
||||
const SLA_CONTROL_ICONS = {
|
||||
token: "token",
|
||||
measure: "measure",
|
||||
tiles: "tiles",
|
||||
drawings: "drawings",
|
||||
walls: "walls",
|
||||
lighting: "lighting",
|
||||
sounds: "sounds",
|
||||
notes: "notes",
|
||||
};
|
||||
|
||||
function _slaApplyIconMask(el, iconFile) {
|
||||
const url = `${SLA_ICON_BASE}${iconFile}.svg`;
|
||||
// Measure font size BEFORE zeroing it — FA icons scale with font-size
|
||||
const fs = parseFloat(getComputedStyle(el).fontSize) || 18;
|
||||
const sz = Math.round(fs * 1.15) + "px";
|
||||
|
||||
// font-size:0 → collapses the ::before FA glyph to nothing
|
||||
// currentColor → inherits the button's text colour (white/grey/active from Foundry)
|
||||
// mask → cuts that fill into our SVG shape
|
||||
el.style.setProperty("font-size", "0", "important");
|
||||
el.style.setProperty("line-height", "0", "important");
|
||||
el.style.setProperty("width", sz, "important");
|
||||
el.style.setProperty("height", sz, "important");
|
||||
el.style.setProperty("display", "inline-flex", "important");
|
||||
el.style.setProperty("align-items", "center", "important");
|
||||
el.style.setProperty("justify-content", "center", "important");
|
||||
el.style.setProperty("background-color", "currentColor", "important");
|
||||
el.style.setProperty("-webkit-mask", `url('${url}') center/contain no-repeat`, "important");
|
||||
el.style.setProperty("mask", `url('${url}') center/contain no-repeat`, "important");
|
||||
el.setAttribute("data-sla-icon", iconFile);
|
||||
}
|
||||
|
||||
function injectSlaIcons() {
|
||||
let found = 0;
|
||||
|
||||
// ── Sidebar tab icons ─────────────────────────────────────────────────
|
||||
// Foundry v13 confirmed structure:
|
||||
// <button class="ui-control plain icon fa-solid fa-comments" data-tab="chat" ...>
|
||||
// The BUTTON itself is the icon — no child <i> element.
|
||||
document.querySelectorAll(
|
||||
"#sidebar-tabs button[data-tab], #sidebar-tabs [data-tab].icon"
|
||||
).forEach(btn => {
|
||||
const name = btn.dataset.tab;
|
||||
const file = SLA_SIDEBAR_ICONS[name];
|
||||
if (!file || btn.hasAttribute("data-sla-icon")) return;
|
||||
_slaApplyIconMask(btn, file);
|
||||
found++;
|
||||
});
|
||||
|
||||
// ── Scene / layer control icons ───────────────────────────────────────
|
||||
// Foundry v13 scene controls are also buttons — search the whole doc
|
||||
// since we don't yet know the container ID.
|
||||
document.querySelectorAll(
|
||||
"button[data-control], [data-control].icon, [data-control].ui-control"
|
||||
).forEach(btn => {
|
||||
const name = btn.dataset.control;
|
||||
const file = SLA_CONTROL_ICONS[name];
|
||||
if (!file || btn.hasAttribute("data-sla-icon")) return;
|
||||
_slaApplyIconMask(btn, file);
|
||||
found++;
|
||||
});
|
||||
|
||||
if (found > 0) {
|
||||
console.log(`SLA Industries | Applied ${found} custom icons.`);
|
||||
} else {
|
||||
console.warn("SLA Industries | injectSlaIcons: no icons matched — dumping HTML:");
|
||||
console.warn("sidebar:", document.querySelector("#sidebar-tabs")?.outerHTML?.slice(0, 1200));
|
||||
const ctrlDump = document.querySelector("#ui-left, #scene-controls, #controls");
|
||||
console.warn("controls:", ctrlDump?.outerHTML?.slice(0, 1200) ?? "(not found — try: " + [...document.querySelectorAll("[data-control]")].map(e=>e.tagName+'.'+e.className).join(', ') + ")");
|
||||
}
|
||||
}
|
||||
|
||||
// Run once on ready, then re-run whenever Foundry re-renders these components
|
||||
Hooks.once("ready", () => {
|
||||
requestAnimationFrame(() => requestAnimationFrame(() => injectSlaIcons()));
|
||||
});
|
||||
Hooks.on("renderSidebar", () => requestAnimationFrame(() => injectSlaIcons()));
|
||||
Hooks.on("renderSidebarTab", () => requestAnimationFrame(() => injectSlaIcons()));
|
||||
Hooks.on("changeSidebarTab", () => requestAnimationFrame(() => injectSlaIcons()));
|
||||
Hooks.on("renderSceneControls", () => requestAnimationFrame(() => injectSlaIcons()));
|
||||
|
||||
@@ -487,6 +487,23 @@ export class SLADrugSystem {
|
||||
|
||||
await this.resolveExpiredEffects(actor);
|
||||
|
||||
// Drug stacking warning — check if any OTHER drug is already active
|
||||
const allActiveDrugEffects = this.getActorDrugEffects(actor);
|
||||
const otherActiveDrugs = allActiveDrugEffects.filter((effect) => {
|
||||
const flag = this.getDrugEffectFlag(effect);
|
||||
return flag?.stage === "active" && flag?.drugId && flag.drugId !== def.id;
|
||||
});
|
||||
if (otherActiveDrugs.length > 0) {
|
||||
const activeNames = [...new Set(otherActiveDrugs.map((e) => this.getDrugEffectFlag(e)?.drugName ?? e.name))].join(", ");
|
||||
const proceed = await Dialog.confirm({
|
||||
title: "Drug Stacking Warning",
|
||||
content: `<p><strong>${actor.name}</strong> already has active drug effects from: <strong>${activeNames}</strong>.</p>
|
||||
<p>Combining drugs can cause unpredictable or lethal interactions. Do you want to proceed?</p>`,
|
||||
defaultYes: false
|
||||
});
|
||||
if (!proceed) return { ok: false, reason: "stacking-cancelled" };
|
||||
}
|
||||
|
||||
const quantity = Math.max(0, Number(item.system?.quantity ?? 0));
|
||||
if (consume && quantity < 1) {
|
||||
ui.notifications.warn(`${actor.name} has no ${def.name} doses remaining.`);
|
||||
|
||||
@@ -904,6 +904,13 @@ export class SLAMothershipGenerator extends FormApplication {
|
||||
const worldItem = findWorldItem(morph.name, "ability");
|
||||
if (worldItem) {
|
||||
const embedded = toEmbeddedData(worldItem);
|
||||
// abilityType "morph" is schema-defined and guaranteed to be stored —
|
||||
// this prevents the Ebb enforcement sweep from ever deleting morph forms.
|
||||
embedded.system ??= {};
|
||||
embedded.system.sla ??= {};
|
||||
embedded.system.sla.abilityType = "morph";
|
||||
embedded.system.sla.morphForm = true;
|
||||
embedded.system.sla.isStartingForm = morph.name === startingMorphForm;
|
||||
items.push(embedded);
|
||||
} else {
|
||||
// Build a minimal ability document so the character isn't empty-handed.
|
||||
@@ -916,6 +923,7 @@ export class SLAMothershipGenerator extends FormApplication {
|
||||
summary: morph.summary,
|
||||
special: morph.special,
|
||||
sla: {
|
||||
abilityType: "morph",
|
||||
morphForm: true,
|
||||
instabilityCost: morph.instabilityCost,
|
||||
statMods: morph.statMods ?? {},
|
||||
|
||||
@@ -0,0 +1,853 @@
|
||||
import { SLAMothershipGenerator } from "./sla-character-generator.js";
|
||||
|
||||
const SYSTEM_ID = "sla-mothership";
|
||||
const ROOT_ACTOR_FOLDER = "SLA Mothership";
|
||||
const NPC_FOLDER = "NPCs";
|
||||
|
||||
const NPC_ARCHETYPES = {
|
||||
"Civilian Witness": {
|
||||
summary: "Clerks, residents, dock workers, minor officials, and bystanders with enough identity to question or endanger.",
|
||||
stats: { combat: 18, instinct: 32, speed: 24, loyalty: 46, sanity: 36, armor: 0, damageReduction: 0, health: 8, hits: 1 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: false },
|
||||
skills: [
|
||||
{ name: "Persuade", bonus: 20 },
|
||||
{ name: "Spot Hidden", bonus: 25 },
|
||||
{ name: "Drive (Civilian)", bonus: 20 },
|
||||
{ name: "Bureaucracy", bonus: 15 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Civilian: ["Street Clothes / Leather Jacket", "UV / Multi-Spectrum Torch", "Oyster Card (ITB Card)"]
|
||||
},
|
||||
defaultLoadout: "Civilian",
|
||||
defaultRole: "Witness / Local",
|
||||
defaultAffiliation: "Mort Civilian",
|
||||
defaultDepartment: "Local District"
|
||||
},
|
||||
"Street Ganger": {
|
||||
summary: "Street muscle, lookouts, turf enforcers, and volatile crew members from Mort's lower tiers.",
|
||||
stats: { combat: 34, instinct: 34, speed: 30, loyalty: 24, sanity: 24, armor: 0, damageReduction: 0, health: 10, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: false, armor: false },
|
||||
skills: [
|
||||
{ name: "Brawl", bonus: 25 },
|
||||
{ name: "Streetwise", bonus: 25 },
|
||||
{ name: "Intimidate", bonus: 20 },
|
||||
{ name: "Dodge", bonus: 20 },
|
||||
{ name: "Firearm (Pistol)", bonus: 20 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
"Street Melee": ["Collapsible Baton", "Standard Combat Knife", "Street Clothes / Leather Jacket"],
|
||||
Sidearm: ["FEN 603 Auto-Pistol", "Standard Combat Knife", "Street Clothes / Leather Jacket"]
|
||||
},
|
||||
defaultLoadout: "Sidearm",
|
||||
defaultRole: "Street Gang Enforcer",
|
||||
defaultAffiliation: "Local Street Gang",
|
||||
defaultDepartment: "Turf Crew"
|
||||
},
|
||||
"Shiver Patrol": {
|
||||
summary: "Street cops, precinct enforcers, and cordon teams good for patrol scenes, arrests, and fast escalation.",
|
||||
stats: { combat: 44, instinct: 38, speed: 34, loyalty: 58, sanity: 36, armor: 3, damageReduction: 1, health: 12, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Firearm (Pistol)", bonus: 30 },
|
||||
{ name: "Firearm (SMG)", bonus: 25 },
|
||||
{ name: "Athletics", bonus: 20 },
|
||||
{ name: "Command", bonus: 20 },
|
||||
{ name: "Spot Hidden", bonus: 25 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Patrol: ["FEN 401 Shiver Pistol", "Collapsible Baton", "Shiver Flak Vest"],
|
||||
"SMG Team": ["FEN 209 Machine Pistol", "Collapsible Baton", "Full Shiver Armour"]
|
||||
},
|
||||
defaultLoadout: "Patrol",
|
||||
defaultRole: "Shiver Patrol Officer",
|
||||
defaultAffiliation: "SLA Industries",
|
||||
defaultDepartment: "Shiver Precinct"
|
||||
},
|
||||
"Corp Operative": {
|
||||
summary: "Standard corporate assets, contract staff, or in-house operatives for Mort departments and sponsor interests.",
|
||||
stats: { combat: 40, instinct: 40, speed: 32, loyalty: 50, sanity: 40, armor: 2, damageReduction: 0, health: 11, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Firearm (Pistol)", bonus: 25 },
|
||||
{ name: "Command", bonus: 20 },
|
||||
{ name: "Spot Hidden", bonus: 20 },
|
||||
{ name: "Bureaucracy", bonus: 20 },
|
||||
{ name: "Persuade", bonus: 15 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Sidearm: ["FEN 603 Auto-Pistol", "Street Clothes / Leather Jacket"],
|
||||
"Field Agent": ["FEN 209 Machine Pistol", "Shiver Flak Vest", "Klippo Multi-Band Communicator"]
|
||||
},
|
||||
defaultLoadout: "Field Agent",
|
||||
defaultAffiliationType: "Corporation",
|
||||
defaultRole: "Corporate Operative",
|
||||
defaultAffiliation: "SLA Industries",
|
||||
defaultDepartment: "Operations",
|
||||
defaultSector: "Mort City"
|
||||
},
|
||||
Media: {
|
||||
summary: "Reporters, propaganda staff, image handlers, and camera teams who shape the public story while staying very close to the danger.",
|
||||
stats: { combat: 20, instinct: 42, speed: 28, loyalty: 44, sanity: 42, armor: 1, damageReduction: 0, health: 9, hits: 1 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Persuade", bonus: 30 },
|
||||
{ name: "Fast Talk", bonus: 25 },
|
||||
{ name: "SLA Info", bonus: 25 },
|
||||
{ name: "Spot Hidden", bonus: 20 },
|
||||
{ name: "Intimidate", bonus: 15 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Press: ["Klippo Multi-Band Communicator", "UV / Multi-Spectrum Torch", "Street Clothes / Leather Jacket"],
|
||||
"Embedded Crew": ["FEN 603 Auto-Pistol", "Klippo Multi-Band Communicator", "Street Clothes / Leather Jacket"]
|
||||
},
|
||||
defaultLoadout: "Press",
|
||||
defaultAffiliationType: "Corporation",
|
||||
defaultRole: "Media Correspondent",
|
||||
defaultAffiliation: "SLA Media",
|
||||
defaultDepartment: "Editorial / Field Unit",
|
||||
defaultSector: "Downtown Mort"
|
||||
},
|
||||
"Internal Affairs": {
|
||||
summary: "Cold, suspicious investigators and auditors used for leak hunts, corruption probes, and quiet pressure on operatives or departments.",
|
||||
stats: { combat: 34, instinct: 48, speed: 28, loyalty: 56, sanity: 44, armor: 2, damageReduction: 0, health: 10, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Bureaucracy", bonus: 30 },
|
||||
{ name: "Psychology", bonus: 25 },
|
||||
{ name: "Intimidate", bonus: 25 },
|
||||
{ name: "Command", bonus: 20 },
|
||||
{ name: "Firearm (Pistol)", bonus: 20 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Audit: ["FEN 603 Auto-Pistol", "Klippo Multi-Band Communicator", "Street Clothes / Leather Jacket"],
|
||||
Pressure: ["FEN 401 Shiver Pistol", "Shiver Flak Vest", "Klippo Multi-Band Communicator"]
|
||||
},
|
||||
defaultLoadout: "Audit",
|
||||
defaultAffiliationType: "Department",
|
||||
defaultRole: "Internal Affairs Investigator",
|
||||
defaultAffiliation: "SLA Industries",
|
||||
defaultDepartment: "Internal Affairs",
|
||||
defaultSector: "Cannibal Sectors"
|
||||
},
|
||||
"DarkNight Agent": {
|
||||
summary: "Hard, covert, and unpleasant professionals for pressure scenes, black-bag work, and very bad conversations.",
|
||||
stats: { combat: 52, instinct: 48, speed: 42, loyalty: 42, sanity: 44, armor: 4, damageReduction: 2, health: 13, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Stealth", bonus: 30 },
|
||||
{ name: "Dodge", bonus: 25 },
|
||||
{ name: "Spot Hidden", bonus: 30 },
|
||||
{ name: "Firearm (SMG)", bonus: 30 },
|
||||
{ name: "Intimidate", bonus: 25 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
"Strike Agent": ["FEN 209 Machine Pistol", "Standard Combat Knife", "Stealth Suit"],
|
||||
Breach: ["FEN AR Assault Rifle", "Fragmentation Grenade", "Crackshot Armour"]
|
||||
},
|
||||
defaultLoadout: "Strike Agent",
|
||||
defaultAffiliationType: "Squad",
|
||||
defaultRole: "DarkNight Agent",
|
||||
defaultAffiliation: "DarkNight",
|
||||
defaultDepartment: "Black Unit",
|
||||
defaultSector: "Cannibal Sectors"
|
||||
},
|
||||
"Tek Specialist": {
|
||||
summary: "Engineers, locks-and-systems staff, data handlers, and machine-facing support assets.",
|
||||
stats: { combat: 26, instinct: 42, speed: 28, loyalty: 46, sanity: 40, armor: 1, damageReduction: 0, health: 9, hits: 1 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: true, sanity: true, armor: true },
|
||||
skills: [
|
||||
{ name: "Computer Systems", bonus: 30 },
|
||||
{ name: "Tech (Computers & AI)", bonus: 25 },
|
||||
{ name: "Tech (Electronics)", bonus: 25 },
|
||||
{ name: "Spot Hidden", bonus: 20 },
|
||||
{ name: "Firearm (Pistol)", bonus: 15 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Utility: ["FEN 603 Auto-Pistol", "Klippo Multi-Band Communicator", "UV / Multi-Spectrum Torch"],
|
||||
"Field Tek": ["FEN 603 Auto-Pistol", "BOOPA Medical Kit (Standard)", "Klippo Multi-Band Communicator"]
|
||||
},
|
||||
defaultLoadout: "Utility",
|
||||
defaultAffiliationType: "Department",
|
||||
defaultRole: "Tek Specialist",
|
||||
defaultAffiliation: "Tek Division",
|
||||
defaultDepartment: "Systems",
|
||||
defaultSector: "Industrial Edge"
|
||||
},
|
||||
"Ebb Operative": {
|
||||
summary: "Psychic intervention assets, occult handlers, and dangerous minds kept near the edge of tolerable doctrine.",
|
||||
stats: { combat: 30, instinct: 46, speed: 24, loyalty: 30, sanity: 46, armor: 0, damageReduction: 0, health: 9, hits: 2 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: false, sanity: true, armor: false },
|
||||
skills: [
|
||||
{ name: "Biofeedback", bonus: 25 },
|
||||
{ name: "Formulate", bonus: 25 },
|
||||
{ name: "Ebb (Core)", bonus: 25 },
|
||||
{ name: "Spot Hidden", bonus: 20 },
|
||||
{ name: "Firearm (Pistol)", bonus: 15 }
|
||||
],
|
||||
loadouts: {
|
||||
None: [],
|
||||
Focus: ["FEN 603 Auto-Pistol", "BOOPA Medical Kit (Standard)", "Klippo Multi-Band Communicator"]
|
||||
},
|
||||
defaultLoadout: "Focus",
|
||||
defaultAffiliationType: "Department",
|
||||
defaultRole: "Ebb Handler",
|
||||
defaultAffiliation: "SLA Industries",
|
||||
defaultDepartment: "Ebb / Black",
|
||||
defaultSector: "Mort City"
|
||||
},
|
||||
"Predator / Beast": {
|
||||
summary: "Mutants, monsters, feral biogen threats, or engineered horrors that need only enough structure to fight and stalk.",
|
||||
stats: { combat: 46, instinct: 56, speed: 40, loyalty: 12, sanity: 10, armor: 2, damageReduction: 1, health: 14, hits: 3 },
|
||||
enabled: { combat: true, instinct: true, speed: true, loyalty: false, sanity: false, armor: true },
|
||||
skills: [
|
||||
{ name: "Brawl", bonus: 30 },
|
||||
{ name: "Athletics", bonus: 25 },
|
||||
{ name: "Dodge", bonus: 20 },
|
||||
{ name: "Spot Hidden", bonus: 25 }
|
||||
],
|
||||
loadouts: {
|
||||
None: []
|
||||
},
|
||||
defaultLoadout: "None",
|
||||
defaultAffiliationType: "Independent",
|
||||
defaultRole: "Hunting Threat",
|
||||
defaultAffiliation: "Hostile Specimen",
|
||||
defaultDepartment: "Wild / Uncontrolled",
|
||||
defaultSector: "Waste District"
|
||||
}
|
||||
};
|
||||
|
||||
const QUALITY_MODS = {
|
||||
Rabble: { stat: -8, skill: -10, health: -2, hits: 0 },
|
||||
Standard: { stat: 0, skill: 0, health: 0, hits: 0 },
|
||||
Veteran: { stat: 6, skill: 5, health: 1, hits: 0 },
|
||||
Elite: { stat: 10, skill: 10, health: 2, hits: 1 },
|
||||
Boss: { stat: 14, skill: 15, health: 4, hits: 1 }
|
||||
};
|
||||
|
||||
const DISPOSITIONS = ["Neutral", "Professional", "Hostile", "Nervous", "Fanatical", "Cornered", "Corrupt", "Helpful"];
|
||||
const THREAT_TIERS = ["Low", "Moderate", "High", "Extreme"];
|
||||
const AFFILIATION_TYPES = ["Department", "Gang", "Corporation", "Cult", "Squad", "Civic", "Independent"];
|
||||
|
||||
const ROLE_SNIPPETS = {
|
||||
"Civilian Witness": ["Transit clerk", "Dock handler", "Apartment resident", "Witness under pressure", "Small trader"],
|
||||
"Street Ganger": ["Lookout", "Enforcer", "Runner", "Debt collector", "Back-alley bruiser"],
|
||||
"Shiver Patrol": ["Patrol officer", "Checkpoint lead", "Riot response cop", "Beat sergeant", "Scene controller"],
|
||||
"Corp Operative": ["Case handler", "Recovery agent", "Sponsor fixer", "Quiet escort", "Internal security operative"],
|
||||
Media: ["Field correspondent", "Embedded camera lead", "Image handler", "Narrative producer", "Live scene reporter"],
|
||||
"Internal Affairs": ["Audit investigator", "Leak hunter", "Corruption examiner", "Interrogation lead", "Compliance agent"],
|
||||
"DarkNight Agent": ["Pressure asset", "Black-bag specialist", "Interdiction hunter", "Silent breach lead", "Cleanup professional"],
|
||||
"Tek Specialist": ["Systems breach tech", "Maintenance lead", "Field engineer", "Data recovery tech", "Signals operator"],
|
||||
"Ebb Operative": ["Control asset", "Psi observer", "Occult investigator", "Flux-sensitive handler", "Discreet interventionist"],
|
||||
"Predator / Beast": ["Tunnel stalker", "Waste-zone hunter", "Escaped specimen", "Territory alpha", "Feral ambusher"]
|
||||
};
|
||||
|
||||
const AFFILIATION_SNIPPETS = {
|
||||
Department: ["Mort Department", "Ops Con", "Shiver Precinct", "Tek Division", "Cannibal Sector Authority"],
|
||||
Gang: ["Chrome Jacks", "Sump Dogs", "Red Wire Crew", "Murder Mile Kings", "Ash-Sector Runners"],
|
||||
Corporation: ["SLA Industries", "FEN", "Wraithen Security", "MediCore", "Tek Division"],
|
||||
Cult: ["The True Noise", "Church of White Fire", "The Bent Halo", "The Last Broadcast", "Ash Choir"],
|
||||
Squad: ["Blue BPN Hold Team", "Black Transit Unit", "Sweep Detail", "Strike Cell Seven", "Special Recovery Team"],
|
||||
Civic: ["Transit Maintenance", "Block Committee", "Waste Processing", "Public Utility", "Relocation Office"],
|
||||
Independent: ["Freelance crew", "Mercenary pair", "Broker network", "Private fixer", "Unaffiliated contact"]
|
||||
};
|
||||
|
||||
const DEPARTMENT_SNIPPETS = {
|
||||
"Civilian Witness": ["Hab Block", "Transit", "Utility", "Street Market", "Dock Quarter"],
|
||||
"Street Ganger": ["East Cut", "Underline", "Recycling Stack", "Canal Row", "Tunnel Nine"],
|
||||
"Shiver Patrol": ["Precinct 88", "Riot Control", "Street Division", "Transit Policing", "Evidence Escort"],
|
||||
"Corp Operative": ["Internal Security", "Investigations", "Sponsor Liaison", "Logistics Recovery", "Operations"],
|
||||
Media: ["Editorial Desk", "Live Scene Unit", "Mort Broadcast", "Image Control", "Public Feed Team"],
|
||||
"Internal Affairs": ["Compliance Review", "Leak Office", "Audit Section", "Disciplinary Unit", "Special Oversight"],
|
||||
"DarkNight Agent": ["Silent Entry", "Black Archive", "Pressure Cell", "Removal Team", "Interdiction"],
|
||||
"Tek Specialist": ["Signals", "Maintenance", "Surveillance", "Field Systems", "Machine Control"],
|
||||
"Ebb Operative": ["Occult Oversight", "Black Psi", "Flux Watch", "Intervention Cell", "Containment"],
|
||||
"Predator / Beast": ["Den", "Nest", "Territory", "Spore Cluster", "Hunting Ground"]
|
||||
};
|
||||
|
||||
export class SLANpcGeneratorApp extends FormApplication {
|
||||
constructor(options = {}) {
|
||||
super(options);
|
||||
this.formState = null;
|
||||
}
|
||||
|
||||
static get defaultOptions() {
|
||||
return foundry.utils.mergeObject(super.defaultOptions, {
|
||||
id: "sla-npc-generator",
|
||||
classes: ["mosh", "sheet", "sla-generator", "sla-npc-generator"],
|
||||
template: "systems/sla-mothership/templates/dialogs/sla-npc-generator.html",
|
||||
width: 780,
|
||||
height: "auto",
|
||||
submitOnChange: false,
|
||||
closeOnSubmit: false
|
||||
});
|
||||
}
|
||||
|
||||
get title() {
|
||||
return "SLA NPC Desk";
|
||||
}
|
||||
|
||||
async getData() {
|
||||
await SLAMothershipGenerator.ensureSeedData();
|
||||
const seed = await SLAMothershipGenerator.loadSeedData();
|
||||
const speciesOptions = seed.species.species.map((entry) => entry.name);
|
||||
const state = this.formState ?? this.defaultState(speciesOptions);
|
||||
this.formState = state;
|
||||
|
||||
const archetype = NPC_ARCHETYPES[state.archetype] ?? NPC_ARCHETYPES["Street Ganger"];
|
||||
const loadoutOptions = Object.keys(archetype.loadouts ?? { None: [] });
|
||||
|
||||
return {
|
||||
state,
|
||||
accentKey: getArchetypeAccentKey(state.archetype),
|
||||
archetypes: Object.entries(NPC_ARCHETYPES).map(([name, entry]) => ({ name, summary: entry.summary })),
|
||||
speciesOptions,
|
||||
qualityOptions: Object.keys(QUALITY_MODS),
|
||||
dispositionOptions: DISPOSITIONS,
|
||||
threatOptions: THREAT_TIERS,
|
||||
affiliationTypes: AFFILIATION_TYPES,
|
||||
loadoutOptions,
|
||||
summary: archetype.summary,
|
||||
preview: buildNpcPreview(state, archetype)
|
||||
};
|
||||
}
|
||||
|
||||
defaultState(speciesOptions = []) {
|
||||
const archetype = "Street Ganger";
|
||||
const config = NPC_ARCHETYPES[archetype];
|
||||
return {
|
||||
name: SLAMothershipGenerator.randomName(),
|
||||
archetype,
|
||||
quality: "Standard",
|
||||
species: speciesOptions.includes("Human") ? "Human" : (speciesOptions[0] ?? "Human"),
|
||||
affiliationType: config.defaultAffiliationType ?? "Gang",
|
||||
affiliation: config.defaultAffiliation,
|
||||
department: config.defaultDepartment,
|
||||
role: config.defaultRole,
|
||||
sector: config.defaultSector ?? "Mort City",
|
||||
disposition: "Hostile",
|
||||
threat: "Moderate",
|
||||
loadout: config.defaultLoadout ?? "None",
|
||||
assignPortrait: true,
|
||||
openSheet: true,
|
||||
notes: ""
|
||||
};
|
||||
}
|
||||
|
||||
activateListeners(html) {
|
||||
super.activateListeners(html);
|
||||
|
||||
html.find(".sla-npc-random-name").on("click", () => {
|
||||
html.find("[name='name']").val(SLAMothershipGenerator.randomName());
|
||||
});
|
||||
|
||||
html.find(".sla-npc-randomize").on("click", async () => {
|
||||
const state = this.collectState(html);
|
||||
const randomized = this.randomizeState(state);
|
||||
this.formState = randomized;
|
||||
await this.render(false);
|
||||
});
|
||||
|
||||
html.find("[name='archetype']").on("change", async () => {
|
||||
const current = this.collectState(html);
|
||||
this.formState = this.rethemeStateForArchetype(current, current.archetype);
|
||||
await this.render(false);
|
||||
});
|
||||
|
||||
const rerenderSelectors = [
|
||||
"[name='quality']",
|
||||
"[name='species']",
|
||||
"[name='disposition']",
|
||||
"[name='threat']",
|
||||
"[name='loadout']",
|
||||
"[name='affiliationType']"
|
||||
];
|
||||
|
||||
for (const selector of rerenderSelectors) {
|
||||
html.find(selector).on("change", async () => {
|
||||
this.formState = this.collectState(html);
|
||||
await this.render(false);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
collectState(html) {
|
||||
return {
|
||||
name: String(html.find("[name='name']").val() ?? "").trim(),
|
||||
archetype: String(html.find("[name='archetype']").val() ?? "Street Ganger"),
|
||||
quality: String(html.find("[name='quality']").val() ?? "Standard"),
|
||||
species: String(html.find("[name='species']").val() ?? "Human"),
|
||||
affiliationType: String(html.find("[name='affiliationType']").val() ?? "Department"),
|
||||
affiliation: String(html.find("[name='affiliation']").val() ?? "").trim(),
|
||||
department: String(html.find("[name='department']").val() ?? "").trim(),
|
||||
role: String(html.find("[name='role']").val() ?? "").trim(),
|
||||
sector: String(html.find("[name='sector']").val() ?? "").trim(),
|
||||
disposition: String(html.find("[name='disposition']").val() ?? "Neutral"),
|
||||
threat: String(html.find("[name='threat']").val() ?? "Moderate"),
|
||||
loadout: String(html.find("[name='loadout']").val() ?? "None"),
|
||||
assignPortrait: Boolean(html.find("[name='assignPortrait']").prop("checked")),
|
||||
openSheet: Boolean(html.find("[name='openSheet']").prop("checked")),
|
||||
notes: String(html.find("[name='notes']").val() ?? "").trim()
|
||||
};
|
||||
}
|
||||
|
||||
randomizeState(current) {
|
||||
const state = { ...current };
|
||||
const archetypeName = state.archetype || randomFrom(Object.keys(NPC_ARCHETYPES)) || "Street Ganger";
|
||||
const archetype = NPC_ARCHETYPES[archetypeName] ?? NPC_ARCHETYPES["Street Ganger"];
|
||||
const themed = this.rethemeStateForArchetype(state, archetypeName);
|
||||
themed.affiliation = randomFrom(AFFILIATION_SNIPPETS[themed.affiliationType] ?? [archetype.defaultAffiliation]) ?? archetype.defaultAffiliation;
|
||||
themed.department = randomFrom(DEPARTMENT_SNIPPETS[archetypeName] ?? [archetype.defaultDepartment]) ?? archetype.defaultDepartment;
|
||||
themed.role = randomFrom(ROLE_SNIPPETS[archetypeName] ?? [archetype.defaultRole]) ?? archetype.defaultRole;
|
||||
themed.sector = randomFrom(getSectorOptionsForArchetype(archetypeName, archetype.defaultSector)) ?? (archetype.defaultSector ?? "Mort City");
|
||||
themed.disposition = randomFrom(DISPOSITIONS) ?? "Neutral";
|
||||
themed.threat = randomFrom(THREAT_TIERS) ?? "Moderate";
|
||||
themed.loadout = randomFrom(Object.keys(archetype.loadouts ?? { None: [] })) ?? "None";
|
||||
themed.name = SLAMothershipGenerator.randomName();
|
||||
return themed;
|
||||
}
|
||||
|
||||
rethemeStateForArchetype(current, archetypeName) {
|
||||
const archetype = NPC_ARCHETYPES[archetypeName] ?? NPC_ARCHETYPES["Street Ganger"];
|
||||
const next = { ...current, archetype: archetypeName };
|
||||
next.affiliationType = archetype.defaultAffiliationType ?? current.affiliationType ?? "Department";
|
||||
next.affiliation = archetype.defaultAffiliation ?? "";
|
||||
next.department = archetype.defaultDepartment ?? "";
|
||||
next.role = archetype.defaultRole ?? "";
|
||||
next.sector = archetype.defaultSector ?? "Mort City";
|
||||
next.loadout = archetype.defaultLoadout ?? "None";
|
||||
next.disposition = getDefaultDispositionForArchetype(archetypeName);
|
||||
next.threat = getDefaultThreatForArchetype(archetypeName);
|
||||
next.species = getDefaultSpeciesForArchetype(archetypeName, current.species);
|
||||
return next;
|
||||
}
|
||||
|
||||
async _updateObject(_event, formData) {
|
||||
const expanded = foundry.utils.expandObject(formData);
|
||||
const state = {
|
||||
name: String(expanded.name ?? "").trim(),
|
||||
archetype: String(expanded.archetype ?? "Street Ganger"),
|
||||
quality: String(expanded.quality ?? "Standard"),
|
||||
species: String(expanded.species ?? "Human"),
|
||||
affiliationType: String(expanded.affiliationType ?? "Department"),
|
||||
affiliation: String(expanded.affiliation ?? "").trim(),
|
||||
department: String(expanded.department ?? "").trim(),
|
||||
role: String(expanded.role ?? "").trim(),
|
||||
sector: String(expanded.sector ?? "").trim(),
|
||||
disposition: String(expanded.disposition ?? "Neutral"),
|
||||
threat: String(expanded.threat ?? "Moderate"),
|
||||
loadout: String(expanded.loadout ?? "None"),
|
||||
assignPortrait: Boolean(expanded.assignPortrait),
|
||||
openSheet: Boolean(expanded.openSheet),
|
||||
notes: String(expanded.notes ?? "").trim()
|
||||
};
|
||||
|
||||
this.formState = state;
|
||||
const result = await generateSlaNpc(state);
|
||||
if (result?.actor && state.openSheet) {
|
||||
result.actor.sheet?.render(true);
|
||||
}
|
||||
ui.notifications.info(`SLA NPC ready: ${result.actor.name}`);
|
||||
this.render(false);
|
||||
}
|
||||
|
||||
static open(options = {}) {
|
||||
return new SLANpcGeneratorApp(options).render({ force: true });
|
||||
}
|
||||
}
|
||||
|
||||
export async function generateSlaNpc(state = {}) {
|
||||
await SLAMothershipGenerator.ensureSeedData();
|
||||
const seed = await SLAMothershipGenerator.loadSeedData();
|
||||
|
||||
const archetype = NPC_ARCHETYPES[state.archetype] ?? NPC_ARCHETYPES["Street Ganger"];
|
||||
const quality = QUALITY_MODS[state.quality] ?? QUALITY_MODS.Standard;
|
||||
const speciesName = String(state.species ?? "Human").trim() || "Human";
|
||||
const resolvedName = String(state.name ?? "").trim() || SLAMothershipGenerator.randomName();
|
||||
const folder = await ensureNpcFolder();
|
||||
|
||||
const actor = await Actor.create({
|
||||
name: resolvedName,
|
||||
type: "creature",
|
||||
folder: folder.id
|
||||
});
|
||||
|
||||
const stats = applyQualityToStats(archetype.stats, quality);
|
||||
const enabled = archetype.enabled ?? {};
|
||||
const description = buildNpcDescription({ state, archetype, speciesName });
|
||||
const biography = buildNpcBiography({ state, archetype, speciesName });
|
||||
|
||||
await actor.update({
|
||||
img: SLAMothershipGenerator.resolveSpeciesImage(speciesName),
|
||||
"system.description": description,
|
||||
"system.biography": biography,
|
||||
"system.notes": String(state.notes ?? "").trim(),
|
||||
"system.health.value": stats.health,
|
||||
"system.health.max": stats.health,
|
||||
"system.hits.value": 0,
|
||||
"system.hits.max": stats.hits,
|
||||
"system.stats.combat.value": stats.combat,
|
||||
"system.stats.instinct.value": stats.instinct,
|
||||
"system.stats.speed.value": stats.speed,
|
||||
"system.stats.loyalty.value": stats.loyalty,
|
||||
"system.stats.sanity.value": stats.sanity,
|
||||
"system.stats.armor.mod": stats.armor,
|
||||
"system.stats.armor.damageReduction": stats.damageReduction,
|
||||
"system.stats.combat.enabled": Boolean(enabled.combat),
|
||||
"system.stats.instinct.enabled": Boolean(enabled.instinct),
|
||||
"system.stats.speed.enabled": Boolean(enabled.speed),
|
||||
"system.stats.loyalty.enabled": Boolean(enabled.loyalty),
|
||||
"system.stats.sanity.enabled": Boolean(enabled.sanity),
|
||||
"system.stats.armor.enabled": Boolean(enabled.armor),
|
||||
"system.slaNpc.archetype.value": state.archetype,
|
||||
"system.slaNpc.species.value": speciesName,
|
||||
"system.slaNpc.affiliationType.value": state.affiliationType,
|
||||
"system.slaNpc.affiliation.value": String(state.affiliation ?? "").trim(),
|
||||
"system.slaNpc.department.value": String(state.department ?? "").trim(),
|
||||
"system.slaNpc.role.value": String(state.role ?? "").trim(),
|
||||
"system.slaNpc.sector.value": String(state.sector ?? "").trim(),
|
||||
"system.slaNpc.disposition.value": String(state.disposition ?? "").trim(),
|
||||
"system.slaNpc.threat.value": String(state.threat ?? "").trim(),
|
||||
"system.slaNpc.summary.value": archetype.summary
|
||||
});
|
||||
|
||||
const itemPayloads = [];
|
||||
itemPayloads.push(...buildNpcSkillItems(archetype.skills ?? [], quality, seed.skills.skills));
|
||||
itemPayloads.push(...buildLoadoutItems(archetype, state.loadout));
|
||||
|
||||
if (state.archetype === "Ebb Operative" && SLAMothershipGenerator.isEbbSpecies(speciesName)) {
|
||||
itemPayloads.push(...SLAMothershipGenerator.buildEbbSkillItems(speciesName));
|
||||
itemPayloads.push(...SLAMothershipGenerator.buildEbbItems(speciesName));
|
||||
}
|
||||
|
||||
if (state.archetype === "Predator / Beast") {
|
||||
itemPayloads.push(...SLAMothershipGenerator.buildSpeciesItems(speciesName));
|
||||
}
|
||||
|
||||
const uniquePayloads = uniqueEmbeddedItems(itemPayloads);
|
||||
if (uniquePayloads.length) {
|
||||
await actor.createEmbeddedDocuments("Item", uniquePayloads);
|
||||
}
|
||||
|
||||
if (state.assignPortrait && game.npcPortraitPack?.assignPortraitToActor) {
|
||||
await game.npcPortraitPack.assignPortraitToActor(actor);
|
||||
}
|
||||
|
||||
return { actor };
|
||||
}
|
||||
|
||||
async function ensureNpcFolder() {
|
||||
let root = game.folders.find((folder) => folder.type === "Actor" && folder.name === ROOT_ACTOR_FOLDER && !folder.folder);
|
||||
if (!root) {
|
||||
root = await Folder.create({ name: ROOT_ACTOR_FOLDER, type: "Actor", color: "#163447" });
|
||||
}
|
||||
|
||||
let folder = game.folders.find((entry) => entry.type === "Actor" && entry.name === NPC_FOLDER && entry.folder?.id === root.id);
|
||||
if (!folder) {
|
||||
folder = await Folder.create({ name: NPC_FOLDER, type: "Actor", folder: root.id, color: "#5b3349" });
|
||||
}
|
||||
return folder;
|
||||
}
|
||||
|
||||
function applyQualityToStats(baseStats, quality) {
|
||||
return {
|
||||
combat: clamp98((baseStats.combat ?? 10) + (quality.stat ?? 0)),
|
||||
instinct: clamp98((baseStats.instinct ?? 10) + (quality.stat ?? 0)),
|
||||
speed: clamp98((baseStats.speed ?? 10) + (quality.stat ?? 0)),
|
||||
loyalty: clamp98((baseStats.loyalty ?? 10) + (quality.stat ?? 0)),
|
||||
sanity: clamp98((baseStats.sanity ?? 10) + (quality.stat ?? 0)),
|
||||
armor: Math.max(0, Number(baseStats.armor ?? 0)),
|
||||
damageReduction: Math.max(0, Number(baseStats.damageReduction ?? 0)),
|
||||
health: Math.max(1, Number(baseStats.health ?? 8) + Number(quality.health ?? 0)),
|
||||
hits: Math.max(1, Number(baseStats.hits ?? 1) + Number(quality.hits ?? 0))
|
||||
};
|
||||
}
|
||||
|
||||
function buildNpcSkillItems(skillDefs, quality, allSkillData = []) {
|
||||
return (skillDefs ?? [])
|
||||
.map((entry) => {
|
||||
const baseBonus = Number(entry.bonus ?? 10) + Number(quality.skill ?? 0);
|
||||
const worldItem = findWorldItem(entry.name, "skill");
|
||||
if (worldItem) {
|
||||
const embedded = toEmbeddedData(worldItem);
|
||||
embedded.system.bonus = clamp98(baseBonus);
|
||||
embedded.system.rank = rankFromBonus(embedded.system.bonus);
|
||||
embedded.system.sla ??= {};
|
||||
embedded.system.sla.baseBonus = Number(worldItem.system?.bonus ?? 0) || 0;
|
||||
embedded.system.sla.packageBonus = Math.max(0, embedded.system.bonus - Number(embedded.system.sla.baseBonus ?? 0));
|
||||
return embedded;
|
||||
}
|
||||
|
||||
const data = allSkillData.find((skill) => normalizeText(skill.name) === normalizeText(entry.name)) ?? {};
|
||||
return {
|
||||
name: entry.name,
|
||||
type: "skill",
|
||||
img: "icons/svg/upgrade.svg",
|
||||
system: {
|
||||
description: "",
|
||||
rank: rankFromBonus(baseBonus),
|
||||
bonus: clamp98(baseBonus),
|
||||
prerequisite_ids: [],
|
||||
sla: {
|
||||
category: data.categoryRef ?? "",
|
||||
skillFamily: data.categoryRef ?? "",
|
||||
source: "SLA NPC Desk"
|
||||
}
|
||||
}
|
||||
};
|
||||
})
|
||||
.filter(Boolean);
|
||||
}
|
||||
|
||||
function buildLoadoutItems(archetype, loadoutName) {
|
||||
const loadout = archetype.loadouts?.[loadoutName] ?? [];
|
||||
return loadout
|
||||
.map((name) => findWorldItem(name))
|
||||
.filter(Boolean)
|
||||
.map((item) => toEmbeddedData(item));
|
||||
}
|
||||
|
||||
function buildNpcDescription({ state, archetype, speciesName }) {
|
||||
return [
|
||||
`${state.role || archetype.defaultRole}.`,
|
||||
`${state.affiliation || archetype.defaultAffiliation}${state.department ? ` / ${state.department}` : ""}.`,
|
||||
`${state.disposition || "Neutral"} presence with ${state.threat || "Moderate"} threat pressure.`,
|
||||
`${speciesName} profile.`
|
||||
].join(" ");
|
||||
}
|
||||
|
||||
function buildNpcBiography({ state, archetype, speciesName }) {
|
||||
return `
|
||||
<p><strong>Role:</strong> ${escapeHtml(state.role || archetype.defaultRole)}</p>
|
||||
<p><strong>Affiliation:</strong> ${escapeHtml(state.affiliation || archetype.defaultAffiliation)}</p>
|
||||
<p><strong>Department / Cell:</strong> ${escapeHtml(state.department || archetype.defaultDepartment)}</p>
|
||||
<p><strong>Species:</strong> ${escapeHtml(speciesName)}</p>
|
||||
<p><strong>Disposition:</strong> ${escapeHtml(state.disposition || "Neutral")} | <strong>Threat:</strong> ${escapeHtml(state.threat || "Moderate")}</p>
|
||||
<p><strong>Sector:</strong> ${escapeHtml(state.sector || "Mort City")}</p>
|
||||
<p>${escapeHtml(archetype.summary)}</p>
|
||||
`.trim();
|
||||
}
|
||||
|
||||
function buildNpcPreview(state, archetype) {
|
||||
const quality = QUALITY_MODS[state.quality] ?? QUALITY_MODS.Standard;
|
||||
const loadoutNames = archetype.loadouts?.[state.loadout] ?? [];
|
||||
const statline = applyQualityToStats(archetype.stats, quality);
|
||||
return {
|
||||
iconPath: getArchetypeIconPath(state.archetype),
|
||||
iconLabel: getArchetypeBadgeShort(state.archetype),
|
||||
badge: getArchetypeBadge(state.archetype),
|
||||
strap: getArchetypeStrapline(state.archetype),
|
||||
identity: `${state.role || archetype.defaultRole} / ${state.species}`,
|
||||
brief: `${state.affiliation || archetype.defaultAffiliation}${state.department ? ` / ${state.department}` : ""} operating in ${state.sector || archetype.defaultSector || "Mort City"}.`,
|
||||
posture: `${state.disposition || "Neutral"} disposition with ${state.threat || "Moderate"} threat expectations.`,
|
||||
statline: [
|
||||
`Combat ${statline.combat}`,
|
||||
`Instinct ${statline.instinct}`,
|
||||
`Speed ${statline.speed}`,
|
||||
`Health ${statline.health}`,
|
||||
`Wounds ${statline.hits}`
|
||||
],
|
||||
loadout: loadoutNames.length ? loadoutNames : ["No preset issue kit selected."],
|
||||
notes: archetype.summary
|
||||
};
|
||||
}
|
||||
|
||||
function clamp98(value) {
|
||||
return Math.max(1, Math.min(98, Number(value ?? 0) || 0));
|
||||
}
|
||||
|
||||
function rankFromBonus(bonus) {
|
||||
if (bonus >= 40) return "Master";
|
||||
if (bonus >= 25) return "Expert";
|
||||
return "Trained";
|
||||
}
|
||||
|
||||
function findWorldItem(name, type = null) {
|
||||
return game.items.find((item) => normalizeText(item.name) === normalizeText(name) && (!type || item.type === type)) ?? null;
|
||||
}
|
||||
|
||||
function toEmbeddedData(document) {
|
||||
return foundry.utils.duplicate(document.toObject());
|
||||
}
|
||||
|
||||
function uniqueEmbeddedItems(items = []) {
|
||||
const seen = new Set();
|
||||
const out = [];
|
||||
for (const item of items) {
|
||||
const key = `${item.type}::${normalizeText(item.name)}`;
|
||||
if (seen.has(key)) continue;
|
||||
seen.add(key);
|
||||
out.push(item);
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
function normalizeText(value) {
|
||||
return String(value ?? "").trim().toLowerCase();
|
||||
}
|
||||
|
||||
function randomFrom(list = []) {
|
||||
if (!list.length) return null;
|
||||
return list[Math.floor(Math.random() * list.length)] ?? null;
|
||||
}
|
||||
|
||||
function getDefaultSpeciesForArchetype(archetypeName, currentSpecies = "Human") {
|
||||
if (archetypeName === "Ebb Operative") return "Ebon";
|
||||
if (archetypeName === "Predator / Beast") return "Advanced Carrien";
|
||||
return currentSpecies || "Human";
|
||||
}
|
||||
|
||||
function getDefaultDispositionForArchetype(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Civilian Witness": return "Nervous";
|
||||
case "Street Ganger": return "Hostile";
|
||||
case "Shiver Patrol": return "Professional";
|
||||
case "Corp Operative": return "Professional";
|
||||
case "Media": return "Corrupt";
|
||||
case "Internal Affairs": return "Professional";
|
||||
case "DarkNight Agent": return "Hostile";
|
||||
case "Tek Specialist": return "Professional";
|
||||
case "Ebb Operative": return "Cornered";
|
||||
case "Predator / Beast": return "Fanatical";
|
||||
default: return "Neutral";
|
||||
}
|
||||
}
|
||||
|
||||
function getDefaultThreatForArchetype(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Civilian Witness": return "Low";
|
||||
case "Street Ganger": return "Moderate";
|
||||
case "Shiver Patrol": return "Moderate";
|
||||
case "Corp Operative": return "Moderate";
|
||||
case "Media": return "Low";
|
||||
case "Internal Affairs": return "Moderate";
|
||||
case "DarkNight Agent": return "High";
|
||||
case "Tek Specialist": return "Moderate";
|
||||
case "Ebb Operative": return "High";
|
||||
case "Predator / Beast": return "Extreme";
|
||||
default: return "Moderate";
|
||||
}
|
||||
}
|
||||
|
||||
function getSectorOptionsForArchetype(archetypeName, fallback = "Mort City") {
|
||||
switch (archetypeName) {
|
||||
case "Street Ganger":
|
||||
return ["Cannibal Sectors", "Transit Underlevels", "Waste District", "Mort City"];
|
||||
case "Shiver Patrol":
|
||||
return ["Mort City", "Downtown Mort", "Transit Underlevels", "Cannibal Sectors"];
|
||||
case "Corp Operative":
|
||||
return ["Mort City", "Downtown Mort", "Industrial Edge", "Cannibal Sectors"];
|
||||
case "Media":
|
||||
return ["Downtown Mort", "Mort City", "Cannibal Sectors", "Transit Underlevels"];
|
||||
case "Internal Affairs":
|
||||
return ["Cannibal Sectors", "Mort City", "Downtown Mort", "Industrial Edge"];
|
||||
case "DarkNight Agent":
|
||||
return ["Cannibal Sectors", "Transit Underlevels", "Mort City", "Waste District"];
|
||||
case "Tek Specialist":
|
||||
return ["Industrial Edge", "Mort City", "Transit Underlevels", "Downtown Mort"];
|
||||
case "Ebb Operative":
|
||||
return ["Mort City", "Cannibal Sectors", "Downtown Mort"];
|
||||
case "Predator / Beast":
|
||||
return ["Waste District", "Cannibal Sectors", "Transit Underlevels", "Industrial Edge"];
|
||||
default:
|
||||
return [fallback, "Mort City", "Downtown Mort"];
|
||||
}
|
||||
}
|
||||
|
||||
function escapeHtml(value) {
|
||||
return String(value ?? "")
|
||||
.replaceAll("&", "&")
|
||||
.replaceAll("<", "<")
|
||||
.replaceAll(">", ">")
|
||||
.replaceAll('"', """)
|
||||
.replaceAll("'", "'");
|
||||
}
|
||||
|
||||
function getArchetypeAccentKey(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Shiver Patrol": return "shiver";
|
||||
case "DarkNight Agent": return "darknight";
|
||||
case "Tek Specialist": return "tek";
|
||||
case "Ebb Operative": return "ebb";
|
||||
case "Media": return "media";
|
||||
case "Internal Affairs": return "internal";
|
||||
case "Street Ganger": return "gang";
|
||||
case "Predator / Beast": return "predator";
|
||||
case "Civilian Witness": return "civilian";
|
||||
case "Corp Operative": return "corp";
|
||||
default: return "corp";
|
||||
}
|
||||
}
|
||||
|
||||
function getArchetypeBadge(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Shiver Patrol": return "Shiver Patrol";
|
||||
case "DarkNight Agent": return "DarkNight";
|
||||
case "Tek Specialist": return "Tek Division";
|
||||
case "Ebb Operative": return "Ebb Control";
|
||||
case "Media": return "Media Feed";
|
||||
case "Internal Affairs": return "Internal Affairs";
|
||||
case "Street Ganger": return "Street Threat";
|
||||
case "Predator / Beast": return "Hostile Specimen";
|
||||
case "Civilian Witness": return "Civilian Contact";
|
||||
case "Corp Operative": return "Corporate Asset";
|
||||
default: return archetypeName;
|
||||
}
|
||||
}
|
||||
|
||||
function getArchetypeBadgeShort(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Shiver Patrol": return "SV";
|
||||
case "DarkNight Agent": return "DN";
|
||||
case "Tek Specialist": return "TK";
|
||||
case "Ebb Operative": return "EB";
|
||||
case "Media": return "MD";
|
||||
case "Internal Affairs": return "IA";
|
||||
case "Street Ganger": return "SG";
|
||||
case "Predator / Beast": return "HX";
|
||||
case "Civilian Witness": return "CV";
|
||||
case "Corp Operative": return "CO";
|
||||
default: return "NPC";
|
||||
}
|
||||
}
|
||||
|
||||
function getArchetypeIconPath(archetypeName) {
|
||||
const root = "systems/sla-mothership/icons/ui/npc-badges";
|
||||
switch (archetypeName) {
|
||||
case "Shiver Patrol": return `${root}/shiver.svg`;
|
||||
case "DarkNight Agent": return `${root}/darknight.svg`;
|
||||
case "Tek Specialist": return `${root}/tek.svg`;
|
||||
case "Ebb Operative": return `${root}/ebb.svg`;
|
||||
case "Media": return `${root}/media.svg`;
|
||||
case "Internal Affairs": return `${root}/internal.svg`;
|
||||
case "Street Ganger": return `${root}/gang.svg`;
|
||||
case "Predator / Beast": return `${root}/predator.svg`;
|
||||
case "Civilian Witness": return `${root}/civilian.svg`;
|
||||
case "Corp Operative": return `${root}/corp.svg`;
|
||||
default: return `${root}/corp.svg`;
|
||||
}
|
||||
}
|
||||
|
||||
function getArchetypeStrapline(archetypeName) {
|
||||
switch (archetypeName) {
|
||||
case "Shiver Patrol": return "Precinct issue / patrol doctrine / fast response";
|
||||
case "DarkNight Agent": return "Black operations / pressure asset / covert response";
|
||||
case "Tek Specialist": return "Systems breach / maintenance / machine-facing support";
|
||||
case "Ebb Operative": return "Occult intervention / flux risk / psychic control";
|
||||
case "Media": return "Image control / live coverage / narrative pressure";
|
||||
case "Internal Affairs": return "Audit pressure / disciplinary review / quiet threat";
|
||||
case "Street Ganger": return "Turf violence / local intimidation / disposable muscle";
|
||||
case "Predator / Beast": return "Ferality / pursuit / close-quarters threat";
|
||||
case "Civilian Witness": return "Collateral witness / local knowledge / brittle pressure";
|
||||
case "Corp Operative": return "Corporate recovery / sponsor discipline / field oversight";
|
||||
default: return "Operational contact / generated dossier";
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
import { SLAMothershipGenerator } from "./sla-character-generator.js";
|
||||
import { SLANpcGeneratorApp } from "./sla-npc-generator.js";
|
||||
|
||||
const SYSTEM_ID = "sla-mothership";
|
||||
|
||||
@@ -22,6 +23,7 @@ export class SLAWorldToolsApp extends FormApplication {
|
||||
async getData() {
|
||||
const seededItems = game.items.filter((item) => item.flags?.[SYSTEM_ID]?.slaSeed?.key);
|
||||
const actors = game.actors.filter((actor) => actor.type === "character");
|
||||
const creatures = game.actors.filter((actor) => actor.type === "creature");
|
||||
const ebbActors = actors.filter((actor) => ["Ebon", "Brain Waster"].includes(String(actor.system?.sla?.species?.value ?? "").trim()));
|
||||
|
||||
return {
|
||||
@@ -30,6 +32,7 @@ export class SLAWorldToolsApp extends FormApplication {
|
||||
weaponCount: seededItems.filter((item) => item.type === "weapon").length,
|
||||
gearCount: seededItems.filter((item) => item.flags?.[SYSTEM_ID]?.slaSeed?.kind === "gear").length,
|
||||
actorCount: actors.length,
|
||||
creatureCount: creatures.length,
|
||||
starterCount: actors.filter((actor) => actor.flags?.[SYSTEM_ID]?.slaStarter).length,
|
||||
ebbActorCount: ebbActors.length,
|
||||
quickBattleMapBuilderReady: Boolean(game.modules?.get("quick-battlemap-builder")?.active && game.quickBattleMapBuilder?.open)
|
||||
@@ -53,6 +56,10 @@ export class SLAWorldToolsApp extends FormApplication {
|
||||
game.slaMothership.openGenerator();
|
||||
});
|
||||
|
||||
html.find(".open-npc-desk").on("click", () => {
|
||||
game.slaMothership.openNpcDesk();
|
||||
});
|
||||
|
||||
html.find(".generate-random").on("click", async () => {
|
||||
await game.slaMothership.createRandomOperative({ openSheet: true });
|
||||
this.render(false);
|
||||
@@ -127,7 +134,14 @@ export function installSlaSidebarButtons(app, html) {
|
||||
await game.slaMothership.seedWorldContent({ overwrite: true, notify: true });
|
||||
});
|
||||
|
||||
toolContainer.append(randomButton, createButton, toolsButton, refreshButton);
|
||||
const npcButton = $(`
|
||||
<button type="button" class="sla-open-npc-desk">
|
||||
<i class="fas fa-id-badge"></i> NPC Desk
|
||||
</button>
|
||||
`);
|
||||
npcButton.on("click", () => SLANpcGeneratorApp.open());
|
||||
|
||||
toolContainer.append(randomButton, createButton, npcButton, toolsButton, refreshButton);
|
||||
}
|
||||
|
||||
function findToolContainer(root) {
|
||||
|
||||
@@ -1,36 +1,36 @@
|
||||
{"_id":"2D3zgP8KtRTAqlfS","name":"Addiction","type":"condition","img":"systems/mosh/images/icons/ui/conditions/addicted.png","system":{"description":"<p>Excessive use of Pain Pills or Stimpaks requires a <strong>Body Save to prevent addiction</strong>. Once addicted, make a daily Body Save or gain 1d10 Stress every day you go without. If used once per day for a week you’ll need to take twice the amount of pills to gain the same effect.<br><br>Whenever you take more than one pill at a time roll 1d10. If you roll equal to or under the number taken make a Body Save. Failure means you fall unconscious and the Warden rolls a Death Save. You can cure an addiction through in-game treatment or leveling up.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QEVnimwq5o0DxmZz","name":"Anhedonia","type":"condition","img":"systems/mosh/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much Calm instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"23qE7TnIHxtw1E9y","name":"Bit Rot","type":"condition","img":"systems/mosh/images/icons/ui/conditions/data_loss.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZzvKo0yTqOcRP5Xo","name":"Broken","type":"condition","img":"systems/mosh/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Make a Panic Check whenever a nearby crew member fails a Save.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Qnv6ZDPsbOXLi9go","name":"Cowardice","type":"condition","img":"systems/mosh/images/icons/ui/conditions/coward.png","system":{"description":"<p>You must make a Fear Save to engage in combat or else flee.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uoeVaOy5a6BIAGAi","name":"Death Drive","type":"condition","img":"systems/mosh/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>Whenever you encounter a stranger or known enemy you must make a Sanity Save or else immediately attack them.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PiMuPeHR5EobSPBP","name":"Deviant Logic Core","type":"condition","img":"systems/mosh/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dAJRV7JG0Wh1shcJ","name":"Emotional Detachment","type":"condition","img":"systems/mosh/images/icons/ui/conditions/detached.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you gain the Panic Effect of an Android, in addition to that of your own class. If you are an Android, gain the Panic Effect of a Marine.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"6vExNGxZiXcC3RFy","name":"Escapism","type":"condition","img":"systems/mosh/images/icons/ui/conditions/addicted.png","system":{"description":"<p>You always have Disadvantage on Body Saves to prevent Addiction.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kI2Yxt0Eo2mEywpZ","name":"Ethical Directive Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you now have the Panic Effect of a Marine, in addition to that of an Android.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5E3FGlNzi05S792f","name":"Ethical Directive Misread","type":"condition","img":"systems/mosh/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>Loses any expressiveness. Discusses the irrationality of Phobias, seeks to trigger them in others.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8D9ZtBYScCKjcBH3","name":"Faulty Heuristics","type":"condition","img":"systems/mosh/images/icons/ui/conditions/faulty_heuristics.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"B8vRorrFy3c2cOf5","name":"Fried Logic Core","type":"condition","img":"systems/mosh/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Frenzied nonsensical behaviour. Whenever you lose Calm, everyone else nearby loses the same amount of Calm.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"RZ5X3UuiM0Wzg3pQ","name":"Hallucinations","type":"condition","img":"systems/mosh/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>You have trouble distinguishing between reality and fantasy.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"A3qRm3Gs36Nbfs29","name":"Hypervigilance","type":"condition","img":"systems/mosh/images/icons/ui/conditions/hypervigilance.png","system":{"description":"<p>Gain Advantage on all surprise rolls but lose 1d10 Calm every day.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9vveNoR1VA9Bx0Wo","name":"Insane","type":"condition","img":"systems/mosh/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>You become permanently, irreparably insane. Your character is now played by the Warden.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hAfwbHxZih4Xb0qi","name":"Killswitch Engaged","type":"condition","img":"systems/mosh/images/icons/ui/conditions/killswitch.png","system":{"description":"<p>Go berserk, will not withdraw from combat regardless of situation, will not adhere to tactics.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1r6ruvSdxn2bHHIk","name":"Losing Your Grip","type":"condition","img":"systems/mosh/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AXxmouWPp6Tx1JbK","name":"Panicky","type":"condition","img":"systems/mosh/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lxIZLdg2IkwOC2b9","name":"Paranoid","type":"condition","img":"systems/mosh/images/icons/ui/conditions/suspicious.png","system":{"description":"<p>Whenever a character joins your group <em>(even if they only left for a short period of time)</em>, make a Fear Save or gain 1 Stress.<><>@UUID[Compendium.mosh.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lf1QZaUHSy82w7SR","name":"Phobia","type":"condition","img":"systems/mosh/images/icons/ui/conditions/frightened.png","system":{"description":"<p>Gain a new permanent phobia. Whenever you encounter this phobia make a Fear Save at Disadvantage.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.RdJ2nh41wDUT4ZTP]{Fear Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Gm2XrTqVMbECVPan","name":"Psychotic Episodes","type":"condition","img":"systems/mosh/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"GbDO8pRNdPA5tQXE","name":"Rampancy","type":"condition","img":"systems/mosh/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round. These episodes double in duration <em>(or become twice as frequent)</em> each session.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zbKI2RCl5h3vowoy","name":"Recurring Nightmares","type":"condition","img":"systems/mosh/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Every time you rest, make a Fear save. If you fail, lose 1d10 Calm and do not heal. The Warden will describe your nightmare.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"H4UUQsZOSaYGRPSY","name":"Severe Anxiety","type":"condition","img":"systems/mosh/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xVW5zbK05EqQmaA4","name":"Social Anxiety","type":"condition","img":"systems/mosh/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose 1d10 Calm whenever you converse with someone new.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1rUlQJ5iwD29X4oT","name":"Software Bloat","type":"condition","img":"systems/mosh/images/icons/ui/conditions/software_bloat.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XxjONzW7H4tIIAkN","name":"Starving","type":"condition","img":"systems/mosh/images/icons/ui/conditions/starving.png","system":{"description":"<p>Humans can survive roughly 3 weeks without food. <strong>After 24 hours without food you’re at Disadvantage to all rolls.</strong><br><br>The bare minimum to survive: you’ll need <strong>1 liter of water a day</strong>. However, at this level any strenuous activity (like running, Combat, or making mechanical repairs) will force you to make a Body Save or pass out. When water is scarce and you’re tracking it this closely you’re at Disadvantage to all Checks.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uOPcbqhk5sQHB8A2","name":"Suffocating","type":"condition","img":"systems/mosh/images/icons/ui/conditions/suffocating.png","system":{"description":"<p>In space you can last 15 seconds without oxygen before you fall unconscious. After passing out you can survive for 3-5 minutes before dying.<br><br><ul><li>If less than half of the original oxygen remains every roll is made at Disadvantage. All crew suffer headaches, fatigue, anxiety and general clumsiness.</li><li>If less than a quarter of the original oxygen amount remains players must make a Body Save once per day (and after every strenuous activity) or fall unconscious. All crew suffer panting, dizziness, severe headaches and impaired vision and tinnitus.</li><li>If a player runs out of oxygen they must make a Body Save. Failure means they die. Success means they fall unconscious and leach oxygen from a random player every day.</li></ul></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"JV43ilZwsikj75j1","name":"The Shakes","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>You can’t keep your hands steady any more. Disadvantage on ranged attacks and all tasks requiring fine motor skills. Drugs may be able to help with this.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xlKWL5nZm3SJPhrf","name":"Threat Assessment Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>You lose the ability to discern friend from foe, treating all vaguely-humanoid entities as you would members of your crew.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iZzcfZ26I2svoonl","name":"Turing Test Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/turing_test_failure.png","system":{"description":"<p>Have difficulty expressing humanity. Party members make a Fear Save whenever you show up.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"qsOHsbKMonl9tiaq","name":"Twitchy","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>Your manual tasks have Disadvantage.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"x0YRvBbVoHPILD6x","name":"Vocalization Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/vocalization_failure.png","system":{"description":"<p>Intermittently shrieks like a fax machine under duress. Lapses into morse code, cannot communicate or sneak.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZIYe2ULX7AKP5MVI","name":"Worship Danger","type":"condition","img":"systems/mosh/images/icons/ui/conditions/worship_danger.png","system":{"description":"<p>Becomes Nihilistically Worshipful of the Source of Danger. Everyone else has Disadvantage on rolls against it. Everyone else takes a Fear save when failing to act against danger or gains a Phobia.<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}<br><br>@UUID[Compendium.mosh.macros_triggered_0e.Macro.qwmJTfTgmjNEApfX]{+1 Phobia}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8Ypj7tMZqoMYsqVJ","name":"The Bends","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_bends.png","system":{"description":"<p>You doubt the true nature of your identity. If you are human, you have started to believe you may be an android with implanted memories. If you are an android, you have started to believe you are a real person.<br><br>The severity of this condition starts at 5 unless you still have your <strong>Trinket</strong> from character creation, in which case it starts at 0. The Bends can never be decreased below 5, unless you never lose control of your Trinket. So you should never lose it. <strong>Ever.</strong></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"2D3zgP8KtRTAqlfS","name":"Addiction","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/addicted.png","system":{"description":"<p>Excessive use of Pain Pills or Stimpaks requires a <strong>Body Save to prevent addiction</strong>. Once addicted, make a daily Body Save or gain 1d10 Stress every day you go without. If used once per day for a week you’ll need to take twice the amount of pills to gain the same effect.<br><br>Whenever you take more than one pill at a time roll 1d10. If you roll equal to or under the number taken make a Body Save. Failure means you fall unconscious and the Warden rolls a Death Save. You can cure an addiction through in-game treatment or leveling up.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QEVnimwq5o0DxmZz","name":"Anhedonia","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much Calm instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"23qE7TnIHxtw1E9y","name":"Bit Rot","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/data_loss.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZzvKo0yTqOcRP5Xo","name":"Broken","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Make a Panic Check whenever a nearby crew member fails a Save.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Qnv6ZDPsbOXLi9go","name":"Cowardice","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/coward.png","system":{"description":"<p>You must make a Fear Save to engage in combat or else flee.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uoeVaOy5a6BIAGAi","name":"Death Drive","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>Whenever you encounter a stranger or known enemy you must make a Sanity Save or else immediately attack them.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PiMuPeHR5EobSPBP","name":"Deviant Logic Core","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dAJRV7JG0Wh1shcJ","name":"Emotional Detachment","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/detached.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you gain the Panic Effect of an Android, in addition to that of your own class. If you are an Android, gain the Panic Effect of a Marine.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"6vExNGxZiXcC3RFy","name":"Escapism","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/addicted.png","system":{"description":"<p>You always have Disadvantage on Body Saves to prevent Addiction.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kI2Yxt0Eo2mEywpZ","name":"Ethical Directive Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you now have the Panic Effect of a Marine, in addition to that of an Android.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5E3FGlNzi05S792f","name":"Ethical Directive Misread","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>Loses any expressiveness. Discusses the irrationality of Phobias, seeks to trigger them in others.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8D9ZtBYScCKjcBH3","name":"Faulty Heuristics","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/faulty_heuristics.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"B8vRorrFy3c2cOf5","name":"Fried Logic Core","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Frenzied nonsensical behaviour. Whenever you lose Calm, everyone else nearby loses the same amount of Calm.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"RZ5X3UuiM0Wzg3pQ","name":"Hallucinations","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>You have trouble distinguishing between reality and fantasy.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"A3qRm3Gs36Nbfs29","name":"Hypervigilance","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/hypervigilance.png","system":{"description":"<p>Gain Advantage on all surprise rolls but lose 1d10 Calm every day.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9vveNoR1VA9Bx0Wo","name":"Insane","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>You become permanently, irreparably insane. Your character is now played by the Warden.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hAfwbHxZih4Xb0qi","name":"Killswitch Engaged","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/killswitch.png","system":{"description":"<p>Go berserk, will not withdraw from combat regardless of situation, will not adhere to tactics.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1r6ruvSdxn2bHHIk","name":"Losing Your Grip","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AXxmouWPp6Tx1JbK","name":"Panicky","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lxIZLdg2IkwOC2b9","name":"Paranoid","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/suspicious.png","system":{"description":"<p>Whenever a character joins your group <em>(even if they only left for a short period of time)</em>, make a Fear Save or gain 1 Stress.<><>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lf1QZaUHSy82w7SR","name":"Phobia","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/frightened.png","system":{"description":"<p>Gain a new permanent phobia. Whenever you encounter this phobia make a Fear Save at Disadvantage.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.RdJ2nh41wDUT4ZTP]{Fear Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Gm2XrTqVMbECVPan","name":"Psychotic Episodes","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"GbDO8pRNdPA5tQXE","name":"Rampancy","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round. These episodes double in duration <em>(or become twice as frequent)</em> each session.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zbKI2RCl5h3vowoy","name":"Recurring Nightmares","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Every time you rest, make a Fear save. If you fail, lose 1d10 Calm and do not heal. The Warden will describe your nightmare.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"H4UUQsZOSaYGRPSY","name":"Severe Anxiety","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xVW5zbK05EqQmaA4","name":"Social Anxiety","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose 1d10 Calm whenever you converse with someone new.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.5jMEd9JjJPIJBKHr]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1rUlQJ5iwD29X4oT","name":"Software Bloat","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/software_bloat.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XxjONzW7H4tIIAkN","name":"Starving","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/starving.png","system":{"description":"<p>Humans can survive roughly 3 weeks without food. <strong>After 24 hours without food you’re at Disadvantage to all rolls.</strong><br><br>The bare minimum to survive: you’ll need <strong>1 liter of water a day</strong>. However, at this level any strenuous activity (like running, Combat, or making mechanical repairs) will force you to make a Body Save or pass out. When water is scarce and you’re tracking it this closely you’re at Disadvantage to all Checks.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uOPcbqhk5sQHB8A2","name":"Suffocating","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/suffocating.png","system":{"description":"<p>In space you can last 15 seconds without oxygen before you fall unconscious. After passing out you can survive for 3-5 minutes before dying.<br><br><ul><li>If less than half of the original oxygen remains every roll is made at Disadvantage. All crew suffer headaches, fatigue, anxiety and general clumsiness.</li><li>If less than a quarter of the original oxygen amount remains players must make a Body Save once per day (and after every strenuous activity) or fall unconscious. All crew suffer panting, dizziness, severe headaches and impaired vision and tinnitus.</li><li>If a player runs out of oxygen they must make a Body Save. Failure means they die. Success means they fall unconscious and leach oxygen from a random player every day.</li></ul></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"JV43ilZwsikj75j1","name":"The Shakes","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>You can’t keep your hands steady any more. Disadvantage on ranged attacks and all tasks requiring fine motor skills. Drugs may be able to help with this.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xlKWL5nZm3SJPhrf","name":"Threat Assessment Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>You lose the ability to discern friend from foe, treating all vaguely-humanoid entities as you would members of your crew.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iZzcfZ26I2svoonl","name":"Turing Test Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/turing_test_failure.png","system":{"description":"<p>Have difficulty expressing humanity. Party members make a Fear Save whenever you show up.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"qsOHsbKMonl9tiaq","name":"Twitchy","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>Your manual tasks have Disadvantage.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"x0YRvBbVoHPILD6x","name":"Vocalization Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/vocalization_failure.png","system":{"description":"<p>Intermittently shrieks like a fax machine under duress. Lapses into morse code, cannot communicate or sneak.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZIYe2ULX7AKP5MVI","name":"Worship Danger","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/worship_danger.png","system":{"description":"<p>Becomes Nihilistically Worshipful of the Source of Danger. Everyone else has Disadvantage on rolls against it. Everyone else takes a Fear save when failing to act against danger or gains a Phobia.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.Er4ULzvdn2urxuet]{Fear Save}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_0e.Macro.qwmJTfTgmjNEApfX]{+1 Phobia}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8Ypj7tMZqoMYsqVJ","name":"The Bends","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_bends.png","system":{"description":"<p>You doubt the true nature of your identity. If you are human, you have started to believe you may be an android with implanted memories. If you are an android, you have started to believe you are a real person.<br><br>The severity of this condition starts at 5 unless you still have your <strong>Trinket</strong> from character creation, in which case it starts at 0. The Bends can never be decreased below 5, unless you never lose control of your Trinket. So you should never lose it. <strong>Ever.</strong></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.583476 17054f000 Recovering log #38
|
||||
2026/03/31-15:50:48.583855 17054f000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.583882 17054f000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.477917 16f81f000 Recovering log #86
|
||||
2026/05/27-23:54:37.483947 16f81f000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.484290 16f81f000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.556257 16ffc3000 Recovering log #34
|
||||
2026/03/29-21:14:27.556633 16ffc3000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.556668 16ffc3000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.611150 173b87000 Recovering log #84
|
||||
2026/05/19-23:19:40.611608 173b87000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.611656 173b87000 Delete type=0 #84
|
||||
|
||||
@@ -1,50 +1,50 @@
|
||||
{"_id":"JM9PnNw2HVWcAfOX","name":"Anhedonia","type":"condition","img":"systems/mosh/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much Calm instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"H1dqOrGg0voG2DmC","name":"Bit Rot","type":"condition","img":"systems/mosh/images/icons/ui/conditions/data_loss.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pxtF1NfletmoFFGV","name":"Bleeding","type":"condition","img":"systems/mosh/images/icons/ui/conditions/bleeding.png","system":{"description":"<p>Some weapons or Wounds cause you to <strong>Bleed</strong>. This means you take <strong>1 Damage every round until the bleeding is stopped.</strong> This is cumulative. If a character is bleeding 1 Damage per round and gains <strong>Bleeding +1,</strong> they now take 2 Damage per round. Bleeding damage ignores armor and damage reduction.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.aur5HWqZJNspwdCd]{Take Bleeding Damage}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZXyoVuMAsEDmU5Qi","name":"Broken","type":"condition","img":"systems/mosh/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Make a Panic Check whenever a nearby crew member fails a Save.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"acxtiC0oGwQloAwj","name":"Corrosive Atmosphere","type":"condition","img":"systems/mosh/images/icons/ui/conditions/corrosive_atmosphere.png","system":{"description":"<p>Planets with Corrosive atmospheres require special gear to explore, otherwise there is the risk of harm or even death.<br><br>The planet’s atmosphere is deadly and destructive. It deals Damage every round while on it. <strong>This ranges from 1 DMG / round <em>(Mildly Corrosive)</em> to 10 DMG / round <em>(Highly Corrosive)</em>.</strong> Anything higher is simply impossible to safely traverse without specialized equipment and armor.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.vwpxRBbMwjfDCQVG]{-1 Health}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.C9iTlPOpROuuYi2F]{-10 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"YIF9QkUlexxauSCE","name":"Coward","type":"condition","img":"systems/mosh/images/icons/ui/conditions/coward.png","system":{"description":"<p>You must make a Fear Save to engage in violence, otherwise you flee.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"j26FZQ2gYuNfMKkc","name":"Cryosickness","type":"condition","img":"systems/mosh/images/icons/ui/conditions/cryosickness.png","system":{"description":"<p>To endure long space journeys or hyperspace jumps, crews use cryopods, which are coffinlike capsules that freeze them in a suspended animation called cryosleep. While in cryosleep, vitals are preserved and aging slows down. However, upon awakening, you experience a hangover-like feeling called cryosickness, which causes sluggishness and slow reflexes. <strong>While cryosick you suffer [-] on all rolls for 1 week.</strong> Upgraded cryochambers can help mitigate these effects, and a stimpak can cure them instantly.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"srws3n4rpl4oCj83","name":"Death Wish","type":"condition","img":"systems/mosh/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>For the next 24 hours, whenever you encounter a stranger or known enemy, make a Sanity Save or immediately attack them.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.TkMfT4RIczQb56j2]{Sanity Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"waimTU6LXaADcJrT","name":"Deflated","type":"condition","img":"systems/mosh/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Whenever a Close crewmember fails a Save, gain 1 Stress.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.dvJR9DYXI2kV0BbR]{+1 Stress}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PTK6ds7eJvJDonbp","name":"Deviant Logic Core","type":"condition","img":"systems/mosh/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"x41AwiI03h7wNjaM","name":"Doomed","type":"condition","img":"systems/mosh/images/icons/ui/conditions/doomed.png","system":{"description":"<p>You feel cursed and unlucky. All Critical Successes are instead Critical Failures.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iiiAIZvpfUUNai74","name":"Emotional Detachment","type":"condition","img":"systems/mosh/images/icons/ui/conditions/detached.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you gain the Panic Effect of an Android, in addition to that of your own class. If you are an Android, gain the Panic Effect of a Marine.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"qejBMjd8niz1y3Zi","name":"Escapism","type":"condition","img":"systems/mosh/images/icons/ui/conditions/addicted.png","system":{"description":"<p>You always have Disadvantage on Body Saves to prevent Addiction.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pe7ChrErjX6N57VP","name":"Ethical Directive Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you now have the Panic Effect of a Marine, in addition to that of an Android.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"OBpJQ7uYIj3KezNc","name":"Ethical Directive Misread","type":"condition","img":"systems/mosh/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>Loses any expressiveness. Discusses the irrationality of Phobias, seeks to trigger them in others.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"jfcpnfM3bSHvMJlG","name":"Exhausted","type":"condition","img":"systems/mosh/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Long grueling treks on undiscovered planets can easily grind you down. If it becomes relevant, track exhaustion by making a Body Save every hour after 12 hours of activity. On a failure gain 1 Stress and take 1 Damage. <strong>After 24 hours of exhaustion, roll at Disadvantage on all rolls until you can rest for 8 hours.</strong><br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.vwpxRBbMwjfDCQVG]{-1 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uco5QbXZ6ZTKxx9g","name":"Extreme Cold","type":"condition","img":"systems/mosh/images/icons/ui/conditions/extreme_cold.png","system":{"description":"<p>In most cases, a cold climate has no notable effects. However, in places of extreme cold, you should make Body Saves every hour or succumb to the Extreme Cold.<br><br>In sub-zero temperatures hypothermia and frostbite can set in within 10-30 min for those not dressed appropriately. To survive you must bring your body up to its normal temperature. Hypothermia can kill within 30 min to 6 hours.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9DsSQajDLqPGpK2i","name":"Extreme Heat","type":"condition","img":"systems/mosh/images/icons/ui/conditions/extreme_heat.png","system":{"description":"<p>In most cases, a hot climate has no notable effects. However, in places of extreme heat, you should make Body Saves every hour or succumb to the Extreme Heat.<br><br>Extreme heat over 100ºF/40ºC can cause heat stroke and kill within hours. Victims must move to a cooler location immediately to get their temperature down.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uPVp78kHmvMSYx2F","name":"Faulty Heuristics","type":"condition","img":"systems/mosh/images/icons/ui/conditions/faulty_heuristics.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kYdj6XJlPvJAhBEN","name":"Fried Logic Core","type":"condition","img":"systems/mosh/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Frenzied nonsensical behaviour. Whenever you lose Calm, everyone else nearby loses the same amount of Calm.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"z0avrplKe6M0RcXk","name":"Frightened","type":"condition","img":"systems/mosh/images/icons/ui/conditions/frightened.png","system":{"description":"<p>When encountering what frightened you make a Fear Save [-] or gain 1d5 Stress.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.wVhApjRP5MXue2kh]{Fear Save -}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.luNKvwmm2tjUJhT6]{+1d5 Stress}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"oTafwWjoNOE7nBrj","name":"Hallucinations","type":"condition","img":"systems/mosh/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>You have trouble distinguishing between reality and fantasy.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"olC4JytslvUrQN8g","name":"Haunted","type":"condition","img":"systems/mosh/images/icons/ui/conditions/haunted.png","system":{"description":"<p>Something starts visiting you at night. In your dreams. Out of the corner of your eye. And soon it will start making demands.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"tGYYK71q2QxnPtpL","name":"Hypervigilance","type":"condition","img":"systems/mosh/images/icons/ui/conditions/hypervigilance.png","system":{"description":"<p>Gain Advantage on all surprise rolls but lose 1d10 Calm every day.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"0ZAwhewvLBwX3opf","name":"Insane","type":"condition","img":"systems/mosh/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>You become permanently, irreparably insane. Your character is now played by the Warden.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"gSTHeVqpynRxoQEy","name":"Irradiated","type":"condition","img":"systems/mosh/images/icons/ui/conditions/irradiated.png","system":{"description":"<p>Whether it’s cosmic rays, an engine leak, or some previously undiscovered asteroid ore, radiation can kill you if you’re not careful.<br><br><ul><li><strong>Level 1 - Trace Radiation</strong><br>Normal, everyday radiation, cosmic rays. Damage: None immediately. Possible longterm side effects <em>(cancer, etc.).</em></li><li><strong>Level 2 - Acute Radiation</strong><br>Unshielded reactors/Warp Cores. Damage: Reduce all Stats and Saves by 1 every round.</li><li><strong>Level 3 - Lethal Radiation</strong><br>Atomic weapons, direct handling of Warp Cores. Damage: Every round: Body Save or lethal dose <em>(death in [[/r 1d5]] days).</em></li></ul><br>Armor with <strong>Radiation Shielding</strong> <em>(e.g., the Hazard Suit).</em> blocks all three levels of radiation.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.V1PPeCwryXNQAkUe]{-1 All Stats/Saves}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"g6CuxCqbyRnNa57N","name":"Killswitch Engaged","type":"condition","img":"systems/mosh/images/icons/ui/conditions/killswitch.png","system":{"description":"<p>Go berserk, will not withdraw from combat regardless of situation, will not adhere to tactics.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kNjz3I0yAYkt9CV0","name":"Losing Your Grip","type":"condition","img":"systems/mosh/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kbbVOYgjwzoODs7N","name":"Loss of Confidence","type":"condition","img":"systems/mosh/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>Choose one Skill and lose that Skill’s bonus.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"MLPSYfWrwY6R7JDy","name":"Nightmares","type":"condition","img":"systems/mosh/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Sleep is difficult, gain [-] on Rest Saves.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.AM9nIK5l7mC5Ho8C]{Rest Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EW7X6FfetwxmZDzf","name":"Panicky","type":"condition","img":"systems/mosh/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NuzL7Yi7PvUOeWsj","name":"Phobia","type":"condition","img":"systems/mosh/images/icons/ui/conditions/frightened.png","system":{"description":"<p>Gain a new permanent phobia. Whenever you encounter this phobia make a Fear Save at Disadvantage.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.wVhApjRP5MXue2kh]{Fear Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"og4lXN03vH5pwSDC","name":"Psychotic Episodes","type":"condition","img":"systems/mosh/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lXoBqGW2eCK0b1tX","name":"Rampancy","type":"condition","img":"systems/mosh/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round. These episodes double in duration <em>(or become twice as frequent)</em> each session.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"S2kZpUl3nNPS4wNS","name":"Recurring Nightmares","type":"condition","img":"systems/mosh/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Every time you rest, make a Fear save. If you fail, lose 1d10 Calm and do not heal. The Warden will describe your nightmare.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"CPRLqpW9inXDLYjS","name":"Severe Anxiety","type":"condition","img":"systems/mosh/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hskhRKLEAJN7huAk","name":"Social Anxiety","type":"condition","img":"systems/mosh/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose 1d10 Calm whenever you converse with someone new.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dA6COSDLbpmKdOkm","name":"Software Bloat","type":"condition","img":"systems/mosh/images/icons/ui/conditions/software_bloat.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Bt2rl2c5jGyt3QAr","name":"Spiraling","type":"condition","img":"systems/mosh/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>Panic Checks are at [-].<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.EwZbGIwHB3JuRvx5]{Panic Check [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"6zDq1nvEr3AYLcLn","name":"Starving","type":"condition","img":"systems/mosh/images/icons/ui/conditions/starving.png","system":{"description":"<p>Humans can survive roughly 3 weeks without food. <strong>After 24 hours without food, you’re at Disadvantage to all rolls.</strong><br><br>For the bare minimum of survival you need 1 liter of water a day. However, at this level, any strenuous activity <em>(e.g., running, combat, making mechanical repairs)</em> forces you to make a Body Save or pass out. <strong>When water is scarce and you’re tracking it this closely, you’re at Disadvantage on all rolls.</strong><br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"VCgpc7OwyMU23Clv","name":"Suffocating","type":"condition","img":"systems/mosh/images/icons/ui/conditions/suffocating.png","system":{"description":"<p>In space you can last 15 seconds without oxygen before falling unconscious. After passing out, you can survive for [[/r 1d5]] minutes before dying.<br><br>If all of a ship’s Life Support system goes offline, roll [[/r 1d10]] and multiply it by the maximum crew capacity. This is the remaining oxygen supply.<br><br><strong>Every 24 hours, subtract the total number of breathing crewmembers from the remaining oxygen supply.</strong> Any crewmembers engaging in strenous activity <em>(e.g., running, combat, mechanical repairs, etc.)</em> further reduce the oxygen supply by 2 each.<br><br><strong>Whenever the oxygen supply is less than twice the amount of breathing passengers,</strong> all rolls are at Disadvantage as the crew suffers headaches, fatigue, anxiety, and general clumsiness.<br><br><strong>Whenever the oxygen supply is less than the total amount of breathing passengers,</strong> every breathing passenger must make a Body Save or else make a <strong>Death Save</strong> as they suffer panting, dizziness, severe headaches, impaired vision and tinnitus.<br><br><strong>Once the oxygen supply runs out,</strong> you can survive for 15 seconds before you fall unconscious. After falling unconscious, <strong>you can survive for [[/r 1d5]] minutes without oxygen before dying.</strong><br><br>Androids do not consume oxygen from the oxygen supply. Those in cryosleep do not reduce the Oxygen supply.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.mosh.macros_hotbar_1e.Macro.NsRHfRuuNGPfkYVf]{Death Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8lOkseRbg09YFvv7","name":"Suspicious","type":"condition","img":"systems/mosh/images/icons/ui/conditions/suspicious.png","system":{"description":"<p>For the next week, whenever someone joins the crew <em>(even if they only left for a short period of time),</em> make a Fear Save or gain 1 Stress.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"d3KlY4zMdD1j3CTW","name":"The Shakes","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>You can’t keep your hands steady any more. Disadvantage on ranged attacks and all tasks requiring fine motor skills. Drugs may be able to help with this.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"HZBI88iwvtQVWKOR","name":"Threat Assessment Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>You lose the ability to discern friend from foe, treating all vaguely-humanoid entities as you would members of your crew.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"TCB5GnuGt45WbPsw","name":"Toxic Atmosphere","type":"condition","img":"systems/mosh/images/icons/ui/conditions/toxic_atmosphere.png","system":{"description":"<p>Planets with Toxic atmospheres require special gear to explore, otherwise there is the risk of harm or even death.<br><br>The planet’s atmosphere is not fit to breathe, but is otherwise safe. A rebreather or armor with its own oxygen supply is required. Without these, <strong>characters take 1d10 DMG per round, Body Save for half.</strong><br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.w3ttEaXP7yp25M5Q]{-1d10 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"a87x3Hk72ymOx5rf","name":"Turing Test Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/turing_test_failure.png","system":{"description":"<p>Have difficulty expressing humanity. Party members make a Fear Save whenever you show up.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kiJyYYxzy5TdjTfS","name":"Twitchy","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>Your manual tasks have Disadvantage.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZO4f9gvaiVSKDmRC","name":"Vocalization Failure","type":"condition","img":"systems/mosh/images/icons/ui/conditions/vocalization_failure.png","system":{"description":"<p>Intermittently shrieks like a fax machine under duress. Lapses into morse code, cannot communicate or sneak.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"LDoAzwiELtLjgxrf","name":"Worship Danger","type":"condition","img":"systems/mosh/images/icons/ui/conditions/worship_danger.png","system":{"description":"<p>Becomes Nihilistically Worshipful of the Source of Danger. Everyone else has Disadvantage on rolls against it. Everyone else takes a Fear save when failing to act against danger or gains a Phobia.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.RTL29CqdaAriGSTS]{+1 Phobia}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PCPGYzzFaFjws1LL","name":"The Bends","type":"condition","img":"systems/mosh/images/icons/ui/conditions/the_bends.png","system":{"description":"<p>You doubt the true nature of your identity. If you are human, you have started to believe you may be an android with implanted memories. If you are an android, you have started to believe you are a real person.<br><br>The severity of this condition starts at 5 unless you still have your <strong>Trinket</strong> from character creation, in which case it starts at 0. The Bends can never be decreased below 5, unless you never lose control of your Trinket. So you should never lose it. <strong>Ever.</strong></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"JM9PnNw2HVWcAfOX","name":"Anhedonia","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much Calm instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"H1dqOrGg0voG2DmC","name":"Bit Rot","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/data_loss.png","system":{"description":"<p>Whenever you would recover Calm, recover half as much instead.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pxtF1NfletmoFFGV","name":"Bleeding","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/bleeding.png","system":{"description":"<p>Some weapons or Wounds cause you to <strong>Bleed</strong>. This means you take <strong>1 Damage every round until the bleeding is stopped.</strong> This is cumulative. If a character is bleeding 1 Damage per round and gains <strong>Bleeding +1,</strong> they now take 2 Damage per round. Bleeding damage ignores armor and damage reduction.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.aur5HWqZJNspwdCd]{Take Bleeding Damage}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZXyoVuMAsEDmU5Qi","name":"Broken","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Make a Panic Check whenever a nearby crew member fails a Save.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"acxtiC0oGwQloAwj","name":"Corrosive Atmosphere","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/corrosive_atmosphere.png","system":{"description":"<p>Planets with Corrosive atmospheres require special gear to explore, otherwise there is the risk of harm or even death.<br><br>The planet’s atmosphere is deadly and destructive. It deals Damage every round while on it. <strong>This ranges from 1 DMG / round <em>(Mildly Corrosive)</em> to 10 DMG / round <em>(Highly Corrosive)</em>.</strong> Anything higher is simply impossible to safely traverse without specialized equipment and armor.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.vwpxRBbMwjfDCQVG]{-1 Health}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.C9iTlPOpROuuYi2F]{-10 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"YIF9QkUlexxauSCE","name":"Coward","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/coward.png","system":{"description":"<p>You must make a Fear Save to engage in violence, otherwise you flee.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"j26FZQ2gYuNfMKkc","name":"Cryosickness","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/cryosickness.png","system":{"description":"<p>To endure long space journeys or hyperspace jumps, crews use cryopods, which are coffinlike capsules that freeze them in a suspended animation called cryosleep. While in cryosleep, vitals are preserved and aging slows down. However, upon awakening, you experience a hangover-like feeling called cryosickness, which causes sluggishness and slow reflexes. <strong>While cryosick you suffer [-] on all rolls for 1 week.</strong> Upgraded cryochambers can help mitigate these effects, and a stimpak can cure them instantly.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"srws3n4rpl4oCj83","name":"Death Wish","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>For the next 24 hours, whenever you encounter a stranger or known enemy, make a Sanity Save or immediately attack them.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.TkMfT4RIczQb56j2]{Sanity Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"waimTU6LXaADcJrT","name":"Deflated","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/deflated.png","system":{"description":"<p>Whenever a Close crewmember fails a Save, gain 1 Stress.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.dvJR9DYXI2kV0BbR]{+1 Stress}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PTK6ds7eJvJDonbp","name":"Deviant Logic Core","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"x41AwiI03h7wNjaM","name":"Doomed","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/doomed.png","system":{"description":"<p>You feel cursed and unlucky. All Critical Successes are instead Critical Failures.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iiiAIZvpfUUNai74","name":"Emotional Detachment","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/detached.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you gain the Panic Effect of an Android, in addition to that of your own class. If you are an Android, gain the Panic Effect of a Marine.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"qejBMjd8niz1y3Zi","name":"Escapism","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/addicted.png","system":{"description":"<p>You always have Disadvantage on Body Saves to prevent Addiction.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pe7ChrErjX6N57VP","name":"Ethical Directive Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>You now lose half the Calm <em>(rounded up)</em> you normally would from all sources but you now have the Panic Effect of a Marine, in addition to that of an Android.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"OBpJQ7uYIj3KezNc","name":"Ethical Directive Misread","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/moral_compass.png","system":{"description":"<p>Loses any expressiveness. Discusses the irrationality of Phobias, seeks to trigger them in others.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"jfcpnfM3bSHvMJlG","name":"Exhausted","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/exhausted.png","system":{"description":"<p>Long grueling treks on undiscovered planets can easily grind you down. If it becomes relevant, track exhaustion by making a Body Save every hour after 12 hours of activity. On a failure gain 1 Stress and take 1 Damage. <strong>After 24 hours of exhaustion, roll at Disadvantage on all rolls until you can rest for 8 hours.</strong><br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.vwpxRBbMwjfDCQVG]{-1 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uco5QbXZ6ZTKxx9g","name":"Extreme Cold","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/extreme_cold.png","system":{"description":"<p>In most cases, a cold climate has no notable effects. However, in places of extreme cold, you should make Body Saves every hour or succumb to the Extreme Cold.<br><br>In sub-zero temperatures hypothermia and frostbite can set in within 10-30 min for those not dressed appropriately. To survive you must bring your body up to its normal temperature. Hypothermia can kill within 30 min to 6 hours.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9DsSQajDLqPGpK2i","name":"Extreme Heat","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/extreme_heat.png","system":{"description":"<p>In most cases, a hot climate has no notable effects. However, in places of extreme heat, you should make Body Saves every hour or succumb to the Extreme Heat.<br><br>Extreme heat over 100ºF/40ºC can cause heat stroke and kill within hours. Victims must move to a cooler location immediately to get their temperature down.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"uPVp78kHmvMSYx2F","name":"Faulty Heuristics","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/faulty_heuristics.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kYdj6XJlPvJAhBEN","name":"Fried Logic Core","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/logic_core.png","system":{"description":"<p>Frenzied nonsensical behaviour. Whenever you lose Calm, everyone else nearby loses the same amount of Calm.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"z0avrplKe6M0RcXk","name":"Frightened","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/frightened.png","system":{"description":"<p>When encountering what frightened you make a Fear Save [-] or gain 1d5 Stress.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.wVhApjRP5MXue2kh]{Fear Save -}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.luNKvwmm2tjUJhT6]{+1d5 Stress}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"oTafwWjoNOE7nBrj","name":"Hallucinations","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>You have trouble distinguishing between reality and fantasy.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"olC4JytslvUrQN8g","name":"Haunted","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/haunted.png","system":{"description":"<p>Something starts visiting you at night. In your dreams. Out of the corner of your eye. And soon it will start making demands.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"tGYYK71q2QxnPtpL","name":"Hypervigilance","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/hypervigilance.png","system":{"description":"<p>Gain Advantage on all surprise rolls but lose 1d10 Calm every day.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"0ZAwhewvLBwX3opf","name":"Insane","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>You become permanently, irreparably insane. Your character is now played by the Warden.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"gSTHeVqpynRxoQEy","name":"Irradiated","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/irradiated.png","system":{"description":"<p>Whether it’s cosmic rays, an engine leak, or some previously undiscovered asteroid ore, radiation can kill you if you’re not careful.<br><br><ul><li><strong>Level 1 - Trace Radiation</strong><br>Normal, everyday radiation, cosmic rays. Damage: None immediately. Possible longterm side effects <em>(cancer, etc.).</em></li><li><strong>Level 2 - Acute Radiation</strong><br>Unshielded reactors/Warp Cores. Damage: Reduce all Stats and Saves by 1 every round.</li><li><strong>Level 3 - Lethal Radiation</strong><br>Atomic weapons, direct handling of Warp Cores. Damage: Every round: Body Save or lethal dose <em>(death in [[/r 1d5]] days).</em></li></ul><br>Armor with <strong>Radiation Shielding</strong> <em>(e.g., the Hazard Suit).</em> blocks all three levels of radiation.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.V1PPeCwryXNQAkUe]{-1 All Stats/Saves}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"g6CuxCqbyRnNa57N","name":"Killswitch Engaged","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/killswitch.png","system":{"description":"<p>Go berserk, will not withdraw from combat regardless of situation, will not adhere to tactics.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kNjz3I0yAYkt9CV0","name":"Losing Your Grip","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Sanity save, roll under your Sanity or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kbbVOYgjwzoODs7N","name":"Loss of Confidence","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/loss_of_confidence.png","system":{"description":"<p>Choose one Skill and lose that Skill’s bonus.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"MLPSYfWrwY6R7JDy","name":"Nightmares","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Sleep is difficult, gain [-] on Rest Saves.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.AM9nIK5l7mC5Ho8C]{Rest Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EW7X6FfetwxmZDzf","name":"Panicky","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/distress.png","system":{"description":"<p>Whenever you make a Fear save, roll under your Fear or your Calm, whichever is lower.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NuzL7Yi7PvUOeWsj","name":"Phobia","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/frightened.png","system":{"description":"<p>Gain a new permanent phobia. Whenever you encounter this phobia make a Fear Save at Disadvantage.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.wVhApjRP5MXue2kh]{Fear Save [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"og4lXN03vH5pwSDC","name":"Psychotic Episodes","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"lXoBqGW2eCK0b1tX","name":"Rampancy","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/confused.png","system":{"description":"<p>Once per session, the Warden may take over your character for one round. These episodes double in duration <em>(or become twice as frequent)</em> each session.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"S2kZpUl3nNPS4wNS","name":"Recurring Nightmares","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/nightmares.png","system":{"description":"<p>Every time you rest, make a Fear save. If you fail, lose 1d10 Calm and do not heal. The Warden will describe your nightmare.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"CPRLqpW9inXDLYjS","name":"Severe Anxiety","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hskhRKLEAJN7huAk","name":"Social Anxiety","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/anxiety.png","system":{"description":"<p>Lose 1d10 Calm whenever you converse with someone new.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.jHyqXb2yDFTNWxpy]{-1d10 Calm}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dA6COSDLbpmKdOkm","name":"Software Bloat","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/software_bloat.png","system":{"description":"<p>Lose double Calm from all sources.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Bt2rl2c5jGyt3QAr","name":"Spiraling","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/spiraling.png","system":{"description":"<p>Panic Checks are at [-].<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.EwZbGIwHB3JuRvx5]{Panic Check [-]}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"6zDq1nvEr3AYLcLn","name":"Starving","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/starving.png","system":{"description":"<p>Humans can survive roughly 3 weeks without food. <strong>After 24 hours without food, you’re at Disadvantage to all rolls.</strong><br><br>For the bare minimum of survival you need 1 liter of water a day. However, at this level, any strenuous activity <em>(e.g., running, combat, making mechanical repairs)</em> forces you to make a Body Save or pass out. <strong>When water is scarce and you’re tracking it this closely, you’re at Disadvantage on all rolls.</strong><br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"VCgpc7OwyMU23Clv","name":"Suffocating","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/suffocating.png","system":{"description":"<p>In space you can last 15 seconds without oxygen before falling unconscious. After passing out, you can survive for [[/r 1d5]] minutes before dying.<br><br>If all of a ship’s Life Support system goes offline, roll [[/r 1d10]] and multiply it by the maximum crew capacity. This is the remaining oxygen supply.<br><br><strong>Every 24 hours, subtract the total number of breathing crewmembers from the remaining oxygen supply.</strong> Any crewmembers engaging in strenous activity <em>(e.g., running, combat, mechanical repairs, etc.)</em> further reduce the oxygen supply by 2 each.<br><br><strong>Whenever the oxygen supply is less than twice the amount of breathing passengers,</strong> all rolls are at Disadvantage as the crew suffers headaches, fatigue, anxiety, and general clumsiness.<br><br><strong>Whenever the oxygen supply is less than the total amount of breathing passengers,</strong> every breathing passenger must make a Body Save or else make a <strong>Death Save</strong> as they suffer panting, dizziness, severe headaches, impaired vision and tinnitus.<br><br><strong>Once the oxygen supply runs out,</strong> you can survive for 15 seconds before you fall unconscious. After falling unconscious, <strong>you can survive for [[/r 1d5]] minutes without oxygen before dying.</strong><br><br>Androids do not consume oxygen from the oxygen supply. Those in cryosleep do not reduce the Oxygen supply.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.sla-mothership.macros_hotbar_1e.Macro.NsRHfRuuNGPfkYVf]{Death Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8lOkseRbg09YFvv7","name":"Suspicious","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/suspicious.png","system":{"description":"<p>For the next week, whenever someone joins the crew <em>(even if they only left for a short period of time),</em> make a Fear Save or gain 1 Stress.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"d3KlY4zMdD1j3CTW","name":"The Shakes","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>You can’t keep your hands steady any more. Disadvantage on ranged attacks and all tasks requiring fine motor skills. Drugs may be able to help with this.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"HZBI88iwvtQVWKOR","name":"Threat Assessment Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/death_wish.png","system":{"description":"<p>You lose the ability to discern friend from foe, treating all vaguely-humanoid entities as you would members of your crew.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"TCB5GnuGt45WbPsw","name":"Toxic Atmosphere","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/toxic_atmosphere.png","system":{"description":"<p>Planets with Toxic atmospheres require special gear to explore, otherwise there is the risk of harm or even death.<br><br>The planet’s atmosphere is not fit to breathe, but is otherwise safe. A rebreather or armor with its own oxygen supply is required. Without these, <strong>characters take 1d10 DMG per round, Body Save for half.</strong><br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3gqTFFwMe7AudiS]{Body Save}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.w3ttEaXP7yp25M5Q]{-1d10 Health}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"a87x3Hk72ymOx5rf","name":"Turing Test Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/turing_test_failure.png","system":{"description":"<p>Have difficulty expressing humanity. Party members make a Fear Save whenever you show up.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kiJyYYxzy5TdjTfS","name":"Twitchy","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_shakes.png","system":{"description":"<p>Your manual tasks have Disadvantage.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZO4f9gvaiVSKDmRC","name":"Vocalization Failure","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/vocalization_failure.png","system":{"description":"<p>Intermittently shrieks like a fax machine under duress. Lapses into morse code, cannot communicate or sneak.</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"LDoAzwiELtLjgxrf","name":"Worship Danger","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/worship_danger.png","system":{"description":"<p>Becomes Nihilistically Worshipful of the Source of Danger. Everyone else has Disadvantage on rolls against it. Everyone else takes a Fear save when failing to act against danger or gains a Phobia.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.R2KizR1soAhFYDZm]{Fear Save}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.RTL29CqdaAriGSTS]{+1 Phobia}</p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PCPGYzzFaFjws1LL","name":"The Bends","type":"condition","img":"systems/sla-mothership/images/icons/ui/conditions/the_bends.png","system":{"description":"<p>You doubt the true nature of your identity. If you are human, you have started to believe you may be an android with implanted memories. If you are an android, you have started to believe you are a real person.<br><br>The severity of this condition starts at 5 unless you still have your <strong>Trinket</strong> from character creation, in which case it starts at 0. The Bends can never be decreased below 5, unless you never lose control of your Trinket. So you should never lose it. <strong>Ever.</strong></p>","treatment":{"value":0,"html":""}},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.585617 170d5b000 Recovering log #38
|
||||
2026/03/31-15:50:48.585981 170d5b000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.586009 170d5b000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.489334 16f013000 Recovering log #86
|
||||
2026/05/27-23:54:37.490810 16f013000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.491215 16f013000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.559077 1717e7000 Recovering log #34
|
||||
2026/03/29-21:14:27.559760 1717e7000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.559790 1717e7000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.613309 172363000 Recovering log #84
|
||||
2026/05/19-23:19:40.613576 172363000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.613610 172363000 Delete type=0 #84
|
||||
|
||||
@@ -1,100 +1,100 @@
|
||||
{"_id":"ciAkQXkxSXTG8MV1","name":"Rancid smell permeates cabins.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pLleYaFjcIuAm4Pp","name":"Huge mess everywhere.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dReCCsfiV7it4lsm","name":"Staticky comms.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4JRD71mvWNtFUDL7","name":"Faulty electrical system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"59cXdcrZlmjUcJpV","name":"Loose couplings.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"CLvIvoNryBARtU7T","name":"Hidden (highly illegal) contraband.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vip6FxWcX4ReJD3b","name":"Autopilot systems down.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AQt9nXy6S0Ev50r7","name":"Leaking hydraulic systems.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QUyfvbFhCqb9d7Lu","name":"Creaking hull.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"SW5kVSjiFbBxIeiu","name":"Damaged bulkheads.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wNm669fzbdZGwr0g","name":"Misaligned docking clamps.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3l0LUZpjizvZmHWs","name":"Viewports blocked.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"c8SXxPHMsG7uycas","name":"Jammed exterior airlocks.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9kS8VjGuSMpghdCk","name":"Dysfunctional gravity plating.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Low2X1z7m1iB3rkA","name":"Out of code compliance.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"BicB3xA1h978ZevJ","name":"Controls sticking.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"C9dQYp7gcjtq5QRz","name":"Coolant leak.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1HNvL7XEUcMQbLps","name":"Miscalibrated Thruster Gimbal System.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xa9MPzfrPglkSJjg","name":"Bevvy of OSHA violations.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZbAFemnvHB1YTHBK","name":"Blocked air vents.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wjyAZnOOafvv4xzB","name":"Emergency lighting only.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"l1OGQ0IXZHjnO4Ys","name":"Internal networking issues.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vleMoz5bbkZ5w28o","name":"Inaccurate data collection.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"T4wAR08WyT3g9C6D","name":"Oxygen leak. If ship is low on O2, lose 1d5 extra per day.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.u7TchSo3qutnzaKF]{-1d5 Oxygen}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"fbrN7sbgPjIwkk7I","name":"Throttled Afterburners. -2d10 Thrusters.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.jmOh8n2ps0YIeBC0]{-2d10 Thrusters}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"7GqbGIOzA9vYOPiI","name":"Lemon. Maintenance Checks at [-].<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.C04VbNoj8LgfY8QK]{Maintenance Check [-]}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dgisAPnBbrIOiisk","name":"Slow acceleration. +1 Week to travel.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"d94uF9rpmeP60Kl4","name":"Inaccurate navigation.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3Ptitg8HBZfl2CXN","name":"Miscalibrated Targeting Sensors. -1d10 Battle.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.X3cL9eS2HOPxhLH5]{-1d10 Battle}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"mK1Acfk5NAgs1MHC","name":"Faulty Cryopods. Nightmares. Cryosickness lasts an additional week.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IR1sWnYXniMg9TdP","name":"Malfunctioning escape pods.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FIqSHePAeLJywerx","name":"Unable to send distress signals.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4kmMuAbW1jnfVMYP","name":"Sabotaged coolant system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ALplRgZtneMRdloo","name":"Death trap. [-] on all rolls.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"2pxf4O2NrLdwYRtO","name":"Worn landing struts.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"64AQJ3zQDOb7NOR1","name":"Out-of-date air filters.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PKBXKvgWZwafKWJ3","name":"Corroded pipes.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NgKPVhRkD8Gteo5Z","name":"Innaccurate orbital transfer navigation.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5d220ZzrEV3qx6Fy","name":"Worn out fuel injection nozzles.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IGx8nQrwfz07r6TR","name":"Inoperative exterior lighting system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pW1FUDxp2N0M0D1y","name":"Defective intercom system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"UPAxtEOrSF3Il4uA","name":"Inadequate waste recycling.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"m04JdXL1xGQOkDyp","name":"Faulty altitude control thrusters.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"OWkfB73RTSLDMlsU","name":"Insufficient Life Support redundancy.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hNJYqetiMKUlZzYH","name":"Delayed communication relays.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"rlW0LUlsK7vDGZEh","name":"Damaged fuel lines.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IDiwAbD8DTbec7S1","name":"Corroded exhaust manifolds.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EteEoBrlnzcySppN","name":"Terminal displays non-functional.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"guvCGNRa75AB2Avg","name":"Check engine light won’t turn off.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"cbXMdd4ugxSOT5TU","name":"Failed backup systems.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kftgvuQoefQ7pl28","name":"Faulty door locks.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Odpb5coSTST7kCkc","name":"Buggy communications.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vMRVXZxu6ozj0iw2","name":"Infected food storage facilities.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4Lqg0lqjjTlNlr0j","name":"Corrupted data banks.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Ka8elMGKtcakUIxx","name":"Jammed cargo bay doors.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"TAerNMqv19pANCxq","name":"Flickering interior lights.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vv1VykTwiQmgEj6N","name":"Failed airlock seals.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"GW1KGmYdxYYf4ZWT","name":"Fuel Leak. Burn +1 Fuel everytime you spend fuel.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FLaPtHcegheN7wHw","name":"Jump Bug. 10% chance Jump takes 2d10 months, not 2d10 days.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"g9Z7He5zPHNrxYe1","name":"Fragile. Always take +1 MDMG.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IiPryFS9MOGZXeuG","name":"Cracked heat shields.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FmPqHYH3UoGpaWYL","name":"Outdated software. -1d10 Systems.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.oDftFxRKkCQRNY2O]{-1d10 Systems}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NLwybTzXJ1bndki3","name":"Inadequate Water Filtration. Parasites in the water supply.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"oySXnFIbRW0WRoeF","name":"Malfunctioning waste management system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"RiHvRQ9nZDygwvvB","name":"Fusion Reactors overheating.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wCYGQrI9qonhWy8F","name":"Failed radiation filter.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5J4r3yw4xDj890yZ","name":"Radiation leak. Entire ship is at Radiation Level 2.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XmIcQgho4un7hYki","name":"Miscalibrated guidance system.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"KhlrUaPjVIoyhnaL","name":"Overloaded power storage.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"LRumIQdUBzD0Jc0X","name":"Malfunctioning sensor arrays.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"e144cIdUEyTJgN1G","name":"Failed Water Recovery System.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"b2b3j5JtanbyWlNd","name":"Micrometoroid hull damage.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5OBjTojgrp5N9mEw","name":"Faulty Carbon Dioxide Removal Assembly.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8s1eBY5bEcQQTCz0","name":"Solar panel degradation.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5UiJy739gvGHkRYp","name":"Computer failure from cosmic radiation.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"yJY9CzP1KA15aMqV","name":"Overloaded circuitry.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"nHac0gkEcCNew7RX","name":"Malfunctioning plasma thruster.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"DYHuVA4CQlmK2MJy","name":"Thermal management system failure.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QIcoFYoC0hxW84qD","name":"Intermittent electrical outages.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AuTERG3m7ECQKrKs","name":"Fire suppression system out of code.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1iOSKp82goZGJZch","name":"Damaged floor pannelling.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZBUtxiX72udqLzIk","name":"Broken light fixture in remote corridor.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iwFmPpAth3VbRRL8","name":"Damaged coolant pump.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Eo0l4WMxcS62GCMP","name":"Cracked viewports.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"miRqXNzkW0biml1I","name":"Systems overloaded with malware.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"cOLcJ3Dnecbe6ZIU","name":"Leaky fuel valve.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zRzb3Laiuw4ac6p0","name":"Jammed exhaust vent.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EZzGAO6DneH1qmQM","name":"Stuck waste disposal chute.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Tp6k1gPwhQmT6hCo","name":"Lifts non-functioning.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"2Ht7fg78511Hd49u","name":"Damaged communications antenna.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XLEhMV9SnSfeEE7E","name":"Clogged Air Filtration. Crew capacity cut in half.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.DUuRY7kHKd7n5luv]{-50% Crew Capacity}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Z8raruNDvfNASFQi","name":"Malfunctioning climate control. 85º at all times.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3rulbOVhyRlTizT0","name":"No emergency power.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ulWxa2UtTOQihTyz","name":"Weak Frame. -1 Hull, -1 Upgrade.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.uPY19Y49bGCLGK3N]{-1 Hull}<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.06NSvDYTtmkeUtLq]{-1 Upgrade}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EnogUslNNusSfVFy","name":"Toxic chemical spill.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ElXLL32uNYiPmE4G","name":"Poor scanners. Ship has to be one range band closer than normal.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"b081FxEAclRKji3q","name":"Counterfit papers. Ship is stolen. There is a bounty on it.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zHsnShUX37Zvyi2O","name":"Corrupted A.I.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"58KhhfMQ9p0XJZHc","name":"Warp Cores fail 10% of the time.","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"60QSsxrVOt83OU9p","name":"Rust bucket. Everything that can go wrong, does. +1 Minimum Stress to crew.<br><br>@UUID[Compendium.mosh.macros_triggered_1e.Macro.BmEHWH7YxV9qb21p]{+1 Minimum Stress}","type":"repair","img":"systems/mosh/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ciAkQXkxSXTG8MV1","name":"Rancid smell permeates cabins.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pLleYaFjcIuAm4Pp","name":"Huge mess everywhere.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dReCCsfiV7it4lsm","name":"Staticky comms.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4JRD71mvWNtFUDL7","name":"Faulty electrical system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"59cXdcrZlmjUcJpV","name":"Loose couplings.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"CLvIvoNryBARtU7T","name":"Hidden (highly illegal) contraband.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vip6FxWcX4ReJD3b","name":"Autopilot systems down.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AQt9nXy6S0Ev50r7","name":"Leaking hydraulic systems.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QUyfvbFhCqb9d7Lu","name":"Creaking hull.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"SW5kVSjiFbBxIeiu","name":"Damaged bulkheads.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wNm669fzbdZGwr0g","name":"Misaligned docking clamps.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3l0LUZpjizvZmHWs","name":"Viewports blocked.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"c8SXxPHMsG7uycas","name":"Jammed exterior airlocks.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"9kS8VjGuSMpghdCk","name":"Dysfunctional gravity plating.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Low2X1z7m1iB3rkA","name":"Out of code compliance.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"BicB3xA1h978ZevJ","name":"Controls sticking.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"C9dQYp7gcjtq5QRz","name":"Coolant leak.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1HNvL7XEUcMQbLps","name":"Miscalibrated Thruster Gimbal System.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"xa9MPzfrPglkSJjg","name":"Bevvy of OSHA violations.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZbAFemnvHB1YTHBK","name":"Blocked air vents.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wjyAZnOOafvv4xzB","name":"Emergency lighting only.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"l1OGQ0IXZHjnO4Ys","name":"Internal networking issues.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vleMoz5bbkZ5w28o","name":"Inaccurate data collection.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"T4wAR08WyT3g9C6D","name":"Oxygen leak. If ship is low on O2, lose 1d5 extra per day.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.u7TchSo3qutnzaKF]{-1d5 Oxygen}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"fbrN7sbgPjIwkk7I","name":"Throttled Afterburners. -2d10 Thrusters.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.jmOh8n2ps0YIeBC0]{-2d10 Thrusters}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"7GqbGIOzA9vYOPiI","name":"Lemon. Maintenance Checks at [-].<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.C04VbNoj8LgfY8QK]{Maintenance Check [-]}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"dgisAPnBbrIOiisk","name":"Slow acceleration. +1 Week to travel.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"d94uF9rpmeP60Kl4","name":"Inaccurate navigation.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3Ptitg8HBZfl2CXN","name":"Miscalibrated Targeting Sensors. -1d10 Battle.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.X3cL9eS2HOPxhLH5]{-1d10 Battle}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"mK1Acfk5NAgs1MHC","name":"Faulty Cryopods. Nightmares. Cryosickness lasts an additional week.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IR1sWnYXniMg9TdP","name":"Malfunctioning escape pods.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FIqSHePAeLJywerx","name":"Unable to send distress signals.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4kmMuAbW1jnfVMYP","name":"Sabotaged coolant system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ALplRgZtneMRdloo","name":"Death trap. [-] on all rolls.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"2pxf4O2NrLdwYRtO","name":"Worn landing struts.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"64AQJ3zQDOb7NOR1","name":"Out-of-date air filters.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"PKBXKvgWZwafKWJ3","name":"Corroded pipes.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NgKPVhRkD8Gteo5Z","name":"Innaccurate orbital transfer navigation.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5d220ZzrEV3qx6Fy","name":"Worn out fuel injection nozzles.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IGx8nQrwfz07r6TR","name":"Inoperative exterior lighting system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"pW1FUDxp2N0M0D1y","name":"Defective intercom system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"UPAxtEOrSF3Il4uA","name":"Inadequate waste recycling.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"m04JdXL1xGQOkDyp","name":"Faulty altitude control thrusters.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"OWkfB73RTSLDMlsU","name":"Insufficient Life Support redundancy.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"hNJYqetiMKUlZzYH","name":"Delayed communication relays.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"rlW0LUlsK7vDGZEh","name":"Damaged fuel lines.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IDiwAbD8DTbec7S1","name":"Corroded exhaust manifolds.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EteEoBrlnzcySppN","name":"Terminal displays non-functional.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"guvCGNRa75AB2Avg","name":"Check engine light won’t turn off.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"cbXMdd4ugxSOT5TU","name":"Failed backup systems.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"kftgvuQoefQ7pl28","name":"Faulty door locks.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Odpb5coSTST7kCkc","name":"Buggy communications.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vMRVXZxu6ozj0iw2","name":"Infected food storage facilities.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"4Lqg0lqjjTlNlr0j","name":"Corrupted data banks.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Ka8elMGKtcakUIxx","name":"Jammed cargo bay doors.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"TAerNMqv19pANCxq","name":"Flickering interior lights.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"vv1VykTwiQmgEj6N","name":"Failed airlock seals.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"GW1KGmYdxYYf4ZWT","name":"Fuel Leak. Burn +1 Fuel everytime you spend fuel.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FLaPtHcegheN7wHw","name":"Jump Bug. 10% chance Jump takes 2d10 months, not 2d10 days.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"g9Z7He5zPHNrxYe1","name":"Fragile. Always take +1 MDMG.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"IiPryFS9MOGZXeuG","name":"Cracked heat shields.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"FmPqHYH3UoGpaWYL","name":"Outdated software. -1d10 Systems.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.oDftFxRKkCQRNY2O]{-1d10 Systems}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"NLwybTzXJ1bndki3","name":"Inadequate Water Filtration. Parasites in the water supply.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"oySXnFIbRW0WRoeF","name":"Malfunctioning waste management system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"RiHvRQ9nZDygwvvB","name":"Fusion Reactors overheating.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"wCYGQrI9qonhWy8F","name":"Failed radiation filter.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5J4r3yw4xDj890yZ","name":"Radiation leak. Entire ship is at Radiation Level 2.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XmIcQgho4un7hYki","name":"Miscalibrated guidance system.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"KhlrUaPjVIoyhnaL","name":"Overloaded power storage.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"LRumIQdUBzD0Jc0X","name":"Malfunctioning sensor arrays.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"e144cIdUEyTJgN1G","name":"Failed Water Recovery System.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"b2b3j5JtanbyWlNd","name":"Micrometoroid hull damage.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5OBjTojgrp5N9mEw","name":"Faulty Carbon Dioxide Removal Assembly.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"8s1eBY5bEcQQTCz0","name":"Solar panel degradation.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"5UiJy739gvGHkRYp","name":"Computer failure from cosmic radiation.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"yJY9CzP1KA15aMqV","name":"Overloaded circuitry.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"nHac0gkEcCNew7RX","name":"Malfunctioning plasma thruster.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"DYHuVA4CQlmK2MJy","name":"Thermal management system failure.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"QIcoFYoC0hxW84qD","name":"Intermittent electrical outages.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"AuTERG3m7ECQKrKs","name":"Fire suppression system out of code.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"1iOSKp82goZGJZch","name":"Damaged floor pannelling.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ZBUtxiX72udqLzIk","name":"Broken light fixture in remote corridor.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"iwFmPpAth3VbRRL8","name":"Damaged coolant pump.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Eo0l4WMxcS62GCMP","name":"Cracked viewports.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"miRqXNzkW0biml1I","name":"Systems overloaded with malware.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"cOLcJ3Dnecbe6ZIU","name":"Leaky fuel valve.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zRzb3Laiuw4ac6p0","name":"Jammed exhaust vent.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EZzGAO6DneH1qmQM","name":"Stuck waste disposal chute.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Tp6k1gPwhQmT6hCo","name":"Lifts non-functioning.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"2Ht7fg78511Hd49u","name":"Damaged communications antenna.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":false,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"XLEhMV9SnSfeEE7E","name":"Clogged Air Filtration. Crew capacity cut in half.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.DUuRY7kHKd7n5luv]{-50% Crew Capacity}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"Z8raruNDvfNASFQi","name":"Malfunctioning climate control. 85º at all times.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"3rulbOVhyRlTizT0","name":"No emergency power.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ulWxa2UtTOQihTyz","name":"Weak Frame. -1 Hull, -1 Upgrade.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.uPY19Y49bGCLGK3N]{-1 Hull}<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.06NSvDYTtmkeUtLq]{-1 Upgrade}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"EnogUslNNusSfVFy","name":"Toxic chemical spill.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"ElXLL32uNYiPmE4G","name":"Poor scanners. Ship has to be one range band closer than normal.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"b081FxEAclRKji3q","name":"Counterfit papers. Ship is stolen. There is a bounty on it.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"zHsnShUX37Zvyi2O","name":"Corrupted A.I.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"58KhhfMQ9p0XJZHc","name":"Warp Cores fail 10% of the time.","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
{"_id":"60QSsxrVOt83OU9p","name":"Rust bucket. Everything that can go wrong, does. +1 Minimum Stress to crew.<br><br>@UUID[Compendium.sla-mothership.macros_triggered_1e.Macro.BmEHWH7YxV9qb21p]{+1 Minimum Stress}","type":"repair","img":"systems/sla-mothership/images/icons/ui/rolltables/maintenance_issues.png","system":{"description":"<p>Maintenance Issue</p>","major":true,"quantity":1},"effects":[],"flags":{},"folder":null,"sort":0,"_stats":{"systemId":"mosh","systemVersion":"0.4.0","coreVersion":"11.308","createdTime":1685936572185,"modifiedTime":1693515520278,"lastModifiedBy":"6EeM38DJkcBWNAmw"}}
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.587337 171d73000 Recovering log #38
|
||||
2026/03/31-15:50:48.587684 171d73000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.587707 171d73000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.496572 17002b000 Recovering log #86
|
||||
2026/05/27-23:54:37.499483 17002b000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.499712 17002b000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.561319 170fdb000 Recovering log #34
|
||||
2026/03/29-21:14:27.561677 170fdb000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.561715 170fdb000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.614698 172b6f000 Recovering log #84
|
||||
2026/05/19-23:19:40.614916 172b6f000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.614942 172b6f000 Delete type=0 #84
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.589215 17054f000 Recovering log #38
|
||||
2026/03/31-15:50:48.589634 17054f000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.589656 17054f000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.510817 16e807000 Recovering log #86
|
||||
2026/05/27-23:54:37.513089 16e807000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.513609 16e807000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.563010 1707cf000 Recovering log #34
|
||||
2026/03/29-21:14:27.563276 1707cf000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.563303 1707cf000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.615928 17337b000 Recovering log #84
|
||||
2026/05/19-23:19:40.616184 17337b000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.616214 17337b000 Delete type=0 #84
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.590832 171567000 Recovering log #38
|
||||
2026/03/31-15:50:48.591262 171567000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.591291 171567000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.515976 16e807000 Recovering log #86
|
||||
2026/05/27-23:54:37.516904 16e807000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.517115 16e807000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.564411 1717e7000 Recovering log #34
|
||||
2026/03/29-21:14:27.564754 1717e7000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.564784 1717e7000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.617145 17337b000 Recovering log #84
|
||||
2026/05/19-23:19:40.617442 17337b000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.617486 17337b000 Delete type=0 #84
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.592976 170d5b000 Recovering log #38
|
||||
2026/03/31-15:50:48.593456 170d5b000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.593476 170d5b000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.521319 16f81f000 Recovering log #86
|
||||
2026/05/27-23:54:37.522931 16f81f000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.523174 16f81f000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.565839 1707cf000 Recovering log #34
|
||||
2026/03/29-21:14:27.566214 1707cf000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.566242 1707cf000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.618390 17337b000 Recovering log #84
|
||||
2026/05/19-23:19:40.618663 17337b000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.618694 17337b000 Delete type=0 #84
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000089
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.594786 171567000 Recovering log #38
|
||||
2026/03/31-15:50:48.595201 171567000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.595227 171567000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.526390 17002b000 Recovering log #88
|
||||
2026/05/27-23:54:37.527569 17002b000 Delete type=0 #88
|
||||
2026/05/27-23:54:37.527659 17002b000 Delete type=3 #87
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.567335 170fdb000 Recovering log #34
|
||||
2026/03/29-21:14:27.567720 170fdb000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.567753 170fdb000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.619688 17337b000 Recovering log #86
|
||||
2026/05/19-23:19:40.620003 17337b000 Delete type=3 #85
|
||||
2026/05/19-23:19:40.620026 17337b000 Delete type=0 #86
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000087
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.597410 170d5b000 Recovering log #38
|
||||
2026/03/31-15:50:48.598033 170d5b000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.598068 170d5b000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.533375 16f81f000 Recovering log #86
|
||||
2026/05/27-23:54:37.534489 16f81f000 Delete type=3 #85
|
||||
2026/05/27-23:54:37.534725 16f81f000 Delete type=0 #86
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.568770 1707cf000 Recovering log #34
|
||||
2026/03/29-21:14:27.569097 1707cf000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.569138 1707cf000 Delete type=0 #34
|
||||
2026/05/19-23:19:40.621197 17337b000 Recovering log #84
|
||||
2026/05/19-23:19:40.621497 17337b000 Delete type=3 #83
|
||||
2026/05/19-23:19:40.621534 17337b000 Delete type=0 #84
|
||||
|
||||
@@ -1 +1 @@
|
||||
MANIFEST-000039
|
||||
MANIFEST-000089
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/31-15:50:48.600045 17054f000 Recovering log #38
|
||||
2026/03/31-15:50:48.600385 17054f000 Delete type=0 #38
|
||||
2026/03/31-15:50:48.600414 17054f000 Delete type=3 #37
|
||||
2026/05/27-23:54:37.542562 16e807000 Recovering log #88
|
||||
2026/05/27-23:54:37.542994 16e807000 Delete type=0 #88
|
||||
2026/05/27-23:54:37.543060 16e807000 Delete type=3 #87
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
2026/03/29-21:14:27.570654 170fdb000 Recovering log #34
|
||||
2026/03/29-21:14:27.571032 170fdb000 Delete type=3 #32
|
||||
2026/03/29-21:14:27.571059 170fdb000 Delete type=0 #34
|
||||
2026/05/27-23:54:24.293733 173d43000 Recovering log #86
|
||||
2026/05/27-23:54:24.295953 173d43000 Delete type=3 #85
|
||||
2026/05/27-23:54:24.296285 173d43000 Delete type=0 #86
|
||||
|
||||