Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[FE] feat: 프론트엔드 home 기능 구현 #33

Merged
merged 17 commits into from
Nov 14, 2023
Merged
Show file tree
Hide file tree
Changes from 15 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 21 additions & 1 deletion frontEnd/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion frontEnd/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,8 @@
"react": "^18.2.0",
"react-dom": "^18.2.0",
"react-router-dom": "^6.18.0",
"socket.io-client": "^4.7.2"
"socket.io-client": "^4.7.2",
"uuid": "^9.0.1"
},
"devDependencies": {
"@testing-library/jest-dom": "^6.1.4",
Expand All @@ -23,6 +24,7 @@
"@types/node": "^20.8.10",
"@types/react": "^18.2.37",
"@types/react-dom": "^18.2.7",
"@types/uuid": "^9.0.7",
"@typescript-eslint/eslint-plugin": "^6.10.0",
"@typescript-eslint/parser": "^6.10.0",
"@vitejs/plugin-react": "^4.0.3",
Expand Down
Binary file added frontEnd/public/main.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
20 changes: 20 additions & 0 deletions frontEnd/src/components/Button.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import { ReactNode } from 'react';

type ButtonProps = {
children: ReactNode;
onClick: () => void;
fontSize: string;
};

export default function Button({ children, onClick, fontSize }: ButtonProps) {
return (
<button
type="button"
className="px-[1.6vw] py-[14px] bg-mainColor text-white rounded-[15px] font-Pretendard"
onClick={onClick}
style={{ fontSize }}
>
{children}
</button>
);
}
14 changes: 14 additions & 0 deletions frontEnd/src/hooks/useInput.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { useState } from 'react';

export default function useInput(initialValue: string) {
const [inputValue, setInputValue] = useState(initialValue);

const onChange = (event: React.ChangeEvent<HTMLInputElement>) => {
const {
target: { value },
} = event;
setInputValue(value);
};

return { inputValue, onChange };
}
58 changes: 57 additions & 1 deletion frontEnd/src/pages/Home.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,59 @@
import { v4 as uuidv4 } from 'uuid';
import { useNavigate } from 'react-router-dom';
import Button from '@/components/Button';
import useInput from '@/hooks/useInput';

export default function Home() {
return <div>Home</div>;
const navigate = useNavigate();
const { inputValue, onChange } = useInput('');

const handleMakeRoomClick = () => {
const roomId = uuidv4();
navigate(`/${roomId}`);
};

const handleJoinRoomClick = () => {
if (inputValue) navigate(`/${inputValue}`);
};

const handleKeyDown = (event: React.KeyboardEvent<HTMLInputElement>) => {
if (event.key === 'Enter') handleJoinRoomClick();
};

return (
<div className="h-[100vh] w-[100vw] bg-backgroundColor flex justify-center items-center py-[10vw] ">
d0422 marked this conversation as resolved.
Show resolved Hide resolved
<div className="flex flex-col basis-2/4 pc:gap-[130px] mobile:gap-[50px] justify-center items-center ">
<div className="flex flex-col justify-center">
<div className="text-[8.8vw] font-bold font-Pretendard ">AlgoITNi</div>
<div className="text-[1.4vw] font-Pretendard">AlgoITNi를 통해 동료, 친구와 함께 알고리즘을 학습해봐요!</div>
</div>
<div className="flex items-center justify-center w-[37vw] gap-3">
<Button onClick={handleMakeRoomClick} fontSize="1.5vw">
방생성
</Button>
<input
placeholder=""
className="rounded-2xl font-Pretendard px-[1.6vw] py-[14px] text-[1.5vw] w-3/5"
value={inputValue}
onChange={onChange}
onKeyDown={handleKeyDown}
/>

<button
type="button"
className="text-[1.5vw] font-bold text-mainColor font-Pretendard"
onClick={handleJoinRoomClick}
style={{
opacity: inputValue ? '1' : '0.4',
}}
>
참여
</button>
</div>
</div>
<div className="basis-2/4 max-w-[600px] max-h-[600px] mobile:hidden">
<img src="/main.png" alt="main" />
</div>
</div>
);
}
32 changes: 26 additions & 6 deletions frontEnd/src/pages/tests/Home.test.tsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,29 @@
import * as Home from '@pages/Home';
import { fireEvent, render, screen } from '@testing-library/react';
import Home from '@pages/Home';

describe('Home 호출 테스트', () => {
it('Home이 제대로 실행된다.', () => {
jest.spyOn(Home, 'default');
Home.default();
expect(Home.default).toHaveBeenCalled();
jest.mock('uuid', () => {
return { v4: jest.fn(() => 'test') };
});

const mockNavigate = jest.fn();

jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
useNavigate: () => mockNavigate,
}));

describe('Home 테스트', () => {
it('방생성 클릭시, uuid를 url로 갖는 새로운 방을 생성하고, 해당 방 url로 이동한다.', async () => {
render(<Home />);
await fireEvent.click(screen.getByText('방생성'));
expect(mockNavigate).toHaveBeenCalledWith('/test');
});

it('참가 클릭시, input입력창에 입력한 url을 가진 방으로 이동한다.', async () => {
render(<Home />);
const input = screen.getByPlaceholderText('');
fireEvent.change(input, { target: { value: 'inputValue' } });
await fireEvent.click(screen.getByText('참여'));
expect(mockNavigate).toHaveBeenCalledWith('/inputValue');
});
});
5 changes: 5 additions & 0 deletions frontEnd/src/styles/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,8 @@
@tailwind base;
@tailwind components;
@tailwind utilities;
html,
body {
width: 100%;
height: 100%;
}
13 changes: 13 additions & 0 deletions frontEnd/tailwind.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,19 @@ export default {
content: ['./index.html', './src/**/*.{js,ts,jsx,tsx}'],
theme: {
extend: {},
colors: {
mainColor: '#37485D',
backgroundColor: '#F0F2F5',
black: '#0C151C',
white: '#FFFFFF',
},
fontFamily: {
Pretendard: 'Pretendard-Regular',
},
screens: {
mobile: { min: '360px', max: '767px' },
pc: { min: '768px' },
},
},
plugins: [],
};