Unit tests for basic Rune registration
continuous-integration/drone/push Build is failing
Details
continuous-integration/drone/push Build is failing
Details
This commit is contained in:
parent
42bee5e37c
commit
535f6bf79b
|
@ -1,6 +1,8 @@
|
||||||
use crate::dynamic_data::ExecutingMove;
|
use crate::dynamic_data::{ExecutingMove, HitData};
|
||||||
|
use crate::script_implementations::rune::wrappers::dynamic_data::pokemon::RunePokemon;
|
||||||
|
use crate::script_implementations::rune::wrappers::dynamic_data::resolve_script_data;
|
||||||
use crate::script_implementations::rune::wrappers::{impl_rune_wrapper, RuneWrapper};
|
use crate::script_implementations::rune::wrappers::{impl_rune_wrapper, RuneWrapper};
|
||||||
use rune::runtime::{AnyObj, Shared};
|
use rune::runtime::{AnyObj, Object, Shared};
|
||||||
use rune::Any;
|
use rune::Any;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
|
@ -9,6 +11,9 @@ pub fn register(module: &mut rune::Module) -> anyhow::Result<()> {
|
||||||
module.function_meta(RuneExecutingMove::target_count)?;
|
module.function_meta(RuneExecutingMove::target_count)?;
|
||||||
module.function_meta(RuneExecutingMove::number_of_hits)?;
|
module.function_meta(RuneExecutingMove::number_of_hits)?;
|
||||||
module.function_meta(RuneExecutingMove::user)?;
|
module.function_meta(RuneExecutingMove::user)?;
|
||||||
|
module.function_meta(RuneExecutingMove::chosen_move)?;
|
||||||
|
module.function_meta(RuneExecutingMove::use_move)?;
|
||||||
|
module.function_meta(RuneExecutingMove::script)?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
@ -25,4 +30,43 @@ impl RuneExecutingMove {
|
||||||
fn number_of_hits(&self) -> u8 { self.0.number_of_hits() }
|
fn number_of_hits(&self) -> u8 { self.0.number_of_hits() }
|
||||||
#[rune::function]
|
#[rune::function]
|
||||||
fn user(&self) -> Shared<AnyObj> { self.0.user().wrap() }
|
fn user(&self) -> Shared<AnyObj> { self.0.user().wrap() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn chosen_move(&self) -> Shared<AnyObj> { self.0.chosen_move().wrap() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn use_move(&self) -> Shared<AnyObj> { self.0.use_move().wrap() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn script(&self) -> Option<Shared<Object>> { resolve_script_data(self.0.script()) }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn get_hit_data(&self, for_target: RunePokemon, hit: u8) -> anyhow::Result<Shared<AnyObj>> {
|
||||||
|
self.0.get_hit_data(&for_target.0, hit).map(|hit_data| hit_data.wrap())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, Any)]
|
||||||
|
pub struct RuneHitData(pub Arc<HitData>);
|
||||||
|
|
||||||
|
impl_rune_wrapper!(&Arc<HitData>, RuneHitData);
|
||||||
|
|
||||||
|
impl RuneHitData {
|
||||||
|
#[rune::function]
|
||||||
|
fn is_critical(&self) -> bool { self.0.is_critical() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn base_power(&self) -> u8 { self.0.base_power() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn effectiveness(&self) -> f32 { self.0.effectiveness() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn damage(&self) -> u32 { self.0.damage() }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn move_type(&self) -> u8 { u8::from(self.0.move_type()) }
|
||||||
|
|
||||||
|
#[rune::function]
|
||||||
|
fn fail(&self) { self.0.fail() }
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
use rune::alloc::fmt::TryWrite;
|
||||||
use rune::runtime::{AnyObj, Protocol, Shared, VmResult};
|
use rune::runtime::{AnyObj, Protocol, Shared, VmResult};
|
||||||
use rune::{Any, Value};
|
use rune::{Any, Value};
|
||||||
use std::num::Saturating;
|
use std::num::Saturating;
|
||||||
|
@ -21,16 +22,17 @@ pub fn module() -> anyhow::Result<rune::Module> {
|
||||||
module.associated_function(Protocol::MUL_ASSIGN, RuneValueIntWrapper::mul_assign)?;
|
module.associated_function(Protocol::MUL_ASSIGN, RuneValueIntWrapper::mul_assign)?;
|
||||||
module.associated_function(Protocol::PARTIAL_EQ, RuneValueIntWrapper::partial_eq)?;
|
module.associated_function(Protocol::PARTIAL_EQ, RuneValueIntWrapper::partial_eq)?;
|
||||||
module.associated_function(Protocol::EQ, RuneValueIntWrapper::eq)?;
|
module.associated_function(Protocol::EQ, RuneValueIntWrapper::eq)?;
|
||||||
module.associated_function(Protocol::STRING_DISPLAY, RuneValueIntWrapper::string_display)?;
|
module.function_meta(RuneValueIntWrapper::string_display)?;
|
||||||
|
|
||||||
module.ty::<RuneValueBoolWrapper>()?;
|
module.ty::<RuneValueBoolWrapper>()?;
|
||||||
module.function_meta(RuneValueBoolWrapper::rn_as_bool)?;
|
module.function_meta(RuneValueBoolWrapper::rn_as_bool)?;
|
||||||
module.function_meta(RuneValueBoolWrapper::set_value)?;
|
module.function_meta(RuneValueBoolWrapper::set_value)?;
|
||||||
|
module.associated_function(Protocol::PARTIAL_EQ, RuneValueBoolWrapper::eq)?;
|
||||||
module.associated_function(Protocol::EQ, RuneValueBoolWrapper::eq)?;
|
module.associated_function(Protocol::EQ, RuneValueBoolWrapper::eq)?;
|
||||||
module.associated_function(Protocol::STRING_DISPLAY, RuneValueBoolWrapper::string_display)?;
|
module.function_meta(RuneValueBoolWrapper::string_display)?;
|
||||||
|
|
||||||
module.ty::<RuneStringKey>()?;
|
module.ty::<RuneStringKey>()?;
|
||||||
module.associated_function(Protocol::STRING_DISPLAY, RuneStringKey::string_display)?;
|
module.function_meta(RuneStringKey::string_display)?;
|
||||||
|
|
||||||
parameters::register(&mut module)?;
|
parameters::register(&mut module)?;
|
||||||
dynamic_data::register(&mut module)?;
|
dynamic_data::register(&mut module)?;
|
||||||
|
@ -103,36 +105,76 @@ impl RuneValueIntWrapper {
|
||||||
|
|
||||||
fn sub_assign(&mut self, other: i64) { self.value -= other; }
|
fn sub_assign(&mut self, other: i64) { self.value -= other; }
|
||||||
|
|
||||||
fn div_assign(&mut self, other: i64) { self.value /= other; }
|
fn div_assign(&mut self, other: Value) {
|
||||||
|
match other {
|
||||||
|
Value::Integer(other) => self.value /= other,
|
||||||
|
Value::Float(other) => self.div_assign_f64(other),
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn mul_assign(&mut self, other: i64) { self.value *= other; }
|
fn div_assign_f64(&mut self, other: f64) {
|
||||||
|
let v = (self.value.0 as f64 / other).floor();
|
||||||
|
if v > i64::MAX as f64 {
|
||||||
|
self.value = Saturating(i64::MAX);
|
||||||
|
} else if v < i64::MIN as f64 {
|
||||||
|
self.value = Saturating(i64::MIN);
|
||||||
|
} else {
|
||||||
|
self.value = Saturating(v as i64);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn mul_assign(&mut self, other: Value) {
|
||||||
|
match other {
|
||||||
|
Value::Integer(other) => self.value *= other,
|
||||||
|
Value::Float(other) => self.mul_assign_f64(other),
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn mul_assign_f64(&mut self, other: f64) {
|
||||||
|
let v = (self.value.0 as f64 * other).floor();
|
||||||
|
if v > i64::MAX as f64 {
|
||||||
|
self.value = Saturating(i64::MAX);
|
||||||
|
} else if v < i64::MIN as f64 {
|
||||||
|
self.value = Saturating(i64::MIN);
|
||||||
|
} else {
|
||||||
|
self.value = Saturating(v as i64);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn partial_eq(&self, b: i64) -> VmResult<bool> { VmResult::Ok(self.value.0 == b) }
|
fn partial_eq(&self, b: i64) -> VmResult<bool> { VmResult::Ok(self.value.0 == b) }
|
||||||
|
|
||||||
fn eq(&self, b: i64) -> VmResult<bool> { VmResult::Ok(self.value.0 == b) }
|
fn eq(&self, b: i64) -> VmResult<bool> { VmResult::Ok(self.value.0 == b) }
|
||||||
|
|
||||||
fn string_display(&self) -> VmResult<String> { VmResult::Ok(format!("{}", self.value.0)) }
|
#[rune::function(instance, protocol = STRING_DISPLAY)]
|
||||||
|
fn string_display(&self, f: &mut rune::runtime::Formatter) -> VmResult<()> {
|
||||||
|
rune::vm_write!(f, "{}", self.value.0);
|
||||||
|
VmResult::Ok(())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Any, Clone)]
|
#[derive(Any, Clone)]
|
||||||
struct RuneValueBoolWrapper {
|
struct RuneValueBoolWrapper(bool);
|
||||||
value: bool,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl RuneValueBoolWrapper {
|
impl RuneValueBoolWrapper {
|
||||||
pub fn new(value: bool) -> Self { Self { value } }
|
pub fn new(value: bool) -> Self { Self(value) }
|
||||||
|
|
||||||
pub fn as_bool(&self) -> bool { self.value }
|
pub fn as_bool(&self) -> bool { self.0 }
|
||||||
|
|
||||||
#[rune::function(path = RuneValueIntWrapper::as_bool)]
|
#[rune::function(path = RuneValueIntWrapper::as_bool)]
|
||||||
fn rn_as_bool(&self) -> bool { self.value }
|
fn rn_as_bool(&self) -> bool { self.0 }
|
||||||
|
|
||||||
#[rune::function]
|
#[rune::function]
|
||||||
fn set_value(&mut self, value: bool) { self.value = value; }
|
fn set_value(&mut self, value: bool) { self.0 = value; }
|
||||||
|
|
||||||
fn string_display(&self) -> VmResult<String> { VmResult::Ok(format!("{}", self.value)) }
|
#[rune::function(instance, protocol = STRING_DISPLAY)]
|
||||||
|
fn string_display(&self, f: &mut rune::runtime::Formatter) -> VmResult<()> {
|
||||||
|
rune::vm_write!(f, "{}", self.0);
|
||||||
|
VmResult::Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
fn eq(&self, b: bool) -> VmResult<bool> { VmResult::Ok(self.value == b) }
|
fn eq(&self, b: bool) -> VmResult<bool> { VmResult::Ok(self.0 == b) }
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Any, Clone, Debug)]
|
#[derive(Any, Clone, Debug)]
|
||||||
|
@ -141,9 +183,416 @@ pub(super) struct RuneStringKey(pub StringKey);
|
||||||
impl RuneStringKey {
|
impl RuneStringKey {
|
||||||
pub fn new(value: StringKey) -> Self { Self(value) }
|
pub fn new(value: StringKey) -> Self { Self(value) }
|
||||||
|
|
||||||
fn string_display(&self) -> VmResult<String> { VmResult::Ok(format!("{}", self.0)) }
|
#[rune::function(instance, protocol = STRING_DISPLAY)]
|
||||||
|
fn string_display(&self, f: &mut rune::runtime::Formatter) -> VmResult<()> {
|
||||||
|
rune::vm_write!(f, "{}", self.0);
|
||||||
|
VmResult::Ok(())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl RuneWrapper for &StringKey {
|
impl RuneWrapper for &StringKey {
|
||||||
fn wrap(self) -> Shared<AnyObj> { Shared::new(AnyObj::new(RuneStringKey(self.clone())).unwrap()).unwrap() }
|
fn wrap(self) -> Shared<AnyObj> { Shared::new(AnyObj::new(RuneStringKey(self.clone())).unwrap()).unwrap() }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod test {
|
||||||
|
use super::*;
|
||||||
|
use rune::{Context, Diagnostics, Options, Source, Vm};
|
||||||
|
use std::sync::Arc;
|
||||||
|
|
||||||
|
pub fn setup_script(script: &str) -> Vm {
|
||||||
|
let mut context = Context::with_default_modules().unwrap();
|
||||||
|
context.install(module().unwrap()).unwrap();
|
||||||
|
|
||||||
|
let mut sources = rune::Sources::new();
|
||||||
|
sources.insert(Source::memory(script).unwrap()).unwrap();
|
||||||
|
let mut diagnostics = Diagnostics::new();
|
||||||
|
|
||||||
|
let mut options = Options::default();
|
||||||
|
options.debug_info(true);
|
||||||
|
options.memoize_instance_fn(true);
|
||||||
|
options.macros(true);
|
||||||
|
options.bytecode(true);
|
||||||
|
|
||||||
|
let unit = rune::prepare(&mut sources)
|
||||||
|
.with_context(&context)
|
||||||
|
.with_diagnostics(&mut diagnostics)
|
||||||
|
.with_options(&options)
|
||||||
|
.build()
|
||||||
|
.unwrap();
|
||||||
|
if !diagnostics.is_empty() {
|
||||||
|
panic!("Diagnostics: {:?}", diagnostics);
|
||||||
|
}
|
||||||
|
|
||||||
|
Vm::new(Arc::new(context.runtime().unwrap()), Arc::new(unit))
|
||||||
|
}
|
||||||
|
|
||||||
|
macro_rules! execute_vm {
|
||||||
|
($vm:expr, $func:expr, $val:expr) => {{
|
||||||
|
let args = vec![$val.clone()];
|
||||||
|
$vm.execute([$func], args).unwrap().complete().into_result().unwrap()
|
||||||
|
}};
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_set_value() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a.set_value(5);
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_as_int() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a.as_int()
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_int", val);
|
||||||
|
let res = res.as_integer().unwrap();
|
||||||
|
assert_eq!(res, 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_add() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a += 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 15);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_add_overflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a += 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MAX).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MAX);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_sub() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a -= 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_underflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a -= 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MIN).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MIN);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_mul() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a *= 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 50);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_mul_float() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a *= 0.5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_mul_overflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a *= 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MAX).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MAX);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_mul_float_overflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a *= 10.0;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MAX).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MAX);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_mul_float_underflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a *= 10.0;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MIN).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MIN);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_div() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a /= 5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_div_float() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a /= 0.5;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(10).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, 20);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_div_float_overflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a /= 0.0001;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MAX).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MAX);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_div_float_underflow() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a /= 0.0001;
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(i64::MIN).unwrap();
|
||||||
|
execute_vm!(vm, "test_int", val);
|
||||||
|
let v = get_int_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, i64::MIN);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_eq() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a == 5
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(5).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_int", val);
|
||||||
|
let res = res.as_bool().unwrap();
|
||||||
|
assert_eq!(res, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_ineq() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
a == 5
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(6).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_int", val);
|
||||||
|
let res = res.as_bool().unwrap();
|
||||||
|
assert_eq!(res, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_int_wrapper_string_display() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_int(a) {
|
||||||
|
`${a}`
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_int_reference(5).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_int", val);
|
||||||
|
let res = res.into_string().unwrap().take().unwrap().into_std();
|
||||||
|
assert_eq!(res, "5");
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_bool_wrapper_set_value() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_bool(a) {
|
||||||
|
a.set_value(true);
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_bool_reference(false).unwrap();
|
||||||
|
execute_vm!(vm, "test_bool", val);
|
||||||
|
let v = get_bool_reference_value(val).unwrap();
|
||||||
|
assert_eq!(v, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_bool_wrapper_as_bool() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_bool(a) {
|
||||||
|
a.as_bool()
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_bool_reference(true).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_bool", val);
|
||||||
|
let res = res.as_bool().unwrap();
|
||||||
|
assert_eq!(res, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_bool_wrapper_eq() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_bool(a) {
|
||||||
|
a == true
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_bool_reference(true).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_bool", val);
|
||||||
|
let res = res.as_bool().unwrap();
|
||||||
|
assert_eq!(res, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_bool_wrapper_ineq() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_bool(a) {
|
||||||
|
a == true
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_bool_reference(false).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_bool", val);
|
||||||
|
let res = res.as_bool().unwrap();
|
||||||
|
assert_eq!(res, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_bool_wrapper_string_display() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_bool(a) {
|
||||||
|
`${a}`
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = wrap_bool_reference(true).unwrap();
|
||||||
|
let res = execute_vm!(vm, "test_bool", val);
|
||||||
|
let res = res.into_string().unwrap().take().unwrap().into_std();
|
||||||
|
assert_eq!(res, "true");
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_string_key_wrapper_string_display() {
|
||||||
|
let mut vm = setup_script(
|
||||||
|
r#"
|
||||||
|
pub fn test_string_key(a) {
|
||||||
|
`${a}`
|
||||||
|
}
|
||||||
|
"#,
|
||||||
|
);
|
||||||
|
let val = RuneStringKey::new(StringKey::from("test"));
|
||||||
|
let val = Shared::new(AnyObj::new(val).unwrap()).unwrap();
|
||||||
|
let arg = Value::Any(val);
|
||||||
|
let res = execute_vm!(vm, "test_string_key", arg);
|
||||||
|
let res = res.into_string().unwrap().take().unwrap().into_std();
|
||||||
|
assert_eq!(res, "test");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -5,10 +5,7 @@
|
||||||
|
|
||||||
use std::sync::{Arc, LazyLock};
|
use std::sync::{Arc, LazyLock};
|
||||||
|
|
||||||
use pkmn_lib::dynamic_data::{
|
use pkmn_lib::dynamic_data::{DynamicLibrary, PassChoice, PokemonBuilder, ScriptCategory, ScriptOwnerData, TurnChoice};
|
||||||
Battle, BattleParty, DamageSource, DynamicLibrary, ExecutingMove, MoveChoice, PassChoice, PokemonBuilder,
|
|
||||||
PokemonParty, ScriptCategory, ScriptContainer, ScriptOwnerData, TurnChoice, VolatileScriptsOwner,
|
|
||||||
};
|
|
||||||
|
|
||||||
use crate::common::library_loader;
|
use crate::common::library_loader;
|
||||||
|
|
||||||
|
@ -106,75 +103,3 @@ fn load_non_existing_wasm_script() {
|
||||||
|
|
||||||
assert!(script.is_none());
|
assert!(script.is_none());
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Assurance has the interesting properties that it creates a special data script internally, and
|
|
||||||
/// deletes that data script through the get_owner functionality.
|
|
||||||
#[test]
|
|
||||||
fn validate_assurance() {
|
|
||||||
let lib = get_library();
|
|
||||||
let p1 = PokemonBuilder::new(lib.clone(), "charizard".into(), 100)
|
|
||||||
.learn_move("assurance".into())
|
|
||||||
.build()
|
|
||||||
.unwrap();
|
|
||||||
let p2 = PokemonBuilder::new(lib.clone(), "venusaur".into(), 100)
|
|
||||||
.build()
|
|
||||||
.unwrap();
|
|
||||||
let party1 = Arc::new(
|
|
||||||
BattleParty::new(
|
|
||||||
Arc::new(PokemonParty::new_from_vec(vec![Some(p1.clone())])),
|
|
||||||
vec![(0, 0)],
|
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
let party2 = Arc::new(
|
|
||||||
BattleParty::new(
|
|
||||||
Arc::new(PokemonParty::new_from_vec(vec![Some(p2.clone())])),
|
|
||||||
vec![(1, 0)],
|
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
|
|
||||||
let battle = Battle::new(lib.clone(), vec![party1, party2], false, 2, 1, None);
|
|
||||||
|
|
||||||
battle.sides()[0].set_pokemon(0, Some(p1.clone())).unwrap();
|
|
||||||
battle.sides()[1].set_pokemon(0, Some(p2.clone())).unwrap();
|
|
||||||
|
|
||||||
let script = lib
|
|
||||||
.load_script(
|
|
||||||
ScriptOwnerData::None,
|
|
||||||
ScriptCategory::Move,
|
|
||||||
&"double_power_if_target_damaged_in_turn".into(),
|
|
||||||
)
|
|
||||||
.unwrap()
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let mv = p1.learned_moves().read()[0].as_ref().unwrap().clone();
|
|
||||||
let choice = Arc::new(TurnChoice::Move(MoveChoice::new(p1.clone(), mv.clone(), 1, 0)));
|
|
||||||
script.on_before_turn(&choice).unwrap();
|
|
||||||
assert!(battle.sides()[1].has_volatile_script(&"double_power_if_target_damaged_in_turn_data".into()));
|
|
||||||
|
|
||||||
let executing_move = Arc::new(ExecutingMove::new(
|
|
||||||
vec![],
|
|
||||||
1,
|
|
||||||
p1,
|
|
||||||
mv.clone(),
|
|
||||||
mv.move_data().clone(),
|
|
||||||
ScriptContainer::default(),
|
|
||||||
));
|
|
||||||
let mut v = 20_u8;
|
|
||||||
script.change_base_power(&executing_move, &p2, 0, &mut v).unwrap();
|
|
||||||
assert_eq!(v, 20_u8);
|
|
||||||
|
|
||||||
let s = battle.sides()[1].get_volatile_script(&"double_power_if_target_damaged_in_turn_data".into());
|
|
||||||
let binding = s.as_ref().unwrap().get().unwrap().read();
|
|
||||||
let data_script = binding.as_ref().unwrap();
|
|
||||||
|
|
||||||
data_script.on_damage(&p2, DamageSource::Misc, 100, 50).unwrap();
|
|
||||||
|
|
||||||
let mut v = 20_u8;
|
|
||||||
script.change_base_power(&executing_move, &p2, 0, &mut v).unwrap();
|
|
||||||
assert_eq!(v, 40_u8);
|
|
||||||
|
|
||||||
data_script.on_end_turn().unwrap();
|
|
||||||
assert!(!battle.sides()[1].has_volatile_script(&"double_power_if_target_damaged_in_turn_data".into()));
|
|
||||||
}
|
|
||||||
|
|
Loading…
Reference in New Issue