From 3f89f2c1c5c37ad16ec7ebd33e008f8c461e3d46 Mon Sep 17 00:00:00 2001 From: Quaternions <krakow20@gmail.com> Date: Tue, 22 Apr 2025 21:19:24 -0700 Subject: [PATCH] roblox_emulator: implement FindFirstChildWhichIsA --- .../src/runner/instance/instance.rs | 35 +++++++++++++++++-- 1 file changed, 33 insertions(+), 2 deletions(-) diff --git a/lib/roblox_emulator/src/runner/instance/instance.rs b/lib/roblox_emulator/src/runner/instance/instance.rs index 5e4f60c..322ec12 100644 --- a/lib/roblox_emulator/src/runner/instance/instance.rs +++ b/lib/roblox_emulator/src/runner/instance/instance.rs @@ -84,6 +84,21 @@ pub fn find_first_descendant_of_class<'a>(dom:&'a rbx_dom_weak::WeakDom,instance dom.descendants_of(instance.referent()).find(|&inst|inst.class==class) } +pub fn find_first_child_which_is_a<'a>(dom:&'a rbx_dom_weak::WeakDom,instance:&rbx_dom_weak::Instance,superclass:&str)->Option<&'a rbx_dom_weak::Instance>{ + let db=rbx_reflection_database::get(); + let superclass_descriptor=db.classes.get(superclass)?; + instance.children().iter().filter_map(|&r|dom.get_by_ref(r)).find(|inst|{ + db.classes.get(inst.class.as_str()).is_some_and(|descriptor|db.has_superclass(descriptor,superclass_descriptor)) + }) +} +pub fn find_first_descendant_which_is_a<'a>(dom:&'a rbx_dom_weak::WeakDom,instance:&rbx_dom_weak::Instance,superclass:&str)->Option<&'a rbx_dom_weak::Instance>{ + let db=rbx_reflection_database::get(); + let superclass_descriptor=db.classes.get(superclass)?; + dom.descendants_of(instance.referent()).find(|inst|{ + db.classes.get(inst.class.as_str()).is_some_and(|descriptor|db.has_superclass(descriptor,superclass_descriptor)) + }) +} + #[derive(Clone,Copy)] pub struct Instance{ referent:Ref, @@ -193,10 +208,26 @@ impl mlua::UserData for Instance{ methods.add_method("FindFirstChildOfClass",|lua,this,(class,search_descendants):(mlua::String,Option<bool>)|{ let class_str=&*class.to_str()?; dom_mut(lua,|dom|{ + let inst=this.get(dom)?; Ok( match search_descendants.unwrap_or(false){ - true=>find_first_descendant_of_class(dom,this.get(dom)?,class_str), - false=>find_first_child_of_class(dom,this.get(dom)?,class_str), + true=>find_first_descendant_of_class(dom,inst,class_str), + false=>find_first_child_of_class(dom,inst,class_str), + } + .map(|instance| + Instance::new_unchecked(instance.referent()) + ) + ) + }) + }); + methods.add_method("FindFirstChildWhichIsA",|lua,this,(class,search_descendants):(mlua::String,Option<bool>)|{ + let class_str=&*class.to_str()?; + dom_mut(lua,|dom|{ + let inst=this.get(dom)?; + Ok( + match search_descendants.unwrap_or(false){ + true=>find_first_descendant_which_is_a(dom,inst,class_str), + false=>find_first_child_which_is_a(dom,inst,class_str), } .map(|instance| Instance::new_unchecked(instance.referent())