Computer >> Hướng Dẫn Máy Tính >  >> Lập Trình >> CSS

Cách tạo Blog Layout (Bố cục blog) Responsive với CSS

Giới thiệu

Blog layout điển hình gồm: Header/Navbar, Main content area (bài viết chính + sidebar), Footer. Bài viết hướng dẫn xây dựng layout responsive với CSS Grid/Flexbox hiện đại.

Ví dụ hiện đại: CSS Grid Layout (Khuyến nghị)

<!DOCTYPE html>
<html lang="vi">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>Responsive Blog Layout</title>
    <style>
        * { box-sizing: border-box; margin: 0; padding: 0; }
        body { font-family: "Segoe UI", Tahoma, Geneva, Verdana, sans-serif; line-height: 1.6; background: #fafafa; }
        
        /* Layout Grid Container */
        .siteGrid {
            display: grid;
            grid-template-rows: auto 1fr auto;
            min-height: 100vh;
        }
        
        /* Header / Navbar */
        .siteHeader {
            background: #8816b6;
            color: #fff;
            padding: 1rem 2rem;
            position: sticky; top: 0; z-index: 100;
            display: flex; justify-content: space-between; align-items: center;
            flex-wrap: wrap; gap: 1rem;
        }
        .logo { font-size: 1.8rem; font-weight: 700; color: #fff; text-decoration: none; }
        .navList { display: flex; list-style: none; gap: 2rem; }
        .navList a { color: #ffe600; text-decoration: none; font-weight: 500; transition: color 0.2s; }
        .navList a:hover { color: #fff; }
        
        /* Main Layout: Content + Sidebar */
        .mainLayout {
            display: grid;
            grid-template-columns: 1fr;
            gap: 2rem;
            padding: 2rem;
            max-width: 1200px;
            margin: 0 auto;
            width: 100%;
        }
        
        @media (min-width: 768px) {
            .mainLayout {
                grid-template-columns: 3fr 1fr; /* Content 75%, Sidebar 25% */
            }
        }
        
        /* Blog Post */
        .post { background: white; border-radius: 12px; padding: 2rem; box-shadow: 0 2px 8px rgba(0,0,0,0.05); }
        .postHeader { margin-bottom: 1.5rem; }
        .postTitle { font-size: 2rem; color: #2c3e50; margin-bottom: 0.5rem; }
        .postMeta { color: #666; font-size: 0.9rem; }
        .postBody { font-size: 1.1rem; color: #444; line-height: 1.8; }
        .postBody p { margin-bottom: 1rem; }
        
        /* Sidebar */
        .sidebar { display: flex; flex-direction: column; gap: 1.5rem; }
        .widget { background: white; border-radius: 12px; padding: 1.5rem; box-shadow: 0 2px 8px rgba(0,0,0,0.05); }
        .widgetTitle { font-size: 1.2rem; font-weight: 700; color: #2c3e50; margin-bottom: 1rem; padding-bottom: 0.5rem; border-bottom: 2px solid #8816b6; }
        .widgetList { list-style: none; }
        .widgetList li { padding: 0.5rem 0; border-bottom: 1px solid #f0f0f0; }
        .widgetList li:last-child { border-bottom: none; }
        .widgetList a { color: #555; text-decoration: none; transition: color 0.2s; }
        .widgetList a:hover { color: #8816b6; }
        
        /* Footer */
        .siteFooter {
            background: #098d65;
            color: white;
            text-align: center;
            padding: 2rem;
            margin-top: auto;
        }
    </style>
</head>
<body>
    <div class="siteGrid">
        <header class="siteHeader">
            <a href="#" class="logo">↷ MY BLOG ↶</a>
            <nav>
                <ul class="navList">
                    <li><a href="#">Home</a></li>
                    <li><a href="#">About</a></li>
                    <li><a href="#">Contact</a></li>
                </ul>
            </nav>
        </header>
        
        <main class="mainLayout">
            <article class="post">
                <header class="postHeader">
                    <h1 class="postTitle">Tiêu đề bài viết blog</h1>
                    <div class="postMeta">Đăng ngày 15/01/2024 • 5 min read</div>
                </header>
                <div class="postBody">
                    <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.</p>
                    <p>Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.</p>
                    <p>Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.</p>
                </div>
            </article>
            
            <aside class="sidebar">
                <div class="widget">
                    <h3 class="widgetTitle">Bài viết gần đây</h3>
                    <ul class="widgetList">
                        <li><a href="#">Bài viết 2</a></li>
                        <li><a href="#">Bài viết 3</a></li>
                    </ul>
                </div>
                <div class="widget">
                    <h3 class="widgetTitle">Danh mục</h3>
                    <ul class="widgetList">
                        <li><a href="#">Công nghệ</a></li>
                        <li><a href="#">Thiết kế</a></li>
                        <li><a href="#">Marketing</a></li>
                    </ul>
                </div>
            </aside>
        </main>
        
        <footer class="siteFooter">
            <p>© 2024 My Blog. All rights reserved.</p>
        </footer>
    </div>
</body>
</html>

Giải thích cấu trúc Grid

  • .siteGrid: Grid 3 hàng (header, main, footer), min-height: 100vh đẩy footer xuống dưới cùng.
  • .mainLayout: Grid 1 cột mobile, 2 cột (3fr 1fr) tablet/desktop.
  • Không dùng float/position fixed cho footer - Grid layout tự nhiên đẩy footer xuống dưới.

So sánh: Float (cũ) vs Grid (mới)

Tiêu chí Float (Code gốc) CSS Grid (Khuyến nghị)
Code complexityCao (clearfix, width %, margin)Thấp (grid-template-columns)
ResponsiveMedia query phức tạpThay đổi grid-template-columns
Equal height columnsKhó (cần hack)Tự động (align-items: stretch)
Source orderFixedDễ thay đổi (order property)
Browser supportIE6+Modern browsers (IE11+ partial)

Mở rộng: Danh sách bài viết (Post List / Archive)

Dùng Grid cho danh sách card bài viết:

.postGrid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));
    gap: 2rem;
}
.postCard { display: flex; flex-direction: column; }
.postCard .postBody { flex: 1; }

auto-fill + minmax() tạo cột tự động responsive mà không cần media query.