Skip to content
This repository has been archived by the owner on Jul 29, 2024. It is now read-only.

[FE] feat: 카테고리 및 글 드래그앤드롭 기능 구현 #418

Merged
merged 25 commits into from
Sep 20, 2023

Conversation

nangkyeonglim
Copy link
Collaborator

@nangkyeonglim nangkyeonglim commented Sep 16, 2023

🛠️ Issue

✅ Tasks

크게 다음 작업들을 수행했습니다.

  • 글/카테고리 드래그앤 드롭 구현
  • 카테고리에 스크롤이 생길 때 header는 고정되도록 수정
  • 스크롤이 있을 때 카테고리 추가 시 맨 아래로 스크롤 되는 기능 구현
  • 드래그 영역 확장 및 throttle 적용

⏰ Time Difference

  • 12 -> 24

📝 Note

처음에 공통 훅으로 만드려고 하다보니 시간이 오래걸려서 일단 구현을 해봤습니다.

드래그 앤 드롭

카테고리

파란색으로 표시되는 위치로 이동합니다.
기본 카테고리는 이동 불가하고 기본 카테고리 위로는 이동이 불가합니다.

Sep-17-2023 05-05-52

글끼리 순서를 바꿀 수 있습니다.
글을 카테고리 이름 위에 두면 카테고리의 맨 마지막으로 이동합니다.
글을 다른 카테고리 내의 특정 위치에 이동시킬 수 있습니다.

(벡엔드 PR 머지가 안되서 글의 마지막으로 이동 등 특정 순서 이동 때 에러가 발생할 수 있어요. 요청은 잘 가고있는 듯 합니다.)

Sep-17-2023 05-16-13

헤더 고정

원래는 스크롤이 생겼을 때 헤더가 고정되지 않아 또 카테고리를 추가하려면 위로 올려야하는 문제가 있었는데요. 이를 개선하였습니다!

Sep-17-2023 05-20-22) Sep-17-2023 05-23-06

카테고리 추가

스크롤이 생길만큼 카테고리가 많은 상황에서 카테고리를 추가하면 수동으로 스크롤을 내려야 추가된 카테고리를 볼 수 있었습니다.
이를 개선하여 스크롤 아래로 카테고리를 추가할 때 자동으로 스크롤을 내리는 동작을 추가하였습니다.

Sep-17-2023 05-25-39 Sep-17-2023 05-26-47

드래그 영역 확장 및 throttle 적용

스크롤이 생겼을 때 스크롤을 내리거나 올린 곳에 드래그를 하고 싶을 때 기본적으로 영역의 끝에 닿아야만 스크롤 & 드래그가 가능했습니다.
이 영역을 확장하여 좀더 드래그하기 쉽게 개선하였습니다.
여기서 onDrag 이벤트를 사용하게되는데 이는 드래그 하는 동안 몇 ms 마다 계속 발생하기 때문에 쓰로틀링을 적용하였습니다.

image image

Sep-17-2023 05-34-40

@nangkyeonglim nangkyeonglim added 🎨 UI 디자인, UI 🖥️ frontend 프론트엔드 작업 🌟 feature 기능 추가 labels Sep 16, 2023
@nangkyeonglim nangkyeonglim self-assigned this Sep 16, 2023
@echo724
Copy link
Collaborator

echo724 commented Sep 18, 2023

캬.. 멋지네요,,,,, 🥹 일일이 구현하느라 고생 많았습니다..

frontend/src/components/Category/useCategoryMutation.ts Outdated Show resolved Hide resolved
frontend/src/hooks/@common/useDragAndDrop.ts Outdated Show resolved Hide resolved
const updateWritingOrder = useWritingOrderUpdate();
const [draggingIndexList, setDraggingIndexList] = useState<number[]>([]);
const [dragOverIndexList, setDragOverIndexList] = useState<number[]>([]);
const [defaultCategoryId, setDefaultCategoryId] = useState(-1);
Copy link
Collaborator

Choose a reason for hiding this comment

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

defaultCategoryId 무슨 용도로 쓰이는지 궁금합니다. 초기값이 -1 때 생기는 문제점은 없나요?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

기본 카테고리 순서 변경 불가, 기본 카테고리 위로는 순서 변경 불가를 위해 사용하는데 로컬 스토리지 값을 사용하도록 변경하였습니다

frontend/src/components/Category/List/List.tsx Outdated Show resolved Hide resolved
frontend/src/hooks/@common/useDragAndDrop.ts Outdated Show resolved Hide resolved
frontend/src/hooks/@common/useScroll.ts Show resolved Hide resolved
Copy link
Member

@jeonjeunghoon jeonjeunghoon left a comment

Choose a reason for hiding this comment

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

궁금한 점 코멘트에 남겼어요!!
고생 많았어요~!

아 그리고 혹시 낙관적 업데이트도 적용 가능한가용??

frontend/src/components/Category/Item/Item.tsx Outdated Show resolved Hide resolved
frontend/src/components/Category/Item/Item.tsx Outdated Show resolved Hide resolved
frontend/src/components/Category/useDragAndDrop.ts Outdated Show resolved Hide resolved
Comment on lines 22 to 42
const handleDragEnter =
(...ids: number[]): DragEventHandler =>
(e) => {
e.stopPropagation();

// 카테고리 선택하고 글 위에 마우스를 올려도 카테고리로 인식하기 위함.
const dragOverIndex = ids.slice(0, draggingIndexList.length);

// 원래 위치로는 순서 바꾸기 불가.
if (isSameArray(draggingIndexList, dragOverIndex)) {
setDragOverIndexList([]);
return;
}

// 기본 카테고리 위로는 순서 바꾸기 불가.
if (isCategoryDrag() && dragOverIndex[0] === defaultCategoryId) {
setDragOverIndexList([]);
return;
}
setDragOverIndexList(dragOverIndex);
};
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
const handleDragEnter =
(...ids: number[]): DragEventHandler =>
(e) => {
e.stopPropagation();
// 카테고리 선택하고 글 위에 마우스를 올려도 카테고리로 인식하기 위함.
const dragOverIndex = ids.slice(0, draggingIndexList.length);
// 원래 위치로는 순서 바꾸기 불가.
if (isSameArray(draggingIndexList, dragOverIndex)) {
setDragOverIndexList([]);
return;
}
// 기본 카테고리 위로는 순서 바꾸기 불가.
if (isCategoryDrag() && dragOverIndex[0] === defaultCategoryId) {
setDragOverIndexList([]);
return;
}
setDragOverIndexList(dragOverIndex);
};
const handleDragEnter =
(...ids: number[]): DragEventHandler =>
(e) => {
e.stopPropagation();
const dragOverIndex = ids.slice(0, draggingIndexList.length);
const isSamePositionDrag = isSameArray(draggingIndexList, dragOverIndex);
const isDefaultCategoryDrag = isCategoryDrag() && dragOverIndex[0] === defaultCategoryId;
const isImpossibleDrag = isSamePositionDrag || isDefaultCategoryDrag;
setDragOverIndexList(isImpossibleDrag ? [] : dragOverIndex);
};

이건 어떤가요? return 값이 없는 함수라 return 키워드도 제거할 수 있고, 중복된 코드도 줄일 수 있을 것같아요.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

오 좋은데요? 반영하였습니다

frontend/src/components/Category/useDragAndDrop.ts Outdated Show resolved Hide resolved
frontend/src/components/Category/useDragAndDrop.ts Outdated Show resolved Hide resolved
frontend/src/components/Category/useDragAndDrop.ts Outdated Show resolved Hide resolved
frontend/src/components/Category/useDragAndDrop.ts Outdated Show resolved Hide resolved
@ingpyo
Copy link
Collaborator

ingpyo commented Sep 19, 2023

이야 파머니....

@nangkyeonglim
Copy link
Collaborator Author

@jeonjeunghoon

아 그리고 혹시 낙관적 업데이트도 적용 가능한가용??

낙관적 업데이트가 적용하려면 카테고리와 글 목록을 다 상태로 따로 가지고 있어야해서 당장은 어려울 것 같아요..,,

Copy link
Member

@jeonjeunghoon jeonjeunghoon left a comment

Choose a reason for hiding this comment

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

구현하느라 정말 고생 많았어요!
드디어 드래그앤드롭이 되네요 멋져용!!!!

Copy link
Collaborator

@yogjin yogjin left a comment

Choose a reason for hiding this comment

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

수고하셨습니다~

@nangkyeonglim nangkyeonglim merged commit 92cbe0d into develop Sep 20, 2023
@nangkyeonglim nangkyeonglim deleted the feature/drag-and-drop-category-writing-386 branch September 20, 2023 08:31
echo724 pushed a commit that referenced this pull request Sep 22, 2023
* refactor: 카테고리 데이터가 null 인 경우 early return

* feat: 글 및 카테고리 순서 수정 API, 훅 작성

* feat: 타입 가드 유틸 함수 구현

* feat: 글 및 카테고리 순서 수정 API mocking

* feat: 카테고리에 스크롤이 생길 때 `Header`가 고정되도록 수정

* feat: 스크롤이 있을 때 카테고리 추가 시 맨 아래로 스크롤 되는 기능 구현

* design: 카테고리 및 글 hover시 색상 변경

* feat: `throttle` 유틸 함수 구현

* feat: 같은 배열인지 확인하는 유틸 함수 작성

* feat: useDragAndDrop 훅 작성

* feat: 카테고리 드래그 앤 드롭 구현

* feat: 글 드래그 앤 드롭 구현

* feat: 드래그 영역 확장 및 throttle 적용

* refactor: `useDragAndDrop` 훅 파일 이동

* fix: dragEnd 시 버블링으로 인해 2번 API 요청 되는 현상 수정

* refactor: 카테고리 순서 변경 시 테이블 페이지의 글을 받아오는 쿼리 무효화 제거

* refactor: 드래그 종류 확인 함수를 값으로 변경하고 네이밍 수정

* refactor: 마지막 드래그 영역 아이디 상수화

* refactor: 드래그 영역 색 상수화

* docs: 동작 이해를 위한 주석 추가

* refactor: 기본 카테고리 id 로컬스토리지에서 받아오도록 변경

* refactor: `decideDraggingTarget` 조건문 분리

* refactor: `handleDragStart` 버블링 막는 조건문 변경

* refactor: 드래그 위치 인덱스 상수화

* refactor: 드래그 불가한 조건문 명확하게 변경
echo724 pushed a commit that referenced this pull request Oct 6, 2023
* refactor: 카테고리 데이터가 null 인 경우 early return

* feat: 글 및 카테고리 순서 수정 API, 훅 작성

* feat: 타입 가드 유틸 함수 구현

* feat: 글 및 카테고리 순서 수정 API mocking

* feat: 카테고리에 스크롤이 생길 때 `Header`가 고정되도록 수정

* feat: 스크롤이 있을 때 카테고리 추가 시 맨 아래로 스크롤 되는 기능 구현

* design: 카테고리 및 글 hover시 색상 변경

* feat: `throttle` 유틸 함수 구현

* feat: 같은 배열인지 확인하는 유틸 함수 작성

* feat: useDragAndDrop 훅 작성

* feat: 카테고리 드래그 앤 드롭 구현

* feat: 글 드래그 앤 드롭 구현

* feat: 드래그 영역 확장 및 throttle 적용

* refactor: `useDragAndDrop` 훅 파일 이동

* fix: dragEnd 시 버블링으로 인해 2번 API 요청 되는 현상 수정

* refactor: 카테고리 순서 변경 시 테이블 페이지의 글을 받아오는 쿼리 무효화 제거

* refactor: 드래그 종류 확인 함수를 값으로 변경하고 네이밍 수정

* refactor: 마지막 드래그 영역 아이디 상수화

* refactor: 드래그 영역 색 상수화

* docs: 동작 이해를 위한 주석 추가

* refactor: 기본 카테고리 id 로컬스토리지에서 받아오도록 변경

* refactor: `decideDraggingTarget` 조건문 분리

* refactor: `handleDragStart` 버블링 막는 조건문 변경

* refactor: 드래그 위치 인덱스 상수화

* refactor: 드래그 불가한 조건문 명확하게 변경
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
🌟 feature 기능 추가 🖥️ frontend 프론트엔드 작업 🎨 UI 디자인, UI
Projects
None yet
Development

Successfully merging this pull request may close these issues.

카테고리 및 글 드래그앤드롭 기능 구현
5 participants