Skip to content

Commit

Permalink
Merge pull request #28 from mathiasayivor/feat-loading-animation
Browse files Browse the repository at this point in the history
  • Loading branch information
narayan954 authored Oct 1, 2022
2 parents b4e39f6 + 06417a1 commit c14a8fd
Show file tree
Hide file tree
Showing 6 changed files with 192 additions and 15 deletions.
2 changes: 1 addition & 1 deletion index.html
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
<html lang="en">
<head>
<meta charset="UTF-8" />
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
<link rel="icon" type="image/png" href="/favicon-logo.png" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>DummyGram</title>
</head>
Expand Down
55 changes: 43 additions & 12 deletions src/App.jsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
import React, { useState, useEffect } from "react";
import React, { useState, useEffect, useMemo } from "react";
import Post from "./components/Post";
import { db, auth } from "./lib/firebase";
import { Modal, Button, Input } from "@mui/material";
import { makeStyles } from "@mui/styles";
import ImgUpload from "./components/ImgUpload";
import Loader from "./components/Loader";
import AnimatedButton from "./components/AnimatedButton";

function getModalStyle() {
const top = 50;
Expand Down Expand Up @@ -39,6 +41,12 @@ function App() {
const [email, setEmail] = useState("");
const [password, setPassword] = useState("");
const [user, setUser] = useState(null);
const [signingUp, setSigningUp] = useState(false);
const [logginIn, setLogginIn] = useState(false);
const processingAuth = useMemo(
() => logginIn || signingUp,
[logginIn, signingUp]
);

useEffect(() => {
const unsubscribe = auth.onAuthStateChanged((authUser) => {
Expand Down Expand Up @@ -73,23 +81,43 @@ function App() {

const signUp = (e) => {
e.preventDefault();
setSigningUp(true);
auth
.createUserWithEmailAndPassword(email, password)
.then((authUser) => {
return authUser.user.updateProfile({
displayName: username,
});
})
.catch((error) => alert(error.message));
setOpenSignUp(false);
.then(() => {
alert("Signup Successful!");
setOpenSignUp(false);
})
.catch((error) => alert(error.message))
.finally(() => {
setSigningUp(false);
});
};

const signIn = (e) => {
e.preventDefault();
setLogginIn(true);
auth
.signInWithEmailAndPassword(email, password)
.catch((error) => alert(error.message));
setOpenSignIn(false);
.then(() => {
alert("Login successful!");
setOpenSignIn(false);
})
.catch((error) => alert(error.message))
.finally(() => {
setLogginIn(false);
});
};

const signOut = () => {
if (confirm("Are you sure you want to logout?")) {
auth.signOut().finally();
}
};

return (
Expand All @@ -100,10 +128,11 @@ function App() {
alt="instagram"
className="app__header__img"
/>

{user ? (
{processingAuth ? (
<Loader />
) : user ? (
<Button
onClick={() => auth.signOut()}
onClick={signOut}
color="secondary"
variant="contained"
style={{ margin: 5 }}
Expand Down Expand Up @@ -160,14 +189,15 @@ function App() {
value={password}
onChange={(e) => setPassword(e.target.value)}
/>
<Button
<AnimatedButton
type="submit"
onClick={signUp}
variant="contained"
color="primary"
loading={processingAuth}
>
Sign Up
</Button>
</AnimatedButton>
</center>
</form>
</div>
Expand All @@ -193,14 +223,15 @@ function App() {
value={password}
onChange={(e) => setPassword(e.target.value)}
/>
<Button
<AnimatedButton
type="submit"
onClick={signIn}
variant="contained"
color="primary"
loading={processingAuth}
>
Sign In
</Button>
</AnimatedButton>
</center>
</form>
</div>
Expand Down
11 changes: 11 additions & 0 deletions src/components/AnimatedButton.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { Button } from "@mui/material";
import Loader from "./Loader";

export default function AnimatedButton(props) {
const { loading, children, ..._props } = props;
return (
<Button {..._props} disabled={loading}>
{loading ? <Loader /> : children}
</Button>
);
}
10 changes: 8 additions & 2 deletions src/components/ImgUpload.jsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,21 @@
import React, { useState } from "react";
import { db, storage } from "../lib/firebase";
import firebase from "firebase/compat/app";
import Button from "@mui/material/Button";
import AnimatedButton from "./AnimatedButton";

function ImgUpload(props) {
const [image, setImage] = useState(null);
const [caption, setCaption] = useState("");
const [progress, setProgress] = useState(0);
const [uploadingPost, setUploadingPost] = useState(false);

const handleChange = (e) => {
if (e.target.files[0]) {
setImage(e.target.files[0]);
}
};
const handleUpload = () => {
setUploadingPost(true);
const uploadTask = storage.ref(`images/${image.name}`).put(image);
uploadTask.on(
"state_changed",
Expand All @@ -27,8 +29,10 @@ function ImgUpload(props) {
// error function ...
console.log(error);
alert(error.message);
setUploadingPost(false);
},
() => {
setUploadingPost(false);
// complete function ...
storage
.ref("images")
Expand Down Expand Up @@ -62,7 +66,9 @@ function ImgUpload(props) {
value={caption}
/>
<input type="file" name="file" id="file" onChange={handleChange} />
<Button onClick={handleUpload}>Upload</Button>
<AnimatedButton onClick={handleUpload} loading={uploadingPost}>
Upload
</AnimatedButton>
</div>
);
}
Expand Down
93 changes: 93 additions & 0 deletions src/components/Loader.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
/**
* Credits: https://codepen.io/feirer/pen/zovgae
* Patrick Feirer
*
*/

body {
background-color: #fbfbfb;
}

.loader {
box-sizing: border-box;
display: flex;
position: relative;
justify-content: center;
perspective-origin: 60px 60px;
transform-origin: 60px 60px;
border: 0px solid #000000;
flex: 0 0 auto;
flex-flow: column nowrap;
}

.loader:after,
.loader:before {
height: 100%;
width: 100%;
border-radius: 50%;
border-style: solid;
border-width: 2px;
box-sizing: border-box;
content: "";
left: 0;
position: absolute;
top: 0;
}

.loader:after {
-webkit-animation: rotate 1s infinite ease;
animation: rotate 1s infinite ease;
border-color: #3897f0 transparent transparent;
-webkit-transform-origin: 50%;
transform-origin: 50%;
}

.loader:before {
border-color: #c7c7c7;
}

.loader a {
display: block;
font-size: 14px;
margin: -60px 0;
padding: 60px 9px;
position: relative;
text-align: center;
vertical-align: middle;
z-index: 1;
color: #c7c7c7;
text-decoration: none;
font: normal normal 600 normal 14px / 14px proxima-nova, "Helvetica Neue",
Arial, Helvetica, sans-serif;
}

@-webkit-keyframes rotate {
0% {
-webkit-transform: rotate(0deg);
transform: rotate(0deg);
}
to {
-webkit-transform: rotate(360deg);
transform: rotate(360deg);
}
}

@keyframes rotate {
0% {
-webkit-transform: rotate(0deg);
transform: rotate(0deg);
}
to {
-webkit-transform: rotate(360deg);
transform: rotate(360deg);
}
}

.note {
color: #c7c7c7;
text-decoration: none;
font: normal normal 600 normal 12px / 12px proxima-nova, "Helvetica Neue",
Arial, Helvetica, sans-serif;
text-align: center;
width: 100%;
}
36 changes: 36 additions & 0 deletions src/components/Loader.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
import "./Loader.css";

/**
*
* @param {{
* width: number,
* height:number
* }} props
*/
export default function Loader(props) {
const { width, height } = Object.assign(
{
width: 30,
height: 30,
},
props
);

return (
<div
style={{
display: "flex",
justifyContent: "center",
alignItems: "center",
}}
>
<div
className="loader"
style={{
width: `${width}px`,
height: `${height}px`,
}}
/>
</div>
);
}

0 comments on commit c14a8fd

Please sign in to comment.