HTML 완벽 가이드 웹 개발의 첫걸음

HTML 완벽 가이드: 웹 개발의 첫걸음

HTML 완벽 가이드: 웹 개발의 첫걸음

HTML 소개

HTML(HyperText Markup Language)은 웹 페이지를 만들기 위한 표준 마크업 언어입니다. HTML은 웹 페이지의 구조와 내용을 정의하며, 텍스트, 이미지, 비디오 등 다양한 콘텐츠를 표현할 수 있습니다. 모든 웹 개발자가 반드시 마스터해야 하는 기초 기술이며, CSS와 JavaScript와 함께 웹의 3대 핵심 기술 중 하나입니다.

개발 환경 설정

HTML을 시작하기 위해 필요한 것은 단순합니다:

  • 텍스트 에디터: Visual Studio Code, Sublime Text, Atom 등
  • 웹 브라우저: Chrome, Firefox, Safari, Edge 등
  • 파일 확장자: .html 또는 .htm
추천 개발 환경: Visual Studio Code를 사용하면 Live Server 확장 프로그램을 통해 실시간으로 변경사항을 확인할 수 있어 매우 편리합니다.

1. HTML 기본 구조

HTML 문서의 기본 뼈대

모든 HTML 문서는 기본적인 구조를 가지고 있습니다. 이 구조는 웹 브라우저가 문서를 올바르게 해석하고 표시하는 데 필요합니다.

<!DOCTYPE html>
<html lang="ko">
<head>
    <!-- 문서의 메타데이터 영역 -->
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>웹 페이지 제목</title>
</head>
<body>
    <!-- 실제 화면에 표시되는 콘텐츠 영역 -->
    <h1>안녕하세요, HTML!</h1>
    <p>이것은 첫 번째 HTML 문서입니다.</p>
</body>
</html>

주요 구성 요소 설명

<!-- DOCTYPE 선언: HTML5 문서임을 명시 -->
<!DOCTYPE html>

<!-- html 요소: 문서의 루트 요소 -->
<html lang="ko">
    
    <!-- head 요소: 문서 정보를 담는 컨테이너 -->
    <head>
        <!-- 문자 인코딩 설정 -->
        <meta charset="UTF-8">
        
        <!-- 반응형 웹 디자인을 위한 뷰포트 설정 -->
        <meta name="viewport" 
              content="width=device-width, initial-scale=1.0">
        
        <!-- 페이지 설명 -->
        <meta name="description" 
              content="HTML 학습을 위한 예제 페이지입니다">
        
        <!-- 페이지 제목 (브라우저 탭에 표시) -->
        <title>HTML 기본 구조 예제</title>
        
        <!-- 외부 CSS 파일 연결 -->
        <link rel="stylesheet" href="styles.css">
    </head>
    
    <!-- body 요소: 실제 콘텐츠를 담는 컨테이너 -->
    <body>
        <h1>메인 제목</h1>
        <p>본문 내용이 여기에 들어갑니다.</p>
    </body>
</html>

2. 텍스트 관련 요소

HTML은 다양한 텍스트 표현을 위한 요소들을 제공합니다. 제목, 단락, 강조 등 텍스트의 의미와 구조를 명확하게 표현할 수 있습니다.

<!-- 제목 태그 (h1~h6) -->
<h1>가장 큰 제목 (h1)</h1>
<h2>두 번째 제목 (h2)</h2>
<h3>세 번째 제목 (h3)</h3>
<h4>네 번째 제목 (h4)</h4>
<h5>다섯 번째 제목 (h5)</h5>
<h6>가장 작은 제목 (h6)</h6>

<!-- 단락과 줄바꿈 -->
<p>이것은 단락입니다. 단락은 하나의 주제를 가진 글의 묶음입니다.</p>
<p>새로운 단락입니다.<br>
br 태그를 사용하면 같은 단락 내에서 줄바꿈을 할 수 있습니다.</p>

<!-- 텍스트 강조 -->
<p>
    <strong>중요한 텍스트</strong>는 strong 태그를 사용합니다.<br>
    <em>강조하고 싶은 텍스트</em>는 em 태그를 사용합니다.<br>
    <b>굵은 글씨</b>는 b 태그를 사용합니다.<br>
    <i>기울임 글씨</i>는 i 태그를 사용합니다.<br>
    <u>밑줄 텍스트</u>는 u 태그를 사용합니다.<br>
    <s>취소선 텍스트</s>는 s 태그를 사용합니다.
</p>

<!-- 인용문 -->
<blockquote>
    긴 인용문은 blockquote 태그를 사용합니다.
    이 태그는 들여쓰기가 적용되어 인용문임을 시각적으로 표현합니다.
</blockquote>

<p>짧은 인용문은 <q>q 태그를 사용합니다</q>.</p>

<!-- 코드와 사전 형식 텍스트 -->
<p>인라인 코드는 <code>console.log('Hello');</code> 이렇게 표현합니다.</p>

<pre>
사전 형식 텍스트는
    공백과 줄바꿈이
        그대로 유지됩니다.
</pre>

<!-- 기타 텍스트 요소 -->
<p>
    <mark>형광펜 효과</mark>는 mark 태그로 만듭니다.<br>
    <small>작은 글씨</small>는 small 태그를 사용합니다.<br>
    위 첨자는 E=mc<sup>2</sup> 이렇게 표현합니다.<br>
    아래 첨자는 H<sub>2</sub>O 이렇게 표현합니다.
</p>
🖥️ 브라우저 미리보기

가장 큰 제목 (h1)

중요한 텍스트는 strong 태그를 사용합니다.
강조하고 싶은 텍스트는 em 태그를 사용합니다.
형광펜 효과는 mark 태그로 만듭니다.

웹의 핵심은 문서 간의 연결입니다. 링크와 이미지는 웹 페이지를 풍부하게 만드는 중요한 요소입니다.

<!-- 기본 링크 -->
<a href="https://www.example.com">외부 사이트로 이동</a>

<!-- 새 탭에서 열기 -->
<a href="https://www.google.com" target="_blank">새 탭에서 구글 열기</a>

<!-- 같은 페이지 내 이동 (앵커) -->
<a href="#section1">섹션 1로 이동</a>
<h2 id="section1">섹션 1</h2>

<!-- 이메일 링크 -->
<a href="mailto:someone@example.com">이메일 보내기</a>

<!-- 전화번호 링크 -->
<a href="tel:+821012345678">전화 걸기</a>

<!-- 파일 다운로드 -->
<a href="document.pdf" download>PDF 다운로드</a>

<!-- 기본 이미지 -->
<img src="image.jpg" alt="이미지 설명">

<!-- 크기가 지정된 이미지 -->
<img src="photo.jpg" 
     alt="풍경 사진" 
     width="500" 
     height="300">

<!-- 반응형 이미지 -->
<img src="responsive.jpg" 
     alt="반응형 이미지" 
     style="max-width: 100%; height: auto;">

<!-- 이미지 맵 (클릭 가능한 영역) -->
<img src="map.jpg" alt="지도" usemap="#workmap">
<map name="workmap">
    <area shape="rect" 
          coords="34,44,270,350" 
          alt="컴퓨터" 
          href="computer.html">
    <area shape="circle" 
          coords="337,300,44" 
          alt="커피" 
          href="coffee.html">
</map>

<!-- 이미지를 링크로 사용 -->
<a href="https://www.example.com">
    <img src="banner.jpg" alt="클릭하여 이동">
</a>

<!-- picture 요소로 반응형 이미지 제공 -->
<picture>
    <source media="(min-width: 768px)" srcset="large.jpg">
    <source media="(min-width: 480px)" srcset="medium.jpg">
    <img src="small.jpg" alt="반응형 이미지">
</picture>

4. 목록 만들기

HTML은 순서가 있는 목록, 순서가 없는 목록, 그리고 정의 목록을 만들 수 있는 요소들을 제공합니다.

<!-- 순서 없는 목록 (Unordered List) -->
<h3>장보기 목록</h3>
<ul>
    <li>우유</li>
    <li></li>
    <li>계란</li>
    <li>과일
        <ul>
            <li>사과</li>
            <li>바나나</li>
            <li>오렌지</li>
        </ul>
    </li>
</ul>

<!-- 순서 있는 목록 (Ordered List) -->
<h3>레시피 순서</h3>
<ol>
    <li>물을 끓인다</li>
    <li>면을 넣는다</li>
    <li>3분간 끓인다</li>
    <li>스프를 넣는다</li>
    <li>1분 더 끓인다</li>
</ol>

<!-- 다양한 타입의 순서 있는 목록 -->
<ol type="A">
    <li>대문자 알파벳</li>
    <li>순서로 표시</li>
</ol>

<ol type="i">
    <li>로마 숫자</li>
    <li>소문자로 표시</li>
</ol>

<!-- 정의 목록 (Description List) -->
<h3>웹 개발 용어</h3>
<dl>
    <dt>HTML</dt>
    <dd>HyperText Markup Language의 약자로, 웹 페이지의 구조를 정의합니다.</dd>
    
    <dt>CSS</dt>
    <dd>Cascading Style Sheets의 약자로, 웹 페이지의 스타일을 정의합니다.</dd>
    
    <dt>JavaScript</dt>
    <dd>웹 페이지에 동적인 기능을 추가하는 프로그래밍 언어입니다.</dd>
</dl>

5. 테이블 구성

테이블은 데이터를 행과 열로 구성하여 체계적으로 표현할 때 사용합니다.

<!-- 기본 테이블 구조 -->
<table>
    <caption>2024년 1분기 매출 현황</caption>
    <thead>
        <tr>
            <th></th>
            <th>매출액</th>
            <th>전월 대비</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>1월</td>
            <td>1,000만원</td>
            <td>-</td>
        </tr>
        <tr>
            <td>2월</td>
            <td>1,200만원</td>
            <td>+20%</td>
        </tr>
        <tr>
            <td>3월</td>
            <td>1,500만원</td>
            <td>+25%</td>
        </tr>
    </tbody>
    <tfoot>
        <tr>
            <th>합계</th>
            <th colspan="2">3,700만원</th>
        </tr>
    </tfoot>
</table>

<!-- 복잡한 테이블 (병합된 셀) -->
<table border="1">
    <caption>시간표</caption>
    <thead>
        <tr>
            <th>시간</th>
            <th>월요일</th>
            <th>화요일</th>
            <th>수요일</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>09:00</td>
            <td rowspan="2">HTML/CSS</td>
            <td>JavaScript</td>
            <td>React</td>
        </tr>
        <tr>
            <td>10:00</td>
            <!-- 위 셀과 병합됨 -->
            <td colspan="2">프로젝트 실습</td>
        </tr>
    </tbody>
</table>

<!-- 접근성을 고려한 테이블 -->
<table>
    <caption>제품 비교표</caption>
    <thead>
        <tr>
            <th scope="col">제품명</th>
            <th scope="col">가격</th>
            <th scope="col">재고</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <th scope="row">노트북</th>
            <td>150만원</td>
            <td>10개</td>
        </tr>
        <tr>
            <th scope="row">마우스</th>
            <td>3만원</td>
            <td>50개</td>
        </tr>
    </tbody>
</table>

6. 폼과 입력 요소

폼은 사용자로부터 데이터를 입력받아 서버로 전송하는 중요한 인터페이스입니다.

<!-- 회원가입 폼 예제 -->
<form action="/submit" method="post">
    <fieldset>
        <legend>개인 정보</legend>
        
        <!-- 텍스트 입력 -->
        <label for="username">사용자명:</label>
        <input type="text" 
               id="username" 
               name="username" 
               required 
               placeholder="사용자명을 입력하세요">
        <br><br>
        
        <!-- 이메일 입력 -->
        <label for="email">이메일:</label>
        <input type="email" 
               id="email" 
               name="email" 
               required>
        <br><br>
        
        <!-- 비밀번호 입력 -->
        <label for="password">비밀번호:</label>
        <input type="password" 
               id="password" 
               name="password" 
               minlength="8" 
               required>
        <br><br>
        
        <!-- 생년월일 -->
        <label for="birthdate">생년월일:</label>
        <input type="date" 
               id="birthdate" 
               name="birthdate">
        <br><br>
        
        <!-- 전화번호 -->
        <label for="phone">전화번호:</label>
        <input type="tel" 
               id="phone" 
               name="phone" 
               pattern="[0-9]{3}-[0-9]{4}-[0-9]{4}" 
               placeholder="010-1234-5678">
    </fieldset>
    
    <fieldset>
        <legend>추가 정보</legend>
        
        <!-- 라디오 버튼 -->
        <p>성별:</p>
        <input type="radio" id="male" name="gender" value="male">
        <label for="male">남성</label>
        
        <input type="radio" id="female" name="gender" value="female">
        <label for="female">여성</label>
        
        <input type="radio" id="other" name="gender" value="other">
        <label for="other">기타</label>
        <br><br>
        
        <!-- 체크박스 -->
        <p>관심 분야:</p>
        <input type="checkbox" id="web" name="interests" value="web">
        <label for="web">웹 개발</label>
        
        <input type="checkbox" id="mobile" name="interests" value="mobile">
        <label for="mobile">모바일 개발</label>
        
        <input type="checkbox" id="ai" name="interests" value="ai">
        <label for="ai">인공지능</label>
        <br><br>
        
        <!-- 드롭다운 메뉴 -->
        <label for="country">국가:</label>
        <select id="country" name="country">
            <option value="">선택하세요</option>
            <option value="kr">한국</option>
            <option value="us">미국</option>
            <option value="jp">일본</option>
            <option value="cn">중국</option>
        </select>
        <br><br>
        
        <!-- 텍스트 영역 -->
        <label for="message">자기소개:</label><br>
        <textarea id="message" 
                  name="message" 
                  rows="5" 
                  cols="50" 
                  placeholder="자기소개를 입력해주세요"></textarea>
        <br><br>
        
        <!-- 파일 업로드 -->
        <label for="file">이력서 업로드:</label>
        <input type="file" 
               id="file" 
               name="file" 
               accept=".pdf,.doc,.docx">
        <br><br>
        
        <!-- 숫자 입력 -->
        <label for="age">나이:</label>
        <input type="number" 
               id="age" 
               name="age" 
               min="1" 
               max="120" 
               step="1">
        <br><br>
        
        <!-- 범위 선택 -->
        <label for="skill">HTML 숙련도:</label>
        <input type="range" 
               id="skill" 
               name="skill" 
               min="0" 
               max="100" 
               value="50">
    </fieldset>
    
    <!-- 버튼들 -->
    <br>
    <button type="submit">제출</button>
    <button type="reset">초기화</button>
    <button type="button" onclick="alert('클릭!')">일반 버튼</button>
</form>

7. 시맨틱 HTML

시맨틱 HTML은 의미론적 마크업을 통해 문서의 구조를 명확하게 표현합니다. 이는 검색 엔진 최적화(SEO)와 웹 접근성에 매우 중요합니다.

<!-- 시맨틱 HTML5 구조 -->
<header>
    <nav>
        <ul>
            <li><a href="#home"></a></li>
            <li><a href="#about">소개</a></li>
            <li><a href="#services">서비스</a></li>
            <li><a href="#contact">연락처</a></li>
        </ul>
    </nav>
    <h1>웹사이트 제목</h1>
</header>

<main>
    <section id="intro">
        <h2>소개</h2>
        <p>웹사이트에 오신 것을 환영합니다.</p>
    </section>
    
    <article>
        <header>
            <h2>블로그 포스트 제목</h2>
            <time datetime="2024-03-15">2024년 3월 15일</time>
        </header>
        
        <p>블로그 포스트 내용이 여기에 들어갑니다...</p>
        
        <figure>
            <img src="image.jpg" alt="설명 이미지">
            <figcaption>이미지 설명</figcaption>
        </figure>
        
        <footer>
            <p>작성자: 홍길동</p>
        </footer>
    </article>
    
    <aside>
        <h3>관련 링크</h3>
        <ul>
            <li><a href="#">관련 글 1</a></li>
            <li><a href="#">관련 글 2</a></li>
        </ul>
    </aside>
</main>

<footer>
    <address>
        연락처: <a href="mailto:info@example.com">info@example.com</a>
    </address>
    <p>© 2024 회사명. All rights reserved.</p>
</footer>

<!-- 추가 시맨틱 요소들 -->
<details>
    <summary>더 보기</summary>
    <p>숨겨진 내용이 여기에 표시됩니다.</p>
</details>

<dialog open>
    <p>대화 상자 내용</p>
    <button>닫기</button>
</dialog>

<mark>중요한 텍스트</mark>
<time datetime="2024-03-15T10:30">2024년 3월 15일 오전 10시 30분</time>

8. 멀티미디어 요소

HTML5는 오디오와 비디오를 플러그인 없이 직접 재생할 수 있는 요소들을 제공합니다.

<!-- 비디오 요소 -->
<video width="640" 
       height="360" 
       controls 
       autoplay 
       muted 
       loop 
       poster="thumbnail.jpg">
    <source src="video.mp4" type="video/mp4">
    <source src="video.webm" type="video/webm">
    <source src="video.ogg" type="video/ogg">
    브라우저가 video 태그를 지원하지 않습니다.
</video>

<!-- 오디오 요소 -->
<audio controls>
    <source src="audio.mp3" type="audio/mpeg">
    <source src="audio.ogg" type="audio/ogg">
    <source src="audio.wav" type="audio/wav">
    브라우저가 audio 태그를 지원하지 않습니다.
</audio>

<!-- YouTube 비디오 임베드 -->
<iframe width="560" 
        height="315" 
        src="https://www.youtube.com/embed/VIDEO_ID" 
        title="YouTube video player" 
        frameborder="0" 
        allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" 
        allowfullscreen>
</iframe>

<!-- 구글 지도 임베드 -->
<iframe src="https://www.google.com/maps/embed?pb=..." 
        width="600" 
        height="450" 
        style="border:0;" 
        allowfullscreen="" 
        loading="lazy">
</iframe>

<!-- Canvas 요소 (그래픽 그리기용) -->
<canvas id="myCanvas" width="400" height="200">
    브라우저가 canvas를 지원하지 않습니다.
</canvas>

<!-- SVG 그래픽 -->
<svg width="100" height="100">
    <circle cx="50" 
            cy="50" 
            r="40" 
            stroke="green" 
            stroke-width="4" 
            fill="yellow"/>
</svg>

9. 메타 태그와 SEO

메타 태그는 검색 엔진 최적화(SEO)와 소셜 미디어 공유에 중요한 역할을 합니다.

<head>
    <!-- 기본 메타 태그 -->
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    
    <!-- SEO 메타 태그 -->
    <title>페이지 제목 - 60자 이내 권장</title>
    <meta name="description" 
          content="페이지 설명 - 155자 이내로 작성하여 검색 결과에 표시">
    <meta name="keywords" 
          content="HTML, CSS, JavaScript, 웹개발">
    <meta name="author" content="작성자명">
    <meta name="robots" content="index, follow">
    
    <!-- Open Graph 메타 태그 (Facebook, LinkedIn) -->
    <meta property="og:title" content="페이지 제목">
    <meta property="og:description" content="페이지 설명">
    <meta property="og:image" content="https://example.com/image.jpg">
    <meta property="og:url" content="https://example.com/page">
    <meta property="og:type" content="website">
    <meta property="og:locale" content="ko_KR">
    
    <!-- Twitter Card 메타 태그 -->
    <meta name="twitter:card" content="summary_large_image">
    <meta name="twitter:title" content="페이지 제목">
    <meta name="twitter:description" content="페이지 설명">
    <meta name="twitter:image" content="https://example.com/image.jpg">
    
    <!-- 파비콘 -->
    <link rel="icon" type="image/x-icon" href="/favicon.ico">
    <link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png">
    
    <!-- 캐노니컬 URL -->
    <link rel="canonical" href="https://example.com/page">
    
    <!-- 언어 대체 페이지 -->
    <link rel="alternate" hreflang="en" href="https://example.com/en/page">
    <link rel="alternate" hreflang="ko" href="https://example.com/ko/page">
</head>

10. 웹 접근성

웹 접근성은 모든 사용자가 웹 콘텐츠에 접근할 수 있도록 보장하는 중요한 개념입니다.

<!-- ARIA 속성 사용 -->
<nav role="navigation" aria-label="주 메뉴">
    <ul>
        <li><a href="#"></a></li>
        <li><a href="#" aria-current="page">현재 페이지</a></li>
    </ul>
</nav>

<!-- 스킵 네비게이션 -->
<a href="#main-content" class="skip-link">본문으로 건너뛰기</a>

<!-- 랜드마크 역할 -->
<header role="banner">
    <h1>사이트 제목</h1>
</header>

<main role="main" id="main-content">
    <!-- 주요 콘텐츠 -->
</main>

<aside role="complementary" aria-label="사이드바">
    <!-- 보조 콘텐츠 -->
</aside>

<!-- 접근 가능한 폼 -->
<form>
    <label for="email">이메일 주소 (필수)</label>
    <input type="email" 
           id="email" 
           name="email" 
           required 
           aria-required="true"
           aria-describedby="email-help">
    <span id="email-help">유효한 이메일 주소를 입력하세요</span>
</form>

<!-- 접근 가능한 버튼 -->
<button type="button" 
        aria-label="메뉴 열기"
        aria-expanded="false"
        aria-controls="menu">
    <span aria-hidden="true"></span>
</button>

<!-- 접근 가능한 이미지 -->
<img src="chart.png" 
     alt="2024년 1분기 매출 그래프: 1월 100만원, 2월 120만원, 3월 150만원">

<!-- 장식용 이미지 -->
<img src="decoration.png" alt="" role="presentation">

<!-- 라이브 리전 -->
<div role="status" aria-live="polite" aria-atomic="true">
    업데이트된 내용이 여기에 표시됩니다
</div>

<!-- 탭 인터페이스 -->
<div role="tablist">
    <button role="tab" 
            aria-selected="true" 
            aria-controls="panel1">탭 1</button>
    <button role="tab" 
            aria-selected="false" 
            aria-controls="panel2">탭 2</button>
</div>
<div role="tabpanel" id="panel1">탭 1 내용</div>
<div role="tabpanel" id="panel2" hidden>탭 2 내용</div>

11. HTML5 고급 기능

HTML5는 웹 애플리케이션 개발을 위한 다양한 고급 기능과 API를 제공합니다.

<!-- 로컬 스토리지 사용 예제 -->
<script>
// 데이터 저장
localStorage.setItem('username', '홍길동');
localStorage.setItem('theme', 'dark');

// 데이터 읽기
const username = localStorage.getItem('username');
const theme = localStorage.getItem('theme');

// 데이터 삭제
localStorage.removeItem('username');

// 모든 데이터 삭제
localStorage.clear();
</script>

<!-- Geolocation API -->
<button onclick="getLocation()">내 위치 찾기</button>
<p id="location"></p>

<script>
function getLocation() {
    if (navigator.geolocation) {
        navigator.geolocation.getCurrentPosition(showPosition, showError);
    } else {
        document.getElementById("location").innerHTML = 
            "이 브라우저는 Geolocation을 지원하지 않습니다.";
    }
}

function showPosition(position) {
    document.getElementById("location").innerHTML = 
        "위도: " + position.coords.latitude + 
        "
경도: " + position.coords.longitude; } function showError(error) { switch(error.code) { case error.PERMISSION_DENIED: alert("위치 정보 접근이 거부되었습니다."); break; case error.POSITION_UNAVAILABLE: alert("위치 정보를 사용할 수 없습니다."); break; case error.TIMEOUT: alert("위치 정보 요청이 시간 초과되었습니다."); break; case error.UNKNOWN_ERROR: alert("알 수 없는 오류가 발생했습니다."); break; } } </script> <!-- 드래그 앤 드롭 --> <div id="drag1" draggable="true" ondragstart="drag(event)"> 드래그할 수 있는 요소 </div> <div id="dropzone" ondrop="drop(event)" ondragover="allowDrop(event)"> 여기에 드롭하세요 </div> <script> function allowDrop(ev) { ev.preventDefault(); } function drag(ev) { ev.dataTransfer.setData("text", ev.target.id); } function drop(ev) { ev.preventDefault(); var data = ev.dataTransfer.getData("text"); ev.target.appendChild(document.getElementById(data)); } </script> <!-- Web Workers 예제 --> <script> if (typeof(Worker) !== "undefined") { // Worker 생성 const worker = new Worker("worker.js"); // Worker에 메시지 보내기 worker.postMessage({cmd: 'start', msg: 'Hello Worker'}); // Worker로부터 메시지 받기 worker.onmessage = function(e) { console.log('Worker said: ', e.data); }; } </script> <!-- 콘텐츠 편집 가능 --> <div contenteditable="true"> 이 텍스트를 직접 편집할 수 있습니다! </div> <!-- 데이터 속성 --> <div id="product" data-product-id="12345" data-price="29900" data-category="electronics"> 상품 정보 </div> <script> const product = document.getElementById('product'); console.log(product.dataset.productId); // "12345" console.log(product.dataset.price); // "29900" console.log(product.dataset.category); // "electronics" </script> <!-- Progress 요소 --> <label for="file">다운로드 진행률:</label> <progress id="file" value="32" max="100">32%</progress> <!-- Meter 요소 --> <label for="disk">디스크 사용량:</label> <meter id="disk" value="6" min="0" max="10" low="2" high="8" optimum="5"> 6 out of 10 </meter>

12. 실전 예제: 완성된 웹페이지

지금까지 배운 내용을 종합하여 실제 웹페이지를 만들어보겠습니다. 포트폴리오 웹사이트 예제입니다.

<!DOCTYPE html>
<html lang="ko">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>홍길동 - 웹 개발자 포트폴리오</title>
    
    <!-- SEO 메타 태그 -->
    <meta name="description" content="프론트엔드 개발자 홍길동의 포트폴리오 웹사이트">
    <meta name="keywords" content="웹개발, 프론트엔드, HTML, CSS, JavaScript, React">
    
    <!-- Open Graph -->
    <meta property="og:title" content="홍길동 포트폴리오">
    <meta property="og:description" content="웹 개발자 포트폴리오">
    
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }
        
        body {
            font-family: 'Noto Sans KR', sans-serif;
            line-height: 1.6;
            color: #333;
        }
        
        .container {
            max-width: 1200px;
            margin: 0 auto;
            padding: 0 20px;
        }
        
        header {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            padding: 1rem 0;
            position: fixed;
            width: 100%;
            top: 0;
            z-index: 1000;
            box-shadow: 0 2px 5px rgba(0,0,0,0.1);
        }
        
        nav ul {
            list-style: none;
            display: flex;
            justify-content: center;
            align-items: center;
        }
        
        nav li {
            margin: 0 1.5rem;
        }
        
        nav a {
            color: white;
            text-decoration: none;
            transition: opacity 0.3s;
        }
        
        nav a:hover {
            opacity: 0.8;
        }
        
        main {
            margin-top: 60px;
        }
        
        .hero {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            padding: 100px 0;
            text-align: center;
        }
        
        .hero h1 {
            font-size: 3rem;
            margin-bottom: 1rem;
        }
        
        .section {
            padding: 80px 0;
        }
        
        .section:nth-child(even) {
            background-color: #f8f9fa;
        }
        
        h2 {
            text-align: center;
            margin-bottom: 3rem;
            font-size: 2.5rem;
            color: #333;
        }
        
        .skills-grid {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
            gap: 2rem;
            margin-top: 2rem;
        }
        
        .skill-card {
            background: white;
            padding: 2rem;
            border-radius: 10px;
            box-shadow: 0 5px 15px rgba(0,0,0,0.1);
            transition: transform 0.3s;
        }
        
        .skill-card:hover {
            transform: translateY(-5px);
        }
        
        .portfolio-grid {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
            gap: 2rem;
        }
        
        .portfolio-item {
            background: white;
            border-radius: 10px;
            overflow: hidden;
            box-shadow: 0 5px 15px rgba(0,0,0,0.1);
            transition: transform 0.3s;
        }
        
        .portfolio-item:hover {
            transform: scale(1.05);
        }
        
        .portfolio-item img {
            width: 100%;
            height: 200px;
            object-fit: cover;
        }
        
        .portfolio-content {
            padding: 1.5rem;
        }
        
        .contact-form {
            max-width: 600px;
            margin: 0 auto;
        }
        
        .form-group {
            margin-bottom: 1.5rem;
        }
        
        .form-group label {
            display: block;
            margin-bottom: 0.5rem;
            font-weight: bold;
        }
        
        .form-group input,
        .form-group textarea {
            width: 100%;
            padding: 0.8rem;
            border: 1px solid #ddd;
            border-radius: 5px;
            font-size: 1rem;
        }
        
        .form-group textarea {
            resize: vertical;
            min-height: 150px;
        }
        
        .btn {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            padding: 12px 30px;
            border: none;
            border-radius: 5px;
            cursor: pointer;
            font-size: 1rem;
            transition: opacity 0.3s;
        }
        
        .btn:hover {
            opacity: 0.9;
        }
        
        footer {
            background: #333;
            color: white;
            text-align: center;
            padding: 2rem 0;
        }
        
        .social-links {
            margin-top: 1rem;
        }
        
        .social-links a {
            color: white;
            font-size: 1.5rem;
            margin: 0 1rem;
            transition: opacity 0.3s;
        }
        
        .social-links a:hover {
            opacity: 0.7;
        }
        
        @media (max-width: 768px) {
            .hero h1 {
                font-size: 2rem;
            }
            
            nav ul {
                flex-direction: column;
            }
            
            nav li {
                margin: 0.5rem 0;
            }
        }
    </style>
</head>
<body>
    <!-- 스킵 네비게이션 -->
    <a href="#main-content" class="skip-link" style="position: absolute; left: -9999px;">본문으로 건너뛰기</a>
    
    <!-- 헤더 영역 -->
    <header role="banner">
        <nav role="navigation" aria-label="주 메뉴">
            <ul>
                <li><a href="#home"></a></li>
                <li><a href="#about">소개</a></li>
                <li><a href="#skills">기술</a></li>
                <li><a href="#portfolio">포트폴리오</a></li>
                <li><a href="#contact">연락처</a></li>
            </ul>
        </nav>
    </header>
    
    <!-- 메인 콘텐츠 -->
    <main id="main-content" role="main">
        <!-- 히어로 섹션 -->
        <section id="home" class="hero">
            <div class="container">
                <h1>안녕하세요, 홍길동입니다</h1>
                <p>열정적인 웹 개발자</p>
                <a href="#portfolio" class="btn">작업물 보기</a>
            </div>
        </section>
        
        <!-- 소개 섹션 -->
        <section id="about" class="section">
            <div class="container">
                <h2>소개</h2>
                <article>
                    <p>
                        5년 경력의 프론트엔드 개발자입니다. 사용자 경험을 최우선으로 생각하며,
                        깔끔하고 효율적인 코드를 작성하는 것을 목표로 합니다.
                    </p>
                    <p>
                        최신 웹 기술 트렌드를 따라가며, 지속적으로 학습하고 성장하는 개발자입니다.
                        팀워크를 중요시하며, 함께 일하는 동료들과 지식을 공유하는 것을 즐깁니다.
                    </p>
                </article>
            </div>
        </section>
        
        <!-- 기술 스택 섹션 -->
        <section id="skills" class="section">
            <div class="container">
                <h2>기술 스택</h2>
                <div class="skills-grid">
                    <div class="skill-card">
                        <h3>프론트엔드</h3>
                        <ul>
                            <li>HTML5 / CSS3</li>
                            <li>JavaScript (ES6+)</li>
                            <li>React.js</li>
                            <li>Vue.js</li>
                        </ul>
                    </div>
                    <div class="skill-card">
                        <h3>백엔드</h3>
                        <ul>
                            <li>Node.js</li>
                            <li>Express.js</li>
                            <li>MongoDB</li>
                            <li>MySQL</li>
                        </ul>
                    </div>
                    <div class="skill-card">
                        <h3>도구</h3>
                        <ul>
                            <li>Git / GitHub</li>
                            <li>Webpack</li>
                            <li>Docker</li>
                            <li>VS Code</li>
                        </ul>
                    </div>
                </div>
            </div>
        </section>
        
        <!-- 포트폴리오 섹션 -->
        <section id="portfolio" class="section">
            <div class="container">
                <h2>포트폴리오</h2>
                <div class="portfolio-grid">
                    <article class="portfolio-item">
                        <img src="project1.jpg" alt="전자상거래 웹사이트 스크린샷">
                        <div class="portfolio-content">
                            <h3>전자상거래 웹사이트</h3>
                            <p>React와 Node.js를 사용한 풀스택 쇼핑몰</p>
                            <a href="#" class="btn">자세히 보기</a>
                        </div>
                    </article>
                    
                    <article class="portfolio-item">
                        <img src="project2.jpg" alt="태스크 관리 앱 스크린샷">
                        <div class="portfolio-content">
                            <h3>태스크 관리 앱</h3>
                            <p>Vue.js와 Firebase를 활용한 실시간 협업 도구</p>
                            <a href="#" class="btn">자세히 보기</a>
                        </div>
                    </article>
                    
                    <article class="portfolio-item">
                        <img src="project3.jpg" alt="날씨 앱 스크린샷">
                        <div class="portfolio-content">
                            <h3>날씨 앱</h3>
                            <p>OpenWeather API를 활용한 반응형 날씨 애플리케이션</p>
                            <a href="#" class="btn">자세히 보기</a>
                        </div>
                    </article>
                </div>
            </div>
        </section>
        
        <!-- 연락처 섹션 -->
        <section id="contact" class="section">
            <div class="container">
                <h2>연락처</h2>
                <form class="contact-form" action="/submit" method="post">
                    <div class="form-group">
                        <label for="name">이름</label>
                        <input type="text" 
                               id="name" 
                               name="name" 
                               required 
                               aria-required="true">
                    </div>
                    
                    <div class="form-group">
                        <label for="email">이메일</label>
                        <input type="email" 
                               id="email" 
                               name="email" 
                               required 
                               aria-required="true">
                    </div>
                    
                    <div class="form-group">
                        <label for="message">메시지</label>
                        <textarea id="message" 
                                  name="message" 
                                  required 
                                  aria-required="true"></textarea>
                    </div>
                    
                    <button type="submit" class="btn">메시지 보내기</button>
                </form>
            </div>
        </section>
    </main>
    
    <!-- 푸터 영역 -->
    <footer role="contentinfo">
        <div class="container">
            <p>© 2024 홍길동. All rights reserved.</p>
            <div class="social-links">
                <a href="https://github.com" 
                   aria-label="GitHub" 
                   target="_blank">GitHub</a>
                <a href="https://linkedin.com" 
                   aria-label="LinkedIn" 
                   target="_blank">LinkedIn</a>
                <a href="mailto:hong@example.com" 
                   aria-label="Email">Email</a>
            </div>
            <address>
                연락처: <a href="tel:+821012345678">010-1234-5678</a>
            </address>
        </div>
    </footer>
    
    <script>
        // 부드러운 스크롤 효과
        document.querySelectorAll('a[href^="#"]').forEach(anchor => {
            anchor.addEventListener('click', function (e) {
                e.preventDefault();
                const target = document.querySelector(this.getAttribute('href'));
                if (target) {
                    target.scrollIntoView({
                        behavior: 'smooth',
                        block: 'start'
                    });
                }
            });
        });
        
        // 폼 제출 처리
        document.querySelector('.contact-form').addEventListener('submit', function(e) {
            e.preventDefault();
            alert('메시지가 전송되었습니다!');
            this.reset();
        });
        
        // 스크롤 시 헤더 스타일 변경
        window.addEventListener('scroll', function() {
            const header = document.querySelector('header');
            if (window.scrollY > 100) {
                header.style.background = 'rgba(102, 126, 234, 0.95)';
            } else {
                header.style.background = 'linear-gradient(135deg, #667eea 0%, #764ba2 100%)';
            }
        });
    </script>
</body>
</html>

마무리

이 튜토리얼에서는 HTML의 기초부터 고급 기능까지 포괄적으로 다루었습니다. HTML은 웹 개발의 기초이며, 이를 탄탄히 다지는 것이 성공적인 웹 개발자가 되는 첫걸음입니다. 실제 프로젝트에서는 HTML과 함께 CSS와 JavaScript를 활용하여 더욱 동적이고 아름다운 웹사이트를 만들 수 있습니다.

추가 학습을 위한 팁:
  • W3C 표준 문서를 참고하여 최신 HTML 스펙을 확인하세요
  • MDN Web Docs에서 각 요소의 상세한 설명과 예제를 학습하세요
  • 웹 접근성 가이드라인(WCAG)을 숙지하여 모든 사용자를 위한 웹사이트를 만드세요
  • 실제 웹사이트를 분석하고 구조를 파악하는 연습을 하세요
  • CSS와 JavaScript를 함께 학습하여 완전한 웹 페이지를 구현하세요
중요 포인트: HTML은 단순한 마크업 언어가 아니라 웹의 구조와 의미를 정의하는 중요한 언어입니다. 시맨틱 HTML을 사용하고, 웹 접근성을 고려하며, SEO를 최적화하는 것이 현대 웹 개발의 핵심입니다.

댓글 남기기

AI, 코딩, 일상 및 다양한 정보 공유에서 더 알아보기

지금 구독하여 계속 읽고 전체 아카이브에 액세스하세요.

계속 읽기