CILanczosScaleTransform 后出现奇怪的现象

发布于 2024-08-20 00:57:11 字数 3639 浏览 5 评论 0原文

我正在尝试使用 Core Image 和 Lanczos Scale Transform 过滤器进行图像缩放。 当我进行放大时,这很好。但在缩小并保存为 JPEG 时,我发现一类图像会产生奇怪的噪声伪影和行为。

对于 inputScale 倍数为 0.5:0.5、0.25、0.125 等,总是没问题的。 对于其他 inputScale 值,它已损坏。

当我保存为 TIFF、PNG、JPEG2000 或在屏幕上绘图时 - 没问题。 当我保存为 JPG 或 BMP 时 - 它损坏了。

我上传了示例图片: (原始,4272x2848,3.4Mb) [http://www.zoomfoot.com/get/ package/517e2423-7795-4239-a166-03d507ec51d8]

(按噪声缩放,1920x1280,2.2Mb) [http://www.zoomfoot.com/get/ package/6eb64d33-3a30-4e8d-9953-67ce1e7d7ef9]

它也可以很好地在“日落”图像上重现。

我尝试了更多缩放图像的方法。使用 CIAffineTransform 并使用 NSImage 本身进行绘图。两者都提供没有任何噪音的结果。

这是我用于缩放的代码节省:

================= 兰佐斯 ==============


- (NSImage *) scaleLanczosImage:(NSString *)path Width:(int) desiredWidth Height:(int) desiredHeight { CIImage *image=[CIImage imageWithContentsOfURL: [NSURL fileURLWithPath:path]];

CIFilter *scaleFilter = [CIFilter filterWithName:@"CILanczosScaleTransform"]; int originalHeight=[图像范围].size.height; int originalWidth=[图像范围].size.width;

浮点 yScale=(浮点)desiredHeight / (浮点)originalHeight; 浮点数 xScale=(浮点数)desiredWidth / (float)originalWidth; 浮点数=fminf(yScale, xScale);

[scaleFilter setValue:[NSNumber numberWithFloat:scale] forKey:@"inputScale"]; [scaleFilter setValue:[NSNumber numberWithFloat:1.0] forKey:@"inputAspectRatio"]; [scaleFilter setValue: 图像 forKey:@"inputImage"];

图像 = [scaleFilter valueForKey:@"outputImage"];

NSBitmapImageRep*rep = [[NSBitmapImageRep alloc] initWithCIImage:image]; NSMutableDictionary *options=[NSMutableDictionarydictionaryWithObject:[NSDecimalNumber numberWithFloat:1.0] forKey:NSImageCompressionFactor];

[选项 setValue:[NSNumber numberWithBool:YES] forKey:NSImageProgressive]; NSData* jpegData = [代表representationUsingType:NSJPEGFileType 属性:选项];

[jpegData writeToFile:@"/Users/dmitry/tmp/img_4389-800x600.jpg" 原子地:是]; }

================= NSImage ==============


- (void) scaleNSImage:(NSString *)path Width:(int) desiredWidth Height:(int) desiredHeight { NSImage *sourceImage = [[NSImage alloc] initWithContentsOfFile:path]; NSImage *resizedImage = [[NSImage alloc] initWithSize: NSMakeSize(desiredWidth, desiredHeight)];

NSSize 原始大小 = [源图像大小];

[调整大小的图像锁定焦点]; [源图像drawInRect: NSMakeRect(0, 0,desiredWidth,desiredHeight) fromRect: NSMakeRect(0, 0, 原始尺寸.宽度, 原始尺寸.高度) 操作:NSCompositeSourceOver 分数:1.0];

[调整大小的图像解锁焦点];

NSMutableDictionary *options=[NSMutableDictionarydictionaryWithObject:[NSDecimalNumber numberWithFloat:1.0] forKey:NSImageCompressionFactor];

[选项 setValue:[NSNumber numberWithBool:YES] forKey:NSImageProgressive];

NSBitmapImageRep *rep = [[NSBitmapImageRep 分配] initWithData:[resizedImage TIFFRepresentation]];

NSData* jpegData = [代表representationUsingType:NSJPEGFileType 属性:选项];

[jpegData writeToFile:@"~/nsimg_4389-800x600.jpg" 原子地:是];

}

如果有人可以在这里解释或提出一些建议,我真的很感激。

谢谢。

I'm trying to do image scaling using Core Image, using Lanczos Scale Transform filter.
It is fine when I'm doing scaleup. But on scaledown and saving to JPEG I found a class of images which produces strange noise artifacts and behavior.

For inputScale multiples to 0.5: 0.5, 0.25, 0.125 etc it is always fine.
For others inputScale values,it's broken.

When I'm saving to TIFF,PNG,JPEG2000 or draw on screen - it's fine.
When I'm saving to JPG or BMP - it's broken.

I uploaded sample images:
(original, 4272x2848, 3.4Mb)
[http://www.zoomfoot.com/get/package/517e2423-7795-4239-a166-03d507ec51d8]

(scaled with noise, 1920x1280, 2.2Mb)
[http://www.zoomfoot.com/get/package/6eb64d33-3a30-4e8d-9953-67ce1e7d7ef9]

It also, pretty good reproducible on 'sunset' images.

I've tried couple more ways to scale images. Using CIAffineTransform and drawing using NSImage itself. Both provides results without any noise.

Here is the code I was using for scaling & saving:

================= Lanczos ==============


- (NSImage *) scaleLanczosImage:(NSString *)path Width:(int) desiredWidth Height:(int) desiredHeight { CIImage *image=[CIImage imageWithContentsOfURL: [NSURL fileURLWithPath:path]];

CIFilter *scaleFilter = [CIFilter filterWithName:@"CILanczosScaleTransform"]; int originalHeight=[image extent].size.height; int originalWidth=[image extent].size.width;

float yScale=(float)desiredHeight / (float)originalHeight; float xScale=(float)desiredWidth / (float)originalWidth; float scale=fminf(yScale, xScale);

[scaleFilter setValue:[NSNumber numberWithFloat:scale] forKey:@"inputScale"]; [scaleFilter setValue:[NSNumber numberWithFloat:1.0] forKey:@"inputAspectRatio"]; [scaleFilter setValue: image forKey:@"inputImage"];

image = [scaleFilter valueForKey:@"outputImage"];

NSBitmapImageRep* rep = [[NSBitmapImageRep alloc] initWithCIImage:image]; NSMutableDictionary *options=[NSMutableDictionary dictionaryWithObject:[NSDecimalNumber numberWithFloat:1.0] forKey:NSImageCompressionFactor];

[options setValue:[NSNumber numberWithBool:YES] forKey:NSImageProgressive]; NSData* jpegData = [rep representationUsingType:NSJPEGFileType properties:options];

[jpegData writeToFile:@"/Users/dmitry/tmp/img_4389-800x600.jpg" atomically:YES]; }

================= NSImage ==============


- (void) scaleNSImage:(NSString *)path Width:(int) desiredWidth Height:(int) desiredHeight { NSImage *sourceImage = [[NSImage alloc] initWithContentsOfFile:path]; NSImage *resizedImage = [[NSImage alloc] initWithSize: NSMakeSize(desiredWidth, desiredHeight)];

NSSize originalSize = [sourceImage size];

[resizedImage lockFocus]; [sourceImage drawInRect: NSMakeRect(0, 0, desiredWidth, desiredHeight) fromRect: NSMakeRect(0, 0, originalSize.width, originalSize.height) operation: NSCompositeSourceOver fraction: 1.0];

[resizedImage unlockFocus];

NSMutableDictionary *options=[NSMutableDictionary dictionaryWithObject:[NSDecimalNumber numberWithFloat:1.0] forKey:NSImageCompressionFactor];

[options setValue:[NSNumber numberWithBool:YES] forKey:NSImageProgressive];

NSBitmapImageRep *rep = [[NSBitmapImageRep alloc] initWithData:[resizedImage TIFFRepresentation]];

NSData* jpegData = [rep representationUsingType:NSJPEGFileType properties:options];

[jpegData writeToFile:@"~/nsimg_4389-800x600.jpg" atomically:YES];

}

If anyone can explain or suggest something here, i'm really appreciate this.

Thanks.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

天冷不及心凉 2024-08-27 00:57:11

使用 CIImage 进行缩放有一些怪癖。 Dan Wood 的这篇文章会有帮助吗?

There are some quirks with scaling with CIImage. Will this post by Dan Wood help?

独闯女儿国 2024-08-27 00:57:11

我的理解是,由于其性质,硬件 Core Image 渲染器在渲染除屏幕显示之外的任何内容时都会出现一些奇怪的现象。因此,其他情况建议您使用软件渲染器。

http://developer.apple.com/mac/library/qa/ qa2005/qa1416.html

My understanding is that due to its nature, the hardware Core Image renderer has some odd quirks when rendering for anything but on-screen display. So, you are recommended to use the software renderer for other situations.

http://developer.apple.com/mac/library/qa/qa2005/qa1416.html

月亮是我掰弯的 2024-08-27 00:57:11

这绝对是 CoreImage 的错误。将其提交至 bugreport.apple.com

That's definitely a CoreImage bug. File it at bugreport.apple.com

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文