1/* 2* Mega Menu script made by Denis Odintsov for Unlimited Elements 3*/ 4 5function ueMegaMenu(){ 6 //classes 7 var g_ucTemplateWrapperClass, g_elementorClass, g_subArrowClass, g_ucMegaMenuTitleClass, g_ucConnectedClass, g_sectionErrorClass, g_ucSectionErrorClass, g_ucMegaMenuListItemClass, g_ucMegaMenuSectionClass, g_availableIDsClass, g_ucCollapseIndicatorClass, g_ucExpandIndicatorClass, g_ueTipClass, g_ucMobileModeClass, g_ucActiveItemClass, g_ucMenuOpenCLass, g_ucMegaMenuWrapperClass, g_ucMegaMenuListClass, g_ucMegaMenuOverlayClass; 8 9 //selectors 10 var g_ucTemplateWrapperSelector, g_elementorSelector, g_subArrowSelector, g_ucMegaMenuTitleSelector, g_ucConnectedSelector, g_ucSectionErrorSelector, g_ucMegaMenuListItemSelector, g_ucMegaMenuSectionSelector, g_ucCollapseIndicatorSelector, g_ueTipSelector, g_ucMobileModeSelector, g_ucActiveItemSelector, g_ucMegaMenuWrapperSelector, g_ucMegaMenuListSelector, g_ucMegaMenuOverlaySelector; 11 12 //objects 13 var g_objWidget, g_objUCMegaMenuSection, g_objMenuItems, g_objMenuListWrap, g_objBody, g_objHtml; 14 15 //data attributes 16 var g_dataOpenFirst, g_dataOffsetY, g_objMenuList; 17 18 //helpers 19 var g_indicator, g_translateX, g_dataMenuOpen, g_objOverlay, g_menuWrapOffsetLeft, g_viewportWidth, g_dataPositionX, g_dataEditor, g_menuItemTitle, g_showErrors, g_offsetX, g_urlBase, g_dataCloseDelay, g_expanIconHTML, g_collapseIconHTML; 20 var g_isDesktopViewport, g_isNotDesktopViewport, g_isCustomResponsiveViewport, g_isNotCustomResponsiveViewport; 21 var g_arrItems; 22 23 /* 24 * apply template's styles to menu item's section 25 */ 26 function setTemplateStyle(){ 27 var objLayout = jQuery(g_ucTemplateWrapperSelector+' '+g_elementorSelector); 28 var objLayoutClass = objLayout.attr('class'); 29 30 g_objWidget.addClass(objLayoutClass); 31 } 32 33 /* 34 * hide expand icon if no item section found 35 */ 36 function hideIcon(objSection){ 37 if(g_indicator.length == 0) 38 return(false); 39 40 var objSectionArrow = objSection.find(g_subArrowSelector); 41 var objSectionTitle = objSection.find(g_ucMegaMenuTitleSelector); 42 var dataClickable = objSectionTitle.data('clickable-link'); 43 44 if(dataClickable == false) 45 return(false); 46 47 if(dataClickable == true && g_dataMenuOpen == 'click') 48 objSectionArrow.hide(); 49 } 50 51 /* 52 * clone sections and append to its parent item 53 */ 54 function findSections(objSection, menuSectionParent, menuSectionItem, firstMenuSectionParent){ 55 //use clone mentod id in editor and detach method if live page 56 var clonedSectionItem; 57 58 if(g_dataEditor == 'yes') 59 clonedSectionItem = menuSectionItem.clone(); 60 61 if(g_dataEditor == 'no') 62 clonedSectionItem = menuSectionItem.detach(); 63 64 menuSectionParent.html(clonedSectionItem); 65 66 hideIcon(objSection); 67 68 var objMenuSection = menuSectionParent.children(); 69 objMenuSection.addClass(g_ucConnectedClass); 70 71 if(!objMenuSection.hasClass(g_ucConnectedClass)) 72 return(true); 73 74 setTimeout(function(){ 75 76 objMenuSection.css({ 77 'position': 'absolute', 78 'visibility': 'hidden' 79 }); 80 81 if(g_dataOpenFirst == false) 82 return(false); 83 84 var firstObjMenuSection = firstMenuSectionParent.children(); 85 86 firstObjMenuSection.css({ 87 'position': '', 88 'visibility': 'visible' 89 }); 90 91 }, 200) 92 } 93 94 /* 95 * handle section find error 96 */ 97 function showHideErrors(objSection, menuSectionId, menuSectionParent, menuSectionItem) { 98 if(g_showErrors == false) 99 return(false); 100 101 if(menuSectionItem.length > 0) 102 return(false); 103 104 var menuItemTitle = objSection.find(g_ucMegaMenuTitleSelector); 105 var menuItemTitleType = menuItemTitle.data('type'); 106 107 if(menuItemTitleType == 'link') 108 return(false); 109 110 objSection.addClass(g_sectionErrorClass); 111 menuSectionParent.addClass(g_sectionErrorClass); 112 113 menuSectionParent.html("<div class='"+g_ucSectionErrorClass+"'><div class='uc-error'>Couldn't find a section with id: '" + menuSectionId + "'</div></div>"); 114 } 115 116 /* 117 * handle debug hidden template / section 118 */ 119 function debugHiddenElements() { 120 if(g_dataEditor == 'no') 121 return(false); 122 123 //find template for debugging purposes 124 var menuTemplate = jQuery(g_ucTemplateWrapperSelector); 125 var dataDebug = g_objWidget.data("debug"); 126 127 if(dataDebug == false) 128 return(false); 129 130 menuTemplate.css({'display': ''}); 131 } 132 133 /* 134 * set dropdown element full width and position in case custom width is grater than viewport width 135 */ 136 function setFullWidth(menuSectionParent){ 137 menuSectionParent.css({ 138 'width': g_viewportWidth + 'px', 139 'top': '100%', 140 'left': - g_menuWrapOffsetLeft + 'px', 141 'transform': 'translate(0, 0)', 142 'right': 'unset' 143 }); 144 145 var menuItemParent = menuSectionParent.parents(g_ucMegaMenuListItemSelector); 146 147 //set static position to menu-item so dropdown is positioned relatively to menu-list-wrapper 148 menuItemParent.css({ 149 'position': 'static' 150 }); 151 } 152 153 /* 154 * set dropdown element position left 155 */ 156 function setScreenStartPos(menuSectionParent){ 157 menuSectionParent.css({ 158 'left': - g_menuWrapOffsetLeft + 'px', 159 'transform': 'translate(0, 0)' 160 }); 161 162 //find 'elementor' parents and set left positin css propery so mega menu section were positioned with respect to 'elementor' element 163 var objElementorParent = g_objWidget.parents(g_elementorSelector); 164 165 if(objElementorParent.length > 0){ 166 167 var elementorParentOffsetLeft = jQuery(objElementorParent[0]).offset().left; 168 169 menuSectionParent.css({ 170 'left': - g_menuWrapOffsetLeft + elementorParentOffsetLeft + 'px', 171 }); 172 } 173 } 174 175 /* 176 * set position / width 177 */ 178 function setWidthType(widthType, widthTypeFull, widthTypeCustom, customWidthNumber, menuSectionParent, each){ 179 //find 'elementor' parents and set max width property 180 var objElementorParent = g_objWidget.parents(g_elementorSelector); 181 182 if(objElementorParent.length > 0){ 183 var elementorParentWidth = jQuery(objElementorParent[0]).outerWidth(); 184 185 menuSectionParent.css({'max-width': elementorParentWidth + 'px'}); 186 } 187 188 if(widthType == widthTypeFull){ 189 setScreenStartPos(menuSectionParent); 190 menuSectionParent.css({'width': g_viewportWidth + 'px'}); 191 return(false); 192 } 193 194 if(widthType == widthTypeCustom){ 195 menuSectionParent.css({'width': customWidthNumber + 'px'}); 196 } 197 198 if(customWidthNumber == '0' || customWidthNumber == '' || customWidthNumber >= g_viewportWidth){ 199 setFullWidth(menuSectionParent); 200 }else{ 201 202 //set position relative back when dropdown again can be fully visible in the screen 203 g_objMenuItems.eq(each).css({'position': 'relative'}); 204 205 //return values that were set before change of the width to full-width 206 if (g_dataPositionX == "item_left"){ 207 menuSectionParent.css({ 208 'left': '0' 209 }); 210 } 211 212 if (g_dataPositionX == "item_right"){ 213 menuSectionParent.css({ 214 'left': 'unset', 215 'right': '0' 216 }); 217 } 218 219 if (g_dataPositionX == "item_center"){ 220 menuSectionParent.css({ 221 'left': '50%', 222 'right': 'unset' 223 }); 224 } 225 } 226 } 227 228 /* 229 * set position / width for each type of width-type 230 */ 231 function handleWidthType(){ 232 var menuItemsNumber = g_objMenuItems.length; 233 234 for (let i=0; i<menuItemsNumber; i++){ 235 var menuSectionParent = g_objMenuItems.eq(i).find(g_ucMegaMenuSectionSelector); 236 var widthType = g_arrItems[i].dropdown_width; 237 var customWidthNumber = g_arrItems[i].dropdown_width_number; 238
239 setWidthType(widthType, 'full', 'custom', customWidthNumber, menuSectionParent, i); 240 241 if(widthType == 'default'){ 242 var defaultWidthType = g_objMenuList.data('default-width-type'); 243 var defaultWidthNumber = g_objMenuList.data('default-width-number'); 244 245 setWidthType(defaultWidthType, 'default_full', 'default_custom', defaultWidthNumber, menuSectionParent, i) 246 } 247 } 248 } 249 250 /* 251 * debug items ids 252 */ 253 function showHideMenuItemsId(){ 254 var debugMenuItemsId = g_objWidget.data("items-id"); 255 256 if (debugMenuItemsId == false) 257 return(false); 258 259 var availableItemIDsListClass = "available_item_id_s_list"; 260 //show all item ids 261 g_objMenuListWrap.append("<div class='"+g_availableIDsClass+"'>Item Id's List<ul class='"+availableItemIDsListClass+"'></ul></div>"); 262 263 var objItemIdList = g_objWidget.find("."+availableItemIDsListClass); 264 var menuItemsNumber = g_objMenuItems.length; 265 266 for(let i=0; i<=menuItemsNumber-1; i++){ 267 var objMenuItem = g_objMenuItems.eq(i); 268 var objMenuItemDataId = objMenuItem.data("id"); 269 270 //if data-id attribute is empty, skip and go to next data-id 271 if(!objMenuItemDataId){ 272 continue; 273 }else{ 274 objItemIdList.append("<li>" + objMenuItemDataId + "</li>"); 275 } 276 } 277 } 278 279 /* 280 * debug elements ids 281 */ 282 function showHideElementsId(){ 283 var debugElementsId = g_objWidget.data("elements-id"); 284 285 if (debugElementsId == false) 286 return(false); 287 288 var availableSectionIDsListClass = "available_section_id_s_list"; 289 290 //show list of section's ids that can be connected to mega menu items 291 g_objMenuListWrap.append("<div class='"+g_availableIDsClass+"'>Section Id's List<ul class='"+availableSectionIDsListClass+"'></ul></div>"); 292 293 var objSectionIdList = g_objWidget.find("."+availableSectionIDsListClass); 294 var availableSections = jQuery('section'); 295 296 availableSections.each(function(){ 297 var objSectionItem = jQuery(this); 298 var objSectionItemId = objSectionItem.attr('id'); 299 var objSectionItemDisplay = objSectionItem.css('display'); 300 301 //watch only those sections that are displayed on the page 302 if(objSectionItemDisplay == 'none') 303 return(true); 304 305 //if id attribute is empty, skip and go to next id 306 if(!objSectionItemId){ 307 return(true); 308 } 309 310 //check if sections are connected to mega menu items 311 if(objSectionItem.hasClass(g_ucConnectedClass)){ 312 return(true); 313 }else{ 314 //add section's id to the list 315 objSectionIdList.append("<li>" + objSectionItemId + "</li>"); 316 } 317 }); 318 } 319 320 /* 321 * set overlay position to screen left 322 */ 323 function setOverlayPosition(activeMenuItem){ 324 var dataOverlay = g_objOverlay.data('overlay'); 325 326 if(dataOverlay == false) 327 return(false); 328 329 if(g_isCustomResponsiveViewport.matches == true || !activeMenuItem.length) 330 return(false); 331 332 var g_menuListWrapOffsetTop = g_objMenuListWrap.offset().top; 333 var g_menuListWrapOffsetHeight = g_objMenuListWrap.height(); 334 var documentOffsetHeight = jQuery(document).height(); 335 336 var g_objOverlayOffsetTop = g_menuListWrapOffsetTop + g_menuListWrapOffsetHeight; 337 var g_objOverlayOffsetHeight = documentOffsetHeight - g_objOverlayOffsetTop - g_dataOffsetY; 338 339 g_objOverlay.show(); 340 341 var dataOverlayPosition = g_objOverlay.data('overlay-position'); 342 343 g_objOverlay.css({ 344 'width': g_viewportWidth + 'px', 345 'left': - g_menuWrapOffsetLeft + 'px', 346 'transform': 'translate(0, 0)', 347 'height': g_objOverlayOffsetHeight + 'px' 348 }); 349 350 if(dataOverlayPosition == 'under') 351 return(false); 352 353 var overlayTopPosition = -g_menuListWrapOffsetTop; 354 355 g_objOverlay.css({ 356 'top': overlayTopPosition + 'px', 357 'height': documentOffsetHeight + 'px' 358 }); 359 } 360 361 /* 362 * set active disresponsive height 363 */ 364 function setDisactiveResponsiveHeight(){ 365 if(g_isNotCustomResponsiveViewport.matches == true) 366 return(false); 367 368 g_objUCMegaMenuSection.css({'height': '0px'}); 369 } 370 371 /* 372 * set disactive responsive height for parent menu item 373 */ 374 function setActiveResponsiveHeight(activeMenuItem){ 375 if(!activeMenuItem) 376 return(false); 377 378 var menuSectionActive = activeMenuItem.find(g_ucMegaMenuSectionSelector); 379 var menuSectionActiveChild = menuSectionActive.children(); 380 var menuSectionActiveHeight = menuSectionActiveChild.outerHeight(); 381 382
383 if(g_objUCMegaMenuSection.hasClass(g_ucActiveItemClass)){ 384 setDisactiveResponsiveHeight(); 385 menuSectionActive.css({'height': menuSectionActiveHeight + 'px'}); 386 }else{ 387 setDisactiveResponsiveHeight(); 388 } 389 } 390 391 /* 392 *set active menu item icon 393 */ 394 function setActiveArrow(activeItem){ 395 var indicatorActive = activeItem.find(g_subArrowSelector); 396 var objCollapseIndicator = jQuery(g_ucCollapseIndicatorSelector); 397 398 if(objCollapseIndicator.length){ 399 var objCollapseIndicatorItem = objCollapseIndicator.parents(g_ucMegaMenuListItemSelector); 400 401 objCollapseIndicatorItem.find(g_subArrowSelector).html("<span class='"+g_ucExpandIndicatorClass+"'>"+g_expanIconHTML+"</span>"); 402 } 403 404 indicatorActive.html("<span class='"+g_ucCollapseIndicatorClass+"'>"+g_collapseIconHTML+"</span>"); 405 } 406 407 /* 408 * set disactive menu item icon 409 */ 410 function setDisactiveArrow(){ 411 var objCollapseIndicator = jQuery(g_ucCollapseIndicatorSelector); 412 413 if(objCollapseIndicator.length){ 414 var objCollapseIndicatorItem = objCollapseIndicator.parents(g_ucMegaMenuListItemSelector); 415 416 objCollapseIndicatorItem.find(g_subArrowSelector).html("<span class='"+g_ucExpandIndicatorClass+"'>"+g_expanIconHTML+"</span>"); 417 } 418 } 419 420 /* 421 * set top position 100% + padding-bottom of menu-list-wrapper 422 */ 423 function setTopPosition(objElement){ 424 var activeMenuSection = objElement.find(g_ucMegaMenuSectionSelector); 425 var menuListPaddingBottom = g_objMenuList.css('padding-bottom'); 426 427 activeMenuSection.css({ 428 'top': 'calc(100% + ' + menuListPaddingBottom + ')' 429 }); 430 } 431 432 /* 433 * handle positionX option 434 */ 435 function isElementInViewportX(objElement) { 436 var activeMenuSection = objElement.find(g_ucMegaMenuSectionSelector); 437 438 if(!activeMenuSection.length) 439 return(true); 440 441 var activeMenuSectionWidth = activeMenuSection.outerWidth(); 442 var elementPositionLeft = activeMenuSection.offset().left; 443 var elementPositionRight = activeMenuSectionWidth + elementPositionLeft; 444 var isInViewport; 445 446 if (g_dataPositionX == "item_left"){ 447 var menuItemPositionLeft = objElement.offset().left; 448 var elementPositionRight = activeMenuSectionWidth + menuItemPositionLeft + g_offsetX; 449 var elementPositionLeft = activeMenuSection.offset().left; 450 451 //if dropdown width == viewportwidth + width of a scroll bar 452 if(activeMenuSectionWidth == g_viewportWidth) 453 return(true); 454 455 setTopPosition(objElement); 456 457 if(elementPositionLeft < 0){ 458 g_translateX = 0 + 'px'; 459 }else if(elementPositionRight >= g_viewportWidth){ 460 g_translateX = g_viewportWidth - elementPositionRight + g_offsetX + "px"; 461 } 462 463 isInViewport = elementPositionLeft > 0 && elementPositionRight < g_viewportWidth; 464 465 return(isInViewport); 466 } 467 468 if (g_dataPositionX == "item_right"){ 469 var menuItemPositionRight = objElement.offset().left + objElement.outerWidth(); 470 var elementPositionLeft = menuItemPositionRight - activeMenuSectionWidth + g_offsetX; 471 var elementPositionRight = activeMenuSection.offset().left + activeMenuSectionWidth; 472 473 //if dropdown width == viewportwidth + width of a scroll bar 474 if(activeMenuSectionWidth == g_viewportWidth) 475 return(true); 476 477 setTopPosition(objElement); 478 479 if(elementPositionLeft < 0){ 480 g_translateX = Math.abs(elementPositionLeft) + g_offsetX + "px"; 481 }else{ 482 g_translateX = 0 + 'px'; 483 } 484 485 isInViewport = elementPositionLeft > 0 && elementPositionLeft + g_offsetX > 0 && elementPositionRight < g_viewportWidth; 486 487 return(isInViewport); 488 } 489 490 if (g_dataPositionX == "item_center"){ 491 var menuItemPositionLeft = objElement.offset().left; 492 var objElementWidth = objElement.outerWidth(); 493 var elementPositionCenter = menuItemPositionLeft + (objElementWidth / 2); 494 var elementPositionLeft = elementPositionCenter - (activeMenuSectionWidth / 2) + g_offsetX; 495 var elementPositionRight = elementPositionCenter + (activeMenuSectionWidth / 2) + g_offsetX; 496 497 //if dropdown width == viewportwidth + width of a scroll bar 498 if(activeMenuSectionWidth == g_viewportWidth) 499 return(true); 500 501 setTopPosition(objElement); 502 503 if(elementPositionLeft < 0){ 504 g_translateX = '-' + (objElementWidth / 2) - menuItemPositionLeft + 'px'; 505 }else if(elementPositionRight > g_viewportWidth){ 506 g_translateX = 'calc(-50% + ' + (g_viewportWidth - elementPositionRight + g_offsetX) + 'px)'; 507 } 508 509 isInViewport = elementPositionLeft > 0 && elementPositionRight < g_viewportWidth; 510 511 return(isInViewport); 512 } 513 } 514 515 /* 516 * dropdown element style always visible 517 */ 518 function setCssVisiblePositionX(activeMenuSection){ 519 activeMenuSection.css({ 520 "transform": "translate(" + g_translateX + ", 0)" 521 }); 522 } 523 524 /* 525 * set dropdown element position 526 */ 527 function setVisiblePositionX(objElement){ 528 if(g_isCustomResponsiveViewport.matches == true) 529 return(false); 530 531 var activeMenuSection = objElement.find(g_ucMegaMenuSectionSelector); 532 var activeMenuSectionWidth = activeMenuSection.outerWidth(); 533 534 //if activeMenuSectionWidth is less than viewport width - return to original coordinates 535 if(activeMenuSectionWidth > g_viewportWidth) 536 return(false); 537 538 activeMenuSection.css({ 539 "transform": "translate(" + g_offsetX + "px, 0)" 540 }); 541 542 //if position_x is "item_center" than transform calculate with '-50%' 543 if (g_dataPositionX == "item_center" && activeMenuSectionWidth < g_viewportWidth){ 544 activeMenuSection.css({ 545 "transform": "translate(calc(-50% + " + g_offsetX + "px), 0)" 546 }); 547 } 548 549 if(isElementInViewportX(objElement)) 550 return(false); 551 552 //if dropdown does not fit in screen than change coordinates so it is always fully visible 553 setCssVisiblePositionX(activeMenuSection); 554 } 555 556 /* 557 * set dropdown cover element position 558 */ 559 function setCoverPosition(menuSection, menuSectionChild){ 560 if(menuSection.length == 0) 561 return(false); 562 563 if(menuSectionChild.length == 0) 564 return(false); 565 566 var objCover = menuSection.next(); 567 var menuItem = menuSectionChild.parents(g_ucMegaMenuListItemSelector); 568 var objCoverHeight = menuSectionChild.outerHeight(); 569 var objCoverWidth = menuSection.outerWidth(); 570 var menuItemWidth = menuItem.outerWidth(); 571 var menuItemOffsetLeft = menuItem.offset().left; 572 var menuSectionOffsetLeft = menuSection.offset().left; 573 var menuItemOffsetRight = menuItemOffsetLeft + menuItemWidth; 574 var menuSectionOffsetRight = menuSectionOffsetLeft + objCoverWidth; 575 576 objCover.css({ 577 'width': objCoverWidth + 'px', 578 'height': objCoverHeight + 'px' 579 }); 580 581 if (menuItemOffsetLeft == menuSectionOffsetLeft){ 582 objCover.css({ 583 'left': '0px', 584 'right': 'unset' 585 }); 586 } 587 588 if(menuItemOffsetRight == menuSectionOffsetRight){ 589 objCover.css({ 590 'left': 'unset', 591 'right': '0px' 592 }); 593 } 594 595 if (menuItemOffsetLeft > menuSectionOffsetLeft){ 596 var menuItemSectionPositionDeviation = menuItemOffsetLeft - menuSectionOffsetLeft; 597 598 objCover.css({ 599 'right': 'unset', 600 'left': - menuItemSectionPositionDeviation + 'px' 601 }); 602 } 603 604 if (menuItemOffsetLeft < menuSectionOffsetLeft){ 605 var menuItemSectionPositionDeviation = menuSectionOffsetLeft - menuItemOffsetLeft; 606 607 objCover.css({ 608 'right': 'unset', 609 'left': menuItemSectionPositionDeviation + 'px' 610 }); 611 } 612 613 if(objCoverWidth == g_viewportWidth){ 614 objCover.css({ 615 'right': 'unset', 616 'left': - g_menuWrapOffsetLeft + 'px' 617 }); 618 } 619 } 620 621 /* 622 * set active item 623 */ 624 function setActive(activeMenuItem){
625 g_objMenuItems.removeClass(g_ucActiveItemClass); 626 g_objUCMegaMenuSection.removeClass(g_ucActiveItemClass); 627 628 var activeMenuItemSection = activeMenuItem.find(g_ucMegaMenuSectionSelector); 629 630 activeMenuItem.addClass(g_ucActiveItemClass); 631 activeMenuItemSection.addClass(g_ucActiveItemClass); 632 633 // Add area-expended true/false to menu item for accesibility 634 var menuItemTitle = activeMenuItem.find(g_ucMegaMenuTitleSelector); 635 g_objMenuItems.find(g_ucMegaMenuTitleSelector).attr('aria-expanded', 'false'); 636 637 if (menuItemTitle.attr('data-type') == 'section') { 638 menuItemTitle.attr('aria-expanded', 'true'); 639 } 640 641 setTimeout(function(){ 642 activeMenuItemSection.children().css({ 643 'position': '', 644 'visibility': 'visible' 645 }); 646 },100); 647 648 //add active class to menu if menu item section has children 649 if(activeMenuItemSection.children().length){ 650 g_objWidget.addClass(g_ucMenuOpenCLass); 651 652 if(g_isCustomResponsiveViewport.matches == false){ 653 654 g_objBody.addClass(g_ucMenuOpenCLass); 655 g_objHtml.addClass(g_ucMenuOpenCLass); 656 } 657 658 }else{ 659 g_objWidget.removeClass(g_ucMenuOpenCLass); 660 g_objBody.removeClass(g_ucMenuOpenCLass); 661 g_objHtml.removeClass(g_ucMenuOpenCLass); 662 } 663 664 if(g_isCustomResponsiveViewport.matches == true){ 665 setActiveResponsiveHeight(activeMenuItem); 666 } 667 668 setVisiblePositionX(activeMenuItem); 669 handleWidthType(); 670 setTipPosition(activeMenuItemSection); 671 setOverlayPosition(activeMenuItem); 672 673 var menuSectionChild = activeMenuItemSection.children(); 674 675 setCoverPosition(activeMenuItemSection, menuSectionChild); 676 scrollToHead(activeMenuItem); 677 } 678 679 /* 680 * set disactive menu item 681 */ 682 function setDisactive(){ 683 g_objMenuItems.removeClass(g_ucActiveItemClass); 684 g_objUCMegaMenuSection.removeClass(g_ucActiveItemClass); 685 g_objMenuItems.find(g_ucMegaMenuTitleSelector).attr('aria-expanded', 'false'); 686 setDisactiveArrow(); 687 688 setTimeout(function(){ 689 g_objUCMegaMenuSection.children().css({ 690 'position': 'absolute', 691 'visibility': 'hidden' 692 }); 693 },g_dataCloseDelay); 694 695 //remove active class from menu 696 g_objWidget.removeClass(g_ucMenuOpenCLass); 697 698 if(g_isCustomResponsiveViewport.matches == false){ 699 700 g_objBody.removeClass(g_ucMenuOpenCLass); 701 g_objHtml.removeClass(g_ucMenuOpenCLass); 702 } 703 704 if(g_objOverlay.length) 705 g_objOverlay.hide(); 706 } 707 708 /* 709 * create tip 710 */ 711 function createTip(menuSectionParent){ 712 var isTipExist = menuSectionParent.data('tip'); 713 714 if(isTipExist == false) 715 return(false); 716 717 //create padding for the tip 718 if(g_dataOffsetY < 14){ 719 menuSectionParent.css({'padding-top': '14px'}) 720 }else if(g_dataOffsetY >= 14){ 721 menuSectionParent.css({'padding-top': g_dataOffsetY + 'px'}) 722 } 723 724 var objsection = menuSectionParent.find(g_ucConnectedSelector); 725 726 objsection.prepend('<div class="'+g_ueTipClass+'"></div>'); 727 728 var objErrorTip; 729 730 if(menuSectionParent.hasClass(g_sectionErrorClass)){ 731 menuSectionParent.find(g_ucSectionErrorSelector).prepend('<div class="'+g_ueTipClass+'"></div>'); 732 733 objErrorTip = menuSectionParent.find(g_ueTipSelector); 734 735 objErrorTip.css({ 736 'border-top-color': '#cccccc', 737 'border-left-color': '#cccccc' 738 }) 739 } 740 741 var objTip = menuSectionParent.find(g_ueTipSelector); 742 var menuSectionBgColor = objsection.css('background-color'); 743 var dataTipBgColor = menuSectionParent.data('bg-color'); 744 var dataTipMainColor = menuSectionParent.data('tip-color'); 745 var isMenuSectionBorderExist = parseInt(objsection.css('border-width')) > 0; 746 var menuSectionBorderColor = objsection.css('border-color'); 747 748 if(menuSectionBgColor == 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false){ 749 objTip.css({ 750 'border-top-color': dataTipBgColor, 751 'border-left-color': dataTipBgColor, 752 }); 753 } 754 755 if(isMenuSectionBorderExist == true){ 756 objTip.css({ 757 'border-top-color': menuSectionBorderColor, 758 'border-left-color': menuSectionBorderColor, 759 }); 760 } 761 762 if(menuSectionBgColor != 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false){ 763 objTip.css({ 764 'border-top-color': menuSectionBgColor, 765 'border-left-color': menuSectionBgColor, 766 }); 767 } 768 769 if(menuSectionParent.hasClass(g_sectionErrorClass)){ 770 771 objErrorTip.css({ 772 'border-top-color': '#cccccc', 773 'border-left-color': '#cccccc' 774 }) 775 } 776 777 if(dataTipMainColor != ''){ 778 objTip.css({ 779 'border-top-color': dataTipMainColor, 780 'border-left-color': dataTipMainColor, 781 }); 782 } 783 784 if(menuSectionBgColor == 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false && dataTipBgColor == '' && dataTipMainColor == ''){ 785 objTip.css({ 786 'border-top-color': '#C9C9C9', 787 'border-left-color': '#C9C9C9' 788 }); 789 } 790 } 791 792 /* 793 * set position of the tip 794 */ 795 function setTipPosition(menuSectionParent){ 796 if(menuSectionParent.length == 0) 797 return(false); 798 799 var objTip = menuSectionParent.find(g_ueTipSelector); 800 var objsection = menuSectionParent.find(g_ucConnectedSelector); 801 var menuSectionBgColor = objsection.css('background-color'); 802 var menuSectionBorderColor = objsection.css('border-color'); 803 var dataTipBgColor = menuSectionParent.data('bg-color'); 804 var dataTipMainColor = menuSectionParent.data('tip-color'); 805 var isMenuSectionBorderExist = parseInt(objsection.css('border-width')) > 0; 806 var menuItem = menuSectionParent.parents(g_ucMegaMenuListItemSelector); 807 var menuItemWidth = menuItem.width(); 808 var objTipWidth = objTip.width(); 809 var menuSectionWidth = menuSectionParent.width(); 810 var menuItemCenter = menuItemWidth / 2; 811 var menuItemOffsetLeft = menuItem.offset().left; 812 var menuSectionOffsetLeft = menuSectionParent.offset().left; 813 var menuItemOffsetRight = menuItemOffsetLeft + menuItemWidth; 814 var menuSectionOffsetRight = menuSectionOffsetLeft + menuSectionWidth; 815 var menuItemCenterOffsetLeft = menuItemOffsetLeft + menuItemCenter; 816 817 if (menuItemOffsetLeft == menuSectionOffsetLeft){ 818 objTip.css({ 819 'left': (menuItemWidth / 2) + 'px', 820 'right': 'unset' 821 }); 822 } 823 824 if(menuItemOffsetRight == menuSectionOffsetRight){ 825 objTip.css({ 826 'left': 'unset', 827 'right': (menuItemWidth / 2) + 'px' 828 }); 829 } 830 831 if (menuSectionOffsetLeft < menuItemOffsetLeft && menuSectionOffsetRight > menuItemCenterOffsetLeft + objTipWidth){ 832 //find how much menuSectionOffsetLeft is less then menuItemOffsetLeft 833 var menuItemSectionPositionDeviation = menuItemOffsetLeft - menuSectionOffsetLeft; 834 835 objTip.css({ 836 'left': menuItemSectionPositionDeviation + (menuItemWidth / 2) + 'px', 837 'right': 'unset' 838 }); 839 } 840 841 if (menuSectionOffsetLeft < menuItemOffsetLeft && menuSectionOffsetRight <= menuItemCenterOffsetLeft + objTipWidth){ 842 //find how much menuSectionOffsetLeft is less then menuItemOffsetLeft 843 var menuItemSectionPositionDeviation = menuItemOffsetLeft - menuSectionOffsetLeft; 844 845 objTip.css({ 846 'left': 'unset', 847 'right': '0px', 848 'transform': 'translate(0, -50%) rotate(0)', 849 'border-top-color': 'transparent', 850 'border-left-color': 'transparent' 851 }); 852 853 //set right border color 854 if(menuSectionBgColor == 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false){ 855 objTip.css({ 856 'border-right-color': dataTipBgColor 857 }); 858 } 859 860 if(isMenuSectionBorderExist == true){ 861 objTip.css({ 862 'border-right-color': menuSectionBorderColor 863 }); 864 } 865 866 if(menuSectionBgColor != 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false){ 867 objTip.css({ 868 'border-right-color': menuSectionBgColor 869 }); 870 } 871 872 if (menuSectionParent.hasClass(g_sectionErrorClass)){ 873 var objErrorTip = menuSectionParent.find(g_ueTipSelector); 874 875 objErrorTip.css({ 876 'border-right-color': '#cccccc', 877 }); 878 } 879 880 if(dataTipMainColor != ''){ 881 objTip.css({ 882 'border-right-color': dataTipMainColor 883 }); 884 } 885 886 if(menuSectionBgColor == 'rgba(0, 0, 0, 0)' && isMenuSectionBorderExist == false && dataTipBgColor == '' && dataTipMainColor == ''){ 887 objTip.css({ 888 'border-right-color': '#C9C9C9' 889 }); 890 } 891 } 892 893 if (menuSectionOffsetLeft > menuItemOffsetLeft && menuSectionOffsetLeft < menuItemCenterOffsetLeft - objTipWidth){ 894 //find how much menuSectionOffsetLeft is grater then menuItemOffsetLeft 895 var menuItemSectionPositionDeviation = menuSectionOffsetLeft - menuItemOffsetLeft; 896 897 objTip.css({ 898 'left': (menuItemWidth / 2) - menuItemSectionPositionDeviation + 'px', 899 'right': 'unset' 900 }); 901 } 902 903 if (menuSectionOffsetLeft > menuItemOffsetLeft && menuSectionOffsetLeft >= menuItemCenterOffsetLeft - objTipWidth){ 904 //find how much menuSectionOffsetLeft is grater then menuItemOffsetLeft 905 var menuItemSectionPositionDeviation = menuSectionOffsetLeft - menuItemOffsetLeft; 906 907 objTip.css({ 908 'left': '0px', 909 'right': 'unset', 910 'transform': 'translate(0, -50%) rotate(0)', 911 'border-top-color': 'transparent' 912 }); 913 } 914 } 915 916 /* 917 * get menu item offset top position 918 */ 919 function getScrollPos(){ 920 if(g_isNotCustomResponsiveViewport.matches == true) 921 return(false); 922 923 g_objMenuItems.each(function(){ 924 var objItem = jQuery(this); 925 var menuItemOffsetTop = objItem.offset().top; 926
927 objItem.attr('data-scrollpos', menuItemOffsetTop); 928 }); 929 } 930 931 /* 932 * check if element is in viewport 933 */ 934 function isElementInViewport(element){ 935 var elementTop = element.offset().top; 936 var viewportTop = jQuery(window).scrollTop(); 937 938 //check if beginning of the element is in viewport 939 var isInViewport = elementTop > viewportTop; 940 941 return(isInViewport); 942 } 943 944 /* 945 * scroll to head 946 */ 947 function scrollToHead(menuItem){ 948 if(g_isNotCustomResponsiveViewport.matches == true) 949 return(false); 950 951 var menuItemOffsetTop = menuItem.data('scrollpos'); 952 var menuItemSection = menuItem.find(g_ucMegaMenuSectionSelector); 953 954 //wait untill height transition is finished 955 setTimeout(function(){ 956 957 if(isElementInViewport(menuItemSection) == true) 958 return(false); 959 960 g_objMenuListWrap.animate({ 961 scrollTop: menuItemOffsetTop 962 }, 400); 963 }, 400); 964 } 965 966 /* 967 * hide arrows while animation is on 968 */ 969 function showHideArrows(){ 970 if(g_indicator.length == 0) 971 return(false); 972 973 var dataAnimation = g_indicator.data('animate-arrows') 974 975 if(dataAnimation == false) 976 return(false); 977 978 setTimeout(function(){ 979 g_indicator.css({'opacity': 1}); 980 }, 300) 981 } 982 983 /* 984 * set class to menu item title when base url matches 985 */ 986 function checkUrl(){ 987 var itemsNumber = g_objMenuItems.length; 988 989 for(let i=0; i<itemsNumber; i++){ 990 var menuItemTitle = g_objMenuItems.eq(i).find(g_ucMegaMenuTitleSelector); 991 var menuItemUrl = menuItemTitle.attr('href'); 992 993 if(menuItemUrl == g_urlBase){ 994 menuItemTitle.addClass('uc-current-page'); 995 } 996 } 997 } 998 999 /* 1000 * show | hide section in editor 1001 */ 1002 function hideSectionInEditor(menuSectionItem){ 1003 if(g_dataEditor == false) 1004 return(false); 1005 1006 if(menuSectionItem.hasClass(g_ucConnectedClass) == true) 1007 return(false); 1008 1009 var dataShowInEditor = g_objMenuList.data('show-section'); 1010 1011 if(dataShowInEditor == 'no'){ 1012 menuSectionItem.css({ 1013 'position': '', 1014 'visibility': 'visible' 1015 }); 1016 } 1017 1018 if(dataShowInEditor == 'message' || dataShowInEditor == 'hide'){ 1019 menuSectionItem.css({ 1020 'position': 'absolute', 1021 'visibility': 'hidden' 1022 }); 1023 } 1024 } 1025 1026 /* 1027 * open first item on mobile 1028 */ 1029 function openFirstItem(){ 1030 if(g_isNotCustomResponsiveViewport.matches == true) 1031 return(false); 1032 1033 var firstItem = g_objMenuItems.eq(0); 1034 var firsItemTitle = firstItem.find(g_ucMegaMenuTitleSelector); 1035 var dataFirstItemType = firsItemTitle.data('type'); 1036 var dataFirstItemClickable = firsItemTitle.data('clickable-link'); 1037 1038 if(dataFirstItemType != 'section') 1039 return(false); 1040 1041 if(dataFirstItemClickable != false) 1042 return(false); 1043 1044 if(g_dataOpenFirst == false) 1045 return(false); 1046 1047 setActive(firstItem); 1048 setActiveArrow(firstItem); 1049 } 1050 1051 /* 1052 * define item type "section" behaviour 1053 */ 1054 function handleItemTypeSection(){ 1055 var menuSectionParentItem = g_objUCMegaMenuSection.parents(g_ucMegaMenuListItemSelector); 1056 1057 menuSectionParentItem.each(function(){ 1058 var objSection = jQuery(this); 1059 var menuSectionId = objSection.data("id"); 1060 var menuSectionItem = jQuery("#" + menuSectionId); 1061 var menuSectionParent = objSection.find(g_ucMegaMenuSectionSelector); 1062 var firstMenuSectionParent = objSection.eq(0).find(g_ucMegaMenuSectionSelector); 1063 1064 setTemplateStyle(); 1065 1066 findSections(objSection, menuSectionParent, menuSectionItem, firstMenuSectionParent); 1067 1068 showHideErrors(objSection, menuSectionId, menuSectionParent, menuSectionItem); 1069 debugHiddenElements(); 1070 }); 1071 1072 handleWidthType(); 1073 showHideArrows(); 1074 1075 //set visible position of all dropdown sections and then create tip 1076 for(let i = 0; i < g_objMenuItems.length; i++){ 1077 var objMenuItem = g_objMenuItems.eq(i); 1078 var menuSection = objMenuItem.find(g_ucMegaMenuSectionSelector); 1079 var menuSectionChild = menuSection.children(); 1080 1081 setVisiblePositionX(objMenuItem); 1082 1083 createTip(menuSection); 1084 setTipPosition(menuSection); 1085 setCoverPosition(menuSection, menuSectionChild); 1086 } 1087 1088 //handle debug mode 1089 showHideMenuItemsId(); 1090 showHideElementsId(); 1091 1092 if(g_isCustomResponsiveViewport.matches == true){ 1093 g_objMenuListWrap.addClass(g_ucMobileModeClass); 1094 }else{ 1095 g_objMenuListWrap.removeClass(g_ucMobileModeClass); 1096 } 1097
1098 getScrollPos(); 1099 checkUrl(); 1100 openFirstItem(); 1101 } 1102 1103 /* 1104 * define item type "section" behaviour in editor 1105 */ 1106 function handleItemTypeSectionInEditor(){ 1107 g_objMenuItems.each(function(){ 1108 var objSection = jQuery(this); 1109 var menuSectionId = objSection.data("id"); 1110 var menuSectionItem = jQuery("#" + menuSectionId); 1111 var menuSectionParent = objSection.find(g_ucMegaMenuSectionSelector); 1112 1113 1114 showHideErrors(objSection, menuSectionId, menuSectionParent, menuSectionItem); 1115 debugHiddenElements(); 1116 1117 hideSectionInEditor(menuSectionItem) 1118 1119 }); 1120 1121 //handle debug mode 1122 showHideMenuItemsId(); 1123 showHideElementsId(); 1124 } 1125 1126 /* 1127 * handle click event 1128 */ 1129 function menuItemClick(objTitle){ 1130 var activeMenuItemClick = objTitle.parents(g_ucMegaMenuListItemSelector); 1131 1132 if(activeMenuItemClick.hasClass(g_ucActiveItemClass)){ 1133 setDisactive(); 1134 1135 if(g_isCustomResponsiveViewport.matches == true) 1136 setDisactiveResponsiveHeight(); 1137 1138 }else{ 1139 setActive(activeMenuItemClick); 1140 setActiveArrow(activeMenuItemClick); 1141 } 1142 } 1143 1144 /* 1145 * close menu when anchor link click 1146 */ 1147 function closeMenuOnAnchorClick(objTitle){ 1148 var url = objTitle.attr('href'); 1149 1150 //if not anchor do nothing 1151 if (url.indexOf("#") == -1) 1152 return(false); 1153 1154 setDisactive(); 1155 1156 if(g_isCustomResponsiveViewport.matches == false) 1157 return(false); 1158 1159 setDisactiveResponsiveHeight(); 1160 g_objMenuListWrap.removeClass(g_ucMenuOpenCLass); 1161 g_objBody.removeClass(g_ucMenuOpenCLass); 1162 g_objHtml.removeClass(g_ucMenuOpenCLass); 1163 g_objWidget.removeClass(g_ucMenuOpenCLass); 1164 } 1165 1166 /* 1167 * handle click event 1168 */ 1169 function onMenuItemClick(e){ 1170 var objTitle = jQuery(this); 1171 var isItemClickable = objTitle.data('clickable-link'); 1172 var itemType = objTitle.data('type'); 1173 1174 if (g_dataMenuOpen == 'hover'){ 1175 1176 if(g_isDesktopViewport.matches == true && g_isCustomResponsiveViewport.matches == false && itemType != 'link' && isItemClickable == false) 1177 return(false); 1178 1179 if(itemType != 'link' && isItemClickable == false){ 1180 menuItemClick(objTitle); 1181 return(false); 1182 } 1183 1184 if(g_isNotDesktopViewport.matches == true && isItemClickable == true){ 1185 var objTarget = jQuery(e.target); 1186 var objTargetParent = objTarget.parent(); 1187 1188 if(objTargetParent.hasClass(g_ucMegaMenuTitleClass) == false){ 1189 menuItemClick(objTitle); 1190 1191 return(false); 1192 } 1193 1194 if(objTargetParent.hasClass(g_ucMegaMenuTitleClass) == true) 1195 return(true) 1196 1197 } 1198 1199 if(g_isDesktopViewport.matches == true && isItemClickable == true) 1200 return(true); 1201 1202 //close menu when anchor link click 1203 if(itemType == 'link'){ 1204 closeMenuOnAnchorClick(objTitle); 1205 1206 //stop any further function execution 1207 return(true); 1208 } 1209 1210 menuItemClick(objTitle); 1211 } 1212 1213 //close menu when anchor link click 1214 if(itemType == 'link'){ 1215 closeMenuOnAnchorClick(objTitle); 1216 1217 //stop any further function execution 1218 return(true); 1219 } 1220 1221 if(g_isDesktopViewport.matches == true && isItemClickable == true) 1222 return(true); 1223 1224 if(g_isNotDesktopViewport.matches == true && isItemClickable == true){ 1225 1226 var objTarget = jQuery(e.target); 1227 var objTargetParent = objTarget.parent(); 1228 1229 if(objTargetParent.hasClass(g_ucMegaMenuTitleClass) == false){ 1230 menuItemClick(objTitle); 1231 1232 return(false); 1233 } 1234 1235 if(objTargetParent.hasClass(g_ucMegaMenuTitleClass) == true) 1236 return(true) 1237 } 1238 1239 if(isItemClickable == false) 1240 menuItemClick(objTitle); 1241 } 1242 1243 /* 1244 * handle click on body event 1245 */ 1246 function setDisactiveOnbodyClick(event){ 1247 if(g_objMenuItems.hasClass(g_ucActiveItemClass) == false) 1248 return(false); 1249 1250 if(g_isCustomResponsiveViewport.matches == true) 1251 return(false); 1252 1253 //exclude arrow indicator from this function to prevent closing dropdown after arrow click 1254 if(jQuery(event.target).hasClass(g_ucExpandIndicatorClass)) 1255 return(false); 1256 1257 if (!jQuery(event.target).closest(g_objMenuItems).length) 1258 setDisactive(); 1259 } 1260 1261 /* 1262 * handle body click event 1263 */ 1264 function bodyClick(event){ 1265 if (g_dataMenuOpen == 'hover'){ 1266 1267 if(g_isDesktopViewport.matches == true && g_isNotCustomResponsiveViewport.matches == true){ 1268 return(false); 1269 } 1270 1271 setDisactiveOnbodyClick(event); 1272 } 1273 setDisactiveOnbodyClick(event); 1274 } 1275 1276 /* 1277 * close menu on mega-menu-inner-links link-item click 1278 */ 1279 function onInnerLinkClick(){ 1280 setDisactive(); 1281 1282 if(g_isCustomResponsiveViewport.matches == true){ 1283 setDisactiveResponsiveHeight(); 1284 g_objMenuListWrap.removeClass(g_ucMenuOpenCLass); 1285 g_objBody.removeClass(g_ucMenuOpenCLass); 1286 g_objHtml.removeClass(g_ucMenuOpenCLass); 1287 g_objWidget.removeClass(g_ucMenuOpenCLass); 1288 } 1289 1290 openFirstItem(); 1291 } 1292 1293 /* 1294 * handle body click event 1295 */ 1296 function handleMenuItemClick(){ 1297 g_menuItemTitle.on("click", onMenuItemClick); 1298 1299 jQuery(document).on('click', function(event) { 1300 bodyClick(event); 1301 }); 1302 1303 } 1304 1305 /* 1306 * handle mouse enter event on menu item 1307 */ 1308 function onMenuItemMouseEnter(){ 1309 if(g_dataMenuOpen == 'click') 1310 return(false); 1311 1312 if(g_isCustomResponsiveViewport.matches == true) 1313 return(false); 1314 1315 var activeMenuItemHover = jQuery(this); 1316 1317 setActive(activeMenuItemHover); 1318 setActiveArrow(activeMenuItemHover); 1319 } 1320 1321 /* 1322 * set disactive menu item on mouseleave 1323 */ 1324 function onMenuItemMouseLeave(){ 1325 if(g_dataMenuOpen == 'click') 1326 return(false); 1327 1328 if(g_isCustomResponsiveViewport.matches == true) 1329 return(false); 1330 1331 setDisactive(); 1332 } 1333 1334 /* 1335 * handle hover event 1336 */ 1337 function handleMenuItemHover(){ 1338 g_objMenuItems.on('mouseenter', onMenuItemMouseEnter); 1339 g_objMenuListWrap.on('mouseleave', onMenuItemMouseLeave); 1340 } 1341 1342 /* 1343 * handle mega-menu-inner-links link-item click 1344 */ 1345 function handleMenuInnerLinksClick(){ 1346 g_objMenuList.on('close_mega_menu', onInnerLinkClick); 1347 } 1348 1349 /* 1350 * handle menu item open option 1351 */ 1352 function menuItemOpen(){ 1353 handleMenuItemHover(); 1354 handleMenuItemClick(); 1355 handleMenuInnerLinksClick(); 1356 } 1357 1358 /* 1359 * define responsive mode behaviour 1360 */ 1361 function onBurgerMenuClick(){ 1362 g_objMenuListWrap.addClass(g_ucMenuOpenCLass); 1363 g_objBody.addClass(g_ucMenuOpenCLass); 1364 g_objHtml.addClass(g_ucMenuOpenCLass); 1365 } 1366 1367 /* 1368 * close menu on click on the burger 1369 */ 1370 function onCloseBurgerMenuBtnClick(){
1371 g_objMenuItems.removeClass(g_ucActiveItemClass); 1372 1373 g_objUCMegaMenuSection.removeClass(g_ucActiveItemClass); 1374 setDisactiveArrow(); 1375 1376 setDisactiveResponsiveHeight(); 1377 g_objMenuListWrap.removeClass(g_ucMenuOpenCLass); 1378 g_objBody.removeClass(g_ucMenuOpenCLass); 1379 g_objHtml.removeClass(g_ucMenuOpenCLass); 1380 1381 //remove active class from menu 1382 g_objWidget.removeClass(g_ucMenuOpenCLass); 1383 1384 openFirstItem(); 1385 } 1386 1387 /* 1388 * remove from body and menu wrapper open class 1389 */ 1390 function removeOpenClass(){ 1391 if(g_objMenuListWrap.hasClass(g_ucMenuOpenCLass) == false) 1392 return(false); 1393 1394 if(g_objBody.hasClass(g_ucMenuOpenCLass) == false) 1395 return(false); 1396 1397 g_objMenuListWrap.removeClass(g_ucMenuOpenCLass); 1398 g_objBody.removeClass(g_ucMenuOpenCLass); 1399 g_objHtml.removeClass(g_ucMenuOpenCLass); 1400 } 1401 1402 /* 1403 * handle resize event 1404 */ 1405 function onWindowResize(){ 1406 var activeMenuItem = g_objWidget.find(g_ucMegaMenuListItemSelector+g_ucActiveItemSelector); 1407 1408 //set height 0 except active section when resize from desktop to mobile 1409 if(g_isCustomResponsiveViewport.matches == true){ 1410 //add responsive class to wrapper on mobile 1411 g_objMenuListWrap.addClass(g_ucMobileModeClass); 1412 1413 setActiveResponsiveHeight(activeMenuItem); 1414 1415 g_objOverlay.hide(); 1416 } 1417 1418 //remove menu / wrapper open class when breakpoint changes 1419 if(g_isNotCustomResponsiveViewport.matches == true){ 1420 removeOpenClass(); 1421 1422 //remove responsive class from wrapper 1423 g_objMenuListWrap.removeClass(g_ucMobileModeClass); 1424 1425 g_objUCMegaMenuSection.css({'height': 'unset'}); 1426 } 1427 1428 //update viewport width var on scroll 1429 g_viewportWidth = jQuery(window).width(); 1430 1431 //update left position on scroll 1432 g_menuWrapOffsetLeft = g_objMenuListWrap.offset().left; 1433 1434 handleWidthType(); 1435 1436 //set visible position of all dropdown sections / set position of the tip 1437 for(let i = 0; i < g_objMenuItems.length; i++){ 1438 1439 var objMenuItem = g_objMenuItems.eq(i); 1440 var menuSection = objMenuItem.find(g_ucMegaMenuSectionSelector); 1441 var menuSectionChild = menuSection.children(); 1442 1443 setVisiblePositionX(objMenuItem); 1444 1445 setTipPosition(menuSection); 1446 setCoverPosition(menuSection, menuSectionChild); 1447 } 1448 1449 setOverlayPosition(activeMenuItem); 1450 1451 getScrollPos(); 1452 1453 //handle sticky section bug protection 1454 setTimeout(onPageScroll,100); 1455 } 1456 1457 /* 1458 * handle scroll event for sticky section protection 1459 */ 1460 function onPageScroll(){ 1461 var objParentSticky = g_objWidget.parents('.elementor-sticky'); 1462 1463 //only if .elementor-sticky exist 1464 if(!objParentSticky.length) 1465 return(false); 1466 1467 var objActiveMenuSections = jQuery(g_ucMegaMenuSectionSelector+g_ucActiveItemSelector); 1468 var visibleMenuSectionNum = objActiveMenuSections.length; 1469 1470 //only if active menu item section exist 1471 if(!visibleMenuSectionNum) 1472 return(false); 1473 1474 //only if active menu item section number grater than 1 1475 if(visibleMenuSectionNum == 1) 1476 return(false); 1477 1478 objActiveMenuSections.each(function(index, el){ 1479 //look for index 1 only 1480 if(index == 0) 1481 return(true); 1482 1483 //hide opened section with opacity and pointer events 1484 el.style.opacity = 0; 1485 el.style.pointerEvents = 'none'; 1486 1487 if(g_isNotCustomResponsiveViewport.matches == true) 1488 return(true) 1489 1490 jQuery(this).removeClass(g_ucActiveItemClass); 1491 }); 1492 } 1493 1494 /** 1495 * find focused item and trigger event 1496 */ 1497 function findFocusedAndTrigger(e, eventToTrigger){ 1498 //look at each title item 1499 g_menuItemTitle.each(function(){ 1500 var objTitle = jQuery(this); 1501 1502 //if not focused then skip 1503 if(!objTitle.is(':focus')) 1504 return(true); 1505 1506 //if open menu type hover 1507 if(g_dataMenuOpen == 'hover') 1508 objTitle.trigger(eventToTrigger); 1509 1510 var activeMenuItemClick = objTitle.parents(g_ucMegaMenuListItemSelector); 1511 1512 //if open menu type click 1513 //if enter - check if active and open if not 1514 if(g_dataMenuOpen == 'click' && e.keyCode == 13){ 1515 1516 if(activeMenuItemClick.hasClass(g_ucActiveItemClass) == false){ 1517 setActive(activeMenuItemClick); 1518 setActiveArrow(activeMenuItemClick); 1519 } 1520 } 1521 1522 //if esc - check if active and close if opened 1523 if(g_dataMenuOpen == 'click' && e.keyCode == 27){
1524 if(activeMenuItemClick.hasClass(g_ucActiveItemClass) == false) 1525 return(true); 1526 1527 setDisactive(); 1528 } 1529 e.preventDefault(); 1530 }); 1531 } 1532 1533 /** 1534 * find focused item and trigger open 1535 */ 1536 function findFocusedAndOpen(e){ 1537 findFocusedAndTrigger(e, 'mouseenter'); 1538 } 1539 1540 /** 1541 * find focused item and trigger close 1542 */ 1543 function findFocusedAndClose(e){ 1544 findFocusedAndTrigger(e, 'mouseleave'); 1545 } 1546 1547 /** 1548 * open / close with key press 1549 */ 1550 function onKeyDown(e){ 1551 //do not listen on mobile devices 1552 if(g_isCustomResponsiveViewport.matches == true) 1553 return(true); 1554 1555 //if pressed key is enter then trigger open 1556 if(e.keyCode == 13) 1557 findFocusedAndOpen(e); 1558 1559 //if pressed key is esc then trigger close 1560 if(e.keyCode == 27) 1561 findFocusedAndClose(e); 1562 } 1563 1564 /** 1565 * protection from parent backdrop filter css property 1566 **/ 1567 function backdropFilterProtection(){ 1568 //find element with backdrop property 1569 var objElements = g_objWidget.parents('.elementor-element'); 1570 1571 if(!objElements.length) 1572 return(false); 1573 1574 //look at each element 1575 objElements.each(function(){ 1576 var objElement = jQuery(this); 1577 var objElementBackdropProperty = objElement.css('backdrop-filter'); 1578 1579 //if none then skip 1580 if(objElementBackdropProperty == 'none') 1581 return(true); 1582 1583 //if not none then set to none 1584 objElement.css('backdrop-filter', 'none'); 1585 }); 1586 } 1587 1588 /* 1589 * lord icons protection 1590 */ 1591 function lordIconsProtection(){ 1592 var objLordIcons = g_objWidget.find('lord-icon'); 1593 1594 if(!objLordIcons.length) 1595 return(false); 1596 1597 objLordIcons.each(function(){ 1598 var objIcon = jQuery(this); 1599 var srcIcon = objIcon.attr('src'); 1600 1601 objIcon.attr('src','') 1602 1603 setTimeout(function(){ 1604 objIcon.attr('src',srcIcon); 1605 },600); 1606 }); 1607 } 1608 1609 1610 /* 1611 * init menu 1612 */ 1613 this.init = function(objMegaMenu, arrItems, urlAjax, expandIconHTML, collapseIconHTML){ 1614 //init globals 1615 g_objWidget = jQuery(objMegaMenu); 1616 1617 //protection for no menu element found 1618 if(!g_objWidget.length){ 1619 console.log("Mega Menu not found"); 1620 1621 return(false); 1622 } 1623 1624 //classes 1625 g_ucTemplateWrapperClass = "uc-template-wrapper"; 1626 g_elementorClass = "elementor"; 1627 g_subArrowClass = "sub-arrow"; 1628 g_ucMegaMenuTitleClass = "uc-mega_menu_title"; 1629 g_ucConnectedClass = "uc-connected"; 1630 g_sectionErrorClass = "section-error"; 1631 g_ucSectionErrorClass = "uc-section-error"; 1632 g_ucMegaMenuListItemClass = "uc-mega_menu_list_item"; 1633 g_ucMegaMenuSectionClass = "uc-mega_menu_section"; 1634 g_availableIDsClass = "available_id_s"; 1635 g_ucCollapseIndicatorClass = "uc_collapse_indicator"; 1636 g_ucExpandIndicatorClass = "uc_expand_indicator"; 1637 g_ueTipClass = "ue-tip"; 1638 g_ucMobileModeClass = "uc-mobile-mode"; 1639 g_ucActiveItemClass = "uc-active_item"; 1640 g_ucMenuOpenCLass = "uc-menu-open"; 1641 g_ucMegaMenuWrapperClass = "uc-mega_menu-wrapper"; 1642 g_ucMegaMenuListClass = "uc-mega_menu_list"; 1643 g_ucMegaMenuOverlayClass = "uc_mega_menu_overlay"; 1644 1645 //selectors 1646 g_ucTemplateWrapperSelector = "."+g_ucTemplateWrapperClass; 1647 g_elementorSelector = "."+g_elementorClass; 1648 g_subArrowSelector = "."+g_subArrowClass; 1649 g_ucMegaMenuTitleSelector = "."+g_ucMegaMenuTitleClass; 1650 g_ucConnectedSelector = "."+g_ucConnectedClass; 1651 g_ucSectionErrorSelector = "."+g_ucSectionErrorClass; 1652 g_ucMegaMenuListItemSelector = "."+g_ucMegaMenuListItemClass; 1653 g_ucMegaMenuSectionSelector = "."+g_ucMegaMenuSectionClass; 1654 g_ucCollapseIndicatorSelector = "."+g_ucCollapseIndicatorClass; 1655 g_ueTipSelector = "."+g_ueTipClass; 1656 g_ucMobileModeSelector = "."+g_ucMobileModeSelector; 1657 g_ucActiveItemSelector = "."+g_ucActiveItemClass; 1658 g_ucMegaMenuWrapperSelector = "."+g_ucMegaMenuWrapperClass; 1659 g_ucMegaMenuListSelector = "."+g_ucMegaMenuListClass; 1660 g_ucMegaMenuOverlaySelector = "."+g_ucMegaMenuOverlayClass; 1661 1662 //objects 1663 g_objMenuItems = g_objWidget.find(g_ucMegaMenuListItemSelector); 1664 g_indicator = g_objMenuItems.find(g_subArrowSelector); 1665 g_menuItemTitle = g_objWidget.find(g_ucMegaMenuTitleSelector); 1666 g_objUCMegaMenuSection = g_objWidget.find(g_ucMegaMenuSectionSelector); 1667 g_objMenuListWrap = g_objWidget.find(g_ucMegaMenuWrapperSelector); 1668 g_objMenuList = g_objWidget.find(g_ucMegaMenuListSelector); 1669 g_objOverlay = g_objWidget.find(g_ucMegaMenuOverlaySelector); 1670 g_objBody = jQuery("body"); 1671 g_objHtml = jQuery("html"); 1672 1673 //data- attributes
1674 g_dataMenuOpen = g_objMenuList.data("menu-open"); 1675 g_dataOpenFirst = g_objMenuList.data('open-first'); 1676 g_dataOffsetY = g_objMenuList.data("offset-y"); 1677 g_dataPositionX = g_objMenuList.data("position-x"); 1678 g_dataEditor = g_objWidget.data("editor"); 1679 g_showErrors = g_objWidget.data("errors"); 1680 g_offsetX = g_objMenuList.data("offset-x"); 1681 g_dataCloseDelay = g_objMenuList.data("close-delay"); 1682 1683 var customResponsiveBreakpoint = g_objMenuListWrap.data("responsive-breakpoint"); 1684 1685 //helpers 1686 g_menuWrapOffsetLeft = g_objMenuListWrap.offset().left; 1687 g_viewportWidth = jQuery(window).width(); 1688 g_urlBase = urlAjax; 1689 g_isDesktopViewport = window.matchMedia("(min-width: 1025px)"); 1690 g_isNotDesktopViewport = window.matchMedia("(max-width: 1024px)"); 1691 g_isCustomResponsiveViewport = window.matchMedia("(max-width: " + customResponsiveBreakpoint + "px)"); 1692 g_isNotCustomResponsiveViewport = window.matchMedia("(min-width: " + (customResponsiveBreakpoint + 1) + "px)"); 1693 g_expanIconHTML = expandIconHTML; 1694 g_collapseIconHTML = collapseIconHTML; 1695 g_arrItems = arrItems; 1696 1697 //backdrop filter protection 1698 setTimeout(backdropFilterProtection, 200); 1699 1700 //remove any loader that was active 1701 var objLoaders = g_objWidget.find('.uc-mega-menu-item-loader'); 1702 1703 objLoaders.remove(); 1704 1705 //remove uc-arrow-hidden class from sub-arrows 1706 if(g_indicator.length) 1707 g_indicator.removeClass('uc-arrow-hidden'); 1708 1709 //if in editor do nothing with sections 1710 if(g_dataEditor == 'no') 1711 handleItemTypeSection(); 1712 1713 //if in editor debug sections 1714 if(g_dataEditor == 'yes') 1715 handleItemTypeSectionInEditor(); 1716 1717 var burgerMenu = g_objWidget.find(".uc-mega_menu-burger"); 1718 var closeBtn = g_objWidget.find(".uc-mega_menu-close-btn"); 1719 1720 //init events 1721 burgerMenu.on("click", onBurgerMenuClick); 1722 closeBtn.on("click", onCloseBurgerMenuBtnClick); 1723 1724 //if in editor do not open dropdown 1725 if(g_dataEditor == 'yes') 1726 return(false); 1727 1728 menuItemOpen(); 1729 1730 jQuery(window).on('resize', function(){ 1731 setTimeout(onWindowResize,100) 1732 }); 1733 1734 jQuery(window).on('scroll', function(){ 1735 setTimeout(onPageScroll,100); 1736 }); 1737 1738 g_objMenuListWrap.on('scroll', function(){ 1739 setTimeout(onPageScroll,100); 1740 }); 1741 1742 jQuery(window).on("keydown", function(e){ 1743 onKeyDown(e); 1744 }); 1745 1746 //lord icons load protection 1747 lordIconsProtection(); 1748 1749 //trigger resize after init to fix layout issue 1750 window.dispatchEvent(new Event('resize')); 1751 } 1752}
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.