1jQuery.cookie = function(name, value, options) { 2if (typeof value != 'undefined') { 3options = options || {}; 4if (value === null) { 5value = ''; 6options.expires = -1; 7} 8var expires = ''; 9if (options.expires && typeof options.expires == 'number') { 10var date; 11date = new Date(); 12date.setTime(date.getTime() + (options.expires * 24 * 60 * 60 * 1000)); 13expires = '; expires=' + date.toUTCString(); 14} 15document.cookie = [name, '=', encodeURIComponent(value), expires].join(''); 16} else { 17var cookieValue = null; 18if (document.cookie && document.cookie != '') { 19var cookies = document.cookie.split(';'); 20for (var i = 0; i < cookies.length; i++) { 21var cookie = jQuery.trim(cookies[i]); 22if (cookie.substring(0, name.length + 1) == (name + '=')) { 23cookieValue = decodeURIComponent(cookie.substring(name.length + 1)); 24break; 25} 26} 27} 28return cookieValue; 29} 30}; 31function setInputWidth() { 32var width = $("#text1").width(); 33$("#input_text").width(width < 700 ? 700 : width).focus(); 34} 35function convertToHtml(text) { 36return text.replace(/&/g, "&").replace(/</g, "<"); 37} 38function Klava() { 39this.maxLinesText = 3; 40this.maxLinesDict = 5; 41this.sum_error = 0; 42this.count_error = 0; 43this.sum_time = 0; 44this.sum_length = 0; 45this.lines = [{text: "", id: 0}]; 46this.text = [""]; 47this.error_symbols = []; 48this.reset_timer = null; 49this.time_start = null; 50this.position = 0; 51this.mode = "text"; 52this.currentLine = 0; 53this.currentText = 0; 54this.setLines = function(startIndex) { 55var rand = Math.floor(Math.random() * this.text.length); 56var str = this.text[rand]; 57if (this.mode == "dict") { 58var alang = str.split(" = "); 59var avars = alang.length > 1 ? alang[1].split(" ; ") : []; 60if (startIndex == this.currentLine) { 61$("#question").text(alang[0]); 62this.currentText = rand; 63} 64var text = ""; 65if (avars.length > 0) { 66var rand2 = Math.floor(Math.random() * avars.length); 67text = avars[rand2] + "¶"; 68} 69this.lines[startIndex] = {text: text, id: rand}; 70if (startIndex < (this.maxLinesDict - 1)) { 71this.setLines(startIndex + 1); 72} 73} else { 74var index = startIndex; 75while (str.length > 0) { 76if (str.length > 80) { 77var line1_pos = str.substring(0, 81).lastIndexOf(" "); 78this.lines[index] = {text: str.substring(0, line1_pos) + String.fromCharCode(160), id: rand}; 79str = str.substring(line1_pos + 1); 80} else { 81this.lines[index] = {text: str + "¶", id: rand}; 82str = ""; 83} 84index ++; 85} 86if (this.lines.length < (this.maxLinesText - 1) && this.text.length > 1) { 87this.setLines(index); 88} 89} 90} 91this.showLines = function(inputLen) { 92var error_symbols = []; 93for (var i in this.error_symbols) { 94error_symbols[i] = this.error_symbols[i]; 95} 96for (var index = 0; index < (this.mode == "dict" ? this.maxLinesDict : this.maxLinesText); index ++) { 97var end = this.lines[index].text.substring(index == 0 ? inputLen : 0); 98var end_line = ""; 99for (var i = 0; i < end.length; i ++) { 100var symbol = end.substring(i, i + 1); 101if (error_symbols[symbol.toLowerCase()] > 0) { 102end_line = end_line + '<span class="error">' + convertToHtml(symbol) + '</span>'; 103error_symbols[symbol.toLowerCase()] --; 104} else { 105end_line = end_line + convertToHtml(symbol); 106} 107} 108$("#text" + (index + 1)).html((inputLen > 0 && index == 0 ? '<span class="printed">'+convertToHtml(this.lines[index].text.substring(0, inputLen))+'</span>' : "")+end_line); 109} 110} 111this.selLanguage = function() { 112} 113this.showStat = function(speed, errors) { 114var abs_speed = (this.sum_time == 0 ? 0 : (this.sum_length / this.sum_time) * 60); 115var out_abs_error = (this.sum_length == 0 ? 0 : (Math.round((this.sum_error / this.sum_length) * 100 * 100) / 100)); 116var out_error = (Math.round(errors * 100) / 100); 117$("#stat").html( 118"["+Math.round(speed / 6)+"/"+Math.round(abs_speed / 6)+"]words/min"+ 119" "+ 120"["+Math.round(speed)+"/"+Math.round(abs_speed)+"]chars/min"+ 121" "+ 122"["+out_error.toFixed(2)+"/"+out_abs_error.toFixed(2)+"]%" 123); 124} 125this.linesUp = function() { 126for (var i = 0; i < this.lines.length - 1; i ++) { 127this.lines[i] = this.lines[i + 1]; 128$("#text" + (i + 1)).html(convertToHtml(this.lines[i].text)); 129} 130this.lines.pop(); 131} 132this.init = function() { 133this.sum_error = 0; 134this.sum_time = 0; 135this.sum_error = 0; 136this.sum_length = 0; 137this.showStat(0, 0); 138this.error_symbols = []; 139this.currentLine = (this.mode == "dict" ? Math.floor(Math.random() * 7) : 0); 140this.softInit(); 141$("#question").toggle(this.mode == "dict"); 142$("div.data").toggleClass("dict", this.mode == "dict"); 143$("div.text").show(); 144for (var i = ((this.mode == "dict" ? this.maxLinesDict : this.maxLinesText) + 1); i <= 7; i ++) { 145$("#text" + i).parent("div.text").hide(); 146} 147} 148this.softInit = function() { 149if (this.timer) { 150window.clearTimeout(this.timer); 151} 152this.time_start = null; 153this.count_error = 0; 154$("#input_text").val("").removeClass("error"); 155this.lines = [{text: "", id: 0}]; 156this.setLines(0); 157this.position = 0; 158this.showLines(0); 159setInputWidth(); 160} 161this.initLanguage = function() { 162var language = $("#sel_language").val(); 163var klava = this; 164$.ajax({ 165url: language + ".txt", 166success: function(data) { 167klava.text = data.replace(/\t/g, " ").replace(/ {2,}/g, " ").replace(/^ /g, "").replace(/\r/g, "").replace(/\n\n/g,"\n").split("\n"); 168if (language.indexOf("dict_") == 3) { 169klava.mode = "dict"; 170} else { 171klava.mode = "text"; 172} 173klava.init(); 174}, 175error: function() { 176alert("Error"); 177} 178}); 179var lang = language.substring(0, 2); 180if (lang == "en" && ! $("#sel_keyboard option:selected").hasClass("en")) { 181$("#sel_keyboard").val("qwerty").change(); 182} 183if (lang == "ru" && ! $("#sel_keyboard option:selected").hasClass("ru")) { 184$("#sel_keyboard").val("rus_win").change(); 185} 186$("#sel_keyboard option").hide(); 187$("#sel_keyboard ." + lang).show(); 188} 189this.initKeyboard = function() { 190var keyboard = $("#sel_keyboard").val(); 191$("div.keyboard").hide(); 192$("#kb_" + keyboard).show(); 193if (keyboard == "dzen") { 194$("#show_color").hide(); 195} else { 196$("#show_color").show(); 197} 198} 199this.initColor = function() { 200if ($("#show_color").get(0).checked) { 201$("#keyboard div.block").removeClass("bw"); 202} else { 203$("#keyboard div.block").addClass("bw"); 204} 205} 206} 207$(function() { 208var klava = new Klava(); 209$("#sel_reload").click(function() { 210klava.softInit(); 211}); 212if ($.cookie("klavarog_language")) 213$("#sel_language").val($.cookie("klavarog_language")); 214$("#sel_language").change(function() { 215var language = $(this).val(); 216$.cookie("klavarog_language", language, {expires: 100}); 217klava.initLanguage(); 218$("#input_text").focus(); 219}); 220klava.initLanguage(); 221if ($.cookie("klavarog_keyboard")) 222$("#sel_keyboard").val($.cookie("klavarog_keyboard")); 223$("#sel_keyboard").change(function() { 224var keyboard = $(this).val(); 225$.cookie("klavarog_keyboard", keyboard, {expires: 100}); 226klava.initKeyboard(); 227$("#input_text").focus(); 228}); 229klava.initKeyboard(); 230if ($.cookie("klavarog_color")) 231$("#show_color").get(0).checked = ($.cookie("klavarog_color") != "false"); 232$("#show_color").change(function() { 233$.cookie("klavarog_color", $(this).get(0).checked, {expires: 100}); 234klava.initColor(); 235$("#input_text").focus(); 236}).click(function() { 237$(this).change(); 238}); 239klava.initColor(); 240//$("div.mac_enter").css({position: "absolute", marginLeft: ($.browser.opera ? 489 : 0), zIndex: -2, display: "inline", height: 56}); 241$("div.mac_enter").css({position: "absolute", marginLeft: 0, zIndex: -2, display: "inline", height: 56}); 242$("#input_text").keyup(function(event) { 243if (klava.reset_timer) { 244window.clearTimeout(klava.reset_timer); 245} 246klava.reset_timer = window.setTimeout(function() { 247$("#input_text").val("").keyup(); 248}, 15000); 249if (klava.time_start == null) { 250klava.time_start = new Date(); 251} 252var input = $(this).val(); 253if (event.which == 13) { 254input = input + "¶"; 255$(this).val(input); 256} 257if (input == "") { 258klava.time_start = null; 259klava.count_error = 0; 260} 261if (klava.mode == "dict") { 262var is_not_error = false;
263for (var i = 0; i < klava.maxLinesDict; i ++) { 264if (klava.lines[i].text.substring(0, input.length) == input) { 265is_not_error = true; 266$("#text" + (i + 1)).html('<span class="printed">'+convertToHtml(klava.lines[i].text.substring(0, input.length))+'</span>'+convertToHtml(klava.lines[i].text.substring(input.length))); 267} else { 268$("#text" + (i + 1)).html(convertToHtml(klava.lines[i].text)); 269} 270} 271$(this).toggleClass("error", ! is_not_error); 272} else { 273var top_line = klava.lines[0].text.replace(String.fromCharCode(160), " "); 274var symbol = top_line.substring(klava.position, klava.position + 1).toLowerCase(); 275if (top_line.substring(0, input.length) != input.substring(0, top_line.length)) { 276if ( ! $(this).hasClass("error")) { 277klava.count_error ++; 278if (symbol != " " && symbol != "¶") { 279klava.error_symbols[symbol] = (klava.error_symbols[symbol] ? klava.error_symbols[symbol] + 7 : 7); 280} 281window.status = event.which; 282$(this).addClass("error"); 283klava.showLines(klava.position); 284} 285} else if (top_line != "") { 286if (klava.error_symbols[symbol] > 0 && klava.position < input.length) { 287klava.error_symbols[symbol] = klava.error_symbols[symbol] - 1; 288} 289klava.position = input.length; 290$(this).removeClass("error"); 291if (input.length >= top_line.length) { 292$(this).val(input.substring(top_line.length)); 293var time_stop = new Date(); 294var time = (time_stop - klava.time_start) / 1000; 295klava.sum_time += time; 296klava.sum_length += top_line.length; 297var speed = (input.length / time) * 60; 298var errors = (klava.count_error / input.length) * 100; 299klava.sum_error += klava.count_error; 300klava.count_error = 0; 301klava.position = 0; 302klava.time_start = null; 303klava.showStat(speed, errors); 304klava.linesUp(); 305if (klava.lines.length < klava.maxLinesText) { 306klava.setLines(klava.lines.length); 307} 308setInputWidth(); 309$(this).keyup(); 310} else { 311klava.showLines(input.length); 312} 313} 314} 315}).keyup(); 316});
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.