
This video is only available to subscribers. Start a subscription today to get access to this and 470 other videos.
Rendering the Final Image
Episode
#301
|
15 minutes
| published on
September 8, 2017
| Uses Xcode-9.0-beta3, swift-4
Subscribers Only
In this episode we take the captured image and run the perspective correction filter on it in order to turn a skewed rect back into a flat rectangle. We then display the image on the screen for a few seconds as a preview mechanism.
This episode is part of a series: Camera Capture and Detection.
1. Intro 1 min |
2. Setting Up The Project 9 min |
3. Camera Preview and Sample Buffer 10 min |
4. Drawing on Top of the Video Preview 14 min |
5. Fixing the Coordinates 7 min |
6. Perspective Outlining 9 min |
7. Camera Sounds and UI 12 min |
8. Rendering the Final Image 15 min |
9. Capturing High Resolution Photos 17 min |
10. Adding a Flash Toggle Camera Control 12 min |
Episode Links
Perspective Correction
private func perspectiveCorrect(_ image: CIImage, rectFeature: CIRectangleFeature) -> CIImage? {
let perspectiveFilter = CIFilter(name: kCIPerspectiveCorrection)!
perspectiveFilter.setValue(image, forKey: kCIInputImageKey)
let corners = [
(rectFeature.topLeft, "inputTopLeft"),
(rectFeature.topRight, "inputTopRight"),
(rectFeature.bottomRight, "inputBottomRight"),
(rectFeature.bottomLeft, "inputBottomLeft"),
]
for (point, key) in corners {
let vector = CIVector(cgPoint: point)
perspectiveFilter.setValue(vector, forKey: key)
}
guard let correctedImage = perspectiveFilter.outputImage else { return nil }
return correctedImage
}
Displaying the image on screen
private func displayImage(ciImage: CIImage) {
guard let cgImage = ciContext.createCGImage(ciImage, from: ciImage.extent) else {
fatalError()
}
let image = UIImage(cgImage: cgImage, scale: UIScreen.main.scale, orientation: .up)
let imageView = UIImageView(image: image)
imageView.frame = view.bounds
imageView.backgroundColor = UIColor(white: 0, alpha: 0.8)
imageView.contentMode = .scaleAspectFit
imageView.alpha = 0
view.addSubview(imageView)
UIView.animate(withDuration: 0.3) {
imageView.alpha = 1
}
DispatchQueue.main.asyncAfter(deadline: .now() + 2) {
UIView.animate(withDuration: 0.3, animations: {
imageView.alpha = 0
}, completion: { completed in
imageView.removeFromSuperview()
self.detectRectangles = true
})
}
}
Fixing the rotation of the image
Running the application, we can see that if we capture the image, it is displayed in a rotated fashion. To fix this, we can chain another filter to our perspective correction method in order to rotate the image to the proper orientation.
let extent = correctedImage.extent
let transformFilter = CIFilter(name: kCIAffineTransform)!
/*----*
| |
*----*/
var transform = CGAffineTransform(translationX: extent.midX, y: -extent.midY)
transform = transform.rotated(by: -.pi/2)
transform = transform.translatedBy(x: -extent.midX, y: extent.midY)
transformFilter.setValue(correctedImage, forKey: kCIInputImageKey)
transformFilter.setValue(transform, forKey: kCIInputTransformKey)
return transformFilter.outputImage