/* ** ** ** ** ** JPG.js ** ** a lightweight vanilla js library ** ** ** ** */ console.dir('= jpg.js initialized ='); /*====================================== = PRIMARY OBJECT = ======================================*/ let JPG = {}; // JPG! JPG.util = {}, // Utility functions; contained here JPG.fns = {}, // App functions; contained in library.js JPG.vars = {}, // Transient variables JPG.user = {}; // User specific data JPG.util.regex = []; // Regex array JPG.vars.ua = window.navigator.userAgent; // User agent from window JPG.vars.platform = window.navigator.platform; // User platform from window JPG.vars.ms; // MS browser boolean JPG.user.ua; // User agent JPG.user.os; // User OS JPG.user.mobile; // Mobile boolean /*============================================= = JPG UTILITY FUNCTIONS = =============================================*/ // DOM element selector JPG.util.EL = (el) => { switch (el.slice(0, 1)) { case '#': JPG.vars.$el = document.getElementById(el.slice(1, el.length)); break; case '.': JPG.vars.$el = document.getElementsByClassName(el.slice(1, el.length)); break; default: JPG.vars.$el = document.getElementsByTagName(el); break; } return JPG.vars.$el; }; // Add class to element JPG.util.addClass = (el, className, delay) => { setTimeout(function () { if (document.body.classList) { el.classList.add(className); } else { el.className += ' ' + className; } }, delay || 0); }; // Remove class from element JPG.util.removeClass = (el, className, delay) => { setTimeout(function () { if (document.body.classList) { el.classList.remove(className); } else { el.className = el.className.replace(' ' + className, ''); } }, delay || 0); }; // Forward/backward lookup regex JPG.util.regex[0] = /(\d)(?=(\d{3})+(?!\d))/g; JPG.util.regex[1] = /\B(?=(\d{3})+(?!\d))/g; // Number formatter, US standard 3 digit ',' w/ $USD option JPG.util.numFormat = (num, currencySymbol) => { Number.prototype.format = function () { return this.toString().replace(JPG.util.regex[0], "$1,"); }; // OPTIONAL: $ formatting if (currencySymbol == true) { return '$' + num.format(); } else { return num.format(); } }; // Random number generator, mutable JPG.util.randomNumber = (limit, limiter) => { // limiter = 0 for arrays, 1 for standard, n for custom return Math.floor( (Math.random() * limit) + limiter ); }; // Quick Sort algorithm JPG.util.quickSort = (data) => { // If only 1 piece of data, return that if (data.length < 2) { return data; } // Declare first value as pivot and the left/right temp arrays let pivot = data[0], left = [], right = []; // Lump sort > / < value to pivot for (let i = 1; i < data.length; i++) { if (data[i] < pivot) { left.push(data[i]); } else { right.push(data[i]); } } // Recursively sort left of pivot and right of pivot using spread operator return [ ...JPG.util.quickSort(left), pivot, ...JPG.util.quickSort(right) ]; }; // Detect User Agent JPG.util.detectUserAgent = () => { let msie = JPG.vars.ua.indexOf('MSIE '), trident = JPG.vars.ua.indexOf('Trident/'); // Boolean for MS browser (msie > 0 || trident > 0) ? JPG.vars.ms = true : JPG.vars.ms = false; // Temporary JPG.user.ua = JPG.vars.ua; console.dir('USER AGENT: ' + JPG.user.ua); }; // Detect OS JPG.util.detectPlatform = () => { let macosPlatforms = ['Macintosh', 'MacIntel', 'MacPPC', 'Mac68K'], windowsPlatforms = ['Win32', 'Win64', 'Windows', 'WinCE'], iosPlatforms = ['iPhone', 'iPad', 'iPod']; // Check for platform if (macosPlatforms.indexOf(JPG.vars.platform) !== -1) { JPG.user.os = 'Mac OS'; } else if (iosPlatforms.indexOf(JPG.vars.platform) !== -1) { JPG.user.os = 'iOS'; } else if (windowsPlatforms.indexOf(JPG.vars.platform) !== -1) { JPG.user.os = 'Windows'; } else if (/Android/.test(JPG.vars.ua)) { JPG.user.os = 'Android'; } else if (!JPG.user.os && /Linux/.test(JPG.vars.platform)) { JPG.user.os = 'Linux'; } console.dir('OPERATING SYSTEM: ' + JPG.user.os); }; // Detect Mobile, returns boolean JPG.util.detectMobileTablet = () => { JPG.user.mobile = (typeof window.orientation !== "undefined") || (navigator.userAgent.indexOf('IEMobile') !== -1); }; // Page reload JPG.util.reloadPage = () => { window.location.reload(); }; // String truncator JPG.util.truncateString = (text, textLength) => { if (text.length > textLength) { return text.substring(0, textLength) + '...'; } else { return text; } }; // Fake page destruction JPG.util.destroyPage = (bgColor) => { let all = document.querySelectorAll('body *:not(script):not(style):not(link)'); document.querySelector('html').style.background = bgColor; document.querySelector('body').style.background = bgColor; document.querySelector('body').style.overflow = 'hidden'; for (let el of all) { let dur = (Math.random() * 3 + 1).toFixed(3), del = Math.round(Math.random() * 3000 + 1); el.style.transition = 'transform ' + dur + 's'; setTimeout( () => { el.style.transform += ' translateY(100vh)'; }, del ); } }; // Node, array, or string includes a child or value JPG.util.has = (input, n, strict, inputPosition) => { /* * input: Parent node || array || string * n: Child node || value * strict: true || false, init false * inputPosition: number (starting position), init 0 */ // If value inits null, return and log if (input == null || n == null) { console.dir('JPG.util.has: input || n is null'); return; } // Strict check if (!strict && n.nodeType < 1) { // strict === false || undefined input = input.toLowerCase(); n = n.toLowerCase(); } // Array, String, DOM Element check if (Array.isArray(input) == true && typeof input == 'object') { console.dir('JPG.util.has: array'); return input.includes(n); // output: true || false } else if (typeof input == 'string' || typeof input == 'number') { console.dir('JPG.util.has: string'); return input.includes(n, inputPosition); // output: true || false } else if (n.nodeType > 0) { console.dir('JPG.util.has: DOM element'); return input.contains(n); // output: true || false } else { throw 'JPG.util.has: else'; return; } }; // Returns array with all elements JPG.util.siblings = (element, filterEl, script) => { /* * element: node to search for siblings * filterEl: only return elements that match this * script: init false, if true will omit script tags as children */ let siblings = []; // Filter function function filterWillOnlyReturnThis(element, filteredEl) { return element.nodeName.toLowerCase() == filteredEl; }; // Sets up the algorithm sequentially element = element.parentNode.firstChild; // Do and when while becomes false quit do { if ( !filterEl || filterWillOnlyReturnThis(element, filterEl) ) { // filterEl == undefined || filtering for element if (!script) { // script == undefined || null || false if (element.nodeType === 1) { siblings.push(element); } } else { // script == true if (element.nodeType === 1 && element.nodeName != 'SCRIPT') { siblings.push(element); } } } } while (element = element.nextSibling); return siblings; }; // AJAX utility JPG.util.ajax = (element, requestType, filePath, formDataElement, outputElement) => { let oData; // In case of form data let xhr = new XMLHttpRequest(); if (!formDataElement) { // GET xhr.onreadystatechange = function () { if (this.readyState == 4 && this.status == 200) { JPG.util.EL(element).innerHTML = this.responseText; } }; xhr.open(requestType, filePath, true); // xhr.setRequestHeader('Content-type', 'text/html'); // OPTIONAL: If type is atypical. Content-type is for files. xhr.send(); } else { // POST, Form oData = new FormData(JPG.util.EL(element)); xhr.onload = function () { if (this.status == 200) { JPG.util.EL(outputElement).innerHTML = this.responseText; } }; xhr.open(requestType, filePath, true); xhr.send(oData); } }; console.dir('= jpg.js successfully loaded =');