Multiple Pickerviews - swift

I want to build a viewcontroller which contains three pickerviews (which has three same options). I am having problems on how to show one specific row to the label. My code:
I changed other parts still getting errors. Edited variables' first letters to lowercase.
#IBOutlet weak var picker1: UIPickerView!
#IBOutlet weak var picker2: UIPickerView!
#IBOutlet weak var picker3: UIPickerView!
var Array = ["Shake","Swipe Up","Swipe Right"]
#IBOutlet weak var label1: UILabel!
#IBOutlet weak var label2: UILabel!
#IBOutlet weak var label3: UILabel!
var placementAnswer = 0
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
picker1.delegate = self
picker1.dataSource = self
picker1.tag = 1
picker2.delegate = self
picker2.dataSource = self
picker2.tag = 2
picker3.delegate = self
picker3.dataSource = self
picker3.tag = 3
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return Array[row]
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return Array.count
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
#IBAction func save3(_ sender: AnyObject) {
}
#IBAction func save2(_ sender: AnyObject) {
}
#IBAction func save1(_ sender: AnyObject) {
if (placementAnswer == 0){
label1.text = "Shake"
}
else if(placementAnswer == 1){
label1.text = "Swipe Up"
}
else{
label1.text = "Swipe Right"
}
if (placementAnswer == 0){
label2.text = "Shake"
}
else if(placementAnswer == 1){
label2.text = "Swipe Up"
}
else{
label2.text = "Swipe Right"
}
if (placementAnswer == 0){
label3.text = "Shake"
}
else if(placementAnswer == 1){
label3.text = "Swipe Up"
}
else{
label3.text = "Swipe Right"
}
}
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
picker1.delegate = self
picker1.dataSource = self
picker1.tag = 1
picker2.delegate = self
picker2.dataSource = self
picker1.tag = 2
picker3.delegate = self
picker3.dataSource = self
picker1.tag = 3
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if pickerView.tag == 1 {
// do things for pickerview 1
label1.text = row
}
else if pickerView.tag == 2 {
// do things for pickerview 2
label2.text = row
}else {
// do for pickerview 3
}
placementAnswer = row
}
}

Differentiate by using tag
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
picker1.delegate = self
picker1.dataSource = self
picker1.tag = 1
picker2.delegate = self
picker2.dataSource = self
picker1.tag = 2
picker3.delegate = self
picker3.dataSource = self
picker1.tag = 3
}
so in your delegate methods just check the tag
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return Array[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if pickerView.tag == 1 {
// do things for pickerview 1
Label1.text = Array[row]
}
else if pickerView.tag == 2 {
// do things for pickerview 2
Label2.text = Array[row]
}else {
// do for pickerview 3
}
}

Here you are # h44f33z. How I can make each section dependent with each other? for example, if i choose "shake" for behavior name 1, it wont be available for behavior name 2 and 3. Each behavior name section will have one corresponding action. thanks!

Related

TextField return nil if never reselected

In my EditVC, I performed segue from selected CellForRow At indexPath to editVC.
In Edit VC. I want to expect results of data return as it is IF there is no modification. However, issue is if I did not rechoose/reselect the row at pickerView again, it will auto return nil.
I want to have results of if User did not modify the data/specific data only, other data will remain the same.
This is the results of print statement.
// This results is perform correctly for what I want IF I RESELECT THE PICKERVIEW IN TEXTFIELD BUT WILL AMEND MY CATEGORY DATABASE AS WELL.
currentTransaction.categoryID : Optional(9)
selectedCategory.categoryID : 9
currentTransaction.categoryTypeID : Optional(1)
selectedCategory.categoryTypeID : 1
currentTransaction.categorytype.name = Optional("EXPENSE 9")
selectedCategory.name = EXPENSE 9
// If I never reselect the pickerview in textfield
currentTransaction.categoryID : Optional(0) /* Suppose to be 9 */
selectedCategory.categoryID : 0 /* Suppose to be 9 */
currentTransaction.categoryTypeID : Optional(0) /* Suppose to be 1 */
selectedCategory.categoryTypeID : 0 /* Suppose to be 1 */
currentTransaction.categoryType.name = Optional("") /* Suppose to be EXPENSE 9 */
selectedCategory.name = /* Suppose to be EXPENSE 9 */
class EditTransactionTableViewController: UITableViewController {
let realm = try! Realm()
var selectedTransaction : Transaction? //selectedTransaction From TransactionVC's CellForRow
var categories : Results<Category>!
var currentCategories : Results<Category>!
var selectedCategory = Category()
#IBOutlet weak var amountTF: UITextField!
//PickerView for keyboard
lazy var pickerView : UIPickerView = UIPickerView()
//Segment Control
#IBOutlet weak var categorySCoutlet: UISegmentedControl!
#IBOutlet weak var categoryTF: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
amountTF.text = selectedTransaction?.amount
categoryTF.text = selectedTransaction?.categoryType?.name
categorySCoutlet.selectedSegmentIndex = selectedTransaction?.categoryType?.categoryTypeID as! Int
loadData()
setupPicker()
}
#IBAction func categoryTypeSC(_ sender: UISegmentedControl) {
guard let type = CategoryType(id: sender.selectedSegmentIndex) else {
fatalError("error")
}
currentCategories = categories.filter("categoryTypeID == %#", type.rawValue)
categoryTF.text = currentCategories.first?.name
pickerView.reloadAllComponents()
// pickerView.selectRow(0, inComponent: 0, animated: true)
}
//MARK:- Edit Transaction Btn
#IBAction func editTransactionButtonTapped(_ sender: UIButton) {
if let currentTransaction = selectedTransaction {
try! realm.write {
currentTransaction.amount = amountTF.text!
//Success modification if got RESELECT row of category BUT will return "" if never reselect and cause categories list become chosen categoryID, name , and type
currentTransaction.categoryType?.categoryID = selectedCategory.categoryID
currentTransaction.categoryType?.categoryTypeID = selectedCategory.categoryTypeID
currentTransaction.categoryType!.name = selectedCategory.name
print("currenttransaction.categoryID : \(currentTransaction.categoryType?.categoryID)")
print("selectedCategory.categoryID : \(selectedCategory.categoryID)")
print("currenttransaction.categoryTypeID : \(currentTransaction.categoryType?.categoryTypeID)")
print("selectedCategory.categoryTypeID : \(selectedCategory.categoryTypeID)")
print("currenttranasction.categorytype.name = \(currentTransaction.categoryType?.name)")
print("selectedcategory.name = \(selectedCategory.name)")
}
}
DataManager.shared.transVC.tableView.reloadData()
dismiss(animated: true, completion: nil)
}
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
super.touchesBegan(touches, with: event)
if touches.first?.view == view {
categoryTF.resignFirstResponder()
}
}
// MARK: - Data Manipulation
func loadData() {
categories = realm.objects(Category.self)
}
}
//MARK:- UIPICKERVIEW DELEGATE
extension EditTransactionTableViewController : UIPickerViewDelegate, UIPickerViewDataSource {
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return currentCategories.count
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return currentCategories[row].name
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
categoryTF.text = currentCategories[row].name
selectedCategory = currentCategories[row]
}
//MARK:- Picker Helper
func setupPicker() {
// currentCategories = categories.filter("categoryTypeID == %#", CategoryType.income.rawValue)
currentCategories = categories.filter("categoryTypeID == %#", selectedTransaction?.categoryType?.categoryTypeID)
categoryTF.inputView = pickerView
pickerView.delegate = self
pickerView.dataSource = self
categorySCoutlet.setTitle("Income", forSegmentAt: 0)
categorySCoutlet.setTitle("Expense", forSegmentAt: 1)
categorySCoutlet.addTarget(self, action: #selector(categoryTypeSC(_:)), for: .valueChanged)
}
}

Two UIPickerViews in one ViewController

Two PickerViews selectTypeOfWorkChoices & selectLocationChoices do not appear correctly.
A function dismissPickerView() seems working well. However, another function "createPickerView()" has some problems. Although UIpickerviews appear, I cannot see the choices in UIPickerViews and I don't know why.
Could anyone help me figure out what's wrong with my code, please??
#IBOutlet weak var selectTypeOfWorkChoices: UIPickerView!
#IBOutlet weak var selectLocationChoices: UIPickerView!
override func viewDidLoad() {
super.viewDidLoad()
createPickerView()
dismissPickerView()
}
var typeOfWork = ["--", "a", "b", "c"]
var location = ["--", "A", "B", "C"]
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
var countrows : Int = typeOfWork.count
if pickerView == selectLocationChoices {
countrows = self.location.count
}
return countrows
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if pickerView == selectTypeOfWorkChoices {
let titleRow = typeOfWork[row]
return titleRow
}
else if pickerView == selectLocationChoices {
let titleRow = location[row]
return titleRow
}
return ""
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if pickerView == selectTypeOfWorkChoices {
selectedPriority = typeOfWork[row]
selectTypeOfWork.text = selectedPriority
self.selectTypeOfWork.text = self.typeOfWork[row]
}
else if pickerView == selectLocationChoices {
locationSelectedPriority = location[row]
selectLocation.text = locationSelectedPriority
self.selectLocation.text = self.location[row]
}
}
var selectedPriority : String?
var locationSelectedPriority : String?
func createPickerView() {
let pickerView = UIPickerView()
pickerView.delegate = self
self.selectTypeOfWorkChoices.delegate = self
self.selectTypeOfWorkChoices.dataSource = self
self.selectLocationChoices.delegate = self
self.selectLocationChoices.dataSource = self
selectTypeOfWork.inputView = selectTypeOfWorkChoices
selectLocation.inputView = selectLocationChoices
}
#objc func dismissPickerView() {
let toolBar = UIToolbar()
toolBar.sizeToFit()
let doneButton = UIBarButtonItem(title:"Done", style: .plain, target: self, action: #selector(self.dismissKeyboard))
toolBar.setItems([doneButton], animated: false)
toolBar.isUserInteractionEnabled = true
selectTypeOfWork.inputAccessoryView = toolBar
selectLocation.inputAccessoryView = toolBar
}
#objc func dismissKeyboard () {
view.endEditing(true)
}
Reload the picker view after assigning an input view to your text field.
func createPickerView() {
let pickerView = UIPickerView()
pickerView.delegate = self
self.selectTypeOfWorkChoices.delegate = self
self.selectTypeOfWorkChoices.dataSource = self
self.selectLocationChoices.delegate = self
self.selectLocationChoices.dataSource = self
selectTypeOfWork.inputView = selectTypeOfWorkChoices
selectLocation.inputView = selectLocationChoices
//Reload Pickerview
self.selectTypeOfWorkChoices.reloadAllComponents()
self.selectLocationChoices.reloadAllComponents()
}

PickerView will reload by itself with wrong behavior Swift 4.2

My pickerView was going very well, but don't know why just get wrong behavior after rebuild the project folder.
The component[0] will reload itself but I didn't write any code for it!
Below are the codes:
DropdownListExtension.swift
extension UITextField: UITextFieldDelegate {
func loadAddressDropdownData(data: [String], zipField: UITextField!) {
self.inputView = AddressPickerView(pickerData: data, cityField: self, zipField: zipField)
// ToolBar
let toolBar = UIToolbar()
// Adding Button ToolBar
// ...Init ToolBar
self.inputAccessoryView = toolBar
}
#objc func doneClick() {
self.resignFirstResponder()
}
#objc func cancelClick() {
self.resignFirstResponder()
}
}
AddressPickerView.swift
class AddressPickerView : UIPickerView, UIPickerViewDataSource, UIPickerViewDelegate {
var pickerData : [String]!
var pickerTextField : UITextField!
var zipTextField: UITextField!
var selectedRow = 0
var selectedCity = "臺北市"
init(pickerData: [String], cityField: UITextField, zipField: UITextField) {
super.init(frame: CGRect.zero)
self.pickerData = pickerData
self.pickerTextField = cityField
self.zipTextField = zipField
self.delegate = self
self.dataSource = self
DispatchQueue.main.async{
if pickerData.count > 0 {
self.pickerTextField.text = self.pickerData[0]
} else {
self.pickerTextField.text = nil
}
}
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 2
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
if component == 0{
return pickerData.count
}else {
switch selectedCity{
//...
default:
return 0
}
}
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if component == 0{
return pickerData[row]
} else {
switch selectedCity{
//...
default:
return ""
}
}
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
print(component)
if component == 0 {
pickerTextField.text = pickerData[row]
selectedRow = row
selectedCity = pickerData[row]
pickerView.reloadComponent(1)
}else {
switch selectedCity{
case "臺北市":
zipTextField.text = taipei[row]
case "基隆市":
zipTextField.text = keelung[row]
//...
default:
return print("")
}
}
}
}
Please help me for fix it, I spent almost 3 das but still cannot figure out the problem...

How to change UIPickerViewData when I select the different UITextField?

I want to show a UIPickerView when tapping a UITextField.
And I made a 'place' UITextField with a UIPickerView.
But, I don't know how to make another UITextField with a UIPickerView.
I tried to use 'switch', but UITextField was not a value, so I couldn't do it with 'switch'.
I want to change UIPickerViewData when I select the different UITextField.
How can I do?
Here's the codes.
Thank you!
#IBOutlet weak var place: UITextField!
#IBOutlet weak var product: UITextField!
#IBOutlet weak var number: UITextField!
let placeArray = ["A", "B", "C", "D", "E", "F"]
let productArray = ["Apple", "Banana", "Grape"]
let numberArray = ["1", "2", "3", "4", "5", "6"]
var pickerView = UIPickerView()
var textField: UITextField!
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return placeArray.count
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
place.text = placeArray[row]
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return placeArray[row]
}
override func viewDidLoad() {
super.viewDidLoad()
pickerView.delegate = self
pickerView.dataSource = self
let tapGesture = UITapGestureRecognizer(target: self, action: #selector(displayPickerView))
tapGesture.numberOfTapsRequired = 1
place.addGestureRecognizer(tapGesture)
}
#objc private func displayPickerView() {
if textField == nil {
self.textField = UITextField(frame: .zero)
textField.inputView = self.pickerView
self.view.addSubview(textField)
}
textField.becomeFirstResponder()
}
Very simple way to do this.
var placePickerView = UIPickerView()
var productPickerView = UIPickerView()
var numberPickerView = UIPickerView()
override func viewDidLoad() {
super.viewDidLoad()
placePickerView.delegate = self
placePickerView.dataSource = self
place.inputView = placePickerView
productPickerView.delegate = self
productPickerView.dataSource = self
product.inputView = productPickerView
numberPickerView.delegate = self
numberPickerView.dataSource = self
number.inputView = numberPickerView
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
var numberOfRows: Int = 1
if pickerView == placePickerView {
numberOfRows = placeArray.count
} else if pickerView == productPickerView {
numberOfRows = productArray.count
} else if pickerView == numberPickerView {
numberOfRows = numberArray.count
}
return numberOfRows
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if pickerView == placePickerView {
place.text = placeArray[row]
} else if pickerView == productPickerView {
productType.text = productArray[row]
} else if pickerView == numberPickerView {
transactionType.text = numberArray[row]
}
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
var title: String?
if pickerView == placePickerView {
title = placeArray[row]
} else if pickerView == productPickerView {
title = productArray[row]
} else if pickerView == numberPickerView {
title = numberArray[row]
}
return title
}

result from multiple UIPickers

I work in a project that has two pickers and one button.
When the user chooses from the first and second pickers
he click on the button .. and show the result in the textfield ..
for example:
if he chooses from the first picker "Jed" and from the second picker "Ahmed"..
now if he clicks the button the result will be in the textfield shown "OK" ..
this is what I did so far .. I don't know why its crashing when I click on the button ..
import UIKit
class ViewController: UIViewController , UIPickerViewDelegate , UIPickerViewDataSource {
#IBOutlet weak var theResult: UITextField!
#IBOutlet weak var cityTxt2: UITextField!
#IBOutlet weak var cityTxt: UITextField!
var city = ["Jed" , "Med" , "Ruh"]
var city2 = ["ahmed" , "mohammed" , "mustafa"]
let picker = UIPickerView()
let picker2 = UIPickerView()
override func viewDidLoad() {
super.viewDidLoad()
picker.delegate = self
picker.dataSource = self
picker2.delegate = self
picker2.dataSource = self
cityTxt.inputView = picker
cityTxt2.inputView = picker2
}
public func numberOfComponents(in pickerView: UIPickerView) -> Int{
return 1
}
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int{
if (pickerView == self.picker) {
return city.count
}
else if (pickerView == self.picker2) {
return city2.count
}
return city.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if (pickerView == self.picker) {
return city[row]
}
else if (pickerView == self.picker2) {
return city2[row]
}
return city[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if (pickerView == picker) {
self.cityTxt.text = self.city[row]
}
else if (pickerView == picker2) {
self.cityTxt2.text = self.city2[row]
}
self.view.endEditing(false)
}
#IBAction func getTheResult(_ sender: Any) {
let R1 = cityTxt.text
let R2 = cityTxt2.text
if (R1 == "Jed") && (R2 == "ahmed"){
theResult.text = "OK"
}else{
theResult.text = ""
}
}
}
I think the problem is in the Button
because when I click on it .. the program will crash ..