Skip to content

Commit

Permalink
アカウント画面変更とPWAに追加ボタンを実装
Browse files Browse the repository at this point in the history
  • Loading branch information
MurakawaTakuya committed Jan 9, 2025
1 parent d245e8d commit cfc3367
Show file tree
Hide file tree
Showing 9 changed files with 268 additions and 69 deletions.
Binary file added public/img/iOSPWA.webp
Binary file not shown.
82 changes: 42 additions & 40 deletions src/Components/Account/AuthForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import { RoundedButton } from "./LoggedInView";
const CenteredToggleButtonGroup = styled(ToggleButtonGroup)({
display: "flex",
justifyContent: "center",
marginBottom: "16px",
marginBottom: "10px",
});

export default function AuthForm() {
Expand Down Expand Up @@ -84,13 +84,13 @@ export default function AuthForm() {
</CenteredToggleButtonGroup>
{formMode === "register" ? (
<>
<Typography>新規登録</Typography>
<Typography sx={{ marginBottom: "5px" }}>新規登録</Typography>
<form onSubmit={handleRegisterSubmit}>
<Box
sx={{
display: "flex",
flexDirection: "column",
gap: 2,
gap: "12px",
}}
>
<TextField
Expand Down Expand Up @@ -139,13 +139,13 @@ export default function AuthForm() {
</>
) : (
<>
<Typography>ログイン</Typography>
<Typography sx={{ marginBottom: "5px" }}>ログイン</Typography>
<form onSubmit={handleLoginSubmit}>
<Box
sx={{
display: "flex",
flexDirection: "column",
gap: 2,
gap: "12px",
}}
>
<TextField
Expand Down Expand Up @@ -185,41 +185,43 @@ export default function AuthForm() {
</form>
</>
)}
<Divider>または</Divider>
<RoundedButton
fullWidth
variant="outlined"
onClick={handleGoogleLogin}
disabled={loading}
>
{loading && loadingType === "Google" ? (
<>
<CircularProgress size={24} sx={{ marginRight: 1 }} />
Googleアカウントでログイン
</>
) : (
"Googleアカウントでログイン"
)}
</RoundedButton>
<RoundedButton
fullWidth
variant="outlined"
onClick={handleGuestLogin}
disabled={loading}
>
{loading && loadingType === "Guest" ? (
<>
<CircularProgress size={24} sx={{ marginRight: 1 }} />
ゲストログイン
</>
) : (
"ゲストログイン"
)}
</RoundedButton>
<Typography level="body-xs">
ゲストログインを使用するとアカウントを作成せずに閲覧できます。
(投稿機能は使用できません。)
</Typography>
<Divider sx={{ margin: "12px 0" }}>または</Divider>
<div style={{ display: "flex", flexWrap: "wrap", gap: "12px" }}>
<RoundedButton
fullWidth
variant="outlined"
onClick={handleGoogleLogin}
disabled={loading}
>
{loading && loadingType === "Google" ? (
<>
<CircularProgress size={24} sx={{ marginRight: 1 }} />
Googleアカウントでログイン
</>
) : (
"Googleアカウントでログイン"
)}
</RoundedButton>
<RoundedButton
fullWidth
variant="outlined"
onClick={handleGuestLogin}
disabled={loading}
>
{loading && loadingType === "Guest" ? (
<>
<CircularProgress size={24} sx={{ marginRight: 1 }} />
ゲストログイン
</>
) : (
"ゲストログイン"
)}
</RoundedButton>
<Typography level="body-xs">
ゲストログインを使用するとアカウントを作成せずに閲覧できます。
(投稿機能は使用できません。)
</Typography>
</div>
</>
);
}
42 changes: 25 additions & 17 deletions src/Components/Account/LoggedInView.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import styles from "@/app/account/page.module.scss";
import NameUpdate from "@/Components/NameUpdate/NameUpdate";
import NotificationButton from "@/Components/NotificationButton/NotificationButton";
import { handleSignOut } from "@/utils/Auth/signOut";
import { getSuccessRate } from "@/utils/successRate";
import { useUser } from "@/utils/UserContext";
Expand All @@ -10,7 +10,7 @@ import { useEffect, useState } from "react";

export const RoundedButton = styled(Button)(({ theme }) => ({
borderRadius: "30px",
padding: theme.spacing(1.5, 3),
padding: theme.spacing(1.3, 2.5),
}));

export default function LoggedInView() {
Expand Down Expand Up @@ -41,7 +41,7 @@ export default function LoggedInView() {
}

return (
<>
<div style={{ display: "flex", flexDirection: "column", gap: "10px" }}>
{user.loginType === "Guest" ? (
<Typography level="body-lg" sx={{ textAlign: "center" }}>
ゲストとしてログイン中
Expand All @@ -68,10 +68,29 @@ export default function LoggedInView() {
</Typography>
)}

{/* ゲストかメール未認証の場合は閲覧以外の機能を使用できなくする */}
{user.loginType !== "Guest" && user.isMailVerified && (
<>
<div style={{ display: "flex", flexDirection: "column", gap: "3px" }}>
<div
style={{
display: "flex",
flexDirection: "column",
alignItems: "center",
gap: "5px",
}}
>
<div
className={styles.buttonContainer}
style={{ margin: "10px 0" }}
>
<div>
<NameUpdate />
</div>
<div>
<RoundedButton variant="contained" onClick={handleSignOut}>
ログアウト
</RoundedButton>
</div>
</div>
<Typography level="title-md" sx={{ textAlign: "center" }}>
連続達成日数: {userStats.streak}日目
</Typography>
Expand All @@ -82,19 +101,8 @@ export default function LoggedInView() {
達成回数: {userStats.completed}
</Typography>
</div>
<div style={{ display: "flex", justifyContent: "space-evenly" }}>
<NameUpdate />
<NotificationButton />
</div>
<Typography color="neutral" sx={{ textAlign: "center" }}>
通知を有効にすると、目標が未達成の場合に期限の5分前に通知を送信します。
</Typography>
</>
)}

<RoundedButton variant="contained" onClick={handleSignOut}>
ログアウト
</RoundedButton>
</>
</div>
);
}
8 changes: 4 additions & 4 deletions src/Components/NavigationMenu/NavigationMenu.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ export default function NavigationMenu() {
<ListItemDecorator>
<FormatListBulletedIcon />
</ListItemDecorator>
My content
<span style={{ fontWeight: 600 }}>自分の目標</span>
</Tab>
<Tab
disableIndicator
Expand All @@ -114,7 +114,7 @@ export default function NavigationMenu() {
<ListItemDecorator>
<GroupIcon />
</ListItemDecorator>
Discover
<span style={{ fontWeight: 600 }}>みんなの投稿</span>
</Tab>
<Tab
disableIndicator
Expand All @@ -130,7 +130,7 @@ export default function NavigationMenu() {
<ListItemDecorator>
<Person />
</ListItemDecorator>
Profile
<span style={{ fontWeight: 600 }}>アカウント</span>
</Tab>
<Tab
disableIndicator
Expand All @@ -146,7 +146,7 @@ export default function NavigationMenu() {
<ListItemDecorator>
<HomeIcon />
</ListItemDecorator>
Top
<span style={{ fontWeight: 600 }}>トップ</span>
</Tab>
</TabList>
</Tabs>
Expand Down
14 changes: 11 additions & 3 deletions src/Components/NotificationButton/NotificationButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,11 @@ import { useEffect, useState } from "react";
import { RoundedButton } from "../Account/LoggedInView";
import { showSnackBar } from "../SnackBar/SnackBar";

export default function NotificationButton() {
export default function NotificationButton({
defaultDisabled = true,
}: {
defaultDisabled?: boolean;
}) {
const { user } = useUser();
const [notificationTokenGenerating, setNotificationTokenGenerating] =
useState(false);
Expand Down Expand Up @@ -104,15 +108,19 @@ export default function NotificationButton() {
<RoundedButton
variant="outlined"
onClick={handleDisableNotification}
disabled={!isNotificationActive}
disabled={!isNotificationActive || defaultDisabled}
>
通知を解除
</RoundedButton>
) : (
<RoundedButton
variant="outlined"
onClick={handleEnableNotification}
disabled={notificationTokenGenerating || isNotificationActive}
disabled={
notificationTokenGenerating ||
isNotificationActive ||
defaultDisabled
}
startIcon={
notificationTokenGenerating ? <CircularProgress size={20} /> : null
}
Expand Down
88 changes: 88 additions & 0 deletions src/Components/PWAButton/PWAButton.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
"use client";
import { useEffect, useRef, useState } from "react";
import { RoundedButton } from "../Account/LoggedInView";
import { showSnackBar } from "../SnackBar/SnackBar";

interface BeforeInstallPromptEvent extends Event {
prompt: () => Promise<void>;
}

declare global {
interface WindowEventMap {
beforeinstallprompt: BeforeInstallPromptEvent;
appinstalled: Event;
}
}

export const PWAButton = ({
defaultDisabled = true,
}: {
defaultDisabled?: boolean;
}) => {
const deferredPromptRef = useRef<BeforeInstallPromptEvent | null>(null);
const [ready, setReady] = useState(false);
const [isAleadyInstalled, setIsAlreadyInstalled] = useState(false);

useEffect(() => {
const checkIfInstalled = () => {
const isStandalone = window.matchMedia(
"(display-mode: standalone)"
).matches;
const isIosStandalone =
"standalone" in window.navigator &&
(window.navigator as unknown as { standalone: boolean }).standalone;
setIsAlreadyInstalled(isStandalone || Boolean(isIosStandalone));
};

checkIfInstalled();

const beforeInstallPromptHandler = (event: BeforeInstallPromptEvent) => {
setReady(true);
deferredPromptRef.current = event;
};

const appInstalledHandler = () => {
console.log("PWA was successfully installed!");
showSnackBar({
message: "アプリに追加しました。ホーム画面から起動してください。",
type: "success",
});
};

window.addEventListener("beforeinstallprompt", beforeInstallPromptHandler);
window.addEventListener("appinstalled", appInstalledHandler); // appinstalledイベントをリッスン

return () => {
window.removeEventListener(
"beforeinstallprompt",
beforeInstallPromptHandler
);
window.removeEventListener("appinstalled", appInstalledHandler);
};
}, []);

const handleClickInstall = async () => {
const deferredPrompt = deferredPromptRef.current;
if (deferredPrompt) {
deferredPrompt.prompt();
}
};

return (
<>
{isAleadyInstalled ? (
<RoundedButton variant="outlined" color="success" disabled>
アプリに追加済み!
</RoundedButton>
) : (
<RoundedButton
variant="outlined"
disabled={!ready || defaultDisabled}
onClick={handleClickInstall}
>
アプリに追加
</RoundedButton>
)}
</>
);
};
19 changes: 19 additions & 0 deletions src/app/account/page.module.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
.buttonContainer {
display: flex;
gap: 15px;
justify-content: center;
width: 100%;

& > div {
display: flex;
width: 100%;

&:nth-child(1) {
justify-content: flex-end;
}

&:nth-child(2) {
justify-content: flex-start;
}
}
}
Loading

0 comments on commit cfc3367

Please sign in to comment.