2

我需要在图像通过 GPUImage 管道时对其进行缩放。我正在将图像输出到另一个文件。

这是我的简单管道:

UIImage *inputImage = [UIImage imageNamed:@"8x8.png"]; // The WID.jpg example is greater than 2048 pixels tall, so it fails on older devices

sourcePicture = [[GPUImagePicture alloc] initWithImage:inputImage];

transformFilter = [[GPUImageTransformFilter alloc] init];
transformFilter.affineTransform = CGAffineTransformMakeScale(2.0, 2.0);

[sourcePicture addTarget:transformFilter];
[transformFilter prepareForImageCapture];

[sourcePicture processImage];

UIImage *currentFilteredImage = [transformFilter imageFromCurrentlyProcessedOutput];

NSData *dataForPNGFile = UIImagePNGRepresentation(currentFilteredImage);

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];

NSError *error = nil;
if (![dataForPNGFile writeToFile:[documentsDirectory stringByAppendingPathComponent:@"filtered1.png"] options:NSAtomicWrite error:&error])
{
    return;
}

输入图像是 8x8 像素,我想输出 16x16 像素的图像。

上述管道目前存在两个问题:

1)输出的图片尺寸还是8x8像素,虽然原图已经缩放了2.0,但是已经被裁剪回原来的尺寸了。

2) 输出图像模糊,这与我在 iPhone photo App 中查看非常小的图像时得到的效果相同。我认为它很可能是默认情况下在管道中某处应用的平滑函数。

我只想缩放输入图像而不进行任何平滑处理,以使像素保持清晰。

编辑:通过替换

transformFilter.affineTransform = CGAffineTransformMakeScale(2.0, 2.0);

[transformFilter forceProcessingAtSize:CGSizeMake(16.0, 16.0)];

我现在有一个 16x16 像素的缩放图像,但图像仍然模糊。

编辑2:

如果我将 8x8 图像缩放为 320x320,则结果与在 iPhone 照片应用程序中查看相同的 8x8 像素图像相同。它完全模糊,像素在像素边界处出现明亮的亮点。这表明问题不在于核心 GPUImage 代码,而在于 GPUImage 依赖于核心图像的功能。

有没有办法只使用 GPUImage 代码来扩展并完全避免核心图像?

编辑 3:我在 GPUImage github 项目上发布了失真问题,您可以在此处阅读完整的问题和回复

结果是我需要将 minFilter 和 magFilter 纹理参数设置为 GL_NEAREST 而不是 GL_LINEAR;

我的最终解决方案是克隆 GPUImagePicture 类并在 initWithCGImage: 选择器更改:

if (self.shouldSmoothlyScaleOutput)
        {
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
        }

至:

if (self.shouldSmoothlyScaleOutput)
        {
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
        }
        else
        {
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
        }
4

0 回答 0