Свойство для данных сборщика не сохранит результат цикла for

#ios #swift #uipickerview #var

#iOS #swift #uipickerview #var

Вопрос:

Я новичок в Swift и внедряю свой первый UIPickerView. Это работает нормально, если я устанавливаю pickerData непосредственно в viewDidLoad like pickerData = ["item1", "item2"] . Но мне нужно создать элементы средства выбора из базы данных Firebase.

Я могу просто создать элементы средства выбора, используя метод, который извлекает данные из базы данных и создает список. Затем я беру этот список и создаю свои элементы сборщика. Я могу распечатать массив и вижу, что массив сконструирован правильно.

Но когда массив завершен, он, по-видимому, либо снова становится пустым, и мой pickerview пуст, либо мой pickerview был настроен до того, как массив был завершен, и поэтому он пуст.

Я пробовал использовать Dispatch.main.async в нескольких местах, включая оператор завершения в моей функции извлечения данных, вокруг построения pickerData и т.д. Я также пытался поместить весь код для извлечения данных и построения pickerData массива в viewDidLoad , но это всегда одно и то же. pickerData не сохраняет массив, который я создал для него, и pickerView пуст.

Вот мой код (написанный на Xcode 10, Swift 4.2), из viewDidLoad :

 func viewDidLoad() {
    // Set up the pickerview
    ToyService.getToyList(kid: self.kid!) { (toyList) in
        self.pickerData.removeAll()

        // Go through each toy item and create a picker item from it

        for item in toyList {
            // Set up a formatter to work with the price as a string
            let formatter = NumberFormatter()
            formatter.numberStyle = .decimal
            formatter.minimumFractionDigits = 2
            formatter.maximumFractionDigits = 2

            let price = formatter.string(from: item.price!)
            let pickerItem:String = item.title!   " "   "($"   price!   ")"

            self.pickerData.append(pickerItem)

            print(self.pickerData)
        }

        print("here's the pickerdata: (self.pickerData)")
    }

    print("here's the pickerdata again: (self.pickerData)")
} // end of viewDidLoad
  

Вывод инструкций print выглядит следующим образом (обратите внимание, что последняя инструкция print печатается первой, и она печатает пустой массив!):

вот снова pickerdata: []

[«кукла ($ 0.75)»]

[«кукла ($ 0.75)», «медведь ($ 0.75)»]

[«кукла ($ 0.75)», «медведь ($ 0.75)», «грузовик ($ 0.75)»]

[«кукла ($ 0.75)», «медведь ($ 0.75)», «грузовик ($ 0.75)», «блоки ($ 0.75)»]

вот данные сборщика: [«кукла ($ 0.75)», «медведь ($ 0.75)», «грузовик ($ 0.75)», «блоки ($ 0.75)»]

Комментарии:

1. Закрытие вызывается асинхронным, поэтому последняя печать вызывается до завершения закрытия? Что такое ToyService?

2. ToyService — это метод в отдельном классе для извлечения данных из базы данных firebase. @Sh_Khan дал правильный ответ. Это было так просто, и все же я не смог найти его через два дня. Спасибо вам обоим. Это был мой первый вопрос по SO.

Ответ №1:

Вам необходимо перезагрузить pickerView внутри завершения, поскольку оно асинхронное

 for item in toyList {   
  // ......
  self.pickerData.append(pickerItem)
  print(self.pickerData)
}
self.pickerView.reloadAllComponents()
  

Комментарии:

1. Это было все. Я должен был знать, что для pickerview была перезагрузка, как для tableview. Спасибо!