Dynamic UITextView mislocation behavior

2019-04-22 19:58发布

问题:

I am trying to have a textview similar to iPhone messages, where the textview initially has a constraint (height <= 100) and the scrollEnabled = false

This is a link to the project: https://github.com/akawther/TextView

The text view increases in height based on the content size as in the image on the left until it reaches the height of 100, then the scrollEnabled is set to true. It works perfectly until I click the "send" button on the lower right where the textView should become empty and go back to the original height and scrollEnabled becomes false. The middle image shows what happens when I click the button. When I start typing the textview moves down as you see in the last image on the right. I want to be able to click the button and eliminate the behavior shown on the middle image, how can I fix this?

import UIKit

class ViewController: UIViewController, UITextViewDelegate {

@IBOutlet weak var bottomConstraint: NSLayoutConstraint!
@IBOutlet weak var messageTextView: UITextView!
@IBOutlet weak var parent: UIView!
let messageTextViewMaxHeight: CGFloat = 100


override func viewDidLoad() {
    super.viewDidLoad()

    self.messageTextView.delegate = self
}

@IBAction func Reset(sender: AnyObject) {
    messageTextView.text = ""
    messageTextView.frame.size.height = messageTextView.contentSize.height
    messageTextView.scrollEnabled = false
    self.parent.layoutIfNeeded()
}

func textViewDidChange(textView: UITextView) {
    if textView.frame.size.height >= self.messageTextViewMaxHeight {

        textView.scrollEnabled = true

    } else {
        textView.scrollEnabled = false
        textView.frame.size.height = textView.contentSize.height
    }
}

}

You can replicate my issue by following these steps in the github project: 1. keep typing words and pressing enters until you start seeing the scroll 2. Click the button you will see that the textview goes up in the blue container. This is the issue I want to eliminate!

回答1:

Try bellow code :-

@IBAction func Reset(sender: AnyObject) {
        messageTextView.scrollEnabled = false
        messageTextView.text = ""
        messageTextView.frame.size.height = messageTextView.contentSize.height
        parent.frame.size.height = 20

    self.view.layoutIfNeeded()
}

func textViewDidChange(textView: UITextView) {
    if textView.contentSize.height >= self.messageTextViewMaxHeight {

        textView.scrollEnabled = true

    } else {

        textView.frame.size.height = textView.contentSize.height
        textView.scrollEnabled = false
    }
}


回答2:

Your issue is that the UITextView has conflicting properties:

  • Place on the screen
  • Size

The size being constrained will cause an issue when you need a resizable TextView. Also, when the TextView is resized, its location is being changed in this case.

Alternate method to approach the issue:

Try setting constraints to its location in relation to the bottom of the screen. When the Keyboard appears, you should move the TextView up with it. Also setting constraints on the height of a resizable TextView is bad practice unless you are planning on forcing the user to scroll.

Hope this helps.



回答3:

If you are using auto layout, you should be updating to constraint instead of updating the textView.frame.Try create a IBOutlet for your textView heightConstraint then set the updated height to it.

IBOutlet weak var textViewHeightConstraint: NSLayoutConstraint!

//calculate the height and update the constant
textViewHeightConstraint.constant = textView.contentSize.height