How to Show only one Component when UIPickerView have Multiple Components? - ios

I have two Componenets in UIPickerView. One is for country and another is for city. I want to show only one component when clicked on Country Button and another one will show when clicked on the City Button.
#IBOutlet weak var myPicker: UIPickerView!
var pickerData = [["India", "Pakistan", "Bangladesh", "USA", "Afganistan", "Russia", "Nepal", "Bhutan"], ["Chandigarh", "Punjab", "Ludhiana", "Amritsar", "Shimal", "Una"]]
override func viewDidLoad() {
super.viewDidLoad()
myPicker.isHidden = true
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return pickerData.count
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData[component].count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return pickerData[component][row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
// print(pickerData[row])
showCountry.text = pickerData[component][row]
}
#IBAction func showCountry(_ sender: Any) {
myPicker.isHidden = false
}
For Now when I click on country, it shows both components but I just want to show one componenet in pickerview.

you can do it by just handling it in conditions as requirement
import UIKit
class ViewController: UIViewController,UIPickerViewDelegate,UIPickerViewDataSource {
var pickerData = [["India", "Pakistan", "Bangladesh", "USA", "Afganistan", "Russia", "Nepal", "Bhutan"], ["Chandigarh", "Punjab", "Ludhiana", "Amritsar", "Shimal", "Una"]]
#IBOutlet weak var myPicker: UIPickerView!
var check : Int = 0
override func viewDidLoad() {
super.viewDidLoad()
myPicker.isHidden = true
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
if check == 1 {
return 1
}
else
{
return 1
}
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData[component].count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if check == 1 {
return pickerData[0][row]
}
else
{
return pickerData[1][row]
}
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
// print(pickerData[row])
// showCountry.text = pickerData[component][row]
}
#IBAction func showCountry(_ sender: Any) {
check = 1
myPicker.reloadAllComponents()
myPicker.isHidden = false
}
#IBAction func showcity(_ sender: Any) {
check = 2
myPicker.reloadAllComponents()
myPicker.isHidden = false
}
}
Hope this will help you

If you want select one picker and country and city
numberOfComponents
should be 2
or if you want select one picker and country than select again to city
numberOfComponent
should be 1
but careful this state
//e.g
#IBOutlet weak var myPicker: UIPickerView!
var pickerData = [["India", "Pakistan", "Bangladesh", "USA", "Afganistan", "Russia", "Nepal", "Bhutan"], ["Chandigarh", "Punjab", "Ludhiana", "Amritsar", "Shimal", "Una"]]
var isSelectingCountry = true
var selectedCountry: String!
var selectedCity: String!
override func viewDidLoad() {
super.viewDidLoad()
myPicker.isHidden = true
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData[isSelectingCountry ? 0 : 1].count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
let index = isSelectingCountry ? 0 : 1
return pickerData[index][row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
// print(pickerData[row])
//showCountry.text = pickerData[component][row]
if isSelectingCountry {
isSelectingCountry = false
selectedCountry = pickerData[0][row]
} else {
selectedCity = pickerData[1][row]
}
}
#IBAction func showCountry(_ sender: Any) {
// if you want reset picker for start with country uncomment below line
//isSelectingCountry = true
myPicker.isHidden = false
}
and you can use selectedCity and selectedCountry

Related

Multiple pickerviews in single viewController

Is it possible to have a single pickerView in swift which changes its value based on the button pressed. I could not figure out a way to implement more than one parameter through pickerView in a single ViewController. An alternative solution like a dropdown menu is fine too. Example/functional code would be great if provided. This is for a quiz app which would take multiple parameters.
class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
#IBOutlet weak var pickerView: UIPickerView!
#IBOutlet weak var selectionBtn: UIButton!
let animals = ["Lion", "Dog", "Monkey", "Cat", "Bat"]
override func viewDidLoad() {
pickerView.isHidden = true
pickerView.delegate = self
pickerView.dataSource = self
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
}
#IBAction func selectPressed(_ sender: UIButton) {
if pickerView.isHidden {
pickerView.isHidden = false
}
}
public func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return animals.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return animals[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
selectionBtn.setTitle(animals[row], for: .normal)
pickerView.isHidden = true
}
}
Yes by having more than 1 data source
let animals1 = ["Lion", "Dog", "Monkey", "Cat", "Bat"]
let animals2 = ["Lion", "Dog", "Monkey", "Cat", "Bat"]
var mainData = [String]()
public func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return mainData.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, fo rComponent component: Int) -> String? {
return mainData[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
selectionBtn.setTitle(mainData[row], for: .normal)
pickerView.isHidden = true
}
assign mainData to say animal1
and reload
pickerView.reloadAllComponents()
Keep a separate array and put your array into it according to your logic. Use that array in pickerview. Try This:
let animals = ["Lion", "Dog", "Monkey", "Cat", "Bat"]
let secondAnimals = ["Lion1", "Dog1", "Monkey1", "Cat1", "Bat1"]
let pickerArray = [String]()
#IBAction func selectPressed(_ sender: UIButton) {
pickerArray = animals //change it according to your logic
pickerView.reloadAllComponents()
pickerView.isHidden = !pickerView.isHidden
}
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerArray.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return pickerArray[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
selectionBtn.setTitle(pickerArray[row], for: .normal)
pickerView.isHidden = true
}
You can have two arrays to populate the picker like this
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int{
if numb == 1
{
return firstArray.count
}
else
return secondArray.count
}
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if numb == 1
{
return firstArr[row]
}
else
{
return secondArr[row]
}
}
Whenever you have to change the data source for datepicker, make sure after that you are calling method
picker.reloadAllComponents()
Take flag and use appropriate data source.
let say you added 2 PickerView to your View
- set the 1st picker´s tag as 1 & 2 for the 2nd picker under the Attributes Inspector
- CTRL + drag from each picker to the top yellow View Controller icon and choose dataSource.Repeate the same choosing delegate
- repeate the above for the other picker too
- add pickerview & pickerviewdelegation to your ViewController class:
class ViewController: UIViewController,UIPickerViewDataSource,UIPickerViewDelegate {
in your ViewController class, create empty arrays for the pickers:
var picker1Options = []
var picker2Options = []
on viewDidLoad() method, populate the arrays with your content:
picker1Options = ["p1 1","p1 2","p1 3","p1 4","p1 5"]
picker2Options = ["p2 1","p2 2","p2 3","p2 4","p2 5"]
implement the delegate & pickerview methods:
func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
if (pickerView.tag == 1){
return picker1Options.count
}else{
return picker2Options.count
}
}
func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String! {
if (pickerView.tag == 1){
return "\(picker1Options[row])"
}else{
return "\(picker2Options[row])"
}
}
Hope this will help.
let arrAny : [String] = [String]()
button action:
#IBAction func btn2Pressed(_ sender: UIButton) {
arrAny = ["Lion1", "Dog1", "Monkey1", "Cat1", "Bat1"]
if pickerView.isHidden {
pickerView.isHidden = false
}
}
#IBAction func btn1Pressed(_ sender: UIButton) {
arrAny = ["Lion", "Dog", "Monkey", "Cat", "Bat"]
if pickerView.isHidden {
pickerView.isHidden = false
}
}
pickerView delegate:
public func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return arrAny.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return arrAny[row]
}

Invalid redeclaration of 'numberOfComponents(in:)' error

Here's my code. I would say the steps I have taken, but they just don't make sense and I'd get made fun of, I am very new to Swift and Xcode. But how do I declare a group of components? I thought I spaced them enough, I have honestly searched for guides, but no one really focuses on dropdowns and variables within the dropdowns.
import UIKit
class SecondViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {
#IBOutlet weak var backBTN: UIButton!
#IBOutlet weak var label: UILabel!
#IBOutlet weak var labelTwo: UILabel!
#IBOutlet weak var pickerView: UIPickerView!
#IBOutlet weak var pickerviewTwo: UIPickerView!
var pickerData = ["X", "Y"]
var pickerdataTwo = ["R","D","C"]
override func viewDidLoad() {
super.viewDidLoad()
pickerView.delegate = self
pickerView.dataSource = self
pickerviewTwo.delegate = self
pickerviewTwo.dataSource = self
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return pickerData[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
label.text = pickerData[row]
}
func numberOfComponents(in pickerviewTwo: UIPickerView) -> Int {
return 1
}
func pickerviewTwo(_ pickerviewTwo: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerdataTwo.count
}
func pickerviewTwo(_ pickerviewTwo: UIPickerView, titleForRow row: Int, forComponent
component: Int) -> String? {
return pickerdataTwo[row]
}
func pickerviewTwo(_ pickerviewTwo: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
labelTwo.text = pickerdataTwo[row]
}
}
Your picker view code is wrong. First, I would recommend changing the names of them from pickerView and pickerViewTwo to something more descriptive.
The required functions for picker view can't be used multiple times, thus you are getting the error. The proper way to do it is:
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent
component: Int) -> String? {
//After renaming the first pickerView to topPickerView
if pickerView == topPickerView {
return pickerData[row]
}
else {
return pickerDataTwo[row]
}
}
There should be an if-else in each of the required functions, with the if statement saying that if pickerView == oneOfThePickerViewsName, with the if else statement. Whats happening is when the pickers are being set up, it checks which picker it is and uses the code for that.
Here is how the rest should be formatted:
//pickerView has been renamed to topPickerView
func numberOfComponents(in pickerView: UIPickerView) -> Int {
//You wouldn't need to do this here as its the same for both of them.
//
if pickerView == topPickerView
{
return 1
}
else
{
return 1
}
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
if pickerView == topPickerView
{
return pickerData.count
}
else
{
return pickerdataTwo.count
// should actually be formatted pickerDataTwo because of camelCase.
}
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent
component: Int) -> String? {
if pickerView == topPickerView
{
return pickerData[row]
}
else
{
return pickerdataTwo[row]
// should actually be formatted pickerDataTwo because of camelCase.
}
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent
component: Int) {
if pickerView == topPickerView
{
label.text = pickerData[row]
}
else
{
labelTwo.text = pickerdataTwo[row]
// should actually be formatted pickerDataTwo because of camelCase.
}
}

How to set title for row in PickerView in Swift 3?

I need to give title for rows according to array but I don't know how to do this. I'm new to iOS.
class ViewController: UIViewController , UIPickerViewDelegate, UIPickerViewDataSource{
#IBOutlet weak var pickerView: UIPickerView!
#IBOutlet weak var label: UILabel!
var names: Array<String>?
var department: Array<String>?
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
names = ["Vineeta", "Shubham" ,"Anand", "Vivek", "Akshay", "Harshit", "Vikas", "Prasoon", "Sunil"]
department = ["iOS","Angular", ".Net", "iOS","iOS", ".Net", "Android","Android", "Angular"]
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 2
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return 9
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
if component == 0 {
[names o]
}
}
}
don't forget UIPickerViewDelegate,UIPickerViewDataSource
#IBOutlet weak var picker: UIPickerView!
override func viewDidLoad() {
super.viewDidLoad()
pickerData = ["X","Y"]
picker.delegate = self
picker.dataSource = self
}
func numberOfComponents(in pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData.count
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return pickerData[row]
}
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
let selectedText = pickerData[row]
}
Use this code -
func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int
{
if component == 0
{
return names?.count
}
else
{
return department?.count
}
}
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String?
{
if component == 0
{
return names?[row]
}
else
{
return department?[row]
}
}

Acces to viewController from a pickerView

On a sight I have a PickerView and a button. Depending on the choice in the pickerview (I have 4 lines) I would like clicking on a button to go on a specific view. Now, whatever my choice is, I'm always on the same view (saline). Below is my code of the controller. If anyone can help me understand my mistake?
import UIKit
class SommaireGeneralViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {
#IBOutlet weak var picker: UIPickerView!
var PlacementAnswer = 0
var liste = ["Sommaire général", "Région Est", "Région Ouest", "Région Sud", "Région Nord"]
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
self.picker.delegate = self
self.picker.dataSource = self
}
func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return liste[row]
}
func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return liste.count
}
func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(pickerView: UIPickerView, attributedTitleForRow row: Int, forComponent component: Int) -> NSAttributedString? {
let titleData = liste[row]
let myTitle = NSAttributedString(string: titleData, attributes: [NSFontAttributeName:UIFont(name: "Georgia", size: 10.0)!,NSForegroundColorAttributeName:UIColor.whiteColor()])
return myTitle
}
#IBAction func Voir(sender: AnyObject) {
if (PlacementAnswer == 0) {
self.performSegueWithIdentifier("Saline", sender: self)
} else if (PlacementAnswer == 1){
self.performSegueWithIdentifier("1", sender: self)
return
}
func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
PlacementAnswer = row
}
func prepareForSegue(id: UIStoryboardSegue, sender: AnyObject?) {
if "Saline" == id.identifier {
}
else if "1" == id.identifier {
}
}
}
Hello, finally it's working, I put the code that can be used for others.
Cheers and thank you again for the info
import UIKit
class SommaireGeneralViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {
#IBOutlet weak var picker: UIPickerView!
enum ActionSheetTag: Int {
case ActionSheet0
case ActionSheet1
}
var PlacementAnswer = Int()
let liste = ["Sommaire général", "Région Est", "Région Ouest", "Région Sud", "Région Nord"]
override func viewDidLoad() {
super.viewDidLoad()
self.picker.delegate = self
self.picker.dataSource = self
}
func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return liste[row]
}
func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return liste.count
}
func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(pickerView: UIPickerView, attributedTitleForRow row: Int, forComponent component: Int) -> NSAttributedString? {
let titleData = liste[row]
let myTitle = NSAttributedString(string: titleData, attributes: [NSFontAttributeName:UIFont(name: "Georgia", size: 10.0)!,NSForegroundColorAttributeName:UIColor.whiteColor()])
return myTitle
}
#IBAction func Voir(sender: AnyObject) {
if (PlacementAnswer == 0) {
self.performSegueWithIdentifier("Saline", sender: self)
} else if (PlacementAnswer == 1){
self.performSegueWithIdentifier("Autre", sender: self)
}
}
func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if let tag = ActionSheetTag(rawValue: row) {
switch tag {
case .ActionSheet0:
PlacementAnswer = 0
case .ActionSheet1:
PlacementAnswer = 1
}
}
}
}
You tried tag and enum? If your answer is no, try this and return the output to me.
enum ActionSheetTag: Int {
case ActionSheet1
case ActionSheet2
}
.
.
.
func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
if let tag = ActionSheetTag(rawValue: pickerView.tag) {
switch tag {
case .ActionSheet1:
PlacementAnswer = 0
case .ActionSheet2:
PlacementAnswer = 1
}
}
}
Hope it helps.

UIPickerView Pop-Up

What is wrong with the code that I have produced? I am trying to get a UIPickerView to pop up when the textfield is tapped then go away once a selection is made. The textfield is supposed to present what was selected after.
import UIKit
class CreateAJob_View_ControllerViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource, UITextFieldDelegate {
#IBOutlet var pickerTextField: UITextField!
#IBOutlet var picker: UIPickerView!
var pickerData:[String] = [String]()
override func viewDidLoad() {
super.viewDidLoad()
picker.hidden = true;
pickerTextField.text = "A4";
self.pickerTextField.delegate = self
self.picker.delegate = self
self.picker.dataSource = self
pickerData = ["A0","A1","A2","A3","A4","A5","A6","A7","A8","A9","A10"]
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
return 1
}
func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
return pickerData.count
}
func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
return pickerData[row]
}
func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
pickerTextField.text = pickerData[row];
picker.hidden = true;
}
func textFieldShouldBeginEditing(textField: UITextField) -> Bool {
pickerTextField.hidden = false
return false
}
}
You need to change these two methods this way:
func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
self.pickerTextField.hidden = false;
self.picker.hidden = true;
self.pickerTextField.text = pickerData[row];
}
func textFieldShouldBeginEditing(textField: UITextField) -> Bool {
self.pickerTextField.hidden = true
self.picker.hidden = false;
return false
}

Resources