HEIC/HEIF: From iPhone to Web
Convert iPhone HEIC photos for web use. Learn about HEIF format, conversion tools, automation strategies, and why you shouldn't serve HEIC directly on the web.
HEIC (High Efficiency Image Container) is the default photo format on iPhones, offering excellent quality at small file sizes. However, it’s not suitable for direct web use. This guide covers everything you need to know about handling HEIC files for web projects.
Understanding HEIC/HEIF
What’s the Difference?
| Term | Meaning |
|---|---|
| HEIF | High Efficiency Image Format - the container format |
| HEIC | HEIF with HEVC (H.265) codec - Apple’s implementation |
Why iPhones Use HEIC
| Feature | HEIC | JPEG |
|---|---|---|
| File size | 50% smaller | Baseline |
| Quality | Better at same size | Good |
| 10-bit color | Yes | No |
| HDR support | Yes | No |
| Live Photos | Yes | No |
Browser Support
| Browser | HEIC Support |
|---|---|
| Safari (macOS/iOS) | Yes |
| Chrome | No |
| Firefox | No |
| Edge | No |
Bottom line: Don’t serve HEIC on the web. Convert to JPEG, WebP, or AVIF.
Converting HEIC Files
Command-Line Tools
Using ImageMagick:
magick input.heic output.jpg
magick input.heic -quality 85 output.jpg
Using libheif:
heif-convert input.heic output.jpg -q 85
Using sips (macOS built-in):
sips -s format jpeg input.heic --out output.jpg
Node.js Conversion
const heicConvert = require('heic-convert');
const sharp = require('sharp');
const fs = require('fs').promises;
async function convertHeicToWeb(inputPath, outputDir) {
const inputBuffer = await fs.readFile(inputPath);
const jpegBuffer = await heicConvert({
buffer: inputBuffer,
format: 'JPEG',
quality: 0.9
});
const baseName = path.basename(inputPath, '.heic');
await fs.writeFile(path.join(outputDir, baseName + '.jpg'), jpegBuffer);
await sharp(jpegBuffer)
.webp({ quality: 80 })
.toFile(path.join(outputDir, baseName + '.webp'));
await sharp(jpegBuffer)
.avif({ quality: 65 })
.toFile(path.join(outputDir, baseName + '.avif'));
}
Python Conversion
from PIL import Image
import pillow_heif
pillow_heif.register_heif_opener()
def convert_heic(input_path, output_path):
img = Image.open(input_path)
if img.mode in ('RGBA', 'P'):
img = img.convert('RGB')
img.save(output_path, 'JPEG', quality=85)
Using Sirv for Automatic Conversion
Sirv automatically converts HEIC uploads:
<img src="https://your-site.sirv.com/photos/vacation.heic?format=optimal">
Sirv handles:
- Automatic HEIC detection
- On-the-fly conversion to WebP/AVIF
- Browser-based format negotiation
- No manual conversion needed
Handling iPhone Photo Uploads
Server-Side Handler
const multer = require('multer');
const heicConvert = require('heic-convert');
const sharp = require('sharp');
const upload = multer({ storage: multer.memoryStorage() });
app.post('/upload', upload.single('image'), async (req, res) => {
let imageBuffer = req.file.buffer;
const mimeType = req.file.mimetype;
if (mimeType === 'image/heic' || mimeType === 'image/heif') {
imageBuffer = await heicConvert({
buffer: imageBuffer,
format: 'JPEG',
quality: 0.9
});
}
const result = await sharp(imageBuffer)
.resize(1600, 1600, { fit: 'inside', withoutEnlargement: true })
.webp({ quality: 80 })
.toBuffer();
await saveToStorage(result);
res.json({ success: true });
});
File Size Comparison
| Format | Size | Quality |
|---|---|---|
| HEIC (original) | 1.8 MB | Excellent |
| JPEG 85% | 2.4 MB | Good |
| WebP 80% | 1.2 MB | Good |
| AVIF 65% | 0.8 MB | Good |
Best Practices
1. Never Serve HEIC on the Web
<!-- Do this instead -->
<picture>
<source srcset="photo.avif" type="image/avif">
<source srcset="photo.webp" type="image/webp">
<img src="photo.jpg" alt="Description">
</picture>
2. Convert on Upload, Not on Request
Convert images once during upload rather than on every request.
3. Use a CDN with HEIC Support
CDNs like Sirv handle conversion automatically.
4. Preserve Metadata When Needed
HEIC files contain rich EXIF data. Use tools like exifr to extract and preserve metadata during conversion.
Conclusion
HEIC/HEIF is great for iPhone storage but requires conversion for web use:
- Don’t serve HEIC directly - Only Safari supports it
- Convert to WebP/AVIF - Better compression than JPEG
- Automate conversion - Handle uploads automatically
- Use CDNs - Sirv converts HEIC on-the-fly
With proper handling, you can accept HEIC uploads from iPhone users while serving optimized images to all browsers.