Skip to content

Commit

Permalink
[FE] 리뷰 작성 페이지에서 동적으로 에러가 생기는 경우, 해당 에러를 읽어주는 기능 (#891)
Browse files Browse the repository at this point in the history
* feat: Checkbox 선택 여부를 스크린 리더 사용자에게 안내하는 기능 추가

* feat: 탭 접근성 강화
1. Checkbox와 CheckboxItem의 탭 포커스 분리
2. CheckboxItem에 포커싱됐을 때 엔터를 누르면 해당 체크박스를 선택할 수 있는 기능 추가
3. CheckboxItem의 focus시 outline 색상을 primary로 변경

* feat: 에러 메세지가 등장하는 경우 해당 에러 메세지 컴포넌트에 포커스를 주는 훅 작성

* feat: useFocusMessage 훅 적용

* feat: CheckboxItem을 전체 선택했을 때도 선택 여부를 알려주도록 변경

* refactor: handleKeyDown 이벤트 핸들러에서 사용하는 ChangeEvent 타입 캐스팅을 partial을 사용해 명확하게 변경

* refactor: 업데이트된 sr-only 스타일 반영
  • Loading branch information
ImxYJL authored and skylar1220 committed Nov 5, 2024
1 parent 4e30ee2 commit 060d5d3
Show file tree
Hide file tree
Showing 5 changed files with 50 additions and 4 deletions.
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { CheckboxItem } from '@/components';
import { useModals } from '@/hooks';
import { useMultipleChoice } from '@/pages/ReviewWritingPage/form/hooks';
import { useMultipleChoice, useFocusMessage } from '@/pages/ReviewWritingPage/form/hooks';
import { StrengthUnCheckModal } from '@/pages/ReviewWritingPage/modals/components';
import { ReviewWritingCardQuestion } from '@/types';

Expand Down Expand Up @@ -28,6 +28,8 @@ const MultipleChoiceAnswer = ({ question }: MultipleChoiceAnswerProps) => {
},
);

const { messageRef } = useFocusMessage<HTMLParagraphElement>({ isMessageShown: isOpenLimitGuide });

const handleModalCancelButtonClick = () => {
closeModal(MODAL_KEY.confirm);
};
Expand All @@ -51,7 +53,9 @@ const MultipleChoiceAnswer = ({ question }: MultipleChoiceAnswerProps) => {
))}
<S.LimitGuideMessage>
{isOpenLimitGuide && (
<p data-testid="limitGuideMessage">😅 최대 {question.optionGroup?.maxCount}개까지 선택가능해요</p>
<p data-testid="limitGuideMessage" tabIndex={-1} ref={messageRef} aria-live="assertive">
😅 최대 {question.optionGroup?.maxCount}개까지 선택가능해요
</p>
)}
</S.LimitGuideMessage>
{isOpen(MODAL_KEY.confirm) && (
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { useTextAnswer } from '@/pages/ReviewWritingPage/form/hooks';
import { useFocusMessage, useTextAnswer } from '@/pages/ReviewWritingPage/form/hooks';
import { ReviewWritingCardQuestion } from '@/types';

import * as S from './styles';
Expand All @@ -12,6 +12,8 @@ const TextAnswer = ({ question }: TextAnswerProps) => {
question,
});

const { messageRef } = useFocusMessage<HTMLParagraphElement>({ isMessageShown: errorMessage !== '' });

const textLength = `${text.length} / ${maxLength}`;

return (
Expand All @@ -24,7 +26,9 @@ const TextAnswer = ({ question }: TextAnswerProps) => {
onBlur={handleTextAnswerBlur}
/>
<S.TextareaInfoContainer>
<S.ReviewTextareaError>{errorMessage}</S.ReviewTextareaError>
<S.ReviewTextareaError tabIndex={-1} ref={messageRef} aria-live="assertive">
{errorMessage}
</S.ReviewTextareaError>
<S.ReviewTextLength>{textLength}</S.ReviewTextLength>
</S.TextareaInfoContainer>
</S.TextareaContainer>
Expand Down
1 change: 1 addition & 0 deletions frontend/src/pages/ReviewWritingPage/form/hooks/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,4 @@ export { default as useMutateReview } from './useMutateReview';
export { default as useCurrentCardIndex } from './useCurrentCardIndex';
export { default as useNavigateBlocker } from './useNavigateBlocker';
export { default as useResetFormRecoil } from './useResetFormRecoil';
export { default as useFocusMessage } from './useFocusMessage';
21 changes: 21 additions & 0 deletions frontend/src/pages/ReviewWritingPage/form/hooks/useFocusMessage.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { useRef, useEffect } from 'react';

interface useMessageFocusProps {
isMessageShown: boolean;
}

const useFocusMessage = <T extends HTMLElement = HTMLElement>({ isMessageShown }: useMessageFocusProps) => {
const messageRef = useRef<T | null>(null);

useEffect(() => {
if (isMessageShown && messageRef.current) {
messageRef.current.focus();
}
}, [isMessageShown]);

return {
messageRef,
};
};

export default useFocusMessage;
16 changes: 16 additions & 0 deletions frontend/src/styles/globalStyles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,22 @@ const globalStyles = (theme: Theme) => css`
background: transparent;
}
}
.sr-only {
position: absolute;
overflow: hidden;
width: 0.1rem;
height: 0.1rem;
margin: -0.1rem;
padding: 0;
white-space: nowrap;
clip: rect(0, 0, 0, 0);
border: 0;
}
`;

export default globalStyles;

0 comments on commit 060d5d3

Please sign in to comment.