promise.all()
can be used to queue up a few asynchronous calls to load before a subsquent script is called.- This can be useful for preloading libraries before some scripts that depend on the library are called.
this.searchTrigger.addEventListener('click', () => {
// Lazyload Typeahead and Bloodhound libraries.
Promise.all([
getTypeAhead(),
getBloodhound(),
]).then((loadedModules) => {
const Bloodhound = loadedModules[1].default;
if (! Bloodhound) {
return;
}
this.setUpAutocomplete(Bloodhound);
this.setAutocompleteCustomizations();
// Make sure search field is focused.
this.searchField.focus();
});
});
- A frame represents low level events which the browser had to complete to draw your webpage to the screen.
- Note the long vertical dashed lines for frame boundaries
- Frame Events explained here: https://aerotwist.com/blog/the-anatomy-of-a-frame/
- To get pixels from your webpage onto the screen, the browser paints such pixels.
- Painting is an expensive operation.
- In Dev tools, use "Performance" tab and run recording. "Paint" events will appear as green blocks in the Main thread.
- translateZ() hack can be used to promote a paint to it's own layer and move the operation from the Main thread to the GPU. This helps reduce the operation cost (https://aerotwist.com/blog/on-translate3d-and-layer-creation-hacks/)
- Alternatively, the
will-change
property can help browsers identify paint events that should happen on the GPU. - Knowing when to promote a layer will be valuable during your performance optimisation journey
- https://developers.google.com/web/tools/chrome-devtools/network-performance/
- When the browser encounters a
<script>
tag, it must pause rendering and execute the script immediately - Find scripts that arent needed for page load and mark them asynchronous or defer their execution to speed up load time.
- By marking this script with the async attribute and moving it to the bottom of the document's
<body>
, the page can load without waiting for the script - async is commonly used for third-party-scripts that are randomly placed in the DOM
- defer scripts is loaded after domContentLoaded is finished (domContentLoaded is the point when both the DOM is ready and there are no stylesheets that are blocking JavaScript execution).
- https://developers.google.com/web/tools/chrome-devtools/network-performance/reference
- Green in the Waterfall view indicates "Wait" or Time To First Byte (TTFB)
- Blue indicates "Download" time
- Sort Waterfall by right-clicking on table header
export default class MagazineTimeline extends Component {
this.stickNavThrottle = new Throttle(
this.setStickyNav.bind(this), // 'this' becomes bound to Class and not Throttle
'scroll',
document,
50
);
}
-https://code.tutsplus.com/tutorials/create-bookmarklets-the-right-way--net-18154
-
Use debounce on
window
resize events, for example, where a callback function only needs to fire once after resize is complete. -
Use throttle on
window
scroll events, for example, where a callback function can fire many times while scrolling (such as, when calculating scroll depth or when an element in the viewport). -
https://css-tricks.com/the-difference-between-throttling-and-debouncing/
-
https://css-tricks.com/debouncing-throttling-explained-examples/
- https://davidwalsh.name/fetch
- https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API/Using_Fetch#Making_fetch_requests
// This will replace image src not found on local CDN with a remote CDN
(function () {
console.clear();
Array.prototype.forEach.call(document.querySelectorAll('img'), (el) => {
fetch(el.src,{mode: 'no-cors', method: 'get'}).then(function(response) {
if(200 !== response.status) {
console.log('Image src missing: ', el.src);
const newsrc = el.src.replace('old_url', 'new_url');
// @todo: update additional attributes for lazyloading to work
el.src = newsrc;
el.srcset = newsrc;
el.dataset.src = newsrc;
el.dataset.srcset = newsrc;
console.log('Image src updated: ', el.src);
}
})
});
}());
- distance top of page has past the top of the view port in pixels
- useful when calculating scroll depth percentage of page
// Basic formula for calculating scroll percentage
const pageWrap = document.querySelector('.page-wrapper');
const currY = window.scrollY;
const postHeight = window.innerHeight;
const scrollHeight = pageWrap.offsetHeight;
const scrollPercent = (currY / (scrollHeight - postHeight)) * 100;
- for each
iframe
, wait until it has loaded thenaddEventListener
to a submit button within the iframe. Set asetTimeout
to calculate a new height of theiframe
based on the length of the content.
Array.prototype.forEach.call(iframes, (el) => {
el.onload = function () {
const iframe = el.contentWindow.document;
iframe.addEventListener('click', (e) => {
if (e.target && e.target.matches('input[type="submit"]')) {
const self = this;
setTimeout(() => {
const newHeight =
self.contentWindow.document.body.scrollHeight + 50;
self.height = `${newHeight}px`;
}, 500);
}
});
};
});
- Wait until DOM has completely loaded then fire script.
- deprecated function in jQuery.
jQuery(window).load(function() {
// Stuff here will not fire until DOM has loaded completely.
// Including AJAX
});