尝试动态更改UITextView高度时遇到问题

Han*_*nXu 2 ios

我正在使用iOS7.

我想根据内容高度动态更改我的UITextView的高度.但是,我发现在iOS7中,contentSize是一团糟.例如,当我删除一行时,contentSize不会改变,但我希望它的高度会降低.

所以我写下面的内容

- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text {
    //  increase a line
    if ([text isEqualToString:@"\n"]) {
        _FRAME_SET_H(textView, textView.contentSize.height + 24.0f);

    //  decrease a line
    } else if (range.length == 1 && [textView.text hasSuffix:@"\n"]) {
        _FRAME_SET_H(textView, textView.contentSize.height - 24.0f);

    } else {
        _FRAME_SET_H(textView, textView.contentSize.height);
    }

    return YES;
}
Run Code Online (Sandbox Code Playgroud)

一切正常,直到我输入一个很长的文本:

在此输入图像描述

当文本足够长以引起自动换行时,contentSize不会改变!

谁能帮助我?

我想要的很简单:根据内容更改UITextView的高度.但是,我已经花了两天多的时间,但仍未解决.

iOS7中的UITextView是如此的错误.


我试图按照Uptown Apps的解决方案.以下是我的新代码(稍微更改以适应我的其他项目):

- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text {
    return YES;
}

- (void)textViewDidChange:(UITextView *)textView {
    CGRect rect = [textView.text
                   boundingRectWithSize:CGSizeMake(300, CGFLOAT_MAX)
                   options:NSStringDrawingUsesLineFragmentOrigin
                   attributes:@{NSFontAttributeName: textView.font}
                   context:nil];
    _FRAME_SET_H(textView, rect.size.height);

    _FRAME_SET_H(self, _FRAME_H(textView) + _BLOCK_PADDING * 2);
}
Run Code Online (Sandbox Code Playgroud)

然而,麻烦仍然存在.在下图中,白色rect是UITextView,黑色背景是其superview.

当我启动应用程序时,UITextView的高度为0,屏幕如下所示: 在此输入图像描述

然后我输入'A',屏幕变成: 在此输入图像描述

你看到有两个问题:1)高度不够.2)插入符号很奇怪!

然后我输入更多'a',屏幕变成: 在此输入图像描述

然后我输入'return'来改变一条线,屏幕变成: 在此输入图像描述

是的,它不会改变!但我希望它增加它的高度以包括新的空白行.

然后我输入'A',屏幕变成: 在此输入图像描述

高度增加,但新文本没有显示,插入符号也没有.我想这也是因为身高还不够.

然后我输入另一个'a',屏幕变成: 在此输入图像描述

字母出现,但只有一半......

顺便说一下,当我使用UILabel时,我可以使用这种方法获得正确的文本高度!(即调用boundingRectWithSize :)

Upt*_*pps 5

- 编辑 -

请参阅如何将UITextView的大小调整为其内容?

文本更改后,您可以返回到使用contentSize的原始解决方案.我调整了这段代码来使用amaxHeight

- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text {
    return YES;
}

- (void)textViewDidChange:(UITextView *)textView
{
    CGFloat maxHeight = 312.0f;
    CGFloat fixedWidth = textView.frame.size.width;
    CGSize newSize = [textView sizeThatFits:CGSizeMake(fixedWidth, MAXFLOAT)];
    CGRect newFrame = textView.frame;
    newFrame.size = CGSizeMake(fmaxf(newSize.width, fixedWidth), fminf(newSize.height, maxHeight));
    textView.frame = newFrame;
}
Run Code Online (Sandbox Code Playgroud)

- 原始答案 -

您是否尝试等待文本更改,然后使用NSString方法获取大小?我没有测试过这个,但它应该让你开始朝着正确的方向前进.

- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text {
    return YES;
}

- (void)textViewDidChange:(UITextView *)textView{

    CGFloat myMaxSize = 568.0f; // Set to max height you would ever want your textView to expand to

    CGRect frameRect = textView.frame;
    CGRect rect = [textView.text 
boundingRectWithSize:CGSizeMake(frameRect.size.width, CGFLOAT_MAX)
             options:NSStringDrawingUsesLineFragmentOrigin 
          attributes:@{NSFontAttributeName: textView.font} 
             context:nil];

    CGSize size = rect.size;
    if (size.height > myMaxSize) {
        size.height = myMaxSize;
    }

    frameRect.size = size;
    [textView setFrame:frameRect];

}
Run Code Online (Sandbox Code Playgroud)