I need a script for my website in which there will be a paragraph provided to our visitor. He will be asked for his reading rate like words per minute he can read. Then according to this asked rate the words in that particular paragraph will get highlighted.

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
	"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html>
<head>
<title>Airshow :: Highlight words</title>
<style type="text/css">
#para { margin:0 0 012px 0; width:400px; padding:10px; border:1px solid #999999; font-family:vaerdana,arial; font-size:11pt; }
.highlight { background-color:yellow; }
</style>

<script>
function highlightText(){
	var p = document.getElementById('para');//Get the text div
	var r = document.getElementById('readingRate');//Get the reading rate
	if(!p || !r) { return; }//exit the function if 
	var txt = p.innerHTML;//Get the text
	var rr = parseInt(r.value);//Get the reading rate value
	//Apply algorithm here as necessary to multiply/divide/add/subtract the user's value into what you actually want, eg ...
	//rr = rr * 4;
	//or just let the user value pass through with no algorithm.
	var openingTag = '<span class="highlight">';//used to start the highlight
	var closingTag = '</span>';//used to terminate the highlight
	var openingTagPattern = /<span class=.?highlight.?>/i;//Used to remove the highlight start tag
	var closingTagPattern = /<\/span>/i;//Used to remove the highlight end tag
	txt = txt.replace(openingTagPattern, '').replace(closingTagPattern, '');//Remove existing span tags
	var txtArray = txt.split(' ');// Each word is now an element in an array.
	txtArray = txtArray.slice(0, rr).concat([closingTag]).concat(txtArray.slice(rr));// ... and closing tag after n words.
	p.innerHTML = openingTag + txtArray.join(' ');
}
</script>
</head>
<body>
<div id="para">
I need a script for my website in which there will be a paragraph provided to our visitor. He will be asked for his reading rate like words per minute he can read. Then according to this asked rate the words in that particular paragraph will get highlighted.
</div>
Reading rate&nbsp;<input id="readingRate" value="" size="5">&nbsp;
<input type="button" onclick="highlightText();" value ="Go">
</body>
</html>

Yehtech,

Even better, try this version with bug fix for Opera/Firefox, which for some reason behave slightly differently from IE. Probably in replace() .

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
	"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html>
<head>
<title>Airshow :: Highlight words</title>
<style type="text/css">
#para { margin:0 0 012px 0; width:400px; padding:10px; border:1px solid #999999; font-family:vaerdana,arial; font-size:11pt; }
.highlight { background-color:yellow; }
</style>

<script>
function highlightText(){
	var p = document.getElementById('para');//Get the text div
	var r = document.getElementById('readingRate');//Get the reading rate
	if(!p || !r) { return; }//exit the function if either element is not found
	var txt = p.innerHTML;//Get the text
	var rr = (!r || r.value === '') ? 0 : parseInt(r.value);//Get the reading rate value
	//Apply algorithm here as necessary to multiply/divide/add/subtract the user's value into what you actually want, eg ...
	//rr = rr * 4;
	//or just let the user value pass through with no algorithm.
	var openingTag = '<span class="highlight">';//used to start the highlight
	var closingTag = '</span>';//used to terminate the highlight
	var openingTagPattern = /<span class=.?highlight.?>/i;//Used to remove the highlight start tag
	var closingTagPattern = /<\/span>/i;//Used to remove the highlight end tag
	txt = txt.replace(openingTagPattern, '').replace(closingTagPattern, '').replace('  ', ' ');//Remove existing span tags and double spaces
	var txtArray = txt.split(' ');// Each word is now an element in an array.
	txtArray = txtArray.slice(0, rr).concat([closingTag]).concat(txtArray.slice(rr));// Add closing tag after rr words.
	p.innerHTML = openingTag + txtArray.join(' ');// Prepend opening tag to re-joined text and insert back in its div.
}
</script>
</head>
<body>
<div id="para">
I need a script for my website in which there will be a paragraph provided to our visitor. He will be asked for his reading rate like words per minute he can read. Then according to this asked rate the words in that particular paragraph will get highlighted.
</div>
Reading rate&nbsp;<input id="readingRate" value="" size="5">&nbsp;
<input type="button" onclick="highlightText();" value ="Go">
</body>
</html>

Airshow

dude thanks for this script....i want also that after 1 minute the next words get selected according to the entered rate....

like see

for example

Paragraph:

My name is yehtech. I am a man.

in this paragraph if user enters 2 words per minute then firstly

My name is yehtech. I am man.

then after one min this changes to

My name is yehtech. I am man.

then after one min again

My name is yehtech. I am man.

Aha, you should have said - it's Karaoke! :D

You'll like this:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
	"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html>
<head>
<title>Airshow :: Highlight words</title>
<style type="text/css">
.para { margin:12px 0 012px 0; width:400px; padding:10px; border:2px solid #999999; font-family:vaerdana,arial; font-size:11pt; }
.highlight { background-color:yellow; }
</style>

<script>
function highlightText(){
	var p = document.getElementById('para');//Get the text div
	var r = document.getElementById('readingRate');//Get the reading rate
	if(!p || !r) { return; }//exit the function if either element is not found
	var txt = p.innerHTML;//Get the text
	var rr = (!r || r.value === '') ? 0 : parseInt(r.value);//Get the reading rate value
	//Apply algorithm here as necessary to multiply/divide/add/subtract the user's value into what you actually want, eg ...
	//rr = rr * 4;
	//or just let the user value pass through with no algorithm.
	var openingTag = '<span class="highlight">';//used to start the highlight
	var closingTag = '</span>';//used to terminate the highlight
	var openingTagPattern = /<span class=.?highlight.?>/i;//Used to remove the highlight start tag
	var closingTagPattern = /<\/span>/i;//Used to remove the highlight end tag
	txt = txt.replace(openingTagPattern, '').replace(closingTagPattern, '').replace('  ', ' ');//Remove existing span tags and double spaces
	var txtArray = txt.split(' ');// Each word is now an element in an array.
	txtArray = txtArray.slice(0, rr).concat([closingTag]).concat(txtArray.slice(rr));// Add closing tag after rr words.
	p.innerHTML = openingTag + txtArray.join(' ');// Prepend opening tag to re-joined text and insert back in its div.
}

var Highlighter = function (){
	var allow=false, t=null, pos=0, p=null, r=null, txt='', txtArray=[];
	var openingTag = '<span class="highlight">';// Used to start the highlight
	var closingTag = '</span>';// Used to terminate the highlight
	var openingTagPattern = /<span class=['"]?highlight['"]?>\s?/i;// Used to remove the highlight start tag
	var closingTagPattern = /<\/span>\s?/i;// Used to remove the highlight end tag
	var get = function() { txt = p.innerHTML; };
	var remove = function() { 
		txt = txt.replace(openingTagPattern, '').replace(closingTagPattern, '').replace('  ', ' ');
	};//Remove existing span tags and reduce double spaces
	var split = function() { txtArray = txt.split(/ /); };// Each word is now an element in an array.
	var write = function() { 
		p.innerHTML = txtArray.join(' '); 
	};// Re-joined text and insert back in its div.
	var setAllow = function(bool) {
		allow = bool;
		p.style.borderColor = (bool) ? 'blue' : '#999999';
	};
	return {
		init : function() {
			p = document.getElementById('para2');// Get the text div
			r = document.getElementById('readingRate2');// Get the reading rate
		},
		highlight : function() {
			clearTimeout(t);// In case there's another call up the spout.
			if(!p || !r) { return; }// Exit the function if either element is not found
			var rr = (!r || r.value === '') ? 0 : parseFloat(r.value);// Get the reading rate value
			get();
			remove();
			split();
			txtArray = txtArray.slice(0, pos)
				.concat([openingTag])
				.concat(txtArray.slice(pos, pos+rr))
				.concat([closingTag])
				.concat(txtArray.slice(pos+rr));// Insert highlight tags
			write();
			if(allow && (pos+rr)<txtArray.length) {
				pos += rr;
				t = setTimeout('Highlighter.highlight()', 1000);//Set to 60000 for one minute intervals
			}
			else {
				Highlighter.stop();
				Highlighter.reset();
			}
		},
		start : function() {
			setAllow(true);
			t = null;
			Highlighter.highlight();
		},
		stop : function() {
			setAllow(false);
			clearTimeout(t);
		},
		reset : function() {
			pos = 0;
			get();
			remove();
			split();
			write();
		}
	};
}();

onload = function(){
	Highlighter.init();
}
</script>
</head>
<body>
<div id="para" class="para">
I need a script for my website in which there will be a paragraph provided to our visitor. He will be asked for his reading rate like words per minute he can read. Then according to this asked rate the words in that particular paragraph will get highlighted.
</div>
Reading rate&nbsp;<input id="readingRate" value="" size="5">&nbsp;
<input type="button" onclick="highlightText();" value ="Go">

<div id="para2" class="para">
In the town where I was born <br>
Lived a man who sailed the seas <br>
And he told us of his life <br>
In the <b>land of</b> submarines <br>
So we sailed up to the sun <br>
Till we found the sea of green <br>
And we lived beneath the waves <br>
In our yellow submarine <br>
We all <b>live in a</b> yellow submarine <br>
Yellow submarine, yellow submarine <br>
We all live in a yellow submarine <br>
Yellow submarine, yellow submarine
</div>
Reading rate&nbsp;<input id="readingRate2" value="2" size="5">&nbsp;
<input type="button" onclick="Highlighter.start();" value ="Start">&nbsp;
<input type="button" onclick="Highlighter.stop();"  value ="Stop">&nbsp;
<input type="button" onclick="Highlighter.reset();" value ="Reset">&nbsp;

</body>
</html>

Tested in IE6, FF 3.0.10, Opera 9.01 .

Note that the code doesn't like HTML markup. I found that I could get away with <br>s but only with spaces before them. Just about any other markup breaks the text with random unpredictable results.

With more time the code could be improved to handle markup but for now avoid it. Maybe someone can offer improvements to my code. There may be a wholly RegExp solution, not involving .split() .join()?

Timing is set to 1000 milliseconds (one second) for debugging. Set to 60000 for one minute. The line has a comment against it.

Airshow

thanks Airshow....its awesome....i loved it.....good job man...i think u r an expert at javascript....

can u guide me where i can learn advanced javascript from....

Yehtech,

Just pleased to know you're happy with it.

can u guide me where i can learn advanced javascript from....

Simple. Read and watch everything by Douglas Crockford.

And enjoy every minute of it.

Airshow

This question has already been answered. Start a new discussion instead.