[drupalday2017] - Async navigation with a lightweight ES6 framework
ES6 with Babel.js
-
Upload
bran-van-der-meer -
Category
Internet
-
view
146 -
download
4
Transcript of ES6 with Babel.js
ES6
Agenda
1. Why & How
2. ES6 features
Why & How
1
gulp.src('src/static/js/**/*.js') .pipe(babel()) .pipe(uglify()) .pipe(gulp.dest('dist/static/js/'))
ES6 features
2
ArrowsFeature
Arrows
• Function shorthand• Syntax: =>• Lexical this
Arrows
var odds = evens.map(v => v + 1);//=>var odds = evens.map(function(v) { return v + 1;});
Arrows: Lexical this
var bob = { _name: "Bob", _friends: [], printFriends: function() { this._friends.forEach(f => console.log(this._name, f)); }}
Enhanced Object LiteralsFeature
Enhanced Object Literals
var obj = { handler, toString() { return "d " + super.toString(); }}
ClassesFeature
Classes
• Just syntactic sugar• Still a prototypal system• Compiles to:• IIFE• c.prototype = Object.create(p.prototype);• parent.call(this, x, y);
• Functions added to the prototype• etc.
Classes
class SkinnedMesh extends THREE.Mesh { constructor(geometry, materials) { super(geometry, materials); this.idMatrix = SkinnedMesh.matrix(); } update(camera) { super.update(); }}
Template StringsFeature
Template Strings
// Multiline strings`In ES6 this is now legal.`
// String interpolationvar name = "Bob", time = "today";`Hello ${name}, how are you ${time}?`
DestructuringFeature
Destructuring: List matching
var [m, d, y] = [3, 14, 1977];//=>var m = 3, d = 14, y = 1977;
Destructuring: Object matchingvar {op, lhs, rhs} = getASTNode();//=>var _ast = getASTNode();var op = _ast.op, lhs = _ast.lhs, rhs = _ast.rhs;
Destructuring: Parameter positionfunction g({name: x}) { console.log(x); //=> 5}
g({name: 5})
Default, Rest, SpreadFeature
Default parameter values
function f(x, y=12) { return x + y;}
f(3) //=> 15
Rest: Trailing parameters
function f(x, ...y) { return x * y.length;}
f(3, "hello", true) //=> 6
Spread array values
function f(x, y, z) { return x + y + z;}
f(...[1,2,3]) //=> 6
Let & ConstFeature
let is the new var
Block scoping
{ let x = 2; x; //=> 2}x; //=> undefined
Block scoping
for (let i = 0; i < 10; i++) { console.log(i * 10);}i; //=> undefined
Const
pi + 2; //=> Not defined errorconst pi = 3.14;pi = 3.15; //=> Silent fail
const obj = { 'a': 'b' };obj = 3; //=> Silent failobj.a = 'c'; //=> Works!
SymbolsFeature
Symbols: Private data
var MyModule = (function() { var myKey = Symbol(); function MyModule(private) { this[myKey] = private; } return MyModule;})();
var c = new MyModule("hello");
Iterators & For..OfFeature
Iterator
• An object that has a method with key:Symbol.iterator
• That method returns an object with a next() method
• The next() method keeps returning the next item
Iterator: example
Counter[Symbol.iterator] = function() {
let step = 0;
return {
next() {
return {value: step+1, done: false};
}
};
}
Iterator: Array
let arr = ['a', 'b', 'c'];
let iter = arr[Symbol.iterator]();
iter.next() //=> { value: 'a', done: false }
iter.next() //=> { value: 'b', done: false }
iter.next() //=> { value: 'c', done: false }
iter.next()
//=> { value: undefined, done: true }
For…Of
• A way of iterating an iterator• But nothing else!
For…Of
let arr = [3, 5, 7];arr.foo = "hello";
for (let i in arr) { console.log(i); //=> 0, 1, 2, "foo"}
for (let i of arr) { console.log(i); //=> 3, 5, 7}
GeneratorsFeature
Generator
• An Iterator factory• A function that can be paused and
resumed• Syntax: function* myFn() {}• Syntax: yield• Returns an Iterator internally
Generator
function* idMaker() { var index = 0; while(true) yield index++;}
var gen = idMaker();
gen.next().value //=> 0gen.next().value //=> 1gen.next().value //=> 2
Looks sync, is async
co(function* () {
let [croftStr, bondStr] = yield Promise.all([
getFile('http://server.co/croft.json'),
getFile('http://server.co/bond.json'),
]);
let croftJson = JSON.parse(croftStr);
let bondJson = JSON.parse(bondStr);
});
ModulesFeature
Modules
// lib/math.js
export function sum(x, y) {
return x + y;
}
export var pi = 3.141593;
// app.js
import * as m from "lib/math";
alert("2π = " + m.sum(m.pi, m.pi));
Module LoaderFeature
Module Loader
System .import('lib/math') .then(function(m) { alert("2π = " + m.sum(m.pi, m.pi)); });
Map, SetWeakMap, WeakSetFeature
Map
• Associative Collection• Keys can be any variable type• Iterable• Unordered
Map: example
let map = new Map(); map.set('foo', 123);
map.size //=> 1map.get('foo') //=> 123map.has('foo') //=> truemap.delete('foo') //=> truemap.has('foo') //=> false
WeakMap
• Associative Collection• Keys must be objects• Keys not prevented from garbage-
collection• Same API as Map• Not an Iterable• Unordered
Set
• Collection of uniques• No keys, just values• Iterable• Unordered
Set: example
let set = new Set(['red', 'green', 'blue']);
set //=> Set {'red', 'green', 'blue'}
WeakSet
• Collection of uniques• No keys, just values• Keys not prevented from garbage-
collection• Same API as Set• Not an Iterable• Unordered
ProxiesFeature
Proxying an object
var target = {};
var handler = {
get: function(receiver, name) {
return `Hello, ${name}!`;
}
};
var p = new Proxy(target, handler);
p.world === 'Hello, world!';
Proxying a function
var target = function() { return 'target'; };
var handler = {
apply: function(receiver, ...args) {
return 'proxy';
}
};
var p = new Proxy(target, handler);
p() === 'proxy';
Subclassable Built-insFeature
Array, Date, Element, etc.
class MyArray extends Array { constructor(...args) { super(...args); }}
Standard libraryFeatures
Stdlib: Number
Number.EPSILONNumber.isInteger(Infinity) //=> falseNumber.isNaN("NaN") //=> false
Stdlib: String
"abcde".includes("cd") //=> true"abc".repeat(3) //=> "abcabcabc"
Stdlib: Math
Math.acosh(3) //=> 1.762747174039086Math.hypot(3, 4) //=> 5Math.imul(16, 16) //=> 256
Stdlib: Array
Array.from(nodeList) //=> […]
Array.of(1, 2, 3) //=> [1, 2, 3]
[0, 0, 0].fill(7, 1) //=> [0, 7, 7]
[1, 2, 3].find(x => x == 3) //=> 3
[1, 2, 3].findIndex(x => x == 2) //=> 1
[1, 2, 3, 4, 5].copyWithin(3, 0) //=> [1, 2, 3, 1, 2]
["a", "b", "c"].entries() //=> iterator [0, "a"], …
["a", "b", "c"].keys() //=> iterator 0, 1, 2
["a", "b", "c"].values() //=> iterator "a", "b", "c"
Binary & Octal LiteralsFeature
Binary & Octal Literals
0b111110111 === 503 //=> true0o767 === 503 //=> true
PromisesFeature
Promises
function timeout(duration = 0) {
return new Promise((resolve, reject) => {
setTimeout(resolve, duration);
})
}
timeout(1000)
.then(() => {
return timeout(2000);
});
Reflect APIFeature
Reflect API
Reflect.get(target, name, [receiver])
Reflect.set(target, name, value, [receiver])
Reflect.has(target, name) //=> first class `name in obj`
Reflect.apply(target, receiver, args)
Reflect.construct(target, args) //=> apply on constructor
Reflect.getOwnPropertyDescriptor(target, name)
Reflect.defineProperty(target, name, desc) //=> return vs. throw
Reflect.getPrototypeOf(target)
Reflect.setPrototypeOf(target, newProto)
Reflect.deleteProperty(target, name) //=> first class `delete o[n]`
Reflect.enumerate(target)
Reflect.preventExtensions(target)
Reflect.isExtensible(target)
Reflect.ownKeys(target)
Tail CallsFeature
Recursion
function factorial(n, acc = 1) { if (n <= 1) return acc; return factorial(n - 1, n * acc);}
factorial(6) //=> 720
Recursion
factorial(6) // allocate memory and save state
6 * factorial(5) // allocate memory and save state
6 * (5 * factorial(4)) // allocate mem...
6 * (5 * (4 * factorial(3))) // allocate mem...
6 * (5 * (4 * (3 * factorial(2)))) // allocate mem...
6 * (5 * (4 * (3 * (2 * factorial(1))))) // allocate mem...
6 * (5 * (4 * (3 * (2 * (1 * factorial(0)))))) // allocate mem... (max depth)
6 * (5 * (4 * (3 * (2 * (1 * 1)))))
6 * (5 * (4 * (3 * (2 * 1))))
6 * (5 * (4 * (3 * 2)))
6 * (5 * (4 * 6))
6 * (5 * 24)
6 * 120
720
factorial(600000)
Tail Calls
function factorial(n, acc = 1) { if (n <= 1) return acc; return factorial(n - 1, n * acc);}
factorial(100000)
Have fun!
Questions?