source: SMC/trunk/SMC/src/web/scripts/js/query_input/qi.js @ 6834

Last change on this file since 6834 was 6834, checked in by matej.durco@oeaw.ac.at, 9 years ago

clean up of files and code

File size: 17.6 KB
Line 
1
2// Module QueryInput
3// provides a jQuery plugin with the same name.
4!function ($, console) {
5    // could expose the defaults: $.fn.QueryInput.defaults =
6    //{q:{label:"Query", widget:"text"}, submit:{value:"Search", widget:"submit"}}
7    var defaults = {
8        params: {},
9        input_prefix: "input-",
10        slider_style: {width: "80px", display: "inline-block", "font-size": "70%", margin: "6px 12px 0 2px"},
11        onValueChanged: function () {},
12        fcs_source: "http://193.170.82.207:8680/exist/apps/sade/amc/fcs?operation=scan&x-format=json&scanClause="
13    };
14   
15    var module = {};
16
17    /**
18     * @class QueryInput
19 * generate a customizable query_input UI, a input form with fields/widgets based on settings
20 * options: multiple params/fields,
21 * indexes, different widgets
22 *
23 * dependencies: jQuery, jquery-ui: slider, autocomplete
24 
25 * @author vronk, Andy Basch
26 * @version 2013-01-17
27 */
28/* we could make it a class (instead of jQuery plugin)
29       function QueryInput(elem,s) */
30    module.QueryInput = function (options)
31{
32   /** the dom-element to generate the query input in */
33   var elem=this;
34   
35    /** main variable holding all the settings for qi, especially also all params and their allowed values, and their current value
36      * it is constructed here by merging the default and the user options passed as parameter to .QueryInput()
37      */
38   var settings = $.extend(true, {}, defaults, options);
39       
40        /** gets the current value for a parameter
41         * accepting settings as reliable source of current value
42         * i.e. changes in input have to change the .value in settings.
43         * This is assured by calling setParamValue upon input-change.
44         * public by calling: $(elem).data("qi").getParamValue(param_key);
45         * @public
46         */
47        settings.getParamValue = function (key) {
48            if (this.params[key]) {
49                return this.params[key].value;
50            } else {
51                return "";
52            }
53        };
54
55        /** allow to update the current value in settings from outside */
56        settings.setParamValue = function (key, value) {
57
58            if (settings.params[key]) {
59                settings.params[key].value = value;
60            }
61            // callback:
62            settings.onValueChanged.call(settings, value);
63            return value;
64        };
65     
66    blendInParams(); 
67
68        // makes the settings publicly available as .data("qi")
69   elem.data("qi",settings); 
70   init(settings);   
71
72  function init(s) {
73    //empty the target element - TODO:optional
74    elem.html('');
75    generateWidgets(s.params, elem);
76  }
77   
78  /** run through the params and generate the widget for every param */
79  function generateWidgets (params, trg_container) {
80       
81        $(trg_container).append("<form />");
82        var form = $(trg_container).find("form");
83       
84      for ( var key in params ) {
85         var param = params[key];
86         console.log("creating widget: " + param.widget + " for: " + key);
87        // if input already exists - fill it with the default value
88        if ($('#' + settings.input_prefix + key).length) {
89            $('#' + settings.input_prefix + key).value = param.value;   
90         } else if (trg_container)  {
91            var label= param.label ? param.label : key;
92            var new_input_label = param.label === '' ? $('') : $(
93                            "<label for='" + settings.input_prefix + key + "'>" + label+ "</label>"
94                            );
95                    var new_input=null, new_widget=null;
96           
97            switch (param.widget) {
98                case "text":
99                  new_input = genText(key, param);   
100                  break;
101                case "checkbox":
102                  new_input = genCheckBox(key, param);
103                  break;
104                case "hidden":
105                  new_input = genHidden(key, param);
106                  break;
107                case "submit":
108                  new_input = genSubmit (key, param);   
109                  break;
110                case "selectone":
111                  new_input = genCombo(key, param);   
112                  break;
113                case "multiselect":
114                            var elems = genMultiselect(key, param);
115                            new_input = elems[0];
116                            new_widget = elems[1];
117                            break;
118                        case "autocomplete":
119                  new_input = genAutocomplete (key, param);   
120                  break;
121               case "cql":
122                  var cql_elems = QueryInput_CQL.genCQLInput(key, param);
123                  new_input = cql_elems[0];
124                  new_widget = cql_elems[1]; 
125                  break;
126                case "vkb-cql":                       
127                            var cql_elems = QueryInput_CQL.genCQLInput(key, param);
128                            new_input = genVKBCombo(key, param, cql_elems[0]);
129                            new_widget = cql_elems[1];
130                            break;
131                        case "link":
132                  new_input = genLink (key, param);   
133                  break;
134                case "slider":
135                  var slider_elems = genSlider(key, param);
136                  new_input = slider_elems[0];
137                  new_widget = slider_elems[1]; 
138                  break;
139                default:
140                  console.log("no such widget: " + param.widget + " for: " + key); 
141              }   
142       
143          if (new_input) {
144                        var new_input = $(new_input);
145                        new_input.data("key", key)
146                        .addClass("type-" + param.widget + (param.additional_classes === undefined ? '' :  ' ' + param.additional_classes))
147                                .attr("id", settings.input_prefix + key)
148                             .data("param-object", param);
149                     
150            if (param.data !== undefined) {
151                            for (var k in param.data) {
152                                new_input.attr("data-" + k, param.data[k]);
153                            }
154                        }
155                       
156                        if (param.widget !== "link") {
157                 // set initial valuelink
158                 $(new_input).val(param.value);
159                     
160                /* update settings and widgets upon value-change */
161                new_input.change(function () {
162                           setParamValue(this);
163                            });
164                        }
165                       
166                        if (new_input_label !== undefined) {
167                            new_input_label.attr('for', settings.input_prefix + key);
168                            if (param.additional_label_classes !== undefined) {
169                                new_input_label.addClass(param.additional_label_classes);
170                            }
171                        }
172                        if (settings.params[key].label_after_input === true) {
173                            $(form).append(new_input, new_input_label, new_widget);
174                        } else {
175                            $(form).append(new_input_label, new_input, new_widget);
176                        }
177                    }
178                }
179            } // end for
180       
181       
182    }
183/*
184    function formatForm(inputs) {
185      for ( var key in inputs ) {
186   
187      }
188        <table>
189        </table>
190    }
191*/
192    function genText(key, param_settings) {
193         
194        var input = $("<input />");
195         $(input).attr("name",key);
196         
197        if (param_settings.size)
198                $(input).attr("size", param_settings.size);
199
200            return input;
201    }
202   
203    function genCheckBox(key, param_settings) {
204         
205        var input = $("<input type='checkbox'/>");
206            $(input).attr("name", key);
207            if (param_settings.checked !== undefined)
208                $(input).attr("checked", param_settings.checked);
209
210            return input;
211        }
212       
213        function genVKBCombo(key, param_settings, preconfigured_input) {
214            preconfigured_input.attr("data-context", param_settings.cql_config.settings.context);
215            preconfigured_input.addClass("virtual-keyboard-input");
216            var input = $('<span class="virtual-keyboard-input-combo virtual-keyboard-input-above">' +
217                        $('<div>').append(preconfigured_input).html() +
218                        '<input type="checkbox" value="unused" class="virtual-keyboard-toggle" id="vkbt' + key + '"/>' +
219                        '<label for="vkbt' + key + '" class="virtual-keyboard-first-three">ÀöÌ</label>');
220           
221            return input;
222        }
223
224        function genHidden(key, unused) {
225
226            var input = $("<input type='hidden'  />");
227            $(input).attr("name", key);
228
229            return input;
230        }
231
232        function genLink(key, unused) {
233
234            var a = $("<a>" + key + "</a>");
235        a.attr("href", generateLink());
236       
237            $(a).mousedown(function(e) {
238                $(this).attr("target", "_blank");
239                $(this).attr("href", generateLink());
240         });
241        return a;
242    }
243   
244    function genSubmit(key, param_settings) {
245         
246        var input = $("<input type='submit'/>");
247         $(input).attr("name",key);
248         $(input).attr("value",param_settings.label);
249        return input;
250    }
251       
252    /** generating our own comboboxes, because very annoying trying to use some of existing jquery plugins (easyui.combo, combobox, jquery-ui.autocomplete) */ 
253    function genCombo (key, param_settings) {
254   
255        var select = $("<select id='widget-" + key + "' />");
256            //select.attr("id", settings.input_prefix + key)
257           
258       if (param_settings.static_source) {
259              //var scanURL = settings.fcs_source +  param_settings.index
260              var source_url = param_settings.static_source.replace(/&amp;/g, '&');
261                // if static source - try to retrieve the data
262              $.getJSON(source_url, function(data) {
263                    param_settings.values = data.terms;
264                    param_settings.values.forEach(function(v) { $(select).append("<option value='" + v.value + "' >" + v.label + "</option>") });
265                    //console.log($(input).autocomplete().source);
266              });
267       
268             //param_settings.source = fcsScan;
269        } else if (param_settings.values) {
270            //    $(input).autocomplete(param_settings);
271            if (typeof  param_settings.values[0] ==='object') {// accept format with value and label
272                  param_settings.values.forEach(function(v) { $(select).append("<option value='" + v.value +"' >" + v.label + "</option>") });
273               } else { 
274                   param_settings.values.forEach(function(v) { $(select).append("<option value='" + v +"' >" + v + "</option>") });
275             }
276        } else { /* if no values,  rather make a textbox out of it? */ 
277          //select =
278        }
279       
280        select.attr("id", settings.input_prefix + key)
281        return select;
282    }
283
284    /** generate autocomplete */ 
285    function genAutocomplete (key, param_settings) {
286       
287        var input = $("<input />");
288         $(input).attr("name",key)
289   //     console.log(key, param_settings.static_source);
290        if (param_settings.static_source) {
291              //var scanURL = settings.fcs_source +  param_settings.index
292              var source_url = param_settings.static_source.replace(/&amp;/g, '&');
293                // if static source - try to retrieve the data
294              $.getJSON(source_url, function(data) {
295                    param_settings.source = data.terms
296                    $(input).autocomplete(param_settings);
297                    //console.log($(input).autocomplete().source);
298              });
299       
300             //param_settings.source = fcsScan;
301        } else {
302        $(input).autocomplete(param_settings);
303        }
304         
305        return input;
306        }
307
308        /** generate a multiselect*/
309        function genMultiselect(key, param_settings) {
310
311            var parent = $("<div/>");
312            var select = $("<select multiple='multiple' id='widget-" + key + "' />");
313            select.attr("name", key);
314            //select.attr("id", settings.input_prefix + key)
315            parent.append(select);
316
317            if (param_settings.static_source) {
318                //var scanURL = settings.fcs_source +  param_settings.index
319                var source_url = param_settings.static_source.replace(/&amp;/g, '&');
320                // if static source - try to retrieve the data
321                $.getJSON(source_url, function (data) {
322                    param_settings.values = data.terms
323                    param_settings.values.forEach(function (v) {
324                        $(select).append("<option value='" + v.value + "' >" + v.label + "</option>")
325                    });
326                    //console.log($(input).autocomplete().source);
327                });
328
329                //param_settings.source = fcsScan;
330    }
331
332   
333    else if (param_settings.values) {
334                //    $(input).autocomplete(param_settings);
335                param_settings.values.forEach(function (v) {
336                    $(select).append("<option value='" + v + "' >" + v + "</option>")
337                });
338            } else { /* if no values,  rather make a textbox out of it? */
339                //select =
340            }
341
342            select.attr("id", settings.input_prefix + key)
343            select.chosen(param_settings);
344            return [select, parent.find("#input_context_chosen")];
345        }
346
347
348        function fcsScan(request, response) {
349        response($.ui.autocomplete.filter(
350                          scan.terms, request.term));
351            // extractLast( request.term )
352    }
353         
354    /** generate a slider based on settings
355        @returns an array of two elements: actual input-element with value and a div-container for the slider widget
356    */
357    function genSlider (key, param_settings) {
358
359        var new_input = $("<input />");
360            new_input.attr("id", settings.input_prefix + key)
361                 .val(param_settings.value)
362                 .attr("size", 3);
363     
364        var new_widget = $("<div class='widget-" + param_settings.widget + "'></div>");
365            new_widget.attr("id", "widget-" + key)
366                      .css(settings.slider_style)
367                      .slider( param_settings)
368               
369                        // set both-ways references between the input-field and its slider - necessary for updating
370                        .data("related-input-field",new_input)
371                        .data("related-widget",new_widget);
372                     
373            new_widget.bind("slidechange", function(event, ui) {
374                $(this).data("related-input-field").val(ui.value);
375                // update the settings-object, but with the (updated) value of the related input-field
376                setParamValue($(this).data("related-input-field"));
377            });
378           
379            /* update the widget upon input value-change (updating the settings-value is handled in the general part */
380            new_input.bind("change", function () {
381                   var related_widget = $(this).data("related-widget");
382                   if ($(related_widget).hasClass("widget-slider")) {
383                    $(related_widget).slider("option", "value", $(this).val()); }
384             });
385             
386           return [new_input,new_widget]; 
387    } 
388   
389   
390    /** update the current value in settings */
391    function setParamValue(input_object) {
392        var param_object = $(input_object).data("param-object");
393        param_object.value= $(input_object).val();
394        var key = $(input_object).data("key");
395        var value = settings.params[key].value;
396       
397        // callback:
398        settings.onValueChanged.call( input_object,value );
399        return value;
400        }
401
402        /** generate a query-link out of the current values of the params */
403    function generateLink()
404    {
405      var url = "?";
406
407            for ( var key in settings.params) {
408           if (settings.params[key].value) {
409                 url += key + "=" + settings.params[key].value + "&"; 
410             }     
411            }
412           
413           return url;
414       }
415
416    /** overwrite settings with param-values from the URL-search string if available
417       not using $.extend(), because we still want only known/defined params overriden, not adding new params that might be in the url (?) */
418       function blendInParams() {
419           var params= getUrlParams();
420             for ( var key in settings.params ) {
421                if (params[key]) {settings.params[key].value=params[key]; }
422             }
423       }
424 
425         /** get params from the uri */
426        function getUrlParams() {
427            var currentURI = new URI();
428            var params = currentURI.search(true);
429            return params;
430        }
431
432
433
434  };     // end $.fn.QueryInput
435
436
437    /* TODO: add defaults for widgets, like:
438     widgets: {slider: {style:{width:"80px", display:"inline-block", "font-size": "70%",  margin: "6px 12px 0 2px"}}},
439     */
440   
441    // publish;
442    // this.QueryInput = module;
443    $.fn.QueryInput = module.QueryInput;
444
445}(jQuery, console);
446
Note: See TracBrowser for help on using the repository browser.