debugging the sort order stuff, changed some terminology, only
[Evergreen.git] / Open-ILS / web / opac / skin / default / js / result_common.js
1
2 var recordsHandled = 0;
3 var recordsCache = [];
4 var lowHitCount = 4;
5
6 /* set up the event handlers */
7 G.evt.result.hitCountReceived.push(resultSetHitInfo);
8 G.evt.result.recordReceived.push(resultDisplayRecord, resultAddCopyCounts);
9 G.evt.result.copyCountsReceived.push(resultDisplayCopyCounts);
10 G.evt.result.allRecordsReceived.push(resultBuildCaches, resultDrawSubjects, resultDrawAuthors, resultDrawSeries);
11 //G.evt.result.allRecordsReceived.push(resultBuildCaches );
12
13 attachEvt('result','lowHits',resultLowHits);
14 attachEvt('result','zeroHits',resultZeroHits);
15
16 attachEvt( "common", "locationUpdated", resultSBSubmit );
17 function resultSBSubmit(){searchBarSubmit();}
18
19 /* do this after we have ID's so the rank for mr pages will be correct */
20 attachEvt("result", "preCollectRecords", resultPaginate);
21
22 /* returns the last 'index' postion ocurring in this page */
23 function resultFinalPageIndex() {
24         if(getHitCount() < (getOffset() + getDisplayCount())) 
25                 return getHitCount() - 1;
26         return getOffset() + getDisplayCount() - 1;
27 }
28
29 /* set the search result info, number of hits, which results we're 
30         displaying, links to the next/prev pages, etc. */
31 function resultSetHitInfo() { 
32
33         try{searchTimer.stop()}catch(e){}
34
35         if( findCurrentPage() == MRESULT ) {
36                 if(getHitCount() <= lowHitCount && getTerm())
37                         runEvt('result', 'lowHits');
38                 if(getHitCount() == 0) {
39                         runEvt('result', 'zeroHits');
40                         return;
41                 }
42         }
43
44         var c;  
45         if( getDisplayCount() > (getHitCount() - getOffset()))  c = getHitCount();
46         else c = getDisplayCount() + getOffset();
47
48         var pages = getHitCount() / getDisplayCount();
49         if(pages % 1) pages = parseInt(pages) + 1;
50
51         G.ui.result.current_page.appendChild(text( (getOffset()/getDisplayCount()) + 1));
52         G.ui.result.num_pages.appendChild(text(pages + ")")); /* the ) is dumb */
53
54         G.ui.result.offset_start.appendChild(text(getOffset() + 1));
55         G.ui.result.offset_end.appendChild(text(c));
56         G.ui.result.result_count.appendChild(text(getHitCount()));
57         unHideMe(G.ui.result.info);
58 }
59
60 function resultLowHits() {
61         showCanvas();
62         unHideMe($('result_low_hits'));
63         if(getHitCount() > 0)
64                 unHideMe($('result_low_hits_msg'));
65
66         var sreq = new Request(CHECK_SPELL, getTerm());
67         sreq.callback(resultSuggestSpelling);
68         sreq.send();
69
70         var words = getTerm().split(' ');
71         var word;
72         while( word = words.shift() ) {
73                 var areq = new Request(FETCH_CROSSREF, getStype(), getTerm() );
74                 areq.callback(resultLowHitXRef);
75                 areq.send();
76         }
77
78         if( !(getForm() == null || getForm() == 'all' || getForm == "") ) {
79                 var a = {};
80                 a[PARAM_FORM] = "all";
81                 $('low_hits_remove_format_link').setAttribute('href',buildOPACLink(a));
82                 unHideMe($('low_hits_remove_format'));
83         }
84
85         resultSuggestSearchClass();
86 }
87
88 var lowHitsXRefLink;
89 var lowHitsXRefLinkParent;
90 function resultLowHitXRef(r) {
91         if(!lowHitsXRefLink){
92                 lowHitsXRefLinkParent = $('low_hits_xref_link').parentNode;
93                 lowHitsXRefLink = lowHitsXRefLinkParent.removeChild($('low_hits_xref_link'));
94         }
95         var res = r.getResultObject();
96         var arr = res.from;
97         arr.concat(res.also);
98         if(arr && arr.length > 0) {
99                 unHideMe($('low_hits_cross_ref'));
100                 var word;
101                 var c = 0;
102                 while( word = arr.shift() ) {
103                         if(c++ > 20) break;
104                         var a = {};
105                         a[PARAM_TERM] = word;
106                         var template = lowHitsXRefLink.cloneNode(true);
107                         template.setAttribute('href',buildOPACLink(a));
108                         template.appendChild(text(word));
109                         lowHitsXRefLinkParent.appendChild(template);
110                         lowHitsXRefLinkParent.appendChild(text(' '));
111                 }
112         }
113 }
114
115 function resultZeroHits() {
116         showCanvas();
117         unHideMe($('result_low_hits'));
118         unHideMe($('result_zero_hits_msg'));
119         if(getTerm()) resultExpandSearch(); /* advanced search */
120 }
121
122 function resultExpandSearch() {
123         var top = findOrgDepth(globalOrgTree);
124         if(getDepth() == top) return;
125         unHideMe($('low_hits_expand_range'));
126         var par = $('low_hits_expand_link').parentNode;
127         var template = par.removeChild($('low_hits_expand_link'));
128
129         var bottom = getDepth();
130         while( top < bottom ) {
131                 var a = {};
132                 a[PARAM_DEPTH] = top;
133                 var temp = template.cloneNode(true);
134                 temp.appendChild(text(findOrgTypeFromDepth(top).opac_label()))
135                 temp.setAttribute('href',buildOPACLink(a));
136                 par.appendChild(temp);
137                 top++;
138         }
139 }
140
141 function resultSuggestSearchClass() {
142         var stype = getStype();
143         if(stype == STYPE_KEYWORD) return;
144         var a = {}; var ref;
145         unHideMe($('low_hits_search_type'));
146         if(stype != STYPE_TITLE) {
147                 ref = $('low_hits_title_search');
148                 unHideMe(ref);
149                 a[PARAM_STYPE] = STYPE_TITLE;
150                 ref.setAttribute('href',buildOPACLink(a));
151         }
152         if(stype != STYPE_AUTHOR) {
153                 ref = $('low_hits_author_search');
154                 unHideMe(ref);
155                 a[PARAM_STYPE] = STYPE_AUTHOR;
156                 ref.setAttribute('href',buildOPACLink(a));
157         }
158         if(stype != STYPE_SUBJECT) {
159                 ref = $('low_hits_subject_search');
160                 unHideMe(ref);
161                 a[PARAM_STYPE] = STYPE_SUBJECT;
162                 ref.setAttribute('href',buildOPACLink(a));
163         }
164         if(stype != STYPE_KEYWORD) {
165                 ref = $('low_hits_keyword_search');
166                 unHideMe(ref);
167                 a[PARAM_STYPE] = STYPE_KEYWORD;
168                 ref.setAttribute('href',buildOPACLink(a));
169         }
170         if(stype != STYPE_SERIES) {
171                 ref = $('low_hits_series_search');
172                 unHideMe(ref);
173                 a[PARAM_STYPE] = STYPE_SERIES;
174                 ref.setAttribute('href',buildOPACLink(a));
175         }
176 }
177
178 function resultSuggestSpelling(r) {
179         var res = r.getResultObject();
180         if(res) {
181                 unHideMe($('did_you_mean'));
182                 var arg = {};
183                 arg[PARAM_TERM] = res;
184                 $('spell_check_link').setAttribute(
185                         'href', buildOPACLink(arg) );
186                 $('spell_check_link').appendChild(text(res));
187         }
188 }
189
190
191 function resultPaginate() {
192         var o = getOffset();
193
194         if( !((o + getDisplayCount()) >= getHitCount()) ) {
195
196                 var args = {};
197                 args[PARAM_OFFSET]      = o + getDisplayCount();
198                 args[PARAM_SORT]                = SORT;
199                 args[PARAM_SORT_DIR] = SORT_DIR;
200
201                 G.ui.result.next_link.setAttribute("href", buildOPACLink(args)); 
202                 addCSSClass(G.ui.result.next_link, config.css.result.nav_active);
203
204                 args[PARAM_OFFSET] = getHitCount() - (getHitCount() % getDisplayCount());
205                 G.ui.result.end_link.setAttribute("href", buildOPACLink(args)); 
206                 addCSSClass(G.ui.result.end_link, config.css.result.nav_active);
207         }
208
209         if( o > 0 ) {
210
211                 var args = {};
212                 args[PARAM_SORT]                = SORT;
213                 args[PARAM_SORT_DIR] = SORT_DIR;
214
215                 args[PARAM_OFFSET] = o - getDisplayCount();
216                 G.ui.result.prev_link.setAttribute( "href", buildOPACLink(args)); 
217                 addCSSClass(G.ui.result.prev_link, config.css.result.nav_active);
218
219                 args[PARAM_OFFSET] = 0;
220                 G.ui.result.home_link.setAttribute( "href", buildOPACLink(args)); 
221                 addCSSClass(G.ui.result.home_link, config.css.result.nav_active);
222         }
223         if(getDisplayCount() < getHitCount())
224                 unHideMe($('start_end_links_span'));
225
226         showCanvas();
227         try{searchTimer.stop()}catch(e){}
228 }
229
230
231 /* display the record info in the record display table 'pos' is the 
232                 zero based position the record should have in the display table */
233 function resultDisplayRecord(rec, pos, is_mr) {
234
235         if(rec == null) rec = new mvr(); /* so the page won't die if there was an error */
236         recordsHandled++;
237         recordsCache.push(rec);
238
239         var r = table.rows[pos + 1];
240         
241         try {
242                 var rank = parseFloat(ranks[pos + getOffset()]);
243                 rank            = parseInt( rank * 100 );
244                 var relspan = $n(r, "relevancy_span");
245                 relspan.appendChild(text(rank));
246                 unHideMe(relspan.parentNode);
247         } catch(e){ }
248
249         var pic = $n(r, config.names.result.item_jacket);
250         pic.setAttribute("src", buildISBNSrc(cleanISBN(rec.isbn())));
251
252         var title_link = $n(r, config.names.result.item_title);
253         var author_link = $n(r, config.names.result.item_author);
254
255         if( is_mr )  {
256                 var onlyrec = onlyrecord[ getOffset() + pos ];
257                 if(onlyrec) {
258                         var args = {};
259                         args.page = RDETAIL;
260                         args[PARAM_OFFSET] = 0;
261                         args[PARAM_RID] = onlyrec;
262                         args[PARAM_MRID] = rec.doc_id();
263                         pic.parentNode.setAttribute("href", buildOPACLink(args));
264                         title_link.setAttribute("href", buildOPACLink(args));
265                         title_link.appendChild(text(normalize(truncate(rec.title(), 65))));
266                         
267                 } else {
268                         buildTitleLink(rec, title_link); 
269                         var args = {};
270                         args.page = RRESULT;
271                         args[PARAM_OFFSET] = 0;
272                         args[PARAM_MRID] = rec.doc_id();
273                         pic.parentNode.setAttribute("href", buildOPACLink(args));
274                 }
275
276         } else {
277                 buildTitleDetailLink(rec, title_link); 
278                 var args = {};
279                 args.page = RDETAIL;
280                 args[PARAM_OFFSET] = 0;
281                 args[PARAM_RID] = rec.doc_id();
282                 pic.parentNode.setAttribute("href", buildOPACLink(args));
283
284                 unHideMe($n(r,'place_hold_span'));
285                 $n(r,'place_hold_link').setAttribute(
286                         'href','javascript:holdsDrawWindow("'+rec.doc_id()+'");');
287         }
288
289         buildSearchLink(STYPE_AUTHOR, rec.author(), author_link);
290
291         if(! is_mr ) {
292         
293                 if(!isNull(rec.edition()))      {
294                         unHideMe( $n(r, "result_table_extra_span"));
295                         $n(r, "result_table_edition_span").appendChild( text( rec.edition()) );
296                 }
297                 if(!isNull(rec.pubdate())) {
298                         unHideMe( $n(r, "result_table_extra_span"));
299                         unHideMe($n(r, "result_table_pub_span"));
300                         $n(r, "result_table_pub_span").appendChild( text( rec.pubdate() ));
301                 }
302                 if(!isNull(rec.publisher()) ) {
303                         unHideMe( $n(r, "result_table_extra_span"));
304                         unHideMe($n(r, "result_table_pub_span"));
305                         $n(r, "result_table_pub_span").appendChild( text( " " + rec.publisher() ));
306                 }
307         }
308
309         resultBuildFormatIcons( r, rec, is_mr );
310
311         unHideMe(r);
312         
313         runEvt("result", "recordDrawn", rec.doc_id(), title_link);
314
315         if(resultPageIsDone())  {
316                 //showCanvas();
317                 /* hide the 'now loading...' message */
318                 /*
319                 hideMe(G.ui.common.loading);
320                 */
321                 runEvt('result', 'allRecordsReceived', recordsCache);
322         }
323 }
324
325 function _resultFindRec(id) {
326         for( var i = 0; i != recordsCache.length; i++ ) {
327                 var rec = recordsCache[i];
328                 if( rec && rec.doc_id() == id )
329                         return rec;
330         }
331         return null;
332 }
333
334
335 function resultBuildFormatIcons( row, rec, is_mr ) {
336
337         var ress = rec.types_of_resource();
338
339         for( var i in ress ) {
340
341                 var res = ress[i];
342                 var link = $n(row, res + "_link");
343                 link.title = res;
344                 var img = link.getElementsByTagName("img")[0];
345                 removeCSSClass( img, config.css.dim );
346
347                 var f = getForm();
348                 if( f != "all" ) {
349                         if( f == modsFormatToMARC(res) ) 
350                                 addCSSClass( img, "dim2_border");
351                 }
352
353                 var args = {};
354                 args[PARAM_OFFSET] = 0;
355                 args[PARAM_FORM] = modsFormatToMARC(res);
356
357                 if(is_mr) {
358                         args.page = RRESULT;
359                         args[PARAM_MRID] = rec.doc_id();
360                 } else {
361                         args.page = RDETAIL
362                         args[PARAM_RID] = rec.doc_id();
363                 }
364
365                 link.setAttribute("href", buildOPACLink(args));
366
367         }
368 }
369
370
371 function resultPageIsDone(pos) {
372         return (recordsHandled == getDisplayCount() 
373                 || recordsHandled + getOffset() == getHitCount());
374 }
375
376 var resultCCHeaderApplied = false;
377
378 /* -------------------------------------------------------------------- */
379 /* dynamically add the copy count rows based on the org type 'countsrow' 
380         is the row into which we will add TD's to hold the copy counts 
381         This code generates copy count cells with an id of
382         'copy_count_cell_<depth>_<pagePosition>'  */
383 function resultAddCopyCounts(rec, pagePosition) {
384
385         var r = table.rows[pagePosition + 1];
386         var countsrow = $n(r, config.names.result.counts_row );
387         var ccell = $n(countsrow, config.names.result.count_cell);
388
389         var nodes = orgNodeTrail(findOrgUnit(getLocation()));
390         var node = nodes[0];
391         var type = findOrgType(node.ou_type());
392         ccell.id = "copy_count_cell_" + type.depth() + "_" + pagePosition;
393         ccell.title = type.opac_label();
394         //addCSSClass(ccell, config.css.result.cc_cell_even);
395
396         var lastcell = ccell;
397         var lastheadcell = null;
398
399         var cchead = null;
400         var ccheadcell = null;
401         if(!resultCCHeaderApplied) {
402                 ccrow = $('result_thead_row');
403                 ccheadcell =  ccrow.removeChild($n(ccrow, "result_thead_ccell"));
404                 var t = ccheadcell.cloneNode(true);
405                 lastheadcell = t;
406                 t.appendChild(text(type.opac_label()));
407                 ccrow.appendChild(t);
408                 resultCCHeaderApplied = true;
409         }
410
411         if(nodes[1]) {
412
413                 var x = 1;
414                 var d = findOrgDepth(nodes[1]);
415                 var d2 = findOrgDepth(nodes[nodes.length -1]);
416
417                 for( var i = d; i <= d2 ; i++ ) {
418         
419                         ccell = ccell.cloneNode(true);
420
421                         //if((i % 2)) removeCSSClass(ccell, "copy_count_cell_even");
422                         //else addCSSClass(ccell, "copy_count_cell_even");
423
424                         var node = nodes[x++];
425                         var type = findOrgType(node.ou_type());
426         
427                         ccell.id = "copy_count_cell_" + type.depth() + "_" + pagePosition;
428                         ccell.title = type.opac_label();
429                         countsrow.insertBefore(ccell, lastcell);
430                         lastcell = ccell;
431
432                         if(ccheadcell) {
433                                 var t = ccheadcell.cloneNode(true);
434                                 t.appendChild(text(type.opac_label()));
435                                 ccrow.insertBefore(t, lastheadcell);
436                                 lastheadcell = t;
437                         }
438                 }
439         }
440
441         unHideMe($("search_info_table"));
442 }
443
444 /* collect copy counts for a record using method 'methodName' */
445 function resultCollectCopyCounts(rec, pagePosition, methodName) {
446         if(rec == null || rec.doc_id() == null) return;
447         var req = new Request(methodName, getLocation(), rec.doc_id(), getForm() );
448         req.request.userdata = [ rec, pagePosition ];
449         req.callback(resultHandleCopyCounts);
450         req.send();
451 }
452
453 function resultHandleCopyCounts(r) {
454         runEvt('result', 'copyCountsReceived', r.userdata[0], r.userdata[1], r.getResultObject()); 
455 }
456
457
458 /* display the collected copy counts */
459 function resultDisplayCopyCounts(rec, pagePosition, copy_counts) {
460         if(copy_counts == null || rec == null) return;
461         var i = 0;
462         while(copy_counts[i] != null) {
463                 var cell = $("copy_count_cell_" + i +"_" + pagePosition);
464                 /*
465                 var span = cell.getElementsByTagName("div")[0];
466                 */
467                 cell.appendChild(text(copy_counts[i].available + " / " + copy_counts[i].count));
468
469                 i++;
470         }
471 }
472
473