thinpic_flutter 0.0.2
thinpic_flutter: ^0.0.2 copied to clipboard
A Flutter image compression library using the powerful C language VIPS library
thinpic_flutter #
A high-performance Flutter FFI plugin for image compression using the VIPS image processing library. This plugin provides efficient image compression with various optimization strategies for different use cases.
Features #
- Multiple Compression Strategies: Basic, size-constrained, large image, DSLR, and smart compression
- Cross-Platform: Works on Android, iOS, macOS, Linux, and Windows
- High Performance: Native C implementation using VIPS library
- Memory Efficient: Automatic buffer management and cleanup
- Thread-Safe: Thread-safe operations with proper synchronization
- Quality Control: Precise quality settings from 1-100
- Smart Compression: Automatic quality adjustment to meet target file sizes
Installation #
Add this to your pubspec.yaml
:
dependencies:
thinpic_flutter: ^0.0.1
API Reference #
Core Compression Functions #
compressImage(String inputPath, int quality)
Basic image compression with quality control.
Parameters:
inputPath
(String): Path to the input image filequality
(int): Compression quality from 1-100 (1 = lowest, 100 = highest)
Returns: CompressedImageResult
Example:
import 'package:thinpic_flutter/thinpic_flutter.dart';
final result = compressImage('/path/to/image.jpg', 80);
if (isCompressionSuccessful(result)) {
final bytes = compressedResultToBytes(result);
// Use the compressed image bytes
freeCompressedBuffer(result.data); // Important: Free the buffer to prevent memory leaks
}
compressImageWithSize(String inputPath, int quality, int targetWidth, int targetHeight)
Advanced compression with optional size parameters and aspect ratio preservation.
Parameters:
inputPath
(String): Path to the input image filequality
(int): Compression quality from 1-100targetWidth
(int): Target width in pixels (0 = no constraint)targetHeight
(int): Target height in pixels (0 = no constraint)
Resize Behavior:
- If both width and height are provided, the smallest dimension is used to maintain aspect ratio
- If only width is provided, height is calculated to maintain aspect ratio
- If only height is provided, width is calculated to maintain aspect ratio
- If both are 0 or negative, no resizing is applied (same as basic compression)
Returns: CompressedImageResult
Example:
// Width only - height calculated automatically
final result1 = compressImageWithSize('/path/to/image.jpg', 80, 1920, 0);
// Height only - width calculated automatically
final result2 = compressImageWithSize('/path/to/image.jpg', 80, 0, 1080);
// Both dimensions - smallest used to maintain aspect ratio
final result3 = compressImageWithSize('/path/to/image.jpg', 80, 1920, 1080);
// No resizing (same as basic compression)
final result4 = compressImageWithSize('/path/to/image.jpg', 80, 0, 0);
compressLargeImage(String inputPath, int quality)
Optimized compression for large images with enhanced memory management.
Parameters:
inputPath
(String): Path to the input image filequality
(int): Compression quality from 1-100
Returns: CompressedImageResult
Use Case: Best for images larger than 5MB or high-resolution photos.
Example:
final result = compressLargeImage('/path/to/large_image.jpg', 85);
compressLargeDslrImage(String inputPath, int quality)
Specialized compression optimized for DSLR camera images with enhanced quality preservation.
Parameters:
inputPath
(String): Path to the input image filequality
(int): Compression quality from 1-100
Returns: CompressedImageResult
Use Case: Best for professional DSLR photos that need high-quality compression.
Example:
final result = compressLargeDslrImage('/path/to/dslr_photo.jpg', 90);
smartCompressImage(String inputPath, int targetKb, int type)
Smart compression that automatically adjusts quality to meet target file size.
Parameters:
inputPath
(String): Path to the input image filetargetKb
(int): Target file size in kilobytestype
(int): Compression type (1 = high quality, 0 = low quality)
Quality Strategy:
- High Quality (type = 1): Starts at 93% quality, applies 1.3x resize, targets 20% tolerance
- Low Quality (type = 0): Starts at 85% quality, no resize, targets 20% tolerance
Returns: CompressedImageResult
Example:
// High quality compression targeting 500KB
final result1 = smartCompressImage('/path/to/image.jpg', 500, 1);
// Low quality compression targeting 200KB
final result2 = smartCompressImage('/path/to/image.jpg', 200, 0);
Utility Functions #
getImageInfo(String inputPath)
Retrieves detailed information about an image without compression.
Parameters:
inputPath
(String): Path to the input image file
Returns: ImageInfo
ImageInfo Properties:
width
(int): Image width in pixelsheight
(int): Image height in pixelsbands
(int): Number of color bands (3 for RGB, 4 for RGBA, etc.)orientation
(int): Image orientation metadataneeds_resize
(int): Whether resizing is recommendednew_width
(int): Recommended new widthnew_height
(int): Recommended new height
Example:
final info = getImageInfo('/path/to/image.jpg');
final (width, height) = getImageDimensions(info);
print('Image dimensions: ${width}x${height}');
isCompressionSuccessful(CompressedImageResult result)
Checks if compression was successful.
Parameters:
result
(CompressedImageResult): Result from any compression function
Returns: bool
Example:
final result = compressImage('/path/to/image.jpg', 80);
if (isCompressionSuccessful(result)) {
// Compression succeeded
} else {
// Compression failed
}
compressedResultToBytes(CompressedImageResult result)
Converts compression result to Dart bytes.
Parameters:
result
(CompressedImageResult): Result from any compression function
Returns: Uint8List
Example:
final result = compressImage('/path/to/image.jpg', 80);
if (isCompressionSuccessful(result)) {
final bytes = compressedResultToBytes(result);
// Use bytes for file writing, network upload, etc.
}
freeCompressedBuffer(Pointer<Uint8> buffer)
Frees the native memory buffer to prevent memory leaks.
Parameters:
buffer
(Pointer
Example:
final result = compressImage('/path/to/image.jpg', 80);
// Use the result...
freeCompressedBuffer(result.data); // Important: Free the buffer to prevent memory leaks
getImageDimensions(ImageInfo info)
Extracts width and height from ImageInfo as a tuple.
Parameters:
info
(ImageInfo): Image information from getImageInfo
Returns: (int width, int height)
Example:
final info = getImageInfo('/path/to/image.jpg');
final (width, height) = getImageDimensions(info);
shutdownVips()
Shuts down the VIPS library. Call this when your app is terminating.
Example:
// Call this in your app's dispose or shutdown method
shutdownVips();
testVipsBasic()
Tests basic VIPS functionality. Returns 1 if successful, 0 if failed.
Returns: int
Example:
final testResult = testVipsBasic();
if (testResult == 1) {
print('VIPS is working correctly');
} else {
print('VIPS test failed');
}
Data Structures #
CompressedImageResult #
class CompressedImageResult {
Pointer<Uint8> data; // Pointer to compressed image data
int length; // Length of compressed data in bytes
int success; // 1 if successful, 0 if failed
}
ImageInfo #
class ImageInfo {
int width; // Image width in pixels
int height; // Image height in pixels
int bands; // Number of color bands
int orientation; // Image orientation
int needs_resize; // Whether resizing is recommended
int new_width; // Recommended new width
int new_height; // Recommended new height
}
Best Practices #
1. Memory Management #
Always free the compressed buffer when you're done with it to prevent memory leaks:
final result = compressImage('/path/to/image.jpg', 80);
try {
if (isCompressionSuccessful(result)) {
final bytes = compressedResultToBytes(result);
// Use the bytes...
}
} finally {
freeCompressedBuffer(result.data); // Important: Free the buffer
}
2. Quality Settings #
- 90-100: High quality, minimal compression
- 70-89: Good quality, moderate compression
- 50-69: Acceptable quality, significant compression
- 30-49: Low quality, high compression
- 1-29: Very low quality, maximum compression
3. Function Selection #
- Basic compression: Use
compressImage()
for simple needs - Size constraints: Use
compressImageWithSize()
for specific dimensions - Large images: Use
compressLargeImage()
for files > 5MB - DSLR photos: Use
compressLargeDslrImage()
for professional photos - Target file size: Use
smartCompressImage()
for specific file size requirements
4. Error Handling #
final result = compressImage('/path/to/image.jpg', 80);
if (isCompressionSuccessful(result)) {
final bytes = compressedResultToBytes(result);
if (bytes.isNotEmpty) {
// Use the compressed image
} else {
print('Compression succeeded but no data returned');
}
} else {
print('Compression failed');
}
Platform Support #
- ✅ Android (ARM64, x86_64)
- ✅ iOS (ARM64, x86_64) (in progress)
Dependencies #
- VIPS: High-performance image processing library
- FFI: Dart foreign function interface
- pthread: Thread safety and synchronization
License #
MIT License - see LICENSE file for details.
Contributing #
Contributions are welcome! Please feel free to submit a Pull Request.
Support #
For issues and questions, please visit the GitHub repository.