Skip to content

fix + feat: Model Ultra Necrozma's transformation, and let form conditions name their base form - #1616

Open
MiquelRForgeFlow wants to merge 3 commits into
PokeAPI:masterfrom
MiquelRForgeFlow:master-fix-ultra-necrozma
Open

fix + feat: Model Ultra Necrozma's transformation, and let form conditions name their base form#1616
MiquelRForgeFlow wants to merge 3 commits into
PokeAPI:masterfrom
MiquelRForgeFlow:master-fix-ultra-necrozma

Conversation

@MiquelRForgeFlow

@MiquelRForgeFlow MiquelRForgeFlow commented Jul 21, 2026

Copy link
Copy Markdown
Contributor

Change description

Ultra Necrozma couldn't be represented properly: it's a battle-only form that can only be reached from Dusk Mane or Dawn Wings, but pokemon_form_conditions had no way to say which form a transformation starts from.

This PR:

  1. Trigger Ultra Necrozma with the held Ultranecrozium Z using the existing held-item trigger (same pattern as Mega stones).
  2. Add a nullable base_form FK to PokemonFormCondition, so a battle-only form change can name the sibling form(s) it transforms from. Exposed on a form's trigger_conditions (REST) and as a base_form relationship (GraphQL). Nullable, so existing conditions are unaffected.
  3. Populate base_form wherever the base is a specific, unambiguous sibling rather than the default form: Ultra Necrozma (← Dusk Mane / Dawn Wings), Ash Greninja (← Battle Bond), Complete Zygarde (← 10% / 50% Power Construct), (Galarian) Zen Darmanitan, Meowstic / Tatsugiri / Magearna megas, Toxtricity / Urshifu Gmax, and Mimikyu Busted.

Battle forms that transform from their default/any form (Mega Charizard, most Gigantamax, Alcremie, Pyroar, Floette…) are intentionally left null.

Out of scope: Minior's forms are modelled inconsistently (is_battle_only flags + condition placement) and need a separate cleanup PR; not touched here.

AI coding assistance disclosure

I used AI to determine which files needed to be touched, and to check if new code is coherent.

Contributor check list

  • I have written a description of the contribution and explained its motivation.
  • I have written tests for my code changes (if applicable).
  • I have read and understood the AI Assisted Contribution guidelines.
  • I will own this change in production, and I am prepared to fix any bugs caused by my code change.

@MiquelRForgeFlow

Copy link
Copy Markdown
Contributor Author

@Naramsim

@MiquelRForgeFlow
MiquelRForgeFlow force-pushed the master-fix-ultra-necrozma branch from c74520c to 6641ec2 Compare July 22, 2026 11:59
@MiquelRForgeFlow

MiquelRForgeFlow commented Jul 23, 2026

Copy link
Copy Markdown
Contributor Author

By the way, the battle-only thing is the only assured fact. I can make that fix a part. And leave the ultra-burst-item vs held-item for discussion.

@jemarq04

Copy link
Copy Markdown
Member

It should probably just be held-item specifying the Ultranecrozium Z I think. Though finding a way to specify the required base form to specify Dawn/Dusk form is something we can consider going forward

@MiquelRForgeFlow
MiquelRForgeFlow marked this pull request as draft July 23, 2026 20:30
@MiquelRForgeFlow

Copy link
Copy Markdown
Contributor Author

I can make that fix a part

Done in #1619.

Though finding a way to specify the required base form to specify Dawn/Dusk form is something we can consider going forward

Fine by me, let's think how to do it. Probably a new column in some place. Any suggestion?

@MiquelRForgeFlow
MiquelRForgeFlow force-pushed the master-fix-ultra-necrozma branch from 6641ec2 to 1b79fac Compare July 27, 2026 18:30
@MiquelRForgeFlow MiquelRForgeFlow changed the title Add Ultra Burst trigger and make Ultra Necrozma battle-only fix: trigger Ultra Necrozma with held Ultranecrozium Z Jul 27, 2026
@MiquelRForgeFlow

Copy link
Copy Markdown
Contributor Author

Following up on the base-form question

Though finding a way to specify the required base form to specify Dawn/Dusk form is something we can consider going forward.

I'd like to propose a minimal way to cover this now, since it's the missing piece for Ultra Necrozma (and several other in-battle form changes).

The problem. pokemon_form_conditions already records how a battle-only form is triggered (here: held ultranecrozium-z), but not which sibling form it transforms from. Ultra Necrozma is special because it can only be reached from Dusk Mane or Dawn Wings (not from base Necrozma) so a single implicit "base = default form" assumption doesn't hold, and there can be more than one base.

Proposal. Add a nullable base_form_id column to pokemon_form_conditions (FK to Pokemon, mirroring how pokemon_evolution already stores base_form_id/evolved_form_id inline). It stays NULL for the common case where the base is the default/implicit form (Mega, Gmax, Primal…), so the change is fully additive and every existing row is untouched.

For Ultra Necrozma this becomes two rows (same held-item trigger, one per base form):

pokemon_form_id,form_trigger_id,trigger_item_id,trigger_ability_id,trigger_move_id,base_form_id
10316,1,969,,,10155   # necrozma-ultra ← necrozma-dusk-mane
10316,1,969,,,10156   # necrozma-ultra ← necrozma-dawn-wings

The API would surface it under the existing trigger_conditions on the form (as a base_form summary object, like base_form on evolution details), so no new endpoint is needed.

Why a column rather than a new table. It's the same pattern pokemon_evolution already uses for base_form_id, and the surface area is small: one nullable FK, a migration, one field in the PokemonFormCondition build loader, and one field in PokemonFormConditionSerializer.

Broader value. This isn't just Necrozma; it lets consumers stop heuristically guessing the base form for other in-battle changes, e.g.:

  • Zygarde Complete ← 10%/50% Power Construct
  • Greninja Ash ← Battle Bond
  • Darmanitan Zen ← Standard, Galarian Zen ← Galarian Standard

One open question: base_form_id → Pokemon keeps it consistent with pokemon_evolution.base_form (that's why the example uses pokémon IDs 10155/10156), but it does mean this row mixes a pokemon_form id with a pokemon id. Happy to point it at PokemonForm instead if you'd prefer intra-table consistency.

If this direction sounds good, I'll add the column, migration, loader, serializer field, and the Necrozma rows in this PR.

@MiquelRForgeFlow
MiquelRForgeFlow force-pushed the master-fix-ultra-necrozma branch 2 times, most recently from 9d707b3 to 7386fda Compare July 28, 2026 14:17
Use the existing held-item trigger with ultranecrozium-z--held (like Mega/Primal held-item transformations).
Add a nullable base_form FK to PokemonFormCondition so a battle-only form
change can name the sibling form(s) it transforms from. Ultra Necrozma uses
it to record that it comes from Dusk Mane or Dawn Wing (two rows sharing
the held Ultranecrozium Z trigger).

Exposed on a form's trigger_conditions in the REST API and as a base_form
relationship in GraphQL. The column is nullable, so existing conditions
(Mega, Gigantamax, Primal…) are unaffected.
Populate the base_form column (added in the previous commit) for every
battle-only form change whose base is a specific sibling rather than the
default form, so consumers no longer have to infer it:

  - Ash Greninja              ← Battle Bond
  - Complete Zygarde          ← 10% / 50% Power Construct
  - (Galarian) Zen Darmanitan ← (Galarian) Standard
  - Meowstic megas            ← Male / Female
  - Tatsugiri megas           ← Curly / Droopy / Stretchy
  - Toxtricity Gmax           ← Amped / Low-Key
  - Urshifu Gmax              ← Single Strike / Rapid Strike
  - Mimikyu Busted            ← Disguised / Totem Disguised
  - Magearna megas            ← Magearna / Original
@MiquelRForgeFlow
MiquelRForgeFlow marked this pull request as ready for review July 28, 2026 14:28
@MiquelRForgeFlow
MiquelRForgeFlow force-pushed the master-fix-ultra-necrozma branch from 7386fda to cbd02ef Compare July 28, 2026 14:28
@MiquelRForgeFlow MiquelRForgeFlow changed the title fix: trigger Ultra Necrozma with held Ultranecrozium Z feat: let form conditions specify a base form Jul 28, 2026
@MiquelRForgeFlow MiquelRForgeFlow changed the title feat: let form conditions specify a base form fix + feat: Model Ultra Necrozma's transformation, and let form conditions name their base form Jul 28, 2026
@MiquelRForgeFlow

Copy link
Copy Markdown
Contributor Author

Hello, this PR is ready. I implemented the per review proposal. It contains a migration script.

One open question: base_form_id → Pokemon keeps it consistent with pokemon_evolution.base_form (that's why the example uses pokémon IDs 10155/10156), but it does mean this row mixes a pokemon_form id with a pokemon id. Happy to point it at PokemonForm instead if you'd prefer intra-table consistency.

I pointed it to PokemonForm, it was making more sense. Also I populate base_form wherever the base is a specific, unambiguous sibling rather than the default form, except the Minior case. Minior's forms are modelled inconsistently (is_battle_only flags + condition placement) and need a separate cleanup PR after this one.

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.

2 participants