자바스크립트 초보들이 모두 거쳐간다는 투두리스트.
사실 만든 지 좀 됐는데 요즘 블로그에 글 올릴 시간은 커녕 코딩할 시간도 없어서 허덕이던 터라 미루고 미루다 이제야 올린다..
작성하고, 지우고, 남은 할 일 개수를 카운트하는 아주 기본적인 기능만 가진 투두리스트다.
HTML / CSS
<section class="todoList">
<header class="todoList__title"><span>To Do List</span></header>
<form class="inputContianer">
<input type="text" name="textbox" id="todoInput">
<label class="input__icon">+</label>
<input type="text" name="emptyBox" id="" style="display:none">
</form>
<div class="todoList__main">
</div>
<footer class="todoList__foot">
<p class="todoList__foot__task">You have 4 pending tasks</p><button class="todoList__foot__clearbtn">Clear
All</button>
</footer>
</section>
* {
box-sizing: border-box;
-webkit-font-smoothing: antialiased;
-ms-overflow-style: none; /* IE and Edge */
scrollbar-width: none; /* Firefox */
font-family: "Noto Sans KR", sans-serif;
&::-webkit-scrollbar {
display: none; /* Chrome, Safari, Opera*/
}
}
button {
outline: none;
border: none;
}
body {
margin: 0px;
height: 100vh;
background-image: linear-gradient(62deg, #8ec5fc 0%, #e0c3fc 100%);
background-size: cover;
}
.todoList {
display: flex;
flex-direction: column;
margin: 100px auto;
width: 80%;
max-width: 450px;
height: 50%;
text-align: center;
background-color: white;
padding: 20px;
border: none;
-webkit-box-shadow: 10px 11px 15px -2px #418d8e;
box-shadow: 10px 11px 15px -2px #418d8e;
}
.todoList__title {
width: 100%;
height: 50px;
}
.todoList__title span {
font-size: 25px;
display: block;
margin-top: 10px;
}
.inputContianer {
display: flex;
flex-direction: row;
align-items: center;
height: 30px;
flex-wrap: nowrap;
margin: 10px 0px;
}
#todoInput {
width: 90%;
border: 1px solid rgba(0, 0, 0, 0.2);
height: 30px;
font-size: 16px;
}
.input__icon {
font-size: 23px;
height: 100%;
line-height: 27px;
margin-left: 10px;
cursor: pointer;
background-color: blueviolet;
color: white;
font-weight: bold;
width: 10%;
&:hover {
background-color: lightskyblue;
transition: 300ms ease-in;
}
}
.todoList__main {
height: 300px;
background-color: white;
overflow-y: scroll;
}
.todoList__main__item {
display: flex;
align-items: center;
justify-content: space-between;
padding-left: 20px;
background-color: whitesmoke;
margin: 10px 0px;
}
.trash {
padding: 20px;
cursor: pointer;
&:hover {
background-color: red;
color: white;
transition: 300ms ease-in;
}
}
.todoList__foot {
width: 100%;
height: 50px;
display: flex;
font-size: 14px;
align-items: center;
padding-top: 20px;
justify-content: space-between;
}
.todoList__foot__task {
font-size: 13px;
}
.todoList__foot__clearbtn {
width: 90px;
height: 30px;
background-color: blueviolet;
outline: none;
line-height: 10px;
border: none;
color: white;
cursor: pointer;
&:hover {
background-color: lightskyblue;
transition: 300ms ease-in;
}
}
JavaScript
const textInput = document.querySelector("#todoInput");
const todoList = document.querySelector(".todoList__main");
const todoTask = document.querySelector(".todoList__foot__task");
todoTask.innerHTML = `You have ${todoList.childElementCount} pending tasks`;
const addBtn = document.querySelector(".input__icon");
const clearAllBtn = document.querySelector(".todoList__foot__clearBtn");
let idCount = 0;
textInput.addEventListener("change", handleInput);
todoList.addEventListener("click", deleteBtn);
clearAllBtn.addEventListener("click", clickClearAll);
function addToDo(text) {
const todoItem = document.createElement("div");
todoItem.className = "todoList__main__item";
todoItem.dataset.id = `${idCount}`;
todoItem.innerHTML = `<p class="todoList__main__item--text">${text}</p>
<button class="trash deleteBtn" data-id=${idCount}>
<i class="trash fa-solid fa-trash-can" data-id=${idCount}></i>
</button>`;
todoList.append(todoItem);
idCount++;
todoList.scrollTo(0, todoList.lastChild.getBoundingClientRect().y);
}
function ChangeTaskNum() {
todoTask.innerHTML = `You have ${todoList.childElementCount} pending tasks`;
}
function handleInput(e) {
if (textInput.value == undefined) {
return;
}
addToDo(textInput.value);
ChangeTaskNum();
textInput.value = " ";
}
function deleteBtn(event) {
let tagName = event.target.tagName;
let targetCount = event.target.dataset.id;
if (tagName !== "BUTTON" && tagName !== "I") {
return;
} else {
let todoItem = document.querySelector(
`.todoList__main__item[data-id="${targetCount}"]`
);
todoItem.remove();
}
}
function clickClearAll() {
while (todoList.hasChildNodes()) {
todoList.removeChild(todoList.firstChild);
}
ChangeTaskNum();
}
별다른 특이사항은 없으나 당시에 나는 동적으로 HTML을 생성할 때 안에서 addEventListener를 만들어줄 수 있다는 사실을 모르고 일일히 dataset을 부여하고 삭제할 때마다 dataset을 대조하는 굉장히 비효율적인 방식으로 만들었다..
'Language & Framework > 실습' 카테고리의 다른 글
바닐라 자바스크립트로 드래그앤 드롭 장바구니 만들기(웹개발 기능 대회 문제) (0) | 2022.03.31 |
---|---|
드림코딩 브라우저 101 완강 후기 (0) | 2022.03.30 |
드림코딩 무료 강의 미니 게임 만들기 (0) | 2022.03.23 |
IntersectionObserver를 활용하여 스크롤시 Navbar에 효과 주기 (0) | 2022.03.10 |
바닐라 자바스크립트로 스크롤 위치에 따라 변하는 애니메이션 구현하기. 아주 간단. (0) | 2022.02.28 |