How to make text bold in CSS
font-weight sets how thick the letters are. bold (the same as 700) makes text bold, and normal (the same as 400) is regular text.
Headings, <th>, <b> and <strong> are bold by default because of the browser's own stylesheet, so font-weight: normal is how you take bold away. For when to use <b> or <strong> in the HTML itself, see HTML bold.
The numeric scale: 100 to 900
The numbers have standard names that font families follow:
| Value | Common name |
|---|---|
100 | Thin |
200 | Extra Light |
300 | Light |
400 | Normal (Regular) |
500 | Medium |
600 | Semi Bold |
700 | Bold |
800 | Extra Bold |
900 | Black (Heavy) |
Any number from 1 to 1000 is valid, so 450 and 650 are allowed too. Whether you see a difference depends on the font: the browser can only draw weights the font actually has.
system-ui is the operating system's interface font, which usually ships many weights. If every line above looks like one of two weights, your system font only has regular and bold.
Why a weight shows no change
A font is a set of files, often one per weight. When the exact weight is missing, the browser picks the nearest one it has:
- For
500, it tries 500, then lighter weights, then heavier ones. - For
600and above, it tries heavier weights first, then lighter ones. - If there is no bold file at all, most browsers fake one by thickening the regular letters (synthetic bold).
Compare a font with many weights against serif, which on most systems has only regular and bold:
In the serif column, 300 and 500 usually fall back to the regular face and 600 to the bold face. That is the answer to most "font-weight not working" questions: the CSS is fine, the font lacks the weight. A variable font (one file with a weight axis) draws every value within its weight range smoothly.
bolder and lighter
bolder and lighter are relative to the weight the element inherits. They step to the next weight group rather than adding a fixed amount:
| Parent weight | bolder gives | lighter gives |
|---|---|---|
| 100 to 349 | 400 | 100 |
| 350 to 549 | 700 | 100 |
| 550 to 749 | 900 | 400 |
| 750 to 900 | 900 | 700 |
Real-world pattern: a weight scale in variables
Pick three or four weights for the whole site and name them, instead of scattering numbers:
:root {
--weight-regular: 400;
--weight-medium: 500;
--weight-bold: 700;
}
body { font-weight: var(--weight-regular); }
button { font-weight: var(--weight-medium); }
h1, h2 { font-weight: var(--weight-bold); }
Common mistakes
- Expecting every number to look different. Only weights the font contains render distinctly.
- Using
<b>for a button label. Style the button withfont-weight; keep<b>and<strong>for text. - Quoting the number.
font-weight: "700"is invalid and ignored. Writefont-weight: 700. - Bold for emphasis everywhere. When everything is bold, nothing stands out. Keep body text at 400.
- Thin weights for small text. 100 to 300 at small sizes is hard to read, especially on low contrast backgrounds.
Frequently Asked Questions
How do I make text bold in CSS?
Use font-weight: bold; or the equivalent number font-weight: 700; on the element. To remove bold from a heading or a <strong>, set font-weight: normal; (400).
What are the font-weight values?
Numbers from 1 to 1000, usually written in hundreds: 100 thin, 200 extra light, 300 light, 400 normal, 500 medium, 600 semibold, 700 bold, 800 extra bold, 900 black. The keywords normal and bold are 400 and 700, and bolder and lighter are relative to the parent.
Is font-weight bold the same as 700?
Yes. bold computes to 700 and normal computes to 400, so the two forms render identically.
Why does font-weight 500 or 600 look the same as normal or bold?
The font does not have that weight. When a font only ships 400 and 700, the browser picks the closest available file, so 500 renders like 400 and 600 like 700. Load a font with more weights or a variable font.
Should I use CSS font-weight or the <b> tag?
Use <strong> when the words are important, <b> for text that is only styled differently, and font-weight for visual design such as buttons, labels and headings. The tags carry meaning; the property is only appearance.