绑定来自ObservableObject的值

时间:2019-12-10 03:47:41

标签: swift swiftui combine

目标:

我有一个--------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-205-8a9038a015ee> in <module> ----> 1 sentence['city'] ={} 2 3 for city in city_state.city: 4 for text in sentence.sentence: 5 words = text.split() ~\Anaconda3\lib\site-packages\pandas\core\frame.py in __setitem__(self, key, value) 3117 else: 3118 # set column -> 3119 self._set_item(key, value) 3120 3121 def _setitem_slice(self, key, value): ~\Anaconda3\lib\site-packages\pandas\core\frame.py in _set_item(self, key, value) 3192 3193 self._ensure_valid_index(value) -> 3194 value = self._sanitize_column(key, value) 3195 NDFrame._set_item(self, key, value) 3196 ~\Anaconda3\lib\site-packages\pandas\core\frame.py in _sanitize_column(self, key, value, broadcast) 3389 3390 # turn me into an ndarray -> 3391 value = _sanitize_index(value, self.index, copy=False) 3392 if not isinstance(value, (np.ndarray, Index)): 3393 if isinstance(value, list) and len(value) > 0: ~\Anaconda3\lib\site-packages\pandas\core\series.py in _sanitize_index(data, index, copy) 3999 4000 if len(data) != len(index): -> 4001 raise ValueError('Length of values does not match length of ' 'index') 4002 4003 if isinstance(data, ABCIndexClass) and not copy: ValueError: Length of values does not match length of index 模型。它具有一个ObservableObject属性,我想使用这个Bool属性来初始化一个Bool变量。

问题:

  1. 如何将@Binding转换为@ObservableObject
  2. 创建@Binding是初始化@State的唯一方法吗?

注意:

  • 我知道我可以使用@Binding / @ObservedObject,并且看到它的用处,但是我不确定一个简单的按钮是否需要访问整个模型。
  • 还是我的理解不正确?

代码:

@EnvironmentObject

3 个答案:

答案 0 :(得分:2)

@Query("select a,b.bedType,b.roomCategory from RoomDetail a left outer join RoomMaster b on a.roomId = b.id where lower(a.roomNumber) interests like %:roomNumber% OR interests LIKE %:bedTypeName% OR interests LIKE %:categoryName%") Page<RoomDetail> findByRoomNumberBedTypeRoomCategor( @Param("roomNumber") String roomNumber, Pageable paging); 变量可以通过以下方式创建:

  1. Binding变量的投影值提供了@State
  2. Binding<Value>变量的投影值提供了一个包装器,您可以从中获取@ObservedObject的所有属性
  3. 第2点也适用于Binding<Subject>
  4. 您可以通过传递getter和setter的闭包来创建Binding变量,如下所示:
@EnvironmentObject

注意:

  • 正如@nayem指出的那样,您需要在视图中使用let button = SaleButton(isOn: .init(get: { car.isReadyForSale }, set: { car.isReadyForSale = $0} )) / @State / @Observed,SwiftUI才能自动检测更改。
  • 使用@EnvironmentObject前缀可以方便地访问预测值。

答案 1 :(得分:1)

struct ContentView: View {
    @EnvironmentObject var car: Car

    var body: some View {
        SaleButton(isOn: self.$car.isReadyForSale)
    }
}

class Car: ObservableObject {
    @Published var isReadyForSale = true
}

struct SaleButton: View {
    @Binding var isOn: Bool

    var body: some View {
        Button(action: {
            self.isOn.toggle()
        }) {
            Text(isOn ? "On" : "Off")
        }
    }
}

确保您的SceneDelegate中包含以下内容:

// Create the SwiftUI view that provides the window contents.
let contentView = ContentView()
    .environmentObject(Car())

答案 2 :(得分:1)

  1. 您可以选择几种方法来观察ObservableObject。如果要与对象的状态保持同步,则不可避免地要观察有状态对象的状态。在选项中,最常见的是:

    • @State
    • @ObservedObject
    • @EnvironmentObject

这取决于您,哪种适合您的用例。

  1. 不。但是您需要有一个可以在任何时间点对该对象所做的任何更改都可以观察到的对象。

实际上,您将拥有以下内容:

class Car: ObservableObject {
    @Published var isReadyForSale = true
}

struct ContentView: View {

    // It's upto you whether you want to have other type 
    // such as @State or @ObservedObject
    @EnvironmentObject var car: Car

    var body: some View {
        SaleButton(isOn: $car.isReadyForSale)
    }

}

struct SaleButton: View {
    @Binding var isOn: Bool
    var body: some View {
        Button(action: {
            self.isOn.toggle()
        }) {
            Text(isOn ? "Off" : "On")
        }
    }
}

如果您准备好使用@EnvironmentObject,将使用以下方法初始化视图:

let contentView = ContentView().environmentObject(Car())