Add-on Development
An add-on runs at custom-assembly scope. Use it for extension behavior that should start when HyperionX loads HyperionX.Custom.dll and stop when that assembly is unloaded.
| Difficulty | Execution scope | Applies to |
|---|---|---|
| Advanced | Desktop process | HyperionX 1.1.10 |
An add-on runs inside HyperionX and can affect platform stability. Keep the surface small, release every resource in OnUnload(), and test a failing add-on before distributing it.
Contract
Add-ons use:
using HyperionX.Core.DataCalc.Addons;
namespace HyperionX.Custom.Addons;
The base class exposes:
| Member | Purpose |
|---|---|
Name | Display name; defaults to the class name. |
Version | Add-on version; defaults to 1.0. |
IsLoaded | Whether the base lifecycle completed loading. |
Context | Current AddonContext. |
OnLoad() | Acquire resources and subscribe to events. |
OnUnload() | Unsubscribe and dispose resources. |
Print(object) | Write a message to the HyperionX log. |
AddonContext.Dispatcher is the documented way to schedule work that must run on the desktop UI thread.
Minimal add-on
In Tools → Code Lab, select Addon → Simple addon.
using HyperionX.Core.DataCalc.Addons;
namespace HyperionX.Custom.Addons;
public class SessionLoggerAddon : AddonBase
{
public override string Name => "Session Logger";
public override string Version => "1.0";
protected override void OnLoad()
{
Print($"{Name} {Version} loaded.");
}
protected override void OnUnload()
{
Print($"{Name} unloaded.");
}
}
Save it under Custom\Addons, then build the full custom project. Code Lab emission alone does not start the add-on. Complete desktop runtime activation—use Compile Project, another runtime compile trigger, or restart HyperionX—then confirm the load message in the platform log. When the desktop runtime loads the custom assembly, it discovers concrete AddonBase subclasses, creates each one, and calls its load lifecycle.
Lifecycle
Desktop runtime compile and load
↓
Previous add-ons: OnUnload()
↓
Previous custom assembly unloads
↓
New custom assembly loads
↓
Add-on type discovered and constructed
↓
OnLoad()
↓
Add-on remains active
↓
Next reload or application shutdown
↓
OnUnload()
HyperionX isolates add-on load and unload exceptions per add-on and writes failures to the log. An add-on is retained only after OnLoad() succeeds. If OnLoad() throws, HyperionX does not later call OnUnload() for that failed instance, so OnLoad() must roll back anything it acquired before the failure.
Only successfully loaded add-ons participate in the later unload pass. Test an activation failure as well as a normal load/unload cycle.
Resource ownership pattern
Store every owned subscription or disposable so OnUnload() can reverse OnLoad().
private System.Threading.CancellationTokenSource? _stopping;
protected override void OnLoad()
{
_stopping = new System.Threading.CancellationTokenSource();
Print("Background service ready.");
}
protected override void OnUnload()
{
_stopping?.Cancel();
_stopping?.Dispose();
_stopping = null;
}
For event subscriptions, unsubscribe the same handler instance you registered. For timers, stop and dispose them. Do not leave background callbacks holding the old collectible custom assembly in memory.
UI-thread work
WPF objects must be created and mutated on the UI dispatcher.
protected override void OnLoad()
{
Context.Dispatcher?.InvokeAsync(() =>
{
Print("UI dispatcher is available.");
// Create or update documented UI integrations here.
});
}
Do not block the dispatcher with network calls, file scans, long calculations, or synchronous waits. Perform background work off-thread, then dispatch only the small UI update.
Supported boundary
The stable add-on contract in HyperionX 1.1.10 is deliberately narrow: identity, load/unload, logging, and dispatcher access. AddonContext.Session exposes the host session object, but undocumented session members are platform internals and may change. Public add-ons should not depend on an internal window, view-model, or service unless that member is documented as an extension API.
For external processes, web services, or language-independent integrations, use the local desktop API instead of an in-process add-on.
Build and recovery checklist
- Use a public, concrete class with a public parameterless constructor.
- Keep
OnLoad()fast and exception-safe. - Make
OnLoad()transactional: clean up partial work in its owncatchorfinallybefore rethrowing. - Make
OnUnload()safe after any successfully completed load. - Unsubscribe events and cancel background work.
- Dispatch UI access through
Context.Dispatcher. - Never store API keys or account credentials in source.
- Build with other custom scripts present and inspect the platform log.
- Test repeated build/reload cycles, not only the first load.
- If the add-on prevents a clean build, move its
.csfile outside the custom tree and rebuild.
Continue with Build, test, and debug, Script lifecycle, and Risk and Security.