I need to determine minimum width adequate for displaying a possibly wrapped dynamic HTML string. Without word-wrapping this is simple: create a span, set its innerHTML and read offsetWidth. However, I'm not sure how to force linebreaks... Easiest incomplete approach I see is to replace all spaces by <br/>, but lines can be wrapped not only on spaces but also e.g. on hyphens.
So, basically, I want a browser to lay out sth. like
Max.
word-
wrapped
string
<----->
somewhere off-screen to measure width of the longest contained word. Is there a generic way to do that?
EDIT
I.e., for no line wraps:
function computeWidth (str) { // code to make it off-screen and caching omitted
var span = document.createElement ('span');
document.body.appendChild (span);
span.innerHTML = str;
return span.offsetWidth;
}
How would I write a similar function which forces line breaks on str, presumably playing with span.style?
You can use CSS work-break / word-wrap and programmatically inserted soft-hyphens (, but I'd advise you to read up on cross browser problems regarding soft hyphens, as there are quite a few - I normally us the unicode for a soft hypen (U+00AD), but your mileage may vary), and then determine the width with javascript using the range object and measuring cursor offset from the left.
I'm suggesting the use of soft-hyphens, because even the same browser will normally break words differently depending on the OS / which dictionary (on OSX) is used. If that's not an issue for you, you can do it without soft hyphens.
Afaik there is no generic way to get what you want in html/js (it's different if you were using something like flash).
Range object:
https://developer.mozilla.org/en-US/docs/Web/API/range
A different approach would be using the canvas object, but you would probably not get exact results there, as there is just too much factors influencing text rendering in browsers nowadays (font, size, kerning, tracking, ...)
Again another approach would be using <pre> tags / whitespace: pre-wrap, setting the font to what you normally use, and then either emulate breaking words by inserting linebreaks or copying them from still another span/div/whatever set up with word wrap - I haven't tested this yet, but if it works, it might be easer than iterating with the range object.
Edit: Just so it's not only in the comments, still another solution:
Start your container with width 1px, then increase the width, checking the height every time ; when the height decreases, go back one step, and you got your width. Simplest implementation would use 1px increase/1px decrease, but you could of course optimize it to using something like a binary search algorithm, e.g. starting with 1px, then 2px, then 4px increases, then the same backwards, and forwards again and so on till you have a result at a 1px step. But that's only if the 1px inc/dec sollution is too slow ;)
Use the CSS word-break rule:
The word-break CSS property is used to specify how (or if) to break lines within words.
Normal
Use the default line break rule.
break-all
Word breaks may be inserted between any character for non-CJK (Chinese/Japanese/Korean) text.
keep-all
Don't allow word breaks for CJK text. Non-CJK text behavior is same as normal.
<p style="word-break:break-all;">
Max.word-wrapped string<----->
</p>
(source)
Try to play with the word-break Property.
More here: http://www.w3schools.com/cssref/tryit.asp?filename=trycss3_word-break
You should try:
word-break: break-all;
Add it to the CSS like in this fiddle, or read here.
Related
In HTML5, how do you skip 5 spaces in a <div>? For example, how do you do this:
"Drumroll... [5 spaces] Something!"
<div>Drumroll... [5 spaces] Something!</div> just outputs "Drumroll... Something!"
There does not seem to be any tags such as <indent> that I have found to indent in the middle of a sentence.
      works, but is there a more efficient way? Such as...
<skip 10px></skip>
Specifically, I am looking for the solution to insert exactly 1,000 spaces easily, for example.
This is not perfectly five spaces, and I'm not sure if there's a way to do it without using five consecutive s, but this will allow you to add a specifiable amount of space inline.
<p>Drumroll...<span style="margin-left:50px;"></span>something</p>
http://jsfiddle.net/5drHj/1/
Another option might be to use the <pre> tag...
<pre>Drumroll... something</pre>
http://jsfiddle.net/5drHj/2/
If you do decide to use consecutive you could use a javascript loop (or php loop for server side construction) to add the 1000 s
Edit: At the risk of losing my tick, I'd like to point out that the answer given by #vals is a third option, and perhaps the most elegant of the three.
No, there is no such element in HTML. Long ago, there was the nonstandard <spacer> tag, but it was abandoned. You are supposed to use CSS for things like this. Wrap some preceding text in a <span> element and set padding-left: 1.25em on it. Tune the value as needed. The width of a space depends on font but is on the average around 0.25em.
The question that you pose in the first half of the question (How to insert spaces easily), is achieved with the property:
white-space: pre;
It means that your text is pre-formatted, and the white spaces should stay as they are. Then just insert those spaces.
fiddle
If you want to insert 1000 spaces, then we are talking probably about alignment, and there is a huge amount of posibilities. (padding specified in em being the most obvious), but you should then give more details of your situation.
I am having issues wrapping some words in the item list.
I have converted item list into XSLT page. Tried setting column width to some value but it gets overridden and stretched out as cells contain some long words without spaces. I tried adding word-wrap: break-word; as inline styling, but it is instantly marked red with message:
This property is marked invalid because it's not supported by the
current schema.
If I save the page anyways it works how it's supposed to work, but if I navigate somewhere else from current list, everything resets and I am back to square one.
How do I fix this? Is there some global CSS which would enable the use of word-wrap? In essence, I want word wrapping in cells of standard view. Even of long space-less words.
I have a table with column contents that could be potentially long. From a design/usability standpoint, is it better to wrap the text or provide a scroll bar within the column to view the entire text?
Personally, I think wrapping the text is better. But I wanted to know what have others done in such a situation?
I ALWAYS page my content rather than wrapping or scrolling. It's super easy with jQuery DataTables and it gives the user further opportunities to filter, limit, and sort the data.
This solution also gives you the option to scroll data as well, and to dynamically adjust columns or do show/hides. But I've never gotten to that point. One one of my applications, using Ajax and Pipelining (which are supported by the plugin) it handles 3+ million records without a hiccup. Also, note that it can use jQuery's Themeroller, which can style the table simply and even from the user end on the fly if so desired.
I usually let the text wrap into the cell. But, what do you mean by "potentially long"?
I use a calendar plugin and sometimes the title gets long- i made the decision to break the string in the middle if needed- Supported in CSS3 only- other wise it just wraps
My css
.fc-event-title {
text-wrap: unrestricted;
word-wrap: break-word;
}
and will only happen if mywordisexteremlylong and wont fit properly in a small cell
But this is very extreme so that it does not overflow into the next cell.
But otherwise i dont break the word if there is enough space.
I have a comment box, if they enter long one word, "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
the box will break(text out of div), i have used overflow:hidden but my friend want it to break like normal text.
Any idea how to fix ?
In order for overflow to hide content that is larger than it's containers' dimensions, the container must have a set width. But even so, CSS doesn't break long words. (Except for IE, which has the word-wrap: break-word instruction. Further reading.)
If you're using some sort of server side processing (I assume you are), you could manipulate text content by breaking up long words at a preset length and thus avoid overflowing.
You need to use whatever server language you have to devise some way to break the string up. You could use a combination of regex (to check for long unbroken strings) and then combine it with some string split function in order to insert some newlines or something.
In actionscript 3, my TextField has :
CSS styling
embedded fonts
textAlign : CENTER
autoSize : CENTER
... when italics are used the very right character gets slightly cut off (specially caps).
It basically seems that it fails detecting the right size.
I've had this problem before but just wondered is there a nice workaround (instead of checking textWidth or offsetting text etc.)?
Initialize your textField as you always do, using multiline, autosize, htmlText...
Then do this little trick :
// saving wanted width and height plus 1px to get some space for last char
var savedWidth = myTextField.width + 1;
var savedHeight = myTextField.height + 1;
// removing autoSize, wich is the origin of the problem i think
myTextField.autoSize = "none";
// now manually autoSizing the textField with saved values
myTextField.width = savedWidth;
myTextField.height = savedHeight;
Not that it is much comfort to you, but Flash sometimes has trouble with this seemingly simple task. CSS styling of html TextField was a nice addition but it has caused headaches for text-rendering. In fact I very rarely use CSS for styling text for that reason. I can only imagine that combining bold, italic and normal type faces within the HTML causes Flash to get some of the width calculations wrong which causes autoSize to set the mask a tiny bit short. I hope very much that the new text rendering engine in Flash Player 10 will finally fix these issues (it certainly looks better in theory).
So my solution is never to use HTML with the exception being when I require <a> links in my text ... and there are even some tricky text shifting issues there. In those cases I avoid mixing different font weights and font styles within the same text field. All other cases I use TextFormat directly on TextField.
I suppose if you can't get out of your current architecture (for some reason) you could try adding to the end of your html encoded strings. Or you could manually set the width of the field and not rely on autoSize (as you have mentioned). But if you keep on the CSS/HTML route you may find another new and painful limitation just when you don't want it.
I've had issues with TextField masks behaving differently in the Flash preview, and in the actual browser plugin. Usually, and this is strange to me, it would appear more correctly in the browser. Have you tried running the swf in a browser to see if the problem is actually an annoyance rather than a permanent problem?
I had said this:
My in-ideal approach to solving this is to attach a change event to the TextField which always adds a space after the last character of the field. And then to remember to trim this space off when using the value.
But that didn't take into account that this probably doesn't have a change event and that it's an HTML rendered text field. To add a trailing space in the HTML text field throw in an again, that's not really fixing the problem.