mirror of
https://github.com/DerTyp7/dertyp7.github.io.git
synced 2025-10-29 21:02:09 +01:00
Add ScrollToTop component and skills section
This commit is contained in:
@@ -1,6 +1,7 @@
|
|||||||
import "@styles/App.scss";
|
import "@styles/App.scss";
|
||||||
import Header from "@components/Header";
|
import Header from "@components/Header";
|
||||||
import About from "@components/About";
|
import About from "@components/About";
|
||||||
|
import ScrollToTop from "@components/ScrollToTop";
|
||||||
|
|
||||||
export default function App() {
|
export default function App() {
|
||||||
return (
|
return (
|
||||||
@@ -10,6 +11,14 @@ export default function App() {
|
|||||||
</div>
|
</div>
|
||||||
<Header />
|
<Header />
|
||||||
<About />
|
<About />
|
||||||
|
<About />
|
||||||
|
<div id="skills">
|
||||||
|
<h2>
|
||||||
|
<a href="#skills">Skills</a>
|
||||||
|
</h2>
|
||||||
|
{/* Add your skills content here */}
|
||||||
|
</div>
|
||||||
|
<ScrollToTop />
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
56
src/components/ScrollToTop.tsx
Normal file
56
src/components/ScrollToTop.tsx
Normal file
@@ -0,0 +1,56 @@
|
|||||||
|
import { useState, useEffect } from "react";
|
||||||
|
import "@styles/ScrollToTop.scss";
|
||||||
|
|
||||||
|
export default function ScrollToTop() {
|
||||||
|
const [isScrolledUp, setIsScrolledUp] = useState(false);
|
||||||
|
|
||||||
|
const toggleVisibilityAndDirection = () => {
|
||||||
|
if (window.scrollY < 150) {
|
||||||
|
setIsScrolledUp(false);
|
||||||
|
} else {
|
||||||
|
setIsScrolledUp(window.scrollY === 0 ? false : true);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const scrollTo = () => {
|
||||||
|
if (isScrolledUp) {
|
||||||
|
window.scrollTo({
|
||||||
|
top: 0,
|
||||||
|
behavior: "smooth",
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
const skillsElement = document.getElementById("skills");
|
||||||
|
if (skillsElement) {
|
||||||
|
skillsElement.scrollIntoView({ behavior: "smooth" });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
window.addEventListener("scroll", toggleVisibilityAndDirection);
|
||||||
|
return () =>
|
||||||
|
window.removeEventListener("scroll", toggleVisibilityAndDirection);
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="scrollToTop">
|
||||||
|
<div onClick={scrollTo}>
|
||||||
|
<svg
|
||||||
|
className={`arrow ${isScrolledUp ? "up" : "down"}`}
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
width="24"
|
||||||
|
height="24"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
fill="none"
|
||||||
|
stroke="currentColor"
|
||||||
|
strokeWidth="2"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
>
|
||||||
|
<line x1="12" y1="19" x2="12" y2="5"></line>
|
||||||
|
<polyline points="5 12 12 5 19 12"></polyline>
|
||||||
|
</svg>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
36
src/styles/ScrollToTop.scss
Normal file
36
src/styles/ScrollToTop.scss
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
// src/styles/ScrollToTop.scss
|
||||||
|
.scrollToTop {
|
||||||
|
position: fixed;
|
||||||
|
bottom: 20px;
|
||||||
|
right: 20px;
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
.arrow {
|
||||||
|
transition: transform 200ms ease-in-out;
|
||||||
|
|
||||||
|
&.up {
|
||||||
|
transform: rotate(0deg);
|
||||||
|
}
|
||||||
|
|
||||||
|
&.down {
|
||||||
|
transform: rotate(-180deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
animation: pulse 1s infinite;
|
||||||
|
color: var(--color-accent);
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes pulse {
|
||||||
|
0% {
|
||||||
|
transform: scale(1);
|
||||||
|
}
|
||||||
|
50% {
|
||||||
|
transform: scale(1.4);
|
||||||
|
}
|
||||||
|
100% {
|
||||||
|
transform: scale(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user