【问题标题】:Setting UITextView cursor position to end of text将 UITextView 光标位置设置为文本末尾
【发布时间】:2012-05-25 15:04:56
【问题描述】:

我整个上午都在寻找解决方案,但还没有找到可行的方法。

我有一个文本视图,其中包含一些我不希望用户能够修改的现有固定文本。在这种情况下,我的每个文本视图都以“1.”、“2.”等开头。他们输入的文本将被编号以供我稍后执行。

我不希望用户能够删除此文本(它本质上是“永久的”)。我也不想让他们开始在这个前置文本的中间添加文本。

为了解决这个问题,我做了:

-(BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text 
{
    if (range.location < 3) return NO;

    return YES;
}

这很好用,除了如果用户触摸视图的“1.”、“2.”等部分中的任何位置,它会将光标设置在那里,然后阻止用户输入文本,因为范围位置检查。在这种情况下,我想做的是将光标(可能在 textViewDidBeginEditing 中)设置到视图中文本的末尾。但是,无论我使用什么 selectedRange 组合,我都无法让该死的光标移动到最后。任何帮助将不胜感激。

【问题讨论】:

  • 更简单的方法是将您的数字放在一个标签中,正对您的文本视图,以便它们看起来像是同一个句子的一部分。然后,他们将只能更改适当的部分。

标签: ios uitextview


【解决方案1】:

将光标移到末尾

textView.selectedRange = NSMakeRange([textView.text length], 0);

或将光标移动到第三个字符之后

textView.selectedRange = NSMakeRange(3, 0);

另一种可能更好的方法可能是在用户开始编辑时清除前三个字符,然后在编辑结束后将它们重新添加。

【讨论】:

  • 这正是我试图做的。但是,无论我是否设置了 selectedRange,光标似乎总是将自己放在视图被触摸的位置。好吧,如果用户触摸有文本的地方,它会将光标放在文本中间的某个位置,否则如果用户触摸空白区域,它会将光标放在末尾。似乎最后有一个额外的步骤覆盖了触摸位置的范围。
  • 检查我的答案here 涉及performSelector:withObject:afterDelay 我知道这已经晚了,但是......无论如何HTH
【解决方案2】:

已经很晚了,但我在一些博客中找到了可行的解决方案。它需要一点技巧

- (void) textViewDidBeginEditing:(UITextView*)textview
{
   [self performSelector:@selector(placeCursorAtEnd:) withObject:textview afterDelay:0.01];
}

- (void)placeCursorAtEnd:(UITextView *)textview
{
     NSUInteger length = textview.text.length;

    textview.selectedRange = NSMakeRange(length, 0);
}

【讨论】:

  • 嗨,我使用“messageInputBar.inputTextView.textStorage.insert(attString, at: messageInputBar.inputTextView.selectedRange.length)”将图像附加为 NSAttachment,但光标始终位于第一个字符和占位符文本中仍然显示
  • 我在 iOS 15 上使用 SwiftUI 中的 UITextViewUIViewRepresentable,这个技巧对我来说非常有效。我猜延迟允许视图接受触摸位置,然后快速覆盖它。快速调用:perform(#selector(self.placeCursorAtEnd(_:)), with: textView, afterDelay: 0.01)
【解决方案3】:

您可以考虑注册到UIKeyboardWillShowNotification,并在收到通知后,将textview 的userInteractionEnabled 设置为NO

另外,实现shouldChangeTextInRange 方法的方式是,如果replacementText 等于字符串@"",则不要更改文本(@"" 表示用户正在点击退格键)。当用户完成文本编辑后恢复用户交互,然后就可以了。

祝你好运!

【讨论】:

  • 这似乎是最好的方法。设置范围似乎不起作用,有点愚蠢。
【解决方案4】:

我试图创建一个货币字段。我不希望用户按整个字段并可能删除格式化的文本。我发现将光标保持在末尾的最简单方法是在 UITextField 的子类中执行以下操作

-(void) setSelectedTextRange:(UITextRange *)selectedTextRange{

    [super setSelectedTextRange:selectedTextRange];
    self.text = self.text;
}

【讨论】:

    【解决方案5】:
    extension UITextView {
        func moveCoursoreToEnd(){
            selectedTextRange = textRange(from:endOfDocument, to: endOfDocument)
        }
    }
    

    【讨论】:

    【解决方案6】:

    此方法隐藏自动更正&键盘不跳转。

    - (void)rejectAutoCorrectSuggestionInTextView:(UITextView *)textView
    {
        if ([textView isFirstResponder])
        {
            NSString *original = textView.text;
            NSRange originalRange = textView.selectedRange;
            CGPoint originalOffset = textView.contentOffset;
    
            [UIView animateWithDuration:.00001 animations:^{
                textView.text = [textView.text stringByAppendingString:@"|"];
                NSRange range;
                range.location = textView.text.length-1;
                range.length = 0;
                textView.selectedRange = range;
                textView.text = [textView.text substringToIndex:textView.text.length - 1];
            }];
    
            NSString *final = textView.text;
    
            if (![original isEqualToString:final])
            {
                textView.text = original;
                textView.selectedRange = originalRange;
                [textView setContentOffset:originalOffset animated:NO];
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2011-05-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-12-28
      • 1970-01-01
      • 1970-01-01
      • 2011-02-22
      相关资源
      最近更新 更多