Skip to content

Instantly share code, notes, and snippets.

@BrunoScheltzke
Created July 6, 2020 21:23
Show Gist options
  • Save BrunoScheltzke/1043061249db079aa3ed77dbb760582f to your computer and use it in GitHub Desktop.
Save BrunoScheltzke/1043061249db079aa3ed77dbb760582f to your computer and use it in GitHub Desktop.
Round image view with option to enable a picker view to select image from camera or gallery
//
// RoundImageView.swift
//
// Created by Bruno Scheltzke on 04/06/20.
// Copyright © 2020 Bruno Scheltzke. All rights reserved.
//
import UIKit
protocol RoundImagePickerDelegate {
func didSelect(image: UIImage)
}
@IBDesignable
class RoundImageView: UIImageView {
var delegate: RoundImagePickerDelegate?
@IBInspectable
var shouldEdit: Bool = false {
didSet {
editButton.isHidden = !shouldEdit
}
}
let editButton = UIButton()
var imagePicker: ImagePicker!
override func awakeFromNib() {
super.awakeFromNib()
setupImagePicker()
layer.borderColor = UIColor.systemBlue.cgColor
layer.borderWidth = 1
}
private func setupImagePicker() {
isUserInteractionEnabled = true
editButton.setTitle("Editar", for: .normal)
editButton.setTitleColor(.systemBlue, for: .normal)
editButton.translatesAutoresizingMaskIntoConstraints = false
addSubview(editButton)
editButton.bottomAnchor.constraint(equalTo: bottomAnchor).isActive = true
editButton.centerXAnchor.constraint(equalTo: centerXAnchor).isActive = true
editButton.heightAnchor.constraint(equalTo: heightAnchor, multiplier: 0.3).isActive = true
editButton.addTarget(self, action: #selector(getImage), for: .touchUpInside)
let tap = UITapGestureRecognizer(target: self, action: #selector(getImage))
addGestureRecognizer(tap)
let window = UIApplication.shared.windows.first
imagePicker = ImagePicker(presentationController: window?.rootViewController, delegate: self)
}
override func layoutSubviews() {
super.layoutSubviews()
clipsToBounds = true
layer.cornerRadius = frame.size.width/2
}
@objc func getImage() {
guard shouldEdit else { return }
imagePicker.present(from: self)
}
}
extension RoundImageView: ImagePickerDelegate {
func didSelect(image: UIImage?) {
guard let image = image else { return }
self.image = image
delegate?.didSelect(image: image)
}
}
public protocol ImagePickerDelegate: class {
func didSelect(image: UIImage?)
}
open class ImagePicker: NSObject {
private let pickerController: UIImagePickerController
private weak var presentationController: UIViewController?
private weak var delegate: ImagePickerDelegate?
public init(presentationController: UIViewController?, delegate: ImagePickerDelegate) {
self.pickerController = UIImagePickerController()
super.init()
self.presentationController = presentationController
self.delegate = delegate
self.pickerController.delegate = self
self.pickerController.allowsEditing = true
self.pickerController.mediaTypes = ["public.image"]
}
private func action(for type: UIImagePickerController.SourceType, title: String) -> UIAlertAction? {
guard UIImagePickerController.isSourceTypeAvailable(type) else {
return nil
}
return UIAlertAction(title: title, style: .default) { [unowned self] _ in
self.pickerController.sourceType = type
self.presentationController?.present(self.pickerController, animated: true)
}
}
public func present(from sourceView: UIView) {
let alertController = UIAlertController(title: nil, message: nil, preferredStyle: .actionSheet)
if let action = self.action(for: .camera, title: "Take photo") {
alertController.addAction(action)
}
if let action = self.action(for: .savedPhotosAlbum, title: "Camera roll") {
alertController.addAction(action)
}
if let action = self.action(for: .photoLibrary, title: "Photo library") {
alertController.addAction(action)
}
alertController.addAction(UIAlertAction(title: "Cancel", style: .cancel, handler: nil))
if UIDevice.current.userInterfaceIdiom == .pad {
alertController.popoverPresentationController?.sourceView = sourceView
alertController.popoverPresentationController?.sourceRect = sourceView.bounds
alertController.popoverPresentationController?.permittedArrowDirections = [.down, .up]
}
self.presentationController?.present(alertController, animated: true)
}
private func pickerController(_ controller: UIImagePickerController, didSelect image: UIImage?) {
controller.dismiss(animated: true, completion: nil)
self.delegate?.didSelect(image: image)
}
}
extension ImagePicker: UIImagePickerControllerDelegate {
public func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
self.pickerController(picker, didSelect: nil)
}
public func imagePickerController(_ picker: UIImagePickerController,
didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey: Any]) {
guard let image = info[.editedImage] as? UIImage else {
return self.pickerController(picker, didSelect: nil)
}
self.pickerController(picker, didSelect: image)
}
}
extension ImagePicker: UINavigationControllerDelegate {
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment