<리뷰>
후기 작성하기 버튼 생성(review.js)
import { reviewPosting } from "./review-posting.js";
- 후기 작성하기 버튼 클릭 시 reviewPosting 함수가 실행될 예정이라 import를 먼저 해준다
let isRpBtnRendered = false;
- 리뷰 목록과 마찬가지로 작성창이 렌더 됐는지 안 됐는지 확인할 변수가 필요하다
// 이용후기 버튼 눌렀을 때 실행되는 함수
export function review(exhibition_id) {
...
if (rvAllItemsOrganizer.style.display === "none") {
...
// 동행구하기 작성창 연 채로 리뷰 보기 눌렀을 때 작성창 닫아주는 코드
const accompanyPostBox = document.getElementById("accompanyPostBox")
if (accompanyPostBox) {
accompanyPostBox.parentElement.removeChild(accompanyPostBox)
}
// 후기 작성하기 버튼 생성
if (payload) {
if (!isRpBtnRendered) {
const reviewList = document.getElementById("reviewList")
const reviewPostingBtn = document.createElement("button")
reviewPostingBtn.setAttribute("class", "show-rv-posting")
reviewPostingBtn.setAttribute("id", "reviewPostingBtn")
reviewPostingBtn.innerText = "후기 작성하기"
reviewList.prepend(reviewPostingBtn)
reviewPostingBtn.addEventListener("click", function () {
reviewPosting(exhibition_id);
});
isRpBtnRendered = true;
}
// 사라졌던 후기 작성하기 버튼 다시 보이게 하기
var showRvPosting = document.querySelector(".show-rv-posting");
showRvPosting.style.display = "block";
}
if (!isReviewsRendered) {
...
} else {
...
// 후기 작성창 연 채로 이용후기 버튼 다시 눌렀을 때 작성창 닫아주는 코드
const reviewPostBox = document.getElementById("reviewPostBox")
if (reviewPostBox) {
reviewPostBox.parentElement.removeChild(reviewPostBox)
}
}
}
- 일단 7~10번째 줄, 34~37번째줄은 주석 그대로다
- 리뷰에서 동행으로 넘어갔다가 다시 리뷰로 돌아오거나 리뷰에서 작성창을 열었다가 다시 리뷰버튼을 눌러서 리뷰 목록을 닫은 경우에 작성창을 없앤다
- 닫는다고 써놨지만 실제로는 렌더했던 걸 삭제하는 코드다
- isRpBtnRendered 변수를 이용해서 diplay 상태만 바꿔보려고 했으나 동행글 js에서 저 변수를 import 하면 동행글 js에서는 상태를 바꿔줄 수가 없어서 에러가 난다 호환이 안 된달까..?
- 내 배움이 부족해서 제대로 활용하지 못한 걸수도 있지만 일단 에러를 만났기 때문에 그냥 작성창 렌더한 걸 삭제하는 것으로 결정했다
- 12~22번째줄은 로그인한 사용자인 경우, 작성창이 렌더되지 않은 상태라면 작성창을 생성한다 그리고 작성하기 버튼 클릭 시 reviewPosting(exhibition_id) 함수가 실행되도록 했다
- 23번째줄은 리뷰 목록 조회랑 마찬가지로 렌더되었으니 해당 변수를 true로 바꿔서 작성창이 중복 생성되는 것을 막았다
- 26~27번째줄은 아래 후기 작성창 렌더 부분을 봐야 아는 건데 후기 작성창이 렌더되기 전에 후기 작성하기 버튼을 없앤다 그래서 리뷰목록을 닫거나 동행글 보기를 눌렀다가 다시 리뷰 보기로 돌아온 경우 리뷰 작성하기 버튼을 보이게 한 것이다
후기 작성창 렌더(review-posting.js)
import { postReviewAPI, payload, payloadParse } from "./api.js";
- 우선 필요한 함수를 import한다
- postReviewAPI랑 payload는 아직 필요하진 않는데 미리 import 했다
export function reviewPosting(exhibition_id) {
// 후기 작성하기 버튼 안 보이게 하기
var showRvPosting = document.querySelector(".show-rv-posting");
showRvPosting.style.display = "none";
- 후기 작성창이 렌더되면 작성하기 버튼을 안 보이게 한다
- 근데 지금 생각해보니 없애는 거 말고 작성창 닫기 버튼을 만들어도 좋을 것 같다
- 작성, 수정, 삭제 구현 다 되면 해보자...ㅎㅎ지금 할 게 밀렸으니
// 후기 작성창이 없을 때 렌더하기
let reviewPostBox = document.getElementById("reviewPostBox")
if (!reviewPostBox) {
const reviewList = document.getElementById("reviewList")
const grayBox = document.createElement("form")
grayBox.setAttribute("class", "rp-gray-box")
grayBox.setAttribute("id", "reviewPostBox")
// 이미지 업로드
const imgBox = document.createElement("div")
imgBox.setAttribute("class", "rp-img-box")
const fileBox = document.createElement("div")
fileBox.setAttribute("class", "rp-filebox")
const uploadName = document.createElement("input")
uploadName.setAttribute("class", "rp-upload-name")
uploadName.setAttribute("value", "후기 이미지 업로드")
uploadName.setAttribute("placeholder", "후기 이미지 업로드")
fileBox.appendChild(uploadName)
const file = document.createElement("label")
file.setAttribute("for", "file")
file.innerText = "파일찾기"
fileBox.appendChild(file)
const inputFile = document.createElement("input")
inputFile.setAttribute("type", "file")
inputFile.setAttribute("accept", ".jpg,.jpeg,.png,.gif,.bmp")
inputFile.setAttribute("capture", "camera")
fileBox.appendChild(inputFile)
imgBox.appendChild(fileBox)
grayBox.appendChild(imgBox)
const purpleBox = document.createElement("div")
purpleBox.setAttribute("class", "rp-purple-box")
const row1InPurple = document.createElement("div")
row1InPurple.setAttribute("class", "rp-row1-in-purple")
// 닉네임
const nicknameBox = document.createElement("div")
nicknameBox.setAttribute("class", "rp-nickname-box")
nicknameBox.innerText = payloadParse.nickname
row1InPurple.appendChild(nicknameBox)
// 별점
const stars = document.createElement("div")
stars.setAttribute("class", "rp-stars")
for (let i = 1; i <= 5; i++) {
let star = document.createElement("img")
star.setAttribute("class", "rp-star")
star.setAttribute("src", "/static/img/empty-star.png")
star.setAttribute("id", `star${i}`)
star.setAttribute("value", `${i}`)
star.addEventListener("click", function () {
fillStars(i);
});
stars.appendChild(star)
}
row1InPurple.appendChild(stars)
purpleBox.appendChild(row1InPurple)
const row2InPurple = document.createElement("div")
row2InPurple.setAttribute("class", "row2-in-purple")
// 후기 내용
const reviewContent = document.createElement("textarea")
reviewContent.setAttribute("class", "rp-review-content")
reviewContent.setAttribute("placeholder", "후기 내용을 입력해주세요.")
row2InPurple.appendChild(reviewContent)
purpleBox.appendChild(row2InPurple)
const row3InPurple = document.createElement("div")
row3InPurple.setAttribute("class", "rp-row3-in-purple")
// 후기작성 버튼
const rvPostingBtn = document.createElement("button")
rvPostingBtn.setAttribute("type", "button")
rvPostingBtn.setAttribute("class", "rp-review-posting-btn")
rvPostingBtn.setAttribute("id", "rvPostingBtn")
rvPostingBtn.innerText = "입력완료"
row3InPurple.appendChild(rvPostingBtn)
purpleBox.appendChild(row3InPurple)
grayBox.appendChild(purpleBox)
reviewList.prepend(grayBox)
}
- 여기서는 isRendered 변수를 쓰는 대신 작성창 박스를 불러와서 그 박스가 있으면 작성창을 만들지 않고 없으면 만들게끔 했다
- js로 작성창을 만들면서 css가 좀 깨졌지만 여튼 이렇게 만들어진다
// 별 채우기
const starIds = ['star1', 'star2', 'star3', 'star4', 'star5'];
function fillStars(n) {
for (let i = 0; i < starIds.length; i++) {
const star = document.getElementById(starIds[i]);
if (i < n) {
star.setAttribute('src', '/static/img/filled-star.png');
} else {
star.setAttribute('src', '/static/img/empty-star.png');
}
}
}
- 별 채우는 코드는 따로 작성해줬다
<동행글>
- 리뷰 작성창 만드는 것과 로직이 똑같다