]> git.evergreen-ils.org Git - working/Evergreen.git/blob - Open-ILS/web/js/dojo/openils/widget/FacetSidebar.js
LP#1482400: when activating a PO, provide better progress updates
[working/Evergreen.git] / Open-ILS / web / js / dojo / openils / widget / FacetSidebar.js
1 /* ---------------------------------------------------------------------------
2  * Copyright (C) 2010  Equinox Software, Inc
3  * Mike Rylander <miker@esilibrary.com>
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License
7  * as published by the Free Software Foundation; either version 2
8  * of the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  * ---------------------------------------------------------------------------
15  */
16
17 /*  Example markup:
18
19 <div id='facetSidebarContainer' class='hide_me'>
20
21     <div class="side_bar_item" style="margin-top: 10px; font-weight: bold;">
22         <span>&navigate.facetRefine;</span>
23     </div>
24
25     <div
26         dojoType='openils.widget.FacetSidebar'
27         searchBox='facet_box'
28         searchSubmit='search_submit'
29         facetLimit='5'
30         maxValuesPerFacet='10'
31         classOrder='[{"name":"author","facetOrder":["personal","corporate"]},{"name":"subject","facetOrder":["topic"]},"series",{"name":"subject","facetOrder":["name","geographic"]}]'
32     >
33         <script type='dojo/method' event='populate'><![CDATA[
34             var f_sidebar = this;
35             attachEvt("result", "allRecordsReceived", function () {
36                 if(!resultFacetKey) return;
37                 if (f_sidebar.facetCacheKey) return; // already rendered it
38
39                 dojo.removeClass('facetSidebarContainer','hide_me');
40
41                 f_sidebar.facetCacheKey = resultFacetKey;
42                 f_sidebar.render();
43             });
44         ]]></script>
45     </div>
46 </div>
47
48  */
49
50
51 if(!dojo._hasResource["openils.widget.FacetSidebar"]) {
52
53     dojo._hasResource["openils.widget.FacetSidebar"] = true;
54     dojo.provide("openils.widget.FacetSidebar");
55     dojo.require("openils.widget.Searcher");
56
57     dojo.declare(
58         'openils.widget.FacetSidebar',
59         [dijit._Widget, dijit._Templated],
60         {   
61
62             templateString : '<div dojoAttachPoint="myTop"><div dojoAttachPoint="containerNode"></div><div class="facetClassContainer" dojoAttachPoint="facetClasses"></div></div>',
63             widgetsInTemplate: false,
64
65             facetData : {},
66             facetCacheKey : '',
67             searchBox : '',
68             classOrder : null, // Array of cmc.name values, OR array of objects with name and facetOrder properties
69             displayItemLimit : 999, // Number of distinctly described entries (classes or facets), that have values, to display from classOrder
70             searchSubmit : '',
71             facetLimit : 10,
72             maxValuesPerFacet : 100,
73
74             startup : function () {
75                 this.populate();
76                 this.inherited(arguments)
77             },
78
79             populate : function () {},
80
81             render : function () {
82                 if (!this.facetCacheKey) return;
83
84                 if (openils.widget.Searcher._cache.facetData) {
85                     this.facetData = openils.widget.Searcher._cache.facetData;
86                     this._render_callback();
87                 } else {
88                     var limit = dojo.isIE ? this.facetLimit : this.maxValuesPerFacet;
89                     var self = this;
90                     fieldmapper.standardRequest( 
91                         [ 'open-ils.search', 'open-ils.search.facet_cache.retrieve'], 
92                         { async : true,
93                           params : [this.facetCacheKey, limit],
94                           oncomplete : function(r) {
95                               var facetData = r.recv().content();
96                               if (!facetData) return;
97                               self.facetData = openils.widget.Searcher._cache.facetData = facetData;
98                               self._render_callback();
99                           }
100                         }
101                     );
102                 }
103
104             },
105
106             _render_callback : function(facetData) {
107                 var facetData = this.facetData;
108                 var classes = openils.widget.Searcher._cache.arr.cmc;
109                 if (this.classOrder && this.classOrder.length > 0) {
110                     classes = [];
111                     dojo.forEach(
112                         this.classOrder,
113                         function(x) {
114                             if (dojo.isObject(x)) classes.push(x);
115                             else classes.push({name:x});
116                         }
117                     );
118                 }
119
120                 var displayedItems = 0;
121                 var me = this;
122                 dojo.forEach(
123                     classes,
124                     function (x) {
125                         var possible_facets = [];
126                         if (x.facetOrder) {
127                             dojo.forEach(x.facetOrder, function(fname) {
128                                 var maybe_facet = dojo.filter(
129                                     openils.widget.Searcher._cache.arr.cmf,
130                                     function (y) {
131                                         if (y.field_class == x.name && y.name == fname && facetData[y.id]) {
132                                             if (displayedItems < me.displayItemLimit) {
133                                                 displayedItems++;
134                                                 return 1;
135                                             }
136                                         }
137                                         return 0;
138                                     }
139                                 )[0];
140                                 if (maybe_facet) possible_facets.push(maybe_facet);
141                             });
142                         } else {
143                             possible_facets = dojo.filter(
144                                 openils.widget.Searcher._cache.arr.cmf,
145                                 function (y) {
146                                     if (y.field_class == x.name && facetData[y.id]) {
147                                         if (displayedItems < me.displayItemLimit) {
148                                             displayedItems++;
149                                             return 1;
150                                         }
151                                     }
152                                     return 0;
153                                 }
154                             );
155                         }
156                         if (possible_facets.length > 0) me.addClass( x.name, possible_facets );
157                     }
158                 );
159             },
160
161             addClass : function (thisclass, facets) {
162                 return new openils.widget.FacetSidebar.facetClass(
163                     { facetLimit: this.facetLimit, searchBox : this.searchBox, searchSubmit : this.searchSubmit, facetClass : thisclass, facetData : this.facetData, facetList : facets }
164                 ).placeAt(this.facetClasses, 'last');
165             }
166         }
167     );
168
169     dojo._hasResource["openils.widget.FacetSidebar.facetClass"] = true;
170     dojo.provide("openils.widget.FacetSidebar.facetClass");
171
172     dojo.declare(
173         'openils.widget.FacetSidebar.facetClass',
174         [dijit._Widget, dijit._Templated],
175         {   
176
177             templateString :
178 '<div class="facetClassLabelContainer">' +
179 '  <div class="facetClassLabel" dojoAttachPoint="facetClassLabel"></div>' +
180 '  <div class="facetFieldContainer" dojoAttachPoint="facetFields"></div>' +
181 '</div>',
182             widgetsInTemplate: false,
183
184             facetLimit : 10,
185             facetClass : '',
186             facetData : null,
187             facetList : null,
188             searchBox : '',
189             searchSubmit : '',
190
191             postCreate : function () {
192                 if (!this.facetClass) return;
193                 if (!this.facetData) return;
194
195                 var myclass = this.facetClass;
196
197                 var fclass = dojo.filter(openils.widget.Searcher._cache.arr.cmc, function (x) { if (x.name == myclass) return 1; return 0; })[0];
198                 this.facetClassLabel.innerHTML = fclass.label;
199
200                 var me = this;
201                 dojo.forEach(
202                     this.facetList,
203                     function (f) { me.addFacets(f); }
204                 );
205             },
206
207             addFacets : function (f) {
208                 return new openils.widget.FacetSidebar.facetField(
209                     { facetLimit: this.facetLimit, searchBox : this.searchBox, searchSubmit : this.searchSubmit, facet : f, facetData : this.facetData[f.id] }
210                 ).placeAt( this.facetFields, 'last' );
211             }
212         }
213     );
214
215     dojo._hasResource["openils.widget.FacetSidebar.facetField"] = true;
216     dojo.provide("openils.widget.FacetSidebar.facetField");
217
218     dojo.declare(
219         'openils.widget.FacetSidebar.facetField',
220         [dijit._Widget, dijit._Templated],
221         {   
222
223             templateString : 
224 '<div class="facetField" dojoAttachPoint="myTop">' +
225 '  <div class="extraFacetFieldsWrapper" dojoAttachPoint="toggleExtraFacetFieldsWrapper"><button class="toggleExtraFacetFieldsButton" dojoType="dijit.form.Button" dojoAttachPoint="toggleExtraFacetFields" dojoAttachEvent="onClick:toggleExtraFacets"></button></div>' +
226 '  <div class="facetFieldLabel" dojoAttachPoint="facetLabel"></div>' +
227 '  <div class="facetFields" dojoAttachPoint="facetFields"></div>' +
228 '  <div class="facetFields hide_me" dojoAttachPoint="extraFacetFields"></div>' +
229 '</div>',
230
231             widgetsInTemplate: true,
232             facet : null,
233             facetData : null,
234             facetLimit : 10,
235             searchBox : '',
236             searchSubmit : '',
237             extraHidden : true,
238
239             postCreate : function () {
240                 this.nls = dojo.i18n.getLocalization("openils.widget", "Searcher");
241                 var me = this;
242                 var keylist = []; for (var i in this.facetData) { keylist.push(i); }
243
244                 keylist = keylist.sort(function(a,b){
245                     if (me.facetData[a] < me.facetData[b]) return 1;
246                     if (me.facetData[a] > me.facetData[b]) return -1;
247                     if (a < b) return -1;
248                     if (a > b) return 1;
249                     return 0;
250                 });
251
252                 this.facetLabel.innerHTML = this.facet.label;
253                 this.toggleExtraFacetFields.setLabel(this.nls.more);
254
255                 var pos = 0;
256                 dojo.forEach(
257                     keylist,
258                     function(value){
259
260                         var have_it = dojo.byId(me.searchBox).value.indexOf(me.facet.field_class + '|' + me.facet.name + '[' + value + ']') > -1;
261
262                         var container = dojo.create('div',{'class':'facetFieldLine'});
263                         dojo.create('span',{'class':'facetFieldLineCount', innerHTML: me.facetData[value]},container);
264
265                         if (have_it) {
266                             dojo.create('a',{href : '#', 'class':'facetFieldLineValue', onclick : function(){ me.undoSearch(value); return false;}, innerHTML: '<b>(' + value + ')</b>'},container);
267                         } else {
268                             dojo.create('a',{href : '#', 'class':'facetFieldLineValue', onclick : function(){ me.doSearch(value); return false;}, innerHTML: value},container);
269                         }
270
271                         if (pos >= me.facetLimit) dojo.place(container,me.extraFacetFields,'last');
272                         else dojo.place(container,me.facetFields,'last');
273
274                         pos++;
275                     }
276                 );
277
278                 if (pos < me.facetLimit + 1) dojo.query(this.toggleExtraFacetFieldsWrapper).toggleClass('hide_me');
279
280             },
281
282             toggleExtraFacets : function () {
283                 dojo.query(this.extraFacetFields).toggleClass('hide_me');
284                 this.extraHidden = !this.extraHidden;
285                 this.extraHidden ? this.toggleExtraFacetFields.setLabel(this.nls.more) : this.toggleExtraFacetFields.setLabel(this.nls.less);
286             },
287
288             undoSearch : function (value) {
289                 var sb = dojo.byId(this.searchBox);
290                 sb.value = sb.value.replace(this.facet.field_class + '|' + this.facet.name + '[' + value + ']','');
291                 dojo.byId(this.searchSubmit).click();
292             },
293
294             doSearch : function (value) {
295                 dojo.byId(this.searchBox).value += ' ' + this.facet.field_class + '|' + this.facet.name + '[' + value + ']';
296                 dojo.byId(this.searchSubmit).click();
297             }
298         }
299     );
300
301
302 }
303