Developers
10 TOP-LEVEL ITEMSREI Integration
Croparia IF approaches REI in almost the same spirit as JEI: the Recipe API provides a shared recipe abstraction, and the compatibility layer maps that abstraction onto REI's category and display system.
The main difference is that REI introduces ReiDisplay<R> explicitly as a dedicated display object.
Mental model
The key REI-side objects are:
ReiClient- the REI client plugin entrypoint
ReiCategory<R>- the recipe category
ReiDisplay<R>- the concrete display wrapper
TypedSerializer<R>- provider of type information, workstations, and recipe queries
You can read the relationship like this:
DisplayableRecipeprovides the basic display dataTypedSerializerprovides type identity and query accessReiCategorydescribes how a family of recipes should lookReiDisplaywraps one actual recipe instance into the form REI expects
ReiCategory
Croparia IF's ReiCategory<R> base class implements DisplayCategory<ReiDisplay<R>> and already takes care of:
- generating the
CategoryIdentifierfromTypedSerializer.getId() - default title translation
- default icon resolution
- building workstation entries from
TypedSerializer.getStations()
So most concrete categories only need to:
- extend
ReiCategory<R> - return the correct
TypedSerializer<R> - implement layout and drawing logic
Just like on the JEI side, if the workstation list is empty, the default icon logic is no longer enough and should be overridden.
ReiDisplay
Unlike JEI, REI wraps each recipe inside ReiDisplay<R>.
Its main job is to:
- hold the real recipe instance or
RecipeHolder - associate it with the correct
ReiCategory - expose the category identifier and display content to REI
So ReiCategory is mainly "how does this family render?", while ReiDisplay is "how is this concrete recipe instance represented?"
That separation fits REI's own API model quite well and keeps display-object management clearer.
The role of TypedSerializer inside REI
Just like with JEI, REI integration relies heavily on TypedSerializer. It mainly provides:
- the category ID
- the workstation list
- all
RecipeHoldervalues for the current recipe type
When displays are registered, ReiClient will typically call:
category.getRecipeType().findHolders()
and then wrap each holder into ReiDisplay<R>.
So if TypedSerializer is not configured correctly, REI problems usually follow right behind it.
Registration flow
Croparia IF's REI registration flow can be summarized like this:
- maintain a list of
ReiCategory<?>instances inReiClient - register categories and workstations through
registerCategories(...) - register displays for every category through
registerDisplays(...)
Compared with JEI, REI adds an extra display wrapper layer, but the overall pattern is still "start from TypedSerializer, then map runtime recipes into the display system."
Difference from JEI
If you already read JEI integration, the main REI-side distinction is:
- JEI works more directly with categories and recipe types
- REI makes the display object explicit
But in Croparia IF's design, both sides still share the same core data sources:
DisplayableRecipeTypedSerializer- the preset input and output types
That means most recipe-side design work does not need to be duplicated separately for JEI and REI.
Tips
- Keep type and workstation information inside
TypedSerializerinstead of scattering it across REI-specific classes. - Before debugging display or layout issues, first make sure
findHolders()is returning the correct runtime recipes. - If JEI and REI begin to drift too far apart, the first thing to inspect is whether
DisplayableRecipeis exposing a consistent display model. - Complex UIs may still justify separate JEI and REI layout code, but try not to let them evolve into different data models.