/* Name: Theme Base Written by: Okler Themes - (http://www.okler.net) Theme Version: 12.0.0 */ // Theme window.theme = {}; // Theme Common Functions window.theme.fn = { getOptions(opts) { if (typeof(opts) == 'object') { return opts; } else if (typeof(opts) == 'string') { try { return JSON.parse(opts.replace(/'/g, '"').replace(';', '')); } catch (e) { return {}; } } else { return {}; } }, execPluginFunction(functionName, context) { const args = Array.prototype.slice.call(arguments, 2); const namespaces = functionName.split("."); const func = namespaces.pop(); for (let i = 0; i < namespaces.length; i++) { context = context[namespaces[i]]; } return context[func](...args); }, intObs(selector, functionName, intObsOptions, alwaysObserve) { const $el = document.querySelectorAll(selector); let intersectionObserverOptions = { rootMargin: '0px 0px 200px 0px' }; if (Object.keys(intObsOptions).length) { intersectionObserverOptions = $.extend(intersectionObserverOptions, intObsOptions); } const observer = new IntersectionObserver(entries => { for (const entry of entries) { if (entry.intersectionRatio > 0) { if (typeof functionName === 'string') { const func = Function('return ' + functionName)(); } else { const callback = functionName; callback.call($(entry.target)); } // Unobserve if (!alwaysObserve) { observer.unobserve(entry.target); } } } }, intersectionObserverOptions); $($el).each(function() { observer.observe($(this)[0]); }); }, intObsInit(selector, functionName) { const $el = document.querySelectorAll(selector); const intersectionObserverOptions = { rootMargin: '200px' }; const observer = new IntersectionObserver(entries => { for (const entry of entries) { if (entry.intersectionRatio > 0) { const $this = $(entry.target); let opts; const pluginOptions = theme.fn.getOptions($this.data('plugin-options')); if (pluginOptions) opts = pluginOptions; theme.fn.execPluginFunction(functionName, $this, opts); // Unobserve observer.unobserve(entry.target); } } }, intersectionObserverOptions); $($el).each(function() { observer.observe($(this)[0]); }); }, dynIntObsInit(selector, functionName, pluginDefaults) { const $el = document.querySelectorAll(selector); $($el).each(function() { const $this = $(this); let opts; const pluginOptions = theme.fn.getOptions($this.data('plugin-options')); if (pluginOptions) opts = pluginOptions; const mergedPluginDefaults = theme.fn.mergeOptions(pluginDefaults, opts); const intersectionObserverOptions = { rootMargin: theme.fn.getRootMargin(functionName, mergedPluginDefaults), threshold: 0 }; if (!mergedPluginDefaults.forceInit) { const observer = new IntersectionObserver(entries => { for (const entry of entries) { if (entry.intersectionRatio > 0) { theme.fn.execPluginFunction(functionName, $this, mergedPluginDefaults); // Unobserve observer.unobserve(entry.target); } } }, intersectionObserverOptions); observer.observe($this[0]); } else { theme.fn.execPluginFunction(functionName, $this, mergedPluginDefaults); } }); }, getRootMargin(plugin, {accY}) { switch (plugin) { case 'themePluginCounter': return accY ? `0px 0px ${accY}px 0px` : '0px 0px 200px 0px'; break; case 'themePluginAnimate': return accY ? `0px 0px ${accY}px 0px` : '0px 0px 200px 0px'; break; case 'themePluginIcon': return accY ? `0px 0px ${accY}px 0px` : '0px 0px 200px 0px'; break; case 'themePluginRandomImages': return accY ? `0px 0px ${accY}px 0px` : '0px 0px 200px 0px'; break; default: return '0px 0px 200px 0px'; break; } }, mergeOptions(obj1, obj2) { const obj3 = {}; for (var attrname in obj1) { obj3[attrname] = obj1[attrname]; } for (var attrname in obj2) { obj3[attrname] = obj2[attrname]; } return obj3; }, execOnceTroughEvent($el, event, callback) { const self = this, dataName = self.formatDataName(event); $($el).on(event, function() { if (!$(this).data(dataName)) { // Exec Callback Function callback.call($(this)); // Add data name $(this).data(dataName, true); // Unbind event $(this).off(event); } }); return this; }, execOnceTroughWindowEvent($el, event, callback) { const self = this, dataName = self.formatDataName(event); $($el).on(event, function() { if (!$(this).data(dataName)) { // Exec Callback Function callback(); // Add data name $(this).data(dataName, true); // Unbind event $(this).off(event); } }); return this; }, formatDataName(name) { name = name.replace('.', ''); return name; }, isElementInView($el) { const rect = $el[0].getBoundingClientRect(); return ( rect.top <= (window.innerHeight / 3) ); }, getScripts(arr, path) { const _arr = $.map(arr, scr => $.getScript((path || "") + scr)); _arr.push($.Deferred(({resolve}) => { $(resolve); })); return $.when(..._arr); }, showErrorMessage(title, content) { $('.modalThemeErrorMessage').remove(); $('body').append('
'); var modalThemeErrorMessage = document.getElementById('modalThemeErrorMessage'); var modalThemeErrorMessage = bootstrap.Modal.getOrCreateInstance(modalThemeErrorMessage); modalThemeErrorMessage.show(); } }; (((theme = {}, $) => { /* Local Environment Warning */ try { if ("file://" === location.origin) { if ($('[data-icon]').length || $('iframe').length) { theme.fn.showErrorMessage('Local Environment Warning', 'SVG Objects, Icons, YouTube and Vimeo Videos might not show correctly on local environment. For better result, please preview on a server.'); } } } catch (e) {} /* Browser Selector */ $.extend({ browserSelector() { // jQuery.browser.mobile (http://detectmobilebrowser.com/) (a => {(jQuery.browser=jQuery.browser||{}).mobile=/(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows (ce|phone)|xda|xiino/i.test(a)||/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i.test(a.substr(0,4))})(navigator.userAgent||navigator.vendor||window.opera); // Touch const hasTouch = 'ontouchstart' in window || navigator.msMaxTouchPoints; const u = navigator.userAgent, ua = u.toLowerCase(), is = t => ua.includes(t), g = 'gecko', w = 'webkit', s = 'safari', o = 'opera', h = document.documentElement, b = [(!(/opera|webtv/i.test(ua)) && /msie\s(\d)/.test(ua)) ? (`ie ie${parseFloat(navigator.appVersion.split("MSIE")[1])}`) : is('firefox/2') ? `${g} ff2` : is('firefox/3.5') ? `${g} ff3 ff3_5` : is('firefox/3') ? `${g} ff3` : is('gecko/') ? g : is('opera') ? o + (/version\/(\d+)/.test(ua) ? ` ${o}${RegExp.jQuery1}` : (/opera(\s|\/)(\d+)/.test(ua) ? ` ${o}${RegExp.jQuery2}` : '')) : is('konqueror') ? 'konqueror' : is('chrome') ? `${w} chrome` : is('iron') ? `${w} iron` : is('applewebkit/') ? `${w} ${s}${/version\/(\d+)/.test(ua) ? ` ${s}${RegExp.jQuery1}` : ''}` : is('mozilla/') ? g : '', is('j2me') ? 'mobile' : is('iphone') ? 'iphone' : is('ipod') ? 'ipod' : is('mac') ? 'mac' : is('darwin') ? 'mac' : is('webtv') ? 'webtv' : is('win') ? 'win' : is('freebsd') ? 'freebsd' : (is('x11') || is('linux')) ? 'linux' : '', 'js']; c = b.join(' '); if ($.browser.mobile) { c += ' mobile'; } if (hasTouch) { c += ' touch'; } h.className += ` ${c}`; // Edge Detect const isEdge = /Edge/.test(navigator.userAgent); if(isEdge) { $('html').removeClass('chrome').addClass('edge'); } // Dark and Boxed Compatibility if($('body').hasClass('dark')) { $('html').addClass('dark'); } if($('body').hasClass('boxed')) { $('html').addClass('boxed'); } } }); $.browserSelector(); /* Browser Workarounds */ if (/iPad|iPhone|iPod/.test(navigator.platform)) { // iPad/Iphone/iPod Hover Workaround $(document).ready($ => { $('.thumb-info').attr('onclick', 'return true'); }); } /* Tabs */ if( $('a[data-bs-toggle="tab"]').length ) { $('a[data-bs-toggle="tab"]').on('shown.bs.tab', function({target}) { const $tabPane = $($(target).attr('href')); // Carousel Refresh if($tabPane.length) { $tabPane.find('.owl-carousel').trigger('refresh.owl.carousel'); } // Change Active Class $(this).parents('.nav-tabs').find('.active').removeClass('active'); $(this).addClass('active').parent().addClass('active'); }); if( window.location.hash ) { $(window).on('load', () => { if( window.location.hash !== '*' && $( window.location.hash ).get(0) ) { new bootstrap.Tab( $('a.nav-link[href="'+ window.location.hash +'"]:not([data-hash])')[0] ).show(); } }); } } /* On Load Scroll */ if( !$('html').hasClass('disable-onload-scroll') && window.location.hash && !['#*'].includes( window.location.hash ) ) { window.scrollTo(0, 0); $(window).on('load', () => { setTimeout(() => { const target = window.location.hash; let offset = ( $(window).width() < 768 ) ? 180 : 90; if (!$(target).length) { return; } if ( $("a[href$='" + window.location.hash + "']").is('[data-hash-offset]') ) { offset = parseInt( $("a[href$='" + window.location.hash + "']").first().attr('data-hash-offset') ); } else if ( $("html").is('[data-hash-offset]') ) { offset = parseInt( $("html").attr('data-hash-offset') ); } if (isNaN(offset)) { offset = 0; } $('body').addClass('scrolling'); $('html, body').animate({ scrollTop: $(target).offset().top - offset }, 600, 'easeOutQuad', () => { $('body').removeClass('scrolling'); }); }, 1); }); } /* * Text Rotator */ $.fn.extend({ textRotator(options) { const defaults = { fadeSpeed: 500, pauseSpeed: 100, child: null }; var options = $.extend(defaults, options); return this.each(function() { const o = options; const obj = $(this); const items = $(obj.children(), obj); items.each(function() { $(this).hide(); }) if (!o.child) { var next = $(obj).children(':first'); } else { var next = o.child; } $(next).fadeIn(o.fadeSpeed, () => { $(next).delay(o.pauseSpeed).fadeOut(o.fadeSpeed, function() { let next = $(this).next(); if (next.length == 0) { next = $(obj).children(':first'); } $(obj).textRotator({ child: next, fadeSpeed: o.fadeSpeed, pauseSpeed: o.pauseSpeed }); }) }); }); } }); /* * Notice Top bar */ const $noticeTopBar = { $wrapper: $('.notice-top-bar'), $closeBtn: $('.notice-top-bar-close'), $header: $('#header'), $body: $('.body'), init() { const self = this; if( !$.cookie('portoNoticeTopBarClose') ) { self .build() .events(); } else { self.$wrapper.parent().prepend( '' ); self.$wrapper.remove(); } return this; }, build() { const self = this; $(window).on('load', () => { setTimeout(() => { self.$body.css({ 'margin-top': self.$wrapper.outerHeight(), 'transition': 'ease margin 300ms' }); $('#noticeTopBarContent').textRotator({ fadeSpeed: 500, pauseSpeed: 5000 }); if( ['absolute', 'fixed'].includes( self.$header.css('position') ) ) { self.$header.css({ 'top': self.$wrapper.outerHeight(), 'transition': 'ease top 300ms' }); } $(window).trigger('notice.top.bar.opened'); }, 1000); }); return this; }, events() { const self = this; self.$closeBtn.on('click', e => { e.preventDefault(); self.$body.animate({ 'margin-top': 0, }, 300, () => { self.$wrapper.remove(); self.saveCookie(); }); if( ['absolute', 'fixed'].includes( self.$header.css('position') ) ) { self.$header.animate({ top: 0 }, 300); } // When header has shrink effect if( self.$header.hasClass('header-effect-shrink') ) { self.$header.find('.header-body').animate({ top: 0 }, 300); } $(window).trigger('notice.top.bar.closed'); }); return this; }, checkCookie() { const self = this; if( $.cookie('portoNoticeTopBarClose') ) { return true; } else { return false; } return this; }, saveCookie() { const self = this; $.cookie('portoNoticeTopBarClose', true); return this; } }; if( $('.notice-top-bar').length ) { $noticeTopBar.init(); } /* * Image Hotspots */ if( $('.image-hotspot').length ) { $('.image-hotspot') .append('') .append(''); } /* * Reading Progress */ if( $('.progress-reading').length ) { function updateScrollProgress() { const pixels = $(document).scrollTop(); pageHeight = $(document).height() - $(window).height() progress = 100 * pixels / pageHeight; $('.progress-reading .progress-bar').width(parseInt(progress) + "%"); } $(document).on('scroll ready', () => { updateScrollProgress(); }); $(document).ready(() => { $(window).afterResize(() => { updateScrollProgress(); }); }); } /* * Page Transition */ if( $('body[data-plugin-page-transition]').length ) { let link_click = false; $(document).on('click', 'a', function(e){ link_click = $(this); }); $(window).on("beforeunload", e => { if( typeof link_click === 'object' ) { const href = link_click.attr('href'); if( href.indexOf('mailto:') != 0 && href.indexOf('tel:') != 0 && !link_click.data('rm-from-transition') ) { $('body').addClass('page-transition-active'); } } }); $(window).on("pageshow", ({persisted, originalEvent}) => { if( persisted || originalEvent.persisted) { if( $('html').hasClass('safari') ) { window.location.reload(); } $('body').removeClass('page-transition-active'); } }); } /* * Clone Element */ if( $('[data-clone-element]').length ) { $('[data-clone-element]').each(function() { const $el = $(this), content = $el.html(), qty = $el.attr('data-clone-element'); for (let i = 0; i < qty; i++) { $el.html($el.html() + content); } }); } if( $('[data-clone-element-to]').length ) { $('[data-clone-element-to]').each(function() { const $el = $(this); const content = $el.html(); const $to = $($el.attr('data-clone-element-to')); $to.html($to.html() + content); }); } /* * Thumb Info Floating Caption */ $('.thumb-info-floating-caption').each(function() { $(this) .addClass('thumb-info-floating-element-wrapper') .append( ''+ $(this).data('title') +'' ); if( $(this).data('type') ) { $('.thumb-info-floating-caption-title', $(this)) .append( '