ios - 使用 Core Image 自定义滤镜在两个图像之间实现颜色传输

标签 ios core-image

我一直在尝试弄清楚如何执行从源图像到另一图像的颜色转移。

我想创建的过滤器需要 2 张完全相同大小的图像(ImageAImageB)。滤镜生成的输出图像将颜色的所有像素从 imageA 更改为 imageB 相同像素位置的颜色。

检查图像。我需要使用 ImageA 作为源并将 ImageB 作为一种颜色 mask ,将蓝色像素更改为绿色和紫色像素。正如您所看到的,只有与绿色和紫色区域重叠的蓝色区域发生了变化(将灰色视为透明...)

enter image description here

我的问题是: 1)这是可行的吗? 2)我应该使用通用内核吗?根据我的理解,颜色内核也应该可以工作,但我不确定我是否可以将 2 个图像传递给颜色内核。

您能否提供内核代码示例?

在每个像素上执行的非常简单的非优化伪代码可能是这样的:

color func (source imageA, source imageB, color colorToChange) {

    if imageA.currentpixel.color == colorToChange{
      if imageB.getPixel(imageA.currentPixel).color not transparent{
        return imageB.getPixel(imageA.currentPixel).color
      }
    }
    return imageA.currentPixel.color
}

这是我正在使用的当前过滤器(虽然我得到了奇怪的结果)

kernel vec4 coreImageKernel(sampler image, sampler msk, __color color)
{
    vec4 a = sample(image, samplerCoord(image));

    if (length(a - color) == 0.0){
        return sample(msk, samplerCoord(msk));
    }else{
        return a;
    }   
}

最佳答案

使用 CIKernel 是可能的,但我不相信使用简单的 CIColorKernel,因为您需要使用两个 CIImages

它仍然是非常简单的代码。您需要三个输入,在您的示例中,“IMAGE A”、“IMAGE B”和要忽略的图像 B 像素颜色。由于 CoreImage 是逐像素工作的,因此您只需要处理两个图像中的当前像素即可。

基本代码是这样的:

kernel vec4 createResult(sampler imageA, sampler imageB, vec4 backgroundColor) {
    vec4 pixelA = sample(imageA, samplerCoord(imageA));
    vec4 pixelB = sample(imageB, samplerCoord(imageB));
    if (pixelA == backgroundColor) {
        return pixelA;
    } else if (pixelB == backgroundColor) {
        return pixelA;
    } else {
        return pixelB;
    }
}

这是未经测试的内核代码,因此可能存在语法错误。但这是逻辑:

  • 从两个图像中传入一个像素以及背景颜色
  • 如果 pixelA 是背景色,则它不是“点”,所以不要更改它
  • 如果 pixelB 是背景色,则它不是一行您满意的点,所以不要更改它
  • 如果pixelB不是背景色,输出它

请注意,只有当两个像素都不是背景色时,才能到达项目符号 #4。

最后一点 - Apple 决定弃用 OpenGL。在 WWDC '18 之后,我花了一周时间将我的内核代码更改为 Metal 2 代码,但(还)没有成功。颜色内核?简单的。但是同时具有扭曲和一般内核的东西......与获取周围像素相关的东西仍然让我望而却步。我认为这与我编写 samplerTransform 的方式有关,但没有时间研究它。

应该将其用作“基于金属的”内核,因为我确实复制了一个简单的传递作为 CIKernel。请注意!

关于ios - 使用 Core Image 自定义滤镜在两个图像之间实现颜色传输,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51594333/

相关文章:

iOS Swift : Closures (Callbacks) versus Delegates, 什么时候使用哪个?

ios - 未安装分发证书/私钥

objective-c - 旋转和调整 CIImage 的大小

ios - 如何在 iOS 应用程序中用马赛克填充画线?

ios - Swift 2 中的 MPNowPlayingInfoCenter nowPlayingInfo 错误

ios - SearchBar 的 UITextField 填充?

ios - 如何为缩略图快速加载图像的低分辨率版本?或者简单地说,如何最好地创建缩略图?

cocoa - 从 IKImageBrowserView 获取 CGImageRef

ios - 使用 CoreImage 获取颜色计数/主要(不是平均)?

ios - CISpotLight 过滤器和零结果