1/** 2 * DokuWiki Mikio Template Javascript 3 * 4 * @link http://dokuwiki.org/template:mikio 5 * @author James Collins <james.collins@outlook.com.au> 6 * @license GPLv2 (http://www.gnu.org/licenses/gpl-2.0.html) 7 */ 8"use strict"; 9 10var mikio = { 11 queueResize: false, 12 13 ready: function() { 14 this.addToggleClick('mikio-sidebar-toggle', 'mikio-sidebar-collapse'); 15 this.addToggleClick('mikio-navbar-toggle', 'mikio-navbar-collapse'); 16 this.addDropdownClick('mikio-nav-dropdown', 'mikio-dropdown'); 17 18 window.onresize = function() { 19 if(!this.queueResize) { 20 this.queueResize = true; 21 window.setTimeout(function() { 22 this.queueResize = false; 23 Array.from(document.getElementsByClassName('mikio-dropdown')).forEach(function(elem) { 24 if(!elem.classList.contains('closed')) { 25 elem.classList.add('closed'); 26 } 27 }); 28 }, 100); 29 } 30 }; 31 32 // Mikio-Dropdown - Click 33 Array.from(document.getElementsByClassName('mikio-dropdown')).forEach(function(elem) { 34 elem.addEventListener('click', function(event) { 35 event.stopPropagation(); 36 }); 37 }); 38 39 // Mikio-Dropdown - Close when clicked outside dropdown 40 Array.from(document.getElementsByTagName('body')).forEach(function(elem) { 41 elem.addEventListener('click', function(event) { 42 Array.from(document.getElementsByClassName('mikio-dropdown')).forEach(function(elem) { 43 if(!elem.classList.contains('closed')) { 44 elem.classList.add('closed'); 45 } 46 }); 47 }); 48 }); 49 50 // Mikio-Navbar-Toggle - Fix 51 Array.from(document.getElementsByClassName('mikio-navbar-toggle')).forEach(function(elem) { 52 elem.classList.add('closed'); 53 }); 54 55 // Mikio-Dropdown - Fix 56 Array.from(document.getElementsByClassName('mikio-dropdown')).forEach(function(elem) { 57 elem.classList.add('closed'); 58 }); 59 60 // Input File - Cleanup 61 Array.from(document.querySelectorAll('input[type=file]')).forEach(function(elem) { 62 var style = window.getComputedStyle(elem); 63 64 if(style.display != 'none') { 65 var parentElem = elem.parentElement; 66 var fileRect = elem.getBoundingClientRect(); 67 var parentRect = parentElem.getBoundingClientRect(); 68 var spanElem = document.createElement('span'); 69 70 elem.style.opacity = 0; 71 parentElem.style.position = 'relative'; 72 spanElem.innerHTML = 'Choose file...'; 73 spanElem.classList.add('mikio-input-file'); 74 spanElem.style.left = Math.floor(fileRect.left - parentRect.left) + 'px'; 75 spanElem.style.width = Math.floor(fileRect.right - fileRect.left) + 'px'; 76 mikio.insertAfter(spanElem, elem); 77 78 spanElem.addEventListener('click', function(event) { 79 if(event.target.parentElement.tagName.toLowerCase() != 'label') { 80 let sibling = mikio.getPrevSibling(event.target, 'input'); 81 if(typeof sibling !== 'undefined') { 82 sibling.click(); 83 } 84 } 85 }); 86 87 elem.addEventListener('change', function() { 88 if(this.files.length > 0) { 89 let mikioInput = mikio.getNextSibling(this, '.mikio-input-file'); 90 if(typeof mikioInput !== 'undefined') { 91 mikioInput.innerHTML = this.files[0].name; 92 } 93 } 94 }); 95 } 96 }); 97 98 // Input - Span (Placeholder) clear when typing [Causing issue with some plugins - why is there here?] 99 // Array.from(document.querySelectorAll('label.block input.edit')).forEach(function(elem) { 100 // elem.addEventListener('keyup', function(event) { 101 // var sibling = mikio.getPrevSibling(event.target, 'span'); 102 103 // if(sibling) { 104 // if(event.target.value != '') { 105 // sibling.style.display = 'none'; 106 // } else { 107 // sibling.style.display = 'block'; 108 // } 109 // } 110 // }); 111 // }); 112 113 // Admin - Exit button 114 Array.from(document.querySelectorAll('a[rel="exit-admin"]')).forEach(function(elem) { 115 elem.addEventListener('click', function(event) { 116 event.preventDefault(); 117 118 var href = window.location.protocol + "//" + window.location.host + "/" + window.location.pathname; 119 120 var params = window.location.search; 121 if(params !== '') { 122 params = params.substr(1).split('&'); 123 if(params.length > 1) { 124 href += '?'; 125 params.forEach(function(p) { 126 if(p.substring(0, 3) == 'id=') { 127 href += p; 128 } 129 }); 130 } 131 } 132 133 window.location = href; 134 }); 135 }); 136 137 // Admin - Back button 138 Array.from(document.querySelectorAll('a[rel="exit-page"]')).forEach(function(elem) { 139 elem.addEventListener('click', function(event) { 140 event.preventDefault(); 141 142 var href = window.location.protocol + "//" + window.location.host + "/" + window.location.pathname; 143 144 var params = window.location.search; 145 if(params != '') { 146 params = params.substr(1).split('&'); 147 if(params.length > 1) { 148 href += '?'; 149 params.forEach(function(p) { 150 if(p.substring(0, 5) != 'page=') { 151 href += p + '&'; 152 } 153 }); 154 } 155 } 156 157 window.location = href; 158 }); 159 }); 160 161 // Admin - Resize large text blocks in tasks 162 Array.from(document.querySelectorAll('.admin_tasks span.prompt')).forEach(function(elem) { 163 if(elem.offsetHeight > 48) { 164 elem.style.fontSize = '80%'; 165 } 166 }); 167 168 // Media Manager - ui-resizable is always auto 169 var mediaChangedObserver = new MutationObserver(function(mutationsList) { 170 for(let mutation of mutationsList) { 171 if (mutation.type === 'childList') { 172 if(mutation.addedNodes) { 173 mutation.addedNodes.forEach(function(node) { 174 if(node.nodeName == 'LI') { 175 176 } 177 }); 178 } 179 } 180 181 if (mutation.type === 'attributes' && mutation.attributeName == 'style' && mutation.target && mutation.target.style.height) { 182 mutation.target.style.height = ''; 183 } 184 } 185 }); 186 187 var target = document.getElementById('mediamanager__page'); 188 if(target) { 189 mediaChangedObserver.observe(target, {attributes: true, childList: true, subtree: true}); 190 } 191 192 // Media Manager - file click 193 Array.from(document.querySelectorAll('#mediamanager__page .filelist')).forEach(function(elem) { 194 elem.addEventListener('click', function(event) { 195 var liElem = event.target.closest('li'); 196 if(liElem && event.target.closest('ul.thumbs')) { 197 var aElem = liElem.querySelector('dd.name a'); 198 if(aElem) aElem.click(); 199 } 200 }); 201 }); 202 203 // Popup Media Manager - clean file info 204 var mediaPopupFileInfoClean = function(elem) { 205 var file = {resolution: '', date: '', time: '', size: ''}; 206 207 var infoElem = elem.querySelector('span.info'); 208 if(infoElem) { 209 var infoText = infoElem.innerText.replace(/(<[^>]*>|[\(\)])/g, ''); 210 var detail = infoText.split(' '); 211 while(detail.length < 4) { 212 detail.unshift(''); 213 } 214 215 infoElem.innerHTML = detail[0] + '<br>' + detail[1] + ' ' + detail[2] + '<br>' + detail[3]; 216 } 217 218 console.log('there'); 219 Array.from(elem.querySelectorAll('img')).forEach(function(elem) { 220 elem.removeAttribute('width'); 221 elem.removeAttribute('height'); 222 }); 223 } 224 225 var mediaPopupObserver = new MutationObserver(function(mutationsList) { 226 for(let mutation of mutationsList) { 227 if (mutation.type === 'childList') { 228 if(mutation.addedNodes) { 229 mutation.addedNodes.forEach(function(node) { 230 if(node.nodeName == 'DIV') { 231 mediaPopupFileInfoClean(node); 232 } 233 }); 234 } 235 } 236 } 237 }); 238 239 var target = document.getElementById('media__content'); 240 if(target) { 241 Array.from(target.querySelectorAll('div.odd, div.even')).forEach(function(elem) { 242 mediaPopupFileInfoClean(elem); 243 }); 244 245 mediaPopupObserver.observe(target, {attributes: false, childList: true}); 246 } 247 248 if(typeof mikioFooterRun === "function") mikioFooterRun(); 249 }, 250 251 insertAfter: function(newNode, existingNode) { 252 existingNode.parentNode.insertBefore(newNode, existingNode.nextSibling); 253 }, 254 255 addToggleClick: function(elemToggle, elemCollapse) { 256 this.addEventListenerByClassName(elemToggle, 'click', function(event) { 257 event.preventDefault(); 258 event.stopPropagation(); 259 let nextSibling = mikio.getNextSibling(this, '.' + elemCollapse); 260 261 if(typeof nextSibling !== 'undefined') { 262 mikio.toggleCollapse(this, nextSibling); 263 } 264 }); 265 }, 266 267 addDropdownClick: function(elemToggle, elemCollapse) { 268 this.addEventListenerByClassName(elemToggle, 'click', function(event) { 269 event.preventDefault(); 270 event.stopPropagation(); 271 272 var dropdown = this.querySelector('.' + elemCollapse); 273 if(dropdown) { 274 mikio.toggleDropdown(dropdown); 275 } 276 }); 277 }, 278 279 addEventListenerByClassName: function(className, eventType, callback) { 280 Array.from(document.getElementsByClassName(className)).forEach(function(elem) { 281 elem.addEventListener(eventType, callback); 282 }); 283 }, 284 285 getNextSibling: function(elem, selector) { 286 var sibling = elem.nextElementSibling; 287 288 while (sibling) { 289 if (sibling.matches(selector)) return sibling; 290 sibling = sibling.nextElementSibling; 291 } 292 }, 293 294 getPrevSibling: function(elem, selector) { 295 var sibling = elem.previousElementSibling; 296 297 while (sibling) { 298 if (sibling.matches(selector)) return sibling; 299 sibling = sibling.previousElementSibling; 300 } 301 }, 302 303 toggleCollapse: function(objToggle, objCollapse) { 304 if(objToggle.classList.contains('closed')) { 305 objToggle.classList.remove('closed'); 306 var height = objCollapse.offsetHeight; 307 objCollapse.style.overflow = 'hidden'; 308 objCollapse.style.height = 0; 309 objCollapse.style.paddingTop = 0; 310 objCollapse.style.paddingBottom = 0; 311 objCollapse.style.marginTop = 0; 312 objCollapse.style.marginBottom = 0; 313 objCollapse.offsetHeight; 314 objCollapse.style.boxSizing = 'border-box'; 315 objCollapse.style.transitionProperty = "height, margin, padding"; 316 objCollapse.style.transitionDuration = '500ms'; 317 objCollapse.style.height = height + 'px'; 318 objCollapse.style.removeProperty('padding-top'); 319 objCollapse.style.removeProperty('padding-bottom'); 320 objCollapse.style.removeProperty('margin-top'); 321 objCollapse.style.removeProperty('margin-bottom'); 322 window.setTimeout(function() { 323 objCollapse.style.removeProperty('height'); 324 objCollapse.style.removeProperty('overflow'); 325 objCollapse.style.removeProperty('transition-duration'); 326 objCollapse.style.removeProperty('transition-property'); 327 objCollapse.style.removeProperty('box-sizing'); 328 }, 500); 329 } else { 330 objCollapse.style.transitionProperty = 'height, margin, padding'; 331 objCollapse.style.transitionDuration = '500ms'; 332 objCollapse.style.boxSizing = 'border-box'; 333 objCollapse.style.height = objCollapse.offsetHeight + 'px'; 334 objCollapse.offsetHeight; 335 objCollapse.style.overflow = 'hidden'; 336 objCollapse.style.height = 0; 337 objCollapse.style.paddingTop = 0; 338 objCollapse.style.paddingBottom = 0; 339 objCollapse.style.marginTop = 0; 340 objCollapse.style.marginBottom = 0; 341 window.setTimeout(function() { 342 objToggle.classList.add('closed'); 343 objCollapse.style.removeProperty('height'); 344 objCollapse.style.removeProperty('padding-top'); 345 objCollapse.style.removeProperty('padding-bottom'); 346 objCollapse.style.removeProperty('margin-top'); 347 objCollapse.style.removeProperty('margin-bottom'); 348 objCollapse.style.removeProperty('overflow'); 349 objCollapse.style.removeProperty('transition-duration'); 350 objCollapse.style.removeProperty('transition-property'); 351 objCollapse.style.removeProperty('box-sizing'); 352 }, 500); 353 } 354 }, 355 356 357 toggleDropdown: function(objToggle) { 358 if(objToggle.classList.contains('closed')) { 359 objToggle.classList.remove('closed'); 360 } else { 361 objToggle.classList.add('closed'); 362 } 363 364 Array.from(document.getElementsByClassName('mikio-dropdown')).forEach(function(elem) { 365 if(!elem.classList.contains('closed') && elem != objToggle) { 366 elem.classList.add('closed'); 367 } 368 }); 369 }, 370 371 setHeroSubTitle: function(str) { 372 Array.from(document.getElementsByClassName('mikio-hero-subtitle')).forEach(function(elem) { 373 elem.innerHTML = str; 374 }); 375 }, 376 377 setHeroImage: function(str) { 378 var heroImages = document.getElementsByClassName('mikio-hero-image'); 379 380 if(heroImages.length > 0) { 381 Array.from(document.getElementsByClassName('mikio-hero-image')).forEach(function(elem) { 382 elem.style.backgroundImage = 'url(\'' + str + '\')'; 383 elem.classList.add('mikio-hero-image-resize'); 384 }); 385 } else { 386 Array.from(document.getElementsByClassName('mikio-hero-text')).forEach(function(elem) { 387 elem.insertAdjacentHTML('afterend', '<div class="mikio-hero-image mikio-hero-image-resize" style="background-image:url(\'' + str + '\');"></div>'); 388 }); 389 } 390 }, 391 392 setHeroColor: function(str) { 393 var colors = str.trim().replace(/ +(?= )/g,'').split(/(?!\(.*)\s(?![^(]*?\))/g); 394 if(colors.length > 0 && colors[0] != '') { 395 Array.from(document.getElementsByClassName('mikio-hero')).forEach(function(elem) { 396 elem.style.backgroundColor = colors[0]; 397 }); 398 399 if(colors.length > 1) { 400 Array.from(document.getElementsByClassName('mikio-hero-title')).forEach(function(elem) { 401 elem.style.color = colors[1]; 402 }); 403 } 404 405 if(colors.length > 2) { 406 Array.from(document.getElementsByClassName('mikio-hero-subtitle')).forEach(function(elem) { 407 elem.style.color = colors[2]; 408 }); 409 } 410 411 if(colors.length > 3) { 412 Array.from(document.getElementsByClassName('mikio-hero')).forEach(function(parentElem) { 413 Array.from(parentElem.querySelectorAll('.mikio-breadcrumbs ul li a')).forEach(function(elem) { 414 elem.style.color = colors[3]; 415 }); 416 417 Array.from(parentElem.querySelectorAll('.mikio-breadcrumbs ul li, .mikio-breadcrumbs ul li a')).forEach(function(elem) { 418 elem.style.color = colors[3]; 419 elem.onmouseover = function() { this.style.color = (colors.length > 4 ? colors[4] : 'initial'); }; 420 elem.onmouseout = function() { this.style.color = colors[3]; }; 421 }); 422 }); 423 } 424 } 425 }, 426 427 setTags: function(str) { 428 Array.from(document.getElementsByClassName('mikio-tags')).forEach(function(elem) { 429 elem.innerHTML = str; 430 }); 431 } 432}; 433 434 435if(document.readyState != 'loading') { 436 mikio.ready(); 437} else { 438 document.addEventListener('DOMContentLoaded', function() { mikio.ready() }); 439} 440