xmartlabs / Eureka

Elegant iOS form builder in Swift
https://eurekacommunity.github.io
MIT License
11.77k stars 1.33k forks source link

How to launch an action from a value selected in Actionsheet row #32

Closed everestman27 closed 8 years ago

everestman27 commented 8 years ago

I have the following requirement and trying to see how best to achieve it using Eureka Form..any inputs would be great. 1) User clicks on the "Select File from" row. The value of the row is thumbnail of a file selected with a UILabel appended to it describing the file name

2) Selecting the row launches an Actionsheet with various file selection options "example: select from camera roll, select from Google Drive, etc.".

3) Selecting a specific action leads to a custom logic to retrieve the file from the data source and download into the App and create a low-res image of the file.

4) Once action is completed, the actionsheet is dismissed and the Eureka Form Row updated.

I tried the following but it didn't work: a) Actionsheet Row - however, don't see an custom call back that is called on selecting a specific actionsheet option value that can be in turn used to present a viewcontroller b) creating an new actionsheet in onCellSelection method call on a row - however that didn't pop up any actionsheet on clicking the cell.

Thanks in advance

clooth commented 8 years ago

There is the FormDelegate protocol that has a func rowValueHasBeenChanged(row: BaseRow, oldValue: Any, newValue: Any) method.

Maybe try that?

AtharvaVaidya commented 8 years ago

Use a labelRow and use the cellSelection function to bring up an actionSheet and then you can mention what you want to do in the completion callback of the UIAlertAction.

everestman27 commented 8 years ago

I tried labelRow with cellSelection function that creates an actionsheet (using UIAlertcontroller) and get the following error "...Attempting to load the view of a view controller while it is deallocating is not allowed and may result in undefined behavior .."

AtharvaVaidya commented 8 years ago

Here's my code and it doesn't give me any error:

.onCellSelection{(cell, row) in

                let alert = UIAlertController(title: "Photo", message: "", preferredStyle: UIAlertControllerStyle.ActionSheet)
                let takePhoto = UIAlertAction(title: "Take a photo", style: UIAlertActionStyle.Default, handler: {(alert: UIAlertAction!) in

                        if UIImagePickerController.isSourceTypeAvailable(.Camera)
                        {
                            let picker = UIImagePickerController()
                            picker.sourceType = .Camera
                            picker.delegate = self
                            picker.allowsEditing = false
                            self.presentViewController(picker, animated: true, completion: nil)
                        }

                    })

                let chooseAPhoto = UIAlertAction(title: "Photo Library", style: UIAlertActionStyle.Default, handler: {(alert: UIAlertAction!) in

                    if UIImagePickerController.isSourceTypeAvailable(.SavedPhotosAlbum)
                    {
                        let picker = UIImagePickerController()
                        picker.sourceType = UIImagePickerControllerSourceType.SavedPhotosAlbum
                        picker.delegate = self
                        picker.allowsEditing = false
                        self.presentViewController(picker, animated: true, completion: nil)
                    }

                })

                let cancel = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.Cancel, handler: nil)

                alert.addAction(takePhoto)
                alert.addAction(chooseAPhoto)
                alert.addAction(cancel)
                self.presentViewController(alert, animated: true, completion: nil)
            }
everestman27 commented 8 years ago

thank you @AtharvaVaidya for the sample code. It works..I realized I forgot to add self.presentViewController(alertviewcontroller...) line and hence the error.

In terms of display of the information back in the Row cell, the scenario I have is when there is no data, display just the LabelRow ("Select File From.."), but if there is data, display the a Row as "ImageView representing thumbnail of selected file + UILabel". What would be the best way to implement this conditional Row value display.

everestman27 commented 8 years ago

@clooth I tried your suggestion of overriding the row value has changed method..however, that results in "Declaration from extension can't be overridden yet" error.

func rowValueHasBeenChanged(row: BaseRow, oldValue: Any, newValue: Any)

AtharvaVaidya commented 8 years ago

Get the row you want to hide by

self.form.rowByTag("Your row's tag")

Then

if (data == nil) //Check if there is data
{
 row.hidden = true
}
mtnbarreto commented 8 years ago

@clooth Could you achieve it?

rowValueHasBeenChanged has been moved to FormController so you can override it now. Alternatively you can use onChange row callback to do something whenever a row value changes.

The approach using a LabelRow is ok, also the approach using the ActionSheetRow along with onChange callback. However will still be hard to show the label and the image on the right of the cell and I strongly recommend you to create a custom row in this case.

Regards