出力形式 API
Sharp は複数の画像出力形式をサポートしており、各形式には特定のオプションと用途があります。
JPEG 形式
基本的な使い方
javascript
import sharp from 'sharp';
sharp('input.png')
.jpeg()
.toFile('output.jpg');JPEG オプション
javascript
sharp('input.png')
.jpeg({
quality: 80, // 品質 (1-100)
progressive: false, // プログレッシブ JPEG
chromaSubsampling: '4:4:4', // クロマサブサンプリング
mozjpeg: false, // mozjpeg エンコーダを使用
trellisQuantisation: false, // トレリス量子化
overshootDeringing: false, // オーバーシュートデリンギング
optimiseScans: false, // スキャン最適化
quantisationTable: 0 // 量子化テーブル
})
.toFile('output.jpg');品質設定
javascript
// 高品質
sharp('input.png').jpeg({ quality: 95 })
// 中品質
sharp('input.png').jpeg({ quality: 80 })
// 低品質(小ファイル)
sharp('input.png').jpeg({ quality: 50 })PNG 形式
基本的な使い方
javascript
sharp('input.jpg')
.png()
.toFile('output.png');PNG オプション
javascript
sharp('input.jpg')
.png({
progressive: false, // プログレッシブ PNG
compressionLevel: 6, // 圧縮レベル (0-9)
adaptiveFiltering: false, // 適応フィルタリング
palette: false, // パレットモード
quality: 100, // 品質 (パレットモードのみ)
colours: 256, // 色数 (パレットモードのみ)
dither: 0.5, // ディザリング (0-1)
force: false // PNG 出力を強制
})
.toFile('output.png');透明度の処理
javascript
// 透明度を保持
sharp('input.png')
.png()
.toFile('output.png');
// 白背景を追加
sharp('input.png')
.flatten({ background: { r: 255, g: 255, b: 255 } })
.png()
.toFile('output.png');WebP 形式
基本的な使い方
javascript
sharp('input.jpg')
.webp()
.toFile('output.webp');WebP オプション
javascript
sharp('input.jpg')
.webp({
quality: 80, // 品質 (1-100)
alphaQuality: 100, // 透明度品質 (1-100)
lossless: false, // 可逆圧縮
nearLossless: false, // ニア可逆圧縮
smartSubsample: false, // スマートサブサンプリング
reductionEffort: 4, // 圧縮努力 (0-6)
mixed: false, // 混合モード
force: false // WebP 出力を強制
})
.toFile('output.webp');可逆 WebP
javascript
// 可逆圧縮
sharp('input.png')
.webp({ lossless: true })
.toFile('output.webp');
// ニア可逆圧縮
sharp('input.png')
.webp({ nearLossless: true, quality: 60 })
.toFile('output.webp');AVIF 形式
基本的な使い方
javascript
sharp('input.jpg')
.avif()
.toFile('output.avif');AVIF オプション
javascript
sharp('input.jpg')
.avif({
quality: 80, // 品質 (1-100)
lossless: false, // 可逆圧縮
effort: 4, // 圧縮努力 (0-6)
chromaSubsampling: '4:4:4', // クロマサブサンプリング
force: false // AVIF 出力を強制
})
.toFile('output.avif');TIFF 形式
基本的な使い方
javascript
sharp('input.jpg')
.tiff()
.toFile('output.tiff');TIFF オプション
javascript
sharp('input.jpg')
.tiff({
quality: 80, // 品質 (1-100)
compression: 'jpeg', // 圧縮方式
pyramid: false, // ピラミッドモード
tile: false, // タイルモード
tileSize: 256, // タイルサイズ
xres: 1, // X 解像度
yres: 1, // Y 解像度
resolutionUnit: 'inch', // 解像度単位
force: false // TIFF 出力を強制
})
.toFile('output.tiff');圧縮オプション
javascript
// JPEG 圧縮
sharp('input.jpg').tiff({ compression: 'jpeg' })
// LZW 圧縮
sharp('input.jpg').tiff({ compression: 'lzw' })
// 圧縮なし
sharp('input.jpg').tiff({ compression: 'none' })
// Deflate 圧縮
sharp('input.jpg').tiff({ compression: 'deflate' })生形式 (raw)
生ピクセルデータの出力
javascript
// RGB 生データを出力
const rawData = await sharp('input.jpg')
.raw()
.toBuffer();
// RGBA 生データを出力
const rawData = await sharp('input.jpg')
.ensureAlpha()
.raw()
.toBuffer();マルチ形式出力
複数の形式を同時に出力
javascript
const image = sharp('input.jpg').resize(800, 600);
// 複数の形式を出力
await Promise.all([
image.clone().jpeg({ quality: 80 }).toFile('output.jpg'),
image.clone().png().toFile('output.png'),
image.clone().webp({ quality: 80 }).toFile('output.webp'),
image.clone().avif({ quality: 80 }).toFile('output.avif')
]);レスポンシブ画像
javascript
async function generateResponsiveImages(inputPath) {
const sizes = [320, 640, 1280, 1920];
const formats = ['jpeg', 'webp', 'avif'];
const promises = [];
for (const size of sizes) {
for (const format of formats) {
const image = sharp(inputPath).resize(size);
switch (format) {
case 'jpeg':
promises.push(
image.clone().jpeg({ quality: 80 })
.toFile(`output-${size}.jpg`)
);
break;
case 'webp':
promises.push(
image.clone().webp({ quality: 80 })
.toFile(`output-${size}.webp`)
);
break;
case 'avif':
promises.push(
image.clone().avif({ quality: 80 })
.toFile(`output-${size}.avif`)
);
break;
}
}
}
await Promise.all(promises);
}形式検出
ファイル拡張子に基づいて形式を自動選択
javascript
function getOutputFormat(filename) {
const ext = filename.split('.').pop().toLowerCase();
switch (ext) {
case 'jpg':
case 'jpeg':
return 'jpeg';
case 'png':
return 'png';
case 'webp':
return 'webp';
case 'avif':
return 'avif';
case 'tiff':
case 'tif':
return 'tiff';
default:
return 'jpeg';
}
}
async function convertImage(inputPath, outputPath) {
const format = getOutputFormat(outputPath);
const image = sharp(inputPath);
switch (format) {
case 'jpeg':
await image.jpeg({ quality: 80 }).toFile(outputPath);
break;
case 'png':
await image.png().toFile(outputPath);
break;
case 'webp':
await image.webp({ quality: 80 }).toFile(outputPath);
break;
case 'avif':
await image.avif({ quality: 80 }).toFile(outputPath);
break;
case 'tiff':
await image.tiff({ compression: 'jpeg' }).toFile(outputPath);
break;
}
}パフォーマンス最適化
ストリーム出力
javascript
const fs = require('fs');
// ストリーム処理
fs.createReadStream('input.jpg')
.pipe(sharp().jpeg({ quality: 80 }))
.pipe(fs.createWriteStream('output.jpg'));メモリ最適化
javascript
// ファイルではなく Buffer を使用
const buffer = await sharp('input.jpg')
.jpeg({ quality: 80 })
.toBuffer();
// 直接レスポンスに出力
app.get('/image', async (req, res) => {
const buffer = await sharp('input.jpg')
.resize(300, 200)
.jpeg({ quality: 80 })
.toBuffer();
res.set('Content-Type', 'image/jpeg');
res.send(buffer);
});