gpt4 book ai didi

objective-c - NSImage 到 NSBitmapImageRep

转载 作者:太空狗 更新时间:2023-10-30 03:20:10 28 4
gpt4 key购买 nike

如何将 NSImage 转换为 NSBitmapImageRep?我有代码:

- (NSBitmapImageRep *)bitmapImageRepresentation
{
NSBitmapImageRep *ret = (NSBitmapImageRep *)[self representations];

if(![ret isKindOfClass:[NSBitmapImageRep class]])
{
ret = nil;
for(NSBitmapImageRep *rep in [self representations])
if([rep isKindOfClass:[NSBitmapImageRep class]])
{
ret = rep;
break;
}
}

if(ret == nil)
{
NSSize size = [self size];

size_t width = size.width;
size_t height = size.height;
size_t bitsPerComp = 32;
size_t bytesPerPixel = (bitsPerComp / CHAR_BIT) * 4;
size_t bytesPerRow = bytesPerPixel * width;
size_t totalBytes = height * bytesPerRow;

NSMutableData *data = [NSMutableData dataWithBytesNoCopy:calloc(totalBytes, 1) length:totalBytes freeWhenDone:YES];

CGColorSpaceRef space = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB);

CGContextRef ctx = CGBitmapContextCreate([data mutableBytes], width, height, bitsPerComp, bytesPerRow, CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB), kCGBitmapFloatComponents | kCGImageAlphaPremultipliedLast);

if(ctx != NULL)
{
[NSGraphicsContext saveGraphicsState];
[NSGraphicsContext setCurrentContext:[NSGraphicsContext graphicsContextWithGraphicsPort:ctx flipped:[self isFlipped]]];

[self drawAtPoint:NSZeroPoint fromRect:NSZeroRect operation:NSCompositeCopy fraction:1.0];

[NSGraphicsContext restoreGraphicsState];

CGImageRef img = CGBitmapContextCreateImage(ctx);

ret = [[NSBitmapImageRep alloc] initWithCGImage:img];
[self addRepresentation:ret];

CFRelease(img);
CFRelease(space);

CGContextRelease(ctx);
}
}


return ret;
}

它可以工作,但会导致内存泄漏。至少当我将它与 ARC 一起使用时。使用 initWithData:[nsimagename TIFFRepresentation] 它无法正常工作。一些图像的表现不好。我认为这取决于图像的格式和色彩空间。还有其他方法可以实现吗?


mrwalker 建议解决方案的结果:

原图:
enter image description here

转换为 bitmapimagerep 并返回图像 1 次:
enter image description here

转换为 bitmapimagerep 并返回图像 3 次:
enter image description here

如你所见,每次转换为 NSBitmapImageRep 后图像都会变暗

最佳答案

@Julius:您的代码太复杂了,并且包含多个错误。我将只对第一行进行更正:

- (NSBitmapImageRep *)bitmapImageRepresentation
{
for( NSImageRep *rep in [self representations] )
if( [rep isKindOfClass:[NSBitmapImageRep class]] ) return rep;
return nil;
}

这将提取第一个 NSBitmapImageRep,如果它是表示中的成员,或者将返回 nil,如果没有 NSBitmapImageRep。我会给你另一种解决方案,无论 NSImageReps 在表示中如何,它总是有效:NSBitmapImageRepNSPDFImageRepNSCGImageSnapshotRep 或 ...

- (NSBitmapImageRep *)bitmapImageRepresentation
{
CGImageRef CGImage = [self CGImageForProposedRect:nil context:nil hints:nil];
return [[[NSBitmapImageRep alloc] initWithCGImage:CGImage] autorelease];
}

或者为了避免 NSImage 的子类化,你可以这样写:

NSImage *img = [[[NSImage alloc] initWithContentsOfFile:filename] autorelease];
CGImageRef CGImage = [img CGImageForProposedRect:nil context:nil hints:nil];
NSBitmapImageRep *rep = [[[NSBitmapImageRep alloc] initWithCGImage:CGImage] autorelease];

这只会返回一个 NSBitmapImageRep,如果图像包含多个表示(例如,来自 TIFF 文件的大量 NSBitmapImageRep),这可能不够好。但是添加一些代码很简单。

关于objective-c - NSImage 到 NSBitmapImageRep,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12896831/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com