Skip to content

Commit

Permalink
Adding Binding DynamicProperty implementation (#31)
Browse files Browse the repository at this point in the history
* [Optimize] Update folder structure

* Update Binding DynamicProperty implementation
  • Loading branch information
Kyle-Ye authored Jan 31, 2024
1 parent 499da60 commit 72be177
Show file tree
Hide file tree
Showing 4 changed files with 52 additions and 5 deletions.
55 changes: 51 additions & 4 deletions Sources/OpenSwiftUI/DataAndStorage/ModelData/Binding/Binding.swift
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@
//
// Created by Kyle on 2023/11/5.
// Lastest Version: iOS 15.5
// Status: Blocked by DynamicProperty
// Status: Complete
// ID: 5436F2B399369BE3B016147A5F8FE9F2

/// A property wrapper type that can read and write a value owned by a source of
/// truth.
Expand Down Expand Up @@ -297,9 +298,55 @@ extension Binding {
}

extension Binding: DynamicProperty {
// TODO:
// public static func _makeProperty<V>(in buffer: inout _DynamicPropertyBuffer, container: _GraphValue<V>, fieldOffset: Int, inputs: inout _GraphInputs) {
// }
private struct ScopedLocation: Location {
var base: AnyLocation<Value>
var wasRead: Bool

init(base: AnyLocation<Value>) {
self.base = base
self.wasRead = base.wasRead
}

func get() -> Value {
base.get()
}

func set(_ value: Value, transaction: Transaction) {
base.set(value, transaction: transaction)
}

func update() -> (Value, Bool) {
base.update()
}
}

private struct Box: DynamicPropertyBox {
var location: LocationBox<ScopedLocation>?

typealias Property = Binding
func destroy() {}
func reset() {}
mutating func update(property: inout Property, phase: _GraphInputs.Phase) -> Bool {
if let location {
if location.location.base !== property.location {
self.location = LocationBox(location: ScopedLocation(base: property.location))
if location.wasRead {
self.location!.wasRead = true
}
}
} else {
location = LocationBox(location: ScopedLocation(base: property.location))
}
let (value, isUpdated) = location!.update()
property.location = location!
property._value = value
return isUpdated ? location!.wasRead : false
}
}

public static func _makeProperty<V>(in buffer: inout _DynamicPropertyBuffer, container: _GraphValue<V>, fieldOffset: Int, inputs: inout _GraphInputs) {
buffer.append(Box(), fieldOffset: fieldOffset)
}
}

// MARK: - Binding Internal API
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ protocol DynamicPropertyBox<Property>: DynamicProperty {
associatedtype Property: DynamicProperty
func destroy()
func reset()
func update(property: inout Property, phase: _GraphInputs.Phase) -> Bool
mutating func update(property: inout Property, phase: _GraphInputs.Phase) -> Bool
func getState<Value>(type: Value.Type) -> Binding<Value>?
}

Expand Down

0 comments on commit 72be177

Please sign in to comment.