@@ -4,56 +4,72 @@ use leptos::{html::AnyElement, *};
4
4
/// https://github.com/solidjs/solid/blob/main/packages/solid/web/src/index.ts#L56
5
5
#[ component]
6
6
pub fn Teleport (
7
+ #[ prop( default = true . into( ) , into) ] immediate : MaybeSignal < bool > ,
7
8
#[ prop( into, optional) ] mount : Option < web_sys:: Element > ,
8
9
#[ prop( optional, into) ] element : Option < HtmlElement < AnyElement > > ,
9
10
#[ prop( optional) ] children : Option < Children > ,
10
11
) -> impl IntoView {
11
12
cfg_if ! { if #[ cfg( all( target_arch = "wasm32" , any( feature = "csr" , feature = "hydrate" ) ) ) ] {
12
- use leptos:: wasm_bindgen:: JsCast ;
13
- use leptos:: leptos_dom:: Mountable ;
14
- use thaw_utils:: with_hydration_off;
13
+ let mount_fn = StoredValue :: new( None :: <Box <dyn FnOnce ( ) -> ( ) >>) ;
15
14
16
- let mount = mount. unwrap_or_else( || {
17
- document( )
18
- . body( )
19
- . expect( "body element to exist" )
20
- . unchecked_into( )
21
- } ) ;
22
-
23
- if let Some ( element) = element {
24
- let render_root = element;
25
- let _ = mount. append_child( & render_root) ;
26
- on_cleanup( move || {
27
- let _ = mount. remove_child( & render_root) ;
28
- } ) ;
29
- } else if let Some ( children) = children {
30
- let container = document( )
31
- . create_element( "div" )
32
- . expect( "element creation to work" ) ;
33
- with_hydration_off( || {
34
- let _ = container. append_child( & children( ) . into_view( ) . get_mountable_node( ) ) ;
15
+ mount_fn. set_value( Some ( Box :: new( move || {
16
+ let mount = mount. unwrap_or_else( || {
17
+ use leptos:: wasm_bindgen:: JsCast ;
18
+ document( )
19
+ . body( )
20
+ . expect( "body element to exist" )
21
+ . unchecked_into( )
35
22
} ) ;
36
23
37
- let render_root = container;
38
- let _ = mount. append_child( & render_root) ;
39
- on_cleanup( move || {
40
- let _ = mount. remove_child( & render_root) ;
41
- } ) ;
42
- } else {
43
- return ;
44
- } ;
24
+ if let Some ( element) = element {
25
+ let render_root = element;
26
+ let _ = mount. append_child( & render_root) ;
27
+ on_cleanup( move || {
28
+ let _ = mount. remove_child( & render_root) ;
29
+ } ) ;
30
+ } else if let Some ( children) = children {
31
+ let container = document( )
32
+ . create_element( "div" )
33
+ . expect( "element creation to work" ) ;
34
+
35
+ thaw_utils:: with_hydration_off( || {
36
+ use leptos:: leptos_dom:: Mountable ;
37
+ let _ = container. append_child( & children( ) . into_view( ) . get_mountable_node( ) ) ;
38
+ } ) ;
39
+
40
+ let render_root = container;
41
+ let _ = mount. append_child( & render_root) ;
42
+ on_cleanup( move || {
43
+ let _ = mount. remove_child( & render_root) ;
44
+ } ) ;
45
+ }
46
+ } ) ) ) ;
47
+
48
+ let owner = Owner :: current( ) ;
49
+ Effect :: new( move |_| {
50
+ if immediate. get( ) {
51
+ mount_fn. update_value( |mount_fn| {
52
+ if let Some ( f) = mount_fn. take( ) {
53
+ with_owner( owner. unwrap( ) , move || {
54
+ f( ) ;
55
+ } ) ;
56
+ }
57
+ } ) ;
58
+ }
59
+ } ) ;
45
60
} else {
46
61
let _ = mount;
62
+ let _ = immediate;
47
63
#[ cfg( not( feature = "ssr" ) ) ]
48
64
{
49
65
let _ = element;
50
66
let _ = children;
51
67
}
52
68
#[ cfg( feature = "ssr" ) ]
53
69
if element. is_none( ) {
54
- if let Some ( children) = children {
70
+ if let Some ( children) = children {
55
71
// Consumed hydration `id`
56
- let _ = children( ) ;
72
+ let _ = children( ) ;
57
73
}
58
74
}
59
75
} }
0 commit comments