본문 바로가기
ios 뽀개기/objective-c

ios 카메라를 만드는 두가지 방법 2

by 인생여희 2018. 12. 3.
반응형



첫번째 방법














//

//  ViewController.h

//  CarmeraExam1

//


//


#import <UIKit/UIKit.h>

#import <AVFoundation/AVFoundation.h>

@interface ViewController : UIViewController


//프레임을 강제로 연속 캡쳐

@property (weak, nonatomic) IBOutlet UIView *frameforcapture;


//순간적으로 찍은 이미지 보이게

@property (weak, nonatomic) IBOutlet UIImageView *imageV;


- (IBAction)takePhoto:(id)sender;


@end




//

//  ViewController.m

//  CarmeraExam1

//



//


#import "ViewController.h"


@interface ViewController ()

@end


@implementation ViewController


//카메라 작동 시작을 선언!

AVCaptureSession *session;

//카메라 출력 담당

AVCaptureStillImageOutput *StilImageOutput;

//AVCapturePhotoOutput



- (void)viewDidLoad {

    [super viewDidLoad];

    // Do any additional setup after loading the view, typically from a nib.

}



- (void)didReceiveMemoryWarning {

    [super didReceiveMemoryWarning];

    // Dispose of any resources that can be recreated.

}



//뷰가 나타낼때

-(void)viewWillAppear:(BOOL)animated{

    

    //카메라를 작동시킬 세션 초기화

    session = [[AVCaptureSession alloc]init];

    [session setSessionPreset:AVCaptureSessionPresetPhoto];

    

    //디바이스 설정

    AVCaptureDevice *inputDevice = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];

    NSError *error;

    //입력을 담당

    AVCaptureDeviceInput *deviceInput = [AVCaptureDeviceInput deviceInputWithDevice:inputDevice error:&error];

    

    //카메라 세션에 입력을 담당하는 AVCaptureDeviceInput 넣어줌

    if ([session canAddInput:deviceInput]) {

        [session addInput:deviceInput];

    }

    

    //영상이 나올 화면을 위에서 만든 session 으로 초기화

    AVCaptureVideoPreviewLayer *previewLayer = [[AVCaptureVideoPreviewLayer alloc]initWithSession:session];

   

    //PreviewLayer의 사이즈를 조정하는 역할을 한다.

    [previewLayer setVideoGravity:AVLayerVideoGravityResizeAspectFill];

    

    

    //루트 레이어 설정

    CALayer *rootLayer = [[self view] layer];

    [rootLayer setMasksToBounds:YES];

    

    //현재 연속으로 캡쳐할 프레임 객체 생성

    CGRect frame = _frameforcapture.frame;

    

    //미리보기 레이어에 연속으로 캡쳐할 프레임 객체 넣어주고

    [previewLayer setFrame:frame];

    

    //루트레이어에 미리보기 레이어 넣어줌

    [rootLayer insertSublayer:previewLayer above:0];   //rootLayer -> previewLayer -> frame

    

    //이미지를 출력할 객체 생성 초기화

    StilImageOutput = [[AVCaptureStillImageOutput alloc]init];

    NSDictionary *outputSettings = [[NSDictionary alloc] initWithObjectsAndKeys:AVVideoCodecTypeJPEG,AVVideoCodecKey, nil];

    [StilImageOutput setOutputSettings:outputSettings];

    

    [session addOutput:StilImageOutput];

    

    //세션 시작

    [session startRunning];

    

}



- (IBAction)takePhoto:(id)sender {

    AVCaptureConnection *videoConnection = nil;

    for (AVCaptureConnection *connection in StilImageOutput.connections) {

        for (AVCaptureInputPort *port in [connection inputPorts]) {

            if ([[port mediaType] isEqual:AVMediaTypeVideo]) {

                videoConnection = connection;

                break;

            }

        }

    }

   

    

    [StilImageOutput captureStillImageAsynchronouslyFromConnection:videoConnection completionHandler:^(CMSampleBufferRef  _Nullable imageDataSampleBuffer, NSError * _Nullable error) {

        

        if (imageDataSampleBuffer != NULL) {

            //이미지 데이터 버퍼가 존재한다면

            NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageDataSampleBuffer];

            

            UIImage *image = [UIImage imageWithData:imageData];

            self->_imageV.image = image;

        

            /*jpegStillImageNSDataRepresentation

             AVCaptureStillImageOutput의 메소드 하나로 위 메서드에서 생성한 버퍼를 이미지 데이터로 변환한다.

             이 이미지는 uiimage 로 만들 수 있고, cgimage로 전환했다가 다시 uIimage로 변환 가능*/

        }

        

    }];


}

@end


두번째 방법




//

//  ViewController.h


//


#import <UIKit/UIKit.h>


//카메라를 구현하기 위한 델리게이트 상속

@interface ViewController : UIViewController <UIImagePickerControllerDelegate, UINavigationControllerDelegate>


@property (strong, nonatomic) IBOutlet UIImageView *imageHolder;



- (IBAction)cameraButtonClicked:(id)sender;


- (IBAction)localButtonClicked:(id)sender;


- (IBAction)saveButtonClicked:(id)sender;

@end



//

//  ViewController.m

//  CarmeraExam2


//


#import "ViewController.h"


@interface ViewController ()


@end


@implementation ViewController


@synthesize imageHolder;


- (void)viewDidLoad {

    [super viewDidLoad];

    // Do any additional setup after loading the view, typically from a nib.

    NSLog(@"viewDidLoad 호출");

}


- (void)didReceiveMemoryWarning {

    [super didReceiveMemoryWarning];

    

}



- (IBAction)cameraButtonClicked:(id)sender {

    NSLog(@"cameraButtonClicked 호출");

    //이미지 피커 컨트롤러 호출

    UIImagePickerController *pickerCtrl = [[UIImagePickerController alloc]init];

    [pickerCtrl setDelegate:self];

    //편집허용

    [pickerCtrl setAllowsEditing:YES];

    [pickerCtrl setSourceType:UIImagePickerControllerSourceTypeCamera];

    [self presentViewController:pickerCtrl animated:YES completion:nil];

}


//사진 라이브러리 호출

- (IBAction)localButtonClicked:(id)sender {

     NSLog(@"localButtonClicked 호출");

    //이미지 피커 컨트롤러 호출

    UIImagePickerController *pickerCtrl = [[UIImagePickerController alloc]init];

    [pickerCtrl setDelegate:self];

    //편집 허용

    [pickerCtrl setAllowsEditing:YES];

    [pickerCtrl setSourceType:UIImagePickerControllerSourceTypePhotoLibrary];

    [self presentViewController:pickerCtrl animated:YES completion:nil];

}


//저장

- (IBAction)saveButtonClicked:(id)sender {

    

    

    UIAlertController *alert= [UIAlertController alertControllerWithTitle:@"Yes or No?"

                                                                    message:@"사진첩에 저장하시겠습니까?"

                                                             preferredStyle:UIAlertControllerStyleAlert];


    UIAlertAction* ok = [UIAlertAction actionWithTitle:@"네"

                                                 style:UIAlertActionStyleDefault

                                              handler:^(UIAlertAction * action)

                                              {

                                                        UIImage *pickedImage = self->imageHolder.image;

                                                         UIImageWriteToSavedPhotosAlbum(pickedImage, nil, nil, nil);

                                                         NSLog(@"사진첩에 저장되었습니다.");

                                                        [self->imageHolder setImage:[UIImage imageNamed:@"empty.png"]];

                                                  }];

    

    

    UIAlertAction* cancel = [UIAlertAction actionWithTitle:@"아니요."

                                                     style:UIAlertActionStyleDefault

                              handler:^(UIAlertAction * action)

                                                      {

                                                          }];

     

    [alert addAction:ok];

    [alert addAction:cancel];

     

    [self presentViewController:alert animated:YES completion:nil];



}


#pragma mark UIImagePickerViewControllerDelegate

//이미지 피커뷰 컨트롤러 델리게이트 메소드


//카메라로 사진찍고 선택누르기

-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary<NSString *,id> *)info{

    //successfully picked   / handed over

    NSLog(@"imagePickerController 호출");

    UIImage *pickedImage = info[UIImagePickerControllerEditedImage];

    [imageHolder setImage:pickedImage];

    

     //저장할 경로 얻기

     NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);

     NSString *documentsDirectory = [paths objectAtIndex:0];

     NSString *imagePath = [documentsDirectory stringByAppendingPathComponent:@"latest_photo.png"];

    

    

    NSLog(@"paths  %@" , paths);

    // /var/mobile/Containers/Data/Application/0BDB0C7B-5FC7-4F47-A46F-4EF2FB521EE5/Documents

    NSLog(@"documentsDirectory %@" , documentsDirectory);

    //    var/mobile/Containers/Data/Application/0BDB0C7B-5FC7-4F47-A46F-4EF2FB521EE5/Documents

    NSLog(@"imagePath %@"  , imagePath);

    //  var/mobile/Containers/Data/Application/0BDB0C7B-5FC7-4F47-A46F-4EF2FB521EE5/Documents/latest_photo.png

    

     //피커에서 이미지 선택 및 저장

     NSString *mediaType = [info objectForKey:UIImagePickerControllerMediaType];

     NSLog(@"mediaType %@"  , mediaType); //public.image

    

    //파일에 저장하기

     if ([mediaType isEqualToString:@"public.image"]){

//          UIImage *pickedImage2 = info[UIImagePickerControllerEditedImage];

//         NSData *webData = UIImagePNGRepresentation(pickedImage2);

//         [webData writeToFile:imagePath atomically:YES];

         

         NSLog(@"저장되었습니다.");

          [self dismissViewControllerAnimated:YES completion:nil];

     }else{

         NSLog(@"저장실패");

     }

}



//취소

-(void) imagePickerControllerDidCancel:(UIImagePickerController *)picker{

    

    // handle cancel

    NSLog(@"imagePickerControllerDidCancel 호출");

    [self dismissViewControllerAnimated:YES completion:nil];

}


@end



//path is /private/var/containers/Shared/SystemGroup/

//파일디렉토리에 저장하기

//https://stackoverflow.com/questions/4957972/iphone-uiimagepickercontroller-save-the-image-to-app-folder


예제 파일 다운로드

무제 폴더.zip



반응형

댓글