← All articles 8 min read

Image Splitter: 6 Ways to Split Images Into Grids

Splitting an image means cutting it into a grid of smaller tiles — 2x2, 3x3, or any NxM arrangement you need. The tiles can be reassembled later, printed separately, used in web layouts, or posted as an Instagram grid.

The use cases are more varied than you might expect:

Each method below handles a different workflow. The quick reference table helps you pick the right one, then jump to the detailed section.

Quick Reference: Image Splitting Methods Compared

Method Best For Grid Support Batch Cost Skill Level
Pixotter Quick browser-based splits Any NxM Yes Free Beginner
Photoshop v26.3 Designers already in Adobe Slice tool, guides Manual $22.99/mo Intermediate
GIMP v2.10.38 Free desktop alternative Script-Fu + Guillotine Semi-auto Free Intermediate
ImageMagick v7.1.1 CLI automation, scripting Any NxM via -crop Yes Free Advanced
Python Pillow 10.4 Custom logic, pipelines Fully programmable Yes Free Advanced
CSS Grid Display-only (no file output) Any layout N/A Free Intermediate

Our recommendation: For one-off splits, use Pixotter's crop tool — it runs in your browser, handles any grid size, and produces downloadable tiles in seconds. For automation or pipelines, ImageMagick or Python Pillow are the right tools.


Method 1: Split Images Online with Pixotter

The fastest path from "I have one image" to "I have grid tiles" is a browser-based tool. Pixotter's crop tool processes everything client-side via WebAssembly — your images never leave your device.

How to split an image into a grid with Pixotter:

  1. Open pixotter.com/crop.
  2. Drop your image onto the upload zone.
  3. Select the grid split mode and choose your grid dimensions (2x2, 3x3, 4x4, or custom rows and columns).
  4. Adjust tile boundaries if you need uneven splits.
  5. Click Split and download all tiles as individual files or a zip.

The entire operation takes under 10 seconds for a typical 4000x3000 image. Since processing is local, there are no file size limits or upload queues. You can also chain operations — resize your image first to exact dimensions, then split it, and download everything in one session.

For Instagram-specific splitting with correct post ordering and 1080x1080 tile dimensions, see our dedicated Instagram grid splitter guide.


Method 2: Photoshop v26.3 — Slice Tool

Photoshop's Slice tool was built for web designers who needed to chop layouts into image segments, and it works perfectly for grid splitting.

Steps:

  1. Open your image in Photoshop v26.3.
  2. Select the Slice tool (shortcut: C, then cycle to Slice).
  3. Right-click the image and choose Divide Slice.
  4. Enter the number of rows and columns. For a 3x3 grid: 3 horizontal, 3 vertical.
  5. Go to File → Export → Save for Web (Legacy) or use Export As.
  6. Choose your output format (JPEG, PNG, or WebP) and quality settings.
  7. Click Save. Photoshop creates a folder with individually numbered tiles.

Tips:

Limitations: Photoshop requires a Creative Cloud subscription ($22.99/mo for the Photography plan). It is overkill if splitting is all you need, but if you already have it open for other editing, Slice is fast.


Method 3: GIMP v2.10.38 — Script-Fu and Guillotine

GIMP has a built-in approach: place guides at your grid lines, then use the Guillotine function to cut along them. Script-Fu automates the guide placement.

Manual method:

  1. Open your image in GIMP v2.10.38.
  2. Go to Image → Guides → New Guide (by Percent). For a 3x3 grid, place vertical guides at 33.3% and 66.6%, and horizontal guides at 33.3% and 66.6%.
  3. Go to Image → Slice Using Guides (called "Guillotine" in some versions under Filters → Light and Shadow → Guillotine).
  4. GIMP creates separate image windows for each tile.
  5. Export each tile via File → Export As.

Automated method with Script-Fu:

Open Filters → Script-Fu → Console and paste:

; GIMP v2.10.38 Script-Fu: split image into 3x3 grid
(let* (
  (image (car (gimp-file-load RUN-NONINTERACTIVE "/path/to/image.jpg" "image.jpg")))
  (width (car (gimp-image-width image)))
  (height (car (gimp-image-height image)))
  (cols 3)
  (rows 3)
  (col-width (/ width cols))
  (row-height (/ height rows))
)
  ; Add vertical guides
  (let loop ((i 1))
    (when (< i cols)
      (gimp-image-add-vguide image (* i col-width))
      (loop (+ i 1))))
  ; Add horizontal guides
  (let loop ((i 1))
    (when (< i rows)
      (gimp-image-add-hguide image (* i row-height))
      (loop (+ i 1))))
  ; Guillotine
  (plug-in-guillotine RUN-NONINTERACTIVE image (car (gimp-image-get-active-drawable image)))
)

Change cols and rows to any grid dimensions. Each tile opens as a new image — use File → Export As on each, or write additional Script-Fu to batch-export.

Limitations: GIMP's Guillotine creates new image windows rather than auto-saving files, so exporting 9+ tiles gets tedious without additional scripting. For batch splitting, ImageMagick is a better choice.


Method 4: ImageMagick v7.1.1 — The -crop Flag

ImageMagick is the go-to CLI tool for image manipulation. Its -crop flag splits images with a single command and outputs numbered tile files automatically.

Split into equal grid tiles:

# ImageMagick v7.1.1: split image into 3x3 grid
magick input.jpg -crop 3x3@ +repage +adjoin tile_%02d.jpg

This divides the image into a 3 columns by 3 rows grid and outputs tile_00.jpg through tile_08.jpg. The @ after the dimensions tells ImageMagick to interpret 3x3 as a grid count rather than pixel dimensions. +repage resets the virtual canvas for each tile, and +adjoin ensures separate output files.

Split into tiles of a specific pixel size:

# ImageMagick v7.1.1: split into 500x500 pixel tiles
magick input.jpg -crop 500x500 +repage +adjoin tile_%02d.jpg

If the image dimensions are not evenly divisible by 500, the rightmost column and bottom row will contain smaller tiles. To handle this gracefully, resize first:

# Resize to exact multiple, then split
magick input.jpg -resize 1500x1500! -crop 3x3@ +repage +adjoin tile_%02d.jpg

The ! flag forces exact dimensions (ignoring aspect ratio). If you need to preserve aspect ratio, use Pixotter's resize tool to crop-fit to your target dimensions before splitting.

Split into horizontal or vertical strips:

# ImageMagick v7.1.1: split into 4 horizontal strips
magick input.jpg -crop 1x4@ +repage +adjoin strip_%02d.jpg

# ImageMagick v7.1.1: split into 3 vertical strips
magick input.jpg -crop 3x1@ +repage +adjoin strip_%02d.jpg

Batch split multiple images:

# ImageMagick v7.1.1: batch split all JPEGs in a directory into 2x2 grids
for img in *.jpg; do
  name="${img%.*}"
  magick "$img" -crop 2x2@ +repage +adjoin "${name}_tile_%02d.jpg"
done

For batch cropping with a visual interface instead of the command line, see our batch crop images guide.

Why ImageMagick is the best CLI option: One command, automatic file output, scriptable, handles any grid size, and it is available on every major OS via package managers (brew install imagemagick, apt install imagemagick, choco install imagemagick).


Method 5: Python Pillow 10.4

When you need custom splitting logic — variable tile sizes, overlap between tiles, metadata preservation, or integration into a larger pipeline — Python with Pillow gives you full control.

Basic grid split:

# Requires: pip install Pillow==10.4.0
from PIL import Image
from pathlib import Path

def split_image(image_path: str, rows: int, cols: int, output_dir: str = "tiles") -> list[str]:
    """Split an image into a rows x cols grid of tiles."""
    img = Image.open(image_path)
    width, height = img.size
    tile_w = width // cols
    tile_h = height // rows

    Path(output_dir).mkdir(parents=True, exist_ok=True)
    saved = []

    for row in range(rows):
        for col in range(cols):
            left = col * tile_w
            upper = row * tile_h
            right = left + tile_w if col < cols - 1 else width
            lower = upper + tile_h if row < rows - 1 else height

            tile = img.crop((left, upper, right, lower))
            filename = f"{output_dir}/tile_{row}_{col}.png"
            tile.save(filename)
            saved.append(filename)

    return saved

# Split into 3x3 grid
files = split_image("panorama.jpg", rows=3, cols=3)
print(f"Created {len(files)} tiles: {files}")

Split with overlap (useful for ML training data):

# Requires: pip install Pillow==10.4.0
from PIL import Image
from pathlib import Path

def split_with_overlap(image_path: str, tile_size: int, overlap: int, output_dir: str = "tiles") -> list[str]:
    """Split image into overlapping tiles of tile_size x tile_size pixels."""
    img = Image.open(image_path)
    width, height = img.size
    step = tile_size - overlap

    Path(output_dir).mkdir(parents=True, exist_ok=True)
    saved = []
    idx = 0

    y = 0
    while y + tile_size <= height:
        x = 0
        while x + tile_size <= width:
            tile = img.crop((x, y, x + tile_size, y + tile_size))
            filename = f"{output_dir}/tile_{idx:04d}.png"
            tile.save(filename)
            saved.append(filename)
            idx += 1
            x += step
        y += step

    return saved

# 256x256 tiles with 32px overlap
files = split_with_overlap("satellite.tif", tile_size=256, overlap=32)

Recombine tiles (for verification):

After splitting, you often want to verify by reassembling. The inverse operation is combining tiles back into one image — covered in detail in our combine images guide.

# Requires: pip install Pillow==10.4.0
from PIL import Image

def combine_tiles(tile_paths: list[str], rows: int, cols: int, output_path: str) -> None:
    """Reassemble grid tiles into a single image."""
    tiles = [Image.open(p) for p in tile_paths]
    tile_w, tile_h = tiles[0].size
    result = Image.new("RGB", (cols * tile_w, rows * tile_h))

    for idx, tile in enumerate(tiles):
        row, col = divmod(idx, cols)
        result.paste(tile, (col * tile_w, row * tile_h))

    result.save(output_path)

Method 6: CSS Grid (Display-Only Splitting)

Sometimes you do not need separate tile files — you need a single image displayed as a grid in a web page. CSS can split an image visually without any server-side processing.

<!-- Display one image as a 3x3 visual grid -->
<div style="
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-template-rows: repeat(3, 1fr);
  width: 600px;
  height: 600px;
  gap: 2px;
">
  <div style="background: url('photo.jpg') 0% 0% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 50% 0% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 100% 0% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 0% 50% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 50% 50% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 100% 50% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 0% 100% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 50% 100% / 300% 300%;"></div>
  <div style="background: url('photo.jpg') 100% 100% / 300% 300%;"></div>
</div>

The background-size: 300% 300% scales the image to 3x its container, then background-position shifts to show the correct tile. For an NxN grid, set background-size to N*100% and space positions evenly.

When this makes sense: Reveal animations (tiles appear one at a time), hover effects (zoom into a section), or puzzle games where users rearrange tiles. The browser loads one image file, so there is no download overhead from multiple tiles.

When this does not work: You need actual separate image files — for printing, uploading to social media, or processing in another tool. Use one of the file-based methods above instead.


Common Grid Dimensions and Use Cases

Grid Tiles Typical Use
2x2 4 Before/after comparisons, quad photo layouts
3x3 9 Instagram profile grids, puzzle games
4x4 16 Print posters (A3 across 16 A5 sheets)
3x1 3 Instagram carousel, horizontal panorama strips
1x3 3 Vertical infographic sections, scroll-reveal panels
NxN (custom) Varies ML training data, map tiles, sprite extraction

For Instagram-specific grid dimensions and posting order, see our complete Instagram grid splitting tutorial.


Tips for Clean Splits

Prep your source image first. If your image dimensions are not evenly divisible by your grid, tiles will have unequal sizes. Resize to exact multiples before splitting. A 3000x3000 image splits cleanly into a 3x3 grid (1000x1000 tiles), but a 2999x3001 image produces mismatched edges. Pixotter's resize tool can crop-fit to exact pixel dimensions.

Name tiles systematically. Use row_col naming (tile_0_0.png, tile_0_1.png) rather than sequential numbering. When you need to reassemble, row-column names encode the grid position directly.

Preserve the original. Always keep the source image. Reassembling tiles from lossy formats (JPEG) introduces generation loss at tile boundaries. Split from the original, not from a previously compressed copy.

Match format to purpose. PNG for tiles that need transparency or lossless quality. JPEG for photos where file size matters. WebP for web delivery with good compression. Our best image format guide covers the tradeoffs in detail.

Check for visual continuity. After splitting, open adjacent tiles side by side. Seams should be invisible — if you see offset lines or color shifts, the crop coordinates are off by a pixel.


Frequently Asked Questions

How do I split an image into a 3x3 grid?

Use ImageMagick: magick input.jpg -crop 3x3@ +repage +adjoin tile_%02d.jpg. This outputs 9 tiles numbered 00-08. For a visual tool, Pixotter's crop tool lets you select 3x3 and download all tiles in one click.

What image formats work for splitting?

All standard raster formats: JPEG, PNG, WebP, AVIF, TIFF, BMP, and GIF. Vector formats (SVG) need to be rasterized first. For the best quality, split from PNG or TIFF originals — JPEG recompression at tile boundaries can create visible artifacts.

Can I split an image into unequal sections?

Yes. In Photoshop, drag slice boundaries manually. In Python Pillow, specify custom crop coordinates for each tile instead of using equal division. ImageMagick supports pixel-based cropping: magick input.jpg -crop 800x600+0+0 +repage top_left.jpg extracts an 800x600 region from the top-left corner.

How do I split a panorama into strips?

Use a 1-row grid: magick panorama.jpg -crop 4x1@ +repage +adjoin strip_%02d.jpg creates 4 vertical strips. For horizontal strips from a tall image, use 1x4@. This is useful for carousel posts or scroll-triggered reveals.

Does splitting reduce image quality?

Not if you use PNG or another lossless format. Splitting is just cropping — the pixel data within each tile is identical to the original. If you save tiles as JPEG, each tile undergoes its own compression pass, which can introduce artifacts at low quality settings. Use quality 90+ for JPEG tiles to keep degradation invisible.

How do I reassemble split tiles back into one image?

ImageMagick can stitch tiles: magick montage tile_*.jpg -tile 3x3 -geometry +0+0 reassembled.jpg. In Python, use Image.paste() to place tiles at their grid positions. Our combine images guide covers five different reassembly methods in detail.

What is the difference between splitting and cropping?

Cropping extracts one region from an image and discards the rest. Splitting divides the entire image into multiple tiles — every pixel ends up in exactly one output file. Splitting is essentially multiple crops applied in a grid pattern. For single-region extraction, use Pixotter's crop tool. For grid splitting, use any method in this guide.

How do I automate splitting hundreds of images?

Write a shell loop with ImageMagick: for img in *.jpg; do magick "$img" -crop 3x3@ +repage +adjoin "${img%.*}_tile_%02d.jpg"; done. For more complex logic (conditional grid sizes, metadata routing), use the Python Pillow script above inside a directory iterator. For batch cropping without code, see our batch crop images tool.