Last active
October 7, 2024 13:54
-
-
Save emrecamasuvi/e3dfe86b898f3def7298 to your computer and use it in GitHub Desktop.
#js #javascript #snippets
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// random numbergenerator between 0 and 1 | |
var randomNum = Math.floor(Math.random() * 2); | |
// insert html | |
export const insertHTML = (el, html) => el.insertAdjacentHTML("afterbegin", html); | |
export const replaceHTML = (el, html) => { | |
el.replaceChildren(); | |
insertHTML(el, html); | |
}; | |
// same memoize function from before | |
const memoize = (fn) => { | |
let cache = {}; | |
return (...args) => { | |
let n = args[0]; | |
if (n in cache) { | |
console.log('Fetching from cache', n); | |
return cache[n]; | |
} | |
else { | |
console.log('Calculating result', n); | |
let result = fn(n); | |
cache[n] = result; | |
return result; | |
} | |
} | |
} | |
const factorial = memoize( | |
(x) => { | |
if (x === 0) { | |
return 1; | |
} | |
else { | |
return x * factorial(x - 1); | |
} | |
} | |
); | |
console.log(factorial(5)); // calculated | |
console.log(factorial(6)); // calculated for 6 and cached for 5 | |
// hack: split/join with zero-width-space is used to disable | |
// chrome's "intelligent" autofill from attempting to fill | |
// credit card and email details in the identification fields | |
`xxx`.split('').join('​') | |
// date ISO 8601 Extended format `YYYY-MM-DDTHH:mm:ss:sssZ` | |
new Date('2019-06-11T00:00') // dont use like this | |
// OR BETTER ==> 11th June 2019, 5:23:59am, Local Time | |
new Date(2019, 5, 13, 5, 23, 59) // beware month zero indexed | |
// can convert to utc | |
new Date(Date.UTC(2019, 5, 13, 5, 23, 59)) | |
// getDay: Gets day of the week (0-6) according to local time. Day of the week begins with Sunday (0) and ends with Saturday (6). | |
// memoize | |
function memoize (fn) { | |
const cache = {}; | |
return function () { | |
var key = Array.prototype.slice.call(arguments).join('-'); | |
if (cache[key]) { | |
return cache[key]; | |
} | |
cache[key] = fn.apply(this, arguments) | |
return cache[key]; | |
}; | |
} | |
// async await best use case | |
const checkLogin = async () => { | |
if(userIsLoggedIn) { | |
await apiCall(); | |
} | |
deleteSession(); | |
}; | |
// A Promise with a timeout | |
// Beware though that any other error that may occur in apiCall will also go to the .catch handler, so you need to be able to determine if the error is the timeout or an actual error. | |
const apiCall = url => fetch(url); | |
const timeout = time => { | |
return new Promise((resolve, reject) => { | |
setTimeout(() => reject('Promise timed out'), time); | |
}); | |
}; | |
Promise.race([apiCall(url), timeout(1000)]) | |
.then(response => { | |
// response from apiCall was successful | |
}) | |
.catch(err => { | |
// handle the timeout | |
}); | |
// intersection observer | |
makeProductButtonsStickyOnMobile() { | |
if (!('IntersectionObserver' in window)) { | |
return | |
} | |
const anchorDomElForTriggering = document.querySelector('[data-context="product-tile"]') | |
const productTilesWrapper = document.querySelector('[data-context="checkout-standard-products-sp2"]') | |
var intersectionObserver = new IntersectionObserver( | |
(entries) => { | |
const method = entries[0].intersectionRatio <= 0 ? 'remove' : 'add' | |
productTilesWrapper.classList[method]('productTiles--sticky-on-mobile') | |
}, | |
{ | |
root: null, | |
threshold: [0.0, 1.0], | |
} | |
) | |
intersectionObserver.observe(anchorDomElForTriggering) | |
} | |
// random ID generator by seconds lol | |
(+new Date() + Math.floor(Math.random() * 999999)).toString(36); | |
// module pattern #1 | |
var MyThingy = (function() { | |
function doSomethingCool() { | |
console.log("cool"); | |
} | |
function internalSomething() { | |
console.log("internal"); | |
} | |
function anotherNiftyThing() { | |
// Note that within the scoping function, functions can | |
// call each other direct. | |
doSomethingCool(); | |
internalSomething(); | |
} | |
return { | |
doSomethingCool: doSomethingCool, | |
anotherNiftyThing: anotherNiftyThing | |
}; | |
})(); | |
// module pattern #2.1 | |
var MODULE = (function() { | |
var my = {}, | |
privateVariable = 1; | |
function privateMethod() { | |
// ... | |
} | |
my.moduleProperty = 1; | |
my.moduleMethod = function() { | |
// ... | |
}; | |
return my; | |
})(); | |
// module pattern #2.2 | |
var MODULE = (function(my) { | |
my.anotherMethod = function() { | |
// added method... | |
}; | |
return my; | |
})(MODULE); | |
// dom manipulation | |
var frag = document.createDocumentFragment(); | |
var myDiv = document.createElement("div"); | |
var im = document.createElement("img"); | |
im.src = "im.gif"; | |
myDiv.id = "myDiv"; | |
myDiv.appendChild(im); | |
frag.appendChild(myDiv); | |
/* append */ document.body.appendChild(frag); | |
/* prepend */ document.body.insertBefore(frag, document.body.firstChild); | |
// dom manipulation 2 (better?) | |
var p, t, frag; | |
frag = document.createDocumentFragment(); | |
p = document.createElement("p"); | |
t = document.createTextNode("first paragraph"); | |
p.appendChild(t); | |
frag.appendChild(p); | |
document.body.appendChild(frag); | |
var text = "link to camasuvi"; | |
var url = "http://www.camasuvi.net"; | |
text.link(url); // outputs: <a href="http://www.camasuvi.net">link to camasuvi</a> | |
var textToBeReplaced = document.createTextNode("xxx"); | |
imageToBeChanged.parentNode.replaceChild(textToBeReplaced, imageToBeChanged); | |
// most efficient text replacement (dont use parent.innerHTML) | |
// h1.textContent = data.title | |
parent.firstChild.nodeValue = "xxx"; | |
parent.firstChild.data = "yyy"; | |
// Use the template tag to create HTML templates and appendChild to insert new HTML | |
```html | |
<template id="card_template"> | |
<article class="card"> | |
<h3></h3> | |
<div class="card__body"> | |
<div class='card__body__image'></div> | |
<section class='card__body__content'> | |
</section> | |
</div> | |
</article> | |
</template> | |
``` | |
and | |
```javascript | |
function createCardElement(title, body) { | |
const template = document.getElementById('card_template'); | |
const element = template.content.cloneNode(true).firstElementChild; | |
const [cardTitle] = element.getElementsByTagName("h3"); | |
const [cardBody] = element.getElementsByTagName("section"); | |
[cardTitle.textContent, cardBody.textContent] = [title, body]; | |
return element; | |
} | |
container.appendChild(createCardElement( | |
"Frontend System Design: Fundamentals", | |
"This is a random content" | |
)) | |
``` | |
// Use createDocumentFragment with appendChild to Batch Inserts | |
```javascript | |
const fragment = document.createDocumentFragment(); | |
for (let i = 0; i < 1000; i++) { | |
const li = document.createElement('li'); | |
li.textContent = `Item ${i}`; | |
fragment.appendChild(li); | |
} | |
document.getElementById('myList').appendChild(fragment); | |
``` | |
// Associate data to DOM nodes with WeakMap | |
```javascript | |
let DOMdata = { 'logo': 'Frontend Masters' }; | |
let DOMmap = new WeakMap(); | |
let el = document.querySelector(".FmLogo"); | |
DOMmap.set(el, DOMdata); | |
console.log(DOMmap.get(el)); // { 'logo': 'Frontend Masters' } | |
el.remove(); // DOMdata is able to be garbage collected | |
``` | |
// get content from script and serve it to html | |
hamburgerMenuEvents() { | |
const domEl = document.getElementById("js-hook-for-hamburger-menu-toggle"); | |
const modalScript = document.getElementById("js-hook-for-header-modal"); | |
const modalHtml = modalScript.innerHTML; | |
domEl.addEventListener('click', () => { | |
const newModalEl = document.getElementById("js-hook-for-hamburger-menu-toggle-wrapped"); | |
if (!newModalEl) { | |
let element = this.createDomElement(modalHtml); | |
element = element.firstChild; | |
element.id = 'js-hook-for-hamburger-menu-toggle-wrapped'; | |
document.body.appendChild(element); | |
} | |
}); | |
} | |
createDomElement(content) { | |
let d, frag; | |
d = document.createElement('div'); | |
frag = document.createDocumentFragment(); | |
d.innerHTML = content; | |
frag.appendChild(d); | |
return frag; | |
} | |
sanitizer(str) { | |
var tmp = document.createElement('div'); | |
tmp.textContent = str; | |
return tmp.innerHTML; | |
} | |
// Shuffle an array of numbers | |
var numbers = [5, 458, 120, -215, 228, 400, 122205, -85411]; | |
numbers = numbers.sort(function() { | |
return Math.random() - 0.5; | |
}); | |
// Verify that a given argument is a number | |
function isNumber(n) { | |
return !isNaN(parseFloat(n)) && isFinite(n); | |
} | |
// Get the max or the min in an array of numbers | |
var numbers = [5, 458, 120, -215, 228, 400, 122205, -85411]; | |
var maxInNumbers = Math.max.apply(Math, numbers); | |
var minInNumbers = Math.min.apply(Math, numbers); | |
// return color hex code | |
"#" + (~~(Math.random() * (1 << 24))).toString(16); | |
"#" + Math.floor(Math.random() * 16777215).toString(16); | |
// sort numbers in arr | |
function compareCanonically(a, b) { | |
return a < b ? -1 : a > b ? 1 : 0; | |
} | |
[-1, -20, 7, 50].sort(compareCanonically); // [ -20, -1, 7, 50 ] | |
// credits to davidwalsh blog | |
function debounce(func, wait, immediate) { | |
var timeout; | |
return function() { | |
var context = this, | |
args = arguments; | |
var later = function() { | |
timeout = null; | |
if (!immediate) func.apply(context, args); | |
}; | |
var callNow = immediate && !timeout; | |
clearTimeout(timeout); | |
timeout = setTimeout(later, wait); | |
if (callNow) func.apply(context, args); | |
}; | |
} | |
var myEfficientFn = debounce(function() { | |
// All the taxing stuff you do | |
}, 250); | |
window.addEventListener("resize", myEfficientFn); | |
// credits to davidwalsh blog | |
// once helper func to ensure a given function can only be called once | |
function once(fn, context) { | |
var result; | |
return function() { | |
if (fn) { | |
result = fn.apply(context || this, arguments); | |
fn = null; | |
} | |
return result; | |
}; | |
} | |
// once Usage | |
var canOnlyFireOnce = once(function() { | |
console.log("Fired!"); | |
}); | |
canOnlyFireOnce(); // "Fired!" | |
canOnlyFireOnce(); // nada | |
// dom clone work | |
var oldnode = document.getElementById("result"), | |
clone = oldnode.cloneNode(true); | |
// work with the clone... | |
// when you're done: | |
oldnode.parentNode.replaceChild(clone, oldnode); | |
// reduce | |
bigData.reduce(function(acc, value) { | |
if (value % 2 === 0) { | |
acc.push(value * 2); | |
} | |
return acc; | |
}, []); | |
// angular debug helpers | |
$($0) || angular.element($0); | |
$($0).scope(); | |
$($0).scope().$parent; | |
$($0).isolateScope(); //for directive scopes | |
// run $($0).scope().isFoo = true to set isFoo | |
// run $($0).scope().$digest() | |
// credits to http://eng.localytics.com/tips-and-tricks-for-debugging-unfamiliar-angularjs-code/ | |
/** | |
* copied from lodash | |
* | |
* @private | |
* @param {Object} source The object to copy properties from. | |
* @param {Array} props The property names to copy. | |
* @param {Object} [object={}] The object to copy properties to. | |
* @param {Function} [customizer] The function to customize copied values. | |
* @returns {Object} Returns `object`. | |
*/ | |
function copyObjectWith(source, props, object, customizer) {} | |
// TSDoc style comment | |
export class Statistics { | |
/** | |
* Returns the average of two numbers. | |
* | |
* @remarks | |
* This method is part of the {@link core-library#Statistics | Statistics subsystem}. | |
* | |
* @param x - The first input number | |
* @param y - The second input number | |
* @returns The arithmetic mean of `x` and `y` | |
* | |
* @beta | |
*/ | |
} | |
// ES6 | |
function foo(bar = 2) {} | |
function foo({ a = 1, b = 2 } = {}) {} | |
function sum(left = 1, right = 2) { | |
return left + right; | |
} //sum()=3, sum(6)=8 | |
function concat() { | |
return Array.prototype.slice.call(arguments).join(" "); | |
} | |
/* becomes better with "...rest operator" arraylike to array */ | |
function concat(...words) { | |
return words.join(" "); | |
} | |
// spread operator | |
let cities = ["San Francisco", "Los Angeles"]; | |
let places = ["Miami", ...cities, "Chicago"]; // ['Miami', 'San Francisco', 'Los Angeles', 'Chicago'] | |
// Instance methods | |
// new Foo().bar /* should be */ class Foo { bar () {} } | |
// Static methods | |
// Foo.isPonyFoo() /* should be */ { static isPonyFoo () {} } | |
// ES6+ | |
users.find(function(o) { | |
return o.age < 40; | |
}); | |
users.findIndex(function(o) { | |
return o.age >= 40; | |
}); | |
array.includes(124); // boolean | |
"food".includes("foo"); // boolean | |
"abc".repeat(2); // "abcabc" | |
Number.isNaN(42 / "x"); //boolean | |
Object.is(NaN, NaN); //boolean true | |
Object.is(0, -0); //boolean true | |
// Repeat a string | |
document.write("Hello ".repeat(3) + "<br />"); | |
// Does a string start with a value | |
const myName = "Emre"; | |
myName.startsWith("Em"); | |
myName.endsWith("re"); | |
myName.includes("mre"); | |
// Rest parameters, which are preceeded by `...` become an array | |
// You can only have 1 rest parameter and it must be defined last | |
function getSumMore(...vals) { | |
let sum = 0; | |
for (let i = 0, len = vals.length; i < len; i++) { | |
sum += vals[i]; | |
} | |
document.write(`The sum is ${sum}<br />`); | |
} | |
getSumMore(1, 2, 3, 4); | |
// You create object literals like this | |
function createAnimal(name, owner) { | |
return { | |
// Properties | |
name, | |
owner, | |
// Create a method | |
getInfo() { | |
return `${this.name} is owned by ${this.owner}`; | |
}, | |
// Objects can contain other objects | |
address: { | |
street: "123 Main St", | |
city: "Pittsburgh" | |
} | |
}; | |
} | |
var spot = createAnimal("Spot", "Doug"); | |
document.write(`${Object.getOwnPropertyNames(spot).join(" ")} <br />`); | |
// A Symbol is like an enumerated type that can be used as | |
// identifiers and they can't be changed (immutable). | |
// Create a symbol that is used like a label in an array | |
// You can provide a description in quotes | |
let capital = Symbol("State Capital"); | |
let pennsylvania = {}; | |
pennsylvania[capital] = "Harrisburg"; | |
document.write(`Capital of PA : ${pennsylvania[capital]}<br />`); | |
// Get the description | |
document.write(`Symbol Capital : ${capital.toString()}<br />`); | |
// You can share symbols by using symbol.for() | |
let employNum = Symbol.for("Employee Number"); | |
let bobSmith = {}; | |
bobSmith[employNum] = 10; | |
let sallyMarks = {}; | |
sallyMarks[employNum] = 11; | |
document.write(`Bob : ${bobSmith[employNum]}<br />`); | |
document.write(`Sally : ${sallyMarks[employNum]}<br />`); | |
// ---------- ARRAYS ---------- | |
let array2 = Array.from("word"); | |
let array3 = Array.from(array1, value => value * 2); | |
for (let val of array3) document.write(`Array Val : ${val}<br />`); | |
// ---------- SETS ---------- | |
// A Set is a list of values with no duplicates | |
var randSet = new Set(); | |
randSet.add(10); | |
randSet.add("Word"); | |
// Check to see if set contains a value | |
// | |
document.write(`Has 10 : ${randSet.has(10)}<br />`); | |
// Get size of Set | |
document.write(`Set Size : ${randSet.size}<br />`); | |
// Delete item from list | |
randSet.delete(10); | |
// Iterate a Set | |
for (let val of randSet) document.write(`Set Val : ${val}<br />`); | |
// ---------- MAPS ---------- | |
// A Map is a collection of key/value pairs | |
var randMap = new Map(); | |
randMap.set("key1", "Random String"); | |
randMap.set("key2", 10); | |
// Get values | |
document.write(`key1 : ${randMap.get("key1")}<br />`); | |
document.write(`key2 : ${randMap.get("key2")}<br />`); | |
// Get size | |
document.write(`Map Size : ${randMap.size}<br />`); | |
// Iterate Map | |
randMap.forEach(function(value, key) { | |
document.write(`${key} : ${value}<br />`); | |
}); | |
console.log("%cNusret Baba was here!", "color: #ff9500; font-size:24px;"); | |
// for each w/ promise | |
db.allDocs({ include_docs: true }) | |
.then(function(result) { | |
return Promise.all( | |
result.rows.map(function(row) { | |
return db.remove(row.doc); | |
}) | |
); | |
}) | |
.then(function(arrayOfResults) { | |
// etc | |
}); | |
// promise w/ sync func | |
getUserByName("nolan") | |
.then(function(user) { | |
return getUserAccountById(user.id); | |
}) | |
.then(function(userAccount) { | |
// I got a user account! | |
}); | |
// promise w/ error | |
getUserByName("nolan") | |
.then(function(user) { | |
if (user.isLoggedOut()) { | |
throw new Error("user logged out!"); // throwing a synchronous error! | |
} | |
if (inMemoryCache[user.id]) { | |
return inMemoryCache[user.id]; // returning a synchronous value! | |
} | |
return getUserAccountById(user.id); // returning a promise! | |
}) | |
.then(function(userAccount) { | |
// I got a user account! | |
}) | |
.catch(function(err) { | |
// Boo, I got an error! | |
}); | |
// when you use the then(resolveHandler, rejectHandler) format, the rejectHandler won't actually catch an error if it's thrown by the resolveHandler itself | |
somePromise() | |
.then(function() { | |
return someOtherPromise(); | |
}) | |
.catch(function(err) { | |
// OK! handles even resolveHandler error | |
}); | |
// always pass a function into then() | |
// Promise.resolve('foo').then(Promise.resolve('bar')).then( .. => returns foo instead of bar | |
Promise.resolve("foo") | |
.then(function() { | |
return Promise.resolve("bar"); | |
}) | |
.then(function(result) { | |
// .. => returns bar OK! | |
}); | |
// credits to: Nolan Lawson | |
// "https://pouchdb.com/2015/05/18/we-have-a-problem-with-promises.html" | |
// Use requestAnimationFrame for visual changes | |
function updateScreen(time) { | |
// Make visual updates here. | |
} | |
requestAnimationFrame(updateScreen); | |
// array unique and duplicates | |
const findDuplicates = source => { | |
const keys = Object.keys(source[0]); | |
let unique = [], | |
duplicates = []; | |
source.forEach((item, idx) => { | |
if (idx == 0) { | |
unique.push(item); | |
return; | |
} | |
const resultItem = unique.find(resultItem => { | |
let notFound = true; | |
keys.forEach(key => { | |
notFound = notFound && item[key] != resultItem[key]; | |
}); | |
return !notFound; | |
}); | |
(!resultItem ? unique : duplicates).push(item); | |
}); | |
return { unique: unique, duplicates: duplicates }; | |
}; | |
const uniquesAndDuplicates = findDuplicates(uniqueAndDuplicateArray); | |
const uniqueWithArrayFrom = Array.from(new Set(uniqueAndDuplicateArray)); | |
const uniqueWithSpreadOperator = [...new Set(cars)]; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment