annotate doc/html/search/search.js @ 69:1df0d2eb701c

flow: Created branch 'release/1.0.0'.
author Adam Stark <adamstark@users.noreply.github.com>
date Tue, 08 Jul 2014 12:22:37 +0100
parents 105999275c2e
children d6d9df2db3e1
rev   line source
adamstark@60 1 // Search script generated by doxygen
adamstark@60 2 // Copyright (C) 2009 by Dimitri van Heesch.
adamstark@60 3
adamstark@60 4 // The code in this file is loosly based on main.js, part of Natural Docs,
adamstark@60 5 // which is Copyright (C) 2003-2008 Greg Valure
adamstark@60 6 // Natural Docs is licensed under the GPL.
adamstark@60 7
adamstark@60 8 var indexSectionsWithContent =
adamstark@60 9 {
adamstark@65 10 0: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000011101101000001100101010000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
adamstark@60 11 1: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
adamstark@60 12 2: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
adamstark@65 13 3: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000011101101000001100101000000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
adamstark@61 14 4: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
adamstark@61 15 5: "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"
adamstark@60 16 };
adamstark@60 17
adamstark@60 18 var indexSectionNames =
adamstark@60 19 {
adamstark@60 20 0: "all",
adamstark@60 21 1: "classes",
adamstark@60 22 2: "files",
adamstark@60 23 3: "functions",
adamstark@61 24 4: "enums",
adamstark@61 25 5: "pages"
adamstark@60 26 };
adamstark@60 27
adamstark@60 28 function convertToId(search)
adamstark@60 29 {
adamstark@60 30 var result = '';
adamstark@60 31 for (i=0;i<search.length;i++)
adamstark@60 32 {
adamstark@60 33 var c = search.charAt(i);
adamstark@60 34 var cn = c.charCodeAt(0);
adamstark@60 35 if (c.match(/[a-z0-9]/))
adamstark@60 36 {
adamstark@60 37 result+=c;
adamstark@60 38 }
adamstark@60 39 else if (cn<16)
adamstark@60 40 {
adamstark@60 41 result+="_0"+cn.toString(16);
adamstark@60 42 }
adamstark@60 43 else
adamstark@60 44 {
adamstark@60 45 result+="_"+cn.toString(16);
adamstark@60 46 }
adamstark@60 47 }
adamstark@60 48 return result;
adamstark@60 49 }
adamstark@60 50
adamstark@60 51 function getXPos(item)
adamstark@60 52 {
adamstark@60 53 var x = 0;
adamstark@60 54 if (item.offsetWidth)
adamstark@60 55 {
adamstark@60 56 while (item && item!=document.body)
adamstark@60 57 {
adamstark@60 58 x += item.offsetLeft;
adamstark@60 59 item = item.offsetParent;
adamstark@60 60 }
adamstark@60 61 }
adamstark@60 62 return x;
adamstark@60 63 }
adamstark@60 64
adamstark@60 65 function getYPos(item)
adamstark@60 66 {
adamstark@60 67 var y = 0;
adamstark@60 68 if (item.offsetWidth)
adamstark@60 69 {
adamstark@60 70 while (item && item!=document.body)
adamstark@60 71 {
adamstark@60 72 y += item.offsetTop;
adamstark@60 73 item = item.offsetParent;
adamstark@60 74 }
adamstark@60 75 }
adamstark@60 76 return y;
adamstark@60 77 }
adamstark@60 78
adamstark@60 79 /* A class handling everything associated with the search panel.
adamstark@60 80
adamstark@60 81 Parameters:
adamstark@60 82 name - The name of the global variable that will be
adamstark@60 83 storing this instance. Is needed to be able to set timeouts.
adamstark@60 84 resultPath - path to use for external files
adamstark@60 85 */
adamstark@60 86 function SearchBox(name, resultsPath, inFrame, label)
adamstark@60 87 {
adamstark@60 88 if (!name || !resultsPath) { alert("Missing parameters to SearchBox."); }
adamstark@60 89
adamstark@60 90 // ---------- Instance variables
adamstark@60 91 this.name = name;
adamstark@60 92 this.resultsPath = resultsPath;
adamstark@60 93 this.keyTimeout = 0;
adamstark@60 94 this.keyTimeoutLength = 500;
adamstark@60 95 this.closeSelectionTimeout = 300;
adamstark@60 96 this.lastSearchValue = "";
adamstark@60 97 this.lastResultsPage = "";
adamstark@60 98 this.hideTimeout = 0;
adamstark@60 99 this.searchIndex = 0;
adamstark@60 100 this.searchActive = false;
adamstark@60 101 this.insideFrame = inFrame;
adamstark@60 102 this.searchLabel = label;
adamstark@60 103
adamstark@60 104 // ----------- DOM Elements
adamstark@60 105
adamstark@60 106 this.DOMSearchField = function()
adamstark@60 107 { return document.getElementById("MSearchField"); }
adamstark@60 108
adamstark@60 109 this.DOMSearchSelect = function()
adamstark@60 110 { return document.getElementById("MSearchSelect"); }
adamstark@60 111
adamstark@60 112 this.DOMSearchSelectWindow = function()
adamstark@60 113 { return document.getElementById("MSearchSelectWindow"); }
adamstark@60 114
adamstark@60 115 this.DOMPopupSearchResults = function()
adamstark@60 116 { return document.getElementById("MSearchResults"); }
adamstark@60 117
adamstark@60 118 this.DOMPopupSearchResultsWindow = function()
adamstark@60 119 { return document.getElementById("MSearchResultsWindow"); }
adamstark@60 120
adamstark@60 121 this.DOMSearchClose = function()
adamstark@60 122 { return document.getElementById("MSearchClose"); }
adamstark@60 123
adamstark@60 124 this.DOMSearchBox = function()
adamstark@60 125 { return document.getElementById("MSearchBox"); }
adamstark@60 126
adamstark@60 127 // ------------ Event Handlers
adamstark@60 128
adamstark@60 129 // Called when focus is added or removed from the search field.
adamstark@60 130 this.OnSearchFieldFocus = function(isActive)
adamstark@60 131 {
adamstark@60 132 this.Activate(isActive);
adamstark@60 133 }
adamstark@60 134
adamstark@60 135 this.OnSearchSelectShow = function()
adamstark@60 136 {
adamstark@60 137 var searchSelectWindow = this.DOMSearchSelectWindow();
adamstark@60 138 var searchField = this.DOMSearchSelect();
adamstark@60 139
adamstark@60 140 if (this.insideFrame)
adamstark@60 141 {
adamstark@60 142 var left = getXPos(searchField);
adamstark@60 143 var top = getYPos(searchField);
adamstark@60 144 left += searchField.offsetWidth + 6;
adamstark@60 145 top += searchField.offsetHeight;
adamstark@60 146
adamstark@60 147 // show search selection popup
adamstark@60 148 searchSelectWindow.style.display='block';
adamstark@60 149 left -= searchSelectWindow.offsetWidth;
adamstark@60 150 searchSelectWindow.style.left = left + 'px';
adamstark@60 151 searchSelectWindow.style.top = top + 'px';
adamstark@60 152 }
adamstark@60 153 else
adamstark@60 154 {
adamstark@60 155 var left = getXPos(searchField);
adamstark@60 156 var top = getYPos(searchField);
adamstark@60 157 top += searchField.offsetHeight;
adamstark@60 158
adamstark@60 159 // show search selection popup
adamstark@60 160 searchSelectWindow.style.display='block';
adamstark@60 161 searchSelectWindow.style.left = left + 'px';
adamstark@60 162 searchSelectWindow.style.top = top + 'px';
adamstark@60 163 }
adamstark@60 164
adamstark@60 165 // stop selection hide timer
adamstark@60 166 if (this.hideTimeout)
adamstark@60 167 {
adamstark@60 168 clearTimeout(this.hideTimeout);
adamstark@60 169 this.hideTimeout=0;
adamstark@60 170 }
adamstark@60 171 return false; // to avoid "image drag" default event
adamstark@60 172 }
adamstark@60 173
adamstark@60 174 this.OnSearchSelectHide = function()
adamstark@60 175 {
adamstark@60 176 this.hideTimeout = setTimeout(this.name +".CloseSelectionWindow()",
adamstark@60 177 this.closeSelectionTimeout);
adamstark@60 178 }
adamstark@60 179
adamstark@60 180 // Called when the content of the search field is changed.
adamstark@60 181 this.OnSearchFieldChange = function(evt)
adamstark@60 182 {
adamstark@60 183 if (this.keyTimeout) // kill running timer
adamstark@60 184 {
adamstark@60 185 clearTimeout(this.keyTimeout);
adamstark@60 186 this.keyTimeout = 0;
adamstark@60 187 }
adamstark@60 188
adamstark@60 189 var e = (evt) ? evt : window.event; // for IE
adamstark@60 190 if (e.keyCode==40 || e.keyCode==13)
adamstark@60 191 {
adamstark@60 192 if (e.shiftKey==1)
adamstark@60 193 {
adamstark@60 194 this.OnSearchSelectShow();
adamstark@60 195 var win=this.DOMSearchSelectWindow();
adamstark@60 196 for (i=0;i<win.childNodes.length;i++)
adamstark@60 197 {
adamstark@60 198 var child = win.childNodes[i]; // get span within a
adamstark@60 199 if (child.className=='SelectItem')
adamstark@60 200 {
adamstark@60 201 child.focus();
adamstark@60 202 return;
adamstark@60 203 }
adamstark@60 204 }
adamstark@60 205 return;
adamstark@60 206 }
adamstark@60 207 else if (window.frames.MSearchResults.searchResults)
adamstark@60 208 {
adamstark@60 209 var elem = window.frames.MSearchResults.searchResults.NavNext(0);
adamstark@60 210 if (elem) elem.focus();
adamstark@60 211 }
adamstark@60 212 }
adamstark@60 213 else if (e.keyCode==27) // Escape out of the search field
adamstark@60 214 {
adamstark@60 215 this.DOMSearchField().blur();
adamstark@60 216 this.DOMPopupSearchResultsWindow().style.display = 'none';
adamstark@60 217 this.DOMSearchClose().style.display = 'none';
adamstark@60 218 this.lastSearchValue = '';
adamstark@60 219 this.Activate(false);
adamstark@60 220 return;
adamstark@60 221 }
adamstark@60 222
adamstark@60 223 // strip whitespaces
adamstark@60 224 var searchValue = this.DOMSearchField().value.replace(/ +/g, "");
adamstark@60 225
adamstark@60 226 if (searchValue != this.lastSearchValue) // search value has changed
adamstark@60 227 {
adamstark@60 228 if (searchValue != "") // non-empty search
adamstark@60 229 {
adamstark@60 230 // set timer for search update
adamstark@60 231 this.keyTimeout = setTimeout(this.name + '.Search()',
adamstark@60 232 this.keyTimeoutLength);
adamstark@60 233 }
adamstark@60 234 else // empty search field
adamstark@60 235 {
adamstark@60 236 this.DOMPopupSearchResultsWindow().style.display = 'none';
adamstark@60 237 this.DOMSearchClose().style.display = 'none';
adamstark@60 238 this.lastSearchValue = '';
adamstark@60 239 }
adamstark@60 240 }
adamstark@60 241 }
adamstark@60 242
adamstark@60 243 this.SelectItemCount = function(id)
adamstark@60 244 {
adamstark@60 245 var count=0;
adamstark@60 246 var win=this.DOMSearchSelectWindow();
adamstark@60 247 for (i=0;i<win.childNodes.length;i++)
adamstark@60 248 {
adamstark@60 249 var child = win.childNodes[i]; // get span within a
adamstark@60 250 if (child.className=='SelectItem')
adamstark@60 251 {
adamstark@60 252 count++;
adamstark@60 253 }
adamstark@60 254 }
adamstark@60 255 return count;
adamstark@60 256 }
adamstark@60 257
adamstark@60 258 this.SelectItemSet = function(id)
adamstark@60 259 {
adamstark@60 260 var i,j=0;
adamstark@60 261 var win=this.DOMSearchSelectWindow();
adamstark@60 262 for (i=0;i<win.childNodes.length;i++)
adamstark@60 263 {
adamstark@60 264 var child = win.childNodes[i]; // get span within a
adamstark@60 265 if (child.className=='SelectItem')
adamstark@60 266 {
adamstark@60 267 var node = child.firstChild;
adamstark@60 268 if (j==id)
adamstark@60 269 {
adamstark@60 270 node.innerHTML='&#8226;';
adamstark@60 271 }
adamstark@60 272 else
adamstark@60 273 {
adamstark@60 274 node.innerHTML='&#160;';
adamstark@60 275 }
adamstark@60 276 j++;
adamstark@60 277 }
adamstark@60 278 }
adamstark@60 279 }
adamstark@60 280
adamstark@60 281 // Called when an search filter selection is made.
adamstark@60 282 // set item with index id as the active item
adamstark@60 283 this.OnSelectItem = function(id)
adamstark@60 284 {
adamstark@60 285 this.searchIndex = id;
adamstark@60 286 this.SelectItemSet(id);
adamstark@60 287 var searchValue = this.DOMSearchField().value.replace(/ +/g, "");
adamstark@60 288 if (searchValue!="" && this.searchActive) // something was found -> do a search
adamstark@60 289 {
adamstark@60 290 this.Search();
adamstark@60 291 }
adamstark@60 292 }
adamstark@60 293
adamstark@60 294 this.OnSearchSelectKey = function(evt)
adamstark@60 295 {
adamstark@60 296 var e = (evt) ? evt : window.event; // for IE
adamstark@60 297 if (e.keyCode==40 && this.searchIndex<this.SelectItemCount()) // Down
adamstark@60 298 {
adamstark@60 299 this.searchIndex++;
adamstark@60 300 this.OnSelectItem(this.searchIndex);
adamstark@60 301 }
adamstark@60 302 else if (e.keyCode==38 && this.searchIndex>0) // Up
adamstark@60 303 {
adamstark@60 304 this.searchIndex--;
adamstark@60 305 this.OnSelectItem(this.searchIndex);
adamstark@60 306 }
adamstark@60 307 else if (e.keyCode==13 || e.keyCode==27)
adamstark@60 308 {
adamstark@60 309 this.OnSelectItem(this.searchIndex);
adamstark@60 310 this.CloseSelectionWindow();
adamstark@60 311 this.DOMSearchField().focus();
adamstark@60 312 }
adamstark@60 313 return false;
adamstark@60 314 }
adamstark@60 315
adamstark@60 316 // --------- Actions
adamstark@60 317
adamstark@60 318 // Closes the results window.
adamstark@60 319 this.CloseResultsWindow = function()
adamstark@60 320 {
adamstark@60 321 this.DOMPopupSearchResultsWindow().style.display = 'none';
adamstark@60 322 this.DOMSearchClose().style.display = 'none';
adamstark@60 323 this.Activate(false);
adamstark@60 324 }
adamstark@60 325
adamstark@60 326 this.CloseSelectionWindow = function()
adamstark@60 327 {
adamstark@60 328 this.DOMSearchSelectWindow().style.display = 'none';
adamstark@60 329 }
adamstark@60 330
adamstark@60 331 // Performs a search.
adamstark@60 332 this.Search = function()
adamstark@60 333 {
adamstark@60 334 this.keyTimeout = 0;
adamstark@60 335
adamstark@60 336 // strip leading whitespace
adamstark@60 337 var searchValue = this.DOMSearchField().value.replace(/^ +/, "");
adamstark@60 338
adamstark@60 339 var code = searchValue.toLowerCase().charCodeAt(0);
adamstark@60 340 var hexCode;
adamstark@60 341 if (code<16)
adamstark@60 342 {
adamstark@60 343 hexCode="0"+code.toString(16);
adamstark@60 344 }
adamstark@60 345 else
adamstark@60 346 {
adamstark@60 347 hexCode=code.toString(16);
adamstark@60 348 }
adamstark@60 349
adamstark@60 350 var resultsPage;
adamstark@60 351 var resultsPageWithSearch;
adamstark@60 352 var hasResultsPage;
adamstark@60 353
adamstark@60 354 if (indexSectionsWithContent[this.searchIndex].charAt(code) == '1')
adamstark@60 355 {
adamstark@60 356 resultsPage = this.resultsPath + '/' + indexSectionNames[this.searchIndex] + '_' + hexCode + '.html';
adamstark@60 357 resultsPageWithSearch = resultsPage+'?'+escape(searchValue);
adamstark@60 358 hasResultsPage = true;
adamstark@60 359 }
adamstark@60 360 else // nothing available for this search term
adamstark@60 361 {
adamstark@60 362 resultsPage = this.resultsPath + '/nomatches.html';
adamstark@60 363 resultsPageWithSearch = resultsPage;
adamstark@60 364 hasResultsPage = false;
adamstark@60 365 }
adamstark@60 366
adamstark@60 367 window.frames.MSearchResults.location = resultsPageWithSearch;
adamstark@60 368 var domPopupSearchResultsWindow = this.DOMPopupSearchResultsWindow();
adamstark@60 369
adamstark@60 370 if (domPopupSearchResultsWindow.style.display!='block')
adamstark@60 371 {
adamstark@60 372 var domSearchBox = this.DOMSearchBox();
adamstark@60 373 this.DOMSearchClose().style.display = 'inline';
adamstark@60 374 if (this.insideFrame)
adamstark@60 375 {
adamstark@60 376 var domPopupSearchResults = this.DOMPopupSearchResults();
adamstark@60 377 domPopupSearchResultsWindow.style.position = 'relative';
adamstark@60 378 domPopupSearchResultsWindow.style.display = 'block';
adamstark@60 379 var width = document.body.clientWidth - 8; // the -8 is for IE :-(
adamstark@60 380 domPopupSearchResultsWindow.style.width = width + 'px';
adamstark@60 381 domPopupSearchResults.style.width = width + 'px';
adamstark@60 382 }
adamstark@60 383 else
adamstark@60 384 {
adamstark@60 385 var domPopupSearchResults = this.DOMPopupSearchResults();
adamstark@60 386 var left = getXPos(domSearchBox) + 150; // domSearchBox.offsetWidth;
adamstark@60 387 var top = getYPos(domSearchBox) + 20; // domSearchBox.offsetHeight + 1;
adamstark@60 388 domPopupSearchResultsWindow.style.display = 'block';
adamstark@60 389 left -= domPopupSearchResults.offsetWidth;
adamstark@60 390 domPopupSearchResultsWindow.style.top = top + 'px';
adamstark@60 391 domPopupSearchResultsWindow.style.left = left + 'px';
adamstark@60 392 }
adamstark@60 393 }
adamstark@60 394
adamstark@60 395 this.lastSearchValue = searchValue;
adamstark@60 396 this.lastResultsPage = resultsPage;
adamstark@60 397 }
adamstark@60 398
adamstark@60 399 // -------- Activation Functions
adamstark@60 400
adamstark@60 401 // Activates or deactivates the search panel, resetting things to
adamstark@60 402 // their default values if necessary.
adamstark@60 403 this.Activate = function(isActive)
adamstark@60 404 {
adamstark@60 405 if (isActive || // open it
adamstark@60 406 this.DOMPopupSearchResultsWindow().style.display == 'block'
adamstark@60 407 )
adamstark@60 408 {
adamstark@60 409 this.DOMSearchBox().className = 'MSearchBoxActive';
adamstark@60 410
adamstark@60 411 var searchField = this.DOMSearchField();
adamstark@60 412
adamstark@60 413 if (searchField.value == this.searchLabel) // clear "Search" term upon entry
adamstark@60 414 {
adamstark@60 415 searchField.value = '';
adamstark@60 416 this.searchActive = true;
adamstark@60 417 }
adamstark@60 418 }
adamstark@60 419 else if (!isActive) // directly remove the panel
adamstark@60 420 {
adamstark@60 421 this.DOMSearchBox().className = 'MSearchBoxInactive';
adamstark@60 422 this.DOMSearchField().value = this.searchLabel;
adamstark@60 423 this.searchActive = false;
adamstark@60 424 this.lastSearchValue = ''
adamstark@60 425 this.lastResultsPage = '';
adamstark@60 426 }
adamstark@60 427 }
adamstark@60 428 }
adamstark@60 429
adamstark@60 430 // -----------------------------------------------------------------------
adamstark@60 431
adamstark@60 432 // The class that handles everything on the search results page.
adamstark@60 433 function SearchResults(name)
adamstark@60 434 {
adamstark@60 435 // The number of matches from the last run of <Search()>.
adamstark@60 436 this.lastMatchCount = 0;
adamstark@60 437 this.lastKey = 0;
adamstark@60 438 this.repeatOn = false;
adamstark@60 439
adamstark@60 440 // Toggles the visibility of the passed element ID.
adamstark@60 441 this.FindChildElement = function(id)
adamstark@60 442 {
adamstark@60 443 var parentElement = document.getElementById(id);
adamstark@60 444 var element = parentElement.firstChild;
adamstark@60 445
adamstark@60 446 while (element && element!=parentElement)
adamstark@60 447 {
adamstark@60 448 if (element.nodeName == 'DIV' && element.className == 'SRChildren')
adamstark@60 449 {
adamstark@60 450 return element;
adamstark@60 451 }
adamstark@60 452
adamstark@60 453 if (element.nodeName == 'DIV' && element.hasChildNodes())
adamstark@60 454 {
adamstark@60 455 element = element.firstChild;
adamstark@60 456 }
adamstark@60 457 else if (element.nextSibling)
adamstark@60 458 {
adamstark@60 459 element = element.nextSibling;
adamstark@60 460 }
adamstark@60 461 else
adamstark@60 462 {
adamstark@60 463 do
adamstark@60 464 {
adamstark@60 465 element = element.parentNode;
adamstark@60 466 }
adamstark@60 467 while (element && element!=parentElement && !element.nextSibling);
adamstark@60 468
adamstark@60 469 if (element && element!=parentElement)
adamstark@60 470 {
adamstark@60 471 element = element.nextSibling;
adamstark@60 472 }
adamstark@60 473 }
adamstark@60 474 }
adamstark@60 475 }
adamstark@60 476
adamstark@60 477 this.Toggle = function(id)
adamstark@60 478 {
adamstark@60 479 var element = this.FindChildElement(id);
adamstark@60 480 if (element)
adamstark@60 481 {
adamstark@60 482 if (element.style.display == 'block')
adamstark@60 483 {
adamstark@60 484 element.style.display = 'none';
adamstark@60 485 }
adamstark@60 486 else
adamstark@60 487 {
adamstark@60 488 element.style.display = 'block';
adamstark@60 489 }
adamstark@60 490 }
adamstark@60 491 }
adamstark@60 492
adamstark@60 493 // Searches for the passed string. If there is no parameter,
adamstark@60 494 // it takes it from the URL query.
adamstark@60 495 //
adamstark@60 496 // Always returns true, since other documents may try to call it
adamstark@60 497 // and that may or may not be possible.
adamstark@60 498 this.Search = function(search)
adamstark@60 499 {
adamstark@60 500 if (!search) // get search word from URL
adamstark@60 501 {
adamstark@60 502 search = window.location.search;
adamstark@60 503 search = search.substring(1); // Remove the leading '?'
adamstark@60 504 search = unescape(search);
adamstark@60 505 }
adamstark@60 506
adamstark@60 507 search = search.replace(/^ +/, ""); // strip leading spaces
adamstark@60 508 search = search.replace(/ +$/, ""); // strip trailing spaces
adamstark@60 509 search = search.toLowerCase();
adamstark@60 510 search = convertToId(search);
adamstark@60 511
adamstark@60 512 var resultRows = document.getElementsByTagName("div");
adamstark@60 513 var matches = 0;
adamstark@60 514
adamstark@60 515 var i = 0;
adamstark@60 516 while (i < resultRows.length)
adamstark@60 517 {
adamstark@60 518 var row = resultRows.item(i);
adamstark@60 519 if (row.className == "SRResult")
adamstark@60 520 {
adamstark@60 521 var rowMatchName = row.id.toLowerCase();
adamstark@60 522 rowMatchName = rowMatchName.replace(/^sr\d*_/, ''); // strip 'sr123_'
adamstark@60 523
adamstark@60 524 if (search.length<=rowMatchName.length &&
adamstark@60 525 rowMatchName.substr(0, search.length)==search)
adamstark@60 526 {
adamstark@60 527 row.style.display = 'block';
adamstark@60 528 matches++;
adamstark@60 529 }
adamstark@60 530 else
adamstark@60 531 {
adamstark@60 532 row.style.display = 'none';
adamstark@60 533 }
adamstark@60 534 }
adamstark@60 535 i++;
adamstark@60 536 }
adamstark@60 537 document.getElementById("Searching").style.display='none';
adamstark@60 538 if (matches == 0) // no results
adamstark@60 539 {
adamstark@60 540 document.getElementById("NoMatches").style.display='block';
adamstark@60 541 }
adamstark@60 542 else // at least one result
adamstark@60 543 {
adamstark@60 544 document.getElementById("NoMatches").style.display='none';
adamstark@60 545 }
adamstark@60 546 this.lastMatchCount = matches;
adamstark@60 547 return true;
adamstark@60 548 }
adamstark@60 549
adamstark@60 550 // return the first item with index index or higher that is visible
adamstark@60 551 this.NavNext = function(index)
adamstark@60 552 {
adamstark@60 553 var focusItem;
adamstark@60 554 while (1)
adamstark@60 555 {
adamstark@60 556 var focusName = 'Item'+index;
adamstark@60 557 focusItem = document.getElementById(focusName);
adamstark@60 558 if (focusItem && focusItem.parentNode.parentNode.style.display=='block')
adamstark@60 559 {
adamstark@60 560 break;
adamstark@60 561 }
adamstark@60 562 else if (!focusItem) // last element
adamstark@60 563 {
adamstark@60 564 break;
adamstark@60 565 }
adamstark@60 566 focusItem=null;
adamstark@60 567 index++;
adamstark@60 568 }
adamstark@60 569 return focusItem;
adamstark@60 570 }
adamstark@60 571
adamstark@60 572 this.NavPrev = function(index)
adamstark@60 573 {
adamstark@60 574 var focusItem;
adamstark@60 575 while (1)
adamstark@60 576 {
adamstark@60 577 var focusName = 'Item'+index;
adamstark@60 578 focusItem = document.getElementById(focusName);
adamstark@60 579 if (focusItem && focusItem.parentNode.parentNode.style.display=='block')
adamstark@60 580 {
adamstark@60 581 break;
adamstark@60 582 }
adamstark@60 583 else if (!focusItem) // last element
adamstark@60 584 {
adamstark@60 585 break;
adamstark@60 586 }
adamstark@60 587 focusItem=null;
adamstark@60 588 index--;
adamstark@60 589 }
adamstark@60 590 return focusItem;
adamstark@60 591 }
adamstark@60 592
adamstark@60 593 this.ProcessKeys = function(e)
adamstark@60 594 {
adamstark@60 595 if (e.type == "keydown")
adamstark@60 596 {
adamstark@60 597 this.repeatOn = false;
adamstark@60 598 this.lastKey = e.keyCode;
adamstark@60 599 }
adamstark@60 600 else if (e.type == "keypress")
adamstark@60 601 {
adamstark@60 602 if (!this.repeatOn)
adamstark@60 603 {
adamstark@60 604 if (this.lastKey) this.repeatOn = true;
adamstark@60 605 return false; // ignore first keypress after keydown
adamstark@60 606 }
adamstark@60 607 }
adamstark@60 608 else if (e.type == "keyup")
adamstark@60 609 {
adamstark@60 610 this.lastKey = 0;
adamstark@60 611 this.repeatOn = false;
adamstark@60 612 }
adamstark@60 613 return this.lastKey!=0;
adamstark@60 614 }
adamstark@60 615
adamstark@60 616 this.Nav = function(evt,itemIndex)
adamstark@60 617 {
adamstark@60 618 var e = (evt) ? evt : window.event; // for IE
adamstark@60 619 if (e.keyCode==13) return true;
adamstark@60 620 if (!this.ProcessKeys(e)) return false;
adamstark@60 621
adamstark@60 622 if (this.lastKey==38) // Up
adamstark@60 623 {
adamstark@60 624 var newIndex = itemIndex-1;
adamstark@60 625 var focusItem = this.NavPrev(newIndex);
adamstark@60 626 if (focusItem)
adamstark@60 627 {
adamstark@60 628 var child = this.FindChildElement(focusItem.parentNode.parentNode.id);
adamstark@60 629 if (child && child.style.display == 'block') // children visible
adamstark@60 630 {
adamstark@60 631 var n=0;
adamstark@60 632 var tmpElem;
adamstark@60 633 while (1) // search for last child
adamstark@60 634 {
adamstark@60 635 tmpElem = document.getElementById('Item'+newIndex+'_c'+n);
adamstark@60 636 if (tmpElem)
adamstark@60 637 {
adamstark@60 638 focusItem = tmpElem;
adamstark@60 639 }
adamstark@60 640 else // found it!
adamstark@60 641 {
adamstark@60 642 break;
adamstark@60 643 }
adamstark@60 644 n++;
adamstark@60 645 }
adamstark@60 646 }
adamstark@60 647 }
adamstark@60 648 if (focusItem)
adamstark@60 649 {
adamstark@60 650 focusItem.focus();
adamstark@60 651 }
adamstark@60 652 else // return focus to search field
adamstark@60 653 {
adamstark@60 654 parent.document.getElementById("MSearchField").focus();
adamstark@60 655 }
adamstark@60 656 }
adamstark@60 657 else if (this.lastKey==40) // Down
adamstark@60 658 {
adamstark@60 659 var newIndex = itemIndex+1;
adamstark@60 660 var focusItem;
adamstark@60 661 var item = document.getElementById('Item'+itemIndex);
adamstark@60 662 var elem = this.FindChildElement(item.parentNode.parentNode.id);
adamstark@60 663 if (elem && elem.style.display == 'block') // children visible
adamstark@60 664 {
adamstark@60 665 focusItem = document.getElementById('Item'+itemIndex+'_c0');
adamstark@60 666 }
adamstark@60 667 if (!focusItem) focusItem = this.NavNext(newIndex);
adamstark@60 668 if (focusItem) focusItem.focus();
adamstark@60 669 }
adamstark@60 670 else if (this.lastKey==39) // Right
adamstark@60 671 {
adamstark@60 672 var item = document.getElementById('Item'+itemIndex);
adamstark@60 673 var elem = this.FindChildElement(item.parentNode.parentNode.id);
adamstark@60 674 if (elem) elem.style.display = 'block';
adamstark@60 675 }
adamstark@60 676 else if (this.lastKey==37) // Left
adamstark@60 677 {
adamstark@60 678 var item = document.getElementById('Item'+itemIndex);
adamstark@60 679 var elem = this.FindChildElement(item.parentNode.parentNode.id);
adamstark@60 680 if (elem) elem.style.display = 'none';
adamstark@60 681 }
adamstark@60 682 else if (this.lastKey==27) // Escape
adamstark@60 683 {
adamstark@60 684 parent.searchBox.CloseResultsWindow();
adamstark@60 685 parent.document.getElementById("MSearchField").focus();
adamstark@60 686 }
adamstark@60 687 else if (this.lastKey==13) // Enter
adamstark@60 688 {
adamstark@60 689 return true;
adamstark@60 690 }
adamstark@60 691 return false;
adamstark@60 692 }
adamstark@60 693
adamstark@60 694 this.NavChild = function(evt,itemIndex,childIndex)
adamstark@60 695 {
adamstark@60 696 var e = (evt) ? evt : window.event; // for IE
adamstark@60 697 if (e.keyCode==13) return true;
adamstark@60 698 if (!this.ProcessKeys(e)) return false;
adamstark@60 699
adamstark@60 700 if (this.lastKey==38) // Up
adamstark@60 701 {
adamstark@60 702 if (childIndex>0)
adamstark@60 703 {
adamstark@60 704 var newIndex = childIndex-1;
adamstark@60 705 document.getElementById('Item'+itemIndex+'_c'+newIndex).focus();
adamstark@60 706 }
adamstark@60 707 else // already at first child, jump to parent
adamstark@60 708 {
adamstark@60 709 document.getElementById('Item'+itemIndex).focus();
adamstark@60 710 }
adamstark@60 711 }
adamstark@60 712 else if (this.lastKey==40) // Down
adamstark@60 713 {
adamstark@60 714 var newIndex = childIndex+1;
adamstark@60 715 var elem = document.getElementById('Item'+itemIndex+'_c'+newIndex);
adamstark@60 716 if (!elem) // last child, jump to parent next parent
adamstark@60 717 {
adamstark@60 718 elem = this.NavNext(itemIndex+1);
adamstark@60 719 }
adamstark@60 720 if (elem)
adamstark@60 721 {
adamstark@60 722 elem.focus();
adamstark@60 723 }
adamstark@60 724 }
adamstark@60 725 else if (this.lastKey==27) // Escape
adamstark@60 726 {
adamstark@60 727 parent.searchBox.CloseResultsWindow();
adamstark@60 728 parent.document.getElementById("MSearchField").focus();
adamstark@60 729 }
adamstark@60 730 else if (this.lastKey==13) // Enter
adamstark@60 731 {
adamstark@60 732 return true;
adamstark@60 733 }
adamstark@60 734 return false;
adamstark@60 735 }
adamstark@60 736 }
adamstark@60 737
adamstark@60 738 function setKeyActions(elem,action)
adamstark@60 739 {
adamstark@60 740 elem.setAttribute('onkeydown',action);
adamstark@60 741 elem.setAttribute('onkeypress',action);
adamstark@60 742 elem.setAttribute('onkeyup',action);
adamstark@60 743 }
adamstark@60 744
adamstark@60 745 function setClassAttr(elem,attr)
adamstark@60 746 {
adamstark@60 747 elem.setAttribute('class',attr);
adamstark@60 748 elem.setAttribute('className',attr);
adamstark@60 749 }
adamstark@60 750
adamstark@60 751 function createResults()
adamstark@60 752 {
adamstark@60 753 var results = document.getElementById("SRResults");
adamstark@60 754 for (var e=0; e<searchData.length; e++)
adamstark@60 755 {
adamstark@60 756 var id = searchData[e][0];
adamstark@60 757 var srResult = document.createElement('div');
adamstark@60 758 srResult.setAttribute('id','SR_'+id);
adamstark@60 759 setClassAttr(srResult,'SRResult');
adamstark@60 760 var srEntry = document.createElement('div');
adamstark@60 761 setClassAttr(srEntry,'SREntry');
adamstark@60 762 var srLink = document.createElement('a');
adamstark@60 763 srLink.setAttribute('id','Item'+e);
adamstark@60 764 setKeyActions(srLink,'return searchResults.Nav(event,'+e+')');
adamstark@60 765 setClassAttr(srLink,'SRSymbol');
adamstark@60 766 srLink.innerHTML = searchData[e][1][0];
adamstark@60 767 srEntry.appendChild(srLink);
adamstark@60 768 if (searchData[e][1].length==2) // single result
adamstark@60 769 {
adamstark@60 770 srLink.setAttribute('href',searchData[e][1][1][0]);
adamstark@60 771 if (searchData[e][1][1][1])
adamstark@60 772 {
adamstark@60 773 srLink.setAttribute('target','_parent');
adamstark@60 774 }
adamstark@60 775 var srScope = document.createElement('span');
adamstark@60 776 setClassAttr(srScope,'SRScope');
adamstark@60 777 srScope.innerHTML = searchData[e][1][1][2];
adamstark@60 778 srEntry.appendChild(srScope);
adamstark@60 779 }
adamstark@60 780 else // multiple results
adamstark@60 781 {
adamstark@60 782 srLink.setAttribute('href','javascript:searchResults.Toggle("SR_'+id+'")');
adamstark@60 783 var srChildren = document.createElement('div');
adamstark@60 784 setClassAttr(srChildren,'SRChildren');
adamstark@60 785 for (var c=0; c<searchData[e][1].length-1; c++)
adamstark@60 786 {
adamstark@60 787 var srChild = document.createElement('a');
adamstark@60 788 srChild.setAttribute('id','Item'+e+'_c'+c);
adamstark@60 789 setKeyActions(srChild,'return searchResults.NavChild(event,'+e+','+c+')');
adamstark@60 790 setClassAttr(srChild,'SRScope');
adamstark@60 791 srChild.setAttribute('href',searchData[e][1][c+1][0]);
adamstark@60 792 if (searchData[e][1][c+1][1])
adamstark@60 793 {
adamstark@60 794 srChild.setAttribute('target','_parent');
adamstark@60 795 }
adamstark@60 796 srChild.innerHTML = searchData[e][1][c+1][2];
adamstark@60 797 srChildren.appendChild(srChild);
adamstark@60 798 }
adamstark@60 799 srEntry.appendChild(srChildren);
adamstark@60 800 }
adamstark@60 801 srResult.appendChild(srEntry);
adamstark@60 802 results.appendChild(srResult);
adamstark@60 803 }
adamstark@60 804 }
adamstark@60 805