What is Canvas
Raster basics
Learn how a pixel-based bitmap surface differs from vector markup.

This page is a self-contained introduction to the HTML5 <canvas> element and its 2D drawing API—a raster surface JavaScript paints pixel by pixel. You will understand what canvas is, add it to a page, draw your first shapes, compare canvas with SVG, and know where to go next in the topic index.
Raster basics
Learn how a pixel-based bitmap surface differs from vector markup.
<canvas> tag
Add a canvas element, then draw into it with a short script.
Context methods
Meet fillRect, strokeRect, paths, arcs, text, and clearRect.
Canvas vs SVG
Choose Canvas, SVG, or PNG/JPEG for the right job.
Hands-on labs
Practice five snippets with View Output and Try It Yourself.
Full roadmap
Jump from lines and rectangles to text, color, and transforms.
HTML5’s <canvas> element provides a way to dynamically render graphics, charts, animations, and other visualizations directly within a web page. Unlike SVG, which stores shapes as DOM nodes, canvas is raster-based—it generates a pixel bitmap that you paint programmatically with JavaScript.
Think of canvas as a blank sheet of graph paper: once you draw on it, the image is a grid of colored pixels. To move a shape, you typically clear the canvas and redraw everything in its new position rather than updating a single element, the way you would with SVG or regular DOM nodes.
The Canvas 2D API is powerful and flexible, letting you build interactive, dynamic content in the browser without plugins—from simple charts to full 2D games.
Games, dashboards, and creative tools need to redraw thousands of pixels every frame without the overhead of DOM elements. Canvas gives you pixel-level control, high-performance animation, and image manipulation in a single, script-driven surface.
Read and write individual pixels with getImageData for filters and effects.
Redraw the canvas each frame with requestAnimationFrame for 60fps motion.
Listen for mouse, touch, and keyboard events to build games and drawing tools.
Draw photos, crop regions, and apply compositing effects on top of pixels.
In short: add a <canvas> element, grab its 2D context with JavaScript, and call drawing methods to paint pixels—clearing and redrawing to animate.
Start with the HTML element itself. Always set explicit width and height attributes—the drawing resolution in pixels:
<canvas id="myCanvas" width="400" height="200"></canvas> On its own, an empty canvas is just a blank rectangle. Add JavaScript to get the 2D rendering context and draw a filled rectangle:
const canvas = document.getElementById('myCanvas');
const ctx = canvas.getContext('2d');
// Draw a red rectangle
ctx.fillStyle = 'red';
ctx.fillRect(10, 10, 100, 100); | Piece | Role |
|---|---|
<canvas> | Root element; width/height set the pixel drawing resolution |
getContext('2d') | Returns the CanvasRenderingContext2D object used for every draw call |
fillStyle | Color, gradient, or pattern used by the next fill operation |
fillRect(x, y, w, h) | Draws a filled rectangle at position (x, y) with size w × h |
Continue to Try It Yourself (tryit=1) to edit the bare markup, or tryit=2 to edit the red-rectangle script live.
The Canvas 2D API provides a wide range of methods for drawing shapes, paths, text, images, and more. Each links to its dedicated tutorial when one exists:
| Method | What it does | Tutorial |
|---|---|---|
fillRect(x, y, w, h) | Draws a filled rectangle | Draw Rectangles |
strokeRect(x, y, w, h) | Draws the outline of a rectangle | Draw Rectangles |
clearRect(x, y, w, h) | Clears a rectangular area (transparent) | — |
beginPath() / moveTo() / lineTo() | Starts a path and draws straight segments | Draw Lines |
arc(x, y, r, start, end) | Draws a circular arc | Draw Arc |
quadraticCurveTo() / bezierCurveTo() | Draws curved path segments | Quadratic · Bezier |
fillText(text, x, y) | Draws filled text at a position | Text |
save() / restore() | Pushes and pops the current style/transform state | States |
translate() / rotate() / scale() | Moves, rotates, and scales the drawing origin | Transform |
drawImage() | Draws an image, video frame, or another canvas | Manipulating Images |
| Task | Code snippet |
|---|---|
| Get context | const ctx = canvas.getContext('2d'); |
| Fill color | ctx.fillStyle = '#2563eb'; |
| Draw rectangle | ctx.fillRect(20, 20, 120, 80); |
| Draw line | ctx.moveTo(0,0); ctx.lineTo(100,50); ctx.stroke(); |
| Draw text | ctx.fillText('Hi', 10, 20); |
| Clear canvas | ctx.clearRect(0, 0, canvas.width, canvas.height); |
| Animation frame | requestAnimationFrame(draw); |
All can display graphics, but they solve different problems.
bitmap surfaceBest for games, dense charts, particle effects, and pixel manipulation drawn with JavaScript. Scales cleanly only if redrawn.
vector markupBest for icons, logos, diagrams, and UI illustrations that must stay sharp, styleable, and DOM-accessible.
raster imageBest for photos, textures, and complex imagery baked into a fixed pixel grid.
Learn more in the SVG Introduction when you need scalable, DOM-accessible vector graphics.
Reach for canvas whenever your graphic must redraw fast, react to pixels, or simulate a real drawing surface.
Sprites, tile maps, and HUDs that redraw every frame with the animation loop.
Thousands of data points render faster as pixels than as individual DOM/SVG nodes.
Crop, filter, and composite images with direct pixel access via getImageData.
Particle systems, signature pads, and whiteboards that draw freehand strokes.
Simple logos and UI icons that must stay crisp at any size belong in SVG, not canvas.
Key benefit: canvas can redraw huge numbers of shapes every frame without the DOM overhead that vector or HTML-node approaches carry.
Browse every Canvas tutorial on CodeToFun, grouped by learning path. Start with Draw Lines.
Five starter demos. Use View Output to preview here, or open Try It Yourself to edit and run live (?tryit=1 through 5).
Start with the bare canvas tag, then draw a rectangle, shapes, text, and finally an animation.
The minimum HTML needed before any JavaScript runs.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>My Canvas</title>
</head>
<body>
<canvas id="myCanvas" width="400" height="200"></canvas>
</body>
</html> An empty canvas renders as a transparent box the size of its width and height attributes—nothing is drawn until JavaScript runs.
Classic first drawing: get the 2D context and call fillRect.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Red Rectangle</title>
</head>
<body>
<canvas id="myCanvas" width="400" height="200"></canvas>
<script>
const canvas = document.getElementById('myCanvas');
const ctx = canvas.getContext('2d');
ctx.fillStyle = 'red';
ctx.fillRect(10, 10, 100, 100);
</script>
</body>
</html> We obtain a reference to the canvas element and its 2D rendering context (getContext('2d')). Then we set fillStyle and draw a filled rectangle with fillRect(x, y, width, height). Continue in the Draw Rectangles tutorial.
Combine a semi-transparent rectangle, a stroked outline, and a filled circle in one drawing.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Fill and Stroke</title>
</head>
<body>
<canvas id="myCanvas" width="400" height="200"></canvas>
<script>
const ctx = document.getElementById('myCanvas').getContext('2d');
ctx.fillStyle = 'rgba(37, 99, 235, 0.35)';
ctx.fillRect(40, 40, 140, 90);
ctx.strokeStyle = '#0f172a';
ctx.lineWidth = 4;
ctx.strokeRect(30, 30, 160, 110);
ctx.beginPath();
ctx.arc(280, 100, 50, 0, Math.PI * 2);
ctx.fillStyle = '#dc2626';
ctx.fill();
ctx.strokeStyle = '#991b1b';
ctx.lineWidth = 3;
ctx.stroke();
</script>
</body>
</html> Each shape sets its own fillStyle/strokeStyle before painting. The circle uses beginPath(), arc(), then fill() and stroke()—the same path pattern used throughout the Canvas API. See Draw Arc for more.
Render a bold heading and a smaller subtitle with fillText.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Canvas Text</title>
</head>
<body>
<canvas id="myCanvas" width="400" height="200"></canvas>
<script>
const ctx = document.getElementById('myCanvas').getContext('2d');
ctx.fillStyle = '#0f172a';
ctx.font = 'bold 28px system-ui, sans-serif';
ctx.fillText('Hello, Canvas!', 40, 80);
ctx.font = '16px Verdana, sans-serif';
ctx.fillStyle = '#64748b';
ctx.fillText('Draw labels, scores, and chart titles.', 40, 120);
</script>
</body>
</html> font accepts CSS-style font shorthand; fillText(text, x, y) paints the baseline at y. Learn alignment and stroke text in the Text tutorial.
A red square moves horizontally using requestAnimationFrame.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Canvas Animation</title>
</head>
<body>
<canvas id="myCanvas" width="400" height="200"></canvas>
<script>
const canvas = document.getElementById('myCanvas');
const ctx = canvas.getContext('2d');
let x = 0;
const dx = 2;
function draw() {
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = 'red';
ctx.fillRect(x, 10, 50, 50);
x += dx;
if (x > canvas.width) {
x = 0;
}
requestAnimationFrame(draw);
}
draw();
</script>
</body>
</html> Each frame: clear old pixels with clearRect, update x, then draw again. requestAnimationFrame syncs the loop with the browser’s refresh rate (~60fps) for smooth motion.
Real-world places where canvas shows up every day on the web.
Sprites, tile maps, and physics loops running entirely in the browser.
Example: a platformer or puzzle game HUD.
Fast-rendering line, bar, and scatter charts with thousands of points.
Example: a Chart.js dashboard widget.
Crop, filter, and composite images directly in the browser.
Example: an in-browser avatar cropper.
Freehand strokes captured from mouse, touch, or pen events.
Example: a signature pad or collaborative whiteboard.
Confetti, snow, fire, and other animated pixel effects.
Example: a celebratory confetti burst on a success page.
Gauges, sliders, and visualizations that HTML/CSS can’t easily express.
Example: a circular progress ring or color picker wheel.
Pro Tip: if the graphic redraws often or reacts to pixels, canvas usually beats SVG or plain DOM elements for performance.
Why canvas is an excellent choice for dynamic, pixel-driven graphics.
Read and write raw pixel data for filters, effects, and image processing.
Handles thousands of moving objects better than the same count of DOM/SVG nodes.
Mouse, touch, and keyboard events power drawing tools and games.
drawImage and pixel access enable cropping, filters, and compositing.
getContext('webgl') enables hardware-accelerated 3D on the same canvas element.
Pro Tip: keep drawing logic in small, reusable functions so games and charts stay easy to test and extend.
Follow these practices for clean, performant canvas drawing.
width and height attributesSize the canvas with HTML attributes, not CSS alone, to avoid a stretched, blurry bitmap.
requestAnimationFrame for animationIt syncs with the browser’s refresh rate and pauses in background tabs, unlike setInterval.
clearRect before redrawingClear the previous frame first, or old pixels smear into the new drawing.
save()/restore()Avoid one shape’s style or transform leaking into the next drawing call.
devicePixelRatio for retina screensScale the backing bitmap up and CSS size down for sharp lines on high-DPI displays.
Pro Tip: know basic JavaScript first—variables, functions, and document.getElementById—then add one drawing command and watch pixels appear immediately.
Avoid these mistakes when canvas does not look or behave as expected.
Setting width/height in CSS without matching HTML attributes stretches the bitmap and blurs drawings.
→ Set width/height attributes to the real pixel resolution you draw at.
clearRect in animationSkipping the clear step each frame leaves a smeared trail of previous drawings.
→ Call ctx.clearRect(0, 0, canvas.width, canvas.height) at the top of the draw loop.
Canvas shapes are pixels, not elements—you cannot attach a click listener to a single drawn circle.
→ Compute hit-testing manually with pointer coordinates, or use isPointInPath().
Calling getElementById before the canvas exists returns null and throws on getContext.
→ Place the script after the canvas tag, or run it in a DOMContentLoaded handler.
Very large bitmaps (especially with devicePixelRatio scaling) consume memory and slow every redraw.
→ Cap resolution to what the layout actually needs, and profile before scaling up further.
Pro Tip: if nothing appears, check that getContext('2d') did not return null, that fill/stroke colors are not transparent, and that coordinates fall inside the canvas bounds.
getContext('2d') returns the drawing API object for a canvas element.
fillStyle, strokeStyle, lineWidth, and font configure the next draw call.
Call fillRect, stroke, fillText, drawImage, and more.
clearRect wipes the frame; repeat inside requestAnimationFrame for motion.
fillStyle paints interiors; strokeStyle paints outlines—set both before the matching draw call.width/height attributes, not just CSS, to avoid a blurry, stretched canvas.Quick Takeaway: get the 2D context, set styles, draw, and clear + redraw each frame for animation—canvas is JavaScript-driven pixels from start to finish.
The HTML5 Canvas 2D API has been supported in all major browsers for years, with no polyfill required for modern projects.
Use
Bottom line: Safe for production sites. WebGL (getContext('webgl')) is available for hardware-accelerated 3D on the same element when you need it.
HTML5 Canvas is a versatile, powerful surface for dynamic graphics on the web. Its pixel-level control, animation performance, and scripting flexibility make it the right tool whenever SVG or plain CSS falls short.
By understanding getContext('2d') and the core drawing methods, you can build everything from simple charts to full 2D games—one fillRect or stroke call at a time.
Practice the five examples above, then continue to Canvas Draw Lines—the first Core Drawing topic in the sidebar.
Get the context, set styles, draw, and clear + redraw for animation. Compare with SVG when you need scalable, DOM-accessible graphics instead.
width and height attributes on the canvas elementrequestAnimationFrame for smooth animationsclearRect before redrawing animated scenessave() and restore()devicePixelRatio for sharp retina displaysDraw pixel-perfect graphics the Canvas 2D way.
Pixels, not DOM nodes
BasicsYour drawing API
StructurePaint shapes and paths
StyleclearRect + requestAnimationFrame
MotionFirst Core Drawing topic
PathAdd a <canvas width="400" height="200"></canvas> element, then call canvas.getContext('2d') in JavaScript to draw shapes, text, and animations pixel by pixel. Canvas can export its pixels to an image with canvas.toDataURL()—handy for saving drawings or screenshots without a server round trip.
Learn the first Core Drawing topic in the sidebar—beginPath, moveTo, lineTo, and stroke styles.
9 people found this page helpful