abi_stable/docs/sabi_trait_inherent.rs
1/*!
2Shared docs for inherent items of `sabi_trait` trait objects.
3
4`<trait>` here is a generic way to refer to the name of "a trait that's
5annotated with the [`sabi_trait`] attribute macro".
6
7[The trait used in method examples
8](../../sabi_trait/doc_examples/trait.Action.html):
9```rust
10#[abi_stable::sabi_trait]
11pub trait Action: Debug {
12 /// Gets the current value of `self`.
13 fn get(&self) -> usize;
14
15 /// Adds `val` into `self`, returning the new value.
16 fn add_mut(&mut self, val: usize) -> usize;
17
18 /// Adds `val` into `self`, returning the new value.
19 #[sabi(last_prefix_field)]
20 fn add_into(self, val: usize) -> usize;
21}
22# fn main(){}
23```
24
25
26# Methods
27
28These are the common methods for the `<trait>_TO` ffi-safe trait object type
29generated by the [`sabi_trait`] attribute.
30
31-[`from_ptr`](#from_ptr-method)
32
33-[`from_value`](#from_value-method)
34
35-[`from_const`](#from_const-method)
36
37-[`from_sabi`](#from_sabi-method)
38
39-[`sabi_reborrow_mut`](#sabi_reborrow_mut-method)
40
41-[`sabi_reborrow`](#sabi_reborrow-method)
42
43
44
45
46## `from_ptr` method
47
48```text
49impl<'lt, ErasedPtr, …> Trait_TO<'lt, ErasedPtr, …> {
50 pub fn from_ptr<Ptr, Downcasting>(
51 pointer: Ptr,
52 can_it_downcast: Downcasting
53 ) -> Self
54```
55
56Constructs `<trait>_TO` from a pointer to a type that implements `<trait>`
57
58The `can_it_downcast` parameter describes whether the trait object can be
59converted back into the original type or not.<br>
60Its possible values are [`TD_CanDowncast`] and [`TD_Opaque`].
61
62[Method docs for `Action_TO::from_ptr`
63](../../sabi_trait/doc_examples/struct.Action_TO.html#method.from_ptr)
64
65**Example**:
66```rust
67use abi_stable::{
68 sabi_trait::doc_examples::Action_TO,
69 std_types::{RArc, RBox},
70 type_level::downcasting::TD_CanDowncast,
71 RMut, RRef,
72};
73
74// From an RBox
75{
76 // The type annotation is purely for the reader.
77 let mut object: Action_TO<'static, RBox<()>> =
78 Action_TO::from_ptr(RBox::new(10_usize), TD_CanDowncast);
79
80 assert_eq!(object.get(), 10);
81
82 assert_eq!(object.add_mut(3), 13);
83 assert_eq!(object.get(), 13);
84
85 // consumes `object`, now it can't be used anymore.
86 assert_eq!(object.add_into(7), 20);
87}
88
89// From a reference
90{
91 // `Action_TO`s constructed from `&` are `Action_TO<'_, RRef<'_, ()>>`
92 // since `&T` can't soundly be transmuted back and forth into `&()`
93 let object: Action_TO<'static, RRef<'static, ()>> =
94 Action_TO::from_ptr(&20_usize, TD_CanDowncast);
95
96 assert_eq!(object.get(), 20);
97}
98
99// From a mutable reference
100{
101 let mut val = 30_usize;
102
103 // `Action_TO`s constructed from `&mut` are `Action_TO<'_, RMut<'_, ()>>`
104 // since `&mut T` can't soundly be transmuted back and forth into `&mut ()`
105 let mut object: Action_TO<'static, RMut<'_, ()>> =
106 Action_TO::from_ptr(&mut val, TD_CanDowncast);
107
108 assert_eq!(object.get(), 30);
109
110 assert_eq!(object.add_mut(3), 33);
111 assert_eq!(object.get(), 33);
112
113 drop(object);
114
115 assert_eq!(val, 33);
116}
117
118// From an RArc
119{
120 let object: Action_TO<'static, RArc<()>> =
121 Action_TO::from_ptr(RArc::new(40), TD_CanDowncast);
122
123 assert_eq!(object.get(), 40);
124}
125
126```
127
128## `from_value` method
129
130```text
131impl<'lt, …> Trait_TO<'lt, RBox<()>, …> {
132 pub fn from_value<_OrigPtr, Downcasting>(
133 pointer: _OrigPtr,
134 can_it_downcast: Downcasting
135 ) -> Self
136```
137
138Constructs `<trait>_TO` from a type that implements `<trait>`,
139wrapping that value in an [`RBox`].
140
141The `can_it_downcast` parameter describes whether the trait object can be
142converted back into the original type or not.<br>
143Its possible values are [`TD_CanDowncast`] and [`TD_Opaque`].
144
145[Method docs for `Action_TO::from_value`
146](../../sabi_trait/doc_examples/struct.Action_TO.html#method.from_value)
147
148**Example**:
149```rust
150use abi_stable::{
151 sabi_trait::doc_examples::Action_TO, std_types::RBox,
152 type_level::downcasting::TD_CanDowncast,
153};
154
155// The type annotation is purely for the reader.
156let mut object: Action_TO<'static, RBox<()>> =
157 Action_TO::from_value(100_usize, TD_CanDowncast);
158
159assert_eq!(object.get(), 100);
160
161assert_eq!(object.add_mut(3), 103);
162assert_eq!(object.get(), 103);
163
164// consumes `object`, now it can't be used anymore.
165assert_eq!(object.add_into(7), 110);
166
167```
168
169
170## `from_const` method
171
172```text
173impl<'lt, 'sub, …> Trait_TO<'lt, RRef<'sub, ()>, …> {
174 pub const fn from_const<T, Downcasting>(
175 pointer: &'sub T,
176 can_it_downcast: Downcasting,
177 ) -> Self
178```
179
180Const-constructs `<trait>_TO` from a constant that
181implements `<trait>`,
182
183The `can_it_downcast` parameter describes whether the trait object can be
184converted back into the original type or not.<br>
185Its possible values are [`TD_CanDowncast`] and [`TD_Opaque`].
186
187[Method docs for `Action_TO::from_const`
188](../../sabi_trait/doc_examples/struct.Action_TO.html#method.from_const)
189
190**Example:**
191```rust
192use abi_stable::{
193 sabi_trait::doc_examples::Action_trait::{Action_CTO, Action_TO},
194 std_types::RBox,
195 type_level::downcasting::TD_CanDowncast,
196};
197
198const TO: Action_CTO<'_, '_> = Action_TO::from_const(&200, TD_CanDowncast);
199
200assert_eq!(TO.get(), 200);
201
202```
203
204
205## `from_sabi` method
206
207```text
208impl<'lt, ErasedPtr, …> Trait_TO<'lt, ErasedPtr, …> {
209 pub fn from_sabi(obj: Trait_Backend<'lt, ErasedPtr, …>) -> Self
210```
211
212Constructs `<trait>_TO` from the backend trait object type,
213either [`RObject`] or [`DynTrait`].
214
215[Method docs for `Action_TO::from_sabi`
216](../../sabi_trait/doc_examples/struct.Action_TO.html#method.from_sabi)
217
218This allows calling methods on the `.obj` field of `<trait>_TO`
219that consume the backend and return it back.
220
221For [`Action_TO`] specifically, [`RObject`] is the backend.
222
223**Example:**
224```rust
225use abi_stable::{
226 pointer_trait::{CanTransmuteElement, OwnedPointer},
227 sabi_trait::{
228 doc_examples::Action_trait::{Action_Interface, Action_TO},
229 RObject,
230 },
231 std_types::RBox,
232 type_level::downcasting::TD_CanDowncast,
233};
234
235let mut object: Action_TO<'static, RBox<()>> =
236 Action_TO::from_value(700, TD_CanDowncast);
237
238object = try_downcast::<_, u32>(object).unwrap_err();
239
240object = try_downcast::<_, String>(object).unwrap_err();
241
242assert_eq!(*try_downcast::<_, usize>(object).unwrap(), 700);
243
244fn try_downcast<P, T>(
245 object: Action_TO<'static, P>,
246) -> Result<P::TransmutedPtr, Action_TO<'static, P>>
247where
248 T: 'static,
249 // This bound is required to call `downcast_into` on the `obj: RObject<…>` field
250 P: OwnedPointer<PtrTarget = ()> + CanTransmuteElement<T>,
251{
252 object
253 .obj
254 .downcast_into()
255 .map_err(|e| Action_TO::from_sabi(e.into_inner()))
256}
257
258```
259
260## `sabi_reborrow` method
261
262```text
263impl<'lt, ErasedPtr, …> Trait_TO<'lt, ErasedPtr, …> {
264 pub fn sabi_reborrow<'r>(&'r self) -> Trait_TO<'lt, RRef<'r, ()>, …> {
265```
266
267Reborrows a `&'r <trait>_TO<'lt, …>` into a `<trait>_TO<'lt, RRef<'r, ()>, …>`.
268
269[Method docs for `Action_TO::sabi_reborrow`
270](../../sabi_trait/doc_examples/struct.Action_TO.html#method.sabi_reborrow)
271
272This allows passing the trait object to functions that take a
273`<trait>_TO<'b, RRef<'a, ()>, …>`,
274and functions generic over the traits that `<trait>_TO` implements.
275
276This method is only available for traits that either:
277- require neither Send nor Sync,
278- require `Send + Sync`.
279
280**Example**:
281```rust
282use abi_stable::{
283 sabi_trait::doc_examples::Action_TO, std_types::RBox,
284 type_level::downcasting::TD_CanDowncast, RRef,
285};
286
287let mut object: Action_TO<'static, RBox<()>> =
288 Action_TO::from_value(300_usize, TD_CanDowncast);
289
290assert_eq!(to_debug_string(object.sabi_reborrow()), "300");
291
292assert_eq!(object.add_mut(7), 307);
293assert_eq!(get_usize(object.sabi_reborrow()), 307);
294
295assert_eq!(object.add_mut(14), 321);
296// last use of `object`, so we can move it into the function
297assert_eq!(to_debug_string(object), "321");
298
299fn to_debug_string<T>(x: T) -> String
300where
301 T: std::fmt::Debug,
302{
303 format!("{:?}", x)
304}
305
306fn get_usize(x: Action_TO<'_, RRef<'_, ()>>) -> usize {
307 x.get()
308}
309
310```
311
312## `sabi_reborrow_mut` method
313
314```text
315impl<'lt, ErasedPtr, …> Trait_TO<'lt, ErasedPtr, …> {
316 pub fn sabi_reborrow_mut<'r>(&'r mut self) -> Trait_TO<'lt, RMut<'r, ()>, …> {
317```
318
319Reborrows a `&'r mut <trait>_TO<'b, …>` into a `<trait>_TO<'b, RMut<'r, ()>, …>`.
320
321[Method docs for `Action_TO::sabi_reborrow_mut`
322](../../sabi_trait/doc_examples/struct.Action_TO.html#method.sabi_reborrow_mut)
323
324This allows passing the trait object to functions that take a
325`<trait>_TO<'b, RMut<'a, ()>, …>`,
326and functions generic over the traits that `<trait>_TO` implements.
327
328This method is only available for traits that either:
329- require neither Send nor Sync,
330- require `Send + Sync`.
331
332**Example**:
333```rust
334use abi_stable::{
335 pointer_trait::AsMutPtr, sabi_trait::doc_examples::Action_TO, std_types::RBox,
336 type_level::downcasting::TD_CanDowncast,
337};
338
339let mut object: Action_TO<'static, RBox<()>> =
340 Action_TO::from_value(400_usize, TD_CanDowncast);
341
342assert_eq!(add_mut(object.sabi_reborrow_mut(), 6), 406);
343
344assert_eq!(add_mut(object.sabi_reborrow_mut(), 10), 416);
345
346// last use of `object`, so we can move it into the function
347assert_eq!(add_mut(object, 20), 436);
348
349fn add_mut<P>(mut x: Action_TO<'_, P>, how_much: usize) -> usize
350where
351 // Needed for calling mutable methods on `Action_TO`
352 P: AsMutPtr<PtrTarget = ()>,
353{
354 x.add_mut(how_much)
355}
356
357```
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373[`sabi_trait`]: ../../attr.sabi_trait.html
374
375[`RObject`]: ../../sabi_trait/struct.RObject.html
376
377[`DynTrait`]: ../../struct.DynTrait.html
378
379[`RBox`]: ../../std_types/struct.RBox.html
380
381[`Action_TO`]: ../../sabi_trait/doc_examples/struct.Action_TO.html
382
383[`TD_CanDowncast`]: ../../type_level/downcasting/struct.TD_CanDowncast.html
384
385[`TD_Opaque`]: ../../type_level/downcasting/struct.TD_Opaque.html
386
387*/