Skip to content

Commit

Permalink
Added native class example
Browse files Browse the repository at this point in the history
  • Loading branch information
HalidOdat committed Aug 15, 2020
1 parent f917c7f commit fd36121
Show file tree
Hide file tree
Showing 2 changed files with 85 additions and 1 deletion.
84 changes: 84 additions & 0 deletions boa/examples/classes.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
use boa::builtins::object::{Class, ClassBuilder};
use boa::builtins::value::*;
use boa::exec::*;
use boa::realm::Realm;
use boa::*;

use gc::{Finalize, Trace};

#[derive(Debug, Trace, Finalize)]
struct Person {
name: String,
age: u32,
}

impl Person {
fn say_hello(this: &Value, _: &[Value], ctx: &mut Interpreter) -> ResultValue {
if let Some(object) = this.as_object() {
if let Some(person) = object.downcast_ref::<Person>() {
println!(
"Hello my name is {}, I'm {} years old",
person.name, person.age
);
return Ok(Value::undefined());
}
}
ctx.throw_type_error("'this' is not a Person object")
}
}

impl Class for Person {
const NAME: &'static str = "Person";
const LENGTH: usize = 2;

fn constructor(_this: &Value, args: &[Value], ctx: &mut Interpreter) -> Result<Self, Value> {
let name = ctx.to_string(&args.get(0).cloned().unwrap_or_default())?;
let age = ctx.to_uint32(&args.get(1).cloned().unwrap_or_default())?;

let person = Person {
name: name.to_string(),
age,
};

Ok(person)
}

fn methods(class: &mut ClassBuilder) -> Result<(), Value> {
class.method("sayHello", 0, Self::say_hello);
class.static_method("is", 1, |_this, args, _ctx| {
if let Some(arg) = args.get(0) {
if let Some(object) = arg.as_object() {
if object.is::<Person>() {
return Ok(true.into());
}
}
}
Ok(false.into())
});

Ok(())
}
}

fn main() {
let realm = Realm::create();
let mut context = Interpreter::new(realm);

context.register_global_class::<Person>().unwrap();

forward_val(
&mut context,
r"
let person = new Person('John', 19);
person.sayHello();
if (Person.is(person)) {
console.log('person is a Person class instance.');
}
if (!Person.is('Hello')) {
console.log('\'Hello\' string is not a Person class instance.');
}
",
)
.unwrap();
}
2 changes: 1 addition & 1 deletion boa/src/builtins/object/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ pub trait Class: NativeObject {
Self: Sized;

/// Initializes the internals and the methods of the class.
fn methods(class: &mut ClassBuilder<'_>) -> ResultValue;
fn methods(class: &mut ClassBuilder<'_>) -> Result<(), Value>;
}

/// Class builder which allows adding methods and static methods to the class.
Expand Down

0 comments on commit fd36121

Please sign in to comment.