feat: loading icon on button

This commit is contained in:
Huh Hyeongjun 2025-02-25 18:24:20 +09:00
parent 96e41161b4
commit e1bd5868ed
2 changed files with 125 additions and 66 deletions

View File

@ -1,5 +1,6 @@
import { useAreaStore } from "@/state/areaStore";
import { css } from "@emotion/react";
import { css, keyframes } from "@emotion/react";
import { Loader2 } from "lucide-react";
import React, { useState } from "react";
interface Building {
@ -8,11 +9,20 @@ interface Building {
geometry?: { lat: number; lng: number }[];
}
const spinAnimation = keyframes`
from { transform: rotate(0deg); }
to { transform: rotate(360deg); }
`;
export function BuildingHeights({ area }: { area: any }) {
const [buildings, setBuildings] = useState<Building[]>([]);
const [loading, setLoading] = useState(false);
const appendAreas = useAreaStore((state) => state.appendAreas);
const requestBuildings = () => {
setLoading(true);
const south = area[1].lat;
const west = area[1].lng;
const north = area[0].lat;
@ -40,6 +50,9 @@ export function BuildingHeights({ area }: { area: any }) {
})
.catch((error) => {
console.error("Error fetching building data:", error);
})
.finally(() => {
setLoading(false);
});
};
@ -70,6 +83,14 @@ export function BuildingHeights({ area }: { area: any }) {
})}
onClick={requestBuildings}
>
{loading && (
<Loader2
css={css({
animation: `${spinAnimation} 1s linear infinite`,
})}
size={16}
/>
)}
request
</button>
<ul

View File

@ -1,5 +1,10 @@
import { useCarStore } from "@/state/carStore";
import { css } from "@emotion/react";
import { DetailedHTMLProps, ButtonHTMLAttributes, useState } from "react";
import { Modal } from "../modal/Modal";
import { Column } from "../flex/Column";
import { Title } from "../text/Title";
import { Description } from "../text/Description";
const TOP_PANEL_HEIGHT = "3rem";
const BORDER_COLOR = "#ededf290";
@ -7,86 +12,119 @@ const BORDER_COLOR = "#ededf290";
const breakpoints = [768];
const mq = breakpoints.map((bp) => `@media (max-width: ${bp}px)`);
interface ButtonProps
extends DetailedHTMLProps<
ButtonHTMLAttributes<HTMLButtonElement>,
HTMLButtonElement
> {
isShow?: boolean;
}
export function TopNav({ step }: { step: number }) {
const setThirdMode = useCarStore((state) => state.setThirdMode);
const [openModal, setOpenModal] = useState(false);
return (
<div
css={css({
display: "flex",
transition: ".5s",
transform: "translate(0px, 0px)",
position: "fixed",
top: 0,
left: 0,
width: "100%",
height: TOP_PANEL_HEIGHT,
backgroundColor: "#ffffff50",
backdropFilter: "blur(12px)",
borderBottom: `1px solid ${BORDER_COLOR}`,
zIndex: 9999,
justifyContent: "space-between",
alignItems: "center",
})}
>
<>
<div
css={css({
paddingLeft: "2rem",
alignItems: "center",
flexDirection: "row",
display: "flex",
gap: "0.75rem",
transition: ".5s",
transform: "translate(0px, 0px)",
position: "fixed",
top: 0,
left: 0,
width: "100%",
height: TOP_PANEL_HEIGHT,
backgroundColor: "#ffffff50",
backdropFilter: "blur(12px)",
borderBottom: `1px solid ${BORDER_COLOR}`,
zIndex: 9999,
justifyContent: "space-between",
alignItems: "center",
})}
>
<span
<div
css={css({
fontSize: "14px",
fontWeight: "600",
color: "#5b5d63",
paddingLeft: "2rem",
alignItems: "center",
flexDirection: "row",
display: "flex",
gap: "0.75rem",
})}
>
🗺 Map3d
</span>
</div>
<span
css={css({
fontSize: "14px",
fontWeight: "600",
color: "#5b5d63",
})}
>
🗺 Map3d
</span>
</div>
<div
css={css({
padding: "0rem 0rem",
[mq[0]]: {
display: "none",
},
})}
></div>
<div
css={css({
padding: "0rem 0rem",
[mq[0]]: {
display: "none",
},
})}
></div>
<div
css={css({
paddingRight: "1rem",
display: "flex",
flexDirection: "row",
gap: "0.5rem",
[mq[0]]: {
display: "none",
},
})}
>
<button
style={{
display: step == 2 ? "" : "none",
color: "#000000",
backgroundColor: "#ffffff96",
backdropFilter: "blur(8px)",
border: "none",
padding: "0.5rem 1rem",
borderRadius: "8px",
fontWeight: "300",
fontSize: "12px",
outline: "rgba(240, 240, 244, 0.51) solid 0.1rem",
}}
onClick={() => setThirdMode(true)}
<div
css={css({
paddingRight: "2rem",
display: "flex",
flexDirection: "row",
gap: "0.5rem",
})}
>
Car Mode
</button>
<NavButton
isShow={true}
onClick={() => window.open("https://github.com/cartesiancs/map3d")}
>
GitHub
</NavButton>
<NavButton isShow={step >= 1} onClick={() => setOpenModal(true)}>
Options
</NavButton>
<NavButton isShow={step == 2} onClick={() => setThirdMode(true)}>
Car Mode
</NavButton>
</div>
</div>
</div>
<Modal isOpen={openModal} onClose={() => setOpenModal(false)}>
<Column gap="0.5rem">
<Title>Options </Title>
</Column>
</Modal>
</>
);
}
export function NavButton(props: ButtonProps) {
return (
<button
css={css({
color: "#000000",
backgroundColor: "#ffffff96",
backdropFilter: "blur(8px)",
border: "none",
padding: "0.5rem 1rem",
borderRadius: "8px",
fontWeight: "300",
fontSize: "12px",
outline: "rgba(240, 240, 244, 0.51) solid 0.1rem",
display: props.isShow ? "" : "none",
cursor: "pointer",
})}
{...props}
>
{props.children}
</button>
);
}