frontend: add Loading
This commit is contained in:
parent
98e5ef06c0
commit
cf9b0d53c1
@ -5,6 +5,7 @@ import Hosting from './components/Hosting';
|
|||||||
import InitialSetup from './components/InitialSetup';
|
import InitialSetup from './components/InitialSetup';
|
||||||
import Program from './components/Program';
|
import Program from './components/Program';
|
||||||
import Snowflakes from './components/Snowflakes';
|
import Snowflakes from './components/Snowflakes';
|
||||||
|
import { FullScreenLoading } from './components/Loading';
|
||||||
|
|
||||||
function App() {
|
function App() {
|
||||||
const [isNavOpen, setIsNavOpen] = useState(false);
|
const [isNavOpen, setIsNavOpen] = useState(false);
|
||||||
@ -15,6 +16,7 @@ function App() {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
|
<FullScreenLoading/>
|
||||||
<Snowflakes />
|
<Snowflakes />
|
||||||
<InitialSetup />
|
<InitialSetup />
|
||||||
|
|
||||||
|
|||||||
@ -4,6 +4,7 @@ import { GUESTS } from '../constants/constants';
|
|||||||
import useFetchUser from '../utils/fetchUser'; // Import your custom hook
|
import useFetchUser from '../utils/fetchUser'; // Import your custom hook
|
||||||
import { useNotification } from '../NotificationContext';
|
import { useNotification } from '../NotificationContext';
|
||||||
import ApologyMessage from './Attendance';
|
import ApologyMessage from './Attendance';
|
||||||
|
import {Loading} from './Loading';
|
||||||
|
|
||||||
const InitialSetup = () => {
|
const InitialSetup = () => {
|
||||||
const [cookie, setCookie] = useCookies();
|
const [cookie, setCookie] = useCookies();
|
||||||
@ -14,7 +15,7 @@ const InitialSetup = () => {
|
|||||||
const [isPasswordSet, setIsPasswordSet] = useState(false); // To track if password is set
|
const [isPasswordSet, setIsPasswordSet] = useState(false); // To track if password is set
|
||||||
const [userAttendance, setUserAttendance] = useState<boolean | null>(null);
|
const [userAttendance, setUserAttendance] = useState<boolean | null>(null);
|
||||||
|
|
||||||
const { userSet, passwordCreate, signUser, validToken, getAttendance } = useFetchUser(); // Destructure functions from the hook
|
const { userSet, passwordCreate, signUser, validToken, getAttendance, isLoading } = useFetchUser(); // Destructure functions from the hook
|
||||||
const notify = useNotification();
|
const notify = useNotification();
|
||||||
|
|
||||||
const checkUserPassword = async (name: string) => {
|
const checkUserPassword = async (name: string) => {
|
||||||
@ -76,6 +77,14 @@ const InitialSetup = () => {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (isLoading) {
|
||||||
|
return (
|
||||||
|
<div style={styles.container}>
|
||||||
|
<Loading/>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div style={styles.container}>
|
<div style={styles.container}>
|
||||||
<h2 style={styles.title}>Выбери себя</h2>
|
<h2 style={styles.title}>Выбери себя</h2>
|
||||||
|
|||||||
29
frontend/src/components/Loading.css
Normal file
29
frontend/src/components/Loading.css
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
.spinner {
|
||||||
|
font-size: 100px; /* Adjust size as needed */
|
||||||
|
animation: spin 2s linear infinite; /* Spin animation */
|
||||||
|
position: fixed; /* Keep the snowflake in a fixed position */
|
||||||
|
top: 50%; /* Adjust vertical position */
|
||||||
|
left: 50%; /* Center horizontally */
|
||||||
|
transform: translateX(-50%); /* Center the snowflake */
|
||||||
|
z-index: 10000; /* Ensure it's above the full-screen loading */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Keyframes for spinning */
|
||||||
|
@keyframes spin {
|
||||||
|
0% { transform: translateX(-50%) rotate(0deg); }
|
||||||
|
100% { transform: translateX(-50%) rotate(360deg); }
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
.full-screen {
|
||||||
|
display: flex; /* Use flexbox for centering */
|
||||||
|
align-items: center; /* Center vertically */
|
||||||
|
justify-content: center; /* Center horizontally */
|
||||||
|
height: 100vh; /* Full viewport height */
|
||||||
|
width: 100vw; /* Full viewport width */
|
||||||
|
background-color: rgba(4, 0, 0); /* Semi-transparent background */
|
||||||
|
position: fixed; /* Fix it in the viewport */
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
z-index: 9999; /* Ensure it's above other content */
|
||||||
|
}
|
||||||
34
frontend/src/components/Loading.tsx
Normal file
34
frontend/src/components/Loading.tsx
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
import React, { useEffect, useState } from 'react';
|
||||||
|
import './Loading.css'; // Import CSS for styling
|
||||||
|
|
||||||
|
export const Loading: React.FC = () => {
|
||||||
|
return (
|
||||||
|
<div className="spinner">
|
||||||
|
🎅🏻
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export const FullScreenLoading: React.FC = () => {
|
||||||
|
const [isLoading, setIsLoading] = useState(true);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
// Set a timeout to change the loading state
|
||||||
|
const timer = setTimeout(() => {
|
||||||
|
setIsLoading(false);
|
||||||
|
}, 1000); // 1000 ms = 1 second
|
||||||
|
|
||||||
|
// Cleanup function to clear the timeout if the component unmounts
|
||||||
|
return () => clearTimeout(timer);
|
||||||
|
}, []); // Empty dependency array means it runs once on mount
|
||||||
|
|
||||||
|
if (!isLoading) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="full-screen">
|
||||||
|
<Loading />
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
@ -6,7 +6,7 @@
|
|||||||
height: 100%;
|
height: 100%;
|
||||||
pointer-events: none; /* Make snowflakes non-interactive */
|
pointer-events: none; /* Make snowflakes non-interactive */
|
||||||
overflow: hidden; /* Hide overflow */
|
overflow: hidden; /* Hide overflow */
|
||||||
z-index: 1000; /* Ensure snowflakes are above other content */
|
z-index: 998; /* Ensure snowflakes are above other content */
|
||||||
}
|
}
|
||||||
|
|
||||||
.snowflake {
|
.snowflake {
|
||||||
|
|||||||
@ -1,14 +1,18 @@
|
|||||||
import { useCookies } from 'react-cookie';
|
import { useCookies } from 'react-cookie';
|
||||||
import { API_URL } from '../constants/constants';
|
import { API_URL } from '../constants/constants';
|
||||||
import { hashPassword } from './hashPassword';
|
import { hashPassword } from './hashPassword';
|
||||||
|
import { useState } from 'react';
|
||||||
|
|
||||||
const useFetchUser = () => {
|
const useFetchUser = () => {
|
||||||
|
const [isLoading, setIsLoading] = useState(false)
|
||||||
const [apiCookie, setApiCookie] = useCookies(['apiToken']);
|
const [apiCookie, setApiCookie] = useCookies(['apiToken']);
|
||||||
const [, setUserNameCookie] = useCookies(['userName'])
|
const [, setUserNameCookie] = useCookies(['userName'])
|
||||||
|
|
||||||
const userSet = async (userName: string): Promise<boolean> => {
|
const userSet = async (userName: string): Promise<boolean> => {
|
||||||
try {
|
try {
|
||||||
|
setIsLoading(true)
|
||||||
const response = await fetch(`${API_URL}/users/isSet?userName=${encodeURIComponent(userName)}`);
|
const response = await fetch(`${API_URL}/users/isSet?userName=${encodeURIComponent(userName)}`);
|
||||||
|
setIsLoading(false)
|
||||||
if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
|
if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
return data; // Assuming the server returns true/false
|
return data; // Assuming the server returns true/false
|
||||||
@ -84,6 +88,7 @@ const useFetchUser = () => {
|
|||||||
|
|
||||||
const validToken = async (token: string | undefined): Promise<boolean> => {
|
const validToken = async (token: string | undefined): Promise<boolean> => {
|
||||||
try {
|
try {
|
||||||
|
setIsLoading(true)
|
||||||
const response = await fetch(`${API_URL}/login/validateToken`, {
|
const response = await fetch(`${API_URL}/login/validateToken`, {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
headers: {
|
headers: {
|
||||||
@ -93,6 +98,7 @@ const useFetchUser = () => {
|
|||||||
token
|
token
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
setIsLoading(false)
|
||||||
|
|
||||||
if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
|
if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
@ -156,7 +162,7 @@ const useFetchUser = () => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return { userSet, passwordCreate, signUser, validToken, updateAttendance, getAttendance };
|
return { userSet, passwordCreate, signUser, validToken, updateAttendance, getAttendance, isLoading };
|
||||||
};
|
};
|
||||||
|
|
||||||
export default useFetchUser;
|
export default useFetchUser;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user