mlua_magic_macros
Simple, magical proc-macros to export Rust structs and enums to mlua with minimal boilerplate.
🚀 What It Does
This crate provides a set of attribute macros that write the "magic" glue code to automatically generate impl mlua::UserData for your Rust types.
- Expose struct fields as Lua properties (
player.hp). - Expose enum unit variants as Lua constructors (
PlayerStatus.Idle()). - Expose Rust methods (
&self,&mut self, andstatic) as Lua methods (player:take_damage(10)).
📦 Installation
Add this to your Cargo.toml:
[]
= { = "0.11.4", = ["lua54", "macros"] } # Or the version you are using
= "0.1.2" # Or the version you are using
✨ Quick Start Example
Here is a complete, copy-pasteable example.
1. The Rust Code
Define your types and "decorate" them with the macros.
use *;
use mlua_magic_macros;
// STEP 1: Decorate your enum
// STEP 2: Compile the UserData impl for the enum
// This generates `impl mlua::UserData for PlayerStatus`
compile!;
// STEP 1: Decorate your struct
// STEP 1 (continued): Decorate the impl block
// STEP 2: Compile the UserData impl for the struct
// This generates `impl mlua::UserData for Player`
compile!;
// STEP 3: Load the types into a Lua instance
2. The Lua Script
Now you can call your Rust code from Lua as if it were a native Lua table.
-- run_lua_code.lua
-- Call the static `new` function
local player = Player.;
print;
-- Access struct fields directly (from `#[structure]`)
print;
print;
-- Access enum variants (from `#[enumeration]`)
print; -- "Idle"
print; -- `true`
-- Call a `&mut self` method
player:;
print; -- 70
-- You can even set fields!
player. = PlayerStatus.;
print; -- "Attacking"
player:
print; -- 0
print; -- `false`
📚 API Guide
This crate uses a 3-step process:
- Decorate: Add attributes (
#[...]) to your types to tell the macros what to export. - Compile: Use the
compile!(...)macro to generate theimpl mlua::UserDatablock. - Load: Use the
load!(...)macro at runtime to register your types with aLuainstance. You can also manually load your types if our API doesn't allow you to do something.
Step 1: Decorate
| Macro | Target | Purpose |
|---|---|---|
#[enumeration] |
enum |
Exposes unit variants as static functions (e.g., MyEnum.VariantA()). |
#[structure] |
struct |
Exposes fields as readable/writable properties (e.g., my_struct.field). |
#[implementation] |
impl |
Exposes functions as methods (e.g., MyType.new(), my_inst:do_thing()). |
Step 2: Compile
The compile! macro generates the final impl mlua::UserData and impl mlua::FromLua for your type.
compile!;
Step 3: Load
The load! macro registers your compiled types as globals in Lua.
let lua = new;
// This is like running:
// _G.Player = (proxy for Player UserData)
// _G.PlayerStatus = (proxy for PlayerStatus UserData)
load!;
License
This crate is licensed under the MIT license.