The bull's kick/dash/slam/roll and movement particles were ~112 lines of
hand-built CPUParticles3D in player.gd, bypassing the Fx system entirely
(Fx.spawn had zero callers) — so Siim couldn't author them in the inspector.
- Add six inspector-editable effect scenes (bull_slam/kick/dash one-shots +
bull_hoof_dust/charge_trail/roll_sparks continuous); wire player.gd to
Fx.spawn() / new Fx.attach(); register them + the gallery + smoke test.
- Extract the coded, non-particle slam rings + kick flash into a new
bull_impact_fx.gd component (bull_legs.gd pattern).
- Drop 12 now-obsolete DP dust look-params (the .tscn owns the look now).
- Trim god-file comment noise: rewrite an AI-placeholder barrel block to typed
code, drop dead commented-out bounce/topple code, fix stale post-reorg file
paths (Assets/… → art/…, PascalCase scene names → snake_case).
- Document the Siim workflow in systems/fx/README.md; update CLAUDE.md.
player.gd 1307 → 944 lines. Full suite green.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CCyaJPTHCH9EDthpf4A5Sj
The lobby hub replaced the between-fights map, leaving the whole map
subsystem unused. Remove it:
- Delete MapScreen.tscn + map_screen.gd (the dead screen) and map_node.gd
(the MapNode class).
- Strip map generation + navigation from run_state.gd (~90 lines:
_generate_map/_link_rows/reachable/select_node/node_at/current_node/
run_complete/complete_current_level, plus map/player_row/col/pending_row/col).
ensure_run() now guards on a _run_active flag instead of the map array, so
the shell reloading for each fight still can't wipe the run in progress.
- Simplify active_level() to the lobby flow (override -> lobby -> gate -> arena).
- Drop the now-unread LevelDef.color / is_boss fields and the _make_level args.
- Remove the map test from logic_test.gd.
Live flow unchanged (lobby gates via choose_level, wins via return_to_lobby).
Full headless suite green; menu + shell boot into the lobby clean.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FBbGXbzg3SD6ZBSadPPF5H
Rename the Blender working files to plain role names, dropping the version
noise: bull_v11 -> bull, matador_v03 -> matador, publik_mees_v01 ->
publik_mees, and collapse anim_bull2 into anim_bull (identical rig, newer
save kept; older duplicate dropped). Repoint create_matador_anims.py (blend
input + fbx export name), render_anim_preview.py and CLAUDE.md at the new
names.
The anim_* and sword files link the model blends as Blender libraries
(//bull_v11.blend, //matador_v03.blend, //publik_mees_v01.blend), so those
links need repointing once in Blender. The game is unaffected — it ships the
exported fbx/glb, not the .blend sources (art/blender/ is Godot-ignored).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FBbGXbzg3SD6ZBSadPPF5H
Relocate the Blender working files into art/blender/ (Godot-ignored via
the .gdignore that travels with them) and lowercase the ANIM_* files to
snake_case: anim_bull, anim_bull2, anim_matador, anim_publik_mees. Drop
the stray matador2.gd.uid (no matador2.gd exists).
Repoint .gitignore (preview + blend-backup patterns), render_anim_preview.py
and CLAUDE.md at art/blender/, and update the anim-doc references from the
deleted matador_v02 to matador_v03.
No game impact: art/blender/ sits outside Godot's import graph (confirmed:
no .blend imported, preview stays gitignored, menu boots clean).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FBbGXbzg3SD6ZBSadPPF5H
Group all raw art by role under art/ (characters, levels, weapons, fx,
anim, textures, ui, icons, fonts, hdri, materials), matching the earlier
code reorg. Files are snake_case; asset uids are preserved so uid:// refs
still resolve, and every res:// path reference is rewritten across scenes,
scripts and project.godot.
- Move the used assets out of Assets/ Animations/ fonts/ HUD/ HDRI/
Materials/ into art/; remove those dirs.
- Materials snake_cased: barrel_metal, barrel_wood, bear_claw_fx, fire.
- Delete unreferenced assets: alternate models, empty stub scripts,
superseded BEAR_*.tres, marketing/spare PNGs, a spare font weight and
the orphan M_Barrel_wood.gdshader.
- Blender: drop .blend auto-backups and matador_v01/v02 (+ stale v02 fbx);
keep matador_v03 and repoint create_matador_anims.py to it. .gitignore
now blocks all Blender/*.blend[0-9] backups.
- GLB Extract-Textures siblings (art/levels/*.png) kept and tracked.
- Document the art/ layout in CLAUDE.md.
Headless suite green; menu and gameplay shell boot clean.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FBbGXbzg3SD6ZBSadPPF5H
An unreferenced duplicate of levels/bear_level.tscn (the canonical bear level) that
git add -A pulled in by accident. Return it to untracked — it's kept on disk so
Richard can decide whether it's an accidental editor save-out to delete.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017KoYBYQgRyY1zDHXMsXY3V
The team hosts on Gitea, so .github/workflows/ci.yml is dead weight. The Gitea
workflow (.gitea/workflows/ci.yml) is the single source of CI: lint + headless
tests on push/PR, plus the daily safety-net run.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017KoYBYQgRyY1zDHXMsXY3V
Add a schedule trigger (04:00 UTC daily) + workflow_dispatch to the Gitea CI, plus a
guard job: on push/PR it passes straight through, but on the daily run it asks the
Gitea API whether main's tip already carries a successful 'ci/headless' commit status
and, if so, skips the test job. The test job stamps that status when green, so a
commit already verified at push time is never re-tested — the nightly only spends a
runner on a tip whose push-time run was missed, skipped, or failed.
Also fix a cold-cache bug the nightly would have hit anyway: CI always starts without
a .godot cache, and a single 'godot --import' pass leaves .fbx/.glb-derived scenes
unresolved (the first pass imports base assets, the second resolves dependents), so
the headless tests couldn't load them. Import now runs twice.
Needs Gitea >= 1.21 (schedule) / >= 1.23 (the manual-run button); the auto-injected
GITEA_TOKEN needs statuses:write for the marker, granted via workflow permissions.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017KoYBYQgRyY1zDHXMsXY3V
Move the 40-odd root-level scripts and scenes into a tree that groups by role,
per the approved roadmap (WS2/WS3): actors/{player,matador,bear}, systems/{combat,
fx,input,debug,render,crowd,config}, ui/, props/ (was tscn_s/). Rename the shell
scene.tscn -> levels/game_shell.tscn and every PascalCase scene to snake_case
(Player.tscn -> player.tscn, MainMenu.tscn -> main_menu.tscn, etc.) so the
case-insensitive web/macOS filesystems can't alias two files together.
Done as a scripted move: each file travels with its .uid; every quoted res:// path
across scenes, scripts, .tres, and project.godot's 9 autoloads is rewritten; the
.godot uid/class cache is rebuilt from scratch. Scenes still resolve by uid, so the
rewrite is belt-and-suspenders. Lint globs (run_tests.sh + both CI workflows) now
walk the new dirs; an orphan animation_tree.gd.uid and 7 pre-existing trailing-
whitespace lints (barrel/torch, never covered by the old root-only glob) are cleaned.
Full suite green on both sides. Asset consolidation (Assets/Animations/fonts ->
art/) is deferred — moving imported .glb/.png/.ttf is safer done in the editor.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017KoYBYQgRyY1zDHXMsXY3V
These .gd files were committed earlier without their generated .uid siblings; the
repo tracks .uid everywhere else, so commit them too and stop each machine
regenerating (and churning) the resource UIDs.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Pq1VX2o1ZfiNRdCjD294wf
Gitea Actions is GitHub-Actions-compatible and reads .gitea/workflows/, so the
lint + headless-test gate runs on the team's own Gitea host. Unlike the GitHub
workflow it installs Godot (curl) and gdtoolkit (venv) with plain shell steps, so
it doesn't depend on the chickensoft setup-godot action being reachable from a
self-hosted runner — only actions/checkout and upload-artifact remain external,
both covered by Gitea's default action proxy.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Pq1VX2o1ZfiNRdCjD294wf
_seed_placeholders.gd is a one-off generator, not a shipped effect — it belongs
with the other headless tooling (bake_crowd_sheet, preview_*), not in the fx/
runtime dir Siim edits. Rename it to tools/seed_fx_placeholders.gd (matching the
dir's verb_noun convention) and repoint the two doc-comment references.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Pq1VX2o1ZfiNRdCjD294wf
The bull's Hitbox already routed through DamageEvent, but the spear, the bear's
maul, and the matador's reach-gore still did raw Object.call(&"take_sword_hit", ...)
— the exact scattered string paths DamageEvent was meant to retire. Add a single
static DamageEvent.deal(target, cause, at, source, knock_up) that builds the typed
event and hands it to receive_damage(), falling back to the legacy string call for
any not-yet-migrated victim, and route all four attackers (Hitbox included) through
it. The damage_pipeline characterization test proves the bull's outcomes are
unchanged.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Pq1VX2o1ZfiNRdCjD294wf
Hitbox now builds a DamageEvent (cause + hit position + shaped knock-up) and
calls the bull's new receive_damage(), instead of two stringly Object.call()s.
receive_damage adapts over the existing pip/knock-up logic so behaviour is
identical -- the characterization test drives both the string and typed paths
and asserts the same outcomes. Wire fx/damage/harness tests into run_tests.sh
+ CLAUDE.md. All hitbox guard tests green (stab, bear hitbox, ram, charge).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmG3mQGVXZUPDVapmdbWZ1
Replace code-buried CPUParticles with inspector-editable effect scenes fired
through one Fx autoload: code names the effect (Fx.spawn(&"blood_burst", xform)),
the .tscn owns the look. Ships four placeholder effects (blood_burst, slam_dust,
spark, hit_flash) seeded from the old code params, a self-freeing one_shot_effect
root helper, a live preview gallery, and an FX style guide for Siim. CPUParticles
only (mobile GLES3 constraint). Existing call sites untouched -- migrated later.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The single payload every attack will route through, replacing the stringly
Object.call(&"take_sword_hit", "gored") paths. Standalone for now; the
per-actor slices wire hitbox.gd and the bull/matador/bear receivers onto it.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmG3mQGVXZUPDVapmdbWZ1
Asserts computed Control geometry instead of pixels: HUD/menu stay on-screen,
text fits its box, tap targets >=44px, and the options scroll can reach its
overflow -- across five resolutions plus a +40% pseudo-locale pass. Wired into
run_tests.sh and the CLAUDE.md test list. 16/16 pass headless.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmG3mQGVXZUPDVapmdbWZ1
Delete 17 tracked *.tmp editor autosaves and three verified-unreferenced
orphans (Assets/bear_level.tscn, Assets/matador_2.tscn, matador_2.gd), and
gitignore *.tmp so they never return. The real Assets/bear_level_arena.glb is
kept — it still backs levels/bear_level.tscn.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmG3mQGVXZUPDVapmdbWZ1
2026-09-05 00:01:06 +03:00
16 changed files with 7 additions and 142 deletions
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.