Skip to content

Commit ec6f364

Browse files
committed
create: Desktop version
1 parent a1bf1dc commit ec6f364

38 files changed

+3509
-1
lines changed

.eslintrc.cjs

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
module.exports = {
2+
root: true,
3+
env: { browser: true, es2020: true },
4+
extends: [
5+
'eslint:recommended',
6+
'plugin:@typescript-eslint/recommended',
7+
'plugin:react-hooks/recommended',
8+
],
9+
ignorePatterns: ['dist', '.eslintrc.cjs'],
10+
parser: '@typescript-eslint/parser',
11+
plugins: ['react-refresh'],
12+
rules: {
13+
'react-refresh/only-export-components': [
14+
'warn',
15+
{ allowConstantExport: true },
16+
],
17+
},
18+
}

.github/workflows/deploy.yml

+49
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
name: Deploy
2+
3+
on:
4+
push:
5+
branches:
6+
- main
7+
8+
jobs:
9+
build:
10+
name: Build
11+
runs-on: ubuntu-latest
12+
13+
steps:
14+
- name: Checkout repo
15+
uses: actions/checkout@v3
16+
17+
- name: Setup Node
18+
uses: actions/setup-node@v3
19+
20+
- name: Install dependencies
21+
uses: bahmutov/npm-install@v1
22+
23+
- name: Build project
24+
run: npm run build
25+
26+
- name: Upload production-ready build files
27+
uses: actions/upload-artifact@v3
28+
with:
29+
name: production-files
30+
path: ./dist
31+
32+
deploy:
33+
name: Deploy
34+
needs: build
35+
runs-on: ubuntu-latest
36+
if: github.ref == 'refs/heads/main'
37+
38+
steps:
39+
- name: Download artifact
40+
uses: actions/download-artifact@v3
41+
with:
42+
name: production-files
43+
path: ./dist
44+
45+
- name: Deploy to GitHub Pages
46+
uses: peaceiris/actions-gh-pages@v3
47+
with:
48+
github_token: ${{ secrets.GITHUB_TOKEN }}
49+
publish_dir: ./dist

.gitignore

+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
# Logs
2+
logs
3+
*.log
4+
npm-debug.log*
5+
yarn-debug.log*
6+
yarn-error.log*
7+
pnpm-debug.log*
8+
lerna-debug.log*
9+
10+
node_modules
11+
dist
12+
dist-ssr
13+
*.local
14+
15+
# Editor directories and files
16+
.vscode/*
17+
!.vscode/extensions.json
18+
.idea
19+
.DS_Store
20+
*.suo
21+
*.ntvs*
22+
*.njsproj
23+
*.sln
24+
*.sw?

README.md

+37-1
Original file line numberDiff line numberDiff line change
@@ -1 +1,37 @@
1-
# FM-Pomodoro
1+
# Frontend Mentor - Pomodoro app solution
2+
3+
This is a solution to the [Pomodoro app challenge on Frontend Mentor](https://www.frontendmentor.io/challenges/pomodoro-app-KBFnycJ6G). Frontend Mentor challenges help you improve your coding skills by building realistic projects.
4+
5+
## Table of contents
6+
7+
- [Frontend Mentor - Pomodoro app solution](#frontend-mentor---pomodoro-app-solution)
8+
- [Table of contents](#table-of-contents)
9+
- [Overview](#overview)
10+
- [Screenshot](#screenshot)
11+
- [Links](#links)
12+
- [My process](#my-process)
13+
- [Built with](#built-with)
14+
- [Author](#author)
15+
16+
17+
## Overview
18+
19+
### Screenshot
20+
21+
![](./screenshot.jpg)
22+
23+
### Links
24+
25+
- Solution URL: [Github URL](https://github.com/SecretariatV/FM-Pomodoro)
26+
- Live Site URL: [Live Site URL](https://secretariatv.github.io/FM-Pomodoro)
27+
28+
## My process
29+
30+
### Built with
31+
32+
- [React](https://reactjs.org/) - JS library
33+
- [Styled Components](https://styled-components.com/) - For styles
34+
35+
## Author
36+
37+
- Frontend Mentor - [@SecretariatV](https://www.frontendmentor.io/profile/SecretariatV)

index.html

+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="UTF-8" />
5+
<link rel="icon" type="image/svg+xml" href="/favicon-32x32.png" />
6+
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
7+
<link rel="preconnect" href="https://fonts.googleapis.com" />
8+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
9+
<link
10+
href="https://fonts.googleapis.com/css2?family=Kumbh+Sans:[email protected]&display=swap"
11+
rel="stylesheet"
12+
/>
13+
<link
14+
href="https://fonts.googleapis.com/css2?family=Roboto+Slab:[email protected]&display=swap"
15+
rel="stylesheet"
16+
/>
17+
<link
18+
href="https://fonts.googleapis.com/css2?family=Space+Mono:ital,wght@0,400;0,700;1,400;1,700&display=swap"
19+
rel="stylesheet"
20+
/>
21+
<title>Frontend Mentor | Pomodoro app</title>
22+
</head>
23+
<body>
24+
<div id="root"></div>
25+
<script type="module" src="/src/main.tsx"></script>
26+
</body>
27+
</html>

package.json

+39
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
{
2+
"name": "fm-pomodoro",
3+
"private": true,
4+
"version": "0.0.0",
5+
"type": "module",
6+
"author": "OVB",
7+
"scripts": {
8+
"dev": "vite",
9+
"build": "tsc -b && vite build",
10+
"lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
11+
"preview": "vite preview",
12+
"predeploy": "npm run build",
13+
"deploy": "gh-pages -d dist",
14+
"test": "cypress open"
15+
},
16+
"dependencies": {
17+
"clsx": "^2.1.1",
18+
"gh-pages": "^6.1.1",
19+
"react": "^18.3.1",
20+
"react-dom": "^18.3.1",
21+
"sass": "^1.77.6",
22+
"styled-components": "^6.1.11"
23+
},
24+
"devDependencies": {
25+
"@testing-library/jest-dom": "^6.4.6",
26+
"@testing-library/react": "^16.0.0",
27+
"@types/node": "^20.14.11",
28+
"@types/react": "^18.3.3",
29+
"@types/react-dom": "^18.3.0",
30+
"@typescript-eslint/eslint-plugin": "^7.13.1",
31+
"@typescript-eslint/parser": "^7.13.1",
32+
"@vitejs/plugin-react": "^4.3.1",
33+
"eslint": "^8.57.0",
34+
"eslint-plugin-react-hooks": "^4.6.2",
35+
"eslint-plugin-react-refresh": "^0.4.7",
36+
"typescript": "^5.2.2",
37+
"vite": "^5.3.1"
38+
}
39+
}

public/favicon-32x32.png

1.04 KB
Loading

src/App.tsx

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import { PomodoroApp } from "@components/app";
2+
import GlobalStyles from "@styles/globalStyles";
3+
4+
const App = () => {
5+
return (
6+
<>
7+
<GlobalStyles />
8+
<PomodoroApp />
9+
</>
10+
);
11+
};
12+
13+
export default App;

src/assets/check.svg

+4
Loading

src/assets/close.svg

+8
Loading

src/assets/down.svg

+4
Loading

src/assets/downhover.svg

+4
Loading

src/assets/setting.svg

+6
Loading

src/assets/up.svg

+4
Loading

src/assets/uphover.svg

+4
Loading

src/components/app/index.module.scss

+32
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
@use "@styles/globalStyles.scss" as G;
2+
3+
.body {
4+
display: flex;
5+
flex-direction: column;
6+
align-items: center;
7+
8+
&_title {
9+
font-size: 32px;
10+
font-weight: 700;
11+
color: var(--gray);
12+
position: relative;
13+
z-index: 5;
14+
}
15+
16+
&_setting {
17+
margin-top: 63px;
18+
background-color: transparent;
19+
border: 0;
20+
outline: 0;
21+
cursor: pointer;
22+
transition: all ease-in-out 0.2s;
23+
24+
&:hover {
25+
filter: drop-shadow(3px 3px 1px red) drop-shadow(-1px 3px 4px blue);
26+
}
27+
}
28+
}
29+
30+
.input {
31+
display: none;
32+
}

src/components/app/index.tsx

+75
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
import TabBar from "@components/tab";
2+
import S from "./index.module.scss";
3+
import Clock from "@components/clock";
4+
import { useState } from "react";
5+
import settingIcon from "@assets/setting.svg";
6+
import Modal from "@components/modal";
7+
8+
export interface ISettingProps {
9+
pomodoro: number;
10+
short: number;
11+
long: number;
12+
type: string;
13+
font: string;
14+
color: string;
15+
}
16+
17+
export const PomodoroApp = () => {
18+
const [settings, setSettings] = useState<ISettingProps>({
19+
pomodoro: 25,
20+
short: 5,
21+
long: 15,
22+
type: "pomodoro",
23+
font: "kumbh",
24+
color: "red",
25+
});
26+
const [openModal, setOpenModal] = useState<boolean>(false);
27+
28+
const handleClick = () => {
29+
setOpenModal(true);
30+
};
31+
32+
return (
33+
<>
34+
<div className={S.body}>
35+
<span className={S.body_title}>pomodoro</span>
36+
<TabBar setting={settings} setSetting={setSettings} />
37+
<Clock setting={settings} />
38+
<button className={S.body_setting} onClick={handleClick}>
39+
<img src={settingIcon} alt="Setting Icon" />
40+
</button>
41+
</div>
42+
{openModal && (
43+
<Modal
44+
setting={settings}
45+
setSetting={setSettings}
46+
setModal={setOpenModal}
47+
/>
48+
)}
49+
<input
50+
type="checkbox"
51+
name="kumbh"
52+
id="kumbh"
53+
checked={settings.font === "kumbh"}
54+
className={S.input}
55+
readOnly
56+
/>
57+
<input
58+
type="checkbox"
59+
name="roboto"
60+
id="roboto"
61+
checked={settings.font === "roboto"}
62+
className={S.input}
63+
readOnly
64+
/>
65+
<input
66+
type="checkbox"
67+
name="space"
68+
id="space"
69+
checked={settings.font === "space"}
70+
className={S.input}
71+
readOnly
72+
/>
73+
</>
74+
);
75+
};

0 commit comments

Comments
 (0)