https://jacarandahealth.org/syssuree/unlimited-elements-for-elemen…/filters/ue_filters.js?ver=2.0.20
1//UE Filters Version 1.27 2 3function UEDynamicFilters(){ 4 5 var g_objFilters, g_filtersData, g_urlBase; 6 var g_urlAjax, g_lastGridAjaxCall, g_cache = {}, g_objBody; 7 var g_remote = null, g_lastSyncGrids, g_initFiltersCounter = 0; 8 9 var t = this; 10 11 var g_showDebug = false; 12 var g_debugInitMode = false; 13 14 var g_debugBeforeRefreshMode = false; //debug filters state before refresh 15 16 var g_isGutenberg = false; 17 18 var g_types = { 19 PAGINATION:"pagination", 20 LOADMORE:"loadmore", 21 TERMS_LIST:"terms_list", 22 SEARCH: "search", 23 SELECT: "select", 24 SUMMARY: "summary", 25 GENERAL: "general", 26 GENERAL_MOBILE_DRAWER: "mobilefilters" 27 }; 28 29 var g_vars = { 30 CLASS_DIV_DEBUG:"uc-div-ajax-debug", 31 CLASS_GRID:"uc-filterable-grid", 32 CLASS_GRID_NOREFRESH:"uc-grid-norefresh", //grid that will not refresh 33 DEBUG_AJAX_OPTIONS: false, 34 CLASS_CLICKED:"uc-clicked", 35 CLASS_HIDDEN: "uc-filter-hidden", //don't refresh with this class 36 CLASS_INITING: "uc-filter-initing", 37 CLASS_INITING_HIDDEN: "uc-initing-filter-hidden", 38 CLASS_SKIP_REFRESH: "uc-filters-norefresh", //on some grid parent 39 CLASS_REFRESH_SOON: "uc-ajax-refresh-soon", 40 EVENT_SET_HTML_ITEMS: "uc_ajax_sethtml", 41 CLASS_FILTER_INITED:"ucfilters--filter-inited", 42 ATTRIBUTE_URLADD:"ajaxurladd", 43 GRID_DATA_SKIP_HTML: "skip_set_html", 44 45 //grid events 46 47 EVENT_BEFORE_REFRESH: "uc_before_ajax_refresh", //on grid 48 EVENT_AJAX_REFRESHED: "uc_ajax_refreshed", //on grid 49 EVENT_AJAX_REFRESHED_BODY: "uc_ajax_refreshed_body", //on body 50 EVENT_UPDATE_ACTIVE_FILTER_ITEMS: "update_active_filter_items", //on grid 51 EVENT_UNSELECT_FILTER: "uc_unselect_filter", //on grid 52 EVENT_SILENT_FILTER_CHANGE: "uc_silent_filter_change", //on grid 53 54 EVENT_DOM_UPDATED: "uc_dom_updated", //on body 55 56 //events on filters 57 58 EVENT_INIT_FILTER:"init_filter", 59 EVENT_INIT_FILTER_TYPE:"init_filter_type", 60 EVENT_GET_FILTER_DATA:"get_filter_data", 61 EVENT_FILTER_RELOADED: "uc_ajax_reloaded", 62 63 //grid actions 64 65 ACTION_CLEAR_FILTERS: "clear_filters", //on grid 66 ACTION_REFRESH_GRID: "uc_refresh", //listen on grid 67 ACTION_GET_FILTERS_URL: "uc_get_filters_url", //listen on grid 68 ACTION_FILTER_CHANGE: "uc_filter_change", //listen on grid 69 ACTION_FILTER_UNSELECT_BY_KEY: "unselect_by_key", //listen on grid 70 71 REFRESH_MODE_PAGINATION: "pagination", 72 REFRESH_MODE_LOADMORE: "loadmore", 73 trashold_handle:null, 74 class_widget_wrapper:"elementor-widget", 75 current_postid:null, 76 ucpage_url:null 77 }; 78 79 var g_options = { 80 is_cache_enabled:true, 81 urlkey_taxsap:"~" 82 }; 83 84 /** 85 * console log some string 86 */ 87 function trace(str){ 88 console.log(str); 89 } 90 91 function ________GENERAL_______________(){} 92 93 94 95 /** 96 * add url param 97 */ 98 function addUrlParam(url, param, value){ 99 100 if(url){ 101 if(url.indexOf("?") == -1) 102 url += "?"; 103 else 104 url += "&"; 105 } 106 107 if(typeof value == "undefined") 108 url += param; 109 else 110 url += param + "=" + value; 111 112 return(url); 113 } 114 115 116 /** 117 * get object property 118 */ 119 function getVal(obj, name, defaultValue){ 120 121 if(!defaultValue) 122 var defaultValue = ""; 123 124 var val = ""; 125 126 if(!obj || typeof obj != "object") 127 val = defaultValue; 128 else if(obj.hasOwnProperty(name) == false){ 129 val = defaultValue; 130 }else{ 131 val = obj[name]; 132 } 133 134 return(val); 135 } 136 137 /** 138 * turn string value ("true", "false") to string 139 */ 140 function strToBool(str){ 141 142 switch(typeof str){ 143 case "boolean": 144 return(str); 145 break; 146 case "undefined": 147 return(false); 148 break; 149 case "number": 150 if(str == 0) 151 return(false); 152 else 153 return(true); 154 break; 155 case "string": 156 str = str.toLowerCase(); 157 158 if(str == "true" || str == "1") 159 return(true); 160 else 161 return(false); 162 163 break; 164 } 165 166 return(false); 167 }; 168 169 /** 170 * get offsets distance 171 */ 172 function getOffsetsDistance(offset1, offset2){ 173 174 var dx = offset2.left-offset1.left; 175 var dy = offset2.top-offset1.top; 176 177 return Math.sqrt(dx*dx+dy*dy); 178 } 179 180 /** 181 * round number to one decimal 182 */ 183 function roundToOneDecimal(num) { 184 if (num % 1 !== 0) { 185 return num.toFixed(1); // Round to 1 decimal place 186 } else { 187 return num.toFixed(0); // Keep the whole number 188 } 189 } 190 191 192 /** 193 * get closest object by offset 194 */ 195 function getClosestByOffset(objParents, objElement, isVertical){ 196 197 if(objParents.length == 0){ 198 throw new Error("get closest by offset error - grids not found"); 199 } 200 201 if(g_showDebug == true){ 202 203 trace("get closest grids for"); 204 trace(objElement) 205 trace("parents"); 206 trace(objParents); 207 } 208 209 var objClosest = null; 210 var minDiff = 1000000; 211 212 var elementOffset = objElement.offset(); 213 214 jQuery.each(objParents, function(index, parent){ 215 216 var objParent = jQuery(parent); 217 218 var objGrid = jQuery(parent); //return this one 219 220 var distance = 0; 221 222 var isVisible = objParent.is(":visible"); 223 224 var constantHeight = null; 225 226 if(isVisible == false){ 227 objParent = objParent.parent(); 228 } 229 230 var parentOffset = objParent.offset(); 231 232 if(isVertical == true){ 233 234 var offsetY = elementOffset.top; 235 var parentY = parentOffset.top; 236 237 //get bottom of the parent 238 239 if(parentY < offsetY) 240 parentY += objParent.height(); 241 242 var distance = Math.abs(offsetY - parentY); 243 244 }else{ 245 246 var parentOffset = objParent.offset(); 247 248 var distance = getOffsetsDistance(parentOffset, elementOffset); 249 } 250 251 if(g_showDebug == true){ 252 253 trace(objParent); 254 trace("distance: " + distance); 255 256 trace("is vertical: " + isVertical); 257 } 258 259 if(distance < minDiff){ 260 minDiff = distance; 261 objClosest = objGrid; 262 } 263 264 }); 265 266 if(g_showDebug == true){ 267 268 trace("filter: "); 269 trace(objElement); 270 271 trace("Closest grid found:"); 272 trace(objClosest); 273 } 274 275 276 return(objClosest); 277 } 278 279 /** 280 * get all grids 281 */ 282 function getAllGrids(type){ 283 284 if(type == "loaded_only") 285 var objGrids = jQuery("."+ g_vars.CLASS_GRID).not(".ucfilters--grid-inited"); 286 else 287 var objGrids = jQuery("."+ g_vars.CLASS_GRID); 288 289 return(objGrids); 290 } 291 292 293 /** 294 * get grid from parents containers 295 */ 296 function getGridFromParentContainers(objSource){ 297 298 var objParents = objSource.parents(); 299 var objGrid = null; 300 301 if(g_showDebug == true){ 302 303 trace("get from parent containers"); 304 trace(objParents); 305 } 306 307 objParents.each(function(){ 308 309 var objParent = jQuery(this); 310 311 objGrid = objParent.find("."+ g_vars.CLASS_GRID); 312 313 //if grid found return it and exit loop 314 if(objGrid.length >= 1) 315 return(false); 316 317 }); 318 319 320 return(objGrid); 321 } 322 323
324 /** 325 * get closest grid to some object 326 */ 327 function getClosestGrid(objSource){ 328 329 //in case there are nothing: 330 var objGrids = getAllGrids(); 331 332 if(objGrids.length == 0) 333 return(null); 334 335 if(g_showDebug == true){ 336 337 trace("get closest grids"); 338 trace(objSource); 339 trace(objGrids); 340 } 341 342 //get grid from parents 343 344 if(objGrids.length == 1) 345 return(objGrids); 346 347 //narrow by group 348 var group = objSource.data("connectgroup"); 349 350 if(group){ 351 var objGridsGroup = objGrids.filter("[data-filtergroup="+group+"]"); 352 353 if(objGridsGroup.length > 0){ 354 355 if(objGridsGroup.length == 1) 356 return(objGridsGroup); 357 358 objGrids = objGridsGroup; 359 } 360 361 }else{ 362 363 //get from same container - if group not set 364 365 var objGrid = getGridFromParentContainers(objSource); 366 367 if(objGrid && objGrid.length == 1) 368 return(objGrid); 369 } 370 371 372 //get closest by offset 373 374 if(objGrid && objGrid.length > 1) 375 objGrids = objGrid; 376 377 var objSingleGrid = getClosestByOffset(objGrids, objSource, true); 378 379 if(objSingleGrid && objSingleGrid.length == 1) 380 return(objSingleGrid); 381 382 //return first grid in the list 383 384 var objFirstGrid = jQuery(objGrids[0]); 385 386 return(objFirstGrid); 387 } 388 389 390 391 /** 392 * add filter object to grid 393 */ 394 function bindFilterToGrid(objGrid, objFilter){ 395 396 if(g_showDebug){ 397 trace("bind filter to grid"); 398 399 trace(objFilter); 400 } 401 402 var arrFilters = objGrid.data("filters"); 403 var objTypes = objGrid.data("filter_types"); 404 405 if(!arrFilters) 406 arrFilters = []; 407 408 if(!objTypes) 409 objTypes = {}; 410 411 var type = getFilterType(objFilter); 412 413 //validate double types 414 415 if(objTypes.hasOwnProperty(type)){ 416 417 switch(type){ 418 case g_types.LOADMORE: 419 420 trace("Double filter not allowed"); 421 trace("existing Filters:"); 422 trace(arrFilters); 423 424 trace("Second Filter"); 425 trace(objFilter); 426 427 trace("Grid:"); 428 trace(objGrid); 429 430 showElementError(objFilter, "Double load more button for one grid not allowed") 431 return(false); 432 break; 433 } 434 435 } 436 437 objTypes[type] = true; 438 439 var filterID = objFilter.attr("id"); 440 441 //handle sticky 442 443 var objElementorStickySpacer = objFilter.closest(".elementor-sticky__spacer"); 444 if(objElementorStickySpacer.length) 445 return(true); 446 447 448 //----- validate existing ----- 449 450 var objExistingFilter = arrFilters.filter(function(objFilterInArray){ 451 return objFilterInArray.attr("id") == filterID; 452 }); 453 454 if(objExistingFilter && objExistingFilter.length) 455 throw new Error("Can't bind filter to grid, it's already exists: " + filterID); 456 457 arrFilters.push(objFilter); 458 459 //add init after filters 460 var isInitAfter = objFilter.data("initafter"); 461 462 if(!isInitAfter) 463 isInitAfter = isSpecialFilterInitAfter(objFilter, objGrid); 464 465 if(g_showDebug){ 466 trace("init after: "+isInitAfter); 467 } 468 469 if(isInitAfter === true){ 470 addFilterToInitAfter(objFilter, objGrid); 471 } 472 473 objGrid.data("filters", arrFilters); 474 475 objGrid.data("filter_types", objTypes); 476 477 } 478 479 /** 480 * 481 * get element widget id from parent wrapper 482 */ 483 function getElementWidgetID(objElement){ 484 485 if (!objElement || objElement.length === 0) 486 throw new Error("Element not found"); 487 488 var objWidget = objElement.closest("."+g_vars.class_widget_wrapper); 489 490 if (objWidget.length === 0) 491 throw new Error("Element parent not found with class: "+g_vars.class_widget_wrapper); 492 493 var widgetID = objWidget.data("id"); 494 495 if (!widgetID) 496 throw new Error("widget id not found"); 497 498 return widgetID; 499 } 500 501 502 /** 503 * get the grid widget object from elementor element id 504 */ 505 function getGridFromElementorElementID(elementID, group, showDebug){ 506 507 var selector = "."+g_vars.class_widget_wrapper+"[data-id='"+elementID+"']"; 508 509 var objElement = g_objBody.find(selector); 510 511 if(showDebug == true){ 512 trace("selector: "+selector); 513 trace("element: "); 514 trace(objElement); 515 } 516 517 if(objElement.length == 0) 518 return(null); 519 520 var selectorGrid = "."+g_vars.CLASS_GRID; 521 522 var objGrid = objElement.find(selectorGrid); 523 524 if(showDebug == true){ 525 trace("selector grid: "+selectorGrid); 526 trace("grid: "); 527 trace(objGrid); 528 } 529 530 if(objGrid.length == 1) 531 return(objGrid); 532 533 if(objGrid.length == 0) 534 return(null); 535 536 //more then one, filter by group 537 if(group){ 538 objGrid = objGrid.filter("[data-filtergroup="+group+"]"); 539 } 540 541 if(showDebug == true){ 542 trace("after group filter: "+group); 543 trace(objGrid); 544 } 545 546 if(objGrid.length != 1) 547 return(null); 548 549 550 return(objGrid); 551 } 552 553 554 555 /** 556 * get another group widgets 557 */ 558 function getGroupWidgets(arrSyncedGrids, objElement){ 559 560 var group = objElement.data("filtergroup"); 561 562 if(!group) 563 return(arrSyncedGrids); 564 565 var objGrids = jQuery("."+ g_vars.CLASS_GRID); 566 567 if(objGrids.length < 2) 568 return(arrSyncedGrids); 569 570 var elementID = objElement.attr("id"); 571 572 var objDataGrids = objGrids.filter("[data-filtergroup='"+group+"']:not(#" + elementID + ")"); 573 574 if(objDataGrids.length == 0) 575 return(arrSyncedGrids); 576 577 jQuery.each(objDataGrids, function(index, grid){ 578 579 var objGrid = jQuery(grid); 580 581 arrSyncedGrids.push(objGrid); 582 }); 583 584 585 586 return(arrSyncedGrids); 587 } 588 589 /** 590 * get synced widget IDs 591 */ 592 function getSyncedWidgetData(objElement){ 593 594 var arrSyncedGrids = []; 595 596 if(g_remote) 597 arrSyncedGrids = g_remote.getSyncedElements(objElement); 598 599 if(!arrSyncedGrids) 600 arrSyncedGrids = []; 601 602 arrSyncedGrids = getGroupWidgets(arrSyncedGrids, objElement); 603 604 if(!arrSyncedGrids || arrSyncedGrids.length == 0) 605 return(false); 606 607 var arrWidgetIDs = []; 608 609 var objGrids = null; 610 611 for(var index in arrSyncedGrids){ 612 613 var objGrid = arrSyncedGrids[index]; 614 615 if(objGrid.hasClass(g_vars.CLASS_GRID) == false){ 616 617 var message = "Please enable ajax on all synced widgets"; 618 var message2 = "Please enable ajax on this synced widget, it's missing class: "+g_vars.CLASS_GRID; 619 620 showElementError(objGrid, message2); 621 622 showAjaxError(message); 623 throw new Error(message); 624 return(false); 625 } 626 627 var objWidgetID = getElementWidgetID(objGrid); 628 629 //add to jquery collection 630 631 if(!objGrids) 632 objGrids = objGrid; 633 else 634 objGrids = objGrids.add(objGrid); 635 636 arrWidgetIDs.push(objWidgetID); 637 } 638 639 var strWidgetIDs = arrWidgetIDs.toString(); 640 641 var objOutput = {}; 642 objOutput["ids"] = strWidgetIDs; 643 objOutput["grids"] = objGrids; 644 645 return(objOutput); 646 } 647 648 649 /** 650 * get element layout data 651 */ 652 function getElementLayoutData(objElement, addSyncedGrids){ 653 654 //get widget id 655 var widgetID = getElementWidgetID(objElement); 656 var objWidget = objElement.parents("."+g_vars.class_widget_wrapper); 657 658 //get synced grids 659 var objSyncedData = null; 660
661 //add sync if allowed and available 662 663 if(addSyncedGrids){ 664 665 var objSyncedData = getSyncedWidgetData(objElement); 666 667 if(g_showDebug && objSyncedData){ 668 669 trace("sync data"); 670 trace(objSyncedData); 671 } 672 }else{ 673 674 if(g_showDebug) 675 trace("skip sync grid"); 676 677 } 678 679 //get layout id 680 681 if(g_isGutenberg == false){ 682 683 var objLayout = objWidget.parents(".elementor"); 684 685 if(objLayout.length == 0) 686 throw new Error("layout not found"); 687 688 var layoutID = objLayout.data("elementor-id"); 689 690 if(!layoutID) 691 layoutID = objLayout.data("id"); 692 693 }else{ //gutenberg 694 695 var layoutID = g_vars.current_postid; 696 } 697 698 699 var output = {}; 700 701 output["widgetid"] = widgetID; 702 output["layoutid"] = layoutID; 703 704 if(objSyncedData){ 705 output["synced_widgetids"] = objSyncedData["ids"]; 706 output["synced_grids"] = objSyncedData["grids"]; 707 } 708 709 return(output); 710 } 711 712 /** 713 * show element error above it 714 */ 715 function showElementError(objElement, error){ 716 717 var objParent = objElement.parent(); 718 719 if(g_showDebug == true){ 720 trace("Show Error Message for: "); 721 trace(objElement); 722 trace(error); 723 } 724 725 var objError = objParent.find(".uc-filers-error-message"); 726 if(objError.length == 0){ 727 objParent.append("<div class='uc-filers-error-message' style='color:red;position:absolute;top:-24px;left:0px;background-color:rgba(230, 230, 230, 0.8);padding:3px;font-size:12px;border:5px solid white;'></div>"); 728 var objError = objParent.find(".uc-filers-error-message"); 729 objParent.css("border","1px solid red !important"); 730 } 731 732 objError.append(error); 733 734 objError.css("top",-objError.height()-5); 735 736 } 737 738 /** 739 * get grid empty message 740 */ 741 function getGridEmptyMessage(objGrid){ 742 743 var gridID = objGrid.attr("id"); 744 745 if(!gridID) 746 return(null); 747 748 var objEmptyMessage = jQuery("#"+gridID+"_empty_message"); 749 750 if(objEmptyMessage.length == 0) 751 return(null); 752 753 return(objEmptyMessage); 754 } 755 756 /** 757 * get active filter items, if no items - return 0 758 */ 759 function getGridActiveFilterItems(objGrid){ 760 761 var arrActiveItems = objGrid.data("active_filters_items"); 762 763 if(!arrActiveItems) 764 return(null); 765 766 if(arrActiveItems.length == 0) 767 return(null); 768 769 return(arrActiveItems); 770 } 771 772 773 /** 774 * get filters that are selected 775 */ 776 function getSelectedFilters(objFilters, roleArg){ 777 778 if(!objFilters) 779 var objFilters = objGrid.data("filters"); 780 781 if(!objFilters) 782 return(false); 783 784 var arrSelectedFilters = []; 785 786 jQuery.each(objFilters, function(index, filter){ 787 788 var objFilter = jQuery(filter); 789 var isSelected = objFilter.hasClass("uc-has-selected"); 790 791 if(!roleArg && isSelected == true){ 792 arrSelectedFilters.push(objFilter); 793 return(true); 794 } 795 796 var role = objFilter.data("role"); 797 798 if(role == roleArg){ 799 var isSelected = objFilter.hasClass("uc-has-selected"); 800 if(isSelected) 801 arrSelectedFilters.push(objFilter); 802 } 803 804 }); 805 806 return(arrSelectedFilters); 807 } 808 809 810 function ________FILTERS_______________(){} 811 812 813 /** 814 * get the parent 815 */ 816 function getFiltersParent(objFilters){ 817 818 //init the events 819 var objParent = objFilters.parents(".elementor"); 820 821 if(objFilters.length > 1 && objParent.length > 1) 822 objParent = objFilters.parents("body"); 823 824 if(objParent.length > 1){ 825 objParent = jQuery(objParent[0]); 826 } 827 828 if(objParent.length == 0) 829 objParent = objFilters.parents("body"); 830 831 return(objParent); 832 } 833 834 /** 835 * get filter wrapper 836 */ 837 function getFilterWrapper(objFilter){ 838 839 var objParent = objFilter.parent(); 840 841 if(objParent.hasClass("uc-checkbox-filter-accordion-container")) 842 objParent = objParent.parent(); 843 844 return(objParent); 845 } 846 847 848 /** 849 * get filter type 850 */ 851 function getFilterType(objFilter, getGeneralType){ 852 853 if(objFilter.hasClass("uc-filter-pagination")) 854 return(g_types.PAGINATION); 855 856 if(objFilter.hasClass("uc-filter-load-more")) 857 return(g_types.LOADMORE); 858 859 var filterType = objFilter.data("filtertype") 860 861 if(filterType == g_types.GENERAL && getGeneralType === true){ 862 863 var generalType = objFilter.data("generaltype"); 864 return(generalType); 865 } 866 867 if(filterType) 868 return(filterType); 869 870 //if not found - throw error 871 872 trace("Filter type not found: "); 873 trace(objFilter); 874 875 throw new Error("wrong filter type"); 876 877 } 878 879 880 /** 881 * clear all filters 882 */ 883 function clearAllFilters(objGrid){ 884
885 clearChildFilters(objGrid, null, true, null, true); 886 } 887 888 /** 889 * get grid filters or null 890 */ 891 function getGridFilters(objGrid){ 892 893 var objFilters = objGrid.data("filters"); 894 895 if(!objFilters) 896 return(null); 897 898 if(objFilters.length == 0) 899 return(null); 900 901 return(objFilters); 902 } 903 904 905 /** 906 * clear non main grid filters 907 * hide children and just clear the main filters 908 */ 909 function clearChildFilters(objGrid, objCurrentFilter, isHideChildren, termID, isClearAll){ 910 911 var objFilters = getGridFilters(objGrid); 912 913 if(!objFilters) 914 return(false); 915 916 var currentFilterID = null; 917 918 if(objCurrentFilter) 919 var currentFilterID = objCurrentFilter.attr("id"); 920 921 jQuery.each(objFilters, function(index, filter){ 922 923 var objFilter = jQuery(filter); 924 var filterID = objFilter.attr("id"); 925 926 if(filterID == currentFilterID) 927 return(true); 928 929 var role = objFilter.data("role"); 930 931 //clear all others if that option selected 932 933 if(role != "child" && role != "main" && role != "term_child"){ 934 935 if(isClearAll == true){ 936 clearFilter(objFilter); 937 } 938 939 return(true); 940 } 941 942 var isHide = false;
943 var isShow = false; 944 945 switch(role){ 946 case "term_child": 947 if(isHideChildren == true) 948 isHide = true; 949 950 var linkedTermID = objFilter.data("childterm"); 951 952 if(linkedTermID == termID){ //show the filter 953 954 objFilter.removeClass(g_vars.CLASS_HIDDEN); 955 objFilter.removeClass(g_vars.CLASS_INITING); 956 objFilter.removeClass(g_vars.CLASS_INITING_HIDDEN); 957 }else{ 958 isHide = true; 959 } 960 961 break; 962 case "child": 963 964 if(isHideChildren == true) 965 isHide = true; 966 else{ 967 //hide the filters and refresh 968 969 objFilter.removeClass(g_vars.CLASS_HIDDEN); 970 971 objFilter.addClass(g_vars.CLASS_INITING); 972 objFilter.addClass(g_vars.CLASS_INITING_HIDDEN); 973 974 } 975 976 break; 977 default: 978 979 if(isClearAll == true){ 980 clearFilter(objFilter); 981 } 982 983 return(true); 984 break; 985 } 986 987 //hide the child filters and not refresh 988 989 if(isHide == true) 990 objFilter.addClass(g_vars.CLASS_HIDDEN); 991 992 clearFilter(objFilter); 993 994 }); 995 996 } 997 998 /** 999 * clear some filter 1000 */ 1001 function clearFilter(objFilter){ 1002 1003 var type = getFilterType(objFilter); 1004 1005 switch(type){ 1006 case g_types.TERMS_LIST: 1007 var objSelectedItems = objFilter.find(".ue_taxonomy_item.uc-selected"); 1008 objSelectedItems.removeClass("uc-selected"); 1009 1010 var objAll = objFilter.find(".ue_taxonomy_item.uc-item-all"); 1011 objAll.addClass("uc-selected"); 1012 1013 break; 1014 case g_types.SELECT: 1015 1016 var objSelect = objFilter.find("select"); 1017 objSelect.val(""); 1018 1019 //must leave one selected 1020 var objSelected = objFilter.find("option:selected"); 1021 1022 if(objSelected.length == 0) 1023 objFilter.find("option:first-child").prop("selected","selected"); 1024 1025 break; 1026 default: 1027 case g_types.SEARCH: 1028 case g_types.GENERAL: 1029 objFilter.trigger("clear_filter"); 1030 break; 1031 } 1032 1033 } 1034 1035 /** 1036 * unselect filter item 1037 */ 1038 function unselectFilterItem(objGrid, key){ 1039 1040 var objFilters = getGridFilters(objGrid); 1041 1042 if(!objFilters) 1043 return(false); 1044 1045 jQuery.each(objFilters, function(index, filter){ 1046 1047 var objFilter = jQuery(filter); 1048 1049 objFilter.trigger(g_vars.ACTION_FILTER_UNSELECT_BY_KEY, [key]); 1050 1051 }); 1052 1053 } 1054 1055 /** 1056 * return true if the filter skip's it's action - like under mobile drawer 1057 */ 1058 function isFilterSkipAction(objFilter){ 1059 1060 var objParentSkipRefresh = objFilter.parents("." + g_vars.CLASS_SKIP_REFRESH); 1061 1062 if(objParentSkipRefresh.length) 1063 return(true); 1064 1065 return(false); 1066 } 1067 1068 /** 1069 * return if the grid has some child filters 1070 */ 1071 function hasChildFilters(objGrid){ 1072 1073 var objFilters = getGridFilters(objGrid); 1074 1075 if(!objFilters) 1076 return(false); 1077 1078 for(var index in objFilters){ 1079 1080 var objFilter = objFilters[index]; 1081 var role = objFilter.data("role"); 1082 if(role == "child") 1083 return(true); 1084 } 1085 1086 return(false); 1087 } 1088 1089 /** 1090 * check and trigger skip action to the grid if needed 1091 * run before the refresh on some filter click 1092 * for the mobile drawer (off canvas) 1093 */ 1094 function checkTriggerSkipAction(objFilter, objGrid){ 1095 1096 var isSkipAction = isFilterSkipAction(objFilter); 1097 if(isSkipAction == false) 1098 return(false); 1099 1100 if(g_showDebug == true) 1101 trace("skip refresh - silent change triggered"); 1102 1103 var filterRole = objFilter.data("role"); 1104 1105 objGrid.trigger(g_vars.EVENT_SILENT_FILTER_CHANGE); 1106 1107 initGrid_setActiveFiltersData(objGrid); 1108 1109 //refresh children only main / children available 1110 if(filterRole == "main" && hasChildFilters(objGrid)){ 1111 1112 if(g_showDebug == true) 1113 trace("refresh children only"); 1114 1115 objGrid.data(g_vars.GRID_DATA_SKIP_HTML, true); 1116 refreshAjaxGrid(objGrid); 1117 } 1118 1119 1120 return(true); 1121 } 1122 1123 function ________PAGINATION_FILTER______(){} 1124 1125 1126 /** 1127 * get pagination selected url or null if is current 1128 */ 1129 function getPaginationSelectedData(objPagination){ 1130 1131 var objCurrentLink = objPagination.find("a.current,span.current"); 1132 1133 if(objCurrentLink.length == 0) 1134 return(null); 1135 1136 var url = objCurrentLink.attr("href"); 1137 1138 var numPage = objCurrentLink.text(); 1139 1140 if(jQuery.isNumeric(numPage) == false) 1141 numPage = null; 1142 1143 numPage = Number(numPage); 1144 1145 if(numPage === 1) 1146 numPage = null; 1147 1148 var output = {}; 1149 output["url"] = url; 1150 output["page"] = numPage; 1151 1152 return(output); 1153 } 1154 1155 1156 /** 1157 * on ajax pagination click 1158 */ 1159 function onAjaxPaginationLinkClick(event){ 1160 1161 var objLink = jQuery(this); 1162 1163 //if no grid attached - act like a regular link 1164 1165 var objPagination = objLink.parents(".uc-filter-pagination"); 1166 1167 var objGrid = objPagination.data("grid"); 1168 1169 if(!objGrid || objGrid.length == 0 || objPagination.hasClass("uc-no-ajax")){ 1170 1171 return(true); 1172 } 1173
1174 //run the ajax, prevent default 1175 event.preventDefault(); 1176 1177 var objLinkCurrent = objPagination.find(".current"); 1178 1179 1180 //on next button click 1181 1182 if(objLink.hasClass("next")){ 1183 1184 var nextLink = objLinkCurrent.next(); 1185 1186 var objNextLink = jQuery(nextLink); 1187 1188 objNextLink.trigger("click"); 1189 1190 return(false); 1191 } 1192 1193 1194 //on prev button click 1195 1196 if(objLink.hasClass("prev")){ 1197 1198 var prevLink = objLinkCurrent.prev(); 1199 1200 var objPrevLink = jQuery(prevLink); 1201 1202 objPrevLink.trigger("click"); 1203 1204 return(false); 1205 } 1206 1207 objLinkCurrent.removeClass("current"); 1208 1209 objLink.addClass("current"); 1210 1211 var objGrid = objPagination.data("grid"); 1212 1213 objPagination.addClass(g_vars.CLASS_CLICKED); 1214 1215 if(g_showDebug == true){ 1216 1217 trace("click on pagination!!!, no grid refresh"); 1218 trace(objLink); 1219 1220 }else{ 1221 1222 refreshAjaxGrid(objGrid, g_vars.REFRESH_MODE_PAGINATION); 1223 1224 } 1225 1226 return(false); 1227 } 1228 1229 1230 function ________LOAD_MORE_______________(){} 1231 1232 1233 /** 1234 * get current load more page 1235 */ 1236 function getLoadMoreUrlData(objFilter){ 1237 1238 var objData = objFilter.find(".uc-filter-load-more__data"); 1239 1240 var nextOffset = objData.data("nextoffset"); 1241 if(!nextOffset) 1242 nextOffset = null; 1243 1244 var numItems = objFilter.data("numitems"); 1245 1246 if(!numItems) 1247 numItems = null; 1248 1249 //affect only single grids 1250 1251 var isSingleGridOnly = objFilter.data("affect_single_grid"); 1252 1253 1254 var data = {}; 1255 data.offset = nextOffset; 1256 data.numItems = numItems; 1257 data.singlegrid = isSingleGridOnly; 1258 1259 return(data); 1260 } 1261 1262 1263 /** 1264 * do the load more operation 1265 */ 1266 function onLoadMoreClick(){ 1267 1268 var objLink = jQuery(this); 1269 1270 var objLoadMore = objLink.parents(".uc-filter-load-more"); 1271 1272 var objData = objLoadMore.find(".uc-filter-load-more__data"); 1273 1274 var isMore = objData.data("more"); 1275 1276 if(isMore == false) 1277 return(false); 1278 1279 var objGrid = objLoadMore.data("grid"); 1280 1281 if(!objGrid || objGrid.length == 0) 1282 throw new Error("Grid not found!"); 1283 1284 //run the ajax, prevent default 1285 1286 objLoadMore.addClass(g_vars.CLASS_CLICKED); 1287 1288 refreshAjaxGrid(objGrid, g_vars.REFRESH_MODE_LOADMORE); 1289 1290 } 1291 1292 function ________SELECT_______________(){} 1293 1294 /** 1295 * init select filter, select the selected item (avoid cache) 1296 */ 1297 function initSelectFilter(objFilter){ 1298 1299 var objSelected = objFilter.find(".uc-selected"); 1300 1301 if(objSelected.length == 0) 1302 return(false); 1303 1304 var value = objSelected.attr("value"); 1305 1306 var objSelect = objFilter.find("select"); 1307 1308 objSelect.val(value); 1309 1310 } 1311 1312 1313 function ________TERMS_LIST_______________(){} 1314 1315 /** 1316 * unselect by key terms list and select 1317 */ 1318 function termsFilterUnselectByKey(event,key){ 1319 1320 var objFilter = jQuery(this); 1321 1322 var selectedTerm = getTermsListSelectedTerm(objFilter); 1323 1324 if(!selectedTerm) 1325 return(false); 1326 1327 var selectedKey = getVal(selectedTerm,"key"); 1328 1329 if(selectedKey != key) 1330 return(false); 1331 1332 //if key match - clear filter and set no refresh. 1333 1334 clearFilter(objFilter); 1335 1336 setNoRefreshFilter(objFilter); 1337 } 1338 1339 1340 /** 1341 * on terms list click 1342 */ 1343 function onTermsLinkClick(event){ 1344 1345 var className = "uc-selected"; 1346 1347 event.preventDefault(); 1348 1349 var objLink = jQuery(this); 1350 1351 if(objLink.hasClass("uc-grid-filter")){ 1352 1353 var objTermsFilter = objLink; 1354 1355 }else{ 1356 1357 var objTermsFilter = objLink.parents(".uc-grid-filter"); 1358 } 1359 1360 var filterType = getFilterType(objTermsFilter); 1361 1362 if(filterType == g_types.SELECT){ 1363 1364 var objLink = objTermsFilter.find("option:selected"); 1365 } 1366 1367 if(filterType == g_types.TERMS_LIST){ 1368 1369 var objActiveLinks = objLink.siblings("."+className).not(objLink); 1370 1371 objActiveLinks.removeClass(className); 1372 objLink.addClass(className); 1373 1374 } 1375 1376 var objGrid = objTermsFilter.data("grid"); 1377 1378 if(!objGrid || objGrid.length == 0) 1379 throw new Error("Grid not found"); 1380 1381 //if main filter - clear other filters 1382 1383 var filterRole = objTermsFilter.data("role"); 1384 1385 var termID = objLink.data("id"); 1386 1387 //set refresh - if all and there are hidden items - refresh 1388 var isRefresh = false; 1389 1390 if(!termID){ 1391 var objHiddenItems = objTermsFilter.find(".uc-item-hidden"); 1392 if(objHiddenItems.length) 1393 isRefresh = true; 1394 } 1395 1396 var isHideChildren = false;
1397 if(!termID) 1398 isHideChildren = true; 1399 1400 //set not refresh next iteration, because of the clicked 1401 if(isRefresh == false) 1402 setNoRefreshFilter(objTermsFilter); 1403 1404 if(filterRole == "main") 1405 clearChildFilters(objGrid, objTermsFilter, isHideChildren, termID); 1406 1407 //skip action 1408 1409 var isSkipAction = checkTriggerSkipAction(objTermsFilter, objGrid); 1410 1411 if(isSkipAction == true) 1412 return(false); 1413 1414 1415 if(g_showDebug == true){ 1416 trace("refresh grid - on term click"); 1417 } 1418 1419 //refresh grid 1420 refreshAjaxGrid(objGrid); 1421 1422 } 1423 1424 1425 /** 1426 * get terms list term id 1427 */ 1428 function getTermsListSelectedTerm(objFilter){ 1429 1430 if(!objFilter) 1431 return(null); 1432 1433 var filterType = getFilterType(objFilter); 1434 1435 var objSelected = objFilter.find(".uc-selected"); 1436 1437 if(filterType == g_types.SELECT){ 1438 1439 var objSelected = objFilter.find("option:selected"); 1440 1441 }else{ 1442 1443 var objSelected = objFilter.find(".uc-selected"); 1444 } 1445 1446 if(objSelected.length == 0){ 1447 1448 if(g_showDebug == true){ 1449 trace("no selected found, skipping..."); 1450 } 1451 1452 return(null); 1453 } 1454 1455 //check for hidden 1456 1457 if(filterType == g_types.TERMS_LIST && objSelected.hasClass("uc-item-hidden") == true){ 1458 1459 if(g_showDebug == true){ 1460 1461 trace("the selected object"); 1462 trace(objSelected); 1463 trace("the term is hidden, skipping..."); 1464 1465 } 1466 1467 return(null); 1468 } 1469 1470 if(objSelected.length > 1) 1471 objSelected = jQuery(objSelected[0]); 1472 1473 var objTerm = getFilterElementData(objSelected); 1474 1475 return(objTerm); 1476 } 1477 1478 /** 1479 * select items in terms list by terms 1480 */ 1481 function termListSelectItems(objFilter, arrTerms){ 1482 1483 //deselect 1484 var objSelected = objFilter.find(".uc-selected"); 1485 1486 objSelected.removeClass("uc-selected"); 1487 1488 //select by term 1489 1490 jQuery.each(arrTerms, function(index, term){ 1491 1492 var termID = getVal(term,"id"); 1493 var objItem = objFilter.find("a.ue_taxonomy_item[data-id='"+termID+"']"); 1494 1495 if(objItem.length == 0) 1496 return(true); 1497 1498 objItem.addClass("uc-selected"); 1499 }); 1500 1501 1502 } 1503 1504 function ________GENERAL_FILTER_______________(){} 1505 1506 /** 1507 * init general filter 1508 */ 1509 function initGeneralFilter(objFilter){ 1510 1511 objFilter.on(g_vars.ACTION_FILTER_CHANGE, onGeneralFilterChange); 1512 1513 } 1514 1515 1516 1517 /** 1518 * on general filter change 1519 */ 1520 function onGeneralFilterChange(event, params){ 1521 1522 event.stopPropagation(); 1523 1524 var isRefresh = getVal(params, "refresh"); 1525 1526 var objFilter = jQuery(this); 1527 1528 var filterType = objFilter.data("filtertype"); 1529 1530 if(filterType != "general"){ 1531 1532 trace(objFilter); 1533 1534 throw new Error("Not a general filter on action: " + g_vars.ACTION_FILTER_CHANGE); 1535 return(false); 1536 } 1537 1538 if(isRefresh !== true) 1539 setNoRefreshFilter(objFilter); 1540 1541 var objGrid = objFilter.data("grid"); 1542 1543 if(!objGrid || objGrid.length == 0){ 1544 1545 trace(objGrid); 1546 1547 throw new Error("Wrong filter change"); 1548 return(false); 1549 } 1550 1551 var filterRole = objFilter.data("role"); 1552 1553 if(filterRole == "main"){ 1554 1555 var isHideChildren = false; 1556 1557 //if no items selected - hide all children 1558 var objData = getGeneralFilterData(objFilter); 1559 if(!objData) 1560 isHideChildren = true; 1561 1562 clearChildFilters(objGrid, objFilter, isHideChildren); 1563 } 1564 1565 //check for skip action 1566 1567 var isSkipAction = checkTriggerSkipAction(objFilter, objGrid); 1568 1569 if(isSkipAction == true) 1570 return(false); 1571 1572 1573 if(g_showDebug == true){ 1574 1575 trace("refresh grid - on general filter change"); 1576 trace(objFilter); 1577 1578 } 1579 1580 refreshAjaxGrid(objGrid); 1581 1582 return(false); 1583 } 1584 1585 1586 /** 1587 * select filter items by terms, without refresh, just set selected 1588 */ 1589 function selectFilterItemsByTerms(objFilters, arrTerms){ 1590 1591 if(!objFilters || objFilters.length == 0) 1592 return(false); 1593 1594 if(!arrTerms || arrTerms.length == 0) 1595 return(false); 1596 1597 jQuery.each(objFilters,function(index, filter){ 1598 1599 var objFilter = jQuery(filter); 1600 1601 selectFilterItems(objFilter, arrTerms); 1602 1603 }); 1604 1605 } 1606 1607 /** 1608 * select filter items 1609 */ 1610 function selectFilterItems(objFilter, arrTerms){ 1611 1612 var type = getFilterType(objFilter); 1613 1614 switch(type){ 1615 //case g_types.SELECT: 1616 case g_types.TERMS_LIST: 1617 1618 termListSelectItems(objFilter, arrTerms); 1619 1620 break; 1621 case g_types.GENERAL: 1622 1623 objFilter.trigger("uc_select_items", arrTerms); 1624 1625 break; 1626 } 1627 1628 } 1629
1630 /** 1631 * get filter data 1632 */ 1633 function getGeneralFilterData(objFilter){ 1634 1635 var filterDataObj = {}; 1636 objFilter.trigger(g_vars.EVENT_GET_FILTER_DATA, filterDataObj); 1637 1638 var filterData = getVal(filterDataObj, "output"); 1639 1640 return(filterData); 1641 } 1642 1643 1644 function ________INIT_FILTERS_______________(){} 1645 1646 /** 1647 * init terms related filer (terms list and select) 1648 */ 1649 function initTermsRelatedFilter(objFilter){ 1650 1651 objFilter.on(g_vars.ACTION_FILTER_UNSELECT_BY_KEY, termsFilterUnselectByKey); 1652 1653 } 1654 1655 1656 /** 1657 * get filter taxonomy id's 1658 */ 1659 function getFilterTaxIDs(objFilter, objIDs){ 1660 1661 var type = getFilterType(objFilter); 1662 1663 //skip the if 1664 if(type == g_types.SELECT) 1665 var objItems = objFilter.find(".uc-select-filter__option"); 1666 else 1667 var objItems = objFilter.find(".ue_taxonomy_item"); 1668 1669 if(objItems.length == 0) 1670 return(objIDs); 1671 1672 jQuery.each(objItems, function(index, item){ 1673 1674 var objItem = jQuery(item); 1675 var taxID = objItem.data("id"); 1676 1677 if(!taxID) 1678 return(true); 1679 1680 objIDs[taxID] = true; 1681 }); 1682 1683 1684 return(objIDs); 1685 } 1686 1687 /** 1688 * get tax id's list string from assoc object 1689 */ 1690 function getTermDsList(objIDs){ 1691 1692 var strIDs = ""; 1693 for(var id in objIDs){ 1694 1695 if(jQuery.isNumeric(id) == false) 1696 continue; 1697 1698 if(strIDs) 1699 strIDs += ","; 1700 1701 strIDs += id; 1702 } 1703 1704 return(strIDs); 1705 } 1706 1707 1708 function ________DATA_______________(){} 1709 1710 1711 /** 1712 * map meta compare operator to URL word, empty for equals 1713 */ 1714 function getMetaCompareUrlWord(compare){ 1715 1716 if(!compare || compare === "=" || compare === "equals") 1717 return(""); 1718 1719 var map = { 1720 "!=": "notequals", 1721 ">": "greater", 1722 "<": "less", 1723 ">=": "greaterequal", 1724 "<=": "lessequal", 1725 "LIKE": "like", 1726 "NOT LIKE": "notlike", 1727 "IN": "in", 1728 "NOT IN": "notin", 1729 "BETWEEN": "between", 1730 "NOT BETWEEN": "notbetween", 1731 "EXISTS": "exists", 1732 "NOT EXISTS": "notexists" 1733 }; 1734 1735 if(map[compare]) 1736 return(map[compare]); 1737 1738 var lower = ("" + compare).toLowerCase(); 1739 1740 for(var op in map){ 1741 if(map[op] === lower) 1742 return(map[op]); 1743 } 1744 1745 return(""); 1746 } 1747 1748 1749 /** 1750 * selected meta pair for init mode: key:value[:compare] 1751 */ 1752 function getMetaSelectedPair(objMeta){ 1753 1754 var metaKey = getVal(objMeta, "meta_key"); 1755 1756 if(!metaKey) 1757 metaKey = getVal(objMeta, "slug"); 1758 1759 if(!metaKey) 1760 return(""); 1761 1762 var metaValue = getVal(objMeta, "meta_value"); 1763 1764 if(!metaValue) 1765 metaValue = ""; 1766 1767 var metaPair = metaKey + g_options.urlkey_taxsap + metaValue; 1768 var compareWord = getMetaCompareUrlWord(getVal(objMeta, "compare")); 1769 1770 if(compareWord) 1771 metaPair += g_options.urlkey_taxsap + compareWord; 1772 1773 return(metaPair); 1774 } 1775 1776 1777 /** 1778 * grouping key for meta items: key, or key + compare word 1779 */ 1780 function getMetaGroupedQueryKey(objItem, keyName, extraName){ 1781 1782 var key = objItem[keyName]; 1783 1784 if(!key || !extraName) 1785 return(key); 1786 1787 var word = getMetaCompareUrlWord(objItem[extraName]); 1788 1789 if(!word) 1790 return(key); 1791 1792 return(key + "\x1e" + word); 1793 } 1794 1795 1796 /** 1797 * handle item, add to key->values map 1798 * keyName/valueName: "taxonomy"/"slug" for terms, "meta_key"/"meta_value" for meta 1799 * extraName: optional, groups meta by compare as well 1800 */ 1801 function buildGroupedValuesQuery_handleItem(objItem, arrGrouped, keyName, valueName, extraName){ 1802 1803 var key = getMetaGroupedQueryKey(objItem, keyName, extraName); 1804 var value = objItem[valueName]; 1805 1806 if(!key) 1807 return(arrGrouped); 1808 1809 if(value === null || typeof value === "undefined") 1810 value = ""; 1811 1812 var objValues = getVal(arrGrouped, key); 1813 if(!objValues) 1814 objValues = {}; 1815 1816 objValues[value] = true; 1817 arrGrouped[key] = objValues; 1818 1819 return(arrGrouped); 1820 } 1821 1822 /** 1823 * get values string (dot separated) 1824 * adds .* for AND relation when multiple values 1825 */ 1826 function buildGroupedValuesQuery_getStrValues(objValues, isGroup){ 1827 1828 var isDebug = false; 1829 1830 if(isDebug == true){ 1831 trace("get str values"); 1832 trace(objValues); 1833 trace("is group:" + isGroup); 1834 } 1835 1836 var strValues = ""; 1837 1838 var moreThenOne = false;
1839 var isEndSlugFound = false; 1840 var isOrSlugFound = false; 1841 1842 for (var value in objValues){ 1843 1844 if(value === "__ucand__"){ 1845 isEndSlugFound = true; 1846 continue 1847 } 1848 1849 if(value === "__ucor__"){ 1850 isOrSlugFound = true; 1851 continue 1852 } 1853 1854 if(strValues){ 1855 moreThenOne = true; 1856 strValues += "."; 1857 } 1858 1859 strValues += value; 1860 } 1861 1862 if(isDebug == true){ 1863 trace("more then one: "+moreThenOne); 1864 trace("is end found: "+isEndSlugFound); 1865 } 1866 1867 var addAnd = (moreThenOne == true && isGroup !== true || isEndSlugFound); 1868 1869 if(isOrSlugFound === true) 1870 addAnd = false; 1871 1872 if(addAnd) 1873 strValues += ".*"; 1874 1875 if(isDebug) 1876 trace("str values: "+strValues); 1877 1878 return(strValues); 1879 } 1880 1881 1882 /** 1883 * build grouped values query string 1884 * format: key:value1.value2.*;key2:value3 1885 * used for ucterms (taxonomy:slugs) and ucmeta (meta_key:values[:compare]) 1886 */ 1887 function buildGroupedValuesQuery(arrItems, keyName, valueName, extraName){ 1888 1889 var isDebug = false; 1890 1891 if(!keyName) 1892 keyName = "taxonomy"; 1893 1894 if(!valueName) 1895 valueName = "slug"; 1896 1897 var query = ""; 1898 1899 var arrGrouped = {}; 1900 var arrGroupItems = []; 1901 1902 if(isDebug == true){ 1903 trace("arr items"); 1904 trace(arrItems); 1905 } 1906 1907 jQuery.each(arrItems, function(index, objItem){ 1908 1909 //group 1910 if(jQuery.isArray(objItem) && objItem.length != 0){ 1911 1912 if(objItem.length == 1){ 1913 arrGrouped = buildGroupedValuesQuery_handleItem(objItem[0], arrGrouped, keyName, valueName, extraName); 1914 return; 1915 } 1916 1917 var arrGroupMap = {}; 1918 1919 jQuery.each(objItem, function(index, groupItem){ 1920 1921 arrGroupMap = buildGroupedValuesQuery_handleItem(groupItem, arrGroupMap, keyName, valueName, extraName); 1922 }); 1923 1924 arrGroupItems.push(arrGroupMap); 1925 1926 }else{ //single 1927 1928 arrGrouped = buildGroupedValuesQuery_handleItem(objItem, arrGrouped, keyName, valueName, extraName); 1929 } 1930 1931 }); 1932 1933 if(isDebug == true){ 1934 trace("first arr grouped"); 1935 trace(arrGrouped); 1936 } 1937 1938 if(jQuery.isEmptyObject(arrGrouped) && jQuery.isEmptyObject(arrGroupItems)) 1939 return(null); 1940 1941 if(isDebug == true){ 1942 trace("group items"); 1943 trace(arrGroupItems); 1944 } 1945 1946 var isMultipleGroups = (arrGroupItems.length > 1); 1947 1948 jQuery.each(arrGroupItems, function(index, objGroupKeys){ 1949 1950 jQuery.each(objGroupKeys, function(key, objValues){ 1951 1952 var strValues = buildGroupedValuesQuery_getStrValues(objValues, true); 1953 1954 var strAdd = strValues; 1955 if(isMultipleGroups === true && strValues.indexOf(".") !== -1){ 1956 strAdd = "|"+strValues+"|"; //OR inside the group - only when multiple groups 1957 } 1958 1959 var objKeyValues = getVal(arrGrouped, key); 1960 if(!objKeyValues) 1961 objKeyValues = {}; 1962 1963 objKeyValues[strAdd] = true; 1964 1965 arrGrouped[key] = objKeyValues; 1966 }); 1967 1968 }); 1969 1970 1971 if(isDebug == true){ 1972 trace("The result after grouping"); 1973 trace(arrGrouped); 1974 } 1975 1976 jQuery.each(arrGrouped, function(groupKey, objValues){ 1977 1978 var strValues = buildGroupedValuesQuery_getStrValues(objValues); 1979 1980 var key = groupKey; 1981 var compareWord = ""; 1982 var sepIndex = groupKey.indexOf("\x1e"); 1983 1984 if(sepIndex !== -1){ 1985 key = groupKey.substring(0, sepIndex); 1986 compareWord = groupKey.substring(sepIndex + 1); 1987 } 1988 1989 var strPart = key + g_options.urlkey_taxsap + strValues; 1990 1991 if(compareWord) 1992 strPart += g_options.urlkey_taxsap + compareWord; 1993 1994 if(query) 1995 query += ";"; 1996 1997 query += strPart; 1998 1999 }); 2000 2001 if(isDebug == true){ 2002 trace("query"); 2003 trace(query); 2004 } 2005 2006 return(query); 2007 } 2008 2009 /** 2010 * build terms query 2011 * ucterms=category:blog.cocktails.design.* 2012 */ 2013 function buildTermsQuery(arrTerms){ 2014 2015 return buildGroupedValuesQuery(arrTerms, "taxonomy", "slug"); 2016 } 2017 2018 /** 2019 * build meta query - same format as terms, optional compare word 2020 * ucmeta=meta_key:value1.value2;meta_key:value:notequals 2021 */ 2022 function buildMetaQuery(arrMeta){ 2023 2024 //normalize: ensure meta_key exists (fallback from slug) 2025 var arrNormalized = []; 2026 2027 jQuery.each(arrMeta, function(index, item){ 2028 2029 if(jQuery.isArray(item)){ 2030 2031 var arrGroup = []; 2032 2033 jQuery.each(item, function(groupIndex, groupItem){ 2034 2035 if(!groupItem) 2036 return(true); 2037 2038 if(!groupItem.meta_key && groupItem.slug) 2039 groupItem.meta_key = groupItem.slug; 2040 2041 if(typeof groupItem.meta_value === "undefined" || groupItem.meta_value === null) 2042 groupItem.meta_value = ""; 2043 2044 if(!groupItem.compare) 2045 groupItem.compare = "="; 2046 2047 arrGroup.push(groupItem); 2048 }); 2049 2050 arrNormalized.push(arrGroup); 2051 2052 }else{ 2053 2054 if(!item) 2055 return(true); 2056 2057 if(!item.meta_key && item.slug) 2058 item.meta_key = item.slug; 2059 2060 if(typeof item.meta_value === "undefined" || item.meta_value === null) 2061 item.meta_value = ""; 2062 2063 if(!item.compare) 2064 item.compare = "="; 2065 2066 arrNormalized.push(item); 2067 } 2068 2069 }); 2070 2071 return buildGroupedValuesQuery(arrNormalized, "meta_key", "meta_value", "compare"); 2072 } 2073 2074 /** 2075 * get selected filter element data 2076 */ 2077 function getFilterElementData(objElement){ 2078 2079 var id = objElement.data("id"); 2080 var title = objElement.data("title"); 2081 var key = objElement.data("key"); 2082 var type = objElement.data("type"); 2083
2084 if(!id && !key) 2085 return(null); 2086 2087 2088 switch(type){ 2089 case "taxonomy": 2090 default: 2091 var slug = objElement.data("slug"); 2092 var taxonomy = objElement.data("taxonomy"); 2093 2094 var objTerm = { 2095 "type": type, 2096 "id": id, 2097 "slug": slug, 2098 "taxonomy": taxonomy, 2099 "title": title, 2100 "key": key 2101 }; 2102 return(objTerm); 2103 2104 break; 2105 case "author": 2106 2107 var username = objElement.data("username"); 2108 2109 var objAuthor = { 2110 "type": type, 2111 "id": id, 2112 "username": username, 2113 "title": title, 2114 "key": key 2115 }; 2116 return(objAuthor); 2117 2118 break; 2119 case "meta": 2120 2121 var slug = objElement.data("slug"); 2122 var metaKey = objElement.data("metakey"); 2123 var metaValue = objElement.data("metavalue"); 2124 var compare = objElement.data("compare"); 2125 2126 if(!metaKey) 2127 metaKey = slug; 2128 2129 if(!metaValue) 2130 metaValue = ""; 2131 2132 if(!compare) 2133 compare = "="; 2134 2135 var objMeta = { 2136 "type": type, 2137 "id": id, 2138 "slug": slug, 2139 "meta_key": metaKey, 2140 "meta_value": metaValue, 2141 "compare": compare, 2142 "title": title, 2143 "key": key 2144 }; 2145 return(objMeta); 2146 2147 break; 2148 } 2149 2150 } 2151 2152 2153 function ________AJAX_CACHE_________(){} 2154 2155 /** 2156 * get ajax url 2157 */ 2158 function getAjaxCacheKeyFromUrl(ajaxUrl){ 2159 2160 var key = ajaxUrl; 2161 2162 key = key.replace(g_urlAjax, ""); 2163 key = key.replace(g_urlBase, ""); 2164 2165 //replace special signs 2166 key = replaceAll(key, "/",""); 2167 key = replaceAll(key, "?","_"); 2168 key = replaceAll(key, "&","_"); 2169 key = replaceAll(key, "=","_"); 2170 2171 return(key); 2172 } 2173 2174 /** 2175 * get ajax cache key 2176 */ 2177 function getAjaxCacheKey(ajaxUrl, action, objData){ 2178 2179 if(g_options.is_cache_enabled == false) 2180 return(false); 2181 2182 //cache only by url meanwhile 2183 2184 if(jQuery.isEmptyObject(objData) == false) 2185 return(false); 2186 2187 if(action) 2188 return(false); 2189 2190 var cacheKey = getAjaxCacheKeyFromUrl(ajaxUrl); 2191 2192 if(!cacheKey) 2193 return(false); 2194 2195 return(cacheKey); 2196 } 2197 2198 2199 /** 2200 * cache ajax response 2201 */ 2202 function cacheAjaxResponse(ajaxUrl, action, objData, response){ 2203 2204 var cacheKey = getAjaxCacheKey(ajaxUrl, action, objData); 2205 2206 if(!cacheKey) 2207 return(false); 2208 2209 //some precoutions for overload 2210 if(g_cache.length > 100) 2211 return(false); 2212 2213 g_cache[cacheKey] = response; 2214 2215 } 2216 2217 2218 function ________AJAX_RESPONSE_______________(){} 2219 2220 /** 2221 * replace the grid debug 2222 */ 2223 function operateAjax_setHtmlDebug(response, objGrid){ 2224 2225 //replace the debug 2226 var htmlDebug = getVal(response, "html_debug"); 2227 2228 if(!htmlDebug) 2229 return(false); 2230 2231 var gridParent = objGrid.parents("." + g_vars.class_widget_wrapper); 2232 2233 var objDebug = gridParent.find(".uc-debug-query-wrapper"); 2234 2235 if(objDebug.length == 0) 2236 return(false); 2237 2238 objDebug.replaceWith(htmlDebug); 2239 } 2240 2241 2242 /** 2243 * set html grid from ajax response 2244 */ 2245 function operateAjax_setHtmlGrid(response, objGrid, isLoadMore){ 2246 2247 if(g_showDebug == true){ 2248 trace("set html grid, response: "); 2249 trace(response); 2250 2251 trace("obj grid:"); 2252 trace(objGrid); 2253 } 2254 2255 if(objGrid.length == 0) 2256 return(false); 2257 2258 //skip set html if exists 2259 if(objGrid.data(g_vars.GRID_DATA_SKIP_HTML) === true){ 2260 2261 if(g_showDebug == true) 2262 trace("skip set html"); 2263 2264 objGrid.data(g_vars.GRID_DATA_SKIP_HTML,false); 2265 return(false); 2266 } 2267 2268 var objItemsWrapper = getGridItemsWrapper(objGrid); 2269 var objItemsWrapper2 = getGridItemsWrapper(objGrid, true); 2270 2271 if(g_showDebug == true){ 2272 trace("items wrapper 1: "); 2273 trace(objItemsWrapper); 2274 2275 trace("items wrapper 2:"); 2276 trace(objItemsWrapper2); 2277 } 2278 2279 2280 if(!objItemsWrapper || objItemsWrapper.length == 0) 2281 throw new Error("Missing items wrapper: .uc-items-wrapper"); 2282 2283 operateAjax_setHtmlDebug(response, objGrid); 2284 2285 //set grid items 2286 2287 //if init filters mode, and no items response - don't set 2288 if(response.hasOwnProperty("html_items") == false) 2289 return(false); 2290 2291 var htmlItems = getVal(response, "html_items"); 2292 2293 var htmlItems2 = null; 2294 2295 if(objItemsWrapper2) 2296 htmlItems2 = getVal(response, "html_items2"); 2297 2298 //replace widget id 2299 var gridID = objGrid.attr("id"); 2300 2301 htmlItems = replaceAll(htmlItems, "%uc_widget_id%", gridID); 2302 2303 if(htmlItems2) 2304 htmlItems2 = replaceAll(htmlItems2, "%uc_widget_id%", gridID); 2305 2306 var isCustomRefresh = objGrid.data("custom-sethtml"); 2307 2308 //show / hide empty message if available and empty response 2309 var objEmptyMessage = getGridEmptyMessage(objGrid); 2310 2311 if(objEmptyMessage){ 2312 if(htmlItems == "") 2313 objEmptyMessage.show(); 2314 else 2315 objEmptyMessage.hide(); 2316 } 2317 2318 //set the query data
2319 var queryDataOriginal = getVal(response, "query_data"); 2320 var queryIDs = getVal(response,"query_ids"); 2321 2322 var queryData = jQuery.extend({}, queryDataOriginal); 2323 2324 //add to old data 2325 2326 if(isLoadMore == true){ 2327 2328 var currentQueryData = objGrid.attr("querydata"); 2329 2330 var objCurrentData = jQuery.parseJSON(currentQueryData); 2331 var currentNumPosts = getVal(objCurrentData, "count_posts"); 2332 2333 queryData.count_posts += currentNumPosts; 2334 2335 var currentQueryIDs = objGrid.data("postids"); 2336 2337 if(queryIDs && currentQueryIDs) 2338 queryIDs = currentQueryIDs + "," + queryIDs; 2339 } 2340 2341 //query data replace 2342 2343 if(queryData){ 2344 2345 objGrid.removeAttr("querydata"); 2346 2347 var jsonData = JSON.stringify(queryData); 2348 objGrid.attr("querydata", jsonData); 2349 2350 objGrid.data("querydata", queryData); 2351 } 2352 2353 //post id's replace 2354 2355 objGrid.removeAttr("data-postids"); 2356 objGrid.attr("data-postids", queryIDs); 2357 objGrid.data("postids", queryIDs); 2358 2359 2360 //if custom refresh - just save the new html in data 2361 if(isCustomRefresh == true){ 2362 2363 objGrid.trigger(g_vars.EVENT_SET_HTML_ITEMS,[htmlItems, isLoadMore, htmlItems2]); 2364 return(false); 2365 } 2366 2367 2368 if(!htmlItems2) 2369 htmlItems2 = ""; 2370 2371 if(isLoadMore === true){ 2372 2373 if(g_showDebug == true){ 2374 trace("append load more"); 2375 } 2376 2377 objItemsWrapper.append(htmlItems); 2378 2379 if(objItemsWrapper) 2380 objItemsWrapper.append(htmlItems2); 2381 2382 }else{ 2383 2384 objItemsWrapper.html(htmlItems); 2385 2386 if(objItemsWrapper2 && objItemsWrapper2.length) 2387 objItemsWrapper2.html(htmlItems2); 2388 2389 } 2390 2391 2392 return(true); 2393 } 2394 2395 2396 /** 2397 * refresh synced grids 2398 */ 2399 function operateAjax_setHtmlSyngGrids(response, objGrid, isLoadMore){ 2400 2401 var objSyncWidgetsResponse = getVal(response, "html_sync_widgets"); 2402 2403 if(g_showDebug == true){ 2404 trace("set html sync grids"); 2405 trace(objSyncWidgetsResponse); 2406 } 2407 2408 var queryData = getVal(response,"query_data"); 2409 2410 if(!objSyncWidgetsResponse){ 2411 2412 if(g_showDebug == true){ 2413 trace("no sync widgets response"); 2414 } 2415 2416 return(false); 2417 } 2418 2419 var group = objGrid.data("filtergroup"); 2420 2421 jQuery.each(objSyncWidgetsResponse, function(elementID, childResponse){ 2422 2423 var objGridWidget = getGridFromElementorElementID(elementID, group); 2424 2425 if(!objGridWidget){ 2426 2427 if(g_showDebug == true){ 2428 trace("no grid widget found: "+elementID); 2429 2430 getGridFromElementorElementID(elementID,group,true); //for debug 2431 } 2432 2433 return(true); 2434 } 2435 2436 if(g_showDebug == true){ 2437 trace("set sync grid!"); 2438 trace(objGridWidget); 2439 trace(childResponse); 2440 } 2441 2442 2443 objGridWidget.removeClass(g_vars.CLASS_REFRESH_SOON); 2444 2445 childResponse.query_data = queryData; 2446 2447 operateAjax_setHtmlGrid(childResponse, objGridWidget, isLoadMore); 2448 2449 objGridWidget.trigger(g_vars.EVENT_AJAX_REFRESHED); 2450 g_objBody.trigger(g_vars.EVENT_AJAX_REFRESHED_BODY, [objGridWidget]); 2451 2452 }); 2453 2454 } 2455 2456 2457 /** 2458 * replace filters html 2459 */ 2460 function operateAjax_setHtmlWidgets(response, objFilters){ 2461 2462 if(!objFilters) 2463 return(false); 2464 2465 if(objFilters.length == 0) 2466 return(false); 2467 2468 var objHtmlWidgets = getVal(response, "html_widgets"); 2469 2470 if(!objHtmlWidgets) 2471 return(false); 2472 2473 if(objHtmlWidgets.length == 0) 2474 return(false); 2475 2476 var objHtmlDebug = getVal(response, "html_widgets_debug"); 2477 2478 jQuery.each(objFilters, function(index, objFilter){ 2479 2480 var widgetID = getElementWidgetID(objFilter); 2481 2482 if(!widgetID) 2483 return(true); 2484 2485 var html = getVal(objHtmlWidgets, widgetID); 2486 2487 if(!html) 2488 return(true); 2489 2490 var objHtml = jQuery(html); 2491 2492 var htmlInner = objHtml.html(); 2493 2494 //set the class 2495 2496 var filterClassName = objHtml.attr("class"); 2497 2498 filterClassName += " "+g_vars.CLASS_FILTER_INITED; 2499 2500 objFilter.attr("class", filterClassName); 2501 2502 objFilter.removeClass(g_vars.CLASS_INITING); 2503 objFilter.removeClass(g_vars.CLASS_REFRESH_SOON); 2504 2505 objFilter.html(htmlInner); 2506 2507 2508 2509 //---- put the debug if exists 2510 2511 var htmlDebug = null; 2512 2513 if(objHtmlDebug) 2514 var htmlDebug = getVal(objHtmlDebug, widgetID); 2515 2516 if(htmlDebug){ 2517 var objParent = objFilter.parents("." + g_vars.class_widget_wrapper); 2518 var objDebug = objParent.find(".uc-div-ajax-debug"); 2519 2520 if(objDebug.length) 2521 objDebug.replaceWith(htmlDebug); 2522 } 2523 2524 objFilter.trigger(g_vars.EVENT_FILTER_RELOADED); 2525 2526 }); 2527 2528 } 2529
2530 /** 2531 * scroll to grid top 2532 */ 2533 function scrollToGridTop(objGrid){ 2534 2535 var gapTop = 150; 2536 2537 var gridOffset = objGrid.offset().top; 2538 2539 var gridTop = gridOffset - gapTop; 2540 2541 if(gridTop < 0) 2542 gridTop = 0; 2543 2544 //check if the grid top is visible 2545 2546 var currentPos = jQuery(window).scrollTop(); 2547 2548 if(currentPos <= gridOffset) 2549 return(false); 2550 2551 window.scrollTo({ top: gridTop, behavior: 'smooth' }); 2552 2553 } 2554 2555 2556 /** 2557 * operate the response 2558 */ 2559 function operateAjaxRefreshResponse(response, objGrid, objFilters, isLoadMore, isNoScroll){ 2560 2561 var isGridRefreshed = operateAjax_setHtmlGrid(response, objGrid, isLoadMore); 2562 2563 operateAjax_setHtmlWidgets(response, objFilters); 2564 2565 operateAjax_setHtmlSyngGrids(response, objGrid, isLoadMore); 2566 2567 objGrid.trigger(g_vars.EVENT_AJAX_REFRESHED,[{isLoadMore:isLoadMore}]); 2568 g_objBody.trigger(g_vars.EVENT_AJAX_REFRESHED_BODY, [objGrid]); 2569 2570 //trigger body as well 2571 2572 //scroll to grid top 2573 if(isLoadMore == false && isGridRefreshed == true && isNoScroll !== true){ 2574 2575 setTimeout(function(){ 2576 2577 scrollToGridTop(objGrid); 2578 2579 },200); 2580 2581 } 2582 2583 } 2584 2585 2586 /** 2587 * replace all occurances 2588 */ 2589 function replaceAll(text, from, to){ 2590 2591 return text.split(from).join(to); 2592 }; 2593 2594 2595 2596 2597 /** 2598 * get response from ajax cache 2599 */ 2600 function getResponseFromAjaxCache(ajaxUrl, action, objData){ 2601 2602 var cacheKey = getAjaxCacheKey(ajaxUrl, action, objData); 2603 2604 if(!cacheKey) 2605 return(false); 2606 2607 var response = getVal(g_cache, cacheKey); 2608 2609 return(response); 2610 } 2611 2612 2613 function ________AJAX_______________(){} 2614 2615 /** 2616 * set this filter not to refresh next time 2617 */ 2618 function setNoRefreshFilter(objFilter){ 2619 2620 objFilter.data("uc_norefresh",true); 2621 2622 } 2623 2624 /** 2625 * show ajax error, should be something visible 2626 */ 2627 function showAjaxError(message){ 2628 2629 alert(message); 2630 2631 } 2632 2633 /** 2634 * get the debug object 2635 */ 2636 function getDebugObject(){ 2637 2638 var objGrid = g_lastGridAjaxCall; 2639 2640 if(!objGrid) 2641 return(null); 2642 2643 var objDebug = objGrid.find("."+g_vars.CLASS_DIV_DEBUG); 2644 2645 if(objDebug.length) 2646 return(objDebug); 2647 2648 //insert if not exists 2649 2650 objGrid.after("<div class='"+g_vars.CLASS_DIV_DEBUG+"' style='padding:10px;display:none;background-color:#D8FCC6'></div>"); 2651 2652 var objDebug = jQuery("body").find("."+g_vars.CLASS_DIV_DEBUG); 2653 2654 return(objDebug); 2655 } 2656 2657 2658 /** 2659 * show ajax debug 2660 */ 2661 function showAjaxDebug(str){ 2662 2663 trace("Ajax Error! - Check the debug"); 2664 2665 str = jQuery.trim(str); 2666 2667 if(!str || str.length == 0) 2668 return(false); 2669 2670 var objStr = jQuery(str); 2671 2672 if(objStr.find("header").length || objStr.find("body").length){ 2673 str = "Wrong ajax response!"; 2674 } 2675 2676 var objDebug = getDebugObject(); 2677 2678 if(!objDebug || objDebug.length == 0){ 2679 2680 alert(str); 2681 2682 throw new Error("debug not found"); 2683 } 2684 2685 objDebug.show(); 2686 objDebug.html(str); 2687 2688 } 2689 2690 2691 /** 2692 * small ajax request 2693 */ 2694 function ajaxRequest(ajaxUrl, action, objData, onSuccess){ 2695 2696 if(g_debugInitMode === true){ 2697 2698 trace("debug init mode - skip request"); 2699 return(false); 2700 } 2701 2702 if(g_showDebug == true){ 2703 trace("ajax request"); 2704 trace(ajaxUrl); 2705 } 2706 2707 if(!objData) 2708 var objData = {}; 2709 2710 if(typeof objData != "object") 2711 throw new Error("wrong ajax param"); 2712 2713 //check response from cache 2714 var responseFromCache = getResponseFromAjaxCache(ajaxUrl, action, objData); 2715 2716 if(responseFromCache){ 2717 2718 //simulate ajax request 2719 setTimeout(function(){ 2720 onSuccess(responseFromCache); 2721 }, 300); 2722 2723 return(false); 2724 } 2725 2726 var ajaxData = {}; 2727 ajaxData["action"] = "unlimitedelements_ajax_action"; 2728 ajaxData["client_action"] = action; 2729 2730 var ajaxtype = "get"; 2731 2732 if(jQuery.isEmptyObject(objData) == false){ 2733 ajaxData["data"] = objData; 2734 ajaxtype = "post"; 2735 } 2736 2737 2738 var ajaxOptions = { 2739 type:ajaxtype, 2740 url:ajaxUrl, 2741 success:function(response){ 2742 2743 if(!response){ 2744 showAjaxError("Empty ajax response!"); 2745 return(false); 2746 } 2747 2748 if(typeof response != "object"){ 2749 2750 try{ 2751 2752 response = jQuery.parseJSON(response); 2753 2754 }catch(e){ 2755 2756 showAjaxDebug(response); 2757 2758 showAjaxError("Ajax Error!!! not ajax response"); 2759 return(false); 2760 } 2761 } 2762 2763 if(response == -1){ 2764 showAjaxError("ajax error!!!"); 2765 return(false); 2766 } 2767 2768 if(response == 0){ 2769 showAjaxError("ajax error, action: <b>"+action+"</b> not found"); 2770 return(false); 2771 } 2772 2773 if(response.success == undefined){ 2774 showAjaxError("The 'success' param is a must!"); 2775 return(false); 2776 } 2777 2778 2779 if(response.success == false){ 2780 showAjaxError(response.message); 2781 return(false); 2782 } 2783 2784 cacheAjaxResponse(ajaxUrl, action, objData, response); 2785 2786 if(typeof onSuccess == "function"){ 2787 2788 onSuccess(response); 2789 } 2790 2791 }, 2792 error:function(jqXHR, textStatus, errorThrown){ 2793 2794 switch(textStatus){ 2795 case "parsererror": 2796 case "error": 2797 2798 //showAjaxError("parse error"); 2799 2800 showAjaxDebug(jqXHR.responseText); 2801 2802 break; 2803 } 2804 } 2805 } 2806 2807 if(ajaxtype == "post"){ 2808 ajaxOptions.dataType = 'json'; 2809 ajaxOptions.data = ajaxData 2810 } 2811 2812 var handle = jQuery.ajax(ajaxOptions); 2813 2814 return(handle); 2815 } 2816 2817 2818 2819 /** 2820 * get grid items wrapper 2821 */ 2822 function getGridItemsWrapper(objGrid, isSecond){ 2823 2824 var classItems = "uc-items-wrapper"; 2825 2826 if(isSecond == true) 2827 classItems = "uc-items-wrapper2"; 2828 2829 if(objGrid.hasClass(classItems)) 2830 return(objGrid); 2831 2832 var objItemsWrapper = objGrid.find("."+classItems); 2833 2834 if(objItemsWrapper.length == 0 && isSecond == false) 2835 throw new Error("Missing items wrapper - with class: uc-items-wrapper"); 2836 2837 if(objItemsWrapper.length == 0) 2838 return(null); 2839 2840 return(objItemsWrapper); 2841 } 2842 2843 2844 /** 2845 * set ajax loader 2846 */ 2847 function showAjaxLoader(objElement){ 2848 2849 objElement.addClass("uc-ajax-loading"); 2850 } 2851 2852 /** 2853 * hide ajax loader 2854 */ 2855 function hideAjaxLoader(objElement){ 2856 2857 objElement.removeClass("uc-ajax-loading"); 2858 } 2859 2860 2861 /** 2862 * show multiple ajax loader 2863 */ 2864 function showMultipleAjaxLoaders(objElements, isShow){ 2865 2866 if(!objElements) 2867 return(false); 2868 2869 if(objElements.length == 0) 2870 return(false); 2871 2872 jQuery.each(objElements,function(index, objElement){ 2873 2874 objElement = jQuery(objElement); 2875 2876 if(isShow == true){ 2877 2878 showAjaxLoader(objElement); 2879 } 2880 else 2881 hideAjaxLoader(objElement); 2882 }); 2883 2884 } 2885 2886 2887 /** 2888 * refresh ajax grid 2889 */ 2890 function refreshAjaxGrid(objGrid, refreshType){ 2891 2892 var isLoadMore = (refreshType == g_vars.REFRESH_MODE_LOADMORE); //for the output 2893 var isFiltersInit = (refreshType == "filters" || refreshType == "filters_children"); 2894 2895 //for the options - not refresh other filters 2896 var isLoadMoreMode = (refreshType == g_vars.REFRESH_MODE_LOADMORE || refreshType == g_vars.REFRESH_MODE_PAGINATION); 2897 2898 //get all grid filters 2899 var objFilters = objGrid.data("filters"); 2900 2901 if(!objFilters) 2902 return(false); 2903 2904 if(objFilters.length == 0) 2905 return(false); 2906 2907 if(objGrid.hasClass(g_vars.CLASS_GRID_NOREFRESH)) 2908 return(false); 2909 2910 var params = {}; 2911 if(refreshType == "filters_children") 2912 params["filters_init_type"] = "children"; 2913 2914 params["refresh_type"] = refreshType; 2915 2916 var objAjaxOptions = getGridAjaxOptions(objFilters, objGrid, isFiltersInit, isLoadMoreMode, params); 2917 2918 if(!objAjaxOptions){ 2919 2920 trace("ajax options are null"); 2921 return(false); 2922 } 2923 2924 var ajaxUrl = objAjaxOptions["ajax_url"]; 2925 var urlReplace = objAjaxOptions["url_replace"]; 2926 var arrTerms = objAjaxOptions["terms"]; 2927 2928 if(g_vars.DEBUG_AJAX_OPTIONS == true){ 2929 2930 trace("DEBUG AJAX OPTIONS");
2931 trace(objAjaxOptions); 2932 return(false); 2933 } 2934 2935 //set the url params 2936 var behave = objGrid.data("filterbehave"); 2937 2938 var isSetUrl = (behave == "mixed" || behave == "mixed_back"); 2939 2940 if(isFiltersInit == false && isSetUrl === true){ 2941 2942 try{ 2943 2944 if(behave == "mixed_back"){ 2945 2946 //save state for back button 2947 2948 var gridID = objGrid.attr("id"); 2949 2950 //save initial state 2951 var isStateEmpty = jQuery.isEmptyObject(history.state); 2952 2953 var objState = {"ucaction":"change", "ajaxurl":ajaxUrl, "gridid":gridID, selected_terms:arrTerms}; 2954 2955 if(isStateEmpty){ 2956 2957 var ajaxUrlInitial = objGrid.data("initajaxurl"); 2958 2959 objState["ajaxurl"] = ajaxUrlInitial; 2960 2961 history.replaceState(objState, null, urlReplace); 2962 } 2963 2964 history.pushState(objState, null, urlReplace); //with back 2965 2966 } 2967 else 2968 history.replaceState({}, null, urlReplace); //without back 2969 2970 }catch(error){ 2971 trace("history push state error"); 2972 trace(error); 2973 } 2974 } 2975 2976 2977 initGrid_setActiveFiltersData(objGrid, objAjaxOptions); 2978 2979 doGridAjaxRequest(ajaxUrl, objGrid, objFilters, isLoadMore, isFiltersInit); 2980 2981 } 2982 2983 2984 /** 2985 * do the actual grid ajax request 2986 */ 2987 function doGridAjaxRequest(ajaxUrl, objGrid, objFilters, isLoadMore, isFiltersInit){ 2988 2989 var objEmptyMessage = getGridEmptyMessage(objGrid); 2990 2991 //set the loaders 2992 2993 if(isLoadMore !== true && isFiltersInit !== true){ 2994 2995 showAjaxLoader(objGrid); 2996 2997 if(objEmptyMessage) 2998 showAjaxLoader(objEmptyMessage); 2999 } 3000 3001 var objFiltersToReload = objFilters.filter(function(objFilter){ 3002 3003 return objFilter.hasClass(g_vars.CLASS_REFRESH_SOON); 3004 }); 3005 3006 showMultipleAjaxLoaders(objFiltersToReload, true); 3007 3008 if(g_lastSyncGrids && isLoadMore !== true){ 3009 3010 showMultipleAjaxLoaders(g_lastSyncGrids, true); 3011 } 3012 3013 //ajax reload 3014 g_lastGridAjaxCall = objGrid; 3015 3016 objGrid.trigger(g_vars.EVENT_BEFORE_REFRESH); 3017 3018 var lastAjaxHandle = objGrid.data("last_ajax_refresh_handle"); 3019 3020 if(lastAjaxHandle){ 3021 lastAjaxHandle.abort(); 3022 } 3023 3024 //--- debug before refresh 3025 3026 if(g_debugBeforeRefreshMode == true){ 3027 3028 alert("Debug before refresh - please turn if off"); 3029 return(false); 3030 } 3031 3032 var ajaxHandle = ajaxRequest(ajaxUrl,null,null, function(response){ 3033 3034 if(isLoadMore !== true){ 3035 hideAjaxLoader(objGrid); 3036 3037 if(objEmptyMessage) 3038 hideAjaxLoader(objEmptyMessage); 3039 } 3040 3041 showMultipleAjaxLoaders(objFilters, false); 3042 3043 if(g_lastSyncGrids) 3044 showMultipleAjaxLoaders(g_lastSyncGrids, false); 3045 3046 operateAjaxRefreshResponse(response, objGrid, objFilters, isLoadMore); 3047 3048 onAfterGridRefresh(objGrid); 3049 3050 }); 3051 3052 objGrid.data("last_ajax_refresh_handle", ajaxHandle); 3053 3054 } 3055 3056 /** 3057 * do some actions after grid refresh, if needed 3058 */ 3059 function onAfterGridRefresh(objGrid){ 3060 3061 //refresh child grids 3062 3063 var isInitRefesh = objGrid.data("init_refresh_child_filters"); 3064 3065 if(isInitRefesh === true){ 3066 3067 objGrid.removeData("init_refresh_child_filters"); 3068 3069 //refresh child filters if there are selected main after init 3070 3071 var objFilters = objGrid.data("filters"); 3072 3073 var arrSelectedMain = getSelectedFilters(objFilters, "main"); 3074 3075 if(arrSelectedMain.length) 3076 refreshAjaxGrid(objGrid, "filters_children"); 3077 } 3078 3079 } 3080 3081 3082 function ________STATE_RELATED_______________(){} 3083 3084 3085 /** 3086 * do history 3087 */ 3088 function changeToHistoryState(state){ 3089 3090 if(g_showDebug == true){ 3091 trace("change to history"); 3092 trace(state); 3093 } 3094 3095 var ajaxUrl = getVal(state, "ajaxurl"); 3096 3097 var gridID = getVal(state, "gridid"); 3098 3099 var arrTerms = getVal(state, "selected_terms"); 3100 3101 if(!gridID) 3102 return(false); 3103 3104 if(!ajaxUrl) 3105 return(false); 3106 3107 var objGrid = jQuery("#"+gridID); 3108 3109 var objFilters = objGrid.data("filters"); 3110 3111 if(!objFilters) 3112 return(false); 3113 3114 //select by terms 3115 3116 selectFilterItemsByTerms(objFilters, arrTerms); 3117 3118 var responseFromCache = getResponseFromAjaxCache(ajaxUrl); 3119 3120 if(!responseFromCache){ 3121 3122 //do ajax request 3123 3124 doGridAjaxRequest(ajaxUrl, objGrid, objFilters); 3125 3126 return(false); 3127 } 3128 3129 //get data from cache 3130 3131 //trace("restore"); 3132 //trace(responseFromCache); 3133 3134 operateAjaxRefreshResponse(responseFromCache, objGrid, objFilters, false, true); 3135 3136 } 3137
3138 /** 3139 * on pop state, if it's a grid state, set the grid 3140 */ 3141 function onPopState(){ 3142 3143 if(!history.state) 3144 return(true); 3145 3146 var action = getVal(history.state, "ucaction"); 3147 3148 if(!action) 3149 return(true); 3150 3151 switch(action){ 3152 case "change": 3153 3154 changeToHistoryState(history.state); 3155 3156 break; 3157 default: 3158 throw new Error("Wrong history action: " + action); 3159 break; 3160 } 3161 3162 } 3163 3164 3165 function ________RUN_______________(){} 3166 3167 3168 /** 3169 * get url filters string 3170 */ 3171 function getGridUrlFiltersString(objGrid){ 3172 3173 var objAjaxOptions = getGridAjaxOptions_simple(objGrid); 3174 3175 if(!objAjaxOptions) 3176 return(""); 3177 3178 var strFilters = getVal(objAjaxOptions, "filters_string"); 3179 3180 return(strFilters); 3181 } 3182 3183 3184 /** 3185 * get simply the grid ajax options 3186 */ 3187 function getGridAjaxOptions_simple(objGrid){ 3188 3189 var objFilters = objGrid.data("filters"); 3190 3191 if(!objFilters) 3192 return(null); 3193 3194 var objAjaxOptions = getGridAjaxOptions(objFilters, objGrid, false,false,{getonly:true}); 3195 3196 if(!objAjaxOptions) 3197 return(null); 3198 3199 return(objAjaxOptions); 3200 } 3201 3202 /** 3203 * check that element is hidden only by display:none. ":hidden" checks width and height as well 3204 */ 3205 function isElementHiddenByDisplayNone(objElement) { 3206 3207 var element = objElement[0]; 3208 3209 var hidden = window.getComputedStyle(element).display == "none"; 3210 3211 return hidden; 3212 }; 3213 3214 /** 3215 * get operator term 3216 */ 3217 function getObjOperatorTerm(operator, dataTerms){ 3218 var slug = (operator == "and")?"__ucand__":"__ucor__"; 3219 var firstTerm = dataTerms[0]; 3220 var objOperatorTerm = { 3221 taxonomy: firstTerm.taxonomy, 3222 slug: slug, 3223 id:null 3224 }; 3225 3226 return(objOperatorTerm); 3227 } 3228 3229 /** 3230 * get operator marker for meta items (same as terms __ucand__/__ucor__) 3231 */ 3232 function getObjOperatorMeta(operator, dataMeta){ 3233 3234 var opValue = (operator == "and") ? "__ucand__" : "__ucor__"; 3235 var firstMeta = dataMeta[0]; 3236 var metaKey = getVal(firstMeta, "meta_key"); 3237 3238 if(!metaKey) 3239 metaKey = getVal(firstMeta, "slug"); 3240 3241 return({ 3242 type: "meta", 3243 meta_key: metaKey, 3244 meta_value: opValue, 3245 compare: getVal(firstMeta, "compare", "="), 3246 slug: opValue, 3247 id: null 3248 }); 3249 } 3250 3251 /** 3252 * get grid ajax options 3253 */ 3254 function getGridAjaxOptions(objFilters, objGrid, isFiltersInitMode, isLoadMoreMode, params){ 3255 3256 if(!isLoadMoreMode) 3257 var isLoadMoreMode = false; 3258 3259 if(g_showDebug){ 3260 trace("getGridAjaxOptions"); 3261 3262 trace("Filters:"); 3263 trace(objFilters); 3264 3265 trace("grid:"); 3266 trace(objGrid); 3267 trace("is init: " + isFiltersInitMode); 3268 3269 trace("params: "); 3270 trace(params); 3271 3272 } 3273 3274 //filter only visible elements (by it's parents) 3275 3276 var objVisibleFilters = objFilters.filter(function(objFilter){ 3277 3278 var objParent = getFilterWrapper(objFilter); 3279 3280 var isHidden = isElementHiddenByDisplayNone(objParent); 3281 3282 return(!isHidden); 3283 }); 3284 3285 3286 if(objVisibleFilters.length < objFilters.length){ 3287 3288 if(objVisibleFilters.length == 0){ 3289 3290 if(g_showDebug) 3291 trace("no visible filters"); 3292 3293 var objFilters = []; 3294 } 3295 else{ //test for mobile drawer 3296 3297 var objFirstFilter = jQuery(objVisibleFilters[0]); 3298 var visibleFilterType = getFilterType(objFirstFilter, true); 3299 3300 //exception for mobile drawer 3301 if(visibleFilterType != g_types.GENERAL_MOBILE_DRAWER){ 3302 3303 var objFilters = objVisibleFilters; 3304 3305 if(g_showDebug){ 3306 trace("Visible Filters: "); 3307 trace(objFilters); 3308 } 3309 } 3310 3311 }//end else 3312 3313 3314 } //end visible filters test 3315 3316 3317 if(!objFilters || objFilters.length == 0) 3318 return(null); 3319 3320 var urlReplace = g_urlBase; 3321 3322 var urlAjax = g_urlBase; 3323 3324 var strRefreshIDs = ""; 3325 3326 var isReplaceMode = false; 3327 var page = null; 3328 var offset = null; 3329 var numItems = null; 3330 var arrTerms = []; 3331 var objTaxIDs = {}; 3332 var objAuthorIDs = {}; 3333 var strSelectedTerms = ""; 3334 var strSelectedAuthors = ""; 3335 var strSelectedMeta = ""; 3336 var search = ""; 3337 var price_from, price_to; 3338 var arrAuthors = []; 3339 var arrMeta = []; 3340 var orderby = null; 3341 var orderby_metaname = null; 3342 var orderby_metatype = null; 3343 var orderdir = null; 3344 var title_start = null; 3345 var addSyncedGrids = true; 3346 var arrAllFiltersData; //all data gethered for the active filters 3347 var arrFiltersForInit = []; 3348 var urlAddFromFilters = ""; 3349 var isPaginationClicked = false;
3350 var isGetUrlOnly = getVal(params,"getonly"); 3351 3352 var initModeType = getVal(params,"filters_init_type"); 3353 3354 var initModeChildrens = false; 3355 if(isFiltersInitMode == true && initModeType == "children") 3356 initModeChildrens = true; 3357 3358 var wasInitMode = objGrid.data("was_init_mode"); 3359 3360 var arrFilterIDs = {}; 3361 3362 var advancedSearchFilterID; 3363 3364 var refreshType = getVal(params,"refresh_type"); 3365 3366 if(refreshType == g_vars.REFRESH_MODE_PAGINATION) 3367 isPaginationClicked = true; 3368 3369 var child_auto, childAutoTaxonomy, childAutoSlug, childAutoString = ""; 3370 3371 //get ajax options 3372 jQuery.each(objFilters, function(index, objFilter){ 3373 3374 //protection against duplicate id's 3375 var id = objFilter.attr("id"); 3376 3377 if(arrFilterIDs.hasOwnProperty(id) == true){ 3378 3379 trace("problematic filter: "); 3380 trace(objFilter); 3381 3382 trace("original filter found: "); 3383 trace(arrFilterIDs[id]); 3384 3385 trace("filters list: "); 3386 trace(objFilters); 3387 3388 throw new Error("Duplicate Filter ID found: " + id); 3389 } 3390 3391 arrFilterIDs[id] = objFilter; 3392 3393 var isNoRefresh = objFilter.data("uc_norefresh"); 3394 var filterRole = objFilter.data("role"); 3395 3396 var type = getFilterType(objFilter); 3397 3398 if(g_showDebug == true){ 3399 3400 trace("filter: "+type+", role: "+filterRole); 3401 trace(objFilter); 3402 } 3403 3404 var urlAdd = objFilter.attr(g_vars.ATTRIBUTE_URLADD); 3405 3406 if(urlAdd) 3407 urlAddFromFilters = addUrlParam(urlAddFromFilters, urlAdd); 3408 3409 switch(type){ 3410 case g_types.PAGINATION: 3411 3412 //run pagination only if it's clicked, unless reset pagination 3413 var isClicked = objFilter.hasClass(g_vars.CLASS_CLICKED); 3414 if(isClicked == true || isFiltersInitMode == true){ 3415 3416 var paginationData = getPaginationSelectedData(objFilter); 3417 3418 var paginationPage = getVal(paginationData, "page"); 3419 3420 if(paginationPage) 3421 page = paginationPage; //never set the url 3422 3423 //set page from url 3424 if(isFiltersInitMode == true && !page && g_vars.ucpage_url) 3425 page = g_vars.ucpage_url; 3426 3427 if(g_showDebug){ 3428 trace("pagination data"); 3429 trace(paginationData); 3430 } 3431 3432 objFilter.removeClass(g_vars.CLASS_CLICKED); 3433 } 3434 3435 3436 break; 3437 case g_types.LOADMORE: 3438 3439 //check if loadmore is before grid in init mode 3440 var isLoadMoreBeforeGrid = false; 3441 if(isFiltersInitMode == true){ 3442 var offsetLoadMore = objFilter.offset(); 3443 var offsetGrid = objGrid.offset(); 3444 3445 if(offsetLoadMore.top < offsetGrid.top){ 3446 isLoadMoreBeforeGrid = true; 3447 3448 if(g_showDebug == true) 3449 trace("Loadmore before grid - process in init mode"); 3450 } 3451 } 3452 3453 if(isFiltersInitMode == true && isLoadMoreBeforeGrid == false) 3454 return(true); 3455 3456 //run load more only if it's clicked, unless reset load more 3457 var isClicked = objFilter.hasClass(g_vars.CLASS_CLICKED); 3458 if(isClicked == true){ 3459 3460 var loadMoreData = getLoadMoreUrlData(objFilter); 3461 offset = loadMoreData.offset; 3462 numItems = loadMoreData.numItems; 3463 3464 var isSingleGrid = loadMoreData.singlegrid; 3465 3466 if(isSingleGrid == true) 3467 addSyncedGrids = false; 3468 3469 if(!offset) 3470 urlAjax = null; 3471 3472 objFilter.removeClass(g_vars.CLASS_CLICKED); 3473 } 3474 3475 break; 3476 case g_types.TERMS_LIST: 3477 case g_types.SELECT: 3478 3479 //if not init mode - take first item 3480 var objTerm = getTermsListSelectedTerm(objFilter); 3481 var filterSource = objFilter.data("filtersource"); 3482 3483 if(objTerm){ 3484 3485 if(isFiltersInitMode == false){ 3486 3487 if(filterSource == "authors") 3488 arrAuthors.push(objTerm); 3489 else if(filterSource == "meta") 3490 arrMeta.push(objTerm); 3491 else 3492 arrTerms.push(objTerm); 3493 } 3494 else{ 3495 3496 //INIT MODE 3497 3498 //add terms if the filter is not initing itself 3499 var isInit = objFilter.data("initafter"); 3500 3501 //add terms, if only children mode and the filter not child 3502 if(initModeChildrens == true && filterRole != "child") 3503 arrTerms.push(objTerm); 3504 else 3505 if(isInit != true){ 3506 3507 if(filterSource == "authors") 3508 arrAuthors.push(objTerm); 3509 else if(filterSource == "meta") 3510 arrMeta.push(objTerm); 3511 else 3512 arrTerms.push(objTerm); 3513 3514 } 3515 3516 //set selected terms string 3517 3518 var termID = objTerm.id; 3519 3520 if(filterSource == "authors"){ 3521 3522 if(strSelectedAuthors) 3523 strSelectedAuthors +=","; 3524 3525 strSelectedAuthors += termID; 3526 } 3527 else if(filterSource == "meta"){ 3528 3529 var metaPair = getMetaSelectedPair(objTerm); 3530 3531 if(metaPair){ 3532 if(strSelectedMeta) 3533 strSelectedMeta +=","; 3534 3535 strSelectedMeta += metaPair; 3536 } 3537 } 3538 else{ 3539 if(strSelectedTerms) 3540 strSelectedTerms +=","; 3541 3542 strSelectedTerms += termID; 3543 } 3544 3545 } 3546 } 3547 3548 //replace mode 3549 3550 var modeReplace = objFilter.data("replace-mode"); 3551 if(modeReplace === true) 3552 isReplaceMode = true; 3553 3554 if(isLoadMoreMode == true) 3555 isNoRefresh = true; 3556 3557 //debug 3558 if(g_showDebug == true){ 3559 3560 trace("Selected Term: "); 3561 trace(objTerm); 3562 } 3563 3564 break; 3565 case g_types.SUMMARY: 3566 3567 isNoRefresh = true; 3568 3569 //take nothing 3570 break; 3571 case g_types.SEARCH: 3572 3573 isNoRefresh = true; 3574 3575 var objInput = objFilter.find("input"); 3576 3577 search = objInput.val(); 3578 search = search.trim(); 3579 3580 //add id 3581 var isAdvancedSearch = objFilter.data("advancedsearch"); 3582 3583 if(isAdvancedSearch == true) 3584 advancedSearchFilterID = getElementWidgetID(objFilter); 3585 3586 break; 3587 case g_types.GENERAL: 3588 3589 var generalType = objFilter.data("generaltype"); 3590 3591 if(generalType == g_types.GENERAL_MOBILE_DRAWER) 3592 return(true); 3593 3594 var generalIsNoRefresh = objFilter.data("norefresh"); 3595 3596 if(generalIsNoRefresh === true) 3597 isNoRefresh = true; 3598 3599 var filterData = getGeneralFilterData(objFilter); 3600 3601 //add terms 3602 3603 var dataTerms = getVal(filterData,"terms"); 3604 3605 if(dataTerms && dataTerms.length){ 3606 3607 var isOperatoeAdded = false;
3608 3609 if(filterRole == "main"){ 3610 3611 var operator = getVal(filterData,"operator"); 3612 3613 if(operator === "and" || operator === "or"){ 3614 var objOperatorTerm = getObjOperatorTerm(operator, dataTerms); 3615 3616 dataTerms.push(objOperatorTerm); 3617 isOperatoeAdded = true; 3618 } 3619 } 3620 3621 if(dataTerms.length == 1){ //single term 3622 arrTerms.push(dataTerms[0]); 3623 } 3624 3625 if(dataTerms.length > 1){ //multiple terms 3626 //push the end or or operator 3627 var operator = getVal(filterData,"operator"); 3628 3629 if(isOperatoeAdded == false){ 3630 3631 if(operator === "and" || operator === "or"){ 3632 var objOperatorTerm = getObjOperatorTerm(operator, dataTerms); 3633 3634 dataTerms.push(objOperatorTerm); 3635 } 3636 } 3637 3638 arrTerms.push(dataTerms); //multiple (grouping) 3639 } 3640 3641 3642 //set selected terms string if init mode 3643 3644 if(isFiltersInitMode == true && dataTerms && dataTerms.length){ 3645 3646 var arrTermsForSelect = []; 3647 3648 if(jQuery.isArray(arrTerms)) 3649 arrTermsForSelect = arrTerms.flat(); 3650 3651 jQuery.each(arrTermsForSelect, function(index, term){ 3652 3653 var termID = getVal(term,"id"); 3654 3655 if(!termID) 3656 return(true); 3657 3658 if(strSelectedTerms) 3659 strSelectedTerms +=","; 3660 3661 strSelectedTerms += termID; 3662 }); 3663 3664 } 3665 } 3666 3667 //add authors 3668 var dataAuthors = getVal(filterData,"authors"); 3669 3670 if(dataAuthors && dataAuthors.length){ 3671 3672 //gather authors list 3673 jQuery.each(dataAuthors, function(index, author){ 3674 arrAuthors.push(author); 3675 }); 3676 3677 //set selected authors string if init mode 3678 3679 if(isFiltersInitMode == true){ 3680 3681 jQuery.each(dataAuthors, function(index, author){ 3682 3683 var authorID = getVal(author,"id"); 3684 3685 if(!authorID) 3686 return(true); 3687 3688 if(strSelectedAuthors) 3689 strSelectedAuthors +=","; 3690 3691 strSelectedAuthors += authorID; 3692 }); 3693 3694 } 3695 } 3696 3697 //add meta - same grouping as terms (checkbox OR = group, no .*) 3698 var dataMeta = getVal(filterData,"meta"); 3699 3700 if(dataMeta && dataMeta.length){ 3701 3702 var isMetaOperatorAdded = false; 3703 3704 if(filterRole == "main"){ 3705 3706 var metaOperator = getVal(filterData,"operator"); 3707 3708 if(metaOperator === "and" || metaOperator === "or"){ 3709 dataMeta.push(getObjOperatorMeta(metaOperator, dataMeta)); 3710 isMetaOperatorAdded = true; 3711 } 3712 } 3713 3714 if(dataMeta.length == 1){ 3715 arrMeta.push(dataMeta[0]); 3716 } 3717 3718 if(dataMeta.length > 1){ 3719 3720 var metaOperator = getVal(filterData,"operator"); 3721 3722 if(isMetaOperatorAdded == false){ 3723 3724 if(metaOperator === "and" || metaOperator === "or") 3725 dataMeta.push(getObjOperatorMeta(metaOperator, dataMeta)); 3726 } 3727 3728 arrMeta.push(dataMeta); //multiple (grouping) - OR by default 3729 } 3730 3731 if(isFiltersInitMode == true){ 3732 3733 jQuery.each(dataMeta, function(index, metaItem){ 3734 3735 var metaValue = getVal(metaItem,"meta_value"); 3736 3737 if(metaValue === "__ucand__" || metaValue === "__ucor__") 3738 return(true); 3739 3740 var metaPair = getMetaSelectedPair(metaItem); 3741 3742 if(!metaPair) 3743 return(true); 3744 3745 if(strSelectedMeta) 3746 strSelectedMeta +=","; 3747 3748 strSelectedMeta += metaPair; 3749 }); 3750 3751 } 3752 } 3753 3754 3755 if(g_showDebug == true){ 3756 trace("Filter Data:"); 3757 trace(filterData); 3758 } 3759 3760 if(generalType == "price" && isFiltersInitMode == false){ 3761 3762 var priceFromArg = getVal(filterData,"price_from"); 3763 var priceToArg = getVal(filterData,"price_to"); 3764 3765 if(priceFromArg) 3766 price_from = roundToOneDecimal(priceFromArg); 3767 3768 if(priceToArg) 3769 price_to = roundToOneDecimal(priceToArg); 3770 } 3771 3772 3773 //add title start 3774 3775 var titleStartArg = getVal(filterData, "title_start"); 3776 if(titleStartArg) 3777 title_start = titleStartArg; 3778 3779 //handle sort 3780 var argOrderby = getVal(filterData,"orderby"); 3781 if(argOrderby && argOrderby != "default"){ 3782 orderby = argOrderby; 3783 3784 orderby_metaname = getVal(filterData,"metaname"); 3785 orderby_metatype = getVal(filterData,"metatype"); 3786 } 3787 3788 var argOrderDir = getVal(filterData,"orderdir"); 3789 if(argOrderDir && argOrderDir != "default") 3790 orderdir = argOrderDir; 3791 3792 if(isLoadMoreMode == true) 3793 isNoRefresh = true; 3794 3795 break; 3796 default: 3797 throw new Error("Unknown filter type: "+type); 3798 break; 3799 } 3800 3801 3802 //handle filters init mode 3803 3804 if(isFiltersInitMode == true){ 3805 3806 var isInit = objFilter.data("initafter"); 3807 3808 3809 if(isInit != true){ 3810 isNoRefresh = true; 3811 } 3812 3813 //refresh parents only 3814 if(initModeChildrens == false && filterRole == "child") 3815 isNoRefresh = true; 3816 3817 //refresh children only 3818 if(initModeChildrens == true && filterRole != "child") 3819 isNoRefresh = true; 3820 3821 if(isNoRefresh == false){ 3822 arrFiltersForInit.push(objFilter); 3823 } 3824 3825 } 3826 3827 3828 //if hidden - no refresh 3829 3830 var isFilterHidden = objFilter.hasClass(g_vars.CLASS_HIDDEN); 3831 if(isFilterHidden == true) 3832 isNoRefresh = true; 3833 3834 objFilter.data("uc_norefresh",false); 3835 3836 var isMainFilter = (filterRole == "main"); 3837 var isTermChild = (filterRole == "term_child"); 3838 3839 //add to refresh filter if it's qualify 3840 3841 var isRefresh = true; 3842 3843 if(isFiltersInitMode == false && (isMainFilter === true || isTermChild == true)) 3844 isRefresh = false;
3845 3846 if(isNoRefresh === true) 3847 isRefresh = false; 3848 3849 if(g_showDebug == true){ 3850 trace("Filter Refresh: "+isRefresh); 3851 if(isRefresh == true){ 3852 trace("isFiltersInitMode: "+isFiltersInitMode); 3853 trace("isMainFilter: "+isMainFilter); 3854 trace("isTermChild: "+isTermChild); 3855 trace("isNoRefresh: "+isNoRefresh); 3856 } 3857 } 3858 3859 if(isRefresh == true){ 3860 3861 var filterWidgetID = getElementWidgetID(objFilter); 3862 3863 //add test tax id's for init mode 3864 var filterSource = objFilter.data("filtersource"); 3865 if(filterSource == "authors" && isFiltersInitMode == true){ 3866 //add test author id's for init mode 3867 objAuthorIDs = getFilterTaxIDs(objFilter, objAuthorIDs); 3868 }else{ 3869 objTaxIDs = getFilterTaxIDs(objFilter, objTaxIDs); 3870 } 3871 3872 if(strRefreshIDs) 3873 strRefreshIDs += ","; 3874 3875 strRefreshIDs += filterWidgetID; 3876 3877 if(!isGetUrlOnly) 3878 objFilter.addClass(g_vars.CLASS_REFRESH_SOON); 3879 } 3880 3881 if(filterRole == "main"){ 3882 var objTerm = getTermsListSelectedTerm(objFilter); 3883 3884 if(objTerm && objTerm != null){ 3885 3886 childAutoTaxonomy = objTerm.taxonomy; 3887 childAutoSlug = objTerm.slug; 3888 } 3889 } 3890 3891 if(filterRole == "child_auto" && arrTerms.length){ 3892 child_auto = true; 3893 3894 if(childAutoTaxonomy && childAutoSlug){ 3895 childAutoString = "&ucmainterm=" + childAutoTaxonomy + ":" + childAutoSlug; 3896 } 3897 3898 } 3899 3900 3901 }); //end filters iteration 3902 3903 3904 //add init filters additions 3905 3906 var urlAddition_filtersTest = ""; 3907 var strTaxIDs = getTermDsList(objTaxIDs); 3908 var strAuthorIDs = getTermDsList(objAuthorIDs); 3909 3910 if(isFiltersInitMode == true){ 3911 3912 if(!strTaxIDs && !strAuthorIDs && arrFiltersForInit.length == 0) 3913 urlAjax = null; 3914 else{ 3915 3916 if(urlAddition_filtersTest) 3917 urlAddition_filtersTest += "&"; 3918 3919 urlAddition_filtersTest += "modeinit=true"; 3920 } 3921 } 3922 3923 //test terms - only if there are terms in query, or mode init 3924 3925 if(strTaxIDs && (search || arrTerms.length || isFiltersInitMode == true || wasInitMode === true) ){ 3926 3927 if(urlAddition_filtersTest) 3928 urlAddition_filtersTest += "&"; 3929 3930 urlAddition_filtersTest += "testtermids="+strTaxIDs; 3931 } 3932 3933 //test authors - only if there are authors in query, or mode init (author mode) 3934 if(strAuthorIDs && (search || arrAuthors.length || isFiltersInitMode == true || wasInitMode === true) ){ 3935 3936 if(urlAddition_filtersTest) 3937 urlAddition_filtersTest += "&"; 3938 3939 urlAddition_filtersTest += "testauthorids="+strAuthorIDs; 3940 } 3941 3942 g_lastSyncGrids = null; 3943 3944 if(urlAjax == null) 3945 return(null); 3946 3947 var dataLayout = getElementLayoutData(objGrid, addSyncedGrids); 3948 3949 var widgetID = dataLayout["widgetid"]; 3950 var layoutID = dataLayout["layoutid"]; 3951 3952 //disable synced 3953 3954 if(addSyncedGrids == false){ 3955 3956 var syncedWidgetIDs = false; 3957 g_lastSyncGrids = null; 3958 3959 }else{ 3960 3961 var syncedWidgetIDs = getVal(dataLayout,"synced_widgetids"); 3962 g_lastSyncGrids = getVal(dataLayout,"synced_grids"); 3963 } 3964 3965 var urlFilterString = ""; 3966 3967 var urlAddition = "ucfrontajaxaction=getfiltersdata&layoutid="+layoutID+"&elid="+widgetID; 3968 3969 urlAjax = addUrlParam(urlAjax, urlAddition); 3970 3971 if(g_isGutenberg == true) 3972 urlAjax = addUrlParam(urlAjax, "platform=gutenberg"); 3973 3974 if(syncedWidgetIDs) 3975 urlAjax += "&syncelids="+syncedWidgetIDs; 3976 3977 if(urlAddition_filtersTest) 3978 urlAjax = addUrlParam(urlAjax, urlAddition_filtersTest); 3979 3980 if(price_from){ 3981 urlAjax += "&ucpricefrom="+price_from; 3982 3983 if(g_showDebug == true){ 3984 trace("add price from"); 3985 trace(urlAjax); 3986 } 3987 } 3988 3989 if(price_to){ 3990 urlAjax += "&ucpriceto="+price_to; 3991 3992 if(g_showDebug == true){ 3993 trace("add price to"); 3994 trace(urlAjax); 3995 } 3996 } 3997 3998 if(title_start){ 3999 4000 if(g_showDebug == true) 4001 trace("add title start: "+title_start); 4002 4003 urlAjax += "&titlestart="+title_start; 4004 urlReplace = addUrlParam(urlReplace, "titlestart="+title_start); 4005 } 4006 4007 4008 if(page){ 4009 urlAjax += "&ucpage="+page; 4010 4011 urlReplace = addUrlParam(urlReplace, "ucpage="+page); 4012 } 4013 4014 if(numItems) 4015 urlAjax += "&uccount="+numItems; 4016 4017 if(arrTerms.length){ 4018 4019 var strTerms = buildTermsQuery(arrTerms); 4020 4021 if(strTerms){ 4022 urlAjax += "&ucterms="+strTerms; 4023 //set the url params as well 4024 urlReplace = addUrlParam(urlReplace, "ucterms="+strTerms); 4025 urlFilterString = addUrlParam(urlFilterString, "ucterms="+strTerms); 4026 } 4027 4028 } 4029 4030 //add authors 4031 if(arrAuthors.length){ 4032 4033 var strAuthors = ""; 4034 jQuery.each(arrAuthors, function(index, author){ 4035 var authorID = getVal(author, "id"); 4036 if(authorID){ 4037 if(strAuthors) 4038 strAuthors += ","; 4039 strAuthors += authorID; 4040 } 4041 }); 4042 4043 if(strAuthors){ 4044 urlAjax += "&ucauthors="+strAuthors; 4045 urlReplace = addUrlParam(urlReplace, "ucauthors="+strAuthors); 4046 urlFilterString = addUrlParam(urlFilterString, "ucauthors="+strAuthors); 4047 } 4048 } 4049 4050 //add meta 4051 if(arrMeta.length){ 4052 4053 var strMeta = buildMetaQuery(arrMeta); 4054 4055 if(strMeta){ 4056 urlAjax += "&ucmeta="+strMeta; 4057 urlReplace = addUrlParam(urlReplace, "ucmeta="+strMeta); 4058 urlFilterString = addUrlParam(urlFilterString, "ucmeta="+strMeta); 4059 } 4060 } 4061 4062 if(child_auto && arrTerms.length && childAutoString != ""){ 4063 urlAjax += childAutoString; 4064 } 4065 4066 if(orderby){ 4067 4068 urlAjax += "&ucorderby="+orderby; 4069 urlReplace = addUrlParam(urlReplace, "ucorderby="+orderby); 4070 4071 if(orderby_metaname){ 4072 urlAjax += "&ucorderby_meta="+orderby_metaname; 4073 urlReplace = addUrlParam(urlReplace, "ucorderby_meta="+orderby_metaname); 4074 } 4075 4076 if(orderby_metatype){ 4077 urlAjax += "&ucorderby_metatype="+orderby_metatype; 4078 urlReplace = addUrlParam(urlReplace, "ucorderby_metatype="+orderby_metatype); 4079 } 4080 4081 } 4082 4083 if(orderdir){ 4084 urlAjax += "&ucorderdir="+orderdir; 4085 4086 urlReplace = addUrlParam(urlReplace, "ucorderdir="+orderdir); 4087 } 4088 4089 if(isFiltersInitMode && strSelectedTerms && strSelectedTerms !== "undefined") 4090 urlAjax += "&ucinitselectedterms="+strSelectedTerms; 4091 4092 if(isFiltersInitMode && strSelectedAuthors && strSelectedAuthors !== "undefined") 4093 urlAjax += "&ucinitselectedauthors="+strSelectedAuthors; 4094 4095 if(isFiltersInitMode && strSelectedMeta && strSelectedMeta !== "undefined") 4096 urlAjax += "&ucinitselectedmeta="+strSelectedMeta; 4097
4098 //add refresh ids 4099 if(strRefreshIDs) 4100 urlAjax += "&addelids="+strRefreshIDs; 4101 4102 if(isReplaceMode == true) 4103 urlAjax += "&ucreplace=1"; 4104 4105 //search 4106 if(search){ 4107 search = encodeURIComponent(search); 4108 4109 //search = escape(search); 4110 4111 urlAjax = addUrlParam(urlAjax, "ucs=" + search); 4112 4113 urlFilterString = addUrlParam(urlFilterString, "ucs=" + search); 4114 4115 urlReplace = addUrlParam(urlReplace, "ucs=" + search); 4116 4117 //add special search id 4118 if(advancedSearchFilterID) 4119 urlAjax = addUrlParam(urlAjax, "ucsid=" + advancedSearchFilterID); 4120 4121 } 4122 4123 //avoid duplicates - exclude, disable the offset 4124 4125 if(objGrid.hasClass("uc-avoid-duplicates")){ 4126 4127 var objCurrentGrid = objGrid; 4128 if(isLoadMoreMode == true) 4129 objCurrentGrid = null; //load with exclude but without offset 4130 4131 var strExcludePostIDs = getExcludePostIDs(objCurrentGrid); //exclude current grid 4132 4133 if(strExcludePostIDs){ 4134 urlAjax += "&ucexclude="+strExcludePostIDs; 4135 4136 if(isLoadMoreMode == true) 4137 offset = null; 4138 4139 urlFilterString = addUrlParam(urlFilterString, "ucexclude=" + strExcludePostIDs); 4140 } 4141 4142 } 4143 4144 4145 if(offset){ 4146 urlAjax += "&ucoffset="+offset; 4147 4148 urlFilterString = addUrlParam(urlFilterString, "offset=" + offset); 4149 4150 } 4151 4152 //add custom additional attributes 4153 4154 if(urlAddFromFilters){ 4155 urlAjax += addUrlParam(urlAjax, urlAddFromFilters); 4156 urlFilterString = addUrlParam(urlFilterString, urlAddFromFilters); 4157 } 4158 4159 //remove the "?" from first 4160 if(urlFilterString) 4161 urlFilterString = urlFilterString.substring(1); 4162 4163 4164 //remember init mode 4165 if(isFiltersInitMode == true) 4166 objGrid.data("was_init_mode",true); 4167 4168 4169 if(g_showDebug == true){ 4170 4171 trace("url ajax: " + urlAjax); 4172 } 4173 4174 var output = {}; 4175 output["ajax_url"] = urlAjax; 4176 output["url_replace"] = urlReplace; 4177 output["terms"] = arrTerms; 4178 output["meta"] = arrMeta; 4179 output["authors"] = arrAuthors; 4180 output["search"] = search; 4181 output["title_start"] = title_start; 4182 output["filters_string"] = urlFilterString; 4183 4184 if(g_showDebug == true){ 4185 4186 trace("output: "); 4187 trace(output); 4188 4189 trace("End getGridAjaxOptions function"); 4190 } 4191 4192 4193 4194 return(output); 4195 } 4196 4197 4198 /** 4199 * get all exclude post ids from all avoid duplicates grids 4200 * if it's a single avoid duplicates grid - don't get excludes 4201 */ 4202 function getExcludePostIDs(objCurrentGrid){ 4203 4204 //check if it's only one grid involved 4205 if(!objCurrentGrid) 4206 var objGrids = jQuery(".uc-avoid-duplicates"); 4207 else 4208 var objGrids = jQuery(".uc-avoid-duplicates").not(objCurrentGrid); 4209 4210 if(objGrids.length == 0) 4211 return(""); 4212 4213 //check if rand of only grid, get id's, else not 4214 4215 if(objGrids.length == 1 && !objCurrentGrid){ 4216 var queryData = objGrids.attr("querydata"); 4217 4218 var objQueryData = JSON.parse(queryData); 4219 var orderby = getVal(objQueryData,"orderby"); 4220 4221 if(orderby != "rand") 4222 return(""); 4223 } 4224 4225 4226 //get all the id's of all including the existing. 4227 4228 var strIDs = ""; 4229 4230 jQuery.each(objGrids, function(index, grid){ 4231 var objGrid = jQuery(grid); 4232 4233 var postIDs = objGrid.data("postids"); 4234 4235 if(!postIDs) 4236 return(true); 4237 4238 if(strIDs) 4239 strIDs += ","; 4240 4241 strIDs += postIDs; 4242 }); 4243 4244 4245 return(strIDs); 4246 } 4247 4248 function ________INIT_AFTER_______________(){} 4249 4250 /** 4251 * add filter to grid init after array 4252 */ 4253 function addFilterToInitAfter(objFilter, objGrid){ 4254 4255 var role = objFilter.data("role"); 4256 4257 var key = "filters_init_after"; 4258 4259 if(role == "child") 4260 key = "filters_init_after_children"; 4261 4262 objFilter.data("initafter",true); 4263 4264 var arrFiltersInitAfter = objGrid.data(key); 4265 4266 if(!arrFiltersInitAfter) 4267 arrFiltersInitAfter = []; 4268 4269 arrFiltersInitAfter.push(objFilter); 4270 4271 if(g_showDebug == true) 4272 trace("Add init after: "+key+" | "+objFilter.attr("id") ); 4273 4274 objGrid.data(key, arrFiltersInitAfter); 4275 4276 } 4277 4278 /** 4279 * check filters init after 4280 */ 4281 function isSpecialFilterInitAfter(objFilter, objGrid){ 4282 4283 var type = getFilterType(objFilter); 4284 4285 if(type != g_types.PAGINATION && type != g_types.LOADMORE) 4286 return(false); 4287 4288 var offsetPagination = objFilter.offset(); 4289 var offsetGrid = objGrid.offset(); 4290 4291 if(offsetPagination.top < offsetGrid.top){ 4292 4293 if(g_showDebug == true) 4294 trace("Set "+type+" to ajax init"); 4295 4296 return(true); 4297 } 4298 4299 return(false); 4300 } 4301 4302 /** 4303 * check if there is a need to refresh child filters 4304 * grid related, other filters are set in the settings 4305 */ 4306 function initGrid_setInitFiltersAfterLoad(objGrid){ 4307
4308 //get all grid filters 4309 var objFilters = objGrid.data("filters"); 4310 4311 if(!objFilters) 4312 return(false); 4313 4314 if(objFilters.length == 0) 4315 return(false); 4316 4317 //check if there are filters with selected 4318 4319 var arrSelectedFilters = getSelectedFilters(objFilters); 4320 4321 if(arrSelectedFilters.length == 0) 4322 return(false); 4323 4324 //add to refresh all not selected filters 4325 4326 jQuery.each(objFilters, function(index, filter){ 4327 4328 var objFilter = jQuery(filter); 4329 var type = getFilterType(objFilter); 4330 4331 //skip not related to filter types 4332 switch(type){ 4333 case g_types.PAGINATION: 4334 case g_types.LOADMORE: 4335 return(true); 4336 break; 4337 } 4338 4339 var isSelected = objFilter.hasClass("uc-has-selected"); 4340 4341 if(isSelected == true) 4342 return(true); 4343 4344 //skip by role. main don't add to init after 4345 var filterRole = objFilter.data("role"); 4346 if(filterRole == "main") 4347 return(true); 4348 4349 //add to grid and option to refresh 4350 4351 var objGrid = objFilter.data("grid"); 4352 4353 addFilterToInitAfter(objFilter, objGrid); 4354 4355 }); 4356 4357 } 4358 4359 4360 function ________INIT_______________(){} 4361 4362 4363 /** 4364 * init the globals 4365 */ 4366 function initGlobals(){ 4367 4368 if(typeof g_strFiltersData === "undefined") 4369 return(false); 4370 4371 g_filtersData = JSON.parse(g_strFiltersData); 4372 4373 if(jQuery.isEmptyObject(g_filtersData)){ 4374 4375 trace("filters error - filters data not found"); 4376 return(false); 4377 } 4378 4379 g_urlBase = getVal(g_filtersData, "urlbase"); 4380 g_urlAjax = getVal(g_filtersData, "urlajax"); 4381 4382 var platform = getVal(g_filtersData, "platform"); 4383 4384 //switch to gutenberg 4385 4386 if(platform == "gutenberg"){ 4387 g_isGutenberg = true; 4388 g_vars.class_widget_wrapper = "ue-widget-root"; 4389 g_vars.current_postid = getVal(g_filtersData, "postid"); 4390 } 4391 4392 //ucpage url 4393 var ucpage = getVal(g_filtersData,"ucpage"); 4394 if(jQuery.isNumeric(ucpage)) 4395 g_vars.ucpage_url = ucpage; 4396 4397 //url keys 4398 4399 var objUrlKeys = getVal(g_filtersData, "urlkeys"); 4400 4401 var taxSap = getVal(objUrlKeys, "tax_sap"); 4402 if(taxSap) 4403 g_options.urlkey_taxsap = taxSap; 4404 4405 var isShowDebug = getVal(g_filtersData, "debug"); 4406 4407 if(isShowDebug == true) 4408 g_showDebug = true; 4409 4410 if(g_showDebug == true) 4411 trace("Show Filters Debug"); 4412 4413 if(!g_urlBase){ 4414 trace("ue filters error - base url not inited"); 4415 return(false); 4416 } 4417 4418 if(!g_urlAjax){ 4419 trace("ue filters error - ajax url not inited"); 4420 return(false); 4421 } 4422 4423 //trace(g_options); 4424 4425 return(true); 4426 } 4427 4428 4429 /** 4430 * init filter and bing to grid 4431 */ 4432 function initFilter(objFilter, type){ 4433 4434 var objGrid = getClosestGrid(objFilter); 4435 4436 var error = "Filter Parent not found! Please put the posts element on the page, and turn on 'Enable Post Filtering' option on it"; 4437 4438 if(!objGrid){ 4439 4440 4441 //pagination can work without parent as regular link 4442 4443 var type = getFilterType(objFilter); 4444 if(type == g_types.PAGINATION) 4445 return(false); 4446 4447 showElementError(objFilter, error); 4448 return(null); 4449 } 4450 4451 var isAjax = objGrid.data("ajax"); 4452 4453 if(isAjax == false){ 4454 showElementError(objFilter, error); 4455 return(false); 4456 } 4457 4458 //bind grid to filter 4459 objFilter.data("grid", objGrid); 4460 4461 //bind filter to grid 4462 bindFilterToGrid(objGrid, objFilter); 4463 4464 4465 //set data var 4466 if(g_showDebug == true) 4467 objFilter.attr("data-showdebug", true); 4468 4469 switch(type){ 4470 case g_types.TERMS_LIST: 4471 initTermsRelatedFilter(objFilter); 4472 break; 4473 case g_types.SELECT: 4474 initSelectFilter(objFilter); 4475 initTermsRelatedFilter(objFilter); 4476 break; 4477 case g_types.GENERAL: //general filter events 4478 initGeneralFilter(objFilter); 4479 break; 4480 } 4481 4482 4483 objFilter.trigger(g_vars.EVENT_INIT_FILTER); 4484 4485 } 4486 4487 4488 /** 4489 * init filter events by types 4490 */ 4491 function initFilterEventsByTypes(arrTypes, arrGeneralTypes, objFilters, objParent){ 4492 4493 if(!arrTypes || arrTypes.length == 0) 4494 return(false); 4495 4496 if(g_showDebug == true){ 4497 trace("Init filter events for parent"); 4498 trace(arrTypes); 4499 trace(objParent); 4500 } 4501 4502 for(var type in arrTypes){ 4503 4504 switch(type){ 4505 case g_types.PAGINATION: 4506 4507 objParent.on("click",".uc-filter-pagination a", onAjaxPaginationLinkClick); 4508 4509 break; 4510 case g_types.LOADMORE: 4511 4512 //load more 4513 objParent.on("click",".uc-filter-load-more__link", onLoadMoreClick); 4514 break; 4515 case g_types.TERMS_LIST: 4516 4517 objParent.on("click",".ue_taxonomy.uc-grid-filter a.ue_taxonomy_item", onTermsLinkClick); 4518 4519 break; 4520 case g_types.SEARCH: 4521 4522 //do nothing for init 4523 4524 break; 4525 case g_types.SELECT: 4526 4527 objParent.on("change", ".uc-select-filter__select", onTermsLinkClick); 4528 4529 break; 4530 case g_types.SUMMARY: 4531 //do nothing for now 4532 break; 4533 case g_types.GENERAL: 4534 //the init is from the general types 4535 break; 4536 default: 4537 trace("init by type - unrecognized type: "+type); 4538 break; 4539 } 4540 } 4541 4542 if(!arrGeneralTypes || arrGeneralTypes.length == 0) 4543 return(false); 4544 4545 4546 //init the general types 4547 4548 for(var generalType in arrGeneralTypes){ 4549 4550 var objFirstFilter = arrGeneralTypes[generalType]; 4551 4552 objFirstFilter.trigger(g_vars.EVENT_INIT_FILTER_TYPE,[objParent]); 4553 4554 } 4555 4556 } 4557 4558 4559 4560 4561 /** 4562 * init pagination filter 4563 */ 4564 function initFilters(objFilters){ 4565
4566 if(g_showDebug == true){ 4567 4568 trace("init filters"); 4569 4570 if(objFilters.length == 0) 4571 trace("no filters found"); 4572 else 4573 trace(objFilters); 4574 } 4575 4576 var numFilters = objFilters.length; 4577 4578 if(numFilters == 0) 4579 return(false); 4580 4581 var arrTypes = {}; 4582 var arrGeneralTypes = {}; 4583 4584 var objParent = getFiltersParent(objFilters); 4585 4586 jQuery.each(objFilters, function(index, filter){ 4587 4588 var objFilter = jQuery(filter); 4589 var type = getFilterType(objFilter); 4590 4591 //set single filter 4592 if(numFilters === 1){ 4593 objFilter.attr("data-singlefilter",true); 4594 } 4595 4596 initFilter(objFilter, type); 4597 4598 //collect the general type 4599 4600 arrTypes[type] = true; 4601 4602 if(type == g_types.GENERAL){ 4603 var generalType = objFilter.data("generaltype"); 4604 4605 if(!generalType){ 4606 trace(objFilter); 4607 throw new Error("The filter is missing generaltype data"); 4608 } 4609 4610 if(arrGeneralTypes.hasOwnProperty(generalType) == false) 4611 arrGeneralTypes[generalType] = objFilter; 4612 4613 } 4614 4615 objFilter.addClass(g_vars.CLASS_FILTER_INITED); 4616 4617 }); 4618 4619 initFilterEventsByTypes(arrTypes, arrGeneralTypes, objFilters, objParent); 4620 4621 } 4622 4623 4624 /** 4625 * set init state ajax url for each grid (for go back) 4626 */ 4627 function initGrid_setAjaxUrl(objGrid){ 4628 4629 var behave = objGrid.data("filterbehave"); 4630 4631 if(behave != "mixed_back") 4632 return(false); 4633 4634 //get all grid filters 4635 var objFilters = objGrid.data("filters"); 4636 4637 if(!objFilters) 4638 return(false); 4639 4640 if(objFilters.length == 0) 4641 return(false); 4642 4643 var objAjaxOptions = getGridAjaxOptions(objFilters, objGrid,false,false,{getonly:true}); 4644 4645 var ajaxUrlInit = getVal(objAjaxOptions, "ajax_url"); 4646 4647 objGrid.data("initajaxurl", ajaxUrlInit); 4648 4649 } 4650 4651 4652 /** 4653 * set active filters data - for third party connections, active filters and clear button 4654 */ 4655 function initGrid_setActiveFiltersData(objGrid, objAjaxOptions){ 4656 4657 if(!objAjaxOptions) 4658 var objAjaxOptions = getGridAjaxOptions_simple(objGrid); 4659 4660 4661 var arrTerms = getVal(objAjaxOptions, "terms"); 4662 var arrMeta = getVal(objAjaxOptions, "meta"); 4663 var arrAuthors = getVal(objAjaxOptions, "authors"); 4664 4665 if(!jQuery.isArray(arrTerms)) 4666 arrTerms = []; 4667 4668 if(!jQuery.isArray(arrMeta)) 4669 arrMeta = []; 4670 4671 if(!jQuery.isArray(arrAuthors)) 4672 arrAuthors = []; 4673 4674 arrTerms = arrTerms.concat(arrMeta, arrAuthors); 4675 4676 if(jQuery.isArray(arrTerms)) 4677 arrTerms = arrTerms.flat(); 4678 4679 // Create a new array for filtered items 4680 var filteredTerms = []; 4681 4682 jQuery.each(arrTerms, function(index, term) { 4683 4684 if(!term) 4685 return(true); 4686 4687 var slug = getVal(term, "slug"); 4688 var metaValue = getVal(term, "meta_value"); 4689 4690 // Skip operator markers used for grouping (__ucand__/__ucor__) 4691 if (slug === "__ucand__" || slug === "__ucor__" || slug === "__and__" || slug === "__or__") 4692 return(true); 4693 4694 if (metaValue === "__ucand__" || metaValue === "__ucor__") 4695 return(true); 4696 4697 filteredTerms.push(term); 4698 }); 4699 4700 // Assign the filtered array back to arrTerms 4701 arrTerms = filteredTerms; 4702 4703 var search = getVal(objAjaxOptions, "search"); 4704 4705 if(search) 4706 search = search.trim(); 4707 4708 if(search){ 4709 var objSearch = { 4710 type:"search", 4711 "key": "search|"+search, 4712 "title": search 4713 }; 4714 4715 if(!arrTerms) 4716 var arrTerms = []; 4717 4718 arrTerms.push(objSearch); 4719 } 4720 4721 //title start 4722 var titleStart = getVal(objAjaxOptions, "title_start"); 4723 4724 if(titleStart){ 4725 4726 var objTitleStart = { 4727 type:"titlestart", 4728 "key": "titlestart|"+titleStart, 4729 "title": titleStart 4730 }; 4731 4732 if(!arrTerms) 4733 var arrTerms = []; 4734 4735 arrTerms.push(objTitleStart); 4736 } 4737 4738 4739 objGrid.data("active_filters_items", arrTerms); 4740 objGrid.trigger(g_vars.EVENT_UPDATE_ACTIVE_FILTER_ITEMS, [arrTerms]); 4741 4742 } 4743 4744 4745 /** 4746 * init the grids, ininital filters refresh, 4747 * set active filters, and update initial url's 4748 */ 4749 function initGrids(){ 4750 4751 var objGrids = getAllGrids("loaded_only"); 4752 4753 if(objGrids.length == 0) 4754 return(false); 4755 4756 if(g_showDebug == true){ 4757 trace("init grids"); 4758 trace(objGrids); 4759 } 4760 4761 jQuery.each(objGrids, function(index, grid){ 4762 4763 var objGrid = jQuery(grid); 4764 4765 //--- set go back url if needed 4766 4767 initGrid_setAjaxUrl(objGrid); 4768 4769 initGrid_setInitFiltersAfterLoad(objGrid); 4770 4771 //--- set active filters (for clear and active filters links) 4772 4773 initGrid_setActiveFiltersData(objGrid); 4774 4775 4776 //--- refresh init filters 4777 4778 var objInitFilters = objGrid.data("filters_init_after"); 4779 4780 var isMainFiltersRefreshed = false;
4781 if(objInitFilters && objInitFilters.length > 0){ 4782 4783 isMainFiltersRefreshed = true; 4784 4785 if(g_showDebug == true){ 4786 trace("ajax init Filters"); 4787 trace(objInitFilters); 4788 } 4789 4790 refreshAjaxGrid(objGrid, "filters"); 4791 } 4792 4793 //--- refresh init filters - children 4794 4795 var objInitFiltersChildren = objGrid.data("filters_init_after_children"); 4796 4797 if(objInitFiltersChildren && objInitFiltersChildren.length > 0){ 4798 4799 if(isMainFiltersRefreshed == false){ 4800 4801 if(g_showDebug == true){ 4802 trace("ajax init child Filters"); 4803 trace(objInitFiltersChildren); 4804 } 4805 4806 refreshAjaxGrid(objGrid, "filters_children"); 4807 4808 } 4809 else 4810 objGrid.data("init_refresh_child_filters", true); 4811 } 4812 4813 objGrid.addClass("ucfilters--grid-inited"); 4814 4815 }); 4816 4817 4818 return(objGrids); 4819 } 4820 4821 /** 4822 * init grids events 4823 */ 4824 function initGridsEvents(objGrids){ 4825 4826 //init grids events 4827 4828 if(!objGrids || objGrids.length == 0) 4829 return(false); 4830 4831 4832 //grid several action 4833 4834 objGrids.on(g_vars.ACTION_REFRESH_GRID,function(){ 4835 4836 var objGrid = jQuery(this); 4837 4838 if(g_showDebug == true){ 4839 trace("Refresh grid - by event:" + g_vars.ACTION_REFRESH_GRID); 4840 console.trace(); 4841 } 4842 4843 refreshAjaxGrid(objGrid); 4844 }); 4845 4846 4847 objGrids.on(g_vars.ACTION_GET_FILTERS_URL,function(){ 4848 4849 var objGrid = jQuery(this); 4850 4851 var urlFilters = getGridUrlFiltersString(objGrid); 4852 4853 return(urlFilters); 4854 }); 4855 4856 //clear filters from event 4857 4858 objGrids.on(g_vars.ACTION_CLEAR_FILTERS, function(){ 4859 4860 var objGrid = jQuery(this); 4861 4862 var arrActiveFilterItems = getGridActiveFilterItems(objGrid); 4863 4864 //if already cleared - no need 4865 if(!arrActiveFilterItems) 4866 return(null); 4867 4868 clearAllFilters(objGrid, null, true); 4869 4870 objGrid.trigger(g_vars.ACTION_REFRESH_GRID); 4871 4872 }); 4873 4874 //unselect filter from event 4875 4876 objGrids.on(g_vars.EVENT_UNSELECT_FILTER, function(event, key){ 4877 4878 var objGrid = jQuery(this); 4879 4880 unselectFilterItem(objGrid, key); 4881 4882 objGrid.trigger(g_vars.ACTION_REFRESH_GRID); 4883 }); 4884 4885 } 4886 4887 /** 4888 * init events 4889 */ 4890 function initGeneralEvents(){ 4891 4892 addEventListener('popstate', onPopState); 4893 4894 g_objBody.on(g_vars.EVENT_DOM_UPDATED, runInitFilters); 4895 4896 } 4897 4898 4899 /** 4900 * validate the grids 4901 */ 4902 function validateGrid(objGrid){ 4903 4904 //check for |raw absence 4905 4906 var isAjax = objGrid.data("ajax"); 4907 4908 if(isAjax === "'true'") 4909 showElementError(objGrid, "This grid configured wrong way, missing |raw in html attributes"); 4910 4911 } 4912 4913 4914 /** 4915 * add some validation to the grids 4916 */ 4917 function validateGrids(){ 4918 4919 var objGrids = getAllGrids("loaded_only"); 4920 4921 jQuery.each(objGrids, function(index, grid){ 4922 4923 var objGrid = jQuery(grid); 4924 4925 validateGrid(objGrids); 4926 }); 4927 } 4928 4929 4930 /** 4931 * run init filters 4932 */ 4933 function runInitFilters(){ 4934 4935 validateGrids(); 4936 4937 //get the filters 4938 var objFilters = jQuery(".uc-grid-filter, .uc-filter-pagination").not("." + g_vars.CLASS_FILTER_INITED); 4939 4940 //wait for load... 4941 4942 var objFiltersLoading = objFilters.filter(".uc-waitforload"); 4943 4944 if(objFiltersLoading.length && g_initFiltersCounter < 2){ 4945 4946 if(g_showDebug == true){ 4947 trace(objFiltersLoading); 4948 trace("Wait for Load!"); 4949 } 4950 4951 setTimeout(runInitFilters, 500); 4952 4953 g_initFiltersCounter++; 4954 4955 objFilters = null; 4956 objFiltersLoading = null; 4957 4958 return(false); 4959 } 4960 4961 //init for the next time 4962 g_initFiltersCounter = 0; 4963 4964 initFilters(objFilters); 4965 4966 //init all grids with several stuff like init filters, active modes and url's 4967 var objGrids = initGrids(); 4968 4969 initGridsEvents(objGrids); 4970 4971 } 4972 4973 4974 /** 4975 * init 4976 */ 4977 function init(){ 4978 4979 g_objBody = jQuery("body"); 4980 4981 var success = initGlobals(); 4982 //run again on fail 3 times 4983 if(success == false){ 4984 4985 if(typeof window.ueFiltersTimeoutCounter != "undefined") 4986 window.ueFiltersTimeoutCounter++; 4987 else 4988 window.ueFiltersTimeoutCounter = 0; 4989 4990 if(window.ueFiltersTimeoutCounter == 3){ 4991 trace("Failed to init filters"); 4992 return(false); 4993 } 4994 4995 setTimeout(init, 200); 4996 4997 return(false); 4998 } 4999 5000 //init remote object if exists 5001 if(typeof UERemoteConnection == "function") 5002 g_remote = window.ueRemoteConnection; 5003 5004 runInitFilters(); 5005 5006 initGeneralEvents(); 5007 5008 5009 //run init again on elementor popup 5010 5011 jQuery( document ).on( 'elementor/popup/show', function(event, id, objPopup){ 5012 5013 g_objBody.trigger(g_vars.EVENT_DOM_UPDATED); 5014 5015 }); 5016 5017 5018 } 5019 5020 5021 /** 5022 * is element in viewport 5023 */ 5024 this.isElementInViewport = function(objElement) { 5025 5026 var elementTop = objElement.offset().top; 5027 var elementBottom = elementTop + objElement.outerHeight(); 5028 5029 var viewportTop = jQuery(window).scrollTop(); 5030 var viewportBottom = viewportTop + jQuery(window).height(); 5031 5032 return (elementBottom > viewportTop && elementTop < viewportBottom); 5033 } 5034 5035 /** 5036 * run function with trashold, default is 500 5037 */ 5038 this.runWithTrashold = function(func, trashold){ 5039 5040 if(!trashold) 5041 var trashold = 500; 5042 5043 if(g_vars.trashold_handle) 5044 clearTimeout(g_vars.trashold_handle); 5045 5046 g_vars.trashold_handle = setTimeout(func, trashold); 5047 5048 }; 5049 5050 /** 5051 * get filter element data 5052 */ 5053 this.getFilterElementData = function(objElement){ 5054 5055 var objData = getFilterElementData(objElement); 5056 5057 return(objData); 5058 } 5059 5060 /** 5061 * get filter parent query data 5062 */ 5063 this.getFilterGridQueryData = function(objFilter){ 5064 5065 var objGrid = objFilter.data("grid"); 5066 if(!objGrid) 5067 return(null); 5068
5069 var queryData = objGrid.attr("querydata"); 5070 if(!queryData) 5071 return(null); 5072 5073 var objData = jQuery.parseJSON(queryData); 5074 5075 if(g_showDebug == true){ 5076 console.log("getQueryData (filter, grid, querydata): ",objFilter, objGrid, queryData); 5077 } 5078 5079 return(objData); 5080 } 5081 5082 /** 5083 * get key 5084 */ 5085 this.getFilterItemKey = function(objItem){ 5086 5087 if(!objItem || objItem.length == 0) 5088 return(null); 5089 5090 var key = objItem.data("key"); 5091 5092 if(key) 5093 return(key); 5094 5095 //fallback 5096 5097 key = "term|" + objItem.data("taxonomy") + "|" + objItem.data("slug"); 5098 5099 return(key); 5100 } 5101 5102 5103 /** 5104 * get value 5105 */ 5106 this.getVal = function(obj, name, defaultValue){ 5107 5108 return getVal(obj, name, defaultValue); 5109 } 5110 5111 /** 5112 * get filters by type 5113 * return jquery object 5114 */ 5115 this.getGridFiltersByType = function(objGrid, filterType){ 5116 5117 if(!filterType) 5118 throw new Error("getGridFiltersByType error - enter type as second param"); 5119 5120 var arrFilters = getGridFilters(objGrid); 5121 5122 if(arrFilters.length == 0) 5123 return(jQuery()); 5124 5125 var objChosenFilters = jQuery(); 5126 5127 jQuery.each(arrFilters, function(index, objFilter){ 5128 5129 var type = getFilterType(objFilter, true); 5130 5131 if(type == filterType){ 5132 objChosenFilters = objChosenFilters.add(objFilter); 5133 } 5134 5135 }); 5136 5137 return(objChosenFilters); 5138 } 5139 5140 5141 /** 5142 * init the class 5143 */ 5144 function construct(){ 5145 5146 if(!jQuery){ 5147 trace("Filters not loaded, jQuery not loaded"); 5148 return(false); 5149 } 5150 5151 jQuery("document").ready(function(){ 5152 setTimeout(init, 200); 5153 }); 5154 5155 } 5156 5157 construct(); 5158 5159} 5160 5161g_ucDynamicFilters = new UEDynamicFilters();
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.