44

Let's say I have a DIV: <div></div> and I want to find out with JS what its line-height is. I know one can check the style attribute style.lineHeight, but I want to check the actual line-height, without it depending on the existence of a CSS rule.

Assuming the font family and font size are the same, both should output the same line-height:

<div>One line of text</div>
<div>Two <br /> Lines of text</div>

How can I get the line-height of an element with JavaScript?

0

9 Answers 9

34

The answer is actually using .clientHeight. As Gaby said, this is not really reliable/trustworthy. However, it is! Here:

function getLineHeight(el) {
    var temp = document.createElement(el.nodeName), ret;
    temp.setAttribute("style", "margin:0; padding:0; "
        + "font-family:" + (el.style.fontFamily || "inherit") + "; "
        + "font-size:" + (el.style.fontSize || "inherit"));
    temp.innerHTML = "A";

    el.parentNode.appendChild(temp);
    ret = temp.clientHeight;
    temp.parentNode.removeChild(temp);

    return ret;
}

"Clone" the properties of your element into a new one, get the new's clientHeight, delete the temporary element, and return it's height;

10
  • 2
    Be wary though, that since you are appending it to the document, it will inherit the styling of that part. It does not mean that the element you test for, has the same line-height, as some inner rule might be overriding it.. The line-height is not constant across the document.. Commented Dec 23, 2010 at 9:26
  • I think I just fixed it, I did think of this from the start but I kinda was too lazy to put it there lol. I replaced document with element.parentNode :D
    – JCOC611
    Commented Dec 23, 2010 at 19:08
  • 1
    @Davy8: I'm glad this is still helpful after so long!
    – JCOC611
    Commented Oct 4, 2012 at 21:18
  • @MuhammadUmer: check out the other two answers and you'll see why it's not really an option.
    – JCOC611
    Commented Jul 10, 2013 at 2:33
  • 2
    @MuhammadUmer: yeah although it would probably depend on many things...so it's better to know an exact value than an ambiguous normal.
    – JCOC611
    Commented Jul 10, 2013 at 22:07
18

Explained at quirksmode : http://www.quirksmode.org/dom/getstyles.html

example: http://www.jsfiddle.net/gaby/UXNs2/

function getStyle(el,styleProp)
{
    var x = document.getElementById(el);
    if (x.currentStyle)
        var y = x.currentStyle[styleProp];
    else if (window.getComputedStyle)
        var y = document.defaultView.getComputedStyle(x,null).getPropertyValue(styleProp);
    return y;
}

and use it like

getStyle('test', 'line-height' )
6
  • 6
    Pretty interesting, although it returns "normal" rather than a number, at least in Chrome.
    – JCOC611
    Commented Dec 8, 2010 at 22:31
  • I am not sure if you can get more info out of that case, since normal is a valid value for line-height. See stackoverflow.com/questions/3614323/… Commented Dec 8, 2010 at 22:42
  • Indeed, but when I wrote the question I was looking for something like .clientWidth(), which is used to retrieve the "real" width of an element.
    – JCOC611
    Commented Dec 8, 2010 at 22:46
  • 2
    you could use the clientHeight of the element, but it will need to only have a single line to work (and no padding etc.. not very trustworthy). Also note that IE will also return normal and it need to be called with lineHeight and not line-height. Commented Dec 8, 2010 at 23:01
  • yes, I wonder if there is any way to get the line height the way .clientHeight() gets the element height
    – JCOC611
    Commented Dec 9, 2010 at 1:33
11

This solution works for me. It uses the value of the line-height property when it has been set explicitly or, when the value has not been set, it calculates the value by finding the difference in the height of the object when its contents are augmented by one line.

function calculateLineHeight (element) {

  var lineHeight = parseInt(getStyle(element, 'line-height'), 10);
  var clone;
  var singleLineHeight;
  var doubleLineHeight;

  if (isNaN(lineHeight)) {
    clone = element.cloneNode();
    clone.innerHTML = '<br>';
    element.appendChild(clone);
    singleLineHeight = clone.offsetHeight;
    clone.innerHTML = '<br><br>';
    doubleLineHeight = clone.offsetHeight;
    element.removeChild(clone);
    lineHeight = doubleLineHeight - singleLineHeight;
  }

  return lineHeight;
}
7

This is easy now with window.getComputedStyle.

function getLineHeight(el: HTMLSpanElement) {
  return window.getComputedStyle(el).lineHeight;
}
2
  • This actually worked for me. Thanks
    – Melvin
    Commented Jan 27, 2022 at 23:55
  • This doesn't work when the source CSS is line-height: normal; as normal is a valid computed value.
    – Dai
    Commented Oct 10, 2022 at 7:02
5

See currentStyle for IE and getComputedStyle() for other browsers (also supported by IE9).

2
  • 1
    Assuming element references a HTML DIV Element, element.currentStyle returns undefined and element.getComputedStyle() throws error (undefined too), in Chrome.
    – JCOC611
    Commented Dec 8, 2010 at 22:26
  • although this method is explained in the second answer
    – JCOC611
    Commented Dec 8, 2010 at 22:28
3

It’s fairly complicated. I made an npm package for clamping text to a certain number of lines or a pixel height.

You can’t just check line-height. Sometimes that’s normal which is no help at all.

You can’t put the text in another element because it may receive different styles.

The most solid method I found was to remove all text from the element and measure its height. Then add a line and measure the height. the height the first line adds isn’t always the same as subsequent lines. Then add another line. The second and all subsequent lines all add the same amount.

My tool exposes a method called calculateTextMetrics() that which uses the above strategy and returns the resulting measurements.

https://github.com/tvanc/lineclamp#getting-text-metrics

1

One intuitive way (that doesn't require element reference) is to use selection and range APIs to get cursor height.

const range = window.getSelection().getRangeAt(0);
const height = (range.getClientRects()[0]).height;

ref: https://developer.mozilla.org/en-US/docs/Web/API/Element/getClientRects

1
  • Unfortunately range.getClientRects gives the border box of the element... equivalent to element.getClientRects. So for elements that are not inline (block, inline-block, etc), it will not be accurate.
    – Azmisov
    Commented Jan 17, 2023 at 23:19
1

The line-height: normal is actually 110% to 120% of the font-size. So, based on this fact, I use this code everywhere I need to get the line height of any element.

JavaScript:

function getLineHeight(elem) {
    let computedStyle = window.getComputedStyle(elem);
    let lineHeight = computedStyle.getPropertyValue('line-height');
    let lineheight;
    
    if (lineHeight === 'normal') {
        let fontSize = computedStyle.getPropertyValue('font-size'); // Get Font Size
        lineheight = parseFloat(fontSize) * 1.2; // 'normal' Line Height Equals To 120% Of Font Size In Most Browsers
    } else {
        lineheight = parseFloat(lineHeight); // The Line Height That Is Not 'normal'
    }
    
    return lineheight;
}
-1

This is the best way to me. No error for me so far

function getLineHeight(element) {

oldHtml = element.innerHTML

element.innerHTML = "A"
lineHeight = element.offsetHeight

element.innerHTML = oldHtml

return lineHeight }

Not the answer you're looking for? Browse other questions tagged or ask your own question.