반응형

맛집 카드가 늘어날수록 맛집을 한눈에 보기가 어려워진다.
이런 리스트 페이지에서 꼭 필요한 필터링 기능을 이번 포스팅에서 구현해보려고 한다.
1. HTML 부분 추가
index.html에 검색 필터 영역을 추가해본다.
<div class="controls">
<input type="text" id="searchInput" placeholder="검색 (이름, 설명)" />
<select id="categoryFilter">
<option value="">전체 카테고리</option>
<option value="korean">한식</option>
<option value="bunsik">분식</option>
<option value="japanese">일식</option>
<option value="western">양식</option>
<option value="cafe">카페</option>
</select>
<select id="sortSelect">
<option value="">정렬 없음</option>
<option value="priceAsc">가격 낮은순</option>
<option value="priceDesc">가격 높은순</option>
<option value="latest">최신순</option>
</select>
</div>
style.css도 보기 좋게 수정
.controls {
display: flex;
justify-content: flex-end;
align-items: center;
gap: 10px;
margin: 20px 0;
border-radius: 10px;
}
.controls input,
.controls select {
height: 50px;
padding: 0 12px;
font-size: 13px;
border-radius: 8px;
border: 1px solid #ddd;
transition: all 0.2s ease;
}
#searchInput {
width: 100%;
}
.controls input:focus,
.controls select:focus {
outline: none;
border-color: #4dabf7;
box-shadow: 0 0 0 2px rgba(77, 171, 247, 0.2);
}
2. script.js 에서 필터링 구현
기존에는 renderList 함수에서 리스트를 모두 렌더링해왔었다.
이번 수정에서는 applyFilterSort라는 함수를 만들어서 검색, 카테고리필터, 정렬 기능을 넣을것이다.
우선 script.js 상단에 filteredList 라는 전역변수를 만든다.
let filteredList = [];
이 filteredList는 필터가 적용된 리스트를 담게 된다.
기존 renderList함수를 간단하게 변경한다.
async function renderList() {
const loading = document.getElementById("loading");
const container = document.getElementById("cardList");
loading.style.display = "block";
container.innerHTML = "";
try {
restaurants = await fetchData();
applyFilterSort(); // 필터처리는 applyFilterSort에서 함
} catch (err) {
console.error(err);
container.innerHTML = "데이터 불러오기 실패";
} finally {
loading.style.display = "none";
}
}
필터 처리를 해줄 applyFilterSort는 다음과 같다
function applyFilterSort() {
let list = [...restaurants];
// 검색
const keyword =
document.getElementById("searchInput")?.value.toLowerCase() || "";
if (keyword) {
list = list.filter(
(item) =>
item.name.toLowerCase().includes(keyword) ||
(item.comment || "").toLowerCase().includes(keyword),
);
}
// 카테고리 필터
const category = document.getElementById("categoryFilter")?.value;
if (category) {
list = list.filter((item) => item.category === category);
}
// 정렬
const sort = document.getElementById("sortSelect")?.value;
if (sort === "priceAsc") {
list.sort((a, b) => a.price - b.price);
} else if (sort === "priceDesc") {
list.sort((a, b) => b.price - a.price);
} else if (sort === "latest") {
list.sort((a, b) => new Date(b.createdAt) - new Date(a.createdAt));
}
renderCards(list); // 렌더링은 별도 처리
}
문자열 검색 / 카테고리별 검색 / 가격,최신순 정렬이 가능해졌다.
렌더링은 별도의 함수를 만들었다.
내용은 기존 포스팅 내용과 동일하다
function renderCards(list) {
const container = document.getElementById("cardList");
container.innerHTML = "";
list.forEach((item) => {
const card = document.createElement("div");
card.className = "card";
card.classList.add(item.category);
card.innerHTML = `
<div class="card-header">
<div class="title">${item.name}</div>
${item.price ? `<div class="price">${item.price}원</div>` : ""}
</div>
<div class="category">${categoryLabel[item.category]}</div>
<div class="desc">${item.comment || ""}</div>
<div class="card-actions">
<button class="delete-btn" onclick="deleteItem('${item.id}')">삭제</button>
<button class="edit-btn" onclick="editItem('${item.id}')">수정</button>
</div>
`;
container.appendChild(card);
});
}
이제 만든 함수를 이벤트와 연결해준다.
script.js에 아래 코드를 삽입한다.
document
.getElementById("searchInput")
?.addEventListener("input", applyFilterSort);
document
.getElementById("categoryFilter")
?.addEventListener("change", applyFilterSort);
document
.getElementById("sortSelect")
?.addEventListener("change", applyFilterSort);
검색박스에 문자열 입력이 있을때, 카테고리 필터 셀렉트박스가 변경될때, 정렬 셀렉트박스가 변경될때
applyFilterSort 함수를 호출하게 되는 구조이다.
이렇게까지만 하면 간단하게 필터링이 완성된다!
다음 포스팅은 마지막으로 별점 리뷰를 구현할 예정!
반응형
'개발 > 이것저것' 카테고리의 다른 글
| [JavaScript] 나만 쓰는 맛집 리스트 만들기 (카드 UI 구현) - 6. 리뷰 구현 (2) | 2026.04.22 |
|---|---|
| [JavaScript] 나만 쓰는 맛집 리스트 만들기 (카드 UI 구현) - 4. 구글 시트 UPDATE (1) | 2026.04.18 |
| [JavaScript] 나만 쓰는 맛집 리스트 만들기 (카드 UI 구현) - 3. 구글 시트로 CRUD 만들기 (0) | 2026.04.17 |
| [JavaScript] 나만 쓰는 맛집 리스트 만들기 (카드 UI 구현) - 2. 구글 시트 연동하기 (1) | 2026.04.16 |
| [JavaScript] 나만 쓰는 맛집 리스트 만들기 (카드 UI 구현) - 1. 기본 레이아웃 (0) | 2026.04.15 |