Prepare independent successor playtest with spawn recovery and casualty feedback

This commit is contained in:
2026-09-19 22:12:52 +02:00
parent 61e165ef5b
commit 6cf989a060
266 changed files with 134064 additions and 154 deletions
+28 -12
View File
@@ -32,12 +32,16 @@ def perform_alignment(guard, require_idle, mouse, observe, geometry, calibration
return _perform_alignment(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, clock=clock, sleep=sleep, notify=notify)
def perform_facing(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, *, clock, sleep, notify):
def perform_facing(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, *, clock, sleep, notify, profile="standard"):
"""Separate facing-only outcome; requires exact disabled-door/lock diagnostics."""
return _perform_alignment(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, clock=clock, sleep=sleep, notify=notify, facing=True)
return _perform_alignment(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, clock=clock, sleep=sleep, notify=notify, facing=True, profile=profile)
def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, *, clock, sleep, notify, facing=False):
def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibration, approach_evidence, report, *, clock, sleep, notify, facing=False, profile="standard"):
need(type(profile) is str and profile in ('standard', 'coarse') and (facing or profile == 'standard'), 'Unknown or non-facing coarse profile')
coarse = profile == 'coarse'
need(not coarse or (report.get('coarse_facing_requested') is True and report.get('coarse_approach_requested') is True and report.get('selection_requested') is True), 'Coarse facing requires explicit matching capabilities')
max_pixels, desired_angle, max_angle = (384, 25., 35.) if coarse else (128, 10., 15.)
proof_key = 'facing_proof' if facing else 'alignment_proof'
event_prefix = 'facing' if facing else 'alignment'
need(proof_key not in report, 'Alignment attempt already exists')
@@ -48,6 +52,7 @@ def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibratio
approach.get('nonce') == pinned['nonce'] and approach.get('geometry') == pinned and
approach_evidence.get('last_sample') == approach.get('final_sample'),
'Alignment requires independently completed same-run approach')
need(not coarse or approach.get('profile') == 'coarse', 'Coarse facing requires the accepted coarse approach')
prior = approach.get('samples', [])
need(prior and prior[-1]['sample'] == approach['final_sample'], 'Original approach final body sample unavailable')
body = vector(prior[-1]['origin'])
@@ -70,9 +75,10 @@ def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibratio
'initial_sample': None, 'final_sample': None, 'selection_samples': [], 'motions': [], 'samples': []}
report[proof_key] = state
if facing:
if coarse: state['profile'] = profile
state['facing_samples'] = []
del state['selection_samples']
previous = None; active_turn = None; requests = 0
previous = None; active_turn = None; requests = 0; pixels = 0
def neutral(s):
return abs(s['forward']) <= .01 and length(s['input']) <= .01 and length(s['velocity']) <= .05
@@ -109,7 +115,7 @@ def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibratio
if active_turn is not None:
before_yaw, sign = active_turn
change = delta(yaw(s['direction']), before_yaw)
need(abs(change) <= 15, 'Native yaw exceeded alignment turn bound')
need(abs(change) <= max_angle, 'Native yaw exceeded alignment turn bound')
if abs(change) >= .05:
need(change*sign > 0, 'Native yaw reversed alignment request')
if previous:
@@ -169,12 +175,20 @@ def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibratio
while clock() < deadline:
pair = selection_pair()
if pair:
current = read()
pair = selection_pair()
if not pair:
continue
if not facing:
current = read()
pair = selection_pair()
if not pair:
continue
# Facing already has a fully consumed, guarded stable pair.
# Return its exact span; selection still consumes all later
# history and rechecks ownership before any wheel request.
require_idle()
need(clock() < deadline, 'Frozen alignment deadline exceeded at completion')
completed_at = clock()
if facing:
need(started <= completed_at and 0 <= completed_at-state['samples'][-1]['received_monotonic'] <= .5,
'Final native alignment observation is stale or clock reversed')
need(completed_at < deadline, 'Frozen alignment deadline exceeded at completion')
state['facing_samples' if facing else 'selection_samples'] = pair; state['completed'] = True
return state
error = delta(bearing(current), yaw(current['direction']))
@@ -191,9 +205,11 @@ def _perform_alignment(guard, require_idle, mouse, observe, geometry, calibratio
error = delta(bearing(before), yaw(before['direction']))
if abs(error) <= 3:
current = before; continue
desired = max(-10., min(10., .75*error))
dx = max(-128, min(128, int(round(desired/gain))))
desired = max(-desired_angle, min(desired_angle, .75*error))
dx = max(-max_pixels, min(max_pixels, int(round(desired/gain))))
if dx == 0: dx = 1 if desired/gain > 0 else -1
need(pixels+abs(dx) <= 768, 'Alignment cumulative pixel budget exhausted')
pixels += abs(dx) # Retire the attempted input before any uncertain native write.
active_turn = (yaw(before['direction']), dx*gain)
mouse.move(dx, 0, guard, deadline=deadline)
requests += 1