diff --git a/gen_7_scripts/src/test_script.rs b/gen_7_scripts/src/test_script.rs index 38f36e6..583e854 100644 --- a/gen_7_scripts/src/test_script.rs +++ b/gen_7_scripts/src/test_script.rs @@ -1,6 +1,6 @@ use pkmn_lib_interface::app_interface::list::ImmutableList; use pkmn_lib_interface::app_interface::{ - get_hash, DataLibrary, DynamicLibrary, EffectParameter, TurnChoice, + get_hash, DamageSource, DataLibrary, DynamicLibrary, EffectParameter, TurnChoice, }; use pkmn_lib_interface::dbg; use pkmn_lib_interface::handling::{Script, ScriptCapabilities}; @@ -46,5 +46,12 @@ impl Script for TestScript { "On before turn for user: {}", choice.user().species().name() ); + choice.user().damage(50, DamageSource::Misc); + if let TurnChoice::Move(d) = choice { + dbg!( + "On before turn for move choice: {}", + d.used_move().move_data().name() + ); + } } } diff --git a/pkmn_lib_interface/src/app_interface/dynamic_data/turn_choices.rs b/pkmn_lib_interface/src/app_interface/dynamic_data/turn_choices.rs index ae99823..522f8b7 100644 --- a/pkmn_lib_interface/src/app_interface/dynamic_data/turn_choices.rs +++ b/pkmn_lib_interface/src/app_interface/dynamic_data/turn_choices.rs @@ -1,7 +1,8 @@ -use crate::app_interface::Pokemon; +use crate::app_interface::{LearnedMove, Pokemon}; use crate::handling::cached_value::CachedValue; use crate::handling::temporary::Temporary; -use crate::{cached_value, ExternRef, ExternalReferenceType}; +use crate::{cached_value, wasm_value_getters, ExternRef, ExternalReferenceType, Script}; +use alloc::boxed::Box; use alloc::rc::Rc; struct BaseTurnChoiceData { @@ -11,6 +12,9 @@ struct BaseTurnChoiceData { struct MoveTurnChoiceDataInner { base: BaseTurnChoiceData, + used_move: CachedValue, + target_side: CachedValue, + target_index: CachedValue, } #[derive(Clone)] struct MoveTurnChoiceDataTemporary { @@ -29,12 +33,50 @@ pub enum TurnChoice { } impl TurnChoice { - pub fn user(&self) -> Pokemon { + fn base(&self) -> &BaseTurnChoiceData { match self { - TurnChoice::Move(data) => data.temp.value().inner.base.user.value(), - _ => panic!("Unknown turn choice type"), + TurnChoice::Move(d) => &d.temp.value_ref().inner.base, + TurnChoice::Item() => unimplemented!(), + TurnChoice::Switch() => unimplemented!(), + TurnChoice::Flee => unimplemented!(), + TurnChoice::Pass => unimplemented!(), } } + + pub fn user(&self) -> Pokemon { + self.base().user.value() + } + + pub fn speed(&self) -> u32 { + unsafe { turn_choice_get_speed(self.base().reference) } + } + + pub fn has_failed(&self) -> bool { + unsafe { turn_choice_has_failed(self.base().reference) } + } + + pub fn fail(&self) { + unsafe { turn_choice_fail(self.base().reference) } + } +} + +impl MoveTurnChoiceData { + pub fn used_move(&self) -> LearnedMove { + self.temp.value().inner.used_move.value() + } + pub fn target_side(&self) -> u8 { + self.temp.value().inner.target_side.value() + } + pub fn target_index(&self) -> u8 { + self.temp.value().inner.target_index.value() + } + pub fn priority(&self) -> i8 { + unsafe { turn_choice_move_priority(self.temp.value().inner.base.reference.cast()) } + } + + pub fn move_script(&self) -> Option<&Box> { + unsafe { turn_choice_move_script(self.temp.value().inner.base.reference.cast()).as_ref() } + } } impl ExternalReferenceType for TurnChoice { @@ -59,6 +101,13 @@ impl ExternalReferenceType for MoveTurnChoiceDataTemporary { turn_choice_get_user(reference.cast()).get_value().unwrap() }), }, + used_move: cached_value!({ + turn_choice_move_used_move(reference.cast()) + .get_value() + .unwrap() + }), + target_side: cached_value!({ turn_choice_move_target_side(reference.cast()) }), + target_index: cached_value!({ turn_choice_move_target_index(reference.cast()) }), }), } } @@ -67,6 +116,15 @@ impl ExternalReferenceType for MoveTurnChoiceDataTemporary { extern "wasm" { fn turn_choice_get_kind(r: ExternRef) -> u8; fn turn_choice_get_user(r: ExternRef) -> ExternRef; + fn turn_choice_get_speed(r: ExternRef) -> u32; + fn turn_choice_has_failed(r: ExternRef) -> bool; + fn turn_choice_fail(r: ExternRef); + + fn turn_choice_move_used_move(r: ExternRef) -> ExternRef; + fn turn_choice_move_target_side(r: ExternRef) -> u8; + fn turn_choice_move_target_index(r: ExternRef) -> u8; + fn turn_choice_move_priority(r: ExternRef) -> i8; + fn turn_choice_move_script(r: ExternRef) -> *const Box; } #[no_mangle] diff --git a/pkmn_lib_interface/src/handling/extern_ref.rs b/pkmn_lib_interface/src/handling/extern_ref.rs index 6ea9a25..213bece 100644 --- a/pkmn_lib_interface/src/handling/extern_ref.rs +++ b/pkmn_lib_interface/src/handling/extern_ref.rs @@ -18,6 +18,7 @@ impl ExternRef { self.p } + #[inline] pub fn get_value(&self) -> Option where T: ExternalReferenceType, diff --git a/pkmn_lib_interface/src/handling/temporary.rs b/pkmn_lib_interface/src/handling/temporary.rs index 9bfca69..ca7c7c2 100644 --- a/pkmn_lib_interface/src/handling/temporary.rs +++ b/pkmn_lib_interface/src/handling/temporary.rs @@ -1,4 +1,4 @@ -use crate::{dbg, println, ExternRef, ExternalReferenceType}; +use crate::{ExternRef, ExternalReferenceType}; use alloc::boxed::Box; use core::cell::Cell; use core::mem::forget; @@ -20,6 +20,7 @@ where T: ExternalReferenceType, T: Clone, { + #[inline] pub fn from_reference(reference: ExternRef) -> Self { let temporaries = unsafe { &mut TEMPORARIES }; let existing = temporaries.get(&reference.get_internal_index()); @@ -47,10 +48,16 @@ where Self { value: ptr } } + #[inline] pub fn value(&self) -> T { unsafe { self.value.as_ref().unwrap().value.clone() } } + #[inline] + pub fn value_ref(&self) -> &T { + unsafe { &self.value.as_ref().unwrap().value } + } + pub(crate) fn mark_as_deleted(reference: ExternRef) { let temporaries = unsafe { &mut TEMPORARIES }; let existing = temporaries.get(&reference.get_internal_index());