@johnfmorton/deep-zoom-viewer
v0.1.1
Published
A modern TypeScript library for viewing tiled DeepZoom (DZI) images with smooth pan/zoom interactions
Downloads
134
Maintainers
Readme
deep-zoom-viewer
A modern TypeScript library for viewing tiled DeepZoom (DZI) images with smooth pan/zoom interactions.
Features
- Supports DeepZoom (DZI) and Zoomify tile formats
- Smooth pan and zoom with mouse and touch support
- Optional toolbar with zoom controls and fullscreen toggle
- Navigator minimap showing viewport position
- LRU tile caching for optimal performance
- Tile fade-in transitions
- Center-out tile loading priority
- TypeScript with full type definitions
- Zero runtime dependencies (browser)
- CLI tool for generating DZI tiles from images
Installation
npm install @johnfmorton/deep-zoom-viewerQuick Start
import { DeepZoomViewer } from '@johnfmorton/deep-zoom-viewer';
const viewer = new DeepZoomViewer('container', {
source: '/images/my-image.dzi',
toolbar: true,
navigator: true
});
// Listen to events
viewer.on('zoom', ({ zoom }) => console.log('Zoom:', zoom));
viewer.on('click', ({ imageX, imageY }) => console.log('Clicked:', imageX, imageY));
// Programmatic control
viewer.setZoom(0.5);
viewer.panTo(1000, 500);
viewer.reset();
// Cleanup when done
viewer.destroy();HTML Setup
<div id="container" style="width: 800px; height: 600px;"></div>
<script type="module">
import { DeepZoomViewer } from '@johnfmorton/deep-zoom-viewer';
new DeepZoomViewer('container', {
source: '/images/photo.dzi'
});
</script>Configuration Options
| Option | Type | Default | Description |
|--------|------|---------|-------------|
| source | string | required | Path to DZI file or Zoomify directory |
| tileSource | 'deepzoom' \| 'zoomify' \| 'auto' | 'auto' | Tile format (auto-detected) |
| minZoom | number | fit-to-view | Minimum zoom level |
| maxZoom | number | 1.0 | Maximum zoom (1.0 = native resolution) |
| constrainPan | boolean | true | Keep image within viewport |
| toolbar | boolean | false | Show zoom controls |
| navigator | boolean | false | Show minimap |
| animationDuration | number | 300 | Transition duration (ms) |
Events
| Event | Data | Description |
|-------|------|-------------|
| ready | - | Viewer initialized |
| zoom | { zoom, source } | Zoom level changed |
| pan | { centerX, centerY, source } | Viewport panned |
| viewChange | { centerX, centerY, zoom, source } | Any view change |
| click | { imageX, imageY, viewportX, viewportY } | Image clicked/tapped |
| tileLoad | { tile } | Tile finished loading |
| tileError | { tile, error } | Tile failed to load |
| tilesLoaded | - | All visible tiles loaded |
| fullscreen | { isFullscreen } | Fullscreen state changed |
| resize | { width, height } | Viewport resized |
API Methods
View Control
// Zoom
viewer.setZoom(0.5); // Set zoom level
viewer.zoomIn(); // Zoom in by 1.5x
viewer.zoomOut(); // Zoom out by 1.5x
viewer.getZoom(); // Get current zoom
// Pan
viewer.panTo(x, y); // Pan to image coordinates
viewer.getCenter(); // Get current center { x, y }
// Reset
viewer.reset(); // Reset to fit viewCoordinate Conversion
// Convert between viewport and image coordinates
const imgPos = viewer.viewportToImage(viewportX, viewportY);
const vpPos = viewer.imageToViewport(imageX, imageY);UI Components
viewer.setToolbarVisible(true);
viewer.setNavigatorVisible(true);Utilities
viewer.getImageSize(); // { width, height }
viewer.getViewportSize(); // { width, height }
viewer.refresh(); // Force re-render
viewer.destroy(); // Clean up resourcesGenerating DZI Tiles
Use the CLI tool to convert images to DZI format:
# Basic usage
npx @johnfmorton/deep-zoom-viewer generate input.jpg output/
# With options
npx @johnfmorton/deep-zoom-viewer generate input.jpg output/ \
--tile-size 256 \
--format jpg \
--quality 85CLI Options
| Option | Default | Description |
|--------|---------|-------------|
| -s, --tile-size | 256 | Tile size in pixels |
| -o, --overlap | 0 | Tile overlap in pixels |
| -f, --format | jpg | Output format (jpg, png, webp) |
| -q, --quality | 85 | Output quality (1-100) |
Output Structure
output/
├── image.dzi # DZI XML descriptor
└── image_files/
├── 0/ # Smallest tier
│ └── 0_0.jpg
├── 1/
│ ├── 0_0.jpg
│ └── 1_0.jpg
└── N/ # Full resolution tier
└── ...DeepZoom Format
DZI XML File
<?xml version="1.0" encoding="UTF-8"?>
<Image TileSize="256" Overlap="0" Format="jpg"
xmlns="http://schemas.microsoft.com/deepzoom/2008">
<Size Width="4000" Height="3000"/>
</Image>Tile Naming
Tiles are named {column}_{row}.{format} (e.g., 3_2.jpg).
Advanced Usage
Custom Tile Source
import { TileSource, DeepZoomViewer } from '@johnfmorton/deep-zoom-viewer';
class CustomTileSource extends TileSource {
async load() {
return {
width: 4000,
height: 3000,
tileSize: 256,
overlap: 0,
format: 'jpg'
};
}
getTileUrl(tier, col, row) {
return `/tiles/${tier}/${col}_${row}.jpg`;
}
getType() {
return 'custom';
}
}Accessing Internal Components
// For advanced customization
import { Viewport, TilePyramid, TileManager } from '@johnfmorton/deep-zoom-viewer';Browser Support
- Chrome 80+
- Firefox 75+
- Safari 13+
- Edge 80+
Development
# Install dependencies
npm install
# Start dev server
npm run dev
# Run tests
npm test
# Build
npm run build
# Generate docs
npm run docsLicense
MIT
