UIPickerView in UIKIt

UIPickerView is a versatile component in the UIKit framework, providing a user interface element that allows users to select from a list of values. In this article, we will explore what UIPickerViews are, the various functionalities they offe

article

UIPickerView in UIKit


UIPickerView is a versatile component in the UIKit framework, providing a user interface element that allows users to select from a list of values. In this article, we will explore what UIPickerViews are, the various functionalities they offer, and provide practical code examples to demonstrate how you can implement and customize them in your iOS projects.


What is a UIPickerView?


A UIPickerView is a UIControl that provides a spinning wheel interface for selecting values from multiple sets of options. It is commonly used for choosing items from a list, such as selecting a date, time, or other options. UIPickerView is highly customizable and can be used to create complex selection interfaces in your apps.


What Can You Do with UIPickerViews?


UIPickerViews offer a range of functionalities and customization options. Here are some key things you can do with UIPickerViews:


  • Single or Multiple Components: Create pickers with one or multiple components (columns).
  • Custom Data Source: Provide custom data for the picker components.
  • Custom Appearance: Customize the appearance of the picker, including row height, font, and color.
  • Handle Value Changes: Use delegate methods to respond to user selections.
  • Dynamic Updates: Dynamically update the picker’s data based on user interactions.

Implementing UIPickerView in Swift


Let's dive into some code examples to see how you can create, customize, and work with UIPickerViews in Swift.


To create a simple UIPickerView, you need to initialize it, set its data source and delegate, and add it to your view. Here is an example:


import UIKit

class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
    let pickerData = ["Option 1", "Option 2", "Option 3"]

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .white

        // Create a UIPickerView
        let pickerView = UIPickerView()
        pickerView.dataSource = self
        pickerView.delegate = self
        pickerView.center = view.center
        pickerView.translatesAutoresizingMaskIntoConstraints = false

        // Add the picker view to the view
        view.addSubview(pickerView)

        // Set Auto Layout constraints
        NSLayoutConstraint.activate([
            pickerView.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            pickerView.centerYAnchor.constraint(equalTo: view.centerYAnchor)
        ])
    }

    // UIPickerViewDataSource Methods
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        return pickerData.count
    }

    // UIPickerViewDelegate Methods
    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
        return pickerData[row]
    }

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        print("Selected: \(pickerData[row])")
    }
}

In this example, we create a UIPickerView and set its data source and delegate to the view controller. We implement the required data source and delegate methods to provide data to the picker and handle user selections.


Creating a UIPickerView with Multiple Components


You can create a UIPickerView with multiple components (columns) by adjusting the data source methods. Here is an example:


import UIKit

class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
    let pickerData = [
        ["Option 1", "Option 2", "Option 3"],
        ["Item A", "Item B", "Item C"]
    ]

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .white

        // Create a UIPickerView
        let pickerView = UIPickerView()
        pickerView.dataSource = self
        pickerView.delegate = self
        pickerView.center = view.center
        pickerView.translatesAutoresizingMaskIntoConstraints = false

        // Add the picker view to the view
        view.addSubview(pickerView)

        // Set Auto Layout constraints
        NSLayoutConstraint.activate([
            pickerView.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            pickerView.centerYAnchor.constraint(equalTo: view.centerYAnchor)
        ])
    }

    // UIPickerViewDataSource Methods
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return pickerData.count
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        return pickerData[component].count
    }

    // UIPickerViewDelegate Methods
    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) {
        let selectedOption = pickerData[component][row]
        print("Selected: \(selectedOption) in component \(component)")
    }
}

In this example, we create a UIPickerView with two components. Each component has its own set of options, and the data source methods are adjusted to return the appropriate number of components and rows. The delegate methods handle the display and selection of data for each component.


Customizing UIPickerView Appearance


You can customize the appearance of UIPickerView to match the design of your application. Here is an example of customizing the row height and the font of the picker:


import UIKit

class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
    let pickerData = ["Option 1", "Option 2", "Option 3"]

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .white

        // Create a UIPickerView
        let pickerView = UIPickerView()
        pickerView.dataSource = self
        pickerView.delegate = self
        pickerView.center = view.center
        pickerView.translatesAutoresizingMaskIntoConstraints = false

        // Add the picker view to the view
        view.addSubview(pickerView)

        // Set Auto Layout constraints
        NSLayoutConstraint.activate([
            pickerView.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            pickerView.centerYAnchor.constraint(equalTo: view.centerYAnchor)
        ])
    }

    // UIPickerViewDataSource Methods
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        return pickerData.count
    }

    // UIPickerViewDelegate Methods
    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
        return pickerData[row]
    }

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        print("Selected: \(pickerData[row])")
    }

    func pickerView(_ pickerView: UIPickerView, rowHeightForComponent component: Int) -> CGFloat {
        return 50.0
    }

    func pickerView(_ pickerView: UIPickerView, viewForRow row: Int, forComponent component: Int, reusing view: UIView?) -> UIView {
        var label: UILabel

        if let reusedView = view as? UILabel {
            label = reusedView
        } else {
            label = UILabel()
        }

        label.text = pickerData[row]
        label.textAlignment = .center
        label.font = UIFont.systemFont(ofSize: 24)
        return label
    }
}

In this example, we customize the row height of the UIPickerView by implementing the pickerView(_:rowHeightForComponent:) method. We also customize the font and appearance of the labels in the picker by implementing the pickerView(_:viewForRow:forComponent:reusing:) method.


Dynamically Updating UIPickerView Data


You can dynamically update the data in UIPickerView based on user interactions or other events. Here is an example of updating the picker data when a button is pressed:


import UIKit

class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
    var pickerData = ["Option 1", "Option 2", "Option 3"]
    let pickerView = UIPickerView()

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .white

        // Configure the picker view
        pickerView.dataSource = self
        pickerView.delegate = self
        pickerView.center = view.center
        pickerView.translatesAutoresizingMaskIntoConstraints = false

        // Add the picker view to the view
        view.addSubview(pickerView)

        // Set Auto Layout constraints
        NSLayoutConstraint.activate([
            pickerView.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            pickerView.centerYAnchor.constraint(equalTo: view.centerYAnchor)
        ])

        // Add a button to update the picker data
        let updateButton = UIButton(type: .system)
        updateButton.setTitle("Update Data", for: .normal)
        updateButton.addTarget(self, action: #selector(updatePickerData), for: .touchUpInside)
        updateButton.translatesAutoresizingMaskIntoConstraints = false
        view.addSubview(updateButton)

        // Set Auto Layout constraints for the button
        NSLayoutConstraint.activate([
            updateButton.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            updateButton.topAnchor.constraint(equalTo: pickerView.bottomAnchor, constant: 20)
        ])
    }

    @objc func updatePickerData() {
        pickerData = ["New Option 1", "New Option 2", "New Option 3"]
        pickerView.reloadAllComponents()
    }

    // UIPickerViewDataSource Methods
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        return pickerData.count
    }

    // UIPickerViewDelegate Methods
    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
        return pickerData[row]
    }

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        print("Selected: \(pickerData[row])")
    }
}

In this example, we dynamically update the data in the UIPickerView by changing the data source array and calling reloadAllComponents(). When the button is pressed, the picker data is updated and the picker view is refreshed to reflect the new data.


Conclusion


UIPickerViews are powerful tools for providing selection interfaces in your iOS applications. In this article, we've covered the basics of what UIPickerViews are, their various functionalities, and provided practical code examples to help you implement and customize them in your own projects. From creating simple pickers to customizing their appearance and dynamically updating their data, mastering UIPickerViews is essential for building intuitive and user-friendly interfaces.


Understanding and effectively utilizing UIPickerViews can significantly enhance your app's usability and user experience. Experiment with different UIPickerView properties and techniques to create dynamic and engaging selection interfaces in your iOS applications.

instructor

Exodai INSTRUCTOR!

Johan t'Sas

Owner and Swift developer!