Jump to content

Determine where to truncate text in iframe so it doesnt cut-off


jdp

Recommended Posts

Im capturing RSS data via a PHP script and then displaying it via an iframe in my HTML. The RSS articles obviously vary in length and I can only fit 10 lines total of text in the iframe. What I want to do is only display enough text so a new article wont be started if it wont display in its entirety in the iframe.

 

Normally I would think this would need to be done on the browser side as the server wouldn't know about the size of the iframe, font size etc. In this particular case all of that can be determined as this is only going to run a single specific kiosk.

 

I'm not sure how to begin to go about this either from the server side or if necessary from the browser side.

 

Iinitially tried setting overflow to hidden in the iframe but this sometimes leads to cutting off multi-line articles.

 

Some help would be appreciated

 

Link to comment
Share on other sites

You want to completely hide articles when they can't fit? So there will be a blank space there? Are you sure? Are you sure you don't want to do something like apply opacity to the bottom of the frame so it's clear there's more to the article?

Link to comment
Share on other sites

Thanks for your reply.

 

I do think I want to completely hide articles that wont fit. The way thing usually work out is that 6 or 7 articles completely fit, either perfectly using up all 10 lines, or with just one empty blank line at the bottom. I would rather have the one blank line then have it break the story.

 

The question is really how to go about this. How do I get the PHP to calculate that displayed at X font size and frame size Y that story 1 of  XXX characters will take up 2 lines? So that the PHP can serve up the correct number of articles.

Link to comment
Share on other sites

You are not going to be able to have PHP "calculate" what will fit. Well, you can, but it is a LOT of work and would never be completely accurate anyway.

 

1. PHP can't know what size the text is being displayed to the user because users can change their browser settings to display items smaller or larger.

 

2. Even if you assume all users are setting their browser display at 100%, PHP has no way to measure the length of text such as a language like PostScript can. Plus, PHP has no logic to know when text will wrap to the next line. You would have to create a library of every character and how much space it takes up. This can be different based on font properties (font face, bold, italic, case, engind/beginning of word, etc.). Plus, you would have to build logic so PHP can "know" when the text will wrap to the next line based on available horizontal space.

 

You are talking about an immense amount of work and you will likely never be 100% accurate.

 

You could instead put each article into separate DIVs and find some way to put those divs into the iframe such that the div will either be visible (if it completely fits in the iframe) or invisible (if the entire div doesn't fit in the iframe). How to do this, not sure exactly. There may be a CSS property to do this (best approach if it works). Otherwise, you could create divs for the maximum number of articles that "could" fit. Then use JavaScript to measure the height of the divs - starting with the first div. Once, you calculate that a div will not fit in the remaining space, make it (and the remaining divs) hidden.

Link to comment
Share on other sites

You might make use of imagettfbbox function. Although it is a GD image function, it doesn't require an image.

 

This example outputs four lines text in 10pt calibri font. It gets the size of the text using the above function to get the size for the div element (+2 to allow for the border). The text just fits the box.

$text = "The quick brown fox\njumps over\nthe lazy\ndog";

$sz=imagettfbbox(10,0,'c:/windows/fonts/calibri.ttf',$text);

$w =  abs($sz[4]-$sz[0]) + 2;

$h =  abs($sz[5]-$sz[1]) + 2;

echo "<div style='font-family: calibri; font-size:10pt; width:{$w}px; height: {$h}px; overflow:hidden; border: 1px solid gray'>"

        . nl2br($text)

        . "</div>";

post-3105-0-58331400-1520443969_thumb.png

Link to comment
Share on other sites

My opinion: serve up a small number of articles that seems like it would cover 95% of displays, then use Javascript to detect when there is room for more and AJAX to fetch the content.

 

You can guess overall length by just counting characters and newlines. Do some quick testing to see how many characters on average fit in some amount of space and rely on the law of averages to get you the rest of the way.

Link to comment
Share on other sites

Both of these ideas are good. Thanks.

I've been playing around with iimagettfbbox. I was able to send it the (know size) of the iframe and the font and size I am using. I then wrote a little function that determines how many lines the article will take up. From this I should be able to compute the size of the next article and see if there is enough room to display it or not.

 

Since the PHP is running on a hosted unix server I uploaded the TTF font. I assume there is no way around this?

Thanks

Link to comment
Share on other sites

I do think I want to completely hide articles that wont fit. The way thing usually work out is that 6 or 7 articles completely fit, either perfectly using up all 10 lines, or with just one empty blank line at the bottom. I would rather have the one blank line then have it break the story.

The technique Requinix offered, does not completely hide the article. It simply fades out (increases the opacity) of a section of an article at the bottom of a div. Here's an article that shows a couple of ways of doing this although it's a bit old at this point. There are numerous stack overflow questions that cover this and have some solutions and related discussion.

 

There are a number of different ways to fade out an element that has overflowed its boundaries. Like most things, the support for all browsers varies somewhat and you might have to experiment to find out which fit your targets.

 

Here is a jsfiddle that has a simple and effective css solution you might try out:

Link to comment
Share on other sites

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.