-
Notifications
You must be signed in to change notification settings - Fork 2
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
Refactor/#244 기존 SongDetailPage 컴포넌트에 새로운 플로우와 시안을 적용한다. #261
Conversation
1. 기존 nowPlayingTrack 상태에 사용된 rank는 변동 가능한 값이므로 part의 id로 변경 2. 이에 따른 props 변경
api 응답 type 그대로 받도록 수정
1. 테스트가 끝난 컴포넌트의 상태를 공유하기 위해 변경하였음. 2. 파일명 변경
1. 기존 isPlaying은 플레이어의 play와 혼동이 생길 가능성이 많았음. 개선을 통해 플레이중인 트랙이라는 의미를 강조함 2. 이에따라 props가 변경되었음
1. 플레이어 초기화 이후 ref에 할당하도록 개선 2. 관련 이벤트 핸들러 생성
1. 타이머, 플레이어 프로바이더의 함수에서 pause 관련 함수 제거 2. 트랙 컴포넌트의 타이머가 영상 상태와 동기화 되도록 수정
실행중인 파트 기준이 rank -> partId 로 변경됨에 따라 로직을 삭제함
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
리뷰에 도움되도록 주석 달아놓았습니다~
} | ||
}, [videoPlayer, playerState]); | ||
|
||
useEffect(() => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
반복 재생 이펙트 이동 및 로직 개선
const DEFAULT_PART_ID = -1; | ||
|
||
const KillingPartInterface = ({ killingParts, songId }: KillingPartInterfaceProps) => { | ||
const [nowPlayingTrack, setNowPlayingTrack] = useState<KillingPart['id']>(DEFAULT_PART_ID); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이제 변동 가능한 rank 대신 고정값인 id로 관리합니다!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 rank는 왜 변동가능하고 id는 왜 고정인가요? 둘 다 똑같은 KillingPart의 정보 아닌가요?
rank로 관리하나 id로 관리하나 무슨 차이인지 잘 모르겠어요
역으로 생각하면 서버에서 내려주는 killingParts에는 rank가 순서대로 고정적으로 담겨있고,
나머지 정보가 변동된다고 해석할 수도 있을 것 같은데 뭐가 고정이고 뭐가 변동이라는 말인가요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
제 설명이 다소 애매하고 부족했네요.
생각했던 부분을 전부 나열하는게 오히려 좋을것 같아서 아래에 다 적어봅니다!
{killingPart && <CommentList songId={id} partId={killingParts[killingRank! - 1].id} />}
리팩터링 전에는 page컴포넌트가 KillingRank 상태를 가지고 있었고, rank로 killingPart를 찾고,
이걸 코멘트 리스트에 id를 넘기는데 쓰이고 있었어요.
이 부분에서 기존에 있던 KillingRank state대신, nowPlayingTrack state에 담는 값을 id로 바꾸면서
하나로 통일하면 좋겠다고 생각했어요~
또 이 과정에서 "part의 id는 순위가 변동된다고 변하지 않고, rank는 순위에 변동에 따라 바뀌니깐
rank가 어떤걸 정하는 내부적 기준
이 되면 언젠가 의미적으로 햇갈릴 수 있겠다" 막연하게 생각하기도 했고요!
이제 변동 가능한 rank 대신 고정값인 id로 관리합니다!
이 문장 하나로는 택도 없었네요 ㅠ
역으로 생각하면 서버에서 내려주는 killingParts에는 rank가 순서대로 고정적으로 담겨있고,
나머지 정보가 변동된다고 해석할 수도 있을 것 같은데 뭐가 고정이고 뭐가 변동이라는 말인가요?
코난의 의문이 확실히 이해됩니다!
혹시 위 이유들을 읽어보시고 여전히 의문이 남으면 직접 이야기 해주세요!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
리팩터링 전에는 page컴포넌트가 KillingRank 상태를 가지고 있었고, rank로 killingPart를 찾고,
이걸 코멘트 리스트에 id를 넘기는데 쓰이고 있었어요.
이 부분에서 기존에 있던 KillingRank state대신, nowPlayingTrack state에 담는 값을 id로 바꾸면서
하나로 통일하면 좋겠다고 생각했어요~
그렇군요 👍👍
|
||
// const stopPlaying = () => { | ||
// const isPlaying = videoPlayer?.getPlayerState() === 1; | ||
useEffect(() => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
progress bar를 위한 타이머 effect
플레이어 상태를 따라갑니다.
|
||
const Thumbnail = ({ ...props }: ThumbnailProps) => { | ||
const Thumbnail = ({ size = 'lg', ...props }: ThumbnailProps) => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
사이즈 수정 가능하도록 props 추가
playerVars: { start, rel: 0 }, | ||
events: { | ||
onReady: ({ target: player }) => (videoPlayer.current = player), | ||
onStateChange: updatePlayerState, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
playerState 이용하기 위한 이벤트
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
고생하셨습니다 👍👍
코멘트는 전반적으로 어떤 의도로 작성하셨는지 궁금해서 남긴 질문들입니다!
그리고 아래 2가지 추가 질문에 대해서 알려주세용~
- useCallback의 사용 기준을 모르겠어요.
- videoPlayer가 ref로 바뀐 이유가 궁금해요.
if (!comments) { | ||
return null; | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
refactor: 코멘트 컴포넌트 props타입 변경
💬 커밋 메세지로 확인 안되어서 그런데 이건 왜 고치신건가요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
커밋을 잘 나누지 못했네요...
만약 comments 배열 자체가 없거나, comments 배열은 있는데 코멘트가 없어도
랜더링은 진행되어서 댓글 0개
는 보여주는게 좋겠다 생각했어요!
const DEFAULT_PART_ID = -1; | ||
|
||
const KillingPartInterface = ({ killingParts, songId }: KillingPartInterfaceProps) => { | ||
const [nowPlayingTrack, setNowPlayingTrack] = useState<KillingPart['id']>(DEFAULT_PART_ID); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 rank는 왜 변동가능하고 id는 왜 고정인가요? 둘 다 똑같은 KillingPart의 정보 아닌가요?
rank로 관리하나 id로 관리하나 무슨 차이인지 잘 모르겠어요
역으로 생각하면 서버에서 내려주는 killingParts에는 rank가 순서대로 고정적으로 담겨있고,
나머지 정보가 변동된다고 해석할 수도 있을 것 같은데 뭐가 고정이고 뭐가 변동이라는 말인가요?
}; | ||
|
||
const isPlaying = killingPart.rank === nowPlayingTrack; | ||
const isNowPlayingTrack = killingPart.rank === nowPlayingTrack; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
const isNowPlayingTrack = killingPart.rank === nowPlayingTrack; | |
const isNowPlayingTrack = killingPart.id === nowPlayingTrack; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이런일이! 수정하겠습니다!
@@ -13,49 +15,74 @@ import type React from 'react'; | |||
|
|||
interface KillingPartTrackProps { | |||
killingPart: KillingPart; | |||
isPlaying: boolean; | |||
changePlayingTrack: React.ChangeEventHandler<HTMLInputElement>; | |||
isNowPlayingTrack: boolean; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 네이밍에 now는 왜 붙는지 궁금해요
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
개인적으로는 현재 실행중인 트랙이라는 의미를 명확하게 나타내주는게 좋다고 생각했어요
개발 당시에 유튜브 플레이어 관련해서도 isPlaying과 비슷한 의미를 가지는 변수가 있어서 여기서 오는 혼동을 막기위한 이유도 있었어요!
// videoPlayer?.playVideo(); | ||
// }; | ||
const getPlayIcon = useCallback(() => { | ||
if (!isNowPlayingTrack || playerState === 2) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if (!isNowPlayingTrack || playerState === 2) { | |
if (!isNowPlayingTrack || playerState === YT.PlayerState.PAUSED) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
아 이렇게 접근 가능하군요!
하나 배워갑니다! 바로 반영할게요!
// videoPlayer?.seekTo(start, false); | ||
// videoPlayer?.playVideo(); | ||
// }; | ||
const getPlayIcon = useCallback(() => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 왜 useCallback이어야 되는지 궁금해요
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
timer 관련 상태덕분에... 이 함수는 0.1초 마다 매번 새로 만들어지는데요!
타이머 상태로 인한 리랜더링에는 새로 생성되지 않도록 했습니다!
onChange={toggleTrackPlayAndStop} | ||
onClick={toggleTrackPlayAndStop} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 onChange, onClick 둘 다 있는 이유가 뭔가요??
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
라디오 버튼이라 동일한 버튼을 다시 클릭 했을때는 onChange가 터지지 않았어요
재 클릭으로 노래를 멈추게 하려면 클릭이벤트가 필요했습니다!
const SIZE = { | ||
md, | ||
lg, | ||
} as const; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 나눠져있는걸 합쳐도 될 것 같아요
const SIZE = { | |
md, | |
lg, | |
} as const; | |
const SIZE_VARIANTS = { | |
md: css` | |
width: 60px; | |
height: 60px; | |
`, | |
lg: css` | |
width: 70px; | |
height: 70px; | |
`, | |
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
확실히 굳이 나뉘어져 있을 필요가 없네요!
좋은 의견 감사합니다~!
const updatePlayerState: YT.PlayerEventHandler<YT.PlayerEvent> = useCallback(({ target }) => { | ||
const state = target.getPlayerState(); | ||
|
||
setPlayerState(state); | ||
}, []); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 onStateChange는 왜 여기서 정의되어 넘겨주고있고,
player는 왜 onReady에서 set하는건가요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
대화를 통해 의미파악 완료했습니다 ㅎ
프로바이더 한곳에서 관리하도록 변경했습니다!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💬 커스텀훅이 아니라 컨텍스트인 이유가 있을까요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이 부분은 타이머를 커먼으로 가져가느냐,
도메인 종속으로 가져가면서 유튜브 플레이어와 합체시키느냐
고민하다가 그대로 남은 부분입니다.
현 상태로는 코난 말씀대로 커스텀훅인 편이 훨씬 좋겠네요!
다만 아직 (제 머리속)정리가 덜 되어서, 추후에 기능이 정리되면 그때 변경해도 될까요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
리뷰 감사합니다!
답변 및 리뷰 반영 했으니 확인해주세요 ㅎㅎ
본문 코멘트에 대한 답변도 남깁니다 ㅎ
-
useCallback의 사용 기준을 모르겠어요.
충분히 이해됩니다..하하...
제가 의식적으로 메모이제이션을 활용해보고자 노력중인데,
아직 손에 익지 않다보니 어떤 부분은 적용되고, 어떤 부분은 적용되지 않은 상태일거에요.
기준은랜더링에 의해 새롭게 생성될 필요가 없는 값, 함수에는 모두 적용하자!
인데
빼먹은 부분도 많습니다.
성장하는 과정 어딘가 같아요.. 넓은 아량으로 이해해 주시면 감사하겠습니다! -
videoPlayer가 ref로 바뀐 이유가 궁금해요.
플레이어를 상태에 담아 사용했을 때 이점이 없다고 생각했습니다.
랜더링에 영향을 미치지 않는 요소라고 생각했기 때문이에요!
우코와 종종 이야기 나왔던 부분이라 이번 기회로 수정했습니다.
💬 긴가 민가 한데, state로 관리했을 때 이점이 있을까요? 따로 이야기 나눠보시죠!
if (!comments) { | ||
return null; | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
커밋을 잘 나누지 못했네요...
만약 comments 배열 자체가 없거나, comments 배열은 있는데 코멘트가 없어도
랜더링은 진행되어서 댓글 0개
는 보여주는게 좋겠다 생각했어요!
const DEFAULT_PART_ID = -1; | ||
|
||
const KillingPartInterface = ({ killingParts, songId }: KillingPartInterfaceProps) => { | ||
const [nowPlayingTrack, setNowPlayingTrack] = useState<KillingPart['id']>(DEFAULT_PART_ID); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
제 설명이 다소 애매하고 부족했네요.
생각했던 부분을 전부 나열하는게 오히려 좋을것 같아서 아래에 다 적어봅니다!
{killingPart && <CommentList songId={id} partId={killingParts[killingRank! - 1].id} />}
리팩터링 전에는 page컴포넌트가 KillingRank 상태를 가지고 있었고, rank로 killingPart를 찾고,
이걸 코멘트 리스트에 id를 넘기는데 쓰이고 있었어요.
이 부분에서 기존에 있던 KillingRank state대신, nowPlayingTrack state에 담는 값을 id로 바꾸면서
하나로 통일하면 좋겠다고 생각했어요~
또 이 과정에서 "part의 id는 순위가 변동된다고 변하지 않고, rank는 순위에 변동에 따라 바뀌니깐
rank가 어떤걸 정하는 내부적 기준
이 되면 언젠가 의미적으로 햇갈릴 수 있겠다" 막연하게 생각하기도 했고요!
이제 변동 가능한 rank 대신 고정값인 id로 관리합니다!
이 문장 하나로는 택도 없었네요 ㅠ
역으로 생각하면 서버에서 내려주는 killingParts에는 rank가 순서대로 고정적으로 담겨있고,
나머지 정보가 변동된다고 해석할 수도 있을 것 같은데 뭐가 고정이고 뭐가 변동이라는 말인가요?
코난의 의문이 확실히 이해됩니다!
혹시 위 이유들을 읽어보시고 여전히 의문이 남으면 직접 이야기 해주세요!
}; | ||
|
||
const isPlaying = killingPart.rank === nowPlayingTrack; | ||
const isNowPlayingTrack = killingPart.rank === nowPlayingTrack; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이런일이! 수정하겠습니다!
@@ -13,49 +15,74 @@ import type React from 'react'; | |||
|
|||
interface KillingPartTrackProps { | |||
killingPart: KillingPart; | |||
isPlaying: boolean; | |||
changePlayingTrack: React.ChangeEventHandler<HTMLInputElement>; | |||
isNowPlayingTrack: boolean; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
개인적으로는 현재 실행중인 트랙이라는 의미를 명확하게 나타내주는게 좋다고 생각했어요
개발 당시에 유튜브 플레이어 관련해서도 isPlaying과 비슷한 의미를 가지는 변수가 있어서 여기서 오는 혼동을 막기위한 이유도 있었어요!
// videoPlayer?.playVideo(); | ||
// }; | ||
const getPlayIcon = useCallback(() => { | ||
if (!isNowPlayingTrack || playerState === 2) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
아 이렇게 접근 가능하군요!
하나 배워갑니다! 바로 반영할게요!
// videoPlayer?.seekTo(start, false); | ||
// videoPlayer?.playVideo(); | ||
// }; | ||
const getPlayIcon = useCallback(() => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
timer 관련 상태덕분에... 이 함수는 0.1초 마다 매번 새로 만들어지는데요!
타이머 상태로 인한 리랜더링에는 새로 생성되지 않도록 했습니다!
onChange={toggleTrackPlayAndStop} | ||
onClick={toggleTrackPlayAndStop} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
라디오 버튼이라 동일한 버튼을 다시 클릭 했을때는 onChange가 터지지 않았어요
재 클릭으로 노래를 멈추게 하려면 클릭이벤트가 필요했습니다!
const SIZE = { | ||
md, | ||
lg, | ||
} as const; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
확실히 굳이 나뉘어져 있을 필요가 없네요!
좋은 의견 감사합니다~!
const updatePlayerState: YT.PlayerEventHandler<YT.PlayerEvent> = useCallback(({ target }) => { | ||
const state = target.getPlayerState(); | ||
|
||
setPlayerState(state); | ||
}, []); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
대화를 통해 의미파악 완료했습니다 ㅎ
프로바이더 한곳에서 관리하도록 변경했습니다!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이 부분은 타이머를 커먼으로 가져가느냐,
도메인 종속으로 가져가면서 유튜브 플레이어와 합체시키느냐
고민하다가 그대로 남은 부분입니다.
현 상태로는 코난 말씀대로 커스텀훅인 편이 훨씬 좋겠네요!
다만 아직 (제 머리속)정리가 덜 되어서, 추후에 기능이 정리되면 그때 변경해도 될까요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@@ -36,21 +39,15 @@ const killingPart: KillingPart = { | |||
}; | |||
|
|||
const KillingPartTrackWithHook = () => { | |||
const [nowPlayingTrack, setNowPlayingTrack] = useState(-1); | |||
const [nowPlayingTrack, setNowPlayingTrack] = useState<KillingPart['id']>(-1); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
저번에도 비슷한 질문을 해주신것 같은데요!
개발자의 타입 추론
목적으로 접근해 보는건 어떨까요??
해당 코드가 항상 killingPart의 id 만을 받아야 하는 상태인것을 아는 상황이라면 number로 두어도 이해가 되겠지만,
코드를 처음 보는 개발자 입장에서는 이해가 어려울 수도 있겠죠!
number는 조금 넓은 타입이니까요.
위와 같은 이유로 저는 객체 타입의 하위 타입? 이라면 조금더 좁혀서 명시해 주고 있습니다!
답변이 되었을까요?
|
||
const updatePlayer = useCallback((player: YT.Player) => setVideoPlayer(player), []); | ||
const pause = useCallback(() => videoPlayer.current?.pauseVideo(), []); | ||
const play = useCallback(() => videoPlayer.current?.playVideo(), []); | ||
|
||
const seekTo = useCallback( | ||
(start: number) => { | ||
videoPlayer.current?.seekTo(start, true); | ||
play(); | ||
}, | ||
[play] | ||
); | ||
|
||
const initPlayer: YT.PlayerEventHandler<YT.PlayerEvent> = useCallback(({ target }) => { | ||
videoPlayer.current = target; | ||
}, []); | ||
|
||
const updatePlayerState: YT.PlayerEventHandler<YT.PlayerEvent> = useCallback(({ target }) => { | ||
const state = target.getPlayerState(); | ||
|
||
setPlayerState(state); | ||
}, []); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이렇게 함수로 다 래핑한 이유가 궁금해요...(이유: 간단한 로직인데 새로운 함수로 선언되어 있는 부분이 많아서 변수명을 제 뇌 메모리에 쌓아두어야 하는데, 메모리 절대량이 적어요 ㅠㅠ)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
프로젝트 내에
videoPlayer.current?.pauseVideo()
videoPlayer.current?.playVideo()
videoPlayer.current?.seekTo()
가 자주 사용되더라고요
자주 사용되는 함수를 미리 선언해두어서 길이를 줄여보았습니다!
seekTo는 PlayVideo와 같이 쓰여서 묶어두었고요
if ( | ||
!isNowPlayingTrack || | ||
playerState === YT.PlayerState.PAUSED || | ||
playerState === YT.PlayerState.BUFFERING |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
킬링파트를 듣던 중, 인터넷이 불안정하여 재생 중간에 유튜브가 버퍼링되면 다시 reset되나요?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
맞습니다... ㅠ
현재 상태로는 일시정지가 없기 때문에 버퍼링시에 멈춰버립니다
반대로 두면 버퍼링시에 멈추지 않고 나아갑니다
-수정-
버퍼링시에는 일시정지를 하도록 수정하였습니다!
해당 로직을 수정하면 프로그래스 바가 의도대로 동작하지 않아서 추가 수정중입니다!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
수정 완료
const count = useCallback(() => { | ||
setCountedTime((prev) => prev + 0.1); | ||
}, []); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
함수로 감싼 이유가 궁금해요...2
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
해당 함수가 여러곳에서 사용되고 있었을 때 분리한 부분입니다!
하지만 지금은 딱 1번 사용되고 있으니, 분리되어있을 필요가 없네요! 수정하도록 하겠습니다!
const [isStart, setIsStart] = useState(false); | ||
const [autoRestart, setAutoRestart] = useState(false); | ||
|
||
const initialTimeRef = useRef(time); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ref로 주신 이유가 있을까요?
<FlexContainer> | ||
<TitleWrapper aria-label="Top 3 킬링파트 듣기"> | ||
<ItalicTitle aria-hidden="true">Top 3</ItalicTitle> | ||
<NormalTitle aria-hidden="true"> Killing part</NormalTitle> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
<NormalTitle aria-hidden="true"> Killing part</NormalTitle> | |
<NormalTitle aria-hidden="true">Killing part</NormalTitle> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
다른 스타일의 텍스트 사이에 띄어쓰기가 필요해서 넣었습니다!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
아하! 띄어쓰기로 간격을 주지말고 TitleWrapper를 flex로 변경하고 간격을 주면 어떨까요??
<TitleWrapper aria-label="Top 3 킬링파트 듣기">
<ItalicTitle aria-hidden="true">Top 3</ItalicTitle>
<Spacing direction="horizontal" size={10} />
<NormalTitle aria-hidden="true">Killing part</NormalTitle>
</TitleWrapper>
노래 한곡 재생이 끝나도 댓글 창이 유지되도록 수정
1. 구간 반복 기능이 노래의 재생과 타이머에 영향을 미치지 않도록 개선하였음. 개선 전 반복 기능 토글 시 파트의 처음으로 돌아감 타이머가 초기화됨 개선 후 반복 기능 토글 시 토글 기능만 on off 되고 파트의 처음으로 가지 않음. 타이머가 초기화 되지 않음. 기존 개별 Track컴포넌트에 적용했던 TimerProvider를 killingPartInterface 컴포넌트에 적용함.
개선 전 개선 후 관련 기능 잘 돌아갑니다 ㅠㅠ |
📝작업 내용
기존 ToggleGroup 컴포넌트를 KillingpartTrackList 컴포넌트로 대체
DetailPage내 컴포넌트, 상태, effect 분리
기존 구간 반복 기능 개선
기존 댓글 기능이 그대로 동작하도록 함.
추가 작업
Player & Youtube 관련
etc
💬리뷰 참고사항
로직에 대한 의문이 있을 것 같아요.
무조건 물어봐 주세요!
디자인 변경 전
디자인 변경 후
#️⃣연관된 이슈
close #244