IOS Swift - dynamically increasing the height of a UITextView and parent UIView

I almost completely move the UITextView over the keyboard, increasing / decreasing its height depending on the amount of text, and then returning it to its original position. However, I am having problems letting the parent UIView grow with the UITextView.

enter image description hereenter image description hereenter image description here

If I uncomment the last line of the updateParentView () method to update the parent UIView to its updated size, nothing resizes, including the UITextView.

class ViewController: UIViewController, UITextViewDelegate { var kPreferredTextViewToKeyboardOffset: CGFloat = 0.0 var keyboardFrame: CGRect = CGRect.nullRect var keyboardIsShowing: Bool = false @IBOutlet weak var commentView: UIView! @IBOutlet weak var textView: UITextView! @IBOutlet weak var sendButton: UIButton! override func viewDidLoad() { super.viewDidLoad() // Do any additional setup after loading the view. NSNotificationCenter.defaultCenter().addObserver(self, selector: "keyboardWillShow:", name: UIKeyboardWillShowNotification, object: nil) NSNotificationCenter.defaultCenter().addObserver(self, selector: "keyboardWillHide:", name: UIKeyboardWillHideNotification, object: nil) // Make it look like UITextField self.textView.contentInset = UIEdgeInsetsMake(0.0, 0.0, 0.0, 0.0) self.textView.sizeToFit() let lightestGrayColor: UIColor = UIColor( red: 224.0/255.0, green: 224.0/255.0, blue:224.0/255.0, alpha: 1.0 ) self.textView.layer.borderColor = lightestGrayColor.CGColor self.textView.layer.borderWidth = 0.6 self.textView.layer.cornerRadius = 6.0 self.textView.clipsToBounds = true self.textView.layer.masksToBounds = true } override func viewWillDisappear(animated: Bool) { super.viewWillDisappear(animated) NSNotificationCenter.defaultCenter().removeObserver(self) } func keyboardWillShow(notification: NSNotification) { self.keyboardIsShowing = true if let info = notification.userInfo { self.keyboardFrame = (info[UIKeyboardFrameEndUserInfoKey] as NSValue).CGRectValue() self.arrangeViewOffsetFromKeyboard() } } func keyboardWillHide(notification: NSNotification) { self.keyboardIsShowing = false self.returnViewToInitialFrame() } func arrangeViewOffsetFromKeyboard() { var theApp: UIApplication = UIApplication.sharedApplication() var windowView: UIView? = theApp.delegate!.window! var textFieldLowerPoint: CGPoint = CGPointMake(self.commentView!.frame.origin.x, self.commentView!.frame.origin.y + self.commentView!.frame.size.height) var convertedTextViewLowerPoint: CGPoint = self.view.convertPoint(textFieldLowerPoint, toView: windowView) var targetTextViewLowerPoint: CGPoint = CGPointMake(self.commentView!.frame.origin.x, self.keyboardFrame.origin.y - kPreferredTextViewToKeyboardOffset) var targetPointOffset: CGFloat = targetTextViewLowerPoint.y - convertedTextViewLowerPoint.y var adjustedViewFrameCenter: CGPoint = CGPointMake(self.view.center.x, self.view.center.y + targetPointOffset) UIView.animateWithDuration(0.2, animations: { self.view.center = adjustedViewFrameCenter }) } func returnViewToInitialFrame() { var initialViewRect: CGRect = CGRectMake(0.0, 0.0, self.view.frame.size.width, self.view.frame.size.height) if (!CGRectEqualToRect(initialViewRect, self.view.frame)) { UIView.animateWithDuration(0.2, animations: { self.view.frame = initialViewRect }); } } func textViewDidBeginEditing(textView: UITextView) { // print("text view did begin editing\n") // if(self.keyboardIsShowing) { self.arrangeViewOffsetFromKeyboard() } } func textViewDidChange(textView: UITextView) { print("text view did change\n") let textViewFixedWidth: CGFloat = self.textView.frame.size.width let newSize: CGSize = self.textView.sizeThatFits(CGSizeMake(textViewFixedWidth, CGFloat(MAXFLOAT))) var newFrame: CGRect = self.textView.frame // var textViewYPosition = self.textView.frame.origin.y var heightDifference = self.textView.frame.height - newSize.height // if (abs(heightDifference) > 5) { newFrame.size = CGSizeMake(fmax(newSize.width, textViewFixedWidth), newSize.height) newFrame.offset(dx: 0.0, dy: heightDifference) // updateParentView(heightDifference: heightDifference) } self.textView.frame = newFrame } func updateParentView(#heightDifference: CGFloat) { // var newContainerViewFrame: CGRect = self.commentView.frame // var containerViewHeight = self.commentView.frame.size.height print("container view height: \(containerViewHeight)\n") // var newContainerViewHeight = containerViewHeight - heightDifference print("new container view height: \(newContainerViewHeight)\n") // var containerViewHeightDifference = containerViewHeight - newContainerViewHeight print("container view height difference: \(containerViewHeightDifference)\n") // newContainerViewFrame.size = CGSizeMake(self.commentView.frame.size.width, newContainerViewHeight) // newContainerViewFrame.offset(dx: 0.0, dy: containerViewHeightDifference) // // self.commentView.frame = newContainerViewFrame } func textViewDidEndEditing(textView: UITextView) { // print("text view did end editing\n") // textView.resignFirstResponder() } } 
+5
source share
2 answers

This is what worked for me. In my case, I have a text view under a table view. Thus, as the text view grows in height, the parent view is not what needs to be changed - the view above the text view is what needs to be changed (for me it was a table view). So, here is what I implemented in the updateParentView function.

 func updateParentView(heightDifference: CGFloat) { // var newContainerViewFrame: CGRect = self.commentTableView.frame // let containerViewHeight = self.commentTableView.frame.size.height print("container view height: \(containerViewHeight)\n") // let newContainerViewHeight = containerViewHeight + heightDifference print("new container view height: \(newContainerViewHeight)\n") // let containerViewHeightDifference = containerViewHeight - newContainerViewHeight print("container view height difference: \(containerViewHeightDifference)\n") // newContainerViewFrame.size = CGSizeMake(self.commentTableView.frame.size.width, newContainerViewHeight) // newContainerViewFrame.origin.y - containerViewHeightDifference // self.commentTableView.frame = newContainerViewFrame } 

Now that the text view is increasing in height, the table view is "sliding" to newContainerViewFrame.origin.y - containerViewHeightDifference . See screenshot below.

Screenshot example

+3
source

I have a really simple answer, hope this helps. What I have is pretty simple and does not contain code. I did everything according to restrictions . Here are a couple of images that will help me:

This is what I have

enter image description here

This is how it really looks

enter image description here

It is important that the TextView this property is not checked in the property inspector:

enter image description here

Then you simply set the top, leading, end and bottom for each view and set it without height for any of them. Everything will grow when you set parental views with him! :)

+4
source

Source: https://habr.com/ru/post/1211894/


All Articles