Document flow loading cycle
-
DOMContentLoaded is when the page elements are loaded, but some resources, such as images, cannot be seen, but the page can interact normally, such as scrolling, entering characters, etc. $(document).ready(), which is often used in jQuery, actually listens for DOMContentLoaded.
-
Load means that all resources (images, audio, videos, etc.) on a page have been loaded. $(document).load() in jQuery listens for the load event.
// load
window.onload = function() {};
// DOMContentLoaded
function ready(fn) {
if (document.addEventListener) {
document.addEventListener(
'DOMContentLoaded'.function() {
document.removeEventListener('DOMContentLoaded'.arguments.callee, false);
fn();
},
false
);
}
/ / if the IE
else if (document.attachEvent) {
// Ensure that the event is still safely triggered when the page is loaded in an iframe
document.attachEvent('onreadystatechange'.function() {
if (document.readyState == 'complete') {
document.detachEvent('onreadystatechange'.arguments.callee); fn(); }});// If it is Internet Explorer and the page is not in iframe, polling calls the doScroll method to check whether the DOM is loaded
if (document.documentElement.doScroll && typeof window.frameElement === 'undefined') {
try {
document.documentElement.doScroll('left');
} catch (error) {
return setTimeout(arguments.callee, 20); } fn(); }}}Copy the code
- readystatechange
Document has a readyState property to describe the loading state of document. A change in the readyState will trigger the readyStatechange event.
- Loading: Documents are being loaded
- Interactive: The document is finished loading and parsed, but sub-resources such as images, styles, and frames are still loading
- Complete: The document and child resources have finished loading and this state indicates that the loading event will be triggered.
Therefore, we can also use this event to determine the loading status of the DOM.
- beforeunload
Beforeunload events are triggered when a browser window, document or device resource is about to unload, the document is still visible, and the event can be cancelled at this point.
- unload
When a document or a resource is about to be unloaded, it is triggered after beforeUnload, PageHide time and the document is in a specific state:
- All resources still exist
- All resources are invisible to end users
- Invalid interface interaction
- Errors do not stop the process of uninstalling documents.
document.addEventListener("DOMContentLoaded".function (event) {
console.log("Initial DOM load and parse");
});
window.addEventListener("load".function (event) {
console.log("All resources in window have loaded.");
});
document.onreadystatechange = function () {
console.log(document.readyState)
if (document.readyState === "complete") {
console.log('Initial DOM, load parsing done')}}window.addEventListener("beforeunload".function (event) {
console.log('Closing soon')
event.returnValue = "\o/";
});
window.addEventListener('unload'.function (event) {
console.log('About to close 1');
});
Copy the code
Performance API
The Performance interface enables you to obtain Performance information about the current page.
- Performance.timing
View the Performance. Timing object in Chrome:
PerformanceTiming {
connectEnd: 1568364862807
connectStart: 1568364862530
domComplete: 1568364863751
domContentLoadedEventEnd: 1568364863699
domContentLoadedEventStart: 1568364863698
domInteractive: 1568364863694
domLoading: 1568364863438
domainLookupEnd: 1568364862529
domainLookupStart: 1568364862529
fetchStart: 1568364862529
loadEventEnd: 1568364863785
loadEventStart: 1568364863751
navigationStart: 1568364862499
redirectEnd: 0
redirectStart: 0
requestStart: 1568364862807
responseEnd: 1568364863437
responseStart: 1568364863434
secureConnectionStart: 1568364862530
unloadEventEnd: 0
unloadEventStart: 0
}
Copy the code
The browser status is as follows:
The red line on the left represents the process of the network transport layer, while the red line on the right represents the various event states browsed by the server after bytes are transmitted back. This stage includes document parsing by the browser, DOM tree construction, layout and drawing, etc.
- NavigationStart: Indicates the Unix timestamp at the end of the uninstallation from the previous document. If there is no previous document, this value will be equal to fetchStart.
- UnloadEventStart: Indicates the time stamp of the previous web page (in the same domain as the current page) unload. If there is no previous web page unload or the previous web page is in a different domain than the current page, the value is 0.
- UnloadEventEnd: Returns the time stamp on which the back off function of the previous page unload time binding has finished executing.
- RedirectStart: The time when the first HTTP redirect occurs. The value is 0 only when there is a redirect within the same domain name.
- RedirectEnd: The time when the last HTTP redirection is complete. The value is 0 only when there is a redirect within the same domain name.
- FetchStart: The time when the browser is ready to fetch a document using an HTTP request, before checking the local cache.
- DomainLookupStart/domainLookupEnd: DNS domain name of start/end time, if you use the local cache (i.e. no DNS queries) or persistent connection, with fetchStart values are equal
- ConnectStart: time when the HTTP (TCP) connection is started or re-established. If the connection is persistent, the value is the same as the fetchStart value.
- ConnectEnd: time when the HTTP (TCP) connection is established (handshake is completed). If the connection is persistent, the value is the same as the fetchStart value.
- SecureConnectionStart: indicates the start time of the HTTPS connection. If the HTTPS connection is not secure, the value is 0.
- RequestStart: The time when the HTTP request starts reading the real document (after the connection is established), including reading from the cache locally.
- ResponseStart: The time at which the HTTP starts receiving the response (first byte is retrieved), including reading from the local cache.
- ResponseEnd: The time when the HTTP response has been fully received (the last byte fetched), including reading from the local cache.
- DomLoading: Parsing the time to render the DOM tree, document. readyState becomes loading, and readyStatechange events are thrown.
- domInteractive: When the DOM tree is parsed, document. readyState will change to interactive, and readyStatechange events will be thrown. Note that the DOM tree has been parsed, and resources within the page have not started to load.
- DomContentLoadedEventStart: after DOM parsing is complete, the starting time of the resources within the web page loading, before the DOMContentLoaded event is thrown.
- DomContentLoadedEventEnd: after DOM parsing is complete, within the web resource loaded time (e.g., JS) script loading has been completed.
- DomComplete: When the DOM tree is parsed and the resources are ready, document. readyState becomes complete and the readyStatechange event is thrown.
- LoadEventStart: The load event is sent to the document, which is the time the LOAD callback function starts executing.
- LoadEventEnd: The time for the load event’s callback function to finish executing.
Calculate the loading time:
// Calculate the load time
function getPerformanceTiming() {
var t = performance.timing;
var times = {};
// The time the page has finished loading, the time the user waits for the page to be available
times.loadPage = t.loadEventEnd - t.navigationStart;
// Time to parse the DOM tree structure
times.domReady = t.domComplete - t.responseEnd;
// Redirection time
times.redirect = t.redirectEnd - t.redirectStart;
// DNS query time
times.lookupDomain = t.domainLookupEnd - t.domainLookupStart;
// Read the first byte of the page
times.ttfb = t.responseStart - t.navigationStart;
// The time when the resource request is finished loading
times.request = t.responseEnd - t.requestStart;
// The time when the onload callback is executed
times.loadEvent = t.loadEventEnd - t.loadEventStart;
// DNS cache time
times.appcache = t.domainLookupStart - t.fetchStart;
// The time to uninstall the page
times.unloadEvent = t.unloadEventEnd - t.unloadEventStart;
// The time when TCP establishes the connection and completes the handshake
times.connect = t.connectEnd - t.connectStart;
return times;
}
Copy the code
- Performance.navigation
- RedirectCount: 0 // How many times the page has been redirected
- type: 0
- 0 indicates that the page is displayed normally.
- 1: refresh the page through window.location.reload();
- 2 indicates that you can move forward or backward to the page.
- 255 indicates other methods
- Performance.memory
- JsHeapSizeLimit: specifies the memory size limit
- TotalJSHeapSize: Available memory
- UsedJSHeapSize: Memory occupied by JS objects
Core Web Vitals
Core Web Vitals is a subset of Web Vitals applied to all Web pages. They will be shown in all the performance testing tools provided by Google. Each Core Web Vitals represents a different aspect of the user experience and is measurable in that area. And reflects the true experience of user-centered key results.
Web core performance metrics evolve over time. In 2020, the focus will be on three aspects of the user experience: loading, interactivity, and visual stability.
Largest Contentful Paint (LCP)
: To measure the loading experience, to provide a good user experience, the LCP should occur within 2.5 seconds after the page is first started.First Input Delay(FID)
: To measure interactivity, the FID of a page should be less than 100msCumulative Layout Shift(CLS)
: As a measure of visual stability, a page’s CLS should be less than 0.1
LCP: Maximum content element rendering
A measure of the loading experience.
Originally we used the Load, DOMContentLoaded events, but they didn’t necessarily correspond to what was actually on the user’s screen.
We then tried using user-centric update performance metrics, such as First Content Paint(FCP), which captures only the very beginning of the loading experience. This metric is not accurate if the page starts with a loading animation.
Later, the industry began recommending the use of First Meaningful Paint(FMP) and Speed Index(SI)(both available in Lighthouse), but these metrics were complex and difficult to interpret, with a high rate of false positives.
define
Largest Contentful Paint (LCP) measures the render time of the Largest content element visible within the standard report viewport. To provide a good user experience, a site should strive for maximum content rendering within 2.5 seconds of the page starting to load.
Elements of concern
LCP does not count all elements, it only focuses on:
- Img element
- The SVG element in images
- Video elements
- through
url()
The function loads the elements of the background image - Block-level elements that contain text nodes or other children of inline text elements
To calculate
What we need to focus on is the largest element on the page that has the largest drawing area.
The so-called drawing area can be understood as the “footprint” of each element on the screen. If an element extends out of the screen, or is cropped, it is not counted.
The area calculation of image elements is slightly different because the image can be enlarged or shrunk using CSS, that is, the image has the difference between the rendered area and the real area. In the calculation of LCP, the drawing area of the picture will be the smaller of the two. For example, if the rendered area is smaller than the real area, take the rendered area and vice versa.
The page is linear during loading, and elements are rendered once rather than instantaneously, so the element with the largest rendering area changes over time.
If the element is deleted, the LCP algorithm no longer considers the element, and if the deleted element happens to be the element with the largest “draw area”, a new performance entry is created using the element with the largest “draw area”.
This process only requires the user’s first scroll or first user input (mouse click, keyboard keystroke, etc.), which means that once the user starts interacting with the page, new performance metrics are not reported.
To optimize the
The most common reasons for poor LCP are:
- The server response time is slow
- Blocks rendered JS and CSS
- The resource loading time is slow
- Client-side rendering
So we improve the LCP from the above perspective.
Specific measures include:
- Cache HTML offline pages and cache page resources to reduce browser requests for resources
- Reduce resource group calculation rendering, compress CSS/JS, merge, cascade, inline, etc
- Optimize the picture, convert the format to JPG, webP and so on, reduce the size of the picture, load the request speed
- Rewrite HTML, compress whitespace, and remove comments
- Make links as quickly as possible using Preconnet, and make DNS lookups as quickly as possible using dnS-prefect
- Load request speed using CDN
- Compress pages using Gzip
- Use SW to cache resources, requests, etc
FID: the first interactive event
First Contentful Paint(FCP) measures how fast your site loads, but how fast you draw is only the general part. Equally important is how fast your site reacts when the user tries to interact with these pixels.
define
First Input Delay (FID) records the time it takes for a user to interact with a page for the First time. FID affects the First impact of a user on page interaction and responsiveness. To provide a good user experience, the site should have a first input delay of less than 100 milliseconds
FID occurs between FCP and TTI because the page is partially displayed but not fully interactive. This phase of user interaction tends to have large latency.
When the browser receives user input operations, the main thread is busy executing a long task. The browser can respond to user input operations only after the task is completed. The time he must wait is the FID value for the user on this page.
To optimize the
On the one hand, we can reduce js execution time as above:
- Shrink and compress JS files
- Lazily loads js that are not needed on the first screen
- Reduce unused polyfills
On the other hand, we can break down time-consuming tasks:
- Run time-consuming tasks independently using the Web Worker.
CLS: Visual stability
Unexpected movement of page content occurs as a result of asynchronously loading resources or dynamically adding DOM elements to the page above existing content.
define
Cumulative Layout Shift (CLS) measures the Cumulative Layout Shift (CLS), which measures the Cumulative Layout change score of all individual Layout changes for each unexpected style move that occurs over the life of the page. Layout movement can occur at any time visible elements change position from the current frame to the next. To provide a good user experience, websites should strive for a CLS score of less than 0.1.
To calculate
Layout offset score, used to calculate the indicator of element movement. Is the product of two indexes (influence score, distance score) of the target element:
Layout offset score = Impact score * Distance scoreCopy the code
The influence score is the union of the visible areas of all unstable elements in the previous and current frames (the portion of the total area of the station viewport).
Here, for example, an element that occupies half of the viewport in the previous frame moves down 25% in the next frame. The red curve is the union of the visible regions of the elements in the two frames. In this case, the impact score is 0.75
Distance score, which is the maximum distance any unstable element can move in the frame/maximum viewport size:
In this example, the maximum viewport size is height, and the unstable element moves 25% of the viewport height, which gives a distance score of 0.25.
Thus, in this example, the final CLS score is: 0.75 * 0.25 = 0.1875.
To optimize the
1. Never use dimensionless elements
Image and video elements should always contain width and height attributes, which modern browsers use to set the default aspect ratio for images. Aspect-radio can also be used to specify the aspect ratio in advance:
img {
aspect-ratio: attr(width) / attr(height);
}
Copy the code
For responsive images, you can use srcset to define images so that the browser can choose between images, as well as the size of each image:
<img
width="1000"
height="1000"
src="puppy-1000.jpg"
srcset="puppy-1000.jpg 1000w, puppy-2000.jpg 2000w, puppy-3000.jpg 3000w"
alt="ConardLi"
/>
Copy the code
2. Perform other operations
- Never insert content on top of existing content, except in response to user interaction. This ensures expected layout changes
- Rather than animate properties that trigger layout changes.
- Reserve space for advertising space in advance
- Be alert to font changes and use
font-display
Tell the browser to use the system font for rendering by default and replace it when the custom font has been downloaded
@font-face {
font-family: 'Pacifico';
font-style: normal;
font-weight: 400;
src: local('Pacifico Regular'), local('Pacifico-Regular'), url(https://fonts.gstatic.com/xxx.woff2) format('woff2');
font-display: swap;
}
Copy the code
Alternatively, font files can be preloaded using .
To obtain parameters
Method 1: Google provides Web-vitals to make it easy to call these three parameters
import {getCLS, getFID, getLCP} from 'web-vitals';
getCLS(console.log, true);
getFID(console.log); // Does not take a `reportAllChanges` param.
getLCP(console.log, true);
Copy the code
Its return function provides three metrics:
- Name: indicates the indicator name
- Id: INDICATES the ID of the local analysis
- Delta: The difference between the current value and the last value obtained
Indicators can be reported using Google Analytics:
import {getCLS, getFID, getLCP} from 'web-vitals';
function sendToGoogleAnalytics({name, delta, id}) {
ga('send'.'event', {
eventCategory: 'Web Vitals'.eventAction: name,
eventValue: Math.round(name === 'CLS' ? delta * 1000 : delta),
eventLabel: id,
nonInteraction: true}); } getCLS(sendToGoogleAnalytics); getFID(sendToGoogleAnalytics); getLCP(sendToGoogleAnalytics);Copy the code
Method 2: Use the Chrome plug-in
If you don’t want to calculate them in an application, you can also use the Chrome plugin Web-Vitals-Extension to get these metrics.
Other common performance indicators
FP: Draws the event for the first time
FP(First Paint time) is the First “point in time” on the timeline. It represents the time when the browser First transmits pixels to the screen, and when the page First visually changes on the screen.
This is what we call white screen time (the time between the time the browser responds to user input and the time the browser starts displaying content).
White screen time = Enter url in address bar and press enter - first element appears in browserCopy the code
Factors that affect blank screen time: network, server performance, and front-end page structure design
It is generally considered that the time when the browser starts rendering the tag or finishes parsing the is the point at which the white screen ends. To obtain a blank screen event, refer to the following code:
<head>.<script>
// Usually at the end of the head tag, put a mark, which is usually treated as white screen time
performance.mark("first paint time");
</script>
</head>
<body>.<script>
// get the first paint time
const fp = Math.ceil(performance.getEntriesByName('first paint time') [0].startTime);
</script>
</body>
Copy the code
FCP: First content drawing event
FCP(First Contentful Paint) represents the First time the browser paints “content” to the screen.
Only the first time you draw text, images, non-white canvas or SVG is counted as FCP.
This is what we call the first screen time (the time the browser takes from the time the user enters the web address to the time the first screen content is rendered):
First screen time = Address enter the URL and press Enter - browser first screen rendering completeCopy the code
There are often different opinions as to whether the first screen time includes image loading, but that’s irrelevant.
Common methods for calculating the first screen time are as follows:
- First screen module label
Because the browser parses HTML in order, when parsing an element, it considers the first screen to be complete, and adds script after the second element to calculate the time when the first screen is complete.
// End time of the first screen
window.firstPaint = Date.now();
// First screen time
console.log(firstPaint - performance.timing.navigationStart);
Copy the code
- Statistics the slowest image/IFrame in the first screen
Images or iframe resources are usually the slowest to load in the first screen, so it can be interpreted that when images or iframes are loaded, the first screen must be complete.
Because browsers limit the number of TCP connections per page, not all images can be downloaded and displayed immediately. We only need to listen on all images in the first screen onload event, get the picture onload time maximum, and subtract this maximum value from navigationStart to get the approximate first screen time.
<body>
<div class="app-container">
<img src="a.png" onload="heroImageLoaded()">
<img src="b.png" onload="heroImageLoaded()">
<img src="c.png" onload="heroImageLoaded()">
</div>
<script>
// Determine the first screen time according to the core elements in the first screen
performance.clearMarks("hero img displayed");
performance.mark("hero img displayed");
function heroImageLoaded() {
performance.clearMarks("hero img displayed");
performance.mark("hero img displayed");
}
</script>. .<script>
// get the first screen loaded time
const fmp = Math.ceil(performance.getEntriesByName('hero img displayed') [0].startTime);
</script>
</body>
Copy the code
:::tip Note that the main difference between FP and FCP is that FP is the point in time when the browser begins to draw content onto the screen, as long as there is a visual change, no matter what the content triggers the visual change.
In contrast, FCP refers to the first time a browser draws content from the DOM, such as text, images, SVG, CANVAS, etc. This point in time is called FCP
The time point of FP and FCP may be the same, or it may be FP first and THEN FCP.
FMP: First major content draw event
FirstMeaningfulPaint, the first major content rendering time, is not defined in a standardized way. In practice, the time when the highest rated visible content on the page appears on the screen is the FCP time
Statistical method: We can use the Mutation Observer to observe the changes of page nodes in the first 30s of page loading. The new/removed nodes are added to/removed from the Intersection Observer. In this way, the visible time points of page elements and the cross information between elements and the visible area can be obtained. The weights are evaluated according to the type of elements, and then the visibility, cross-area area, and the product of the weight values are evaluated as elements. According to the information obtained above, the time point is X weeks, the total score of visible elements at this time point is Y weeks, and the minimum event corresponding to the highest point is taken as the time point when the main content of the page appears on the screen.
Currently there is no unified logic, Ali has a standard for the highest visible increment element, using depth-first traversal, details can be refer to here
LT: long task
The 50ms threshold is a conclusion summarized from RAIL model, which is a conclusion obtained from Google’s research on user perception, similar to yonghua’s perception/patience threshold. For tasks exceeding this threshold, users will perceive page lag.
To calculate
// Jartto's Demo
const observer = new PerformanceObserver((list) = > {
for (const entry of list.getEntries()) {
// TODO...
console.log(entry); }}); observer.observe({entryTypes: ['longtask']});
Copy the code
TTI: page interaction time
TTI(Time To Internative): The Time from the start of a page To the Time when its main subresources are loaded To respond quickly To user input (no time-consuming tasks).
To calculate
A rough estimate can be made by domContentLoadedEventEnd:
TTI: domContentLoadedEventEnd - navigationStart,
Copy the code
If you need a more detailed calculation, that is, if, you can get the data by using the Tti – Polyfill provided by Google:
import ttiPolyfill from 'tti-polyfill';
ttiPolyfill.getFirstConsistentlyInteractive(opts).then((tti) = > {
// Use `tti` value in some way.
});
Copy the code
TBT: total page blocking duration
Total Blocking Time (TBT) : TBT summarizes the Blocking duration of all user operations during loading. The Blocking portion in any long task between FCP and TTI is summarized.
reference
- Web Performance Optimization – First screen and white screen time
- How are FCP/FMP/FP defined and counted respectively
- Interpret the next generation of Web performance experiences and quality metrics
- webdev: Metrics
- webdev: Web Vitals