티스토리 뷰

https://todo-list-one-delta.vercel.app/

To-do List

todo-list-one-delta.vercel.app

vercel 배포 후 수정
깃허브 README

https://github.com/123456soobin-choi/TodoList

GitHub - 123456soobin-choi/TodoList: project_TodoList_React

project_TodoList_React. Contribute to 123456soobin-choi/TodoList development by creating an account on GitHub.

github.com

React-redux 숙련 주차 개인 과제_TodoList v.2

- v2.0.0 수정 및 추가한 기능(과제 요구사항 외)

1. favicon 넣었음 - 북마크하면 favicon 보임
2. logo 넣고 hover - rotate 주기
3. input : focus 되었을 때와 value 가질 때 label 에 이벤트
4. 각각의 todo list(card) hover - scale 1.1 크기 키우기
5. todo가 없으면 이미지와 글자 보여주기

- vercel 배포 후 수정한 부분

1. nanoid 활용 - 문자열 일부 자르기

import { customAlphabet } from "nanoid";

const nanoid = customAlphabet("01234567899abcedf", 6);

https://velog.io/@lifeisbeautiful/React-nanoid-%EC%82%AC%EC%9A%A9%ED%95%98%EA%B8%B0

[React] 아이언맨도 사랑하는 nanoid 사용하기

[React] nanoid 사용하기

velog.io

2. todo의 isDone true/false에 따라 이미지 다르게 보여주기

Empty.jsx
: src 안에 써야 한다니!

      <img
        src={isDone ? DoneIcon : WorkingIcon}
        alt="No data"
        className="done"
      />

TodoList.jsx

<Empty isDone={false}>Add something to do...</Empty>
<Empty isDone={true}>Done with your work</Empty>

- 시간이 더 있었다면 넣고 싶었던 기능(아쉬운 점)

1. Button active event 추가
2. Details page icon 및 tooltip 추가
3. Details page에서 todo 정보를 뿌려줄 때 아래의 액션 함수를 사용하지 않고 useSelector를 사용했는데 이 방법도 해봤으면 더 이해가 잘 됐을 것 같다.
todos.js

/* 원래는 이런 형태의 함수
const addTodo= () > {
  return{
    type: "ADD_TODO",
    todo: {id: 3, title: 새로운 todo
    }
  };
};
*/

// Action Creater
const ADD_TODO = "ADD_TODO";
const DELETE_TODO = "DELETE_TODO";
const TOGGLE_TODO = "TOGGLE_TODO";
// const GET_TODO = "GET_TODO";

//새로운 todo를 추가하는 것
export const addTodo = (todo) => {
  return {
    type: ADD_TODO,
    todo,
  };
};

//기존 todo의 id key의 id value 리턴
export const deleteTodo = (id) => {
  return {
    type: DELETE_TODO,
    id,
  };
};

export const toggleTodo = (id) => {
  return {
    type: TOGGLE_TODO,
    id,
  };
};

// export const getTodoById = (id) => {
//   return {
//     type: GET_TODO,
//     id,
//   };
// };

// 초기 상태값
const initialState = { todoList: [] };

// reducer
//배열 []에 추가하거나 삭제하거나 isDone 상태 바꿈
const todos = (state = initialState, action) => {
  switch (action.type) {
    case ADD_TODO:
      return {
        ...state,
        todoList: [...state.todoList, action.todo],
      };

    case DELETE_TODO:
      return {
        ...state,
        todoList: [...state.todoList.filter((todo) => todo.id !== action.id)],
      };

    case TOGGLE_TODO:
      return {
        ...state,
        todoList: [
          ...state.todoList.map((todo) =>
            todo.id === action.id ? { ...todo, isDone: !todo.isDone } : todo
          ),
        ],
      };

    // case GET_TODO:
    //   return {
    //     ...state,
    //     todoList: [...state.todoList.filter((todo) => todo.id === action.id)],
    //   };

    default:
      return { ...state };
  }
};

export default todos;

4. todo 수정하기 기능 추가
5. todo 북마크? 고정해서 따로 보여주는 기능 추가
6. og 이미지 넣기
7. 반응형으로 구현하기
8. 커서 포인터 별로 만들어보기

TROBLE SHOOTING

1. input에 값을 입력하는데 console에 제대로 찍히지 않았음
Form 파일의 changeInput 함수는 key로 input의 속성 중 하나인 name, value로 유저가 입력한 값(제목, 타이틀)을 가지는데
<label> 에서 {name} 으로 적어서 났던 오류였음
→ {label}로 적으니 해결됨

  return (
    <StyledInput>
      <input
        name={name}
        type="text"
        placeholder=""
        onBlur={handleFloat}
        className={hasContent ? "has-content" : ""}
        onChange={onChange}
        value={value}
      />
      <label htmlFor={name} className="label">
        {label}
      </label>
    </StyledInput>
  );

CODE REVIEW_1

1. Form.jsx : InputForm

const Form = () => {
  //인풋에 들어갈 새로운 todo 초기값 선언
  const [todo, setTodo] = useState({ title: "", content: "" });

  //인풋에 값이 입력될 때 발생할 이벤트 함수
  const changeInput = (e) => {
    const { name, value } = e.target;
    setTodo({
      ...todo,
      [name]: value,
    });

    // console.log(todo);
  };

  //dispatch 액션 객체 addTodo를 todos.js의 reducer, todos로 보내줄 거야!
  const dispatch = useDispatch(); //dispatch 변수 선언

  //추가하기 버튼 클릭 시 발생할 이벤트 함수
  const clickaddTodo = () => {
    if (todo.title === "" || todo.content === "") {
      return alert("입력해주세요!");
    } //유효성 검사

    //nanoid 문자열 자르기
    const nanoid = customAlphabet("01234567899abcedf", 3);
    //새로운 todo를 만들어서 액션객체에 담아서 모듈 todos.js로 보내기
    //value는 무엇? 새롭게 만든 todo의 title => todo.title
    const newTodo = {
      title: todo.title,
      content: todo.content,
      isDone: false,
      id: nanoid(),
    };
    dispatch(addTodo(newTodo));

    //추가된 후 인풋 초기화
    setTodo({ title: "", content: "" });

    // console.log(newTodo);
  };

이 부분이 핵심이었다.
dispatch를 사용하기 위해 변수를 선언하고, input에 입력되는 값을 담을 새로운 변수 newTodo를 만든 후 addTodo (액션객체를 반환하는 Action Creater)에 넣어서 reducer에게 보낸다.

  const dispatch = useDispatch(); 
  
    const newTodo = {
      title: todo.title,
      content: todo.content,
      isDone: false,
      id: nanoid(),
    };
    
    dispatch(addTodo(newTodo));

reducer는 새로운 데이터가 추가된 배열 자체를 갈아끼운다. 즉, 새로운 state를 반환함
*todos.js

  switch (action.type) {
    case ADD_TODO:
      return {
        ...state,
        todoList: [...state.todoList, action.todo],
      };


👊🏻 오늘 한 일

  • 10시 Redux 숙련 주차 시험 - 오류 해결 및 설명
  • 12시 숙련 주차 시험 모범 답안 물어보기👍🏻
  • 12:30 ~ 2:30 하체 웨이트 및 스트레칭
  • 4:00 ~ TodoList v.2 - Git tag 버전 관리 & push
  • TodoList v.2 - Vercel 배포 및 과제 제출
  • 숙련 주차 팀 과제 간단히 읽어보기
  • 숙련 주차 팀 과제(keyword 선정) & 글쓰기
  • 19시 숙련 주차 시험 문제 풀이 세션
  • 22시 기술매니저님
  • TodoList v.2 - 기능 일부 수정/ 추가
  • TodoList v.2 README update
  • TodoList v.2 - CODE REVIEW ⭐️

😲 오늘 느낀 점

리덕스 너무 어렵다. 아무것도 안 보고 혼자 처음부터 끝까지 쓰라고 하면 못할 것 같다. 당장 다다음주부터 미니 프로젝트인데 걱정이다...
일요일에 시간을 내서 간단한 투두리스트를 처음부터 다시 만들어야겠다..!

👏🏻 오늘의 칭찬

시험에 최선을 다했다. 새벽에 집중이 잘 됐다.

🤔 오늘 아쉬운 점

디테일 페이지에 정보를 저장하는 방식을 다르게 해보려고 했는데 못 했다.

  • React- redux 강의 들으며 개념 정리
  • [프로그래머스] 35. 문자열 정렬하기 - Git push

이건 못 했음.
code review를 오늘 끝내려고 했는데 이만 자야할 듯...

⛵️ 내일 할 일

  • 9시 React 심화 주차 발제
  • TodoList v.2 - CODE REVIEW ⭐️
  • React- redux 강의 들으며 개념 정리
  • [프로그래머스] 35. 문자열 정렬하기 - Git push
  • 내일 발제 자료 보고 추가하기