11//! Functionality for declaring Objective-C classes.
22//!
3- //! Classes can be declared using the [`ClassDecl `] struct. Instance variables
3+ //! Classes can be declared using the [`ClassBuilder `] struct. Instance variables
44//! and methods can then be added before the class is ultimately registered.
55//!
66//! # Example
1111//!
1212//! ```no_run
1313//! use objc2::{class, sel};
14- //! use objc2::declare::ClassDecl ;
14+ //! use objc2::declare::ClassBuilder ;
1515//! use objc2::runtime::{Class, Object, Sel};
1616//!
1717//! let superclass = class!(NSObject);
18- //! let mut decl = ClassDecl ::new("MyNumber", superclass).unwrap();
18+ //! let mut decl = ClassBuilder ::new("MyNumber", superclass).unwrap();
1919//!
2020//! // Add an instance variable
2121//! decl.add_ivar::<u32>("_number");
@@ -78,6 +78,10 @@ macro_rules! method_decl_impl {
7878 ( $( $t: ident) ,* ) => (
7979 method_decl_impl!( -T , R , extern "C" fn ( & T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
8080 method_decl_impl!( -T , R , extern "C" fn ( & mut T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
81+ method_decl_impl!( -T , R , unsafe extern "C" fn ( * const T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
82+ method_decl_impl!( -T , R , unsafe extern "C" fn ( * mut T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
83+ method_decl_impl!( -T , R , unsafe extern "C" fn ( & T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
84+ method_decl_impl!( -T , R , unsafe extern "C" fn ( & mut T , Sel $( , $t) * ) -> R , $( $t) ,* ) ;
8185 ) ;
8286}
8387
@@ -120,10 +124,14 @@ fn log2_align_of<T>() -> u8 {
120124/// A type for declaring a new class and adding new methods and ivars to it
121125/// before registering it.
122126#[ derive( Debug ) ]
123- pub struct ClassDecl {
127+ pub struct ClassBuilder {
124128 cls : NonNull < Class > ,
125129}
126130
131+ #[ doc( hidden) ]
132+ #[ deprecated = "Use `ClassBuilder` instead." ]
133+ pub type ClassDecl = ClassBuilder ;
134+
127135// SAFETY: The stuff that touch global state does so using locks internally.
128136//
129137// Modifying the class itself can only be done through `&mut`, so Sync is
@@ -134,11 +142,11 @@ pub struct ClassDecl {
134142// when doing so...).
135143//
136144// Finally, there are no requirements that the class must be registered on the
137- // same thread that allocated it.
138- unsafe impl Send for ClassDecl { }
139- unsafe impl Sync for ClassDecl { }
145+ // same thread that allocated it (so Send is safe) .
146+ unsafe impl Send for ClassBuilder { }
147+ unsafe impl Sync for ClassBuilder { }
140148
141- impl ClassDecl {
149+ impl ClassBuilder {
142150 fn as_ptr ( & self ) -> * mut ffi:: objc_class {
143151 self . cls . as_ptr ( ) . cast ( )
144152 }
@@ -150,16 +158,16 @@ impl ClassDecl {
150158 NonNull :: new ( cls. cast ( ) ) . map ( |cls| Self { cls } )
151159 }
152160
153- /// Constructs a [`ClassDecl `] with the given name and superclass.
161+ /// Constructs a [`ClassBuilder `] with the given name and superclass.
154162 ///
155163 /// Returns [`None`] if the class couldn't be allocated, or a class with
156164 /// that name already exist.
157165 pub fn new ( name : & str , superclass : & Class ) -> Option < Self > {
158166 Self :: with_superclass ( name, Some ( superclass) )
159167 }
160168
161- /// Constructs a [`ClassDecl `] declaring a new root class with the given
162- /// name.
169+ /// Constructs a [`ClassBuilder `] declaring a new root class with the
170+ /// given name.
163171 ///
164172 /// Returns [`None`] if the class couldn't be allocated.
165173 ///
@@ -173,11 +181,10 @@ impl ClassDecl {
173181 /// Functionality it expects, like implementations of `-retain` and
174182 /// `-release` used by ARC, will not be present otherwise.
175183 pub fn root ( name : & str , intitialize_fn : extern "C" fn ( & Class , Sel ) ) -> Option < Self > {
176- let mut decl = Self :: with_superclass ( name, None ) ;
177- if let Some ( ref mut decl) = decl {
178- unsafe { decl. add_class_method ( sel ! ( initialize) , intitialize_fn) } ;
179- }
180- decl
184+ Self :: with_superclass ( name, None ) . map ( |mut this| {
185+ unsafe { this. add_class_method ( sel ! ( initialize) , intitialize_fn) } ;
186+ this
187+ } )
181188 }
182189
183190 /// Adds a method with the given name and implementation.
@@ -191,9 +198,10 @@ impl ClassDecl {
191198 ///
192199 /// The caller must ensure that the types match those that are expected
193200 /// when the method is invoked from Objective-C.
194- pub unsafe fn add_method < F > ( & mut self , sel : Sel , func : F )
201+ pub unsafe fn add_method < T , F > ( & mut self , sel : Sel , func : F )
195202 where
196- F : MethodImplementation < Callee = Object > ,
203+ T : Message + ?Sized , // TODO: Disallow `Class`
204+ F : MethodImplementation < Callee = T > ,
197205 {
198206 let encs = F :: Args :: ENCODINGS ;
199207 let sel_args = count_args ( sel) ;
@@ -290,8 +298,8 @@ impl ClassDecl {
290298
291299 // fn add_property(&self, name: &str, attributes: &[ffi::objc_property_attribute_t]);
292300
293- /// Registers the [`ClassDecl `], consuming it, and returns a reference to
294- /// the newly registered [`Class`].
301+ /// Registers the [`ClassBuilder `], consuming it, and returns a reference
302+ /// to the newly registered [`Class`].
295303 pub fn register ( self ) -> & ' static Class {
296304 // Forget self, otherwise the class will be disposed in drop
297305 let cls = ManuallyDrop :: new ( self ) . cls ;
@@ -300,7 +308,7 @@ impl ClassDecl {
300308 }
301309}
302310
303- impl Drop for ClassDecl {
311+ impl Drop for ClassBuilder {
304312 fn drop ( & mut self ) {
305313 unsafe { ffi:: objc_disposeClassPair ( self . as_ptr ( ) ) }
306314 }
@@ -309,20 +317,24 @@ impl Drop for ClassDecl {
309317/// A type for declaring a new protocol and adding new methods to it
310318/// before registering it.
311319#[ derive( Debug ) ]
312- pub struct ProtocolDecl {
320+ pub struct ProtocolBuilder {
313321 proto : NonNull < Protocol > ,
314322}
315323
316- // SAFETY: Similar to ClassDecl
317- unsafe impl Send for ProtocolDecl { }
318- unsafe impl Sync for ProtocolDecl { }
324+ #[ doc( hidden) ]
325+ #[ deprecated = "Use `ProtocolBuilder` instead." ]
326+ pub type ProtocolDecl = ProtocolBuilder ;
327+
328+ // SAFETY: Similar to ClassBuilder
329+ unsafe impl Send for ProtocolBuilder { }
330+ unsafe impl Sync for ProtocolBuilder { }
319331
320- impl ProtocolDecl {
332+ impl ProtocolBuilder {
321333 fn as_ptr ( & self ) -> * mut ffi:: objc_protocol {
322334 self . proto . as_ptr ( ) . cast ( )
323335 }
324336
325- /// Constructs a [`ProtocolDecl `] with the given name.
337+ /// Constructs a [`ProtocolBuilder `] with the given name.
326338 ///
327339 /// Returns [`None`] if the protocol couldn't be allocated.
328340 pub fn new ( name : & str ) -> Option < Self > {
@@ -386,7 +398,7 @@ impl ProtocolDecl {
386398 }
387399 }
388400
389- /// Registers the [`ProtocolDecl `], consuming it and returning a reference
401+ /// Registers the [`ProtocolBuilder `], consuming it and returning a reference
390402 /// to the newly registered [`Protocol`].
391403 pub fn register ( self ) -> & ' static Protocol {
392404 unsafe {
0 commit comments