【问题标题】:How to make UIImagePickerController for camera and photo library at the same time in swift如何在swift中同时为相机和照片库制作UIImagePickerController
【发布时间】:2017-06-02 16:41:34
【问题描述】:

我使用 UIImagePickerController 通过 iPhone 的相机拍照。

我想同时显示“拍照”和“选择照片”。

我的代码

imagePicker =  UIImagePickerController()
imagePicker.delegate = self
imagePicker.sourceType = .camera
//imagePicker.sourceType = .PhotoLibrary
presentViewController(imagePicker, animated: true, completion: nil)

我尝试同时使用imagePicker.sourceType = .CameraimagePicker.sourceType = .PhotoLibrary 来执行此操作,但它不起作用...

谢谢

【问题讨论】:

标签: ios swift uiimagepickercontroller


【解决方案1】:

导入UIImagePickerControllerDelegate并创建一个变量来分配UIImagePickerController var imagePicker = UIImagePickerController() 并设置imagePicker.delegate = self

创建一个操作表以显示“相机”和“照片库”的选项。

在您的按钮单击操作上:

@IBAction func buttonOnClick(_ sender: UIButton)
{
    self.btnEdit.setTitleColor(UIColor.white, for: .normal)
    self.btnEdit.isUserInteractionEnabled = true
    
    let alert = UIAlertController(title: "Choose Image", message: nil, preferredStyle: .actionSheet)
    alert.addAction(UIAlertAction(title: "Camera", style: .default, handler: { _ in
        self.openCamera()
    }))
    
    alert.addAction(UIAlertAction(title: "Gallery", style: .default, handler: { _ in
        self.openGallary()
    }))
    
    alert.addAction(UIAlertAction.init(title: "Cancel", style: .cancel, handler: nil))
    
    /*If you want work actionsheet on ipad
    then you have to use popoverPresentationController to present the actionsheet,
    otherwise app will crash on iPad */
    switch UIDevice.current.userInterfaceIdiom {
    case .pad:
        alert.popoverPresentationController?.sourceView = sender
        alert.popoverPresentationController?.sourceRect = sender.bounds
        alert.popoverPresentationController?.permittedArrowDirections = .up
    default:
        break
    }
    
    self.present(alert, animated: true, completion: nil)
}


func openCamera()
    {
        if(UIImagePickerController .isSourceTypeAvailable(UIImagePickerController.SourceType.camera))
        {
            imagePicker.sourceType = UIImagePickerController.SourceType.camera
            imagePicker.allowsEditing = true
            self.present(imagePicker, animated: true, completion: nil)
        }
        else
        {
            let alert  = UIAlertController(title: "Warning", message: "You don't have camera", preferredStyle: .alert)
            alert.addAction(UIAlertAction(title: "OK", style: .default, handler: nil))
            self.present(alert, animated: true, completion: nil)
        }
    }

    func openGallary()
    {
        imagePicker.sourceType = UIImagePickerController.SourceType.photoLibrary
        imagePicker.allowsEditing = true
        self.present(imagePicker, animated: true, completion: nil)
    }

下载SwiftSwiftUI的示例项目

【讨论】:

  • 感谢您的回答,iPad 中的 UIActionSheet 崩溃,如何解决?
  • 您可以在 iPad 中使用弹出框代替 UIActionSheet。或参考此链接stackoverflow.com/questions/3743512/…
  • 解决方案很棒,但我发现了一个基于场景的错误,我在 imagePickerControllerDidCancel 函数(来自您的 GitHub 项目)下添加了“imagePicker.dismiss(动画:true,完成:nil)”,并且每次第一次运行或重新启动,尝试以下步骤重现错误: 1.选择个人资料>拍照 2.点击取消(不要点击照片) 3.现在再次点击选择个人资料>选择照片 4.你会看到 imagePicker 的取消按钮有消失了。记得通过从内存中清除应用程序来重新启动应用程序以重现此错误。
  • @Saathwik 你是对的。有问题,我修好了。在您的项目中替换此代码func imagePickerControllerDidCancel(_ picker: UIImagePickerController) { picker.isNavigationBarHidden = false self.dismiss(animated: true, completion: nil) }
  • github 项目中也解决了这个问题,感谢@Saathwik。
【解决方案2】:

斯威夫特 5 +:

带有相机和图库的操作表:

//MARK:- Image Picker
    @IBAction func imagePickerBtnAction(selectedButton: UIButton)
    {

        let alert = UIAlertController(title: "Choose Image", message: nil, preferredStyle: .actionSheet)
        alert.addAction(UIAlertAction(title: "Camera", style: .default, handler: { _ in
            self.openCamera()
        }))

        alert.addAction(UIAlertAction(title: "Gallery", style: .default, handler: { _ in
            self.openGallery()
        }))

        alert.addAction(UIAlertAction.init(title: "Cancel", style: .cancel, handler: nil))

        self.present(alert, animated: true, completion: nil)
    }

相机图像选择器功能:

func openCamera()
{
    if UIImagePickerController.isSourceTypeAvailable(UIImagePickerController.SourceType.camera) {
        let imagePicker = UIImagePickerController()
        imagePicker.delegate = self
        imagePicker.sourceType = UIImagePickerController.SourceType.camera
        imagePicker.allowsEditing = false
        self.present(imagePicker, animated: true, completion: nil)
    }
    else
    {
        let alert  = UIAlertController(title: "Warning", message: "You don't have camera", preferredStyle: .alert)
        alert.addAction(UIAlertAction(title: "OK", style: .default, handler: nil))
        self.present(alert, animated: true, completion: nil)
    }
}

图库图片选择器功能:

 func openGallery()
{
    if UIImagePickerController.isSourceTypeAvailable(UIImagePickerController.SourceType.photoLibrary){
        let imagePicker = UIImagePickerController()
        imagePicker.delegate = self
        imagePicker.allowsEditing = true
        imagePicker.sourceType = UIImagePickerController.SourceType.photoLibrary
        self.present(imagePicker, animated: true, completion: nil)
    }
    else
    {
        let alert  = UIAlertController(title: "Warning", message: "You don't have permission to access gallery.", preferredStyle: .alert)
        alert.addAction(UIAlertAction(title: "OK", style: .default, handler: nil))
        self.present(alert, animated: true, completion: nil)
    }
}

ImagePicker 委托:

//MARK:-- ImagePicker delegate
    func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
    if let pickedImage = info[.originalImage] as? UIImage {
        // imageViewPic.contentMode = .scaleToFill
    }
    picker.dismiss(animated: true, completion: nil)
}

【讨论】:

    【解决方案3】:

    设置委托如下:

    UIImagePickerControllerDelegate,UINavigationControllerDelegate
    

    获取一个图像视图,以便我们可以显示选定/捕获的图像:

    @IBOutlet weak var imageViewPic: UIImageView!
    

    使用设备相机捕获新图像:

    if UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.camera) {
            let imagePicker = UIImagePickerController()
            imagePicker.delegate = self
            imagePicker.sourceType = UIImagePickerControllerSourceType.camera
            imagePicker.allowsEditing = false
            self.present(imagePicker, animated: true, completion: nil)
        }
    

    对于从图库中选择照片:

    if UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.photoLibrary){
            let imagePicker = UIImagePickerController()
            imagePicker.delegate = self
            imagePicker.allowsEditing = true
            imagePicker.sourceType = UIImagePickerControllerSourceType.photoLibrary
            self.present(imagePicker, animated: true, completion: nil)
        }
    

    这是委托方法:

         //MARK: - ImagePicker delegate
    func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
        if let pickedImage = info[UIImagePickerControllerOriginalImage] as? UIImage {
           // imageViewPic.contentMode = .scaleToFill
            imageViewPic.image = pickedImage
        }
        picker.dismiss(animated: true, completion: nil)
    }
    

    info.plist 中设置访问相机和照片的权限,例如:

    <key>NSCameraUsageDescription</key>
    <string>This app will use camera</string>
    <key>NSPhotoLibraryUsageDescription</key>
    <string>You can select photo</string>
    

    100% 工作和测试

    【讨论】:

    • 图书馆访问警告未出现。
    【解决方案4】:

    创建视图控制器并在情节提要中添加按钮和图像

    在视图控制器中添加 UIImagePickerControllerDelegate、UINavigationControllerDelegate 协议

    相机动作按钮输入以下代码

    let imagePickerController = UIImagePickerController()
        imagePickerController.delegate = self
        let actionsheet = UIAlertController(title: "Photo Source", message: "Choose A Sourece", preferredStyle: .actionSheet)
        actionsheet.addAction(UIAlertAction(title: "Camera", style: .default, handler: { (action:UIAlertAction)in
            if UIImagePickerController.isSourceTypeAvailable(.camera){
                imagePickerController.sourceType = .camera
                self.present(imagePickerController, animated: true, completion: nil)
            }else
            {
                print("Camera is Not Available")
            }
    
    
    
        }))
        actionsheet.addAction(UIAlertAction(title: "Photo Library", style: .default, handler: { (action:UIAlertAction)in
            imagePickerController.sourceType = .photoLibrary
            self.present(imagePickerController, animated: true, completion: nil)
        }))
        actionsheet.addAction(UIAlertAction(title: "Cancel", style: .cancel, handler: nil))
        self.present(actionsheet,animated: true, completion: nil)
    

    在视图控制器中添加以下功能

     func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
        let image = info[UIImagePickerControllerOriginalImage] as! UIImage
        imageView.image = image
        picker.dismiss(animated: true, completion: nil)
        }
        func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
        picker.dismiss(animated:  true, completion: nil)
        }
    }
    

    在 info.plist 中添加行

     Privacy - Photo Library Usage Description
    Privacy - Camera Usage Description
    

    【讨论】:

      【解决方案5】:

      我创建了这个漂亮的项目,通过这四行代码,您可以从相机或库中获取图像,并通过如下一行应用漂亮的滤镜:-

      let picker = PickerController()
      picker.applyFilter = true // to apply filter after selecting the picture by default false
      picker.selectImage(self){ image in
          // Use the picture
      }
      

      Here's the link of the project.

      【讨论】:

        【解决方案6】:
        //MARK:- Camera and Gallery
        
            func showActionSheet(){
        
                //Create the AlertController and add Its action like button in Actionsheet
                let actionSheetController: UIAlertController = UIAlertController(title: NSLocalizedString("Upload Image", comment: ""), message: nil, preferredStyle: .actionSheet)
                actionSheetController.view.tintColor = UIColor.black
                let cancelActionButton: UIAlertAction = UIAlertAction(title: NSLocalizedString("Cancel", comment: ""), style: .cancel) { action -> Void in
                    print("Cancel")
                }
                actionSheetController.addAction(cancelActionButton)
        
                let saveActionButton: UIAlertAction = UIAlertAction(title: NSLocalizedString("Take Photo", comment: ""), style: .default)
                { action -> Void in
                    self.camera()
                }
                actionSheetController.addAction(saveActionButton)
        
                let deleteActionButton: UIAlertAction = UIAlertAction(title: NSLocalizedString("Choose From Gallery", comment: ""), style: .default)
                { action -> Void in
                    self.gallery()
                }
                actionSheetController.addAction(deleteActionButton)
                self.present(actionSheetController, animated: true, completion: nil)
            }
        
            func camera()
            {
                let myPickerControllerCamera = UIImagePickerController()
                myPickerControllerCamera.delegate = self
                myPickerControllerCamera.sourceType = UIImagePickerController.SourceType.camera
                myPickerControllerCamera.allowsEditing = true
                self.present(myPickerControllerCamera, animated: true, completion: nil)
        
            }
        
            func gallery()
            {
        
                let myPickerControllerGallery = UIImagePickerController()
                myPickerControllerGallery.delegate = self
                myPickerControllerGallery.sourceType = UIImagePickerController.SourceType.photoLibrary
                myPickerControllerGallery.allowsEditing = true
                self.present(myPickerControllerGallery, animated: true, completion: nil)
        
            }
        
        
            //MARK:- ***************  UIImagePickerController delegate Methods ****************
        
            func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
        
                // The info dictionary may contain multiple representations of the image. You want to use the original.
                guard let selectedImage = info[.originalImage] as? UIImage else {
                    fatalError("Expected a dictionary containing an image, but was provided the following: \(info)")
                }
        
                // Set photoImageView to display the selected image.
                imageUserProfile.image = selectedImage
        
                // Dismiss the picker.
                dismiss(animated: true, completion: nil)
            }
        

        【讨论】:

        • 只回答这个在 iOS 13 上对我有用的问题
        • @Torben545 : 我总是只放执行的代码
        【解决方案7】:

        Swift 5 调用函数的简单方法

        //MARK Life Cycles
        override func viewDidLoad() {
            super.viewDidLoad()
            choosePicture
        }
        
        
        
        extension AddBook: UIPickerViewDelegate, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
        
        @objc func choosePicture(){
            let alert  = UIAlertController(title: "Select Image", message: "", preferredStyle: .actionSheet)
            alert.modalPresentationStyle = .overCurrentContext
            alert.addAction(UIAlertAction(title: "Camera", style: .default, handler: { (action) in
                self.openCamera()
            }))
            alert.addAction(UIAlertAction(title: "Photo Library", style: .default, handler: { (action) in
                self.openGallary()
            }))
            
            alert.addAction(UIAlertAction(title: "Cancel", style: .cancel, handler: nil))
            
            let popoverController = alert.popoverPresentationController
            
            popoverController?.permittedArrowDirections = .up
            
            
            self.present(alert, animated: true, completion: nil)
        }
        
        func openCamera() {
            if(UIImagePickerController .isSourceTypeAvailable(UIImagePickerController.SourceType.camera))
            {
                imagePicker.sourceType = UIImagePickerController.SourceType.camera
                imagePicker.allowsEditing = true
                self.present(imagePicker, animated: true, completion: nil)
            }
            else
            {
                let alert  = UIAlertController(title: "Warning", message: "You don't have camera", preferredStyle: .alert)
                alert.addAction(UIAlertAction(title: "OK", style: .default, handler: nil))
                self.present(alert, animated: true, completion: nil)
            }
        }
        
        func openGallary() {
            imagePicker.sourceType = UIImagePickerController.SourceType.photoLibrary
            imagePicker.allowsEditing = true
            self.present(imagePicker, animated: true, completion: nil)
        }
        
        
        
        func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
            picker.dismiss(animated: true, completion: nil)
        }
        
        
        private func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
            // picker.supportedInterfaceOrientations = .
            if let image  = info[UIImagePickerController.InfoKey.originalImage.rawValue] as? UIImage {
                
                    if btnPicOther.tag == 1 {
                        btnPicOther.setImage(image, for: .normal)
                    }
                    else if btnPicBack.tag == 1 {
                        btnPicBack.setImage(image, for: .normal)
                    }
                    else if btnPicFront.tag == 1{
                        btnPicFront.setImage(image, for: .normal)
                    }
                    picker.dismiss(animated: true, completion: nil)
                }
            }
        }
        

        【讨论】:

          【解决方案8】:

          Swift 5:您可以使用下面的相机图像:

          1. 创建一个项目

          2. 在主 Storyboard 中,在底部添加两个按钮并添加 imageView 并链接到 viewController。

          3. Info.plist 中添加 Privacy - Camera Usage Description 权限,如下所示:

          4. 在视图控制器中粘贴以下代码:

            class ViewController: UIViewController {
            
               @IBOutlet weak var imageView: UIImageView!
            
               override func viewDidLoad() {
                  super.viewDidLoad()       
                }
            
             @IBAction func btnPhotGalary(_ sender: Any) {
                let picker = UIImagePickerController()
                picker.sourceType = .photoLibrary
                picker.delegate = self
                present(picker, animated: true)
              }
            
            @IBAction func btnCapture(_ sender: Any) {
              let picker = UIImagePickerController()
              picker.sourceType = .camera
              //for camera front
              // picker.cameraDevice = .front
               picker.delegate = self
               picker.allowsEditing = false
               present(picker, animated: true)
              }
              }
            
              extension ViewController :UIImagePickerControllerDelegate,UINavigationControllerDelegate{
            
            func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
                picker.dismiss(animated: true, completion: nil)
              }
            
            func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
                picker.dismiss(animated: true, completion: nil)
                guard let originalImage = info[UIImagePickerController.InfoKey.originalImage] as? UIImage else {
                 return
               }
                //for image rotation
                let image =  originalImage.upOrientationImage()
                imageView.image = image
              }
            
            }
            
             extension UIImage {
                func upOrientationImage() -> UIImage? {
                 switch imageOrientation {
                    case .up:
                     return self
                 default:
                   UIGraphicsBeginImageContextWithOptions(size, false, scale)
                    draw(in: CGRect(origin: .zero, size: size))
                    let result = UIGraphicsGetImageFromCurrentImageContext()
                      UIGraphicsEndImageContext()
                    return result
                   }
                 }
             }
            
          1. 完整源代码在 GitHub 中:https://github.com/enamul95/UIImagePicker.git

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2017-04-15
            • 1970-01-01
            • 2019-02-23
            • 1970-01-01
            • 2017-12-06
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多