OSStatus GeneratePreviewForURL(void *thisInterface, QLPreviewRequestRef preview, CFURLRef url, CFStringRef contentTypeUTI, CFDictionaryRef options) { CGDataProviderRef dataProvider = CGDataProviderCreateWithURL(url); if (!dataProvider) return -1; CFDataRef data = CGDataProviderCopyData(dataProvider); CGDataProviderRelease(dataProvider); if (!data) return -1; int width, height, channels; unsigned char* rgbadata = SOIL_load_image_from_memory(CFDataGetBytePtr(data), CFDataGetLength(data), &width, &height, &channels, SOIL_LOAD_RGBA); CFStringRef format=CFStringCreateWithBytes(NULL, CFDataGetBytePtr(data) + 0x54, 4, kCFStringEncodingASCII, false); CFRelease(data); if (!rgbadata) return -1; CGColorSpaceRef rgb = CGColorSpaceCreateDeviceRGB(); CGContextRef context = CGBitmapContextCreate(rgbadata, width, height, 8, width * 4, rgb, kCGImageAlphaPremultipliedLast); SOIL_free_image_data(rgbadata); CGColorSpaceRelease(rgb); if (!context) return -1; CGImageRef image = CGBitmapContextCreateImage(context); CGContextRelease(context); if (!image) return -1; /* Add basic metadata to title */ CFStringRef name = CFURLCopyLastPathComponent(url); CFTypeRef keys[1] = {kQLPreviewPropertyDisplayNameKey}; CFTypeRef values[1] = {CFStringCreateWithFormat(NULL, NULL, CFSTR("%@ (%dx%d %@)"), name, width, height, format)}; CFDictionaryRef properties = CFDictionaryCreate(NULL, (const void**)keys, (const void**)values, 1, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks); CFRelease(name); context = QLPreviewRequestCreateContext(preview, CGSizeMake(width, height), true, properties); CGContextDrawImage(context, CGRectMake(0, 0, width, height), image); QLPreviewRequestFlushContext(preview, context); CGContextRelease(context); CFRelease(format); CFRelease(properties); return noErr; }
OSStatus GeneratePreviewForURL(void *thisInterface, QLPreviewRequestRef preview, CFURLRef url, CFStringRef contentTypeUTI, CFDictionaryRef options) { if (url == NULL) { return -1; } //fprintf(stderr, "GeneratePreviewForURL\n"); CGImageRef imageRef = GetPngImage(url, contentTypeUTI); if (imageRef != NULL) { CGSize contextSize = CGSizeMake(CGImageGetWidth(imageRef), CGImageGetHeight(imageRef)); float ratio = contextSize.width / contextSize.height; //fprintf(stderr, "imageSize: %fx%f, ratio: %f\n", contextSize.width, contextSize.height, ratio); if ((contextSize.width > MAX_SIZE) || (contextSize.height > MAX_SIZE)) { if (contextSize.width > contextSize.height) { contextSize.width = MAX_SIZE; contextSize.height = MAX_SIZE/ratio; } else { contextSize.width = MAX_SIZE*ratio; contextSize.height = MAX_SIZE; } } else if ((contextSize.width < MIN_SIZE) || (contextSize.height < MIN_SIZE)) { if (contextSize.width < contextSize.height) { contextSize.width = MIN_SIZE; contextSize.height = MIN_SIZE/ratio; } else { contextSize.width = MIN_SIZE*ratio; contextSize.height = MIN_SIZE; } if ((contextSize.width > MAX_SIZE) || (contextSize.height > MAX_SIZE)) { if (contextSize.width > contextSize.height) { contextSize.width = MAX_SIZE; contextSize.height = MAX_SIZE/ratio; } else { contextSize.width = MAX_SIZE*ratio; contextSize.height = MAX_SIZE; } } } //fprintf(stderr, "contextSize: %fx%f\n", contextSize.width, contextSize.height); CGContextRef cgContext = QLPreviewRequestCreateContext(preview, contextSize, TRUE, NULL); if (cgContext != NULL) { CGContextSaveGState(cgContext); { CGRect contextRect = CGRectMake(0, 0, contextSize.width, contextSize.height); CGContextDrawImage(cgContext, contextRect, imageRef); } CGContextRestoreGState(cgContext); QLPreviewRequestFlushContext(preview, cgContext); CFRelease(cgContext); } CFRelease(imageRef); } return noErr; }