Complete CSS + Tailwind Course Material

10 core CSS days with a 4-day Tailwind continuation

14
Core Days
100+
Concepts
60+
Code Examples
25+
Exercises

★ Core path: 10 CSS days, then 4 Tailwind days covering utilities, responsiveness, motion, Flowbite, config, and production best practices

Table of Contents

Day 1CSS Overview & Syntax Day 2Text & Font Styling Day 3The Box Model Day 4Glassmorphism, Dimensions & Images Day 5Links, Lists, Tables & Forms Day 6Div, Class, ID, Position & Float Day 7Icons & CSS Layout (Display) Day 8Visibility, Cursors, Overflow & Selectors Day 9Pseudo Classes, Dropdown & Animation Day 10Transition, Transformation & Gradients Day 11Media Query & Advanced CSS Day 12Effects, Filters & Advanced Pseudo NEW (day13)CSS Custom Properties (var) NEW (day14)SCSS & CSS Preprocessors NEW (day15)calc(), clamp() & CSS Math NEW (day17)Modern CSS (Container Queries, @supports, clip-path…) Day 11Tailwind Foundations & Setup Day 12Utilities, Layout & Responsive Design Day 13States, Dark Mode, Motion & Interactions Day 14Flowbite, Config, Components & Tailwind Capstone
Day 06

CSS Overview & Syntax

Understanding what CSS is, how it works, and how to connect it to HTML

What is CSS?

CSS stands for Cascading Style Sheets. It is a language used to describe the visual presentation of HTML documents — colours, fonts, spacing, layout, animations, and more. While HTML defines the structure and content of a webpage, CSS controls how that content looks.

The word "Cascading" is crucial. It means that multiple style rules can apply to the same element, and there is a defined order of priority (the cascade) that decides which rule wins. This is the "Theory of Proximity" — the closer a style rule is to the element, the more priority it generally has.

Advantages of CSS
Structure of CSS — Selector, Property & Value

Every CSS rule is made up of three parts: a selector, a property, and a value. Together they form a declaration block.

/* Anatomy of a CSS Rule */ selector /* WHO to style */ { property: value; /* WHAT to change: HOW to change it */ } /* Real example */ h1 { color: red; /* property: color, value: red */ font-size: 32px; /* property: font-size, value: 32px */ text-align: center; /* property: text-align, value: center */ } /* ↑ Selector ↑ Declaration Block */
Three Ways to Add CSS

CSS can be written in three different places. Understanding the difference helps you choose the right approach for each situation.

1. Inline CSS — style attribute

Written directly on an HTML element using the style attribute. Highest specificity but hardest to maintain.

2. Internal CSS — <style> tag

Written inside a <style> tag in the <head>. Good for single-page projects or page-specific overrides.

<!-- 1. INLINE — directly on the element --> <p style="color: red; font-size: 18px;">This text is red</p> <!-- 2. INTERNAL — inside <style> in <head> --> <head> <style> p { color: blue; font-size: 18px; } </style> </head> <!-- 3. EXTERNAL — separate .css file, linked in <head> --> <head> <link rel="stylesheet" href="style.css"/> </head>
Best practice: Always use External CSS for real projects. It keeps HTML clean, allows one file to style an entire website, and makes maintenance easy. Use Internal CSS only for quick tests or email templates. Avoid Inline CSS except for dynamic styles added by JavaScript.
Theory of Proximity — CSS Rule Overriding

When multiple CSS rules target the same element, the browser must decide which one wins. This decision follows a strict order of priority — often called the Theory of Proximity or the CSS Cascade:

Priority order (highest to lowest):
Inline style → Internal style → External stylesheet → Browser default

Additionally, within the same level, a rule written later in the file overrides one written earlier. This is why the order of your CSS rules matters.

/* style.css — external stylesheet */ p { color: blue; } /* ← this loses */ <!-- Internal in <head> --> <style> p { color: green; } </style> /* ← this loses too */ <!-- Inline on the element — WINS --> <p style="color: red;">I am red</p>
⚠️ This is why inline styles can be so difficult — they override everything else including your carefully written stylesheet. Avoid them in production work.

✏️ Day 6 Exercise

  1. Every student should be able to state the Theory of Proximity (CSS cascade order) in their own words with an example.
  2. Create an HTML page that demonstrates all three ways to add CSS — inline, internal, and external — on the same page, showing which one wins.
Day 07

CSS Text & Font Styling

Controlling how text looks — direction, spacing, alignment, decorations, and fonts

Text Properties
PropertyValues & ExampleWhat it does
directionltr | rtlSets text direction — left-to-right or right-to-left (for Arabic, Hebrew etc.)
letter-spacing2px | -1px | normalSpace between individual characters
word-spacing5px | normalSpace between words
text-indent30px | 2emIndents the first line of a paragraph
text-alignleft | right | center | justifyHorizontal alignment of text within its block
text-decorationnone | underline | overline | line-throughAdds or removes lines on text
text-transformuppercase | lowercase | capitalize | noneChanges letter casing without editing HTML
text-shadow2px 2px 4px #000Adds shadow behind text (X offset, Y offset, blur, colour)
colorred | #ff0000 | rgb(255,0,0)Sets the foreground (text) colour
h1 { text-transform: uppercase; letter-spacing: 0.1em; /* em = relative to font size */ text-align: center; text-shadow: 2px 2px 6px rgba(0,0,0,0.4); } p { text-indent: 2em; /* indent first line of each paragraph */ word-spacing: 4px; text-align: justify; /* stretch text to fill the line */ } a { text-decoration: none; /* removes the default underline on links */ }
CSS Colours — Three Ways to Write Them

CSS supports many formats for specifying colour. The most common are names, hexadecimal, and RGB/RGBA.

/* 1. Colour Names — 140+ named colours in CSS */ .box { color: tomato; background: aliceblue; } /* 2. Hexadecimal — #RRGGBB — most commonly used */ .box { color: #ff6347; } /* ff=red, 63=green, 47=blue */ .box { color: #f63; } /* shorthand: #RGB = #RRGGBB */ /* 3. RGB — Red, Green, Blue values (0–255 each) */ .box { color: rgb(255, 99, 71); } /* 4. RGBA — adds Alpha (opacity: 0=transparent, 1=solid) */ .box { background: rgba(255, 99, 71, 0.5); } /* 50% transparent */ /* 5. HSL — Hue(0-360°) Saturation(%) Lightness(%) */ .box { color: hsl(9, 100%, 64%); } /* same tomato colour */
Font Properties
PropertyValuesWhat it does
font-family'Arial', sans-serifSets the typeface. Always provide a fallback (generic family like sans-serif)
font-stylenormal | italic | obliqueMakes text italic
font-variantnormal | small-capsDisplays text in small capitals
font-weightnormal | bold | 100–900Controls thickness. 400=normal, 700=bold
font-size16px | 1em | 1rem | 2vw | 120%Size of the text
CSS Measurement Units Explained

Choosing the right unit is one of the most important decisions in CSS. Units divide into two categories: absolute (fixed, real-world size) and relative (scale based on something else).

UnitTypeMeaningBest Used For
pxAbsoluteOne screen pixel. Always the same size.Borders, shadows, exact dimensions
%RelativePercentage of the parent element's sizeFluid layouts, widths
emRelativeRelative to the current element's font-size. 2em = 2× current fontSpacing, padding that scales with text
remRelativeRelative to the ROOT element's font-size (usually 16px). Consistent & predictable.Font sizes, consistent spacing
vwRelative1% of the viewport (screen) WIDTHFull-width sections, hero text
vhRelative1% of the viewport HEIGHTFull-screen sections
cm / inAbsolutePhysical centimetres / inchesPrint stylesheets only
💡 rem is your best friend for font sizes. If the root font size is 16px, then 1rem = 16px, 1.5rem = 24px, 2rem = 32px. When a user increases their browser font size for accessibility, rem-based layouts scale correctly — px-based ones don't.

✏️ Day 7 Exercise

  1. Create a formal letter format page using proper text alignment, text-indent for paragraphs, font-family choices, and correct use of spacing properties.
  2. Experiment: set the root font-size to 10px on the body, then use rem units for all font sizes — so 1.6rem = 16px, 2.4rem = 24px. This makes rem arithmetic easier.
Day 08

The CSS Box Model

Background, border, padding, margin, outline, box-sizing, box-shadow, and border-radius

The Box Model — Core Concept

Every HTML element is a rectangular box. The CSS Box Model describes the four layers that make up every box, from inside out:

Content → Padding → Border → Margin

Content — the actual text or image. Sized by width and height.
Padding — transparent space INSIDE the border, between content and border.
Border — the visible line surrounding the padding and content.
Margin — transparent space OUTSIDE the border, separating this element from others.

.box { /* Content area */ width: 300px; height: 200px; /* Padding — space inside the border */ padding: 20px; /* all 4 sides */ /* Border — the visible frame */ border: 2px solid black; /* Margin — space outside the border */ margin: 30px; } /* Total rendered width = 300 + 20+20 (padding) + 2+2 (border) = 344px */
Background Properties
PropertyValuesDescription
background-colorred | #fff | rgba(0,0,0,0.5)Fills the element's background with a solid colour or transparent colour
background-imageurl('img.jpg') | noneSets an image as the background
background-repeatrepeat | no-repeat | repeat-x | repeat-yControls whether/how the background image tiles
background-attachmentscroll | fixed | localfixed creates a parallax-like effect where the image stays still as you scroll
background-positioncenter | top left | 50% 50%Where to position the background image within the element
background-sizeauto | cover | contain | 100px 200pxcover fills the element (may crop). contain fits the whole image (may leave gaps).
.hero { background-image: url('hero.jpg'); background-size: cover; /* fill the div, crop if needed */ background-position: center center; /* keep focal point centred */ background-repeat: no-repeat; background-attachment: fixed; /* parallax effect */ } /* Background shorthand */ .hero { background: url('hero.jpg') center / cover no-repeat fixed; }
Border, Padding, Margin & Outline
/* BORDER — shorthand: width style color */ .box { border: 2px solid #333; } .box { border-style: dotted | dashed | solid | double | groove | ridge | inset | outset | none | hidden; } /* Individual sides */ .box { border-top: 3px solid red; } .box { border-bottom: 1px dashed gray; } .box { border-left: 5px solid blue; } /* PADDING shorthand values */ .box { padding: 20px; } /* all 4 sides = 20px */ .box { padding: 10px 20px; } /* top+bottom=10, left+right=20 */ .box { padding: 10px 20px 5px 15px; } /* top right bottom left (clockwise) */ /* MARGIN — same shorthand rules as padding */ .box { margin: 0 auto; } /* 0 top+bottom, auto left+right = CENTRES a block element */ /* Negative margins — pull elements closer together */ .box { margin-top: -20px; } /* moves element UP by 20px, overlaps the element above */ /* OUTLINE — like border but outside it, does not affect layout */ input:focus { outline: 2px solid blue; } /* accessibility — shows focus state */ input { outline: none; } /* removes it (be careful — harms accessibility) */
box-sizing — The Most Important Rule in Modern CSS

By default, width and height only size the content area. Padding and border are added on top, making elements larger than expected. This is called content-box behaviour and causes constant confusion.

box-sizing: border-box changes this so that width includes the padding and border. This is what virtually every professional uses.

/* Add this to the TOP of EVERY CSS file you write */ *, *::before, *::after { box-sizing: border-box; } /* Content-box (default — confusing) */ .box { width: 200px; padding: 20px; border: 2px solid; } /* ↑ Actual rendered width = 200 + 20+20 + 2+2 = 244px ← SURPRISE! */ /* Border-box (predictable) */ .box { box-sizing: border-box; width: 200px; padding: 20px; border: 2px solid; } /* ↑ Actual rendered width = 200px exactly. Padding eats INTO the width. */
box-shadow & border-radius
/* BOX SHADOW — x-offset y-offset blur spread color */ .card { box-shadow: 2px 4px 10px 0px rgba(0,0,0,0.2); } .card { box-shadow: inset 0 2px 4px rgba(0,0,0,0.3); } /* inset = inside the box */ /* Multiple shadows — separated by comma */ .card { box-shadow: 0 2px 4px rgba(0,0,0,0.1), 0 8px 24px rgba(0,0,0,0.15); } /* BORDER-RADIUS — rounds corners */ .box { border-radius: 8px; } /* slightly rounded */ .card { border-radius: 12px; } /* modern card look */ .pill { border-radius: 999px; } /* fully rounded pill/badge shape */ .circle { border-radius: 50%; } /* perfect circle (element must be square) */ /* Individual corner control */ .box { border-radius: 4px 16px 4px 16px; } /* top-left top-right bottom-right bottom-left */

✏️ Day 8 Exercise

  1. Create a frame for an image using all box model properties — border, padding, box-shadow (with inset shadow) and border-radius.
  2. Create a transparent form using RGBA background colours and outline styling.
Day 09

Glassmorphism, CSS Dimensions & Images

Mastering image display, filters, dimensions, and the popular glass-card UI effect

Glassmorphism Effect

Glassmorphism is a UI design trend that creates a frosted-glass appearance — transparent or semi-transparent surfaces with a blur effect on the background behind them. It relies on three key CSS properties: background with RGBA, backdrop-filter: blur(), and a subtle border.

/* The glass card recipe */ .glass-card { background: rgba(255, 255, 255, 0.15); /* semi-transparent white */ backdrop-filter: blur(12px); /* blurs what's BEHIND the card */ border: 1px solid rgba(255,255,255,0.3); border-radius: 16px; box-shadow: 0 8px 32px rgba(0,0,0,0.2); padding: 30px; } /* You MUST have a colourful background behind the glass for it to work */ .background { background: linear-gradient(135deg, #667eea, #764ba2); /* or a background image */ }
Dimensions
.box { width: 400px; height: 300px; max-width: 100%; /* never exceed the viewport — essential for responsive design */ min-width: 200px; /* never shrink below 200px */ max-height: 500px; min-height: 100px; } /* Common responsive image rule */ img { max-width: 100%; /* image never overflows its container */ height: auto; /* maintains aspect ratio */ display: block; /* removes the small gap below inline images */ }
CSS Filters

The filter property applies visual effects to elements — blur, brightness, contrast, colour shifts, and more. These work on images, divs, or any HTML element.

Filter FunctionUnitEffect
blur(px)pxApplies Gaussian blur. blur(5px)
brightness(%)0–1 or %0 = black, 1 = normal, 2 = double brightness
contrast(%)%0% = grey, 100% = normal, 200% = high contrast
invert(%)%100% = completely inverted (like a negative photo)
hue-rotate(deg)degRotates colours around the colour wheel
saturate(%)%0% = greyscale, 100% = normal, 200% = very vivid
sepia(%)%Adds warm brown vintage tone. 100% = full sepia
opacity(%)%100% = fully visible, 0% = fully transparent
grayscale(%)%100% = black and white image
drop-shadow()x y blur colourLike box-shadow but follows the image outline (not the box)
img { filter: grayscale(100%); } /* black and white */ img:hover { filter: grayscale(0%); } /* colour on hover */ .dark-mode { filter: invert(1) hue-rotate(180deg); } /* fake dark mode hack */ .vintage { filter: sepia(60%) contrast(110%) brightness(90%); } /* combine multiple */

✏️ Day 9 Exercise

  1. Fade an image using RGBA — overlay a semi-transparent colour on top of an image using a pseudo-element or stacked backgrounds.
  2. Build a glassmorphism card with a gradient background, a blurred glass panel on top, containing text and an icon.
Day 10

CSS Links, Lists, Tables & Forms

Styling interactive elements for a polished, usable interface

Links — LVHA Rule

Links have four states that must be styled in a specific order to work correctly: Link → Visited → Hover → Active. Writing them in the wrong order causes some states to be overridden and never visible.

/* Always write in LVHA order */ a:link { color: #1a56db; text-decoration: none; } /* unvisited link */ a:visited { color: #7e3af2; } /* already clicked */ a:hover { color: #e02424; text-decoration: underline; } /* mouse over */ a:active { color: #e3a008; } /* being clicked */
List Styling
ul { list-style-type: disc | circle | square | none; } ol { list-style-type: decimal | lower-roman | upper-roman | lower-alpha | upper-alpha; } /* Custom image bullet */ ul { list-style-image: url('bullet.png'); } /* Building a nav menu from a list */ ul.nav { list-style: none; /* remove bullets */ display: flex; /* lay items horizontally */ gap: 20px; padding: 0; margin: 0; } ul.nav li a { color: white; text-decoration: none; padding: 10px 16px; border-radius: 6px; transition: background 0.2s; } ul.nav li a:hover { background: rgba(255,255,255,0.15); }
CSS Table Styling
table { width: 100%; border-collapse: collapse; } /* collapse merges double borders */ th, td { border: 1px solid #ddd; padding: 12px 16px; text-align: left; } th { background: #1a56db; color: white; } tr:nth-child(even) { background: #f8fafc; } /* zebra striping */ tr:hover { background: #eff6ff; } /* hover row highlight */ /* Responsive table */ .table-wrapper { overflow-x: auto; } /* scroll on small screens */
CSS Form Styling
input[type="text"], input[type="email"], textarea { width: 100%; padding: 12px 16px; border: 2px solid #e5e7eb; border-radius: 8px; font-size: 1rem; outline: none; transition: border-color 0.2s; } input:focus, textarea:focus { border-color: #1a56db; /* highlight on focus — important for accessibility */ box-shadow: 0 0 0 3px rgba(26,86,219,0.2); } input::placeholder { color: #9ca3af; font-style: italic; } /* Textarea resize control */ textarea { resize: vertical; /* none | both | horizontal | vertical */ min-height: 120px; box-sizing: border-box; }

✏️ Day 10 Exercise

  1. Create a Ludo Game Design using CSS grid, borders, and colours.
  2. Build a styled contact form with focus states, placeholder styling, and a styled submit button.
Day 11

Div, Class, ID, Positioning & Float

The building blocks of CSS layout — understanding how elements flow and stack

div, span, class, id — The Core HTML Hooks

<div> — a generic block-level container. It creates a new line before and after itself. Used to group other elements for styling or layout.

<span> — a generic inline container. It does not create a new line. Used to style a word or part of a sentence without disrupting the text flow.

class — a reusable label. Multiple elements can share the same class. Targeted with .className in CSS.

id — a unique identifier. Only ONE element per page should have a given id. Targeted with #idName in CSS. Has higher specificity than class.

CSS position property
ValueBehaviourCommon Use
staticDefault. Element follows the normal document flow. top/left/right/bottom have no effect.Default for all elements
relativeElement stays in the document flow but can be nudged with top/left/right/bottom relative to where it would normally sit. Creates a positioning context for children.Small adjustments; parent for absolute children
absoluteRemoved from document flow. Positioned relative to the nearest ancestor with position: relative (or the page if none). Other elements ignore it.Tooltips, badges, overlays, dropdowns
fixedRemoved from document flow. Always positioned relative to the browser viewport. Stays in place when you scroll.Sticky headers, nav bars, cookie banners, chat buttons
stickyBehaves like relative until the user scrolls past a threshold, then acts like fixed. Returns to relative when the parent scrolls away.Section headers that stick while reading, table headers
/* Pattern: parent relative + child absolute */ .card { position: relative; /* establishes coordinate system for children */ } .badge { position: absolute; top: -8px; /* 8px above the card's top edge */ right: -8px; /* 8px to the right of the card */ } /* Sticky header */ header { position: sticky; top: 0; /* stick when it reaches 0px from top of viewport */ z-index: 100; /* stay above other content */ }
z-index — Stacking Order

When positioned elements overlap, z-index controls which one appears on top. Higher values appear in front. It only works on elements with position other than static.

.modal-overlay { position: fixed; z-index: 1000; } /* above everything */ .header { position: sticky; z-index: 100; } /* above content */ .dropdown { position: absolute; z-index: 50; } /* above normal content */
float — Legacy Layout (still relevant for text wrap)
img { float: left; margin-right: 20px; } /* text wraps around the image */ img { float: right; margin-left: 20px; } /* image on right, text wraps left */ /* Always clear floats to prevent parent collapse */ .parent::after { content: ""; display: table; clear: both; }
💡 In modern CSS, use Flexbox or Grid for layout. Float is now mainly used for wrapping text around images — its original purpose.

✏️ Day 11 Exercise

  1. Create a page with an image placed at each of the four corners using position: absolute on a position: relative parent.
  2. Create a bull's-eye target using border-radius: 50% and position: absolute with centring.
  3. Create the form provided by the instructor using proper positioning techniques.
Day 12

Icons & CSS Layout — Display Property

Using icon libraries and mastering Flexbox and Grid for modern layouts

Icon Libraries

Icon libraries provide scalable vector icons as CSS classes. They load a font file where each character maps to an icon shape. You add one <link> to your HTML head and then use <i> tags with specific class names.

<!-- Font Awesome --> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.0/css/all.min.css"/> <i class="fa-solid fa-house"></i> <i class="fa-brands fa-github"></i> <!-- Google Material Icons --> <link rel="stylesheet" href="https://fonts.googleapis.com/icon?family=Material+Icons"/> <i class="material-icons">home</i> <!-- Bootstrap Icons --> <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons/font/bootstrap-icons.css"/> <i class="bi bi-house-fill"></i> <!-- Styling icons like text — because they ARE a font --> i.fa-house { font-size: 24px; color: #1a56db; }
CSS Display Values
ValueBehaviour
blockTakes the full available width. Creates a new line before and after. Width/height/margin work fully.
inlineOnly as wide as its content. No new lines. Width and height are ignored. Vertical margin/padding mostly ignored.
inline-blockSits inline with text but respects width/height. Best of both worlds.
noneElement is removed from the page completely — invisible and takes up no space.
flexOne-dimensional layout. Aligns children in a row or column with powerful alignment tools.
gridTwo-dimensional layout. Defines rows AND columns simultaneously.
Flexbox — Complete Reference

Flexbox makes it trivially easy to centre content, distribute items with equal spacing, and create responsive row/column layouts. It operates on two axes: the main axis (set by flex-direction) and the cross axis (perpendicular to it).

/* CONTAINER properties */ .flex-container { display: flex; /* Direction — main axis */ flex-direction: row; /* row | row-reverse | column | column-reverse */ /* Alignment along the MAIN axis (horizontal if row) */ justify-content: flex-start; /* flex-start | flex-end | center | space-between | space-around | space-evenly */ /* Alignment along the CROSS axis (vertical if row) */ align-items: center; /* flex-start | flex-end | center | baseline | stretch */ /* For MULTIPLE rows of content */ align-content: space-between; /* same values as justify-content */ /* Allow wrapping to next line */ flex-wrap: wrap; /* nowrap | wrap | wrap-reverse */ gap: 16px; /* spacing between flex items */ } /* ITEM properties */ .flex-item { flex: 1; /* grow + shrink + basis. flex:1 = share space equally */ align-self: flex-end; /* override align-items for just this one item */ order: 2; /* visual order (default 0, lower = earlier) */ } /* THE most common Flexbox trick — perfect centring */ .centre-everything { display: flex; justify-content: center; align-items: center; min-height: 100vh; /* full viewport height */ }
CSS Grid — Complete Reference
/* CONTAINER */ .grid { display: grid; grid-template-columns: 1fr 2fr 1fr; /* 3 columns: 1:2:1 ratio */ grid-template-rows: 80px auto 60px; /* 3 rows: fixed auto fixed */ gap: 20px; /* Shorthand: rows / columns */ grid-template: 80px auto 60px / 1fr 2fr 1fr; /* Repeat shorthand */ grid-template-columns: repeat(4, 1fr); /* 4 equal columns */ grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); /* responsive! */ } /* ITEMS — span across cells */ .header { grid-column: 1 / -1; } /* span all columns */ .sidebar { grid-row: 2 / 4; } /* span 2 rows */ .hero { grid-column: span 2; } /* span 2 columns */

✏️ Day 12 Exercise

  1. Create a navigation bar using Flexbox with a logo on the left, nav links in the centre, and action buttons on the right.
  2. Create a full-page layout using CSS Grid with a header, two-column body (sidebar + content), and footer.
Day 13

Visibility, Cursors, Overflow & CSS Selectors

Fine-grained display control and the full power of CSS selector syntax

Visibility vs display:none
.box { visibility: hidden; } /* invisible BUT still occupies space in layout */ .box { visibility: visible; } /* normal display */ .box { display: none; } /* invisible AND layout space is removed */ .box { opacity: 0; } /* invisible BUT space kept AND still responds to clicks */
CSS Selectors — Full Reference
SelectorSyntaxWhat it targets
Universal*Every single element on the page
Typep, h1, divAll elements of that HTML tag
Class.classNameAll elements with that class attribute
ID#idNameThe one element with that id attribute
Groupingh1, h2, pMultiple selectors sharing the same rules
Descendant.nav aAll <a> anywhere inside .nav (any depth)
Child.nav > aOnly DIRECT <a> children of .nav
Adjacent Siblingh1 + pOnly the first <p> immediately after an h1
General Siblingh1 ~ pAll <p> siblings that come after h1
Attributeinput[type="email"]Elements with a specific attribute value
Pseudo-Classes & Pseudo-Elements
/* STATES */ a:link { } /* unvisited link */ a:visited { } /* visited link */ :hover { } /* mouse over */ :active { } /* being clicked */ :focus { } /* keyboard/click focus */ :checked { } /* checked checkbox or radio */ /* POSITION */ :first-child { } /* first child of its parent */ :last-child { } /* last child */ :nth-child(2n) { } /* every even child */ :nth-child(3) { } /* exactly the 3rd child */ :not(.active) { } /* any element WITHOUT .active class */ /* LANGUAGE */ :lang(fr) { } /* element with lang="fr" attribute */ /* PSEUDO-ELEMENTS — double colon */ ::first-letter { } /* only the very first character */ ::first-line { } /* only the first rendered line of text */ ::before { } /* inserts generated content BEFORE element's content */ ::after { } /* inserts generated content AFTER element's content */ ::placeholder { } /* the placeholder text inside input fields */ ::selection { } /* text the user has highlighted/selected */

✏️ Day 13 Exercise

  1. Create a simple image carousel using only HTML and CSS (using :checked and adjacent sibling selectors).
  2. Create a Draught (Checkers) Game board design using CSS Grid and :nth-child for the alternating squares.
  3. Create a Testimonial section and a Landing Page as provided.
Day 14

Dropdown Menus & CSS Animation

Building interactive dropdowns and controlling element movement with @keyframes

CSS-Only Dropdown
/* HTML Structure */ <!-- <nav> <ul> <li class="dropdown"> <a href="#">Services</a> <ul class="dropdown-menu"> <li><a href="#">Web Design</a></li> </ul> </li> </ul> </nav> --> /* CSS */ .dropdown { position: relative; } .dropdown-menu { position: absolute; top: 100%; /* directly below the parent */ left: 0; min-width: 180px; background: white; box-shadow: 0 4px 16px rgba(0,0,0,0.15); border-radius: 8px; list-style: none; padding: 8px 0; /* HIDDEN by default */ opacity: 0; visibility: hidden; transform: translateY(-8px); transition: all 0.25s ease; } /* SHOW on hover using descendant selector */ .dropdown:hover .dropdown-menu { opacity: 1; visibility: visible; transform: translateY(0); }
CSS Animation — @keyframes

CSS Animations allow elements to change from one set of styles to another over time, without JavaScript. You define the animation with @keyframes, then apply it to an element with the animation property.

/* Step 1: Define the animation */ @keyframes slidein { from { transform: translateX(-100%); opacity: 0; } to { transform: translateX(0); opacity: 1; } } /* Using percentages for more control */ @keyframes bounce { 0% { transform: translateY(0); } 40% { transform: translateY(-30px); } 60% { transform: translateY(-15px); } 80% { transform: translateY(-5px); } 100% { transform: translateY(0); } } /* Step 2: Apply the animation */ .banner { animation-name: slidein; animation-duration: 0.6s; animation-timing-function: ease-out; /* ease | linear | ease-in | ease-out | ease-in-out | cubic-bezier() */ animation-delay: 0.2s; animation-iteration-count: 1; /* or infinite */ animation-direction: normal; /* normal | reverse | alternate | alternate-reverse */ animation-fill-mode: both; /* forwards | backwards | both | none */ /* Shorthand */ animation: slidein 0.6s ease-out 0.2s 1 normal both; }
💡 animation-fill-mode: forwards means the element keeps the final keyframe styles after the animation ends. Without it, the element snaps back to its original style.

✏️ Day 14 Exercise

  1. Add a dropdown menu to the navbar built in Day 12, with a smooth fade/slide animation.
  2. Create an animated car that drives from one side of the screen to the other and back — a to-and-fro movement — using @keyframes and animation-direction: alternate.
Day 15

Transition, Transformation & Gradients

Smooth state changes, visual warping, colour gradients, and browser compatibility

CSS Transition

Transitions create a smooth change from one CSS state to another — like a button changing colour when hovered. Unlike animations, transitions only happen when a property value changes (usually triggered by :hover, :focus, or a class toggle via JavaScript). You define how long the change takes and how it accelerates.

.btn { background: #1a56db; color: white; padding: 12px 24px; border-radius: 8px; /* Define WHAT changes, HOW LONG, TIMING, DELAY */ transition-property: background, transform, box-shadow; transition-duration: 0.3s; transition-timing-function: ease; transition-delay: 0s; /* Shorthand — most common way */ transition: all 0.3s ease; } .btn:hover { background: #1971c2; transform: translateY(-2px); box-shadow: 0 8px 20px rgba(26,86,219,0.4); }
Transformations
/* ROTATE — spins element clockwise around its centre */ .box { transform: rotate(45deg); } .box { transform: rotate(-90deg); } /* counter-clockwise */ /* TRANSLATE — moves element (does not affect layout) */ .box { transform: translate(50px, -20px); } /* right 50px, up 20px */ .box { transform: translateX(50px); } .box { transform: translateY(-20px); } /* SKEW — tilts/shears the element */ .box { transform: skewX(20deg); } .box { transform: skewY(10deg); } .box { transform: skew(20deg, 10deg); } /* SCALE — resizes element (no units — 1=normal, 2=double) */ .box { transform: scale(1.5); } .box { transform: scaleX(2); } /* stretch horizontally only */ /* COMBINING — order matters! Applied right to left */ .box { transform: rotate(15deg) scale(1.2) translateX(20px); }
Browser Support Prefixes

Older browsers sometimes required a vendor prefix before they supported standard CSS properties. While mostly unnecessary in 2025 for modern browsers, you may still encounter them in legacy codebases or when supporting older mobile browsers.

.box { /* Vendor prefixes — write the prefixed versions first */ -webkit-transform: rotate(45deg); /* Chrome, Safari, older Edge, iOS */ -moz-transform: rotate(45deg); /* Firefox (old) */ -o-transform: rotate(45deg); /* Opera (old) */ transform: rotate(45deg); /* standard — always last */ -webkit-backdrop-filter: blur(10px); /* Still needed for Safari */ backdrop-filter: blur(10px); } /* Modern solution: PostCSS Autoprefixer handles this automatically */
💡 Use the tool Autoprefixer (a PostCSS plugin) to add vendor prefixes automatically. Or check caniuse.com to see which browsers need a prefix for any property.

✏️ Day 15 Exercise

  1. Create a rotating image — an image that spins continuously using @keyframes and the rotate() transform.
  2. Fill a box using linear-gradient — experiment with direction, multiple stops, and hard stop lines.
Day 16

Media Queries, CSS Rule Override, Nesting & Logical Properties

Building responsive, maintainable, and internationally adaptable CSS

Media Queries — Responsive Design

A media query applies CSS conditionally — only when a specified condition about the user's device or environment is true. The most common condition is the screen width, enabling different layouts for phones, tablets, and desktops from a single HTML file.

@media (max-width: 768px) { /* These styles only apply on screens 768px wide or NARROWER */ .grid { grid-template-columns: 1fr; } /* 1 column on mobile */ nav { display: none; } /* hide desktop nav */ } @media (min-width: 769px) and (max-width: 1024px) { .grid { grid-template-columns: 1fr 1fr; } /* 2 columns on tablet */ } @media (prefers-color-scheme: dark) { body { background: #111; color: #eee; } /* user's OS is in dark mode */ } @media print { .no-print { display: none; } /* hide nav/buttons when printing */ }
CSS Rule Override — Specificity & !important

Every CSS selector has a specificity score. When two rules conflict, the higher score wins — regardless of order. The scoring is: inline style (1-0-0-0) > ID (0-1-0-0) > class/pseudo-class (0-0-1-0) > tag (0-0-0-1).

!important overrides ALL specificity rules. It should be used sparingly — mainly to override third-party library styles you cannot modify.

p { color: gray; } /* score: 0-0-0-1 — loses */ .text { color: blue; } /* score: 0-0-1-0 — beats tag */ p.text { color: green; } /* score: 0-0-1-1 — beats plain class */ #intro { color: orange; } /* score: 0-1-0-0 — beats all above */ <p style="color:red"> /* score: 1-0-0-0 — beats everything except !important */ .override { color: hotpink !important; } /* wins regardless of any other rule */
CSS Nesting (Native — No Preprocessor Needed)
/* Without nesting — repetitive */ .card { background: white; padding: 20px; } .card h3 { color: navy; } .card p { color: gray; } .card:hover { box-shadow: 0 4px 12px rgba(0,0,0,0.1); } /* With nesting — organised. & = the parent selector */ .card { background: white; padding: 20px; & h3 { color: navy; } & p { color: gray; } &:hover { box-shadow: 0 4px 12px rgba(0,0,0,0.1); } /* Nest @media inside the selector */ @media (max-width: 600px) { padding: 14px; } }
Logical Properties — Direction-Aware Styling
/* Physical (fixed — breaks in RTL languages) */ .box { margin-left: 16px; padding-right: 24px; border-left: 3px solid blue; } /* Logical (adapts — works in Arabic, Hebrew, Japanese etc.) */ .box { margin-inline-start: 16px; /* left in LTR, right in RTL */ padding-inline-end: 24px; border-inline-start: 3px solid blue; padding-inline: 24px; /* shorthand for both inline sides */ padding-block: 16px; /* shorthand for top and bottom */ inline-size: 300px; /* same as width */ block-size: 200px; /* same as height */ }

✏️ Day 16 Exercise

  1. Take the landing page created in Day 13 and make it fully mobile-responsive using media queries — it should look good at 375px, 768px, and 1280px widths.
  2. Refactor your CSS to use CSS Custom Properties (var) for all colours and spacing values.
Day 17

CSS Effects, Filters & Advanced Pseudo Classes

Professional visual effects using pure CSS

::before and ::after — The Content Injection Technique

::before and ::after create a virtual element as the first or last child of the selected element. They require the content property. The injected content is not in the HTML — it exists only in CSS. They are block-level by default only when given display: block; otherwise they are inline.

/* Quote marks added with CSS, not HTML */ blockquote::before { content: '"'; font-size: 4em; color: gray; line-height: 0; } /* Required badge */ label.required::after { content: ' *'; color: red; } /* Overlay effect — a dark tint over an image */ .hero { position: relative; background-image: url('hero.jpg'); } .hero::after { content: ''; /* empty — just creates the element */ position: absolute; inset: 0; /* top:0; right:0; bottom:0; left:0 */ background: rgba(0,0,0,0.5); } /* Glow effect */ .glow-box { position: relative; } .glow-box::after { content: ''; position: absolute; inset: -4px; background: linear-gradient(45deg, #ff6b6b, #4ecdc4, #6c5ce7); border-radius: inherit; z-index: -1; filter: blur(8px); opacity: 0.8; }
Common CSS Effects Reference
/* GROW EFFECT on hover */ .card { transition: transform 0.3s ease; } .card:hover { transform: scale(1.05); } /* DROP SHADOW EFFECT */ .card { transition: box-shadow 0.3s ease; } .card:hover { box-shadow: 0 20px 40px rgba(0,0,0,0.2); } /* FLIP EFFECT — 3D card flip */ .flip-card { perspective: 1000px; } .flip-inner { position: relative; transition: transform 0.7s; transform-style: preserve-3d; } .flip-card:hover .flip-inner { transform: rotateY(180deg); } .flip-front, .flip-back { position: absolute; inset: 0; backface-visibility: hidden; } .flip-back { transform: rotateY(180deg); } /* PRELOADER / SPINNER */ @keyframes spin { to { transform: rotate(360deg); } } .spinner { width: 40px; height: 40px; border: 4px solid #ddd; border-top-color: #1a56db; border-radius: 50%; animation: spin 0.8s linear infinite; } /* INVERT EFFECT */ .btn:hover { filter: invert(1); }
★ NEW

CSS Custom Properties — var()

Creating reusable, dynamic CSS variables for maintainable, themeable stylesheets

What Are CSS Custom Properties? NEW

CSS Custom Properties (also called CSS Variables) allow you to store a value in a named variable and reuse it throughout your stylesheet. If you want to change your brand colour, you change it in one place and every property using that variable updates automatically.

They are defined with two dashes: --variable-name. They are used with the var() function: var(--variable-name). They follow the cascade and can be scoped to any element.

/* Define variables on :root so they're available everywhere */ :root { --color-primary: #1a56db; --color-secondary: #0e9f6e; --color-text: #111827; --color-bg: #f9fafb; --spacing-sm: 8px; --spacing-md: 16px; --spacing-lg: 32px; --radius: 8px; --shadow: 0 4px 12px rgba(0,0,0,0.1); --font-size-base: 1rem; --font-size-lg: 1.25rem; } /* Use them with var() */ body { background: var(--color-bg); color: var(--color-text); } .btn { background: var(--color-primary); padding: var(--spacing-sm) var(--spacing-md); border-radius: var(--radius); } .card { box-shadow: var(--shadow); padding: var(--spacing-lg); } /* FALLBACK VALUE — used if variable is not defined */ .box { color: var(--color-accent, #e3a008); } /* uses #e3a008 if --color-accent missing */ /* THEMING — override variables in a scope */ .dark-theme { --color-bg: #111827; /* all children in .dark-theme now use dark colours */ --color-text: #f9fafb; } /* DARK MODE using media query + variables */ @media (prefers-color-scheme: dark) { :root { --color-bg: #111827; --color-text: #f9fafb; } } /* Variables are live — JavaScript can update them too */ /* document.documentElement.style.setProperty('--color-primary', '#ff0000'); */
✅ Use CSS Custom Properties from Day 1 of every project. They make global colour/spacing changes trivial and are the foundation of any professional design system or theme.
★ NEW

SCSS & CSS Preprocessors

Writing smarter CSS with Sass/SCSS, LESS, Stylus, and PostCSS

What is a CSS Preprocessor? NEW

A CSS preprocessor is a tool that extends CSS with programming-like features — variables, nesting, functions, loops, conditions — then compiles your enhanced code down to standard CSS that browsers understand. The most popular is Sass/SCSS.

While native CSS has added many of these features (custom properties, nesting), preprocessors still offer power for large projects: file splitting, mixins, loops, and build-time calculations.

SCSS Variables, Nesting & Mixins NEW
// ── SCSS VARIABLES — compile-time, use $ ── $primary: #1a56db; $spacing: 16px; $radius: 8px; .btn { background: $primary; padding: $spacing; border-radius: $radius; } // ── NESTING — mirrors HTML structure ── .nav { background: #111; ul { display: flex; list-style: none; } a { color: white; &:hover { color: $primary; } // & = .nav a } } // ── MIXINS — reusable chunks of CSS ── @mixin flex-center { display: flex; align-items: center; justify-content: center; } @mixin card($padding: 20px) { // default argument background: white; border-radius: $radius; padding: $padding; box-shadow: 0 2px 8px rgba(0,0,0,0.1); } .hero { @include flex-center; } .modal { @include card(32px); } // ── FILE SPLITTING — organise large projects ── // _variables.scss, _buttons.scss, _nav.scss ... @use 'variables'; @use 'components/buttons'; @use 'layout/grid';
LESS, Stylus, PostCSS — Quick Comparison NEW
ToolVariable SyntaxStrengthsStatus
Sass/SCSS$variableMost features, huge community, excellent tooling, file splitting⭐ Most popular
LESS@variableSimilar to SCSS, was used in Bootstrap 3Declining
Stylusvariable (bare)Most flexible syntax, optional colons/bracesNiche use
PostCSSPlugin-based transformation — Autoprefixer, future CSS, minification⭐ Widely used in build tools
ℹ️ In 2025, with native CSS nesting, custom properties, and @layer — plain CSS covers most needs. Learn SCSS when joining teams that use it, or for very large multi-file projects.
★ NEW

CSS Math Functions — calc(), clamp(), min(), max()

Performing calculations directly in CSS for fluid, responsive layouts

calc() — Mixing Units in Calculations NEW

calc() lets you perform mathematical operations (+ - * /) inside a CSS value — and you can mix different units. This is impossible to do without it. The most powerful use is subtracting a fixed amount from a percentage.

/* Sidebar + main content — subtract sidebar width from full width */ .sidebar { width: 260px; } .main { width: calc(100% - 260px); } /* responsive remaining space */ /* Full height minus header */ .content { min-height: calc(100vh - 70px); } /* Negative margin trick — extend element beyond its container */ .full-bleed { margin-inline: calc(-1 * var(--page-padding)); } /* Can use custom variables inside calc */ :root { --header-height: 64px; } .page-body { padding-top: calc(var(--header-height) + 20px); }
clamp() — Fluid Responsive Values NEW

clamp(minimum, preferred, maximum) lets a value scale fluidly between a minimum and maximum. It's perfect for fluid typography — text that grows with the viewport without hard breakpoints.

/* Fluid font: minimum 1rem, scales with viewport, max 3rem */ h1 { font-size: clamp(1rem, 4vw, 3rem); } /* Fluid padding */ .container { padding-inline: clamp(16px, 5vw, 80px); } /* Fluid width */ .card { width: clamp(200px, 50%, 500px); }
min() and max() NEW
/* min() — picks the SMALLER of the given values */ .box { width: min(400px, 100%); } /* never larger than 400px, never larger than container */ /* max() — picks the LARGER of the given values */ .text { font-size: max(16px, 2vw); } /* never smaller than 16px */
💡 clamp(min, preferred, max) is equivalent to max(min, min(preferred, max)). Use clamp for fluid typography — it replaces dozens of media query breakpoints for font sizes.
★ NEW

Modern CSS — What's New & What to Learn Next

Container Queries, @supports, clip-path, aspect-ratio, @layer, scroll-behavior

@supports — Feature Detection in CSS NEW

@supports works like @media but tests whether the browser supports a specific CSS property and value. It lets you write fallback code for browsers that don't support modern features — the same concept as progressive enhancement.

/* Only apply if the browser supports backdrop-filter */ @supports (backdrop-filter: blur(10px)) { .glass { backdrop-filter: blur(10px); background: rgba(255,255,255,0.2); } } /* Fallback for browsers that do NOT support it */ @supports not (backdrop-filter: blur(10px)) { .glass { background: rgba(255,255,255,0.9); } /* opaque fallback */ } /* Test grid support */ @supports (display: grid) { .layout { display: grid; grid-template-columns: 1fr 2fr; } }
Container Queries — The Future of Responsive Design NEW

Media queries respond to the viewport width. Container queries respond to the width of the element's container. This means a card component can adapt its layout based on how much space it's given — not the screen size. The same card can be a full row in a wide sidebar and a compact thumbnail when in a narrow column.

/* Step 1: Make the parent a containment context */ .card-wrapper { container-type: inline-size; container-name: card; /* optional name for specificity */ } /* Step 2: Query the CONTAINER width */ @container (min-width: 400px) { .card { display: flex; /* horizontal when container is wide */ gap: 16px; } .card img { width: 120px; } } /* Default (narrow): stacked */ .card { display: block; } .card img { width: 100%; }
💡 Container queries solve one of the hardest problems in component-based design. A .card component no longer needs to know where it lives — it just adapts to whatever space it's given. This is the future of CSS.
clip-path — Custom Element Shapes NEW

clip-path crops an element to a custom shape — triangles, circles, hexagons, or any polygon. Content outside the clip path is hidden. It's used for hero sections with diagonal cuts, image shapes, and decorative elements.

.circle { clip-path: circle(50%); } .diamond { clip-path: polygon(50% 0%, 100% 50%, 50% 100%, 0% 50%); } .triangle { clip-path: polygon(50% 0%, 100% 100%, 0% 100%); } .slant { clip-path: polygon(0 0, 100% 0, 100% 80%, 0 100%); } .hex { clip-path: polygon(25% 5%, 75% 5%, 100% 50%, 75% 95%, 25% 95%, 0 50%); } /* Animate the clip path */ .btn::after { clip-path: circle(0% at 50% 50%); transition: clip-path 0.4s ease; } .btn:hover::after { clip-path: circle(150% at 50% 50%); /* ripple reveal effect */ }
💡 Use the free tool clippy.abhimanyu.io to visually generate clip-path polygon values by dragging points.
aspect-ratio & scroll-behavior NEW
/* ASPECT-RATIO — maintain proportion without padding hacks */ .video-wrapper { aspect-ratio: 16 / 9; } /* always 16:9 ratio */ .square { aspect-ratio: 1; } /* 1:1 = perfect square */ .portrait-card { aspect-ratio: 3 / 4; } /* portrait photo proportion */ /* SCROLL-BEHAVIOR — smooth scrolling for anchor links */ html { scroll-behavior: smooth; } /* Now clicking <a href="#section"> smoothly scrolls to that section */ /* SCROLL-PADDING-TOP — offset for sticky header */ html { scroll-behavior: smooth; scroll-padding-top: 80px; /* prevent sticky header from covering the target */ }
@layer — Controlling the Cascade NEW

@layer lets you explicitly organise your CSS into named layers and define their priority order. Styles in higher-priority layers always win, regardless of specificity. This solves the age-old problem of fighting specificity wars with third-party libraries.

/* Define the order: base < components < utilities */ @layer base, components, utilities; @layer base { * { box-sizing: border-box; } body { font-family: sans-serif; } } @layer components { .btn { background: blue; color: white; padding: 8px 16px; } } @layer utilities { /* Utilities always win — no !important needed */ .bg-red { background: red; } .hidden { display: none; } .mt-auto { margin-top: auto; } } /* Unlayered styles (outside any @layer) always beat layered ones */
💡 @layer is what frameworks like Tailwind CSS and modern design systems use under the hood. Understanding it gives you control over even the most complex CSS architectures.
Guide

Suggested Learning Path & Topics Added

A summary of new additions and recommended study order

Topics Added to This Course Material NEW
Topic AddedWhere It FitsWhy It Matters
CSS Custom Properties (var)After Day 16Essential for maintainable, themeable CSS. Used in every professional project.
SCSS / PreprocessorsAfter Day 16Used widely in team/company codebases. Required knowledge for most frontend jobs.
calc()Day 8 / Day 15Mixing units — e.g. calc(100% - 260px) — is impossible without it.
clamp(), min(), max()Day 15 / Day 16Fluid responsive typography without breakpoints. Modern best practice.
@supportsDay 16Progressive enhancement — graceful fallbacks for unsupported features.
Container Queries (@container)After Day 16The evolution of media queries. Component-level responsiveness.
clip-pathDay 17Creating non-rectangular element shapes. Widely used in modern UI.
aspect-ratioDay 9 / Day 12Replaces the old padding-hack for maintaining image/video proportions.
scroll-behavior + scroll-padding-topDay 13 / Day 16Smooth anchor scrolling with sticky header offset. Two lines of CSS.
@layerDay 16 AdvancedExplicit cascade management. Used in Tailwind, Bootstrap 5+ and all modern frameworks.
CSS Math in specificityDay 16:is(), :where(), :has() — powerful modern selectors that simplify complex rules.
Recommended Additional Topics for the Curriculum

✏️ Final Capstone Project

  1. Build a fully responsive personal portfolio website from scratch using only HTML and CSS — no frameworks.
  2. Requirements: sticky navigation with dropdown, hero section with glassmorphism card, skills section using Grid, project cards with hover effects, contact form with validation styling, CSS custom properties for all colours, and a dark mode toggle using prefers-color-scheme.
  3. Bonus: Refactor the CSS into SCSS with variables, mixins, and file partials. Compare the before/after and present your findings.
Tailwind Continuation

Days 11 to 14 — Utility-First CSS and Component Workflows

This continuation picks up after the CSS capstone and shows how modern teams move faster with Tailwind CSS. The flow is deliberate: foundations, utilities and layout, interactive states and dark mode, then Flowbite and production patterns.

Day 11

Tailwind Foundations, Utility Thinking & Setup

Understand Tailwind's utility-first model, when it helps, and how to start with the CDN or a proper build setup.

What Tailwind CSS Changes

Tailwind CSS is a utility-first framework. Instead of creating a custom class and then writing CSS for it, you compose small single-purpose classes directly in HTML. This removes a large part of the constant context-switching between HTML and CSS files.

It does not replace your CSS knowledge. It compresses that knowledge into a naming system. If you already understand spacing, colour, layout, states, and responsiveness, Tailwind becomes very fast to read and write.

Tailwind vs Traditional CSS
Traditional CSS
.hero-card { background: white; padding: 24px; border-radius: 16px; box-shadow: 0 10px 24px rgba(0,0,0,.08); }
Tailwind
class="bg-white p-6 rounded-2xl shadow-xl"
Two Common Setup Paths

1. CDN for learning

Add the Tailwind CDN script to an HTML file and start typing utility classes immediately. Best for practice, demos, and classwork.

2. Build process for real projects

Use npm and a Tailwind config file so unused classes are removed in production and your design tokens are controlled properly.

<!-- Learning setup with CDN --> <script src="https://cdn.tailwindcss.com"></script> <h1 class="text-4xl font-bold text-cyan-600 text-center mt-10"> Hello, Tailwind CSS </h1>

✏️ Day 11 Exercise

  1. Create a blank HTML file and add Tailwind via CDN.
  2. Build a profile card with a heading, paragraph, button, and shadow using only utility classes.
  3. Write a short comparison explaining when you would choose raw CSS and when you would choose Tailwind.
Day 12

Utilities, Layout, Spacing & Responsive Design

Learn the utility vocabulary for text, colour, spacing, flexbox, grid, and breakpoint-driven layout changes.

The Utility Vocabulary You Must Know
Tailwind ClassMeaningUse
text-3xlLarge text sizeHeadings and section titles
font-semiboldWeight 600Buttons, labels, headings
bg-slate-900Dark backgroundHero sections, dark cards
p-6 / px-6 / py-3Padding utilitiesInternal spacing
rounded-xlLarge radiusCards and panels
shadow-lgBox shadowElevation and depth
flex / items-center / justify-betweenFlexbox utilitiesOne-dimensional layout
grid / grid-cols-3 / gap-6Grid utilitiesCards, dashboards, galleries
md:grid-cols-2Breakpoint modifierTablet and desktop layouts
hidden md:flexVisibility by screen sizeDesktop nav, responsive menus
Responsive Thinking

Tailwind is mobile-first. Classes without prefixes apply everywhere. A prefix like md: means “apply this from 768px and above”. You solve the mobile layout first, then enhance the design as screen space increases.

<section class="px-4 md:px-8 lg:px-16"> <div class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-6"> <div class="bg-white rounded-xl shadow p-6">Card 1</div> <div class="bg-white rounded-xl shadow p-6">Card 2</div> <div class="bg-white rounded-xl shadow p-6">Card 3</div> <div class="bg-white rounded-xl shadow p-6">Card 4</div> </div> </section>
The fastest way to become productive is to memorize the spacing scale, the breakpoint prefixes, and the top 20 layout utilities. After that, most class names become predictable.

✏️ Day 12 Exercise

  1. Build a 4-card feature grid that stacks on mobile, becomes 2 columns on tablets, and 4 columns on desktop.
  2. Create a responsive navigation shell with a desktop link row and a mobile hamburger button.
  3. Recreate a pricing section using only utility classes.
Day 13

Interactive States, Dark Mode, Motion & Hover Patterns

Use Tailwind for hover, focus, active, group interactions, animations, and dark mode-ready interfaces.

State Variants

State variants are prefixes such as hover:, focus:, active:, disabled:, and group-hover:. They let you create rich interactions without writing custom CSS selectors.

<button class="bg-blue-600 text-white px-6 py-3 rounded-lg transition-all duration-200 hover:bg-blue-700 hover:shadow-lg active:scale-95 focus-visible:outline-none focus-visible:ring-4 focus-visible:ring-blue-300"> Submit </button> <div class="group bg-white rounded-xl p-5 shadow transition-colors hover:bg-slate-50"> <h3 class="font-semibold text-slate-900 group-hover:text-cyan-700">Dashboard</h3> <p class="text-slate-500 mt-2">Child elements can react to parent hover.</p> </div>
Dark Mode

Tailwind supports dark mode with the dark: prefix. In real projects, most teams use a class-based strategy so the user can toggle themes and save that preference.

<body class="bg-white dark:bg-slate-950 text-slate-900 dark:text-slate-100"> <div class="bg-white dark:bg-slate-800 border border-slate-200 dark:border-slate-700 rounded-xl p-6"> <h2 class="text-xl font-bold">Dark Mode Card</h2> <p class="text-slate-600 dark:text-slate-300 mt-2">The same component adapts to the selected theme.</p> </div> </body>
Motion and Transform Utilities

✏️ Day 13 Exercise

  1. Create a button system with hover, active, focus-visible, and disabled states.
  2. Add dark mode styling to a card, form, and page background.
  3. Build a small dashboard panel that uses group hover and a subtle lift animation.
Day 14

Flowbite Components, Config, JIT & Production Best Practices

Move from raw utilities to reusable components and production-ready Tailwind workflows.

Flowbite in a Tailwind Workflow

Flowbite is a Tailwind-based component library. It gives you prebuilt navbars, modals, dropdowns, tables, drawers, and forms without forcing a totally different styling model. You can still edit classes directly because the components are made with standard Tailwind utilities.

<script src="https://cdn.tailwindcss.com"></script> <link href="https://cdnjs.cloudflare.com/ajax/libs/flowbite/2.2.1/flowbite.min.css" rel="stylesheet" /> <button data-modal-target="demoModal" data-modal-toggle="demoModal" class="bg-cyan-600 text-white px-6 py-2 rounded-lg"> Open Modal </button> <script src="https://cdnjs.cloudflare.com/ajax/libs/flowbite/2.2.1/flowbite.min.js"></script>
Config, Arbitrary Values & Best Practices

✏️ Tailwind Capstone

  1. Build a landing page using Tailwind and Flowbite with a sticky responsive navbar, hero, features grid, pricing section, modal CTA, and footer.
  2. Add a dark mode toggle and save the user's preference.
  3. Extract repeated patterns into reusable component classes or shared utility patterns.