ios - CGImageCreateWithImageInRect subimages are zoomed and misplaced -
i want experiment real-time filtering of subregions of iphone camera feed. idea display filtered regions overlaid on screen can see filtering results in real-time move camera.
it seems should straightforward extract frame subimages via cgimagecreatewithimageinrect , put them in uiimageviews. resulting images zoomed , misplaced, , i'm lost why.
here's app running. note subimages zoomed , not aligned guide boxes
i've looked through many, many posts , blogs, , closest i've found problem in post:
cannot crop touched location cgimagecreatewithimageinrect in swift
but solution relies on features of uiimageview source, uiview , avcapturevideopreviewlayer i'm using don't have. , it's not clear me why fix works in case.
my code obtains preview frames pixel buffers via avcapturevideodataoutputsamplebufferdelegate : captureoutput : didoutputsamplebuffer , converts them cgimages input cgimagecreatewithimageinrect. rect parameters use guide boxes' uiview.frame members.
here's source:
import uikit import avfoundation class viewcontroller: uiviewcontroller, avcapturevideodataoutputsamplebufferdelegate { @iboutlet weak var previewview: uiview! @iboutlet weak var datetimecapture: uiimageview! @iboutlet weak var machineidamttime: uiimageview! @iboutlet weak var ticketid: uiimageview! @iboutlet weak var datetimecapturebox: uiview! @iboutlet weak var machineidamttimecapturebox: uiview! @iboutlet weak var ticketidcapturebox: uiview! var convertctx: cicontext? var capturesession: avcapturesession? var stillimageoutput: avcapturestillimageoutput? var previewlayer: avcapturevideopreviewlayer? var overlaylayer: calayer? override func viewdidload() { super.viewdidload() convertctx = cicontext(options: nil) // guide boxes set black in ib can see them // clear them here datetimecapturebox.backgroundcolor = uicolor.clearcolor() machineidamttimecapturebox.backgroundcolor = uicolor.clearcolor() ticketidcapturebox.backgroundcolor = uicolor.clearcolor() // set color bright green , border useful width datetimecapturebox.layer.bordercolor = uicolor.greencolor().cgcolor datetimecapturebox.layer.borderwidth = 5 machineidamttimecapturebox.layer.bordercolor = uicolor.greencolor().cgcolor machineidamttimecapturebox.layer.borderwidth = 5 ticketidcapturebox.layer.bordercolor = uicolor.greencolor().cgcolor ticketidcapturebox.layer.borderwidth = 5 } override func viewwillappear(animated: bool) { super.viewwillappear(animated) capturesession = avcapturesession() capturesession!.sessionpreset = avcapturesessionpresetphoto let backcamera = avcapturedevice.defaultdevicewithmediatype(avmediatypevideo) var error: nserror? var input: avcapturedeviceinput! { input = try avcapturedeviceinput(device: backcamera) } catch let error1 nserror { error = error1 input = nil } if error == nil && capturesession!.canaddinput(input) { capturesession!.addinput(input) stillimageoutput = avcapturestillimageoutput() stillimageoutput!.outputsettings = [avvideocodeckey: avvideocodecjpeg] if capturesession!.canaddoutput(stillimageoutput) { capturesession!.addoutput(stillimageoutput) previewlayer = avcapturevideopreviewlayer(session: capturesession) previewlayer!.videogravity = avlayervideogravityresizeaspect previewlayer!.connection?.videoorientation = avcapturevideoorientation.portrait previewview!.layer.addsublayer(previewlayer!) capturesession!.startrunning() } } let videooutput = avcapturevideodataoutput() videooutput.setsamplebufferdelegate(self, queue: dispatch_get_main_queue()) if capturesession!.canaddoutput(videooutput) { capturesession!.addoutput(videooutput) videooutput.connectionwithmediatype(avmediatypevideo).videoorientation = avcapturevideoorientation.portrait videooutput.connectionwithmediatype(avmediatypevideo).videoscaleandcropfactor = 1.0 } } override func viewdidappear(animated: bool) { super.viewdidappear(animated) previewlayer!.frame = previewview.bounds } func captureoutput(captureoutput: avcaptureoutput!, didoutputsamplebuffer samplebuffer: cmsamplebuffer!, fromconnection connection: avcaptureconnection!) { // 1. image data cmsamplebuffer cvpixelbuffer let pixelbuffer = cmsamplebuffergetimagebuffer(samplebuffer) // 2. ciimage can cgimage // need in order extract rectangular subimage // via cgimagecreatewithimageinrect let cameraciimage = ciimage(cvpixelbuffer: pixelbuffer!) // 3. cgimage let cameracgimage = convertciimagetocgimage(cameraciimage) self.datetimecapture.image = uiimage(cgimage: cgimagecreatewithimageinrect(cameracgimage, datetimecapturebox.frame)!) self.machineidamttime.image = uiimage(cgimage: cgimagecreatewithimageinrect(cameracgimage, machineidamttimecapturebox.frame)!) self.ticketid.image = uiimage(cgimage: cgimagecreatewithimageinrect(cameracgimage, ticketidcapturebox.frame)!) } func convertciimagetocgimage(inputimage: ciimage) -> cgimage! { return convertctx!.createcgimage(inputimage, fromrect: inputimage.extent) } func captureoutput(captureoutput: avcaptureoutput!, diddropsamplebuffer samplebuffer: cmsamplebuffer!, fromconnection connection: avcaptureconnection!) { // print("drop") } }
Comments
Post a Comment