Để tạo Menu Icon (hamburger menu) chỉ với CSS, code như sau:
Ví dụ cơ bản: 3 đường gạch
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
.menu-icon {
width: 40px;
height: 7px;
background-color: blue;
margin: 5px 2px;
border-radius: 4px;
transition: all 0.3s ease;
}
</style>
</head>
<body>
<h2>Sample Menu Icon</h2>
<div class="menu-icon"></div>
<div class="menu-icon"></div>
<div class="menu-icon"></div>
</body>
</html>
Nâng cao: Animated Hamburger → X (Checkbox hack)
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
.hamburger {
position: relative;
width: 40px; height: 30px;
cursor: pointer;
display: flex; flex-direction: column;
justify-content: space-between;
}
.hamburger span {
display: block;
width: 100%; height: 4px;
background: #333;
border-radius: 2px;
transition: all 0.3s ease;
transform-origin: center;
}
/* Checkbox hack - ẩn checkbox */
.hamburger input { display: none; }
/* Khi checked: biến thành X */
.hamburger input:checked + span:nth-child(1) {
transform: translateY(13px) rotate(45deg);
}
.hamburger input:checked + span:nth-child(2) {
opacity: 0;
}
.hamburger input:checked + span:nth-child(3) {
transform: translateY(-13px) rotate(-45deg);
}
</style>
</head>
<body>
<label class="hamburger">
<input type="checkbox">
<span></span><span></span><span></span>
</label>
</body>
</html>
Nâng cao: Animated Hamburger → X (JS toggle class)
<button class="hamburger" aria-expanded="false" aria-label="Menu">
<span class="bar"></span>
<span class="bar"></span>
<span class="bar"></span>
</button>
<style>
.hamburger {
background: none; border: none; padding: 8px;
display: flex; flex-direction: column; gap: 5px;
cursor: pointer;
}
.bar {
width: 30px; height: 3px;
background: currentColor;
border-radius: 2px;
transition: transform 0.3s, opacity 0.3s;
transform-origin: center;
}
.hamburger[aria-expanded="true"] .bar:nth-child(1) {
transform: translateY(8px) rotate(45deg);
}
.hamburger[aria-expanded="true"] .bar:nth-child(2) { opacity: 0; }
.hamburger[aria-expanded="true"] .bar:nth-child(3) {
transform: translateY(-8px) rotate(-45deg);
}
</style>
<script>
const btn = document.querySelector('.hamburger');
btn.addEventListener('click', () => {
const expanded = btn.getAttribute('aria-expanded') === 'true';
btn.setAttribute('aria-expanded', !expanded);
});
</script>
Accessibility Checklist
- ✅ Dùng
<button>(không phải div/span) — focusable, Enter/Space kích hoạt - ✅
aria-expandedbáo trạng thái cho screen reader - ✅
aria-labelhoặcaria-labelledbymô tả chức năng - ✅ Focus indicator rõ ràng (
:focus-visible) - ✅ Color contrast đủ cho các thanh (bar)
CSS Art: Menu Icon styles khác
/ * Dots menu (kebab) */
.dots-menu { display: flex; flex-direction: column; gap: 4px; }
.dots-menu span { width: 6px; height: 6px; border-radius: 50%; background: currentColor; }
/ * Meatballs menu (3 dots ngang) */
.meatballs { display: flex; gap: 4px; }
.meatballs span { width: 6px; height: 6px; border-radius: 50%; background: currentColor; }