There have been similar questions asked, but the solutions do mesh with what I'm trying to do. Basically, I have an article with a title (<h1>
). I don't want to control the length of the title, but I also don't want the title to appear on multiple lines. Is there a way with css or jQuery to resize text based on the width of a <div>
tag?
I know what I would do with pseudocode if I could detect the overlap of the text to the edge of the <div>
:
var fontize = $("#title").css("font-size");
var i = /*remove unit from integer*/
while( /*text overlaps div*/ ){
$("#title").css("font-size", --i+"pt");
}
If there's a CSS attribute I can set that would be even nicer, but I can't seem to find one (overflow wouldn't work in this situation).
CSS no, Javascript yes
There's no way you could do this using CSS, but you can do it in javascript/jQuery. To help you with your pseudo code because you already know what to do. It's just that you don't know how to detect excess width.
The best way would be to have a DIV with following (at least) style:
then copy your text to it and set some starting font size. Then you can iterate through your while loop and stop when div's width is appropriate. Then set calculated font size to your original title.
This way this checking will be hidden from user's eyes and it will therefore work faster as well.
BTW: This is the usual way how auto growing
textarea
scripts work. They use dummy divs with same style settings as the original text area and adjust area's height as the user types in text. So Text area can be quite small at first but if user types in lots of text it will auto grow to accommodate content.While loop optimization
You could optimize your while loop to decrease the number of iterations considerably by doing this:
There is a jquery plugin available on github that probably just do what you want. It is called jquery-quickfit. It uses Jquery to provide a quick and dirty approach to fitting text into its surrounding container.
HTML:
Javascript:
More information: https://github.com/chunksnbits/jquery-quickfit
My solution, as a jQuery extension based on Robert Koritnik's answer:
This actually creates a temporary span inheriting important properties, and compares the width difference. Granted, the while loop needs to be optimised (reduce by a percentage difference calculated between the two sizes).
Example usage:
Check out this example here http://codepen.io/LukeXF/pen/yOQWNb, you can use a simple function on page load and page resize to make the magic happen. Though be careful not lag out the client from too many function calls. (The example has a delay).
I understand that this question seems to have been answered fairly thoroughly, but there were some instances where solutions here would may cause other issues. For example, tkahn's library looked to be very useful, but it changed the display of the element it was attached to, which could prove to be a problem. In my case, it prevented me from centering the text both vertically and horizontally. After some messing around and experimenting, I have come up with a simple method involving jQuery to fit the text on one line without needing to modify any attributes of the parent element. Note that in this code, I have used Robert Koritnik's suggestion for optimizing the while loop. To use this code, simply add the "font_fix" class to any divs containing text needing to be fit to it in one line. For a header, this may require an extra div around the header. Then, either call this function once for a fixed size div, or set it to a resize and/or orientation listener for varying sizes.
Now, I've added an additional case where the text is chopped off if it gets too small (below the minimum threshold passed into the function) for convenience. Another thing that happens once that threshold is reached that may or may not be desired is the changing of the max width to 100%. This should be changed for each user's scenario. Finally, the whole purpose of posting this answer as an alternate is for its abilities to center the content within the parent div. That can be easily done by adding css attributes to the inner div class as follows:
Hope this helped someone!
This may be overkill for what you require, but I found this library to be very helpful:
http://fittextjs.com/
It's only good for single lines though, so I'm not certain if that fits your requirement.