Browse Source

add prerequisites

Gregg Tavares 7 years ago
parent
commit
b4945713e1

+ 1 - 1
threejs/lessons/index.md

@@ -1,6 +1,6 @@
 Title: Three.js Fundamentals
 
-Learn Three.js
+This is a set of article to help learn Three.js.
 
 {{{include "threejs/lessons/toc.html"}}}
 

+ 5 - 5
threejs/lessons/threejs-fundamentals.md

@@ -7,15 +7,15 @@ it as easy as possible to get 3D content on a webpage.
 
 Three.js is often confused with WebGL since more often than
 not, but not always, three.js uses WebGL to draw 3D.
-WebGL is a very low-level
-system that only draws points, lines, and triangles. To do
-anything useful with WebGL generally requires quite a bit of
+[WebGL is a very low-level system that only draws points, lines, and triangles](https://webglfundamentals.org). 
+To do anything useful with WebGL generally requires quite a bit of
 code and that is where three.js comes in. It handlings things
-like scenes, lights, shadows, materials, textures, all things that you'd
+like scenes, lights, shadows, materials, textures, 3d math, all things that you'd
 have to write yourself if you were to use WebGL directly.
 
 These tutorials assume you already know JavaScript and, for the
-most part they will use ES6 style JavaScript. Most browsers
+most part they will use ES6 style JavaScript. [See here for a
+terse list of prerequisites](threejs-prerequisites.html). Most browsers
 that support three.js are auto-updated so most users should
 be able to run this code. If you'd like to make this code run
 on older browsers look into a transpiler like [Babel](http://babel.io).

+ 290 - 0
threejs/lessons/threejs-prerequisites.md

@@ -0,0 +1,290 @@
+Title: Three.js Prerequisites
+Description: What you need to know to use this site.
+
+These articles are meant to help you learn how to use three.js.
+They assume you know how to program in JavaScript. They assume
+you know what the DOM is, how to write HTML as well as create DOM elements
+in JavaScript. They assume you know how to use `<script>` tags to
+include external JavaScript files as well as inline scripts.
+They assume you know some CSS and that you know what
+[CSS selectors are](https://developer.mozilla.org/en-US/docs/Learn/CSS/Introduction_to_CSS/Selectors). 
+They also assume you know ES5, ES6 and maybe some ES7.
+They assume you know that the browser runs JavaScript only via events and callbacks.
+They assume you know what a closure is.
+
+Here's some brief refreshers and notes
+
+## `document.querySelector` and `document.querySelectorAll`
+
+You can use `document.querySelector` to select the first element
+that matches a CSS selector. `document.querySelectorAll` returns
+all elements that match a CSS selector.
+
+## You don't need `onbody`
+
+Lots of 20yr old pages use HTML like
+
+    <body onload="somefunction()">
+
+That style is deprecated. Put your scripts
+at the bottom of the page.
+
+```
+<html>
+  <head>
+    ...
+  </head>
+  <body>
+     ...
+  </body>
+  <script src="script1.js"></script>
+  <script>
+    // inline javascript
+  </script>
+</html>
+```
+
+or [use the `defer` property](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script).
+
+## You don't need `type="text/javascript"`
+
+modern
+
+    <script>...</script>
+
+outdated
+
+    <script type="text/javascript"></script>
+
+## Always use `strict` mode
+
+Put `'use strict';` at the top of every JavaScript file.
+
+## Know how closures work
+
+```
+function a(v) {
+  const foo = v;
+  return function() {
+     return foo;
+  };
+}
+
+const f = a(123);
+const g = a(456);
+console.log(f());  // prints 123
+console.log(g());  // prints 456
+```
+
+In the code above the function `a` creates a new function every time it's called. That
+funciton *closes* over the variable `foo`. Here's [more info](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures).
+
+## Understand how `this` works
+
+`this` is not magic. It's effectively a variable that is automatically passed to functions just like
+an argument is passed to function. The simple explaintion is when you call a function directly
+like
+
+    somefunction(a, b, c);
+
+This will be `null` where as when you call a function via the dot operator `.` like this
+
+    someobject.somefunction(a, b, c);
+
+This will be set to `someobject`.
+
+The parts where people get confused is with callbacks.
+
+     const callback = someobject.somefunction;
+     loader.load(callback);
+
+doesn't work as someone inexperienced might expect because when
+`loader.load` calls the callback it's not calling it with the dot `.` operator
+so by default `this` will be null (unless the loader explicitly sets it to someting).
+If you want `this` to be `someobject` when the callback happens you need to 
+tell JavaScript that by binding it to the function.
+
+     const callback = someobject.somefunction.bind(someobject);
+     loader.load(callback);
+
+[*this* article might help](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/this).
+
+## ES5/ES6/ES7 stuff
+
+### `var` is deprecated. Use `const` and/or `let`
+
+There is no reason to use `var` **EVER** and at this point it's considered bad practice
+to use it at all. Use `const` if the variable will never be reassigned which is most of
+the time. Use `let` in those cases where the value changes.
+
+### Use `for(elem of collection)` never `for(elem in collection)`
+
+`for of` is new, `for in` is old. `for in` had issues that are solved by `for of`
+
+As one example you can iterate over all the key/value pairs of an object with
+
+```
+for (const [key, value] of Object.entries(someObject)) {
+  console.log(key, value);
+}
+```
+
+### Use `forEach`, `map`, and `filter`  where useful
+
+Arrays added the functions [`forEach`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/forEach, 
+[`map`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map), and 
+[`filter`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter) and
+are used fairly extensively in modern JavaScript.
+
+### Use destructuring
+
+Assume an object `const dims = {width: 300, height: 150}`
+
+old code
+
+     const width = dims.width;
+     const height = dims.height;
+
+new code
+
+     const {width, height} = dims;
+
+### Use object declaration short cuts
+
+old code
+
+```
+ const width = 300;
+ const height = 150;
+ const obj = {
+   width: width,
+   height: height,
+   area: function() {
+     return this.width * this.height
+   },
+ };
+```
+
+new code
+
+```
+ const width = 300;
+ const height = 150;
+ const obj = {
+   width,
+   height,
+   area() {
+     return this.width * this.height;
+   },
+ };
+```
+
+### Use the spread operator `...`
+
+The spread operator has a ton of uses. Example
+
+```
+ function log(className, ...args) {
+   const elem = document.createElement('div');
+   elem.className = className;
+   elem.textContent = [...args].join(' ');
+   document.body.appendChild(elem);
+ }
+```
+
+Another example
+
+```
+const position = [1, 2, 3];
+somemesh.position.set(...position);
+```
+
+### Use `class`
+
+The syntax for making class like objects pre ES5 was unfamilar to most programmers.
+As of ES5 you can now [use the `class` keyword](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes).
+
+### Use arrow functions where appropriate
+
+This is especially useful with callbacks and promises.
+
+```
+loader.load((texture) => {
+  // use textrue
+});
+```
+
+Arrow functions bind `this`. They are a shortcut for
+
+```
+(function(args) {/* code */}).bind(this))
+```
+
+### Promises as well as async/await
+
+Promises help with asynchronous code. Async/await help
+use promises.
+
+It's too big a topic to go into here but you can [read up
+on promises here](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Using_promises)
+and [async/await here]().
+
+### Use Template Literals
+
+Template literals are strings using backticks instead of quotes.
+
+    const foo = `this is a template literal`;
+
+Template literals have basically 2 features. One is they can be multi-line
+
+```
+const foo = `this
+is
+a
+template
+literal`;
+const bar = "this\nis\na\ntemplate\nliteral";
+```
+
+`foo` and `bar` above are the same.
+
+The other is that you can pop out of string mode and insert snippets of
+JavaScript using `${javascript-expression}`. This is the template part. Example:
+
+```
+const r = 192;
+const g = 255;
+const b = 64;
+const rgbCSSColor = `rgb(${r},${g},${b})`;
+```
+
+or
+
+```
+const color = [192, 255, 64];
+const rgbCSSColor = `rgb(${color.join(',')})`;
+```
+
+or
+
+```
+const aWidth = 10;
+const bWidth = 20;
+someElement.style.width = `${aWidth + bWidth}px`;
+```
+
+# Consider using Visual Studio Code
+
+Of course use whatever editor you want but if you haven't tried it consider using [Visual Studio Code](https://code.visualstudio.com/)
+for JavaScript and after installing it [setup eslint](https://marketplace.visualstudio.com/items?itemName=dbaeumer.vscode-eslint).
+It might take a few minutes to setup but it will help you immensely with finding bugs in your JavaScript.
+
+As a simple example if you enable [the `no-undef` rule](https://eslint.org/docs/rules/no-undef) then VSCode via ESLint will
+warn you of many undefined variables. You'll get warnings using `THREE` so add `/* global THREE */` at the top of your JavaScript files.
+
+# If you really need to support legacy browsers use a transpiler
+
+Most modern browsers are auto-updated so using all these features will help you 
+be productive and avoid bugs. That said, if you're on a project that absolutely
+must support old browsers there are [tools that will take your ES5/ES6/ES7 code
+and transpile the code back to pre ES5 Javascript](https://babeljs.io).

+ 1 - 0
threejs/lessons/toc.html

@@ -12,6 +12,7 @@
   </ul>
   <li>Reference</li>
   <ul>
+    <li><a href="/threejs/lessons/threejs-prerequisites.html">Material Table</a></li>
     <li><a href="/threejs/lessons/threejs-material-table.html">Material Table</a></li>
   </ul>
 </ul>