14 minLesson 3 of 40
HTML5 Foundations
Links, Images & Media
Links, Images & Media
HTML links connect pages together, and images and media bring content to life. This lesson covers every attribute and best practice you need to build accessible, performant web pages.
Links (anchor tags)
<!-- External link -->
<a href="https://example.com">Visit Example</a>
<!-- Internal page link -->
<a href="/about">About Us</a>
<a href="./contact.html">Contact</a>
<!-- Same-page anchor link -->
<a href="#section-id">Jump to section</a>
<h2 id="section-id">This Section</h2>
<!-- Email and phone links -->
<a href="mailto:hello@example.com">Email us</a>
<a href="tel:+15551234567">Call us</a>
<!-- Download link -->
<a href="/files/report.pdf" download>Download Report</a>
<a href="/files/report.pdf" download="annual-report-2026.pdf">Download</a>
<!-- Open in new tab (always add rel="noopener" for security) -->
<a href="https://example.com" target="_blank" rel="noopener noreferrer">
External Link
</a>
Why rel="noopener noreferrer" matters: Without it, the new tab can access your page via window.opener — a security vulnerability called reverse tabnapping.
Images
<!-- Basic image -->
<img src="photo.jpg" alt="A mountain at sunset">
<!-- alt text rules:
- Describe the content and purpose
- Decorative images: alt="" (empty, NOT missing)
- Icons with text next to them: alt=""
- Never: alt="image" or alt="photo"
-->
<!-- Width and height — prevent layout shift -->
<img src="hero.jpg" alt="Office team" width="800" height="450">
<!-- Lazy loading (don't load until near viewport) -->
<img src="below-fold.jpg" alt="Product" loading="lazy" width="400" height="300">
<!-- Eager loading for above-fold images -->
<img src="hero.jpg" alt="Hero" loading="eager">
<!-- High-priority fetch hint for LCP images -->
<img src="hero.jpg" alt="Hero" fetchpriority="high">
Responsive Images
<!-- srcset: multiple resolutions -->
<img
src="photo-800.jpg"
srcset="photo-400.jpg 400w,
photo-800.jpg 800w,
photo-1200.jpg 1200w"
sizes="(max-width: 600px) 400px,
(max-width: 1200px) 800px,
1200px"
alt="Responsive photo"
width="1200"
height="800"
>
<!-- picture: different formats and art direction -->
<picture>
<!-- Modern formats first (browser picks first it supports) -->
<source type="image/avif" srcset="hero.avif">
<source type="image/webp" srcset="hero.webp">
<!-- Fallback for old browsers -->
<img src="hero.jpg" alt="Company headquarters" width="1200" height="600">
</picture>
<!-- Art direction: different crop for mobile -->
<picture>
<source media="(max-width: 600px)" srcset="hero-mobile.jpg">
<source media="(max-width: 1200px)" srcset="hero-tablet.jpg">
<img src="hero-desktop.jpg" alt="Product showcase">
</picture>
Figure and Figcaption
<!-- Semantic image with caption -->
<figure>
<img src="chart.png" alt="Bar chart showing Q3 sales by region">
<figcaption>Figure 1: Q3 2026 sales performance by region</figcaption>
</figure>
<!-- Figures can also wrap code, quotes, etc. -->
<figure>
<blockquote>
<p>The best way to predict the future is to create it.</p>
</blockquote>
<figcaption>— Peter Drucker</figcaption>
</figure>
Video
<video
width="800"
height="450"
controls
poster="thumbnail.jpg"
preload="metadata"
>
<source src="video.mp4" type="video/mp4">
<source src="video.webm" type="video/webm">
<p>Your browser doesn't support video. <a href="video.mp4">Download it</a></p>
</video>
<!-- Autoplay video (muted required for autoplay to work in most browsers) -->
<video autoplay muted loop playsinline>
<source src="background.mp4" type="video/mp4">
</video>
Video attributes:
controls— show player controlsautoplay— start immediately (requiresmuted)muted— no audioloop— replay when finishedplaysinline— play inline on iOS (not fullscreen)poster— thumbnail shown before playpreload—"none"|"metadata"|"auto"
Audio
<audio controls>
<source src="podcast.mp3" type="audio/mpeg">
<source src="podcast.ogg" type="audio/ogg">
Your browser doesn't support audio.
</audio>
Embedded Content (iframes)
<!-- YouTube embed -->
<iframe
width="560"
height="315"
src="https://www.youtube.com/embed/VIDEO_ID"
title="Video title"
frameborder="0"
allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture"
allowfullscreen
loading="lazy"
></iframe>
<!-- Google Maps embed -->
<iframe
src="https://maps.google.com/maps?q=New+York&output=embed"
width="600"
height="400"
style="border:0"
allowfullscreen
loading="lazy"
title="Office location map"
></iframe>
SVG
<!-- Inline SVG (styleable with CSS, accessible) -->
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="24" height="24" aria-hidden="true">
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"/>
</svg>
<!-- SVG as img (simpler but not styleable) -->
<img src="logo.svg" alt="Company logo" width="120" height="40">
Next lesson: Forms — building accessible, user-friendly forms with HTML5.
📱
Get Notes Free →Get this course's notes on Telegram!
Free cheat sheets, summaries & practice exercises