Focus CW field immediately when CW enabled, move focus to main text view when return key pressed
Closes #226
This commit is contained in:
parent
de0198946e
commit
bf3f735062
|
@ -13,15 +13,19 @@ struct ComposeEmojiTextField: UIViewRepresentable {
|
||||||
|
|
||||||
@EnvironmentObject private var uiState: ComposeUIState
|
@EnvironmentObject private var uiState: ComposeUIState
|
||||||
|
|
||||||
@Binding private var text: String
|
@Binding var text: String
|
||||||
private let placeholder: String
|
let placeholder: String
|
||||||
private var didChange: ((String) -> Void)?
|
let becomeFirstResponder: Binding<Bool>?
|
||||||
private var didEndEditing: (() -> Void)?
|
let focusNextView: Binding<Bool>?
|
||||||
|
private var didChange: ((String) -> Void)? = nil
|
||||||
|
private var didEndEditing: (() -> Void)? = nil
|
||||||
private var backgroundColor: UIColor? = nil
|
private var backgroundColor: UIColor? = nil
|
||||||
|
|
||||||
init(text: Binding<String>, placeholder: String) {
|
init(text: Binding<String>, placeholder: String, becomeFirstResponder: Binding<Bool>? = nil, focusNextView: Binding<Bool>? = nil) {
|
||||||
self._text = text
|
self._text = text
|
||||||
self.placeholder = placeholder
|
self.placeholder = placeholder
|
||||||
|
self.becomeFirstResponder = becomeFirstResponder
|
||||||
|
self.focusNextView = focusNextView
|
||||||
self.didChange = nil
|
self.didChange = nil
|
||||||
self.didEndEditing = nil
|
self.didEndEditing = nil
|
||||||
}
|
}
|
||||||
|
@ -52,6 +56,7 @@ struct ComposeEmojiTextField: UIViewRepresentable {
|
||||||
|
|
||||||
view.delegate = context.coordinator
|
view.delegate = context.coordinator
|
||||||
view.addTarget(context.coordinator, action: #selector(Coordinator.didChange(_:)), for: .editingChanged)
|
view.addTarget(context.coordinator, action: #selector(Coordinator.didChange(_:)), for: .editingChanged)
|
||||||
|
view.addTarget(context.coordinator, action: #selector(Coordinator.returnKeyPressed), for: .primaryActionTriggered)
|
||||||
|
|
||||||
// otherwise when the text gets too wide it starts expanding the ComposeView
|
// otherwise when the text gets too wide it starts expanding the ComposeView
|
||||||
view.setContentCompressionResistancePriority(.defaultLow, for: .horizontal)
|
view.setContentCompressionResistancePriority(.defaultLow, for: .horizontal)
|
||||||
|
@ -71,6 +76,14 @@ struct ComposeEmojiTextField: UIViewRepresentable {
|
||||||
}
|
}
|
||||||
context.coordinator.didChange = didChange
|
context.coordinator.didChange = didChange
|
||||||
context.coordinator.didEndEditing = didEndEditing
|
context.coordinator.didEndEditing = didEndEditing
|
||||||
|
context.coordinator.focusNextView = focusNextView
|
||||||
|
|
||||||
|
if becomeFirstResponder?.wrappedValue == true {
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
uiView.becomeFirstResponder()
|
||||||
|
becomeFirstResponder?.wrappedValue = false
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func makeCoordinator() -> Coordinator {
|
func makeCoordinator() -> Coordinator {
|
||||||
|
@ -84,6 +97,7 @@ struct ComposeEmojiTextField: UIViewRepresentable {
|
||||||
unowned var uiState: ComposeUIState!
|
unowned var uiState: ComposeUIState!
|
||||||
var didChange: ((String) -> Void)?
|
var didChange: ((String) -> Void)?
|
||||||
var didEndEditing: (() -> Void)?
|
var didEndEditing: (() -> Void)?
|
||||||
|
var focusNextView: Binding<Bool>?
|
||||||
|
|
||||||
var skipSettingTextOnNextUpdate = false
|
var skipSettingTextOnNextUpdate = false
|
||||||
|
|
||||||
|
@ -96,6 +110,10 @@ struct ComposeEmojiTextField: UIViewRepresentable {
|
||||||
didChange?(text.wrappedValue)
|
didChange?(text.wrappedValue)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@objc func returnKeyPressed() {
|
||||||
|
focusNextView?.wrappedValue = true
|
||||||
|
}
|
||||||
|
|
||||||
func textFieldDidBeginEditing(_ textField: UITextField) {
|
func textFieldDidBeginEditing(_ textField: UITextField) {
|
||||||
uiState.currentInput = self
|
uiState.currentInput = self
|
||||||
updateAutocompleteState(textField: textField)
|
updateAutocompleteState(textField: textField)
|
||||||
|
|
|
@ -47,6 +47,8 @@ struct ComposeView: View {
|
||||||
@EnvironmentObject var uiState: ComposeUIState
|
@EnvironmentObject var uiState: ComposeUIState
|
||||||
|
|
||||||
@State private var globalFrameOutsideList: CGRect = .zero
|
@State private var globalFrameOutsideList: CGRect = .zero
|
||||||
|
@State private var contentWarningBecomeFirstResponder = false
|
||||||
|
@State private var mainComposeTextViewBecomeFirstResponder = false
|
||||||
|
|
||||||
@OptionalStateObject private var poster: PostService?
|
@OptionalStateObject private var poster: PostService?
|
||||||
@State private var isShowingPostErrorAlert = false
|
@State private var isShowingPostErrorAlert = false
|
||||||
|
@ -145,12 +147,20 @@ struct ComposeView: View {
|
||||||
.listRowSeparator(.hidden)
|
.listRowSeparator(.hidden)
|
||||||
|
|
||||||
if draft.contentWarningEnabled {
|
if draft.contentWarningEnabled {
|
||||||
ComposeEmojiTextField(text: $draft.contentWarning, placeholder: "Write your warning here")
|
ComposeEmojiTextField(
|
||||||
|
text: $draft.contentWarning,
|
||||||
|
placeholder: "Write your warning here",
|
||||||
|
becomeFirstResponder: $contentWarningBecomeFirstResponder,
|
||||||
|
focusNextView: $mainComposeTextViewBecomeFirstResponder
|
||||||
|
)
|
||||||
.listRowInsets(EdgeInsets(top: 4, leading: 8, bottom: 4, trailing: 8))
|
.listRowInsets(EdgeInsets(top: 4, leading: 8, bottom: 4, trailing: 8))
|
||||||
.listRowSeparator(.hidden)
|
.listRowSeparator(.hidden)
|
||||||
}
|
}
|
||||||
|
|
||||||
MainComposeTextView(draft: draft)
|
MainComposeTextView(
|
||||||
|
draft: draft,
|
||||||
|
becomeFirstResponder: $mainComposeTextViewBecomeFirstResponder
|
||||||
|
)
|
||||||
.listRowInsets(EdgeInsets(top: 4, leading: 8, bottom: 4, trailing: 8))
|
.listRowInsets(EdgeInsets(top: 4, leading: 8, bottom: 4, trailing: 8))
|
||||||
.listRowSeparator(.hidden)
|
.listRowSeparator(.hidden)
|
||||||
|
|
||||||
|
@ -170,6 +180,11 @@ struct ComposeView: View {
|
||||||
.listStyle(.plain)
|
.listStyle(.plain)
|
||||||
.disabled(isPosting)
|
.disabled(isPosting)
|
||||||
.padding(.bottom, uiState.autocompleteState != nil ? 46 : 0)
|
.padding(.bottom, uiState.autocompleteState != nil ? 46 : 0)
|
||||||
|
.onChange(of: draft.contentWarningEnabled) { newValue in
|
||||||
|
if newValue {
|
||||||
|
contentWarningBecomeFirstResponder = true
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private var header: some View {
|
private var header: some View {
|
||||||
|
|
|
@ -35,7 +35,7 @@ struct MainComposeTextView: View {
|
||||||
|
|
||||||
let minHeight: CGFloat = 150
|
let minHeight: CGFloat = 150
|
||||||
@State private var height: CGFloat?
|
@State private var height: CGFloat?
|
||||||
@State private var becomeFirstResponder: Bool = false
|
@Binding var becomeFirstResponder: Bool
|
||||||
@State private var hasFirstAppeared = false
|
@State private var hasFirstAppeared = false
|
||||||
@ScaledMetric private var fontSize = 20
|
@ScaledMetric private var fontSize = 20
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue