Skip to main content

luaur_rt/
metamethod.rs

1//! The [`MetaMethod`] enum. Mirrors `mlua::MetaMethod` (Luau-relevant subset).
2//!
3//! A metamethod name can be supplied to `add_meta_method` / `add_meta_field`
4//! either as a `&str` (`"__add"`) or as a [`MetaMethod`] variant
5//! ([`MetaMethod::Add`]). Both implement [`Into<String>`] via the
6//! `From<MetaMethod> for String` impl below, so the userdata registrars accept
7//! either spelling, exactly like mlua.
8
9use std::fmt;
10
11/// Kinds of metamethods that can be overridden on userdata.
12///
13/// Mirrors `mlua::MetaMethod`. The variant set is the Luau-relevant subset
14/// (bitwise operators specific to Lua 5.3/5.4 are omitted; Luau does not use
15/// them as metamethods).
16#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
17#[non_exhaustive]
18pub enum MetaMethod {
19    /// The `+` operator (`__add`).
20    Add,
21    /// The `-` operator (`__sub`).
22    Sub,
23    /// The `*` operator (`__mul`).
24    Mul,
25    /// The `/` operator (`__div`).
26    Div,
27    /// The `%` operator (`__mod`).
28    Mod,
29    /// The `^` operator (`__pow`).
30    Pow,
31    /// The unary minus operator (`__unm`).
32    Unm,
33    /// The floor-division `//` operator (`__idiv`).
34    IDiv,
35    /// The string concatenation operator `..` (`__concat`).
36    Concat,
37    /// The length operator `#` (`__len`).
38    Len,
39    /// The `==` operator (`__eq`).
40    Eq,
41    /// The `<` operator (`__lt`).
42    Lt,
43    /// The `<=` operator (`__le`).
44    Le,
45    /// Index access `obj[key]` (`__index`).
46    Index,
47    /// Index write access `obj[key] = value` (`__newindex`).
48    NewIndex,
49    /// The call operator `obj(...)` (`__call`).
50    Call,
51    /// The `__tostring` metamethod.
52    ToString,
53    /// The `__iter` metamethod (Luau).
54    Iter,
55    /// The `__type`/`__name` metafield.
56    Type,
57}
58
59impl MetaMethod {
60    /// The Lua metamethod name (e.g. `"__add"`). Mirrors `mlua::MetaMethod::name`.
61    pub const fn name(self) -> &'static str {
62        match self {
63            MetaMethod::Add => "__add",
64            MetaMethod::Sub => "__sub",
65            MetaMethod::Mul => "__mul",
66            MetaMethod::Div => "__div",
67            MetaMethod::Mod => "__mod",
68            MetaMethod::Pow => "__pow",
69            MetaMethod::Unm => "__unm",
70            MetaMethod::IDiv => "__idiv",
71            MetaMethod::Concat => "__concat",
72            MetaMethod::Len => "__len",
73            MetaMethod::Eq => "__eq",
74            MetaMethod::Lt => "__lt",
75            MetaMethod::Le => "__le",
76            MetaMethod::Index => "__index",
77            MetaMethod::NewIndex => "__newindex",
78            MetaMethod::Call => "__call",
79            MetaMethod::ToString => "__tostring",
80            MetaMethod::Iter => "__iter",
81            MetaMethod::Type => "__type",
82        }
83    }
84}
85
86impl fmt::Display for MetaMethod {
87    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
88        f.write_str(self.name())
89    }
90}
91
92impl From<MetaMethod> for String {
93    fn from(mm: MetaMethod) -> String {
94        mm.name().to_string()
95    }
96}
97
98impl PartialEq<MetaMethod> for &str {
99    fn eq(&self, other: &MetaMethod) -> bool {
100        *self == other.name()
101    }
102}
103
104impl PartialEq<MetaMethod> for String {
105    fn eq(&self, other: &MetaMethod) -> bool {
106        self == other.name()
107    }
108}