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

질문 별 메모 기능 추가 및 카테고리 탭 리팩토링 #209

Closed
wants to merge 179 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
179 commits
Select commit Hold shift + click to select a range
1f3a113
chore: CI를 위한 YML 파일 생성
shin-jisong Jul 15, 2024
b9d02e5
chore: CI 루트 디렉토리 설정 추가
shin-jisong Jul 15, 2024
71e2808
chore: ci 스크립트 수정
tkdgur0906 Jul 19, 2024
1c0e58d
chore: cd 스크립트 작성
tkdgur0906 Jul 19, 2024
779471f
chore: ci 브랜치 명 수정
tkdgur0906 Jul 19, 2024
38b9f89
chore: cd 브랜치 명 수정
tkdgur0906 Jul 19, 2024
0bc0dc1
chore: 스프링부트 세팅
JINU-CHANG Jul 19, 2024
662ad3b
chore: cd 브랜치 추가
tkdgur0906 Jul 19, 2024
1428a8b
chore: ci 브랜치 추가
tkdgur0906 Jul 19, 2024
7cc6818
chore: h2 데이터베이스 연결
JINU-CHANG Jul 21, 2024
d679c24
chore: 예외 처리 및 응답 객체 생성
JINU-CHANG Jul 21, 2024
2d9ea6c
chore: swagger 세팅
JINU-CHANG Jul 21, 2024
dfa3a11
chore: BaseEntity 세팅
JINU-CHANG Jul 21, 2024
cd62673
chore: RuntimeException 예외처리 추가
JINU-CHANG Jul 21, 2024
a2ff2a2
fix: gitignore 적용
JINU-CHANG Jul 21, 2024
d76666b
chore: cd 파일 프로젝트명 변경
shin-jisong Jul 22, 2024
71bdf33
chore: ci 파일 프로젝트명 변경
shin-jisong Jul 22, 2024
6679f18
chore: ci에 dev-fe 브랜치 삭제
tkdgur0906 Jul 22, 2024
f24e557
chore: cd 브랜치 dev만 적용
tkdgur0906 Jul 22, 2024
c10c927
백엔드 CI/CD 설정을 추가한다. (#21)
JINU-CHANG Jul 22, 2024
97149d3
백엔드 초기 환경 설정을 한다. (#22)
JINU-CHANG Jul 22, 2024
fb752dd
chore: cd 파일 프로젝트명 변경
shin-jisong Jul 22, 2024
e4b62fb
백엔드 CD 설정 오류를 수정한다. (#43)
JINU-CHANG Jul 22, 2024
e0bc151
dev 브랜치와 dev-be 브랜치의 코드 상태를 병합시킨다. (#45)
shin-jisong Jul 22, 2024
4b566b7
feat: Room 엔티티 생성
shin-jisong Jul 22, 2024
099b2e8
feat: User 엔티티 생성
shin-jisong Jul 22, 2024
6f8eb4e
feat: Checklist 엔티티 생성
shin-jisong Jul 22, 2024
cc162ba
feat: 카테고리 조회 기능 구현
JINU-CHANG Jul 22, 2024
256889a
feat: BaseEntity 추가
shin-jisong Jul 22, 2024
a1bd2da
feat: 체크리스트 옵션 추가
shin-jisong Jul 22, 2024
6c4e9ce
feat: 옵션 정보 생성
shin-jisong Jul 22, 2024
617e5b0
feat: 카테고리 우선순위 생성 기능 구현
JINU-CHANG Jul 22, 2024
c450d90
feat: 도메인 생성자 추가
shin-jisong Jul 22, 2024
45241b7
feat: ChecklistQuestion 엔티티 생성
shin-jisong Jul 22, 2024
be220e7
feat: option id 포함 여부 확인 함수 구현
shin-jisong Jul 22, 2024
13841a1
feat: 체크리스트 생성을 위한 DTO들 생성
shin-jisong Jul 22, 2024
f9f4394
feat: 체크리스트 생성을 위한 Repository 생성
shin-jisong Jul 22, 2024
dcc317a
feat: 카테고리 우선순위 저장관련 검증 메서드 추가
JINU-CHANG Jul 23, 2024
9b94b48
refactor: 카테고리 id 타입 변경
JINU-CHANG Jul 23, 2024
71caa02
카테고리 조회 기능을 구현한다. (#48)
tkdgur0906 Jul 23, 2024
a63b727
refactor: IntegrationTestSupport 파일 추가
JINU-CHANG Jul 23, 2024
a3c09ff
Merge remote-tracking branch 'origin/dev-be' into feat/47-category-pr…
JINU-CHANG Jul 23, 2024
23145e6
fix: 카테고리 아이디 타입 변경으로 인한 문법 오류 해결
JINU-CHANG Jul 23, 2024
5d350ba
feat: 체크리스트 질문 목록 생성
shin-jisong Jul 23, 2024
90970c3
style: 옵션 중요한 순으로 정렬
shin-jisong Jul 23, 2024
468ad5f
feat: 룸 정보에 주소 추가
shin-jisong Jul 23, 2024
4384daf
feat: yml 파일 작성하는 스크립트 추가
JINU-CHANG Jul 23, 2024
91863de
feat: yml 파일 작성하는 스크립트 추가
JINU-CHANG Jul 23, 2024
20e933e
feat: Cors관련 설정파일 추가
JINU-CHANG Jul 23, 2024
241ec74
refactor: id 타입 변경(Integer -> int)
JINU-CHANG Jul 23, 2024
65c3142
refactor: 불필요한 @Repository 어노테이션 제거
JINU-CHANG Jul 23, 2024
d1f610a
feat: domain equals, hashcode, toString 메서드 재정의
JINU-CHANG Jul 23, 2024
2f1c2e4
카테고리 우선순위 저장 기능을 구현한다. (#65)
shin-jisong Jul 23, 2024
96965b0
feat: 초기 schema, data sql 설정
shin-jisong Jul 23, 2024
41bf353
feat: 테이블명 추가
shin-jisong Jul 23, 2024
cf81782
feat: Grade 생성
shin-jisong Jul 23, 2024
d54aea2
feat(QuestionList): 질문 포함 여부 확인 기능 구현
shin-jisong Jul 23, 2024
06e3e82
feat: API 형식에 따른 DTO 구조 변경
shin-jisong Jul 23, 2024
1dbcc81
feat: ChecklistQuestion 레포지토리 생성
shin-jisong Jul 23, 2024
1979f7c
feat: 체크리스트 저장 시 예외 처리 구현
shin-jisong Jul 23, 2024
80f44f0
feat(Room): 테이블 이름 지정
shin-jisong Jul 23, 2024
8ca7bac
feat: 체크리스트 저장 기능 구현
shin-jisong Jul 23, 2024
667bf21
Merge remote-tracking branch 'origin/dev-be' into feat/70-cors-config
JINU-CHANG Jul 23, 2024
d9ca7a7
test: 테스트 환경 세팅
shin-jisong Jul 23, 2024
f2a7912
chore: 테스트 의존성 추가
shin-jisong Jul 23, 2024
9e33ee4
test: 테스트 기본 코드 작성
shin-jisong Jul 23, 2024
e385279
feat: 중첩 DTO 검증 구현
shin-jisong Jul 23, 2024
b626249
test: 체크리스트 방 정보 작성 E2E 테스트
shin-jisong Jul 23, 2024
ec990a7
test: 옵션 포함 테스트
shin-jisong Jul 23, 2024
af8962d
test: 질문 리스트 포함 테스트
shin-jisong Jul 23, 2024
bee4f57
test: 체크리스트 방 정보 작성 서비스 테스트
shin-jisong Jul 23, 2024
8ce6fb9
style: 코드 재정렬
shin-jisong Jul 23, 2024
acd7d06
Merge branch 'dev-be' into feat/47-write-checklist-api
shin-jisong Jul 23, 2024
24df144
fix: merge 충돌 해결
shin-jisong Jul 23, 2024
d56ae04
Cors 설정파일을 추가한다. (#71)
shin-jisong Jul 24, 2024
0aa98c0
refactor(Option): 접근제어자 수정 및 Integer을 int로 변경
shin-jisong Jul 24, 2024
71e4c53
refactor(ChecklistService): 변수명 변경
shin-jisong Jul 24, 2024
b48cd1a
test(ChecklistE2ETest): 오타 수정
shin-jisong Jul 24, 2024
a65d810
test: 테스트 컨벤션 반영
shin-jisong Jul 24, 2024
44694ef
test: 테스트 값 견고하게 변경
shin-jisong Jul 24, 2024
6d9c9fc
test: 중복 어노테이션 제거
shin-jisong Jul 24, 2024
fd384eb
test: static import 적용
shin-jisong Jul 24, 2024
f2d17cb
refactor: JoinColumn으로 nullable 설정 제거
shin-jisong Jul 24, 2024
d15d588
refactor(Checklist): 기본 생성자 활용해서 생성자 수정
shin-jisong Jul 24, 2024
1b3b8fa
refactor: URI 명확히 수정
shin-jisong Jul 24, 2024
4dc0c8c
style: 가독성 있게 코드 개행
shin-jisong Jul 24, 2024
97d0979
feat: 뱃지 추가
JINU-CHANG Jul 24, 2024
3e48abe
feat: 체크리스트 방 정보 작성 검증 코드 추가
shin-jisong Jul 24, 2024
0f66137
feat: 엔티티에 불필요 Table 어노테이션 제거
shin-jisong Jul 24, 2024
2b22c57
test: hasMessage ExceptionCode 사용
shin-jisong Jul 24, 2024
8fecebf
refactor: QuestionList -> Questionlist
shin-jisong Jul 24, 2024
58380b0
refactor(Question): categoryId 필드 제거
shin-jisong Jul 24, 2024
837a02d
체크리스트 방 정보 작성 API를 구현한다. (#75)
tsulocalize Jul 24, 2024
ef373bd
refactor: category에 질문 리스트 필드 추가
shin-jisong Jul 24, 2024
356f7f4
feat: 체크리스트 질문 조회 DTO 생성
shin-jisong Jul 24, 2024
6af37c6
refactor(Questionlist): 필드 접근제어자 수정
shin-jisong Jul 24, 2024
5f1a857
refactor: 스키마 자료형 수정
shin-jisong Jul 24, 2024
adfcd36
feat: 체크리스트 질문 조회 기능 구현
shin-jisong Jul 24, 2024
0268d7f
refactor(ChecklistService): 체크리스트 질문 조회 기능 메서드 분리
shin-jisong Jul 24, 2024
8a46ba0
test: 체크리스트 질문 조회 E2E 테스트
shin-jisong Jul 24, 2024
422e540
test: 체크리스트 질문 조회 서비스 테스트
shin-jisong Jul 24, 2024
e4a6be9
test: 질문 제목, 부제목 조회 테스트
shin-jisong Jul 24, 2024
3ba8379
feat: 뱃지 설명 포맷 추가
JINU-CHANG Jul 24, 2024
32161bc
Merge remote-tracking branch 'origin/dev-be' into feat/84-checklist-list
JINU-CHANG Jul 24, 2024
0de41fc
feat: 뱃지 기능 중간 저장
JINU-CHANG Jul 24, 2024
b4b20de
refactor(ChecklistService): 메서드 반환 타입 List로 변경
shin-jisong Jul 25, 2024
bd3d8d6
refactor(Category): 질문 저장하는 자료형 Set으로 변경
shin-jisong Jul 25, 2024
61ff6bd
feat: 사용자 체크리스트 리스트 조회 기능 구현
JINU-CHANG Jul 25, 2024
3b5c9cd
뱃지 도메인을 추가한다. (#81)
tkdgur0906 Jul 25, 2024
7abb357
Merge branch 'dev-be' into feat/84-checklist-list
JINU-CHANG Jul 25, 2024
a1e26f1
Merge branch 'dev-be' into feat/76-read-checklist-questions
shin-jisong Jul 25, 2024
c93534a
체크리스트 질문 조회 API를 구현한다. (#83)
JINU-CHANG Jul 25, 2024
6086eda
Merge branch 'dev-be' into feat/84-checklist-list
JINU-CHANG Jul 25, 2024
f44b0f4
fix: 코드 충돌 해결
JINU-CHANG Jul 25, 2024
943753e
feat: 방비교 기능 구현
JINU-CHANG Jul 25, 2024
1bff3c3
feat(Category): 질문이 카테고리에 있는지 판별하는 기능 구현
shin-jisong Jul 25, 2024
7cbfcbb
feat: 사용자 체크리스트 조회 DTO 생성
shin-jisong Jul 25, 2024
feea5e5
feat: 사용자 체크리스트 조회 기능 구현
shin-jisong Jul 25, 2024
32ee0d9
방 비교 결과 조회 API를 만든다. (#100)
tkdgur0906 Jul 25, 2024
4e11a57
Merge branch 'dev-be' into feat/89-read-writed-checklist
tkdgur0906 Jul 25, 2024
90f0d68
fix: merge 후 충돌 해결
shin-jisong Jul 25, 2024
8e2b29b
작성한 체크리스트를 조회하는 API를 구현한다. (#101)
shin-jisong Jul 25, 2024
aab5331
1차 스프린트 API를 배포한다. (#105)
shin-jisong Jul 25, 2024
ae3fb1e
fix: 루트 수정
shin-jisong Jul 25, 2024
c4154c9
cd 오류를 해결한다. (#108)
shin-jisong Jul 25, 2024
16274c4
fix: corsFilter 도입
shin-jisong Jul 25, 2024
ca064f1
CORS 오류를 해결한다. (#110)
shin-jisong Jul 25, 2024
963ebb5
fix: null 예외처리 및 @Transactional 추가
JINU-CHANG Jul 25, 2024
b69305a
Lazy Initialization 예외를 해결한다. (#112)
JINU-CHANG Jul 25, 2024
23444df
feat: cd 스크립트에 서버 로그 파일 위치 지정
tkdgur0906 Jul 25, 2024
81ada2c
배포 서버의 로그가 기록되지 않는 문제를 해결한다. (#119)
tkdgur0906 Jul 25, 2024
6b90e6b
fix: 카테고리 중복 질문 제거 및 순서 보장
Jul 26, 2024
a72eaab
질문 목록 조회 시 질문 순서, 목록이 잘못 조회되는 문제를 해결한다. (#135)
tkdgur0906 Jul 26, 2024
238db8d
2차 스프린트 기간 기능을 Dev에 머지한다. (#159)
healim01 Jul 29, 2024
0f0067d
refactor: 서비스, 컨트롤러 클래스 삭제
JINU-CHANG Jul 29, 2024
c93a691
feat: 체크리스트 방 정보 작성 API 구현
shin-jisong Jul 29, 2024
bb2de37
feat: 체크리스트 질문 조회 API 구현
shin-jisong Jul 29, 2024
67f4c25
feat: 작성한 체크리스트 조회 API 구현
tkdgur0906 Jul 29, 2024
e99fa88
feat: 카테고리 조회 API 구현
Jul 29, 2024
d213fcf
refactor: 사용자 체크리스트 리스트 조회 API 수정 반영
JINU-CHANG Jul 29, 2024
d8f8185
feat: 카테고리 우선순위 저장 API 구현
Jul 29, 2024
ea3c992
refactor: 방 비교 결과 API 수정 반영
JINU-CHANG Jul 29, 2024
87ee8cd
refactor: request, response dto 패키지 분리
tkdgur0906 Jul 30, 2024
4096981
refactor: DTO request/response package 분리
Jul 30, 2024
e38d09d
Merge remote-tracking branch 'origin/refactor/143-written-checklist-r…
JINU-CHANG Jul 30, 2024
ae6498c
fix: 머지 후 실패하는 코드 수정
JINU-CHANG Jul 30, 2024
e4d0281
Merge remote-tracking branch 'origin/168-category-api' into dev-be
JINU-CHANG Jul 30, 2024
aa130ad
fix: 머지 실패 시 오류 해결
JINU-CHANG Jul 30, 2024
ea3a056
fix: 머지 실패 시 오류 해결
JINU-CHANG Jul 30, 2024
d2bb55b
[BE] 1차 스프린트 리팩토링을 dev 브랜치에 반영한다. (#176)
JINU-CHANG Jul 30, 2024
86032e2
refactor: 변경된 api 타입으로 체크리스트 전반적 로직 수정
ooherin Jul 31, 2024
dc696c7
refactor: 타입 반영 완료
ooherin Jul 31, 2024
5405cc1
Merge branch 'dev-fe' of https://github.com/woowacourse-teams/2024-ba…
ooherin Jul 31, 2024
fda4c73
fix: 병합 충돌 해결
ooherin Jul 31, 2024
9a869df
fix: 옵션 모달 선택 버그 해결
ooherin Aug 1, 2024
178989e
fix: 훅함수 이름 수정 및 반영
ooherin Aug 1, 2024
8e9c717
fix: 병합 충돌 해결
ooherin Aug 1, 2024
3ee8f23
--amend
ooherin Aug 1, 2024
f772a9c
fix: 불필요한 파일 삭제
ooherin Aug 1, 2024
db540d4
fix: 변경된 데이터로 테스트 수정
ooherin Aug 1, 2024
2469242
[BE] 체크리스트 방 정보 작성 API에 기능을 추가 구현한다 (#189)
shin-jisong Aug 1, 2024
f0c8ad3
feat: 체크리스트 탭에 z-index 지정
ooherin Aug 1, 2024
7c8d43b
fix: 병합 충돌 해결
ooherin Aug 1, 2024
978e2a0
[BE] 체크리스트 조회 API에 기능을 추가 구현한다. (#192)
tkdgur0906 Aug 1, 2024
64a4cd8
refactor: 아코디언 헤더를 재사용 가능하도록 리팩토링
ooherin Aug 1, 2024
ad439d0
[BE] 커스텀 체크리스트 수정 기능을 구현한다. (#191)
tsulocalize Aug 1, 2024
85d6927
docs: 방끗 소개글 추가
healim01 Aug 2, 2024
fef13ba
feat: 메모 토글 버튼 생성
ooherin Aug 2, 2024
88abb07
fix: 아코디언 기존 디자인으로 변경
ooherin Aug 2, 2024
bb116c9
[BE] 카카오 서버로부터 사용자 정보를 가져온다. (#198)
JINU-CHANG Aug 2, 2024
dd26582
Merge remote-tracking branch 'origin/dev' into dev-be
JINU-CHANG Aug 2, 2024
7d617aa
dev-be를 dev브랜치와 병합한다. (#207)
JINU-CHANG Aug 2, 2024
1f83264
fix: 카테고리 탭 질문 에러 해결 및 리팩토링
ooherin Aug 3, 2024
b864bdb
refactor: 체크리스트 질문 answer 관련 훅으로 리팩토링
ooherin Aug 3, 2024
53110df
fix: 병합 충돌 해결
ooherin Aug 3, 2024
cc63430
feat: 메모 퍼블리싱 및 useInput 생성
ooherin Aug 3, 2024
bcbb432
feat: 메모 기능 추가 및 질문에 카테고리 키를 쓰도록 수정
ooherin Aug 3, 2024
6b96a2b
Merge branch 'dev' of https://github.com/woowacourse-teams/2024-bang-…
ooherin Aug 3, 2024
99d84ea
fix: 변경된 로직에 따라 테스트 수정
ooherin Aug 3, 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: 6 additions & 0 deletions frontend/src/assets/assets.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,10 @@ import LampIcon from '@/assets/icons/lamp-icon.svg';
import BangGgoodTextIcon from '@/assets/icons/logo.svg';
import QuestionDot from '@/assets/icons/question-dot.svg';

/*memo */
import MemoEmpty from '@/assets/icons/memo-empty.svg';
import MemoFilled from '@/assets/icons/memo-filled.svg';

export {
ArrowBack,
ArrowDownSmall,
Expand All @@ -61,6 +65,8 @@ export {
LocationLineIcon,
LocationLogo,
LocationLogoActive,
MemoEmpty,
MemoFilled,
MyPageLogo,
MyPageLogoActive,
Plus,
Expand Down
3 changes: 3 additions & 0 deletions frontend/src/assets/icons/memo-empty.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions frontend/src/assets/icons/memo-filled.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions frontend/src/components/ChecklistDetail/CheckListAnswer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import styled from '@emotion/styled';

import { QuestionDot } from '@/assets/assets';
import FaceMark from '@/components/common/FaceMark/FaceMark';
import { emotionPhrase } from '@/components/NewChecklist/ChecklistQuestion/ChecklistQuestion';
import { EMOTION_PHARSE } from '@/constants/emotion';
import { ChecklistQuestionWithAnswer } from '@/types/checklist';

interface Props {
Expand All @@ -24,7 +24,7 @@ const ChecklistAnswer = ({ QuestionAndAnswer }: Props) => {
<S.Answer>
<FaceMark>
<FaceMark.FaceIcon emotion={answer} isFilled={true} />
<FaceMark.Footer>{emotionPhrase[answer]}</FaceMark.Footer>
<FaceMark.Footer>{EMOTION_PHARSE[answer]}</FaceMark.Footer>
</FaceMark>
</S.Answer>
</S.Container>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ interface Props {
createdAt: string;
}

const RoomInfoSection = ({ room, score, createdAt }: Props) => {
const RoomInfoSection = ({ room, score }: Props) => {
// TODO: 로딩 중일 때 스켈레톤표시
if (!room) return null;
const { roomName, deposit, rent, address, contractTerm, floor, floorLevel, station, walkingTime, realEstate } = room;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,58 +1,72 @@
import styled from '@emotion/styled';
import { useState } from 'react';

import { QuestionDot } from '@/assets/assets';
import { ArrowUpSmall, MemoEmpty, MemoFilled, QuestionDot } from '@/assets/assets';
import FaceMark from '@/components/common/FaceMark/FaceMark';
import useChecklistStore from '@/store/useChecklistStore';
import { useTabContext } from '@/components/common/Tabs/TabContext';
import QuestionMemo from '@/components/NewChecklist/ChecklistQuestion/QuestionMemo';
import { EMOTION_PHARSE, EMOTIONS } from '@/constants/emotion';
import useChecklistAnswer from '@/hooks/useChecklistAnswer';
import { flexCenter } from '@/styles/common';
import { ChecklistQuestion } from '@/types/checklist';
import { Emotion, EmotionType } from '@/types/emotionAnswer';
import { EmotionType } from '@/types/emotionAnswer';

interface Props {
question: ChecklistQuestion;
}

export const emotionPhrase: Record<EmotionType | string, string> = {
BAD: '별로에요',
SOSO: '평범해요',
GOOD: '좋아요',
null: '-',
};

const ChecklistQuestion = ({ question }: Props) => {
const { questionId } = question;
const { deleteAnswer, addAnswer, questionSelectedAnswer } = useChecklistStore();
const { updateAnswer, findCategoryQuestion } = useChecklistAnswer();
const { currentTabId } = useTabContext();

const [isMemoOpen, setIsMemoOpen] = useState(false);

const { answer, memo } = findCategoryQuestion({ categoryId: currentTabId, questionId });

const handleClick = (newAnswer: EmotionType) => {
if (questionSelectedAnswer(questionId) === newAnswer) {
deleteAnswer(questionId);
} else {
addAnswer({ questionId: questionId, newAnswer });
}
updateAnswer({ categoryId: currentTabId, questionId: questionId, newAnswer });
};

const handleCloseMemo = () => {
setIsMemoOpen(false);
};

const emotions: Emotion[] = [
{ name: 'BAD', id: 1 },
{ name: 'SOSO', id: 2 },
{ name: 'GOOD', id: 3 },
];
const handleOpenMemo = () => {
setIsMemoOpen(true);
};

return (
<S.Container>
<S.Title>
<QuestionDot />
{question?.title}
</S.Title>
{question?.subtitle && <S.Subtitle>•{question?.subtitle}</S.Subtitle>}

{question?.subtitle && <S.Subtitle>{question?.subtitle}</S.Subtitle>}

<S.ButtonBox>
{isMemoOpen ? (
<ArrowUpSmall onClick={handleCloseMemo} />
) : memo?.length ? (
<MemoFilled onClick={handleOpenMemo} />
) : (
<MemoEmpty onClick={handleOpenMemo} />
)}
</S.ButtonBox>

<S.Options>
{emotions.map(emotion => {
{EMOTIONS.map(emotion => {
const { name: emotionName, id } = emotion;
return (
<FaceMark onClick={() => handleClick(emotionName)} key={id}>
<FaceMark.FaceIcon emotion={emotionName} isFilled={questionSelectedAnswer(questionId) === emotionName} />
<FaceMark.Footer>{emotionPhrase[emotionName]}</FaceMark.Footer>
<FaceMark.FaceIcon emotion={emotionName} isFilled={answer === emotionName} />
<FaceMark.Footer>{EMOTION_PHARSE[emotionName]}</FaceMark.Footer>
</FaceMark>
);
})}
</S.Options>
{isMemoOpen && <QuestionMemo questionId={questionId} text={memo} />}
</S.Container>
);
};
Expand All @@ -61,10 +75,15 @@ export default ChecklistQuestion;

const S = {
Container: styled.div`
position: relative;
padding: 16px;

background-color: ${({ theme }) => theme.palette.white};
border-radius: 8px;
`,
Title: styled.div`
display: flex;
width: 90%;
margin: 5px 0;

font-size: ${({ theme }) => theme.text.size.medium};
Expand All @@ -88,4 +107,17 @@ const S = {
margin-top: 10px;
justify-content: space-between;
`,
ButtonBox: styled.div`
position: absolute;
top: 10px;
right: 10px;
border-radius: 50%;
width: 40px;
height: 40px;
${flexCenter}

:hover {
background-color: ${({ theme }) => theme.palette.background};
}
`,
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import styled from '@emotion/styled';

import Button from '@/components/common/Button/Button';
import { useTabContext } from '@/components/common/Tabs/TabContext';
import Textarea from '@/components/common/Textarea/Textarea';
import useChecklistAnswer from '@/hooks/useChecklistAnswer';
import useInput from '@/hooks/useInput';

interface Props {
questionId: number;
text: string;
}
const QuestionMemo = ({ questionId, text }: Props) => {
const { currentTabId } = useTabContext();
const { onChange, value } = useInput(text);
const { updateMemo } = useChecklistAnswer();

const handleUpdateMemo = () => {
updateMemo({ categoryId: currentTabId, questionId, newMemo: value });
};

return (
<S.Container>
<Textarea height="medium" value={value} onChange={onChange} />
<S.ButtonBox>
<Button label="저장" size="xSmall" isSquare={true} color="dark" onClick={handleUpdateMemo} />
</S.ButtonBox>
</S.Container>
);
};

export default QuestionMemo;

const S = {
Container: styled.div`
position: relative;
margin-top: 15px;
`,
ButtonBox: styled.div`
position: absolute;
right: 10px;
bottom: 10px;
`,
};
44 changes: 29 additions & 15 deletions frontend/src/components/common/Accordion/AccodionHeader.tsx
Original file line number Diff line number Diff line change
@@ -1,23 +1,27 @@
import styled from '@emotion/styled';

import { ArrowDownSmall, ArrowUpSmall } from '@/assets/assets';
import { useAccordionContext } from '@/components/common/Accordion/AccordionContext';
import { flexCenter, title2 } from '@/styles/common';

interface Props {
text: string;
id: number;
openButton?: React.ReactNode;
closeButton?: React.ReactNode;
text?: string;
isMarked?: boolean;
}
const AccordionHeader = ({ text, id }: Props) => {
const AccordionHeader = ({ id, openButton, closeButton, text, isMarked = true }: Props) => {
const { isAccordionOpen, handleAccordionOpenChange } = useAccordionContext();

return (
<S.HeaderContainer onClick={() => handleAccordionOpenChange(id)}>
<S.FlexBox>
<S.HeaderMark isMarked={isAccordionOpen(id)} />
<S.FlexBetween>
<S.HeaderMark isMarked={isMarked} />
<S.HeaderTitle>{text}</S.HeaderTitle>
</S.FlexBox>
<S.ArrowBox>{isAccordionOpen(id) ? <ArrowUpSmall /> : <ArrowDownSmall />}</S.ArrowBox>
<S.OpenBox onClick={() => handleAccordionOpenChange}>
{isAccordionOpen(id) ? openButton : closeButton}
</S.OpenBox>
</S.FlexBetween>
</S.HeaderContainer>
);
};
Expand All @@ -26,12 +30,11 @@ export default AccordionHeader;

const HeaderContainer = styled.div`
display: flex;
width: 100%;
height: 50px;
position: relative;
height: 45px;

background-color: ${({ theme }) => theme.palette.white};
border-radius: 12px;
justify-content: space-between;
gap: 10px;
`;

Expand All @@ -40,22 +43,32 @@ const FlexBox = styled.div`
gap:10px;
`;

const FlexBetween = styled.div`
display: flex;
height: 100%;
justify-content: space-between;
`;

const HeaderTitle = styled.div`
${title2}
${title2};
display: flex;
padding-left: 15px;
align-items: center;
`;

const HeaderMark = styled.div<{ isMarked: boolean }>`
opacity: ${({ isMarked }) => (isMarked ? 1 : 0)};
width: 12px;
height: 100%;

background-color: ${({ theme }) => theme.palette.yellow500};
border-radius: 8px 0 0 8px;
transition: opacity 0.3s ease;
`;

const ArrowBox = styled.div`
width: 50px;
const OpenBox = styled.div<{ onClick?: () => void }>`
position: absolute;
top: 10px;
right: 10px;
${flexCenter}
`;

Expand All @@ -64,5 +77,6 @@ const S = {
HeaderMark,
HeaderTitle,
FlexBox,
ArrowBox,
OpenBox,
FlexBetween,
};
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ export const Default: Story = {
render: () => {
return (
<Accordion>
<Accordion.header text={'청결도'} id={1}></Accordion.header>
<Accordion.header id={1} text="청결도" />
<Accordion.body id={1}>
<ul>
<li>list 1</li>
Expand Down
5 changes: 2 additions & 3 deletions frontend/src/components/common/Accordion/Accordion.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
import styled from '@emotion/styled';
import { PropsWithChildren } from 'react';

import AccordionHeader from '@/components/common/Accordion/AccodionHeader';
import AccordionBody from '@/components/common/Accordion/AccordionBody';
import { AccordionProvider } from '@/components/common/Accordion/AccordionContext';
import { flexColumn } from '@/styles/common';

interface Props extends PropsWithChildren {
// TODO: 내부 children 선언 혹은 extend 할지 통일하기
interface Props {
children?: React.ReactNode;
width?: string;
}

Expand Down
12 changes: 8 additions & 4 deletions frontend/src/components/common/Button/Button.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import styled from '@emotion/styled';
import { title2, title3, title4 } from '@/styles/common';
import theme from '@/styles/theme';

type ButtonSize = 'small' | 'medium' | 'full';
type ButtonSize = 'xSmall' | 'small' | 'medium' | 'full';
type ColorOption = 'light' | 'dark' | 'disabled';

interface Props extends React.HTMLAttributes<HTMLButtonElement> {
Expand Down Expand Up @@ -33,7 +33,7 @@ export default Button;

const S = {
Button: styled.button<{ size: ButtonSize; color: ColorOption; isSquare: boolean }>`
${({ isSquare }) => (isSquare ? 'border-radius: 8px' : 'border-radius: 100px')};
${({ isSquare }) => (isSquare ? 'border-radius: 4px' : 'border-radius: 100px')};
${({ size }) => sizeStyles[size]};
${({ color }) => ColorStyles[color]};
cursor: pointer;
Expand All @@ -53,13 +53,13 @@ const ColorStyles = {
}
`,
dark: css`
background-color: ${theme.palette.black};
background-color: ${theme.palette.grey600};

color: ${theme.palette.white};

&:hover,
&:active {
background-color: ${theme.palette.grey600};
background-color: ${theme.palette.black};
}
`,
disabled: css`
Expand All @@ -70,6 +70,10 @@ const ColorStyles = {
};

const sizeStyles = {
xSmall: css`
padding: 8px 15px;
${title4}
`,
small: css`
padding: 10px 24px;
${title4}
Expand Down
Loading
Loading