Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Example/SDWebImagePDFCoder-Example-macOS/ViewController.m
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ - (void)viewDidLoad {
NSAssert(pdfData.length > 0, @"PDF Data export failed");
}
}];
[imageView2 sd_setImageWithURL:pdfURL2 placeholderImage:nil options:SDWebImageRetryFailed context:@{SDWebImageContextPDFImageSize : @(imageView2.bounds.size)} progress:nil completed:^(UIImage * _Nullable image, NSError * _Nullable error, SDImageCacheType cacheType, NSURL * _Nullable imageURL) {
[imageView2 sd_setImageWithURL:pdfURL2 placeholderImage:nil options:SDWebImageRetryFailed context:@{SDWebImageContextImageThumbnailPixelSize : @(imageView2.bounds.size)} progress:nil completed:^(UIImage * _Nullable image, NSError * _Nullable error, SDImageCacheType cacheType, NSURL * _Nullable imageURL) {
if (image) {
NSLog(@"PDF load animation success");
[NSAnimationContext runAnimationGroup:^(NSAnimationContext * _Nonnull context) {
Expand Down
15 changes: 6 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ You can modify the code or use some other PDF files to check the compatibility.
+ tvOS 9+
+ macOS 10.11+
+ watchOS 2+
+ Xcode 11+
+ Xcode 13+

## Installation

Expand Down Expand Up @@ -50,7 +50,7 @@ SDWebImagePDFCoder is available through [Swift Package Manager](https://swift.or
```swift
let package = Package(
dependencies: [
.package(url: "https://github.com/SDWebImage/SDWebImagePDFCoder.git", from: "0.6")
.package(url: "https://github.com/SDWebImage/SDWebImagePDFCoder.git", from: "1.0")
]
)
```
Expand Down Expand Up @@ -115,24 +115,21 @@ imageView.sd_setImage(with: url, placeholderImage: nil, options: [], context: [.

`SDWebImagePDFCoder` provide an easy way to export the PDF image generated from framework, to the original PDF data.

Note: For firmware which is below iOS/tvOS 11+, UIImage does not support PDF vector image as well as exporting. The bitmap form of PDF does not support PDF data export as well.
If the input image is already vector PDF based, will export that instead (fast).
Else we will create an empty PDF page with the bitmap image drawn on (slow).

+ Objective-C

```objectivec
UIImage *pdfImage; // UIImage with vector image, or NSImage contains `NSPDFImageRep`
if (pdfImage.sd_isVector) { // This API available in SDWebImage 5.6.0
NSData *pdfData = [pdfImage sd_imageDataAsFormat:SDImageFormatPDF];
}
NSData *pdfData = [pdfImage sd_imageDataAsFormat:SDImageFormatPDF]; // May return the vector data, or create new PDF with current image drawn on
```

+ Swift

```swift
let pdfImage: UIImage // UIImage with vector image, or NSImage contains `NSPDFImageRep`
if pdfImage.sd_isVector { // This API available in SDWebImage 5.6.0
let pdfData = pdfImage.sd_imageData(as: .PDF)
}
let pdfData = pdfImage.sd_imageData(as: .PDF) // May return the vector data, or create new PDF with current image drawn on
```

## Screenshot
Expand Down
28 changes: 24 additions & 4 deletions SDWebImagePDFCoder/Classes/SDImagePDFCoder.m
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ - (UIImage *)decodedImageWithData:(NSData *)data options:(SDImageCoderOptions *)
BOOL prefersBitmap = NO;
CGSize imageSize = CGSizeZero;
BOOL preserveAspectRatio = YES;

// Parse args
if (options[SDImageCoderDecodePDFPageNumber]) {
pageNumber = [options[SDImageCoderDecodePDFPageNumber] unsignedIntegerValue];
Expand Down Expand Up @@ -101,20 +101,20 @@ - (BOOL)canEncodeToFormat:(SDImageFormat)format {

- (NSData *)encodedDataWithImage:(UIImage *)image format:(SDImageFormat)format options:(SDImageCoderOptions *)options {
if (![self.class supportsVectorPDFImage]) {
return nil;
return [self.class createPDFDataWithBitmapImage:image];
}
#if SD_MAC
// Pixel size use `NSImageRepMatchesDevice` to avoid CGImage bitmap format
NSRect imageRect = NSMakeRect(0, 0, NSImageRepMatchesDevice, NSImageRepMatchesDevice);
NSImageRep *imageRep = [image bestRepresentationForRect:imageRect context:nil hints:nil];
if (![imageRep isKindOfClass:NSPDFImageRep.class]) {
return nil;
return [self.class createPDFDataWithBitmapImage:image];
}
return ((NSPDFImageRep *)imageRep).PDFRepresentation;
#else
CGPDFPageRef page = ((CGPDFPageRef (*)(id,SEL))[image methodForSelector:SDCGPDFPageSEL])(image, SDCGPDFPageSEL);
if (!page) {
return nil;
return [self.class createPDFDataWithBitmapImage:image];
}

// Draw the PDF page using PDFContextToData
Expand Down Expand Up @@ -175,6 +175,26 @@ - (UIImage *)createVectorPDFWithData:(nonnull NSData *)data pageNumber:(NSUInteg
return image;
}

#pragma mark - Bitmap PDF creation
+ (NSData *)createPDFDataWithBitmapImage:(UIImage *)image {
CGImageRef imageRef = image.CGImage;
if (!imageRef) {
return nil;
}
NSMutableData *pdfData = [NSMutableData data];
CGDataConsumerRef pdfConsumer = CGDataConsumerCreateWithCFData((__bridge CFMutableDataRef)pdfData);

CGSize imageSize = CGSizeMake(CGImageGetWidth(imageRef), CGImageGetHeight(imageRef));
CGRect mediaBox = CGRectMake(0, 0, imageSize.width, imageSize.height);
CGContextRef context = CGPDFContextCreate(pdfConsumer, &mediaBox, NULL);

CGContextBeginPage(context, &mediaBox);
CGContextDrawImage(context, mediaBox, imageRef);
CGContextEndPage(context);

return [pdfData copy];
}

+ (BOOL)supportsVectorPDFImage {
#if SD_MAC
// macOS's `NSImage` supports PDF built-in rendering
Expand Down