CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-sharp

High performance Node.js image processing library for resizing JPEG, PNG, WebP, GIF, AVIF and TIFF images

80

1.01x
Overview
Eval results
Files

output-formats.mddocs/

Output and Formats

Sharp supports comprehensive output options with format-specific optimizations and extensive metadata control.

Capabilities

Core Output Methods

Write processed images to files or buffers.

/**
 * Write image to file with automatic format detection
 * @param fileOut - Output file path
 * @param callback - Optional callback function
 * @returns Promise resolving to output information
 */
toFile(fileOut: string, callback?: (err: Error, info: OutputInfo) => void): Promise<OutputInfo>;

/**
 * Write image to Buffer
 * @param options - Buffer output options
 * @returns Promise resolving to Buffer
 */
toBuffer(options?: BufferOptions): Promise<Buffer>;

/**
 * Write image to Buffer with metadata
 * @param options - Buffer output options with resolveWithObject: true
 * @returns Promise resolving to object with data and info
 */
toBuffer(options: { resolveWithObject: true }): Promise<{ data: Buffer; info: OutputInfo }>;

interface OutputInfo {
  /** Output format identifier */
  format: string;
  /** Output file size in bytes */
  size: number;
  /** Output width in pixels */
  width: number;
  /** Output height in pixels */
  height: number;
  /** Number of channels in output */
  channels: number;
  /** Whether premultiplication was used */
  premultiplied: boolean;
  /** Crop offset (when using crop strategies) */
  cropOffsetLeft?: number;
  cropOffsetTop?: number;
  /** Trim offset (when using trim) */
  trimOffsetLeft?: number;
  trimOffsetTop?: number;
}

interface BufferOptions {
  /** Resolve with object containing data and info */
  resolveWithObject?: boolean;
}

Usage Examples:

// Write to file (format auto-detected from extension)
const info = await sharp('input.jpg')
  .resize(800, 600)
  .toFile('output.webp');
console.log(`Output: ${info.width}x${info.height}, ${info.size} bytes`);

// Write to buffer
const buffer = await sharp('input.png')
  .jpeg({ quality: 90 })
  .toBuffer();

// Write to buffer with metadata  
const { data, info } = await sharp('input.tiff')
  .png()
  .toBuffer({ resolveWithObject: true });

JPEG Output

High-quality JPEG output with extensive compression controls.

/**
 * Configure JPEG output options
 * @param options - JPEG-specific options
 * @returns Sharp instance for chaining
 */
jpeg(options?: JpegOptions): Sharp;

interface JpegOptions {
  /** Quality level (1-100, default 80) */
  quality?: number;
  /** Use progressive encoding */
  progressive?: boolean;
  /** Chroma subsampling ('4:2:0' or '4:4:4') */
  chromaSubsampling?: string;
  /** Apply trellis quantization */
  trellisQuantisation?: boolean;
  /** Apply overshoot deringing */
  overshootDeringing?: boolean;
  /** Optimize progressive scans */
  optimiseScans?: boolean;
  optimizeScans?: boolean;
  /** Optimize Huffman coding tables */
  optimiseCoding?: boolean;
  optimizeCoding?: boolean;
  /** Quantization table (0-8) */
  quantisationTable?: number;
  quantizationTable?: number;
  /** Use mozjpeg encoder defaults */
  mozjpeg?: boolean;
}

Usage Examples:

// High-quality JPEG
await sharp('input.png')
  .jpeg({
    quality: 95,
    progressive: true,
    optimizeCoding: true
  })
  .toFile('high-quality.jpg');

// Web-optimized JPEG
await sharp('input.tiff')
  .jpeg({
    quality: 85,
    progressive: true,
    mozjpeg: true
  })
  .toFile('web-optimized.jpg');

// Print-quality JPEG
await sharp('input.raw')
  .jpeg({
    quality: 100,
    chromaSubsampling: '4:4:4',
    trellisQuantisation: true
  })
  .toFile('print-quality.jpg');

PNG Output

Lossless PNG output with compression and palette options.

/**
 * Configure PNG output options
 * @param options - PNG-specific options
 * @returns Sharp instance for chaining
 */
png(options?: PngOptions): Sharp;

interface PngOptions {
  /** Use progressive (interlaced) encoding */
  progressive?: boolean;
  /** zlib compression level (0-9, default 6) */
  compressionLevel?: number;
  /** Use adaptive row filtering */
  adaptiveFiltering?: boolean;
  /** Quality for palette reduction (0-100, default 100) */
  quality?: number;
  /** CPU effort for file size reduction (1-10, default 7) */
  effort?: number;
  /** Use palette-based encoding */
  palette?: boolean;
  /** Maximum palette colors */
  colours?: number;
  colors?: number;
  /** Floyd-Steinberg dithering level */
  dither?: number;
}

Usage Examples:

// High compression PNG
await sharp('input.jpg')
  .png({
    compressionLevel: 9,
    adaptiveFiltering: true,
    effort: 10
  })
  .toFile('compressed.png');

// Palette PNG for web
await sharp('input.jpg')
  .png({
    palette: true,
    colors: 256,
    quality: 90,
    dither: 1.0
  })
  .toFile('palette.png');

// Progressive PNG
await sharp('input.bmp')
  .png({
    progressive: true,
    compressionLevel: 6
  })
  .toFile('progressive.png');

WebP Output

Modern WebP format with excellent compression and quality.

/**
 * Configure WebP output options
 * @param options - WebP-specific options
 * @returns Sharp instance for chaining
 */
webp(options?: WebpOptions): Sharp;

interface WebpOptions {
  /** Quality level (1-100, default 80) */
  quality?: number;
  /** Alpha channel quality (0-100, default 100) */
  alphaQuality?: number;
  /** Use lossless compression */
  lossless?: boolean;
  /** Use near-lossless compression */
  nearLossless?: boolean;
  /** Use smart chroma subsampling */
  smartSubsample?: boolean;
  /** Auto-adjust deblocking filter */
  smartDeblock?: boolean;
  /** CPU effort for file size reduction (0-6, default 4) */
  effort?: number;
  /** Animation loop count */
  loop?: number;
  /** Frame delays for animation */
  delay?: number | number[];
  /** Minimize animation file size */
  minSize?: boolean;
  /** Allow mixed lossy/lossless frames */
  mixed?: boolean;
  /** Encoding preset */
  preset?: 'default' | 'photo' | 'picture' | 'drawing' | 'icon' | 'text';
}

Usage Examples:

// High-quality WebP
await sharp('input.jpg')
  .webp({
    quality: 90,
    effort: 6
  })
  .toFile('high-quality.webp');

// Lossless WebP
await sharp('input.png')
  .webp({
    lossless: true
  })
  .toFile('lossless.webp');

// Animated WebP
await sharp('frames/*.jpg')
  .webp({
    quality: 80,
    loop: 0,
    delay: [100, 200, 150]
  })
  .toFile('animated.webp');

AVIF Output

Next-generation AVIF format with superior compression.

/**
 * Configure AVIF output options
 * @param options - AVIF-specific options
 * @returns Sharp instance for chaining
 */
avif(options?: AvifOptions): Sharp;

interface AvifOptions {
  /** Quality level (1-100, default 50) */
  quality?: number;
  /** Use lossless compression */
  lossless?: boolean;
  /** CPU effort (0-9, default 4) */
  effort?: number;
  /** Chroma subsampling ('4:2:0' or '4:4:4') */
  chromaSubsampling?: string;
  /** Bit depth (8, 10, or 12) */
  bitdepth?: 8 | 10 | 12;
}

Usage Examples:

// Standard AVIF
await sharp('input.jpg')
  .avif({
    quality: 60,
    effort: 6
  })
  .toFile('compressed.avif');

// High bit-depth AVIF
await sharp('input.tiff')
  .avif({
    quality: 80,
    bitdepth: 10,
    effort: 9
  })
  .toFile('hdr.avif');

TIFF Output

Professional TIFF output with multiple compression options.

/**
 * Configure TIFF output options
 * @param options - TIFF-specific options
 * @returns Sharp instance for chaining
 */
tiff(options?: TiffOptions): Sharp;

interface TiffOptions {
  /** Quality for JPEG compression (1-100, default 80) */
  quality?: number;
  /** Compression method */
  compression?: 'none' | 'jpeg' | 'deflate' | 'packbits' | 'ccittfax4' | 'lzw' | 'webp' | 'zstd' | 'jp2k';
  /** Compression predictor */
  predictor?: 'none' | 'horizontal' | 'float';
  /** Create image pyramid */
  pyramid?: boolean;
  /** Create tiled TIFF */
  tile?: boolean;
  /** Tile width (default 256) */
  tileWidth?: number;
  /** Tile height (default 256) */
  tileHeight?: number;
  /** Horizontal resolution (pixels/mm) */
  xres?: number;
  /** Vertical resolution (pixels/mm) */
  yres?: number;
  /** Resolution unit */
  resolutionUnit?: 'inch' | 'cm';
  /** Bit depth reduction */
  bitdepth?: 1 | 2 | 4 | 8;
  /** Use miniswhite for 1-bit images */
  miniswhite?: boolean;
}

Usage Examples:

// Compressed TIFF
await sharp('input.jpg')
  .tiff({
    compression: 'lzw',
    predictor: 'horizontal'
  })
  .toFile('compressed.tiff');

// High-resolution print TIFF
await sharp('input.raw')
  .tiff({
    compression: 'none',
    xres: 300,
    yres: 300,
    resolutionUnit: 'inch'
  })
  .toFile('print.tiff');

// Tiled TIFF for large images
await sharp('huge-input.tiff')
  .tiff({
    tile: true,
    tileWidth: 512,
    tileHeight: 512,
    compression: 'jpeg',
    quality: 90
  })
  .toFile('tiled.tiff');

Additional Formats

Sharp supports many other formats with specific options.

/**
 * Configure HEIF/HEIC output
 */
heif(options?: HeifOptions): Sharp;

/**
 * Configure GIF output (requires ImageMagick)
 */
gif(options?: GifOptions): Sharp;

/**
 * Configure JPEG 2000 output
 */
jp2(options?: Jp2Options): Sharp;

/**
 * Configure JPEG-XL output (experimental)
 */
jxl(options?: JxlOptions): Sharp;

/**
 * Configure raw pixel output
 */
raw(options?: RawOptions): Sharp;

interface FormatInfo {
  id: string;
  input: { file: boolean; buffer: boolean; stream: boolean };
  output: { file: boolean; buffer: boolean; stream: boolean };
}

/**
 * Force specific output format
 */
toFormat(format: string | FormatInfo, options?: any): Sharp;

Deep Zoom Tiles

Generate tiled image pyramids for web viewing.

/**
 * Generate tiled pyramid output
 * @param options - Tile generation options
 * @returns Sharp instance for chaining
 */
tile(options?: TileOptions): Sharp;

interface TileOptions {
  /** Tile size in pixels (1-8192, default 256) */
  size?: number;
  /** Tile overlap in pixels (0-8192, default 0) */
  overlap?: number;
  /** Tile rotation angle (multiple of 90) */
  angle?: number;
  /** Background color */
  background?: string | RGBA;
  /** Pyramid depth */
  depth?: 'onepixel' | 'onetile' | 'one';
  /** Skip blank tiles threshold */
  skipBlanks?: number;
  /** Container format */
  container?: 'fs' | 'zip';
  /** Tile layout */
  layout?: 'dz' | 'iiif' | 'iiif3' | 'zoomify' | 'google';  
  /** Center tiles */
  centre?: boolean;
  center?: boolean;
  /** IIIF identifier */
  id?: string;
  /** Zip directory basename */
  basename?: string;
}

Usage Examples:

// Deep Zoom tiles
await sharp('large-image.jpg')
  .tile({
    size: 512,
    overlap: 2,
    layout: 'dz'
  })
  .toFile('tiles.dzi');

// IIIF tiles
await sharp('manuscript.tiff')
  .tile({
    layout: 'iiif',
    id: 'https://example.com/iiif/manuscript',
    size: 256
  })
  .toFile('iiif-tiles');

// Zoomify tiles
await sharp('artwork.png')
  .tile({
    layout: 'zoomify',
    background: 'white'
  })
  .toFile('zoomify-tiles');

Metadata Handling

Control metadata preservation and modification in output images.

/**
 * Keep all metadata from input
 */
keepMetadata(): Sharp;

/**
 * Keep EXIF metadata
 */
keepExif(): Sharp;

/**
 * Set EXIF metadata
 */
withExif(exif: Exif): Sharp;

/**
 * Merge EXIF metadata with existing
 */
withExifMerge(exif: Exif): Sharp;

/**
 * Keep ICC color profile
 */
keepIccProfile(): Sharp;

/**
 * Set ICC color profile
 */
withIccProfile(profile: string, options?: WithIccProfileOptions): Sharp;

/**
 * Keep XMP metadata
 */
keepXmp(): Sharp;

/**
 * Set XMP metadata
 */
withXmp(xmp: string): Sharp;

/**
 * Set custom metadata
 */
withMetadata(metadata?: WriteableMetadata): Sharp;

interface WriteableMetadata {
  /** Image density (DPI) */
  density?: number;
  /** EXIF orientation (1-8) */
  orientation?: number;
}

Usage Examples:

// Preserve all metadata
await sharp('input.jpg')
  .resize(800, 600)
  .keepMetadata()
  .toFile('resized-with-metadata.jpg');

// Custom EXIF data
await sharp('input.jpg')
  .withExif({
    IFD0: {
      Copyright: '© 2024 Example Corp',
      Artist: 'Jane Photographer'
    }
  })
  .jpeg()
  .toFile('with-copyright.jpg');

// Set color profile
await sharp('input.jpg')
  .withIccProfile('srgb')
  .toFile('color-managed.jpg');

Performance and Quality

Format Selection Guide:

  • JPEG: Best for photographs, good compression
  • PNG: Best for graphics with transparency, lossless
  • WebP: Excellent compression, modern browser support
  • AVIF: Superior compression, limited support
  • TIFF: Professional workflows, uncompressed or lossless compression

Quality vs Size Trade-offs:

const optimizeForWeb = async (input, output) => {
  const { width } = await sharp(input).metadata();
  
  // Choose format and quality based on content and size
  if (width > 1920) {
    // Large images: prioritize compression
    await sharp(input)
      .resize({ width: 1920, fit: 'inside' })
      .webp({ quality: 80, effort: 6 })
      .toFile(output);
  } else {
    // Smaller images: balance quality and size
    await sharp(input)
      .webp({ quality: 90, effort: 4 })
      .toFile(output);
  }
};

Install with Tessl CLI

npx tessl i tessl/npm-sharp

docs

color-channels.md

composition.md

constructor-input.md

index.md

metadata-stats.md

operations-filters.md

output-formats.md

resize-geometry.md

utilities-performance.md

tile.json