Как изменить количество строк в компоненте UIPickerView на основе выбранного значения в другом компоненте - PullRequest
0 голосов
/ 09 января 2020

В приложении Google Calendar есть функция, с помощью которой вы можете настроить отправку уведомления перед событием. Если вы не знакомы с ним, оно выглядит следующим образом:

Пользовательское уведомление Календаря Google

По сути, это окно выбора, состоящее из двух компонентов, первый из которых отображает числа для пользователь выбирает, а второй показывает единицы времени («минуты», «часы», «дни», «недели»). Когда пользователь выбирает единицу времени, цифры меняются. Например, если пользователь выбирает «минуты» в качестве своей единицы, первый компонент будет показывать числа от 1 до 60. Если он выбирает «часы», первый компонент будет показывать от 1 до 24. При выборе «дни» будет отображаться от 1 до 28, и «недели» будут показывать от 1 до 4.

Я хочу разработать аналогичную функцию, но когда я запускаю свой код, я получаю ошибку «Индекс вне диапазона». Ошибка возникает в последней функции в этом фрагменте кода. В разделе отладки значение «row» равно 0. Я думаю, что ошибка связана с различиями в размерах массивов, но я не уверен. Вся помощь приветствуется!

import UIKit
class AlarmSet
{
    func timeIntervals() -> [String]
    {
        return ["minutes", "hours", "days", "weeks"]
    }

    func timeValues(time: String) -> [Int]
    {
        switch time
        {
            case "minutes":
                return Array(1...60)
            case "hours":
                return Array(1...24)
            case "days":
                return Array(1...28)
            case "weeks":
                return [1, 2, 3, 4]
            default:
                return [0]
        }
    }
}

class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate 
{

    @IBOutlet weak var addAlarm: UIButton!
    @IBOutlet weak var alarmView: UIPickerView!

    //The first component of the picker displays numbers
    var picker1Options:[Int] = []
    //The second picker displays units of time (minutes, hours, etc.)
    var picker2Options:[String] = []

    override func viewDidLoad()
    {
        super.viewDidLoad()
        alarmView.delegate = self
        alarmView.dataSource = self
        alarmView.delegate?.pickerView?(alarmView, didSelectRow: 0, inComponent: 0)
        alarmView.delegate?.pickerView?(alarmView, didSelectRow: 0, inComponent: 1)

        alarmView.isHidden = true
        let alarm = AlarmSet();

        picker2Options = alarm.timeIntervals()
        let firstValue = picker2Options[0]
        picker1Options = alarm.timeValues(time: firstValue)

        // Do any additional setup after loading the view.
    }

    func numberOfComponents(in pickerView: UIPickerView) -> Int
    {
        return 2
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int
    {
        if component == 1
        {
            return picker2Options.count
        }
        else
        {
            return picker1Options.count
        }
    }

    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String?
    {
        if component == 0 
        {
            return "\(picker1Options[row])"
        } 
        else 
        {
        return "\(picker2Options[row])"
        }
    }

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int)
    {
        if component == 1
        {
            let alarm = AlarmSet();
            //Out of range error is on this next line
            let currentValue = picker2Options[row]
            picker1Options = alarm.timeValues(time: currentValue)
            pickerView.reloadAllComponents()
        }
    }
}

1 Ответ

1 голос
/ 09 января 2020

Вы вызываете

alarmView.delegate?.pickerView?(alarmView, didSelectRow: 0, inComponent: 1

в своем viewDidLoad перед тем, как установить свой picker2Options var, поэтому он пытается получить доступ к picker2Options [0], когда picker2Options пуст. Установите массивы перед вызовом метода делегата

...