Chapter 14: SVG image
What does image actually do?
It references an external image file and draws it inside the SVG coordinate system — just like placing a sticker on your drawing.
Important facts (2025–2026 reality):
- Browsers must support JPEG, PNG, and SVG files inside <image>
- They may support others (WebP, GIF, etc.), but don’t rely on it — stick to JPG/PNG/SVG for safety
- The embedded image is not turned into vectors — it stays raster (can pixelate when zoomed too much)
- But because it’s inside SVG, you can still transform, clip, mask, filter, and animate it with SVG power
Core attributes — the ones you almost always need
| Attribute | Meaning | Required? | Default | Common values / notes |
|---|---|---|---|---|
| href | The URL/source of the image | Yes | — | “photo.jpg”, “icons/logo.svg”, “#local-def-id” |
| x | Left position (top-left corner of image) | No | 0 | number, %, etc. |
| y | Top position | No | 0 | number, %, etc. |
| width | Displayed width | Yes | 0 (→ invisible) | number, %, “auto” (SVG 2, spotty support) |
| height | Displayed height | Yes | 0 (→ invisible) | number, %, “auto” |
| preserveAspectRatio | How to handle different aspect ratios | No | “xMidYMid meet” | “xMidYMid slice”, “none”, etc. (like object-fit) |
| crossorigin | CORS setting (for tainted canvas / filters) | No | — | “anonymous”, “use-credentials” |
Modern note: Use href (SVG 2). Older code still uses xlink:href — both work in 2026, but prefer href.
If you forget width or height → image usually disappears (size = 0 × 0).
Here are some clear diagrams showing how x, y, width, height position the image rectangle:
Example 1 – Basic photo inside SVG
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
<svg width="500" height="400" style="border:1px solid #ddd; background:#f8f9fa;"> <image href="https://images.unsplash.com/photo-1600585154340-be6161a56a0c?w=800" x="50" y="50" width="400" height="300" /> </svg> |
Result: A nice photo placed 50 units from left/top, sized to 400×300.
(Use your own image URL or local path like “my-photo.jpg”.)
Example 2 – Preserve aspect ratio + cropping (like object-fit: cover)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
<svg width="300" height="300"> <rect width="100%" height="100%" fill="#eee"/> <image href="https://images.unsplash.com/photo-1517849845537-4d257902454a?w=800" x="0" y="0" width="300" height="300" preserveAspectRatio="xMidYMid slice" <!-- crops to fill, centers --> /> <text x="150" y="280" font-size="28" text-anchor="middle" fill="white" stroke="black" stroke-width="1"> Cover mode </text> </svg> |
Try changing to “xMidYMid meet” (letterbox / contain) vs “none” (stretch / ignore ratio).
Here are visual examples of preserveAspectRatio values:
Example 3 – Embedding another SVG file (very powerful)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
<svg width="400" height="200"> <!-- Background --> <rect width="100%" height="100%" fill="#673AB7"/> <!-- Embed external SVG icon/logo --> <image href="https://upload.wikimedia.org/wikipedia/commons/3/33/Vanamo_Logo.svg" x="80" y="30" width="240" height="140" preserveAspectRatio="xMidYMid meet" /> </svg> |
→ The embedded SVG stays vector — sharp at any zoom!
Example 4 – Clipping / masking an image with SVG shapes
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
<svg width="320" height="320"> <defs> <clipPath id="circleClip"> <circle cx="160" cy="160" r="140"/> </clipPath> </defs> <image href="https://images.unsplash.com/photo-1628258334105-2a0b3d6efee1?w=800" x="0" y="0" width="320" height="320" clip-path="url(#circleClip)" /> </svg> |
→ Image is clipped to a perfect circle — very common for avatars.
Quick comparison: Ways to show images involving SVG
| Method | When to use | Pros | Cons |
|---|---|---|---|
| <img src=”file.svg”> | Simple standalone SVG | Easy, cacheable, lazy-load | Limited interactivity / CSS control |
| Inline <svg> with shapes | Pure vector drawings | Full control, style with CSS, small file | Code longer for complex art |
| <image> inside SVG | Raster photo + vector overlays / effects | Filters, clip, mask, animate raster | Raster can pixelate, bigger file if photo |
| <foreignObject> | Real HTML/CSS inside SVG | Full HTML content | Heavy, accessibility issues sometimes |
Common beginner mistakes
- Forget width & height → image invisible
- Wrong path in href → blank space
- Using very large photos without sizing → huge SVG file / slow load
- Expecting raster image to stay sharp forever → no, only vector parts do
- CORS issues with filters/masks → add crossorigin=”anonymous” on external images
Mini practice for you
- Place any photo of a person and clip it to a heart shape (use <clipPath> with heart <path>)
- Embed a small SVG icon (like a logo) in the corner of a larger photo
- Make a polaroid-style frame: <rect> border + shadow filter + centered photo
Paste your code if you want feedback — I’ll review it like we’re sitting together 😄
Any part confusing? The preserveAspectRatio options? Clipping? Embedding SVG vs raster? Just tell me — we’ll zoom in with more examples until it clicks! 🚀
