diff --git a/godot-codegen/src/conv/type_conversions.rs b/godot-codegen/src/conv/type_conversions.rs index d87fc7b84..e9f25465b 100644 --- a/godot-codegen/src/conv/type_conversions.rs +++ b/godot-codegen/src/conv/type_conversions.rs @@ -236,8 +236,8 @@ fn to_rust_type_uncached(full_ty: &GodotTy, ctx: &mut Context) -> RustTy { RustTy::EngineClass { tokens: quote! { Gd<#qualified_class> }, - arg_view: quote! { ObjectArg<#qualified_class> }, - impl_as_arg: quote! { impl AsObjectArg<#qualified_class> }, + object_arg: quote! { ObjectArg<#qualified_class> }, + impl_as_object_arg: quote! { impl AsObjectArg<#qualified_class> }, inner_class: ty, } } @@ -266,7 +266,7 @@ fn to_rust_expr_inner(expr: &str, ty: &RustTy, is_inner: bool) -> TokenStream { return match ty { RustTy::BuiltinIdent(ident) if ident == "Variant" => quote! { Variant::nil() }, RustTy::EngineClass { .. } => { - quote! { ObjectArg::null() } + quote! { Gd::null_arg() } } _ => panic!("null not representable in target type {ty:?}"), } diff --git a/godot-codegen/src/generator/default_parameters.rs b/godot-codegen/src/generator/default_parameters.rs index 7012af66f..6bc6d3976 100644 --- a/godot-codegen/src/generator/default_parameters.rs +++ b/godot-codegen/src/generator/default_parameters.rs @@ -247,30 +247,33 @@ fn make_extender( default_value, } = param; - let type_ = type_.param_decl(); + let (field_type, needs_conversion) = type_.private_field_decl(); // Initialize with default parameters where available, forward constructor args otherwise let init = if let Some(value) = default_value { - quote! { #name: #value } + make_field_init(name, value, needs_conversion) } else { quote! { #name } }; - result.builder_fields.push(quote! { #name: #type_ }); + result.builder_fields.push(quote! { #name: #field_type }); result.builder_args.push(quote! { self.#name }); result.builder_inits.push(init); } for param in default_fn_params { let FnParam { name, type_, .. } = param; - let type_ = type_.param_decl(); + let param_type = type_.param_decl(); + let (_, field_needs_conversion) = type_.private_field_decl(); + + let field_init = make_field_init(name, "e! { value }, field_needs_conversion); let method = quote! { #[inline] - pub fn #name(self, value: #type_) -> Self { + pub fn #name(self, value: #param_type) -> Self { // Currently not testing whether the parameter was already set Self { - #name: value, + #field_init, ..self } } @@ -281,3 +284,11 @@ fn make_extender( result } + +fn make_field_init(name: &Ident, expr: &TokenStream, needs_conversion: bool) -> TokenStream { + if needs_conversion { + quote! { #name: #expr.as_object_arg() } + } else { + quote! { #name: #expr } + } +} diff --git a/godot-codegen/src/generator/functions_common.rs b/godot-codegen/src/generator/functions_common.rs index 85fac7263..a052de160 100644 --- a/godot-codegen/src/generator/functions_common.rs +++ b/godot-codegen/src/generator/functions_common.rs @@ -320,8 +320,8 @@ pub(crate) fn make_params_exprs<'a>( // Objects (Gd) use implicit conversions via AsObjectArg. Only use in non-virtual functions. match ¶m.type_ { RustTy::EngineClass { - arg_view, - impl_as_arg, + object_arg: arg_view, + impl_as_object_arg: impl_as_arg, .. } if !is_virtual => { // Parameter declarations in signature: impl AsObjectArg diff --git a/godot-codegen/src/models/domain.rs b/godot-codegen/src/models/domain.rs index 373cfc71f..51918de85 100644 --- a/godot-codegen/src/models/domain.rs +++ b/godot-codegen/src/models/domain.rs @@ -621,10 +621,10 @@ pub enum RustTy { tokens: TokenStream, /// Tokens with `ObjectArg` (used in `type CallSig` tuple types). - arg_view: TokenStream, + object_arg: TokenStream, /// Signature declaration with `impl AsObjectArg`. - impl_as_arg: TokenStream, + impl_as_object_arg: TokenStream, /// only inner `T` #[allow(dead_code)] // only read in minimal config @@ -639,12 +639,20 @@ impl RustTy { pub fn param_decl(&self) -> TokenStream { match self { RustTy::EngineClass { - arg_view: raw_gd, .. - } => raw_gd.clone(), + impl_as_object_arg, .. + } => impl_as_object_arg.clone(), other => other.to_token_stream(), } } + /// Returns `( , )`. + pub fn private_field_decl(&self) -> (TokenStream, bool) { + match self { + RustTy::EngineClass { object_arg, .. } => (object_arg.clone(), true), + other => (other.to_token_stream(), false), + } + } + pub fn return_decl(&self) -> TokenStream { match self { Self::EngineClass { tokens, .. } => quote! { -> Option<#tokens> },