[팀프로젝트] 영화 상세페이지 - 영화 리뷰 댓글창 구현 (1)

liinyeye·2024년 5월 2일
0

Project

목록 보기
5/44

팀프로젝트 소개

개요

  1. 개인과제에서 작성한 [내배캠 인기영화 콜렉션]을 발전시키는 팀 프로젝트
  2. 팀원들의 프로젝트 N개 중 1개를 대표로 선택, 팀 프로젝트로 발전

필수요구사항

  • 상세페이지 구현 + 상세페이지에서 메인페이지로 이동 기능까지
  • 상세 페이지 영화 리뷰 작성 기능 구현
  • UX를 고려한 validation check

맡은 부분 : 상세 페이지 영화 리뷰 작성 기능 구현

localStorage를 이용하여 댓글 기능 만들기

html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Comment</title>
    <link rel="stylesheet" href="detail.css" />
    <script type="module" src="comment.js"></script>
  </head>
  <body>
    <main>
      <div class="review__title">
        <h3>Review</h3>
        <span>12233</span>
      </div>
      <section class="comment-make__box">
        <img
          class="user-image"
          src="https://static.vecteezy.com/system/resources/thumbnails/005/276/776/small/logo-icon-person-on-white-background-free-vector.jpg"
        />
        <form class="comment-write__box">
          <div class="id-password__box">
            <input id="username" type="text" required placeholder="Username" />
            <input
              id="password"
              type="password"
              required
              placeholder="Password"
            />
          </div>
          <div class="comment-write">
            <textarea
              id="write"
              placeholder="감상평을 남겨주세요."
              required
            ></textarea>
            <button class="wrtie-btn">
              <i class="fa-solid fa-pen-to-square fa-lg"></i>
            </button>
          </div>
        </form>
      </section>
      <ul class="comment__wrapper"></ul>
    </main>
    <script
      src="https://kit.fontawesome.com/748fe0d700.js"
      crossorigin="anonymous"
    ></script>
  </body>
</html>

javascript

먼저 html 요소들을 가져와서 변수를 지정해줬다.

const commentForm = document.querySelector(".comment-write__box");
const usernameInput = document.getElementById("username");
const passwordInput = document.getElementById("password");
const commentInput = document.getElementById("write");

form에 submit이벤트를 실행시켰을 때, 로컬스토리지에 값을 가져오고, 저장하고, 댓글을 그리는 것까지 handleSubmitForm함수 안에서 실행시켜준다.

const handleSubmitForm = (event) => {
  event.preventDefault();
  // 입력된 이름, 댓글 내용 가져오기
  const username = usernameInput.value;
  const password = passwordInput.value;
  const comment = commentInput.value;
  //값 비우기, 변수의 값에는 영향 x
  usernameInput.value = "";
  passwordInput.value = "";
  commentInput.value = "";
  //로컬 스토리지에 username이랑 password 저장

  // 값을 담을 새로운 객체 생성
  let newComment = {
    user: username,
    password: password,
    review: comment,
  };
  // 1. 로컬스토리지에서 가져온다.
  const commentsArr = getComments();

  // 새로운 배열에 객체 값 넣어주기
  // 2. 로컬스토리지에 있는 데이터에 추가한다.
  commentsArr.unshift(newComment); //push는 배열 뒤부터 추가, unshift는 앞에서부터 추가

  saveComments(commentsArr); //commentsArr배열을 추가해서 저장
  generateComment(newComment);
};

commentForm.addEventListener("submit", handleSubmitForm);

코멘트를 로컬스토리지에 저장해줄 때는, 객체나 배열을 브라우저에서 읽을 수 있도록 JSON.stringify() 메서드를 사용해서 JSON 데이터 형태로 저장해준다.

//여기서 comments는 인자로 사용
const saveComments = (comments) => {
  localStorage.setItem("comments", JSON.stringify(comments));
};

로컬스토리지에서 다시 데이터를 가져올 때는, 자바스크립트가 읽을 수 있도록 JSON.parse() 메서드로 JSON 형식으로 파싱하여 댓글 배열로 반환한다. 저장된 값이 없다면 빈 배열을 return해주도록 한다. 그리고 데이터를 담은 새로운 배열은 handleSubmitForm 함수와 generateComment 함수에서 사용할 수 있다.

// 로컬 스토리지에서 댓글 배열 가져오기
const getComments = () => {
  const savedComments = localStorage.getItem("comments");

  if (savedComments) {
    return JSON.parse(savedComments); //다시 배열로 바꿔주기
  } else {
    return [];
  }
};

댓글을 만들 때는 우선 html을 그려줄 요소를 가져온 뒤 내용을 초기화 해준다. getComments()로 만들었던 배열을 함수 안에서 사용할 수 있도록 commentDrawn 변수에 다시 할당시켜주고, forEach을 사용해 이 배열을 순회하면서 innerHTML로 댓글을 그려준다.

const generateComment = () => {
  const commentBox = document.querySelector(".comment__wrapper");
  commentBox.innerHTML = "";

  let commentDrawn = getComments();
  //commentsDrawn를 순회하면서 댓글 그리기
  commentDrawn.forEach((element) => {
    commentBox.innerHTML += `
  <li class="comment__box">
    <img
    class="user-image"
    src="https://static.vecteezy.com/system/resources/thumbnails/005/276/776/small/logo-icon-person-on-white-background-free-vector.jpg"
    />
    <section class="comment">
    <h4>${element.user}</h4>
    <p>${element.review}</p>
    </section>
    <div class="rate">
    <i class="fa-regular fa-thumbs-up fa-lg"></i>
    <span>55</span>
    </div>
</li>`;
  });
};

마지막으로 페이지가 로드될 때, 작성된 댓글을 보여줄 수 있도록 해준다.

// 4. 페이지가 로드될 때 기존 댓글 불러오기
window.onload = function () {
  generateComment();
};

궁금한 점과 부족한 내용

  • 한 페이지 안에서만 댓글창을 구현하는게 아니다보니 각각 다른 영화 상세페이지마다 댓글이 다른 값을 가져야하는데, 이 부분을 어떻게 해야할지 살펴봐야할 것 같다.
  • 처음에 handleSubmitForm함수에서 배열을 정의하지 않고, saveComments함수로 값을 저장할 때 외부에서 배열을 정의해줬었는데, 이렇게 하니 페이지를 새로고침하고 다시 댓글을 적을 때 기존의 값이 사라지는 문제가 있었다. 그래서 함수 안에서 다시 배열을 선언해주고, 가져올 배열값을 다시 할당해줬다. 아직 함수 안에서 다시 함수를 사용해주고, 인자를 활용하는 부분이 부족한 것 같다.
profile
웹 프론트엔드 UXUI

0개의 댓글