A body pressed against a tree trunk slides along it on the ground, with no tick turning it back #23

Merged
agra merged 5 commits from task/3931-walking-into-a-tree-trunk-stutters-press into master 2026-10-30 14:13:10 +02:00
Owner

Tracker: #3931

Walking into a trunk's faceted proxy no longer creeps sideways and then snaps back. The body slides round the trunk, uphill or down, island trees included, and stays on walkable ground. Only a walk aimed straight into a flat facet stops against it, on a slope as on flat ground.

For the check in the app: walk into and around trees on the hills, firs and island trees, from every side. A walk within a fraction of a degree of straight into a facet stops there; at master the slope pushed such a walk sideways along the trunk, a few millimetres a tick.

The branch merges master d962aee (#3930's trunks cut and reseated), and every figure below is on that map.

Why it stuttered

  • The step up never landed beside a trunk. A body walks up a slope by stepping up, moving across, then dropping back onto the ground. A trunk proxy widens downward: its facets and edges lean about 1° back. So a capsule pressed against one could not drop at all: the drop met the facet at once. With the step up failing, the walk fell back to the level move. Walking downhill beside a trunk, the drop failed the same way and the body left the ground.
  • The level move gave two different answers. It treated the walkable slope as a wall too. Sliding along the slope first and then the trunk ended somewhere else from the reverse order. Which came first depended on whether the feet were exactly on the slope at the start of the tick, so the result flipped every few ticks: +6 mm, +6 mm … then −25 mm.
  • Island-tree tops reported a wrong normal. These proxies have a flat fanned top within reach of the stepped-up capsule. The fan's middle triangles have both of their edges inner at a rim corner, so a capsule beside that corner was pushed along the top's normal, straight up or down. The drop beside these trunks then stopped on a contact that isn't there.

What changes

  • src/physics/collision.sx, the world format. A corner is inner only where every edge meeting at its point is inner. A contact at any other corner takes the gap's direction. The world file carries these corners in the inner byte, so the format goes to version 6 and the next bake rewrites it.

  • Sweeps report what they touched. Contact, SweepHit and SolidHit carry a Feature: the face, an outer edge with its direction, or a corner. For a sphere or capsule body, a point along its core counts as an edge and an end as a corner.

  • src/sim/player.sx.

    • The drop (settle, through dropped) slides down a wall it meets, a face or an edge leaning within UPRIGHT (5°) of upright, unless it already stands on ground. Faces leaning further are left as before, so walking off a bank of 60° to 82° does not surge.

    • The level move becomes slideAcross, and it keeps every wall it has met. The rest of the move goes the longest of these ways that goes into no wall met, or stops:

      • along a face too steep to stand on, slid as along a wall;
      • up standing ground along its plane, no longer slid along the slope's contour as along a wall;
      • along the crease of standing ground and another wall, as far as the move goes along the crease.

      The result does not depend on which wall is met first. A move counts up to ACROSS_WALLS (8) contacts, since climbing meets the terrain's triangles and a trunk's face and edge one by one.

    • stepAcross takes whichever of the move across and the step up goes farther along the move, not just farther.

    Climbing the ground matters where a trunk leans out over the head, as island trees' proxies do. There the step up's rise meets the overhang at once, and the move across has to carry the body. Slid along the slope's contour, a walk uphill was turned along the slope, away from the way round the trunk, and then stopped against the trunk.

Evidence

  • tests/sim_trunks.sx (about 10 s) walks a body into trunk proxies:

    • hand-built frustums of the fir and island-tree proxy shapes, plus one leaning 4.5°, each on 0°, 10° and 20° slopes, from 16 directions at 5 offsets;
    • a straight frustum shaped as an island tree's proxy, of radius 0.4 m at its foot 1.2 m underground, its sides leaning 3° out to its top 1.64 m up, on 5°, 10°, 15° and 20° slopes. Each of its 8 facets is walked at 10° to 60° off its normal either way, aimed at its middle, and the two facets facing across the slope are walked head-on too;
    • a leaning capsule body;
    • a trunk at a step's edge;
    • the task's fir at (−33.58, 11.61, −52.56);
    • every 25th tree of the first map's forest, three island trees where a stepped-up capsule meets the top's corner, and the island tree at (103.71, −120.11) walked into uphill from its east.

    It requires that no tick turns the motion back by more than 120° (moves of at least 1 mm), that every tick stands on the ground, and that no walk stops, that is, ends with 30 ticks each moving under 0.1 mm. Each slanted walk at the island-shaped frustum must also end past the trunk. The head-on walks there slide along the crease at 0.28 to 1.17 mm a tick. The test also pins the drop's limits:

    • Walking or sprinting off banks of 60°, 70°, 80° and 82°, 0.2, 0.4 and 0.5 m high, straight off and 1 rad from straight, moves no farther in a tick than walking. At this head every one of the 48 moves 0 m farther. The 80° and 82° banks pin UPRIGHT from above: with it at 0.15, 0.2 or 0.3 rad the test fails (at 0.15, sprinting off the 0.5 m 82° bank at 1 rad moves 4.1 mm farther; at 0.2 and 0.3, walking off the 0.5 m 80° bank at 1 rad moves 3.0 cm farther), and at 0.6 the 60° and 70° banks fail too.
    • Walking onto a block's corner climbs it.

    With 8fbb9e0's src/, the stop checks fail:

    • the island-tree frustums on the 10° and 20° slopes, 14 of 80 walks each;
    • the island-shaped frustum, 12, 10, 13 and 14 of 98 walks on the 5°, 10°, 15° and 20° slopes, 8 to 12 slanted walks there ending short of the trunk, and one on the 20° slope turning back;
    • the leaning capsule, 6 of 80;
    • the first map's trunks, 17 of 444;
    • the island trees, all 3 walks at (103.71, −120.11) from its east.

    With 018b8ff's src/ on the merged map, rebaked, the frustum, capsule, step-edge, fir, forest and island-tree cases fail too (for example "the first map's trunks: … 44 of 444 do" turn back, "261 of 444 do not" stand every tick).

  • tests/physics_queries.sx gains two cases:

    • a capsule beside a fanned prism top's rim corner is pushed away level by all 9 triangles there, and rising past the corner meets nothing (both fail at 018b8ff);
    • a capsule sunk beside a corner inside a flat floor is pushed straight up by all 6 triangles there.
  • The task's aggregate probe walks into every fifth tree, 2172 walks, plus the same walks turned away as a control. A walk stops when each of its last 30 of 90 ticks moves under 0.1 mm.

    snap back pushed back leave the ground stop
    into trunks, master d962aee 205 (170 at least 3 times) 292 1226 524
    into trunks, this head 0 0 0 6
    turned away, master d962aee 36 44 138 73
    turned away, this head 0 0 0 0

    Of the 6 walks into trunks that stop at this head, 4 stop at master too. The other 2 walk along a world axis to within 0.075° of straight into a fir's facet. At master they moved 0.078 m and 0.109 m over their last 30 ticks, because the slope's contour pushed them sideways along the trunk 2.6 and 3.6 mm a tick. At 8fbb9e0, 91 walks into trunks and 17 turned away stopped, 53 and 5 of them walking on at master.

  • The island trees from review run 1882, at this head:

    • (103.71, −120.11), yaw π/2, 0.3 m aside. It meets a facet 2° off its normal and slides along it, uphill, at 2.1 mm a tick. 8fbb9e0 stops it from tick 21; master went 25 mm a tick downhill along the trunk, then on.
    • (−81.50, −127.19), yaw π, 0.1 m aside. It slides round and walks 2.0 m in its last 30 ticks. 8fbb9e0 stops it.
  • The task's trunk_one.sx. The body now slides round the trunk's west side: dx −30, −32, −28, −21, −20, −20, −14 mm a tick while climbing, then on north. At master it repeats +6.3 mm then −29.4 mm every 6 ticks.

  • sak-gate full (gate run 942) passed 37 of 37 on 2b7c0ac.

  • Every existing test passes unchanged. tests/physics_seeded.sx only gains the new feature field in the SweepHit it builds. Copies of 12 sim, walk and first-map tests were made to print every figure they check, 2,107 in all. Against 8fbb9e0, 2 differ:

    • sim_swim's swimmer climbing from a 1.2 m deep bed onto a 0.8 m bank ends at (−0.2031, 0.7208) for (−0.2091, 0.7151);
    • first_map_world's walk into a fir comes 0.427447 m near its axis for 0.427327 m.
  • Mutants. Each was run against the sim tests, first_map_world and walk. These fail at least one:

    • UPRIGHT at 0.05, 0.15, 0.2, 0.3 or 0.6;
    • corners read by their edges only;
    • the drop never sliding;
    • the move sliding along each wall in the order met;
    • the slope slid along as a wall, not climbed;
    • no creases;
    • the crease taken as far as the move slid along the other wall goes;
    • ACROSS_WALLS 4;
    • moves checked against walls' level normals;
    • the climb or the crease without its clearance;
    • faces too steep to stand on climbed too.

    Five pass every test. Over the aggregate each still gives 0 snaps, 0 pushed back, 0 off the ground and the same stops:

    • creases between two standing faces left out, ACROSS_WALLS 6, and a contact facing straight up or down stopping the move: no walk changes;
    • stepAcross by level distance changes 1406 walks, and choosing the longest way by its length rather than its level length changes 137.
Tracker: [#3931](https://sak.swipelab.com/tasks/3931) Walking into a trunk's faceted proxy no longer creeps sideways and then snaps back. The body slides round the trunk, uphill or down, island trees included, and stays on walkable ground. Only a walk aimed straight into a flat facet stops against it, on a slope as on flat ground. **For the check in the app:** walk into and around trees on the hills, firs and island trees, from every side. A walk within a fraction of a degree of straight into a facet stops there; at master the slope pushed such a walk sideways along the trunk, a few millimetres a tick. The branch merges master d962aee (#3930's trunks cut and reseated), and every figure below is on that map. ## Why it stuttered - **The step up never landed beside a trunk.** A body walks up a slope by stepping up, moving across, then dropping back onto the ground. A trunk proxy widens downward: its facets and edges lean about 1° back. So a capsule pressed against one could not drop at all: the drop met the facet at once. With the step up failing, the walk fell back to the level move. Walking downhill beside a trunk, the drop failed the same way and the body left the ground. - **The level move gave two different answers.** It treated the walkable slope as a wall too. Sliding along the slope first and then the trunk ended somewhere else from the reverse order. Which came first depended on whether the feet were exactly on the slope at the start of the tick, so the result flipped every few ticks: +6 mm, +6 mm … then −25 mm. - **Island-tree tops reported a wrong normal.** These proxies have a flat fanned top within reach of the stepped-up capsule. The fan's middle triangles have both of their edges inner at a rim corner, so a capsule beside that corner was pushed along the top's normal, straight up or down. The drop beside these trunks then stopped on a contact that isn't there. ## What changes - **`src/physics/collision.sx`, the world format.** A corner is inner only where every edge meeting at its point is inner. A contact at any other corner takes the gap's direction. The world file carries these corners in the inner byte, so the format goes to version 6 and the next bake rewrites it. - **Sweeps report what they touched.** `Contact`, `SweepHit` and `SolidHit` carry a `Feature`: the face, an outer edge with its direction, or a corner. For a sphere or capsule body, a point along its core counts as an edge and an end as a corner. - **`src/sim/player.sx`.** - The drop (`settle`, through `dropped`) slides down a wall it meets, a face or an edge leaning within `UPRIGHT` (5°) of upright, unless it already stands on ground. Faces leaning further are left as before, so walking off a bank of 60° to 82° does not surge. - The level move becomes `slideAcross`, and it keeps every wall it has met. The rest of the move goes the longest of these ways that goes into no wall met, or stops: - along a face too steep to stand on, slid as along a wall; - up standing ground along its plane, no longer slid along the slope's contour as along a wall; - along the crease of standing ground and another wall, as far as the move goes along the crease. The result does not depend on which wall is met first. A move counts up to `ACROSS_WALLS` (8) contacts, since climbing meets the terrain's triangles and a trunk's face and edge one by one. - `stepAcross` takes whichever of the move across and the step up goes farther along the move, not just farther. Climbing the ground matters where a trunk leans out over the head, as island trees' proxies do. There the step up's rise meets the overhang at once, and the move across has to carry the body. Slid along the slope's contour, a walk uphill was turned along the slope, away from the way round the trunk, and then stopped against the trunk. ## Evidence - **`tests/sim_trunks.sx`** (about 10 s) walks a body into trunk proxies: - hand-built frustums of the fir and island-tree proxy shapes, plus one leaning 4.5°, each on 0°, 10° and 20° slopes, from 16 directions at 5 offsets; - a straight frustum shaped as an island tree's proxy, of radius 0.4 m at its foot 1.2 m underground, its sides leaning 3° out to its top 1.64 m up, on 5°, 10°, 15° and 20° slopes. Each of its 8 facets is walked at 10° to 60° off its normal either way, aimed at its middle, and the two facets facing across the slope are walked head-on too; - a leaning capsule body; - a trunk at a step's edge; - the task's fir at (−33.58, 11.61, −52.56); - every 25th tree of the first map's forest, three island trees where a stepped-up capsule meets the top's corner, and the island tree at (103.71, −120.11) walked into uphill from its east. It requires that no tick turns the motion back by more than 120° (moves of at least 1 mm), that every tick stands on the ground, and that no walk stops, that is, ends with 30 ticks each moving under 0.1 mm. Each slanted walk at the island-shaped frustum must also end past the trunk. The head-on walks there slide along the crease at 0.28 to 1.17 mm a tick. The test also pins the drop's limits: - Walking or sprinting off banks of 60°, 70°, 80° and 82°, 0.2, 0.4 and 0.5 m high, straight off and 1 rad from straight, moves no farther in a tick than walking. At this head every one of the 48 moves 0 m farther. The 80° and 82° banks pin `UPRIGHT` from above: with it at 0.15, 0.2 or 0.3 rad the test fails (at 0.15, sprinting off the 0.5 m 82° bank at 1 rad moves 4.1 mm farther; at 0.2 and 0.3, walking off the 0.5 m 80° bank at 1 rad moves 3.0 cm farther), and at 0.6 the 60° and 70° banks fail too. - Walking onto a block's corner climbs it. With 8fbb9e0's `src/`, the stop checks fail: - the island-tree frustums on the 10° and 20° slopes, 14 of 80 walks each; - the island-shaped frustum, 12, 10, 13 and 14 of 98 walks on the 5°, 10°, 15° and 20° slopes, 8 to 12 slanted walks there ending short of the trunk, and one on the 20° slope turning back; - the leaning capsule, 6 of 80; - the first map's trunks, 17 of 444; - the island trees, all 3 walks at (103.71, −120.11) from its east. With 018b8ff's `src/` on the merged map, rebaked, the frustum, capsule, step-edge, fir, forest and island-tree cases fail too (for example "the first map's trunks: … 44 of 444 do" turn back, "261 of 444 do not" stand every tick). - **`tests/physics_queries.sx`** gains two cases: - a capsule beside a fanned prism top's rim corner is pushed away level by all 9 triangles there, and rising past the corner meets nothing (both fail at 018b8ff); - a capsule sunk beside a corner inside a flat floor is pushed straight up by all 6 triangles there. - **The task's aggregate probe** walks into every fifth tree, 2172 walks, plus the same walks turned away as a control. A walk stops when each of its last 30 of 90 ticks moves under 0.1 mm. | | snap back | pushed back | leave the ground | stop | |---|---|---|---|---| | into trunks, master d962aee | 205 (170 at least 3 times) | 292 | 1226 | 524 | | into trunks, this head | 0 | 0 | 0 | 6 | | turned away, master d962aee | 36 | 44 | 138 | 73 | | turned away, this head | 0 | 0 | 0 | 0 | Of the 6 walks into trunks that stop at this head, 4 stop at master too. The other 2 walk along a world axis to within 0.075° of straight into a fir's facet. At master they moved 0.078 m and 0.109 m over their last 30 ticks, because the slope's contour pushed them sideways along the trunk 2.6 and 3.6 mm a tick. At 8fbb9e0, 91 walks into trunks and 17 turned away stopped, 53 and 5 of them walking on at master. - **The island trees from review run 1882**, at this head: - (103.71, −120.11), yaw π/2, 0.3 m aside. It meets a facet 2° off its normal and slides along it, uphill, at 2.1 mm a tick. 8fbb9e0 stops it from tick 21; master went 25 mm a tick downhill along the trunk, then on. - (−81.50, −127.19), yaw π, 0.1 m aside. It slides round and walks 2.0 m in its last 30 ticks. 8fbb9e0 stops it. - **The task's `trunk_one.sx`.** The body now slides round the trunk's west side: dx −30, −32, −28, −21, −20, −20, −14 mm a tick while climbing, then on north. At master it repeats +6.3 mm then −29.4 mm every 6 ticks. - `sak-gate full` (gate run 942) passed 37 of 37 on 2b7c0ac. - **Every existing test passes unchanged.** `tests/physics_seeded.sx` only gains the new `feature` field in the `SweepHit` it builds. Copies of 12 sim, walk and first-map tests were made to print every figure they check, 2,107 in all. Against 8fbb9e0, 2 differ: - sim_swim's swimmer climbing from a 1.2 m deep bed onto a 0.8 m bank ends at (−0.2031, 0.7208) for (−0.2091, 0.7151); - first_map_world's walk into a fir comes 0.427447 m near its axis for 0.427327 m. - **Mutants.** Each was run against the sim tests, `first_map_world` and `walk`. These fail at least one: - `UPRIGHT` at 0.05, 0.15, 0.2, 0.3 or 0.6; - corners read by their edges only; - the drop never sliding; - the move sliding along each wall in the order met; - the slope slid along as a wall, not climbed; - no creases; - the crease taken as far as the move slid along the other wall goes; - `ACROSS_WALLS` 4; - moves checked against walls' level normals; - the climb or the crease without its clearance; - faces too steep to stand on climbed too. Five pass every test. Over the aggregate each still gives 0 snaps, 0 pushed back, 0 off the ground and the same stops: - creases between two standing faces left out, `ACROSS_WALLS` 6, and a contact facing straight up or down stopping the move: no walk changes; - `stepAcross` by level distance changes 1406 walks, and choosing the longest way by its length rather than its level length changes 137.
A corner reads as inner only where every edge meeting at its point is
inner, and the world file carries those corners beside the inner edges
(version 6). A triangle whose two edges at a corner are inner but whose
corner lies on the surface's rim, as the middle triangles of a fanned top
do, no longer pushes a capsule beside that corner along its face's normal.
agra changed title from A body pressed against a tree trunk slides along it smoothly, with no snap back to A body pressed against a tree trunk slides along it on the ground, with no tick turning it back 2026-10-30 11:13:34 +02:00
A drop slides down a wall it meets, a face or an edge leaning within 5° of
upright, so the step up beside a trunk that widens downward lands, and a
walk downhill beside one stays on the ground; a sweep now reports whether
it met a face, an edge or a corner. A level move slides along every wall
it has met at once, starting from the move it was given, so a slope taken
for a wall and a trunk end it in the same place whichever it meets first.
Of the level walk and the step up, the one that goes farther along the
move is taken.
The move across the ground climbs standing ground along its plane, and goes along the crease of the ground and a face too steep to stand on, rather than sliding along the slope's contour as along a wall.
agra merged commit 6c24bd0b0b into master 2026-10-30 14:13:10 +02:00
Sign in to join this conversation.
No reviewers
No labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
sx/hulken!23
No description provided.