Fix cylinder wall-climb strafe lock and add terrain pipette support
- PlayerCharacterController: latch the wall-strafe sign once at strafe start instead of re-deriving it from the camera every frame, which flipped at the 90-degree point while circling a cylinder and caused a back-and-forth lock. Flat walls stay bit-identical; reset on enter/exit. - MeshPainter.Pick: dispatch terrain hits to a splat-layer blend (full PBR channels), terrain trees / grass / sky to rendered screen-color, keeping texel-accurate picks for the paint mesh and foreign materials. - Includes Unity auto-reserialization of SampleScene and three Supercyan pack assets (URP material upgrades, skybox/lighting) from the import. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
1 parent
85bd7c7791
commit
9dab4a742e
6 files changed
+1153
-27
No files matched your search
@@ -160,6 +160,7 @@ public class PlayerCharacterController : MonoBehaviour
|
||||
private float _lostContactTimer;
|
||||
private float _wallOffset; // current lean-out distance from the wall (mouse drag)
|
||||
private float _wallYaw; // body yaw offset from facing the wall (mouse drag); held until leaving
|
||||
private int _wallStrafeSign; // latched sideways direction (camera picks it once per strafe); 0 = unlatched
|
||||
private bool _offsetDragging; // true while the offset/rotation is being set (pauses camera orbit)
|
||||
private bool _climbLeftGround; // true once the capsule has left the ground while climbing (enables ground-detach)
|
||||
private readonly RaycastHit[] _wallProbe = new RaycastHit[8];
|
||||
@@ -365,6 +366,7 @@ public class PlayerCharacterController : MonoBehaviour
|
||||
_slideSpeed = 0f;
|
||||
_wallOffset = 0f;
|
||||
_wallYaw = 0f;
|
||||
_wallStrafeSign = 0;
|
||||
_climbLeftGround = false;
|
||||
}
|
||||
}
|
||||
@@ -447,8 +449,21 @@ public class PlayerCharacterController : MonoBehaviour
|
||||
if (wallUp.sqrMagnitude > 1e-6f) wallUp.Normalize();
|
||||
Vector3 wallRight = Vector3.Cross(_wallNormal, wallUp);
|
||||
if (wallRight.sqrMagnitude > 1e-6f) wallRight.Normalize();
|
||||
if (cameraTransform && Vector3.Dot(cameraTransform.right, wallRight) < 0f)
|
||||
|
||||
// Pick the strafe sign ONCE from the camera when a strafe begins, then hold it.
|
||||
// Re-deciding it every frame flips wallRight while rounding a curved (cylindrical)
|
||||
// wall: exactly at 90 deg to the camera the dot crosses zero, so the sideways input
|
||||
// inverts frame-to-frame and you lock there, jittering back and forth. Latching keeps
|
||||
// a strafe continuous around the curve; it resets when the strafe input releases so
|
||||
// the next one re-syncs to the camera.
|
||||
bool strafing = Mathf.Abs(h) > 1e-4f;
|
||||
if (!strafing)
|
||||
_wallStrafeSign = 0;
|
||||
else if (_wallStrafeSign == 0)
|
||||
_wallStrafeSign = (cameraTransform && Vector3.Dot(cameraTransform.right, wallRight) < 0f) ? -1 : 1;
|
||||
if (_wallStrafeSign < 0)
|
||||
wallRight = -wallRight;
|
||||
|
||||
alongSurface = wallUp * v + wallRight * h;
|
||||
}
|
||||
if (alongSurface.sqrMagnitude > 1f) alongSurface.Normalize();
|
||||
@@ -760,6 +775,7 @@ public class PlayerCharacterController : MonoBehaviour
|
||||
_verticalVelocity = 0f;
|
||||
_wallOffset = 0f;
|
||||
_wallYaw = 0f;
|
||||
_wallStrafeSign = 0;
|
||||
_offsetDragging = false;
|
||||
_climbLeftGround = false;
|
||||
_mantling = false;
|
||||
|
||||
Reference in new issue
Block a user