Mega UI
Getting started
What you need installed, and the shortest path from nothing to an app on the store computer.
What you need
| Thing | Which one |
|---|---|
| Game | Megastore Simulator |
| Loader | BepInEx 5 (Mono) — not 6 |
| Library | MegaUI.dll in BepInEx/plugins/ |
| SDK | .NET SDK 6 or newer, targeting netstandard2.1 |
Megastore is a Mono game; Supermarket Simulator is IL2CPP. Installing the wrong loader makes every mod stay silent, which looks exactly like a broken mod. If you have modded Supermarket before, this is the difference that catches you.
1 · Reference the library
Two references and nothing else. Note what is missing: no UnityEngine.UI,
no TextMeshPro. A mod that draws a whole screen with Mega UI does not reference a single UI
assembly.
<Reference Include="MegaUI">
<HintPath>C:\...\BepInEx\plugins\rodopoulos\MegaUI.dll</HintPath>
<Private>false</Private>
</Reference>
<Reference Include="BepInEx">
<HintPath>C:\...\BepInEx\core\BepInEx.dll</HintPath>
<Private>false</Private>
</Reference>Without it MSBuild copies MegaUI.dll into your output, and whoever ships that folder puts a second Mega UI into BepInEx/plugins. BepInEx then drops one of the two by duplicate guid, and which copy survives is not your choice.
2 · Declare the dependency
[BepInPlugin(Guid, "My Mod", "1.0.0")]
[BepInDependency(MegaUiApi.ModGuid, BepInDependency.DependencyFlags.HardDependency)]
public sealed class Plugin : BaseUnityPlugin
{
public const string Guid = "MyMod";
}Use Hard when your mod is only a screen: BepInEx then refuses to load your
plugin at all if the library is missing, which gives one clear line in the log instead of a
TypeLoadException halfway through Awake.
Use Soft if your mod does other things too, and check
MegaUiApi.IsRegistered before touching the API.
3 · Register and describe
private void Awake()
{
var app = MegaUiApi.Register(Guid, new AppDefinition
{
Title = "Stock Report",
Icon = UiIcon.Builtin("package"),
});
if (!app.Ok)
{
Logger.LogError($"Mega UI refused this app: {app.Problem}");
return;
}
app.Build(ui =>
{
ui.Header("Warehouse");
ui.Row(r =>
{
r.Label("Boxes in storage");
r.Spacer();
r.Value(() => Warehouse.Count.ToString());
});
ui.Button("Order more", Warehouse.Order);
});
}That is the whole mod. Build it, drop the dll in BepInEx/plugins/, open the store
computer, and your icon is on the desktop.
Why Build takes a lambda
Your Awake runs long before there is a store computer in the scene. Mega UI keeps
your recipe and cooks it when the window actually exists — and again if the desktop is
rebuilt, which happens more than once per session.
You never hold a reference to anything on screen. No field for a label you have to keep updating, nothing to null-check after a scene change, nothing to dispose.
Where to go next
- Widgets — everything you can put on a screen
- Rows and cards — how to get a label left and a value right
- Screen builder — stack widgets in the browser and copy the C#