2017-03-24 34 views
0

我在从选取器返回值并将其与属性值进行比较时遇到问题。基本上,我有一个Floor实体,它具有属性“floorNumber”。从选取器中,我需要获取楼层号并将其与正确的实体对象相匹配,以便我可以开始将房间分配到各个楼层。我已经实现了代表和数据源的选择器,并查看了本网站上的其他问题,但我感到有点困惑。 请看我的执行情况,请告诉我我做错了什么。我有一个可选的“pickFloor”,即使它正在设置,它也是零,如果我尝试打开它,它会崩溃。感谢您的帮助如何从选取器中获取值(或索引)并将其与实体的属性值进行比较?

class SetNumberOfRoomsPerFloor: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource { 

    //MARK: - Properties 

    @IBOutlet private weak var floorPicker: UIPickerView! 

    @IBOutlet private weak var numberOfRoomsPerFloor: UITextField! 

    private var managedObjectContext: NSManagedObjectContext! 

    internal var floorValue: Int16? 

    private var convertedFloorValues = [String]() 

    private var storedFloors = [Floors]() 

    private var pickedFloor: Int16? 

    private var roomNumberValue: Int16 { 
     get { 
      return Int16(numberOfRoomsPerFloor.text!)! 
     } 
    } 

    override func viewDidLoad() { 
     super.viewDidLoad() 
     managedObjectContext = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext 
     floorPicker.delegate = self 
     floorPicker.dataSource = self 
     loadFloorData() 
     spinnerItems() 
    } 

    @IBAction func setTheFloors(_ sender: UIButton) { 
     if storedFloors.count > 0 { 
      if storedFloors.first?.floorNumber == pickedFloor { 
       storedFloors.first?.numberOfRooms = roomNumberValue 
       print("\(storedFloors.first?.floorNumber) + \(storedFloors.first?.numberOfRooms)") 
      } 
     } 
    } 

    @IBAction func nextStep(_ sender: UIButton) {} 

    private func loadFloorData() { 
     let floorRequest: NSFetchRequest<Floors> = Floors.fetchRequest() 
     do { 
      storedFloors = try managedObjectContext.fetch(floorRequest) 
     } catch { 
      print("could not load data from core \(error.localizedDescription)") 
     } 
    } 

    private func spinnerItems() { 
     for i in 0...floorValue! - 1 { 
      convertedFloorValues.append(String(i)) 
     } 
    } 

    public func numberOfComponents(in pickerView: UIPickerView) -> Int { 
     return 1 
    } 
    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int { 
     return convertedFloorValues.count 
    } 
    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? { 
     return convertedFloorValues[row] 
    } 

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) { 
     let selection = Int16(convertedFloorValues[row]) // not sure I have to do this part. 
     pickedFloor = selection 
    } 
} 
+0

是否有可能比Int16大?我能看到实际的错误吗?在移动pickerView之前,pickFloor可能会解开这个问题。 PickerView不会在它初始化的组件上调用didSelectRow,所以如果你想要你必须手动初始化pickFloor到pickerView启动的同一个位置。 – Sethmr

+0

在setTheFloors方法检查等同性时,pickFloor的错误是“意外发现零,而解包值”。如果我拿!那么代码块不会被执行。如果我放!然后错误。它没有被分配所选项目或索引的值。当我测试它时,我已经移动了选择器,并且发生了同样的事情。我将如何将选定的行值或索引分配给拾取的变量?谢谢 –

+0

在didSelectRow里面,在做其他行之前先打印convertedFloorValues,然后看看它说了什么。 – Sethmr

回答

1

在这个函数中,你应该就像我说的意见,didSelectRow从来没有得到,如果你不实际移动选择器视图称为为此

private func spinnerItems() { 
    for i in 0...floorValue! - 1 { 
     convertedFloorValues.append(String(i)) 
    } 
    if convertedFloorValues.count >= 1 { 
     pickedFloor = Int16(convertedFloorValues[0]) 
    } 
} 

+0

好吧,明白了。说得通。非常感谢你。您是否确认,假设用户为所有楼层设置了房间,函数实现周期是通过Floor类型的所有实体对象还是仅仅是第一个?谢谢 –

+0

我无法理解这个问题。我也很困惑,为什么你将一个字符串转换为int16。 – Sethmr

+0

对不起,我指的是setTheFloors函数。谢谢 –

1

如果pickerview然后pickedFloor用户没有选择任何内容将是nil.Try这一点。

@IBAction func setTheFloors(_ sender: UIButton) { 
    if storedFloors.count > 0 { 
     if storedFloors.first?.floorNumber == convertedFloorValues[floorPicker.selectedRow(inComponent: 0)] { 
      storedFloors.first?.numberOfRooms = roomNumberValue 
      print("\(storedFloors.first?.floorNumber) + \(storedFloors.first?.numberOfRooms)") 
     } 
    } 
} 
+0

谢谢你的回答。我也有一些困惑,也许你可以帮助我。假设用户为所有楼层设置房间,那么函数实现将循环所有Floor类型的实体对象还是第一个?谢谢 –

+0

如果我实现你的解决方案,我还需要didSelectRow函数吗? –

+0

不可以。您不需要函数和变量'pickedFloor'。 –

相关问题