Uwowea Core
Core utilities shared by Uwowea addons.
Requirements
- World of Warcraft
- The addon is loaded as
Uwowea_Core
The command system uses WoW's global SlashCmdList API. No additional
libraries are required.
Installation
- Place the Core project folder in your WoW
Interface/AddOnsdirectory. - Ensure the installed addon folder is named
Uwowea_Core. - Enable Uwowea Library: Core in the AddOns list, then reload the game UI.
For a consuming addon, declare Core as a dependency in its .toc file so the
global Commands API is loaded before the addon code runs:
## Dependencies: Uwowea_Core
Usage
The addon exposes the global Commands registry. Add Uwowea_Core as a
dependency and create a registry during addon initialization:
local commands = Commands.New("MY_ADDON", "/myaddon")
The complete command setup is documented below.
Command system
Commands.lua provides a registry for WoW chat commands. A registry owns one
SlashCmdList entry and can contain any number of subcommands.
Basic usage
local commands = Commands.New("SELFBUFFTRACKER", {
"/sbt",
"/buff",
})
commands:AddCommand(Commands.Command(
"add",
function(spell)
print("Adding buff:", spell)
end,
"Adds a buff to track",
nil,
true
))
commands:AddCommand(Commands.Command(
"remove",
function(spell)
print("Removing buff:", spell)
end,
"Removes a buff from tracking",
{ "del" }
))
commands:Register()
This creates the following WoW slash command registration:
SLASH_SELFBUFFTRACKER1 = "/sbt"
SLASH_SELFBUFFTRACKER2 = "/buff"
SlashCmdList["SELFBUFFTRACKER"] = ...
The commands can then be used as:
/sbt add Well Fed
/buff del Well Fed
The add command above uses raw argument mode, so all text after add is
passed to the handler as one value. Whitespace does not need to be grouped
with quotes:
function(spell)
-- spell == "Well Fed"
end
Register() should be called once after all subcommands have been added.
Calling it again, or using a SlashCmdList key that is already registered,
raises an error instead of silently replacing an existing handler.
API
Commands.New(name, slashCommands)
Creates a command registry.
nameis the uppercase key used inSlashCmdList. It may contain letters, numbers, and underscores, but must start with a letter.slashCommandsis one slash alias or a table of aliases. The leading/is added automatically when it is omitted.
local commands = Commands.New("MY_ADDON", "/myaddon")
Commands.Command(name, handler, description, aliases, rawArguments)
Creates a subcommand definition.
nameis the subcommand name.handleris called with the parsed arguments as positional values.descriptionis shown byPrintHelp().aliasesis an optional table of subcommand aliases.rawArgumentsis an optional boolean. Whentrue, the complete text after the subcommand name is passed to the handler as one string.
Handlers can use any parameter names they need:
commands:AddCommand(Commands.Command(
"configure",
function(option, value)
print("Option:", option)
print("Value:", value)
end,
"Changes a configuration value",
{ "config", "set" }
))
The following calls all resolve to the same handler:
/myaddon configure iconSize 64
/myaddon config iconSize 64
/myaddon set iconSize 64
Subcommand names and aliases are case-insensitive.
registry:AddCommand(command)
Adds a command to the registry. Duplicate names and aliases raise an error.
registry:Register()
Registers all slash aliases and creates the SlashCmdList dispatcher. The
dispatcher executes the matching subcommand and prints the command help when
the subcommand is unknown.
registry:Execute(message)
Executes a command message without going through WoW's chat system. This is useful for tests or other integrations.
The method returns false when no subcommand matches. For a matching command
it returns true followed by the return values of the handler.
local handled, result = commands:Execute("configure iconSize 64")
registry:PrintHelp(printFunction)
Prints every registered subcommand. The optional printFunction can be
provided to capture or redirect the output; it defaults to WoW's print.
Argument parsing
Arguments are split on whitespace. Single and double quotes group text into a single argument, and the quote characters are removed:
/sbt add "Power Word: Fortitude"
/sbt add 'Well Fed'
The handler receives:
function(spell)
-- spell == "Power Word: Fortitude"
end
The command name itself is removed before the handler is called. An empty argument list therefore calls the handler with no arguments. Quoting is intended for grouping arguments; escape sequences are not interpreted.
For commands that operate on free-form text, use raw argument mode instead:
commands:AddCommand(Commands.Command(
"add",
function(spell)
print("Adding:", spell)
end,
"Adds a spell by name",
nil,
true
))
This accepts /myaddon add Power Word: Fortitude and passes
"Power Word: Fortitude" as a single handler argument.
Spell API
The Core addon exposes spell helpers through the global Core.Spells table.
The spell files are loaded by Uwowea_Core.toc, so consuming addons only need
to declare Uwowea_Core as a dependency.
Core.Spells:GetInfo(spellIdentifier)
Returns the WoW SpellInfo object for a spell ID or spell name:
local info = Core.Spells:GetInfo(12345)
if info then
print(info.name, info.iconID)
print(info:IsHelpful())
end
The result is cached by the identifier. The method returns nil when the
spell cannot be resolved or when the client does not provide
C_Spell.GetSpellInfo.
The returned value is a Core.SpellInfo object extending WoW's SpellInfo
structure. It keeps the original spell fields and adds methods that use its
own spellID:
local info = Core.Spells:GetInfo(12345)
if info and info:IsHelpful() then
print(info.name, "is helpful")
end
if info and info:IsHarmful() then
print(info.name, "is harmful")
end
These methods do not require the spell ID as an argument.
Core.Spells:GetOverrides(spellIdentifier)
Returns a list of override spell IDs for the supplied spell ID or name. The result includes both Core's known aura overrides and the override returned by the WoW API when available:
for _, overrideSpellID in ipairs(Core.Spells:GetOverrides(spellID)) do
print("Override:", overrideSpellID)
end
The result is always a table and can be empty.
Core.Spells:GetBaseSpell(spellIdentifier)
Returns the base spell ID for an override spell, or nil when no base spell
can be found:
local baseSpellID = Core.Spells:GetBaseSpell(spellID)
if baseSpellID then
print("Base spell:", baseSpellID)
end
The helper checks Core's custom override map first and then uses
C_Spell.GetBaseSpell when that API is available. Spell API calls are guarded
so addons can load without failing on clients that do not expose the
corresponding C_Spell functions.
Unit API
Core.Unit provides an object-oriented proxy over WoW's global Unit*
functions. Create an object for a unit token with Core.Unit.Get():
local player = Core.Player
local target = Core.Target
print(player:Name())
print(player:Class())
print(player:IsDeadOrGhost())
if target:Exists() and player:IsUnit("target") then
print("The target is the player")
end
Core.Unit also exposes ready-to-use instances for the standard WoW unit
tokens:
Core.Unit.Player
Core.Unit.Target
Core.Unit.Focus
Core.Unit.Mouseover
Core.Unit.Pet
Core.Unit.Vehicle
Core.Unit.Party1
Core.Unit.Raid40
Core.Unit.Arena5
Core.Unit.Boss5
Core.Unit.Nameplate40
Use Core.Unit.Get() for a custom or suffixed token, such as targettarget
or partypet1.
The proxy automatically maps shortened method names to the corresponding WoW function:
| Proxy method | WoW function |
|---|---|
unit:Name() |
UnitName(unitToken) |
unit:Class() |
UnitClass(unitToken) |
unit:IsDeadOrGhost() |
UnitIsDeadOrGhost(unitToken) |
unit:Exists() |
UnitExists(unitToken) |
unit:IsUnit(otherToken) |
UnitIsUnit(unitToken, otherToken) |
The full WoW function name is also supported when useful:
local health = player:UnitHealth()
local power = player:UnitPower(0)
The documented Unit functions are implemented as real methods on the proxy. The unit token is automatically supplied as the first argument and additional arguments are passed through unchanged.
Any newer global function whose name starts with Unit can still be called
through the dynamic fallback without requiring another wrapper in Core.
The Core methods and LuaLS annotations are generated from WoW's
UnitDocumentation, so autocomplete includes the documented method names,
parameters, and return values. For functions with multiple return values, all
return types are exposed as a LuaLS tuple:
local mainHand, offHand, ranged = Core.Unit.Player:WeaponAttackPower()
Lua does not preserve names for multiple assigned return values, so use descriptive local variable names in the assignment. The runtime forwards the exact values and return values provided by the WoW API.
Core.Unit.Get() validates only that the token is a non-empty string. It does
not require the unit to exist, so objects can safely be created for dynamic
tokens such as party1, raid5, or nameplate3. The underlying WoW function
determines the return values for invalid or unavailable units.
Game information
The Core addon exposes information about the current WoW client through
Core.GameInfo. It is initialized automatically when GameInfo.lua loads.
Core.GameInfo
The object contains the values returned by WoW's GetBuildInfo():
local gameInfo = Core.GameInfo
print(gameInfo.buildVersion)
print(gameInfo.buildNumber)
print(gameInfo.buildDate)
print(gameInfo.interfaceVersion)
print(gameInfo.localizedVersion)
print(gameInfo.buildInfo)
print(gameInfo.currentVersion)
The detected game type is available as gameInfo.type:
if gameInfo.type then
print(gameInfo.type.name)
print(gameInfo.type.interfaceVersion)
print(gameInfo.type.expansionLevel)
end
Supported game types are available through Core.GameType, including
CLASSIC, FOREVER, TBC, WOTLK, CATACLYSM, MOP, WOD, Legion,
BFA, SL, DF, TWW, Midnight, and LastTitan.
Methods
Core.GameInfo:Init()
Reads the current build information from GetBuildInfo() and updates the
object. The method is called automatically during Core initialization.
Core.GameInfo:IsInicialized()
Returns whether the game information has been initialized. The method keeps
the existing IsInicialized spelling for API compatibility.
Core.GameInfo:CheckInit()
Initializes the object if necessary and returns true:
Core.GameInfo:CheckInit()
Core.GameInfo.Is(gameName)
Checks a game type by its constant name or localized display name:
if Core.GameInfo.Is("The Burning Crusade") then
print("Running on TBC")
end
Core.GameInfo:GetGameVersion()
Prints the current build and interface version values to the chat frame. Use
the fields on Core.GameInfo when the values need to be consumed by addon
logic rather than displayed.
Development
Uwowea_Core.toc is the addon manifest and lists the Lua files loaded by WoW.
Add new runtime files to that manifest in the order required by their
dependencies. Commands.lua must be loaded before code that uses the
Commands global. Core.lua initializes Core.Spells before
AuraOverrides.lua and Spells.lua are loaded.
LuaLS type information in consuming addons
To make the Core types available to LuaLS in another addon, add this Core
project's path to that addon's .luarc.json under workspace.library. For
example, use "../Core" when the addon and Core project are sibling
directories. Add the path to the existing list rather than replacing other
library paths.
The command registry is defined as the global Commands type, so consuming
code can use it directly:
local Commands = _G["Commands"]
Do not add ---@type Commands to this local alias; LuaLS can infer its type
from the workspace definition.
Troubleshooting
- If
Commandsisnil, verify thatUwowea_Coreis installed, enabled, and listed in the consuming addon's.tocdependencies. - If slash commands do not respond, verify that
commands:Register()is called after all subcommands are added and that theSlashCmdListkey is not already used by another addon. - If the command appears in chat but a multi-word value is split into several
arguments, enable
rawArgumentsfor that subcommand or use quotes around the value.

