By TheBurgerShot


2014-08-07 10:43:12 8 Comments

I have some labels which I want to adjust their height to the text, this is the code I wrote for this now

func heightForView(text:String, font:UIFont, width:CGFloat) -> CGFloat{
    let label:UILabel = UILabel(frame: CGRectMake(0, 0, width, CGFloat.max))
    label.numberOfLines = 0
    label.lineBreakMode = NSLineBreakMode.ByWordWrapping
    label.font = font
    label.text = text

    label.sizeToFit()
    return label.frame.height
}

EDIT:

The issue was not in this piece of code, so my fix is in the question itself. It might still be useful for others!

14 comments

@iOS 2018-07-20 06:51:25

In swift 4.1 and Xcode 9.4.1

Only 3 steps

Step 1)

//To calculate height for label based on text size and width
func heightForView(text:String, font:UIFont, width:CGFloat) -> CGFloat {
    let label:UILabel = UILabel(frame: CGRect(x: 0, y: 0, width: width, height: CGFloat.greatestFiniteMagnitude))
    label.numberOfLines = 0
    label.lineBreakMode = NSLineBreakMode.byWordWrapping
    label.font = font
    label.text = text

    label.sizeToFit()
    return label.frame.height
}

Step 2)

//Call this function
let height = heightForView(text: "This is your text", font: UIFont.systemFont(ofSize: 17), width: 300)
print(height)//Output : 41.0

Step 3)

//This is your label
let proNameLbl = UILabel(frame: CGRect(x: 0, y: 20, width: 300, height: height))
proNameLbl.text = "This is your text"
proNameLbl.font = UIFont.systemFont(ofSize: 17)
proNameLbl.numberOfLines = 0
proNameLbl.lineBreakMode = .byWordWrapping
infoView.addSubview(proNameLbl)

@SURESH SANKE 2019-01-30 06:54:11

Nice solution perfectly working......Thanks

@iOS 2019-01-30 06:54:49

@SURESH SANKE Thank you....

@Anorak 2014-08-07 16:43:47

I've just put this in a playground and it works for me.

Updated for Swift 4.0

import UIKit

 func heightForView(text:String, font:UIFont, width:CGFloat) -> CGFloat{
    let label:UILabel = UILabel(frame: CGRectMake(0, 0, width, CGFloat.greatestFiniteMagnitude))
    label.numberOfLines = 0
    label.lineBreakMode = NSLineBreakMode.byWordWrapping
    label.font = font
    label.text = text

    label.sizeToFit()
    return label.frame.height
}

let font = UIFont(name: "Helvetica", size: 20.0)

var height = heightForView("This is just a load of text", font: font, width: 100.0)

Swift 3:

func heightForView(text:String, font:UIFont, width:CGFloat) -> CGFloat{
    let label:UILabel = UILabel(frame: CGRect(x: 0, y: 0, width: width, height: CGFloat.greatestFiniteMagnitude))
    label.numberOfLines = 0
    label.lineBreakMode = NSLineBreakMode.byWordWrapping
    label.font = font
    label.text = text
    label.sizeToFit()

    return label.frame.height
}

enter image description here

@TheBurgerShot 2014-08-08 11:52:37

this works fine for mee too in playground, the error does not seem to occur at this specific place, when i remove the usages of this method it is gonna whine about some println's or just a line with only comments (then it says EXC_BAD_ACCESS code=2 as well)

@Unome 2014-11-05 19:07:18

It works in a playground, but no sizing occurs as desired inside of a view controller in XCode 6.1

@Zorayr 2015-07-12 19:26:11

I am a little hesitant to create a new UILabel per sizing; if this method is used inside layoutSubviews with the tendency to be invoked multiple times per complete layout, the extra object creation may introduce noticeable delays, especially during scrolling.

@bashan 2016-01-30 19:28:43

How do you pass width? the rows width is determined by the size of the screen...

@Siddharth Pancholi 2016-06-02 14:43:50

let textRect = textString.boundingRectWithSize(CGSizeMake(320, 2000), options: .UsesLineFragmentOrigin, attributes: textAttributes, context: nil)

@yildirimosman 2016-12-09 13:42:58

best solution, thanks

@Rouny 2017-05-25 19:57:03

I am unable to call this function in my view controller...Can you suggest me what could be the possible reason?

@Saeed Rahmatolahi 2018-04-21 06:02:29

this will not working as I expected I want the label size equal to my view and height be dynamic depend on text and label be at the bottom of the view how can I do that ?

@ssowri1 2019-02-06 14:45:06

Thank you for your code!

@user7718859 2018-05-30 16:01:31

The Swift 4.1 extension method to calculate label height:

extension UILabel {

    func heightForLabel(text:String, font:UIFont, width:CGFloat) -> CGFloat {
        let label:UILabel = UILabel(frame: CGRect(x: 0, y: 0, width: width, height: CGFloat.greatestFiniteMagnitude))
        label.numberOfLines = 0
        label.lineBreakMode = NSLineBreakMode.byWordWrapping
        label.font = font
        label.text = text

        label.sizeToFit()
        return label.frame.height
    }

}

@Patrick J. 2018-02-25 12:41:53

Swift 4.0

Instead of calculating the text/label height, I just resize the label after inserting the (dynamic) text.

Assuming that myLabel is the UILabel in question:

let myLabel = UILabel(frame: CGRect(x: 0, y: 0, width: *somewidth*, height: *placeholder, e.g. 20*))
myLabel.numberOfLines = 0
myLabel.lineBreakMode = .byWordWrapping
...

And now comes the fun part:

var myLabelText: String = "" {
   didSet {
      myLabel.text = myLabelText
      myLabel.sizeToFit()
   }
}

@7ur7l3 2017-12-21 11:03:06

Swift 4.0

self.messageLabel = UILabel(frame: CGRect(x: 70, y: 60, width:UIScreen.main.bounds.width - 80, height: 30)

messageLabel.text = message

messageLabel.lineBreakMode = .byWordWrapping //in versions below swift 3 (messageLabel.lineBreakMode = NSLineBreakMode.ByWordWrapping)    
messageLabel.numberOfLines = 0 //To write any number of lines within a label scope

messageLabel.textAlignment = .center

messageLabel.textColor = UIColor.white

messageLabel.font = messageLabel.font.withSize(12)

messageLabel.sizeToFit()

Blockquote NSParagraphStyle.LineBreakMode, apply to entire paragraphs, not words within paragraphs.This property is in effect both during normal drawing and in cases where the font size must be reduced to fit the label’s text in its bounding box. This property is set to byTruncatingTail by default.

This link describes the storyboard way of doing the same

@Yannis 2017-12-21 11:10:27

Code-only answers are not considered good practice. Please consider adding some explanations on how your answer addresses the question.

@LeftyT 2016-09-06 16:12:39

based on Anorak's answer, I also agree with Zorayr's concern, so I added a couple of lines to remove the UILabel and return only the CGFloat, I don't know if it helps since the original code doesn't add the UIabel, but it doesn't throw error, so I'm using the code below:

func heightForView(text:String, font:UIFont, width:CGFloat) -> CGFloat{

    var currHeight:CGFloat!

    let label:UILabel = UILabel(frame: CGRectMake(0, 0, width, CGFloat.max))
    label.numberOfLines = 0
    label.lineBreakMode = NSLineBreakMode.ByWordWrapping
    label.font = font
    label.text = text
    label.sizeToFit()

    currHeight = label.frame.height
    label.removeFromSuperview()

    return currHeight
}

@Phan Van Linh 2015-12-23 07:08:14

If you are using AutoLayout, you can adjust UILabel height by config UI only.

For iOS8 or above

  • Set constraint leading/trailing for your UILabel
  • And change the lines of UILabel from 1 to 0

enter image description here

For iOS7

  • First, you need to add contains height for UILabel
  • Then, modify the Relation from Equal to Greater than or Equal

enter image description here

  • Finally, change the lines of UILabel from 1 to 0

enter image description here

Your UILabel will automatically increase height depending on the text

@oyalhi 2016-01-10 08:01:21

And if the label is inside a cell. When and how would you increase the cell height accordingly?

@kennydust 2016-01-29 22:32:54

neat little trick.

@Phan Van Linh 2016-04-20 09:14:41

@oyalhi, if your label is inside a tableview cell, please see my other post stackoverflow.com/a/36277840/5381331

@Bill Thompson 2016-04-29 19:36:46

This worked perfectly for me! Setup the constraints, and it will work properly!

@gadget00 2016-05-28 08:02:16

not working for me...the word "Label" in a UILabel makes height=20. It remains 20 after this setting.

@Phan Van Linh 2016-05-28 08:45:35

@gadget00 make sure you follow 3 steps correctly

@imalice 2018-07-17 07:15:40

Confirm, it works great!

@dimpiax 2015-01-01 15:16:12

I have strong working solution.

in layoutSubviews:

    _title.frame = CGRect(x: 0, y: 0, width: bounds.width, height: 0)
    _title.sizeToFit()
    _title.frame.size = _title.bounds.size

in text setter:

    _title.text = newValue
    setNeedsLayout()

UPD. of course with this UILabel settings:

    _title.lineBreakMode = .ByWordWrapping
    _title.numberOfLines = 0

@Jacob 2016-01-12 16:42:37

Thanks, that worked perfectly!

@dimpiax 2016-01-13 15:58:55

@Jacob, I have updated the code, check with this.

@Shubham bairagi 2015-11-23 05:05:29

just call this method where you need dynamic Height for label

func getHeightforController(view: AnyObject) -> CGFloat {
    let tempView: UILabel = view as! UILabel
    var context: NSStringDrawingContext = NSStringDrawingContext()
    context.minimumScaleFactor = 0.8

    var width: CGFloat = tempView.frame.size.width

    width = ((UIScreen.mainScreen().bounds.width)/320)*width

    let size: CGSize = tempView.text!.boundingRectWithSize(CGSizeMake(width, 2000), options:NSStringDrawingOptions.UsesLineFragmentOrigin, attributes: [NSFontAttributeName: tempView.font], context: context).size as CGSize

    return size.height
}

@Lirik 2015-10-29 10:55:19

Following on @Anorak answer, i added this extension to String and sent an inset as a parameter, because a lot of times you will need a padding to your text. Anyway, maybe some you will find this usefull.

extension String {

    func heightForWithFont(font: UIFont, width: CGFloat, insets: UIEdgeInsets) -> CGFloat {

        let label:UILabel = UILabel(frame: CGRectMake(0, 0, width + insets.left + insets.right, CGFloat.max))
        label.numberOfLines = 0
        label.lineBreakMode = NSLineBreakMode.ByWordWrapping
        label.font = font
        label.text = self

        label.sizeToFit()
        return label.frame.height + insets.top + insets.bottom
    }
}

@Coder_A_D 2016-01-11 14:11:26

label.lineBreakMode = NSLineBreakMode.ByWordWrapping this line helped me thanks.

@Collin 2015-09-25 17:21:02

Here is how to calculate the text height in Swift. You can then get the height from the rect and set the constraint height of the label or textView, etc.

let font = UIFont(name: "HelveticaNeue", size: 25)!
let text = "This is some really long text just to test how it works for calculating heights in swift of string sizes. What if I add a couple lines of text?"

let textString = text as NSString

let textAttributes = [NSFontAttributeName: font]

let textRect = textString.boundingRectWithSize(CGSizeMake(320, 2000), options: .UsesLineFragmentOrigin, attributes: textAttributes, context: nil)

@Philipp Otto 2015-09-22 12:25:40

The solution suggested by Anorak as a computed property in an extension for UILabel:

extension UILabel
{
var optimalHeight : CGFloat
    {
        get
        {
            let label = UILabel(frame: CGRectMake(0, 0, self.frame.width, CGFloat.max))
            label.numberOfLines = 0
            label.lineBreakMode = self.lineBreakMode
            label.font = self.font
            label.text = self.text

            label.sizeToFit()

            return label.frame.height
         }
    }
}

Usage:

self.brandModelLabel.frame.size.height = self.brandModelLabel.optimalHeight)

@Cristina 2017-12-11 17:36:17

Nice solution! Thank you :-)

@Amg91 2018-12-03 18:03:44

Cannot assign to property: 'height' is a get-only property.

@YannickSteph 2015-01-17 19:12:26

I create this extension if you want

extension UILabel {
    func setSizeFont (sizeFont: CGFloat) {
        self.font =  UIFont(name: self.font.fontName, size: sizeFont)!
        self.sizeToFit()
    }
}

@Jordan Amman 2015-01-07 13:11:21

Just by setting:

label.numberOfLines = 0

The label automatically adjusts its height based upon the amount of text entered.

@TheBurgerShot 2016-02-25 08:52:46

This does not make the UILabel to adjust it's height.

Related Questions

Sponsored Content

26 Answered Questions

48 Answered Questions

[SOLVED] Vertically align text to top within a UILabel

31 Answered Questions

[SOLVED] How to make a div 100% height of the browser window?

  • 2009-10-15 21:18:43
  • mike
  • 1715520 View
  • 1883 Score
  • 31 Answer
  • Tags:   html css css3 height

26 Answered Questions

[SOLVED] Multiple lines of text in UILabel

34 Answered Questions

[SOLVED] Adjust UILabel height depending on the text

2 Answered Questions

[SOLVED] Fitting text in UILabel - Swift

0 Answered Questions

Why is the wordWrapping result is different CATextlayer and UILabel

1 Answered Questions

[SOLVED] Swift - UILabel automatically adjusted to text length

  • 2015-01-21 19:29:08
  • DCDC
  • 7649 View
  • 2 Score
  • 1 Answer
  • Tags:   ios swift uilabel

4 Answered Questions

1 Answered Questions

Sponsored Content