할 일 목록 만들기

2025. 9. 2. 20:34·HTML&CSS/HTML&CSS 실습

📚 필수 과제

1. 할 일 입력 영역 구현하기

더보기
더보기
더보기

1️⃣ 목적

  • <input> 또는 <textarea> 태그의 구조와 특징을 익힌다.
  • 사용자 입력값을 JS로 처리하는 방법을 학습한다.

2️⃣ 구현 내용

  • 할 일을 입력받을 입력 필드를 만들어보세요.
/* css 코드 */
/* [추가] 입력 UI 최소 스타일 */
#todo-form { display:flex; gap:8px; align-items:stretch; }
#todo-input { flex:1; padding:10px; border:2px solid gray; border-radius:6px; resize:none; }
#submit-btn { background:green; color:white; border:none; border-radius:6px; padding:0 20px; }
#submit-btn:hover { background:darkgreen; }
        
/* HTML 코드 */   
<!-- [추가] 입력 폼 -->
<form id="todo-form">
  <textarea id="todo-input" placeholder="할 일을 입력하세요..." rows="2"></textarea>
  <button type="submit" id="submit-btn">추가</button>
</form>

/* Javascript 코드 */
// [추가] 1단계: 값 읽기만 (리스트 추가 없음)
const form  = document.getElementById('todo-form');
const input = document.getElementById('todo-input');

form.addEventListener('submit', (e) => {
  e.preventDefault();
  const title = input.value.trim();
  if (!title) return;
  console.log('[입력]', title); // 콘솔 확인용
  input.value = '';
  input.focus();
});

 

2. 할 일 추가 기능 구현하기

더보기
더보기
더보기

1️⃣ 목적

  • 이벤트 리스너의 동작 방식을 이해한다.
  • DOM을 동적으로 조작하는 방법을 익힌다.

2️⃣ 구현 내용

  • 추가 버튼을 클릭하거나 Enter 키 입력 시 목록에 항목을 추가해보세요.
/* css 코드*/
/* [추가] 리스트 카드 레이아웃 */
#todo-list { list-style:none; padding:0; margin-top:16px; }
.todo-item {
  display:flex; justify-content:space-between; align-items:center;
  background:lightgray; border-radius:8px; padding:10px 14px; margin-bottom:10px;
}
.todo-actions { display:flex; gap:8px; }
.edit-btn { background:dodgerblue; color:white; border:none; border-radius:4px; padding:6px 12px; }
.edit-btn:hover { background:royalblue; }
.delete-btn { background:crimson; color:white; border:none; border-radius:4px; padding:6px 12px; }
.delete-btn:hover { background:darkred; }

/* html 코드 */
<!-- [추가] 리스트 영역 -->
<ul id="todo-list"></ul>

/* javascript 코드*/
// [추가] li 생성 함수
const list = document.getElementById('todo-list');

function createItem(title) {
  const li = document.createElement('li');
  li.className = 'todo-item';
  li.innerHTML = `
    <span class="item-title">${title}</span>
    <div class="todo-actions">
      <button class="edit-btn">수정</button>
      <button class="delete-btn">삭제</button>
    </div>
  `;
  return li;
}

// [교체] 1단계 submit 핸들러를 '리스트 추가'로 교체
form.addEventListener('submit', (e) => {
  e.preventDefault();
  const title = input.value.trim();
  if (!title) return;
  list.appendChild(createItem(title));
  input.value = '';
  input.focus();
});

 

리스트형 형태의 todo-list 영역 생성

todo-item 에 입력한 값들이 저장, 저장된 값은 수정과 삭제 버튼을 통해 리스트가 저장되는 형태

 

addEventListener을 통해 리스트를 추가하는 기능을 확보하였고,  공백값을 제거하여 값을 읽고, 값을 저장함

3. 할 일 수정/삭제 기능 구현하기

더보기
더보기
더보기

1️⃣ 목적

  • 이벤트 위임(Event Delegation)의 개념을 이해한다.
  • 사용자 동작에 따라 데이터를 수정/삭제하는 방법을 익힌다.

2️⃣ 구현 내용

  • 생성된 각 항목에 수정 및 삭제 버튼을 만들어 기능을 구현해보세요.
// [추가] 수정/삭제 (이벤트 위임)
list.addEventListener('click', (e) => {
  const target = e.target;
  const li = target.closest('.todo-item');
  if (!li) return;

  if (target.classList.contains('delete-btn')) {
    li.remove();
    return;
  }
  if (target.classList.contains('edit-btn')) {
    const span = li.querySelector('.item-title');
    if (!span) return;
    const next = prompt('할 일 수정', span.textContent);
    if (next === null) return;
    const v = next.trim();
    if (v) span.textContent = v;
  }
});

 

삭제와 수정버튼을 추가함으로서 값을 수정하고 입력하는 과정들을 익히고 이벤트 위임으로 인하여 일일히 <li> 태그를 입력하지 않아도 삭제와 수정이 가능한 기능을 구현해 내었다.

버튼을 클릭함으로서 클릭된 값의 .todo-item을 찾아내고, 만약 찾지 못했다면 함수 종료 진행

4. Enter 키로 추가 기능 구현하기

더보기
더보기
더보기

1️⃣ 목적

  • 키보드 이벤트를 처리하는 방법을 이해한다.
  • 여러 입력 방식을 고려한 UX를 설계할 수 있다.

2️⃣ 구현 내용

  • Enter 키를 눌렀을 때도 할 일이 추가되도록 구현해보세요.
// [추가] Enter=제출 (기본 줄바꿈 막음)
input.addEventListener('keydown', (e) => {
  if (e.key === 'Enter') {
    e.preventDefault();
    form.requestSubmit?.() ?? form.dispatchEvent(new Event('submit', { cancelable:true }));
  }
});

 

keydown 핸들러를 통하여 엔터키가 눌렸을 때 submit 기능을 진행하여 값이 입력되게 하고,  Shift가 눌린 상태에서는 적용되지 않도록 하여 줄바꿈 처리를 하게 기능 구현이 되어있음


❤️‍🔥 도전 과제

1. Shift + Enter 줄바꿈 처리

더보기
더보기
더보기

1️⃣ 목적

  • 키 조합 이벤트 처리 방법을 학습한다.
  • 입력 UX 개선을 위한 예외 처리를 익힌다.

2️⃣ 구현 내용

  • Shift + Enter 키 입력 시 줄바꿈이 적용되도록 구현해보세요.
// [교체] Enter=제출, Shift+Enter=줄바꿈, IME 조합 중이면 무시
input.addEventListener('keydown', (e) => {
  if (e.isComposing || e.keyCode === 229) return; // 한글 조합 중에는 제출 X
  if (e.key === 'Enter' && !e.shiftKey) {
    e.preventDefault();
    form.requestSubmit?.() ?? form.dispatchEvent(new Event('submit', { cancelable:true }));
  }
  // Shift+Enter는 기본 줄바꿈 유지
});

 

기존 이슈였던 한글 값 입력 시 마지막 글자가 중복 입력되는 현상이 있었는데, 이에 대한 기능은 아래 트러블 슈팅의 해결 방법과 같이 진행하여 이슈를 해소했음

 

조건문을 통하여 엔터값이 입력되거나 Shift가 눌리지 않은 상태에서만 값을 입력하고 처리하는 기능을 활성화 시켰음 

이로 인해 Shift + Enter는 줄바꿈 처리 기능을 온전히 수행할 수 있게 되었음

2. 줄바꿈 내용 렌더링 처리

더보기
더보기
더보기

1️⃣ 목적

  • 문자열의 \n 데이터를 HTML 요소로 표현하는 방법을 이해한다.
  • 사용자 입력 포맷을 유지하는 출력 방식을 학습한다.

2️⃣ 구현 내용

  • 줄바꿈된 내용을 그대로 브라우저 화면에 표현되도록 만들어보세요. (<br> 활용 등)
/* CSS 코드 */
/* [추가] 줄바꿈(\n) 화면에 반영 */
.item-title { white-space: pre-line; }


/* HTML 코드*/
        function createItem(title) {
            const li = document.createElement('li');
            li.className = 'todo-item';
            li.innerHTML = `
                  <span class="item-title">${title.replace(/\n/g, '<br>')}</span>
                  <div class="todo-actions">
                  <button class="edit-btn">수정</button>
                  <button class="delete-btn">삭제</button>
                  </div>
                      `;
                  return li;
            }

 

적용하는 방법은 총 2가지 방법이 있는 것으로 확인 

 

CSS 코드 내 선언을 통하여 입력된 값과 줄바꿈 값이 그대로 화면에 반영되도록 렌더링하거나

 

createElement 처리과정에서 item-titme의 값에 줄바꿈 기호를 HTML 줄바꿈 태그로 변환하는 과정을 진행해도 됨 <br> 

3. 동적 textarea 높이 조절

더보기
더보기
더보기

1️⃣ 목적

  • DOM 요소의 높이 제어 및 scrollHeight 속성의 개념을 이해한다.
  • 입력 내용에 따라 레이아웃을 반응형으로 처리하는 방법을 학습한다.

2️⃣ 구현 내용

  • 입력 내용이 늘어날 때 입력창 높이도 자동으로 늘어나도록 구현해보세요.
/* CSS 코드*/
/* [추가] 자동 높이 조절 보정 */
#todo-input { overflow-y:hidden; resize:none; }

/* javascript 코드 */
input.addEventListener('input', () => {
  input.style.height = 'auto';
  input.style.height = input.scrollHeight + 'px';
});

 

CSS 코드를 통해 입력된 값이 늘어나도 스크롤바가 생기지 않게 하고, textarea의 크기를 임의로 조정하지 못하게 기능적인 제한을 두었음

 

추가적인 과정으로 textarea.scrollHeight 를 통해 style.height를 자동으로 조절해주는 javascript를 추가적으로 활용하면 입력된 값에 따라 input 박스 크기가 동적으로 조절 되는 부분을 확인할 수 있음 

 

 


☠️ 트러블 슈팅

  • 문제점 ①
    • Shift + Enter 줄바꿈 처리 이후 Enter로 한글 입력을 했을 때 끝 문자가 중복 입력되는 현상이 발생함
  • 해결 방법 / 고민한 방향
    • 중복값이나 입력값에 대한 조건을 걸어서 오류를 방지해야 하는가?
    • 설정한 기본값에서의 문제점이 있는가? 

    • 두 가지의 해결 방법이 있겠지만 우선, isComposing 특성을 활용하여 문제를 해결해 볼 것
      • isComposing 조건문을 활용해 글자가 완성되기 전 상태에서 Enter 키가 눌리면 keyCode가 229로 들어옴.
        if (e.keyCode === 229 ) return; 으로 막아주면, 조합 중에는 Enter를 무시해서 중복 추가가 되지 않도록 함
  • 문제점 ②
    • textarea 내의 줄바꿈 입력값 기능을 설정한 이후 리스트에 추가된 값이 정렬되지 않고 임의의 결과값으로 나오는 현상 

텍스트의 길이에 따라 죄측 정렬이 아닌 윗 줄의 텍스트 길이를 받아 중간값으로 들어가는 상황 발생

  • 해결 방법 / 고민한 방향
    • ① 줄바꿈 태그 <br>을 어디에 넣어야 할지에 대한 고민을 진행함
      • 실제로 값이 입력되고 나오는 곳인 HTML 안에 줄바꿈 태그를 넣어야 함
      • 리스트를 추가하고 저장하는 값인 li.innerHTML 내 title 값에 replace(/\n/g, '<br>')를 추가하여 적용
        • \n (문자열 줄바꿈) : HTML에서는 무시됨
        • <br> (태그) : HTML이 줄을 실제로 바꿔 렌더링
          즉, replace(/\n/g, '<br>')는 문자열 줄바꿈 기호를 HTML 줄바꿈 태그로 변환하는 개념

 

'HTML&CSS > HTML&CSS 실습' 카테고리의 다른 글

점메추 API Ajax 호출  (0) 2025.09.04
점심메뉴 추천기 API  (0) 2025.09.03
점심메뉴 추천기  (0) 2025.09.03
프로필 페이지 제작  (0) 2025.09.02
'HTML&CSS/HTML&CSS 실습' 카테고리의 다른 글
  • 점메추 API Ajax 호출
  • 점심메뉴 추천기 API
  • 점심메뉴 추천기
  • 프로필 페이지 제작
stark77
stark77
하마의 IT 자기개발 이모저모, 백엔드 개발자로 거듭나기
  • stark77
    하마의 개발자 성장일기
    stark77
  • 전체
    오늘
    어제
    • 분류 전체보기
      • 컴퓨터구조와 운영체제
        • 컴퓨터구조
        • 운영체제
      • SQL 기초
      • Spring
        • 백엔드 기초
        • Spring 실습
      • JAVA
        • Java 실습
      • HTML&CSS
        • HTML&CSS 실습
      • Git&GitHub
        • Git&GitHub 실습
      • 내배캠 끄적끄적
        • Today I Learned
      • 유용한 툴 및 사이트 정리
      • 취미
  • 블로그 메뉴

    • 홈
    • 태그
    • 방명록
  • 링크

  • 공지사항

  • 인기 글

  • 태그

    프로세스와 쓰레드
    HTML&CSS
    SpringSecurity
    WebSocket
    네트워크 기초
    java
    경합조건과 교착상태
    백엔드 기초다지기
    웹소켓
    Spriingboot
    algorithm
    for문
    JPA
    Java 문법기초
    실시간 데이터 처리
    Til
    객체지향
    String.format
    객체지향프로그래밍
    RestTemplate
    MVC
    BEAN
    Stomp
    git
    Github
    Spring
    백엔드 기초
    다형성
    jsp
    thymleaf
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.4
stark77
할 일 목록 만들기
상단으로

티스토리툴바