#swift #swiftui
#swift #swiftui
Вопрос:
Итак, я много читал о SwiftUI и я в замешательстве. Я понимаю @State
, как и как он обновляет представление за кулисами. Я не могу понять, почему, когда я, подпредставление в этом примере автоматически обновляется при изменении состояния в верхнем представлении / структуре, учитывая тот факт, что в подпредставлении var subname
не является @State
свойством. Я бы ожидал, что это не будет обновляться. Может кто-нибудь просветить меня, пожалуйста?
import SwiftUI
struct SwiftUIView: View {
@State private var name = "George"
var body: some View {
VStack{
SubView(subName: name).foregroundColor(.red)
Button(action: {
self.name = "George2"
}) {
Text("Change view name")
}
}
}
}
struct SubView: View {
var subName:String
var body: some View {
Text(subName)
}
}
struct SwiftUIView_Previews: PreviewProvider {
static var previews: some View {
SwiftUIView()
}
}
PS.
Если я изменю подпредставление на
struct SubView: View {
@State var subName:String
var body: some View {
Text(subName)
}
}
он не обновляется, когда я нажимаю кнопку.
Ответ №1:
var subName: Строка
struct SubView: View {
var subName: String
// ...
}
В приведенном выше примере у вас действительно нет состояния. Когда subName
свойство в родительском представлении изменяется, целое SubView
перерисовывается и, таким образом, получает новое значение для subName
свойства. Это в основном константа (попробуйте изменить ее на let
, у вас будет тот же результат).
@State var subName: Строка
struct SubView: View {
@State var subName: String
// ...
}
Здесь у вас есть @State
свойство, которое инициализируется один раз (при первом SubView
создании) и остается неизменным даже при перерисовке представления. Всякий раз, когда вы изменяете subName
переменную в родительском представлении, в подпредставлении она остается неизменной (она может быть изменена из подпредставления, но не изменит родительскую переменную).
@Binding var subName: Строка
struct SubView: View {
@Binding var subName: String
// ...
}
Если у вас есть @Binding
свойство, вы можете напрямую обращаться к родительской @State
переменной. Всякий раз, когда он изменяется в родительском элементе, он изменяется в SubView (и наоборот) — вот почему это называется привязкой.
Ответ №2:
Всякий @State
раз, когда свойство View
изменяется, представление обновляется, что означает, что все его body
содержимое пересчитывается. Поскольку SubView
является частью body
of SwiftUIView
, всякий SwiftUIView
раз, когда обновляется, он перерисовывает его SubView
, используя новое значение своего @State name
свойства.