Compatibility
Minecraft: Java Edition
Platforms
Supported environments
Tags
Creators
Details

MariesLib
I wanted to pull out all the reusable code from Nourished and place it in one library. MariesLib is a shared library behind Marie's mods.
It handles the hard problems auto-classifying thousands of items from modded content, three-tier compat with modpack overrides, player tracking with memory and decay, datapack tooling with validation, a generic dynamic-UI framework, and more so consuming mods can focus on gameplay.
MariesLib 0.1.1-beta is still under development.
Development is ongoing as more systems are being refined, expanded, and stabilized. Recent work has focused on a full dynamic-UI editing framework (drag/resize, cross-component snapping, group edit mode, a slider-based config panel, and a pluggable command-center screen), a generic milestone system that works against any tracked value, and honest classification-confidence fixes across the scanner and runtime resolver.
More updates will be shared as development progresses.
Version 0.1.1-beta.4 is split into four modules:
marie-core: classification, tracking, compat, registries, config, milestonesmarie-commands: command/KubeJS integrationmarie-resources: datapack tooling and validationmarie-ui: the dynamic UI/editing frameworkThis modular structure keeps maintenance manageable and lets individual systems evolve independently.
Community
Questions, suggestions, and development discussions are welcome. A lot of the bug fixes and new features came from here.
Do you need to install this?
Yes: if you use a mod that depends on it.
Mod loaders and launchers that resolve dependencies automatically should pull MariesLib in for you. If a Marie mod fails to load, check that MariesLib is present and up to date.
For mod developers
Every Marie mod requires MariesLib as a separate mod on the classpath. There is no JarJar bundling. Declare marieslib as a required dependency and wire your runtime through MarieContext at bootstrap.
What it provides
| System | What it does |
|---|---|
| Classification | Runtime source resolution, scanner tooling, and classification traces |
| Compat discovery | Three-tier compatibility registry with modpack overrides |
| Registry lifecycle | Lifecycle-aware registries with snapshots, freeze/reset, and reload support |
| Tracking & values | Player value tracking, memory windows, decay, and effect hooks |
| Generic accumulator tracking | Arbitrary numeric trackers (MarieTracking): daily/weekly/monthly periods with retained history, usable for anything a consuming mod wants to count |
| Milestones | One-time achievements, either against nutrient-style intake or against any MarieTracking tracker, registerable via Java, datapack JSON, or KubeJS |
| Notifications | A stacking, mergeable popup system anchored above the XP bar, for discrete player-facing events |
| Dynamic UI | Drag/resize, content-scale/padding editing, cross-component snapping, group edit mode, and a pluggable command-center screen see below |
| Diagnostics | Datapack validation, unknown-item logging, and debug commands |
| Config tooling | Presets, import/export, share codes, and module locks |
| Utilities | JSON helpers, bounded LRU cache, running averages, validation |
It is designed to stay lightweight, modular, and reusable, and to provide a foundation rather than a gameplay framework.
The classification pipeline
This is the core of MariesLib.
When a consuming mod needs to reason about a source it has never seen before, MariesLib resolves it through staged runtime logic:
- Runtime resolution: with caching and cascade fallbacks
- Token normalization: for domain-specific source vocabulary
- Recipe inheritance: with honest, non-suppressive multi-value blending: a name-based keyword match no longer silently locks out a genuinely conflicting recipe signal; contested categories now show up with real, non-inflated confidence instead of a falsely "stable" result
- Override registries: via
config/<modid>/source_overrides.json - **Classification traces so developers can inspect exactly why a source resolved the way it did, step by step
There is also a developer-facing scanner for bulk analysis of unclassified or under-classified sources including multi-value detection (finding sources that should carry more than one category, like a composite recipe item spanning several value groups), an ambiguous-sources report for anything genuinely needing manual review, and a generated starter datapack of recommended tag entries. It is not a player-facing gameplay feature.
The exact pipeline is determined by the consuming mod. MariesLib provides the infrastructure; gameplay decisions remain the responsibility of the mod using it.
Milestones
A generic, one-time achievement system with two flavors:
- Value milestones: cumulative intake against a named value key (e.g. "reach 500 lifetime intake of X").
- Tracker milestones: the newer, fully generic version, working against any registered
MarieTrackingaccumulator. MariesLib has no domain knowledge of what the tracker measures — mining blocks, kills, distance traveled, machine operations, spells cast, anything a consuming mod counts. Each milestone can check either a lifetime cumulative total or the tracker's current period value, and fires exactly once, ever, per player.
Tracker milestones can be registered three ways, and each fits a different kind of author:
| Method | Fits |
|---|---|
| Java API | Mod developers, compiled into the mod |
| Datapack JSON | Modpack authors and players — drop a JSON file in a world-save datapack, no recompiling |
| KubeJS | Scripting-focused modpack authors |
On completion, a milestone can grant a potion effect and/or a vanilla advancement, and fires a listenable event (marie.trackerMilestoneTriggered in KubeJS) so any script or mod can react.
Dynamic UI
A full editing framework for building draggable, resizable, in-game UI panels: built once in MariesLib, usable by any consuming mod.
- Drag & resize: any panel can become player-repositionable and resizable with a couple lines of setup.
- Content scale & padding: independent of box size: growing or shrinking a panel never distorts its text, and a dedicated slider-card editor (
ScaleConfigPanel, via theMarieScaleConfigfacade) lets players tune text scale and padding directly, per panel. - Cross-component snapping (
SnapRegistry): any registered panel's edges can snap against any other registered panel's edges during drag, regardless of whether they share a parent: genuinely independent top-level panels can snap to each other. - Group edit mode (
EditModeCoordinator) — coordinate entering/exiting edit mode across multiple independent panels at once, instead of forcing players to toggle each one separately. - Command Center: a shared, pluggable directory screen. Any consuming mod registers categories and cards into one common registry; a single screen renders all of them together, sidebar-navigated by category. Cards can open a config panel, run a command, or trigger any caller-supplied action.
Everything in this layer lives under dev.marie.framework.ui.api as the stable-facing entry point, with real usage-example javadoc on each facade.
Broad mod compatibility
MariesLib uses a three-tier compat system:
| Tier | Source | Notes |
|---|---|---|
| 1 | data/<modid>/compat/compat_registry.json in the consuming mod |
Base registry |
| 2 | data/<other_modid>/marie_compat.json from loaded mods |
Mod-provided declarations |
| 3 | config/<modid>/compat_overrides.json |
Modpack overrides |
Later tiers merge into earlier entries rather than replacing them wholesale — giving mod authors, addon authors, and modpack creators a predictable override path without recompiling.
Mods built on MariesLib
| Mod | Description |
|---|---|
| Nourished | Nutrition mod for NeoForge 1.21.1 |
| ProjectE Extended Life | (Planned) |
| Thermal Systems | (WIP) |
For mod developers
MariesLib exposes a public API through MarieAPI, plus dedicated facades for specific systems:
// Value tracking
float level = MarieAPI.getValueLevel(player, "Item");
MarieAPI.registerValue(definition);
MarieAPI.registerCompatEntry(definition);
MarieAPI.registerCustomEffect(thresholdEffect);
// Generic accumulator tracking
MarieTracking.registerTracker(TrackerDefinition.daily(id, retentionDays));
MarieTracking.incrementTracker(player, trackerId, amount);
// Tracker milestones
TrackerMilestoneRegistry.register(
TrackerMilestoneDefinition.builder()
.id("mymod:example_milestone")
.trackerId(myTrackerId)
.goal(100f)
.scope(MilestoneScope.LIFETIME)
.rewardEffectId(ResourceLocation.parse("minecraft:speed"))
.build()
);
// Notifications
MarieNotifications.show(NotificationRequest.builder(content, durationTicks).build());
// Dynamic UI
MarieScaleConfig.create(entries, persistenceProvider, Anchor.TOP_RIGHT);
MarieCommandCenter.openScreen();
See the individual reference docs (TRACKER_MILESTONES.md and others) for full usage examples, datapack schemas, and KubeJS bindings.


