Give cross-body bars a true 3D axis and fix the goblet squat hold
The orbit was always a real camera orbit — figure and props share one rigid rotation — but a bar's screen-space angle authored the wrong 3D rod: the default horizontal encoded a rod along the body axis, so barbells hovered fixed on screen and vanished at the head-on view where they should span widest. Line props now take "axis": "z" (both renderers in lockstep, fixture-pinned): the world left-right direction projects through the camera pitch like the floor quad — end-on plates in profile, full span face-on, swinging with the hands in between. Applied to the ten cross-body bars; vertical handles were already orbit-invariant. Goblet Squat's hand pins sat so close to the shoulders that the two-bone IK was degenerate, flipping between a chicken-wing and an elbow-behind solve; re-pinned level with the shoulders so the elbows tuck straight down through the whole rep. Claude-Session: https://claude.ai/code/session_01HJDQQDA9QdP8zByg43H5v3
@@ -1,5 +1,13 @@
|
||||
**July 2026**
|
||||
|
||||
Barbells and pull-up bars in the animated form guide now turn with the figure as the view circles, instead of hovering fixed on screen.
|
||||
|
||||
The goblet squat form guide now holds the weight at the chest with elbows tucked down, instead of flaring oddly.
|
||||
|
||||
Each set you complete is now recorded — adjust the reps or weight you actually did right from the rest screen.
|
||||
|
||||
The Weight Progression chart and workout volume now reflect what you actually lifted, not just the plan.
|
||||
|
||||
A Live Activity now shows your current exercise, set, and rest countdown on the Lock Screen and in the Dynamic Island.
|
||||
|
||||
Any exercise from the library can now be added mid-workout, planned from your last time doing it.
|
||||
|
||||
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 164.1 90.9 L 160.0 90.4 L 160.0 91.3" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 160.0 90.4 Q 163.2 60.6 166.2 32.1" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 166.2 33.5 L 182.9 46.1 L 164.2 36.6" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 147.4 36.0 L 183.8 36.0" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="147.4" cy="36.0" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="183.8" cy="36.0" r="9.799999999999999" fill="#6b7180"/>
|
||||
<path d="M 165.6 32.8 L 165.6 39.1" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="165.6" cy="32.8" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="165.6" cy="39.1" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle id="head" cx="168.2" cy="18.5" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="175.2" y1="18.7" x2="180.1" y2="18.9" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 134.0 121.7 L 129.9 121.2 L 129.9 122.1" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 129.9 121.2 Q 148.2 97.2 162.3 72.1" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 162.3 73.4 L 183.0 70.2 L 162.1 68.8" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 145.3 68.1 L 181.7 68.1" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="145.3" cy="68.1" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="181.7" cy="68.1" r="9.799999999999999" fill="#6b7180"/>
|
||||
<path d="M 163.5 65.0 L 163.5 71.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="163.5" cy="65.0" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="163.5" cy="71.3" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle id="head" cx="170.5" cy="60.9" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="177.5" y1="61.9" x2="182.3" y2="62.6" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 14}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 14}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 173 KiB After Width: | Height: | Size: 157 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 134.0 121.7 L 129.9 121.2 L 129.9 122.1" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 129.9 121.2 Q 148.2 97.2 162.3 72.1" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 162.3 73.4 L 183.0 70.2 L 162.1 68.8" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 145.3 68.1 L 181.7 68.1" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="145.3" cy="68.1" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="181.7" cy="68.1" r="9.799999999999999" fill="#6b7180"/>
|
||||
<path d="M 163.5 65.0 L 163.5 71.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="163.5" cy="65.0" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle cx="163.5" cy="71.3" r="9.799999999999999" fill="#6b7180"/>
|
||||
<circle id="head" cx="170.5" cy="60.9" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="177.5" y1="61.9" x2="182.3" y2="62.6" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 150.0 116.0 Q 106.5 116.0 65.0 116.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 117.2 L 195.3 109.3 L 196.0 148.7 L 206.9 147.6" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 65.0 117.9 L 91.6 131.7 L 93.0 102.2" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 69.0 101.2 L 121.0 101.2" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="69.0" cy="101.2" r="12" fill="#6b7180"/>
|
||||
<circle cx="121.0" cy="101.2" r="12" fill="#6b7180"/>
|
||||
<path d="M 95.0 96.7 L 95.0 105.8" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="95.0" cy="96.7" r="12" fill="#6b7180"/>
|
||||
<circle cx="95.0" cy="105.8" r="12" fill="#6b7180"/>
|
||||
<circle id="head" cx="45.2" cy="113.3" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="46.6" y1="103.4" x2="47.6" y2="96.5" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.5 KiB After Width: | Height: | Size: 2.5 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 150.0 116.0 Q 106.5 116.0 65.0 116.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 117.2 L 195.3 109.3 L 196.0 148.7 L 206.9 147.6" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 65.0 117.9 L 60.6 88.7 L 67.0 59.8" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 43.0 58.9 L 95.0 58.9" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="43.0" cy="58.9" r="12" fill="#6b7180"/>
|
||||
<circle cx="95.0" cy="58.9" r="12" fill="#6b7180"/>
|
||||
<path d="M 69.0 54.4 L 69.0 63.4" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="69.0" cy="54.4" r="12" fill="#6b7180"/>
|
||||
<circle cx="69.0" cy="63.4" r="12" fill="#6b7180"/>
|
||||
<circle id="head" cx="45.2" cy="113.3" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="46.6" y1="103.4" x2="47.6" y2="96.5" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.5 KiB After Width: | Height: | Size: 2.5 KiB |
@@ -8,7 +8,7 @@
|
||||
{"kind": "line", "pts": [[78, 129], [78, 150]], "w": 4},
|
||||
{"kind": "line", "pts": [[144, 129], [144, 150]], "w": 4}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
After Width: | Height: | Size: 354 KiB |
|
Before Width: | Height: | Size: 159 KiB After Width: | Height: | Size: 156 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 150.0 116.0 Q 106.5 116.0 65.0 116.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 117.2 L 195.3 109.3 L 196.0 148.7 L 206.9 147.6" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 65.0 117.9 L 91.6 131.7 L 93.0 102.2" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 69.0 101.2 L 121.0 101.2" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="69.0" cy="101.2" r="12" fill="#6b7180"/>
|
||||
<circle cx="121.0" cy="101.2" r="12" fill="#6b7180"/>
|
||||
<path d="M 95.0 96.7 L 95.0 105.8" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="95.0" cy="96.7" r="12" fill="#6b7180"/>
|
||||
<circle cx="95.0" cy="105.8" r="12" fill="#6b7180"/>
|
||||
<circle id="head" cx="45.2" cy="113.3" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="46.6" y1="103.4" x2="47.6" y2="96.5" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.5 KiB After Width: | Height: | Size: 2.5 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 116.5 109.1 L 112.4 108.6 L 112.4 109.5" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 112.4 108.6 Q 142.6 103.8 169.8 93.5" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 169.8 94.8 L 164.3 114.8 L 158.1 134.6" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 141.4 133.7 L 177.8 133.7" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="141.4" cy="133.7" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="177.8" cy="133.7" r="11.2" fill="#6b7180"/>
|
||||
<path d="M 159.6 130.6 L 159.6 136.9" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="159.6" cy="130.6" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="159.6" cy="136.9" r="11.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="183.4" cy="90.4" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="190.4" y1="91.2" x2="195.3" y2="91.8" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 157.1 90.9 L 153.0 90.4 L 153.0 91.3" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 153.0 90.4 Q 158.3 60.9 163.3 32.7" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 163.3 34.0 L 167.6 54.3 L 160.7 73.8" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 143.9 73.2 L 180.3 73.2" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="143.9" cy="73.2" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="180.3" cy="73.2" r="11.2" fill="#6b7180"/>
|
||||
<path d="M 162.1 70.0 L 162.1 76.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="162.1" cy="70.0" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="162.1" cy="76.3" r="11.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="166.2" cy="19.2" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="173.2" y1="19.7" x2="178.1" y2="20.0" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l", "spine"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 16}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 16}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 262 KiB After Width: | Height: | Size: 263 KiB |
|
Before Width: | Height: | Size: 187 KiB After Width: | Height: | Size: 167 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 116.5 109.1 L 112.4 108.6 L 112.4 109.5" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 112.4 108.6 Q 142.6 103.8 169.8 93.5" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 169.8 94.8 L 164.3 114.8 L 158.1 134.6" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 141.4 133.7 L 177.8 133.7" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="141.4" cy="133.7" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="177.8" cy="133.7" r="11.2" fill="#6b7180"/>
|
||||
<path d="M 159.6 130.6 L 159.6 136.9" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="159.6" cy="130.6" r="11.2" fill="#6b7180"/>
|
||||
<circle cx="159.6" cy="136.9" r="11.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="183.4" cy="90.4" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="190.4" y1="91.2" x2="195.3" y2="91.8" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -1,16 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 320 180" fill="none">
|
||||
<title>Goblet Squat</title>
|
||||
<path d="M 142.9 157.6 L 199.8 157.6 L 199.8 150.1 L 142.9 150.1 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path d="M 142.9 157.6 L 197.4 157.6 L 197.4 150.1 L 142.9 150.1 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path id="leg_l" d="M 164.3 90.6 L 155.0 121.9 L 164.3 148.8 L 156.8 151.3" stroke="#86cfc5" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 160.0 91.0 L 151.5 122.5 L 161.4 149.1 L 154.0 151.8" stroke="#0d9488" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 169.6 30.1 L 191.1 28.5 L 174.4 41.9" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 169.6 30.1 L 163.7 50.5 L 180.9 37.7" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="girdle" d="M 169.6 30.1 L 165.3 30.0 L 165.3 31.4" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="pelvisBar" d="M 164.3 90.6 L 160.0 90.1 L 160.0 91.0" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 160.0 90.1 Q 162.7 59.4 165.3 30.0" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 165.3 31.4 L 186.7 28.1 L 171.5 43.2" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 173.0 48.3 L 173.0 36.8" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="173.0" cy="48.3" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="173.0" cy="36.8" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<path id="arm_r" d="M 165.3 31.4 L 161.1 52.3 L 178.0 39.0" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 179.4 44.1 L 179.4 32.6" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="179.4" cy="44.1" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="179.4" cy="32.6" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle id="head" cx="167.1" cy="16.0" r="7.199999999999999" fill="white" stroke="#3a3f4b" stroke-width="4.32"/>
|
||||
<line id="nose" x1="174.3" y1="16.1" x2="179.3" y2="16.2" stroke="#3a3f4b" stroke-width="2.88" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -1,16 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 320 180" fill="none">
|
||||
<title>Goblet Squat</title>
|
||||
<path d="M 142.9 158.1 L 199.8 158.1 L 199.8 150.6 L 142.9 150.6 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path d="M 142.9 158.1 L 197.4 158.1 L 197.4 150.6 L 142.9 150.6 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path id="leg_l" d="M 157.1 118.0 L 187.1 131.8 L 164.3 149.2 L 171.0 153.4" stroke="#86cfc5" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 178.0 60.9 L 163.3 76.5 L 184.5 72.1" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 178.0 60.9 L 170.7 80.9 L 188.8 69.3" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 152.8 118.3 L 183.3 131.0 L 161.4 149.5 L 168.3 153.3" stroke="#0d9488" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="girdle" d="M 178.0 60.9 L 173.7 60.8 L 173.7 62.2" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="pelvisBar" d="M 157.1 118.0 L 152.8 117.4 L 152.8 118.3" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 152.8 117.4 Q 165.5 89.2 173.7 60.8" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 173.7 62.2 L 160.8 79.3 L 181.6 73.4" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 183.0 78.5 L 183.0 67.0" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="183.0" cy="78.5" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="183.0" cy="67.0" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<path id="arm_r" d="M 173.7 62.2 L 168.2 82.8 L 185.9 70.6" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 187.4 75.7 L 187.4 64.2" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="187.4" cy="75.7" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="187.4" cy="64.2" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle id="head" cx="179.1" cy="47.7" r="7.199999999999999" fill="white" stroke="#3a3f4b" stroke-width="4.32"/>
|
||||
<line id="nose" x1="186.3" y1="48.2" x2="191.3" y2="48.5" stroke="#3a3f4b" stroke-width="2.88" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.2 KiB |
@@ -12,24 +12,24 @@
|
||||
"root": {"pos": [160, 66], "pitch": 5},
|
||||
"spine": [0, 0],
|
||||
"neck": 2, "head": -6,
|
||||
"shoulder_r": 38, "elbow_r": 125,
|
||||
"shoulder_l": 38, "elbow_l": 125,
|
||||
"shoulder_r": 5, "elbow_r": 140,
|
||||
"shoulder_l": 5, "elbow_l": 140,
|
||||
"hip_r": 5, "knee_r": 4, "ankle_r": 0,
|
||||
"hip_l": 5, "knee_l": 4, "ankle_l": 0,
|
||||
"pins": {"foot_r": [162, 148], "foot_l": [166, 150],
|
||||
"hand_r": [176, -2], "hand_l": [180, 0]}
|
||||
"hand_r": [185, -8], "hand_l": [189, -6]}
|
||||
},
|
||||
{
|
||||
"hold": 0.4, "tween": 1.0,
|
||||
"root": {"pos": [150, 104], "pitch": 22},
|
||||
"spine": [0, -4],
|
||||
"neck": 4, "head": -18,
|
||||
"shoulder_r": 46, "elbow_r": 120,
|
||||
"shoulder_l": 46, "elbow_l": 120,
|
||||
"shoulder_r": 15, "elbow_r": 135,
|
||||
"shoulder_l": 15, "elbow_l": 135,
|
||||
"hip_r": 96, "knee_r": 116, "ankle_r": 20,
|
||||
"hip_l": 96, "knee_l": 116, "ankle_l": 20,
|
||||
"pins": {"foot_r": [162, 148], "foot_l": [166, 150],
|
||||
"hand_r": [190, 40], "hand_l": [194, 42]}
|
||||
"hand_r": [196, 36], "hand_l": [200, 38]}
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
|
After Width: | Height: | Size: 222 KiB |
|
Before Width: | Height: | Size: 142 KiB After Width: | Height: | Size: 142 KiB |
@@ -1,16 +1,16 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 320 180" fill="none">
|
||||
<title>Goblet Squat</title>
|
||||
<path d="M 142.9 158.1 L 199.8 158.1 L 199.8 150.6 L 142.9 150.6 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path d="M 142.9 158.1 L 197.4 158.1 L 197.4 150.6 L 142.9 150.6 Z" fill="none" stroke="#b9bec9" stroke-width="2.16" stroke-linejoin="round"/>
|
||||
<path id="leg_l" d="M 157.1 118.0 L 187.1 131.8 L 164.3 149.2 L 171.0 153.4" stroke="#86cfc5" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 178.0 60.9 L 163.3 76.5 L 184.5 72.1" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 178.0 60.9 L 170.7 80.9 L 188.8 69.3" stroke="#a9afba" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 152.8 118.3 L 183.3 131.0 L 161.4 149.5 L 168.3 153.3" stroke="#0d9488" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="girdle" d="M 178.0 60.9 L 173.7 60.8 L 173.7 62.2" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="pelvisBar" d="M 157.1 118.0 L 152.8 117.4 L 152.8 118.3" stroke="#3a3f4b" stroke-width="3.6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 152.8 117.4 Q 165.5 89.2 173.7 60.8" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 173.7 62.2 L 160.8 79.3 L 181.6 73.4" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 183.0 78.5 L 183.0 67.0" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="183.0" cy="78.5" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="183.0" cy="67.0" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<path id="arm_r" d="M 173.7 62.2 L 168.2 82.8 L 185.9 70.6" stroke="#3a3f4b" stroke-width="4.32" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 187.4 75.7 L 187.4 64.2" stroke="#6b7180" stroke-width="2.16" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="187.4" cy="75.7" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle cx="187.4" cy="64.2" r="3.5999999999999996" fill="#6b7180"/>
|
||||
<circle id="head" cx="179.1" cy="47.7" r="7.199999999999999" fill="white" stroke="#3a3f4b" stroke-width="4.32"/>
|
||||
<line id="nose" x1="186.3" y1="48.2" x2="191.3" y2="48.5" stroke="#3a3f4b" stroke-width="2.88" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.2 KiB |
@@ -10,9 +10,9 @@
|
||||
<path id="spine" d="M 150.0 136.0 Q 107.3 127.0 69.3 110.2" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 137.2 L 187.9 111.6 L 203.0 148.0 L 212.8 143.1" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 69.3 112.1 L 99.3 112.3 L 124.0 129.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 100.0 128.1 L 152.0 128.1" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="100.0" cy="128.1" r="13" fill="#6b7180"/>
|
||||
<circle cx="152.0" cy="128.1" r="13" fill="#6b7180"/>
|
||||
<path d="M 126.0 123.6 L 126.0 132.7" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="126.0" cy="123.6" r="13" fill="#6b7180"/>
|
||||
<circle cx="126.0" cy="132.7" r="13" fill="#6b7180"/>
|
||||
<circle id="head" cx="60.2" cy="92.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="68.8" y1="87.6" x2="74.8" y2="84.0" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -10,9 +10,9 @@
|
||||
<path id="spine" d="M 152.0 114.0 Q 108.5 114.0 67.1 111.1" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 152.0 115.2 L 197.5 108.7 L 203.0 147.7 L 213.7 145.3" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 67.1 113.0 L 96.5 107.4 L 126.0 113.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 102.0 112.0 L 154.0 112.0" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="102.0" cy="112.0" r="13" fill="#6b7180"/>
|
||||
<circle cx="154.0" cy="112.0" r="13" fill="#6b7180"/>
|
||||
<path d="M 128.0 107.5 L 128.0 116.6" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="128.0" cy="107.5" r="13" fill="#6b7180"/>
|
||||
<circle cx="128.0" cy="116.6" r="13" fill="#6b7180"/>
|
||||
<circle id="head" cx="54.5" cy="95.8" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="61.8" y1="89.0" x2="67.0" y2="84.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -7,7 +7,7 @@
|
||||
{"kind": "line", "pts": [[50, 122], [88, 122]], "w": 9, "depth": 8},
|
||||
{"kind": "line", "pts": [[68, 127], [68, 150]], "w": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 333 KiB After Width: | Height: | Size: 347 KiB |
|
Before Width: | Height: | Size: 167 KiB After Width: | Height: | Size: 162 KiB |
@@ -10,9 +10,9 @@
|
||||
<path id="spine" d="M 152.0 114.0 Q 108.5 114.0 67.1 111.1" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 152.0 115.2 L 197.5 108.7 L 203.0 147.7 L 213.7 145.3" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 67.1 113.0 L 96.5 107.4 L 126.0 113.0" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 102.0 112.0 L 154.0 112.0" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="102.0" cy="112.0" r="13" fill="#6b7180"/>
|
||||
<circle cx="154.0" cy="112.0" r="13" fill="#6b7180"/>
|
||||
<path d="M 128.0 107.5 L 128.0 116.6" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="128.0" cy="107.5" r="13" fill="#6b7180"/>
|
||||
<circle cx="128.0" cy="116.6" r="13" fill="#6b7180"/>
|
||||
<circle id="head" cx="54.5" cy="95.8" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="61.8" y1="89.0" x2="67.0" y2="84.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 149.8 126.5 Q 127.0 97.8 105.3 70.4" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 149.8 127.5 L 187.2 116.2 L 192.3 149.3 L 201.4 147.1" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 105.3 72.1 L 130.3 77.2 L 114.1 57.8" stroke="#0d9488" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 93.7 57.0 L 137.9 57.0" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="93.7" cy="57.0" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="137.9" cy="57.0" r="10.2" fill="#6b7180"/>
|
||||
<path d="M 115.8 53.2 L 115.8 60.9" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="115.8" cy="53.2" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="115.8" cy="60.9" r="10.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="99.5" cy="54.7" r="8.5" fill="white" stroke="#3a3f4b" stroke-width="5.1"/>
|
||||
<line id="nose" x1="107.3" y1="51.3" x2="112.7" y2="48.9" stroke="#3a3f4b" stroke-width="3.4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 149.8 126.5 Q 127.0 97.8 105.3 70.4" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 149.8 127.5 L 187.2 116.2 L 192.3 149.3 L 201.4 147.1" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 105.3 72.1 L 112.7 48.0 L 107.3 23.5" stroke="#0d9488" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 86.9 22.7 L 131.1 22.7" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="86.9" cy="22.7" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="131.1" cy="22.7" r="10.2" fill="#6b7180"/>
|
||||
<path d="M 109.0 18.9 L 109.0 26.6" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="109.0" cy="18.9" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="109.0" cy="26.6" r="10.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="99.5" cy="54.7" r="8.5" fill="white" stroke="#3a3f4b" stroke-width="5.1"/>
|
||||
<line id="nose" x1="107.3" y1="51.3" x2="112.7" y2="48.9" stroke="#3a3f4b" stroke-width="3.4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -9,7 +9,7 @@
|
||||
{"kind": "line", "pts": [[140, 130], [166, 127]], "w": 8, "depth": 8},
|
||||
{"kind": "line", "pts": [[152, 133], [152, 150]], "w": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
After Width: | Height: | Size: 324 KiB |
|
Before Width: | Height: | Size: 176 KiB After Width: | Height: | Size: 158 KiB |
@@ -11,9 +11,9 @@
|
||||
<path id="spine" d="M 149.8 126.5 Q 127.0 97.8 105.3 70.4" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 149.8 127.5 L 187.2 116.2 L 192.3 149.3 L 201.4 147.1" stroke="#3a3f4b" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 105.3 72.1 L 130.3 77.2 L 114.1 57.8" stroke="#0d9488" stroke-width="5.1" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 93.7 57.0 L 137.9 57.0" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="93.7" cy="57.0" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="137.9" cy="57.0" r="10.2" fill="#6b7180"/>
|
||||
<path d="M 115.8 53.2 L 115.8 60.9" stroke="#6b7180" stroke-width="3.4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="115.8" cy="53.2" r="10.2" fill="#6b7180"/>
|
||||
<circle cx="115.8" cy="60.9" r="10.2" fill="#6b7180"/>
|
||||
<circle id="head" cx="99.5" cy="54.7" r="8.5" fill="white" stroke="#3a3f4b" stroke-width="5.1"/>
|
||||
<line id="nose" x1="107.3" y1="51.3" x2="112.7" y2="48.9" stroke="#3a3f4b" stroke-width="3.4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 150.0 122.0 Q 146.6 79.2 147.7 38.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 123.2 L 194.4 111.4 L 193.0 150.8 L 204.0 151.2" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 147.7 40.3 L 174.8 27.4 L 194.0 4.7" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 172.0 3.8 L 220.0 3.8" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 196.0 -0.3 L 196.0 8.0" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="149.5" cy="18.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="155.3" y1="10.6" x2="159.3" y2="4.9" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 150.0 122.0 Q 146.6 79.2 147.7 38.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 123.2 L 194.4 111.4 L 193.0 150.8 L 204.0 151.2" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 147.7 40.3 L 171.7 58.0 L 194.0 38.2" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 172.0 37.3 L 220.0 37.3" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 196.0 33.2 L 196.0 41.5" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="149.5" cy="18.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="158.2" y1="13.8" x2="164.2" y2="10.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -9,7 +9,7 @@
|
||||
{"kind": "circle", "c": [272, 19], "r": 4, "fill": true, "color": "prop"}
|
||||
]},
|
||||
{"type": "cable", "from": [272, 19], "to": ["hand_r", "hand_l"], "w": 4},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 161 KiB After Width: | Height: | Size: 160 KiB |
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 150.0 122.0 Q 146.6 79.2 147.7 38.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 150.0 123.2 L 194.4 111.4 L 193.0 150.8 L 204.0 151.2" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 147.7 40.3 L 171.7 58.0 L 194.0 38.2" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 172.0 37.3 L 220.0 37.3" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 196.0 33.2 L 196.0 41.5" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="149.5" cy="18.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="158.2" y1="13.8" x2="164.2" y2="10.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 2.4 KiB |
@@ -8,7 +8,7 @@
|
||||
<path id="spine" d="M 157.2 114.9 Q 157.2 84.9 157.2 56.3" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_l" d="M 161.3 56.3 L 160.4 35.7 L 158.6 15.1" stroke="#86cfc5" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 157.2 57.6 L 156.1 37.0 L 155.8 16.3" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 140.4 15.7 L 174.0 15.7" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 157.2 12.8 L 157.2 18.6" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="157.7" cy="42.5" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="164.7" y1="42.0" x2="169.6" y2="41.7" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.0 KiB After Width: | Height: | Size: 2.0 KiB |
@@ -8,7 +8,7 @@
|
||||
<path id="pelvisBar" d="M 161.3 93.0 L 157.2 92.5 L 157.2 93.4" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 157.2 92.5 Q 157.2 62.5 157.2 33.9" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 157.2 35.2 L 175.0 24.3 L 155.8 15.9" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 140.4 15.3 L 174.0 15.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 157.2 12.4 L 157.2 18.2" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="158.2" cy="20.2" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="165.1" y1="19.4" x2="170.0" y2="18.9" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.0 KiB After Width: | Height: | Size: 2.0 KiB |
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["arm_r", "arm_l"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 134 KiB After Width: | Height: | Size: 131 KiB |
@@ -8,7 +8,7 @@
|
||||
<path id="pelvisBar" d="M 161.3 93.0 L 157.2 92.5 L 157.2 93.4" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 157.2 92.5 Q 157.2 62.5 157.2 33.9" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 157.2 35.2 L 175.0 24.3 L 155.8 15.9" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 140.4 15.3 L 174.0 15.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 157.2 12.4 L 157.2 18.2" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="158.2" cy="20.2" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="165.1" y1="19.4" x2="170.0" y2="18.9" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.0 KiB After Width: | Height: | Size: 2.0 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 115.1 110.5 L 111.0 110.0 L 111.0 110.9" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 111.0 110.0 Q 139.9 100.1 164.9 85.3" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 164.9 86.6 L 165.3 107.3 L 164.9 128.0" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 148.2 127.3 L 184.6 127.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="148.2" cy="127.3" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="184.6" cy="127.3" r="9.1" fill="#6b7180"/>
|
||||
<path d="M 166.4 124.2 L 166.4 130.5" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="166.4" cy="124.2" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="166.4" cy="130.5" r="9.1" fill="#6b7180"/>
|
||||
<circle id="head" cx="177.8" cy="79.9" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="184.7" y1="80.5" x2="189.6" y2="80.9" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 162.7 90.9 L 158.6 90.4 L 158.6 91.3" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 158.6 90.4 Q 163.9 60.9 168.9 32.7" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 168.9 34.0 L 173.2 54.3 L 166.3 73.8" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 149.5 73.2 L 185.9 73.2" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="149.5" cy="73.2" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="185.9" cy="73.2" r="9.1" fill="#6b7180"/>
|
||||
<path d="M 167.7 70.0 L 167.7 76.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="167.7" cy="70.0" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="167.7" cy="76.3" r="9.1" fill="#6b7180"/>
|
||||
<circle id="head" cx="171.8" cy="19.2" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="178.8" y1="19.7" x2="183.7" y2="20.0" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l", "spine"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 191 KiB After Width: | Height: | Size: 173 KiB |
@@ -8,9 +8,9 @@
|
||||
<path id="pelvisBar" d="M 115.1 110.5 L 111.0 110.0 L 111.0 110.9" stroke="#0d9488" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 111.0 110.0 Q 139.9 100.1 164.9 85.3" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 164.9 86.6 L 165.3 107.3 L 164.9 128.0" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 148.2 127.3 L 184.6 127.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="148.2" cy="127.3" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="184.6" cy="127.3" r="9.1" fill="#6b7180"/>
|
||||
<path d="M 166.4 124.2 L 166.4 130.5" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle cx="166.4" cy="124.2" r="9.1" fill="#6b7180"/>
|
||||
<circle cx="166.4" cy="130.5" r="9.1" fill="#6b7180"/>
|
||||
<circle id="head" cx="177.8" cy="79.9" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="184.7" y1="80.5" x2="189.6" y2="80.9" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.1 KiB After Width: | Height: | Size: 2.1 KiB |
@@ -179,12 +179,21 @@ authored yaw nothing moves, so the authored look is exact.
|
||||
(`hand_r`, `foot_l`, …) plus the mid joints (`elbow_r`, `knee_l`, …), so a
|
||||
machine pad can ride a knee (`["knee_r", "knee_l"]`) or span a shin
|
||||
(`["knee_r", "foot_r"]`).
|
||||
`bar` lies at a fixed authored-view `angle` (default 0 = horizontal — in
|
||||
side view a two-handed bar is drawn horizontal by convention); `dumbbell`
|
||||
and `pad` default to perpendicular to the lower bone (forearm/shin), or
|
||||
take an explicit `angle`. Under orbit the segment rotates with the scene
|
||||
and foreshortens naturally. `plateR` puts filled discs on both ends
|
||||
(dumbbells default to 4.5).
|
||||
`bar` lies at a fixed authored-view `angle` (default 0 = horizontal);
|
||||
`dumbbell` and `pad` default to perpendicular to the lower bone
|
||||
(forearm/shin), or take an explicit `angle`. Under orbit the segment
|
||||
rotates with the scene and foreshortens naturally. `plateR` puts filled
|
||||
discs on both ends (dumbbells default to 4.5).
|
||||
A cross-body rod — a barbell, pull-up bar, or any grip that really runs
|
||||
left-right *through* both hands — should instead set `"axis": "z"`
|
||||
(superseding `angle`): its world-space direction projects through the
|
||||
camera elevation like the floor quad, so in a profile view it reads
|
||||
end-on (plates nearly concentric, seen from slightly above), opens to
|
||||
its full span face-on, and swings with the figure in between. A fixed
|
||||
screen-space `angle` can't do this — it keeps the rod glued to the
|
||||
authored direction while the body turns under it. Vertical handles
|
||||
(`angle: 90`) don't need it: a world-vertical rod is unchanged by a yaw
|
||||
orbit.
|
||||
- **`roller`** — a machine roller pad seen end-on: a filled disc riding the
|
||||
limb's lower bone near the joint in `at`, on the `side` (+1/−1) of the bone
|
||||
it presses — a leg extension's instep roller (`side: 1`), a leg curl's
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 120.0 130.0 Q 103.0 90.4 95.1 50.1" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 120.0 131.2 L 161.9 112.6 L 164.0 151.9 L 175.0 151.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 95.1 52.0 L 110.1 77.6 L 110.1 48.0" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 103.1 47.1 L 123.1 47.1" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 113.1 45.4 L 113.1 48.8" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="98.6" cy="30.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="108.5" y1="29.3" x2="115.4" y2="28.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 120.0 130.0 Q 103.0 90.4 95.1 50.1" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 120.0 131.2 L 161.9 112.6 L 164.0 151.9 L 175.0 151.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 95.1 52.0 L 112.8 28.1 L 133.6 6.8" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 126.6 5.9 L 146.6 5.9" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 136.6 4.2 L 136.6 7.6" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="98.6" cy="30.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="108.5" y1="29.3" x2="115.4" y2="28.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -9,7 +9,7 @@
|
||||
{"kind": "line", "pts": [[126, 143], [126, 151]], "w": 5},
|
||||
{"kind": "line", "pts": [[110, 151], [142, 151]], "w": 4, "depth": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 148 KiB After Width: | Height: | Size: 168 KiB |
@@ -12,7 +12,7 @@
|
||||
<path id="spine" d="M 120.0 130.0 Q 103.0 90.4 95.1 50.1" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="leg_r" d="M 120.0 131.2 L 161.9 112.6 L 164.0 151.9 L 175.0 151.3" stroke="#3a3f4b" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 95.1 52.0 L 112.8 28.1 L 133.6 6.8" stroke="#0d9488" stroke-width="6" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 126.6 5.9 L 146.6 5.9" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 136.6 4.2 L 136.6 7.6" stroke="#6b7180" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="98.6" cy="30.7" r="10" fill="white" stroke="#3a3f4b" stroke-width="6"/>
|
||||
<line id="nose" x1="108.5" y1="29.3" x2="115.4" y2="28.3" stroke="#3a3f4b" stroke-width="4" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@@ -10,7 +10,7 @@
|
||||
<path id="pelvisBar" d="M 157.1 92.3 L 153.0 91.8 L 153.0 92.7" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 153.0 91.8 Q 156.7 62.0 162.3 33.9" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 162.3 35.3 L 151.5 53.0 L 168.4 40.7" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 162.8 40.1 L 176.8 40.1" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 169.8 38.9 L 169.8 41.3" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="166.2" cy="20.7" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="173.1" y1="21.6" x2="177.9" y2="22.3" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.2 KiB |
@@ -10,7 +10,7 @@
|
||||
<path id="pelvisBar" d="M 157.1 92.3 L 153.0 91.8 L 153.0 92.7" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 153.0 91.8 Q 156.7 62.0 162.3 33.9" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 162.3 35.3 L 158.8 55.7 L 165.6 75.2" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 160.0 74.6 L 174.0 74.6" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 167.0 73.4 L 167.0 75.8" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="166.2" cy="20.7" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="173.1" y1="21.6" x2="177.9" y2="22.3" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.2 KiB |
@@ -8,7 +8,7 @@
|
||||
{"kind": "circle", "c": [186, -58], "r": 4, "fill": true, "color": "prop"}
|
||||
]},
|
||||
{"type": "cable", "from": [186, -58], "to": ["hand_r", "hand_l"], "w": 3},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
|
Before Width: | Height: | Size: 130 KiB After Width: | Height: | Size: 121 KiB |
@@ -10,7 +10,7 @@
|
||||
<path id="pelvisBar" d="M 157.1 92.3 L 153.0 91.8 L 153.0 92.7" stroke="#3a3f4b" stroke-width="3.5" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="spine" d="M 153.0 91.8 Q 156.7 62.0 162.3 33.9" stroke="#3a3f4b" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path id="arm_r" d="M 162.3 35.3 L 158.8 55.7 L 165.6 75.2" stroke="#0d9488" stroke-width="4.2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 160.0 74.6 L 174.0 74.6" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<path d="M 167.0 73.4 L 167.0 75.8" stroke="#6b7180" stroke-width="2.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||
<circle id="head" cx="166.2" cy="20.7" r="7.0" fill="white" stroke="#3a3f4b" stroke-width="4.2"/>
|
||||
<line id="nose" x1="173.1" y1="21.6" x2="177.9" y2="22.3" stroke="#3a3f4b" stroke-width="2.8" stroke-linecap="round"/>
|
||||
<g font-family="-apple-system, Helvetica, sans-serif" font-size="11" fill="#6b7180">
|
||||
|
||||
|
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 2.2 KiB |
|
Before Width: | Height: | Size: 622 KiB After Width: | Height: | Size: 844 KiB |
@@ -340,7 +340,7 @@ def joint_points(geo, ref):
|
||||
sum(p[1] for p in pts) / len(pts)), direction)
|
||||
|
||||
|
||||
def resolve_props(props, geo, anchor, rot=K.IDENTITY, auth_geo=None):
|
||||
def resolve_props(props, geo, anchor, rot=K.IDENTITY, auth_geo=None, pitch=CAMERA_PITCH):
|
||||
"""Props -> drawable primitives for one frame: (background, foreground).
|
||||
|
||||
`geo` is the frame's drawn (possibly orbit-rotated) geometry, `auth_geo`
|
||||
@@ -348,7 +348,9 @@ def resolve_props(props, geo, anchor, rot=K.IDENTITY, auth_geo=None):
|
||||
frame's root canvas anchor, and `rot` the `prop_rotation` between them.
|
||||
Joint positions come from `geo`; everything authored — scene points,
|
||||
cable anchors, bar angles, pad perpendiculars, roller offsets — resolves
|
||||
against `auth_geo` and rotates through `rot`.
|
||||
against `auth_geo` and rotates through `rot`. `pitch` is the camera
|
||||
elevation, needed by `axis` props whose world-space direction projects
|
||||
through it (like the floor quad).
|
||||
"""
|
||||
auth = auth_geo if auth_geo is not None else geo
|
||||
|
||||
@@ -415,11 +417,21 @@ def resolve_props(props, geo, anchor, rot=K.IDENTITY, auth_geo=None):
|
||||
_, d = joint_points(auth, p["at"])
|
||||
if not c or not d:
|
||||
continue
|
||||
if t == "bar" or "angle" in p:
|
||||
if p.get("axis") == "z":
|
||||
# A cross-body rod (barbell, pull-up bar): its true 3D axis is
|
||||
# the world left-right axis, projected through the camera
|
||||
# elevation like the floor quad — a small vertical sliver
|
||||
# end-on in a profile view (the plates read nearly concentric,
|
||||
# seen from slightly above), full span face-on, swinging with
|
||||
# the figure in between, symmetric at 0 and 180.
|
||||
pr = math.radians(pitch)
|
||||
ux, uy = swing((0.0, math.sin(pr)), math.cos(pr))
|
||||
elif t == "bar" or "angle" in p:
|
||||
axis = dirv(p.get("angle", 0)) # fixed authored-view angle
|
||||
ux, uy = swing(axis) # foreshortens under orbit
|
||||
else:
|
||||
axis = (-d[1], d[0]) # perpendicular to the lower bone
|
||||
ux, uy = swing(axis) # foreshortens under orbit
|
||||
ux, uy = swing(axis)
|
||||
h = p.get("halfLen", {"bar": 24, "dumbbell": 7, "pad": 8}[t])
|
||||
a = (c[0] - ux * h, c[1] - uy * h)
|
||||
b = (c[0] + ux * h, c[1] + uy * h)
|
||||
@@ -662,7 +674,7 @@ def render_exercise(folder, figure="neutral", flip=False, strict=False):
|
||||
for nf in norms:
|
||||
out, geo, order, shade = frame_geometry(nf, prof, cam, flip, pitch, mat)
|
||||
resolved.append(out)
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"])
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"], pitch=pitch)
|
||||
geo, prims = apply_zoom(geo, prims, zoom)
|
||||
key_cells.append((geo, order, shade, prims))
|
||||
|
||||
@@ -682,7 +694,7 @@ def render_exercise(folder, figure="neutral", flip=False, strict=False):
|
||||
imgs = []
|
||||
for nf in timeline(resolved):
|
||||
geo, order, shade = geometry(nf)
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"])
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"], pitch=pitch)
|
||||
geo, prims = apply_zoom(geo, prims, zoom)
|
||||
imgs.append(draw_geo(geo, order, shade, working, colors, font=font, prims=prims))
|
||||
imgs[0].save(folder / "preview.gif", save_all=True, append_images=imgs[1:],
|
||||
@@ -716,7 +728,7 @@ def render_orbit(folder, figure="neutral"):
|
||||
posed["pins"] = {}
|
||||
_, geo, order, shade = frame_geometry(posed, prof, cam + off, pitch=pitch, mat=mat)
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"],
|
||||
prop_rotation(pitch, off), auth_geo)
|
||||
prop_rotation(pitch, off), auth_geo, pitch=pitch)
|
||||
geo, prims = apply_zoom(geo, prims, zoom)
|
||||
imgs.append(draw_geo(geo, order, shade, working, colors, font=font, prims=prims))
|
||||
imgs[0].save(folder / "orbit.gif", save_all=True, append_images=imgs[1:],
|
||||
@@ -734,7 +746,7 @@ def contact_sheet(folders, figure="neutral", out=None):
|
||||
mat = mat_bounds(norms, prof, cam, pitch)
|
||||
for i, nf in enumerate(norms, start=1):
|
||||
_, geo, order, shade = frame_geometry(nf, prof, cam, pitch=pitch, mat=mat)
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"])
|
||||
prims = resolve_props(props, geo, nf["root"]["pos"], pitch=pitch)
|
||||
geo, prims = apply_zoom(geo, prims, zoom)
|
||||
cells.append((f"{motion['name']} {i}/{len(norms)}",
|
||||
draw_geo(geo, order, shade, working, PALETTES["default"],
|
||||
@@ -760,7 +772,7 @@ def demo_sheet(folder):
|
||||
norms, prof, cam, pitch, props, zoom = prepare(motion, figure, flip)
|
||||
mat = mat_bounds(norms, prof, cam, pitch)
|
||||
_, geo, order, shade = frame_geometry(norms[idx], prof, cam, flip, pitch, mat)
|
||||
prims = resolve_props(props, geo, norms[idx]["root"]["pos"])
|
||||
prims = resolve_props(props, geo, norms[idx]["root"]["pos"], pitch=pitch)
|
||||
geo, prims = apply_zoom(geo, prims, zoom)
|
||||
cells.append((f"{motion['name']} — {label}",
|
||||
draw_geo(geo, order, shade, working, PALETTES[palette],
|
||||
|
||||
@@ -178,6 +178,10 @@ struct MotionProp: Codable {
|
||||
/// Fixed world angle (degrees, y-up). Default: bars are horizontal;
|
||||
/// dumbbells/pads sit perpendicular to the lower bone.
|
||||
let angle: Double?
|
||||
/// True 3D axis, superseding `angle`: `"z"` marks a cross-body rod
|
||||
/// (barbell, pull-up bar) whose projection foreshortens naturally —
|
||||
/// end-on in a profile view, full span face-on.
|
||||
let axis: String?
|
||||
let halfLen: Double?
|
||||
let w: Double?
|
||||
/// End-disc radius (dumbbell plates default 4.5; bars none).
|
||||
|
||||
@@ -576,10 +576,13 @@ enum MotionSolver {
|
||||
/// `anchor` the frame's root canvas anchor, and `rotation` the `propRotation`
|
||||
/// between them. Joint positions come from `geo`; everything authored — scene
|
||||
/// points, cable anchors, bar angles, pad perpendiculars, roller offsets —
|
||||
/// resolves against `authored` and rotates. Kept 1:1 with the reference
|
||||
/// renderer's `resolve_props` — change them in lockstep.
|
||||
/// resolves against `authored` and rotates. `pitch` is the camera elevation,
|
||||
/// needed by `axis` props whose world-space direction projects through it
|
||||
/// (like the floor quad). Kept 1:1 with the reference renderer's
|
||||
/// `resolve_props` — change them in lockstep.
|
||||
static func resolveProps(_ props: [MotionProp], geo: FigureGeometry, authored: FigureGeometry,
|
||||
anchor: CGPoint, rotation: Mat3?) -> (bg: [PropPrimitive], fg: [PropPrimitive]) {
|
||||
anchor: CGPoint, rotation: Mat3?,
|
||||
pitch: Double = MotionSolver.defaultPitch) -> (bg: [PropPrimitive], fg: [PropPrimitive]) {
|
||||
/// Authored canvas point (+ depth toward the camera) → drawn canvas.
|
||||
func place(_ x: Double, _ y: Double, _ z: Double) -> CGPoint {
|
||||
guard let rotation else { return CGPoint(x: x, y: y) }
|
||||
@@ -654,13 +657,23 @@ enum MotionSolver {
|
||||
}
|
||||
guard let at = prop.at, let now = jointAnchor(geo, at),
|
||||
let auth = jointAnchor(authored, at) else { continue }
|
||||
let axis: CGVector
|
||||
if prop.type == "bar" || prop.angle != nil {
|
||||
axis = direction(prop.angle ?? 0) // fixed authored-view angle
|
||||
let u: CGVector
|
||||
if prop.axis == "z" {
|
||||
// A cross-body rod (barbell, pull-up bar): its true 3D axis
|
||||
// is the world left-right axis, projected through the camera
|
||||
// elevation like the floor quad — a small vertical sliver
|
||||
// end-on in a profile view (the plates read nearly
|
||||
// concentric, seen from slightly above), full span face-on,
|
||||
// swinging with the figure in between, symmetric at 0 and 180.
|
||||
let pr = pitch * .pi / 180
|
||||
let axis = Vec3(0, -sin(pr), cos(pr))
|
||||
let v = rotation?.apply(axis) ?? axis
|
||||
u = CGVector(dx: v.x, dy: -v.y)
|
||||
} else if prop.type == "bar" || prop.angle != nil {
|
||||
u = swing(direction(prop.angle ?? 0)) // fixed authored-view angle, foreshortens under orbit
|
||||
} else {
|
||||
axis = CGVector(dx: -auth.direction.dy, dy: auth.direction.dx)
|
||||
u = swing(CGVector(dx: -auth.direction.dy, dy: auth.direction.dx))
|
||||
}
|
||||
let u = swing(axis) // foreshortens under orbit
|
||||
let h = prop.halfLen ?? defaults.halfLen
|
||||
let a = CGPoint(x: now.point.x - u.dx * h, y: now.point.y - u.dy * h)
|
||||
let b = CGPoint(x: now.point.x + u.dx * h, y: now.point.y + u.dy * h)
|
||||
@@ -764,7 +777,8 @@ struct MotionTimeline {
|
||||
guard !props.isEmpty else { return geo }
|
||||
let rotation = MotionSolver.propRotation(pitch: pitch, yawOffset: yawOffset)
|
||||
(geo.propsBackground, geo.propsForeground) = MotionSolver.resolveProps(
|
||||
props, geo: geo, authored: authored, anchor: frame.rootPos, rotation: rotation)
|
||||
props, geo: geo, authored: authored, anchor: frame.rootPos, rotation: rotation,
|
||||
pitch: pitch)
|
||||
return geo
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 14}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 14}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
{"kind": "line", "pts": [[78, 129], [78, 150]], "w": 4},
|
||||
{"kind": "line", "pts": [[144, 129], [144, 150]], "w": 4}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l", "spine"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 16}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 16}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -12,24 +12,24 @@
|
||||
"root": {"pos": [160, 66], "pitch": 5},
|
||||
"spine": [0, 0],
|
||||
"neck": 2, "head": -6,
|
||||
"shoulder_r": 38, "elbow_r": 125,
|
||||
"shoulder_l": 38, "elbow_l": 125,
|
||||
"shoulder_r": 5, "elbow_r": 140,
|
||||
"shoulder_l": 5, "elbow_l": 140,
|
||||
"hip_r": 5, "knee_r": 4, "ankle_r": 0,
|
||||
"hip_l": 5, "knee_l": 4, "ankle_l": 0,
|
||||
"pins": {"foot_r": [162, 148], "foot_l": [166, 150],
|
||||
"hand_r": [176, -2], "hand_l": [180, 0]}
|
||||
"hand_r": [185, -8], "hand_l": [189, -6]}
|
||||
},
|
||||
{
|
||||
"hold": 0.4, "tween": 1.0,
|
||||
"root": {"pos": [150, 104], "pitch": 22},
|
||||
"spine": [0, -4],
|
||||
"neck": 4, "head": -18,
|
||||
"shoulder_r": 46, "elbow_r": 120,
|
||||
"shoulder_l": 46, "elbow_l": 120,
|
||||
"shoulder_r": 15, "elbow_r": 135,
|
||||
"shoulder_l": 15, "elbow_l": 135,
|
||||
"hip_r": 96, "knee_r": 116, "ankle_r": 20,
|
||||
"hip_l": 96, "knee_l": 116, "ankle_l": 20,
|
||||
"pins": {"foot_r": [162, 148], "foot_l": [166, 150],
|
||||
"hand_r": [190, 40], "hand_l": [194, 42]}
|
||||
"hand_r": [196, 36], "hand_l": [200, 38]}
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
{"kind": "line", "pts": [[50, 122], [88, 122]], "w": 9, "depth": 8},
|
||||
{"kind": "line", "pts": [[68, 127], [68, 150]], "w": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
{"kind": "line", "pts": [[140, 130], [166, 127]], "w": 8, "depth": 8},
|
||||
{"kind": "line", "pts": [[152, 133], [152, 150]], "w": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 12}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
{"kind": "circle", "c": [272, 19], "r": 4, "fill": true, "color": "prop"}
|
||||
]},
|
||||
{"type": "cable", "from": [272, 19], "to": ["hand_r", "hand_l"], "w": 4},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["arm_r", "arm_l"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 24}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
"camera": {"zoom": 0.7},
|
||||
"working": ["leg_r", "leg_l", "spine"],
|
||||
"props": [
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 26, "plateR": 13}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
{"kind": "line", "pts": [[126, 143], [126, 151]], "w": 5},
|
||||
{"kind": "line", "pts": [[110, 151], [142, 151]], "w": 4, "depth": 5}
|
||||
]},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
{"kind": "circle", "c": [186, -58], "r": 4, "fill": true, "color": "prop"}
|
||||
]},
|
||||
{"type": "cable", "from": [186, -58], "to": ["hand_r", "hand_l"], "w": 3},
|
||||
{"type": "bar", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
{"type": "bar", "axis": "z", "at": ["hand_r", "hand_l"], "halfLen": 10}
|
||||
],
|
||||
"frames": [
|
||||
{
|
||||
|
||||
@@ -131,7 +131,7 @@ struct ExerciseMotionTests {
|
||||
bundle.url(forResource: "figure-fixtures", withExtension: "json"),
|
||||
"figure-fixtures.json must be bundled as a WorkoutsTests resource (see project.yml)")
|
||||
let fixtures = try JSONDecoder().decode(FigureFixtures.self, from: Data(contentsOf: url))
|
||||
#expect(fixtures.exercises.count == 47)
|
||||
#expect(fixtures.exercises.count == 64)
|
||||
|
||||
for exercise in fixtures.exercises {
|
||||
let resources = try #require(ExerciseMotionLibrary.resources(for: exercise.name),
|
||||
@@ -164,7 +164,7 @@ struct ExerciseMotionTests {
|
||||
let rotation = MotionSolver.propRotation(pitch: fixtures.pitch, yawOffset: orbit.yaw - cam)
|
||||
let (bg, fg) = MotionSolver.resolveProps(
|
||||
resources.motion.props ?? [], geo: geo, authored: authored,
|
||||
anchor: norms[0].rootPos, rotation: rotation)
|
||||
anchor: norms[0].rootPos, rotation: rotation, pitch: fixtures.pitch)
|
||||
expectPrims(bg, propFixture.bg, "\(exercise.name) orbit \(orbit.yaw) bg")
|
||||
expectPrims(fg, propFixture.fg, "\(exercise.name) orbit \(orbit.yaw) fg")
|
||||
}
|
||||
|
||||