-
Notifications
You must be signed in to change notification settings - Fork 10
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
[4주차] 강다혜 미션 제출합니다. #20
base: master
Are you sure you want to change the base?
Conversation
Feature/setup
Feature/basic layout
Feature/send message
refactor: improve readability
Feature/emoji reaction
hotfix: fix screen max width/height
hotfix/ add fallback
hotfix: use another event
Feature/UI
제출용 branch로 merge
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.
다혜님 과제를 테스트해보면서 UI가 피그마랑 똑같이 정말 잘 구현되어있다는 생각을 했습니다 ㅎㅎ 항상 느끼는 거지만 코드도 깔끔하고 좋네요!! 👍🌟
4주차 과제도 정말 수고 많으셨습니다! 🍀
import CameraIcon from '@assets/CameraIcon'; | ||
import SearchIcon from '@assets/SearchIcon'; |
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.
확실히 절대경로로 import하는게 라인 길이도 줄어들고 훨씬 깔끔하네요! 👍👍 저도 다음 과제에서는 절대경로를 사용해봐야겠습니다!
const myMessageStyle = `bg-blue text-white rounded-r-message-sm | ||
${isFirst ? 'rounded-tr-message-lg' : ''} | ||
${isLast ? 'rounded-br-message-lg' : ''}`; |
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 router = createBrowserRouter([ | ||
{ | ||
path: '/', | ||
element: <MainPage />, | ||
}, | ||
{ | ||
path: '/chat/:id', | ||
element: <ChatPage />, | ||
}, | ||
{ | ||
path: '/follower', | ||
element: <FollowerPage />, | ||
}, | ||
{ | ||
path: '/chat', | ||
element: <ChatListPage />, | ||
}, | ||
]); |
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.
저는 모든 라우팅을 <Route>
태그로 감싸는 방식으로 코드를 작성했는데 이렇게 상수처럼 사용하는 방식도 있네요! 다혜 님 코드를 볼 때마다 항상 변수 사용을 잘 하신다는 생각이 듭니다 ㅎㅎ 간결하고 너무 좋아요!
export default function NavBar({ otherUser }: { otherUser: User }) { | ||
return ( | ||
<nav | ||
className="flex items-center justify-between | ||
w-full h-16 px-4 | ||
border-b border-colors-blue_gray" | ||
> | ||
<div className="flex items-center gap-15px"> | ||
<BackIcon size="24px" /> | ||
|
||
<div className="flex gap-10px"> | ||
<button type="button"> | ||
<img | ||
src={otherUser.profileImgUrl} | ||
alt="user profile" | ||
className="w-icon h-icon rounded-full" | ||
/> | ||
</button> | ||
<div className="flex-col"> | ||
<button type="button"> | ||
<p className="body1">{otherUser.name}</p> | ||
</button> | ||
<p className="body5">{otherUser.id}</p> | ||
</div> | ||
</div> | ||
</div> | ||
|
||
<div className="flex items-center gap-18px"> | ||
<PhoneIcon size="30px" /> | ||
<VideoIcon size="30px" /> | ||
</div> | ||
</nav> | ||
); | ||
} |
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.
PR 코멘트에 /chat/{id}
페이지의 상단 navbar 프로필 사진과 이름을 클릭하면 상대방과 나 사이의 유저 전환이 가능하다고 적어주셨는데 전환 관련 함수가 빠져있는 것 같아요!
onDoubleClick={() => reactToMessage(message.id, userId, '💖')} | ||
> |
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.
반응 기능에서 메시지를 더블클릭하면 텍스트와 요소들이 파란색으로 드래그 되는 현상이 있습니다! 저도 이번주에 이모지 기능을 구현하면서 똑같이 겪었던 문제인데 event.preventDefault();
를 사용하여 해결했습니다. 혹시 도움되실까 해서 코멘트 남깁니다!
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.
안녕하세요 다혜님!
이번 주 코드리뷰를 맡은 송유선입니다. 🤍
다혜님 코드에서는 늘 많은 경험이 묻어나는 것 같아요. 저는 테일윈드를 써본 적이 없는데 (태그 너무 길어지는 거 싫었어요...) 다혜님께서는 테일윈드도 최대한 깔끔하고 구조적으로 쓰시는 것 같아 많이 배웠습니다! 또 절대경로 설정하시는 거나, 커스텀 훅 만드시는 거나 여러모로 다양한 팁들을 많이 알고 계신 것 같아요 ㅎㅎ 다음 주 과제도 저희 함께 파이팅해요 🔥
@@ -0,0 +1,14 @@ | |||
const CracoAlias = require('craco-alias'); |
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.
절대 경로를 사용하셨네요..! 사실 전 대부분 컴포넌트화를 시켰기 때문에 import에서 경로가 자동으로 완성되니까 불편함을 못 겪다가.. 이번에 파일이 많아지면서 폴더 정리를 할 때 애를 먹었어요 😂... 파일을 다른 폴더로 옮기고 싶은데 그럼 경로를 하나하나 수정해줘야 하는 부분이 많아 번거롭더라구요... 그래서 다음엔 꼭 절대 경로를 써봐야겠다고 다짐했답니다. 다혜님께서는 이미 쓰고 계셨군요! 👍🏻
"eslint-plugin-react": "^7.36.1", | ||
"eslint-plugin-react-hooks": "^4.6.2", | ||
"prettier": "^3.3.3", | ||
"tailwindcss": "^3.4.13" |
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.
전 아직 styled-component가 좋은데.. 다들 테일윈드 추천하시더라구요... 저도 담 과제에서는 함 써볼까봐여
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.
쏘큩
border-b border-colors-blue_gray" | ||
> | ||
<div className="flex items-center gap-15px"> | ||
<BackIcon size="24px" /> |
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.
여기에 useNavigate를 활용해서 채팅방 목록으로 돌아가는 경로를 설정해주시면 더욱 좋을 것 같습니다! (+ 미리 navigate 선언하기 + 커서 포인터 추가)
<BackIcon size="24px" /> | |
<BackIcon | |
size="24px" | |
onClick={() => navigate('/chat')} | |
style={{ cursor: 'pointer' }} | |
/> |
const defaultMessageText = ` | ||
relative | ||
body2 | ||
w-fit max-w-256px px-12px py-8px | ||
rounded-message-lg | ||
break-keep whitespace-pre-wrap`; |
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.
재사용 가능성이 있는 걸 미리 이렇게 정의하고 사용하니까 테일윈드 써도 꽤 깔끔하게 보이는 것 같아요..!
다만 제가 다혜 님 페이지를 테스트하다가 발견한 건데, 많은 텍스트를 입력하면 인풋창에는 잘 반영이 되는데 보내진 텍스트에는 반영이 안 되고 잘리더라구요,,, ㅜ
왜 이렇게 한 줄로만 보내지는지 알아보려고 해당 코드를 보니까, 아무래도 break-keep 때문인 것 같아요! 이게 텍스트를 특정 위치에서 강제로 줄바꿈하지 않도록 제한하는 역할을 하니까 한 줄로 나왔던 게 아닐까 합니다... 이 부분만 삭제하시면 텍스트가 말풍선에 제대로 다 담길 것 같아요 :)
그리고 메세지를 더블 클릭하면 반응을 달 수 있는데 지금은 커서가 그 텍스트 입력 모양의 커서라서 포인터로 바꾸면 사용자 관점에서 더욱 편리한 페이지가 될 것 같습니다!
const defaultMessageText = ` | |
relative | |
body2 | |
w-fit max-w-256px px-12px py-8px | |
rounded-message-lg | |
break-keep whitespace-pre-wrap`; | |
const defaultMessageText = ` | |
relative | |
body2 | |
w-fit max-w-256px px-12px py-8px | |
rounded-message-lg | |
whitespace-pre-wrap cursor-pointer`; |
|
||
<div className="flex gap-10px"> | ||
<button type="button"> | ||
<img |
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.
자주 쓰이는 걸 커스텀 훅으로 만든 부분 너무 좋은 것 같아요~~ 그리고 전 전부 그냥 냅다 tsx로 만들었는데ㅋㅋㅋ 다혜님께서 이걸 ts로 작성하신 것 보고 꼼꼼하시다고 느꼈어요 👍🏻
3 & 4주차 미션: React-Messenger
🌊 결과물
배포 링크 :
https://react-messenger-20th.vercel.app/chat
기능 구현
/chat 페이지
/chat/{id} 페이지
🌊 Key Questions - 4주차
React Router의 동적 라우팅(Dynamic Routing)이란 무엇이며, 언제 사용하나요?
예시
/profile/:id
처럼 사용해 id에 따라 각각 다른 사용자의 정보를 보여줄 수 있다./search/:query
경로를 이용하면query
에 따라 검색 결과를 보여줄 수 있다.네트워크 속도가 느린 환경에서 사용자 경험을 개선하기 위해 사용할 수 있는 UI/UX 디자인 전략과 기술적 최적화 방법은 무엇인가요?
이미지 최적화
code splitting
React에서 useState와 useReducer를 활용한 지역 상태 관리와 Context API 및 전역 상태 관리 라이브러리의 차이점을 설명하세요.
useState
useReducer
context API 및. 전역 상태 관리 라이브러리
🌊 Key Questions - 3주차
디자이너로부터 전달받은 피그마 링크, 피그마 캡처본, 디자이너와의 소통 tmi 등
JSX, JS, TSX, TS 각각의 확장자 개념 사용이유와 차이점.
JS
JSX
JSX는 JS의 구문을 확장한 것으로, JS 파일 안에 HTML과 유사한 마크업을 작성할 수 있게 한 것이다.
기존에는 콘텐츠를 HTML, 디자인을 CSS, 로직을 JS 파일에 작성했다. 하지만 JSX를 이용하면 마크업과 렌더링 로직을 같은 파일에 작성할 수 있다!
JSX element는 syntactic sugar로, JSX 코드는 JS 코드로 변환될 수 있다.
따라서 아래와 같은 JSX 코드는
이렇게 컴파일된다!
TS
TSX
TypeScript를 사용하는 이유.
SSR과 CSR 특성 및 차이점.
SSR(Server-Side Rendering)과 CSR(Client-Side Rendering)은 웹을 렌더링하는 두 방식이다.
SSR(Server-Side Rendering)
-SSR은 요청에서 필요한 정보를 파악하고, 적절한 페이지 파일을 가져와 렌더링을 처리한 후, 완성된 HTML과 JS 번들을 돌려주어야 한다.
CSR(Client-Side Rendering)
참고
JavaScript: https://developer.mozilla.org/en-US/docs/Web/JavaScript
Introducing JSX: https://legacy.reactjs.org/docs/introducing-jsx.html
JSX: https://facebook.github.io/jsx/
Writing Markup with JSX: https://react.dev/learn/writing-markup-with-jsx
Using TypeScript: https://react.dev/learn/typescript
https://www.typescriptlang.org/
TypeScript: https://github.com/microsoft/TypeScript
JSX: https://www.typescriptlang.org/docs/handbook/jsx.html
타입스크립트 교과서
SSR 서버 최적화로 비용 아끼기: https://toss.tech/article/ssr-server
Understanding the Difference between CSR and SSR Rendering: https://ritikchourasiya.medium.com/understanding-the-difference-between-csr-and-ssr-rendering-d2fa0eee50e