Skip to main content

dioxus_element_plug/components/
infinite_scroll.rs

1use dioxus::prelude::*;
2
3/// InfiniteScroll props
4#[derive(Props, Clone, PartialEq)]
5pub struct InfiniteScrollProps {
6    #[props(default)]
7    pub children: Element,
8
9    /// Whether there are more items to load
10    #[props(default = false)]
11    pub has_more: bool,
12
13    /// Loading text
14    #[props(default = "Loading...".to_string())]
15    pub loading_text: String,
16
17    /// No more data text
18    #[props(default = "No more".to_string())]
19    pub no_more_text: String,
20
21    /// Distance threshold to trigger load (in px)
22    #[props(default = 0)]
23    pub distance: u32,
24
25    /// Load more event handler
26    #[props(default)]
27    pub on_load: Option<EventHandler<()>>,
28
29    #[props(default)]
30    pub class: Option<String>,
31
32    #[props(default)]
33    pub style: Option<String>,
34}
35
36/// InfiniteScroll component for lazy loading content
37#[component]
38pub fn InfiniteScroll(props: InfiniteScrollProps) -> Element {
39    let mut class_names = vec!["el-infinite-scroll".to_string()];
40    if let Some(ref c) = props.class { class_names.push(c.clone()); }
41
42    rsx! {
43        div {
44            class: "{class_names.join(\" \")}",
45            style: props.style.clone().unwrap_or_default(),
46            {props.children}
47            div {
48                class: "el-infinite-scroll__loading",
49                if props.has_more {
50                    span {
51                        class: "el-infinite-scroll__text",
52                        onclick: move |_| {
53                            if let Some(handler) = props.on_load {
54                                handler.call(());
55                            }
56                        },
57                        "{props.loading_text}"
58                    }
59                } else {
60                    span {
61                        class: "el-infinite-scroll__no-more",
62                        "{props.no_more_text}"
63                    }
64                }
65            }
66        }
67    }
68}