键盘显示时 SwiftUI 背景图像移动
SwiftUI background image moves when keyboard shows
我有一个图像背景,它应该在键盘显示时留在原处,但它却与屏幕上的所有内容一起向上移动。我看到有人推荐使用 ignoresSafeArea(.keyboard)
,而这个问题 ,但都不适合我。这是我超级简化的代码示例。请记住,尽管背景应保持不变,但内容本身仍应像往常一样避开键盘。
struct ProfileAbout: View {
@State var text: String = ""
var body: some View {
VStack {
TextField("write something", text: $text)
Spacer()
Button("SomeButton") {}
}
.background(
Image("BackgroundName")
.resizable()
.aspectRatio(contentMode: .fill)
.ignoresSafeArea(.keyboard)
)
}
}
这是一个可能的救赎:
import SwiftUI
struct ContentView: View {
@Environment(\.verticalSizeClass) var verticalSizeClass
@State var valueOfTextField: String = String()
var body: some View {
GeometryReader { proxy in
Image("Your Image name here").resizable().scaledToFill().ignoresSafeArea()
ZStack {
if verticalSizeClass == UserInterfaceSizeClass.regular { TextFieldSomeView.ignoresSafeArea(.keyboard) }
else { TextFieldSomeView }
VStack {
Spacer()
Button(action: { print("OK!") }, label: { Text("OK").padding(.horizontal, 80.0).padding(.vertical, 5.0).background(Color.yellow).cornerRadius(5.0) }).padding()
}
}
.position(x: proxy.size.width/2, y: proxy.size.height/2)
}
}
var TextFieldSomeView: some View {
return VStack {
Spacer()
TextField("write something", text: $valueOfTextField).padding(5.0).background(Color.yellow).cornerRadius(5.0).padding()
Spacer()
}
}
}
你可以使用 GeometryReader
获取父视图大小
import SwiftUI
import Combine
struct KeyboardAdaptive: ViewModifier {
@State private var keyboardHeight: CGFloat = 0
func body(content: Content) -> some View {
GeometryReader { geometry in
content
.padding(.bottom, keyboardHeight)
.onReceive(Publishers.keyboardHeight) {
self.keyboardHeight = [=10=]
}
}
}
}
extension Publishers {
static var keyboardHeight: AnyPublisher<CGFloat, Never> {
let willShow = NotificationCenter.default.publisher(for: UIApplication.keyboardWillShowNotification)
.map { [=10=].keyboardHeight }
let willHide = NotificationCenter.default.publisher(for: UIApplication.keyboardWillHideNotification)
.map { _ in CGFloat(0) }
return MergeMany(willShow, willHide)
.eraseToAnyPublisher()
}
}
extension View {
func keyboardAdaptive() -> some View {
ModifiedContent(content: self, modifier: KeyboardAdaptive())
}
}
struct ProfileAbout: View {
@State var text: String = ""
var body: some View {
VStack {
TextField("write something", text: $text)
Spacer()
Button("SomeButton") {}
}
.background(
Image("BackgroundName")
.resizable()
.aspectRatio(contentMode: .fill)
.ignoresSafeArea(.keyboard)
)
.keyboardAdaptive()
}
}
我有一个图像背景,它应该在键盘显示时留在原处,但它却与屏幕上的所有内容一起向上移动。我看到有人推荐使用 ignoresSafeArea(.keyboard)
,而这个问题
struct ProfileAbout: View {
@State var text: String = ""
var body: some View {
VStack {
TextField("write something", text: $text)
Spacer()
Button("SomeButton") {}
}
.background(
Image("BackgroundName")
.resizable()
.aspectRatio(contentMode: .fill)
.ignoresSafeArea(.keyboard)
)
}
}
这是一个可能的救赎:
import SwiftUI
struct ContentView: View {
@Environment(\.verticalSizeClass) var verticalSizeClass
@State var valueOfTextField: String = String()
var body: some View {
GeometryReader { proxy in
Image("Your Image name here").resizable().scaledToFill().ignoresSafeArea()
ZStack {
if verticalSizeClass == UserInterfaceSizeClass.regular { TextFieldSomeView.ignoresSafeArea(.keyboard) }
else { TextFieldSomeView }
VStack {
Spacer()
Button(action: { print("OK!") }, label: { Text("OK").padding(.horizontal, 80.0).padding(.vertical, 5.0).background(Color.yellow).cornerRadius(5.0) }).padding()
}
}
.position(x: proxy.size.width/2, y: proxy.size.height/2)
}
}
var TextFieldSomeView: some View {
return VStack {
Spacer()
TextField("write something", text: $valueOfTextField).padding(5.0).background(Color.yellow).cornerRadius(5.0).padding()
Spacer()
}
}
}
你可以使用 GeometryReader
获取父视图大小
import SwiftUI
import Combine
struct KeyboardAdaptive: ViewModifier {
@State private var keyboardHeight: CGFloat = 0
func body(content: Content) -> some View {
GeometryReader { geometry in
content
.padding(.bottom, keyboardHeight)
.onReceive(Publishers.keyboardHeight) {
self.keyboardHeight = [=10=]
}
}
}
}
extension Publishers {
static var keyboardHeight: AnyPublisher<CGFloat, Never> {
let willShow = NotificationCenter.default.publisher(for: UIApplication.keyboardWillShowNotification)
.map { [=10=].keyboardHeight }
let willHide = NotificationCenter.default.publisher(for: UIApplication.keyboardWillHideNotification)
.map { _ in CGFloat(0) }
return MergeMany(willShow, willHide)
.eraseToAnyPublisher()
}
}
extension View {
func keyboardAdaptive() -> some View {
ModifiedContent(content: self, modifier: KeyboardAdaptive())
}
}
struct ProfileAbout: View {
@State var text: String = ""
var body: some View {
VStack {
TextField("write something", text: $text)
Spacer()
Button("SomeButton") {}
}
.background(
Image("BackgroundName")
.resizable()
.aspectRatio(contentMode: .fill)
.ignoresSafeArea(.keyboard)
)
.keyboardAdaptive()
}
}