2009-11-20 3 views
0

J'ai une image jpeg et je veux être capable de la compresser incrémentalement en utilisant Cocoa/Core Image/Core Graphics. Par exemple, j'ai A.jpg (3MB), je comprime A et j'obtiens B.jpg (1MB), je comprime B et j'obtiens C.jpg (400KB), et ainsi de suite jusqu'à ce que l'image ne puisse plus être compressée. J'essaie d'utiliser NSBitmapImageRep representationUsingType: propriétés sans beaucoup de succès. J'utilise un représentant d'image créé à partir de données d'image compressées pour essayer de compresser davantage, mais cela ne fonctionne pas bien, si j'utilise un facteur de compression qui est le même facteur utilisé pour créer les données compressées initiales.Comment compresser l'image jpeg avec Cocoa?

Voici le code que je suis avec Wrangling

 
NSString * fileName = @"largeImage.jpg"; 

NSLog(@"== Initializing ==\n"); 

NSData * imageData = [NSData dataWithContentsOfFile:fileName]; 
NSLog(@"imageData length: %d\n", [imageData length]); 

NSImage * image = [[NSImage alloc] initWithData:imageData]; 
NSBitmapImageRep * bitmapRep = [[image representations] objectAtIndex:0]; 

NSData * data = [bitmapRep representationUsingType:NSJPEGFileType properties:nil]; 
NSLog(@"data length: %d\n", [data length]); 

NSDictionary * dict = [NSDictionary dictionaryWithObject: [NSNumber numberWithFloat:0.5] forKey:NSImageCompressionFactor]; 
NSData * data5 = [bitmapRep representationUsingType:NSJPEGFileType properties:dict]; 
NSLog(@"data5 length: %d\n", [data5 length]); 

NSLog(@"== End ==\n\n"); 

NSLog(@"== Image from Data5 ==\n"); 
NSImage * imageFromData5 = [[NSImage alloc] initWithData:data5]; 
NSBitmapImageRep * bitmapRepFromData5 = [[imageFromData5 representations] objectAtIndex:0]; 

NSData * dataFromImageFromData5 = [bitmapRepFromData5 representationUsingType:NSJPEGFileType properties:nil]; 
NSLog(@"dataFromImageFromData5 length: %d\n", [dataFromImageFromData5 length]); 

dict = [NSDictionary dictionaryWithObject: [NSNumber numberWithFloat:0.5] forKey:NSImageCompressionFactor]; 
NSData * dataFiveFromImageWithData5 = [bitmapRepFromData5 representationUsingType:NSJPEGFileType properties:dict]; 
NSLog(@"dataFiveFromImageWithData5 length: %d\n", [dataFiveFromImageWithData5 length]); 
NSLog(@"== End ==\n\n"); 

Ceci est mon résultat

 
> == Initializing == 
> imageData length: 1882694 
> data length: 1888365 
> data5 length: 1102461 
> == End == 

> == Image from Data5 == 
> dataFromImageFromData5 length: 1646137 
> dataFiveFromImageWithData5 length: 1102115 
> == End == 


Try a different image 
> == Initializing == 
> imageData length: 3620257 
> data length: 2889458 
> data5 length: 1404750 
> == End == 

> == Image from Data5 == 
> dataFromImageFromData5 length: 2007951 
> dataFiveFromImageWithData5 length: 1405398 
> == End == 

Répondre

4

Vous devez diminuer le facteur chaque fois. Recompresser une image JPEG qui n'a pas été éditée, en utilisant le même niveau de qualité ne change pas vraiment le résultat du tout, ce qui devrait expliquer pourquoi vous ne voyez aucune diminution de taille.

(Si vous voulez vous assurer que la qualité ne pourrait se dégrade pas plus que nécessaire, donner un sens à recompresser l'image d'origine encore et avec un facteur diminuant au lieu de les enchaîner comme dans votre exemple.)