source: extensions/GrumPluginClasses/js/ui.dynamicTable.js @ 23963

Last change on this file since 23963 was 17861, checked in by grum, 12 years ago

version 3.5.4
inputPage

. fix bug on page number & total page calculation

CSS

. fix some bugs & improve clear theme

File size: 52.7 KB
Line 
1/**
2 * -----------------------------------------------------------------------------
3 * file: ui.dynamicTable.js
4 * file version: 1.0.1
5 * date: 2012-09-01
6 *
7 * A jQuery plugin provided by the piwigo's plugin "GrumPluginClasses"
8 *
9 * -----------------------------------------------------------------------------
10 * Author     : Grum
11 *   email    : grum@piwigo.com
12 *   website  : http://photos.grum.fr
13 *   PWG user : http://forum.piwigo.org/profile.php?id=3706
14 *
15 *   << May the Little SpaceFrog be with you ! >>
16 * -----------------------------------------------------------------------------
17 *
18 *
19 *
20 *
21 * :: HISTORY ::
22 *
23 * | release | date       |
24 * | 1.0.0   | 2012/06/09 | * first release
25 * |         |            |
26 * | 1.0.1   | 2012/09/01 |  * fix bugs
27 * |         |            |
28 * |         |            |  * add 'group' icon
29 * |         |            |
30 * |         |            |  * add 'save' button
31 * |         |            |
32 * |         |            |
33 * |         |            |
34 * |         |            |
35 * |         |            |
36 *
37 */
38
39
40
41(
42  function($)
43  {
44    /*
45     * plugin 'public' functions
46     */
47    var publicMethods =
48    {
49      init : function (opt)
50        {
51          return this.each(function()
52            {
53              // default values for the plugin
54              var $this=$(this),
55                  timeStamp=new Date(),
56                  data = $this.data('options'),
57                  objects = $this.data('objects'),
58                  properties = $this.data('properties'),
59                  options =
60                    {
61                      autoLoad:true,
62                      columns:[],
63                      postUrl:'',
64                      postData:{},
65                      minHeight:100,
66                      maxHeight:300,
67                      contentLoading:null,
68                      contentLoaded:null,
69                      contentDisplayed:null,
70                      pageChanged:null,
71                      click:null,
72                      saveButtonClick:null,
73                      nbItemsPage:50,
74                      currentPage:1,
75                      sortBoxTitle:'Sort by',
76                      showTotalRow:'auto',     // visible, hidden, auto
77                      showSaveButton:false,
78                      footerString:
79                        {
80                          singular:'% item',
81                          plural:'% items',
82                          waitForDownload:'Please wait, download will start...'
83                        },
84                      pagesNavigator:{},
85                      dialogsButtons:{
86                        ok:'Ok',
87                        cancel:'Cancel',
88                        erase:'Erase filter'
89                      }
90                    };
91
92              // if options given, merge it
93              // if(opt) $.extend(options, opt); ==> options are set by setters
94
95              $this.data('options', options);
96
97
98              if(!properties)
99              {
100                $this.data('properties',
101                  {
102                    objectId:'dt'+Math.ceil(timeStamp.getTime()*Math.random()),
103                    hasSortableButton:false,
104                    nbItems:0,
105                    sortedColumns:[],
106                    filteredColumns:[],
107                    groupedColumns:[],
108                    loadedData:[],
109                    totalRowHasData:false,
110                    downloadWaitState:false
111                  }
112                );
113                properties=$this.data('properties');
114              }
115
116              if(!objects)
117              {
118                objects =
119                  {
120                    headerContainer:$('<table/>',
121                        {
122                          'class':'ui-dynamicTableHeader'
123                        }
124                      ),
125                    header:$('<thead/>',
126                        {
127                          'class':'ui-dynamicTableHeader'
128                        }
129                      ),
130                    headerTr:$('<tr/>'),
131
132
133                    contentContainer:$('<div/>',
134                        {
135                          'class':'ui-dynamicTableContent'
136                        }
137                      ),
138                    content:$('<table/>',
139                        {
140                          'class':'ui-dynamicTableContent'
141                        }
142                      ),
143                    loadingContent:$('<div/>',
144                        {
145                          class:'ui-dynamicTableLoading'
146                        }
147                      ),
148                    loadingContentWorkInProgress:$('<div/>',
149                        {
150                          class:'ui-dynamicTableLoadingWorkInProgress'
151                        }
152                      ),
153
154                    totalRowContent:$('<table/>',
155                        {
156                          'class':'ui-dynamicTableTotalRow'
157                        }
158                      ),
159                    totalRowTr:$('<tr/>'),
160
161
162                    footer:$('<div/>',
163                        {
164                          'class':'ui-dynamicTableFooter'
165                        }
166                      ),
167                    footerSaveButton:$('<div/>',
168                        {
169                          'class':'ui-dynamicTableFooter-saveButton'
170                        }
171                      ),
172                    footerNbItems:$('<div/>',
173                        {
174                          'class':'ui-dynamicTableFooter-nbItems'
175                        }
176                      ),
177                    footerPagesNavigator:$('<div/>',
178                        {
179                          'class':'ui-dynamicTableFooter-pagesNavigator'
180                        }
181                      )
182                  };
183
184                $this
185                  .html('')
186                  .addClass('ui-dynamicTable')
187                  .append(objects.headerContainer.append(objects.header.append(objects.headerTr)))
188                  .append(objects.loadingContent)
189                  .append(objects.loadingContentWorkInProgress)
190                  .append(objects.contentContainer.append(objects.content))
191                  .append(objects.totalRowContent.append(objects.totalRowTr))
192                  .append(objects.footer
193                            .append(objects.footerSaveButton)
194                            .append(objects.footerNbItems)
195                            .append(objects.footerPagesNavigator)
196                         );
197
198                $this.data('objects', objects);
199              }
200
201              privateMethods.setOptions($this, opt);
202            }
203          );
204        }, // init
205      destroy : function ()
206        {
207          return this.each(
208            function()
209            {
210              // default values for the plugin
211              var $this=$(this),
212                  objects = $this.data('objects');
213              objects.content.remove();
214              objects.header.remove();
215              $(window).unbind('resize.'+properties.objectId);
216              $this.removeClass('ui-dynamicTable');
217            }
218          );
219        }, // destroy
220
221      options: function (value)
222        {
223          return(
224            this.each(
225              function()
226              {
227                privateMethods.setOptions($(this), value);
228              }
229            )
230          );
231        }, // options
232
233
234      columns: function (value)
235        {
236          if(value!=null)
237          {
238            // set selected value
239            return(
240              this.each(
241                function()
242                {
243                  privateMethods.setColumns($(this), value, true);
244                }
245              )
246            );
247          }
248          else
249          {
250            var options=this.data('options');
251            return(options.columns);
252          }
253        }, // columns
254
255      column: function (value)
256        {
257          if(value!=null && $.isPlainObject(value))
258          {
259            // set selected value
260            return(
261              this.each(
262                function()
263                {
264                  privateMethods.setColumn($(this), value, true);
265                }
266              )
267            );
268          }
269          else if(value!=null)
270          {
271            var options=this.data('options');
272            for(var i=0;i<options.columns.length;i++)
273            {
274              if(options.columns[i].id==value) return(options.columns[i]);
275            }
276            return({});
277          }
278          else return({});
279        }, // columns
280
281      sortBoxTitle: function (value)
282        {
283          if(value!=null)
284          {
285            // set selected value
286            return(
287              this.each(
288                function()
289                {
290                  privateMethods.setSortBoxTitle($(this), value, true);
291                }
292              )
293            );
294          }
295          else
296          {
297            var options=this.data('options');
298            return(options.sortBoxTitle);
299          }
300        }, // sortBoxTitle
301
302      footerString: function (value)
303        {
304          if(value!=null)
305          {
306            // set selected value
307            return(
308              this.each(
309                function()
310                {
311                  privateMethods.setFooterString($(this), value, true);
312                }
313              )
314            );
315          }
316          else
317          {
318            var options=this.data('options');
319            return(options.footerString);
320          }
321        }, // footerString
322
323      waitForDownload: function (value)
324        {
325          if(value!=null)
326          {
327            // set selected value
328            return(
329              this.each(
330                function()
331                {
332                  privateMethods.setDownloadWaitState($(this), value);
333                }
334              )
335            );
336          }
337          else
338          {
339            var properties=this.data('properties');
340            return(properties.downloadWaitState);
341          }
342        }, // waitForDownload
343
344      autoLoad: function (value)
345        {
346          if(value!=null)
347          {
348            // set selected value
349            return(
350              this.each(
351                function()
352                {
353                  privateMethods.setAutoLoad($(this), value, true);
354                }
355              )
356            );
357          }
358          else
359          {
360            var options=this.data('options');
361            return(options.autoLoad);
362          }
363        }, // autoLoad
364
365
366      showTotalRow : function (value)
367        {
368          if(value!=null)
369          {
370            // set selected value
371            return(
372              this.each(
373                function()
374                {
375                  privateMethods.setShowTotalRow($(this), value);
376                }
377              )
378            );
379          }
380          else
381          {
382            var options=this.data('options');
383            return(options.showTotalRow);
384          }
385        }, // showTotalRow
386
387
388
389      showSaveButton : function (value)
390        {
391          if(value!=null)
392          {
393            // set selected value
394            return(
395              this.each(
396                function()
397                {
398                  privateMethods.setShowSaveButton($(this), value);
399                }
400              )
401            );
402          }
403          else
404          {
405            var options=this.data('options');
406            return(options.showSaveButton);
407          }
408        }, // showSaveButton
409
410
411       currentPage: function (value)
412        {
413          if(value!=null)
414          {
415            // set selected value
416            return(
417              this.each(
418                function()
419                {
420                  privateMethods.setCurrentPage($(this), value, true);
421                }
422              )
423            );
424          }
425          else
426          {
427            var options=this.data('options');
428            return(options.currentPage);
429          }
430        }, // currentPage
431
432      nbItemsPage: function (value)
433        {
434          if(value!=null)
435          {
436            // set selected value
437            return(
438              this.each(
439                function()
440                {
441                  privateMethods.setNbItemsPage($(this), value, true);
442                }
443              )
444            );
445          }
446          else
447          {
448            var options=this.data('options');
449            return(options.currentPage);
450          }
451        }, // nbItemsPage
452
453      postUrl: function (value)
454        {
455          if(value!=null)
456          {
457            // set selected value
458            return(
459              this.each(
460                function()
461                {
462                  privateMethods.setPostUrl($(this), value, true);
463                }
464              )
465            );
466          }
467          else
468          {
469            var options=this.data('options');
470            return(options.postUrl);
471          }
472        }, // postUrl
473
474      postData: function (value)
475        {
476          if(value!=null)
477          {
478            // set selected value
479            return(
480              this.each(
481                function()
482                {
483                  privateMethods.setPostData($(this), value, true);
484                }
485              )
486            );
487          }
488          else
489          {
490            var options=this.data('options');
491            return(options.postData);
492          }
493        }, // postData
494
495      minHeight: function (value)
496        {
497          if(value!=null)
498          {
499            // set selected value
500            return(
501              this.each(
502                function()
503                {
504                  privateMethods.setMinHeight($(this), value, true);
505                }
506              )
507            );
508          }
509          else
510          {
511            var options=this.data('options');
512            return(options.minHeight);
513          }
514        }, // minHeight
515
516      maxHeight: function (value)
517        {
518          if(value!=null)
519          {
520            // set selected value
521            return(
522              this.each(
523                function()
524                {
525                  privateMethods.setMaxHeight($(this), value, true);
526                }
527              )
528            );
529          }
530          else
531          {
532            var options=this.data('options');
533            return(options.maxHeight);
534          }
535        }, // maxHeight
536
537      click: function (value)
538        {
539          if(value!=null && ($.isFunction(value) || value=='clear'))
540          {
541            // set selected value
542            return(
543              this.each(
544                function()
545                {
546                  privateMethods.setEventClick($(this), value);
547                }
548              )
549            );
550          }
551          else
552          {
553            // return the selected value
554            var options=this.data('options');
555
556            if(options)
557            {
558              return(options.click);
559            }
560            else
561            {
562              return(null);
563            }
564          }
565        }, // click
566
567
568      saveButtonClick: function (value)
569        {
570          if(value!=null && ($.isFunction(value) || value=='clear'))
571          {
572            // set selected value
573            return(
574              this.each(
575                function()
576                {
577                  privateMethods.setEventSaveButtonClick($(this), value);
578                }
579              )
580            );
581          }
582          else
583          {
584            // return the selected value
585            var options=this.data('options');
586
587            if(options)
588            {
589              return(options.saveButtonClick);
590            }
591            else
592            {
593              return(null);
594            }
595          }
596        }, // saveButtonClick
597
598      contentLoading: function (value)
599        {
600          if(value!=null && ($.isFunction(value) || value=='clear'))
601          {
602            // set selected value
603            return(
604              this.each(
605                function()
606                {
607                  privateMethods.setEventContentLoading($(this), value);
608                }
609              )
610            );
611          }
612          else
613          {
614            // return the selected value
615            var options=this.data('options');
616
617            if(options)
618            {
619              return(options.contentLoading);
620            }
621            else
622            {
623              return(null);
624            }
625          }
626        }, // contentLoading
627
628      contentLoaded: function (value)
629        {
630          if(value!=null && ($.isFunction(value) || value=='clear'))
631          {
632            // set selected value
633            return(
634              this.each(
635                function()
636                {
637                  privateMethods.setEventContentLoaded($(this), value);
638                }
639              )
640            );
641          }
642          else
643          {
644            // return the selected value
645            var options=this.data('options');
646
647            if(options)
648            {
649              return(options.contentLoaded);
650            }
651            else
652            {
653              return(null);
654            }
655          }
656        }, // contentLoaded
657
658      contentDisplayed: function (value)
659        {
660          if(value!=null && ($.isFunction(value) || value=='clear'))
661          {
662            // set selected value
663            return(
664              this.each(
665                function()
666                {
667                  privateMethods.setEventContentDisplayed($(this), value);
668                }
669              )
670            );
671          }
672          else
673          {
674            // return the selected value
675            var options=this.data('options');
676
677            if(options)
678            {
679              return(options.contentDisplayed);
680            }
681            else
682            {
683              return(null);
684            }
685          }
686        }, // contentDisplayed
687
688      pageChanged: function (value)
689        {
690          if(value!=null && ($.isFunction(value) || value=='clear'))
691          {
692            // set selected value
693            return(
694              this.each(
695                function()
696                {
697                  privateMethods.setEventPageChanged($(this), value);
698                }
699              )
700            );
701          }
702          else
703          {
704            // return the selected value
705            var options=this.data('options');
706
707            if(options)
708            {
709              return(options.pageChanged);
710            }
711            else
712            {
713              return(null);
714            }
715          }
716        }, // pageChanged
717
718      loadedData: function (value)
719        {
720          var properties=$(this).data('properties');
721
722          if(value && $.isNumeric(value) && value>=0 && value<properties.loadedData.length)
723            return(properties.loadedData[value]);
724
725          return(properties.loadedData);
726        }, // loadedData
727
728      /**
729       * refresh table content
730       * @param Integer value: page; if not specified, refresh current page
731       */
732      refreshContent: function (value)
733        {
734          privateMethods.loadContent($(this), value);
735        },
736
737      /**
738       * force table to resize columns
739       */
740      resizeContent: function (value)
741        {
742          privateMethods.setColumnsSize($(this));
743        },
744
745
746    }; // methods
747
748
749    /*
750     * plugin 'private' methods
751     */
752    var privateMethods =
753    {
754      setOptions : function (object, value)
755        {
756          var properties=object.data('properties'),
757              options=object.data('options');
758
759          if(!$.isPlainObject(value)) return(false);
760
761          properties.initialized=false;
762
763          privateMethods.setAutoLoad(object, (value.autoLoad!=null)?value.autoLoad:options.autoLoad);
764          privateMethods.setShowTotalRow(object, (value.showTotalRow!=null)?value.showTotalRow:options.showTotalRow);
765          privateMethods.setShowSaveButton(object, (value.showSaveButton!=null)?value.showSaveButton:options.showSaveButton);
766          privateMethods.setPostData(object, (value.postData!=null)?value.postData:options.postData);
767          privateMethods.setPostUrl(object, (value.postUrl!=null)?value.postUrl:options.postUrl);
768          privateMethods.setMaxHeight(object, (value.maxHeight!=null)?value.maxHeight:options.maxHeight);
769          privateMethods.setMinHeight(object, (value.minHeight!=null)?value.minHeight:options.minHeight);
770          privateMethods.setColumns(object, (value.columns!=null)?value.columns:options.columns);
771          privateMethods.setSortBoxTitle(object, (value.sortBoxTitle!=null)?value.sortBoxTitle:options.sortBoxTitle);
772          privateMethods.setFooterString(object, (value.footerString!=null)?value.footerString:options.footerString);
773          privateMethods.setDialogsButtons(object, (value.dialogsButtons!=null)?value.dialogsButtons:options.dialogsButtons);
774          privateMethods.setPagesNavigator(object, (value.pagesNavigator!=null)?value.pagesNavigator:options.pagesNavigator);
775          //privateMethods.setCurrentPage(object, (value.currentPage!=null)?value.currentPage:options.currentPage);
776          privateMethods.setNbItemsPage(object, (value.nbItemsPage!=null)?value.nbItemsPage:options.nbItemsPage);
777
778          privateMethods.setEventContentLoading(object, (value.contentLoading!=null)?value.contentLoading:options.contentLoading);
779          privateMethods.setEventContentLoaded(object, (value.contentLoaded!=null)?value.contentLoaded:options.contentLoaded);
780          privateMethods.setEventContentDisplayed(object, (value.contentDisplayed!=null)?value.contentDisplayed:options.contentDisplayed);
781          privateMethods.setEventPageChanged(object, (value.pageChanged!=null)?value.pageChanged:options.pageChanged);
782          privateMethods.setEventSaveButtonClick(object, (value.saveButtonClick!=null)?value.saveButtonClick:options.saveButtonClick);
783          privateMethods.setEventClick(object, (value.click!=null)?value.click:options.click);
784
785          $(window).bind('resize.'+properties.objectId, function (event) { privateMethods.setColumnsSize(object); });
786          properties.initialized=true;
787
788
789          if(options.autoLoad)
790            privateMethods.loadContent(object);
791
792        },
793
794      setAutoLoad : function (object, value)
795        {
796          var properties=object.data('properties'),
797              options=object.data('options');
798
799          if((!properties.initialized || value!=options.autoLoad) && (value==true || value==false))
800          {
801            options.autoLoad=value;
802          }
803
804          return(options.autoLoad);
805        }, // setAutoLoad
806
807      setShowTotalRow : function (object, value)
808        {
809          var properties=object.data('properties'),
810              options=object.data('options');
811
812          if((!properties.initialized || value!=options.showTotalRow) && (value=='visible' || value=='hidden' || value=='auto'))
813          {
814            options.showTotalRow=value;
815            if(properties.initialized)
816              privateMethods.showTotalRow(object);
817          }
818
819          return(options.showTotalRow);
820        }, // setShowTotalRow
821
822
823      setShowSaveButton : function (object, value)
824        {
825          var properties=object.data('properties'),
826              options=object.data('options');
827
828          if((!properties.initialized || value!=options.showSaveButton) && (value==true || value==false))
829          {
830            options.showSaveButton=value;
831            if(properties.initialized)
832              privateMethods.showSaveButton(object);
833          }
834
835          return(options.showSaveButton);
836        }, // setShowSaveButton
837
838
839      setColumns : function (object, value)
840        {
841          var options=object.data('options'),
842              objects=object.data('objects');
843
844          if(value!=null && $.isArray(value))
845          {
846            options.columns=[];
847
848            for(var i=0;i<value.length;i++)
849            {
850              privateMethods.setColumn(object, value[i], false);
851            }
852
853            privateMethods.updateTable(object);
854          }
855          return(options.columns);
856        }, //setColumns
857
858      setColumn : function (object, value, updateTable)
859        {
860          var newCol={},
861              options=object.data('options'),
862              objects=object.data('objects');
863
864          if(value!=null && $.isPlainObject(value) && value.id!=null)
865          {
866            newCol.id=value.id;
867            newCol.title=(value.title!=null)?value.title:'';
868            newCol.width=(value.width!=null)?value.width:'';
869            newCol.sortable=(value.sortable=='asc' || value.sortable=='desc')?value.sortable:'no';
870            newCol.group=(value.group==true||value.group==false)?value.group:false;
871            newCol.filter=null;
872
873            if($.isValidFilter(value.filter))
874              newCol.filter=value.filter;
875
876            options.columns.push(newCol);
877
878            if(updateTable) privateMethods.updateTable(object);
879          }
880
881          return(newCol);
882        }, //setColumn
883
884      setMinHeight: function (object, value)
885        {
886          var options=object.data('options'),
887              properties=object.data('properties'),
888              objects=object.data('objects');
889
890          if((!properties.initialized || value!=options.minHeight) && value>0 && value<=options.maxHeight)
891          {
892            options.minHeight=value;
893            objects.contentContainer.attr('style', 'min-height:'+options.minHeight+'px;max-height:'+options.maxHeight+'px;');
894          }
895
896          return(options.minHeight);
897        }, // setMinHeight
898
899      setMaxHeight: function (object, value)
900        {
901          var options=object.data('options'),
902              properties=object.data('properties'),
903              objects=object.data('objects');
904
905          if((!properties.initialized || value!=options.maxHeight) && value>0 && value>=options.minHeight)
906          {
907            options.maxHeight=value;
908            objects.contentContainer.attr('style', 'min-height:'+options.minHeight+'px;max-height:'+options.maxHeight+'px;');
909          }
910
911          return(options.maxHeight);
912        }, // setMaxHeight
913
914
915      setSortBoxTitle : function (object, value)
916        {
917          var options=object.data('options'),
918              properties=object.data('properties');
919
920          if(!properties.initialized || value!=options.sortBoxTitle)
921          {
922            options.sortBoxTitle=value;
923          }
924
925          return(options.sortBoxTitle);
926        }, // setSortBoxTitle
927
928      setFooterString: function (object, value)
929        {
930          var options=object.data('options'),
931              properties=object.data('properties');
932
933
934          if($.isPlainObject(value))
935          {
936            if((!properties.initialized || value.singular!=null) && value.singular!='' && value.singular!=options.footerString.singular)
937              options.footerString.singular=value.singular;
938
939            if((!properties.initialized || value.plural!=null) && value.plural!='' && value.plural!=options.footerString.plural)
940              options.footerString.plural=value.plural;
941
942            if((!properties.initialized || value.waitForDownload!=null) && value.waitForDownload!='' && value.waitForDownload!=options.footerString.waitForDownload)
943              options.footerString.waitForDownload=value.waitForDownload;
944
945            privateMethods.updateNbItems(object);
946          }
947          else if(!properties.initialized || value!=options.footerString)
948          {
949            options.footerString.singular=value;
950            options.footerString.plural=value;
951            privateMethods.updateNbItems(object);
952          }
953
954          return(options.footerString);
955        }, // setFooterString
956
957      setDownloadWaitState: function (object, value)
958        {
959          var options=object.data('options'),
960              properties=object.data('properties');
961
962          if((!properties.initialized || value!=null) && (value==true || value==false) && (value!=properties.downloadWaitState))
963          {
964            properties.downloadWaitState=value;
965            privateMethods.applyDownloadWaitState(object);
966          }
967          return(properties.downloadWaitState);
968        }, // setDownloadWaitState
969
970      setDialogsButtons: function (object, value)
971        {
972          var options=object.data('options'),
973              properties=object.data('properties');
974
975
976          if($.isPlainObject(value))
977          {
978            if((!properties.initialized || value.ok!=null) && value.ok!='')
979              options.dialogsButtons.ok=value.ok;
980
981            if((!properties.initialized || value.cancel!=null) && value.cancel!='')
982              options.dialogsButtons.cancel=value.cancel;
983
984            if((!properties.initialized || value.erase!=null) && value.erase!='')
985              options.dialogsButtons.erase=value.erase;
986
987            privateMethods.updateNbItems(object);
988          }
989
990          return(options.dialogsButtons);
991        }, // setDialogsButtons
992
993      setPostUrl : function (object, value)
994        {
995          var properties=object.data('properties'),
996              options=object.data('options');
997
998          if(!properties.initialized || value!=options.postUrl)
999          {
1000            options.postUrl=value;
1001          }
1002
1003          return(options.postUrl);
1004        }, // setPostUrl
1005
1006      setPostData : function (object, value)
1007        {
1008          var properties=object.data('properties'),
1009              options=object.data('options');
1010
1011          if(!properties.initialized || value!=options.postData)
1012          {
1013            options.postData=value;
1014          }
1015
1016          return(options.postData);
1017        }, // setPostData
1018
1019      setEventContentLoading : function (object, value)
1020        {
1021          var options=object.data('options');
1022
1023          if(value=='clear') value=null;
1024          options.contentLoading=value;
1025          object.unbind('dynamicTableContentLoading');
1026          if(value) object.bind('dynamicTableContentLoading', options.contentLoading);
1027          return(options.contentLoading);
1028        }, //setEventContentLoading
1029
1030      setEventContentLoaded : function (object, value)
1031        {
1032          var options=object.data('options');
1033
1034          if(value=='clear') value=null;
1035          options.contentLoaded=value;
1036          object.unbind('dynamicTableContentLoaded');
1037          if(value) object.bind('dynamicTableContentLoaded', options.contentLoaded);
1038          return(options.contentLoaded);
1039        }, //setEventContentLoaded
1040
1041      setEventContentDisplayed : function (object, value)
1042        {
1043          var options=object.data('options');
1044
1045          if(value=='clear') value=null;
1046          options.contentDisplayed=value;
1047          object.unbind('dynamicTableContentDisplayed');
1048          if(value) object.bind('dynamicTableContentDisplayed', options.contentDisplayed);
1049          return(options.contentDisplayed);
1050        }, //setEventContentDisplayed
1051
1052      setEventPageChanged : function (object, value)
1053        {
1054          var options=object.data('options');
1055
1056          if(value=='clear') value=null;
1057          options.pageChanged=value;
1058          object.unbind('dynamicTablePageChanged');
1059          if(value) object.bind('dynamicTablePageChanged', options.pageChanged);
1060          return(options.pageChanged);
1061        }, //setEventPageChanged
1062
1063      setEventClick : function (object, value)
1064        {
1065          var options=object.data('options'),
1066              objects=object.data('objects');
1067
1068          if(value=='clear') value=null;
1069          options.click=value;
1070          objects.content.find('tr').unbind('click.dynamicTable');
1071          if(value)
1072          {
1073            objects.content.css('cursor', 'pointer');
1074            objects.content.find('tr').bind('click.dynamicTable', options.click);
1075          }
1076          else
1077          {
1078            objects.content.css('cursor', 'default');
1079          }
1080          return(options.click);
1081        }, //setEventClick
1082
1083
1084      setEventSaveButtonClick : function (object, value)
1085        {
1086          var options=object.data('options'),
1087              objects=object.data('objects');
1088
1089          if(value=='clear') value=null;
1090          options.saveButtonClick=value;
1091          objects.footerSaveButton.unbind('click.dynamicTable');
1092          if(value)
1093            objects.footerSaveButton.bind('click.dynamicTable', function (event)
1094              {
1095                options.saveButtonClick(event, privateMethods.getPostProperties(object));
1096              }
1097            );
1098
1099          return(options.saveButtonClick);
1100        }, //setEventSaveButtonClick
1101
1102
1103      setNbItems: function (object, value)
1104        {
1105          var properties=object.data('properties');
1106
1107          if(value!=null && value>=0 && properties.nbItems!=value)
1108          {
1109            properties.nbItems=value;
1110            privateMethods.updateNbItems(object);
1111          }
1112          return(properties.nbItems);
1113        }, //setNbItems
1114
1115      setCurrentPage: function (object, value)
1116        {
1117          var options=object.data('options'),
1118              objects=object.data('objects'),
1119              properties=object.data('properties');
1120
1121          if(options.currentPage!=value && value>0 && value <= objects.footerPagesNavigator.inputPages('nbPages') || value==1)
1122          {
1123            // if value == 1, force reload
1124            options.currentPage=value;
1125            privateMethods.loadContent(object);
1126            if(options.pageChanged) object.trigger('dynamicTablePageChanged', options.currentPage);
1127          }
1128
1129          return(options.currentPage);
1130        }, //setCurrentPage
1131
1132      setNbItemsPage: function (object, value)
1133        {
1134          var options=object.data('options'),
1135              objects=object.data('objects'),
1136              properties=object.data('properties');
1137
1138          if(options.nbItemsPage!=value && value>1)
1139          {
1140            options.nbItemsPage=value;
1141            objects.footerPagesNavigator.inputPages('nbItemsPage', options.nbItemsPage);
1142            privateMethods.setCurrentPage(object, 1);
1143          }
1144          return(options.nbItemsPage);
1145        }, //setNbItemsPage
1146
1147      setPagesNavigator: function (object, value)
1148        {
1149          var options=object.data('options'),
1150              objects=object.data('objects'),
1151              properties=object.data('properties');
1152
1153          options.pagesNavigator=value;
1154          options.pagesNavigator.change=function (event, value)
1155            {
1156              privateMethods.setCurrentPage(object, value);
1157            };
1158          objects.footerPagesNavigator.inputPages(options.pagesNavigator);
1159
1160          return(options.pagesNavigator);
1161        }, //setPagesNavigator
1162
1163      /*
1164       * update DOM for headers & footer & total row
1165       */
1166      updateTable : function (object)
1167        {
1168          var style='',
1169              td=null,
1170              button=null,
1171              eraseButton=null,
1172              options=object.data('options'),
1173              objects=object.data('objects'),
1174              properties=object.data('properties');
1175
1176          objects.headerTr.children().remove();
1177          objects.totalRowTr.children().remove();
1178
1179          properties.hasSortableButton=false;
1180          properties.sortedColumns=[];
1181          properties.filteredColumns=[];
1182
1183          for(var i=0;i<options.columns.length;i++)
1184          {
1185            td=$('<td/>',
1186                  {
1187                    'oId':options.columns[i].id,
1188                  }
1189                ).html(options.columns[i].title);
1190
1191            if(options.columns[i].width!='') td.attr('style', 'width:'+options.columns[i].width+';');
1192
1193            if(options.columns[i].sortable!='no')
1194            {
1195              properties.hasSortableButton=true;
1196              properties.sortedColumns.push(
1197                  {
1198                    id:options.columns[i].id,
1199                    content:options.columns[i].title,
1200                    direction:options.columns[i].sortable
1201                  }
1202                );
1203            }
1204
1205            if(options.columns[i].filter!=null)
1206            {
1207              // filter button
1208              button=$('<div/>',
1209                        {
1210                          class:'ui-dynamicTableFilterButton-inactive'
1211                        }
1212                      )
1213                      .bind('click', i,
1214                         function (event)
1215                         {
1216                           var columnIndex=event.data,
1217                               defaultValue={},
1218                               defaultOperator=options.columns[columnIndex].filter.filterOperators[0],
1219                               $button=$(this);
1220
1221                           if(properties.filteredColumns[columnIndex])
1222                           {
1223                             defaultValue=properties.filteredColumns[columnIndex];
1224                             defaultOperator=properties.filteredColumns[columnIndex].operator;
1225                             eraseButton=options.dialogsButtons.erase;
1226                           }
1227
1228                           $.inputDialogFilterBox(
1229                              {
1230                                buttons:{
1231                                  erase:eraseButton,
1232                                  ok:options.dialogsButtons.ok,
1233                                  cancel:options.dialogsButtons.cancel
1234                                },
1235                                title:options.columns[columnIndex].filter.title,
1236                                filter:{
1237                                  dataType:options.columns[columnIndex].filter.dataType,
1238                                  filterOperators:options.columns[columnIndex].filter.filterOperators,
1239                                  defaultOperator:defaultOperator,
1240                                  defaultValue:defaultValue,
1241                                  data:options.columns[columnIndex].filter.data
1242                                },
1243                                change: function (event, value)
1244                                  {
1245                                    if(value==null)
1246                                    {
1247                                      $button
1248                                        .addClass('ui-dynamicTableFilterButton-inactive')
1249                                        .removeClass('ui-dynamicTableFilterButton-active');
1250                                    }
1251                                    else
1252                                    {
1253                                      $button
1254                                        .removeClass('ui-dynamicTableFilterButton-inactive')
1255                                        .addClass('ui-dynamicTableFilterButton-active');
1256                                      value.id=options.columns[columnIndex].id;
1257                                    }
1258                                    properties.filteredColumns[columnIndex]=value;
1259                                    privateMethods.setCurrentPage(object, 1);
1260                                  }
1261                              }
1262                           );
1263                         }
1264                       );
1265              td.append(button);
1266            } // filter button
1267
1268
1269            if(options.columns[i].group==true)
1270            {
1271              // groupable button
1272              button=$('<div/>',
1273                        {
1274                          class:'ui-dynamicTableGroupButton-inactive'
1275                        }
1276                      )
1277                      .bind('click', i,
1278                         function (event)
1279                         {
1280                           var columnIndex=event.data,
1281                               $button=$(this);
1282
1283                          $button.toggleClass('ui-dynamicTableGroupButton-inactive ui-dynamicTableGroupButton-active');
1284
1285                          if($button.hasClass('ui-dynamicTableGroupButton-active'))
1286                          {
1287                            properties.groupedColumns[columnIndex]=options.columns[columnIndex].id;
1288                          }
1289                          else
1290                          {
1291                            delete properties.groupedColumns[columnIndex];
1292                          }
1293
1294                          privateMethods.setCurrentPage(object, 1);
1295                         }
1296                       );
1297              td.append(button);
1298            } // groupable button
1299
1300
1301            objects.headerTr.append(td);
1302
1303            td=$('<td/>');
1304            if(options.columns[i].width!='') td.attr('style', 'width:'+options.columns[i].width+';');
1305            objects.totalRowTr.append(td);
1306          }
1307
1308          if(properties.hasSortableButton)
1309          {
1310            button=$('<div/>',
1311                      {
1312                        class:'ui-dynamicTableSortButton',
1313                      }
1314                    );
1315            button.bind('click',
1316                    function (event)
1317                      {
1318                        var cWidth=0,
1319                            tWidth=0;
1320
1321                        for(var i=0;i<options.columns.length;i++)
1322                        {
1323                          tWidth=objects.header.find('[oId="'+options.columns[i].id+'"]').width();
1324                          if(tWidth>cWidth) cWidth=tWidth;
1325                        }
1326
1327                        $.inputDialogSortBox(
1328                          {
1329                            buttons:{
1330                              ok:options.dialogsButtons.ok,
1331                              cancel:options.dialogsButtons.cancel
1332                            },
1333                            modal:true,
1334                            width:cWidth,
1335                            height:250,
1336                            autoHeight:false,
1337                            title:options.sortBoxTitle,
1338                            mode:'direction',
1339                            items:properties.sortedColumns,
1340                            change: function (event, value)
1341                              {
1342                                properties.sortedColumns=value;
1343                                privateMethods.setCurrentPage(object, 1);
1344                              }
1345                          }
1346                        );
1347
1348                      }
1349                    );
1350
1351            td=$('<td/>',
1352                  {
1353                    'oId':'sort',
1354                    class:'ui-dynamicTableSortColumn'
1355                  }
1356                ).append(button);
1357            objects.headerTr.append(td);
1358
1359            td=$('<td/>');
1360            objects.totalRowTr.append(td);
1361          }
1362        }, //updateTable
1363
1364      /**
1365       * load table content
1366       *
1367       * @param Integer page: page to load; if not specified, use the current page
1368       */
1369      loadContent : function (object, page)
1370        {
1371          var tmpData=null,
1372              data=null,
1373              tr=null,
1374              td=null,
1375              options=object.data('options'),
1376              objects=object.data('objects'),
1377              properties=object.data('properties');
1378
1379          if(options.postUrl=='') return(false);
1380
1381          if(page>0 && page <= objects.footerPagesNavigator.inputPages('nbPages'))
1382            options.currentPage=page;
1383          privateMethods.displayLoading(object, true);
1384
1385          data=options.postData;
1386          data.currentPage=options.currentPage;
1387          data.nbItemsPage=options.nbItemsPage;
1388
1389          tmpData=privateMethods.getPostProperties(object);
1390          data.sort=tmpData.sort;
1391          data.filter=tmpData.filter;
1392          data.group=tmpData.group;
1393
1394          if(options.contentLoading) object.trigger('dynamicTableContentLoading', data);
1395
1396          $.ajax(
1397            {
1398              type: "POST",
1399              url: options.postUrl,
1400              async: true,
1401              data:data,
1402              success: function(msg)
1403                {
1404                  msg=$.parseJSON(msg);
1405
1406                  if(msg==null || msg.rows==null)
1407                  {
1408                    privateMethods.displayLoading(object, false);
1409                    return(false);
1410                  }
1411
1412                  if(options.contentLoaded) object.trigger('dynamicTableContentLoaded', msg);
1413
1414                  objects.content.find('tr').unbind('click.dynamicTable');
1415                  objects.content.children().remove();
1416                  objects.contentContainer.scrollTop('0px');
1417
1418                  delete properties.loadedData;
1419                  properties.loadedData=[];
1420
1421                  for(var row=0;row<msg.rows.length;row++)
1422                  {
1423                    tr=$('<tr/>', {'oId':row});
1424
1425                    properties.loadedData[row]=msg.rows[row];
1426
1427                    for(var col=0;col<msg.rows[row].length;col++)
1428                    {
1429                      if(col<options.columns.length)
1430                      {
1431                        td=$('<td/>').html(msg.rows[row][col]);
1432
1433                        if((col==msg.rows[row].length-1) && properties.hasSortableButton) td.attr('colspan', '2');
1434                        tr.append(td);
1435                      }
1436                    }
1437                    objects.content.append(tr);
1438                  }
1439
1440                  if(msg.nbItems!=null)
1441                  {
1442                    objects.footerPagesNavigator
1443                      .inputPages('nbItems', msg.nbItems);
1444
1445                    privateMethods.setNbItems(object, msg.nbItems);
1446                    objects.footer.css('display', 'block');
1447
1448                    if(msg.nbItems==0)
1449                    {
1450                      objects.footerPagesNavigator.css('display', 'none');
1451                    }
1452                    else
1453                    {
1454                      objects.footerPagesNavigator.css('display', 'block');
1455                    }
1456                  }
1457                  else
1458                  {
1459                    objects.footer.css('display', 'none');
1460                  }
1461
1462                  if(msg.total!=null && $.isArray(msg.total))
1463                  {
1464                    properties.totalRowHasData=true;
1465                    objects.totalRowTr.children().each(
1466                      function (index)
1467                      {
1468                        $(this).html(msg.total[index]);
1469                      }
1470                    );
1471                  }
1472                  else
1473                  {
1474                    properties.totalRowHasData=false;
1475                  }
1476
1477                  if(options.click)
1478                    objects.content.find('tr').bind('click.dynamicTable', options.click);
1479
1480                  privateMethods.showTotalRow(object);
1481                  privateMethods.setColumnsSize(object);
1482
1483                  if(options.contentDisplayed) object.trigger('dynamicTableContentDisplayed', msg);
1484                  privateMethods.displayLoading(object, false);
1485                },
1486              error: function(msg)
1487                {
1488                  //
1489                  objects.loadingContent.attr('style', 'display:none;');
1490                  objects.loadingContentWorkInProgress.attr('style', 'display:none;');
1491                },
1492            }
1493         );
1494        }, //loadContent
1495
1496      // return a ready-to-use filter/group/sort object
1497      getPostProperties: function (object)
1498        {
1499          var data={},
1500              properties=object.data('properties');
1501
1502          data.sort=[];
1503          for(var i=0;i<properties.sortedColumns.length;i++)
1504          {
1505            data.sort.push(
1506              {
1507                id:properties.sortedColumns[i].id,
1508                direction:(properties.sortedColumns[i].direction=='asc')?'A':'D'
1509              }
1510            );
1511          }
1512          data.filter=[];
1513          for(var i in properties.filteredColumns)
1514          {
1515            data.filter.push(properties.filteredColumns[i]);
1516          }
1517
1518          data.group=[];
1519          for(var i in properties.groupedColumns)
1520          {
1521            data.group.push(properties.groupedColumns[i]);
1522          }
1523          return(data);
1524        }, //getPostProperties
1525
1526      setColumnsSize : function (object)
1527        {
1528          var cols=[],
1529              options=object.data('options'),
1530              properties=object.data('properties'),
1531              objects=object.data('objects');
1532
1533          if(!(objects.header || objects.content)) return(false);
1534          // set columns width
1535          objects.header.find('tr:first td').each(
1536            function (index)
1537            {
1538              cols[index]=$(this).width();
1539            }
1540          );
1541
1542          // resize first row of table content
1543          objects.content.find('tr:first td').each(
1544            function (index)
1545            {
1546              var style='';
1547
1548              if(index==(cols.length-1))
1549              {
1550                style='max-width:';
1551              }
1552              else
1553              {
1554                style='width:';
1555              }
1556              $(this).attr('style', style+cols[index]+'px;');
1557            }
1558          );
1559
1560          // resize total row if displayed
1561          if(options.showTotalRow=='visible' ||
1562             options.showTotalRow=='auto' && properties.totalRowHasData)
1563          {
1564            objects.totalRowTr.find('td').each(
1565              function (index)
1566              {
1567                var style='';
1568
1569                if(index==(cols.length-1))
1570                {
1571                  style='max-width:';
1572                }
1573                else
1574                {
1575                  style='width:';
1576                }
1577                $(this).attr('style', style+cols[index]+'px;');
1578              }
1579            );
1580          }
1581
1582          return(true);
1583        }, //setColumnsSize
1584
1585      displayLoading : function (object, display)
1586        {
1587          var objects=object.data('objects');
1588
1589          if(display)
1590          {
1591            objects.loadingContent.attr('style', 'display:block;width:'+objects.contentContainer.width()+'px;height:'+objects.contentContainer.height()+'px;');
1592            objects.loadingContentWorkInProgress.css(
1593              {
1594                'display':'block',
1595                'width':objects.contentContainer.width()+'px',
1596                'height':objects.contentContainer.height()+'px',
1597                'background-position':Math.round((objects.contentContainer.width()-16)/2)+'px '+Math.round((objects.contentContainer.height()-16)/2)+'px'
1598              }
1599            );
1600          }
1601          else
1602          {
1603            objects.loadingContent.attr('style', 'display:none;');
1604            objects.loadingContentWorkInProgress.attr('style', 'display:none;');
1605          }
1606        }, //displayLoading
1607
1608      showTotalRow : function (object)
1609        {
1610          var options=object.data('options'),
1611              objects=object.data('objects'),
1612              properties=object.data('properties');
1613
1614          switch(options.showTotalRow)
1615          {
1616            case 'visible':
1617              objects.totalRowContent.css('display',  'block');
1618              break;
1619            case 'hidden':
1620              objects.totalRowContent.css('display', 'none');
1621              break;
1622            case 'auto':
1623              if(properties.totalRowHasData)
1624              {
1625                objects.totalRowContent.css('display', 'block');
1626              }
1627              else
1628              {
1629                objects.totalRowContent.css('display', 'none');
1630              }
1631              break;
1632          }
1633        }, // showTotalRow
1634
1635      updateNbItems: function (object)
1636        {
1637          var options=object.data('options'),
1638              objects=object.data('objects'),
1639              properties=object.data('properties');
1640
1641          if(properties.nbItems>1)
1642          {
1643            objects.footerNbItems.html(options.footerString.plural.replace('%', properties.nbItems));
1644          }
1645          else
1646          {
1647            objects.footerNbItems.html(options.footerString.singular.replace('%', properties.nbItems));
1648          }
1649
1650          if(properties.nbItems>0)
1651          {
1652            privateMethods.showSaveButton(object);
1653          }
1654          else
1655          {
1656            privateMethods.showSaveButton(object, true); // force button hide
1657          }
1658
1659        }, // updateNbItems
1660
1661      showSaveButton : function (object, hide)
1662        {
1663          var options=object.data('options'),
1664              objects=object.data('objects');
1665
1666          if(hide==null) hide=false;
1667
1668          if(options.showSaveButton && hide!=true)
1669          {
1670            objects.footerSaveButton.css('display',  'block');
1671          }
1672          else
1673          {
1674            objects.footerSaveButton.css('display',  'none');
1675          }
1676        }, // showSaveButton
1677
1678      applyDownloadWaitState: function (object)
1679        {
1680          var options=object.data('options'),
1681              objects=object.data('objects'),
1682              properties=object.data('properties');
1683
1684          if(properties.downloadWaitState)
1685          {
1686            objects.footerSaveButton
1687              .removeClass('ui-dynamicTableFooter-saveButton')
1688              .addClass('ui-dynamicTableFooter-saveButtonWait');
1689            objects.footerNbItems.html(options.footerString.waitForDownload);
1690          }
1691          else
1692          {
1693            objects.footerSaveButton
1694              .removeClass('ui-dynamicTableFooter-saveButtonWait')
1695              .addClass('ui-dynamicTableFooter-saveButton');
1696            privateMethods.updateNbItems(object);
1697          }
1698        } // applyDownloadWaitState
1699    };
1700
1701
1702    $.fn.dynamicTable = function(method)
1703    {
1704      if(publicMethods[method])
1705      {
1706        return publicMethods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
1707      }
1708      else if(typeof method === 'object' || ! method)
1709      {
1710        return publicMethods.init.apply(this, arguments);
1711      }
1712      else
1713      {
1714        $.error( 'Method ' +  method + ' does not exist on jQuery.dynamicTable' );
1715      }
1716    } // $.fn.dynamicTable
1717
1718  }
1719)(jQuery);
Note: See TracBrowser for help on using the repository browser.