All blog posts

Scaling pixel art without blur.

A practical guide to choosing pixel-art dimensions, scaling by clean multiples, and keeping icons, sprites, watch faces, and Godot assets sharp.

The short version: pick the final canvas early, scale by whole numbers, and keep smoothing out of the export/import path.

The problem

Blur usually means the pixels stopped lining up.

Pixel art is built on hard edges. When an app, browser, game engine, icon pipeline, or watch-face preview resizes it with smoothing, the renderer samples between source pixels and averages neighbouring colours. That is great for photos. It is usually bad for a tiny sword, face, item, or logo that depends on clean square decisions.

The fix is not a magic export button at the end. The fix is to make the artwork for the place it has to land. If the final asset needs to be 64 x 64, work at 64 x 64 or scale from a clean factor like 32 x 32. Do not ask a 48 x 48 source to become 100 x 100 and expect every edge to survive.

Smoothed resize vs exact pixel scale

Fractional32 × 32100 × 1003.13×Snap →source: sword sprite
Destination size
Renderer filter

Pixel-art workflows need nearest neighbor filtering. Toggle to Bilinear to see what happens to the details and edges before changing this setting.

The same sample is drawn twice. The soft side simulates a smoothed fractional resize; the crisp side keeps the grid intact.

Rule one

Choose the final output size before you draw.

Start with the destination. A game item, Discord avatar, Android adaptive icon layer, Wear OS preview, app badge, and Godot sprite all have different constraints. If the final canvas is known, the artwork can be composed to that canvas instead of being squeezed into it later.

This is especially important when the source is a generated image, screenshot, sketch, or rough reference. Those sources can be useful for direction, but they are not the final pixel grid. Reconstruct the useful idea into the target grid by hand or with an editor that makes the canvas size explicit.

Reconstruct, don't rescue

Good presets make the target visible

Pixelpond Engine is being shaped around presets like these so the export size is not an afterthought.

Rule two

Scale by whole numbers whenever possible.

Whole-number scaling means every source pixel becomes an equal block of screen pixels: 16 to 32 is 2x, 32 to 64 is 2x, and 64 to 128 is 2x again. With nearest neighbor, an integer scale keeps every one of those blocks identical, so the artwork just gets bigger without changing the relative size of the pixels. Smoothing filters like bilinear still blend across the block edges and soften them even at a clean multiple, which is why pixel-art pipelines switch the filter off rather than rely on the size alone.

Fractional scaling is where trouble starts. A 48 x 48 sprite enlarged to 100 x 100 has no clean way to distribute its pixels. Some columns have to become wider than others, or the renderer has to blend colours. Either way, the image loses the tidy rhythm that made it read as pixel art.

Clean sizes keep the grid honest

16 × 16item
32 × 32sprite
64 × 64avatar
128 × 128HD icon
256 × 256store asset
512 × 512large icon
This is why small pixel assets often move through 16, 32, 64, 128, 256, 512, and 1024 pixel canvases.

The awkward middle is where blur appears

32 × 32 sword
→ 176 × 176 (5.5×)fractional — steps march
32 × 32 sword
→ 160 × 160 (5×)clean — uniform 5-pixel steps
If a platform requires an unusual size, redraw or clean the result at that size instead of trusting a generic resize.

Rule three

Keep smoothing out of the final renderer.

In the browser, CSS gives you control over image scaling with image-rendering. Use pixelated — it is the value the spec guarantees nearest-neighbour scaling for, so upscales keep their hard edges. crisp-edges is the older, vaguer fallback: declare it first so ancient browsers get something, then let pixelated override it. Even so, exact whole-number sizing is still the safest path.

In Godot, 2D nodes inherit texture filtering through CanvasItem.texture_filter unless you override it. For pixel-art sprites, set the relevant CanvasItem texture filter to Nearest or set the project default canvas texture filter to Nearest, then check snapping settings if your art jitters or lands between pixels.

image-rendering, live

img { image-rendering: auto; }browser default smoothing
image-rendering

On an upscale, crisp-edges and pixelated look the same — both keep the grid hard. The visible jump is from auto to either of them.

Toggle the CSS property the rule teaches. auto smooths the fractional display; crisp-edges and pixelated keep the pixel grid intact.

When an asset looks soft, check the path

01

Canvas

Was the source made for the final size or a clean multiple of it?

02

Resize

Did any export step use a fractional size or smooth resampling?

03

Import

Did the app, browser, or engine enable filtering by default?

04

Placement

Is the sprite, camera, or UI element landing between screen pixels?

Most blur comes from one of these four steps, not from the art style itself.

Design to the visible mask

108 dp canvas — full adaptive layer. Outer area may be clipped.
72 dp viewport — the area the device mask shows. Keep must-read pixels well inside it.

Keep important pixels inside the safe circle. The corners exist for parallax, never for content the wearer must read. The only region guaranteed visible under every mask is a 66 dp circle, so keep critical pixels comfortably inside the viewport edge.

Watch-face and adaptive-icon canvases include a corner zone that may be cropped. Keep the part the wearer must read inside the safe circle.

Use cases

Different platforms need different discipline.

For icons and watch faces, design to the required canvas wherever possible. Android adaptive icons are a useful reminder: the foreground and background layers are 108 x 108dp, but only the inner 72 x 72dp is guaranteed inside the masked viewport. Keep the important pixel shape inside the safe area instead of touching the edge.

For games, whether you're authoring in Aseprite or any other editor, test at the same camera or viewport scale the player will actually see. A sprite can look correct in the editor and still soften when the camera scale, transform, or viewport stretches it at runtime. Heading into a specific engine? Exporting a Godot-ready pixel sprite walks the sheet-plus-metadata path end to end.

Keep a short export checklist

Browser

Use exact display sizes.

Prefer clean pixel dimensions, then use image-rendering for pixel art previews.

Godot

Use Nearest for pixel textures.

Set the CanvasItem texture filter or project canvas texture default, then test the viewport.

Icons

Respect the safe area.

Put the important motif inside the visible mask instead of relying on edge pixels.

The exact UI differs by tool, but the principle is the same: keep the grid explicit all the way through.

Pixelpond workflow

Reconstruct instead of rescuing.

Reconstruct, don't rescue

Pixelpond Engine is being built around the boring part that saves the asset later: choosing a precise canvas, reconstructing the reference into that grid, and exporting a file that already knows where every pixel should land.

The tool can still be useful if you use Aseprite, Photoshop, GIMP, Godot, or any other workflow. The core idea is portable: decide the target, draw to the target, scale cleanly, and verify the final renderer is not smoothing the result. Really this whole guide is one small belief of the studio made concrete — move fast to grab the rough version, then slow down to make every edge land on purpose. That same rhythm runs through everything here; see the studio note on making in the AI wave.

Starting from a generated image instead of a clean source? The companion article on reconstructing AI pixel art covers the step before this one: spotting the symptom and finding the real grid hidden inside the 1024 image.

Reconstruct, don't rescue

Crisp pixel-art checklist

  • Pick the final canvas before drawing or reconstructing.
  • Use common pixel sizes when they fit: 16, 32, 48, 64, 128, 256, 512, or 1024.
  • Prefer whole-number scaling such as 2x, 3x, or 4x.
  • Avoid fractional resize steps unless you plan to clean the art afterward.
  • Disable smoothing or filtering in the final renderer for pixel-art assets.
  • Test the asset at the final screen, camera, viewport, icon, or watch-face size.