]> git.evergreen-ils.org Git - Evergreen.git/blob - Open-ILS/web/opac/skin/default/js/holds.js
removed the hold range selector for staff holds
[Evergreen.git] / Open-ILS / web / opac / skin / default / js / holds.js
1 var holdsOrgSelectorBuilt = false;
2 var holdArgs;
3
4 /* 
5 note: metarecord holds have a holdable_formats field that contains
6 item_type(s)-item_forms(s)-language
7 item_form and language are optional - if language exist and no 
8 item_form is specified, use item_type(s)--language
9 */
10
11 function holdsHandleStaff() {
12         swapCanvas($('xulholds_box'));
13         $('xul_recipient_barcode').focus();
14         $('xul_recipient_barcode').onkeypress = function(evt) 
15                 {if(userPressedEnter(evt)) { _holdsHandleStaff(); } };
16         $('xul_recipient_barcode_submit').onclick = _holdsHandleStaff;
17         $('xul_recipient_me').onclick = _holdsHandleStaffMe;
18 }
19
20 function _holdsHandleStaffMe() {
21         holdArgs.recipient = G.user;
22         holdsDrawEditor();
23 }
24
25 function _holdsHandleStaff() {
26         var barcode = $('xul_recipient_barcode').value;
27         var user = grabUserByBarcode( G.user.session, barcode );
28         if(!user) return;
29         holdArgs.recipient = user;
30         holdsDrawEditor();
31 }
32
33
34
35 /** args:
36   * record, volume, copy (ids)
37   * request, recipient, editHold (objects)
38   */
39
40 function holdsDrawEditor(args) {
41
42         holdArgs = (args) ? args : holdArgs;
43
44         if(isXUL() && holdArgs.recipient == null 
45                         && holdArgs.editHold == null) {
46                 holdsHandleStaff();
47                 return;
48         }
49
50         if(!holdArgs.recipient) holdArgs.recipient = G.user;
51         if(!holdArgs.requestor) holdArgs.requestor = G.user;
52
53         if(!(holdArgs.requestor && holdArgs.requestor.session)) {
54                 detachAllEvt('common','locationChanged');
55                 attachEvt('common','loggedIn', holdsDrawEditor)
56                 initLogin();
57                 return;
58         }
59
60         if(holdArgs.editHold) // flesh the args with the existing hold 
61                 holdArgsFromHold(holdArgs.editHold, holdArgs);
62
63         holdsDrawWindow();
64 }
65
66
67 // updates the edit window with the existing hold's data 
68 function _holdsUpdateEditHold() {
69
70         var hold = holdArgs.editHold;
71         var status = holdArgs.status;
72
73         var orgsel = $('holds_org_selector');
74         setSelector(orgsel, hold.pickup_lib());
75
76         if( hold.capture_time() || status > 2 )
77                 orgsel.disabled = true;
78         else    
79                 orgsel.disabled = false;
80
81
82         $('holds_submit').onclick = holdsEditHold;
83         $('holds_update').onclick = holdsEditHold;
84
85         if(hold.phone_notify()) {
86                 $('holds_enable_phone').checked = true;
87                 $('holds_phone').value = hold.phone_notify();
88
89         } else {
90                 $('holds_phone').disabled = true;
91                 $('holds_enable_phone').checked = false;
92         }
93
94         if(hold.email_notify()) {
95                 $('holds_enable_email').checked = true;
96
97         } else {
98                 $('holds_enable_email').checked = false;
99         }
100 }
101
102 function holdsEditHold() {
103         var hold = holdsBuildHoldFromWindow();
104         if(!hold) return;
105         holdsUpdate(hold);
106         showCanvas();
107         if(holdArgs.onComplete)
108                 holdArgs.onComplete(hold);
109 }
110
111 function holdArgsFromHold(hold, oargs) {
112         var args = (oargs) ? oargs : {};
113         args.type = hold.hold_type();
114         var target = hold.target();
115
116         switch(args.type) {
117                 case 'M':
118                         args.metarecord = target;
119                         break;
120                 case 'T':
121                         args.record = target;
122                         break;
123                 case 'V':
124                         args.volume = target;
125                         break;
126                 case 'C':
127                         args.copy = target;
128                         break;
129         }
130         return args;
131 }
132
133 function holdFetchObjects(hold, doneCallback) {
134
135         var args = (hold) ? holdArgsFromHold(hold) : holdArgs;
136
137         var type = args.type;
138
139         if( type == 'C' ) {
140
141                 if( args.copyObject ) {
142
143                         args.copy = args.copyObject.id();
144                         args.volume = args.copyObject.call_number();
145                         _h_set_vol(args, doneCallback);
146
147                 } else {
148                         var creq = new Request(FETCH_COPY, args.copy);
149
150                         creq.callback(
151                                 function(r) {
152                                         var cp = r.getResultObject();
153                                         args.copyObject = cp;
154                                         args.volume = args.copyObject.call_number();
155                                         _h_set_vol(args, doneCallback);
156                                 }
157                         );
158                         creq.send();
159                 }
160         } else {
161                 if( type == 'V' ) {
162                         _h_set_vol(args, doneCallback);
163
164                 } else {
165                         if( type == 'T' ) {
166                                 _h_set_rec(args, doneCallback);
167                         } else {
168                                 _h_set_rec_descriptors(args, doneCallback);
169                         }
170                 }
171         }
172
173         return args;
174 }
175
176 function _h_set_vol(args, doneCallback) {
177
178         if( args.volumeObject ) {
179                 args.volume = args.volumeObject.id();
180                 args.record = args.volumeObject.record();
181                 _h_set_rec(args, doneCallback);
182
183         } else {
184
185                 var vreq = new Request(FETCH_VOLUME, args.volume);
186                 vreq.callback(
187                         function(r) {
188                                 var vol = r.getResultObject();
189                                 args.volumeObject = vol;
190                                 args.record = vol.record();
191                                 _h_set_rec(args, doneCallback);
192                         }
193                 );
194                 vreq.send();
195         }
196 }
197
198 function _h_set_rec(args, doneCallback) {
199
200         if(args.recordObject) 
201                 args.record = args.recordObject.doc_id();
202         else 
203                 args.recordObject = findRecord( args.record, 'T' );
204         
205         if( args.type == 'T' || args.type == 'M' ) 
206                 _h_set_rec_descriptors(args, doneCallback);
207         else 
208                 if(doneCallback) doneCallback(args);
209 }
210
211
212 function _h_set_rec_descriptors(args, doneCallback) {
213
214         // grab the list of record desciptors attached to this records metarecord 
215         if( ! args.recordDescriptors )  {
216                 var params = { record: args.record };
217
218                 if( ! args.record ) {
219                         if( args.metarecord )
220                                 params = { metarecord : args.metarecord };
221                         else 
222                                 params = { metarecord : args.metarecordObject.doc_id() };
223                 }
224
225                 var req = new Request(FETCH_MR_DESCRIPTORS, params );
226                 req.callback(
227                         function(r) {
228                                 var data = r.getResultObject();
229                                 args.recordDescriptors = data.descriptors;
230                                 args.metarecord = data.metarecord;
231                                 if( args.type == 'M' && ! args.metarecordObject) 
232                                         args.metarecordObject = findRecord(args.metarecord, 'M');       
233                                  
234                                 if(doneCallback) doneCallback(args);
235                         }
236                 );
237                 req.send();
238
239         } else {
240                 if(doneCallback) doneCallback(args);
241         }
242
243         return args;
244 }
245
246
247
248 function holdsDrawWindow() {
249         swapCanvas($('holds_box'));
250         $('holds_cancel').onclick = function(){ runEvt('common', 'holdUpdateCanceled'), showCanvas() };
251         $('holds_submit').onclick = function(){holdsPlaceHold(holdsBuildHoldFromWindow())};
252         $('holds_update').onclick = function(){holdsPlaceHold(holdsBuildHoldFromWindow())};
253         holdFetchObjects(null, 
254                 function(){
255                         __holdsDrawWindow();
256
257                         if(holdArgs.editHold) {
258                                 hideMe($('holds_submit'));
259                                 unHideMe($('holds_update'));
260                                 var req = new Request(FETCH_HOLD_STATUS, 
261                                         G.user.session, holdArgs.editHold.id());
262                                 req.send(true);
263                                 holdArgs.status = req.result();
264                                 _holdsUpdateEditHold();
265                         }  
266                 }
267         );
268 }
269
270 function __holdsDrawWindow() {
271
272         var rec = holdArgs.recordObject;
273         var vol = holdArgs.volumeObject;
274         var copy = holdArgs.copyObject;
275         var mr = holdArgs.metarecordObject;
276
277         rec = (rec) ? rec : mr;
278
279         if(!holdsOrgSelectorBuilt) {
280                 holdsBuildOrgSelector(null,0);
281                 holdsOrgSelectorBuilt = true;
282
283                 var selector = $('holds_org_selector');
284                 var o_loc = findOrgUnit(getOrigLocation());
285                 var t = findOrgType(o_loc.ou_type());
286
287                 if( t.can_have_users() ) 
288                         setSelector(selector, o_loc.id());
289                 else 
290                         setSelector(selector, holdArgs.recipient.home_ou());
291         
292         }
293
294         /*
295         if(isXUL()) {
296                 var dsel = $('holds_depth_selector');
297                 unHideMe($('holds_depth_selector_row'));
298                 if(dsel.getElementsByTagName('option').length == 0) {
299                         var types = globalOrgTypes;
300                         var depth = findOrgDepth(G.user.ws_ou());
301                         iterate(types, 
302                                 function(t) {
303                                         if(t.depth() > depth) return;
304                                         insertSelectorVal(dsel, -1, t.opac_label(), t.depth());
305                                 }
306                         );
307                 }
308         }
309         */
310
311         appendClear($('holds_recipient'), text(
312                 holdArgs.recipient.family_name() + ', ' +  
313                         holdArgs.recipient.first_given_name()));
314         appendClear($('holds_title'), text(rec.title()));
315         appendClear($('holds_author'), text(rec.author()));
316
317         if( holdArgs.type == 'V' || holdArgs.type == 'C' ) {
318
319                 unHideMe($('holds_type_row'));
320                 unHideMe($('holds_cn_row'));
321                 appendClear($('holds_cn'), text(holdArgs.volumeObject.label()));
322
323                 if( holdArgs.type == 'V'  ) {
324                         unHideMe($('holds_is_cn'));
325                         hideMe($('holds_is_copy'));
326
327                 } else {
328                         hideMe($('holds_is_cn'));
329                         unHideMe($('holds_is_copy'));
330                         unHideMe($('holds_copy_row'));
331                         appendClear($('holds_copy'), text(holdArgs.copyObject.barcode()));
332                 }
333
334         } else {
335                 hideMe($('holds_type_row'));
336                 hideMe($('holds_copy_row'));
337                 hideMe($('holds_cn_row'));
338         }
339
340         removeChildren($('holds_format'));
341
342         var mods_formats = rec.types_of_resource();
343         var formats;
344
345         if(holdArgs.recordDescriptors)
346                 formats = holdArgs.recordDescriptors[0].item_type();
347
348         if( holdArgs.type == 'T' ) {
349                 var desc = grep( holdArgs.recordDescriptors,
350                         function(i) {
351                                 return (i.record() == holdArgs.record); 
352                         }
353                 );
354                 formats = desc[0].item_type();
355         }
356
357         if( holdArgs.type == 'M' ) {
358                 var data = holdsParseMRFormats(holdArgs.editHold.holdable_formats());
359                 mods_formats = data.mods_formats;
360                 formats = data.formats;
361         }
362
363
364         for( var i in mods_formats ) {
365                 var res = mods_formats[i];
366                 var img = elem("img");
367                 setResourcePic(img, res);
368                 $('holds_format').appendChild(img);
369                 if(formats)
370                         $('holds_format').appendChild(text(' '+ MARCTypeToFriendly(formats[i]) +' '));
371                 else
372                         $('holds_format').appendChild(text(' '+ mods_formats[i] +' '));
373                 $('holds_format').appendChild(elem('br'));
374         }
375
376
377         $('holds_phone').value = holdArgs.recipient.day_phone();
378         appendClear( $('holds_email'), text(holdArgs.recipient.email()));
379
380         var pref = G.user.prefs[PREF_HOLD_NOTIFY];
381
382         if(pref) {
383                 if( ! pref.match(/email/i) ) 
384                         $('holds_enable_email').checked = false;
385
386                 if( ! pref.match(/phone/i) ) {
387                         $('holds_phone').disabled = true;
388                         $('holds_enable_phone').checked = false;
389                 }
390         }
391
392         appendClear($('holds_physical_desc'), text(rec.physical_description()));
393
394         if(holdArgs.type == 'M') hideMe($('hold_physical_desc_row'));
395
396         holdsSetFormatSelector();
397 }
398
399 function holdsParseMRFormats(str) {
400         var data = str.split(/-/);      
401
402         var formats = [];
403         var mods_formats = [];
404
405         for( var i = 0; i < data[0].length; i++ ) {
406                 formats.push( data[0].charAt(i) );
407                 mods_formats.push( MARCFormatToMods( formats[i] ) );
408         }
409         
410         formats = uniquify(formats);
411         mods_formats = uniquify(mods_formats);
412
413         return {
414                 formats                 : formats,
415                 mods_formats    : mods_formats,
416                 lang                            : data[2],
417                 largeprint              : data[1]
418         };
419 }
420
421
422 function holdsSetFormatSelector() {
423         var type = holdArgs.type;
424         if( type == 'C' || type == 'V' || holdArgs.editHold ) return;
425
426         var data                                = holdsGetFormats();
427         var avail_formats       = data.avail_formats;
428         var sel_formats = data.sel_formats;
429         holdArgs.language = data.lang;
430
431         unHideMe($('holds_alt_formats_row_extras'));
432         var selector = $('hold_alt_form_selector');
433
434         for( var i = 0; i < avail_formats.length; i++ ) {
435                 var form = avail_formats[i];
436                 unHideMe(findSelectorOptByValue(selector, form));
437         }
438 }
439
440
441 function holdsGetFormats() {
442
443         var lang;
444         var formats = [];
445         var sformats = []; // selected formats 
446
447         var type = holdArgs.type;
448         var desc = holdArgs.recordDescriptors;
449         var rec = holdArgs.record;
450         var mrec = holdArgs.metarecord;
451
452         if( type == 'T' ) {
453
454                 for( var i = 0; i < desc.length; i++ ) {
455                         var d = desc[i];
456                         if( d.record() == holdArgs.record ) {
457                                 lang = d.item_lang();
458                                 holdArgs.myFormat =  _t_f_2_format(d.item_type(), d.item_form());
459                                 sformats.push(holdArgs.myFormat);
460                                 break;
461                         }
462                 }
463         }
464
465         for( var i = 0; i < desc.length; i++ ) {
466                 var d = desc[i];
467                 if( d.item_lang() != lang ) continue;
468                 formats.push( _t_f_2_format(d.item_type(), d.item_form()));
469         }
470
471         formats = uniquify(formats);
472
473         return {
474                 lang : lang,
475                 avail_formats : formats, 
476                 sel_formats : sformats
477         };
478 }
479
480
481
482 function _t_f_2_format(type, form) {
483         if( form == 'd' ) return 'at-d';
484         return (type == 'a' || type == 't') ? 'at' : 
485                 ( type == 'i' || type == 'g' || type == 'j' ) ? type : null;
486 }
487
488 function holdsSetSelectedFormats() {
489
490         var cn = $('holds_alt_formats_row').className;
491         if( cn && cn.match(/hide_me/) ) return;
492
493         var selector = $('hold_alt_form_selector');
494         var vals = getSelectedList(selector);
495
496         if(vals.length == 0) return;
497
498         var fstring = "";
499
500         if( contains(vals, 'at-d') ) {
501                 if( contains(vals, 'at') )
502                         fstring = 'at';
503                 else 
504                         fstring = 'at-d';
505         } else {
506                 if( contains(vals, 'at') )
507                         fstring = 'at';
508         }
509
510         for( var i = 0; i < vals.length; i++ ) {
511                 var val = vals[i];
512                 if( !val.match(/at/) ) fstring = val + fstring;
513         }
514
515         if( holdArgs.language ) {
516                 if( fstring.match(/-/) )
517                         fstring = fstring + '-' + holdArgs.language;
518                 else
519                         fstring = fstring + '--' + holdArgs.language;
520         }
521
522
523         return fstring;
524 }
525
526
527 function holdsCheckPossibility(pickuplib) {
528         var rec = holdArgs.record;
529         var type = holdArgs.type;
530         var req = new Request(CHECK_HOLD_POSSIBLE, G.user.session, 
531                         { titleid : rec, patronid : G.user.id(), depth : 0, pickup_lib : pickuplib } );
532         req.send(true);
533         return req.result();
534 }
535
536
537 function holdsBuildOrgSelector(node) {
538
539         if(!node) node = globalOrgTree;
540
541         var selector = $('holds_org_selector');
542         var index = selector.options.length;
543
544         var type = findOrgType(node.ou_type());
545         var indent = type.depth() - 1;
546         var opt = setSelectorVal( selector, index, node.name(), node.id(), null, indent );
547         if(!type.can_have_users()) {
548                 opt.disabled = true;
549                 addCSSClass(opt, 'disabled_option');
550         }
551         
552         for( var i in node.children() ) {
553                 var child = node.children()[i];
554                 if(child) holdsBuildOrgSelector(child);
555         }
556 }
557
558 function holdsBuildHoldFromWindow() {
559
560         var org = getSelectorVal($('holds_org_selector'));
561         var node = findOrgUnit(org);
562         var ntype = findOrgType(node.ou_type());
563         if(!ntype.can_have_users()) {
564                 alertId('holds_pick_good_org');
565                 return;
566         }
567
568         var hold = new ahr();
569         if(holdArgs.editHold) {
570                 hold = holdArgs.editHold;
571                 holdArgs.editHold = null;
572         }
573
574         if( $('holds_enable_phone').checked ) {
575                 var phone = $('holds_phone').value;
576                 if( !phone || !phone.match(REGEX_PHONE) ) {
577                         alert($('holds_bad_phone').innerHTML);
578                         return null;
579                 }
580                 hold.phone_notify(phone);
581
582         } else {
583                 hold.phone_notify("");
584         }
585
586         if( $('holds_enable_email').checked ) 
587                 hold.email_notify(1);
588         else
589                 hold.email_notify(0);
590
591         var target;
592
593         switch(holdArgs.type) {
594                 case 'M':
595                         target = holdArgs.metarecord; break;
596                 case 'T':
597                         target = holdArgs.record; break;
598                 case 'V':
599                         target = holdArgs.volume; break;
600                 case 'C':
601                         target = holdArgs.copy; break;
602         }
603
604
605
606         hold.pickup_lib(org); 
607         hold.request_lib(org); 
608         hold.requestor(holdArgs.requestor.id());
609         hold.usr(holdArgs.recipient.id());
610         hold.target(target);
611         hold.hold_type(holdArgs.type);
612
613         //check for alternate hold formats 
614         var fstring = holdsSetSelectedFormats();
615         if(fstring) { 
616                 hold.hold_type('M'); 
617                 hold.holdable_formats(fstring);
618                 hold.target(holdArgs.metarecord);
619         }
620
621         //alert(fstring); return;
622
623         /*
624         if(isXUL())             
625                 hold.selection_depth(getSelectorVal($('holds_depth_selector')));
626                 */
627
628         return hold;
629 }
630         
631 function holdsPlaceHold(hold) {
632
633         if(!hold) return;
634
635         swapCanvas($('check_holds_box'));
636
637         if( holdArgs.type == 'M' || holdArgs.type == 'T' ) {
638                 if( ! holdsCheckPossibility(hold.pickup_lib() ) ) {
639                         alert($('hold_not_allowed').innerHTML);
640                         swapCanvas($('holds_box'));
641                         return;
642                 }
643         }
644
645         var req = new Request( CREATE_HOLD, holdArgs.requestor.session, hold );
646         req.send(true);
647         var res = req.result();
648
649         if( res == '1' ) alert($('holds_success').innerHTML);
650         else alert($('holds_failure').innerHTML);
651         
652         showCanvas();
653
654         holdArgs = null;
655         runEvt('common', 'holdUpdated');
656 }
657
658 function holdsCancel(holdid, user) {
659         if(!user) user = G.user;
660         var req = new Request(CANCEL_HOLD, user.session, holdid);
661         req.send(true);
662         return req.result();
663         runEvt('common', 'holdUpdated');
664 }
665
666 function holdsUpdate(hold, user) {
667         if(!user) user = G.user;
668         var req = new Request(UPDATE_HOLD, user.session, hold);
669         req.send(true);
670         var x = req.result(); // cause an exception if there is one 
671         runEvt('common', 'holdUpdated');
672 }
673
674