Reputation: 3760
I have a UITextField
with a text alignment set to right embedded in a UICollectionViewCell
. If I tap the UITextField
the cursor should be at the end of the text. Also if I tap the textfield on or before of the beginning of the text.
I tried to set the position in the textFieldDidBeginEditing
delegate method:
func textFieldDidBeginEditing(_ textField: UITextField) {
let position = textField.endOfDocument
textField.selectedTextRange = textField.textRange(from: position, to: position)
}
But this didn't work so I tried it with DispatchQueue.main.async. That works. But I know, that this isn't the most elegant way and it looks like something tries to set the cursor position at the same time.
func textFieldDidBeginEditing(_ textField: UITextField) {
DispatchQueue.main.async {
let position = textField.endOfDocument
textField.selectedTextRange = textField.textRange(from: position, to: position)
}
}
Is there a better solution to set the cursor on the last position?
Upvotes: 1
Views: 2202
Reputation: 1709
Using DispatchQueue
makes my cursor visually jump, since there's a delay. I'm not sure the solution below is better since it adds complexity, but I'm trying it out.
func textFieldDidBeginEditing(_ textField: UITextField) {
_beganEditing = true // if we change cursor position here (with DispatchQueue), cursor jumps ; instead, do in DidChangeSelection
}
func textFieldDidChangeSelection(_ textField: UITextField) {
// We assume this is called right after DidBeginEditing
// Move cursor to end if approp
if (_beganEditing) {
_beganEditing = false
if (_rightAlign) {
let position = textField.endOfDocument
textField.selectedTextRange = textField.textRange(from: position, to: position)
}
}
}
Upvotes: 1