swift - CIImage 像素的 RGB 值
问题描述
CVPixelBuffer
我想ARFrame
实时访问特定区域的平均颜色值。我设法裁剪图像,使用过滤器计算平均颜色,并在转换为CGImage
从像素中获取值后,但不幸的是,它影响了我的应用程序的性能(FPS 降至 30fps 以下)。我认为原因是使用 CGContext。CIImage
有没有办法在不转换为的情况下访问颜色CGImage
?这是我目前正在使用的代码:
func fun() {
let croppVector = CIVector(cgRect: inputImageRect)
guard let filter = CIFilter(
name: "CIAreaAverage",
parameters: [kCIInputImageKey: image, kCIInputExtentKey: croppVector]
),
let outputImage = filter.outputImage,
let cgImage = context.createCGImage(
outputImage,
from: CGRect(x: 0, y: 0, width: 1, height: 1)
),
let dataProvider = cgImage.dataProvider,
let data = CFDataGetBytePtr(dataProvider.data) else { return nil }
let color = UIColor(
red: CGFloat(data[0]) / 255,
green: CGFloat(data[1]) / 255,
blue: CGFloat(data[2]) / 255,
alpha: CGFloat(data[3]) / 255
)
}
解决方案
我认为你可以在这里做的事情并不多——像这样的归约操作很昂贵。
您可以尝试几件事:
- 通过将和选项设置为
CIContext
来设置您不执行任何颜色管理。.workingColorSpace
.outputColorSpace
NSNull()
- 直接渲染到一块内存中,而不是通过
CGImage
. 上下文具有render(_ image: CIImage, toBitmap data: UnsafeMutableRawPointer, rowBytes: Int, bounds: CGRect, format: CIFormat, colorSpace: CGColorSpace?)
您可以使用的方法。nil
也在这里作为色彩空间传递。您应该能够simd_uchar4
像这里一样将“指针”传递给 vardata
。我认为是 4,在这种情况下rowBytes
格式是。.BGRA8
- 在进行平均计算之前,您还可以尝试缩小图像(这已经是缩小操作)。它不会是相同的值,而是一个公平的近似值——它可能会更快。
推荐阅读
- git - Git,克隆的裸仓库的路径不正确(缺少/)
- java - 线程“main”中的异常 java.lang.IllegalArgumentException:没有为 URI“http://xxx.xxx.xxx.xxx:xxxx”的方案“http”安装 NetworkModule
- kubernetes - Azure Kubernetes - Puppeteer 准备 PDF 错误:页面崩溃!在 Page._onTargetCrashed
- excel - 将 Access 表数据复制到 Excel 工作表
- angular - 从浏览器会话中复制 cookie
- rust - Rc::clone(&pointer) 如何增加引用计数?
- r - 如何使用 R 中的后缀组合变量对?
- python - 如何在 python 中将变量从一个 netcdf 文件添加到另一个 netcdf 文件?
- odoo - 继承 res.users 时出现混合苹果和橙子错误
- amazon-web-services - 自定义授权方 AWS CDK