Add fallible type iterators.

This commit is contained in:
Stephen Chung 2022-08-22 13:10:32 +08:00
parent 1deed8cd55
commit 799dd9d9d1
4 changed files with 36 additions and 31 deletions

View File

@ -10,6 +10,14 @@ Bug fixes
* API for registering property getters/setters and indexers to an `Engine` now works with functions that take a first parameter of `NativeCallContext`. * API for registering property getters/setters and indexers to an `Engine` now works with functions that take a first parameter of `NativeCallContext`.
* Missing API function `Module::set_getter_setter_fn` is added. * Missing API function `Module::set_getter_setter_fn` is added.
New features
------------
Fallible type iterators
-----------------------
* For very special needs, the ability to register fallible type iterators is added.
Version 1.9.0 Version 1.9.0
============= =============

View File

@ -641,38 +641,21 @@ impl Engine {
break; break;
} }
let index_value = (x as INT).into(); let index_value = Dynamic::from(x as INT);
#[cfg(not(feature = "no_closure"))] *scope.get_mut_by_index(counter_index).write_lock().unwrap() =
{ index_value;
let index_var = scope.get_mut_by_index(counter_index);
if index_var.is_shared() {
*index_var.write_lock().expect("`Dynamic`") = index_value;
} else {
*index_var = index_value;
}
}
#[cfg(feature = "no_closure")]
{
*scope.get_mut_by_index(counter_index) = index_value;
}
} }
let value = iter_value.flatten(); let value = match iter_value {
Ok(v) => v.flatten(),
Err(err) => {
loop_result = Err(err.fill_position(expr.position()));
break;
}
};
#[cfg(not(feature = "no_closure"))] *scope.get_mut_by_index(index).write_lock().unwrap() = value;
{
let loop_var = scope.get_mut_by_index(index);
if loop_var.is_shared() {
*loop_var.write_lock().expect("`Dynamic`") = value;
} else {
*loop_var = value;
}
}
#[cfg(feature = "no_closure")]
{
*scope.get_mut_by_index(index) = value;
}
#[cfg(not(feature = "unchecked"))] #[cfg(not(feature = "unchecked"))]
if let Err(err) = self if let Err(err) = self

View File

@ -426,10 +426,11 @@ pub type FnBuiltin = fn(NativeCallContext, &mut FnCallArgs) -> RhaiResult;
/// Function that gets an iterator from a type. /// Function that gets an iterator from a type.
#[cfg(not(feature = "sync"))] #[cfg(not(feature = "sync"))]
pub type IteratorFn = dyn Fn(Dynamic) -> Box<dyn Iterator<Item = Dynamic>>; pub type IteratorFn = dyn Fn(Dynamic) -> Box<dyn Iterator<Item = RhaiResultOf<Dynamic>>>;
/// Function that gets an iterator from a type. /// Function that gets an iterator from a type.
#[cfg(feature = "sync")] #[cfg(feature = "sync")]
pub type IteratorFn = dyn Fn(Dynamic) -> Box<dyn Iterator<Item = Dynamic>> + Send + Sync; pub type IteratorFn =
dyn Fn(Dynamic) -> Box<dyn Iterator<Item = RhaiResultOf<Dynamic>>> + Send + Sync;
#[cfg(not(feature = "sync"))] #[cfg(not(feature = "sync"))]
pub type FnPlugin = dyn PluginFunction; pub type FnPlugin = dyn PluginFunction;

View File

@ -2251,11 +2251,24 @@ impl Module {
/// Set a type iterator into the [`Module`]. /// Set a type iterator into the [`Module`].
#[cfg(not(feature = "sync"))] #[cfg(not(feature = "sync"))]
#[inline] #[inline(always)]
pub fn set_iter( pub fn set_iter(
&mut self, &mut self,
type_id: TypeId, type_id: TypeId,
func: impl Fn(Dynamic) -> Box<dyn Iterator<Item = Dynamic>> + 'static, func: impl Fn(Dynamic) -> Box<dyn Iterator<Item = Dynamic>> + 'static,
) -> &mut Self {
self.set_iter_result(type_id, move |x| {
Box::new(func(x).map(Ok)) as Box<dyn Iterator<Item = RhaiResultOf<Dynamic>>>
})
}
/// Set a fallible type iterator into the [`Module`].
#[cfg(not(feature = "sync"))]
#[inline]
pub fn set_iter_result(
&mut self,
type_id: TypeId,
func: impl Fn(Dynamic) -> Box<dyn Iterator<Item = RhaiResultOf<Dynamic>>> + 'static,
) -> &mut Self { ) -> &mut Self {
let func = Shared::new(func); let func = Shared::new(func);
if self.indexed { if self.indexed {