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: 캐러셀 구현한 후, 홈 페이지에 적용 #421

Merged
merged 34 commits into from
Aug 19, 2024
Merged
Show file tree
Hide file tree
Changes from 32 commits
Commits
Show all changes
34 commits
Select commit Hold shift + click to select a range
848b56c
chore: LandingPage를 HomePage로 변경
ImxYJL Aug 15, 2024
60f1902
refactor: 새 HomePage의 Form 부분 퍼블리싱
ImxYJL Aug 15, 2024
5a064a6
refactor: 문자열 길이 검증 함수에서 최소 길이도 검증할 수 있도록 변경
ImxYJL Aug 15, 2024
827a481
test: 변경된 문자열 길이 검증 함수에 대한 테스트 추가
ImxYJL Aug 15, 2024
5fd81d9
refactor: 컴포넌트에 비밀번호 유효성 검사 추가
ImxYJL Aug 15, 2024
d69b555
refactor: ReviewGroupDataModal 스타일 조정
ImxYJL Aug 15, 2024
8c3e235
refactor: URL을 안내하는 모달 이름 수정
ImxYJL Aug 15, 2024
e19ec0e
feat: 리뷰미 소개 페이지 1차 퍼블리싱
ImxYJL Aug 15, 2024
b070350
chore: 불필요한 페이지 삭제
ImxYJL Aug 15, 2024
5b80f51
refactor: 스타일 수정
ImxYJL Aug 16, 2024
1488b6d
refactor: 폼 멘트 수정
ImxYJL Aug 16, 2024
7f3fe82
Merge branch 'develop' of https://github.com/woowacourse-teams/2024-r…
ImxYJL Aug 16, 2024
b720ca0
feat: 입력한 비밀번호를 확인할 수 있는 EyeButton 컴포넌트 작성
ImxYJL Aug 16, 2024
441cb51
refactor: URLGeneratorForm에 EyeButton 적용
ImxYJL Aug 16, 2024
834ad40
refactor: EyeButton 위치 수정
ImxYJL Aug 16, 2024
f85dbf9
chore: 불필요한 import 제거
ImxYJL Aug 16, 2024
332374d
fix: EyeButton 위치 고정
ImxYJL Aug 16, 2024
3b16f3e
refactor: 소개 페이지의 화살표 위치 조정
ImxYJL Aug 16, 2024
c911242
fix: EyeButton 위치 에러 수정
ImxYJL Aug 16, 2024
a79d31c
refactor: EyeButton 크기 조정
ImxYJL Aug 16, 2024
1c75f74
Merge branch 'develop' of https://github.com/woowacourse-teams/2024-r…
ImxYJL Aug 16, 2024
d3656e7
chore: 사용하지 않는 파일 삭제
ImxYJL Aug 16, 2024
353b4ad
fix: h3 삭제
ImxYJL Aug 16, 2024
775b8dc
chore: 사용하지 않는 파일을 index에서 제거
ImxYJL Aug 16, 2024
88616ec
refactor: EyeButton 사이즈 상수화
ImxYJL Aug 17, 2024
eed9e44
refactor: OverviewItem의 배경색을 theme의 배경색으로 변경
ImxYJL Aug 17, 2024
f237a3c
Merge remote-tracking branch 'origin/develop' into fe/feat/397-home-p…
soosoo22 Aug 18, 2024
ec62da1
design: theme.ts에 palePurple 색상 추가
soosoo22 Aug 18, 2024
99bb08e
feat: Carousel 컴포넌트 구현
soosoo22 Aug 18, 2024
7981a76
refactor: 기존 OverviewItem을 Carousel 컴포넌트로 교체
soosoo22 Aug 18, 2024
8f68b0a
design: 홈 페이지 높이 조정
soosoo22 Aug 18, 2024
ac3f1b0
style: css 속성 순서 정렬
soosoo22 Aug 18, 2024
31efb29
Merge remote-tracking branch 'origin/develop' into fe/feat/397-home-p…
soosoo22 Aug 19, 2024
b8db65a
Merge remote-tracking branch 'origin/develop' into fe/feat/397-home-p…
soosoo22 Aug 19, 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
6 changes: 3 additions & 3 deletions frontend/src/components/common/EyeButton/styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,14 @@ import styled from '@emotion/styled';
const EYE_BUTTON_SIZE = '1.6rem';

export const EyeButton = styled.button`
display: inline-block;
cursor: pointer;

position: absolute;
top: calc((100% - ${EYE_BUTTON_SIZE}) / 2);
right: 1rem;

display: inline-block;

width: ${EYE_BUTTON_SIZE};
height: ${EYE_BUTTON_SIZE};

cursor: pointer;
`;
67 changes: 67 additions & 0 deletions frontend/src/pages/HomePage/components/Carousel/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
import { useRef, useState } from 'react';

import * as S from './styles';

interface Slide {
imageSrc: string;
title: string;
description: string[];
}

interface CarouselProps {
slides: Slide[];
pageWidth: number;
pageHeight: number;
gap: number;
offset: number;
}

const Carousel = ({ slides, pageWidth, pageHeight, gap, offset }: CarouselProps) => {
const [page, setPage] = useState(0);
const scrollRef = useRef<HTMLDivElement>(null);

const handleScroll = () => {
if (scrollRef.current) {
const scrollLeft = scrollRef.current.scrollLeft;
const newPage = Math.round(scrollLeft / ((pageWidth + gap) * 10));
setPage(newPage);
}
};

const scrollToPage = (pageIndex: number) => {
if (scrollRef.current) {
scrollRef.current.scrollTo({
left: (pageWidth + gap) * 10 * pageIndex,
behavior: 'smooth',
});
setPage(pageIndex);
}
};

return (
<S.Layout>
<S.ScrollContainer ref={scrollRef} onScroll={handleScroll} gap={gap} offset={offset}>
{slides.map((slide, index) => (
<S.Page key={`slide_${index}`} width={pageWidth} height={pageHeight}>
<S.PageItem onClick={() => scrollToPage(index)}>
<img src={slide.imageSrc} alt={slide.title} style={{ padding: index === 2 ? '3rem' : '2rem' }} />
<S.PageTitle>{slide.title}</S.PageTitle>
<S.PageDescription>
{slide.description.map((desc, index) => (
<S.DescriptionItem key={index}>{desc}</S.DescriptionItem>
))}
</S.PageDescription>
</S.PageItem>
</S.Page>
))}
</S.ScrollContainer>
<S.IndicatorWrapper>
{slides.map((_, index) => (
<S.Indicator key={`indicator_${index}`} focused={index === page} onClick={() => scrollToPage(index)} />
))}
</S.IndicatorWrapper>
</S.Layout>
);
};

export default Carousel;
82 changes: 82 additions & 0 deletions frontend/src/pages/HomePage/components/Carousel/styles.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
import styled from '@emotion/styled';

export const Layout = styled.section`
width: 100%;
padding-left: 3rem;
`;

export const ScrollContainer = styled.div<{ gap: number; offset: number }>`
overflow-x: auto;
display: flex;
gap: ${({ gap }) => `${gap}rem`};

height: 100%;
padding: ${({ offset }) => `0 ${offset}rem`};

&::-webkit-scrollbar {
display: none;
}
`;

export const Page = styled.div<{ width: number; height: number }>`
flex-shrink: 0;
width: ${({ width }) => `${width}rem`};
height: ${({ height }) => `${height}rem`};
`;

export const PageItem = styled.div`
cursor: pointer;

display: flex;
flex-direction: column;
align-items: center;

height: 100%;

background-color: ${({ theme }) => theme.colors.white};
border-radius: 0.8rem;
border-radius: ${({ theme }) => theme.borderRadius.basic};
box-shadow: 0.8rem 1rem 1.6rem hsl(0deg 0% 0% / 0.25);

img {
width: 100%;
height: 25rem;
background-color: ${({ theme }) => theme.colors.palePurple};
border-radius: ${({ theme }) => theme.borderRadius.basic} ${({ theme }) => theme.borderRadius.basic} 0 0;
}
`;

export const PageTitle = styled.p`
margin: 1rem 0;
font-size: ${({ theme }) => theme.fontSize.mediumSmall};
font-weight: ${({ theme }) => theme.fontWeight.bold};
`;

export const PageDescription = styled.div`
width: 100%;
padding-left: 3rem;
`;

export const DescriptionItem = styled.p`
margin: 0.5rem 0;
font-size: ${({ theme }) => theme.fontSize.basic};
`;

export const IndicatorWrapper = styled.div`
display: flex;
justify-content: center;
margin-top: 1.6rem;
`;

export const Indicator = styled.div<{ focused: boolean }>`
cursor: pointer;

width: 1rem;
height: 1rem;
margin: 0 0.5rem;

background-color: ${({ focused, theme }) => (focused ? theme.colors.black : theme.colors.placeholder)};
border-radius: 50%;

transition: background-color 0.3s ease;
`;
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ import styled from '@emotion/styled';
export const FormLayout = styled.form`
display: flex;
flex-direction: column;

justify-content: center;
`;

Expand Down
65 changes: 28 additions & 37 deletions frontend/src/pages/HomePage/components/ReviewMeOverview/index.tsx
Original file line number Diff line number Diff line change
@@ -1,51 +1,42 @@
import ArrowIcon from '@/assets/downArrow.svg';
import OverviewImg1 from '@/assets/overview1.svg';
import OverviewImg2 from '@/assets/overview2.svg';
import OverviewImg3 from '@/assets/overview3.svg';
import WritingIcon from '@/assets/overviewTitle.svg';

import { OverviewItem } from '../index';
import Carousel from '../Carousel';

import * as S from './styles';

const OVERVIEW_TITLE = '리뷰미 사용법';

const OVERVIEW_SLIDES = [
{
imageSrc: OverviewImg1,
title: '리뷰 받는 사람 (You)',
description: ['나의 리뷰 링크를 만들어요', '리뷰어에게 리뷰 링크를 보내요'],
},
{
imageSrc: OverviewImg2,
title: '리뷰 쓰는 사람',
description: ['리뷰 링크에 접속해요', '리뷰 작성하기를 통해 리뷰를 작성해요'],
},
{
imageSrc: OverviewImg3,
title: '리뷰 받는 사람 (You)',
description: ['리뷰 링크에 접속해요', '리뷰 확인을 위한 비밀번호를 입력해요', '받은 리뷰를 확인해요'],
},
];

const ReviewMeOverview = () => {
return (
<S.ReviewMeOverview>
<S.RowSectionContainer>
<S.ColumnSectionContainer>
<S.OverviewTitleContainer>
<img src={WritingIcon} alt="리뷰미 사용법" />
<S.OverviewTitle>리뷰미 사용법</S.OverviewTitle>
</S.OverviewTitleContainer>

<OverviewItem
direction="row"
imageSrc={OverviewImg1}
title="리뷰 받는 사람 (You)"
description={['나의 리뷰 링크를 만들어요', '리뷰어에게 리뷰 링크를 보내요']}
/>
</S.ColumnSectionContainer>
</S.RowSectionContainer>

<S.RowSectionContainer>
<S.ArrowWrapper src={ArrowIcon} alt="화살표 아이콘" />
</S.RowSectionContainer>

<S.RowSectionContainer>
<OverviewItem
direction="column"
imageSrc={OverviewImg2}
title="리뷰 쓰는 사람"
description={['리뷰 링크에 접속해요', '리뷰 작성하기를 통해 리뷰를 작성해요']}
/>

<OverviewItem
direction="column"
imageSrc={OverviewImg3}
title="리뷰 받는 사람 (You)"
description={['리뷰 링크에 접속해요', '리뷰 확인을 위한 비밀번호를 입력해요', '받은 리뷰를 확인해요']}
/>
</S.RowSectionContainer>
<S.ColumnSectionContainer>
<S.OverviewTitleContainer>
<img src={WritingIcon} alt={OVERVIEW_TITLE} />
<S.OverviewTitle>{OVERVIEW_TITLE}</S.OverviewTitle>
</S.OverviewTitleContainer>
<Carousel slides={OVERVIEW_SLIDES} pageWidth={32} pageHeight={40} gap={5} offset={3.6} />
</S.ColumnSectionContainer>
</S.ReviewMeOverview>
);
};
Expand Down
25 changes: 11 additions & 14 deletions frontend/src/pages/HomePage/components/ReviewMeOverview/styles.ts
Original file line number Diff line number Diff line change
@@ -1,23 +1,21 @@
import styled from '@emotion/styled';

export const ReviewMeOverview = styled.section`
position: relative;

overflow: hidden;

width: 65%;
height: 100%;

background-color: ${({ theme }) => theme.colors.lightPurple};

padding: 5rem 10rem;
`;

export const RowSectionContainer = styled.div`
display: flex;
justify-content: center;
gap: 5rem;
`;

export const ColumnSectionContainer = styled.div`
display: flex;
flex-direction: column;
justify-content: center;
height: 100%;
`;

export const ArrowWrapper = styled.img`
Expand All @@ -26,16 +24,15 @@ export const ArrowWrapper = styled.img`

export const OverviewTitleContainer = styled.div`
display: flex;
justify-content: center;
align-items: center;
gap: 1.3rem;
align-items: center;
justify-content: center;

margin-bottom: 3rem;
margin-bottom: 4rem;
`;

export const OverviewTitle = styled.p`
font-size: 3.8rem;
font-weight: ${({ theme }) => theme.fontWeight.bold};

margin-top: 1.3rem;
font-size: ${({ theme }) => theme.fontSize.large};
font-weight: ${({ theme }) => theme.fontWeight.bold};
`;
11 changes: 5 additions & 6 deletions frontend/src/pages/HomePage/components/ReviewURLModal/styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@ export const ReviewURLModal = styled.div`
`;

export const ModalTitle = styled.p`
font-weight: ${({ theme }) => theme.fontWeight.bold};
font-size: 2rem;
margin-bottom: 4.5rem;
font-size: 2rem;
font-weight: ${({ theme }) => theme.fontWeight.bold};
`;

export const ReviewURLModalItem = styled.div`
Expand All @@ -33,13 +33,13 @@ export const Data = styled.span`
`;

export const CheckContainer = styled.div`
font-size: 1.5rem;

display: flex;
gap: 0.6rem;
align-items: center;

margin-top: 2.5rem;

font-size: 1.5rem;
`;

export const Checkbox = styled.input`
Expand All @@ -54,8 +54,7 @@ export const CheckMessage = styled.p`
`;

export const WarningMessage = styled.p`
margin-top: 1rem;
font-size: smaller;
color: ${({ theme }) => theme.colors.red};

margin-top: 1rem;
`;
Original file line number Diff line number Diff line change
Expand Up @@ -5,35 +5,34 @@ export const URLGeneratorForm = styled.section`
align-items: center;
justify-content: center;

padding: 0 9rem;
width: 40%;
padding: 0 9rem;
`;

export const InputContainer = styled.div`
position: relative;
display: flex;
flex-direction: column;
gap: 0.2rem;

position: relative;
`;

export const PasswordInputContainer = styled.div`
display: flex;
position: relative;
display: flex;
`;

export const Label = styled.label`
margin-bottom: 1.2rem;
`;

export const InputInfo = styled.p`
font-size: 1.2rem;
margin: 0.5rem 0.3rem 0.4rem;
font-size: 1.2rem;
`;

export const ErrorMessage = styled.p`
font-size: 1.3rem;
color: ${({ theme }) => theme.colors.red};
height: 1.3rem;
padding-left: 0.7rem;
font-size: 1.3rem;
color: ${({ theme }) => theme.colors.red};
`;
1 change: 1 addition & 0 deletions frontend/src/pages/HomePage/styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,5 @@ import styled from '@emotion/styled';
export const HomePage = styled.div`
display: flex;
width: 100vw;
height: calc(100vh - 7rem); // NOTE: 7rem은 Topbar 높이
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

이렇게 계산식에 들어가는 변수는 따로 변수로 빼는 것도 좋을 것 같아요!

`;
Loading