avm1: Refactor `XmlNodeObject::from_xml_node`

Revert some of e50aea864b for an even
better approach - Remove `XmlNodeObject::empty_node` entirely by
making `XmlNodeObject::from_xml_node` a suitable alternative. That is,
being able to accept a custom `proto` like before.

Also, make it return an `XmlNodeObject` instead of an `Object`, and
add a few `.into()` where needed.
This commit is contained in:
relrelb 2022-02-11 20:48:34 +02:00 committed by relrelb
parent 4e2f7b02fc
commit faa1f3d6b4
3 changed files with 22 additions and 39 deletions

View File

@ -416,8 +416,9 @@ pub fn create_proto<'gc>(
proto: Object<'gc>,
fn_proto: Object<'gc>,
) -> Object<'gc> {
let xmlnode_proto = XmlNodeObject::empty_node(gc_context, Some(proto));
let object = xmlnode_proto.as_script_object().unwrap();
let node = XmlNode::new_text(gc_context, AvmString::default());
let xml_node_proto = XmlNodeObject::from_xml_node(gc_context, node, Some(proto));
let object = xml_node_proto.as_script_object().unwrap();
define_properties_on(PROTO_DECLS, gc_context, object, fn_proto);
xmlnode_proto
xml_node_proto.into()
}

View File

@ -23,41 +23,21 @@ pub struct XmlNodeObjectData<'gc> {
}
impl<'gc> XmlNodeObject<'gc> {
/// Construct a new XML node and object pair.
pub fn empty_node(
gc_context: MutationContext<'gc, '_>,
proto: Option<Object<'gc>>,
) -> Object<'gc> {
let mut xml_node = XmlNode::new_text(gc_context, AvmString::default());
let base_object = ScriptObject::object(gc_context, proto);
let object = XmlNodeObject(GcCell::allocate(
gc_context,
XmlNodeObjectData {
base: base_object,
node: xml_node,
},
))
.into();
xml_node.introduce_script_object(gc_context, object);
object
}
/// Construct an XmlNodeObject for an already existing node.
pub fn from_xml_node(
activation: &mut Activation<'_, 'gc, '_>,
xml_node: XmlNode<'gc>,
) -> Object<'gc> {
let proto = activation.context.avm1.prototypes.xml_node;
Self(GcCell::allocate(
activation.context.gc_context,
gc_context: MutationContext<'gc, '_>,
mut node: XmlNode<'gc>,
proto: Option<Object<'gc>>,
) -> Self {
let object = Self(GcCell::allocate(
gc_context,
XmlNodeObjectData {
base: ScriptObject::object(activation.context.gc_context, Some(proto)),
node: xml_node,
base: ScriptObject::object(gc_context, proto),
node,
},
))
.into()
));
node.introduce_script_object(gc_context, object.into());
object
}
}
@ -79,10 +59,12 @@ impl<'gc> TObject<'gc> for XmlNodeObject<'gc> {
activation: &mut Activation<'_, 'gc, '_>,
this: Object<'gc>,
) -> Result<Object<'gc>, Error<'gc>> {
Ok(XmlNodeObject::empty_node(
Ok(Self::from_xml_node(
activation.context.gc_context,
XmlNode::new_text(activation.context.gc_context, AvmString::default()),
Some(this),
))
)
.into())
}
fn as_xml_node(&self) -> Option<XmlNode<'gc>> {

View File

@ -614,9 +614,9 @@ impl<'gc> XmlNode<'gc> {
match self.get_script_object() {
Some(object) => object,
None => {
let object = XmlNodeObject::from_xml_node(activation, *self);
self.introduce_script_object(activation.context.gc_context, object);
object
let proto = activation.context.avm1.prototypes().xml_node;
XmlNodeObject::from_xml_node(activation.context.gc_context, *self, Some(proto))
.into()
}
}
}