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] #106 - AddChannel 페이지 구현 #161

Merged
merged 26 commits into from
Nov 14, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
941ae50
[FE][Feat] #16 : InputComponent 구현
leedongyull Nov 6, 2024
ef9dc8d
[FE][FEAT] 페이지 구현
leedongyull Nov 7, 2024
4aea9e8
Merge branch 'main' of https://github.com/boostcampwm-2024/web28-DDar…
leedongyull Nov 7, 2024
d209411
[FE][FEAT] #106 : 기본 UI 구현
leedongyull Nov 10, 2024
be8cd95
Merge branch 'feature/fe/#134-makeLayoutComponent' of https://github.…
leedongyull Nov 11, 2024
7ae36c2
Merge branch 'frontend' of https://github.com/boostcampwm-2024/web28-…
leedongyull Nov 12, 2024
69c082c
[Fe][Rename] #106 : AddChannel 페이지 명 변경
leedongyull Nov 12, 2024
94f37b1
Merge branch 'feature/fe/#106-AddChannelUI' of https://github.com/boo…
leedongyull Nov 13, 2024
7297588
[FE][Fix] : Merge 작업
leedongyull Nov 13, 2024
180eda1
Merge branch 'frontend' of https://github.com/boostcampwm-2024/web28-…
leedongyull Nov 13, 2024
9b2ced0
[FE][Style] #106 : rem 단위로 변경 및 기획에 맞게 디자인 수정
leedongyull Nov 13, 2024
01a4683
[FE][Docs] #106 : tsDoc 설명 추가
leedongyull Nov 13, 2024
deb94fc
[FE][Style] #106 : 사용자 추가 버튼 height 추가
leedongyull Nov 14, 2024
bc28144
[FE][Feat] #106 : 사용자 삭제 UI 및 기능 간단히 구현
leedongyull Nov 14, 2024
5a1e8b2
[FE][Feat] #106 : 사용자 삭제 기능 구현 및 mock데이터 추가
leedongyull Nov 14, 2024
67169a6
[FE][Doc] #106 : 사용자 삭제 기능 tsDoc 추가
leedongyull Nov 14, 2024
5c6c96b
[FE][Feat] #106 : svg 대신 react-icons 사용
leedongyull Nov 14, 2024
31a1029
[FE][Style] #106 : 색상 변경 및 디자인 변경
leedongyull Nov 14, 2024
e4a8509
Delete package.json
leedongyull Nov 14, 2024
0cb24d8
Delete pnpm-lock.yaml
leedongyull Nov 14, 2024
3f948ee
Delete frontend/package.json
leedongyull Nov 14, 2024
65c9325
Delete backend/package.json
leedongyull Nov 14, 2024
0639b78
Merge branch 'frontend' of https://github.com/boostcampwm-2024/web28-…
leedongyull Nov 14, 2024
0d88c6a
Merge branch 'frontend' of https://github.com/boostcampwm-2024/web28-…
leedongyull Nov 14, 2024
5b98450
[FE][Feat] #106 : Footer 투명 추가
leedongyull Nov 14, 2024
f176c60
Merge branch 'feature/fe/#106-AddChannelUI' of https://github.com/boo…
leedongyull Nov 14, 2024
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
33 changes: 0 additions & 33 deletions backend/package.json

This file was deleted.

64 changes: 0 additions & 64 deletions frontend/package.json

This file was deleted.

28 changes: 28 additions & 0 deletions frontend/src/component/common/InputBox.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import { ChangeEvent, FocusEvent } from 'react';

export interface IInputBoxProps {
type?: 'text' | 'number' | 'password' | 'email' | 'tel';
placeholder?: string;
onChange?: (event: ChangeEvent<HTMLInputElement>) => void;
onFocus?: (event: FocusEvent<HTMLInputElement>) => void;
onBlur?: (event: FocusEvent<HTMLInputElement>) => void;
className?: string;
}

export const InputBox = ({
type = 'text',
placeholder = '',
onChange,
onFocus,
onBlur,
className = '',
}: IInputBoxProps) => (
<input
type={type}
placeholder={placeholder}
onChange={onChange}
onFocus={onFocus}
onBlur={onBlur}
className={`border-grayscale-75 placeholder:text-grayscale-50 focus:border-grayscale-400 text-grayscale-400 flex h-11 w-full rounded border px-3 text-xs focus:border-2 focus:outline-none ${className}`}
/>
);
13 changes: 8 additions & 5 deletions frontend/src/component/layout/Footer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,13 @@ interface IFooterProps {
title?: string;
onClick?: () => void;
active?: boolean;
isTranperency?: boolean;
}

export const Footer = (props: IFooterProps) => {
const buttonStyle = props.active ? buttonActiveType.ACTIVE : buttonActiveType.PASSIVE;
export const Footer = ({ title, onClick, active = false, isTranperency = true }: IFooterProps) => {
const buttonStyle = active ? buttonActiveType.ACTIVE : buttonActiveType.PASSIVE;

return (
return isTranperency ? (
<footer className="absolute bottom-5 h-[6%] w-[95%]">
<button
className={classNames(
Expand All @@ -24,10 +25,12 @@ export const Footer = (props: IFooterProps) => {
buttonStyle,
)}
type="button"
onClick={props.onClick}
onClick={onClick}
>
{props.title}
{title}
</button>
</footer>
) : (
<div />
);
};
2 changes: 2 additions & 0 deletions frontend/src/component/layout/Layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ interface ILayoutProps {
footerTitle?: string;
footerActive?: boolean;
handleFooterClick?: () => void;
footerTransperency?: boolean;
}

export const Layout = (props: ILayoutProps) => {
Expand All @@ -25,6 +26,7 @@ export const Layout = (props: ILayoutProps) => {
title={props.footerTitle}
onClick={props.handleFooterClick}
active={props.footerActive}
isTranperency={props.footerTransperency}
/>
</>
);
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/component/layout/header/LayoutHeader.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { useContext } from 'react';
import { Header } from '@/component/header/Header';
import { NoticeText } from '@/component/text/NoticeText';
import { HeaderContext } from '@/component/layout/header/LayoutHeaderProvider.tsx';
import { HeaderContext } from '@/component/layout/header/LayoutHeaderProvider';

export const LayoutHeader = () => {
const { headerOption } = useContext(HeaderContext);
Expand Down
1 change: 1 addition & 0 deletions frontend/src/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ time, mark, audio, video {
margin: 0;
padding: 0;
border: 0;
border-style: solid;
font-size: 100%;
font: inherit;
vertical-align: baseline;
Expand Down
143 changes: 142 additions & 1 deletion frontend/src/pages/AddChannel.tsx
Original file line number Diff line number Diff line change
@@ -1 +1,142 @@
export const AddChannel = () => <>Hello</>;
import { useEffect, useState } from 'react';
import classNames from 'classnames';
import { IoClose } from 'react-icons/io5';
import { HiMiniInformationCircle } from 'react-icons/hi2';
import { InputBox } from '../component/common/InputBox';

interface IUser {
id: number;
name: string;
mockData?: number;
}

/**
* Divider 컴포넌트: 구분선 역할을 하는 컴포넌트입니다.
* @return {JSX.Element} 수평선 `<hr />` 요소를 반환합니다.
*/
const Divider = () => <hr className="my-6 w-full border-gray-300" />;

/**
* AddChannel 컴포넌트
*
* 사용자가 경로 이름을 입력하고 최대 5명까지 사용자 추가가 가능합니다.
* 각 사용자는 출발지와 도착지의 설정이 가능합니다.
*
* @return {JSX.Element} 채널 추가 페이지 레이아웃을 반환합니다.
*
* @remarks
* 이 컴포넌트는 사용자가 지정된 이름으로 사용자를 추가하고,
* 추가된 사용자마다 출발지, 도착지, 그리고 경로 설정이 가능합니다.
*
* @example
* ```tsx
* <AddChannel />
* ```
*/

export const AddChannel = () => {
const [users, setUsers] = useState<IUser[]>([{ id: 1, name: '사용자1', mockData: 10 }]);

/**
* 사용자 추가 함수
*
* 현재 사용자 목록에 새로운 사용자를 추가합니다.
* 최대 5명까지 추가할 수 있으며, 그 이상은 추가할 수 없습니다.
*
* @return {void} 반환값이 없습니다.
*
* @remarks
* 사용자가 5명 이상일 경우 추가되지 않도록 제한하고,
* 추가되는 사용자는 '사용자[n]' 형식의 이름을 가집니다.
*
* @example
* ```
* addUser(); // 사용자 추가
* ```
*/
const addUser = () => {
if (users.length === 5) return;
const newUser: IUser = {
id: users.length + 1,
name: `사용자${users.length + 1}`,
mockData: Math.floor(Math.random() * 100),
};
setUsers([...users, newUser]);
};

/**
* 사용자 추가 함수
*
* 현재 사용자 목록에 사용자를 삭제합니다.
* 최대 4명까지 삭제할 수 있으며, 첫 사용자는 삭제할 수 없습니다.
*
* @return {void} 반환값이 없습니다.
*
* @remarks
* 사용자 2번 부터 삭제 버튼이 생깁니다.
* 사용자가 삭제되면 id를 다시 부여하여 빈 부분을 당겨와 채웁니다.
*
* @example
* ```
* deleteUser(3); // 3번 id 사용자 삭제
* ```
*/

const deleteUser = (id: number) => {
const updatedUsers = users
.filter(user => user.id !== id)
.map((user, index) => ({
...user,
id: index + 1,
name: `사용자${index + 1}`,
}));
setUsers(updatedUsers);
};

useEffect(() => {
console.log(users);
}, [users]);

return (
<main className="flex h-full w-full flex-col items-center px-8">
<InputBox placeholder="경로 이름을 입력해주세요. ex) 아들 집 가는 길" />
<Divider />
leedongyull marked this conversation as resolved.
Show resolved Hide resolved
<section className="w-full space-y-4">
{users.map(user => (
<div className="flex flex-row items-center justify-center space-x-2" key={user.id}>
<div className="shadow-userName border-grayscale-400 flex h-12 w-16 items-center justify-center rounded-lg border text-xs">
{user.name}
</div>
<div
className={classNames(
'text-grayscale-150 bg-grayscale-100 m-0 flex h-11 items-center justify-center rounded-md text-xs font-semibold',
user.id > 1 ? 'w-56' : 'w-64',
)}
>
클릭시 출발지/도착지, 경로 설정 가능
</div>
{user.id > 1 && (
<button onClick={() => deleteUser(user.id)}>
<IoClose className="text-grayscale-400 h-6 w-6" />
</button>
)}
</div>
))}
</section>
<section className="text-grayscale-400 my-4 flex flex-row items-center justify-center gap-[2px] text-xs">
<HiMiniInformationCircle className="h-4 w-4 text-black" />
사용자 별로 출발지/도착지(마커), 경로(그림)을 설정할 수 있습니다.
</section>
{users.length < 5 && (
<section className="flex w-full justify-end">
<button
onClick={addUser}
className="bg-grayscale-25 border-gray-75 h-8 w-64 rounded border p-2 text-xs"
>
사용자 추가
</button>
</section>
)}
</main>
);
};
2 changes: 1 addition & 1 deletion frontend/src/pages/DrawRoute.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Footer } from '@/component/Layout/Footer';
import { Footer } from '@/component/layout/Footer';
import { Map } from '@/component/maps/Map';
import { MdArrowBack } from 'react-icons/md';
import { Linedrawer } from '@/component/linedrawer/Linedrawer';
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/pages/GuestView.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { Map } from '@/component/maps/Map.tsx';
import { HeaderContext } from '@/component/layout/header/LayoutHeaderProvider.tsx';
import { HeaderContext } from '@/component/layout/header/LayoutHeaderProvider';
import { useContext, useEffect } from 'react';

export const GuestView = () => {
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/pages/Main.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { Fragment } from 'react';
import { getUserLocation } from '@/hooks/getUserLocation';
import { Map } from '@/component/maps/Map';
import { BottomSheet } from '@/component/bottomsheet/BottomSheet';
import { BottomSheet } from '@/component/BottomSheet/BottomSheet';
import { Content } from '@/component/content/Content';
import { MdFormatListBulleted } from 'react-icons/md';

Expand Down
2 changes: 1 addition & 1 deletion frontend/src/stories/BottomSheet.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import React, { Fragment } from 'react';
import { Meta, Story } from '@storybook/react';
import { BottomSheet } from '@/component/bottomsheet/BottomSheet';
import { BottomSheet } from '@/component/BottomSheet/BottomSheet';
import { Content } from '@/component/content/Content';

export default {
Expand Down
11 changes: 7 additions & 4 deletions frontend/tailwind.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,15 @@ module.exports = {
colors: {
grayscale: {
white: '#FFFFFF',
25: '#FEFEFEF2',
leedongyull marked this conversation as resolved.
Show resolved Hide resolved
50: 'rgba(60, 60, 67, 0.36)',
100: '#B7B7B7',
25: '#FBFBFB',
50: '#A0AEC0',
75: '#E2E8F0',
100: '#EDF2F7',
150: '#AAB6C7',
200: '#6D6D6D',
400: '#555555',
800: '#3E3E3E',
900: '1C1C1C',
900: '#1C1C1C',
},
blueGray: {
200: '#495664',
Expand Down Expand Up @@ -48,6 +50,7 @@ module.exports = {
floatButton: '0 5px 10px rgba(0,0,0,0.3)',
floatMenuButton: '0 4px 4px rgba(0,0,0,0.25)',
float: '0 4px 20px rgba(0, 0, 0, 0.13)',
userName: '5px 4px 7.1px rgba(0, 0, 0, 0.05)',
basic: 'inset 0 0 3px rgba(0, 0, 0, 0.11)',
dark: '0px -6px 20px 0px rgba(0, 0, 0, 0.25)',
},
Expand Down
Loading
Loading