How to tackle real-world web platform performance problems in modern websites and apps? This session starts with a basic understanding of the web platform and then explores to a set of problem/solution pairs built from industry-standard performance guidance. In the talk, we will demonstrate performance tips and tricks that will help you improve the performance of your apps and sites today. We will discuss the following respond to network requests, speed and responsiveness, optimizing media usage, and writing fast JavaScript. These performance tips and tricks apply equally to web sites that run on standards based web browsers, as well as to modern apps.
25. Six Principles to Remember
1) Quickly Respond to Network Requests
2) Minimize Bytes Downloaded
3) Optimize Media Usage
4) Efficiently Structure Markup
5) Know What Your Application is Doing
6) Write Fast JavaScript
89. /* These styles are for the home page. */
HomePage
{
color: red;
}
/* These styles are for the content page. */
ContentPage
{
color: green;
}
Only Include Necessary Styles
Efficiently Structure Markup
90. /* These styles are for the home page. */
HomePage
{
color: red;
}
/* These styles are for the content page. */
ContentPage
{
color: green;
}
Only Include Necessary Styles
Efficiently Structure Markup
91. /* These styles are for the home page. */
HomePage
{
color: red;
}
/* These styles are for the content page. */
ContentPage
{
color: green;
}
Only Include Necessary Styles
Efficiently Structure Markup
110. Align Timers to the Display Frame (16.7)
Know What Your Application is Doing
setInterval(renderLoop, 16.7);
setInterval(renderLoop, 33.4);
16.7 16.716.7
111. Use requestAnimationFrame for Animations
Know What Your Application is Doing
window.requestAnimationFrame(renderLoop);
16.7 16.716.7
115. Native JSON Methods
var jsObjStringParsed = JSON.parse(jsObjString);
var jsObjStringBack = JSON.stringify(jsObjStringParsed);
Use Native JSON Methods
Write Fast JavaScript
116. Numbers in JavaScript
âą All numbers are IEEE 64-bit floating point numbers
- Great for flexibility
- Performance and optimization challenge
31bits
31-bit (tagged) Integers
1bit
1
31bits
Object pointer
1bit
0
32bits
32bits
Floats
32-bit Integers
STACK HEAP
FIXED LENGTH, FASTER ACCESS VARIABLE LENGTH, SLOWER ACCESS
Boxed
117. Avoid creating floats if they are not needed
Fastest way to indicate integer math is |0
var r = 0;
function doMath(){
var a = 5;
var b = 2;
r = ((a + b) / 2) |0 ; // r = 3
r = Math.round((a + b) / 2); // r = 4
}
var r = 0;
function doMath(){
var a = 5;
var b = 2;
r = ((a + b) / 2); // r = 3.5
}
...
var intR = Math.floor(r);
0x005e4148r: 0x00000007r:
0x00000009r:
Number
3.5
STACK HEAP STACK
SLOW FAST
SLOW
118. Take advantage of type-specialization for arithmetic
Create separate functions for ints and floats; use consistent argument types
function Distance(p1, p2) {
var dx = p1.x - p2.x;
var dy = p1.y - p2.y;
var d2 = dx * dx + dy * dy;
return Math.sqrt(d2);
}
var point1 = {x:10, y:10};
var point2 = {x:20, y:20};
var point3 = {x:1.5, y:1.5};
var point4 = {x:0x0AB, y:0xBC};
Distance(point1, point3);
Distance(point2, point4);
function DistanceFloat(p1, p2) {
var dx = p1.x - p2.x;
var dy = p1.y - p2.y;
var d2 = dx * dx + dy * dy;
return Math.sqrt(d2);
}
function DistanceInt(p1,p2) {
var dx = p1.x - p2.x;
var dy = p1.y - p2.y;
var d2 = dx * dx + dy * dy;
return (Math.sqrt(d2) | 0);
}
var point1 = {x:10, y:10};
var point2 = {x:20, y:20};
var point3 = {x:1.5, y:1.5};
var point4 = {x:0x0AB, y:0xBC};
DistanceInt(point1, point2);
DistanceFloat(point3, point4);
SLOW FAST
119. Initialize JavaScript on Demand
Write Fast Loading JavaScript
var userTileScriptsLoaded = false;
function CustomizeUserTile()
{
if (userTileScriptsLoaded == false)
{
var head = document.getElementsByTagName("head")[0];
script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'upload.js';
head.appendChild(script);
}
}
120. Initialize JavaScript on Demand
Write Fast Loading JavaScript
var userTileScriptsLoaded = false;
function CustomizeUserTile()
{
if (userTileScriptsLoaded == false)
{
var head = document.getElementsByTagName("head")[0];
script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'upload.js';
head.appendChild(script);
}
}
121. Initialize JavaScript on Demand
Write Fast Loading JavaScript
var userTileScriptsLoaded = false;
function CustomizeUserTile()
{
if (userTileScriptsLoaded == false)
{
var head = document.getElementsByTagName("head")[0];
script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'upload.js';
head.appendChild(script);
}
}
122. Initialize JavaScript on Demand
Write Fast Loading JavaScript
var userTileScriptsLoaded = false;
function CustomizeUserTile()
{
if (userTileScriptsLoaded == false)
{
var head = document.getElementsByTagName("head")[0];
script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'upload.js';
head.appendChild(script);
}
}
123. Initialize JavaScript on Demand
Write Fast Loading JavaScript
var userTileScriptsLoaded = false;
function CustomizeUserTile()
{
if (userTileScriptsLoaded == false)
{
var head = document.getElementsByTagName("head")[0];
script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'upload.js';
head.appendChild(script);
}
}
124. Avoid chattiness with the DOM
...
//for each rotation
document.body.game.getElementById(elID).classList.remove(oldClass)
document.body.game.getElementById(elID).classList.add(newClass)
...
var element = document.getElementById(elID).classList;
//for each rotation
element.remove(oldClass)
element.add(newClass)
...
JavaScript
DOM
JavaScript
DOM
125. Avoid automatic conversions of DOM values
Values from DOM are strings by default
this.boardSize = document.getElementById("benchmarkBox").value;
for (var i = 0; i < this.boardSize; i++) { //this.boardSize is â25â
for (var j = 0; j < this.boardSize; j++) { //this.boardSize is â25â
...
}
}
this.boardSize = parseInt(document.getElementById("benchmarkBox").value);
for (var i = 0; i < this.boardSize; i++) { //this.boardSize is 25
for (var j = 0; j < this.boardSize; j++) { //this.boardSize is 25
...
}
}
FAST
(25% marshalling cost
reduction in init function)
SLOW
126. function LoopChildren(elm) {
var node = elm.firstChild;
while (node != null) {
node = node.nextSibling;
}
}
Built in DOM Methods Always More Efficient
Use DOM Efficiently
127. function LoopChildren(elm) {
var node = elm.firstChild;
while (node != null) {
node = node.nextSibling;
}
}
Built in DOM Methods Always More Efficient
Use DOM Efficiently
128. function LoopChildren(elm) {
var node = elm.firstChild;
while (node != null) {
node = node.nextSibling;
}
}
Built in DOM Methods Always More Efficient
Use DOM Efficiently
130. Maintain a Small and Healthy DOM
Use DOM Efficiently
Document HTML Body
Element
Element
Element
Element
Element
Element
Element
Element
Element
131.
132. Six Principles to Remember
1) Quickly Respond to Network Requests
2) Minimize Bytes Downloaded
3) Optimize Media Usage
4) Efficiently Structure Markup
5) Know What Your Application is Doing
6) Write Fast JavaScript
133. Overview Concepts
High Performance Websites
Steve Souders, September 2007
Event Faster Websites: Best Practices
Steve Souders, June 2009
High Performance Browser Networking
Ilya Grigorik, September 2013
JavaScript Patterns
High Performance JavaScript
Nicholas Zakas, March 2010
JavaScript the Good Parts
Douglas Crockford, May 2008
JavaScript Patterns
Stoyan Stefanov, September 2010
JavaScript Cookbook
Shelley Powers, July 2010
Microsoft Guidance
Windows Store App: JavaScript Best Practices
MSDN, December 2012
Performance Tricks to Make Apps & Sites Faster
Jatinder Mann, Build 2012
50 Performance Tricks for Windows Store Apps
Jason Weber, Build 2011
Engineering Excellence Performance Guidance
Jason Weber, EE Forum 2011
Internet Explorer Architectural Overview
Jason Weber, PDC 2011
W3C Web Performance
Web Performance Working Group Homepage
Navigation Timing Specification
Blog Posts
1) Measuring Performance with ETW/XPerf
2) Measuring Performance in Lab Environments
3) Browser Subsystems Overview
4) What Common Benchmarks Measure
Tools
Windows Performance Toolkit
Fiddler Web Debugger
Contact
Doris Chen
Twitter: @doristchen
Email: doris.chen@Microsoft.com