使用GPUImage做美颜非常方便,内置已经提供了一个GPUImagePicture作为图片输入Filter。
GPUImagePicture的实现方法是读取图片数据,将其写入到GPUImageFramebuffer,是一种非常高效的方案。我的方案是将image转为CMSampleBufferRef,这样就能复用视频的处理代码。转换代码如下
- (CVPixelBufferRef)pixelBufferFromUIImage:(UIImage *)image {
CGSize frameSize = CGSizeMake(CGImageGetWidth(image.CGImage),CGImageGetHeight(image.CGImage));
NSDictionary *options =
[NSDictionary dictionaryWithObjectsAndKeys:[NSNumber numberWithBool:YES],kCVPixelBufferCGImageCompatibilityKey,
[NSNumber numberWithBool:YES],kCVPixelBufferCGBitmapContextCompatibilityKey,
[NSDictionary dictionary], (id)kCVPixelBufferIOSurfacePropertiesKey, nil];
CVPixelBufferRef pxbuffer = NULL;
int cropWidth = (int)CGImageGetWidth(image.CGImage) & ~15;
int cropHeight = (int)CGImageGetHeight(image.CGImage) & ~1;
CVReturn status =
CVPixelBufferCreate(kCFAllocatorDefault, cropWidth, cropHeight, kCVPixelFormatType_32BGRA, (__bridge CFDictionaryRef)options, &pxbuffer);
NSParameterAssert(status == kCVReturnSuccess && pxbuffer != NULL);
CVPixelBufferLockBaseAddress(pxbuffer, 0);
void *pxdata = CVPixelBufferGetBaseAddress(pxbuffer);
CGColorSpaceRef rgbColorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef context = CGBitmapContextCreate(pxdata, cropWidth, cropHeight,8, CVPixelBufferGetBytesPerRow(pxbuffer),rgbColorSpace,(CGBitmapInfo)kCGBitmapByteOrder32Little | kCGImageAlphaPremultipliedFirst);
CGContextDrawImage(context, CGRectMake(0, 0, cropWidth, cropHeight), image.CGImage);
CGColorSpaceRelease(rgbColorSpace);
CGContextRelease(context);
CVPixelBufferUnlockBaseAddress(pxbuffer, 0);
return pxbuffer;
}
有个坑的地方是,在后面处理的时候会遇到CVOpenGLESTextureCacheCreateTextureFromImage
返回-6638错误,看了官方文档才找到解决方案 https://developer.apple.com/library/archive/qa/qa1781/_index.html
上效果图
![](https://img.qingshiwang.com/i1170744/ba2d08dc43eae6e3.gif)
fu.gif
本站以现代、古代情诗为主,情诗网创办于2013年,以原创爱情诗歌、经典情诗、现代情诗、古代情诗、英文情诗、情诗绝句为主并收集古诗、古诗词、诗歌大全、诗词名句的文学门户。方便您下次继续阅读;可以放在浏览器的收藏夹中(快捷键Ctrl+D);或者看到喜欢或者有趣的诗词可以通过分享按钮给你的好友分享;情诗网是目前最全情诗大全网站之一。并欢迎广大诗歌爱好者阅览投稿!喜欢本站的话请大家把本站告诉给你朋友哦!地址是 www.qingshiwang.com !