mirror of
https://github.com/lune-org/lune.git
synced 2025-04-04 10:30:54 +01:00
Fix every single clippy lint in lune-roblox crate (im tired, boss)
This commit is contained in:
parent
313dbcf65f
commit
7f7cfb54e0
35 changed files with 264 additions and 127 deletions
|
@ -4,6 +4,15 @@ use rbx_dom_weak::types::{Variant as DomValue, VariantType as DomType};
|
|||
|
||||
use super::extension::DomValueExt;
|
||||
|
||||
/**
|
||||
Checks if the given name is a valid attribute name.
|
||||
|
||||
# Errors
|
||||
|
||||
- If the name starts with the prefix "RBX".
|
||||
- If the name contains any characters other than alphanumeric characters and underscore.
|
||||
- If the name is longer than 100 characters.
|
||||
*/
|
||||
pub fn ensure_valid_attribute_name(name: impl AsRef<str>) -> LuaResult<()> {
|
||||
let name = name.as_ref();
|
||||
if name.to_ascii_uppercase().starts_with("RBX") {
|
||||
|
@ -23,6 +32,13 @@ pub fn ensure_valid_attribute_name(name: impl AsRef<str>) -> LuaResult<()> {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Checks if the given value is a valid attribute value.
|
||||
|
||||
# Errors
|
||||
|
||||
- If the value is not a valid attribute type.
|
||||
*/
|
||||
pub fn ensure_valid_attribute_value(value: &DomValue) -> LuaResult<()> {
|
||||
let is_valid = matches!(
|
||||
value.ty(),
|
||||
|
|
|
@ -65,8 +65,10 @@ impl<'lua> DomValueToLua<'lua> for LuaValue<'lua> {
|
|||
|
||||
// NOTE: Some values are either optional or default and we should handle
|
||||
// that properly here since the userdata conversion above will always fail
|
||||
DomValue::OptionalCFrame(None) => Ok(LuaValue::Nil),
|
||||
DomValue::PhysicalProperties(dom::PhysicalProperties::Default) => Ok(LuaValue::Nil),
|
||||
DomValue::OptionalCFrame(None)
|
||||
| DomValue::PhysicalProperties(dom::PhysicalProperties::Default) => {
|
||||
Ok(LuaValue::Nil)
|
||||
}
|
||||
|
||||
_ => Err(e),
|
||||
},
|
||||
|
|
|
@ -6,6 +6,7 @@ pub(crate) trait DomValueExt {
|
|||
|
||||
impl DomValueExt for DomType {
|
||||
fn variant_name(&self) -> Option<&'static str> {
|
||||
#[allow(clippy::enum_glob_use)]
|
||||
use DomType::*;
|
||||
Some(match self {
|
||||
Attributes => "Attributes",
|
||||
|
|
|
@ -54,8 +54,7 @@ impl LuaExportsTable<'_> for Axes {
|
|||
check(&e);
|
||||
} else {
|
||||
return Err(LuaError::RuntimeError(format!(
|
||||
"Expected argument #{} to be an EnumItem, got userdata",
|
||||
index
|
||||
"Expected argument #{index} to be an EnumItem, got userdata",
|
||||
)));
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -13,7 +13,7 @@ use super::{super::*, Color3};
|
|||
/**
|
||||
An implementation of the [BrickColor](https://create.roblox.com/docs/reference/engine/datatypes/BrickColor) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the BrickColor class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `BrickColor` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct BrickColor {
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::items_after_statements)]
|
||||
|
||||
use core::fmt;
|
||||
use std::ops;
|
||||
|
||||
|
@ -16,7 +18,7 @@ use super::{super::*, Vector3};
|
|||
Roblox datatype, backed by [`glam::Mat4`].
|
||||
|
||||
This implements all documented properties, methods &
|
||||
constructors of the CFrame class as of March 2023.
|
||||
constructors of the `CFrame` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct CFrame(pub Mat4);
|
||||
|
@ -44,6 +46,7 @@ impl CFrame {
|
|||
impl LuaExportsTable<'_> for CFrame {
|
||||
const EXPORT_NAME: &'static str = "CFrame";
|
||||
|
||||
#[allow(clippy::too_many_lines)]
|
||||
fn create_exports_table(lua: &Lua) -> LuaResult<LuaTable> {
|
||||
let cframe_angles = |_, (rx, ry, rz): (f32, f32, f32)| {
|
||||
Ok(CFrame(Mat4::from_euler(EulerRot::XYZ, rx, ry, rz)))
|
||||
|
@ -70,8 +73,7 @@ impl LuaExportsTable<'_> for CFrame {
|
|||
Ok(CFrame(Mat4::from_cols(
|
||||
rx.0.extend(0.0),
|
||||
ry.0.extend(0.0),
|
||||
rz.map(|r| r.0)
|
||||
.unwrap_or_else(|| rx.0.cross(ry.0).normalize())
|
||||
rz.map_or_else(|| rx.0.cross(ry.0).normalize(), |r| r.0)
|
||||
.extend(0.0),
|
||||
pos.0.extend(1.0),
|
||||
)))
|
||||
|
@ -197,6 +199,7 @@ impl LuaUserData for CFrame {
|
|||
});
|
||||
}
|
||||
|
||||
#[allow(clippy::too_many_lines)]
|
||||
fn add_methods<'lua, M: LuaUserDataMethods<'lua, Self>>(methods: &mut M) {
|
||||
// Methods
|
||||
methods.add_method("Inverse", |_, this, ()| Ok(this.inverse()));
|
||||
|
@ -228,34 +231,49 @@ impl LuaUserData for CFrame {
|
|||
methods.add_method(
|
||||
"ToWorldSpace",
|
||||
|_, this, rhs: Variadic<LuaUserDataRef<CFrame>>| {
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|cf| *this * *cf)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|cf| *this * *cf)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
methods.add_method(
|
||||
"ToObjectSpace",
|
||||
|_, this, rhs: Variadic<LuaUserDataRef<CFrame>>| {
|
||||
let inverse = this.inverse();
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|cf| inverse * *cf)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|cf| inverse * *cf)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
methods.add_method(
|
||||
"PointToWorldSpace",
|
||||
|_, this, rhs: Variadic<LuaUserDataRef<Vector3>>| {
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|v3| *this * *v3)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|v3| *this * *v3)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
methods.add_method(
|
||||
"PointToObjectSpace",
|
||||
|_, this, rhs: Variadic<LuaUserDataRef<Vector3>>| {
|
||||
let inverse = this.inverse();
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|v3| inverse * *v3)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|v3| inverse * *v3)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
methods.add_method(
|
||||
"VectorToWorldSpace",
|
||||
|_, this, rhs: Variadic<LuaUserDataRef<Vector3>>| {
|
||||
let result = *this - Vector3(this.position());
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|v3| result * *v3)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|v3| result * *v3)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
methods.add_method(
|
||||
|
@ -263,8 +281,10 @@ impl LuaUserData for CFrame {
|
|||
|_, this, rhs: Variadic<LuaUserDataRef<Vector3>>| {
|
||||
let inverse = this.inverse();
|
||||
let result = inverse - Vector3(inverse.position());
|
||||
|
||||
Ok(Variadic::from_iter(rhs.into_iter().map(|v3| result * *v3)))
|
||||
Ok(rhs
|
||||
.into_iter()
|
||||
.map(|v3| result * *v3)
|
||||
.collect::<Variadic<_>>())
|
||||
},
|
||||
);
|
||||
#[rustfmt::skip]
|
||||
|
@ -447,7 +467,7 @@ mod cframe_test {
|
|||
Vec3::new(1.0, 2.0, 3.0).extend(1.0),
|
||||
));
|
||||
|
||||
assert_eq!(CFrame::from(dom_cframe), cframe)
|
||||
assert_eq!(CFrame::from(dom_cframe), cframe);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
@ -468,6 +488,6 @@ mod cframe_test {
|
|||
),
|
||||
);
|
||||
|
||||
assert_eq!(DomCFrame::from(cframe), dom_cframe)
|
||||
assert_eq!(DomCFrame::from(cframe), dom_cframe);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -89,8 +89,7 @@ impl LuaExportsTable<'_> for Color3 {
|
|||
b: (b as f32) / 255f32,
|
||||
}),
|
||||
_ => Err(LuaError::RuntimeError(format!(
|
||||
"Hex color string '{}' contains invalid character",
|
||||
trimmed
|
||||
"Hex color string '{trimmed}' contains invalid character",
|
||||
))),
|
||||
}
|
||||
};
|
||||
|
@ -155,6 +154,7 @@ impl LuaUserData for Color3 {
|
|||
let max = r.max(g).max(b);
|
||||
let diff = max - min;
|
||||
|
||||
#[allow(clippy::float_cmp)]
|
||||
let hue = (match max {
|
||||
max if max == min => 0.0,
|
||||
max if max == r => (g - b) / diff + (if g < b { 6.0 } else { 0.0 }),
|
||||
|
|
|
@ -14,7 +14,7 @@ use super::{super::*, Color3, ColorSequenceKeypoint};
|
|||
/**
|
||||
An implementation of the [ColorSequence](https://create.roblox.com/docs/reference/engine/datatypes/ColorSequence) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the ColorSequence class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `ColorSequence` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
pub struct ColorSequence {
|
||||
|
@ -89,9 +89,9 @@ impl fmt::Display for ColorSequence {
|
|||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
for (index, keypoint) in self.keypoints.iter().enumerate() {
|
||||
if index < self.keypoints.len() - 1 {
|
||||
write!(f, "{}, ", keypoint)?;
|
||||
write!(f, "{keypoint}, ")?;
|
||||
} else {
|
||||
write!(f, "{}", keypoint)?;
|
||||
write!(f, "{keypoint}")?;
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
|
@ -104,7 +104,7 @@ impl From<DomColorSequence> for ColorSequence {
|
|||
keypoints: v
|
||||
.keypoints
|
||||
.iter()
|
||||
.cloned()
|
||||
.copied()
|
||||
.map(ColorSequenceKeypoint::from)
|
||||
.collect(),
|
||||
}
|
||||
|
@ -117,7 +117,7 @@ impl From<ColorSequence> for DomColorSequence {
|
|||
keypoints: v
|
||||
.keypoints
|
||||
.iter()
|
||||
.cloned()
|
||||
.copied()
|
||||
.map(DomColorSequenceKeypoint::from)
|
||||
.collect(),
|
||||
}
|
||||
|
|
|
@ -12,7 +12,7 @@ use super::{super::*, Color3};
|
|||
/**
|
||||
An implementation of the [ColorSequenceKeypoint](https://create.roblox.com/docs/reference/engine/datatypes/ColorSequenceKeypoint) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the ColorSequenceKeypoint class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `ColorSequenceKeypoint` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct ColorSequenceKeypoint {
|
||||
|
|
|
@ -8,7 +8,7 @@ use super::{super::*, Enum};
|
|||
/**
|
||||
An implementation of the [EnumItem](https://create.roblox.com/docs/reference/engine/datatypes/EnumItem) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the EnumItem class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `EnumItem` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct EnumItem {
|
||||
|
|
|
@ -24,8 +24,7 @@ impl LuaUserData for Enums {
|
|||
|_, _, name: String| match Enum::from_name(&name) {
|
||||
Some(e) => Ok(e),
|
||||
None => Err(LuaError::RuntimeError(format!(
|
||||
"The enum '{}' does not exist",
|
||||
name
|
||||
"The enum '{name}' does not exist",
|
||||
))),
|
||||
},
|
||||
);
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::struct_excessive_bools)]
|
||||
|
||||
use core::fmt;
|
||||
|
||||
use mlua::prelude::*;
|
||||
|
@ -56,8 +58,7 @@ impl LuaExportsTable<'_> for Faces {
|
|||
check(&e);
|
||||
} else {
|
||||
return Err(LuaError::RuntimeError(format!(
|
||||
"Expected argument #{} to be an EnumItem, got userdata",
|
||||
index
|
||||
"Expected argument #{index} to be an EnumItem, got userdata",
|
||||
)));
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -64,7 +64,7 @@ impl LuaExportsTable<'_> for Font {
|
|||
let font_from_name =
|
||||
|_, (file, weight, style): (String, Option<FontWeight>, Option<FontStyle>)| {
|
||||
Ok(Font {
|
||||
family: format!("rbxasset://fonts/families/{}.json", file),
|
||||
family: format!("rbxasset://fonts/families/{file}.json"),
|
||||
weight: weight.unwrap_or_default(),
|
||||
style: style.unwrap_or_default(),
|
||||
cached_id: None,
|
||||
|
@ -74,7 +74,7 @@ impl LuaExportsTable<'_> for Font {
|
|||
let font_from_id =
|
||||
|_, (id, weight, style): (i32, Option<FontWeight>, Option<FontStyle>)| {
|
||||
Ok(Font {
|
||||
family: format!("rbxassetid://{}", id),
|
||||
family: format!("rbxassetid://{id}"),
|
||||
weight: weight.unwrap_or_default(),
|
||||
style: style.unwrap_or_default(),
|
||||
cached_id: None,
|
||||
|
@ -208,7 +208,7 @@ pub(crate) enum FontWeight {
|
|||
}
|
||||
|
||||
impl FontWeight {
|
||||
pub(crate) fn as_u16(&self) -> u16 {
|
||||
pub(crate) fn as_u16(self) -> u16 {
|
||||
match self {
|
||||
Self::Thin => 100,
|
||||
Self::ExtraLight => 200,
|
||||
|
@ -317,7 +317,7 @@ impl<'lua> IntoLua<'lua> for FontWeight {
|
|||
None => Err(LuaError::ToLuaConversionError {
|
||||
from: "FontWeight",
|
||||
to: "EnumItem",
|
||||
message: Some(format!("Found unknown Enum.FontWeight value '{}'", self)),
|
||||
message: Some(format!("Found unknown Enum.FontWeight value '{self}'")),
|
||||
}),
|
||||
}
|
||||
}
|
||||
|
@ -330,7 +330,7 @@ pub(crate) enum FontStyle {
|
|||
}
|
||||
|
||||
impl FontStyle {
|
||||
pub(crate) fn as_u8(&self) -> u8 {
|
||||
pub(crate) fn as_u8(self) -> u8 {
|
||||
match self {
|
||||
Self::Normal => 0,
|
||||
Self::Italic => 1,
|
||||
|
@ -411,7 +411,7 @@ impl<'lua> IntoLua<'lua> for FontStyle {
|
|||
None => Err(LuaError::ToLuaConversionError {
|
||||
from: "FontStyle",
|
||||
to: "EnumItem",
|
||||
message: Some(format!("Found unknown Enum.FontStyle value '{}'", self)),
|
||||
message: Some(format!("Found unknown Enum.FontStyle value '{self}'")),
|
||||
}),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,7 +12,7 @@ use super::super::*;
|
|||
/**
|
||||
An implementation of the [NumberRange](https://create.roblox.com/docs/reference/engine/datatypes/NumberRange) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the NumberRange class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `NumberRange` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct NumberRange {
|
||||
|
|
|
@ -14,7 +14,7 @@ use super::{super::*, NumberSequenceKeypoint};
|
|||
/**
|
||||
An implementation of the [NumberSequence](https://create.roblox.com/docs/reference/engine/datatypes/NumberSequence) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the NumberSequence class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `NumberSequence` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
pub struct NumberSequence {
|
||||
|
@ -93,9 +93,9 @@ impl fmt::Display for NumberSequence {
|
|||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
for (index, keypoint) in self.keypoints.iter().enumerate() {
|
||||
if index < self.keypoints.len() - 1 {
|
||||
write!(f, "{}, ", keypoint)?;
|
||||
write!(f, "{keypoint}, ")?;
|
||||
} else {
|
||||
write!(f, "{}", keypoint)?;
|
||||
write!(f, "{keypoint}")?;
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
|
@ -108,7 +108,7 @@ impl From<DomNumberSequence> for NumberSequence {
|
|||
keypoints: v
|
||||
.keypoints
|
||||
.iter()
|
||||
.cloned()
|
||||
.copied()
|
||||
.map(NumberSequenceKeypoint::from)
|
||||
.collect(),
|
||||
}
|
||||
|
@ -121,7 +121,7 @@ impl From<NumberSequence> for DomNumberSequence {
|
|||
keypoints: v
|
||||
.keypoints
|
||||
.iter()
|
||||
.cloned()
|
||||
.copied()
|
||||
.map(DomNumberSequenceKeypoint::from)
|
||||
.collect(),
|
||||
}
|
||||
|
|
|
@ -12,7 +12,7 @@ use super::super::*;
|
|||
/**
|
||||
An implementation of the [NumberSequenceKeypoint](https://create.roblox.com/docs/reference/engine/datatypes/NumberSequenceKeypoint) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the NumberSequenceKeypoint class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `NumberSequenceKeypoint` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct NumberSequenceKeypoint {
|
||||
|
|
|
@ -12,7 +12,7 @@ use super::{super::*, EnumItem};
|
|||
/**
|
||||
An implementation of the [PhysicalProperties](https://create.roblox.com/docs/reference/engine/datatypes/PhysicalProperties) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the PhysicalProperties class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `PhysicalProperties` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct PhysicalProperties {
|
||||
|
|
|
@ -13,7 +13,7 @@ use super::super::*;
|
|||
/**
|
||||
An implementation of the [UDim](https://create.roblox.com/docs/reference/engine/datatypes/UDim) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the UDim class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `UDim` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct UDim {
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::items_after_statements)]
|
||||
|
||||
use core::fmt;
|
||||
use std::ops;
|
||||
|
||||
|
@ -14,7 +16,7 @@ use super::{super::*, UDim};
|
|||
/**
|
||||
An implementation of the [UDim2](https://create.roblox.com/docs/reference/engine/datatypes/UDim2) Roblox datatype.
|
||||
|
||||
This implements all documented properties, methods & constructors of the UDim2 class as of March 2023.
|
||||
This implements all documented properties, methods & constructors of the `UDim2` class as of March 2023.
|
||||
*/
|
||||
#[derive(Debug, Clone, Copy, PartialEq)]
|
||||
pub struct UDim2 {
|
||||
|
|
|
@ -36,8 +36,7 @@ impl LuaExportsTable<'_> for Vector3 {
|
|||
"Z" => Vector3(Vec3::Z),
|
||||
name => {
|
||||
return Err(LuaError::RuntimeError(format!(
|
||||
"Axis '{}' is not known",
|
||||
name
|
||||
"Axis '{name}' is not known",
|
||||
)))
|
||||
}
|
||||
})
|
||||
|
@ -60,8 +59,7 @@ impl LuaExportsTable<'_> for Vector3 {
|
|||
"Back" => Vector3(Vec3::Z),
|
||||
name => {
|
||||
return Err(LuaError::RuntimeError(format!(
|
||||
"NormalId '{}' is not known",
|
||||
name
|
||||
"NormalId '{name}' is not known",
|
||||
)))
|
||||
}
|
||||
})
|
||||
|
|
|
@ -58,6 +58,7 @@ impl DocumentKind {
|
|||
|
||||
Returns `None` if the given dom is empty and as such can not have its kind inferred.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn from_weak_dom(dom: &WeakDom) -> Option<Self> {
|
||||
let mut has_top_level_child = false;
|
||||
let mut has_top_level_service = false;
|
||||
|
|
|
@ -78,6 +78,7 @@ impl Document {
|
|||
| Model | Binary | `rbxm` |
|
||||
| Model | Xml | `rbxmx` |
|
||||
*/
|
||||
#[must_use]
|
||||
#[rustfmt::skip]
|
||||
pub fn canonical_extension(kind: DocumentKind, format: DocumentFormat) -> &'static str {
|
||||
match (kind, format) {
|
||||
|
@ -113,6 +114,10 @@ impl Document {
|
|||
Note that detection of model vs place file is heavily dependent on the structure
|
||||
of the file, and a model file with services in it will detect as a place file, so
|
||||
if possible using [`Document::from_bytes`] with an explicit kind should be preferred.
|
||||
|
||||
# Errors
|
||||
|
||||
Errors if the given bytes are not a valid roblox file.
|
||||
*/
|
||||
pub fn from_bytes_auto(bytes: impl AsRef<[u8]>) -> DocumentResult<Self> {
|
||||
let (format, dom) = Self::from_bytes_inner(bytes)?;
|
||||
|
@ -125,6 +130,10 @@ impl Document {
|
|||
|
||||
This will automatically handle and detect if the document
|
||||
should be decoded using a roblox binary or roblox xml format.
|
||||
|
||||
# Errors
|
||||
|
||||
Errors if the given bytes are not a valid roblox file or not of the given kind.
|
||||
*/
|
||||
pub fn from_bytes(bytes: impl AsRef<[u8]>, kind: DocumentKind) -> DocumentResult<Self> {
|
||||
let (format, dom) = Self::from_bytes_inner(bytes)?;
|
||||
|
@ -138,6 +147,10 @@ impl Document {
|
|||
This will use the same format that the document was created
|
||||
with, meaning if the document is a binary document the output
|
||||
will be binary, and vice versa for xml and other future formats.
|
||||
|
||||
# Errors
|
||||
|
||||
Errors if the document can not be encoded.
|
||||
*/
|
||||
pub fn to_bytes(&self) -> DocumentResult<Vec<u8>> {
|
||||
self.to_bytes_with_format(self.format)
|
||||
|
@ -146,6 +159,10 @@ impl Document {
|
|||
/**
|
||||
Encodes the document as a vector of bytes, to
|
||||
be written to a file or sent over the network.
|
||||
|
||||
# Errors
|
||||
|
||||
Errors if the document can not be encoded.
|
||||
*/
|
||||
pub fn to_bytes_with_format(&self, format: DocumentFormat) -> DocumentResult<Vec<u8>> {
|
||||
let mut bytes = Vec::new();
|
||||
|
@ -172,6 +189,7 @@ impl Document {
|
|||
/**
|
||||
Gets the kind this document was created with.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn kind(&self) -> DocumentKind {
|
||||
self.kind
|
||||
}
|
||||
|
@ -179,6 +197,7 @@ impl Document {
|
|||
/**
|
||||
Gets the format this document was created with.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn format(&self) -> DocumentFormat {
|
||||
self.format
|
||||
}
|
||||
|
@ -186,14 +205,17 @@ impl Document {
|
|||
/**
|
||||
Gets the file extension for this document.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn extension(&self) -> &'static str {
|
||||
Self::canonical_extension(self.kind, self.format)
|
||||
}
|
||||
|
||||
/**
|
||||
Creates a DataModel instance out of this place document.
|
||||
Creates a `DataModel` instance out of this place document.
|
||||
|
||||
Will error if the document is not a place.
|
||||
# Errors
|
||||
|
||||
Errors if the document is not a place.
|
||||
*/
|
||||
pub fn into_data_model_instance(mut self) -> DocumentResult<Instance> {
|
||||
if self.kind != DocumentKind::Place {
|
||||
|
@ -219,7 +241,9 @@ impl Document {
|
|||
/**
|
||||
Creates an array of instances out of this model document.
|
||||
|
||||
Will error if the document is not a model.
|
||||
# Errors
|
||||
|
||||
Errors if the document is not a model.
|
||||
*/
|
||||
pub fn into_instance_array(mut self) -> DocumentResult<Vec<Instance>> {
|
||||
if self.kind != DocumentKind::Model {
|
||||
|
@ -237,9 +261,11 @@ impl Document {
|
|||
}
|
||||
|
||||
/**
|
||||
Creates a place document out of a DataModel instance.
|
||||
Creates a place document out of a `DataModel` instance.
|
||||
|
||||
Will error if the instance is not a DataModel.
|
||||
# Errors
|
||||
|
||||
Errors if the instance is not a `DataModel`.
|
||||
*/
|
||||
pub fn from_data_model_instance(i: Instance) -> DocumentResult<Self> {
|
||||
if i.get_class_name() != data_model::CLASS_NAME {
|
||||
|
@ -266,7 +292,9 @@ impl Document {
|
|||
/**
|
||||
Creates a model document out of an array of instances.
|
||||
|
||||
Will error if any of the instances is a DataModel.
|
||||
# Errors
|
||||
|
||||
Errors if any of the instances is a `DataModel`.
|
||||
*/
|
||||
pub fn from_instance_array(v: Vec<Instance>) -> DocumentResult<Self> {
|
||||
for i in &v {
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::items_after_statements)]
|
||||
|
||||
use mlua::prelude::*;
|
||||
|
||||
use rbx_dom_weak::{
|
||||
|
@ -17,6 +19,7 @@ use crate::{
|
|||
|
||||
use super::{data_model, registry::InstanceRegistry, Instance};
|
||||
|
||||
#[allow(clippy::too_many_lines)]
|
||||
pub fn add_methods<'lua, M: LuaUserDataMethods<'lua, Instance>>(m: &mut M) {
|
||||
m.add_meta_method(LuaMetaMethod::ToString, |lua, this, ()| {
|
||||
ensure_not_destroyed(this)?;
|
||||
|
@ -142,7 +145,7 @@ pub fn add_methods<'lua, M: LuaUserDataMethods<'lua, Instance>>(m: &mut M) {
|
|||
ensure_not_destroyed(this)?;
|
||||
let attributes = this.get_attributes();
|
||||
let tab = lua.create_table_with_capacity(0, attributes.len())?;
|
||||
for (key, value) in attributes.into_iter() {
|
||||
for (key, value) in attributes {
|
||||
tab.set(key, LuaValue::dom_value_to_lua(lua, &value)?)?;
|
||||
}
|
||||
Ok(tab)
|
||||
|
@ -227,8 +230,7 @@ fn instance_property_get<'lua>(
|
|||
if let DomValue::Enum(enum_value) = prop {
|
||||
let enum_name = info.enum_name.ok_or_else(|| {
|
||||
LuaError::RuntimeError(format!(
|
||||
"Failed to get property '{}' - encountered unknown enum",
|
||||
prop_name
|
||||
"Failed to get property '{prop_name}' - encountered unknown enum",
|
||||
))
|
||||
})?;
|
||||
EnumItem::from_enum_name_and_value(&enum_name, enum_value.to_u32())
|
||||
|
@ -246,8 +248,7 @@ fn instance_property_get<'lua>(
|
|||
EnumItem::from_enum_name_and_value(&enum_name, enum_value)
|
||||
.ok_or_else(|| {
|
||||
LuaError::RuntimeError(format!(
|
||||
"Failed to get property '{}' - Enum.{} does not contain numeric value {}",
|
||||
prop_name, enum_name, enum_value
|
||||
"Failed to get property '{prop_name}' - Enum.{enum_name} does not contain numeric value {enum_value}",
|
||||
))
|
||||
})?
|
||||
.into_lua(lua)
|
||||
|
@ -258,14 +259,12 @@ fn instance_property_get<'lua>(
|
|||
Ok(LuaValue::Nil)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"Failed to get property '{}' - missing default value",
|
||||
prop_name
|
||||
"Failed to get property '{prop_name}' - missing default value",
|
||||
)))
|
||||
}
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"Failed to get property '{}' - malformed property info",
|
||||
prop_name
|
||||
"Failed to get property '{prop_name}' - malformed property info",
|
||||
)))
|
||||
}
|
||||
} else if let Some(inst) = this.find_child(|inst| inst.name == prop_name) {
|
||||
|
@ -276,8 +275,7 @@ fn instance_property_get<'lua>(
|
|||
Ok(LuaValue::Function(method))
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
prop_name, this
|
||||
"{prop_name} is not a valid member of {this}",
|
||||
)))
|
||||
}
|
||||
}
|
||||
|
@ -347,16 +345,14 @@ fn instance_property_set<'lua>(
|
|||
}
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"Failed to set property '{}' - malformed property info",
|
||||
prop_name
|
||||
"Failed to set property '{prop_name}' - malformed property info",
|
||||
)))
|
||||
}
|
||||
} else if let Some(setter) = InstanceRegistry::find_property_setter(lua, this, &prop_name) {
|
||||
setter.call((this.clone(), prop_value))
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
prop_name, this
|
||||
"{prop_name} is not a valid member of {this}",
|
||||
)))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,7 +33,7 @@ fn data_model_get_workspace(_: &Lua, this: &Instance) -> LuaResult<Instance> {
|
|||
}
|
||||
|
||||
/**
|
||||
Gets or creates a service for this DataModel.
|
||||
Gets or creates a service for this `DataModel`.
|
||||
|
||||
### See Also
|
||||
* [`GetService`](https://create.roblox.com/docs/reference/engine/classes/ServiceProvider#GetService)
|
||||
|
@ -42,8 +42,7 @@ fn data_model_get_workspace(_: &Lua, this: &Instance) -> LuaResult<Instance> {
|
|||
fn data_model_get_service(_: &Lua, this: &Instance, service_name: String) -> LuaResult<Instance> {
|
||||
if matches!(class_is_a_service(&service_name), None | Some(false)) {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"'{}' is not a valid service name",
|
||||
service_name
|
||||
"'{service_name}' is not a valid service name",
|
||||
)))
|
||||
} else if let Some(service) = this.find_child(|child| child.class == service_name) {
|
||||
Ok(service)
|
||||
|
@ -55,7 +54,7 @@ fn data_model_get_service(_: &Lua, this: &Instance, service_name: String) -> Lua
|
|||
}
|
||||
|
||||
/**
|
||||
Gets a service for this DataModel, if it exists.
|
||||
Gets a service for this `DataModel`, if it exists.
|
||||
|
||||
### See Also
|
||||
* [`FindService`](https://create.roblox.com/docs/reference/engine/classes/ServiceProvider#FindService)
|
||||
|
@ -68,8 +67,7 @@ fn data_model_find_service(
|
|||
) -> LuaResult<Option<Instance>> {
|
||||
if matches!(class_is_a_service(&service_name), None | Some(false)) {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"'{}' is not a valid service name",
|
||||
service_name
|
||||
"'{service_name}' is not a valid service name",
|
||||
)))
|
||||
} else if let Some(service) = this.find_child(|child| child.class == service_name) {
|
||||
Ok(Some(service))
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::missing_panics_doc)]
|
||||
|
||||
use std::{
|
||||
collections::{BTreeMap, VecDeque},
|
||||
fmt,
|
||||
|
@ -55,9 +57,10 @@ impl Instance {
|
|||
.get_by_ref(dom_ref)
|
||||
.expect("Failed to find instance in document");
|
||||
|
||||
if instance.referent() == dom.root_ref() {
|
||||
panic!("Instances can not be created from dom roots")
|
||||
}
|
||||
assert!(
|
||||
!(instance.referent() == dom.root_ref()),
|
||||
"Instances can not be created from dom roots"
|
||||
);
|
||||
|
||||
Self {
|
||||
dom_ref,
|
||||
|
@ -77,9 +80,10 @@ impl Instance {
|
|||
let dom = INTERNAL_DOM.lock().expect("Failed to lock document");
|
||||
|
||||
if let Some(instance) = dom.get_by_ref(dom_ref) {
|
||||
if instance.referent() == dom.root_ref() {
|
||||
panic!("Instances can not be created from dom roots")
|
||||
}
|
||||
assert!(
|
||||
!(instance.referent() == dom.root_ref()),
|
||||
"Instances can not be created from dom roots"
|
||||
);
|
||||
|
||||
Some(Self {
|
||||
dom_ref,
|
||||
|
@ -155,7 +159,7 @@ impl Instance {
|
|||
|
||||
let cloned = dom.clone_multiple_into_external(referents, external_dom);
|
||||
|
||||
for referent in cloned.iter() {
|
||||
for referent in &cloned {
|
||||
external_dom.transfer_within(*referent, external_dom.root_ref());
|
||||
}
|
||||
|
||||
|
@ -172,7 +176,8 @@ impl Instance {
|
|||
* [`Clone`](https://create.roblox.com/docs/reference/engine/classes/Instance#Clone)
|
||||
on the Roblox Developer Hub
|
||||
*/
|
||||
pub fn clone_instance(&self) -> Instance {
|
||||
#[must_use]
|
||||
pub fn clone_instance(&self) -> Self {
|
||||
let mut dom = INTERNAL_DOM.lock().expect("Failed to lock document");
|
||||
let new_ref = dom.clone_within(self.dom_ref);
|
||||
drop(dom); // Self::new needs mutex handle, drop it first
|
||||
|
@ -255,6 +260,7 @@ impl Instance {
|
|||
* [`ClassName`](https://create.roblox.com/docs/reference/engine/classes/Instance#ClassName)
|
||||
on the Roblox Developer Hub
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_class_name(&self) -> &str {
|
||||
self.class_name.as_str()
|
||||
}
|
||||
|
@ -287,7 +293,7 @@ impl Instance {
|
|||
|
||||
dom.get_by_ref_mut(self.dom_ref)
|
||||
.expect("Failed to find instance in document")
|
||||
.name = name.into()
|
||||
.name = name.into();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -327,9 +333,7 @@ impl Instance {
|
|||
pub fn set_parent(&self, parent: Option<Instance>) {
|
||||
let mut dom = INTERNAL_DOM.lock().expect("Failed to lock document");
|
||||
|
||||
let parent_ref = parent
|
||||
.map(|parent| parent.dom_ref)
|
||||
.unwrap_or_else(|| dom.root_ref());
|
||||
let parent_ref = parent.map_or_else(|| dom.root_ref(), |parent| parent.dom_ref);
|
||||
|
||||
dom.transfer_within(self.dom_ref, parent_ref);
|
||||
}
|
||||
|
@ -664,9 +668,8 @@ impl Instance {
|
|||
if predicate(ancestor) {
|
||||
drop(dom); // Self::new needs mutex handle, drop it first
|
||||
return Some(Self::new(ancestor_ref));
|
||||
} else {
|
||||
ancestor_ref = ancestor.parent();
|
||||
}
|
||||
ancestor_ref = ancestor.parent();
|
||||
}
|
||||
|
||||
None
|
||||
|
@ -700,9 +703,8 @@ impl Instance {
|
|||
let queue_ref = queue_item.referent();
|
||||
drop(dom); // Self::new needs mutex handle, drop it first
|
||||
return Some(Self::new(queue_ref));
|
||||
} else {
|
||||
queue.extend(queue_item.children())
|
||||
}
|
||||
queue.extend(queue_item.children());
|
||||
}
|
||||
|
||||
None
|
||||
|
@ -718,8 +720,7 @@ impl LuaExportsTable<'_> for Instance {
|
|||
Instance::new_orphaned(class_name).into_lua(lua)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"Failed to create Instance - '{}' is not a valid class name",
|
||||
class_name
|
||||
"Failed to create Instance - '{class_name}' is not a valid class name",
|
||||
)))
|
||||
}
|
||||
};
|
||||
|
@ -757,7 +758,7 @@ impl LuaUserData for Instance {
|
|||
|
||||
impl Hash for Instance {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
self.dom_ref.hash(state)
|
||||
self.dom_ref.hash(state);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -51,6 +51,13 @@ impl InstanceRegistry {
|
|||
.expect("Missing InstanceRegistry in app data")
|
||||
}
|
||||
|
||||
/**
|
||||
Inserts a method into the instance registry.
|
||||
|
||||
# Errors
|
||||
|
||||
- If the method already exists in the registry.
|
||||
*/
|
||||
pub fn insert_method<'lua>(
|
||||
lua: &'lua Lua,
|
||||
class_name: &str,
|
||||
|
@ -80,6 +87,13 @@ impl InstanceRegistry {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/**
|
||||
Inserts a property getter into the instance registry.
|
||||
|
||||
# Errors
|
||||
|
||||
- If the property already exists in the registry.
|
||||
*/
|
||||
pub fn insert_property_getter<'lua>(
|
||||
lua: &'lua Lua,
|
||||
class_name: &str,
|
||||
|
@ -109,6 +123,13 @@ impl InstanceRegistry {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/**
|
||||
Inserts a property setter into the instance registry.
|
||||
|
||||
# Errors
|
||||
|
||||
- If the property already exists in the registry.
|
||||
*/
|
||||
pub fn insert_property_setter<'lua>(
|
||||
lua: &'lua Lua,
|
||||
class_name: &str,
|
||||
|
@ -138,6 +159,12 @@ impl InstanceRegistry {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/**
|
||||
Finds a method in the instance registry.
|
||||
|
||||
Returns `None` if the method is not found.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn find_method<'lua>(
|
||||
lua: &'lua Lua,
|
||||
instance: &Instance,
|
||||
|
@ -159,6 +186,12 @@ impl InstanceRegistry {
|
|||
})
|
||||
}
|
||||
|
||||
/**
|
||||
Finds a property getter in the instance registry.
|
||||
|
||||
Returns `None` if the property getter is not found.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn find_property_getter<'lua>(
|
||||
lua: &'lua Lua,
|
||||
instance: &Instance,
|
||||
|
@ -180,6 +213,12 @@ impl InstanceRegistry {
|
|||
})
|
||||
}
|
||||
|
||||
/**
|
||||
Finds a property setter in the instance registry.
|
||||
|
||||
Returns `None` if the property setter is not found.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn find_property_setter<'lua>(
|
||||
lua: &'lua Lua,
|
||||
instance: &Instance,
|
||||
|
@ -202,6 +241,16 @@ impl InstanceRegistry {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Gets the class name chain for a given class name.
|
||||
|
||||
The chain starts with the given class name and ends with the root class.
|
||||
|
||||
# Panics
|
||||
|
||||
Panics if the class name is not valid.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn class_name_chain(class_name: &str) -> Vec<&str> {
|
||||
let db = rbx_reflection_database::get();
|
||||
|
||||
|
|
|
@ -23,7 +23,7 @@ pub fn add_methods<'lua, M: LuaUserDataMethods<'lua, Instance>>(methods: &mut M)
|
|||
CLASS_NAME,
|
||||
"SetMaterialColor",
|
||||
terrain_set_material_color,
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
fn get_or_create_material_colors(instance: &Instance) -> MaterialColors {
|
||||
|
|
|
@ -28,6 +28,7 @@ impl DatabaseClass {
|
|||
/**
|
||||
Get the name of this class.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_name(&self) -> String {
|
||||
self.0.name.to_string()
|
||||
}
|
||||
|
@ -37,6 +38,7 @@ impl DatabaseClass {
|
|||
|
||||
May be `None` if no parent class exists.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_superclass(&self) -> Option<String> {
|
||||
let sup = self.0.superclass.as_ref()?;
|
||||
Some(sup.to_string())
|
||||
|
@ -45,6 +47,7 @@ impl DatabaseClass {
|
|||
/**
|
||||
Get all known properties for this class.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_properties(&self) -> HashMap<String, DatabaseProperty> {
|
||||
self.0
|
||||
.properties
|
||||
|
@ -56,6 +59,7 @@ impl DatabaseClass {
|
|||
/**
|
||||
Get all default values for properties of this class.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_defaults(&self) -> HashMap<String, DomVariant> {
|
||||
self.0
|
||||
.default_properties
|
||||
|
@ -71,7 +75,12 @@ impl DatabaseClass {
|
|||
to players at runtime, and top-level class categories.
|
||||
*/
|
||||
pub fn get_tags_str(&self) -> Vec<&'static str> {
|
||||
self.0.tags.iter().map(class_tag_to_str).collect::<Vec<_>>()
|
||||
self.0
|
||||
.tags
|
||||
.iter()
|
||||
.copied()
|
||||
.map(class_tag_to_str)
|
||||
.collect::<Vec<_>>()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -135,14 +144,12 @@ fn make_enum_value(inner: DbClass, name: impl AsRef<str>, value: u32) -> LuaResu
|
|||
let name = name.as_ref();
|
||||
let enum_name = find_enum_name(inner, name).ok_or_else(|| {
|
||||
LuaError::RuntimeError(format!(
|
||||
"Failed to get default property '{}' - No enum descriptor was found",
|
||||
name
|
||||
"Failed to get default property '{name}' - No enum descriptor was found",
|
||||
))
|
||||
})?;
|
||||
EnumItem::from_enum_name_and_value(&enum_name, value).ok_or_else(|| {
|
||||
LuaError::RuntimeError(format!(
|
||||
"Failed to get default property '{}' - Enum.{} does not contain numeric value {}",
|
||||
name, enum_name, value
|
||||
"Failed to get default property '{name}' - Enum.{enum_name} does not contain numeric value {value}",
|
||||
))
|
||||
})
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@ impl DatabaseEnum {
|
|||
/**
|
||||
Get the name of this enum.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_name(&self) -> String {
|
||||
self.0.name.to_string()
|
||||
}
|
||||
|
@ -31,8 +32,9 @@ impl DatabaseEnum {
|
|||
Get all known members of this enum.
|
||||
|
||||
Note that this is a direct map of name -> enum values,
|
||||
and does not actually use the EnumItem datatype itself.
|
||||
and does not actually use the `EnumItem` datatype itself.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_items(&self) -> HashMap<String, u32> {
|
||||
self.0
|
||||
.items
|
||||
|
|
|
@ -30,6 +30,7 @@ impl Database {
|
|||
/**
|
||||
Creates a new database struct, referencing the bundled reflection database.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn new() -> Self {
|
||||
Self::default()
|
||||
}
|
||||
|
@ -40,6 +41,7 @@ impl Database {
|
|||
This will follow the format `x.y.z.w`, which most
|
||||
commonly looks something like `0.567.0.123456789`.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_version(&self) -> String {
|
||||
let [x, y, z, w] = self.0.version;
|
||||
format!("{x}.{y}.{z}.{w}")
|
||||
|
@ -48,15 +50,17 @@ impl Database {
|
|||
/**
|
||||
Retrieves a list of all currently known enum names.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_enum_names(&self) -> Vec<String> {
|
||||
self.0.enums.keys().map(|e| e.to_string()).collect()
|
||||
self.0.enums.keys().map(ToString::to_string).collect()
|
||||
}
|
||||
|
||||
/**
|
||||
Retrieves a list of all currently known class names.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_class_names(&self) -> Vec<String> {
|
||||
self.0.classes.keys().map(|e| e.to_string()).collect()
|
||||
self.0.classes.keys().map(ToString::to_string).collect()
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -108,14 +112,17 @@ impl Database {
|
|||
|
||||
impl LuaUserData for Database {
|
||||
fn add_fields<'lua, F: LuaUserDataFields<'lua, Self>>(fields: &mut F) {
|
||||
fields.add_field_method_get("Version", |_, this| Ok(this.get_version()))
|
||||
fields.add_field_method_get("Version", |_, this| Ok(this.get_version()));
|
||||
}
|
||||
|
||||
fn add_methods<'lua, M: LuaUserDataMethods<'lua, Self>>(methods: &mut M) {
|
||||
methods.add_meta_method(LuaMetaMethod::Eq, userdata_impl_eq);
|
||||
methods.add_meta_method(LuaMetaMethod::ToString, userdata_impl_to_string);
|
||||
methods.add_method("GetEnumNames", |_, this, _: ()| Ok(this.get_enum_names()));
|
||||
methods.add_method("GetClassNames", |_, this, _: ()| Ok(this.get_class_names()));
|
||||
methods.add_method("GetEnumNames", |_, this, (): ()| Ok(this.get_enum_names()));
|
||||
methods.add_method(
|
||||
"GetClassNames",
|
||||
|_, this, (): ()| Ok(this.get_class_names()),
|
||||
);
|
||||
methods.add_method("GetEnum", |_, this, name: String| Ok(this.get_enum(name)));
|
||||
methods.add_method("GetClass", |_, this, name: String| Ok(this.get_class(name)));
|
||||
methods.add_method("FindEnum", |_, this, name: String| Ok(this.find_enum(name)));
|
||||
|
|
|
@ -25,6 +25,7 @@ impl DatabaseProperty {
|
|||
/**
|
||||
Get the name of this property.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_name(&self) -> String {
|
||||
self.1.name.to_string()
|
||||
}
|
||||
|
@ -36,6 +37,7 @@ impl DatabaseProperty {
|
|||
|
||||
For enums this will be a string formatted as `Enum.EnumName`.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_datatype_name(&self) -> String {
|
||||
data_type_to_str(self.1.data_type.clone())
|
||||
}
|
||||
|
@ -45,8 +47,9 @@ impl DatabaseProperty {
|
|||
|
||||
All properties are writable and readable in Lune even if scriptability is not.
|
||||
*/
|
||||
#[must_use]
|
||||
pub fn get_scriptability_str(&self) -> &'static str {
|
||||
scriptability_to_str(&self.1.scriptability)
|
||||
scriptability_to_str(self.1.scriptability)
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -59,6 +62,7 @@ impl DatabaseProperty {
|
|||
self.1
|
||||
.tags
|
||||
.iter()
|
||||
.copied()
|
||||
.map(property_tag_to_str)
|
||||
.collect::<Vec<_>>()
|
||||
}
|
||||
|
|
|
@ -17,7 +17,7 @@ pub fn data_type_to_str(data_type: DataType) -> String {
|
|||
NOTE: Remember to add any new strings here to typedefs too!
|
||||
*/
|
||||
|
||||
pub fn scriptability_to_str(scriptability: &Scriptability) -> &'static str {
|
||||
pub fn scriptability_to_str(scriptability: Scriptability) -> &'static str {
|
||||
match scriptability {
|
||||
Scriptability::None => "None",
|
||||
Scriptability::Custom => "Custom",
|
||||
|
@ -28,7 +28,7 @@ pub fn scriptability_to_str(scriptability: &Scriptability) -> &'static str {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn property_tag_to_str(tag: &PropertyTag) -> &'static str {
|
||||
pub fn property_tag_to_str(tag: PropertyTag) -> &'static str {
|
||||
match tag {
|
||||
PropertyTag::Deprecated => "Deprecated",
|
||||
PropertyTag::Hidden => "Hidden",
|
||||
|
@ -41,7 +41,7 @@ pub fn property_tag_to_str(tag: &PropertyTag) -> &'static str {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn class_tag_to_str(tag: &ClassTag) -> &'static str {
|
||||
pub fn class_tag_to_str(tag: ClassTag) -> &'static str {
|
||||
match tag {
|
||||
ClassTag::Deprecated => "Deprecated",
|
||||
ClassTag::NotBrowsable => "NotBrowsable",
|
||||
|
|
|
@ -20,8 +20,7 @@ pub(crate) fn add_class_restricted_getter<'lua, F: LuaUserDataFields<'lua, Insta
|
|||
field_getter(lua, this)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
field_name, class_name
|
||||
"{field_name} is not a valid member of {class_name}",
|
||||
)))
|
||||
}
|
||||
});
|
||||
|
@ -42,8 +41,7 @@ pub(crate) fn add_class_restricted_setter<'lua, F: LuaUserDataFields<'lua, Insta
|
|||
field_getter(lua, this, value)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
field_name, class_name
|
||||
"{field_name} is not a valid member of {class_name}",
|
||||
)))
|
||||
}
|
||||
});
|
||||
|
@ -64,8 +62,7 @@ pub(crate) fn add_class_restricted_method<'lua, M: LuaUserDataMethods<'lua, Inst
|
|||
method(lua, this, args)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
method_name, class_name
|
||||
"{method_name} is not a valid member of {class_name}",
|
||||
)))
|
||||
}
|
||||
});
|
||||
|
@ -92,8 +89,7 @@ pub(crate) fn add_class_restricted_method_mut<
|
|||
method(lua, this, args)
|
||||
} else {
|
||||
Err(LuaError::RuntimeError(format!(
|
||||
"{} is not a valid member of {}",
|
||||
method_name, class_name
|
||||
"{method_name} is not a valid member of {class_name}",
|
||||
)))
|
||||
}
|
||||
});
|
||||
|
@ -102,7 +98,7 @@ pub(crate) fn add_class_restricted_method_mut<
|
|||
/**
|
||||
Gets or creates the instance child with the given reference prop name and class name.
|
||||
|
||||
Note that the class name here must be an exact match, it is not checked using IsA.
|
||||
Note that the class name here must be an exact match, it is not checked using `IsA`.
|
||||
|
||||
The instance may be in one of several states but this function will guarantee that the
|
||||
property reference is correct and that the instance exists after it has been called:
|
||||
|
|
|
@ -60,12 +60,12 @@ pub(crate) fn find_property_info(
|
|||
value_type: Some(*value_type),
|
||||
..Default::default()
|
||||
},
|
||||
_ => Default::default(),
|
||||
_ => PropertyInfo::default(),
|
||||
});
|
||||
break;
|
||||
} else if let Some(sup) = &class.superclass {
|
||||
// No property found, we should look at the superclass
|
||||
class_name = Cow::Borrowed(sup)
|
||||
class_name = Cow::Borrowed(sup);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
|
@ -87,7 +87,7 @@ pub(crate) fn find_property_info(
|
|||
break;
|
||||
} else if let Some(sup) = &class.superclass {
|
||||
// No default value found, we should look at the superclass
|
||||
class_name = Cow::Borrowed(sup)
|
||||
class_name = Cow::Borrowed(sup);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#![allow(clippy::missing_errors_doc)]
|
||||
|
||||
use std::{any::type_name, cell::RefCell, fmt, ops};
|
||||
|
||||
use mlua::prelude::*;
|
||||
|
@ -5,21 +7,29 @@ use mlua::prelude::*;
|
|||
// Utility functions
|
||||
|
||||
type ListWriter = dyn Fn(&mut fmt::Formatter<'_>, bool, &str) -> fmt::Result;
|
||||
|
||||
#[must_use]
|
||||
pub fn make_list_writer() -> Box<ListWriter> {
|
||||
let first = RefCell::new(true);
|
||||
Box::new(move |f, flag, literal| {
|
||||
if flag {
|
||||
if first.take() {
|
||||
write!(f, "{}", literal)?;
|
||||
write!(f, "{literal}")?;
|
||||
} else {
|
||||
write!(f, ", {}", literal)?;
|
||||
write!(f, ", {literal}")?;
|
||||
}
|
||||
}
|
||||
Ok::<_, fmt::Error>(())
|
||||
})
|
||||
}
|
||||
|
||||
// Userdata metamethod implementations
|
||||
/**
|
||||
Userdata metamethod implementations
|
||||
|
||||
Note that many of these return [`LuaResult`] even though they don't
|
||||
return any errors - this is for consistency reasons and to make it
|
||||
easier to add these blanket implementations to [`LuaUserData`] impls.
|
||||
*/
|
||||
|
||||
pub fn userdata_impl_to_string<D>(_: &Lua, datatype: &D, _: ()) -> LuaResult<String>
|
||||
where
|
||||
|
|
Loading…
Add table
Reference in a new issue