camera app with collection view - ios

I am very new to XCode and Swift. Hope you guys can give me a hand here. I am having a problem that when I click the camera button, and snap a photo and click "Use Photo", the camera will be dismissed and back to the main page again.
What I actually want :
When I click "Use Photo" the main page should show the image taken just now in thumbnail size in collection view.
Camera Example
The expected output
Here is my code :
import UIKit
import CoreLocation
import Photos
import PhotosUI
import MessageUI
let albumName = "CP"
class SpeakerViewController: UIViewController,
CLLocationManagerDelegate, UIImagePickerControllerDelegate,
UINavigationControllerDelegate, UICollectionViewDataSource,
UICollectionViewDelegate, UICollectionViewDelegateFlowLayout,
MFMailComposeViewControllerDelegate {
#IBOutlet var lblLocation: UILabel!
#IBOutlet var tvNews: UITextView!
#IBOutlet var tapView: UIView!
#IBOutlet var btnAlbum: UIButton!
#IBOutlet var btnCamera: UIButton!
#IBOutlet var btnSend: UIButton!
let locationManager = CLLocationManager()
let geoCoder = CLGeocoder()
var latitude = [String]()
var longitude = [String]()
var tap : UITapGestureRecognizer! = UITapGestureRecognizer()
var assetCollection: PHAssetCollection! = PHAssetCollection()
var photoAsset : PHFetchResult<PHAsset>!
var albumFound : Bool = false
var sendLocation : String = ""
var sendContent : String = ""
var imageArray = [UIImage]()
var isCamera : Bool = false
#IBAction func btnBack(_ sender: AnyObject) {
PHPhotoLibrary.shared().performChanges({
PHAssetChangeRequest.deleteAssets(self.photoAsset)
}, completionHandler: {(success, error) in
NSLog("Delete image => %#", (success ? "Success" : "Error"))
self.navigationController?.dismiss(animated: true, completion: nil)
})
}
override func viewDidLoad() {
super.viewDidLoad()
LocalStore.setActiveView("speaker")
self.navigationController?.navigationBar.isTranslucent = false
self.navigationController?.navigationBar.barTintColor = UIColor(red: 255/255, green: 237/255, blue: 0/255, alpha: 1.0)
if(locationManager.responds(to: #selector(CLLocationManager.requestAlwaysAuthorization))) {
locationManager.requestAlwaysAuthorization()
}
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.startUpdatingLocation()
tap = UITapGestureRecognizer(target: self, action: #selector(SpeakerViewController.DismissKeyboard))
let fetchOptions = PHFetchOptions()
fetchOptions.predicate = NSPredicate(format: "title = %#", albumName)
let collection:PHFetchResult = PHAssetCollection.fetchAssetCollections(with: .album, subtype: .any, options: fetchOptions)
if let first_Obj:AnyObject = collection.firstObject{
//found the album
self.albumFound = true
self.assetCollection = first_Obj as! PHAssetCollection
} else {
var albumPlaceholder:PHObjectPlaceholder!
NSLog("\nFolder \"%#\" does not exist\nCreating now...", albumName)
PHPhotoLibrary.shared().performChanges({
let request = PHAssetCollectionChangeRequest.creationRequestForAssetCollection(withTitle: albumName)
albumPlaceholder = request.placeholderForCreatedAssetCollection
},
completionHandler: {success, error in
if(success){
print("Successfully created folder")
self.albumFound = true
let collection = PHAssetCollection.fetchAssetCollections(withLocalIdentifiers: [albumPlaceholder.localIdentifier], options: nil)
self.assetCollection = collection.firstObject as PHAssetCollection!
} else {
print("Error creating folder")
self.albumFound = false
}
})
}
NotificationCenter.default.addObserver(self,
selector: #selector(SpeakerViewController.keyboardShow(_:)),
name: NSNotification.Name.UIKeyboardDidShow,
object: nil)
NotificationCenter.default.addObserver(self,
selector: #selector(SpeakerViewController.keyboardHide(_:)),
name: NSNotification.Name.UIKeyboardDidHide,
object: nil)
NotificationCenter.default.addObserver(self,
selector: #selector(SpeakerViewController.applicationBecameActive(_:)),
name: NSNotification.Name.UIApplicationDidBecomeActive,
object: nil)
NotificationCenter.default.addObserver(self,
selector: #selector(SpeakerViewController.applicationBecameInactive(_:)),
name: NSNotification.Name.UIApplicationWillResignActive,
object: nil)
}
/* Start listening for iCloud user change notifications */
func applicationBecameActive(_ notification: Notification){
print("did become active notification")
if LocalStore.getPostIdMenu() != "0" {
self.navigationController?.dismiss(animated: true, completion: nil)
LocalStore.setPostIdMenu("0")
}
}
func applicationBecameInactive(_ notification: Notification){
print("did become inactive notification")
LocalStore.setPostIdMenu("0")
}
func keyboardShow(_ notification: Notification) {
print("Keyboard Show")
self.view.addGestureRecognizer(tap)
}
func keyboardHide(_ notification: Notification){
print("Keyboard Hide")
self.view.removeGestureRecognizer(tap)
}
override func viewWillAppear(_ animated: Bool) {
//fetch the photo from the collection
self.navigationController?.hidesBarsOnTap = false
self.photoAsset = PHAsset.fetchAssets(in: self.assetCollection, options: nil)
self.collectionView.reloadData()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) {
let alertView = UIAlertController(title: "出现错误", message: "无法检索您的位置", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default){ _ in})
self.present(alertView, animated: true, completion: nil)
}
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
latitude.removeAll()
longitude.removeAll()
let currentLocation = locations.last!
print("didUpdateToLocation: \(currentLocation)")
latitude.append(String(format: "%.8f", currentLocation.coordinate.latitude))
longitude.append(String(format: "%.8f", currentLocation.coordinate.longitude))
print("Latitude \(latitude.count), Longtitude \(longitude.count)")
geoCoder.reverseGeocodeLocation(currentLocation, completionHandler: {(placemarks, error) -> Void in
if(error == nil && placemarks!.count > 0 ) {
let placeMark = placemarks![0] as CLPlacemark
if (placeMark.addressDictionary?["Thoroughfare"] as? String) != nil {
self.lblLocation.text = "\(placeMark.thoroughfare!), \(placeMark.postalCode!), \(placeMark.administrativeArea!)"
print("Location \(placeMark.locality!)\(placeMark.country!)")
self.locationManager.stopUpdatingLocation()
self.sendLocation = self.lblLocation.text!
} else {
print("thoroughfare not found, reupdate coordinate")
self.locationManager.delegate = self
self.locationManager.desiredAccuracy = kCLLocationAccuracyBest
self.locationManager.startUpdatingLocation()
}
} else {
NSLog("%#", error.debugDescription)
}
})
}
func DismissKeyboard() {
view.endEditing(true)
}
#IBOutlet var collectionView: UICollectionView!
#IBAction func btnAlbum(_ sender: AnyObject) {
isCamera = false
if(UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.savedPhotosAlbum)) {
let imagePicker : UIImagePickerController = UIImagePickerController()
imagePicker.sourceType = UIImagePickerControllerSourceType.photoLibrary
imagePicker.mediaTypes = UIImagePickerController.availableMediaTypes(for: .photoLibrary)!
imagePicker.delegate = self
imagePicker.allowsEditing = false
self.present(imagePicker, animated: true, completion: nil)
}
}
#IBAction func btnCamera(_ sender: AnyObject) {
isCamera = true
if(UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.camera)) {
let imagePicker : UIImagePickerController = UIImagePickerController()
imagePicker.sourceType = UIImagePickerControllerSourceType.camera
imagePicker.delegate = self
imagePicker.allowsEditing = false
self.present(imagePicker, animated: true, completion: nil)
} else {
let alert = UIAlertController(title: "出现错误", message: "您的手机没有相机", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alert.dismiss(animated: true, completion: nil)
}))
self.present(alert, animated: true, completion: nil)
}
}
#IBAction func btnSend(_ sender: AnyObject) {
var count : Int = 0
if(self.photoAsset != nil) {
count = self.photoAsset.count
}
if (tvNews.text != "" && count > 0) {
sendContent = tvNews.text
if (MFMailComposeViewController.canSendMail()) {
let emailTitle = "App"
let messageBody = "位置: \(sendLocation) \n\n \(sendContent) \n\n "
let toReceipients = ["test#com"]
let mc : MFMailComposeViewController = MFMailComposeViewController()
mc.mailComposeDelegate = self
mc.setSubject(emailTitle)
mc.setMessageBody(messageBody, isHTML: false)
mc.setToRecipients(toReceipients)
}
for image in self.imageArray {
let photoData : Data = UIImagePNGRepresentation(image)!
mc.addAttachmentData(photoData, mimeType: "image/png", fileName: "CP.png")
}
self.present(mc, animated: true, completion: nil)
} else {
print("No email account found")
}
} else {
let alertView = UIAlertController(title: "出现错误", message: "没有内容或照片", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alertView.dismiss(animated: true, completion: nil)
}))
self.present(alertView, animated: true, completion: nil)
}
}
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
var count : Int = 0
if(self.photoAsset != nil) {
count = self.photoAsset.count
}
return count
}
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let cell: PhotoCollectionViewCell = collectionView.dequeueReusableCell(withReuseIdentifier: "PhotoCell", for: indexPath) as! PhotoCollectionViewCell
let asset : PHAsset = self.photoAsset[(indexPath as NSIndexPath).item] as PHAsset
PHImageManager.default().requestImage(for: asset, targetSize: PHImageManagerMaximumSize, contentMode: .aspectFill, options: nil, resultHandler: {(result, info) in
if let image = result {
cell.setThumbnailImage(image)
self.imageArray.append(image)
}
})
return cell
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if(segue.identifier == "viewLargePhoto") {
if let controller:ViewPhotoViewController = segue.destination as? ViewPhotoViewController {
if let cell = sender as? UICollectionViewCell {
if let indexPath: IndexPath = self.collectionView.indexPath(for: cell) {
controller.index = (indexPath as NSIndexPath).item
controller.photoAsset = self.photoAsset
controller.assetCollection = self.assetCollection
}
}
}
}
}
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
return 4
}
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
return 1
}
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
if(isCamera) {
let image = info["UIImagePickerControllerOriginalImage"] as! UIImage
PHPhotoLibrary.shared().performChanges({
let createAssetRequest = PHAssetChangeRequest.creationRequestForAsset(from: image)
let assetPlaceholder = createAssetRequest.placeholderForCreatedAsset
if let albumChangeRequest = PHAssetCollectionChangeRequest(for: self.assetCollection,
assets: self.photoAsset as PHFetchResult<PHAsset>) {
let enumeration: NSArray = [assetPlaceholder!]
albumChangeRequest.addAssets(enumeration)
}
//CORRECTION Error : App crashes
}, completionHandler: {(success, error) in
NSLog("Adding Image to Library => %#",(success ? "Success" : "Error!"))
//Relocated1
})
//CORRECTION Relocated1
picker.dismiss(animated: true, completion: nil)
} else {
let image = info["UIImagePickerControllerOriginalImage"] as! UIImage
PHPhotoLibrary.shared().performChanges({
let createAssetRequest = PHAssetChangeRequest.creationRequestForAsset(from: image)
let assetPlaceholder = createAssetRequest.placeholderForCreatedAsset
if let albumChangeRequest = PHAssetCollectionChangeRequest(for: self.assetCollection,
assets: self.photoAsset as PHFetchResult<PHAsset>) {
let enumeration: NSArray = [assetPlaceholder!]
albumChangeRequest.addAssets(enumeration)
}
}, completionHandler: {(success, error) in
NSLog("Adding Image to Library => %#",(success ? "Success" : "Error!"))
picker.dismiss(animated: true, completion: nil)
//self.navigationController?.dismiss(animated: true, completion: nil)
})
}
}
func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
picker.dismiss(animated: true, completion: nil)
}
func mailComposeController(_ controller: MFMailComposeViewController, didFinishWith result: MFMailComposeResult, error: Error?) {
switch result {
case .cancelled:
let alertView = UIAlertController(title: "取消电邮", message: "您已经取消电邮", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alertView.dismiss(animated: true, completion: nil)
}))
self.present(alertView, animated: true, completion: nil)
case .saved:
let alertView = UIAlertController(title: "保存电邮", message: "您已经保存电邮", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alertView.dismiss(animated: true, completion: nil)
}))
self.present(alertView, animated: true, completion: nil)
case .sent:
let alertView = UIAlertController(title: "发送电邮", message: "您已经发送您的电邮", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alertView.dismiss(animated: true, completion: nil)
}))
self.present(alertView, animated: true, completion: nil)
case .failed:
let alertView = UIAlertController(title: "发送失败", message: "请检查您的电邮设定", preferredStyle: .alert)
alertView.addAction(UIAlertAction(title: "好的", style: .default, handler: {(alertAction) in
alertView.dismiss(animated: true, completion: nil)
}))
self.present(alertView, animated: true, completion: nil)
//CORRECTION default:
// break
default :
break
}
self.dismiss(animated: false, completion: nil)
}
}
Thanks in advance!

Related

UIImagepickercontroller - Camera is not working

This is my imagepicker class
import UIKit
public protocol ImagePickerDelegate: AnyObject {
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)
}
}
func openCamera() {
self.pickerController.sourceType = .camera
self.presentationController?.present(self.pickerController, animated: true)
}
func openPhotoLibrary() {
self.pickerController.sourceType = .photoLibrary
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: Localization.set(key: .take_photo)) {
alertController.addAction(action)
}
if let action = self.action(for: .savedPhotosAlbum, title: Localization.set(key: .camera_roll)) {
alertController.addAction(action)
}
if let action = self.action(for: .photoLibrary, title: Localization.set(key: .photo_library)) {
alertController.addAction(action)
}
alertController.addAction(UIAlertAction(title: Localization.set(key: .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 {
}
This is how I used this class
self.imagePicker = ImagePicker(presentationController: self, delegate: self)
//MARK:- ImagePickerDelegate
extension AddEditGroupViewController: ImagePickerDelegate {
func didSelect(image: UIImage?) {
if let wnwrappedImage = image , let imageData = wnwrappedImage.jpegData(compressionQuality: 0){
self.changePhotoView.profileImageView.image = wnwrappedImage
imageParams = ["group_photo" : imageData]
}
}
}
It's working fine for photo gallery and saved photo album but When I try to open camera, it's giving me error as follows
**[Camera] Failed to read exposureBiasesByMode dictionary: Error Domain=NSCocoaErrorDomain Code=4864 "*** -[NSKeyedUnarchiver _initForReadingFromData:error:throwLegacyExceptions:]: data is NULL" UserInfo={NSDebugDescription=*** -[NSKeyedUnarchiver _initForReadingFromData:error:throwLegacyExceptions:]: data is NULL}**
Any help would be appreciated

How to pick, display two images on two UIImageViews, and then upload these two chosen images to Firebase Database and Storage?

I want to pick two different images on two imageView's on one ViewController, display them, and after pushing the button save picked images to firebase database and storage to its particular user. My code only able to upload one picked image, not two different, I understand that the problem with UIImagePickerController part, but how can I resolve it. Full code of viewController is below. Please help!!
override func viewDidLoad() {
super.viewDidLoad()
let tapGesture = UITapGestureRecognizer(target: self, action: #selector(SettingProfileViewController.handleSelectProfileImageView(sender:)))
profilePhoto.addGestureRecognizer(tapGesture)
profilePhoto.isUserInteractionEnabled = true
let wallTapGesture = UITapGestureRecognizer(target: self, action: #selector(SettingProfileViewController.handleSelectWallpaperImageView(sender:)))
wallpaperPhoto.addGestureRecognizer(wallTapGesture)
wallpaperPhoto.isUserInteractionEnabled = true
profilePhoto.layer.cornerRadius = 60
profilePhoto.clipsToBounds = true
}
weak var activeImageView:UIImageView? = nil
#objc func handleSelectWallpaperImageView(sender: UIGestureRecognizer){
guard let sendingImageView = sender.view as? UIImageView else {
print("Ooops, received this gesture not from an ImageView")
return
}
activeImageView = sendingImageView
let actionSheet = UIAlertController(title: "New Photo", message: nil, preferredStyle: .actionSheet)
actionSheet.addAction(UIAlertAction(title: "Камера", style: .default, handler: { action in
self.showCamera()
}))
actionSheet.addAction(UIAlertAction(title: "Альбом ", style: .default, handler: {action in
self.showAlbum()
}))
actionSheet.addAction(UIAlertAction(title: "Отмена", style: .cancel, handler: nil))
self.present(actionSheet, animated: true, completion: nil)
}
#objc func handleSelectProfileImageView(sender: UIGestureRecognizer){
guard let sendingImageView = sender.view as? UIImageView else {
print("Ooops, received this gesture not from an ImageView")
return
}
activeImageView = sendingImageView
let actionSheet = UIAlertController(title: "New Photo", message: nil, preferredStyle: .actionSheet)
actionSheet.addAction(UIAlertAction(title: "Камера", style: .default, handler: { action in
self.showCamera()
}))
actionSheet.addAction(UIAlertAction(title: "Альбом ", style: .default, handler: {action in
self.showAlbum()
}))
actionSheet.addAction(UIAlertAction(title: "Отмена", style: .cancel, handler: nil))
self.present(actionSheet, animated: true, completion: nil)
}
func showCamera() {
let cameraPicker = UIImagePickerController()
cameraPicker.delegate = self
cameraPicker.sourceType = .camera
present(cameraPicker, animated: true, completion: nil)
}
func showAlbum(){
let cameraPicker = UIImagePickerController()
cameraPicker.delegate = self
cameraPicker.sourceType = .photoLibrary
present(cameraPicker, animated: true, completion: nil)
}
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
dismiss(animated: true, completion: nil)
if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage{
// selectedImage = image
activeImageView?.image = image
// currentImage = image
}
}
func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
dismiss(animated: true, completion: nil)
}
///для того чтобы загруженные фото, отображались на ProfileViewController
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "profileVC" {
let destination = segue.destination as! ProfileViewController
destination.wImage = activeImageView?.image
}
}
#IBAction func saveTapped(_ sender: Any) {
let db = Firestore.firestore()
let did = Auth.auth().currentUser!.uid
let storageRef = Storage.storage().reference(forURL: "gs://crut-6c67c.appspot.com").child("profile_Image").child(did)
if let pImage = self.activeImageView?.image, let imageData = pImage.jpegData(compressionQuality: 0.1) {
storageRef.putData(imageData, metadata: nil, completion: {(metadata, Error) in
if Error != nil, metadata != nil {
return
}
storageRef.downloadURL { (url: URL?,error: Error?) in
if let profileImageUrl = url?.absoluteString{
db.collection("suppliers").document("ip").collection("ipinfo").document(did).setData(["Profile Image":profileImageUrl], merge: true)
}
}
})
}
let storyBoard: UIStoryboard = UIStoryboard(name: "Profile", bundle: nil)
let profileViewController = storyBoard.instantiateViewController(identifier:profile.Storyboard.profileViewController) as? ProfileViewController
self.view.window?.rootViewController = profileViewController
self.view.window?.makeKeyAndVisible()
}
}
You can make an instance variable in your viewController i.e.
private var isProfilePhotoSelecting = true
When user tap on profileImageView in handleSelectProfileImageView method set isProfilePhotoSelecting to true i.e.
#objc func handleSelectProfileImageView(sender: UIGestureRecognizer){
guard let sendingImageView = sender.view as? UIImageView else {
print("Ooops, received this gesture not from an ImageView")
return
}
// Updated the image under consideration
isProfilePhotoSelecting = true
let actionSheet = UIAlertController(title: "New Photo", message: nil, preferredStyle: .actionSheet)
actionSheet.addAction(UIAlertAction(title: "Камера", style: .default, handler: { action in
self.showCamera()
}))
actionSheet.addAction(UIAlertAction(title: "Альбом ", style: .default, handler: {action in
self.showAlbum()
}))
actionSheet.addAction(UIAlertAction(title: "Отмена", style: .cancel, handler: nil))
self.present(actionSheet, animated: true, completion: nil)
}
And on wallpaperImageView tapping in handleSelectWallpaperImageView method set isProfilePhotoSelecting to false i.e.
#objc func handleSelectWallpaperImageView(sender: UIGestureRecognizer){
guard let sendingImageView = sender.view as? UIImageView else {
print("Ooops, received this gesture not from an ImageView")
return
}
// Updated the image under consideration
isProfilePhotoSelecting = false
let actionSheet = UIAlertController(title: "New Photo", message: nil, preferredStyle: .actionSheet)
actionSheet.addAction(UIAlertAction(title: "Камера", style: .default, handler: { action in
self.showCamera()
}))
actionSheet.addAction(UIAlertAction(title: "Альбом ", style: .default, handler: {action in
self.showAlbum()
}))
actionSheet.addAction(UIAlertAction(title: "Отмена", style: .cancel, handler: nil))
self.present(actionSheet, animated: true, completion: nil)
}
Then update your imagePickerDelegate to :
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage {
if isProfilePhotoSelecting {
profilePhoto.image = image
} else {
wallpaperPhoto.image = image
}
}
dismiss(animated: true, completion: nil)
}
This will help you set both your images to their respective imageView. Then in saveTapped(_:) method you can check both imageViews for images and upload them i.e. Your saveTapped() method should look like this
#IBAction func saveTapped(_ sender: Any) {
let db = Firestore.firestore()
let did = Auth.auth().currentUser!.uid
let storageRef = Storage.storage().reference(forURL: "gs://crut-6c67c.appspot.com")
if let profileImage = self.profilePhoto.image, let imageData = profileImage.jpegData(compressionQuality: 0.1) {
let profileStorage = storageRef.child("profile_Image").child(did)
profileStorage.putData(imageData, metadata: nil, completion: {(metadata, Error) in
if Error != nil, metadata != nil {
return
}
profileStorage.downloadURL { (url: URL?,error: Error?) in
if let profileImageUrl = url?.absoluteString {
db.collection("suppliers").document("ip").collection("ipinfo").document(did).setData(["Profile Image":profileImageUrl], merge: true)
}
}
})
}
if let wallpaperImage = self.wallpaperPhoto.image, let imageData = wallpaperImage.jpegData(compressionQuality: 0.1) {
let wallpaperStorage = storageRef.child("wallpaper_Image").child(did)
wallpaperStorage.putData(imageData, metadata: nil, completion: {(metadata, Error) in
if Error != nil, metadata != nil {
return
}
wallpaperStorage.downloadURL { (url: URL?,error: Error?) in
if let wallpaperImageUrl = url?.absoluteString {
// Do your stuff with wallpaper image url here
}
}
})
}
let storyBoard: UIStoryboard = UIStoryboard(name: "Profile", bundle: nil)
let profileViewController = storyBoard.instantiateViewController(identifier:profile.Storyboard.profileViewController) as? ProfileViewController
self.view.window?.rootViewController = profileViewController
self.view.window?.makeKeyAndVisible()
}
Note: This will not wait for the images to upload as you are waiting for them to upload. But it depends on your usecase if you want to wait until the image uploading completes and then move to ProfileViewController, you can use DispatchGroup for that purpose.
I hope your saving the last choosen image on activeImageView and passing that to Firebase, hence only one image is getting uploaded.
Instead create and Array and both the images choosen from handleSelectWallpaperImageView and handleSelectWallpaperImageView, then loop through the Array and send to Firebase.
Check this for more information: https://stackoverflow.com/a/49934285/1244403
Created option Boolean variable
var isProfilePhotoSelecting:Bool?
#objc func handleSelectWallpaperImageView(sender: UIGestureRecognizer){
isProfilePhotoSelecting = false
///
other code
}
#objc func handleSelectProfileImageView(sender: UIGestureRecognizer){
isProfilePhotoSelecting = true
///
other code
}
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
dismiss(animated: true, completion: nil)
if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage{
if isProfilePhotoSelecting == true {
profilePhoto.image = image
}else {
wallpaperPhoto.image = image
}
}
}
In the saveTapped need to be added storage references to each chosen image and its respective database.
#IBAction func saveTapped(_ sender: Any) {
let db = Firestore.firestore()
let did = Auth.auth().currentUser!.uid
let storageRef = Storage.storage().reference(forURL: "gs://crut-6c67c.appspot.com").child("profile_Image").child(did)
if let profileImage = self.profilePhoto.image, let imageData = profileImage.jpegData(compressionQuality: 0.1){
storageRef.putData(imageData, metadata: nil, completion: {(metadata, Error) in
if Error != nil, metadata != nil {
return
}
storageRef.downloadURL { (url: URL?, error: Error?) in
if let profileImageUrl = url?.absoluteString {
db.collection("suppliers").document("ip").collection("ipinfo").document(did).setData(["Profile Image":profileImageUrl], merge: true)
}
}
})
}
let wallStoreRef = Storage.storage().reference(forURL: "gs://crut-6c67c.appspot.com").child("Wallpaper_Image").child(did)
if let wallpaperImage = self.wallpaperPhoto.image, let imageData = wallpaperImage.jpegData(compressionQuality: 0.1) {
wallStoreRef.putData(imageData, metadata: nil, completion: {(metadata, Error) in
if Error != nil, metadata != nil {
return
}
wallStoreRef.downloadURL { (url: URL?,error: Error?) in
if let wallpaperImageUrl = url?.absoluteString {
// Do your stuff with wallpaper image url here
db.collection("suppliers").document("ip").collection("ipinfo").document(did).setData(["Wallpaper Image":wallpaperImageUrl], merge: true)
}
}
})
}

provideAPIKey: should be called at most once (Swift)

I'm using Google maps and places API and i'm trying to load nearby places in a tableView but everytime i come in this class
import UIKit
import MapKit
import CoreLocation
import GoogleMaps
import GooglePlaces
import Social
import AVFoundation
private let resueIdentifier = "MyTableViewCell"
extension UIViewController {
func present(viewController : UIViewController, completion : (() -> ())? = nil ){
if let presented = self.presentedViewController {
presented.dismiss(animated: true, completion: {
self.present(viewController, animated: true, completion: completion)
})
} else {
self.present(viewController, animated: true, completion: completion)
}
}
}
class CourseClass2: UIViewController, UITableViewDelegate, UITableViewDataSource {
#IBOutlet weak var tableView: UITableView!
struct User {
var name: String
var images: UIImage
var type: String
}
var previuosViewTappedButtonsArray = [String]()
var locationManager:CLLocationManager?
let minimumSpacing : CGFloat = 15 //CGFloat(MAXFLOAT)
let cellWidth: CGFloat = 250
let radius = 5000 // 5km
var category : QCategoryy?
var currentLocation : CLLocationCoordinate2D?
var places: [QPlace] = []
var isLoading = false
var response : QNearbyPlacesResponse?
var rows = 0
var users = [User]()
override func viewDidLoad() {
super.viewDidLoad()
self.title = category?.name
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
determineMyCurrentLocation()
}
override func viewWillDisappear(_ animated: Bool) {
super.viewWillAppear(animated)
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
rows = 0
insertRowsMode3()
tableView.reloadData()
category?.markView()
}
#IBAction func refreshTapped(_ sender: Any) {
rows = 0
insertRowsMode3()
tableView.reloadData()
}
func canLoadMore() -> Bool {
if isLoading {
return false
}
if let response = self.response {
if (!response.canLoadMore()) {
return false
}
}
return true
}
func loadPlaces(_ force:Bool) {
if !force {
if !canLoadMore() {
return
}
}
print("load more")
isLoading = true
NearbyPlaces.getNearbyPlaces(by: category?.name ?? "food", coordinates: currentLocation!, radius: radius, token: self.response?.nextPageToken, completion: didReceiveResponse)
}
func didReceiveResponse(response:QNearbyPlacesResponse?, error : Error?) -> Void {
if let error = error {
let alertController = UIAlertController(title: "Error", message: error.localizedDescription, preferredStyle: .alert)
let actionDismiss = UIAlertAction(title: "Dismiss", style: .cancel, handler: nil)
let actionRetry = UIAlertAction(title: "Retry", style: .default, handler: { (action) in
DispatchQueue.main.async {
self.loadPlaces(true)
}
})
alertController.addAction(actionRetry)
alertController.addAction(actionDismiss)
DispatchQueue.main.async {
self.present(viewController: alertController)
}
}
if let response = response {
self.response = response
if response.status == "OK" {
if let placesDownloaded = response.places {
places.append(contentsOf: placesDownloaded)
}
self.tableView?.reloadData()
} else {
let alert = UIAlertController.init(title: "Error", message: response.status, preferredStyle: .alert)
alert.addAction(UIAlertAction.init(title: "Cancel", style: .cancel, handler: nil))
alert.addAction(UIAlertAction.init(title: "Retry", style: .default, handler: { (action) in
DispatchQueue.main.async {
self.loadPlaces(true)
}
}))
self.present(viewController: alert)
}
isLoading = false
}
else {
print("response is nil")
}
}
func insertRowsMode2() {
tableView.beginUpdates()
for i in 0..<places.count {
insertRowMode2(ind: i, usr: places[i])
}
tableView.endUpdates()
}
func insertRowMode2(ind:Int,usr:QPlace) {
tableView.beginUpdates()
let indPath = IndexPath(row: ind, section: 0)
rows = ind + 1
tableView.insertRows(at: [indPath], with: .right)
tableView.endUpdates()
}
func insertRowsMode3() {
tableView.beginUpdates()
rows = 0
insertRowMode3(ind: 0)
tableView.endUpdates()
}
func insertRowMode3(ind:Int) {
tableView.beginUpdates()
let indPath = IndexPath(row: ind, section: 0)
rows = ind + 1
tableView.insertRows(at: [indPath], with: .right)
guard ind < places.count-1 else { return }
DispatchQueue.main.asyncAfter(deadline: .now()+0.20) {
self.insertRowMode3(ind: ind+1)
}
tableView.endUpdates()
}
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return places.count /* rows */
}
public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! MyTableViewCell
let place = places[indexPath.row]
cell.update(place: place)
if indexPath.row == places.count - 1 {
loadPlaces(false)
}
/* let user = users[indexPath.row]
cell.selectionStyle = .none
cell.myImage.image = user.images
cell.myLabel.text = user.name
cell.myTypeLabel.text = user.type */
return (cell)
}
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
tableView.deselectRow(at: indexPath, animated: true)
UIView.animate(withDuration: 0.2, animations: {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! MyTableViewCell
})
performSegue(withIdentifier: "goToLast" , sender: users[indexPath.row])
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 100
}
func tableView(_ tableView: UITableView, canEditRowAt indexPath: IndexPath) -> Bool {
return true
}
func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
if editingStyle == UITableViewCellEditingStyle.delete {
places.remove(at: indexPath.row)
tableView.deleteRows(at: [indexPath], with: .fade)
}
}
func didReceiveUserLocation(_ userLocation:CLLocation) {
currentLocation = userLocation.coordinate
loadPlaces(true)
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "goToLast" && sender is IndexPath {
let dvc = segue.destination as! FinalClass
dvc.index = (sender as! IndexPath).row
dvc.places = places
dvc.userLocation = currentLocation
/* guard let vc = segue.destination as? FinalClass else { return }
let guest = segue.destination as! FinalClass
if let user = sender as? User {
*/
}
}
#IBAction func IndTapped(_ sender: Any) {
dismiss(animated: true, completion: nil)
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
#IBAction func socialShare(_ sender: Any) {
//Alert
let alert = UIAlertController(title: "Share", message: "First share!", preferredStyle: .actionSheet)
//First action
let actionOne = UIAlertAction(title: "Share on Facebook", style: .default) { (action) in
//Checking if user is connected to Facebook
if SLComposeViewController.isAvailable(forServiceType: SLServiceTypeFacebook)
{
let post = SLComposeViewController(forServiceType: SLServiceTypeFacebook)!
post.setInitialText("First")
post.add(UIImage(named: "uround logo.png"))
self.present(post, animated: true, completion: nil)
} else {self.showAlert(service: "Facebook")}
}
let actionThree = UIAlertAction(title: "Cancel", style: .cancel, handler: nil)
//Add action to action sheet
alert.addAction(actionOne)
alert.addAction(actionThree)
//Present alert
self.present(alert, animated: true, completion: nil)
}
func showAlert(service:String)
{
let alert = UIAlertController(title: "Error", message: "You are not connected to \(service)", preferredStyle: .alert)
let action = UIAlertAction(title: "Dismiss", style: .cancel, handler: nil)
alert.addAction(action)
present(alert, animated: true, completion: nil)
}
}
extension CourseClass2: CLLocationManagerDelegate {
func determineMyCurrentLocation() {
locationManager = CLLocationManager()
locationManager?.delegate = self
locationManager?.desiredAccuracy = kCLLocationAccuracyBest
locationManager?.requestWhenInUseAuthorization()
}
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
let userLocation:CLLocation = locations[0] as CLLocation
manager.stopUpdatingLocation()
print("user latitude = \(userLocation.coordinate.latitude)")
print("user longitude = \(userLocation.coordinate.longitude)")
didReceiveUserLocation(userLocation)
}
func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) {
print("Error \(error)")
errorGettingCurrentLocation(error.localizedDescription)
}
public func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
if status == .authorizedWhenInUse || status == .authorizedAlways {
locationManager?.startUpdatingLocation()
//locationManager.startUpdatingHeading()
} else if status == .denied || status == .restricted {
errorGettingCurrentLocation("Location access denied")
}
}
func errorGettingCurrentLocation(_ errorMessage:String) {
let alert = UIAlertController.init(title: "Error", message: errorMessage, preferredStyle: .alert)
alert.addAction(UIAlertAction.init(title: "Cancel", style: .cancel, handler: nil))
present(alert, animated: true, completion: nil)
}
}
i get the message "error - response status" from this function
func didReceiveResponse(response:QNearbyPlacesResponse?, error : Error?) -> Void {
if let error = error {
let alertController = UIAlertController(title: "Error", message: error.localizedDescription, preferredStyle: .alert)
let actionDismiss = UIAlertAction(title: "Dismiss", style: .cancel, handler: nil)
let actionRetry = UIAlertAction(title: "Retry", style: .default, handler: { (action) in
DispatchQueue.main.async {
self.loadPlaces(true)
}
})
alertController.addAction(actionRetry)
alertController.addAction(actionDismiss)
DispatchQueue.main.async {
self.present(viewController: alertController)
}
}
if let response = response {
self.response = response
if response.status == "OK" {
if let placesDownloaded = response.places {
places.append(contentsOf: placesDownloaded)
}
self.tableView?.reloadData()
} else {
let alert = UIAlertController.init(title: "Error", message: response.status, preferredStyle: .alert)
alert.addAction(UIAlertAction.init(title: "Cancel", style: .cancel, handler: nil))
alert.addAction(UIAlertAction.init(title: "Retry", style: .default, handler: { (action) in
DispatchQueue.main.async {
self.loadPlaces(true)
}
}))
self.present(viewController: alert)
}
isLoading = false
}
else {
print("response is nil")
}
}
so looking in the console i saw this error "((null)) was false: provideAPIKey: should be called at most once" which is perhaps the cause of the problem (even if I'm not sure), i followed the google documentation guide to get the API key for the project, here is my appDelegate where there are my keys (i changed for now the numbers of the key with "My Api key")
import UIKit
import Firebase
import CoreLocation
import GoogleMaps
import GooglePlaces
import FBSDKCoreKit
import GoogleSignIn
import FBSDKShareKit
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate, GIDSignInDelegate {
static let googleMapsApiKey = "MY API Key"
static let googlePlacesAPIKey = "MY API Key"
var window: UIWindow?
var locationManager: CLLocationManager?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
FirebaseApp.configure()
locationManager = CLLocationManager()
locationManager?.requestWhenInUseAuthorization()
GMSServices.provideAPIKey(AppDelegate.googleMapsApiKey)
GMSPlacesClient.provideAPIKey(AppDelegate.googlePlacesAPIKey)
FBSDKApplicationDelegate.sharedInstance().application(application, didFinishLaunchingWithOptions: launchOptions)
IQKeyboardManager.sharedManager().enable = true
IQKeyboardManager.sharedManager().enableAutoToolbar = false
GIDSignIn.sharedInstance().clientID = FirebaseApp.app()?.options.clientID
GIDSignIn.sharedInstance().delegate = self
if GMSServices.provideAPIKey("MY API Key") {
print("good provided keys correctly")
}
else {
print("key didn't provided")
}
return true
}
someone can tell if the problem is a wrong use of the api key or if the keys are wrong or maybe the problem is another ?
Look at what you are doing here:
// once
GMSServices.provideAPIKey(AppDelegate.googleMapsApiKey)
GMSPlacesClient.provideAPIKey(AppDelegate.googlePlacesAPIKey)
FBSDKApplicationDelegate.sharedInstance().application(application, didFinishLaunchingWithOptions: launchOptions)
IQKeyboardManager.sharedManager().enable = true
IQKeyboardManager.sharedManager().enableAutoToolbar = false
GIDSignIn.sharedInstance().clientID = FirebaseApp.app()?.options.clientID
GIDSignIn.sharedInstance().delegate = self
// twice!
if GMSServices.provideAPIKey("MY API Key") {
You are calling provideAPIKey twice!
I know you want to check whether the API key is provided correctly, but the correct way to do this is not to call the method twice. Instead, you should store the return value and check the return value:
// put the return value in "success"
let success = GMSServices.provideAPIKey(AppDelegate.googleMapsApiKey)
GMSPlacesClient.provideAPIKey(AppDelegate.googlePlacesAPIKey)
FBSDKApplicationDelegate.sharedInstance().application(application, didFinishLaunchingWithOptions: launchOptions)
IQKeyboardManager.sharedManager().enable = true
IQKeyboardManager.sharedManager().enableAutoToolbar = false
GIDSignIn.sharedInstance().clientID = FirebaseApp.app()?.options.clientID
GIDSignIn.sharedInstance().delegate = self
// check "success"
if success {

app crashes after accessing photo library

This is what i aded in the info plist
Key : Privacy - Camera Usage Description
Value : deportes wants to access your photos
Key : Privacy - Photo Library Usage Description
Value : deportes wants to access your photos
This the code of the action sheet and after picking the image
#IBAction func didtapc(_ sender: UITapGestureRecognizer) {
let myactionsheet = UIAlertController(title : "profile picture",message:"select",preferredStyle:UIAlertControllerStyle.actionSheet)
let viewpic = UIAlertAction(title:"view pic",style: UIAlertActionStyle.default) { (action) in
let imageview = sender.view as! UIImageView
let newimageview = UIImageView(image: imageview.image)
newimageview.frame = self.view.frame
newimageview.backgroundColor = UIColor.black
newimageview.contentMode = .scaleAspectFit
newimageview.isUserInteractionEnabled = true
let tap = UITapGestureRecognizer(target: self, action: #selector(self.dismissaction))
newimageview.addGestureRecognizer(tap)
self.view.addSubview(newimageview)
}
let photogallery = UIAlertAction(title:"photos",style: UIAlertActionStyle.default) { (action) in
if (UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.savedPhotosAlbum))
{
self.imagepicker.delegate = self
self.imagepicker.sourceType = UIImagePickerControllerSourceType.savedPhotosAlbum
self.imagepicker.allowsEditing = true
self.present(self.imagepicker , animated: true, completion: nil)
self.present(self.imagepicker,animated:true,completion:nil)
}
}
let camera = UIAlertAction(title:"camera",style: UIAlertActionStyle.default) { (action) in
if (UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.camera))
{
self.imagepicker.delegate = self
self.imagepicker.sourceType = UIImagePickerControllerSourceType.camera
self.imagepicker.allowsEditing = true
self.present(self.imagepicker, animated: true, completion: nil)
}
}
myactionsheet.addAction(viewpic)
myactionsheet.addAction(photogallery)
myactionsheet.addAction(camera)
myactionsheet.addAction(UIAlertAction(title: "cancel", style: UIAlertActionStyle.cancel, handler: nil ))
self.present(myactionsheet, animated: true, completion: nil)
}
func dismissaction(sender:UITapGestureRecognizer)
{
sender.view?.removeFromSuperview()
}
func imagepickercontroller( picker : UIImagePickerController, didfinishpickingimage
image:UIImage, editinginfo: [String : AnyObject]?) {
setpc(imageView: self.pc, imageToset: image)
if let imageData: Data = UIImagePNGRepresentation(self.pc.image!)! {
let picref = datbasestorage.child("users/\(self.loggedinuser!.uid)/pc")
let uploadtask = picref.put(imageData,metadata: nil)
{ metadata,error in
if (error == nil)
{
let downloadurl = metadata!.downloadURL()
self.databaseref.child("users").child(self.loggedinuser!.uid).child("pc").setValue(downloadurl!.absoluteString)
}
else
{
print(error?.localizedDescription)
}
}
}
self.dismiss(animated: true, completion: nil)
}
}

Profile page swift 3 errors

This is the code that I have created for my profile page but it has some mistakes that i would like to adjust.
import UIKit
import FirebaseStorage
import FirebaseDatabase
import FirebaseAuth
import Firebase
class ProfileClass: UIViewController, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
#IBOutlet weak var userImagePicker: RoundButton!
#IBOutlet weak var ProfilePicture: RoundImage!
#IBOutlet weak var usernameField: UITextField!
#IBOutlet weak var imageLoader: UIActivityIndicatorView!
var loggedInUser = AnyObject?()
var databaseRef = FIRDatabase.database().reference()
var storageRef = FIRStorage.storage().reference()
var imagePicker = UIImagePickerController()
override func viewDidLoad() {
super.viewDidLoad()
self.loggedInUser = FIRAuth.auth()?.currentUser
self.databaseRef.child("user_profile").child(self.loggedInUser!.uid).observeSingleEvent(of: FIRDataEventType(.Value) { (snapshot:FIRDataSnapshot) in
if(snapshot.value!["usernameField"] !== nil) {
self.usernameField.text = snapshot.value!["usernameField"] as? String
}
if(snapshot.value!["profile_pic"] !== nil) {
let databaseProfilePic = snapshot.value!["profile_pic"]
as! String
let data = NSData(contentsOfURL: NSURL(string: databaseProfilePic)!)
self.setProfilePicture(self.ProfilePicture,imageToSet:UIImage(data:data!)!)
}
}
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
#IBAction func logoutTapped(_ sender: Any) {
let firebaseAuth = FIRAuth.auth()
do {
try firebaseAuth?.signOut()
} catch let signOutError as NSError {
print ("Error signing out: %#", signOutError)
}
self.performSegue(withIdentifier: "goToLogin", sender: self)
}
#IBAction func TapProfileButton(_ sender: RoundButton) {
let myActionShett = UIAlertController(title:"Profile Picture",message:"Select",preferredStyle: UIAlertControllerStyle.actionSheet)
let viewPicture = UIAlertAction(title: "View Picture", style: UIAlertActionStyle.default) { (action) in
let imageView = sender.view as! RoundImage
let newImageView = RoundImage(image: imageView.image)
newImageView.frame = self.view.frame
newImageView.backgroundColor = UIColor.blackColor()
newImageView.contentMode = .scaleAspectFit
newImageView.userInteractionEnabled = true
let tap = UITapGestureRecognizer(target:self,action:#selector(self.dismissFullScreenImage))
newImageView.addGestureRecognizer(tap)
self.view.addSubview(newImageView)
}
let photoGallery = UIAlertAction(title: "Photos", style: UIAlertActionStyle.default) { (action) in
if UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.savedPhotosAlbum)
{
self.imagePicker.delegate = self
self.imagePicker.sourceType = UIImagePickerControllerSourceType.savedPhotosAlbum
self.imagePicker.allowsEditing = true
self.present(self.imagePicker, animated: true, completion: nil)
}
}
let camera = UIAlertAction(title: "Camera", style: UIAlertActionStyle.default)
{ (action) in
if UIImagePickerController.isSourceTypeAvailable(UIImagePickerControllerSourceType.camera)
{
self.imagePicker.delegate = self
self.imagePicker.sourceType = UIImagePickerControllerSourceType.camera
self.imagePicker.allowsEditing = true
self.present(self.imagePicker, animated: true, completion: nil)
}
}
myActionShett.addAction(viewPicture)
myActionShett.addAction(photoGallery)
myActionShett.addAction(camera)
myActionShett.addAction(UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil))
self.present(myActionShett, animated: true, completion: nil)
}
func dismissFullScreenImage(sender:UITapGestureRecognizer)
{
sender.view?.removeFromSuperview()
}
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
self.imageLoader.stopAnimating()
setProfilePicture(self.ProfilePicture,imageToSet: image)
if let imageData: NSData = UIImagePNGRepresentation(self.ProfilePicture, image!)!
{
let profilePicStorageRef = storageRef.child("user_profiles/\(self.loggedInUser!.uid)/profile_pic")
let uploadTask = profilePicStorageRef.putData(imageData, metadata: nil)
{metadata,error in
if(error == nil)
{
let downloadUrl = metadata!.downloadUrl()
self.databaseRef.child("user_profile").child(self.loggedInUser!.uid).child("profile_pic").setValue(downloadUrl!.absoluteString)
}
else
{
print(error?.localizedDescription)
}
self.imageLoader.stopAnimating()
}
}
self.dismiss(animated: true, completion: nil)
}
}
You have to give proper type. You can not initialize object of type AnyObject. and Obviously with not using AnyObject?.

Resources