我已成功将动画GIF加载到NSData
或NSBitmapImageRep
对象中。 Reference for NSBitmapImageRep
我已经想过如何使用以下命令返回数据,例如gif中的帧数:
NSNumber *frames = [bitmapRep valueForProperty:@"NSImageFrameCount"];
但是,我对如何实际访问该帧作为自己的对象感到有点困惑。
我认为这两种方法中的一种会有所帮助,但我不确定他们会如何为我提供个性化的框架。
+ representationOfImageRepsInArray:usingType:properties:
– representationUsingType:properties:
任何帮助表示赞赏。感谢
答案 0 :(得分:6)
我已经想过如何使用以下命令返回数据,例如gif中的帧数:
NSNumber *frames = [bitmapRep valueForProperty:@"NSImageFrameCount"];
但是,我对如何实际访问该帧作为自己的对象感到有点困惑。
要访问特殊框架indexOfFrame
(0 <= indexOfFrame < [frames intValue]
),您只需设置NSImageCurrentFrame
即可完成。无需使用CG功能或制作帧的副本。你可以留在面向对象的Cocoa世界。一个小例子显示了所有GIF帧的持续时间:
NSNumber *frames = [bitmapRep valueForProperty:@"NSImageFrameCount"];
if( frames!=nil ){ // bitmapRep is a Gif imageRep
for( NSUInteger i=0; i<[frames intValue]; i++ ){
[bitmapRep setProperty:NSImageCurrentFrame
withValue:[NSNumber numberWithUnsignedInt:i] ];
NSLog(@"%2d duration=%@",
i, [bitmapRep valueForProperty:NSImageCurrentFrameDuration] );
}
}
另一个例子:将GIF图像的所有帧作为PNG文件写入文件系统:
NSNumber *frames = [bitmapRep valueForProperty:@"NSImageFrameCount"];
if( frames!=nil ){ // bitmapRep is a Gif imageRep
for( NSUInteger i=0; i<[frames intValue]; i++ ){
[bitmapRep setProperty:NSImageCurrentFrame
withValue:[NSNumber numberWithUnsignedInt:i] ];
NSData *repData = [bitmapRep representationUsingType:NSPNGFileType
properties:nil];
[repData writeToFile:
[NSString stringWithFormat:@"/tmp/gif_%02d.png", i ] atomically:YES];
}
}
答案 1 :(得分:2)
我已经想过如何使用以下命令返回数据,例如gif中的帧数:
NSNumber *frames = [bitmapRep valueForProperty:@"NSImageFrameCount"];
但是,我对如何实际访问该帧作为自己的对象感到有点困惑。
据我所知,你不能来自NSBitmapImageRep。
相反,从GIF数据创建CGImageSource,并使用CGImageSourceCreateImageAtIndex
提取每个帧(最好是根据需要)。
或者,您可以尝试setting NSImageCurrentFrame
属性。如果您需要每个帧的代表,请创建与有帧一样多的副本(减去一个,因为您有原始帧),并将每个代表的当前帧设置为不同的数字。但我没有尝试过,所以我不确定它是否真的有用。
基本上,NSBitmapImageRep的GIF支持很奇怪,所以你应该只使用CGImageSource。
我认为这两种方法中的一种会有所帮助,但我不确定他们会如何为我提供个性化的框架。
+ representationOfImageRepsInArray:usingType:properties: – representationUsingType:properties:
不,这些方法用于序列化图像(或图像代表)。它们用于写入数据,而不是读取数据。(注意这些方法在type
参数中期望的常量。)
答案 2 :(得分:1)
如果你想查看iOS的GIF解码器的一些工作源代码(也适用于MacOSX),那么你可以找到它AVGIF89A2MvidResourceLoader.m at github。方法是使用ImageIO框架并调用CGImageSourceCreateWithData()以及CGImageSourceCreateImageAtIndex()来访问文件中的第N个gif图像。但是,有一些棘手的细节涉及检测GIF中是否出现透明像素以及如何将结果写入文件以避免在GIF非常长而可能不明显的情况下耗尽内存。