CSS
What makes the web look like something.
CSS controls the visual presentation of HTML — colors, fonts, spacing, layout, animation. Without CSS, every page is plain text. With it, the same HTML can look completely different.
Core concepts
Selectors
Selectors target the HTML elements you want to style. Type selectors match elements by tag name. Class selectors match by class. ID selectors match a specific element. Combinators let you target elements based on their relationship in the HTML.
/* Type selector */
p { color: #333; }
/* Class selector */
.card { background: white; }
/* ID selector (use sparingly) */
#header { position: fixed; }
/* Descendant: p inside .card */
.card p { font-size: 14px; }
/* Direct child */
.nav > a { color: inherit; }
/* Multiple selectors */
h1, h2, h3 { font-family: serif; }
/* Pseudo-classes */
a:hover { color: blue; }
input:focus { outline: 2px solid blue; }
li:first-child { font-weight: bold; }
li:last-child { border: none; }
/* Pseudo-elements */
p::first-line { text-transform: uppercase; }
.btn::after { content: ' →'; }Colors and typography
Colors can be hex, rgb(), hsl(), or named. Modern CSS prefers hsl() because it's intuitive — hue (0-360), saturation (%), lightness (%). Typography: set font-family, size, weight, line-height, and letter-spacing.
/* Colors */
.primary { color: #c8a96e; }
.secondary { color: rgb(138, 138, 138); }
.muted { color: hsl(0, 0%, 35%); }
.overlay { background: rgba(0, 0, 0, 0.5); }
/* CSS custom properties (variables) */
:root {
--color-bg: #0d0d0d;
--color-text: #f0ede6;
--color-accent: #c8a96e;
}
body {
background: var(--color-bg);
color: var(--color-text);
}
/* Typography */
body {
font-family: 'Inter', system-ui, sans-serif;
font-size: 16px;
font-weight: 300;
line-height: 1.6;
letter-spacing: 0.01em;
}
h1 {
font-size: clamp(36px, 5vw, 80px);
font-weight: 700;
letter-spacing: -0.03em;
line-height: 0.95;
}The box model
Every element is a rectangular box. Content is inside. Padding is space between content and border. Border wraps padding. Margin is space outside the border. box-sizing: border-box makes padding and border count inside the declared width — always use this.
/* Always set this */
*, *::before, *::after {
box-sizing: border-box;
}
.card {
/* Content area */
width: 320px;
height: auto;
/* Padding: inside the border */
padding: 24px;
/* padding: top right bottom left */
padding: 16px 24px;
/* Border */
border: 1px solid #333;
border-radius: 8px;
/* Margin: outside the border */
margin: 0 auto; /* centered */
margin-bottom: 24px;
}
/* Shorthand directions:
4 values: top right bottom left
2 values: top/bottom left/right
1 value: all sides */
padding: 8px 16px 8px 16px;
padding: 8px 16px;
padding: 8px;Flexbox
Flexbox arranges items in a row or column. The parent becomes a flex container; children become flex items. justify-content controls main axis alignment. align-items controls cross axis. gap sets spacing between items.
.nav {
display: flex;
align-items: center;
justify-content: space-between;
gap: 24px;
}
/* Flex direction */
.sidebar {
display: flex;
flex-direction: column;
gap: 16px;
}
/* Center anything */
.centered {
display: flex;
align-items: center;
justify-content: center;
}
/* Wrap to next line */
.tags {
display: flex;
flex-wrap: wrap;
gap: 8px;
}
/* Flex item: grow to fill space */
.main-content {
flex: 1;
}
/* Fixed sidebar, flexible content */
.layout {
display: flex;
gap: 32px;
}
.sidebar { width: 240px; flex-shrink: 0; }
.content { flex: 1; }CSS Grid
Grid is for two-dimensional layout — rows and columns at the same time. Define columns with grid-template-columns. The fr unit distributes available space proportionally. gap sets space between tracks.
/* Basic 2-column grid */
.grid {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 32px;
}
/* 3-column grid */
.cards {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 24px;
}
/* Mixed column widths */
.layout {
display: grid;
grid-template-columns: 280px 1fr;
gap: 64px;
}
/* Auto-fit: as many columns as fit */
.responsive {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
gap: 24px;
}
/* Span multiple columns */
.featured {
grid-column: 1 / -1; /* full width */
}
/* Named areas */
.page {
display: grid;
grid-template-areas:
"header header"
"sidebar main"
"footer footer";
}
.header { grid-area: header; }Responsive design
Media queries apply styles at specific screen widths. Design mobile-first: write base styles for small screens, then add larger-screen overrides. The viewport meta tag in HTML is required for mobile to work correctly.
/* Mobile-first base styles */
.container {
padding: 0 20px;
max-width: 1280px;
margin: 0 auto;
}
.grid {
display: grid;
grid-template-columns: 1fr; /* 1 column on mobile */
gap: 24px;
}
/* Tablet: 768px and up */
@media (min-width: 768px) {
.container {
padding: 0 32px;
}
.grid {
grid-template-columns: 1fr 1fr;
}
}
/* Desktop: 1024px and up */
@media (min-width: 1024px) {
.container {
padding: 0 48px;
}
.grid {
grid-template-columns: repeat(3, 1fr);
}
}
/* Fluid typography: scales with viewport */
h1 {
font-size: clamp(32px, 5vw, 80px);
}Transitions and animations
transition smoothly animates a property change when triggered (hover, focus). animation runs automatically using @keyframes. Always respect prefers-reduced-motion for users who need less motion.
/* Transitions */
.btn {
background: #f0ede6;
color: #0d0d0d;
transition: background 0.25s ease, transform 0.2s ease;
}
.btn:hover {
background: #c8a96e;
transform: translateY(-2px);
}
/* Keyframe animation */
@keyframes fadeIn {
from {
opacity: 0;
transform: translateY(20px);
}
to {
opacity: 1;
transform: none;
}
}
.hero {
animation: fadeIn 0.7s cubic-bezier(0.22, 1, 0.36, 1) forwards;
}
/* Ticker / marquee */
@keyframes scroll {
to { transform: translateX(-50%); }
}
.ticker {
animation: scroll 20s linear infinite;
}
/* Reduced motion */
@media (prefers-reduced-motion: reduce) {
*, *::before, *::after {
animation-duration: 0.001ms !important;
transition-duration: 0.001ms !important;
}
}