优化导航栏动画

This commit is contained in:
lsy 2025-01-10 21:10:21 +08:00
parent cd67ab3f2e
commit b75433cdbd

View File

@ -1,5 +1,4 @@
use super::Toggle;
use crate::utils::dom::{add_element_class, get_document, remove_element_class};
use crate::Route;
use dioxus::{logger::tracing, prelude::*};
use wasm_bindgen::{prelude::Closure, JsCast};
@ -9,14 +8,15 @@ pub fn Navbar() -> Element {
let mut progress_signal = use_signal(|| 0);
let mut progress_hover = use_signal(|| false);
// 监听滚动事件
use_effect(move || {
let window = web_sys::window().unwrap();
let document = get_document().unwrap();
let document = window.document().unwrap();
let document_element = document.document_element().unwrap();
let closure: Closure<dyn FnMut(_)> = Closure::wrap(Box::new(move |_: web_sys::Event| {
if progress_hover() {
return;
}
let closure: Closure<dyn FnMut(_)> = {
Closure::wrap(Box::new(move |_: web_sys::Event| {
let screen_height = document_element.scroll_height() as f64;
let inner_height = window.inner_height().unwrap().as_f64().unwrap();
let scrool_height = window.scroll_y().unwrap();
@ -28,18 +28,16 @@ pub fn Navbar() -> Element {
0.0
};
let percent = (percent.clamp(0.0, 1.0) * 100.0) as i32;
if percent > 0 {
let _ = remove_element_class("nav .progress", "hidden");
} else {
let _ = add_element_class("nav .progress", "hidden");
}
progress_signal.set(percent);
}) as Box<dyn FnMut(_)>);
}) as Box<dyn FnMut(_)>)
};
document
.add_event_listener_with_callback("scroll", closure.as_ref().unchecked_ref())
.unwrap();
closure.forget();
});
rsx! {
nav {
class: "border-red-500 bg-slate-400 text-xl fixed top-0 left-0 right-0",
@ -75,25 +73,32 @@ pub fn Navbar() -> Element {
width: 30
}
div {
class:"progress bg-accent h-7 p-2 rounded-full text-xs flex items-center justify-center min-w-7 transition-all duration-300 hidden",
onmouseenter:move|_|{
class: "progress bg-accent h-7 rounded-full text-xs flex items-center justify-center transition-all duration-300 overflow-hidden",
style: if progress_signal() > 0 {
format!("opacity: 1; transform: translateX(0); width: {}px;", if progress_signal()==100 { "70" } else { "28" })
} else {
"opacity: 0; transform: translateX(100%); width: 0px".to_string()
},
onmouseenter: move |_| {
progress_hover.set(true);
},
onmouseleave:move|_|{
onmouseleave: move |_| {
progress_hover.set(false);
},
onclick:move|_|{
onclick: move |_| {
progress_hover.set(false);
let window = web_sys::window().unwrap();
window.scroll_to_with_x_and_y(0.0, 0.0);
},
div {
class: "px-2 whitespace-nowrap transition-opacity duration-150",
style: "opacity: 1",
{
if progress_hover(){
if progress_hover() {
"".to_string()
}
else{
if progress_signal()==100{
if progress_signal()==100 {
"返回顶部".to_string()
}
else {
@ -105,6 +110,7 @@ pub fn Navbar() -> Element {
}
}
}
}
div {
class:"w-[80%] mx-auto mt-14",
Outlet::<Route> {}