Skip to content

feat(save-editor): group and explain the attribute list - #77

Merged
dh0er merged 8 commits into
mainfrom
claude/magischer-kreis-bug-c44969
Aug 17, 2026
Merged

feat(save-editor): group and explain the attribute list#77
dh0er merged 8 commits into
mainfrom
claude/magischer-kreis-bug-c44969

Conversation

@dh0er

@dh0er dh0er commented Aug 12, 2026

Copy link
Copy Markdown
Owner

The attribute list was a dump of raw engine ids. Some had machine-generated labels that told a player nothing — "Fill ratio (AttributeSet_Thirst)", "Critical level (%)" — several duplicated a control that already existed elsewhere, and a number of them do nothing at all in the game.

Two controls that silently did nothing

MagicianLevel sat in the attribute list under the same name as the Magic Circle row under Skills, in the same tab. Only one of the two worked: the game re-derives the attribute from the skill's GameplayEffect class on load, so a value typed into the field never survived.

Proven in game — a save whose effect class said circle 6 while MagicianLevel still said -1 let the hero use a circle 4 rune, and rune usability is stated against MagicianLevel (every rune writes m_RequiredStats[MagicianLevel] = RequiredMagicCircleLevel, the same machinery a sword uses for Strength).

That makes it the same case as the four Critical_* attributes, hidden earlier for exactly this reason. It joins them. The same exclusion now also applies on the fallback path, where the legacy private-player editor listed every row the core's summary carries without consulting the hidden set.

The advanced list, reworked

Grouped into Combat & movement, Diving, Sleep & rest and Intoxication, with the leftovers under Advanced. A group's sidebar entry only appears when the hero actually carries its attributes.

Every remaining value has a real name and a tooltip on that name saying what it does — in all twelve languages. Both live in one ICU select message per locale, so the whole table is two keys rather than fifty.

Ids that exist in several attribute sets are addressed by a composite key (Health_RecoveryRatePerHourOfSleep). That is what lets the Health and Mana sleep rates carry different wording, and what retires the (AttributeSet_X) suffix the rows used to grow.

Values dropped, and why

Dropped Reason
Toughness, ToughnessA/B/C Encumbrance was cut. Nothing in the script layer reads the value and carrying is unlimited; A/B/C are the coefficients of the curve that was meant to compute it.
16 hunger / thirst / fatigue values The game's optional survival mode, which cannot be switched on.

Both stay editable in the All-data browser — the editor hides what cannot work, it does not refuse access to the bytes.

The survival finding is written up in docs/reference/survival-mode.md: the system is fully built and the six abilities are granted, but the difficulty UI row that would enable it ships hidden behind m_IsShown = false and the remaining gate is native code no script ever calls. Forcing the runtime state true before the hero loaded, with hunger at 900/1000 — the stage that owes −15 % Strength and 1 HP per second — changed nothing. The page records the mechanics, the three places the flag is stored (and the permadeath field sitting next to it), the inventory of hidden values and the steps to re-enable the group, so the decision can be revisited without redoing the investigation.

Testing

  • New tests pin the grouping, the set-qualified hiding, and that every locale carries both a name and a tooltip for every value.
  • flutter test — 541 passed. flutter analyze lib test — no issues. cargo test -p gore-mcp — 310 passed.

🤖 Generated with Claude Code


Note

Low Risk
UI and save-field presentation only; edit paths are unchanged and hidden attributes remain reachable via All data.

Overview
Reworks the curated hero/NPC attribute UI so advanced stats are grouped (Combat / movement, Diving, Sleep & rest, Intoxication, plus Advanced), with localized display names and hover tooltips wired through heroAttributeKey and new attributeManualTooltip strings in all supported locales.

Hiding policy is centralized in heroAttributeHidden (set-aware): drops duplicate or game-derived fields such as MagicianLevel (second “Magic Circle”), unused toughness encumbrance stats, and hunger/thirst/fatigue survival values (still editable under All data). Combat sidebar now surfaces real poise/movement stats instead of an empty combat-skills bucket.

Player typed view, NPC panel, and the legacy private-player attribute list all share the same grouping, filtering, and tooltip plumbing; sidebar labels can wrap to two lines for longer group titles.

Reviewed by Cursor Bugbot for commit 679afce. Bugbot is set up for automated code reviews on this repo. Configure here.

The attribute list carried MagicianLevel as "Magic Circle" — the exact
name the Skills list already uses for the same thing, in the same tab.
Only one of the two did anything: the game re-derives the attribute from
the skill's GameplayEffect class when the save is loaded, so a value
typed into the attribute field never survives.

Proven in game: a save whose effect class said circle 6 while
MagicianLevel still said -1 let the hero use a circle 4 rune, and rune
usability is stated against MagicianLevel.

MagicianLevel therefore joins the four Critical_* attributes in
heroHiddenAttributeIds, for the same reason they are there. It stays
editable in the All-data browser.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 0db4ff1421

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread apps/save-editor/lib/features/editor/domain/hero_attributes.dart
When the typed attribute search fails or comes back empty, the hero pane
falls back to the legacy private-player editor, which listed every row
the core's summary carries — without consulting heroHiddenAttributeIds.
The core includes MagicianLevel in that summary, so on this path the two
identically named Magic Circle controls were still both there, the
ineffective one included.

The four Critical_* ids never surfaced the problem because the core's
private-player summary does not carry them at all.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@dh0er

dh0er commented Aug 12, 2026

Copy link
Copy Markdown
Owner Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Chef's kiss.

Reviewed commit: 8df9e48f19

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@dh0er

dh0er commented Aug 12, 2026

Copy link
Copy Markdown
Owner Author

@codex review

@dh0er

dh0er commented Aug 12, 2026

Copy link
Copy Markdown
Owner Author

@cursor review

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

✅ Bugbot reviewed your changes and found no new issues!

Comment @cursor review or bugbot run to trigger another review on this PR

Reviewed by Cursor Bugbot for commit 8df9e48. Configure here.

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. You're on a roll.

Reviewed commit: 8df9e48f19

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

dh0er and others added 2 commits August 14, 2026 11:42
The advanced attributes were one long list of raw engine ids with
machine-generated labels — "Fill ratio (AttributeSet_Thirst)", "Critical
level (%)" — that told a player nothing, and several of them do nothing
at all.

Grouped into Combat & movement, Diving, Sleep & rest and Intoxication,
with the leftovers still under Advanced. A group's sidebar entry only
appears when the hero actually carries its attributes.

Every remaining value now has a real name and a tooltip on that name
saying what it does in the game, in all twelve languages. Both live in
one ICU select message per locale, so the whole table is two keys.

Ids that exist in several attribute sets are addressed by a composite
key (`Health_RecoveryRatePerHourOfSleep`), which is what lets the Health
and Mana sleep rates carry different wording — and what retires the
"(AttributeSet_X)" suffix the rows used to grow. The separator is an
underscore because ICU rejects a dot in a select arm.

Dropped from the curated view, because the game does not act on them:
Toughness and its three curve coefficients (encumbrance was cut, and
carrying is unlimited), and the sixteen hunger/thirst/fatigue values of
the survival mode that cannot be switched on. All stay editable in the
All-data browser. See docs/reference/survival-mode.md.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Gothic 1 Remake contains a complete hunger/thirst/fatigue system that no
player can reach: the abilities are granted, the attribute sets are
seeded, the per-stage effects are configured — and the difficulty UI row
that would switch it on ships hidden behind m_IsShown = false, with the
remaining gate in native code no script ever calls.

Writing it down because the save editor now hides sixteen attributes on
the strength of it. If a patch switches the mode on, that decision has
to be revisited, and nobody should have to redo the investigation to
know what those values meant.

Covers what it is, why it does not run, what was measured in game, the
three places the flag is stored (and the permadeath field sitting next
to it), the full mechanics including a mis-wired thirst threshold, the
inventory of hidden values, and the steps to re-enable the group.

Registered in the reference index and in the MCP page table, so the
server can serve it as gore://reference/survival-mode.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@dh0er dh0er changed the title fix(save-editor): hide the Magic Circle attribute the game derives feat(save-editor): group and explain the attribute list Aug 14, 2026
Comment thread apps/save-editor/lib/features/editor/domain/npc_attributes.dart Outdated

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: b9ee3af21b

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread apps/save-editor/lib/features/editor/domain/npc_attributes.dart Outdated
…combat group

"XP for executing" and "XP for killing" were nearly the same sentence
twice, and neither said what the difference is.

Gothic has a non-lethal defeat state: an opponent can be beaten down and
left unconscious rather than killed, and finishing off someone who
already lies defeated is a separate act the game even tracks as its own
crime severity. So the pair is now "XP for defeating" (bringing the
character down at all, dead or merely unconscious) against "XP for
finishing off" (killing it while it lies defeated), with tooltips that
name both outcomes.

The combat group was called "Combat skills", which reads as the game's
one-handed/two-handed/bow skills. It holds poise, damage taken and
movement speed instead, so it is "Combat and movement" now, and the
message key follows the meaning.

Both across all twelve languages, each translated with its language's
established term for a downed opponent and for the finishing blow.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 564b68dc76

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread apps/save-editor/lib/features/editor/ui/attribute_detail.dart
dh0er and others added 3 commits August 14, 2026 13:56
"Combat and movement" was too wide for the sidebar. It reads
"Combat / movement" now, in every language, which is the same
information in fewer pixels.

The sidebar tile truncated with an ellipsis at one line, so a heading
that still does not fit lost its second word entirely. It wraps onto a
second line instead; the ellipsis only applies beyond that.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
"Combat / movement" and "Sleep & rest" read as sentence fragments next
to the single-word headings. English UI headings take title case, so the
second word is capitalised.

"Main stats" is carried along for the same reason — it predates this
work, but leaving it lower-case would have made the sidebar mix both
conventions.

Only English changes. German capitalises its nouns regardless, and the
other locales use sentence case for headings on purpose.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
… tooltips

Two gaps in the curated view for NPCs, both from the set-qualified keys
introduced with the grouping work.

The NPC path never passed the attribute set into the shared policy, so
heroAttributeHidden and heroAttributeGroup only ever saw the bare id.
A Fatigue RecoveryRatePerHourOfSleep therefore stayed visible on an NPC
although it is inert, and the real Health and Mana rates landed in
Advanced instead of Sleep. The panel already recovered the set from the
typed path for labels; that logic now lives on NpcAttributeRow itself,
where the filter can reach it too, and grouping, ranking, labels and
tooltips all take it.

The tooltips described what "the hero" absorbs, takes or drinks, but the
same strings render on an NPC row, where they claimed the wrong subject.
Ten of them now name "this character" instead, in all twelve languages —
including a French one whose English original never mentioned the hero
at all.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@dh0er

dh0er commented Aug 17, 2026

Copy link
Copy Markdown
Owner Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Nice work!

Reviewed commit: 679afce864

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@dh0er

dh0er commented Aug 17, 2026

Copy link
Copy Markdown
Owner Author

@codex review

@dh0er

dh0er commented Aug 17, 2026

Copy link
Copy Markdown
Owner Author

@cursor review

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

✅ Bugbot reviewed your changes and found no new issues!

Comment @cursor review or bugbot run to trigger another review on this PR

Reviewed by Cursor Bugbot for commit 679afce. Configure here.

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Another round soon, please!

Reviewed commit: 679afce864

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@dh0er
dh0er merged commit 6c1ceaa into main Aug 17, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant