Преобразование координат CIImage в CGRect из CIFaceFeature
Я пытаюсь поместить квадратный прямоугольник поверх лица пользователя, которое я распознаю, используя CIFaceFeature
в режиме реального времени на весь экран (self.view.frame
) видео канал. Тем не менее, координаты, которые я получаю от CIFaceFeature.bounds
из другой системы координат, чем используемая представлениями. Я попытался преобразовать эти координаты из этого и других примеров. Но так как у меня нет, я запускаю это поверх видео канала, у меня нет изображения, которое я могу передать CIImage
облегчить с преобразованием координат. Ниже приведен пример моей конфигурации, любая идея, как я могу преобразовать в пригодный для использования CGRect
?
func captureOutput(_ output: AVCaptureOutput, didOutput sampleBuffer: CMSampleBuffer, from connection: AVCaptureConnection) {
let imageBuffer = CMSampleBufferGetImageBuffer(sampleBuffer)
let opaqueBuffer = Unmanaged<CVImageBuffer>.passUnretained(imageBuffer!).toOpaque()
let pixelBuffer = Unmanaged<CVPixelBuffer>.fromOpaque(opaqueBuffer).takeUnretainedValue()
let sourceImage = CIImage(cvPixelBuffer: pixelBuffer)
let features = self.faceDetector!.features(in: sourceImage, options: options)
if (features.count != 0) {
let faceImage = sourceImage
let faceDetector = CIDetector(ofType: CIDetectorTypeFace, context: nil, options: [CIDetectorAccuracy: CIDetectorAccuracyHigh])
let faces = faceDetector?.features(in: faceImage) as! [CIFaceFeature]
let transformScale = CGAffineTransform(scaleX: 1, y: -1)
let transform = transformScale.translatedBy(x: 0, y: -faceImage.extent.height)
for feature in features as! [CIFaceFeature] {
faceBounds = feature.bounds
var fb = faceBounds?.applying(transform)
// imageViewSize is the screen frame
let scale = min(imageViewSize.width / fb!.width,
imageViewSize.height / fb!.height)
let dx = (imageViewSize.width - fb!.width * scale) / 2
let dy = (imageViewSize.height - fb!.height * scale) / 2
fb?.applying(CGAffineTransform(scaleX: scale, y: scale))
fb?.origin.x += dx
fb?.origin.y += dy
realFaceRect = fb // COMPLETELY WRONG :'(
}
}
1 ответ
Если кто-то сталкивается с той же проблемой. Вот простое решение
let imgHeight = CGFloat(CVPixelBufferGetHeight(pixelBuffer))
let ratio = self.view.frame.width / self.visage!.imgHeight
func convertFrame(frame: CGRect, ratio: CGFloat) -> CGRect {
let x = frame.origin.y * ratio
let y = frame.origin.x * ratio
let width = frame.height * ratio
let height = frame.width * ratio
return CGRect(x: x, y: y, width: width, height: height)
}
func convertPoint(point: CGPoint, ratio: CGFloat) -> CGPoint {
let x = point.y * ratio
let y = point.x * ratio
return CGPoint(x: x, y: y)
}