You can view these slides at http://jordankasper.com/modern-js
ECMAScript vs JavaScript vs W3C recommendations
ECMAScript vs JavaScript vs W3C recommendations
ECMAScript vs JavaScript vs W3C recommendations
Strict Mode!
"use strict";
Use it inside a function block:
// non-strict code function() { "use strict"; // strict code only! } // more non-strict code
var newInstance = new SomeObject();
var newInstance = Object.create(SomeObject.prototype);
newInstance.constructor();
var dog = { name: "Vincent", age: 9, get humanYears() { return this.age * 7; }, set humanYears(y) { this.age = y / 7; } }; dog.humanYears; // 63 dog.humanYears = 70; // dog.age is now 10 Object.keys(dog); // ["name", "age", "humanYears"]
Array.isArray(someVar); // true/false ["a", "b", "c"].indexOf("b"); // 1 ["a", "b", "c"].forEach(function(value, i, arr) { // ... }); ["a", "b", "c"].map(function(value, i, arr) { return "new value"; }); ["a", "b", "c"].filter(function(value, i, arr) { return true; });
FINALLY.
JSON.stringify({ one: "1", "two": 2 }); // "{"one":"1","two":2}" JSON.parse("{ \"one\": \"1\", \"two\": 2 }"); // { one: "1", "two": 2 }
FINALLY.
var o = { one: "1", two: 2}; function whatIsOne() { return this.one; } whatIsOne(); // undefined, "this" is the window whatIsOne.bind(o)(); // "1", "this" is o whatIsOne(); // undefined again, binding is not persistent
(W3C)
Some of the current working recommendations...
<video id="myVid" src="myVideoFile.mp4" controls></video> <audio id="mySong" src="myAudioFile.mp3" controls></audio> <script> document.getElementById("myVid").play(); document.getElementById("myVid").pause(); document.getElementById("myVid").addEventListener("pause", function() { // do stuff ... }); </script>
Uses the new "Cross Origin Resource Sharing" (CORS) specification.
$.ajax({ url: "http://otherdomain.com/resource", ... });
Request: GET http://otherdomain.com/resource/ HTTP/1.1 Referer: http://mydomain.com/ Origin: http://mydomain.com ...
Response: Access-Control-Allow-Origin: http://mydomain.com Content-Type: application/json ...
<p draggable="true">Some Text</p>
Not impressed yet?
<p id="dragger" draggable="true">Some Text</p>
document.getElementById("dropZone") .addEventListener("dragover", function(e) { // keep browser from being stupid... e.preventDefault(); }) document.getElementById("dropZone") .addEventListener("drop", function(e) { e.target.innerHTML = document.getElementById("dragger").outerHTML; }); <div id="dropZone"></div>
Choose a picture:
<input type="file" id="pic" /> <script> document.getElementById("pic") .addEventListener("change", function(e) { var reader = new FileReader(); reader.onload = function(readEvent) { $("#pic").before( "<img src='"+readEvent.target.result+"' width='50' />" ); }; reader.readAsDataURL(e.target.files[0]); }); </script>
navigator.geolocation.getCurrentPosition( function(position) { position.coords.latitude; position.coords.longitude; }, function() { // error handler // (or the user didn't allow it) } );
<video id="me"></video> <script> navigator.webkitGetUserMedia( {video: true, audio: false}, function(stream) { document.getElementById("me").src = window.URL.createObjectURL(stream); }, function(e) { // uh oh... failed } ); // on button click document.getElementById("me").play(); // or .pause() </script>
No more URL hashes!
document.getElementById("someLink") .addEventListener("click", function(e) { history.pushState( "Some link clicked", "The New Page Title", "/new-url" ); }); window.addEventListener("popstate", function(e) { // do something when the user hits the back button e.state; // "Some previous state" });
Two types: sessionStorage and localStorage
sessionStorage: only lasts while the session is active
(usually meaning the browser window is open)
localStorage: lasts indefinitely
(until the user clears browser data)
Both types of storage only store strings!!
sessionStorage.foo = "bar"; localStorage.foo = "bar"; console.log(localStorage.foo); // "bar" // Want to store bigger objects? var options = { "username": "jakerella", "password": "correcthorsebatterystaple", "lastLoginTime": (new Date()).getTime() }; localStorage.userOptions = JSON.stringify(options); // later on... var oldOptions = JSON.parse(localStorage.userOptions);
var observer = new WebKitMutationObserver(function(mutations) { mutations.forEach(function(mutation) { // handle mutation (or do nothing and move on to the next) }) }); observer.observe(document, { childList: true });
var nodes = document.querySelectorAll(".slide p strong, .dropZone");
var nodes = $(".slide p strong, .dropZone");
http://takashi-matsuo.blogspot.com/2009/12/integrating-websockets-with-appengine.html
var connection = new WebSocket( "ws://api.mydomain.com/chat", ["xmpp"] ); connection.onmessage = function(e) { e.data; // our new message! } connection.onerror = function(e) { // handle errors } ... connection.send("Hello World!");
Don't forget the server!
For asynchronous actions that can happen in the background.
No access to the window or DOM (document).
// IN OUR MAIN SCRIPT var worker = new Worker("some-code.js"); worker.addEventListener("message", function(e) { // handle the result of the work (e.data) }, false); worker.postMessage("Start!"); // IN THE WORKER this.addEventListener("message", function(e) { // do some work, maybe use e.data passed in this.postMessage("I'm done!"); this.close(); // or you could leave it open to receive // more messages and do more work }, false);
Getting binary data as a blob without workarounds...
var xhr = new XMLHttpRequest(); xhr.open("GET", "images/picard.jpg", true); xhr.responseType = "blob"; xhr.onload = function(e) { if (this.status == 200) { var blob = new Blob([this.response], {type: "image/jpg"}); } }; xhr.send();
Sending files!! FINALLY.
document.getElementById("someFile") .addEventListener("change", function(e) { var formData = new FormData(); // the magic: formData.append(this.files[0].name, this.files[0]); var xhr = new XMLHttpRequest(); xhr.open("POST", "/some-script", true); xhr.onload = function(e) { ... }; xhr.send(formData); // will switch to "multipart/form-data" automatically! });
Combine file uploads with better progress notification!
<progress min="0" max="100" value="0" id="upload"></progress>
document.getElementById("someFile") .addEventListener("change", function(e) { ... xhr.upload.onprogress = function(e) { if (e.lengthComputable) { document.getElementById("upload").value = (e.loaded / e.total) * 100); } }; xhr.send(formData); });
Thank you!
You can view these slides at http://jordankasper.com/modern-js