해당 시리즈의 포스트는 개념 및 이론 정리
와 개인적인 코딩 기록
이 혼용되어 포스팅됩니다. 참고 부탁드립니다.
만들어진 리스트 목록의 내용을 수정할 수 있도록 만들어보자.
일단 수정 상황과 아닌 상황을 구별하기 위해서 isEditing
이라는 state를 만들어준다. 물론 이때 사용하는 것은 useState
hook이다. 이때 기본값은 false
로 해준다.
이는 기본적으로 편집상황이 아니라는 것을 나타낸다.
그리고 편집 상황에서 변하는 input의 value값을 반영하여 나타내기 위해 editedTitle
이란 state도 만들어준다.
이때 들어가는 기본 값은 data의 title을 넣어준다.
위에서 만든 isEditing
state값에 따라 화면에 나타나는 redering값을 다르게 컴포넌트 값을 짜준다.
편집 상황에서 나타낼 값은 위 사진에 보이듯 if문
을 이용해 isEditing === true
일 때를 조건으로 나타날 값을 만들어주면 된다.
그리고 사실상 이것이 기본 값이라고 할 수 있는데 isEditing === false
일 때 나타날 값을 else
쪽에 작성해주면 된다.
먼저 기본 상태에서의 기능들을 살펴보자. 리스트 삭제 기능은 이전에 살펴보았으니 편집 화면으로 넘어가도록 하는 버튼 기능 과 체크박스 기능을 살펴보면 된다.
이 부분은 간단하다. 이미 위에서 isEditing
의 값이 true일 때랑 false일 때 나타낼 코드 값을 짜두었다.
그러면 eidt버튼을 통해서는 이 값을 false에서 true값으로 바꿔주도록 하면된다.
<button onClick={()=>setIsEditing(true)}>edit</button>
위 코드 상황을 보면 checkbox로 되어있는 input에 defaultChecked
값이 completed
로 들어오도록 되어있는 것을 볼 수 있다.
이 값은 기본적으로 false로 들어오도록 되어 있다. 이는 리스트 추가하기에서 살펴볼 수 있다.
그리고 이를 바꿔줄 함수로 handleCompleteChage
를 만들어준다.
const handleCompleteChange = () => {
let newTodoData = todoData.map(data => {
if (data.id === id) {
data.completed = !data.completed;
}
return data;
})
setTodoData(newTodoData)
};
이 함수는 해당 체크박스에 해당하는 리스트의 id
값 data에 들어있는 값들의 id와 비교한 후 해당 id가 일치하는 data값의 complete를 반대로 바꿔주고, 그 외의 값은 그냥 내버려둔다.
이때 주의해야할 점은 함수에서 id값이 전달되지 않았음에도
if (data.id === id)
라는 값을 통해 id를 비교하였는데, 그 이유는 코드를 이 포스트에 작성할 수가 없어 생략된 부분이 있지만 이미props
를 통해 이List컴포넌트
는 하나의 id값을 가지고 있기 때문이다.컴포넌트의 설계는 App > Lists > List의 형식이다.
그리고 이렇게 생성된 새 data값을 setTodoData()
를 이용해 반영해주는 것이다.
그리고 이렇게 체크박스가 체크되었을 때 나타나는 css효과도 바뀔 수 있도록 해준다. 이는 위 사진에서 주황생 밑줄을 확인하면 볼 수 있는데 삼항연산자
를 이용해서 className에 completed
의 값에 따라 적용될 class값을 달리 해주어 적용해줄 수 있다.
이제 위에서 만든 버튼을 이용하면 isEditing
의 값을 true로 바꿔주어 편집화면으로 넘어올 수 있을 것이다.
이곳에서 구현해야할 기능은 새로운 값 받기, 저장하기, 취소하기이다.
이는 매우 쉽다. 일단 편집중인 상태의 코드를 보면 input값의 value가 editedTitle
이라는 state가 기본값으로 들어가도록 하였고, 이는 위 state를 생성한 것을 보면 state의 기본값이 해당 리스트의 title이 들어가도록 한 것을 볼 수 있다.
따라서 이 화면에서 input값에는 자동적으로 기존 title값이 들어간다.
그리고 타이핑할 때마다 이 값이 바뀌도록 함수를 만들어주자.
const handleEditChange = (e) => {
setEditedTitle(e.target.value)
}
이 함수 는 매우 쉽다. 타이핑 값을 받아오는 것은 이전에 작성했던 키보드 타이핑값 받기포스트를 참고하면 된다.
새로운 값을 입력해 받아왔다면 이를 data에 새롭게 반영해 저장해주면 된다.
이는 form에서 submit
이 일어날 때와 save버튼이 클릭되었을 때 실행되는 함수를 만들어 구현하도록 하자.
const handleSubmit = (e) => {
e.preventDefault();
let newTodoData = todoData.map((data) => {
if (data.id === id) {
data.title = editedTitle
}
return data;
});
setTodoData(newTodoData);
setIsEditing(false);
}
일단 위에서 e.preventDefault()
는 page가 리로드되는 것을 방지하기 위함이다.
그리고 아래를 살펴보면, 새로운 data값 변수를 만들어주고 해당 변수에 map메소드
를 실행시켰다. 그리고 이 메소드 안에서 id값 비교를 통해 해당 리스트의 id값과 일치하는 id의 data 리스트의 title값을 바뀐 값으로 반영해주었다.
이때도 체크박스 기능구현할 때와 마찬가지로 함수에서 id값이 전달되지 않았음에도
if (data.id === id)
라는 값을 통해 id를 비교가 가능한 이유는 이미props
를 통해 이List컴포넌트
는 하나의 id값을 가지고 있기 때문이다.
그리고 이를 setTodoData
를 통해 data에 적용시키고, setEditing(false)
를 통해 편집상태 화면을 닫아준다.
잘못된 부분에 대한 지적은 얼마든지 환영입니다.
감사합니다.