W3Cx Introduction to JavaScript

W3Cx logo.

W3Cx-5of5-JS.0x - Introduction to JavaScript

W3Cx JS.0x logo.

W3Cx Front-End Web Developer


Table of Contents - W3Cx-5of5-JS.0x - JavaScript Introduction

Syllabus

Course Information

a1. Welcome to JavaScript Introduction

a2. Course forums

a3. Course tools

a4. Why Accessibility is Important

a5. Why Internationalization is Important

a6. About W3C and the Web

Module 1: Introduction to JavaScript

1.1.1 Intro - Module 1: Intro to JavaScript
1.1.2 Module 1 outline
1.2.1 HTML is for structure
1.2.2 CSS is for style
1.2.3 JavaScript is the 'interactive glue'
1.2.4 JavaScript history
1.2.5 Discussion and project
1.3.1 The best way to learn JavaScript
1.3.2 What can be done with JavaScript?
1.3.3 Where to put JavaScript code?
1.3.4 How to debug JavaScript
1.3.5 Discussion and projects
1.4.1 Creating an HTML/CSS/JS project
1.4.2 Using CodePen
1.4.3 Using Sublime Text
1.5.1 JS variables and values
1.5.2 Scope of JS variables
1.5.3 JS data types
1.5.4 Numbers
1.5.5 JS operators and expressions
1.5.6 Number Operators
1.5.7 Strings, part 1
1.5.8 String operators, part 2
1.5.9 Objects, part 1
1.5.10 Arrays, part 1
1.5.11 Functions, part 1
1.6.1 Intro: Simple JS examples to play with
1.6.2 The devtool console
1.6.3 Modifying an HTML document
1.6.4 Modifying CSS styles on the fly
1.6.5 Adding interactivity with events
1.6.6 Using built-in HTML5 APIs
1.6.7 Using third-party JS APIs/libraries
1.6.8 Working with remote data

Module 2: Adding Interactivity to HTML Documents

2.1.1 Intro: Adding Interactivity to HTML documents
2.1.2 Module 2 outline
2.2.1 Boolean values and logical operators
2.2.2 Conditional statements
2.2.3 Loop statements
2.2.4 Discussion and projects
2.3.1 Functions and callbacks
2.4.1 Intro: Adding Interactivity to a Web App
2.4.2 Adding and removing event listeners to a document
2.4.3 The event object
2.4.4 Page lifecycle events
2.4.5 Key events
2.4.6 Dealing with different keyboard layouts
2.4.7 Key and code properties
2.4.8 Mouse events
2.4.9 Form and input field events
2.4.10 Reference tables
2.4.11 Discussion and projects
2.5.1 Introducing the DOM
2.5.2 A warning about the DOM API
2.5.3 Accessing HTML elements
2.5.4 Changing the style of selected HTML elements
2.5.5 Modifying selected HTML elements
2.5.6 Adding new elements to the DOM
2.5.7 Moving HTML elements in the DOM
2.5.8 Removing elements from the DOM
2.6.1 Drawing
2.6.2 Animating
2.6.3 Animating multiple objects
2.6.4 Mouse interactions
2.6.5 Moving a player with the mouse
2.6.6 Adding collision detection
2.6.7 Adding input fields
2.6.8 Discussion and projects

Module 3: Standard HTML5 APIs

3.1.1 Intro: Standard HTML5 APIs
3.1.2 Module 3 outline
3.2.1 Arrays
3.2.2 Strings are arrays of characters
3.2.3 Iterating on array elements
3.2.4 Discussion and projects
3.3.1 Playing audio and video streams
3.3.2 Audio and video player JavaScript API
3.3.3 Examples using the JavaScript API
3.3.4 Using the webcam
3.3.5 Extended examples
3.3.6 Discussion and projects
3.4.1 The Geolocation API
3.4.2 Geolocation and maps
3.4.3 Reverse gecoding
3.4.4 Discussion and projects
3.5.1 Background music (streamed)
3.5.2 Sound effects using howler.js
3.5.3 Adding music and sound effects
3.5.4 [Advanced] a multiple image, sound and music loader
3.5.5 Discussion and projects

Module 4: Structuring Data

4.1.1 Intro: Module 4: Structuring Data
4.1.2 Module 4 outline
4.2.1 Intro: Structuring Data
4.2.2 From objects to arrays
4.2.3 Property declaration syntax
4.2.4 An object can contain another object
4.2.5 Elements, properties and methods
4.2.6 "this": accessing properties
4.2.7 Adding/deleting properties and methods
4.2.8 "this": some final thoughts
4.3.1 Classes: definition
4.3.2 The "new" keyword
4.3.3 Creating objects using modern JavaScript classes
4.3.4 Declaring a class before using it
4.3.5 Creating objects with functions (factories)
4.3.6 Static properties and methods
4.3.7 Advanced Modern JavaScript getters and setters
4.3.8 Discussion and projects
4.4.1 Class and constructor
4.4.2 Adding methods classes

Module 5: Working with Forms

5.1.1 Intro: Working with Forms
5.1.2 Module 5 outline
5.2.1 References and objects
5.2.2 Comparing two objects
5.2.3 The "global" window object
5.2.4 Built-in JS class: Object
5.2.5 Built-in JS class: Array
5.2.6 The most useful methods of the class Array
5.2.7 Built-in JS class: Number
5.2.8 Built-in JS class: String
5.2.9 The most useful methods of the class String
5.2.10 Built-in JavaScript class: Math
5.2.11 Built in JS class: Date
5.3.1 The HTML table basics
5.3.2 The HTML table JavaScript API
5.3.3 HTML forms: best practices
5.3.4 HTML forms and JavaScript
5.3.5 Discussion and projects
5.4.1 What is JSON?
5.4.2 Consuming JSON remote data
5.4.3 The LocalStorage API
5.4.4 Discussion and projects
5.5.1 A contact manager (part 1)
5.5.2 Persistence (part 2)
5.5.3 Display contacts in an HTML5 table (part 3)
5.5.4 Use a form to enter new contacts (part 4)
5.5.5 Discussion and projects
Introduction JavaScript - git

a1. Course Outline:

js.0x-w3cx - W3Cx-5of5-JS.0x JavaScript Introduction

HTML5, CSS and JavaScript are the "classic three" for Web developers and designers. JavaScript lets you add interactive features to your Web sites, including dynamically updated content, controlled multimedia, animated images, and much more.

This course is designed for anyone who is comfortable with programming concepts. No prerequisites are required though we encourage you to follow these two other W3Cx courses: HTML5 and CSS Fundamentals and  CSS Basics.

During this course, you will learn:

You will make good use of your JavaScript skills in the other 2 W3Cx courses included in the  "Front-End Web Developer" W3Cx Professional Certificate program:  HTML5 Coding Essentials and Best Practices and HTML5 Apps and Games.

In the meantime, have fun in this course!

Professional Certificate programs are series of courses designed by industry leaders and/or top universities to build and enhance critical professional skills needed to succeed in today's most in-demand fields.

Banner image for the FEWD professional certificate program.

W3C has designed a  "Front-End Web Developer" (FEWD) Professional Certificate where you will learn all of the necessary skills needed to build interactive and responsive user experiences on the Web. This program will deepen your knowledge of the 3 foundational languages that power the Web: HTML5, CSS and JavaScript.

The W3C FEWD program is composed of 5 courses:

  1. CSS Basics
  2. HTML5 and CSS Fundamentals
  3. HTML5 Coding Essentials and Best Practices
  4. HTML5 Apps and Games
  5. This course JavaScript Introduction

To get a W3C FEWD professional certificate, you must successfully pass and receive a Verified Certificate in the five courses above.

Foreword:

Michel Buffa, author of this course:
“When I work locally, with files located on my computer hard drive, I use the Sublime Text source code editor, Visual Studio Code, WebStorm, NetBeans, depending on the size of the project I'm working on.

Web editors

Traditional source code editors

You can use any source code editor that has good support for HTML, CSS and JavaScript files. For this course, you are free to use whichever you prefer. However, there are some in particular that we recommend.

Sublime text logo.

Sublime Text is a very powerful, multi-platform source code editor, it's semi-free (you can use it without paying, it will pop up a dialog asking you to buy it once in a while, but not very often). Sublime text supports hundreds of plugins to enhance its features.

Snapshot of Sublime Text editing an html/css/js project. VS Code logo.

Visual Studio Code is a free, open source, multi-platform editor by Microsoft.

Snapshot of Visual Studio code editing an html/css/js project.

Other tools

Free of charge:

Not free of charge:

a3. Online editors/IDEs

To help you practice for the duration of the course, you will use the following tools:

JSBin logo.
JS Bin is an open-source collaborative Web development debugging tool. Most of the examples you will find in this course are either on JSBin or on CodePen.

Tutorials can be found on the Web (such as  these ones) or on YouTube. The tool is really simple: just open the link to the provided examples, look at the code, look at the result, etc. And you can modify the examples as you like, you can also modify / clone / save / share them. Keep in mind that it's always better to be logged in (it's free) if you do not want to lose your work.

In our opinion, JSBin is the best online IDE for "live coding": typing and seeing what you are doing in real time, monitoring error messages in the console tab, and debugging your code. We will mainly use this tool for the live coding videos.

JSBin Example Error Code. CodePen logo.
CodePen is similar to JSBin except that its Web site includes a search engine, which is very useful for finding out what others have developed. Looking for a nice HTML5/CSS button style? Just search for "button", etc. It's also easier for us to embed HTML/CSS/JS examples in this course with CodePen than with other online IDEs; this is why so many "pens" are embedded in the course pages.

This is a great service to get you started quickly as it doesn't require you to download anything and you can access it, along with your saved projects from any Web browser. Here's an article which will be of-interest if you use CodePen:  Things you can do with CodePen  [Brent Miller, February 6, 2019].

Snapshot of a 'button' CodePen example. Plunker logo.

Plunker allows us to work online with separate files. So, when we have no choice but to use separate files, we might use this tool.

Snapshot of a Plunker example. Liveweave logo.

LiveWeave is great for writing CSS code or for embedding SVG Graphics in an HTML document, as it includes online wizards and interactive editors. We use it when we have problems with CSS shadows, CSS colors or gradients, or when we want to include an SVG arrow in a document.

Liveweave Code Editor Example. Liveweave Code Editor Example. jsFiddle logo.
JSFiddle is very similar to JSBin and CodePen in terms of features.

Other tools

There are many other online IDEs and new ones appear each year. If you want a real, heavyweight online IDE that has nearly all the features offered by "big IDEs" such as Eclipse, NetBeans and WebStorm, take a look at the  Cloud9 IDE. It's free and will enable you to develop huge projects, that can include many files, it supports uploaded assets such as images, videos and sound files. Furthermore, like Google Docs, it will support multiple users working at the same time on the same project, even on the same file. It's a real collaborative environment.

Michel Buffa, author of this course, developed a whole multitrack audio player this way. This application is available online. (See also screenshots below:)

Multitrack audio player.

100% of the development was done in a Web browser, by Michel Buffa and two friends, using the c9.io (Cloud 9) IDE (to see if online IDEs were a valuable approach):

C9 IDE example.

JavaScript debuggers

Here is a selection of tools to help debug JavaScript code. The instructor will indicate other tools in module 1 of the course.

Browser compatibility

The term browser compatibility refers to the ability of a given Web site to appear fully functional on the browsers available in the market.

The most powerful aspect of the Web is what makes it so challenging to build for: its universality. When you create a Web site, you're writing code that needs to be understood by many different browsers on different devices and operating systems!

To make the Web evolve in a sane and sustainable way for both users and developers, browser vendors work together to standardize new features, whether it's a new  HTML elementCSS property, or  JavaScript API. But different vendors have different priorities, resources, and release cycles --- so it's very unlikely that a new feature will land on all the major browsers at once. As a Web developer, this is something you must consider if you're relying on a feature to build your site.

We are then providing references to the browser support of HTML5 features presented in this course using 2 resources:  Can I Use and  Mozilla Developer Network (MDN) Web Docs.

Can I use

Can I Use provides up-to-date tables for support of front-end Web technologies on desktop and mobile Web browsers. Below is a snapshot of what information is given by CanIUse when searching for "CSS3 colors".

Example of a CanIUse browser support table (using CSS3) colors.

MDN Web Docs

MDN web docs, logo #1. MDN web docs, logo #2.

To help developers make these decisions consciously rather than accidentally,  MDN Web Docs provides browser compatibility tables in its documentation pages, so that when looking up a feature you're considering for your project, you know exactly which browsers will support it.

External resources

W3C Developers logo.

For over 20 years, the W3C has been developing and hosting and open source tools used every day by millions of Web developers and Web designers. All the tools listed below are Web-based, and are available as downloadable sources or as free services on the  W3C Developers tools site.

W3C Validator

The  W3C validator checks the markup validity of various Web document formats, such as HTML.

CSS Validator

The  CSS validator checks Cascading Style Sheets (CSS) and (X)HTML documents that use CSS stylesheets.

Laptop showing unicorn validator.

Unicorn is W3C's unified validator, which helps people improve the quality of their Web pages by performing a variety of checks. Unicorn gathers the results of the popular HTML and CSS validators, as well as other useful services, such as RSS/Atom feeds and http headers.

Link Checker

The W3C Link Checker looks for issues in links, anchors and referenced objects in a Web page, CSS style sheet, or recursively on a whole Web site. For best results, it is recommended to first ensure that the documents checked use valid  HTML Markup and  CSS.

Internationalization Checker

The W3C Internationalization Checker  provides information about various internationalization-related aspects of your page, including the HTTP headers that affect it. It also reports a number of issues and offers advice about how to resolve them.

W3C cheatsheet

The W3C cheatsheet provides quick access to useful information from a variety of specifications published by W3C. It aims at giving in a very compact and mobile-friendly format a compilation of useful knowledge extracted from W3C specifications, completed by summaries of guidelines developed at W3C, in particular Web accessibility guidelines, the Mobile Web Best Practices, and a number of internationalization tips.

W3Cx cheatsheet.

Its main feature is a lookup search box, where one can start typing a keyword and get a list of matching properties/elements/attributes/functions in the above-mentioned specifications, and further details on those when selecting the one of interest.

The W3C cheatsheet is only available as a pure Web application.

Help build the Web Platform!

Most of the technologies you use when developing Web applications and Web sites are designed and standardized in W3C in a completely open and transparent process.

In fact, all W3C specifications are developed in public  GitHub repositories, so if you are familiar with GitHub, you already know how to contribute to W3C specifications! This is all about raising issues (with feedback and suggestions) and/or bringing pull requests to fix identified issues.

Contribute

Contributing to this standardization process might be a bit scary or hard to approach at first, but understanding at a deeper level how these technologies are built is a great way to build your expertise.

GitHub Octocat logo.

If you're looking for an easy way to dive into this standardization process, check out which  issues in the W3C GitHub repositories have been marked as "good first issue" and see if you find anything where you think you would be ready to help.

First steps in Web accessibility

As steward of global Web standards, W3C's mission is to safeguard the openness, accessibility, and freedom of the World Wide Web from a technical perspective.

W3C's primary activity is to develop protocols and guidelines that ensure long-term growth for the Web. The widely adopted Web standards define key parts of what actually makes the World Wide Web work.

Shape the future

W3C Web Incubator Community Group logo.

Another approach is to go and bring feedback on ideas for future technologies: the  W3C Web Platform Community Incubator Group was built as an easy place to get started to provide feedback on new proposals or bring brand-new proposals for consideration.

Happy Web building!

a6. About W3C and the Web

As steward of global Web standards, W3C's mission is to safeguard the openness, accessibility, and freedom of the World Wide Web from a technical perspective.

W3C's primary activity is to develop protocols and guidelines that ensure long-term growth for the Web. The widely adopted Web standards define key parts of what actually makes the World Wide Web work.

A few history bits

Tim Berners-Lee at his desk in CERN, Switzerland 1994.
Tim Berners-Lee at his desk in CERN, 1994

Tim Berners-Lee wrote a proposal in 1989 for a system called the World Wide Web. He then created the first Web browser, server, and Web page. He wrote the first specifications for URLs, HTTP, and HTML.

In October 1994, Tim Berners-Lee founded the World Wide Web Consortium (W3C) at the Massachusetts Institute of Technology, Laboratory for Computer Science [MIT/LCS] in collaboration with  CERN, where the Web originated (see information on the  original CERN Server), with support from DARPA and the  European Commission.

In April 1995, Inria became the first European W3C host, followed by  Keio University of Japan(Shonan Fujisawa Campus) in Asia in 1996. In 2003,  ERCIM took over the role of European W3C Host from Inria. In 2013, W3C announced  Beihang University as the fourth Host.

As of January 2023, W3C is a public-interest non-profit organization incorporated in the United States of America, led by a Board of Directors and employing a global staff across the globe.

A few figures

As of July 2023, W3C:

W3C's core values

Committed to core values of an open Web that promotes innovation, neutrality, and interoperability, W3C and its community are setting the vision and standards for the Web, ensuring the building blocks of the Web are open, accessible, secure, international and have been developed via the collaboration of global technical experts.

The Web is amazing!

Level 2 headings may be created by course providers in the future.

People often use the words "Internet" and "Web" interchangeably, but this usage is technically incorrect.

The Web is an application of the Internet. The Web is the most popular way of accessing the Internet, but other applications of the Internet are  e-mail and ftp for example. One analogy equates the Internet to a road network where the Web is a car, the email is a bicycle, etc.  Read  this article for more details about the difference between Internet and the Web.

Check also this reminder ;)

Tim Berners-Lee invented the WEB & DARPA invented the Internet.

First photo: Tim Berners-Lee is on the left wearing a black shirt that says "I didn't invent the Internet" and Vint Cerf on the right wearing a black shirt that says "I did not invent shit. DARPA did.". Second photo: Both facing backwards, Tim Berners-Lee is on the left wearing a black shirt that says "I invented the Web" and Vint Cerf on the right incorrectly wearing a black shirt that says "I invented the Internet". He didn't.

The W3C community is passionate about creating free and open Web standards. The next video, created in partnership with Microsoft, explains why standards are important to maintain a royalty-free, Open Web Platform, as well as to help shape the Web of the future.

a4. Why accessibility is important

The power of the Web is in its universality. Access by everyone regardless of disability is an essential aspect. Tim Berners-Lee, W3C Director and inventor of the World Wide Web.

When websites and web tools are properly designed and coded, people with disabilities can use them. However, currently many sites and tools are developed with accessibility barriers that make them difficult or impossible for some people to use.

Accessibility is essential for developers and organizations that want to create high-quality websites and web tools, and not exclude people from using their products and services.

Making the web accessible benefits people with and without disabilities, businesses, and society. Accessibility is an important aspect of diversity, equity, and inclusion (DEI).

Video Introduction to Web Accessibility and W3C Standards is a 4-minute video with descriptive transcript and subtitles in over 20 languages.

Who is impacted?

Web accessibility addresses all disabilities, including hearing, learning and cognitive, neurological, physical, speech, and visual disabilities. Some examples of Web accessibility features include:

Web accessibility benefits people with and without disabilities

Web accessibility features also benefit many more users, such as:

The Web is an increasingly important resource in many aspects of life: education, employment, government, commerce, health care, recreation, and more. When Web pages, Web technologies, Web tools, or Web applications are badly designed, they can create barriers that exclude people from using the Web. More information is available in the  W3C Accessibility overview.

First steps in Web accessibility

There are many simple Web accessibility improvements that you can implement and check right away, even when you are new to this topic. Two example excerpts are provided below on this page but you can find more tips and information from W3C/WAI:

Example 1: page title

Good page titles are particularly important for orientation --- to help people know where they are and move between pages open in their browser. The first thing screen readers say when the user goes to a different Web page is the page title. In the Web page markup, they are the <title> within the <head>.

Check #1: There is a title that adequately and briefly describes the content of a page, and that it distinguishes the page from other Web pages.

Example:
1. <head>
2.   ...
3.   <title>Web Accessibility Initiative (WAI) - home page</title>
4.   ...
5. </head>

Example 2: image text alternatives ("alt text")

Text alternatives ("alt text") are a primary way of making visual information accessible, because they can be rendered through any sensory modality (for example, visual, auditory or tactile) to match the needs of the user. Providing text alternatives allows the information to be rendered in a variety of ways by a variety of user agents. For example, a person who cannot see a picture can have the text alternative read aloud using synthesized speech.

Check #2: Every image has alt with appropriate alternative text.

Example: See the W3C logo below. It contains a link that points to the W3C Web site. The text alternative is going to be a brief description of the link target.

<a href="https://w3.org">
  <img src="https://w3.org/Icons/w3c_home.png" width="72" height="48" alt="W3C Web site">
</a>

a5. Why internationalization is important

Access to the Web for all has been a fundamental concern and goal of the W3C since the beginning. It is easy to overlook the needs of people from cultures different to your own, or who use different languages or writing systems, but you have to ensure that any content or application that you design or develop is ready to support the international features that they will need.

'Internationalization' is sometimes abbreviated to 'i18n' in English, because there are 18 characters between the 'i' and the 'n'.

W3C Internationalization Activity logo.

The  W3C Internationalization Activity works with W3C working groups and liaises with other organizations to make it possible to use Web technologies with different languages, scripts, and cultures.

During this course you will learn about some basic internationalization features, such as character encoding and language declarations. If you don't use those features you will create barriers for people from different cultures who are trying to access your content. This is important even if you think you are only designing for a specific community -- communities are made up of diverse individuals, and the Web stretches worldwide.

Unicode

Unicode symbols snapshot.

Text in a computer or on the Web is composed of characters.  Characters represent letters of the alphabet, punctuation, or other symbols.

Unicode is a universal character set, ie. a standard that defines, in one place, all the characters needed for writing languages in use on computers. It is a superset of all other character sets that have been encoded.

As a content author or developer, It is important to clearly distinguish between the concepts of a character set versus a character encoding. You should nowadays always  choose the UTF-8 character encoding for your content or data. This Unicode encoding is a good choice because you can use a single encoding to handle any character you are likely to meet. This greatly simplifies things.

Essential steps in Web i18n

You find below three examples (and checks!) to help you to ensure that your Web page works for people around the world, and to make it work differently for different cultures, where needed. Let's meet the words 'charset' and 'lang', soon to become your favorite markup ;)

Example 1: Character encoding declaration

A character encoding declaration is vital to ensure that the text in your page is recognized by browsers around the world, and not garbled. You will learn more about what this is, and how to use it as you work through the course.  For now, just ensure that it's always there.

Check #1: There is a character encoding declaration near the start of your source code, and  its value is UTF-8.
Example 1:
<head>
  <meta charset="utf-8"/>
  ...
</head>
Example 2: Primary language declaration

For a wide variety of reasons, it's important for a browser to know what language your page is written in, including font selection, text-to-speech conversion, spell-checking, hyphenation and automated line breaking, text transforms, automated translation, and more. You should always indicate the primary language of your page in the <html> tag. Again you will learn how to do this during the course.  You will also learn how to change the language, where necessary, for parts of your document that are in a different language.

Check #2: The HTML tag has a lang attribute which correctly indicates the language of your content.
Example 2: This indicates that the page is in French.
<!doctype html>
<html lang="fr">
  <head>
  ...
Example 3: Cultural bias

People around the world don't always understand cultural references that you are familiar with, for example the concept of a 'home run' in baseball, or a particular type of food. You should be careful when using examples to illustrate ideas.

Also, people in other cultures don't necessarily identify with pictures that you would recognize, for example, hand gestures can have quite unexpected meanings in other parts of the world, and photos of people in a group may not be representative of populations elsewhere.  When creating forms for capturing personal details, you will quickly find that your assumptions about how personal names and addresses work are very different from those of people from other cultures.

Check #3: If your content will be seen by people from diverse cultures, check that your cultural references will be recognized and that there is no inappropriate cultural bias.

Don't worry!

The following 7 quick tips summarize some important concepts of international Web design. They will become more meaningful as you work through the course, so come back and review this page at the end.

  1. Encoding: use the UTF-8 (Unicode) character encoding for content, databases, etc. Always declare the encoding.
  2. Language: declare the language of documents and indicate internal language changes.
  3. Navigation: on each page include clearly visible navigation to localized pages or sites, using the target language.
  4. Escapes: use characters rather than escapes (e.g. á á or á) whenever you can.
  5. Forms: use UTF-8 on both form and server. Support local formats of names/addresses, times/dates, etc.
  6. Localizable styling: use CSS styling for the presentational aspects of your page. So that it's easy to adapt content to suit the typographic needs of the audience, keep a clear separation between styling and semantic content, and don't use 'presentational' markup.
  7. Images, animations & examples: if your content will be seen by people from diverse cultures, check for translatability and inappropriate cultural bias.

You will find more quick tips on the  Internationalization quick tips page. Remember that these tips do not constitute complete guidelines.

Internationalization checker

When you start creating Web pages, you can also run them through the W3C's Internationalization Checker.  If there are internationalization problems with your page, this checker explains what they are and what to do about it.

1.1.1 Introduction - Module 1: Intro to JavaScript (1:46)

Hello everyone, welcome to the wonderful world of JavaScript!

In this module, after giving a brief history of JavaScript and Web browsers, we will explain how HTML, CSS and JavaScript are related to one another. We will see JavaScript in action through numerous interactive examples. We have made sure that all examples can be run directly in the course's Web pages.

Hey, we're teaching Web technologies, after all! We will do that throughout the course, as you will be asked to change some code, tweak this or that example, even if the code details are not fully explained at first. Because, this is how we recommend beginners to learn JavaScript: first look at examples, then tweak some code and see the results of the changes. You will certainly encounter error messages, but no worries, as I will teach you how to debug JavaScript code using your browser's devtool console.

In this first module, you will also learn about JavaScript variables, operators and expressions, and have a first lesson about functions, objects, arrays and strings.

These are the basic concepts of JavaScript and are shared by many other programming languages. We'll then develop together, and step by step, an interactive graphic tool that will use many different features from JavaScript, HTML and CSS. Let's start having fun with JavaScript, now :-)

1.1.2 Module 1 outline

If you thought that a Web browser could only display HTML documents, you were mistaken! ;)

Behind the scenes, an HTML document is nearly always associated with two other standard languages of the Web: CSS and JavaScript. Before looking at the guts of JavaScript, we introduce the basics and play with many examples. We will also have a first look at the browser devtools, and discover how JavaScript is useful.

A word of caution: you will not learn JavaScript in full detail in this course! This is an introductory course designed to help you understand the basic concepts of the language.

1.2.1 HTML is for structure

The "Hyper Text" part: links!

HTML5 logo.

A fundamental key to the World Wide Web is the concept of "hypertext". Hypertext is built on the idea of linking information together, not unlike using footnotes, but far easier and more flexible. The idea is to "mark up" your document with links and define how to break it down into different segments (chapters, sections, paragraphs, tables, figures, etc.)

That's why, in 1989, Tim Berners-Lee began to create a definition of HTML: Hypertext Markup Language, to provide a simple, uniform way to incorporate hyperlinks into a text document.

Illustration of hypertext documents.

He envisioned a technology that would facilitate thoroughly interconnected documents. He wanted authors to be able to connect an idea in one document to the source of the idea in another, or connect a statement with the data that backs up that statement. Traditionally this kind of thing was done with footnotes and bibliographies, which can be cumbersome. This information should be easily transferable from one place to another, so that in reading one document, it is easy to access everything related (linked) to it. Tim Berners-Lee imagined a "Web" of interconnected documents.

He used the metaphor of a Web to emphasize the importance of connections between documents. It was not just a long list of details, but rather a sea of information stretching out in all directions. This sea of information was navigated by a new tool called a "browser".

The "Markup" part: elements, tags and attributes!

The "M" in HTML stands for "Markup", but what does Markup really mean?  Essentially it means to annotate a document with extra information: things like where different sections and paragraphs begin and end, which part is the title, which things should be emphasized and so on.

There are many ways to markup a document, but HTML borrows a technique from an ancestor language, SGML (Standard Generalized Markup Language), which uses angle brackets ("<" and ">") to separate the annotations from the regular text.  In HTML these annotations are called "tags".

For example, consider the following chunk of HTML code (note: you can edit the source code and see the resulting Web page updating in real time):

Codepen: A Tale of Two Cities.
CodePen: A Tale of Two Cities.
HTML:
Source Code:
<body>
  <h1>A Tale of Two Cities</h1>
  <p>
  It was the best of times, it was the worst of times, . . . .
  </p>
  . . .
  <p>
  . . . it is a far, far better rest
  that I go to than I have ever known.
  </p>
</body>

If you eliminated everything in between the angle brackets from the text, for most purposes it would still read the same:

A Tale of Two Cities It was the best of times, it was the worst of times . . . . . . . . . . it is a far, far better rest that I go to than I have ever known.

Once you know that everything in angle brackets is "meta-information", it gives you a lot of flexibility. You can put a lot of different things in between those brackets without any of it showing up (directly) in your finished document. And though you don't usually see directly what's in those angle brackets, they can often have a big effect on how your Web page looks, as well as how it responds and interacts with you.

Here is another, more generic example:

Notes:

CodePen: Who Am I?
CodePen: Who Am I?

Try it out!

It's time to write your first HTML code :-)

You can use a source code editor like Sublime TextAtom,brackets or any lightweight text editor. You can also use more "professional" tools such as  Visual Studio Code NetBeans Eclipse WebStorm, jetbrains, etc.

To try out the simple examples from this course, I'd suggest using an online IDE such as JSBinCodePenPlunker, etc.

During the course, we will show you how to test out simple code snippets in online IDEs, but we will also teach you how to organize your code with folders and files.

The next lesson shows how you can use JSBin, CodePen, and SublimeText in order to test the HTML code provided earlier in this section.

1.2.2 Live coding video: using the course's tools (6:25)

JSBin live coding.

In this lesson, I will show you how to try and tweak the HTML example from the Web page, the one from the course.

I propose first to show you two online tools that are very practical for editing some HTML, CSS and JavaScript code, and seeing in real time the result of your modifications.

In the second time, I will show you how to use the regular source code editor for editing HTML5 files directly on your hard disk.

JSBin template and My Home Page.

In order to use the JSBin.com tool, that is the first one I recommend, you will open a new tab with your browser and you go to JSBin.

JSBin live web site, My Home Page.       JSBin, My Home Page and Who Am I?

For the moment, we are going to use only HTML code. If you want to try the example from the course, just copy and paste the code in the HTML part on JSBin, and you see the result instantly. This is very practical because then you can modify the content, you can change the different values, the different elements... You can type your own text or your own HTML elements and attributes, and so on.

You can also save your work using the "Save snapshot" menu, and if you created an account, it's completely free. And you will be able to find your work the next time. You can share the URL; you can share the Web addresses of your work with friends. They won't to be able to break what you've done because it will be create a new version or clone your own work so that your friends can work on what you've done.

CodePen.io has search engine.

The other online tool, that is very practical, is codepen.io. This one is maybe nicer but I think that JSBin is more practical for typing code. This one is interesting because it's got a search engine, and you can look for existing examples made by others.

CodePen.io, My Home Page.

I just typed "button", and here I can see an example that create buttons. I can see the HTML code; CSS code and I can learn by looking at these examples.

My Home Page, Who am I?

In our case, if you want to create a new example, you just open codepen.io, you click on the "New Pen" button and you copy the HTML code in the HTML part on the editor, and you see the result. Don't forget to save to create an account also. And here, you can download the result for editing that offline if you would like using the "export" option (bottom right of screen in 'edit CodePen' mode).

CodePen, export to zip file.

"Export.zip". With CodePen, I've got a zip file and in the zip file, I've got index.html here. And if I look at the source, it's exactly the source from the example.

With JSBin, you can also download your result: "Download". And in that case, the name of HTML file will be built using the name of your example in the address bar of your browser. But if you click on it, you've got the same result. You've got an HTML file that is local in your hard disk that you can edit later on. You can see that the source code is nearly the same. The only difference is some comments that have been inserted at the top of the file. And if you want to create this example locally on your hard disk, I recommend to install some source code editor. In the course, we propose different ones.

The one I use is "Sublime Text". You go to SublimeText.com Web site. You download, it's free. You can also buy an enhanced version but the free version is ok. You download it. And once it's installed, you can work with it locally. I'm going to show you how to do that. What I recommend is that you create a directory somewhere.

Live web development using Sublime.

Here, I'm creating a directory on my desktop... so, a new directory: "Example 1". And inside that directory, I will create the HTML file. I use the "New file" option from Sublime Text. I copy and paste the code. I use "Save as" and i will save the page as index.html file... you can name it as you like. "index" is very common for the main page of Web site. I then go to the desktop to the « Example 1" directory and i save the file.

Sublime example opened in browser.

And from Sublime Text, you can use the right click "Open in browser" and you can see the result. If I change the code here, my home page "Hello W3Cx students" and I want to see the result, I just save 'CTRL s' or command s on my Mac. I do "Open in the browser" or I can just reload the page, and I can see that I changed the content of the HTML file.

JSBin, Hello W3Cx students.

This is how you can work. Or you can also directly open an example you downloaded from JSBin or from CodePen. My download directory, I can find back the file that I downloaded when I was working with CodePen.io. And here, I have got HTML file. This is the code I prototyped, I tested first using an online environment.

1.2.3 HTML elements

If you are sitting at a coffee shop next to a table of Web developers, you will probably often hear these three words: "Elements", "Tags" and "Attributes".

"Elements" are the pieces themselves, i.e. a paragraph is an element, a header is an element, even the body is an element. Most elements can contain other elements, as the body element would contain header elements, paragraph elements, in fact pretty much all of the visible elements of the Document Object Model (that developers refer to as the "DOM").

As an example, let's look at a simplified version of the last HTML code we presented earlier:

Source Code:
<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Your first HTML page</title>
    <meta charset="utf-8"/>
  </head>
  <body>
    <h1>My home page</h1>
    <p>Hi! Welcome to my Home Page! My name is Michel Buffa, I'm a
      professor at the University of Côte d'Azur, in France, and I'm also
      the author of three W3Cx MOOCS.</p>
  </body>
</html>

Click the red circle next to HTML to unfold this HTML document structure (we can also say "see its DOM structure"):

HTML, red circle in JSBin.

Consider the figure above. It contains a single html element. It turns out this includes within it the entire content of your html file. If you click on the "html" red node, you'll find that it contains two components, a head and a body.

HTML tree structure.

Clicking on each of those will reveal their respective contents. This structure is what we computer scientists call a "tree". Any given element (except for the outermost "html" element) is wholly contained inside another element, referred to as the "parent" element. Not surprisingly, the elements contained within a given element are its "child" elements. And, yes, children of a common parent are often referred to as "siblings".

HTML, with head & body.

Thus, in the example above, the top element is the html element, which contains just two elements, the head and body.  The head element contains a title element and the body contains an h1 element and a p element.  In a more typical example, the body would contain many more children, but for our purpose this is enough. p is for "paragraph" (the text between <p> and </p> will be separated by some space before the next element is displayed in the final HTML page rendering), h1 means "heading level 1", and will be rendered by default in bold with a bigger char size than any other text element, etc.

That may be a great picture, but how do we represent such a structure in a text file?  Well, that's where "tags" come in.

1.2.4 HTML tags

Thinking about HTML tags.

<html>

<BODY>

<p>

<em>

<i>

<b>

"Tags" are what we use to organize a text file (which is just a long string of characters) such that it represents a tree of elements that make up the html document. Tags are not the elements themselves, rather they're the bits of text you use to tell the computer where an element begins and ends. When you "mark up" a document, you generally don't want those extra notes that are not really part of the text to be presented to the reader.

HTML borrows a technique from another language, SGML, to provide an easy way for a computer to determine which parts are "MarkUp" and which parts are the content. By using "<" and ">" as a kind of parentheses, HTML can indicate the beginning and end of a tag, i.e. the presence of "<" tells the browser "this next bit is markup, pay attention".

Whatever that tag (or "open tag") does, it applies to the content following the tag. Unless you want that to be the entire rest of the document, you need to indicate when to stop using that tag and do something else, so "<" and ">" are used again. Since elements are typically nested within other elements, the browser needs to be able to distinguish between the end of the current tag and the beginning of a new tag (representing a nested element). This is done by adding a "/" right after the "<" to indicated that it's a "close tag". To indicate the beginning and end of a paragraph (indicated by the single letter "p") you end up with something like this:

> <p>This is my first paragraph!</p>

The browser sees the letters "<p>" and decides "A new paragraph is starting; I'd better start a new line and maybe indent it". Then when it sees "</p>" it knows that the paragraph it was working on is finished, so it should break the line there before going on to whatever is next.

For example, the "<em>" tag is used for element that needs Emphasis.  The  "<" and ">" indicate that this is a tag, and the "little bits of text" in between tell us what kind of tag it is.  To completely describe the element, it needs an open and close tag, and everything in between the tags is the contents of the element:

Diagram of an element.

Most tags have open and close versions, but there are a few strange ones.  For more info, we strongly recommend that you follow the W3Cx HTML5&CSS Fundamentals  course, but we generally refer to the strange ones as "self closing" tags. Usually these tags represent an element that is completely described by its attributes, and thus there is no need for other content.  So if you see something like this:

> <img src="https://goo.gl/pVxY0e" alt="Floating Flower"/>

… then you should know that the slash at the end of the open tag is sort of a shorthand for a close tag, so you won't see any other indication that this element is now complete. There are also a few tags that don't even use the "/" at the end, they just don't have any close tag at all.  This works because all of the information this tag needs is declared in an "attribute".

The <img> tag is one of them, the "/" at the end is optional and can be removed entirely, this will still be  valid HTML5.

> <img src="https://goo.gl/pVxY0e" alt="Floating Flower">

These elements, without a "/" at the end, are called "void elements". They are : area, base, br, col, embed, hr, img, input, link, menuitem, meta, param, source, track, wbr.

1.2.5 HTML attributes (6:01)

Most of what you can learn about HTML attributes is presented  in the three W3Cx MOOCs about HTML5 (fundamentals, coding essentials, and advanced techniques), but we can introduce the idea briefly in this JavaScript course. Basically, a given element on your Web page can be distinguished by any number of unique or common attributes. For example, we've already seen how an image can be inserted in your Web page, and in that example we used the width attribute of the <img> tag in order to constrain the width of the image:

> <img src="https://pbs.twimg.com/profile_images/110455194/n666194627_2302_400x400.jpg"
>   width=200 alt="Michel Buffa plays rock&roll">

As you might guess, the <img> tag also has a height attribute, as well as others. Different HTML tags share some common attributes that we'll meet in the next section, which are particularly useful when coupled with CSS (id  and class) for applying graphic styles (color, shadow, etc.), but can also  have specific attributes (for example: the src attribute can be found in the <video>, <audio>, <img> tags but not on a <p> or on an <h1> tag!)

Try changing the value of the width attribute in the example below, or add a height attribute, and see the result:

CodePen: pbs.twing profile image.
<img
  src="https://pbs.twimg.com/profile_images/110455194/n666194627_2302_400x400.jpg" 
  width=200 
  alt="Michel Buffa plays rock and roll">
Your first HTML page.

In this lesson, I will show you how to create from scratch an HTML page using some of the most common HTML tags. I will use an online tool for doing that. Like that, you will see some live preview of what I'm doing. I'm using "jsbin.com", and I will work on the HTML part of the editor, and you will see in the output part the results of what I'm doing. JSBin created for me a first template. Most common HTML5 starts with <!DOCTYPE html>, that tells the browser that the file is going to render will be an HTML5 file.

Example: HTML, head and body.

Then, you've got a first element that is called <html> and you've got the closing corresponding element that is </html>. It's a common way with markup languages to have opening and closing tags. And as you saw earlier in the course, when you've got such elements, they will have children. In the HTML tag, we will have a head element and a body element.

JSBin example; template: head and body.

We've got a head element, and an empty body element, here.

Example: HTML, head and body.

In the <head>, usually, we specify the title: "First HTML page". And this title is what will be displayed when you put the cursor on a tab in your browser. Then, it is a good practice to indicate the language: "lang=en" (English). Like that, you will be better indexed by search engines. And then in the body of the document, we will add some really visible content. I start with the very common element, a very common tag.

Example: HTML, head and body.

The tag is the notation between < and > signs and the element is the conceptual thing - like, I'm writing a heading. "This is my first page". This is a heading 1, and you've got 6 levels for typing titles. And also very common, is a paragraph: <p>, </p>, I typed the opening and closing tags. And I enter "this is a paragraph". I write a subheading h2: "My hobbies are:". Ok, you see that the size of headings is different here. And if, in the paragraph, if I go to the next line, this doesn't have an effect here.

The only return to the next line I can do is, either write another paragraph inside the paragraph, or I can use another tag that is useful just for going to the next line without letting some space between paragraphs, it's called <br>. And <br> in that case, I can go to the next line.

Example: HTML, head and body.

If I want to enumerate my hobbies, a very common practice is to use lists. In HTML, you've got an unnumbered list that are composed of list items. For example: "I play guitar", "I code video games". These are my hobbies. "I like movies", etc. If I want, instead of an unnumbered list, a numbered list, I can use an order list.

Example: HTML, head and body.

With <ol> instead of <ul>. In that case, you can see numbers. Another very common element is the "img" tag that is useful for inserting an image in your Web page. The tag "img /" is a self-closing element, so you don't have an opening tag and a closing tag. And you will use different attributes for specifying the size of the image. For example, I want an image of 100 pixels width. You can indicate a description of an image, and this is a good practice. I'm going to insert a picture of Leonardo Di Caprio in this example.

And you've got other different attributes that will not be detailed this time but I recommend you to follow the HTML5 intro. Course and the other course about HTML5 provided by the W3Cx. In order to indicate which image, I want in this page, I need to use the "src" attribute that will take as a value the URL of the image.

For this example, I'm using the images.google.com for finding an image of Leonardo. I pick an image of Leonardo. I display the image and I've got the URL, here, in the address bar. I just copy and paste it and I've got Leonardo Di Caprio in my document.

1.2.6 CSS is for style (1:34)

Hi!

In this short video, I will show you quickly the principle of CSS. I recommend you follow the CSS Basics course from W3Cx if you want to learn this technology more deeply.

HTML is for structure. CSS is another language, by W3C, that it's useful for specifying the look and feel of these elements. How do they fit together...How many spaces between them...What color to use, and so on ...

Example: HTML, head and body.

I'm just going to copy and paste some examples here, and you saw that the look and feel of the document changed. And it's, now, using shadows, borders, background colors, different character fonts and so on.

Example: HTML, head and body.

The CSS file, here, is just using what we call "rules". A rule is a selector, so this means for all "h1" elements in the page, I want to apply these properties.

And each property has a name 'color', and a value 'red'. So, you indicate, for each different elements you selected (the "h1", the "h2", the "p" the paragraph, for the image). You then indicate what you want to change. For example, for the image in the document, you indicate a box-shadow.

CSS: Cascade Style Sheet.

CSS, or Cascading Style Sheets, is a style sheet language used to describe the way an HTML or XML document should look to a user. CSS is where you specify the color, size, spacing, font and other visual aspects of the content that you create in your markup language document.

Usually, you see CSS used alongside HTML to describe the way a Web page looks and feels. You can have a Web page without CSS, but it would be very difficult to make it look the way you want with just HTML. This is why almost every Web page is a combination of HTML and CSS.

CSS • /si-ɛs-ɛs/ • noun 

Stands for "Cascading Style Sheets". A style sheet language for describing how to display an HTML document.

Let's look at an example!

Let's take the (ridiculous) Michel Buffa home page again: Notice the use of some HTML tags: h1, img, p, body etc.

Now, we can add some "CSS rules" to the HTML, and see that the appearance of the resulting HTML page rendering is rather different (click on the HMTL/CSS buttons to see alternatively the HTML or the CSS code, remember you can always make changes to the code: change the color in the CSS part, etc.):

Example CodePen: My Home Page.
CodePen: My Home Page

If you click on the CSS button on the top left of the previous codepen example, you see the CSS rules that have been applied to the HTML document. Let's look at the first one:

Source Code:
1. h1 {
2.   color:red;
3.   background-color:lightGreen;
4.   border:12px solid violet;
5.   padding: 5px;   
6.   border-radius: 15px;
7.   text-align: center;
8. }

This rule turns all the h1s in the document into red text, centered horizontally, on a light green background, with a violet border of 12 pixels (a solid border, not a dashed one), and this border has rounded corners made of arcs of a circle whose radius is 15 pixels.

The part before the opening brace (line 1) is the "CSS selector", it indicates the elements that have their properties changed according to what is inside the braces.

The part inside the braces is a set of properties and values that are useful for setting the look and feel of the selected elements.

Line 2 for example, says that all h1s are colored in red.

CSS rules are applied in sequence

After the previous rule is applied, then the second rule is taken into account, then the next, etc. In this way, you can see that all h2s is in brown (second rule).

The third rule uses what is called "a multiple selector":

1.  p, h1, h2 {
2.    font-family: cursive
3.  }

This one says that all p, h1 and h2 uses a cursive font character. The "," means "and also".

This is also how we indicate in the last rule that images and paragraphs should be moved to the right 50 pixels (property margin-left: 50px).

The id and class attributes

Basically, any given element on your Web page can be identified uniquely with an 'id' attribute, or grouped with a class of other elements by setting the 'class' attribute.

1. <p id="paragraph-1" class="regular-paragraphs">
2.   Call me Ishmael . . .
3. </p>

The paragraph above has a unique identifier: the id attribute whose value is "paragraph-1" and is part of a class of "regular-paragraphs". The letters inside the quotes have no meaning to the computer, they just need to be consistent. They are actually strings.

Again, the fact that the computer does not care what we put in those strings (except for some restrictions) means we can use them to convey meaning to a human developer. I could just as easily have said id='x' and class='y', but anyone looking at that would have no hint what the significance of x and y are. Best practice is to name these things to increase clarity, consistency and brevity.

Let's look at a modified version of Michel Buffa's home page example:

Example CodePen: Update CSS Rules.
CodePen: Update CSS Rule

The last two rules first target the element whose id is 'hobbyTitle', in our case it's the second h2 element:

1. <h2 id="hobbyTitle">My Hobbies</h2>
And here is the CSS rule:
1. #hobbyTitle {
2.   font-family: 'caveat';
3.   font-size:40px;
4.   text-shadow: 4px 4px 2px rgba(150, 150, 150, 1);
5. }

Line 1 uses the "#" character in the selector, meaning that we're going to select an element by its id attribute. In this case, the selector equal to #hobbyTitle, selects the element that has an attribute id="hobbyTitle".

In that case, we use a funny char font called 'caveat' we took from the Google font service (see fonts.google.com), and in order to be able to use it in a font-family CSS property, we included its definition using a <link> tag in the HTML part of the document:

Source Code:
1. <head>
2.   <title>Your first HTML page</title>
3.   <meta charset="utf-8"/>
4.   <link href="https://fonts.googleapis.com/css?family=Caveat"
5.   rel="stylesheet">
6. </head>

The last rule targets all elements that have an attribute class="funny". Notice they can be different elements, we can have a p and an h3 element that have the class="funny" attribute:

1. .funny {
2.   color:purple;
3.   font-family: 'caveat';
4.   font-size:40px;
5. }

This rule changes the color, font family and size of two out of three paragraphs in the HTML element:

1. ...
2. <p class="funny">I also play electric guitar and love
     coding WebAudio applications...</p>
3.   ...
4. <p class="funny">Music, Movies, Video Games, Traveling, Family, etc.</p>

There are many, many, many different CSS properties in existence, and many different ways to select elements. We recommend that you follow the W3Cx CSS Basics and  HTML5&CSS Fundamentals courses to learn more about CSS and about HTML5 basics.

Where can we put the CSS rules: in the HTML file? in another file?

You can do both!

You can embed the CSS rules between a <style>…</style> tag, located inside the <head>…</head> of the HTML documents, like in this example:

Example CodePen: Update CSS Rules.
CodePen: Update CSS Rule

This is OK if you do not have too many CSS rules. In general it's better to put the CSS rules in one or more separate .css files, like this ( open this example in Plunker)

Snapshot of a code editor showing a separate CSS file.

Note that when you use an online IDE, you usually type/paste the CSS rules in a "CSS tab" in the online editor, and it hides all the "plumbing" for you (except the more complete ones such as  Plunker or  AWS Cloud9 that enable you to manage files in the cloud).

1.2.7 Live coding lesson: mixing HTML and CSS (3:49)

Example CodePen: Update CSS Rules.

In this lesson, I will show you how you can include CSS in your HTML file, because we used online tools that hide, in a way, the location of the different languages.

Example CodePen: Update CSS Rules.

If you take this example we described in the previous video, and if I export it using CodePen...and if I look at the zip file that has been downloaded, you can see CSS file are located in the subdirectory and in a .css file. This is a common way for organizing source code when you make a project with HTML and CSS.

Example Web Page: My Home Page.       Example source code: My Home Page.

And if we open the "index.html" file, you can see that, what is really going on if we look at the source code. Actually, in order to include CSS file in an HTML file, we use the "link" tag with the attribute "rel = "stylesheet" and "href" = the name of the file.

CodePen: Link to external CSS Stylesheet.

Here, it means the "style.css" file located in the "css" subdirectory. If I open this project with Sublime Text ... I go to the directory I've just downloaded, and if I open the directory, I can see my hierarchy, here. The "index.html" file that includes the .css file.

CodePen: Example style.css.

And if I open the "style.css". I can see the CSS content here. And it's interesting to use a real source code editor because you've got auto-completion on the name of the properties: "background-color". You can use also some wizard for indicating or choosing the colors. If I take this color, it will give me directly the value and so on. You can edit your CSS, edit your HTML and when you save the result, you can open directly in your browser the file and see the result.

Example CodePen: Update CSS Rules.

Here, I change the background-color of the heading 1. You can also use directly in your HTML, the CSS rules. In that case, instead of using the "link" element, you use the "style" element. <style>, </style>, and like that you can directly include, in the HTML file, the style. I've got "h1" CSS rule, that will indicate how the "h1" will be rendered and I'm no more including an external file.

Example CodePen: Update CSS Rules.

If I save this and "Open in the Browser", I've got the same result here for the "h1". And if I look at the source code, I will see directly in the HTML, the CSS rule.

To sum up, you can have your CSS in external file or inside the HTML file using the "style" element.

1.2.8 JavaScript is the "interactive glue" (4:22)

Hello, your Web browser can only understand three different languages when you ask for a Web page to be rendered in the browser.

Example: edx studio; using 3rd party JS libraries.

Let's take this document for example. We type the URL here, and the document arrives from a remote machine. And this document is a HTML source code that has been interpreted and rendered to give you a nice-looking document.

In this HTML, you can have CSS rules for specifying the look and feel of the document as we saw in the previous example. But you can also have Javascript code and Javascript when its run inside the browser can act as a glue between HTML and CSS. We will use Javascript to provide interactivity to the documents.

Example: CodePen; using JavaScript, before change.       Example: CodePen; using JavaScript, after change.

In this example, the first one on this page, I can click to change the content of the document. We modify what we call the document object model. It's exactly the set of elements that compose the page. When I click, I change the content of the heading. That was previously equal to 'My home page', and then when I clicked on the button, (this is an HTML button), this is how in Javascript we can indicate that we are going to do something when you click on it. In that case, it means call the function named "changeTitle" and the function is here defined between <script> and </script> elements.

In this example, the Javascript lies inside the HTML file and the function is a piece of code that can be run on different conditions. A click on the button executes these two lines of code here. 1st use: interact with the document object model, interact with the HTML elements of the page, add new ones, modify some existing ones, remove some elements.

Example: CodePen; using JavaScript, before change #2.       Example: CodePen; using JavaScript, after change #2.

It can be also use for interactive for the CSS styles of the page. In this example, I click on the button. And instead of modifying the content of the page, I just change the look and feel. I change the CSS style of the heading. If we look at the code quickly without going into details: when I click on the button "button onclick", I call the "changeTitleCSSStyle" function.

In this function will use the "style" attribute of some elements that correspond to the heading 1 and it will indicate that we want the text to be black, the background color to be yellow and the border to be 5 px wide, dashed and colored in red. This was just an example. What we can do with Javascript goes much further than this simple example. We can work with remote data, upload and download data from a remote server. We can use it for making multimedia players, for writing video games, for making music, for building tables on the fly to display some dynamic data that you came after, for example, we enter some text in the search form, etc.

Example: index.html: update heading using JavaScript.

During week 1, we will see other examples with different sort of applications of JavaScript. And, we will first give some explanations about variables, functions, some basics events handling: how to detect a click? how to debug the code? What tools we're going to uses for writing Javascript code, and so on. JavaScript is the third of the "magic trio": HTML5/CSS/JavaScript. It is the only programming language a browser can run (without installing any plugins or extensions), and it's a real standard of the Web (even if not standardized by the W3C).

Why do we call it "the interactive glue between HTML and CSS"?

JavaScript is the perfect glue.

Actually, this description does not do justice to JavaScript, which can do far more than just act as glue. JavaScript can be run outside of the browser (on a nodeJS interpreter on a remote server, or in scripts run by the operating system), but for this intro course, we focus on "JavaScript" in the browser.

In the browser, JavaScript lies between HTML and CSS and will be used together with these two languages. Let's take a look at two small examples:

Example #1: push the button to modify the heading of the page.

Example: index.html: update heading using JavaScript.
CodePen: Use JS to Modify CSS

Example #2: push another button to modify the CSS style (color, background-color, border) of a paragraph in the page.

Example: javascript: update button to modify CSS style.
CodePen: example JS update button to modify CSS style.

We have a closer look at how these examples work in the subsequent parts of the course. These examples are just here to show you how JavaScript can interact with the HTML content and the CSS styles of a Web document. Finally, note that, in these examples, the JavaScript code is located in the HTML of the document.

1.2.9 JavaScript history

JavaScript remains the most commonly used programming language with 67.7% of developers employing it in 2020 (see this  survey's results).

How and why JavaScript was created

Created out of necessity, it is used to build 97.4% of websites, including some of the world's largest, like Facebook and YouTube. Without it, we would not have popular and useful web apps such as Google Maps and eBay.

Photo of Brandan Eich, creator of JavaScript.       Cover page of the Netscape JavaScript 1.2 book. Year 1995.       Netscape logo.

JavaScript was born in 1995 as part of the work of Brendan Eich's team at  Netscape (the ancestor of Mozilla). At that time, Netscape (a hero), in association with Sun MicroSystems (another hero), provided popular server and client-oriented solutions (Netscape Navigator, ancestor of  Firefox) which depended on Java. (Sun Microsystems, the company that created the Java programming language, no longer exists, having been bought by Oracle Corporation in 2009.)

dotJS 2017 - Brandan Eich - A Brief History of JavaScript.
dotJS 2017 - Brandan Eich - A Brief History of JavaScript
Sun Microsystems logo.

But Netscape realized that Java wasn't a suitable language for in-browser use. Netscape thought of JavaScript at the beginning, as a lightweight Java.

JavaScript was initially inspired by Java, but in fact only some naming conventions remained the same. We highly recommend not even trying to look for similarities - this is actually a bad way to start learning JavaScript! We'd rather just say that the only real commonality between these two languages is their names. If you are coming to this course from Java, leave the Java thinking behind!

JavaScript quickly became a success following its first appearance in  Netscape Navigator 2 in March 1996, and it was quickly integrated into other popular browsers. Microsoft also created its own version named JScript (and shipped it with Internet Explorer 3 in 1996 -- It was a dud).

Snapshot of a web page in Netscape Navigator 2.
Netscape Navigator 2 in 1996, with big buttons and plain HTML pages. CSS did NOT exist at that time!
Snapshot of a web page in IE 3.
Internet Explorer 3 in 1996 - look at the official Yahoo page :-) CSS did NOT exist at this time!
ECMA logo.

Towards the end of 1996, JavaScript was standardized by ECMA as the EcmaScript standard.  So no matter whether you see it called JavaScript or EcmaScript, don't worry, it's the same thing. EcmaScript has continued to be released right up to the present day. MS still didn't play ball.

JavaScript detailed timeline.

The present: what is the current version? What about ES6/ES2015/ES2016/ES2017/ ES2018/ES2019/ES2020/ES2021/ES2022? Are these the new names of JavaScript?
Since 1996, multiple versions of JavaScript have appeared. For a long time, the stable version supported by all major browsers deployed on computers and smartphones was EcmaScript version 5 from 2010, but in 2015, a new version known first as EcmaScript 6 or ES 2015 came out with lots of new features (classes, etc.). Since then, every year a new version is published, with some adjustments/novelties. The latest official version is ES2021.
Back in 2015, ES2015 was a pseudonym for the 6th version of the JavaScript programming language to be approved by ECMA International, the standards group responsible for vetting and approving different versions of the language. In June 2015, ECMA International approved the 6th edition of the language. The name, ES2015, was used because the latest version of JavaScript is identified as the 2015 version of ECMAScript (the alternative name for JavaScript).  Read this blog post about all these naming incongruities!
At the beginning, ES2015 was referred to as ES6 and before that, Harmony. Moving forward, ES suffixed with the year of the latest approved standard is the naming convention. The next version was called… ES2016, etc.!

Browser vendors do not wait that ECMA standardizes a version as they start implementing it during the standardization process, which can take months or years (they also contribute to the standardization process all along its life cycle).

The new open development process adopted by the ECMA TC39 committee decided that every year, a new version will occur. This annual publication rate has been effective since 2015.

The current edition of the ECMA-262 standard is the 13th edition, published in June 2022 and is known as ES2022.

Beware: even on recent Web browsers the whole supported feature sets of the latest versions are generally not completely implemented, as it takes time for browser vendors to follow the standards!

Current support for ES2020/ 11th version (June 2020):

There is no easy-to-read table of current browser global support, but caniuse.com can be used to check feature by feature which browsers support them. For example,  this link shows the support for the new "javascript private class fields" feature.

Up to date browsers usually support more than 90% of the features from the version corresponding to the previous year. For example, in 2020, there is good support for ES2019, while certain features from ES2020 won't be implemented before some months.

Which version will we learn?

First of all, this is an introductory course! Not all features of JavaScript need to be covered, in particular the ones that you cannot run in your browser without using advanced tools (there are tools, such as  Babel, that can turn ESxxxx source code into ES5 code that can be run in nearly any browser, but they are tricky to use and not for beginners).

We will cover all the important features of the last version that are relevant for an intro course.

Is JavaScript an important language to learn? What about Java, PHP, C#, Python, Ruby and all the others?

JavaScript is the only programming language you can run in your browser. Without JavaScript there would be no games, no fancy dynamic HTML forms, no interactive maps, no Gmail, no YouTube, no Twitch TV, no Netflix….

JavaScript is integrated into nearly every popular Web browser and is probably the most frequently used language in the world. More than 90% of Web documents now use JavaScript too.

Every computer, smartphone, and tablet uses JavaScript many times a day within the browser and even as native code! Indeed, some applications are compiled from their JavaScript/HTML/CSS version into "classic" applications that can be run without a browser. This compilation step can give an extra performance boost, the NetFlix application, or Office 365 are such applications.

In the beginning, JavaScript was invented to work not only on the client side (in Web browsers) but also on the server side (on the Netscape HTTP Web server back in 1995).

In recent years this trend has returned, thanks to the appearance of the Node.js server/JavaScript interpreter. It's common to see JavaScript applications running on a remote Web server. Mastering JavaScript basics is highly recommended before trying to learn JavaScript server-side programming.

JavaScript is an interpreted language

JavaScript is an interpreted (or just-in-time compiled) language, which means that the code is converted into a machine language at, or just before, runtime. The most popular JavaScript engines are:

External resources

1.2.10 Discussion and project

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

a2. Suggested topics

Optional project

1.3.1 JavaScript Overview (the best way to learn JavaScript) (8:42)

The Best Way to Learn JavaScript.

What it the best method for learning Web Development?

Take a look at one of my websites; 'Web Programming with JavaScript and Python'.

Now, what it the best method for learning JavaScript?

When you are a complete beginner, I will recommend to look at examples, tweak them, change small things, try to understand what the syntax looks like. Even without deep explanations, without reading a book, or studying in details the different concepts of language, you can learn a lot.

To learn everything, a great start is W3Cx. Google it.

HTML for a simple plotting function.

In this section, I propose that you look at a small example without understanding the details, and try to tweak it.

CSS for myFunction; a simple plot function.

Here is the example we provide. It's just an example that draws, that plots, a mathematical function. You can use the mouse wheel to zoom in, zoom out, and you can look at the HTML code.

Example functionPlot; myFunction of sin(x) in red with x axis of 2 times 
    pi and y axis of minus 1 to 1.

There is only very few CSS and very few lines of JavaScript. How can we do the such a complex result? Complex thing drawing the grid with axes, with labels, with a curve, and interact with the mouse.

With only 10 lines of code: it's because we are using what we call an external JavaScript library. Actually, we are using 2 of them here. Because, this one: the "function-plot" JavaScript library, is using internally another one you must include also in the document.

What I propose is that we will start looking at this example. The best way is to click on "Edit on CodePen" label here, it will open the code in the CodePen.io online editor. And… just look at the HTML part here.

CodePen Example; Plotting function library; d3js.org.
CodePen; D3 Plotting

Okay, we can just look at the HTML part and zoom in a little bit. What do we see? We can see that it uses 2 libraries here between <script> and </script> elements. This is how we can insert in the document an external JavaScript file. In that case, it's a remote JavaScript file because we are downloading it using http. It uses this "d3js" JavaScript library that is located at "d3js.org".

JS data driven documents (d3) library.

You can open this in another tab and you will see the documentation and the Web site, the homepage of the Web site, for the "d3js" library. By the way "d3js"is one of the most popular JavaScript libraries for visualizing data.

Let's go back to our example, so you can just tweak the different elements.

HTML, CSS and JS; plotting functions using the function plot library.

If I want to plot a cosine instead of a sine, I don't need to understand the whole syntax here, but I guess that by just typing "cos" here, it will do something.

And indeed, I have just drawn a cosine. If I change this from red to "green", it changes the color. If I change the grid, that is by default "true", if I say "false", I don't have a grid anymore. Okay let's put it back. And I've got some "xAxis" domain: "-1, +1". If I change that for "-10, +10", I can see the result. It's more interesting, if you change this for the x values… instead of going from PI to 2 PI.

HTML, CSS and JS; plotting functions using the function plot library, #2.

I went from 0 to 10 PI. I can see the result here, and so on… Now that you tweak the example, you can try to understand what is going on. Okay, this thing is a name followed by a parenthesis. An open parenthesis with a closing parenthesis. It's a function call. When you've got something like that, in JavaScript, function parenthesis with something in the middle, it's called a "function call".

We're going to call a function, that, in this case, we haven't written, so it's coming from one of the external libraries. In that case, it's the "function-plot" library. What is inside? There are the parameters.

Variable parameters for plotting functions in JS.

And I can use an external name. I can declare that, here, it's equivalent. You see that it works the same here, but I've just separated the two things. If I put directly this thing inside here, like it was before, it still works. Okay, so what is this syntax? In JavaScript, when you've got braces like that, opening braces and closing braces, it's called an object.

And inside an object, you've got properties and values. The properties have names: target, data, function, color, grid. And the values are after a column characters. The target is my function. The data is this thing. The grid is true, and so on…

You separate the different properties of the object using a comma and sometimes, you can have some properties that in turn, have a value that is an object. The xAxis property is equal to an object that has a property domain, that has for values: "-1, 1".

And when you've got brackets, opening and closing brackets, it's like that… That will define arrays of things in JavaScript. And an array of things is a list of enumerable elements. In that case, the domain has two elements: the minimum value and the maximum value.

Additional plotting function; sine in pink.

And here you can see that the data that is plotted, the cosine function, is also an array. If I use the comma and I introduce a second element here. For example, the sine function, and if I change the color, let's make it pink…

More plotting function examples in JS using D3 function plot library.

Look at the result: I've got 2 different functions that have been plotted in my graph. I can, instead of using this, I can maybe plot x2 (x square 2), like this, okay. It should work. Ok, we can see a little bit of it here.

Maybe we will change the domain, so instead of stopping at 1, we go to 10. And if we look at the values, we see the x square function that is a bit better, and if we just plot it for x=0 to x=2… …In that case, I've got another scale for looking at the functions.

Still more plotting functions in JS using the D3 function plot library.

In this first example, you saw how to use an external library, what is the syntax to call a function, and how we can define objects in JavaScript by using a set of properties and values, separated by a comma. And we also had a first encounter with what we call arrays, that are elements separated by commas inside brackets.

FIRST: learn by looking at and tweaking the code in the examples

Well, there is no definitive answer to this question, but I'd recommend firstly looking at small examples, tweaking them and trying to guess what they do. You will rapidly discover that you can learn a lot just by modifying a few lines of JavaScript code, even if you do not understand the whole thing.

During module 1, we give you some basics:

SECOND: take some time to carefully read the sections titled "What you've learnt / let's detail …."

During the course, we provide extra "reference pages" that detail some important parts of the language. For example, in a later section, we explain the concepts of "variables", "values", "operators", "output", etc.

Here is an example - we provide some clues, but it's your job to tweak it!

Here is an example that uses an external JavaScript library useful for plotting math functions. Look at the JavaScript code (click on the JS button) and try to guess where the function is specified, where the range for the x and y values is set, etc. Notice that you can use your mouse wheel to zoom in/out the function plot.

CodePen: Learn JavaScript graphs d3.js.
CodePen: D3 JS Graph

By looking at this example (HTML and JS code), you note a few things:

Two lines in the HTML code that correspond to the inclusion in the document of some external JavaScript code:

1. <script src="https://d3js.org/d3.v3.min.js"></script>
2. <script src="https://mauriciopoppe.github.io/function-plot/js/function-plot.js"></script>

We will examine this soon in a later section of the course, but, in brief, it means that we will use the d3js plotting library and another from github (a famous repository for open source contributions), and located in the github account of a person named "mauriciopoppe", the repository is named "functionPlot" ( "functionPlot JavaScript library").

Then, looking at the JavaScript code of the example (click the JS button on the CodePen example), we see:

Source Code:
1.  functionPlot({
2.    target: '#myFunction',
3.    data: [{<
4.      fn: 'sin(x)',
5.      color: 'red'
6.    }],
7.    grid: true,
8.      yAxis:{domain: [-1, 1]},
9.      xAxis:{domain: [0, 2*Math.PI]}
10. });

Ok, the syntax looks strange if you are not used to JavaScript, but I bet that you guessed that the function plotted is "sin(x)", that the color of the curve is "red", that the range of the x values is [0, 2*PI], and the range of the y values is [-1, 1].

Your job:

To do this:

What can you guess from this example?

A function call

You can think of this code in this way:

1. functionPlot(…);

Where the "…" corresponds to some sort of parameter. When you see a name followed by two parentheses (maybe with something in between) followed by a ";", this is "a function call".

A function is a piece of code defined somewhere else, that can accept parameters (the "thing" between the parentheses), and that will do something. In our case the function's name is "functionPlot" and we can assume (or we read the documentation of the library) that the goal of this function is to plot a mathematical function, as its name tells us.

Function parameters

The "thing" between parentheses is what we call "the parameters of the function": the data we pass to the function so that it can plot different math functions, with different colors, with different ranges for the x and y values, with or without a grid, etc.

Let's have a look at the parameters we used in our example (the ones you tweaked). They are in bold in the source code we saw earlier:

Source Code:
1.  {
2.    target: '#myFunction',
3.    data: [{
4.      fn: 'sin(x)',
5.      color: 'red'
6.    }],
7.    grid: true,
8.    yAxis: {
9.      domain: [-1, 1]
10.   },
11.   xAxis: {
12.     domain: [0, 2*Math.PI]
13.   }
14. }

JavaScript object

In JavaScript you can have simple values like: 2, 5, "hello", "3.14", and you may also encounter more "structured" values that we call "objects". In Module 3 we will address JavaScript objects, but for the moment we will just present them through examples, without too much detail.

A JavaScript object can be defined by two braces with a set of properties/values inside, separated by a comma. Here is a simple object:

1.  {
2.    givenName: "Michel",
3.    familyName: "Buffa"
4.  }

We use the ":" separator between the property name and its value. We use a comma between two properties, and we omit the comma after the last property (or before the ending brace).

In our examples, the properties of the object that is passed as a parameter to the functionPlot(…) call are in bold.

They are respectively:

Coordplane: Grid with x-axis, y-axis, origin & target.

Notice that after each property (color, grid, etc.) there is a ",". Notice that between the name of the properties and the value there is a ":", etc…

Embedded objects

If we look at the values of the xAxis and yAxis properties, they are also objects.

1.  xAxis: {
2.    domain: [0, 2*Math.PI]
3.  }

The data object is even more complicated:

1.  data: [{
2.    fn: 'sin(x)',
3.    color: 'red'
4.  }],

Instead of containing another object like xAxis or yAxis, it contains another sort of object, but inside brackets! In JavaScript, brackets are used to create arrays of "things" (multiple, enumerable things). In this example, the array contains one single object that has two properties:

In arrays, the different elements are separated by commas. Let's try to plot an additional function in our example. We will add f(x) = cos(x) to our example, with a different color:

Source Code:
1.  data: [
2.    {
3.      fn: 'sin(x)',  // First function
4.      color: 'red'
5.    },
6.    {
7.      fn: 'cos(x)',  // Second function
8.      color: 'blue'
9.    }
10. ]
CodePen: JS Graph, #2.
CodePen: D3 JS Graph, #2

Conclusion

Just by looking at one example, and without going into the boring details, you saw:

1.3.2 What can be done with JavaScript (2:23)

Live coding transcript what can be done with JavaScript.

CodePen: what can be done with JavaScript?

Hello! What can be done with JavaScript? Let me show you some examples that are the most common ones.

First, you can change dynamically the content of a Web page.

My home page. Before JS title change.       My home page. This new title has been changed from JavaScript!

Here I've got a Web page, I click on the button and I change the content of the page.

My home page. This is an example of interactivity between JS and the 
    HTML content of a document.

Another thing we can do is to change dynamically the CSS style of some part of the document. I click on the button and I change the style of the title.

Example 'Where am I?'

You can also use, from your JavaScript code, different objects, methods and functions that are defined in your browser, in what we called standard HTML or standard JavaScript APIs. HTML5 comes with many of these APIs for the geolocation, for animation, for making music, and so on. In this example, we use the standard W3C geolocation API that comes with HTML5. You can get from your browser, your current latitude and longitude.

And here, we also use the Google Map APIs; we pass it the longitude and latitude and it displays the map centered on the current position and also displays the surface address. Here we go. I'm located near Antibes in the south of France.

Example; using databases and tables in JS.

You can also work with remote data. So in this code, I'm just sending what we call an Ajax request to a remote server to get a list of users... and once I get this list of users, I just use the HTML table JavaScript API for building dynamically tables. And I use this API to display the data that just came from a remote server.

Example table lookup for members (old and newer) of the Beatles.

There is another example, that uses another database, another online database, for getting the members of a rock band. So, I type "The Beatles". I got from the remote server the list of the members of The Beatles. So, these were the most typical uses of JavaScript Web sites.

What can be done with JavaScript:

1) Interact with the HTML and CSS content of a document, respond to events

We have already seen three examples in previous parts of this week's course material.

Change the HTML main title using JS.
CodePen: Change HTML using JS

This first example used the selector API for selecting a particular element in the document (the main title) and the DOM API for modifying its content.

An API is an application programming interface. In the case of JavaScript, the DOM API is implemented natively by the browser, and you can call several functions/methods or access properties of the DOM:  an object that represents the document (the Web page).

It uses the selector API to target a particular part of the DOM (in our case, the main title of the page), the HTML element with an id attribute equal to "mainTitle". The selector API uses the same syntax as CSS to select elements in the document. In our case, "#mainTitle" is a selector value that means "the element whose id is equal to mainTitle".

var title = document.querySelector("#mainTitle");

It uses the DOM API to change the HTML content of the selected element:

title.innerHTML = "This new title has been changed from JavaScript!";

It listens to click events in order to call the changeTitle() function when we click on the button:

1.  <button onclick="changeTitle();">Click me to change the
    title of the page</button>

And it executes the whole action (changing the title text) in a function (a block of code that is executed only when we call it by adding a parenthesis after its name, followed by a semi colon):

function changeTitle() {
  var title = document.querySelector("#mainTitle");
  title.innerHTML = "This new title has been changed from JavaScript!";
}
CodePen: example of interactivity between javascript & html.
CodePen: Interactivity between JS & HTML

The second example is nearly the same except that we changed the name of the function, and instead of using the DOM API to update the text content of the main title, we use its style property to change its look and feel. Using the style property is a way of altering the CSS property values of this HTML element.

function changeTitleCSSStyle() {
  var title = document.querySelector("#mainTitle");
  title.style.color = 'black';
  title.style.backgroundColor = "yellow";
  title.style.border = "5px dashed red";
}

title is in reality what we call "an object" and style is a property of the title object. The style is an object as well and has attributes that correspond to the different CSS properties we set. For example, style.color returns the color that element has set on it. By calling title.style.color = "yellow"; you can apply the style change dynamically.

Some of you may be wondering what happens when the CSS property being set has a hyphen. The syntax has to be different here, because, for example, if you write  title.style.background-color, JavaScript will try to subtract color from the  title.style.background notation, which is not what you want to happen. To stop this problem from occurring, all the CSS properties are written out in CamelCase: the CSS name background-color becomes backgroundColor, text-size becomes textSize,  border-color becomes borderColor etc.

Don't worry, we will return to this later in this course, these first examples are just here as an introduction.

The third example (outlined in the previous section), which showed how to plot math functions, illustrated that with a few lines of code you can reuse code from others (a third party JavaScript library).

2) Use numerous APIs in addition to the DOM and selector APIs: multimedia, drawing, animating, geolocation, webcam, etc.

Your browser comes with a lot of different "libraries" that are called "standards APIs" for "application programming interfaces". Such APIs are "W3C standards" and are present in all Web browsers that follow the Web Standards. You will have APIs for manipulating multimedia (audio and video), geolocation (getting the longitude and latitude), orientation (on mobile devices), accessing the webcam or the microphone, etc. In a later section we will provide a set of examples that use some of the most useful APIs provided by your Web browser.

Example of an HTML page that embeds an interactive OpenStreet Map (you need to click the CodePen logo on top right to run this example. For security reasons it cannot be run inside this course page).

CodePen: example Geolocation mapping.
CodePen: example geolocation mapping

3) work with remote data / speak with a remote HTTP Web server

You can also download or upload data from your browser to a remote Web server. When this is done from JavaScript the popular term to describe such operations is "AjaX" (Asynchronous JAvascript and Xml), even though XML is not used in any examples you'll see in this course (XML is a language for describing structured data that was very popular a few years ago).

Here is an example that will display the current and past members of famous rock bands:

CodePen: example database lookup band members.
CodePen: database lookup band members

1.3.3 Where to put JavaScript code (7:13)

Where to put JavaScript code.

Welcome!
In this lesson, we will just look at the different locations where we can put JavaScript code. The first place where you can put JavaScript code is inside an HTML document, using the <script> and </script> tags.

We've prepared an example, it's called the "Example 1" in the page, that shows how we can display the value of a variable. A variable is a location in the memory of the computer where we are going to store some values. And the variable has a name and it's declared using the "var" keyword. There are others possibilities we will see later.

CodePen: example 1; JavaScript in the HTML file.
CodePen: Example 1: JS in the .html file

Here we've got the variable called "x" that has the value of 2. And, we use some strange instruction "document.body.innerHTML" for adding to the body of the document some HTML code. "document.body" corresponds in JavaScript to the body element of the document, and the "innerHTML" property corresponds to its HTML content. By doing this, we are adding a bold element JavaScript code executing the value of the variable x=2 and we display the value of the x variable in bold.

CodePen: result of execution Example 1; JavaScript in the HTML file.
CodePen: JS in the .html file.

This is the result of the execution of this code. And this code is not in a function, so it's executed as soon as the page is rendered. When the browser receives this document, it will first display the "h1" then display this paragraph, then executes this code. It will define the variable x, assign the value "2" to it, and then add this string, with the value of "x" inside, to the body of the document.

And finally, we display in the dev tool console: "console.log("JavaScript code executed")". We can open it by clicking on the console button in CodePen, or we can also open the devtools using the "F12" key or "ctrl+alt+i" or "cmd+alt+i" on a Mac. And you see that the "console.log" message has been displayed in the devtool console of your browser.

Script within index.html.

Here, notice that we use the "script" element directly into the body of the document. Another possibility is to a put this code in the head of the document. It's also common practice because it separates clearly the JavaScript code from the HTML body of the document. In that case, the result is the same, except that the JavaScript code is displayed before the rest of the page.

Here we defined the variable x, we added it to the body of the document, and later on we display the body, where the browser renders the body of the document. Okay, what is better? It depends on your application. For the moment, just stay with knowing that you can put scripts in the body or in the head of a document.

Script is in external JavaScript file; script.js.

Another possibility is to use an external JavaScript file. In that case, the same way we showed you how to use an external file for storing the CSS code, we can use the "script" tag with the "src" attribute to include in the HTML document an external JavaScript file. More than one JS file can be called from index.html.

Notice than we can include more than one JavaScript file if we like, like this. In that example, we are including 3 different JavaScript files sequentially.

Find example_3.zip and open using sublime text editor.

I prepared for you an example you can download - it's called "Example_3.zip". I click on it, download it, unpack it, and inside this element, I've got an HTML file. And I open it with my Sublime Text editor.

Include script.js in index.html.

And what I've got here, is that you can see in the HTML header in that case but you can also put this in the body if you like, we included a "script.js" file located under the "js" directory.

Now, add JS to script.js.

I can also open this file. I can see that I display the message called "Function executed" and a function "addSomeText" directly in the script. When is this executed? It's executed when we click on a button. Let's have the button "onclick" call the function "addSomeText".

Click button to call JS function to add content.

Let's execute this, here is the result: "Click me to call a JavaScript function that will add some content to this document". I click and you see that the function have been executed. And finally, the last thing you can do, is to include an external JavaScript source code.

Intro to paper.js library.

You've got an example here, where we use the "paper.js" library and the "paper.js" library, if I open the "paper.js" Web site, is a library for making graphic animations in JavaScript, so you can have plenty of funny things you can do. Things like that, or things like this... Just to be able to use what this library proposes, you need to include the library. If you read the documentation, they will tell that you what you need to include...

CodePen: example paper.js.

Okay -let's open it in CodePen- ...you need to include this JavaScript file. And once you included this JavaScript file... a bit the same way we used the external library for plotting functions... then you can use some functionalities that come from the "paper.js" library. You need to read the documentation to learn how to use it, but here is an example: a set of squares, animated squares, that follow the mouse.

JavaScript code can be located in different places

  1. In your HTML code between <script> and </script> tag
  2. In local files, usually ending with the .js suffix (i.e: in a script.js file), and included using, for example, a syntax such as: <script src="style.js"></script> tag
  3. In external files located on the Web, using their URLs, also using the <script src="https://www.aserver.com/…./js/script.js"></script> tag
Here are some examples:

Example #1: the JavaScript code is included in an HTML file using the  <script>…</script> tag

First variant: in the <body>..</body> of the HTML document

Typically:
Source Code:
1.  <body>
2.    ...
3.    <script>
4.      var x = 2;
5.      // show a message in the body of the html document
6.      document.body.innerHTML += "JavaScript code executed. The value of the variable x is: 
          "+ x + "";
7.      // also print a message in the devtool console
8.      console.log("JavaScript code executed");
9.    </script>
10.   ...
11. </body>

Here is this first example on CodePen:

CodePen: example 1: JS in the .html file.
CodePen: JS in HTML

Old JavaScript examples may use a type attribute: <script type="text/javascript">. The type attribute is now obsolete and should be ignored.

Second variant: in the <head>…</head> of the document

In this example, the <script>…</script> element is placed in the <head>..</head> section of an HTML page.

This time, we placed a JavaScript function that is invoked (called) when a button is clicked:

Source Code:
1.  <head>
2.    <script>
3.      function addSomeText() {
4.        // append a message in the body of the html document
5.        document.body.innerHTML += "
Function executed!";
6. } 7. </script> 8. </head> 9. <body> 10. <button onclick="addSomeText();"Click me to call a JavaScript function that will add 11. some content to this document 12. </button> 13. </body>

Here is this second example on CodePen:

CodePen: example 2: JS in the .html file, but this time in head.
CodePen: Plotting Functions in JS.

Example #2: put the JavaScript code in local .js files

Putting JavaScript code in external scripts files is easy, and offers many advantages:

  1. It separates HTML and code (and also CSS code, if you use external CSS files)
  2. It makes HTML and JavaScript easier to read and maintain
  3. JavaScript files can be reused more easily in other projects
  4. Cached JavaScript files can speed up page loads

A typical example:

1.  <head>
2.    ...
3.    <link rel="stylesheet" href="css/style.css">
4.    <script src="js/script.js"></script>
5.  </head>
To use an external JavaScript file:
  1. In the HTML, put the name of the script file in the src (source) attribute of a <script> tag, like in the typical example above,
  2. JavaScript files must end with the .js extension,
  3. Do no use any <script>…</script> tag in a .js file!
  4. Using an external JavaScript file with <script src="…"></script> is 100% equivalent to using <script>…</script> with the file content between the opening and closing tags.
  5. It's possible to use more than one JavaScript file, just use multiple <script src="…"></script>
Example that uses more than one JavaScript file:
Source Code:
1.  <head>
2.    ...
3.    <link rel="stylesheet" href="css/style.css">
4.    <script src="js/script1.js"></script>
5.    <script src="js/script2.js"></script>
6.    <script src="js/anotherOne.js"></script>
7.    ...
8.  </head>

A typical HTML/CSS/JS project folder structure, when working with external local files.

It is good practice to locate CSS files in a css subfolder, and JavaScript files in a js subfolder.

A typical HTML/CSS/JS project folder structure.

In this example, we have just one CSS file and one JavaScript file:

A typical HTML/CSS/JS project folder, folder expanded.
Contents of the index.html file:
Source Code:
1.  ...
2.  <head>
3.    ...
4.    <link rel="stylesheet" href="css/style.css">
5.    <script src="js/script.js"></script>
6.  </head>
7.  <body>
8.    <h1>Example 3: JavaScript and CSS in local files!</h1>
9.    <button onclick="addSomeText()">Click me to call a
        JavaScript function that will add some content to this
        document</button>
10. </body>
11. </html>
Content of the js/script.js file (JavaScript file):
1.  function addSomeText() {
2.    document.body.innerHTML += "<p>Function executed!</p>";
3.  }
Content of the style.css file:
1.  p {
2.    color:green;
3.  }
How to run this example:
  1. Download the zip file of this project:  Example_3.zip
  2. Unzip/unarchive it somewhere
  3. Double click the index.html file, this will open your Web browser and load the index.html file.
  4. Click on the button in the page

Example #3: use external references to JavaScript files/libraries located on the Web

External JavaScript libraries (they are just big JS files) can be also referenced with a full URL, like in this example:

1. <script src="https://cdnjs.cloudflare.com/ajax/libs/paper.js/0.22/paper.js"></script>

Here, we just included in our HTML document the excellent paperJS  library that can be used to make fancy animations in the HTML canvas element - we will use it later in the course.

Once the library is included, the JavaScript code you will write can call functions located in this library. This "reuse existing" work made by others is really common when working on JavaScript projects.

Here is a running example that uses the paperJS library, included using an external URL:

Example 4: use an external JS file.
CodePen: Example paperJS

1.3.4 How to debug JavaScript

How to debug JavaScript.

Hi, every programmer will make errors. It is very important that you learn how to debug your JavaScript programs, how to see your errors, how to write messages for debugging, tracing what is going on, etc.

Every browser comes with a very powerful set of tools called the devtools.

With my Mac, I can use command "alt + I". So the thing we will going to use the most is the console. A console loads problems or errors. So, if I can clear the messages from here and this is the place where I will see the different error messages I've got in my code.

JSBin example; test console.

Here is an example in JsBin. So, you can click here to see the console or it’s the same thing you can get here.

console.log 'hello'.

If I type something here: console.log("hello"). So this is the instruction you will use the most for printing error messages in the dev toolconsole. If I execute it, it prints "hello", and I can see also in the browser built in console: "hello".

This just a comfortable way to display error messages. If I make some errors, here I've got a script that will display, as soon the page is loaded, "Some JavaScript code has been executed".

JSBin; console.log error check.

If I run the code, here, it displays "Some JavaScript code has been executed".

JSBin; error check on console.log.

If there is a mistake, if I make an error here, for example, I write console with two "l". I can see, in red, some messages: "consolle is not defined", bla, bla, bla...

When you use some online tools like JsBin or CodePen, and so on, it's a bit difficult to debug your code because you are debugging at the same time the code of the tool itself that is written in JavaScript too. Each these tools comes with a way to run your code in what we decode ‘standalone mode’ or ‘debug mode’.

JavaScript debugging using the devtools console.

With JsBin, I click on the small black arrow, here. And if I open the built-in browser console, I can see the error message.

And here, if I click on the link on the right, it will just show the line where my program made a mistake display, as an error. Here, I can see that console needs only one "l", I can fix that.

JSBin; Error check in console.

Another interested thing is that when you use "console.log", you can use it to display some variable values. If I declare a variable named x with a value of 10, I can use «console.log" to display the value of x, using the "+" operator. In that case, if I run my code it will help me by displaying the value of different variables when “console.log” is executed.

CodePen; Debug Mode.

With CodePen, another tool we use a lot in the course, you've got the debug mode. Just save your work and click on "change view mode" we’ve got "debug mode" here. And you can also open the console. If you click on the console button here, you can have a console here, and see what is going on. CodePen does not display the error messages, so is better for debugging to click on the "debug mode", here.

You've got the page in standalone mode, and you can open the dev tool console. With local files, I’ve got another example here with HTML code that uses it some JavaScript code from a "script.js" file. If I make an error here, an error in the name console, I save. I can run the result: "Open in browser". I click, it does nothing. I open the dev tool console and I see where the problem is and I can click on the link on the right and it shows the line with the error.

Let's introduce what is debugging.

You will make errors!

When you are developing a Web Application that contains JavaScript code, you will make errors.

Repeat after me: "I WILL MAKE ERRORS!" ; "I WILL MAKE ERRORS!"

There will be error messages, and you will need to print messages for debugging your code. We will see more advanced debugging techniques at different points in this course, but for the moment, let's see the basics of JavaScript debugging: seeing error messages in the devtool console, or in the "console tab" of your source code editor.

We will not look at the JavaScript syntax here, but more at "JavaScript in the browser", how it works, how to start writing code, etc.

First of all, you need to find a way to debug your code and see errors. If your work does not produce any results, you need to know why!

Your Swiss army knife: your browser devtools, especially the devtool console!

For this you will use the dev. tools of your browser. Press F12 (or ctrl-shift-i) in Windows or cmd-option-i in MacOS to open the dev. tools, then go to the console tab: this is where errors will be displayed, or messages of your own (use the console.log(string) JavaScript function in the JavaScript code embedded in your html page). In the console, you will be able to type any JavaScript command.

Let's look at this example below (or online as a  JS Bin):

Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en>
3.  <head>
4.    <meta charset=utf-8 />
5.    <title>Web Audio API</title>
6.    <script>
7.      console.log("Some JavaScript code has been executed");
8.    </script>
9.  </head>
10. <body>
11.   <h1>JavaScript debugging using the dev tool console</h1>
12. </body>
13. </html>

The simplest way to add JavaScript code in an HTML page is to use the <script>…</script> element.

The code in this example is executed sequentially when the page is loaded: the JavaScript code is executed before the browser could see the rest of the page (as the <script></script> is located before the <body>).

The H1 element, for example, does not exist in the Document Object Model, and has not yet been displayed when the JavaScript code is executed. If we move the <script></script> at the end of the document, then the H1 would have been built before the JavaScript code is executed.

The only line of code we have is console.log("Some JavaScript code has been executed");

This means "display in the JavaScript console the message…". If we open the console tab provided by jsbin.com in a dedicated tab (that redirects all console.log() messages), and re-execute the page (just type a space at the end of a line to re-render the page and display the message in the console), we see the message in the console tab, as well as in the dev. tools console. This is illustrated by the image below (or online):

JSBin: Snapshot of a JavaScript console view.

It is also possible to use the "real dev. tool console", and for this, I recommend running the application in a single window, not in the Js Bin editor. Press the black arrow on the top right of the output window - this will render the page as a standalone Web page, then press F12. You should see:

Snapshot of a JavaScript console view.

Ok, now, let's make an error: change console.log() into consollle.log(). Let's see what happens:

View of the JavaScript console showing an eror.

And if we run it standalone and use the dev. tool console:

View of the JavaScript console (showing the line that caused the error.

And if we click on the line number to the right, the dev. tool shows the source code centered on the line that caused the error:

View of the JavaScript console.

Without such tools, debugging JavaScript code is impossible. You need to look at some basic tutorials on how to use the dev. tools of your browsers, since they differ from one another in the way they work - although the principles remain the same.

1.3.5 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics

Optional projects

1.4.1 Creating Your First HTML/CSS/JS project

Let's create a small HTML/CSS/JS project together.

It's time for you (and me) to create a small HTML/CSS/JS project, step by step, following some best practices. We will do this using different tools: source code editors + files but also two online IDEs (JsBin.com and CodePen.io). We will see how to write/debug the code and also how to migrate a project prototyped with online tools to a project you can run and edit on your hard drive using regular source code editors.

Many things we use in this example may be new to you. Don't worry. We will cover them either later on this week or over the following weeks. It's time to throw you in the deep end of the JavaScript world, getting you to write code, and look at examples etc. And from time to time, we will take a break and have a "real", "academic", look at the concepts of the language you have been using. We think this is the best way for you to learn!

Topic

We will write a small, interactive HTML page that will use some HTML input fields for indicating the name of a math function we'd like to plot, the ranges for the x and y values, the color of the curve etc.

We will first write this application online, using the JsBin.com editor, then we will do the same thing using the CodePen online editor, then, using a regular source code editor and .html, .css and .js files.

Here is what the resulting Web page will look like:

CodePen: Interactive Function Plotter.
CodePen: example interactive math function plotter

1.4.2 Using CodePen (6:46)

CodePen: Interactive Function Plotter.
CodePen: interactive math function plotter

We're going to work from an example we already saw in the course: the math function plotter. In this version, you can see that we added some input fields for changing the color of the curve, for changing the range of the x values, changing interactively the functions we are going to plot, and so on.

CodePen; Plotting Functions with d3js.org.

Let's start from the very basic example we saw earlier on the course. We saw that, the function is located in a "div". And we just added a "section" tag from HTML5, just to identify the part of the document where the function is plotted.

Later on, we'll add another "section" about the input fields and the different controls. You've also got a <body onload='plot();>', that means that when the page is loaded, we execute a JavaScript function named "plot()", that is located here. And it uses the "functionPlot()" function from the external library we use. And it takes a set of parameters that are located at the beginning of the JavaScript part. That will indicate, within the target property, the "id" of the div where we are going to plot the function. In the data property is the function itself: "sin(x)" and its color: red. What can we do to improve this?

CodePen: plot sin(x) color red.       CodePen: plot cosin(x) color red.

At first, we can add some CSS code to make this nicer. I'm going to change the view with CodePen. Let's resize that, and let's work on the CSS part: "Maximize CSS Editor". What I can do, is that I can indicate that the div that contains this function wil have a rounded border, some shadows and so on. Now it's rounded, you can have add some shadows, height, margin and so on. Let's copy and paste some code I’ve prepared. Here we are. Now, what I've got, is a nicer presentation of the function itself.

Add section id='plotSettings' and input type=color id='color' onchange='plot();'.

Now, I'm going to add a section that will contain the different controllers that are input fields from HTML5. I add a section called "plotSettings" that will contain all these controllers. Let's start for example with a controller for the color. What we added here is a label color value and the color input field from HTML5. If I click here, it asks for a color. And we can also add an event listener: "onchange='plot();'". That means: "when the color has been selected, call the plot() function". And you remember that this function is the one that plots the mathematical function, here. The plot function is here.

function plot() define line color parameter green.

What we are going to do in this change color function? It changes the property of the parameters here. Let's add some code for that... How can we get the value of the color from JavaScript before plotting the function? We are going to use the selector API: "document.querySelector(...)" for the input field whose id is "color".

The value, here, is the color itself.

What we do is that we are going to use the color for changing this, here. So "parameters.data"... it's an array. 0 is the first index, the first element that corresponds to the part that I highlight now. .color=color

If I change the color, this line is executed and the color changes. We can use the same principles with other input fields. Let me copy and paste some code I prepared, that will add all these different controllers.

HTML; define labels xMin/xMax and yMin/yMax, color, and function to plot.

Now I've got all the different controllers, and if you look at them, they all have an "onchange" or "oninput" event listener. Now, we’ve got 2 sections, 2 HTML sections: one with an "id='plotSettings'" that corresponds to the different input fields.

And one with an "id='plot'" that corresponds to the function itself (the drawing here). If I want to have a nice look and feel, what I can do is share the same borders and shadow properties from CSS, put the first section with the different input fields on the left and the plot on the right.

CodePen: interactive function plotter, again.
CodePen: Interactive function plotter.

Let me just cut and paste some CSS rules here, that will factorize the common properties for both sections in a section selector. OK, what I've got now, is that I've got a nice balanced view of the whole application.

CodePen example with the starting code used in the video

If you want to code while watching the video,  please open this CodePen. It contains the source code of the example we started coding from.

And  here is the same version with the polyfill for the <input type="color">  input field, not yet supported by Safari.

In case you have a hard time following the video,  here is the full example (this link points to the example from the previous course page).

1.4.3 Using Sublime Text (4:22)

CodePen: example function plot library.

Now, I'm going to show you how we can do the same application using files and a regular source code editor, and working on your local hard disk. I'm going first to create a directory for storing the files on my desktop. "Math plotter app" and I will work inside.

Create subfolders; css and js.

In this folder, I will create a subfolder named "js" for the js files and a subfolder named "css" for the CSS files, and the HTML file will lie in the current directory.

Save as index.html.

With Sublime Text, I can open this folder, the one I just created. And I can start saving the current file as "index.html". I will copy the HTML, CSS and JavaScript source code from the previous example. I just took the previous application.

Create and save style.css and script.js.

And I will copy it in the index.html file. I create a "style.css" and a "script.js" file for holding the JavasCript and CSS files. I copy the source code from the js part of the previous example. I create a new file with the CSS code.

Save as script.js under js subdirectory.

"Save as" ... I include the JavaScript code :<script src="js/script.js">

Remember that the script tag has always a closing tag at this end.

Save as style.css under css subdirectory.

It is not an auto-closing tag. And I use a "link" tag for importing the CSS file.

Test index; open in browser.

I can check that my files are located at the right place and now I can "Open in Browser". Another way to do what we've done manually would have been to use the "Export" button from CodePen.

It will download a zip file, that will contain the whole architecture, the whole folder and subfolder I've already prepared for you. And it will also make the HTML file for you, that will include the JavaScript, but in the end, instead of at the beginning of the source file, like what I did manually.

Using generated code can be useful, but most of the time for a big project or a serious project, you will use a source code editor like Sublime Text.

1.5.1 JS variables and values (5:28)

Live coding lesson: JavaScript variables.

JavaScript variables and values.

In JavaScript, a variable is a container for a value. And a value can be many things: a number, or a string, an object or a complex function.

With variables, the value in the container can change, and to use a variable you first have to declare it. Let's see some examples! You can declare a variable using the keyword "var", and followed by the name of the variable, or you can also use the keyword "let", that came with ES6, with JavaScript version 6.

Before ES6, you could only use "var". There are small differences that I will explain later, but for the moment you can use "var" or you can use "let". Once a variable is declared, you must initialize the variable, this is where you give it a value. And this is done by using the equal sign. Use console.log to display variables.

As you can see, the console.log will display in the console the value of the variable "myName". You can also initialize and declare a variable at the same time.

Declare variable and give it a name.

You see, I declare a variable called myDog and I gave it a name: Rex. Also, you can use these variables in instructions, in expressions like: "the name of my dog is".

Use '+' to concatenate strings.

You can use the "+" operator for concatenating strings, because "myDog" is a string, and in that case you will see: "the name of my dog is" ...followed by the value of the "myDog" variable.

There are also naming rules and conventions for variables. You can give to variables names like "x", "y", "z". If they are just single, one-word names, you use lowercase. But the convention, when you start using composed words, is to use the "lower camel case" syntax.

If your variable name is made of two or more words, write the first one in lowercase, and capitalize every other words. Example: "myFastCar", "my" is lowercase, "Fast" and "Car" are capitalized.

Variables are case sensitive.

Also, variables are case sensitive: do not mix a variable name in lower case and in uppercase. For example, if I give to the small "x" a value of "2", and to big "X" a value of "4", and if I display the value of big "X", then the JavaScript interpreter will know that big "X" is different than small "x".

If you need to use different names like if I've got two fast cars, just, my recommendation: use "myFastCar1", "myFastCar2", etc. Also, you should not use JavaScript reserved words such as "var", "let", "if", "for", "function", etc.

var function = 3; will raise error.

So, var function = 3; will raise an error, I can show that to you in the devtool console, this raises an error. function is reserved.

We will next talk about variable values and variable scopes, and you will see that there is a small difference between "var" and "let" when you declare variables.

In most of the examples seen earlier, we've used the concept of "variable", and we have used them to "store values". It's time to take a break and talk about them :-)

Variables

In order to remember a value, programming languages share the concept of "variables". When you write programs, you will need to store values in the computer's memory. By saving these values in "variables", by giving them a "name" (we call it an identifier), you can reuse them later for display, for computations, etc.

Create (declaring) a variable

With JavaScript versions < 5 (prior to 2015), there was a single way to create (we say "declare") a variable: using the var keyword. But with the subsequent versions (called ES2015/ES2016 or JavaScript 6/7), we can also use the keyword let (this has some subtle differences, which we'll explain later in the course when we will talk about "functions").

JavaScript is weakly typed. Each variable is declared with the keyword var or let. You are not required to specify the type of variable you are creating. After the keyword "var" and a space, just give the name of the variable.

Example:

1.  var myVar;
2.  let x;

The first letter of a variable can only be "$", "_", "a" to "z", or "A" to "Z". The other characters in a name must be any of these, or numeric digits. The name is case sensitive. Variables "myVar" and "MyVar" are different variables.

There are some reserved names that you can't use as a variable name: boolean, if, delete, var, function, etc. as they are reserved words of the JavaScript language.

Give a value to a variable (assign a value to a variable)

A value can be assigned to a declared variable, or even directly in the variable declaration. For this, we use the equal character, also called "the assignment operator".

Example:

(notice at line 4 one way to introduce comments in your code: start a line with "//"!)

1. var myValue;
2. myValue = 78;
3. // With the ES2015 syntax. BTW, lines staring with
4. // are comments!
5. let myNumber = 1.34;

At line 2, we are not saying that "myValue" and "78" are the same, we're saying "hey, I want to store the value 78, and I'm putting it in a variable whose name is "myValue". It's like giving an id to a location somewhere in the memory of the computer.

Using the id "myValue", we store 78 into a memory location identified by the name "myValue": a variable, or if you prefer, a value that can vary over time if we assign a new value to the variable "myValue" (for example by executing myValue = 5;).

You can also declare many variables at once by separating them with a comma. Always end each instruction line with a semi colon.

Example:

1. var myNumber1, myNumber2 = 34, myNumber3;
2. 
3. // Or with the ES2015 syntax, you can also use "let"
4. let x = 1, y = 3, z = 12;

Try the devtool console - you can type code in there too!

Reminder: you can always open the devtool console using F12 on windows, or ctrl-shift i, or cmd-alt-i on other computers.

If we copy and paste the variable declarations from the previous example, and type myNumber2 in the devtool console, it will display 34 (while myNumber1 will have an undefined value):

Source Code:
1.  var myNumber1, myNumber2 = 34, myNumber3;
2.  undefined
3.  // Or with the ES6 syntax you can also use "let"
4.  undefined
5.  let x=1, y=3, z=12;
6.  undefined
7.  x;
8.  1
9.  z
10. 12
11. myNumber2;
12. 34
13. 
14. myNumber1;
15. undefined

Below is an image that explains how you can try JavaScript code in the devtools console:

Devtools console example.

If you try to use a variable that has never been declared, you get an error message:

Error Message: Undeclared type error.

Name conventions for variables

The JavaScript community has some conventions about naming variables:

Example:

1.  var myModel;
2.  // ES2015 syntax
3.  let michelBuffaAge = 51;

Most JavaScript examples you will find are written in the camelCase format. For harmony in the code source, it is a good idea to keep this convention. Sometimes, you will see the snake_case naming convention, which separates each word of a variable with an underscore.

Here's an interesting article:  CamelCase vs underscores: Scientific showdown.

Constants

Constants are variables that cannot be modified after a value has been set.

The naming convention is to use uppercase letters with underscores.

Example: var TIME_LIMIT = 50;

With JavaScript 5, constants were declared as normal variables, using the var keyword, and there were no verifications by the JavaScript interpreter forbidding you to modify them after you assigned a value to them.

With ES2015/2016 it is recommended that you use the keyword const instead of var to declare them. This means that an error will be raised if you try to change their value in the future.

Example:

1.  var TIME_LIMIT;
2.  // ES2015 Syntax
3.  const MAX_GRADE = 20;
Comparison between var: TIME_LIMIT and constant: MAX_GRADE.

Summary

Here are a set of examples (using the let keyword, but they would also work with var):

Source Code:
1.  let a;
2.  let thisIsAVariable;
3.  let and_this_too; // but does not respect the usual naming convention
4.  let mix12three;
5.  // invalid!
6.  let 2three4five; // can't start with a digit!
7.  let a = 1
8.  let v1, v2, v3 = 'hello', v4 = 4, v5;
9.  // Beware with lowercase / uppercase
10. let case_matters = 'lower';
11. let CASE_MATTERS = 'upper';

1.5.2 Scope of JS variables (4:19)

Scope of JavaScript variables.

Let's talk about "variable scopes". The scope of a variable corresponds to the locations in your code where you can use this variable.

When you define… when you declare a variable outside of any functions, it's usable anywhere in your code. It's considered as a "global variable": it belongs to the "global scope". The x variable here, can be used inside a function.

Console.log will display 1.

The console.log inside f1... if I execute f1... will display the value "1" because the variable here is "global". Local vs global variables.

If I've got another function... f2, that declares another variable y, and if I try to display this value from outside of the function, then it does not work...I've got an error: y is not defined. So, you've got "local variables", and "global variables". In the case of local variables, when a variable has the same name as a global variable, then the most local one wins.

Local variable closest takes precedence over global variables.

If I try to display inside F2 the value of x, it will be the closest variable -the local one- that will be displayed. If I execute f2, then it will display "x = 2", it's the value of the local one that is taken into account, not the value of the global one. We call this "masking". The same… if I pass a parameter to a function, and if this parameter has the same name as a global variable, then it acts as a local variable, and it's the value of the local parameter that is taken into account.

Local vs global and 'let' vs 'var'.

This x here, is not the global one: it's the one I passed as a parameter that has the value 10. Now, there are some little variations when I use "let" instead of "var". Let's see some examples.

A variable declared with 'let' in a block is local to the block.

With JavaScript 6, I can use "let" instead of "var". The global scope does not change. If I declare a global variable, it can be used anywhere. But, if I declare a local variable, it's no more local to the whole function in which it is defined, but it's local to the block of instructions that is defined by an opening brace and a closing brace.

If I try to use this variable here, that is defined in the block, outside of the block but inside of the function, the "a"..., the value of the variable "a" here, will not be the value of the local variable here, because this one does not exist, it's not usable here. It will be the global variable "a" that will be used.

This is why the printed value here, when I execute "f" is "1" and not "4".

ReferenceError; b is not defined.

If the variable was named "b" and if I tried to display it, then... I've got an error: "b is not defined".

var b works as a variable local to the WHOLE function.

Remember that if I used "var" in that case it works, because "var" will define a variable local to the whole function, not just to the block of instructions.

Scope of JavaScript variables

1) JavaScript 5 / ES5 scopes, with the var keyword

JavaScript 5 / ES5 has the var keyword for declaring variables.

JavaScript 5 / ES5 has two scopes: 1) a global scope for declaring global variables, and 2) a function scope for declaring variables that are local to a function.

Furthermore, like in most programming languages, inside a function, a local variable masks a global variable that has the same name.

See examples below.

1.1) Global scope / global variable

Global variables are variables declared outside of functions. They can be used anywhere in the code.

Here is an example:

Global scoping of variables.
CodePen: global scoping of variables.
1.2) Local scope / local variable (also called function scope)

Variables declared with the keyword var in a function, are said to be "local to the function". They "mask" any global variable that may have the same name.

When a variable is declared in a function, we also call it simply "a local variable", as opposed to "a global variable". In JavaScript 5 (and this is not common in programming languages), local variables are local to the function. They can be used anywhere inside the function.

Most programming languages have local variables that are limited to the block of instructions between '{' and '}' that contains the variable declaration. We call these variables "block variables". This is the case with variables declared with the let keyword  introduced by JavaScript 6 / ES6. See examples at the end of this section.

Example of a local variable declared in a function, that is NOT local to the block, but to the whole function:

Global and local variables.
CodePen; example global and local variables.

Here is another example that shows the differences between global and local variables, and highlights the "masking" of global variables by local variables when they share the same name.

CodePen: example variables; global and local.
CodePen: example variables, global and local.
1.3) Never declare a variable without the keyword var!

JavaScript is sometimes an overly permissive language. We can make stupid errors that turn out to be very hard to detect. One such error occurs when we forgot to use the var keyword while declaring a local variable.

In JavaScript 5 / ES5, a variable declared in a function without the var keyword, makes it a global variable.

BEST PRACTICE: in JavaScript 5 / ES5, always use the keyword var when declaring a global or a local variable.

Better: use the keyword let if you target browsers that support JavaScript 6 or above.

Here is an example that shows what happens when you forget to use var or let while declaring a local variable:

CodePen: Local and global variable scoping.
CodePen: local and global variable scoping.
Declaring a variable without var in function make it global.
2) Since 2015 and ES2015, there are new scopes, with the let keyword

Modern JavaScript has the let keyword for declaring variables, and the const keyword for declaring constants.

Modern JavaScript has two scopes: 1) a global scope for declaring global variables, and 2) a block scope for declaring variables between { and }. This is similar to what we find in many other programming languages such as Java, C# etc.

Furthermore, like in most programming languages, inside a block, a local variable masks other variables located in higher scopes (global or in another block that contains the current block).

Example of a local variable declared with the let keyword. Its scope is the block:

CodePen: if block is true, let a=4.
CodePen: example let keyword.
3) Recommended way to declare variables: var or let?

Well, all modern browsers support the let and const keywords, however, you might find lots of examples that still use the var keyword…

Anyway, we highly recommend to use let and const instead of var, for declaring variables and constants!

1.5.3 JS data types (5:27)

JavaScript data types.

Let's talk about JavaScript data types. The data type of variable is the kind of value you can give to this variable. With JavaScript, there are many possibilities: even if when you declare a variable, you don't type if data type: "var x=10", the value you give to this variable will help JavaScript figure out the data type of this variable.

JavaScript data types.

And there is an operator named "typeof" that you can use for visualizing the internal data table of variable. So "var x=10", this corresponds to a number.

JavaScript data types.

If I give to "x" a string value like my name, then the type of "x" will be "string". It changed its internal type on the fly, we call this "dynamic typing".

JavaScript data types.

What kind of data types can we get? String, number, we've got also boolean value: "var x = true" or "x = false" corresponds to a boolean value: "typeof x"... boolean.

And I can say "if (x)" then... do something... "console.log("it's true!!!")" and the boolean data types is useful for "if" statements or some other statements that will test boolean value.

In that case, it printed "it's true!!!" because "x" was "true". If I give to "x" the value "false", then if I execute this code, it will do nothing because "x" is false.

JavaScript data types.

We've got also some special values… but "typeof y": undefined. I can test if y is undefined then ....And in that case, you can test if a variable is defined or not.

JavaScript data types.

There is a special data type called "null" that corresponds to "no value". The difference with the null defined variable is that the variable that has the value of null is still defined. Like "y" is not defined here... but if I say "z = null" then "z" is defined.

Ok, this has not been printed because "z" was not undefined. OK, another common value we give to variable is object. An object is something like this: property, value. And if I look at the type of "person", it will say: object. And object is a structured variable, I can use the "." operator to check the value of some property.

So, "person.familyName" will print the value "Buffa" .... "person.name" will print my given name. There is a particular case for arrays. Arrays are defined using "brackets". If I define an array with two names of days in a week: Monday and Tuesday, then, its type is also "object". There is no type that is called "array". Arrays are objects in JavaScript. To sum up, we've got: number, string, Boolean, undefined, and null and object.

Nothing else. And the "typeof" operator can be used to display the type of an object.

What kind of values can we assign to a variable?

Well, there are multiple possibilities: What we call "primitive data types": for example a number, a string, etc. ex: var x = 3; var name = "Buffa";

Red cards depicting primitive data types.
1.  var x = 3; var name = "Buffa";
2.  <a href="" target="_blank" rel="noopener noreferrer">a set of playing cards</a>

Objects (everything that is not a "primitive data type" is an object):

1.  var michel = {firstName:'Michel', lastName:'Buffa'};

There is a set of "predefined objects" in JavaScript (arrays, functions, etc). We will come back on these later in the course.

JavaScript has a small set of primitive data types

These are the simplest forms of data we can use in programming.

Anything that is not listed above is an object (JavaScript objects are covered later in Module 3).

You said JavaScript does not have types for variables?

No! I said that JavaScript is weakly typed; you do not declare the type of variable. In some other languages (Java language syntax, for instance) instead of var x=2; or let name="Buffa"; you would write int x=2; or String name = "Buffa";, with the datatype explicit in the variable declaration.

Knowing the type of a JavaScript variable: the typeof operator

The next section of the course talks about "operators" but there is one that is better introduced in this section: the typeof operator, that is useful for knowing the type of a variable depending in its value (possible values: number, string, boolean, undefined, object, or function)

We will use it in lots of examples in the next three sections.

Dynamic typing. You can use the typeof operator to see the dynamic type of a variable.

This operator is not often use in JavaScript programs, but it's useful for us, for explaining the data types.

1.5.4 Numbers

Numbers 1 thu 9, then 0, twice.

Number values can be:

Type 343 in the devtool console, and after you press the Enter key, the  corresponding value (343) will be displayed.

Examples of integer and decimals:
Source Code:
1.  var n=1;
2.  undefined
3.  > typeof n;
4.  "number"
5. 
6.  > n=1234;
7.  1234
8. 
9.  > typeof n;
10. "number"
11. 
12. > n=1.23;
13. 1.23
14. 
15. > typeof n;
16. "number"
17. 
18. > typeof 123;
19. "number"
3.46e4 equals 3.46 x 10^4 equals 34600

Examples:

Source Code:
1.  > 1e1;
2.  10
3.  
4.  > 1e+1;
5.  10
6. 
7.  > 2e+3;
8.  2000
9. 
10. > typeof 2e+3;
11. "number"
12. 
13. > 2e-3;
14. 0.002
15. 
16. > 123.456E-3;
17. 0.123456
18. 
19. > typeof 2e-3;
20. "number"

Be careful with this, don't start an integer with 0 (zero), JavaScript will understand it as an octal value.

1.  010 equals 8 which means 1 * 8^1 + 0 * 8^0
1.  The number 0456 means 4 * 8^2 + 5 * 8^1 + 6 * 8^0

Question 1: What's the result, as an integer, of the operation: 24 - 024?

Explanation 1: 24 is an integer which equals 24 but 024 is an octal value which equals 20.

Question 2: Which value will be displayed in the devtool console if you type 098 followed by the Enter key?

Explanation 2: 9 and 8 don't exist in base 8 (only 0 to 7), the typed number will be considered as an integer.

0xFF equals 255, 0xF3 means 15 * 16^1 + 3 * 16^0 and the resulting
value is 243

Examples of octal and hexadecimal data types:

Source Code:
1.  > var n3 = 0377;
2.  undefined
3.  
4.  > typeof n3;
5.  "number"
6.  
7.  > n3;
8.  255
9.   
10. > var n4 = 0x00;
11. undefined
12.  
13. > typeof n4;
14. "number"
15.  
16. > n4;
17. 0
18.  
19. > var n5 = 0xFF;
20. undefined
21.  
22. > typeof n5;
23. "number"
24.  
25. > n5;
26. 255
Special values:

The value Infinity (or +Infinity) represents all number values greater than 1.79769313486231570e+308 and -Infinity represents values smaller than -1.79769313486231570e+308.

Finally, Nan represents not-a-number values, for example if you try to divide 0 by 0 (type 0/0 in the devtool console).

1.  > 0 / 0;
2.  NaN
3.  
4.  > 3 / 0;
5.  Infinity

Examples:

Any operation with Infinity gives Infinity as a result:
Source Code:
1.  > Infinity;
2.  Infinity
3.   
4.  > typeof Infinity;
5.  "number"
6.   
7.  > 1e309;
8.  Infinity
9.   
10. > 1e308;
11. 1e+308
12.  
13. > var a = 6 / 0;
14. undefined
15.  
16. > a;
17. Infinity
18.  
19. > var i = -Infinity;
20. undefined
21.  
22. > i;
23. -Infinity
24.  
25. > typeof i;
26. "number"
27. > Infinity - Infinity;
28. NaN
29.   
30. > -Infinity + Infinity;
31. NaN

Source Code:
1.  > Infinity - 20;
2.  Infinity
3.   
4.  > -Infinity * 3;
5.  -Infinity
6.   
7.  > Infinity / 2;
8.  Infinity
9.   
10. > Infinity - 9999999999999;
11. Infinity

Examples with NaN:

NaN is a special value and its type is "Number"!

Source Code:
1.  > typeof NaN;
2.  "number"
3.   
4.  > var a = NaN;
5.  undefined
6.   
7.  > a;
8.  NaN 
9.
10. > var a = 10 * "f";
11. undefined
12.  
13. > a;
14. NaN 
15.  
16. > 1 + 2 + a;
17. NaN

[ADVANCED] Optional explanations about numbers

In JavaScript, numbers are represented with a double-precision 64-bit format (IEEE 754). These 64 bits are used with this table:

Total bits Sign Exponent Significant
64 1 11 52
What does it mean?

First, each number is represented as a float. For example, 1 equals 1.0. But there are approximation errors that are well-known in float calculations. One common example of errors due to the approximation of floating point numbers is that 0.1 + 0.2 does not equal 0.3.

1.  > 0.1 + 0.2;
2.  0.30000000000000004
Devtools console showing 0.1 + 0.2 is not equal to 0.3 but to 0.300000000000004.

Second, an integer has 2^52 relevant bits, the biggest integer is 2^53. There is one bit that determines the sign of the number, so the smallest signed integer is -2^53.

Note: Some arithmetic functions use only numbers with a 32-bit format. Larger numbers will be converted…

For more information about floating point numbers,  follow this link at Wikipedia.

1.5.5 JS operators and expressions

An expression is a small piece of code used to produce a value.

For example, the expression 3 + 5 produces the value 8, and the value 11 alone is also an expression. Within an expression, we can find values, variables, operators, and expressions. The first two have been already described above, all that's left are operators.

In JavaScript, an operator can be unary or binary (plus one ternary operator). A unary operator is applied to one expression. It can be prefixed or suffixed.

Unary operator example:
1.  typeof 'world';

A binary operator is applied to two different expressions, and is both prefixed and suffixed.

Binary operator example:
1.  var x = 45 / 32;
The division operator is binary

Within an expression, we can also use parentheses to force the execution of the expression inside. Parentheses can be used to indicate precedence.

For example, this is an expression: (3 + 2). And the expression (3 + 2) * 4, which equals 20, depends on the expression within the parentheses.

Operators.

In JavaScript, expressions can evaluate to four types, which are: numbers,  strings, booleans, and objects. For example, an expression with the operator -  will evaluate to a number. But an expression with the operator + can evaluate to a number or a string (for addition or concatenation).

1.5.6 Number Operators (4:12)

Live coding video: number operators

CodePen: Number operators.

Welcome to a short video about JavaScript number operators. The different operators you can use in numerical mathematical expressions are:
" + ", " - ", " / ", " * " and modulo, the percent sign (" % ").

You can use these operators in what we call mathematical expressions. An expression is something where you use "12 * 20". And you got a result. You can assign this to a variable: "var x =12 * 20" You can see that you can group different values or ….like this. And then, you can start building some more complex expressions. You've got the "*“ operator for multiplying, "/" for dividing, "+" and "–" for addition and subtraction.

There’s also an operator called modulo for example: "22 % 20". We display the rest of the division "22 % 20". "42 % 20" will display the same value. You can also regroup expressions within parentheses like: "var z = (12*20)/(x+10)".

This will work. It will first compute what is within the parentheses, then use the result for the final computation.

Nothing special to say here, but there are strange operators that are we called the prefix and suffix increment operators. So, if I declare variable "x" that has the value of "10". And if I display it, but I use “–- “ at this end, this will display the value of “x” and after that, it will decrement the value of "x" It will remove 1 from "x ". This is equivalent to writing: "var x= 10" … "console.log(x)"… and "x = x –1".

As you saw, it's longer to type all these instructions, but if I do just "console.log(x--)", it will do the same thing. It will display the current value of “x", but its final value is one less that. You can also post increment or post decrement values: " console.log(++x)". You remember that "x" was equal to "8". In that case, it will display "9" because "x" will be first incremented by one then displayed. If I display the value of "x" it’s "9"... Z= ++x ... "z" will be "9 + 1"… "10".

And "x" will be 10 because it's been incremented. This is equivalent to "x= x+1 ... Z= x". That's all we can say about number operators, nothing special. It's the same syntax you can find in the Java programming language or in c#, Python, or Ruby.

The following arithmetic operators are binary:
+, - , /, *, % (modulo)

Example: 7 % 5 equals 2, which is the remainder of the integer division of 7 by 5

Note: (7 / 5 = 5 * 1 + 2 ).

And there are also unary operators:

++, --, - (the opposite of a number)

++ and -- operators increment or decrement the value of a variable. They can be both prefixed or suffixed, which have different effects:

Examples typed in the devtool console of a browser

Example #1: simple operator use

Source Code:
1.  > 1 + 2;
2.  3
3.  
4.  > var a = 1;
5.  undefined
6.
7.  > var b = 2;
8.  undefined
9.  
10.  > a + 1;
11.  2
12.  
13.  > b + 2;
14.  4
15.  
16.  > a + b;
17.  3
18.  
19.  > var c = a + b;
20.  undefined
21.  
22.  > c;
23.  3

Example #2: more operators

Source Code:
1.  > 1 + 2;
2.  3
3.  
4.  > 99.99 - 11;
5.  88.99
6.  
7.  > 2 * 3;
8.  6
9.  
10.  > 6 / 4;
11.  1.5

Example #3: pre and post increments

Source Code:
1.  > var m = 0;
2.  Undefined
3.
4.  > m;
5.  0
6.  
7.  > // regular use of the + operator
8.  m = m + 1;
9.  1
10.  
11.  > m;
12.  1
13.  
14.  > m = m + 1;
15.  2
16.  
17.  > m;
18.  2
19.  
20.  > // post increment
21.  m++;
22.  2
23.  
24.  > m;
25.  3
26.  > console.log(m++); // will display 3 but after that m is incremented
27.  3
28.  
29.  > m;
30.  4

Below is snapshot with explanations:

Example console log.

Example #4: other versions of post and pre increments

Source Code:
1.  > var a = 123; var b = a++;
2.  Undefined
3.  
4.  > b;
5.  123
6.  
7.  > a;
8.  124
9.  
10.  > var a = 123; var b = ++a;
11.  Undefined
12.  
13.  > b;
14.  124
15.  
16.  > a;
17.  124
18.  
19.  > var a = 123; var b = a--;
20.  undefined
21.  
22.  > b;
23.  123
24.  
25.  > a;
26.  122

Example #5: short variant that mixes assignment and execution of an operator

Binary operators can be used with a shorter syntax when we want to assign the resulting value to a variable at the same time.
Code below (try it in the devtool console of your browser):

1.  > var a = 10;
2.  > a *= 5; // equivalent to a = a * 5;
3.  > console.log(a);
4.  > 50

Example #6: more with pre operators +=, -=, *=, /=

There are good chances you will encounter such code:

Source Code:
1.  > var a = 5;
2.  Undefined
3.  
4.  > a += 3 // equivalent to a = a + 3;
5.  8
6.  
7.  > a -= 2; // equivalent to a = a - 2;
8.  6
9.  
10.  > a *= 10; // equivalent to a = a * 10;
11.  60
12.  
13.  > a /= 5; // equivalent to a = a / 5;
14.  12
15.  
16.  > a %= 2; // equivalent to a = a % 2;
17.  0
18.  
19.  > // this is normal, as it is even

1.5.7 Strings, part 1

General use

To declare or manipulate strings you must write them with single quotes ' or double quotes " around them. Single quotes or double quotes are both accepted, and there is no difference between them in JavaScript. However, the community prefers to use single quote for string - this is not a convention, but a recommendation.

And finally, you cannot start a string with a single and end with a double quotes, or the opposite.

Source Code:
1.  > "Hello World";
2.  "Hello World"
3.   
4.  > "JavaScript Course";
5.  "JavaScript Course"
6. 
7.  > 'With single quotes';
8.  "With single quotes"
9.  
10. > "Do not mix double and single quotes'; // here we opened the string
with double and closed with single quotes
11. VM24763:1 Uncaught SyntaxError: Invalid or unexpected token
Image from the devtool console, from the example above:
Error; devtools console error; do not mix single and double quotes.
There are many reasons to use single quotes when possible:
  1. Double quotes are used in HTML
  2. You must hold the Shift key to type "
  3. Single quotes are easier to read and to type
  4. To output HTML in JavaScript, single quotes are more useful

1.5.8 String operators, part 2 (6:44)

Live coding video: string and string operators

Snapshot of a devtools console error; do not mix single and double quotes.

Strings can be defined using double quotes, or single quotes. Don't mix double and single quotes, it's not going to work. You can mix them, but inside a string defined with single quotes, you can use "hello my name is Michel...". This works because I used double quotes inside a string defined with single quotes. I can do the reverse: use single quotes inside a string defined with double quotes.

But if I wanted to use the single quote like for "I'm your teacher", you see that the color changes because this is not correct. In that case you must use the antislash (\)... Like this… you escape the single quote that confuses the JavaScript interpreter, and you can, in that case, display single quotes inside a string that has been defined using single quotes.

The \ character is also useful for printing special characters. For "s1 = My\n" ... it means "go to the next line"… if I print "s1 = My\\nName\\Is\\Michel". You saw the carriage return here, I came to the next line. Ok, let me fix it by adding \\n
In that case each word is on a different line. You can use also \\t for inserting a tab, and \\\\ for displaying the \\ character itself. In that case, you can display the \\ character itself using double antislash.

Let's talk about string operators. The "+" operator is the most common one, it's useful for concatenating values to any string. Let's look at one example.

Concatenation operator (+).

If I say 'my name is' + 'Michel Buffa', then you see that the result here is the concatenation of the string 'my name is' and the string 'Michel Buffa'. You can also use variables of different types, that will be converted to strings, if some parts of the + operator, some sides of the operator, are strings.

You see that the value of s is the concatenation of the string "value of x " and the number value of x (that was 10), has been converted and concatenated to it.

Variables, strings and concatenation.

There are also some ways to convert variables to strings. x here, is a number, but x = "" + 10; in that case, x is a string. You can also concatenate string values... s1 = "one", s2 = "two", if I concatenate these values here, s is equal to the concatenation of s1 and s2.

Shorthand assignment operator (+=).

There is also an assignment operator called += that can be very useful when concatenating values to a string. Like var s=Hello; s+="My friend", you give a value of s="Hello my Friend".
The += means s = s+something, it adds to the end of s. I can also use strings in mathematical operations, and they can be converted automatically.

Example, string and conversion to number.

I've got s2 that is 10. s2 is a string, and if I do s2=s2 * 2; in that case, s2 has been converted automatically. The value "10" as a string became 10 as a number. And s2 now is a number that is worth twice its previous value.

Example, string, number and Not a Number (NaN).

If I try to use a string that is not a number, not a value that can be converted to a number, like "hello"… in that case - if do the same operation - the result is NaN that means "Not a Number", you cannot convert "hello" to a number that can be used in a mathematical expression or multiplied by two.

Introduction to string operators

The concatenation operator (+)

The operator (+) used with strings is called the concatenation operator, and it allows you to concatenate strings.

Source Code:
1.  // the operator (+)
2.  var s1 = 'one';
3.  var s2= 'two';
4.  var s = s1 + s2;
5. 
6.  s;
7.  // returns 'onetwo'
8.
9.  typeof s;
10. // 'string'

The shorthand assignment operator (+=)

The shorthand assignment operator (+=) can also be used to concatenate strings.

Source Code:
1.  // the assignment operator (+=)
2.  var s1 = 'one';
3.  var s2 = 'two';
4.  s1+= s2; // or directly s1+='two'
5.  s1;
6.  // returns 'onetwo'

The method concat()

Another way to concatenate strings is the method concat():

Source Code:
1.  // the 'concat' method
2.  var s1 = 'one';
3.  var s2 ='two';
4.  var s = s1.concat(s2);
5.  s;
6.  // returns 'onetwo'

All the methods shown above can be used with a variable number of arguments:

Source Code:
1. var s1 = 'Hello';
2. s1 = s1 + ' World' + ' JavaScript';
3.  
4. var s2 = 'Hello';
5. s2+= ' World ' + ' JavaScript';
6.
7. var s3 = 'Hello';
8. s3.concat(' World' , ' JavaScript' );
9. 
10. // s1,s2 and s3 return 'Hello World JavaScript'

Converting strings

A String number in an arithmetic expression is converted to Number, unless the formula is a pure addition.

Source Code:
1.  > var s = '1'; s = 3 * s; typeof s;
2.  "number"
3.  
4.  > s;
5.  3
6.  
7.  > var s = '1'; s++; typeof s;
8.  "number"
9.
10. > s;
11. 2
12.
13. > var s = "100"; typeof s;
14. "string"
15.
16. > s = s * 1;
17. 100
18. 
19. > typeof s;
20. "number"
21. 
22. > var d = "101 dalmatians";
23. Undefined
24. 
25. > d * 1;
26. NaN

The above example is shown in the devtools console:

Devtools console; how to convert a number into a string.

How to convert a Number into a String

There is trick for converting a Number into a String: we concatenate with an empty string, at the beginning of expression (type this in the devtools):

Source Code:
1.  var n = 1;
2.  typeof n;
3.  // returns "number"
4.  n = "" + n;
5.  // returns "1"
6.  typeof n;
7.  // returns "string"

Special character: the "\\"

The \\ is useful for "escaping" special characters. Here are a few examples:

1.  var s = 'I don't know';
2.  var s = "I don't know"; // here the \ is useless
3.  var s = "I don't know";  // same result as previous line
4.  var s = '"Hello", he said.'; // ok, double quotes inside single one will be displayed
5.  var s = "\"Hello\", he said."; // double quotes inside double quotes need to be escaped

Escaping the escape! Use a double "\"

1.  var s = "1\\2"; s;
2.  // returns "1\2"

Special characters starting with "\"

"\n" for "next line":
Source Code:
1.  var s = '\n1\n2\n3\n';
2.  s
3.  // returns "
4.  1
5.  2
6.  3
7.  "
"\r" for "carriage return":
Source Code:
1.  var s = '1\r2';
2.  var s = '1\n\r2';
3.  var s = '1\r\n2';
4.  // the three previous lines give:
5.  "1
6.  2"
"\t" for "insert a tabulation":
1.  var s = "1\t2"
2.  // s is equal to
3.  "1 2"

1.5.9 Objects, part 1

We have already encountered objects in different examples. You can easily recognize these objects:

They are declared using "{" and "}", such as in var p = , givenName and familyName are called "properties" and Michel and Buffa are their respective values.

We are using the "." operator to access their properties or methods. Example : daysOfTheWeek.length (arrays are objects too - special ones, but objects), or document.body or window.innerWidth (try typing that in the devtool console). There are plenty of predefined objects in JavaScript (window, document, navigator, etc.). We have also used console.log(…), and indeed console is a predefined JavaScript object. With the object var p = {givenName:'Michel', familyName: 'Buffa'}, we can access the properties the same way, with: p.givenName and p.familyName.

Take a look at some common objects and properties!

Open your devtool console (F12 or ctrl-alt-i or cmd-alt-i on Mac), go to the console tab and type "window" followed by a ".", normally you should see an auto-completion menu. Start typing "inne" and you should see some possible completions.

Try looking at the values of the size of the current browser window (type window.innerWidth followed by the "enter/return" key, type window.innerHeight, etc.).

Try looking at the vendor of your browser: type "navigator.vendor", try looking at the current URL displayed in your window: type window.location, etc.

We will study these objects later, but for the moment, just play with objects :-)

Source Code:
1.  > window.innerHeight
2.  217
3.  > window.innerWidth
4.  1704
5.  > navigator.vendor
6.  "Google Inc."

You can define your own objects

There are many ways to create your own JavaScript objects. For the moment, let's stick to the simplest one, "singleton objects", and for now all you need to know is that they can have properties that hold values. We will return to objects in Week 4 and cover them in further detail.

Source Code:
1.  var student1 = {
2.    fullName:'John Doe',
3.    age: 23,
4.    city: 'New York',
5.    ssn: "11-22-33-44" // no comma at the end of the last property
6.  }                    // declaration

Accessing an object's properties: we use the operator "."

Source Code:
1.  > student1.ssn
2.  "11-22-33-44"
3.  > student1.age
4.  23
5.  > student1
6.  [object Object] {
7.    age: 23,
8.    city: "New York",
9.    fullName: "John Doe",
10.   ssn: "11-22-33-44"
11. }

1.5.10 Arrays, part 1

Definition: arrays are containers with indexes

Arrays are a special datatype. You declare arrays using brackets, like this:

var daysOfWeek = [];

You can fill them at declaration time:

1.  var daysOfWeek = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday'];
2.  var gradesInMaths = [12, 7, 14, 18, 9, 11];

Elements in an array can be accessed using indexes>

Each element in an array has an index. The first element's index is 0, the second element's index is 1 etc.

To access an element, you use the array variable and "[" followed by the index value followed by "]", as shown in these examples:

Source Code:
1.  var daysOfWeek = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday'];
2.  undefined
3.  daysOfWeek[0]
4.  "Monday"
5.  daysOfWeek[1]
6.  "Tuesday"
7.  daysOfWeek[2]
8.  "Wednesday"
9.  daysOfWeek.length
10. 7

Use the length property of an array to know its length

1.  var daysOfWeek = ['Monday', 'Tuesday', 'Wednesday', 'Thursday','Friday', 'Saturday', 'Sunday'];
2.  undefined
3.  daysOfWeek.length
4.  7

Indeed, there are seven days in a week and the daysOfWeek array has seven elements, indexed from 0 to daysOfWeek.length -1

This way of enumerating all elements (from 0 to the length of the array -1) is very, very common, and will prove to be very useful when you learn how to iterate on an array's elements (Week 2).

You can add elements to an array using a new index

If you want to add a new element at the end of an array, use the index equal to the length of the array.

Source Code:
1.  var daysOfWeek = ['Monday', 'Tuesday', 'Wednesday', 
    'Thursday', 'Friday';, 'Saturday'];
2.  undefined
3.  daysOfWeek.length
4.  6
5.  daysOfWeek[6]
6.  undefined
7.  // NO ELEMENT AT INDEX 6 in an array of 6 elements, first index is 0
    // last 6-1 = 5
8.  > daysOfWeek[6] = 'Sunday'
9.  "Sunday"
10. daysOfWeek.length
11. 7
12. // Sunday, the 7th day of week is at index 6 !

Arrays are JavaScript objects!

Well, this is not so important for the moment, but look:

Source Code:
1.  > var a [];
2.  > typeof a;
3.  "object"
4.  > var a = [1,2,3];
5.  > a
6.  [1, 2, 3]
7.  > a[0]
8.  1
9.  > a[1]
10. 2

And indeed, when you write daysOfWeek.length, you are using the array as an object, and you are using the length property of array objects.

Add an element at the end of an array using the push method

Since arrays are objects, we can do much more with them - in particular, they have more properties and more methods than the push method. You will learn more about this in a later lesson (Arrays part 2), but for the moment, let's focus on the most useful features…

Source Code:
1.  > var daysOfWeek = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'];
2.  undefined
3.  > daysOfWeek.length
4.  6
5.  daysOfWeek.push('Sunday');
6.  7
7.  > daysOfWeek
8.  ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"]
9.  > daysOfWeek.length
10. 7

Arrays and Strings

Strings are arrays of characters!

Consequence:

  1. They are objects too!
  2. They have a length property,
  3. Each individual character can be accessed using an index.
Examples:
Source Code:
1.  > var s = 'one';
2.  > s[0]
3.  "o"
4.  > s[1];
5.  "n"
6.  > s[2];
7.  "e"
8.  > s.length;
9.  3

1.5.11 Functions, part 1

Definition of a function

A function allows you to group code, give it a name and be able to execute it by calling it by name.

Functions always return a value:

Declaring a function

1.  function sum(a, b) {
2.      var c = a + b;
3.      return c;
4.  }

Calling a function

1.  var result = sum(1, 2);
2.  // result is equal to 3
3.  console.log(result)
4.  > 3

Function parameters

If parameters are omitted during the call, JavaScript gives them the value undefined:

1.  > sum(1)
2.  NaN

Functions with a variable number of parameters

An array named "arguments" is created automatically in each function, it contains all the call parameters of the function:

Source Code:
1.  function f() {
1.    return arguments;
1.  }
2.  …
3.  f();
4.  // returns []
5.  …
6.  if( 1, 2, 3, 4, true, ';Michel Buffa';);
7.  // returns [1, 2, 3, 4, true, "Michel Buffa"]

Example of the sum with a variable number of arguments

Source Code:
1.  function newSum() {
2.    var i, res = 0;
3.    var numberOfParameters = arguments.length;
4.    for (i = 0; i < numberOfParameters; i++) {
5.      res += arguments[i];
6.    }
7.    return res;
8.  }
9.  …
10. >>> newSum(1, 1, 1);
11. 3
12. >>> newSum(1, 2, 3, 4);
13. 10

1.6.1 Intro: Simple JS Examples to play with

This section does not detail the examples presented. Some of them are studied later in the course, some won't.

The examples are just here to bring some fun whilst making you play with some various uses of JavaScript. You are invited to look at their source code, and to tweak the examples. Do not worry if you don't understand how they work. We are just giving you "a taste" of JavaScript. There will be no graded exercises about them.

1.6.2 The devtool console

Using the console.log(…) instruction, you can write messages to the devtool console of your browser. This is a common way to debug your code!

For example, let's say you added a button to your Web page, but nothing happens when you click on it. It can be very difficult to spot your error without using the devtool console and console.log(…)!

Example

Let's check that some parts of the code you wrote are executed correctly.

CodePen: button click me to display the value of the x variable.
CodePen: button 'click me' to display value of x var.

Normally, when the button is clicked, we should call the addXToThePage()  function, which in turn should display the value of the variable x inside an HTML paragraph.

Let's check if the function is really executed. We need to add a console.log("In the addXToThePage function"); as the first instruction of the function:

CodePen: write messages to the devtools console.
CodePen: write messages to devtools console.

And let's execute this with the devtool console open (use F12 on Windows, or Cmd-Alt-i on a Mac, or control-shift-i). First, as the provided example is located on CodePen, an online IDE, it's better to execute it in "debug mode". The online IDE will just display a page (see snapshot below) with the code running:

Select Debug mode.

This action opens a new tab with only your code running in it (not the whole codepen IDE + your code!). Open the devtool console (F12 or control-shift-i or cmd-alt-i on Mac), and you should see this:

Console debug.

Now, press the button! An error message appears:

Error message in the devtool console.

Apparently the function name is wrong, addXToToThePage does not exist. We can check the source code by clicking on the YNbvoX:40 link on the right:

Source code that fired the error.

Our first error was that we typed the wrong name in the onclick="…", the name we used : AddXToToThePage has "ToTo" instead of "To". Let's fix that now and try again:

This time we entered the addXToThePage function.

After we've changed the name of the function to the correct one, let's go in debug mode, open the devtool console and click the button. Here is what we get:

CodePen; click me to display the value of the x variable.

Ok, you understand the principle… by using console.log(…) with a string message as parameter, you can make the message appear in the devtool console, confirming that you have executed your code without error at least to this point…

Let's fix this "X"! We'll replace it with an "x" and everything should be ok now:

CodePen; Write messages to the devtool console.
CodePen; write messages to the devtool console.

You can click on the button now….

Going further with console.log

Displaying variable values

Instead of just displaying pure string messages, you can also use the "+" operator to concatenate variable values to the pure character strings.

Example:

1.  var x = 2;
2.   
3.  console.log("The value of x is " + x + " and it';s ok like
    that.");

We typed this code in the devtool console to check what it does:

Type JavaScript code into the console.

You can use as many "+" as you like, the part right after the "+" will be turned into a string if the part in front is a string…

You can also use parentheses in order to display results of simple calculations:

1.  var x = 2;
2.  var y = 4;
3.  console.log("x = " + x);
4.  console.log("y = " + y);
5.   
6.  console.log("The value of (x+y) is " + (x+y) + " and it';s ok like that.");

Result:

Expression displayed using console.log.

You can use any operator (+, -, /, *, etc.), you are not limited to using the "+" operator. And of course, you can use such code in your programs, not only in the devtool console :-)

1.6.3 Modifying an HTML document

Don't worry if we do not explain all the details of this example. In the first module, we're giving you "a taste" of what we can do with JavaScript. Over the following modules, we'll delve deeper into the details…

We've already seen some examples that modify the content of the document dynamically. We changed a title by clicking on a button, we displayed the value of a variable named x in the previous section, etc.

The browser comes with some very powerful APIs (Application Programming Interfaces - a set of predefined objects/functions/variables you can use):

  1. "The selection API" is used for "selecting elements in the document". It uses the same syntax as CSS selectors.
  2. The "DOM API" for "Document Object Model" API. When we used document.body.innerHTML += "<p>The value of x is " + x + "</p>"; in a previous example, we used the DOM API for adding content to the body of the page (page = document).
  3. Another API is called the HTML Table JavaScript API, and is useful for building tables on the fly.
  4. etc.
CodePen: Contact list.
CodePen: contact list.

Just click the button to build the HTML table dynamically. You should see this:

Dynamic contact list; given name, family name.

1.6.4 Modifying CSS styles on the fly

We've already seen some examples in which we modify the style of some parts of a document using JavaScript. Here we show another example of what can be done.

Examples

Example #1: change common properties (color, border, background color)

Change common properties.
CodePen; change common properties.

Example #2: change the background image property using an external image

Change the background image property using an external image.
CodePen; change the background image.

Example #3: Use the background image as a sprite sheet - animate Mario!

Use the background image as a sprite sheet.
CodePen; use background image as a sprite sheet.

Notice how the CSS properties change when we use them from JavaScript:

And the positions, widths and heights are always string values. In our example we used pixel units and a percentage, so we need to add the "px" and "%" character(s) when we manipulate these properties from JavaScript.

1.6.5 Adding interactivity with events

With JavaScript, you can react to user interactions (keyboard, mouse, gamepad), to changes in the lifecycle of your document (page has just loaded or resized, screen has been rotated on a mobile device), or to be notified when a long process has been completed (loading a large image or sound from the network).

We've already seen how we can make a <button> react to a mouse click with <button onclick="…">Click me</button>

Below, we outline some extra examples. In the next course module, we will go into detail about events, and in the following modules, we will study some of the most useful events in even greater depth.

Examples

Example #1: use input events on an HTML input field

CodePen: Use input events on an HTML input field.
CodePen: use input events on HTML input field.

Example #2: listen to mouse events in an HTML5 canvas

The HTML5 canvas is useful for drawing and animating at 60 frames/second. Very detailed tutorials are provided in the W3C  HTML5 Coding Essentials and Best Practices course, while the W3Cx  HTML5 Apps and Games  MOOC addresses how to write video games using the canvas 2D API.

In this JS introductory course, we use HTML5 canvas to draw curves, to make a small game, etc. Small and diverse examples for illustrating some JavaScript data structures such as Arrays or Objects are going to be presented.

Listen to mouse events in an HTML5 canvas.
CodePen: listen to mouse events in HTML canvas.

Example #3: a paint program - click and drag mouse, then release

A paint program - click and drag mouse.
CodePen: a paint program.

Example #4: move a monster in an HTML5 canvas using left and right arrow keys

Move a monster in an HTML5 canvas.
CodePen: move a monster in HTML canvas.

1.6.6 Using built-in HTML5 APIs

Your browser comes with a lot of standard W3C APIs. By standard, we mean "parts of HTML5" or real Web standards that will still work in 10 years. In contrast to "industry standards", W3C standards are meant to be supported by browsers for years to come. These standards are a joint effort by the industry, the community, and W3C to develop stable, reliable standards.

The following example uses some of these APIs, simply to "show the possibilities". Others will be discussed later on in the course, or in other W3Cx courses.

Examples

Example #1: using the WebCam

CLICK ON THE TOP RIGHT OF THE BELOW WINDOW (on the "Codepen" logo) to see this example running. Due to security restrictions, the webcam image cannot be seen in this embedded example anymore.

Look at the JavaScript tab! The  W3Cx HTML5 Coding Essentials and Best Practices course provides many other examples that use the webcam.

CodePen; Example Webcam.
CodePen: example Webcam.

If you want to spend some time having fun with the WebCam, don't forget to try the WebCam Toy demo!

Example #2: using the WebAudio API to build a small synthetizer

Click on the piano keyboard. Use the different buttons, sliders, etc. This example uses the WebAudio API in order to synthesize sounds.

CodePen; Using the WebAudio API to build a small sythesizer.
CodePen: using the webaudio API to build a small sythesizer.
HTML:

I Hope you enjoy this pen, it was a lot of fun to make. Both mouse and keyboard is supported. However, make sure you click onto the preview window before using keyboard.

1.6.7 Using third-party JS APIs/libraries

Thousands of JavaScript libraries exist. Their purposes range from making it easier to plot a math function, playing  chiptune music, animating objects, through to visualizing data and much more.

Examples

We provide some examples below, but feel free to look on the Web for other external libraries.

Example #1: plot mathematical functions using the  function plot JavaScript library

There are numerous libraries for plotting math functions, but this one is pretty easy to use and very powerful. Here is an example that plots f(x) = x^2, then f(x) = sin(x) and finally a mix of fours functions : f(x) = x^2 (in red), f(x) = 3*x (in green), f(x) = cos(x) (in blue) and f(x) = -3*x^2 + x^2 (dashed)

CodePen; Plot mathematical functions.
CodePen: plot mathematical functions.

Here is another much simpler example, please edit the code (click on "edit on codepen") and change the function for something like f(x) = x^3 and look at the result (don't forget to change the xRange and yRange values). If you have trouble,  look here for a solution.

Plot force directed graph using d3.js.
CodePen: plot force directed graph using d3.js.

Example #2: plot a force directed graph using the d3.js JavaScript library

Try to click and drag nodes... All the graphics, animation and force repulsion, is done using the very powerful d3.js plotting library. Look at the HTML source code to see how we included this library in our HTML page. Look at the JS part; it seems complicated, but hey! I guess you can make your own graph with your own colors and your own node labels, without mastering JavaScript ;-) The beauty of this language is that you can find so many examples on the Web that you can easily learn by copying and pasting, tweaking code you haven't even written, etc. Go to codepen.io and use the search button for "d3" and you will find plenty of examples that use that library.

CodePen; A force-directed draggable graph.
CodePen: force-directed draggable graph.

Example #3: play chiptune songs using the chiptune.js library

I really like this example, as it takes me back to my youth playing games on the Commodore 64, the Nintendo NES console, etc. In that prehistoric age, there weren't a lot of kilobytes available in the memory, and most sounds were synthesized, not audio samples. The audio resolution in the past was lower than it is today. Audio chips utilized simpler DSP algorithms with less accuracy, and the sample rate was not the familiar 44.1 kHz that we are accustomed to now. Musicians used tools called "mod players/editors" for creating the music score (you can try a re-creation on the browser of a mod editor to see how it looked in the late 80's).

To try the example below, click on "load demo song", then on the play button. If you want to try other compatible songs, look for any .mod, .it, .xm song on the Web and drag and drop it into the example page. A good resource for such files is The Mod Archive, you can download plenty of chiptune files from there.

CodePen; Chiptune music with WebAudio.
CodePen: chiptune - load demo song.

Example #4: animate a sprite in an HTML5 canvas using the sprite.js library

This is just a small example of the use of the sprite.js library, which makes it easier to animate sprites (sub images from a big image called a "sprite sheet") in an HTML5 canvas. We will see how to use the HTML5 canvas later on in this course. The example is just here to illustrate what can be done using external libraries.

CodePen; Animate a green sprite.
CodePen: animate a green sprite.

1.6.8 Working with remote data

Let's see a few examples on how to work with remote data.

Examples

Example #1: use remote structured data

This example downloads and displays a list of users in a table (see remote data):

CodePen: Use remote structured data.
CodePen: use remote structured data.

Example #2: load and decode remote sounds for use in a video game

This example just shows how to use the HowlerJS external library to load remote sounds, decode them and play them as samples in memory (useful for video games):

CodePen: Load and decode remote sounds for use in a video game.
CodePen: load and decode remote sounds.

2.1.1 Intro Module 2: Adding Interactivity to JS Documents

Lesson: Introduction to Module 2

Learn how to handle events.

In this module, you will learn how to handle events (using a keyboard, a mouse, or a game pad), detect which button has been pressed, what is the position of the mouse pointer, what key has been pressed, etc.

You will discover the DOM API, as this is the standard application programming interface that will be used for interactive with the content of an HTML document.

In addition, we will introduce some new fundamental JavaScript bricks, such as conditional statements, logical operators (if, then, else), and loops. How to display multiple rows in a table, how to draw multiples graphical objects on the screen.

University Cote d'azur W3Cx.

Finally, we will write together a small JavaScript game using the HTML5 canvas API. Animating and drawing shapes at 60 frames/second is a lot of fun, and we'll make you play with the most of the language elements seen so far. And please, as I like video game, don't forget to share your project in the forum. And let other students enjoy your creation :D

2.1.2 Outline: Interactivity with JS

What you will learn in Module 2: Interactivity with JavaScript

2.2.1 Conditional Statements, Loops and Logical Operators (7:33)

Live coding video: boolean value, if…else statement and comparison operators

CodePen; Comparison Operators and the if, else statements.

Comparison operators and the if, else statements.

First, let's look at some code… We've got a "JavaScriptCourse" variable that we're gonna set to true, it's a boolean variable. And we're gonna see how this variable can be tested in a "if" statement. In order to use the "if" statement, we type "if", followed by parentheses, and by a block of instructions, that will be executed only if what is between the parentheses here, is true.

CodePen; This is a JavaScript course.

I'm gonna put this variable that we set to true, and add an instruction inside. We can see in the console that the instruction in the block has been executed, and "This is a JavaScript course" has been printed to the console log. This is because when the thing we test -the expression we test between the parentheses-is true, the block of instructions that follows the "if" statement, is executed.

If I set the variable to false and run the example again, then nothing is executed because the expression is false and the block of instructions is completely avoided. We can improve this example using an else statement. "This is NOT a JavaScript course!" I run it again. And the thing that is executed is the else block of instructions "This is NOT a JavaScript course!". If I set it back to true, you can see that it's a bit like a switch. It prints: "This is a JavaScript course!"

CodePen; Comparison operators.

Ok, let's see now comparison operators. They are: less than, more than, less or equals to, more or equals to, equals equals (that means "equals"), not equals (that means "different"), and a different version of these last two operators, that are called strict equals and strict not equals operators. And they are written === and !== . These last two syntaxes are preferred because they will avoid you a lot of errors.

I will show the differences in a minute, but consider these last with the three equals (===) and not equals equals (==), to be the ones you must use.

CodePen; Comparison operators; baby, child, adult or old.

Let's see some code now... I declared the variable "age" with a value of 1, and I added some if… else statements. If "age" is less than 2, print "I'm a baby", and you can see that this has been executed, because the variable is 1, 1 is less than 2. It's been executed... I can add some "else…if" statements.

CodePen; Comparison operators; baby, child, adult or old.

If age is 10, then in that case I'll go to the else statement and I will test again if in this case, age is less than 18. I'll print "I'm a child". And this works too. Only the second case has been executed.

The "if" block of instructions has been ignored, and the second "if" block of instructions has been executed. I can chain the "else…if" statements like that. And you can notice that I added at the end only an "else" statement, without an "if" behind. This means: "when all the other cases are false, please come here!".

CodePen; Comparison operators; baby, child, adult or old.

If I set my age to be 70, then in that case, all the tests will be false, and I will execute the block of instructions that is just after the last "else", and it prints "I'm old".

CodePen; Comparison operators; baby, child, adult or old.

I can also try… if the variable has some exact value using the == operator. If I set the variable to be 72, then this test is true and it prints "I'm 72" in the devtool console.

CodePen; example using AND operator (&&).

We can also use more than one test at once using logical operators. The double ampersand (&&) here is the AND operator. This will be true only is age is more than 12 and less than 14. If I set the variable to 13, it will print "I'm a young teenager" because both tests here, > 12 and < 14, are true.

CodePen; example using OR operator (||).

I can use also the OR operator. In that case, it will be true if one of the two are true. Let's try with age = 8. With age equals to 8, this is false, age > 12, but age < 14 is true, it prints "I'm a young teenager".

CodePen; example using triple equal sign (===).       CodePen; example using triple equal sign (===).

Finally, let's have a look at the === operator. If I set the age to be "72", but as a string, like this... it prints... let me clear the devtool console and execute it again... it prints "I'm 72" because the age variable, that is a string, has been converted implicitly to a number. If I use the triple equal sign, then it does not print anymore "I'm 72" because age, as a string, has not been converted to a number. And thrust me, it's much better to use the triple equals operator, it will avoid you many errors like considering a string as a number, and so on.

Source code of the example shown in the video

This example is available on CodePen

Before talking about how your JavaScript program can make decisions, such as "if this condition is fulfilled then I'll do this, otherwise I'll do that…", we need to define a few more concepts.

Let's start with "boolean values" and "logical operators".

Boolean values

The boolean type represents a logical entity having two values: true and false.

Use of the keywords true and false:

1.  var b = true; 
2.  var b = false;

A boolean variable should not be enclosed in quotation marks, otherwise it becomes a string variable:

1. var b = 'true'; // b is not a boolean but a string

Undefined and null values

Undefined

undefined is returned when a variable has not been assigned:

Source Code:
1.  var foo;
2.  > foo
3.  undefined
4.   
5.  > typeof foo;
6.  'undefined'
7.   
8.  > if (foo === undefined) {
9.    console.log('The variable foo has no value and is undefined');
10. }
11. 'The variable foo has no value and is undefined'

The above example shows how we can test whether a variable has a value (line 8 uses a conditional statement).

The keyword "undefined" is part of the JavaScript language, so you can assign the undefined value to a variable:

1.  > var foo = undefined; // equivalent to var foo; without giving any value
2.  undefined
3.   
4.  > foo;
5.  undefined

var foo; and var foo = undefined; are equivalent but we recommend that you use the first version to declare the variable (it is shorter, and that reduces the code).

If you try to access a variable that has not been declared before, a ReferenceError will be raised. But the typeof operator will return "undefined":

1.  > bar;
2.  ReferenceError
3.   
4.  > typeof bar;
5.  'undefined'

Logical operators

The logical operators are:

Source Code:
1.  var b = !true; 
2.  b; // false
3.   
4.  var b = !!true;
5.  b; // true
6.   
7.  var b = "one"; 
8.  !b;   false // implicit conversion of "one" to a boolean value
9.   
10. var b = "one"; // implicit conversion of "one" to a boolean value
11. !!b; // true

In an expression with logical operators, as shown in lines 8 and 11 of the previous example, non-boolean values are implicitly converted to boolean.

Lazy evaluation or short-circuit evaluation

Logical expressions are evaluated from left to right. JavaScript uses a mechanism known as "short-circuit evaluation" to prevent the second, third, and nth conditions from being tested in certain cases:

Examples:

Source Code:
1.  var b = 5;
2.  var c = 6;
3.   
4.  if ((b === 5) || (b === 6))  { // the second part is never tested
5.    console.log('b is equal to 5 or equal to 6');
6.  }
7.   
8.  if ((b === 5) && (c === 6)) {  // second part is evaluated
9.    console.log('b  is equal to 5 and c is equal to 6');
10. }
11.  
12. if ((b === 15) && (c === 6)) {  // second part is never evaluated
13.   console.log('b  is equal to 5 and c is equal to 6');
14. } else {
15.   console.log('b not equal to 15 or c not equal to 6');
16. }

Implicit conversions of non boolean values in expressions

Used with logical operators or within statements, non-boolean values are implicitly converted to booleans.

All the following values are evaluated as false:

Everything else is evaluated as true!

1.  var boo = 'hello' && 'world'; // boo is equal to 'world' that is 'true'.

In the above example, 'hello' && 'world' is evaluated as true but will return a value! Indeed, boo will equal 'world' because 'hello' is a string value that is evaluated as true. And 'world' is in also true as it's not one of the value cited in the previous paragraph. If we do : if (boo) then…. we will enter the if statement.

The rule is that both && and || result in the value of (exactly) one of their operands:

External resource:  The && and || Operators in JavaScript

TO SUM UP: it works "normally" if you just think true/false, but the real value affected is not true false, it's one of the operands, that can be seen as true/false.

1.  var boo2 = (0/0) || 43.2 ;

boo2 equals 43.2 because the expression 0/0 equals NaN, which is evaluated as false.

Question:

What is the value of the variable myNumber after the execution of this code?

Source Code:
1.  var myNumber = !1;
2. 
3.  if(myNumber == null){
4.    myNumber = 3;
5.  }
6.  
7.  myNumber = myNumber || 2;

Explanation: after the first line, myNumber equals false. In the if statement, at line 3, false does not equal null. Therefore, the value 3 is not assigned to the var myNumber. In the last line, myNumber is evaluated as false, then the value 2 is given to the variable myNumber.

Comparison operators

What is the difference between == and === in JavaScript?

Equal (==)

Returns true if the operands are strictly equal with type conversion.

Strict equal (===)

Returns true if the operands are strictly equal with no type conversion.

The triple-equals operator never does type coercion. It returns true if both operands reference the same object, or in the case of value types, have the same value.

Some examples:
Source Code:
1.  1 == 1;
2.  // true
3.  
4.  1 == 2;
5.  // false
6.  
7.  /* Here, the interpreter will try to convert the string '1'
8.  into a number before doing the comparison */
9.  
10. 1 == '1';
11. // true:
12.  
13. // with strict equal, no conversion:
14.  
15. 1 === 1;
16. // true
17. 1 === '1';
18. // false

Depending on the context, generally strict equal (or strict not equal) is preferred.

Best practice for beginners: always use === or !== for comparisons.

Here are interesting articles:

Specific case of NaN

As we have already seen, JavaScript has some special values. One of them is NaN: "Not-a-Number".

NaN has this special property:
1.  NaN == NaN;
2.  // false
3.  
4.  NaN === NaN;
5.  // false

Nan is equal to nothing - not even to itself!. But you do have a function to check the NaN value: isNaN(expr).

Source Code:
1.  isNaN(NaN);
2.  // true
3.  
4.  isNaN(0/0);
5.  // true
6.  
7.  isNaN(12);
8.  // false
9.  
10. isNaN('foo');
11. // true

"A reliable way for ECMAScript code to test if a value X is a NaN, is an expression of the form X !== X. The result will be true if, and only if, X is a NaN. " (see the  isNan documentation).

A complete example with isNaN:
Source Code:
1.  var num =0/0;
2.  
3.  if(isNaN(num)){
4.    num = 0;
5.  }
6.  // shortened version with the conditional operator
7.  var num = isNaN(num) ? 0 : num
8.  
9.  // version with logical operator (implicit conversion)
10. var num = num || 0;
11.  
12. /*
13.    <=> num = NaN || 0
14.  
15.    <=> num = false || 0
16. */
17.  
18. num;
19. // returns 0 in this three cases

Of course 0/0 rarely happens, but there are other cases where NaN can appear, for example:

2.2.2 Conditional statements (5:07)

Live coding transcript: switch statement

Switch conditional statement.

Hi! Let's have a look at the switch statement.

Switch conditional statement.

I prepared a small example in which we take a day number between 0 and 6, 0 for Monday, 1 for Tuesday, and so on... And to pick a random number that is an integer, we used a formula like this, that uses a predefined object called Math.

Math.random() between 0 and 1.

Math.random() returns a number between 0 and 1, 6 multiplied by this, will give a number between 0 and 7, and we just return the rounded nearest integer. When we execute this, "picked day number…" you see that it takes some random values each time we execute.

Using math.Random and switch.

If I clear the console and execute this, it will pick a number. And then, here is a first version that uses "if statements" that is a bit naïve. It says: if day equals 0, then print Monday; if day equals 1 ... ; and so on. Why is it naïve? Because we're going to execute all the tests and we all know that only one of them will be true.

Instead of multiplying series the tests, a better version is to use "if… else" statements, like this… so if day equals 0, then print Monday, else if day equals 1, print Tuesday… In that case, we're gonna test just until we find the day, and all the else will be ignored.

Using switch.

A much better version uses a switch. When you've got to make multiple tests, it might be more interesting to use a switch. switch(day). Then you test with the different possible values, using the "case" keyword. "case 0": that means that "if day equals 0, then execute console.log('Monday'). The break here means "ignore all the other cases".

When you put a break after each case, it's a bit like the "if…else" example we saw earlier: only one block of instructions will be executed here...You can see that the 3 different versions with the naive if, the if-else statement and the switch, give the same result.

Be careful because sometimes, if you forget to use a "break", you can enter different case statements. You can make errors if you don't know what to break keyword means, but it can also be useful to regroup cases.

Use switch to display days of the week.

For example, if I want to print "This is a week day, we go to work!", when we've got Monday, Tuesday… any day of the week! And if I want to print "Week end!" for Saturday and Sunday, then I can regroup cases like that.

You see case 0, case 1, case 2, case 3, case 4… and then just use a break after we executed the block of instructions that is related to all these five cases. Doing this, we will print "Week Day…" only if the day has a value of 0, 1, 2, 3 or 4, and we will print "Week end!" if it has a value of 5 or 6.

Use switch; week day and weekends.

Be careful because I saw this error a lot of time with beginners: you must use "case" only with a value after it, not an expression! This thing here case "day greater or equal than 0" or "day less than 4" is not valid. You cannot use an expression here, after the case. This is not going to work. Avoid! This… error!

Example; use an array.

And finally, there is a better solution to the problem I've illustrated. It's not to use any if or any switch…but use an array! If we've got an array that contains all the string values for the days of the week, we can just do a console.log… daysOfTheWeek… brackets, and use the day as an index. And this works too and it's only two lines of code.

Example from the transcript

CodePen example from the lesson above

JavaScript source code is a set of statements. There are a couple of different statement types. We have already seen one of them, the variable statement:

1.  var myVar = 'hello ' + 'world';

We've also seen the expression statement:

1.  3 + 4;
2.
3.  // more often like this
4.  var x = (3 + 4);
5.  var y = (5 + x);

A statement closes with a semicolon, but we will see later that missing semicolons are automatically inserted (for readability reasons, we highly recommend systematically adding a semicolon at the end of all statements).

Statements are generally executed sequentially from top to bottom of the script. However, this flow can be modified by statements such as conditional statements and iteration statements.

The block statement

The block statement is a simple statement which allows us to group a set of statements wrapped in curly braces.

Block statement:

1.  {
2.  var i = 0;
3.  var result = false;
4.  console.log('i = ' + i);
5.  }

The block statement is used by other statements such as the if-statement or for-statement. We will see these statements below.

Conditional statements

All the examples for this section are in this codepen (to run it: click on the "edit on CodePen" label, and once in CodePen, open the devtool console to see the outputs of this program):

CodePen: example; devtool console to see output.
CodePen: example devtool console to see output of this program.

(Please look, edit and try whatever you want. There are parts that are commented - please remove comments and try to understand the results).

Conditional statements are used to execute a unit of code only if a condition is evaluated as true.

The if statement

Syntax:
if ( Expression ) Statement else Statement
if ( Expression ) Statement
The expression may include:

Example #1: if-statement

Source Code:
1.  var num = 10;
2.
3.  if (num === 10) {
4.    num = 20;
5.  }
6.
7.  // num equals 20

Example #2: if-else statement

Source Code:
1.  var num = 10;
2.
3.  if (num >; 10) {
4.    num = 20;
5.  } else {
6.    num = 0;
7.  }
8.
9.  // num equals 0
Reminder:

The following values will evaluate to false:

All other values, including all objects, evaluate to true when passed to a conditional statement.

The if-then-else ternary operator

This ternary operator is a shortcut version of if…then…else.

Let's look at this code example:
Source Code:
1.  var max;
2.  var min = 2;
3.
4.  if (min < 10) {
5.    max = min + 10;
6.  } else {
7.    max = min;
8.  }

Explanation: You can replace this "if-then-else" statement with the ternary operator that uses a syntax with "?" and ":"

1.  var max;
2.  var min;
3.  max = (min < 10)? min+10 : min;

Line 3 can be read as if (min < 10) then max = min+10, else max = min. The "then" part is after the "?" and the "else" part is after the ":" part.

This "short" version is not recommended except for very simple statements that involve a very obvious block of instructions for the "then" and the "else". Usually this syntax is much harder to read for beginners.

Curly braces

Should we use them in if-then-else statements? There are examples without curly braces on the Web: what does this mean?

Here are two versions of the same code.

Version 1: no curly braces
1.  if (a > 2)
2.    result = 'a is bigger than 2';
3.  else
4.    result = 'a is not bigger than 2';
Version 2: with curly braces for delimiting the "then" and "else" blocks.
1.  if (a > 2) {
2.    result = 'a is bigger than 2';
3.  } else {
4.    result = 'a is not bigger than 2';
5.  }

Version 1 and version 2 are equivalent. Indeed, version 1 is correct: you can omit curly braces if the "then" or "else" blocks are made of only one statement (one line of code).

But version 2 is cleaner and more readable, and, in particular, it is much better for maintainability (because you can add a statement just by pressing the enter key. And you can add some extra lines of code without worrying about adding curly braces because you broke the "1 line statement rule").

It is strongly recommended that you always use if-statements enclosed in curly braces.

Of course, one-line if-statements like this:

1.  if (true) doSomething();

…are fast to write, but if you want to add a second statement later it will become more time consuming.

Conclusion: always use curly braces!

The switch statement

In order to avoid having a series of ifs and elses, it is possible to use a switch statement.

The syntax of the switch statement is:
Source Code:
1. switch (expression) {
2.    case value1:
3.      Statement
4.      break; // break can be omitted in that case
5.             // the second test case will be executed
6.             // most of the time we add a break; at the end
7.             // of a "case"
8.
9.    case value2:
10.      Statement
11.      break;
12.
13.   case value3:
14.     Statement
15.     break;
16.
17.   default: // if no case tested true
18.     Statement
19.     break;
20. }

If the value of an expression equals one of the cases (the equality operator evaluated is ===), all the statements next to this case block are executed sequentially until the keyword break is reached.

Example #1: a common switch/case/default example

Source Code:
1.  var gear = '';
2.   
3.  switch (cloudColor) {
4.    case 'green':
5.      gear = 'spacesuit';
6.      break;
7.
8.    case 'black':
9.      gear = 'boots';
10.     break;
11.
12.   case 'grey':
13.     gear = 'umbrella';
14.     break;
15.
16.   case 'white':
17.     gear = 'jacket';
18.     break;
19.
20.   default:
21.     gear = 'watch';
22.     break; // useless if in the last case
23. }          // end of the switch statement

In this example, if the clouds are grey, then my gear will be just an umbrella. If they are white, I'll wear only a jacket, if they are black I'll be nude with just boots (!), and if they are green I'll get a spacesuit. And if the cloud color is none of these, then I'll only wear a watch. The presence of the break keyword at the end of the different cases make the choices 100% exclusive. Only one case can be executed!

Example #2: a switch without "breaks" at the end of each case

Source Code:
1.  var gear = '';
2. 
3.  switch (cloudColor) {
4.    case 'green':
5.      gear += 'spacesuit';
6.      break;
7.
8.    case 'black':
9.      gear += 'boots, ';
10.
11.   case 'grey':
12.     gear += 'umbrella, ';
13.
14.   case 'white':
15.     gear += 'jacket, ';
16.
17.   default:
18.     gear += 'watch';
19. } // end of the switch statement

Explanation: if the clouds are black, then my gear will be 'boots, umbrella, jacket, watch'. If the clouds are green, my gear is a spacesuit (because of the break keyword, other cases will not be tested). If the cloud color is not in the listed colors, then my gear is only a watch (default case).

Example #3: three ways to do condition statements

To finish up this section, here is a complete example (to run it: click on the "edit on codepen" label and once in codepen, open the devtool console to see the outputs of this program):

Look at JS from this example, open devtools.
CodePen: open devtools to see the outputs.

2.2.3 Loop statements (8:06)

Live coding video: loop statements

Loop statements.

Let's talk about loop statements.

There are different loop statements in JavaScript.

While loop, 1 to 3, and sum of sum.

One is the "while" loop statement. It starts with some initializations, you give some values to some variables, then you use the keyword "while" followed by an expression that you will test. It will be evaluated as "true" or "false".

When this expression is false, you continue after the block of instructions that is inside the loop. Let's start with an example. We've got here some initialization: "var n = 1, m = 1;". We've got the keyword "while" followed by the condition, "n less than 4", followed by a block of instructions that will be executed as long as the condition is evaluated as true.

With n = 1, n is less than 4, we execute the block of instructions. Inside the block, n is incremented, n += 1, then n = 2, it's still less than 4, we continue, n = 3, it's still less than 4, we continue, n = 4, then the condition is false: 4 is not strictly less than 4, and we continue after the loop and the console.log is executed.

While loop, n and m.

Let's have a look at the execution of this program. While it's executed, it prints in the body of the loop console.log, it prints n = 1, this is the initial value, n = 2, n = 3… when n = 4 the condition is no more true and we go at the next instruction after the block of instructions of the loop. Inside the loop, we also incremented the variable m by adding the consecutive values of n. And m had a starting value of one. 1 + 1 + 2 + 3 + 4 …. the final result is 10 as you can see.

Do while loop, 0 to less than 20.

The second kind of loops you can use are called the "do…while" loops.

They are very similar to the while loops except that the first execution of the block of instructions does not depend on any condition. The condition of the loop is at the end, after the keyword "while". Do something… while the condition is true… Let's look at this example: we've got a variable i that has a value of zero, and we increment it in the loop, but before incrementing it we print its value.

The final condition is "i strictly less than 20". We are going to execute this for 0, 1, 2... and when i++ will give a value to i that is 20, then the condition will be no more true, and we will finish the execution of the loop and execute the console.log that is here.

Do while loop, 0 thru 19 (under 20).

Look at the devtool console:

We executed the loop for i = 0 to i = 19. After the last display of the value, we incremented i, the condition was false, i is 20 now, and we printed its value.

The last sort of loop statements you can use are called "for" loops. The syntax is like that: "for" followed by parenthesis, followed by a block of instructions. And in the parenthesis you've got three different parts separated by semicolons.

The first part is the initialization part, then the "condition ». As long as the condition is true, the block of instructions will be evaluated. And there is something called the "final expression": it's a set of instructions that will be executed like if they were located at the very end of the loop, as the last instruction.

Usually we increment some variables, or decrement some variables that will make, after a certain number of executions of the loop, the condition false.

For loop, 0 thru 4.

Let's try a small example: we are going to count one by one from an initial value to an end value. You see: I counted from 0 to 5, not included, because of the "less than" operator here. I counted for i equals 0, 1, 2, 3, 4… then, when i is equal to 5 the condition is no more true and we exit the loop.

For loop, 0 thru 4.

We can also use less than or equal to. In this case we counted to the final value and included it.

Increment loop by 2.

We can also increment the loop 2 by 2. In that case (let me clear and execute again), we run the loop with a value of i = 0, i=2, i=4, i=6, the condition is no more true, we exit from the loop.

daysOfTheWeek array enumeration; Monday thru Sunday.

We can also iterate on the elements of an array. This is very common. We've got an array here called "daysOfTheWeek" and we are going to enumerate all the elements inside.

Let's make a "for" loop, and the final value… the number of times we are going to iterate is the number of elements in the array. It's given by the "length" property of the array. What we did: we executed the loop from i = 0, to i = 1, 2, 3, 4, 5, 6, 7! This is the value of "daysOfWeek.length", and we incremented the i variable at the end. We did this for i = 0, 1, 2, 3, 4, 5, 6 and we displayed the element with the index equal to i, inside the loop.

Example from the lesson

Example on CodePen

A loop in the sky.

Loops

A loop is used to run the same block of code several times while a condition is satisfied.

If you have trouble with loops, the online tool  slowmoJS can be really useful: you just have to copy and paste an example into it to run it step by step and see how your program executes loops.

The while statement

With a while statement, a block of code is executed repeatedly while the specified condition is satisfied (evaluates to true).

Syntax:

while ( condition ) statement

The condition is an expression, and the statement can be a block statement.

Typical example of a while statement:

Source Code:
1.  var i = 1, j = 1;
2.   
3.  while ( i < 4 ) {
4.    j += i;
5.    i += 1; 
6.  }
7.  …

The block inside the while (lines 4 and 5) will be executed three times:

Of course, if the condition never evaluates to false, the block will be executed infinitely until the machine crashes… a test like while (i > 0) { …..} will never stop and will eat all the CPU.

Try this example now with  slowmoJS!

The do-while statement

The do-while statement is very similar to the while statement, but its syntax is different:

do statement while ( condition )

Typical example:

Source Code:
1.  var i = 0;
2.  do {
3.    console.log('i = ' + i);
4.      i++;
5.  } while(i < 20);
6.  console.log('Value of i after the do-while statement: ' + i);

The do-while statement executes the content of the loop once before checking the condition of the while, whereas a while statement will check the condition first before executing the content.

A do-while is used for a block of code that must be executed at least once.These situations tend to be relatively rare, thus the simple while-statement is more commonly used.

If you want to "see" the difference,  look at the "do-while" statement with slowmoJS and  the "while" statement slowmoJS.

The for statement

This statement adds some things to the while and do-while statements: an initialization expression and an incrementing expression.

Its syntax is:

for (initialization; condition; incrementation) statement

The three expressions within the parentheses are optional. If the condition is omitted, it is replaced by true (infinite loop).

Typical example (counting from 0 to 10):

1.  for (var i = 0; i <= 10; i++) {
2.    console.log('i = ' + i);
3.  }

We can have more than one instruction in the "initialization part" (var i = 0), and more than one instruction in the "incrementation part" (i++). Here is another example:

1.  for (var i = 1, j = 1; i <= 10; i++, j+=2) {
2.  console.log('i = ' + i + ' j = ' + j);
3.  }

In this example, two variables are defined and assigned within the initialization expression. Before each execution of the block statement, the condition is checked; here we need i <=10. After each execution of the block statement, the incremental expression is executed to increment the variables i by 1 and j by 2.

Open the devtool console of your browser and copy and paste the above code, or  look at the slowmoJS execution.

The for-in statement

The for-in statement is used to iterate through an object (or through an array, which is also an object).

Its syntax is:

1. for ( variable in expression ) statement
Typical example:
Source Code:
1.  var michel = {              // michel is an object
2.      familyName:'Buffa',     // familyName, givenName, age
3.                              // are its properties
4.      givenName: 'Michel',
5.      age: 51
6.  }
7.   
8.  for(var property in michel) {   // the for-in will
9.                                  // enumerate properties
10.     console.log(property);      // will print "familyName",
11.                                 // "givenName",
12.                                 // "age"
13.     console.log(michel[property]);  // michel['givenName']  same 
14.                                     // as michel.givenName
15. }

Before each execution of the block statement, the variable named "property" is assigned with the name of one of the properties (the keys) of the object. We will see further examples of this statement in module 4, which is devoted to the study of JavaScript objects.

[ADVANCED] Other statements

The continue statement

The continue statement is used to stop the execution of a block and start the next iteration of the loop. The difference from the "break" statement is that the loop continues.

Syntax:

1. continue [label]

The label is optional.

Typical example:

Source Code:
1. for(var i = 1, k = 0; i < 5; i++) {
2.   if (i === 3) {
3.     continue;
4.   }
5.
6.   k += 2*i;
7.     console.log('k += ' + (2*i));
8. }
9. console.log('Final k value:' + k)

Copy and paste this example in your devtool console, but first, try to guess what the value of k will be!

Hint: lines 2-4 mean that line 6 will never be executed for i = 3. That means that i*2 will only be added to k for i = 1, 2 and 4...

The break statement

The break statement is used to stop an iteration, a switch or a labelled statement.

Syntax:

1. break [label]

Typical example:

Source Code:
1.  var tab = ['michel', 'john', 'donald', 'paul']; // johh at index = 1
2.  
3.  function isNameInTheArray(name, theArray) {
4.    console.log("Number of elements in the array : " + theArray.length);
5. 
6.    for(var i=0; i < theArray.length; i++) {
7.      console.log('comparing with element in the array at pos ' + i);
8.  
9.      if(theArray[i] === name) {
10.       console.log('the name ' + name +
11.       ' is in the array at pos: ' + i);
12.       break;
13.     } else {
14.       console.log(name + ' is not at pos ' + i);
15.     }
16.   }
17. }
18.
19. // Execute the function
20. isNameInTheArray('john', tab);

Copy and paste in the devtool console. You'll see that the function that compares each element in the array passed as the second parameter with the name 'john', will stop looping after 'john' has been found at index = 1.

Detailed explanations:

2.2.4 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topic of discussion:

Optional projects:

Hint: use the Math.random and Math.round methods, such as in let randomNumber = Math.round(Math.random() * 10); to get a random value between 0 and 10.

For working with input fields, look at section 1.4 from the first module, the math function plotter example used input fields. Or look at the section about DOM in this module.

Quiz.

2.3.1 Functions and Callbacks

Let's see how to declare a function and a callback.

Functions

There are two ways to declare a function.

1) Standard function declaration

We've already seen that functions can be declared using this syntax:

1.  function functionName(parameters) {
2.  // code to be executed
3.  }

A function declared this way can be called like this:

1. functionName(parameters);

Notice that we do not add a semicolon at the end of a function declaration. Semicolons are used to separate executable JavaScript statements, and a function declaration is not an executable statement.

Here is an example:

CodePen: sum function & displayinpage function.
CodePen: sum and displayInPage functions.

In the above example, the sum function returns a value, and the displayInPage function does not return anything.

2) Use a function expression

A JavaScript function can also be defined using an expression that can be stored in a variable. Then, the variable can be used as a function:

Here is a typical example:

CodePen: sum and displayInPage.
CodePen: displayInPage & sum functions.

Notice how the sum and displayInPage functions have been declared. We used a variable to store the function expression, then we can call the functions using the variable name. And we added a semicolon at the end, since we executed a JavaScript instruction, giving a value to a variable.

The "function expression" is an "anonymous function", a function without a name, that represents a value that can be assigned to a variable. Then, the variable can be used to execute the function.

We say that functions are "first class objects" which can be manipulated like any other object/value in JavaScript.

This means that functions can also be used as parameters to other functions. In this case they are called "callbacks".

Callbacks

Indeed, as functions are first-class objects, we can pass a function as an argument, as a parameter to another function and later execute that passed-in function or even return it to be executed later. When we do this, we talk about callback functions in JavaScript: a function passed to another function, and executed inside the function we called.

All the examples of event listeners that you've seen used callback functions. Here is another one that registers mouse click listeners on the window object (the window objects represent the whole HTML document):

CodePen: processClick.
CodePen: processClick function.

In this case, the processClick function is passed as a parameter to the addEventListener method/function.

Callback functions are derived from a programming paradigm known as functional programming. They are very common in JavaScript. We'll use them a lot in the next section of the course, called "Handling events".

2.4.1 Intro: Handling Events

Adding interactivity to a Web application can be achieved by using only CSS, such as by using the :hover pseudo CSS class.

For example:

CodePen: :hover.
CodePen: :hover.

However, firing a specific action when the button is clicked, knowing which mouse button has been used, computing the (x, y) mouse pointer position in the button system coordinate, or executing more complex tasks can only be done through JavaScript.

With JavaScript, a button click, a move of the mouse, a resized window, and many other interactions create what are called "events". The timing and order of events cannot be predicted in advance. We say that "event processing" is asynchronous. Web browsers detect events as they occur, and may pass them to JavaScript code. They do this by allowing you to register functions as event listeners, also called handlers or callbacks for specific events.

Each time an event occurs, the browser puts it in a "queue of events". Then the browser looks at a list of "Event Listeners" and calls the ones that correspond to the type of event "they listen to".

2.4.2 Adding and removing event listeners to a document

Live coding video: adding an event listener to a document

Adding event listener to a document.

Hello. Let's see how events work in JavaScript. In this video, I will show you how to add a simple event listener for detecting clicks or mouse moves, and we will start with the simplest example.

It's listening for events that will occur anywhere on the Web page.

Listen to mouse clicks and add an event listener.

When we add an event listener to the whole page, the syntax is this one: you can type "AddEventListener", followed by the name of the event.

Here we are going to listen to mouse clicks. And then indicate the reference of the callback function that will process the event. Let's write this callback... and let's try it! I clicked on the page anywhere, and an alert message appeared.

This is the first syntax, and there is a variant that is very common in JavaScript, when the length of the callback (source code) is small, you can directly add the callback inside the parenthesis of the AddEventListener call.

anonymous function, callback.

Let's see this example… I'm going to comment the first example, and this time, instead of just adding as an argument the name of the callback, we directly put the body of the callback.

A function... and we don't have to indicate a name: it's an anonymous function, an anonymous callback. When we click on the page, we will execute this callback that is located exactly as the second argument.

If I click on the page, you can see that it works again. And this syntax is very common! Notice the parenthesis, followed by a semicolon at the end, because this is just like a parameter.

It's an anonymous callback function, that is the second argument.

window.onclick = function(evt).

Finally, there is a first syntax, that uses the the object that will fire the event. The window object is the whole document. We start with "on" followed by the name -in lowercase- of the event, and we assign to this property "onclick", we assign directly the function.

anonymous function.

We can directly type the anonymous function, like that. We add a semicolon because this is a an executable statement. And if I click… …it works. Okay, or I could have used the same syntax we saw earlier, with a regular callback function with a name, and we just indicate onclick equal the name of the callback, like this, which is the same name… So if I click, it works.

Online example used in the above lesson

2.4.2 cont'd; Adding and removing event listeners to HTML element

Live coding transcript: adding an event listener to a specific HTML element.

How to add an event listener to html element.

In this lesson, I will show you how to add an event listener to an html element, and not to the whole document, like in the previous lesson.

CodePen: onclick = name of function.

Let's try with a button. One of the easiest way to detect a click on a button is to use the onclick = name of the function, name of the callback that will process the function. In that case, we can locate the body of this callback anywhere in the script element.

We can, for example, put the script element in the head element at the top of the html document. Let's try like that… In that case, you see, when I click, the processClick callback is called. I always add an argument here, that is not used in this example, but it will be the topic of a next video. Here, I'using just the DOM API for adding some text to the document.

CodePen: document.querySelector.

If you want to use the other syntax with addEventListener, you must take some precautions. You will need first to locate the element, so that you can manipulate it from JavaScript. For that, we usually add an id attribute so that we can identify the element. And then we use a script element. I'm putting this one at the end of the document.

There is a good reason for that, that I will explain. And first, I get a reference on the element. For that, we use the selector API: it's a built-in feature that is in your browser, that is very useful for getting references on elements. document.querySelector is the name of the method we are going to use.

And then, we use a CSS3 selector. Notice that the id I use is the same I used in the declaration of the html button.

document.querySelector and addEventListener.
CodePen: querySelector and addEventListener.

Once I've got the reference on the object, I can add the event listener. Let's try it. I click on the button and I get an alert. You must understand that when you execute document.querySelector, the button must exist in the page and must has been rendered. We say that "the DOM of the page must be ready".

When an HTML page is rendered, it's sequential, it goes from top to bottom, so in that case, the button is created, added to the DOM, then the script is executed, and document.querySelector will return a reference on the button.

If I move this script tag before the button, in that case, it's not going to work because the b variable here will correspond to nothing, it will be null because there is not yet a button in the DOM. And if we look at the devtool console, we see "cannot read property addEventListener of null". This occurs at this line, we try to run addEventListener on a variable that is null. Be very careful, do not try to select an HTML element when the DOM is not yet ready.

Online example used in the above lesson

Event listeners: a typical example

Here is one possible syntax for registering an event listener that listens to "click" events on any part of the window (clicks anywhere on a web document will be processed by this event handler):

1. <script>
2.   addEventListener('click', function(evt) {
3.     document.body.innerHTML += 'Button clicked!';
4.   });
5. </script>

Try it below by clicking anywhere on the document:

CodePen: addEventListener function.
CodePen: addEventListener function.

The addEventListener function is one possible syntax for registering a function to be called when a given type of event occurs.

1. addEventListener(type_of_event, callback_function)

In the example below, the type of event is a 'click', and the callback function is the part in bold:

1. function(evt) {
2.    console.log("Button clicked!");
3. }

When this function is small (a few lines of code), it's common practice to put its body as the second parameter of the addEventListener function.

In other words, this:

1.  <script>
2.  addEventListener('click', function(evt) {
3.      document.body.innerHTML += 'Button clicked!';
4.  });
5.  </script>

… is the same as this (the function called when a click occurs has its body "outside" of the addEventListener parameters, and we use its name as the second parameter):

Source Code:
1.  <script>
2.    addEventListener('click', processClick);
3.    function processClick(evt) {
4.      console.log("Button clicked!");
5.    }
6.  </script>

Adding an event listener to specific HTML elements

Instead of listening to event on the whole document (using addEventListener  is the same as using window.addEventListener), we can listen to specific DOM elements. For example, here is how we can listen to clicks on a specific button (whereas clicks on the rest of the document will be ignored).

CodePen: Click me!
CodePen: Click me!

In this example, instead of using the addEventListener method directly, we used it on a DOM object (the button):

  1. Get a reference of the HTML element that can fire the events you want to detect. This is done using the DOM API that we'll cover in detail later in this Module. In this example we used one of the most common/useful methods: var b = document.querySelector("#myButton");
  2. Call the addEventListener method on this object. In the example:  b.addEventListener('click', callback)

Every DOM object has an addEventListener method. Once you get a reference of  any HMTL element from JavaScript, you can start listening to events on it.

An alternative method for adding an event listener to an HTML element: use an "on" attribute (ex: onclick = "….")

Instead of using b.addEventListener('click', callback), it's possible to use an onclick='doSomething();' attribute directly in the HTML tag of the element:

CodePen: processClick(event).
CodePen: processClick(event) example.

This syntax:

1. <button id="myButton" onclick="processClick(event);">Click me!</button>

… is ok when you only need a single event listener to click events for this button, as there can be only one onclick attribute per element. Using the b.addEventListener('click', callback) syntax,  you can register more than one event listener. You'll need rarely to do this, so in my opinion it's fine to choose whichever syntax you like.

Remember that for big projects, it's always better to separate the HTML, CSS and JavaScript code. In this case, I'd recommend that you put all your event listener definitions in a separate JavaScript file, and use the addEventListener syntax in preference to the "on" attributes syntax.

Removing event listeners

When we click on the button, we execute the processClick(evt) callback function, and inside we remove the listener we previously registered. Consequence: if we click on the button again, nothing happens as there is no longer a click event listener attached to it.

CodePen: add and remove event listeners.
CodePen: add and remove event listeners example.

Note that to remove an event listener, you should have added it with its named function, so that we can pass it to both addEventListener and removeEventListener.

2.4.3 The Event Object

The event object is the only parameter passed to event listeners.

Typical example:

1.  function processClick(evt) {
2.      alert("Button clicked!");
3.  }

Each event listener has a single parameter that is  a "DOM event object". It has various properties and methods that can be very useful.

For example, with a 'keyup', 'keydown' or 'keypress' event, the event object contains the code of the key that has been pressed/released, with a 'mousemove' listener we can get the relative position of the mouse in the DOM element that has generated the event, etc.

The event object contains some important properties and methods that are common to all types of events:

It also contains properties that are associated with the type of the event, for example:

In the subsequent sections of this course we will look at the most common types of events in detail.

Reference table

The most useful common properties are:

Most useful properties; type & target.

The most useful common methods are:

Most useful methods; preventDefault & stopPropagation.

2.4.4 Page lifecycle events

Live coding video: page ‘load’ event and the event object

Page lifecycle events.

This time let's talk about the event object, and we'll start looking at different types of events.

Load event; onload = callback.

One of the events you will use is called the 'load' event, and you can apply it on the page using onload equal followed by the name of the callback.

I usually call this callback "init" and this is a good practice: always use a function that will be called when the page is loaded. I'm adding a console.log message just to verify.

onload='init()'; dom is ready.

I open the console, and you can see that if I save the document and run again the example, or if I clear the console and execute it again, this callback is called when the page is loaded… that means "when the DOM is ready".Then, from this function, I can call any other function, I can execute any kind of code, I will never have to wonder… to think: "is the DOM ready?"

function init() page loaded (or not).

For example, to update this part of the page… I use a span with an id attribute. I can locate the span… and like this… using the querySelector method and a CSS selector on the id… "pageStatus" is the id of the element… Then I can change the content of the page… If you look at what is happening when I execute the code, it says "page loaded". This is a very good practice. I nearly always do this on my own softwares.

window.onload = init().

Another variant is that instead of using the "onload" syntax, you can just write window.load = init.

This will produce the same result… onload… and in that case, instead of using body onload…you use window.onload. It's a bit better because you do not mix JavaScript and html, it's a better separation of the different parts of your Web application. You may notice that here I haven't typed the event argument. Every event callback will have an event object passed by the browser when the event is processed.

CodePen: Page Status: Page Loaded.

And this event object can be used to guess what type of event has been fired, can be used to get the different properties of the event, such as the x and y positions of the mouse, the button that has been clicked, the target element that fired the event and so on…

If now, for example, I want to listen to events on a button… a bit in a similar way we presented in a previous example… I can add a listener in the init function…and in this listener, I can, for example, display the name of the button that has been used for clicking. Let's try it… here is the console, I clear it, then I click on the button, and it says it's button 0.

You can also try different types of events, like detecting mouse moves. In that case, we are going to detect mouse moves on the button, and you can see in the console that it works.

You can, for example, use the event object to detect the x position of the mouse.

CodePen: get position of mouse.

There are different properties for getting the position of the mouse, relative to top of the page, relative to the top of the viewport or relative to the the element that fired the event. This is detailed in the section about mouse events.

But here, I'm just showing you one the most common property, that is called clientX: it gives the position of the cursor, relative to the top of the page. Just as an example of using the different properties of the event element.

In the next sections, for each kind of event, we'll detail the different properties and provide examples that show how to use them.

Online example used in the above lesson video.

The page lifecycle events detect when the page is loaded and when the DOM is ready.

Events related to the page lifecycle

There are many other events related to the page life cycle. The most useful ones for an introduction course are shown below:

Load, Resize and Scroll events.

Page event properties

There are no particular properties that need to be mentioned here. Usually, the load event listener corresponds to a JavaScript function that can be seen as "the main" function of your Web application. It is a best practice to start everything after the page has been completely loaded.

In the resize listener, you get the new size of the window, or the new size of some HTML elements in the page (as they might have been resized too when the window was resized), and then you do something (redraw a graphic in an HTML canvas that takes into account the new canvas size, for example).

Example 1: wait until the page is loaded (when the DOM is ready) before doing something

This first variant that uses <body onload="init();">

CodePen: example of body onload = 'init()'.

This second variant: using window.onload = init; in the JavaScript code…

CodePen: example of window.onload = 'init()'.

Example 2: detect a resize of the window

In this example, we're listening to page load and page resize events. When the window is loaded for the first time, or resized, we call the resize() callback function.

The window.innerWidth and window.innerHeight properties are used to display the updated size of the window. We also use screen.width and screen.height to display the screen size.

CodePen: example using window.innerWidth & innerHeight.

Example 3: do something as the page is being scrolled up or down

CodePen: example as page is scrolled.

2.4.5 Key events

Keyboard logo.
This has been a bit of a nightmare for years, as different browsers have had different ways of handling key events and key codes ( read this if you are fond of JavaScript archeology). Fortunately it's much better today, and we are able to rely on methods that should work on any browser.

When you listen to keyboard related events (keydown, keyup or keypressed), the  event parameter passed to the listener function will contain the code of the key that fired the event. Then it is possible to test which key has been pressed or released, like this:

1.  window.addEventListener('keydown', function(event) {
2.     if (event.keyCode === 37) {
3.       //left arrow was pressed
4.     }
5.  });

At line 2, the value "37" is the key code that corresponds to the left arrow. It might be difficult to know which codes represent which real keyboard keys, so here are some handy pointers:

The different key events

Event types related to keyboard

keydown, keyup and keypress.

keyboardEvent properties

These are legacy properties, still used by many JavaScript code around the world. However, we do not recommend that you use them if you are targeting modern browsers. keyCode has a more powerful/easy to use replacement called code (not yet supported by all browsers), that comes with a new key property (see the following pages of the course).

keyCode, shiftKey, ctrlKey & altKey.

Example #1: use keyup and keydown on the window object

CodePen: example using keyup and keydown.
CodePen: example using keyup and keydown.

Example #2: see  keypress on the window object

See the Pen  keyup and keydown events on window by W3Cx ( @w3devcampus)on CodePen

Example #3: detect a combination of keys + modifier keys (shift, ctrl, alt)

Try to type shift-a for example, ctrl-shift-b or alt-f…

CodePen: example detect combination of keys + modifier keys (shift, ctrl, alt).
CodePen: example detect combination of keys + modifier key.

2.4.6 Dealing with different keyboard layouts

Please do not assume that each key is at the same location on the keyboard in every country!

We've shown how to detect keyup, keydown and keypress events using the DOM API, and how to use the keyCode property of the DOM event.

Be careful when you use the key events in your application, as keyboard layouts vary from one country to another. Most first person shooter games (FPS) use three keys located on the top left of your keyboard to move your character. French AZERTY keyboards will use ZQSD for this (Z = up/move forward, Q and D are for left/right and S is for down/move backward), while US keyboards will use WASD, for example. So keep in mind that keys are not located at the same place on keyboards from different countries.

Extract from the " Internationalize your keyboard controls" article on MDN:

"Recently I came across two lovely new graphical demos, and in both cases, the controls would not work on my French  AZERTY keyboard.

There was the wonderful WebGL 2 technological demo  After The Flood, and the very cute Alpaca PeckShaw was nice enough to fix the latter when I told him about the issue. It turns out the Web browser actually exposes a useful API for this."

One keyboard, many layouts

For details, see Wikipedia's keyboard layout page!

QWERTY layout, used in US, GB, etc.

Qwerty keyboard layout. Azerty keyboard layout.
In addition, QWERTZ keyboards are in use in Germany and other European countries, and  DVORAK is another alternative to QWERTY:
DVORAK:
Dvorak layout keyboard.
QWERTZ:
qwertz layout keyboard.
Saudi Arabic keyboard layout (see more  Arabic keyboards):
Saoudian Arabic keyboard layout.
Bangla National (Jatiyo) keyboard:
Bangladesh keyboard layout.

2.4.7 Key and code properties

key and code are new recommended properties you can use with modern browsers.

You may have noticed that in some examples from the previous course page about key events, we used event.key in order to display the character that has been typed. The key property has been introduced with a new W3C API called UI Events (or DOM level 3 events), that has been discussed since 2000.  All major browsers have implemented this very practical key property. It comes with another property named code, which is what keyCode should have been. The value of the code property corresponds to a code that is more readable than the value of the old keyCode property.

But when an AZERTY keyboard user presses the A key, he also gets 'KeyQ' as event.code, yet event.key contains 'a'. This happens because the A key on a AZERTY keyboard is at the same location as the Q key on a QWERTY keyboard.

As for numbers, the top digit bar yields values like 'Digit1', while the numeric pad yields values like 'Numpad1'.

List of codes, the reference keyboard

There's no existing keyboard with all the possible keys. That's why the W3C published a specification just for this. You can read about the existing mechanical layouts around the world, as well as their  reference keyboard. For instance here is their reference keyboard for the alphanumerical part:

Reference alphanumeric keyboard.

Also, please read through  the examples given in the specification. They show very clearly what happens when the user presses various types of keys, both for code and key.

Example that displays the key and code values with your current keyboard

CodePen: display key and code values.
CodePen: display key and code values.

I encourage you to take a look and get at least an overview of this specification.

Please note that the W3C has also published a sibling specification describing the values for the key property.

Current browser support

2.4.8 Mouse events

Hand holding mouse; MouseUp, MouseOver, MouseDrag & MouseDown.

Important note: Remember that many people do not use the mouse and rely on the keyboard to interact with the Web. This requires keyboard access to all functionality, including form controls, input, and other user interface components (learn more).

Detecting mouse events in a canvas is quite straightforward: you add an event listener to the canvas, and the browser invokes that listener when the event occurs.

The example below is about listening to mouseup and mousedown events (when a user presses or releases any mouse button):

Source Code:
1. canvas.addEventListener('mousedown', function (evt) {
2.   // do something with the mousedown event
3. });
4. canvas.addEventListener('mouseup', function (evt) {
5.   // do something with the mouseup event
6. });

The event received by the listener function will be used for getting the button number or the coordinates of the mouse cursor. Before looking at different examples, let's look at the different event types we can listen to.

Mouse events

Event types related to mouse

Mouse event types.

MouseEvent properties

MouseEvent properties; button, clientX/Y, pageX/Y, screenX/Y, altKey, 
    ctrlKey, shiftKey and detail.

Examples

Example #1: detect a click on an element

CodePen: detect a click on an element.
CodePen: detect a click on an element.

Example #2: see the differences between clientX/clientY and pageX/pageY

The source code is not meant to be understood. It uses the jQuery lib. Please move the mouse pointer, and look at the different properties. Then scroll the page (the table at the top will not move), and look at the properties again; notice how pageX/pageY change, since they are relative to the top of the page, even if they are not visible. Click on the codePen label on top right and run this example! It does not work when embedded in this page!

CodePen: difference between clientX, clientY and pageX, pageY.
CodePen: diff between clientX, Y, and pageX, Y.

Example #3: detect a mousemove event and get the mouse position relative to the page

CodePen: detect mouse movement and mouse position relative to the page.
CodePen: detect mousemove and get position.

Example #4: detect a mousemove and get the mouse position relative to the element that fired the event

Here is a first version that does not work well due to a naive use of clientX/PageX and clientY/pageY mouse event properties:

CodePen: detect mouse movement & position relative to fired event.
CodePen: detect mousemove and get position relative to fired event.

Here is another version that uses clientX/clientY and the e.target.getBoundingClientRect() method that returns the bounding rectangle that contains the element that fired the event. The return value has top, left, width, and height properties that describe this rectangle. We can use the top and left properties along with evt.clientX and evt.clientY to fix the mouse position and to get a real position relative to the top left corner of the canvas:

CodePen: get position relative to top left corner of canvas.
CodePen: get position relative to top .
JavaScript Source Code extract:
Source Code:
1. function processMouseMouve(evt) {
2.   var mousePositions = document.querySelector('#mousePositions');
3. 
4.   // adjust mouse position relative to the canvas
5.   var rect = evt.target.getBoundingClientRect()
6.   var mouseX = evt.clientX - rect.left;
7.   var mouseY = evt.clientY - rect.top;
8.
9.   mousePositions.innerHTML = "mouse pos X: " + mouseX +
10.                             " mouse pos Y: " + mouseY +
11.                             "
" 12. }

Example #5: combine mouseup, mousedown, mousemove to implement a click and drag behavior

CodePen: Implement a click and drag behavior.
CodePen: click and drag behavior.

Example #6: create and attach a right-click context menu to any element

CodePen: create and attach a right-click context menu to element.
CodePen: create and attach a right-click context menu to an element.

2.4.9 Form and input field events

Events related to forms

Events related to forms.

FormEvent properties

There are no particular properties that need to be mentioned here. Usually, on a form event listener, we check the content of the different input fields, using their value property. See examples in the part of the course that deals with form events.

Example #1: validating on the fly as the user types in a text input field

First variant: using the 'input' event:

CodePen: simple input field validation.
CodePen: simple input field validation.

Second variant: using the 'keyup' event:

CodePen: using the 'keyup' event.
CodePen: using the 'keyup' event.

Note that HTML5 forms and the multiple facets of form and input field validation are covered in depth in the W3C 

HTML5 Coding Essentials and Best Practices course, which dedicates a whole week to this topic.

Example #2: do something while a slider is being moved

CodePen: do something while a slider is being moved.
CodePen: do something while a slider is being moved.

Example #3: detect value changes in a number input field

CodePen: detect value changes in a number field.
CodePen: detect value changes in a number field.
Example #4: choose a color and do something
CodePen: example; choose a color.
CodePen: choose a color and do something.

2.4.10 Reference tables

Quick summary of event management in JavaScript

HTML5 events:
Picture of keyboard and mouse.

There is no input or output in JavaScript. We treat events caused by user actions as inputs, and we manipulate the DOM structure as output. Usually in a JavaScript application, we will get info such as the key strokes, the mouse button clicks and the mouse position, and we will refer to these variables when determining what action to perform.

In any case, the events are called DOM events, and we use the DOM APIs to create event handlers.

How to listen to events

There are three ways to manage events in the DOM structure. You could attach an event inline in your HTML code like this:

Method #1: declare an event handler in the HTML code

1. <div id="someDiv" onclick="alert('clicked!')"> content of
  the div </div>

This method is very easy to use, but it is not the recommended way to handle events. Indeed, although it currently works, it is deprecated (will probably be abandoned in the future). Mixing 'visual layer' (HTML) and 'logic layer' (JavaScript) in one place is really bad practice and causes a host of problems during development.

Method #2: attach an event handler to an HTML element in JavaScript

1.  document.getElementById('someDiv').onclick = function() {
2.    alert('clicked!');
3.  }

This method is fine, but  you will not be able to attach multiple listener functions. If you need to do this, use the version shown below.

Method #3: register a callback to the event listener with the addEventListener method (preferred  method)

1.  document.getElementById('someDiv').addEventListener('click', function() {
2.    alert('clicked!');
3.  }, false);

Note that the third parameter describes whether the callback has to be called during the captured phase. This is not important for now, just set it to false or ignore it (you can even pass only two parameters to the addEventListener function call and do not set this boolean parameter at all).

Details of the DOM event are passed to the event listener function

When you create an event listener and attach it to an element, the listener will create an event object to describe what happened. This object is provided as a parameter of the callback function:

1.  element.addEventListener('click', function(event) {
2.    // now you can use event object inside the callback
3.  }, false);

Depending on the type of event you are listening to, you will consult different properties from the event object in order to obtain useful information such as: "which keys are pressed down?", "what is the location of the mouse cursor?", "which mouse button has been clicked?", etc.

In the following lessons, we will remind you how to deal with the keyboard and the mouse.

Further reading

In method 1 (above), we mentioned that "mixing 'visual layer' (HTML) and 'logic layer' (JavaScript) … is bad practice", and this is similarly reflected in many style features being deprecated in HTML5 and moved into CSS3. The management philosophy at play here is called "the separation of concerns" and applies in several ways to software development - at the code level, through to the management of staff. It's not part of the course, but professionals may find the following references useful:

Reference tables for events and properties/methods

These tables are provided as a reference. They are a compilation of the most common event types sorted by domain (key, mouse, forms, etc.). For each domain you will see the most useful event types and their properties. In the following course pages, we will show  examples that use most of the events displayed in these tables.

Event object

Most useful common properties:

Type: returns the name of the event & Target: Returns the element that triggered the event.

Most useful common methods:

preventDefault() and stopPropagation() functions.

Page

Events related to the page lifecycle

There are many other events related to the page life cycle. Below are the most useful ones for an intro course:

load, resize and scroll events.

Page event properties

There are no particular properties that need to be mentioned here. Usually, the load event listener corresponds to a JavaScript function that can be seen as "the main" function of your Web Application. It is good practice to start everything after the page has been completely loaded. In the resize listener, you get the new size of the window, or the new size of some HTML elements in the page (as they might have been resized too when the window was resized) and then you do something (redraw a graphic in an HTML canvas that takes into account the new canvas size, for example).

Keyboard

Event types related to keyboard

keydown, keyup and keypress.

keyboardEvent properties

keyCode (now deprecated), shiftKey, ctrlKey and altKey.

Mouse

Event types related to mouse

click, dblclick, many mouse events, and contextmenu.

MouseEvent properties

button, clientX/Y, pageX/Y, screenX/Y, Key and detail.

Forms

Events related to forms

input, change, focus, blur, select and submit.

FormEvent properties

There are no particular properties that need to be mentioned here. Usually, on a form event listener, we check the content of the different input fields, using their value property. See examples in the course, in the part dealing with form events.

2.4.11 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics

Optional project

Hand holding stopwatch.
For inspiration, check this cool game "Typing Frenzy" created by learner @AnthonyRKing (ARK)!
CodePen: Typing Frenzy by ARK.
CodePen: Typing Frenzy

2.5.1 Introducing the DOM

When a user clicks on a link or enters a URL in the address of your Web browser, it downloads the page's HTML text and builds up a model of the document's structure called the DOM (Document Object Model). This model is used to render the HTML page on the screen.

The DOM is a standard that describes how a document must be manipulated. It defines a "language- and platform neutral interface". So, every browser offers the same JavaScript DOM API.

The DOM API is a programming interface the JavaScript programmer can use to modify the HTML content or the CSS style of HTML elements on the fly.

The DOM API provides the document object as a structured object, a group of nodes represented as a tree. We saw this in Module 1 when we revised the basic principles of HTML.

The document object also exposes a large set of methods to access and manipulate the structured document. Through the DOM, look for nodes (html elements that compose the page), move nodes, delete nodes, modify nodes (attributes, content), and also handle their associated events.

In JavaScript, the DOM is accessible through the property document of the global object window. We rarely manipulate the window object directly as it is implicit: window.document is the same as document.

So by using this object, we can access and manipulate our page from JavaScript as a structured document.

Reminder from Module 1: HTML and the DOM

'Elements' are the pieces themselves, i.e., a paragraph, a header, and even the body are elements. Most elements can contain other elements - for example, the body element would contain header elements, paragraph elements, in fact pretty much all of the visible elements of the Document Object Model (developers call it the "DOM").

Let's take, for example, a simplified version of the last HTML code we showed you:

Source Code:
1. <!DOCTYPE html>
2. <html lang="en">
3.   <head>
4.     <title>Your first HTML page</title>
5.     <meta charset="utf-8">
6.  </head>
7.  <body>
8.    <h1>My home page</h1>
9.    <p>Hi! Welcome to my Home Page! My name is Michel Buffa,
10.      I'm a professor at the University of Côte d'Azur, in France,
11.      and I'm also the author
12.      of two other W3CX MOOCS.
13.    </p>
14.  </body>
15. </html>

Click the red circle next to HTML to unfold this HTML document structure (we can also say "see its DOM structure"):

CodePen: html and red circle.
CodePen: html red circle.

Consider the figure above.  It contains a single html element.  It turns out this includes within it the entire content of your html file.  If you click on the "html" red node, you'll find that it contains two components, a head and a body.  Clicking on each of these will reveal their respective contents.  This structure is what we computer scientists call a "tree".  Any given element (except for the outermost 'html' element) is wholly contained inside another element, referred to as the "parent" element.  Not surprisingly, the elements that a given element contains are its "child" elements.  And, yes, children of a common parent are often referred to as "siblings".

Thus, in the example above, the top element is the html element, which contains just two elements, the head and body.  The head element contains a title element and the body contains an h1 element and a p element.  In a more typical example, the body would contain many more children, but for our purposes this is enough. p is for "paragraph" (the text between <p> and </p> will be separated by some space before the next element is displayed in the final HTML page rendering), h1 means "heading level 1", and will be rendered by default in bold with a bigger char size than any other text element, etc.

There are different types of nodes in the DOM

There are different types of nodes, but don't worry - the most useful ones are highlighted in bold.

Exploring the DOM with the devtool console

You can explore the DOM with the devtool console. This time we used Firefox for exploring the DOM, as it proposes a good structured view of the DOM and of its properties/methods:

Firefox devtool console.

If you scroll down the right panel of the devtool console, as in the above screenshot, you will be able to look at all the properties, all the methods, all the event listeners:

w3cx js.0x javascript introduction.

You can also use the "DOM inspector" to locate a particular element with the mouse: click the target icon and click on the element on the page that you want to inspect, this time with Google Chrome, but you will find this option in all modern browsers' devtool consoles:

DOM inspector.

2.5.2 A warning about the DOM API

The DOM and the DOM API can be cumbersome and complicated. There are many methods and properties for manipulating the DOM tree, that are not "very JavaScript". There are historical reasons for this: the DOM wasn't designed exclusively for JavaScript. Rather, it tries to define a language-neutral interface that can be used in other systems as well --- not just HTML but also XML, which is a generic data format with an HTML-like syntax.

HTML5 made some additions that are not in the DOM API but which greatly help the JavaScript programmer (we'll see this in a minute with the "selector API", for example).

We've decided to focus on only 20% of the DOM API and on the selector API (for selecting elements in the DOM). These are the most useful parts and it will give you enough knowledge to solve nearly every problem where you need to manipulate the DOM.

Exclamation mark in red triangle.

2.5.3 Accessing HTML elements

CodePen Overview: Two buttons and four images.
CodePen: two buttons and four images.

This time, let's look a bit more in depth to the different methods for selecting elements in an HTML page, and then do something with these elements.

CodePen: Two buttons defined.
CodePen: two buttons and four images.

I prepared here an HTML document that contains two buttons that do nothing for the moment, and it contains also 4 images.

CodePen: four images defined.

Here are the images... They've got an id: img1, img2, and so on. They've got some URLs and a width.

function init(). window onload = init.

If we look at the JavaScript code I prepared, I added an init function that is called when the page is loaded.

html code onload and button definitions.

You remember from a previous video that we can do that using body onload=init. Or we can use (this is an alternative): window.onload=init.

This is what I did here. When the page is loaded, we are going to first check that the init function is executed. And it's executed after the page is loaded, after the DOM is ready. Then we will select all images, and set some CSS properties.

function init() and console.log 'page loaded, the dom is ready'.

I can have a look at the console, and if I just type anything, it executes again the example, and we see that the console.log in the init function has been executed.

That means that the load event listener has been defined correctly. In order to select all the images, and not only one, we can use the query.SelectorAll method from the document object. I'm using querySelectorAll and by just typing the name of an element, it will select all the elements, the html elements, of this type.

Now, in order to iterate on the collection of elements, you can use the forEach iterator. This one will be detailed later but let's see now a very simple use of it. It takes a single argument that is a callback. Here I'm using just a variable that corresponds to the current image. You can name it as you like. In that case it's "currentImage".

Select images using currentImage.style.border.

If I do currentImage.style.border… you see that when the page is executed, it will take each element from the list of images, and add to each image a border.

Add red border to images.

Let's make it larger! You see, we added a border of 10 pixels width. You can also add a margin. In that case I've got the different images with a margin of 10 pixels at top, left, right and bottom.

Before border added to 1st image. After border added to 1st image.

Let's try to add a border only to the first image. When we click on the first button. If we look at the HTML code, we added an onlick event listener that will call addBorderToFirstImage, a callback defined in the JavaScript code. We can check that the listener works by adding a console.log and clicking on the button. It works!

How to select the first image? We use document.querySelector, and here I can use the id of the image… img1, and then use the style property of the object:

img1.style…, and you see that if I click on the button, then it adds a border. I could have used just "img", in order to select only the first element of type "img". It's the same syntax I used for querySelectorAll, except that in that case it selects just the first one, and you've got the same result.

New function: resizeAllImages.

If I want to resize all the images, I can, in that case, use CSS properties, or you can use the width attribute of the images. In order to select all the images, I'm going to use the same technique I used for adding a border to all the images earlier. I will first select all the images using querySelectorAll, then I will use the foreach iterator, and use the width attribute of each individual image, to set this attribute to a given value…so… if I click here…Oh! The images are only 10 pixels… then maybe this is too small!

Let's try 70 pixels…I click on the button and the images are resized!

I can click on the first button to add a border. You saw the different possibilities.

Accessing HTML elements with the selector API (recommended)

Extract from  HTML5 selectors API -- It's like a Swiss Army Knife for the DOM) : "One of the many reasons for the success of JavaScript libraries like  jQuery and  Prototype, on top of their easing the pain of cross-browser development was how they made working with the DOM far less painful than it had previously been, and indeed how it was with the standard DOM. Being able to use arbitrary CSS selector notation to get matching elements from a document made the standard DOM methods seem antiquated, or at the very least, far too much like hard work.

Luckily, the standards and browser developers took notice. The W3C developed the Selectors API, a way of easily accessing elements in the DOM using standard CSS selector concepts, and browser developers have baked these into all modern browsers, way back to IE8."

The querySelector(CSSSelector) and querySelectorAll(CSSSelector) methods

Ah… these methods owe a lot to  jQuery ! They introduce a way to use CSS selectors (including CSS3 selectors) for requesting the DOM, like jQuery introduced ages ago.

Any CSS  selector can be passed as a parameter for these methods.

Typical use:

Looking for an element in the whole document (the whole HTML page): call the querySelector method (or querySelectorAll) on the document object, that corresponds to the whole DOM tree of your web page:

Example; querySelector and querySelectorAll.
CodePen Example: querySelector & querySelectorAll.

Source code from the above example:

HTML part: we have two buttons that will call a JavaScript function (lines 2 and 6) where we will manipulate the DOM), and we have four images, the first one with an id equal to "img1" (lines 11, 14, 16 and 18).

Source Code:
1.  …
2.  <button onclick="addBorderToFirstImage();">
3.    Add a border to the first image
4.  </button>
5.  <br>
6.  <button onclick="resizeAllImages();">
7.    Resize all images
8.  </button>
9.  <br>
10. <p>Click one of the buttons above!</p>
11. <img src="https://i.imgur.com/Ntvj5rq.png"
12.   id="img1"
13.   width=200>
14. <img src="https://i.imgur.com/yiU59oi.gif"
15.   width=200>
16. <img src="https://i.imgur.com/6FstYbc.jpg"
17.   width=200>
18. <img src="https://i.imgur.com/L97CyS4.png"
19.   width=200>
20. …

JavaScript part: the init function is executed as soon as the page is loaded (and the DOM is ready), in this function we add a shadow and margins to all images (lines 3-21). The two other functions are called when one of the HTML buttons is clicked (line 23 and line 31).

Source Code:
1.  window.onload = init; // run init once the page is loaded
2.
3.  function init() {
4.    // we're sure that the DOM is ready
5.    // before querying it
6.    // this function runs once the page is loaded
7.
8.    // add a shadow to all images
9.    // select all images
10.   var listImages = document.querySelectorAll("img");
11. 
12.   // change all their width to 100px
13.   listImages.forEach(function(img) {
14.     // img = current image
15.     // add a shadow 5px left, 5 pixel down, 15px blur, 5px spread
16.     // grey
17.     img.style.boxShadow = "5px 5px 15px 5px grey";
18.     // add a margin 10px on each side
19.     img.style.margin = "10px";
20.   });
21. }
22. 
23. function addBorderToFirstImage() {
24.   // select the first image with id = img1
25.   var img1 = document.querySelector('#img1');
26. 
27.   // Add a red border, 3px wide
28.   img1.style.border = '3px solid red';
29. }
30. 
31. function resizeAllImages() {
32.   // select all images
33.   var listImages = document.querySelectorAll("img");
34. 
35.   // change all their width to 100px
36.   listImages.forEach(function(img) {
37.     // img = current image, we resize it by changing its
38.     // width attribute
39.     img.width = 100;
40.   });
41. }

Miscellanous examples of use of querySelector(CSSSelector) and querySelectorAll(CSSselector)

Here are some other examples that use more complicated CSS selectors. If you are not familiar with their syntax, we recommend that you follow the CSS basics, and HTML5 and CSS fundamentals courses from W3Cx.

Example #1: get all <li> directly in a <ul> of class nav

CodePen Example; Get all li's in ul class.
CodePen: get all li's within a ul of class nav.
HTML:
Source Code:
1.  <button onclick="firstLiClassRedInUl();">Select first li of
    class red and color it in red</button>
2.  <br>
3.  <button onclick="allLisInUlOfClassNav();">Underline All li in a
    ul of class nav</button>
4. 
5.  <ul class="nav">
6.    <li>Home</li>
7.    <li class="red">Products</li>
8.    <li>About</li>
9.  </ul>
10. Another list:
11. <ul>
12.   <li>Apple</li>
13.   <li class="red">Cherries</li>
14.   <li>Oranges</li>
15. </ul>
JS:
Source Code:
1.  function firstLiClassRedInUl() {
2.    // first li of class="red" in a ul
3.    var elm = document.querySelector("ul li.red");
4.    elm.style.color = 'red';
5.  }
6. 
7.  function allLisInUlOfClassNav() {
8.    // get all li directly in a ul of class nav
9.    var list = document.querySelectorAll("ul.nav > li");
10. 
11.   list.forEach(function(elm) {
12.     elm.style.textDecoration = "underline";
13.   })
14. }

Source Code extracts:

Example #2: display all checked <input type="checkbox"> elements located inside an element of a given id.
Show Checked items inside an element of a given id.
CodePen: Show Checked items.
HTML:
Source Code:
1.  <button onclick="displayListOfCheckedItems();">
2.    Show Checked items
3.  </button>
4.  <br>
5.  <ul id="fruits">
6.    <li>
7.      <input type="checkbox" name="fruit" value="apples">
8.        Apples
9.    </li>
10    <li>
11.      <input type="checkbox" name="fruit" value="oranges">
12.       Oranges
13.   </li>
14.   <li>
15.     <input type="checkbox" name="fruit" value="bananas">
16.       Bananas
17.   </li>
18.   <li>
19.     <input type="checkbox" name="fruit" value="grapes">
20.       Grapes
21.   </li>
22. </ul>

JavaScript code: we select all elements of type input that have an attribute checked equal to true, and located inside an element whose id is "fruits". Notice the use of document.querySelectorAll, for selecting more than one element (line 6), then, we iterate on the list (line 8) and concatenate to the string variable listOfSelectedValues the value of each element (located in its value attribute). This is done in line 9.

Lines 9-12 use the parentNode property of the selected nodes in order to change the color of the <li> (parents of <input> elements selected) in red. In the DOM tree, we selected input elements that are each a child of a <li> element. The text displayed: "Apples", "Oranges" etc. belong to the <li> element. In order to access it from the <input> child we selected, we use elm.parentNode.

Finally, at the end of the document, line 14 adds a message followed by this list:

JavaScript code:
Source Code:
1.  function displayListOfCheckedItems() {
2.    // all inputs that have been checked
3.    var listOfSelectedValues="";
4.
5.    var list = document.querySelectorAll("#fruits input:checked");
6.    list.forEach(function(elm) {
7.      listOfSelectedValues += elm.value + " ";
8.
9.      // Put the li in red.
10.      // the li is the parent of the current input elem stored
11.      // in the elm variable
12.     elm.parentNode.style.color = 'green';
13.   });
14.   document.body.append("You selected: " + listOfSelectedValues);
15. }

We select all elements of type input that have an attribute checked equal to true, and located inside an element whose id is "fruits". Notice the use of document.querySelectorAll, for selecting more than one element (line 6), then, we iterate on the list (line 8) and concatenate to the string variable listOfSelectedValues the value of each element (located in its value attribute). This is done in line 9.

Lines 9-12 use the parentNode property of the selected nodes in order to change the color of the <li> (parents of <input> elements selected) in red. In the DOM tree, we selected input elements that are each a child of a <li> element. The text displayed: "Apples", "Oranges" etc. belong to the <li> element. In order to access it from the <input> child we selected, we use elm.parentNode.

Finally, at the end of the document, line 14 adds a message followed by this list:

Example #3: change the background of all paragraphs <p> in an element of a given id

CodePen: Change background of all paragraphs in element of a given id.
CodePen: Change background of p under element id.
HTML code:
Source Code:
1.  <button onclick="changeBackGroundOfPs('firstDiv');">Change
    backgrounds of p under a given element known by id</button>
2.  <br>
3.  <div id="firstDiv">
4.    <p>First paragraph.</p>
5.    <p>Second paragraph.</p>
6.  </div>

JavaScript code: we build a CSS selector using the id passed as a parameter. In this example, the id is 'firstDiv', the id of the div at line 3 in the above code.

The variable CSS selector at line 2 in the JavaScript code below will have a value equal to "#firstDiv p", that means: select all <p> under an element whose id is "firstDiv". The paragraphs variable is a list that contains the paragraphs selected. Then we iterate on this list (this time using a for loop, which is an alternative method to using the forEach method used in previous examples) (lines 5-7), and we change the background of all selected paragraphs (line 6).

Source Code:
1.  function changeBackGroundOfPs(id) {
2.    var paragraphs = document.querySelectorAll("#" + id + " p");
3.
4.    // Another way to iterate on all elements in a collection
5.    for (var i = 0; i < paragraphs.length; i++ ) {
6.      paragraphs[i].style.backgroundColor = "lightGreen";
7.    }
8.  }
Other examples that use more complex selectors:
Source Code:
1.  // all elements li in ul elements in an element of id=nav
2.  var el = document.querySelector('#nav ul li');
3.
4.  // all li in a ul, but only even elements
5.  var els = document.querySelectorAll('ul li:nth-child(even)');
6.
7.
8.  // all td directly in tr in a form of class test
9.  var els = document.querySelectorAll('form.test > tr > td');
10. 
11. // all paragraphs of class warning or error
12. querySelectorAll("p.warning, p.error");
13. 
14. // first element of id=foo or id=bar
15. querySelector("#foo, #bar");
16.
17. // first p in a div
18. var div = document.getElementById("bar");
19. var p = div.querySelector("p");

Accessing HTML elements with the DOM API (old fashioned)

These methods are from the DOM API and can all be replaced by the querySelector and querySelectorAll methods that we've discussed. They are still used in many JavaScript applications, and are very simple to understand.

From the document we can access the elements composing our Web page in a few ways:

This is equivalent to document.querySelector("#identifier'); (just add a # before the id when using a CSS selector).

Example: var elm = document.getElementById('myDiv'); is equivalent to document.querySelector('#myDiv');

This is equivalent to document.querySelectorAll(tagName);

Example: var list = document.getElementByTagName('img'); is equivalent to document.querySelector('img');

This is equivalent to document.querySelectorAll('.className');

Example: var list = document.getElementByClassName('important'); is equivalent to document.querySelector('.important'); (just add a '.' before the class name when using a CSS selector).

Notice that identifier, tagName and className must be of type String.

2.5.4 Changing the style of selected HTML elements

The style attribute

How to modify an HTML element's CSS properties from JavaScript?

The most common way to modify the CSS style of one of several elements you selected using the DOM or Selector API, is to use the style attribute.

Typical use:
1.  // select the paragraph with id = "paragraph1"
2.  var p = document.querySelector('#paragraph1');
3.  // change its color
4.  p.style.color = 'red';

Warning: with the style attribute, you can modify (or read) any CSS property, but be careful: the syntax changes a little due to the fact that in JavaScript the "-" is a math operator, while in CSS it is used to separate properties made of multiple words, such as background-color.

When using such properties from JavaScript, the rule is simple:

  1. Remove the "-" sign,
  2. Capitalize the word after the "-" sign!

Simple, isn't it?

Examples:

The most useful CSS properties (we do recommend that you follow the W3Cx courses CSS basics, CSS and HTML5 fundamentals from W3Cx to learn more about CSS):

Here are some examples:

Update style within html document.
CodePen: Update styles in document

Using the ClassList interface to change more than one CSS property simultaneously

External resources:

Until now, to manipulate CSS classes of an HTML element was a bit complex, both for verifying the presence of a class name in an element, and for adding or removing classes associated with a given element.

The ClassList interface simplifies it all by acting as a container object and by providing a set of methods to manipulate its content.

The classList property applies to an HTML element, and returns a collection of class names:

1. var elem= document.querySelector("#id1");
2. 
3. var allClasses = elem.classList;
The classList API

The list of methods usable on a classList object are add(), remove(), toggle() and contains().

Source Code:
1.  // By default, start without a class in the div: <div class=""/>
2. 
3.  // Set "foo" as the class by adding it to the classList
4.  div.classList.add('foo'); // now <div class="foo"/>
5.
6.  // Check that the classList contains the class "foo"
7.  div.classList.contains('foo'); // returns true
8.
9.  // Remove the class "foo" from the list
10. div.classList.remove('foo'); // now <div class=""/>
11.
12. // Check if classList contains the class "foo"
13. div.classList.contains('foo'); // returns false: "foo" is gone
14.
15. // Check if class contains the class "foo",
16. // If it does, "foo" is removed, if it doesn't, it's added
17. div.classList.toggle('foo'); // class set to <div class="foo"/>
18. div.classList.toggle('foo'); // class set to <div class=""/>

Another example: add and remove multiple CSS properties in a list of checkboxes

CodePen: show checked items and reset list.
CodePen: show checked items and reset list.

This is a variation of an example from a previous section. This time, when the <input type="checkbox"> elements have been checked, in order to give the parent <li> a background color, a border, and to change the text color, we use a CSS class named "checked":

CSS code:
1.  .checked {
2.    border: 2px dashed #000;
3.    background-color: green;
4.    color:yellow;
5.  }

… and the classList.add(CSS_class) and classList.remove(CSS_class)  methods on the <li> elements:

JavaScript code:
Source Code:
1.  function displayListOfCheckedItems() {
2.    // all inputs that have been checked
3.    var listOfSelectedValues="";
4.    var list = document.querySelectorAll("#fruits input:checked");
5.    list.forEach(function(elm) {
6.      listOfSelectedValues += elm.value + " ";
7.      // get the li parent of the current selected input
8.      var liParent = elm.parentNode;
9.      // add the CSS class .checked
10.     liParent.classList.add("checked");
11.     document.body.append("You selected: " + listOfSelectedValues);
12.   }
13. }
14. function reset() {
15.   var list = document.querySelectorAll("#fruits input");
16.   list.forEach(function(elm) {
17.     > // uncheck
18.     >
19.     > elm.checked = false;
20.     >
21.     > // remove CSS decoration
22.     >
23      > var liParent = elm.parentNode;
24.     >
25.     > liParent.classList.remove("checked");
26.   });
27. }

2.5.5 Modifying selected HTML elements

We've already seen many examples in which we selected one or more elements, and modified their content. Let's summarize all the methods we've seen, and perhaps introduce a few new things…

Properties that can be used to change the value of selected DOM node.

Using the innerHTML property

This property is useful when you want to change all the children of a given element. It can be used to modify the text content of an element, or to insert a whole set of HTML elements inside another one.

Typical use:

Source Code:
1.  var elem = document.querySelector('#myElem');
2.  elem.innerHTML = 'Hello '; // replace content by Hello
3.  elem.innerHTML += 'Michel Buffa', // append at the end
4.  // Michel Buffa in bold
5.  elem.innerHTML = 'Welcome' + elem.innerHTML; // insert Welcome
6.  // at the beginning
7.  elem.innerHTML = ''; // empty the elem

Using the textContent property

It's also possible, with selected nodes/elements that contain text, to use the textContent property to read the text content or to modify it. There are subtle differences that can be seen in the above example (click the 'edit on CodePen" part on the top left, and once in codePen, open the devtool console):

Open the console and look at the JavaScript code.
CodePen: Open the console and look at the JavaScript code.

Extract from the HTML code:

1.  <p id="first">first paragraph</p>
2.  <p id="second"><em>second</em> paragraph</p>

JavaScript code: the comments after lines that start with console.log correspond to what is printed in the devtool debug console. Notice the difference between the textNode value and the innerHTML property values at lines 13-14:

While textContent returns only the text inside the second paragraph, innerHTML also returns the <em>…</em> that surrounds it. However, when we modify the textContent value, it also replaces the text decoration (the <em> is removed), this is done at lines 16-20.

Source Code:
1.  window.onload = init;
2.   
3.  function init() {
4.     // DOM is ready
5.     var firstP = document.querySelector("#first");
6.     console.log(firstP.textContent); // "first paragraph"
7.     console.log(firstP.innerHTML);   // "first paragraph"
8.   
9.     firstP.textContent = "Hello I'm the first paragraph";
10.    console.log(firstP.textContent); // "Hello I'm the first paragraph"
11.                                      
12.    var secondP = document.querySelector("#second");
13.    console.log(secondP.textContent); // "second paragraph"
14.    console.log(secondP.innerHTML);   // "<em>second</em> paragraph"
15. 
16.    secondP.textContent = "Hello I'm the second paragraph";
17.    console.log(secondP.textContent); // "Hello I'm the second
18.                                      // paragraph"
19.    console.log(secondP.innerHTML);   // "Hello I'm the second
20.                                      // paragraph"
21. }

Changing the attributes of selected elements

It's very common to modify the attributes of selected elements: the width of an image, CSS style with the style attribute, value of an input field, etc.

This example shows some of the things we can do:

CodePen: Modifying DOM nodes with textContent and innerHTML.
CodePen (Modifying DOM Nodes with textContent and innerHTML

2.5.6 Adding new elements to the DOM

The DOM API comes with a set of methods you can use on DOM elements.

In general, to add new nodes to the DOM we follow these steps:

  1. Create a new element by calling the createElement() method, using a syntax like:
1. var elm = document.createElement(name_of_the_element)

Examples:

1.  var li = document.createElement('li');
2.  var img = document.createElement('img'); etc.
  1. Set some attributes / values / styles for this element.

Examples:

1.  li.innerHTML = 'This is a new list item in bold!'; // can add HTML in it
2.  li.textContent = 'Another new list item';
3.  li.style.color = 'green'; // green text
4.  img.src = "https://..../myImage.jpg"; // url of the image
5.  img.width = 200;

Add the newly created element to another element in the DOM, using append(), appendChild(), insertBefore() or the innerHTML property.

Examples:

1.  var ul = document.querySelector('#myList');
2.  ul.append(li); // insert at the end, appendChild() could also be used (old)
3.  ul.prepend(li); // insert at the beginning
4.  ul.insertBefore(li, another_element_child_of_ul);// insert in the middle
5.  document.body.append(img); // adds the image at the end of the document
Example #1: use of the createElement(), append() methods and of the textContent attribute
CodePen: Modify attributes of select elements.
CodePen: Modify attributes of select elements.

The DOM API comes with a set of methods you can use on DOM elements.

In general, to add new nodes to the DOM we follow these steps:

  1. Create a new element by calling the createElement() method, using a syntax like:
1.  var elm = document.createElement(name_of_the_element)
Examples:
1.  var li = document.createElement('li');
2.  var img = document.createElement('img'); etc.
  1. Set some attributes / values  / styles for this element.
Examples:
1.  li.innerHTML = '<b>This is a new list item in bold!</b>'; // can add HTML in it
2.  li.textContent = 'Another new list item';
3.  li.style.color = 'green'; // green text
4.  img.src = "https://..../myImage.jpg"; // url of the image
5.  img.width = 200;
  1. Add the newly created element to another element in the DOM, using append(), appendChild(), insertBefore() or the innerHTML property
Examples:
1.  var ul = document.querySelector('#myList');
2.  ul.append(li); // insert at the end, appendChild() could also be used (old)
3.  ul.prepend(li); // insert at the beginning
4.  ul.insertBefore(li, another_element_child_of_ul);// insert in the middle
5.  document.body.append(img); // adds the image at the end of the document
Example #1: use of the createElement(), append() methods and of the textContent attribute
CodePen: Example, createElement, append, and textContent.
CodePen: Enter a number & add to list.

HTML code extract: we use an <input type="number"> for entering a number (line 2). Then if one clicks on the "Add to the list" button, the add() JavaScript function is called (line 3), this will add the typed number to the empty list at line 7. If one presses the "reset" button, it will empty this same list by calling the reset() JavaScript function.

Source Code:
1.  <label for="newNumber">Please enter a number</label>
2.  <input type="number" id="newNumber" value=0>
3.  <button onclick="add();">Add to the list</button>
4.  <br>
5.  <button onclick="reset();">Reset list</button>
6.  <p>You entered:</p>
7.  
8.  <ul id="numbers"></ul>

JavaScript code extract: notice at line 25 the use of the innerHTML property for resetting the content of the <ul> list. innerHTML corresponds to all the sub DOM contained inside the <ul>...</ul>. innerHTML can be used for adding/deleting/modifying a DOM node's content.

Source Code:
1.  function add() {
2.    // get the current value of the input field
3.    var val = document.querySelector('#newNumber').value;
4.  
5.    if((val !== undefined) && (val !== "")) {
6.      // val exists and non empty
7.  
8.      // get the list of numbers. It's a <ul>
9.      var ul = document.querySelector("#numbers");
10. 
11.     // add it to the list as a new <li>
12.     var newNumber = document.createElement("li");
13.     newNumber.textContent = val;
14.     // or newNumber.innerHTML = val
15. 
16.     ul.append(newNumber);
17.   }
18. }
19. 
20. function reset() {
21.   // get the list of numbers. It's a <ul>
22.   var ul = document.querySelector("#numbers");
23. 
24.   // reset it: no children
25.   ul.innerHTML = "";  
26. }
Example #2: using the innerHTML property to add new elements

This is the same example, but in an abbreviated form, using the innerHTML property:

CodePen: Using innerHTML property to add new elements.
CodePen: Example, using innerHTML property.

2.5.7 Moving HTML elements in the DOM

The append(), appendChild() methods normally adds  a new element to an existing one, as shown in this example:

1.  var li = createElement('li');
2.  ul.append(li); // adds the new li to the ul element

One interesting thing to know is that if we do not create the new element, but rather get it from somewhere else in the document, it is then removed from its parents and added to the new parent.

In other words: it moves from its original location to become a child of the targetElem.

Examples
Example #1: a simple one
CodePen: Click a browser image to move to zone area.
CodePen Example #1, Click browser image to move to a zone.
Example #2: a more significant example, that also uses drag'n'drop

Note that this example comes from the HTML5 Apps and Games course. Our plan here is not to explain drag'n'drop in detail, but to show how append() can be used to move an element.

When a user starts to drag an element, the drag() JavaScript function is called. In this function we use the drag'n'drop clipboard to store the id of the image that is being dragged.

When the image is dropped, the drop() method is called. As the drop event listener is declared on the two divs (on the left and the right), we just call append() on the target div element, and this will add the dragged image to the div, while removing it from its original location.

Drag 'n drop browser images in a zone.
CodePen: Example #2, Drag 'n drop images.

2.5.8 Removing elements from the DOM

Removing elements using the removeChild() method

Let's take an example that we've already encountered. This time, you will check the elements you want to remove from the list!

CodePen: Removing elements from the DOM.
CodePen: removing elements from the DOM.

JavaScript code extract: we need to get the <ul> that contains all the <li><input type="checkbox"></li> elements (line 3). This is the element we will use for calling removeChild(...).

The loop on the checked element (lines 5-12) iterates on a list of checked input elements. In order to make both the text (Apples, Oranges, etc.) AND the checkbox disappears, we need to access the different <li> elements that contain the selected checkboxes. This is done in line 10.

Then, we can call ul.removeChild(li) on the <ul> for removing the  <li> that contains the selected element (line 11).

Source Code:
1.  function removeSelected() {
2.    var list = document.querySelectorAll("#fruits input:checked");
3.    var ul = document.querySelector("#fruits");
4.    list.forEach(function(elm) {
5.  
6.      // elm is an <input type="checkbox">, its parent is a li
7.      // we want to remove from the <ul> list
8.      // when we remove the <li>, the <input> will also
9.      // be removed, as it's a child of the <li>
10.     var li = elm.parentNode;
11.     ul.removeChild(li);
12.   });
13. }
Removing all children of an element using the innerHTML property

In the same example, if you look at the reset() JavaScript function, we use the ul's innerHTML property both for emptying the list (lines 3-4) and for appending to it all the initial HTML code (lines 6-17):

Source Code:
1.  function reset() {
2.    var ul = document.querySelector("#fruits");
3.    // Empty the <ul>
4.    ul.innerHTML = "";
5.  
6.    // Adds each list item to the <ul> using innerHTML += ...
7.    ul.innerHTML += "<li><input type='checkbox' name='fruit'  
                      value='apples'>Apples</li>";
8.  
9.    ul.innerHTML += "<input type='checkbox' name='fruit'
10.                   value='oranges'>Oranges</li><br>";
11. 
12.   ul.innerHTML += "<input type='checkbox' name='fruit'
13.                   value='bananas'>Bananas</li><br>";
14. 
15.   ul.innerHTML += "<input type='checkbox' name='fruit'
16.                   value='grapes'>Grapes</li>";
17. }

2.6.1 Drawing (5:36)

Live coding lesson: basic example showing how to draw in a canvas.

How to draw in a canvas.

The HTML5 canvas is a transparent element that is useful for drawing and animating. We'll see some simple examples here, as we're going to finish this week by writing a small, simple game together, that will use most of what we've learnt so far: loops, conditional statements, events, functions, callbacks, simple objects, a few input fields, etc.

A typical HTML code for adding a canvas to a Web page:
Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.  <meta charset="utf-8">
5.  <title>Draw a monster in a canvas</title>
6.  </head>
7.  <body>
8.  <canvas id="myCanvas" width="200" height="200"></canvas>
9.  </body>
10. </html>

The canvas declaration is at line 8. Use attributes to give it a width and a height, but unless you add some CSS properties, you will not see it on the screen because it's transparent!

Let's use CSS to reveal the canvas, for example, add a 1px black border around it:

1.  canvas {
2.    border: 1px solid black;
3.  }

And here is a reminder of best practices when using the canvas:

  1. Use a function that is called AFTER the page is fully loaded (and the DOM is ready), select the canvas in the DOM (this is the init function (as in window.onload = init) we already saw many times).
  2. Then, get a 2D graphic context for this canvas (the context is an object we will use to draw on the canvas, to set global properties such as color, gradients, patterns and line width).
  3. Only then can you can draw something.
  4. Do not forget to use global variables for the canvas and context objects. I also recommend keeping the width and height of the canvas somewhere. These might be useful later.
  5. For each function that will change the context (color, line width, coordinate system, etc.), start by saving the context, and end by restoring it.
Examples
Example #1: some drawing examples (wireframe and filled rectangle, filled circle, filled text, changing colors)
Example canvas; red circle and square, green outlined square.
Extract from the JavaScript code:
Source Code:
1.  // useful to have them as global variables
2.  var canvas, ctx;
3.  
4.  window.onload = function init() {
5.  // called AFTER the page has been loaded
6.  canvas = document.querySelector("#myCanvas");
7.  // important, we will draw with this object
8.  ctx = canvas.getContext('2d');
9.  
10. // ready to go! We can use the context for drawing
11. // or changing colors, line widths, etc.
12. 
13. // filled rectangle
14. ctx.fillStyle = 'red';
15. ctx.fillRect(10, 10, 30, 30);
16. 
17. // wireframe rectangle
18. ctx.strokeStyle = 'green';
19. ctx.lineWidth = 4;
20. ctx.strokeRect(100, 40, 40, 40);
21. 
22. // fill circle, will use current ctx.fillStyle
23. ctx.beginPath();
24. ctx.arc(60, 60, 10, 0, 2*Math.PI);
25. ctx.fill(); // or ctx.stroke() for a wireframe circle
26. 
27. // some text
28. ctx.fillStyle = "purple";
29. ctx.font = "20px Arial";
30. ctx.fillText("Hello!", 60, 20); // or ctx.strokeText for wireframe
31. }
Explanations:
  1. We use a function (line 4) called after the page is loaded (we say "after the DOM is ready"), so that the querySelector at line 6 will return the canvas.  If the page was not completely loaded and if this code had been run before it had finished loading, the canvas value would have been "undefined".
  2. Once we have the canvas, we request a "graphic context" (line 8). This is a variable for 2D or 3D  drawing on a canvas (in our case: 2D!) that we will use for drawing or setting colors, line widths, text fonts, etc.
  3. Then we can draw. Here we show only a few things you can do with the canvas API, but believe me, you can do much more (draw images, gradients, textures, etc.)! At line 15, we draw a filled rectangle. Parameters are the x and y coordinates of the top left corner (x goes to the right, y to the bottom of your screen), and the width and the height of the rectangle. At line 14, we used the fillStyle property of the context to set the color of filled shapes. This means: "now, all filled shapes you are going to draw will be in red!". It's like a global setting.
  4. Lines 17-20 draw a green wireframe rectangle, with a line width equal to 4 pixels. Notice the use of "stroke" instead of "fill" in the property name strokeStyle/fillStyle and in the context method for drawing a rectangle strokeRect/fillRect.
  5. Lines 23-25 draw a filled circle. The syntax is a bit different as circles are parts of a "path" (see the HTML5 fundamentals course, we explain the concept of "path" in the canvas API). Just keep in mind for now that before drawing a circle you need to call beginPath(). The call to arc(x, y, radius, start_angle, end_angle) does not draw the circle, it defines it. The next instruction ctx.fill() at line 25 will draw all shapes that have been defined since a new path began, as filled shapes. Calling ctx.stroke() here, instead of ctx.fill() would have drawn a wireframe circle instead of a filled one. Also note that the filled circle is red even if we did not specify the color. Remember that we set ctx.fillStyle = 'red' at line 14. Unless we change this, all filled shapes will be red.
  6. Lines 28-30 draw a filled text. The call to filltext(message, x, y) draws a filled text at the x,y position; this time in purple as we called ctx.fillStyle='purple' before calling fillText(...)
Example #2: functions that save and restore the context before drawing
CodePen: Functions that save and restore the context before drawing.
CodePen: Functions that save and restore the context before drawing.
Explanations:

This time we've written two functions for a cleaner code: one function that draws a filled rectangle with a given color, and one function that draws a filled circle, with a given color.

The values for x, y, width, height, radius, color can be passed as parameters to these functions.

When a function changes anything to the "global context": filled or stroke color, line width, or the position of the coordinate system (located by default in 0, 0, at the top left of the canvas), then it is good practice to save this context at the beginning of the function, with a call to ctx.save(), and to restore it at the end of the function, with a call to ctx.restore(). In this way, any change to the "global context" won't have any effect outside of the function.

We used also ctx.translate(x, y) in order to move the rectangle and the circle (look, they have been drawn at x=0, y=0, but as we translate the origin of the coordinate system with ctx.translate, the shapes are located in x, y on in the canvas). This is also a good practice: indeed, if we add more shapes (like eyes in the rectangle, in order to draw a monster), using coordinates relative to 0, 0, the whole set of shapes will be translated by the call to ctx.translate(x, y). This will make it easier to draw characters, monsters, etc. as we will see in a third example.

Example #3: draw a monster instead of a simple rectangle or circle

This is where you reap the benefits of your good habits of saving/restoring the context and using ctx.translate(x, y)!

CodePen: DrawMyMonster.
CodePen: DrawMyMonster.

Here is JavaScript code that implements these best practices:

Source Code:
1.  // useful to have them as global variables
2.  var canvas, ctx, w, h;
3.  
4.  
5.  window.onload = function init() {
6.    // Called AFTER the page has been loaded
7.    canvas = document.querySelector("#myCanvas");
8.  
9.    // Often useful
10.   w = canvas.width;
11.   h = canvas.height;
12. 
13.   // <>Important, we will draw with this object
14.   ctx = canvas.getContext('2d');
15. 
16.   // Ready to go!
17.   // Try to change the parameter values to move
18.   // the monster
19.   drawMyMonster(10, 10); // try to change that
20. };
21. 
22. function drawMyMonster(x, y) {
23.   // Draw a big monster!
24.   // Head
25. 
26.   // BEST practice: save the context, use 2D transformations
27.   ctx.save();
28. 
29.   // Translate the coordinate system, draw relative to it
30.   ctx.translate(x, y);
31. 
32.   // (0, 0) is the top left corner of the monster.
33.   ctx.strokeRect(0, 0, 100, 100);
34. 
35.   // Eyes
36.   ctx.fillRect(20, 20, 10, 10);
37.   ctx.fillRect(65, 20, 10, 10);
38. 
39.   // Nose
40.   ctx.strokeRect(45, 40, 10, 40);
41. 
42.   // Mouth
43.   ctx.strokeRect(35, 84, 30, 10);
44. 
45.   // Teeth
46.   ctx.fillRect(38, 84, 10, 10);
47.   ctx.fillRect(52, 84, 10, 10);
48. 
49.   // BEST practice: restore the context
50.   ctx.restore();
51. }

In this small example, we used the context object to draw a monster using the default color (black) and wireframe and filled modes:

2.6.2 Animating

A typical animation loop does the following at regular intervals:

  1. Clear the canvas
  2. Draw graphic objects / shapes
  3. Move graphic shapes / objects
  4. Go to step 1

Optional steps can be:

Examples
Example #1: monster on the move

There are different methods for coding an animation loop in JavaScript, as described in the above video.

The trick is to write a function, and at the end of this function, to ask the browser to call it again in 1/60th of a second if possible. See the CodePen example below:

CodePen: draw drawMyMonster and animate.
CodePen: draw DrawMyMonster and animate.
Example #2: bouncing ball

Here the balls bounce on the sides of the canvas (walls).

CodePen: Bouncing Balls.
CodePen: Bouncing Balls.
Explanations:

This time, we've used "simple objects" for the circle and the rectangles, and we've called them "player" and "ball":

Source Code:
1.  var ball = {
2.    x: 100,
3.    y:100,
4.    radius: 15,
5.    color:'green',
6.    speedX:2,
7.    speedY:1
8.  }
9.  
10. var player = {
11.   x:10,
12.   y:10,
13.   width:20,
14.   height:20,
15.   color:'red'
16. }

With this syntax, it's easier to manipulate "the x pos of the ball" - you just have to use ball.x. we added two properties to the ball object: speedX and speedY. Their value is the number of pixels that will be added to the current ball.x and ball.y position, at each frame of animation.

Let's look at the animation loop:
Source Code:
1.  function mainLoop() {
2.    // 1 - clear the canvas
3.    ctx.clearRect(0, 0, w, h);
4.  
5.    // draw the ball and the player
6.    drawFilledRectangle(player);
7.    drawFilledCircle(ball);
8.  
9.    // animate the ball that is bouncing all over the walls
10.   moveBall(ball);
11. 
12.   // ask for a new animation frame
13.   requestAnimationFrame(mainLoop);
14. }

Now, let's decompose the animation loop in some external functions to make it more readable. At each frame of animation, we will clear the canvas, draw the player as a rectangle, draw the ball as a circle, and move the ball.

You can take a look at the new versions of drawFilledRectangle that now take only one parameter named r, instead of x, y, width, height and a color. We've only changed a few things in its code (changed x to r.x, y to r.y, color to r.color etc.)

Let's look at the moveBall function:
Source Code:
1.  function moveBall(b) {
2.    b.x += b.speedX;
3.    b.y += b.speedY;
4.  
5.    testCollisionBallWithWalls(b);
6.  }

This function is called 60 times per second. So, 60 times per second we modify the b.x and b.y positions of the ball passed as parameter by adding to them the b.speedX and b.speedY property values.

Notice that we call moveBall(ball) from mainLoop. In the moveBall function, the ball passed as a parameter becomes the b parameter. So, when we change the b.x value inside the function, we are in reality changing the x value of the global object ball!

Ok, and at line 5 we call testCollisionBallWithWalls(b), which will test if the ball b hits a vertical or horizontal wall. Let's see an extract of this function now:

Source Code:
1.  function testCollisionBallWithWalls(b) {
2.    // COLLISION WITH VERTICAL WALLS?
3.    if((b.x + b.radius) > w) {
4.      // the ball hit the right wall
5.      // change horizontal direction
6.      b.speedX = -b.speedX;
7.  
8.      // put the ball at the collision point
9.      b.x = w - b.radius;
10.   } ...
11.   ...
12. }

At line 3 you can see the test that checks if the ball b hits the right side of the canvas. The right wall is at w (the width of the canvas) on the X-axis. If we compare (b.x + b.radius) with w, we can check if a part of the ball extends beyond the right wall.

Remember that each 1/60th of a second, the ball moves a certain number of pixels to the right (the exact value is b.speedX). Imagine that the ball moves 10 pixels to the right at each frame of animation. At some point, it will "cross the right wall". We cannot just change the sign of b.speedX to make it go to the other side. If we did this, it may stay stuck against the side with one half of the ball on either side of the wall.

If we now remove b.speedX to the ball.x position, we return the ball to the position it was in before it hit the wall. If we then reverse speedX, the ball will indeed start moving with a reverse horizontal speed. This will work but can give a strange visual effect if the balls moves, say, 20 pixels per frame or more. The ball will never be in a position where the eye can "see it against the wall". This is why experienced game coders know that you just need to put the ball "at the contact position", not to its previous position, before reversing the speed value. This is done at lines 8-9. Try changing speedX to say, 20, and you'll see what we mean.

2.6.3 Animating multiple objects

Let's animate balls and let's start with 3 the animation of 3 balls: ball1, ball2 and ball3. In the animation loop, we draw and move these three balls. Here is the result:

CodePen: animating multiple objects.
CodePen: Animating Multiple Objects.
Extract of the source code: the mainLoop function
Source Code:
1.  function mainLoop() {
2.    // 1 - clear the canvas
3.    ctx.clearRect(0, 0, w, h);
4.  
5.    // draw the balls and the player
6.    drawFilledRectangle(player);
7.  
8.    drawFilledCircle(ball1);
9.    drawFilledCircle(ball2);
10.   drawFilledCircle(ball3);
11. 
12.   // animate the balls bouncing all over the walls
13.   moveBall(ball1);
14.   moveBall(ball2);
15.   moveBall(ball3);
16. 
17.   // ask for a new animation frame
18.   requestAnimationFrame(mainLoop);
19. }

And what if we have 100 balls? We're not going to copy and paste the lines that draw and move the balls 100 times!

Using arrays and loops for creating any number of balls, for animating and moving any number of balls!

New version: look at the createBalls, drawBalls and moveBalls functions now!
CodePen: using arrays and loops.
CodePen: Using Arrays and Loops.
Let's look at the new functions we've added:
createBalls(numberOfBalls), returns an array of balls:
Source Code:
1.  function createBalls(n) {
2.    // empty array
3.    var ballArray = [];
4.  
5.    // create n balls
6.    for(var i=0; i < n; i++) {
7.      var b = {
8.        x:w/2,
9.        y:h/2,
10.       radius: 5 + 30 * Math.random(), // between 5 and 35
11.       speedX: -5 + 10 * Math.random(), // between -5 and + 5
12.       speedY: -5 + 10 * Math.random(), // between -5 and + 5
13.       color: getARandomColor(),
14.     }
15.     // add ball b to the array
16.     ballArray.push(b);
17.   }
18.   // returns the array full of randomly created balls
19.   return ballArray;
20. }
Explanations:
The getARandomColor function
Source Code:
1. function getARandomColor() {
2.    var colors = ['red', 'blue', 'cyan', 'purple',
3.    'pink', 'green', 'yellow'];
4.    // a value between 0 and color.length-1
5.    // Math.round = rounded value
6.    // Math.random() a value between 0 and 1
7.    var colorIndex = Math.round((colors.length-1)*Math.random());
8.    var c = colors[colorIndex];
9.  
10.   // return the random color
11.   return c;
12. }
Explanations:
Functions drawAllBalls and moveAllBalls:
Source Code:
1.  function drawAllBalls(ballArray) {
2.    ballArray.forEach(function(b) {
3.      drawFilledCircle(b);
4.    });
5.  }
6.  
7.  function moveAllBalls(ballArray) {
8.    // iterate on all balls in array
9.    ballArray.forEach(function(b) {
10.     // b is the current ball in the array
11.     b.x += b.speedX;
12.     b.y += b.speedY;
13. 
14.     testCollisionBallWithWalls(b);
15.   });
16. }
Explanations:

2.6.4 Mouse interactions

Mouse logo.

Detecting mouse events in a canvas is quite straightforward: you add an event listener to the canvas, and the browser invokes that listener when the event occurs.

The example below is about listening to mouseup and mousedown events (when a user presses or releases any mouse button):

Source Code:
1.  canvas.addEventListener('mousedown', function (evt) {
2.    // do something with the mousedown event
3.  });
4.  
5.  canvas.addEventListener('mouseup', function (evt) {
6.    // do something with the mouseup event
7.  });

The event received by the listener function will be used for getting the button number or the coordinates of the mouse cursor. Before looking at different examples, let's look at the different event types we can listen to.

The different mouse events (reminder)

In the last example, we saw how to detect the mouseup and mousedown events.

There are other events related to the mouse:

The tricky part: getting the position of the mouse relative to the canvas

When you listen to any of the above events, the event object (we call it a "DOM event"), passed to the listener function, has properties that correspond to the mouse coordinates: clientX and clientY.

However, these are what we call "viewport coordinates". Instead of being relative to the canvas itself, they are relative to the viewport (the visible part of the page).

Most of the time you need to work with the mouse position relative to the canvas, not to the viewport, so you must convert the coordinates between the viewport and the canvas. This will take into account the position of the canvas in the viewport, and the CSS properties that may affect the canvas position (margin, etc.).

Fortunately, there is a method for getting the position and size of any element in the viewport: getBoundingClientRect().

Here is an example that shows the problem:
CodePen: position and size in viewport.
CodePen: Position and Size in viewport.
WRONG code used in this example:
Source Code:
1.  ...
2.  canvas.addEventListener('mousemove', function (evt) {
3.    mousePos = getMousePos(canvas, evt);
4.    var message = 'Mouse position:
        ' + mousePos.x + ',' + mousePos.y;
5.      writeMessage(canvas, message);
6.  }, false);
7.  
8.    ...
9.  function getMousePos(canvas, evt) {
10.   // WRONG!!!
11.   return {
12.     x: evt.clientX,
13.     y: evt.clientY
14.   };
15. }
Mouse position, x and y coordinates.
A good version of the code:
CodePen: getMousePos.
CodePen: getMousePos.
And here is the fixed version of the getMousePos function:
Source Code:
1.  function getMousePos(canvas, evt) {
2.    // necessary to take into account CSS boundaries
3.    var rect = canvas.getBoundingClientRect();
4.    return {
5.      x: evt.clientX - rect.left,
6.      y: evt.clientY - rect.top
7.    };
8.  }
Result (the cursor is approximately at the top left corner):
Mouse position.

How to display the mouse position, and the mouse button that has been pressed or released

This example uses the previous function for computing the mouse position correctly. It listens to mousemove, mousedown and mouseup events, and shows how to get the mouse button number using the evt.button property.

Example:
CodePen: example move mouse and click anywhere.
CodePen: example move mouse and click.
Mouse position: click and release button.
Extract from Source Code:
Source Code:
1.  var canvas, ctx, mousePos, mouseButton;
2.  
3.  window.onload = function init() {
4.    canvas = document.getElementById('myCanvas');
5.    ctx = canvas.getContext('2d');
6.  
7.    canvas.addEventListener('mousemove', function (evt) {
8.      mousePos = getMousePos(canvas, evt);
9.      var message = 'Mouse position:
          ' + mousePos.x + ',' + mousePos.y;
10.     writeMessage(canvas, message);
11.   }, false);
12. 
13.   canvas.addEventListener('mousedown', function (evt) {
14.     mouseButton = evt.button;
15.     var message = "Mouse button " + evt.button + " down at position:
          " + mousePos.x + ',' + mousePos.y;
16.     writeMessage(canvas, message);
17.   }, false);
18. 
19.   canvas.addEventListener('mouseup', function (evt) {
20.     var message = "Mouse up at position:
          " + mousePos.x + ',' + mousePos.y;
21.       writeMessage(canvas, message);
22.   }, false);
23. };
24. 
25. function writeMessage(canvas, message) {
26.   ctx.save();
27.   ctx.clearRect(0, 0, canvas.width, canvas.height);
28.   ctx.font = '18pt Calibri';
29.   ctx.fillStyle = 'black';
30.   ctx.fillText(message, 10, 25);
31.   ctx.restore();
32. }
33. 
34. function getMousePos(canvas, evt) {
35.   // necessary to take into account CSS boudaries
36.   var rect = canvas.getBoundingClientRect();
37.   return {
38.     x: evt.clientX - rect.left,
39.     y: evt.clientY - rect.top
40.   };
41. }

2.6.5 Moving a player with the mouse

This time, we've added a mousemove event listener to the canvas in the init function, and reused the trick that you saw in the previous section to get the correct mouse position:

Working example:
CodePen: working example, get correct mouse position.
CodePen: working example, get correct mouse position.
Extract from the JavaScript Source Code:
Source Code:
1.  var mousePos;
2.  
3.  window.onload = function init() {
4.    ...
5.    // create 10 balls
6.    balls = createBalls(10);
7.  
8.    // add a mousemove event listener to the canvas
9.    canvas.addEventListener('mousemove', mouseMoved);
10. 
11.   // ready to go !
12.   mainLoop();
13. };
14. 
15. function mouseMoved(evt) {
16.   mousePos = getMousePos(canvas, evt);
17. }
18. 
19. function getMousePos(canvas, evt) {
20.   // from the previous section
21.   var rect = canvas.getBoundingClientRect();
22.   return {
23.     x: evt.clientX - rect.left,
24.     y: evt.clientY - rect.top
25.   };
26. }

Line 9 defines a mousemove event listener: the mouseMoved callback function will be called each time the user moves the mouse on the canvas.

The mouseMoved(evt) function uses the trick from the previous section and puts the correct mouse position in the mousePos variable.

With this code, as soon as we move the mouse on top of the canvas, we'll have this mousePos global variable (line 1) that will contain the mouse position (in the form of the mousePos.x and mousePos.y properties).

And here is the new mainLoop function. We added a call to the mousePlayerWithMouse function:
Source Code:
1.  function mainLoop() {
2.    // 1 - clear the canvas
3.    ctx.clearRect(0, 0, w, h);
4.  
5.    // draw the ball and the player
6.    drawFilledRectangle(player);
7.    drawAllBalls(balls);
8.  
9.    // animate the ball that is bouncing all over the walls
10.   moveAllBalls(balls);
11. 
12.   movePlayerWithMouse();
13. 
14.   // ask for a new animation frame
15.   requestAnimationFrame(mainLoop);
16. }
And here is the code of the movePlayerWithMouse function:
Source Code:
1.  function movePlayerWithMouse() {
2.    if(mousePos !== undefined) {
3.      player.x = mousePos.x;
4.      player.y = mousePos.y;
5.    }
6.  }

If the mouse position is defined, the player's x and y position will equal to the positions of the mouse pointer.

The mouse position may be undefined if the animation loop started without the mouse cursor being on top of the canvas. Remember that the mainLoop starts as soon as the page is loaded.

Perhaps it's occurred to you that it might be better to move the player "from its center" instead of from its top left corner. We leave this improvement to you! :-)

2.6.6 Adding collision detection

Let's make it a game by adding collision detection! And try to move the player to all the balls as fast as you can.

CodePen: adding collision detection.
CodePen: adding collision detection.
How do we detect collisions?

First, if you're into game programming, we have a full section about collision detection one of the W3Cx HTML5 Apps and Games course modules.

Blue: no collision, yellow: collision.

We have a player that is a rectangle and other objects that are circles. This is cool, as it allows us to find a short function that tests if a circle collides with a rectangle whose sides are aligned to the X-axis and Y-axis (we implemented this after reading this  thread at StackOverflow):

Source Code:
1.  // Collisions between rectangle and circle
2.  function circRectsOverlap(x0, y0, w0, h0, cx, cy, r) {
3.    var testX=cx;
4.    var testY=cy;
5.  
6.    if (testX < x0) testX=x0;
7.    if (testX > (x0+w0)) testX=(x0+w0);
8.    if (testY < y0) testY=y0;
9.    if (testY > (y0+h0)) testY=(y0+h0);
10. 
11.   return (((cx-testX)...(cx-testX)+(cy-testY)...(cy-testY))< r...r);
12. }

Let's look at our game! This time, we've added into the loop a collision test between the player and the balls. If the player hits a ball, it's removed from the ball array. We did this test in the moveBalls function, as we were already testing collisions with walls for each ball in the array. Let's look at this new version:

Source Code:
1.  function moveAllBalls(ballArray) {
2.    // iterate on all balls in array
3.    ballArray.forEach(function(b, index) {
4.      // b is the current ball in the array
5.      b.x += b.speedX;
6.      b.y += b.speedY;
7.  
8.      testCollisionBallWithWalls(b);
9.  
10.     testCollisionWithPlayer(b, index);
11.   });
12. }
13. 
14. function testCollisionWithPlayer(b, index) {
15.   if(circRectsOverlap(player.x, player.y,
16.     player.width, player.height,
17.     b.x, b.y, b.radius)) {
18.     // we remove the element located at index
19.     // from the balls array
20.     // splice: first parameter = starting index
21.     // second parameter = number of elements to remove
22.     balls.splice(index, 1);
23.   }
24. }
Explanations:

We've also added a function for displaying the number of balls in the array while we are playing. When this number reaches zero, we display "You Win!":

Source Code:
1.  function drawNumberOfBallsAlive(balls) {
2.    ctx.save();
3.    ctx.font="30px Arial";
4.  
5.    if(balls.length === 0) {
6.      ctx.fillText("YOU WIN!", 20, 30);
7.    } else {
8.      ctx.fillText(balls.length, 20, 30);
9.    }
10.   ctx.restore();
11. }

This function is called by the mainLoop:

Source Code:
1.  function mainLoop() {
2.    // 1 - clear the canvas
3.    ctx.clearRect(0, 0, w, h);
4.  
5.    ...
6.    drawNumberOfBallsAlive(balls);
7.    ...
8.  
9.    // ask for a new animation frame
10.   requestAnimationFrame(mainLoop);
11. }

2.6.7 Adding input fields

Let's use some other techniques that we've learnt in this module. There are input fields: sliders, color chooser, number chooser. We are going to use the DOM API to handle them.

We use these input fields to indicate the number of balls we want, the max speed we would like, the color and size of the player, etc.

New version:
CodePen: adding input fields.
CodePen: adding input fields.
Explanations:

HTML code: this time we've used an oninput in each input field, and an onchange attribute on the <select> HTML drop down menu:

Source Code:
1.  <div id="controls">
2.    <label for="nbBalls">Number of balls: </label>
3.    <input type="number" min=1 max=30
4.      value=10 id="nbBalls"
5.    oninput="changeNbBalls(this.value);">
6.    <p></p>
7.  
8.    <label for="nbBalls">Player color: </label>
9.    <input type="color" value='#FF0000'
10.     oninput="changePlayerColor(this.value);">
11.   <p></p>
12. 
13.   <label for="nbBalls">Color of ball to eat: </label>
14.   <select onchange="changeColorToEat(this.value);">
15.     <option value='red'>red</option>
16.     <option value='blue'>blue</option>
17.     <option value='green'>green</option>
18.   </select>
19.   <p></p>
20. 
21.   <label for="nbBalls">Change ball speed: </label>
22.   <input type="range" value='1'
23.     min=0.1 max=3 step=0.1
24.     oninput="changeBallSpeed(this.value);"> +
25.   <p></p>
26. </div>

JavaScript code: we've added some new variables in order to get closer to a real game with a goal, levels, game over menu and so on.

Source Code:
1.  var initialNumberOfBalls; // number of balls at the beginning
2.  var globalSpeedMutiplier = 1; // will change when we move the speed
3.  // slider
4.  var colorToEat = 'red';       // color of the "good" balls to eat
5.  var wrongBallsEaten = goodBallsEaten = 0; // number of good/bad balls
6.  // eaten
7.  var numberOfGoodBalls;        // number of good balls in the set
And here are the callback functions called when you use the input fields:
Source Code:
1.  function changeNbBalls(nb) {
2.    startGame(nb);
3.  }
4.  
5.  function changeColorToEat(color) {
6.    colorToEat = color;
7.    startGame(initialNumberOfBalls);
8.  }
9.  
10. function changePlayerColor(color) {
11.   player.color = color;
12. }
13. 
14. function changeBallSpeed(coef) {
15.   globalSpeedMutiplier = coef;
16. }

Each time we change the number of balls in the game, or the color of the balls you need to eat, we need to restart the game.

Here is the startGame(nb_balls) function:
Source Code:
1.  function startGame(nb) {
2.    do {
3.      balls = createBalls(nb);
4.      initialNumberOfBalls = nb;
5.      numberOfGoodBalls = countNumberOfGoodBalls(balls, colorToEat);
6.    } while(numberOfGoodBalls === 0); // in case no good ball in the set
7.  
8.    wrongBallsEaten = goodBallsEaten = 0;
9.  }
... and here is the function that counts the number of good balls in the newly created set of balls:
Source Code:
1.  function countNumberOfGoodBalls(balls, colorToEat) {
2.    var nb = 0;
3.  
4.    balls.forEach(function(b) {
5.      if(b.color === colorToEat) // we count the number of balls
6.        nb++;                    // of this color in the balls array
7.    });
8.  
9.    return nb;                   // return this number to the caller
10. }

2.6.8 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics
Optional projects
A monster in the shape of a bacteria.

3.1.1 Introduction - Standard HTML API's (1:29)

Intro: standard HTML API's in your browser.

From what we've learned so far, it is time now to enjoy some of the standard API's your browser provides.

This module is centered around the BOM; the "Browser Object Model". That provides standard objects such as the navigator or the window object. We already had a glimpse of these, this time we look at them more into details. In addition, we will look at some HTML5 standards APIs provided by your browser.

For example, the geolocation API will help you display an interactive map centered on your location, or the multimedia API will give you complete controls over audio or video players.

Also, we'll look at persistence APIs that will enable you to load and save data on your hard disk. The next day if you open your Web application, you will able to retrieve these data. This is an important feature. We will come back to features we already played with, such as arrays and iterators, but the main topic is really about browser APIs. We will end this module with a mid-course project, and different difficulty levels will be proposed.

3.1.2 Module 3 outline

Geolocation logo.
What you will learn in Module 3:

Note that this module is more "project oriented", meaning less fundamental concepts are presented.

3.2.1 Arrays (8:57)

CodePen: arrays.
CodePen: arrays.

Let's continue with the arrays. We already encounter them during the first module but this time we will give more details. And maybe we'll come back again to arrays in the next module. Each week, during each module we give some small extra information so that in the end, you will have a good view of each JavaScript concepts.

CodePen: example array.

Let's start with an array called "myarr" that contains some colors. The first thing we must remind is that each element has an index. And the first index is at number 0. If I type in the console...it gives me the first element. "myarr[0]" gives the first element. Arrays in JavaScript are objects.

CodePen: example array, #2.

If I try "typeof myarr" it's says "objects". And objects, in an object-oriented languages, have properties. They are the DNA of the objects, like person has an age, person has a name, an array has the length. As the array is an object, it will have some interesting properties.

CodePen: example array, #3.

One of them is the length...and you access properties using the "." operator. This, the length, corresponds to the number of elements: 1, 2, 3 and 4. The last one, the last element is at index given by the length property -- 1. "purple", the last element, is located at index "myarr.length-1".

CodePen: example array, #4.

If you want to add an element to an array, you've got different possibilities. The most common one, the one that I recommend, is to use a method called "push". red, blue, yellow, purple. Let's add 'orange', like this. Like that, it returns the new length: 5 elements. And if I look at the content of my array, it now has, at the end, the last element I pushed inside: orange. "push" is very useful.

CodePen: example array, #5.

You can also add an element at the end of an existing array by adding it to the index equal to the length of the array. If I do this, we don't have any "green" here...You see, I'm using the index length. If I do like that, it returns the new element we added, and it adds at the end. To be frank, most of the time I use the "push" method.

CodePen: example array, #6.

You can also sort the elements of an array using the "sort" method. Objects have properties: their DNA, their characteristics, and they have methods that correspond to their behavior. You can sort an array because it has a sort method. It's a sort of function associated with the array. If I just call "sort" without any parameter, it returns the array sorted by ascending alphabetical order.

CodePen: example array with an object.

If I want to work with more complex elements, I can make an array with an object. I prepared an array that contains objects, it's called "persons" and each element is an object. If I look at the first element, here. It gives me a person whose familyName is Buffa, whose givenName is Michel, age 51. This corresponds to the first element of the array.

CodePen: example array with an object, #2.

If I want to access some properties of this element, I will use the "." operator. So persons.0.givenName will correspond to Michel, persons.0 is this element, .givenName corresponds to this property.

CodePen: example array with an object, #3.

If I want to sort this array by age for example, I cannot use just persons.sort() as it will not know which criteria I must use or which property I want the sort to be done. We can pass an argument here, that will be a callback, a function called by the "sort" method from the API. And this callback will indicate how we compared 2 different elements. Let's try it! I prepared it.

We can define a function named, for example, compareByAge() that will compare an element named "a" with an element named "b". And we suppose that these elements have an age property, and then we compare. If "a" has a smaller age than "b", we return -1. If the age of the element "a" is bigger than the age of element "b", we return 1, else we return 0 if the ages are equal. And then, we just call "sort", and we pass the name of this comparison function. And in that case, the array is sorted by age: 20, 32, 51. When you call this method, it returns a sorted array but it also sorts the array itself. The array is no more the one we had first, now it's a sorted array.

CodePen: example remove an element from array using splice.

If I want to remove an element from the array, I will use the splice method. The first parameter is the index after which we will remove an element. If I say 0, it means start at index 0, remove 1 element. It will remove the element just after 0. It removed the element named Pig Bodine, it was in the middle. If I look at the array now, we just remove the element in the middle with the age 20.

CodePen: example remove an element from array using splice, #2.

If I want to remove the last element, I can use the "pop" method. You remember that the "push" method adds at the end an element and the "pop" method will just remove the last element. Now, the array contains only the first element, I "popped", i.e., I removed the last element from the array.

Ok that's all for this video, you saw the most common methods: push, pop and sort. You saw that the first element is at index 0, the last element at index length-1 and that you can also use some comparison functions for the sort elements.

ERRATA in the above video:

Source code of the example in the video:
JavaScript arrays

In JavaScript, arrays represent a collection of "things", which may be strings, integer values, decimal values, boolean values, or any sort of JavaScript object.

Source Code:
1.  > var myarr = ['red', 'blue', 'yellow', 'purple'];
2.  Undefined
3.  
4.  > myarr;
5.  ["red", "blue", "yellow", "purple"]
6.  
7.  > myarr[0];
8.  "red"
9.  
10. > myarr[3];
11. "purple"

Each element of an array has a key/index and a value. Here are the keys/indexes and values from the above example:

Table with key and value of the previous array example.

Below is an another example with an array containing three integers. The first element is at index 0, and the last at the index equal to the number of elements.

Source Code:
1.  > var a = [];
2.  > typeof a;
3.  "object"
4.  > var a = [1,2,3];
5.  > a
6.  [1, 2, 3]
7.  > a[0]
8.  1
9.  > a[1]
10. 2
JavaScript arrays are objects and have some useful properties and methods

Note that in JavaScript, arrays are "objects" (lines 2-3 in the above example), which means that they have properties and methods. You can access/call them using the "." operator. Here are the most common properties and methods.

Source Code:
1.  > var a = [1, 3, 2, 5, 7];
2.  undefined
3.  
4.  > a.length; // number of elements
5.  5
6.  
7.  > a.sort(); // sorts element in a
8.  [1, 2, 3, 5, 7]
9.  
10. > a.splice(2, 1); // remove 1 element starting from index=2 (3rd element)
11. [3]
12. 
13. > a; // the '3' has been removed from the array
14. [1, 2, 5, 7]

By default, the sort() method sorts elements alphabetically if they are strings, or from lowest to highest if they are numeric. If you want to sort objects like  {firstName:'michel', lastName:'Buffa', age:51}, you will need to use another method passed as an argument to the sort method, for example to indicate the property you want to use for sorting (e.g., sort by age);

Example with an array of persons (each person is an object):
Source Code:
1.  var persons = [
2.    {givenName: 'Michel', familyName: 'Buffa', age:51},
3.    {givenName: 'Pig', familyName: 'Bodine', age:20},
4.    {givenName: 'Pirate', familyName: 'Prentice', age:32}
5.  ];
6.  
7.  function compareByAge(a,b) { // comparison function, a and b are persons
8.  if (a.age < b.age)        // compare by age
9.    return -1;
10. 
11.   if (a.age > b.age)
12.   return 1;
13. 
14.   return 0;
15. }
16. 
17. persons.sort(compareByAge); // this will call automatically compareByAge
18. // passing all persons from the array, compare
19. // them by age and sort the array.
Explanations:

We will see more methods in the other subsections of this page.

Elements can be of different types in a same array
Source Code:
1.  > var a = [1,2,3];
2.  
3.  > a[2] = 'three';
4.  "three"
5.  
6.  > a
7.  [1, 2, "three"]
Adding elements to an array

We can add new elements using a new index, if you want to add a new element at the end, use the push method!

Source Code:
1.  > var a = [1,2,"three"];
2.  undefined
3.  
4.  > a[3] = 'four';
5.  "four"
6.  
7.  > a;
8.  [1, 2, "three", "four"]
9.  
10. > a[a.length] = "five"; // adding at the end
11. [1, 2, "three", "four", "five"]
12. 
13. > a.push("six"); // but usually we prefer using the push method
    for adding
14. [1, 2, 3, "four", "five", "six"]  // a new element at the end
When using indexes, be careful not to leave "holes" in the array:
Source Code:
1.  > a[7] = 'height';
2.  "height"
3.  
4.  > a;
5.  [1, 2, 3, "four", "five", "six", undefined × 1, "height"]

This array is valid, but having a [6] equal to "undefined" is often prone to errors. Be careful when using absolute indexes for adding elements. We recommend using the push method instead.

Removing elements from an array

The recommended method is to use the splice method:

1.  array.splice(start)
2.  array.splice(start, deleteCount)
Examples:
Source Code:
1.  > a;
2.  [1, 2, 3, "four", "five", "six", undefined × 1, "height"]
3.  
4.  > a.splice(6, 1); // remove element at the seventh index, the undefined one!
5.  [undefined × 1]
6.  
7.  > a;
8.  [1, 2, 3, "four", "five", "six", "height"] // it's no more here :-)
9.  
10. > a.splice(0, 3); // remove the three first elements
11. [1, 2, 3]
12. 
13. > a;
14. ["four", "five", "six", "height"]
15. 
16. > a.splice(a.length-1); // remove the last element
17. "height"
18. 
19. > a;
20. ["four", "five", "six"]
Recommended method for removing the last element: the pop method!
Source Code:
1.  > a
2.  ["four", "five", "six"]
3.  
4.  > a.pop(); // remember push/pop = add / remove element at last position!
5.  "six"
6.  
7.  > a
8.  ["four", "five"]
Trap: the delete method is not good for removing an element from an array!
Source Code:
1.  > delete a[1];
2.  true
3.  
4.  > a;
5.  ["four", undefined × 1] // the element became undefined,
6.  // but it's still in the array!
Arrays of arrays

It is possible for an array to be an element within an array! This example shows an array made of two arrays of three elements each. It's a 2x3 matrix with two rows and three columns!

Source Code:
1.  > var a = [[1,2,3], [4,5,6]]; // a is a matrix: 2 rows, 3 columns.
2.  Undefined
3.  
4.  > a[0]; // first row
5.  [1, 2, 3]
6.  
7.  > a[1]; // second row
8.  [4, 5, 6]
9.  
10. > a[0][0]; // top left element
11. 1
12. 
13. > a[0][1]; // second element, first line
14. 2
15. 
16. > a[0][2]; // third element, first line
17. 3
18. 
19. > a[1][0]; // first element, second line
20. 4
21. 
22. > a[1][1]; // second element, second line
23. 5
24. 
25. > a[1][2]; // third element, second line
26. 6

It is possible to have different arrays with different lengths and different types of element in an array:

Source Code:
1.  > var a = [];
2.  undefined
3.  
4.  > a[0] = [1, 2, 3, 4, 5];
5.  [1, 2, 3, 4, 5]
6.  
7.  > a[1] = ['michel', 'henri', 'francois']
8.  ["michel", "henri", "francois"]
9.  
10. > a
11. [Array(5), Array(3)]

3.2.2 Strings are arrays of characters

Yes, they do look like arrays!

JavaScript strings are "like" arrays of characters, but they have some limitations, and some dedicated properties and methods:

Source Code:
1.  > var s = 'Michel';
2.  undefined
3.  
4.  > s[0];
5.  "M"
6.  
7.  > s[1];
8.  "i"
9.  
10. > s.length;
11. 6

Indeed, the string s behaves like an array, it has the length property like an array, and we can access individual characters using indexes that go from 0 to length-1, like arrays...

However... they are not quite the same as arrays!

You cannot add elements to strings using a non-existent index, you cannot use the push/pop methods for adding/removing  characters at the end of the string:

Source Code:
1.  s.push(' Buffa');
2.  
3.  ERROR: VM5748:1 Uncaught TypeError: s.push is not a function
4.  at <anonymous>:1:3
5.  (anonymous) @ VM5748:1
6.  
7.  s[s.length] = 'B'; // add 'B' at the end?
8.  "B"
9.  
10. s[s.length] = 'u'; // add 'u' at the end?
11. "u"
12. 
13. s[s.length] = 'f'; // add 'f' at the end?
14. "f"
15. 
16. s; // s remained UNCHANGED!
17. "Michel"

You can't even modify a character using an index. Strings are "read only" when using brackets to access individual characters!

Source Code:
1.  > var s = 'Michel';
2.  undefined
3.  
4.  > s[0] = "R"; // Trying to change the 'M' into an 'R'
5.  "R"
6.  
7.  s; // no luck!
8.  "Michel"

You also can't remove characters using the array's splice method:

1.  > s.splice(0, 3);
2.  
3.  ERROR: VM716:1 Uncaught TypeError: s.splice is not a function
4.  at <anonymous>:1:3

How do we add characters to a string, how can we modify a string? How can we delete elements in a string?

Strings come with a whole set of methods, which we'll come to in module 4 when we talk about JavaScript objects (in the section titled "JavaScript predefined objects"). Without going into detail just yet, here are some examples:

Adding a string to the beginning of a string using the + operator:
Source Code:
1.  > var s = 'Michel';
2.  undefined
3.  
4.  > s = "Hello " + s;
5.  "Hello Michel"
6.  
7.  > s = 'O' + s; // equivalent to push('0') with arrays.
8.  "OHello Michel"
Adding a string to the end of another one with the + operator:
Source Code:
1.  > s = 'Michel';
2.  "Michel"
3.  
4.  > s += ' Buffa';
5.  "Michel Buffa"
6.  
7.  > s;
8.  "Michel Buffa"
Adding a string at the end of another one using the concat method:
Source Code:
1.  > var s1 = 'Michel';
2.  undefined
3.  
4.  > var s2 = 'Buffa';
5.  undefined
6.  
7.  > var s3 = s1 + " " + s2; // + can be used to concat more than 2 strings
8.  Undefined
9.  
10. > s3;
11. "Michel Buffa"
12. 
13. > var s4 = s1.concat(s2);
14. Undefined
15. 
16. > s4;
17. "MichelBuffa"
18. 
19. > var s5 = s2.concat(s1);
20. Undefined
21. 
22. s5;
23. "BuffaMichel"
Removing chars from a string using the substring method:
Removing the last char (equivalent to the pop method from arrays):
1.  > var s = 'Michel';
2.  undefined
3.  
4.  > s = s.substring(0, s.length-1);
5.  "Miche"
Removing a certain number of chars starting from a string, starting at a given index:
Source Code:
1.  var s = 'Michel';
2.  
3.  function removeChars(s, startIndex, numberOfCharsToRemove) {
4.  return s.substring(0, startIndex) +   
5.  s.substring(startIndex + numberOfCharsToRemove);
6.  }
7.  
8.  // Remove 3 consecutive chars from s, starting at index = 1.
9.  s = removeChars(s, 1, 3);
10. 
11. console.log(s); // Will display "Mel" in the console
Replacing a char at a given index:
Source Code:
1.  function replaceAt(s, index, character) {
2.    return s.substr(0, index) + character + s.substr(index+character.length);
3.  }
4.  
5.  var s2 = "JavaScript";
6.  s2 = replaceAt(s2, 1, "o");
7.  
8.  console.log(s2); // Will display "JovaScript"
9.  
10. // It also works with a string instead of a simple char
11. s2 = replaceAt(s2, 0, "Coca");
12. console.log(s2); // Will display "CocaScript"

3.2.3 Iterating on array elements (7:22)

CodePen: iterating on array elements.
CodePen: iterating on array elements.

Hello! Let's look at the different methods you can use to iterate on each element of an array. One of the most practical one consists in using the "forEach" iterator we already met during some previous examples, in particular during Module 1.

The syntax is this one, you start with the name of the array, and you type "forEach" with a capital "E". And this method takes a single callback. Usually, we type the callback body between the parenthesis. Declaring an anonymous function, an anonymous callback. And the first example is to use only a single argument that will be the current element while we are iterating. I call it "day" here, and day will be: Monday, Tuesday, Wednesday,... each time, we iterate on the collection of the days, on the array of days.

CodePen: example using document.body.innerHTML.

If I do "document.body.innerHTML"...You see that when the code is executed, for each element in the array, the variable "day" here, will be that day, and we use the DOM API to add at the end of the document's body, the name of the day and we go to the next line.

Here is the result. You can see that we can iterate using this "forEach" iterator, it's very simple. The name, here, is not important. You can call it "singleD", you can call it "d" and it works. You choose the name of the variable.

CodePen: example using document.body.innerHTML, #2.

This iterator also takes optionally a second parameter that will be the index of the element. We can use this index to display, to give some numbers to the elements. Here, it will display the name of the day: Monday is at index, followed by the value of the index, 0. Monday is the element in the array at index 0. Tuesday is the element at the index 1.

CodePen: example document.body.innerHTML with 'for each'.

You can also use a third argument, that is the array itself. Let's call it "arr" and usually, we use the array to display the length of the array or maybe do operations on the array: remove the current element or do something like that. "from an array of" And now you can see that it displays: Monday is at index 0 from an array of 3 elements! "3", we took it from the third argument, and we use the length property from it. This is what we can do with the "forEach" iterator, very practical, very simple.

CodePen: example document.body.innerHTML with 'for each', #2.

Another thing we can do, let me put this in comments, is use a regular "for" loop. Using a "for" loop... so the very automatic way is do like that. And you see we've got the same results we had with the "forEach". It's a bit more complicated because we must declare a variable, initialize it to 0 and this is the first, the starting index in the array. And this "for" loop, if you remember when we detailed them, if you use a strict < operator and if you increment the loop variable at the end, it will go from 0 to this value - 1.

This loop will go from i = 0 to "a.length -1" and "a.length -1" is the index of the last element of the array. This loop will go to through all elements in the array. And we need to use the "a" brackets with the index between the brackets notation to display the value. Which is best? This one or the with the "forEach" iterator? It depends.

CodePen: example document.body.innerHTML with 'for each', #3.

Here you can just go 2 by 2... I can iterate 2 by 2, or I can break the loop in the middle using the "break" keyword and a condition with an "if". All these things I cannot do them easily with the "forEach" operator. If you just need to iterate and do something on each element, use the "forEach" operator. If you need to jump over some elements, do some operations in the middle, stop the iteration, then go for the "for" loop.

Get the source code of the example shown in the video:

Let's study the different methods for iterating on array elements.

Method #1: iterating using forEach

The forEach method takes a single argument that is a function/callback that can have one, two or three parameters:

Typical use with only one parameter (the current element):
Source Code:
1.  var a = ['Monday', 'Tuesday', 'Wednesday'];
2.  
3.  a.forEach(function(day) {
4.    // day is the current element
5.    document.body.innerHTML += day +
6.    "<br>"; // will display Monday, Tuesday, Wednesday
7.  })

This is the most practical way to iterate on each individual element of a collection (array, string);

CodePen: iterating on each element.
CodePen: iterating on each individual element of a collection (array, string).

Now, let's iterate on an array of person, and use two parameters in the callback function in order to get the index of the current element:

CodePen: iterating on an array of person, and use 2 parms in callback function.
CodePen: iterating on an array of person, and use 2 parms in callback function.
Source Code:
var persons = [
    {name:'Michel', age:51},
    {name:'Henri', age:20},
    {name:'Francois', age:29}
  ];

persons.forEach(function(p, index) {
  document.body.innerHTML += p.name + ", age " + p.age +
  ", at index " + index + " in the array<br>";
});
Finally, let's use three parameters, the last one being the array itself

This can be useful if we need to know the length of the array, or do special things within the array (add/change/move elements during the iteration):

CodePen: array iteration.
CodePen: array iteration.

In this example, we used the third parameter (the array) to access its length inside the iteration loop.

Method #2: iterating on an array using regular loop statements

You can use any standard loop statement that we saw during in module 2. The most common way to iterate over an array is to use a for loop from 0 to length-1.

Using this method allows elements to be iterated two by two, or the loop to be broken in the middle using the break instruction, etc.

Iterating over all elements in an array, using a for loop
CodePen: iterating over all elements in an array, using a for loop.
CodePen: iterating over all elements in an array, using a for loop.

Another example where we iterate two by two (just changed the increment in the for loop):

CodePen: iterate two by two.
CodePen: iterate two by two.

3.2.4 Discussion and projects

Please either post your comments/observations/questions or share your creations.

Suggested topics
Optional project: an interactive picture album browser
Source Code:
let myPicturesArray = [ {
  "albumId": 1,
  "id": 1,
  "title": "accusamus beatae ad facilis cum similique qui sunt",
  "url": "https://placehold.it/600/92c952",
  "thumbnailUrl": "https://placehold.it/150/92c952"
  },
  {
  "albumId": 1,
  "id": 2,
  "title": "reprehenderit est deserunt velit ipsam",
  "url": "https://placehold.it/600/771796",
  "thumbnailUrl": "https://placehold.it/150/771796"
  },
  {
  "albumId": 2,
  "id": 51,
  "title": "non sunt voluptatem placeat consequuntur rem
    incidunt",
  "url": "https://placehold.it/600/8e973b",
  "thumbnailUrl": "https://placehold.it/150/8e973b"
  },
  {
  "albumId": 2,
  "id": 52,
  "title": "eveniet pariatur quia nobis reiciendis laboriosam ea",
  "url": "https://placehold.it/600/121fa4",
  "thumbnailUrl": "https://placehold.it/150/121fa4"
  },
  {
  "albumId": 3,
  "id": 127,
  "title": "magnam quia sed aspernatur",
  "url": "https://placehold.it/600/74456b",
  "thumbnailUrl": "https://placehold.it/150/74456b"
  },
  {
  "albumId": 3,
  "id": 128,
  "title": "est facere ut nam repellat numquam quia quia eos",
  "url": "https://placehold.it/600/b0931d",
  "thumbnailUrl": "https://placehold.it/150/b0931d"
}
  ];
CodePen: iterating pictures and create img elements.
CodePen: iterating pictures and create img elements.

3.3.1 Playing audio and video streams

These examples are adapted from the ones in the W3Cx  HTML5 Coding Essentials and Best Practices course, which covers multimedia in depth.  The  HTML5 Advanced Course (HTML5 Apps and Games) also gives further examples covering topics such as making a video player with chapter navigation, clickable transcript, audio EQ, etc.

The <video> element

The <video> element of HTML5 is one of the two "Flash killers" (the other being the <canvas> element). It was designed to replace horrible things like embedded Flash objects that we used to encounter not so long ago.

The new way of doing things is a lot better... (please open this  live example at JS Bin).

The source code of this example shows the typical usage of the <video> element:

<video width="320" height="240" controls="controls">
<source src="movie.mp4" type="video/mp4" />
<source src="movie.ogg" type="video/ogg" />
Your browser does not support the <video> element.
</video>
Please note that:

You will learn more about the different attributes of the <video> element later on in the course.

Restriction: you cannot embed a YouTube or a Daily Motion video using the <video> element

Help! <video src="my youtube video URL"></video>  does not work!

Beware: cannot embed social media videos.

While they use HTML5 to render their videos, these hosting sites (YouTube, etc.)  use rather complex techniques in order to prevent you from using them with the  <video> element. Instead, you often need to embed an <iframe>  that will render the HTML5 videos in your Web site, and of course, the advertising that comes along with them.

Usually you have an "embed" button close to the videos that prompts you with some HTML code that you can copy and paste for embedding.

An example using YouTube:

Here is the HTML code you need to copy and paste in order to embed a video (in this case, a tutorial that tells you how to embed a YouTube video):

<iframe width="560" height="315" src="https://www.youtube.com/embed/ZH1XOsv8Oyo" frameborder="0" allowfullscreen></iframe>

Below is the YouTube video embedded in this page using the above code: it's HTML5 but it's not a <video> element directly inserted in the HTML of this page - it's an <iframe>.

YouTube

Example YouTube video.
The <audio> element
Introduction
HTML5 audio is composed of several layers:

This course focuses on the <audio> element. Please check for  the Web Audio API and other advanced parts of HTML5 in W3Cx's  HTML5 Apps and Games course.

The attributes, event set and JavaScript API of the <audio> element are just a "reduced" version of the ones from the <video> element, and here we will only address their differences and peculiarities.

The <audio> element

The most simple basic example: online example from JSBin

Press play to stream the neigh of a horse:

Horse neigh.
Horse neigh.
The code is very similar to the basic <video> element usage.
Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <meta charset="utf-8">
5.    <title>Using the audio element</title>
6.  </head>
7.  <body>
8.    <audio controls="controls" crossorigin="anonymous">
9.      <source src=<https://mainline.i3s.unice.fr/mooc/week2p1/horse.ogg>
10.     type="audio/ogg" />
11.     <source src=<https://mainline.i3s.unice.fr/mooc/week2p1/horse.mp3>
12.     type="audio/mp3" />
13.     Your browser does not support the audio element.
14.     Download the audio/video in
15.     <a href="https://mainline.i3s.unice.fr/mooc/week2p1/horse.ogg">OGG</a>
16.     or <a href="https://mainline.i3s.unice.fr/mooc/week2p1/horse.mp3">MP3</a>
17.     format.
18.   </audio>
19. </body>
20. </html>

In this example, just as for the <video> element, we used the controls attribute in order to render the play/stop, time, volume and progress widgets.

Notice the other similarities: between the <audio>...</audio> tags, we added a text message that is displayed if the Web browser doesn't support the <audio> element, and we used several <source>...</source> elements that link to different audio formats for the same file. The browser will use the first format it recognizes.

Lines 13-17:  we suggest downloading the audio files if the browser does not support the <audio> element. This is also a best practice!

3.3.2 Audio and video player JavaScript API (9:05)

Live coding transcript: the video element JavaScript API

CodePen: JavaScript API.
CodePen: JavaScript API.

Today, let's have a look at some APIs. An API is a set of functions you can use from your JavaScript code.

Audio/Video player JavaScript API's.

One of them is the audio and video player JavaScript API that will give you the possibility to control a video player from JavaScript, making your own custom video player.

Adding video player to HTML document.

Let's look at one small example. I prepared, here, an HTML document with a video player. In order to include a video player in your document, just use the video HTML5 tag: video... slash video. You indicate with the source tag the URL of the video file that will be streamed into your document. And in order to maximize the compatibility with old browsers, it's recommended to propose the video in different formats. Here, I've got a video file named video.webm, video.ogg, and video.mp4, that is available in different formats.

And when you include a video element with some sources in your HTML document, the browser will ask the remote server and get the video format it prefers. You don't have to wonder which one is the best, your browser will choose.

Audio control overlapping image.

If I click on the video player, you see that... Ok! By adding a controls attribute it will display a control bar with buttons for play, pause... for adjusting the volume... for going forward and backward video and so on. And if I remove this, you don't have anymore the control, bar so you can make you own control bar for the video player. Let's try it!

I'm going just to add a "play" button. A good way to do this is do use the "onclick" event listener and I will call a function named "playVideo()" that will be located in the JavaScript part of my application. The button will call "playVideo()" and I prepared this function in the JavaScript part: playVideo(). In order to control the video player you must get a reference on it. We used the "querySelector()" method we saw earlier in module 2. We're going to do the same thing. And do you remember that we can access elements from the DOM... you can get references on the HTML elements only when the DOM is ready and when the page have be loaded.

We use "window.onload = init" with an init callback that will executed only when the DOM is ready, and inside this function, we will get a reference to the video player.

Window onload initialize with video player.

Let's write it. And I will declare this reference as a global variable. Like this. When I click on the button, I will use the JavaScript API of this object -this video player- and I can call "vid.play()". I click on the button and it plays the video. How can you guess the names of the all the methods you can use?

Video controls in API.

Go to the course, and in the section about the audio and video player JavaScript APIs you got this picture here, that is a link to the W3C specifications. And here you can interactively try the different methods. And the names on the buttons are the names of the different methods you can call when you see parenthesis: play(), pause()...

Example, video controls in API.

And also you've got properties, these properties you can... you can use them for getting information -what is the current time?- for example. Or you can use them also for setting, changing their values. And for example, going back... if I say current time equals 0, or "currentTime +=10", I'm advancing 10 seconds in the video. Some properties are read only or read and write. You also have events... so you can listen to events while the video is being played. And for example, for synchronizing some contents on the page, for detecting when the video is ended.

The "ended" event here, you can see it and so that you can play another video and do some play lists with the videos that are changed: when one is finished, the other starts and so on.

Add play and pause buttons.

Let's go back our example, and we will just implement the "pause" functionality. And we will add a "pause" button. Now I can play the video and I can pause it.

Add rewind button.

If I want to rewind to the beginning...; let's try again! And in order to do this, instead of calling a method...;we will just use the "currentTime" property and set it to 0. Remember from this document, you see the "currentTime" here, it's a property of the video player object.

Test example, rewind currentTime.

Let's try it, play! Rewind! We start again from zero, and so on. If you want to display the "currentTime" while this video is still played. You can add an event listener on the video element "ontimeupdate = isplayTimeWhileVideoIsPlaying()".

Ok, like this: while the video is being played, this method will be called and we can here, for example, display the currentTime... console.log(). Let's me open the console, play the video and you see the current time. You can make a test: if "vid. currentTime greater than 5 seconds", then we pause the video.

Let's try it. Then for example, you can ask a question, making a quiz related to the video, and so on. Ok, this was just to show you some basics of using the JavaScript API of media elements such as the video audio player.

Source code of the example from the lesson:
Audio and video player JavaScript API
Control <audio> and <video> elements from JavaScript

The <video> element has methods, properties/attributes and events that can be manipulated with JavaScript. Using the DOM API it's possible to manipulate an audio or video element as a JavaScript object that has:

Like any HTML element, the <video> element can be manipulated/created using the DOM JavaScript API. Here is an example of programmatically creating a <video> element:

1.  var video = document.createElement('video');
2.  video.src = 'video.mp4';
3.  video.controls = true;
4.  document.body.appendChild(video);

This will create a complete video player for the file "video.mp4", with control buttons, and will add it to the <body> element of the page.

JavaScript API of the <audio> and <video> elements

The JavaScript API gives you powerful tools to manipulate the <video> element, as the video object provides many properties, methods and events.

The complete list of events can be found in the  HTML5 living standard specification.

The list of properties can be found at the  W3C HTML5 Video Events and API page. This page is interesting for Web developers because it shows an interactive view of the different values and events changing over time while the video is playing within the page.

Try that direct link, play with the different buttons and look at the table of events and properties that will change in real time. The displayed names show the properties, events, and methods from the API.

Table: most interesting methods, properties and events.
Here is a table that shows the most interesting methods, properties, and events provided by the <video> element API

We provide this as a quick reminder - keep in mind that the  complete list is much longer!

How to use media properties, methods and events.

Now let's take a look at a set of examples demonstrating how to use the most important of these properties, methods, and events...;

3.3.3 Examples using the JavaScript API

The JavaScript API is useful for implementing playlists, making custom user interfaces and many other interesting things. The "enhanced HTML5 multimedia players" lesson presented further on in the courses relies heavily on this API.

Example #1: how to use external buttons to control the player's behavior

This example gives the first steps towards writing a custom video player. It shows basic usage of the JavaScript API for adding custom buttons to play/pause the video or to go back to the beginning by setting the currentTime property to zero.

Try it online:
CodePen: example media API.
CodePen: example media API.
Example, custom controls.
Source Code extract:
Source Code:
1.  <video id="vid" controls>
2.  <source src=https://mainline.i3s.unice.fr/mooc/samuraiPizzacat.webm
3.  type=video/webm>
4.  ...;
5.  </video>
6.  <p>Example of custom controls:</p>
7.  <button onclick="playVideo();" style="cursor: pointer;">Play</button>
8.  
9.  <button onclick="pauseVideo();" style="cursor: pointer;">Pause</button>
10. 
11. <button onclick="rewindVideo();" style="cursor: pointer;">
12. Back to beginning</button>
13. <script>
14. vid = document.querySelector("#vid");
15. 
16. function playVideo() {
17.   vid.play();
18. }
19. function pauseVideo() {
20.   vid.pause();
21. }
22. 
23. function rewindVideo() {
24.   vid.currentTime = 0;
25. }
26. </script>
Explanations:
Example #2: how to detect the end of a video and start another one

This example listens to the ended event, and calls a callback function when the video is ended.

CodePen: listen and callback.
CodePen: listen and callback.
Source Code:
1.  <video src="video.ogv" id="myVideo">
2.  video not supported
3.  </video>
4.  
5.  <script type='text/javascript'>
6.  var vid = document.querySelector('#myVideo');
7.  vid.addEventListener('ended', playNextVideo, false);
8.  
9.  function playNextVideo(e) {
10. // Whatever you want to do after the event, change the src attribute
11. // of the video element, for example, in order to play another video.
12. }
13. </script>
Example #3: how to manage playlists - sequential movies

This example detects the end of a video, then loads the next video, changes the src attribute of the video element and plays the video.

Check the online example below: use the progress cursor to go near the end of the first video that is being played, and see how it continues with the next video.

CodePen: progress cursor.
CodePen: progress cursor.
Source Code:
Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <meta charset="utf-8"/>
5.    <title>Sequential Movies</title>
6.    <script>
7.      var myVideo;
8.      var currentVideo = 0;
9.      var sources = [
10.     "https://mainline.i3s.unice.fr/mooc/samuraiPizzacat.mp4",
11.     "https://www.archive.org/download/AnimatedMechanicalArtPiecesAtMit/
          P1120973_512kb.mp4"
12.     ];
13. 
14.     // Set the src of the video to the next URL in the playlist.
15.     // If at the end we start again from beginning (the modulo
16.     // source.length does that).
17.     function loadNextVideo() {
18.       myVideo.src = sources[currentVideo % sources.length]
19.       myVideo.load();
20.       currentVideo++;
21.     }
22. 
23.     // listener plays the video.
24.     function loadAndplayNextVideo() {
25.       console.log("playing " + sources[currentVideo % sources.length])
26.       loadNextVideo();
27.       myVideo.play();
28. 
29.     }
30. 
31.     // Called when the page is loaded.
32.     function init(){
33.       // get the video element using the DOM api
34.       myVideo = document.querySelector("#myVideo");
35. 
36.       // Defines a callback function called each time a video ended
37.       myVideo.addEventListener('ended', loadAndplayNextVideo, false);
38. 
39.       // Loads the first video when the page is loaded.
40.       loadNextVideo();
41.     }
42.   </script>
43. </head>
44. <body onload="init()">
45.   <video id="myVideo"
46.     controls>
47.   </video>
48. </body>
49. </html>
Explanations:

3.3.4 Using the webcam

It's very easy to use the getUserMedia API for accessing the webcam.

Here is a version that should work on any recent browser except Apple Safari (which still does not support this API). Note that for security reasons you must host your HTML/CSS/JS page on an HTTPS server for getUserMedia to work.

For security reason, these examples cannot run in the course web pages. Click on "Edit on CodePen" to run them.

First version that uses callbacks (success/error, see the JS code):
CodePen: using callback, #1.
CodePen: using callback, #1.
Second version that uses a new JavaScript syntax called "promises":

This is another way of saying, "Please, browser, try to give me access to the webcam, THEN when the webcam is ready, please tell me so that I can display its stream in a <video> element. Otherwise, send me an alert". (note that we've put the alert in a comment in the CodePen below).

CodePen: using callback promise, #2.
CodePen: using callback promise, #2.

3.3.5 Extended examples

In this section, we propose five extended examples that use more JavaScript and more complex CSS manipulation. They might be a little hard to understand if you are a JavaScript beginner, but don't be afraid to try and test them, look at the code, etc.

Some examples are given "as is", such as the custom video player that uses SVG (at the end of the page); if you are interested, you may view the code.

Example #1: a player showing the use of every type of CSS3 transformation

Please see this example online, originally written by Chris Heilmann, and tuned by us ;).

CodePen: example CSS3 transformation.
CodePen: example CSS3 transformation.

Don't forget to click the JavaScript and CSS tabs of the CodePen in order to display the JavaScript code that creates the buttons on the right of the video, and the CSS that processes the different clicks and applies CSS3 transforms.

This example shows a lot:

Example #2: how to track all possible events and manipulate many properties

This example also shows how to handle failures. See the code and play with this example below:

CodePen: handling events for the video element.
CodePen: example events for the video element.

Below is a piece of code for handling errors during video playback:

Source Code:
1.  ...
2.  
3.  vid.addEventListener('error', function(evt) {
4.    logEvent(evt,'red');
5.  }, false);
6.  
7.  ...
8.  
9.  function logEvent(evt, color) {
10.   switch (evt.type) {
11.     ...;
12.     case 'error':
13.     var error = document.querySelector('video').error;
14. 
15.     switch (error.code) {
16.       case error.MEDIA_ERR_ABORTED:
17.       note.innerHTML = "fetching aborted at the user's request";
18.       break;
19.       case error.MEDIA_ERR_NETWORK:
20.       note.innerHTML = "a network error caused the browser to stop
            fetching the media";
21.       break;
22.       case error.MEDIA_ERR_DECODE:
23.       note.innerHTML = "an error occurred while decoding the media";
24.       break;
25.       case error.MEDIA_ERR_SRC_NOT_SUPPORTED:
26.       note.innerHTML = "the media indicated by the src
27.       attribute was not suitable";
28.       break;
29.       default:
30.       note.innerHTML = "an error occurred";
31.       break;
32.     }
33.     break;
34.   }
35.   ...
36. }
Example #3: how to display a percentage of buffering when using a slow connection

Check the example below:

CodePen: check progress of buffering.
CodePen: example check progress of buffering.

Note that on mobile phones, the video does not start until the user presses the play control or clicks on the video picture. Using the "canplaythrough" event is a trick to call a function that starts the video player as soon as the page is loaded on a desktop computer. This event is not supported by mobile devices, so if you try this example on a mobile, the video will not start automatically.

As explained by the  Apple Developer Web site: "The buffered property is a TimeRanges object: an array of start and stop times, not a single value. Consider what happens if the person watching the media uses the time scrubber to jump forward to a point in the movie that hasn't loaded yet---the movie stops loading and jumps forward to the new point in time, then starts buffering again from there. The buffered property can contain an array of discontinuous ranges. The example simply seeks the end of the array and reads the last value, so it actually shows the percentage into the movie duration for which there is data. "

Source Code extract:
Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <title>JavaScript Progress Monitor</title>
5.    <meta charset="utf-8"/>
6.    <script>
7.      function getPercentProg() {
8.        var myVideo = document.getElementsByTagName('video')[0];
9.        var endBuf = myVideo.buffered.end(0);
10.       var soFar = parseInt(((endBuf / myVideo.duration) ) 100));
11.       document.getElementById("loadStatus").innerHTML = soFar + '%';
12.     }
13. 
14.     // Will be called as soon as the page is ready on desktop computer,
15.     // only when a user clicks on play control or image on mobile.
16.     function myAutoPlay() {
17.       var myVideo = document.getElementsByTagName('video')[0];
18.       myVideo.play();
19.     }
20. 
21.     function addMyListeners(){
22.       var myVideo = document.getElementsByTagName('video')[0];
23.       myVideo.addEventListener('progress', getPercentProg, false);
24. 
25.       // Calls autoplay only if the device is adapted.
26.       myVideo.addEventListener('canplaythrough', myAutoPlay, false);
27.     }
28.   </script>
29. </head>
30. <body onload="addMyListeners()">
31.   <h1>Check progression of buffering before playing a movie. Useful
      with
32.   slow connections (3G, etc.)</h1>
33.   <div>
34.     <video controls>
35.       <source src=https://html5doctor.com/demos/video-canvas-magic/video.webm
36.       type=video/webm>
37.         <source src=https://html5doctor.com/demos/video-canvas-magic/video.ogg
38.         type=video/ogg>
39.         <source src=https://html5doctor.com/demos/video-canvas-magic/video.mp4
40.       type=video/mp4>
41.     </video>
42.     <p id="loadStatus">Buffering)</p>
43.   </div>
44. </body>
45. </html>

Example #4: how to use SVG elements as external controllers

This is the ultimate way of doing a real custom player: redesign your own controls using SVG shapes! This example (try it online) is given "as is" for those of you who may be curious.

Example #5: a custom video player written by a previous student

This is more an example than a tutorial. Maurice, a student who followed the precursor version of this MOOC, had the assignment to write a custom video player with playlist, video thumbnails, custom play/pause/next/previous/volume controls, and present it in a Web page that used a nice layout based on the HTML5 structuring elements studied previously.

Here is the online example. We recommend that you look at the source code:

CodePen: custom video player.
CodePen example custom video player.

3.3.6 Discussion and projects

Please either post your comments/observations/questions or share your creations.

Suggested topics
Optional projects
Project #1: a custom video player

Here are a few ideas to play with the material learned in this section. Your classmates and the team who prepared the course will be happy to look at them and give feedback. Please post URLs of your work in this discussion forum. These projects are optional, meaning that they won't be graded.

Try to write a video  player with a few custom buttons for play/stop/etc. When your custom player is done, please add a way to play several videos one after another (what we call a playlist), etc.

See this example created by a student in one of an earlier earlier version of this MOOC:  custom player with nice CSS and buttons

Project #2: a video quiz!

Media Player logo.

Create a quiz based on videos - here is a proposed story telling:

A few hints:
  1. Use an array with stop times, for example let stopTimes = [5, 10, 20]. This will mean "the video should stop at currentTime = 5, currentTime = 10, currentTime = 20".
  2. You will use a timeupdate event listener on the video, like in the example from the live coding video, and the pause, play and stop methods from the video element JavaScript API. And also an ended event listener for detecting the end of the video.
  3. Start from one of the example in the course (the one from the live coding video): try to make the video stop at 5s ,for example, and then display a question, and a "continue" button. When the button is pressed, the video goes on and stops a bit further, etc.
  4. When this works (the video plays, then stops, you click, it continues, etc.), try to turn the displayed sentence into a quiz: add HTML radio buttons, and when you click the continue button, you will validate the answer, show "correct" or "incorrect", and maybe increment the score.
  5. Feel free to add any feature(s) you'd like.

As always, do not forget to post the URL of your work in the forum so that we can enjoy your creation. Michel will inevitably give you his advice(s), and also tell you that you are the best ;))

Use the discussion forum below!

3.4.1 The Geolocation API

This chapter presents the new Geolocation API and illustrates its use with several examples.

Geolocation logo.

The Geolocation HTML5 JavaScript API is implemented by most modern Web browsers, and uses different means to get the current location: GPS, GSM/3G triangulation, Wifi, IP address, etc.

It is possible to prompt the user to activate the GPS (this is what most GPS navigation software does on mobile phones), or ask for a particular mean among those available. It is also possible to track the current position when it changes. This is useful for writing a navigation application or for tracking in real time the position of different participants in the case of an application that involves several persons at the same time (using WebSockets, for example).

Browser support for the Geolocation API is excellent, both on mobile and on desktop devices.

External resources:

3.4.2 Geolocation and maps

This section presents an example of how to get an interactive map, using  the Leaflet API for OpenStreetMap, and gives links to more resources. Did you know that you can even get an estimation of a physical address from the longitude and latitude, using online Web services?

How to get a map centered on your longitude and latitude
Geolocation map.

This example is just given "as is", as there are so many possibilities for rendering a map with the Leaflet API for OpenStreetMaps. Leafletjs.com). However, we think having such a basic example might be useful.

CodePen: example click to show your location.
CodePen: example click to show your location.
Source Code extract:
HTML part:
Source Code:
1.  <html>
2.  <head>
3.    <meta charset="utf-8">
4.    <title>OpenStreetMap Example</title>
5.    <link rel="stylesheet" href="https://unpkg.com/[email protected]/dist/leaflet.css">
6.    <script src="https://unpkg.com/[email protected]/dist/leaflet.js"></script>
7.  </head>
8.  <body>
9.    <button class="btn" onclick="getLocation(event)">Click to show
        your location with OpenStreetMap</button>
10.   <div id="map" class="map"></div>
11. </body>
12. </html>
JavaScript part:
Source Code:
1.  function getLocation(e) {
2.    e.preventDefault();
3.    if (!navigator.geolocation) {
4.      alert("Browser doesn't support geolocation");
5.    } else {
6.      navigator.geolocation.getCurrentPosition(success, error);
7.    }
8.  }
9.  
10. // Get current position successfully.
11. function success(position) {
12.   var map, marker,
13.   latitude = position.coords.latitude,
14.   longitude = position.coords.longitude;
15. 
16.   // Instance map using leaflet.
17.   map = L.map('map').setView([latitude, longitude], 13);
18. 
19.   // Tile layer using key api at cloudmade.com.
20.   L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
21.     key: '760506895e284217a7442ce2efe97797',
22.     styleId: 103288,
23.     maxZoom: 16
24.   }).addTo(map);
25. 
26.   // Marker using leaflet.
27.   marker = L.marker([latitude, longitude]).addTo(map);
28. 
29.   // Popup in leaflet.
30.   marker.bindPopup('<p>Your location</p>').openPopup();
31. }
32. 
33. // Get current position fail.
34. function error() {
35.   alert('Get current position fail. Please access codepen to get geolocation.');
36. }

3.4.3 Reverse geocoding

cDifferent Web services can be used to get an address from longitude and latitude. Most are free of charge, but they will ask you to register an API key and enter your credit card number. If you send too many requests, you will be charged.Such a service is the [Google Reverse Geocoding JavaScript API](https://developers.google.com/maps/documentation/javascript/examples/geocoding-reverse). For those of you who are really interested to know how this API works, please read the Google documentation and tutorials.

There is also an interesting Leaflet plugin (an extension to Leaflet) based on the [Gisgraphy](https://www.gisgraphy.com/) (free open source framework) service, that comes with a [nice demo of reverse geocoding](https://services.gisgraphy.com/static/leaflet/index.html). Let's see some examples of use.
Example #1: how to get a physical address from the longitude and latitude

Google reverse geocoding example (screenshot only):

Mapquest: longitude and latitude.

Source code of this example (in order to run it, you need a Google API key, used at line 6).

Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <meta charset="utf-8">
5.    <title>Js bin </title>
6.    <script src="https://maps.googleapis.com/maps/api/js?key=PUT_HERE_YOUR_API_KEY&v=3.exp&sensor=false"></script>
7.    <script>
8.      // p elements for displaying lat / long and address
9.      var displayCoords, myAddress;
10. 
11.     // used with the google apis
12.     var geocoder;
13.     var map;
14.     var infowindow = new google.maps.InfoWindow();
15.     var marker;
16. 
17.     // Called when the page is loaded
18.     function init() {
19.       displayCoords=document.getElementById("msg");
20.       myAddress = document.getElementById("address");
21. 
22.       geocoder = new google.maps.Geocoder();
23. 
24.       // In order to show something even before a user clicks on the button
25.       var latlng = new google.maps.LatLng(34.0144, -6.83);
26. 
27.       var mapOptions = {
28.         zoom: 8,
29.         center: latlng,
30.         mapTypeId: 'roadmap'
31.       }
32.       map = new google.maps.Map(document.getElementById('map_canvas'), mapOptions);
33.     } // end of init()
34. 
35.     // Called when the button is clicked
36.     function getLocation() {
37.       if (navigator.geolocation) {
38.         navigator.geolocation.getCurrentPosition(showPosition);
39.       } else {
40.         displayCoords.innerHTML="Geolocation API not supported by your browser.";
41.       }
42.     }
43. 
44.     // Called when a position is available
45.     function showPosition(position) {
46.       displayCoords.innerHTML="Latitude: " + position.coords.latitude +
47.       "<br />Longitude: " + position.coords.longitude;
48. 
49.       // Display the map
50.       showOnGoogleMap(new google.maps.LatLng(position.coords.latitude,
51.       position.coords.longitude));
52.     }
53.     function showOnGoogleMap(latlng) {
54.       // Ask google geocoder for an address once we get a longitude and
55.       // a latitude. In fact, the reverse geocoder sends back an array of "guesses"
56.       // i.e. not just one address object, but several. Each entry in this array
57.       // has several properties such as street, city, etc. We use the "formatted_address"
58.       // one here, but it might be interesting to get the detailed properties in other
59.       // applications like a form with street, city, zip code etc.
60.       geocoder.geocode({'latLng': latlng},reverseGeocoderSuccess);
61. 
62.       function reverseGeocoderSuccess(results, status) {
63.         if (status == google.maps.GeocoderStatus.OK) {
64.           if (results[1]) {
65.             map.setZoom(11);
66.             marker = new google.maps.Marker({
67.               position: latlng,
68.               map: map
69.             });
70.             infowindow.setContent(results[1].formatted_address);
71.             infowindow.open(map, marker);
72. 
73.             // Display address as text in the page
74.             myAddress.innerHTML="Adress: " + results[0].formatted_address;
75.           } else {
76.           alert('No surface address found');
77.           }
78.         } else {
79.           alert('Geocoder failed due to: ' + status);
80.         }
81.       } // end of reverseGeocoderSuccess
82.     } // end of showOnGoogleMap
83.   </script>
84. </head>
85. <body onload="init()">
86.   <title>HTML5 + Geolocalisation + Google Maps API Reverse Geocoding</title>
87. 
88.   <p id="msg">Click the button to get your coordinates:</p>
89.   <p id="address"></p>
90. 
91.   <button onclick="getLocation()">Where am I ?</button>
92.   <div id="map_canvas" style="width: 500px; height: 300px"></div>
93. </body>
94. </html>

Gisgraphy (free service) reverse geocoding example (screenshot only, click on it to see the demo on the Gisgraphy website):

Example #2: reverse geocoding + OpenStreetMap

Important note: these examples below rely on an external  GitHub resource. No related questions are asked in this module's exercises or final exam.

Please, pan and zoom on the map and click. The longitude and latitude are computed from your click and a free reverse geocoding service is used to convert to a physical address.

CodePen: Longitude and Latitude.
CodePen: Longitude and Latitude.
Example #3: shows the address on the map, from your current longitude and latitude

Click on the Codepen logo on the top right to open  the example in Codepen. Due to security reasons, it cannot run embedded in this page.

CodePen: Leaflet control reverse geocoder.
CodePen: Leaflet control reverse geocoder>.
Example #4: use of geolocation, map and reverse geocoder in an HTML form

This is just a variation of the previous examples. We embedded the interactive map in a form, and we display the results of the reverse geocoder in a form field. This example might be useful if you want to pre-fill the address of a registration form, depending on the current location of the person who is registering.

Click on the Codepen logo (on the top right) to run the  online example (for security reasons the embedded version cannot run in this page):

CodePen: example reverse geocoder, again.
CodePen: Leaflet control reverse geocoder>.

3.4.4 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics

Devtool console geolocation simulation.

Optional projects

3.5.1 Background music (streamed)

Warning about the autoplay policy

Since 2018, most browsers have adopted  the Autoplay Policy that prevents any Web page to start making music or playing sounds without a user interaction.

For a user, it means that most examples from this course won't make sounds until you interact with the application (i.e. clicking on the canvas for the game example). For a developer, if you use libraries such as Howler.js, there are good chances that you won't have to change your code. If you are programming with  the WebAudio API, then you'll need to resume the AudioContext after the first user interaction.

Background music (streamed)

In a previous section, we saw how we can add music to our Web page, using the <audio></audio> element. We can even hide its GUI and control the play/pause of the music from JavaScript. Streaming music is perfect for providing a background atmosphere in a video game.

Here is one simple example of background music control from JavaScript:
CodePen: background music control.
CodePen: background music control.

3.5.2 Sound effects using howler.js (4:10)

Live coding lesson: using sound samples
Sound effects using howler.js.

The same way we made the small custom video player, you can also use the audio HTML element that is similar in its use to the video HTML element, for adding to your page an audio player.

Play/pause video and audio.

Here, the audio is streamed from a remote server, the same way with the video element, a video movie is streamed from a remote server.

If you want to add background music to your game, you can use the audio player, but of course you will want to hide completely the buttons. If I remove the controls attribute. Then, I can completely hide the player.

Play/pause, #2.

Here, I kept some buttons for playing music or pausing it. But you saw that you can start playing the music from JavaScript. You can also) directly start the music when the page is loaded. The same way I use the video player, I declare an audio player, here.

Play/pause, #3.

And in JavaScript, I've got my button onclick="play()" that will call a play function, that will get a reference on the player.

Play/pause, #4.

This is the id of the player. You can see it here. And I'm calling the play and pause methods to play and pause the music.

Play sound sample #1.

For sound effects, that will have to be played very fast,) that last a very short time. It's better to load the sounds in memory and then play them. There are small sounds samples that are loaded and decoded and kept in memory for a very fast use within video games. It's a bit complicated to use the low level WebAudio API. Some developers made some high level libraries for making this task easier. One of them is called howler.js.

Audio library howler.js.

This is the Web site --- howler.js "Make working with audio in JavaScript easy". You can read the documentations and look at samples here. The way we used it, is that we've just including it using a script tag.

Play sound sample 1.

This is the inclusion of a minified, a very short version of this library. And then from JavaScript, you can use it.

Play sound sample 1, #2.

Here we've got a button that will play a very short sound... you see. Let's look at the way the play sound is implemented.

Play sound sample 1, #3.

The play sound function just does "sound.play();", but the sound we are referring to, here, has been loaded when the page was ready.

Play sound sample 1, #4.

So "window.onload = init;"... You saw that many times now. From then, we use the Howl library like this. "new Howl": you indicate the URL of your audio file and you've got a callback. A callback is a function that will be executed when the sound has been loaded and decoded. What we do here, is that, by declaring "sound=new Howl", we ask the Howl library to load and decode the sound.

Then, it tells us when the sound is ready to be used and in that case, we enable the button that is greyed and not clickable by default.

Howler.js for using sound samples in memory.

If you want to play short sounds that can occur very rapidly, streamed sound/music is not a good solution. This is where the WebAudio API, made by W3C and implemented by your browser, comes in handy. This API allows you to download and decode sound samples in memory, and play them on demand, using nearly zero CPU and with no delay when you play the sound (no buffering etc.).

However, this API is a bit complicated to use for beginners. Fortunately there are several JavaScript libraries that simplify the use of the WebAudio API.  HowlerJS is one of these.

Example that uses Howler.js to load a sound sample from a remote server, then decode it in memory, and play it:
Play sound sample 1.
CodePen: load sound sample using howlerjs.
HTML code: this is how we say that we are using an external library:
Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <script src="https://cdnjs.cloudflare.com/ajax/libs/howler/1.1.28/howler.min.js"></script>
5.    <title>Simple example that uses howler.js for playing sound
      samples</title>
6.    <meta charset="utf-8">
7.  </head>
8.  <body>
9.    <p>Turn volume 1. As soon as the button becomes enabled, that
      means that the sound sample
10.   has been downloaded and decoded in memory. It can now be played.
      Click on the button to play
11.   this sound. Click it rapidly: you see, it's ok for a game!</p>
12.   <button onclick="playSound();" id="button1" disabled>Play
      sound sample 1</button>
13. </body>
14. </html>
JavaScript code:
Source Code:
1.  window.onload = init;
2.  var sound;
3.  function init() {
4.    var button = document.querySelector("#button1");
5.    sound = new Howl({
6.      urls: [   'https://)/assets/sounds/plop.mp3'],
7.      onload: function () {
8.        console.log("Loaded asset ");
9.        button.disabled = false; // enable the play sound button
10.     }
11.   });
12. }
13. function playSound() {
14.   sound.play();
15. }

The important part is located in lines 5-9: the Howler library is to be used like this: sound = new Howl({...}); The part between the { and } is an object. The url's property is an array with at least one element: the URL of the sound we want to use, located on remote servers. The call to new Howl({...}); will start downloading the sound in background, then, once it has loaded, it will "decode it" (i.e., an mp3 file will use some cpu to be decoded on the fly and played, whereas a decoded sound will use nearly zero cpu, which makes it good for games!).

Finally, once the sound is decoded, the onload callback is executed. In other words, the function after onload: will be executed (at lines 7-9). In this callback, we enable the button because the sound is ready to be played.

The playSound function can only be called when the button is enabled (when the sound sample has been loaded and decoded). In order to play a sound loaded by Howler.JS, we just call the play() method (line14).

3.5.3 Adding music and sound effects

Here is the last version of the game from Module 2 with music and sound effects (when the player eats a ball):

CodePen: music and sound effects.
CodePen: adding music and sound effects.

Look at the HTML part: we included the Howler.js library and we also added an <audio> player (invisible; we removed the controls attribute) for background music.

In the JavaScript code, we start the background music as soon as the page is loaded.

We then used HowlerJS to load a sound sample in background. Only once this sample has been loaded and decoded do we start the animation.

3.5.4 [Advanced] a multiple image, sound and music loader (3:47)

Live coding transcript: a multiple image, sound and music loader
Multiple image, sound and music loader.

I prepared for you) more for advanced users) a multiple image, sound and music loader.

It's a function that you will call) that will load in background, for you, images, sound samples and also deal with streamed music. And when everything is ready, it will call a function of your own that will start the game.

Winter season game; background URLs for image and sounds.

Like this, when the game starts, all images, musics and sounds are ready to go. Let's have a look at it. Here is how it looks like. You define an object called "assetsToLoadURLs" and you indicate the names of the musics, of the sound samples or of the images you want to load, and you indicate their URLs. So "backgroundImage" it's a PNG, logo it's a PNG, "plop" it's a MP3.

Assets loaded for winter game.

And you can also indicate if it's going to be streamed or loaded and decoded in memory for fast access. You can indicate if it's gonna loop, start again at the end. You can indicate the volume) and it will do everything for you. You can indicate background music with "buffer: true", "loop: true". This is a background music will be looped in the background. How do you load all these assets?

loadAssets() function call.

You use the "loadAssets()" function that is provided at this end of this source file but you don't have to look at the details. You don't have to understand in details how it works. Here, in the init() function called when the page is loaded, we display the "Loading assets" ) "Loading assets" message. Then we call "loadAssets()" and we pass the name of the function that will really start the game.

Start animation, drawing, music, etc.

This is where you will start animation, drawing, playing music and so on. And this "loadAssets()" function will use this "assetsToLoadURLs" object we talked earlier.

startGame() function.

Look in the "startGame()" function we're going to use this now. And how are we going to use this for playing music for example?

setInterval on sound effects.

"playHumbug()". You see. The music is just called by its name. "LoadedAssets" the object of the top of the file ".humbug" the name of the music ".play()".

For playing some sound samples, here we are going to play a "plop" sound sample every 1000 milliseconds) every second.

loadAssets.plop.play.

We just do "LoadedAssets.plop.play()" you see the name "plop" comes from here. Instead of using "assetsToLoadURLs" now we are using "LoadedAssets".plop because the "LoadedAssets" will initialize this object here, this variable with the decoded sound samples, with the loaded images and so on.

I hope you will find this useful if you are planning to write a small HTML5 game with lots of JavaScript.

A utility background loader for images, music and sound samples

This comes from the module 2 of the W3Cx  HTML5 Apps and Games course.

In video games, you very often need to load assets before starting the game:

We wrote a multiple "asset loader" to make all these tasks easy.

Here is a small example that you may use if you like, which takes an array of "assets to be loaded", that can be either an image, a sound sample or streamed background music. You call the loadAssets(callback) function, passing as a parameter a single callback function of yours. When all assets are loaded, your callback will be executed, and will get a single parameter: the assets ready to be used!

Example (to hear the music and sound sample, there are two lines to uncomment in the startGame(...) function):

CodePen: load music and sound.
CodePen: load music and sound sample.
Extract from the JavaScript source code:
Source Code:
1.  window.onload = init;
2.
3.
4.  var assetsToLoadURLs = {
5.    backgroundImage: { url: 'https://)/assets/images/background.png' }, 
6.    logo1: { url: "https://)/assets/images/SkywardWithoutBalls.png" },
7.    logo2: { url: "https://)/assets/images/BoundsWithoutBalls.png" },
8.    bell:  { url: "https://)/assets/images/bells.png" },
9.    spriteSheetBunny: { url: 'https://)/assets/images/bunnySpriteSheet.png' },
10.   plop: { url: 'https://)/assets/sounds/plop.mp3',
11.           buffer: false, loop: false, volume: 1.0 },
12.   humbug: { url: 'https://)/assets/sounds/humbug.mp3',
13.             buffer: true, loop: true, volume: 1.0 },
14.   concertino: { url: 'https://)/assets/sounds/christmas_concertino.mp3',
15.                 buffer: true, loop: true, volume: 1.0 },
16.   xmas: { url: 'https://)/assets/sounds/xmas.mp3',
17.           buffer: true, loop: true, volume: 0.6 }
18. };
Source Code:
1.  var loadedAssets; // above assets, ready to be used
2.
3.  function init() {
4.    // Once the page is loaded, we load all assets. We pass the function
5.    // that will be called when assets are ready. In our case "startGame"
6.    // this call will load all assets
7.    loadAssets(startGame);
8.  }
9.
10. function startGame(assetsReadyToBeUsed) {
11.   // This function is executed once all assets are ready.
12.   // It is called by the asset loader, and receives as a unique
13.   // parameter, the assets (sounds, images etc.) ready to be used
14.   // we store them in the loadedAssets variable
15.   loadedAssets = assetsReadyToBeUsed;
16.
17.   // Now we can use them! e.g., draw the images in a canvas
18.   drawImages();
19.
20.   // or play one of the pieces of background music
21.   playHumbug();
22.
23.   // Or use sound samples, for example let's play a plop every second
24.   setInterval(playPlop, 1000);
25. }
26.
27. function playHumbug() {
28.   loadedAssets.humbug.play();
29. }
30.
31. function playPlop() {
32.   loadedAssets.plop.play();
33. }
34.
35. function drawImages() {
36.   var canvas = document.querySelector('#myCanvas');
37.   var ctx = canvas.getContext('2d');
38.
39.   // background image drawImage can have different syntaxes :
40.   // drawImage(img, x, y); or
41.   // drawImage(x, y, width, height),
42.   // for other syntaxes see HTML5 fundamentals course
43.   ctx.drawImage(loadedAssets.backgroundImage,
44.                 0, 0,
45.                 canvas.width, canvas.height);
46.
47.   ctx.drawImage(loadedAssets.bell, 20, 20);
48.
49.   ctx.drawImage(loadedAssets.spriteSheetBunny, 190, 0);
50. }

Two games that have been written by students in the W3C Apps and Games course (which has a module dedicated to game programming):

These games are not for JavaScript beginners, but it's time to spend some time having fun :-) You can look at the source code: it's been written by students like you who followed the HTML5 advanced course.

  1. Star Warriors, written by two Ukrainian ladies who won the first prize in a W3C contest we organized in March 2017:
Star Warrior, an HTML5 games that uses the multiple asset loader.
  1. Skyward Bounds: written in less than a week by a group of students from the HTML5 Apps and Games course, during the Christmas 2016 session.

Michel Buffa helped them actively in the forum, and one student rapidly took the lead in developing the game, while another composed the music, another helped with the graphics, etc.

The game runs on phones, tablets (using touch events), can be resized, rotated, etc. It also uses the multiple asset loader presented.

Audio music.

3.5.5 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Headphones logo.

Suggested topics

Optional projects

4.1.1 Video introduction - Module 4 (1:53)

Video
CodePen: JavaScript objects.

This module is about JavaScript objects.

So far, we've only scratched the surface! And it's time to get into detail. As with many other programming languages, JavaScript objects can be compared to real-life objects. A JavaScript object is an entity with a type and properties that define its characteristics. It also comes with special functions associated to it called methods.

CodePen: from objects to arrays.

Let's take the example of these bottles and this candle. They are different kind of objects, different type of objects. But they also have a color, they also have a weight and they have a material. This candle is made of wax and this bottle is made of glass. The properties define the objects' characteristics, they are the DNA. But they also have a behavior: a bottle can be filled with water or can be emptied. A candle can be lighted on or lighted off. These behaviors are usually implemented, using some particular functions that are tied to the object definition, and we call them "methods".

You'll learn how to create your own classes and how to create to multiples objects from the same class. Furthermore, JavaScript comes with a set of predefined objects, standard objects such as Math, Array, Date, and so on. And it is important for you to know how to use them.

Finally, as usual, we will provide many examples and some optional projects at the end of module.

4.1.2 Module 4 outline

In Module 4, we continue exploring JavaScript Object Oriented Programming:

Finally, you will use these new concepts for improving the small game we started to develop in Module 2!

4.2.1 Introduction

You're already familiar with the concept of objects, but so far we've only seen one simple form, called "objects literals" or "singleton objects". I think we've referred to them as "simple objects" in the course. Here is an example:

1.  var js1 = {
2.    courseName: 'JavaScript intro',
3.    weeks: 5,
4.    madeBy: 'W3Cx',
5.    author: 'Michel Buffa' // no "," after the last property!, even
        if ES5/6 accept it
6.  }
And we access properties values using the "." operator, like this:
1.  js1.author
2.  "Michel Buffa"
3.  
4.  js1.weeks
5.  5

However, we haven't explained 90% of what is going on, and what we can do with "objects". Our objective in this module, is to explain the most important features of objects, while keeping it simple (more advanced topics will be taught in a future "JavaScript Advanced" course, such as prototypes, context binding, etc.).

Features you will learn:

4.2.2 From objects to arrays (6:33)

Live coding transcript: object's properties
From objects to arrays.

This module is about JavaScript object oriented programming. In other words, we'll talk a lot about JavaScript objects.

This first video, we will focus on JavaScript object properties. The properties are these small parts in the object description that describe the object's characteristics. So far, we mainly saw what we call "object literals" or "singleton objects".

They're objects that use this syntax: you use the "let" or the "var" keyword followed by the name of the object, by braces, and between braces you've got some pairs: property name, columns and property value.

In order to access the properties, you use the name of object: js1. You use the '.' operator followed by the name of the properties. js1.weeks will display the value of the week's properties for the object js1: "the JavaScript 1 course lasts 5 weeks". You can also access other properties like author: "Michel Buffa".

CodePen: object: js1.

Then let's have a look at some arrays. Here, we've got an array named "darkVador1asAnArray" and you can access the different elements of an array, using brackets followed by the index, "0" being the first element.

So "darkVador1asAnArray[0]" will display "villain". That is the value of the first element. If you look at "darkVadorAsAnObject", in that case we use the '.' operator and the name of the property: job.

If you look at the two notations, the one with the array and the one with a property name and the '.' operator, they look rather similar. And if you look at the type of the "darkVador1asAnArray" variable, it's an object. In fact, objects declared with braces and pairs of property and name are very very similar to arrays because arrays are objects too.

Brackets and '.' operator.

If I use the name of the property with the brackets notation, look at that: darkVadorAsAnObject[], the name of the property (job) then... you've got the exact same result as if you're using the '.' operator. In JavaScript objects are arrays whose indexes are the property names. They are very very similar.

Book.title, '.' notation.

Look at this object named "book": book.title ... Le Petit Prince and book['title'] will give exactly the same result. Why would you use this notation for accessing properties?

It's because in some cases you can have property names that include spaces or that start with a number.

Example, index.

For example, if I write this: book['1stPublication'] as an index, it works. And if I type the object book, I can see that I defined the property that is named "1stPublication.

Dot '.' notation.

But if I use the '.' notation, and if I try to set this property, it's invalid because the property name when used with the '.' notation cannot start with a number. It's the same if we've got property names that contain spaces like 'date of publication'. I can define a property that has spaces in its name using brackets but not using the '.' notation.

The bracket notation can also be useful when you've got the name of the property in a variable. For example, I've got in the variable named "key", the "title" property name. And I want to access "book.title", except that in that case the name of the property is the value of the "key" variable.

Object can contain object.

I type key ="name" ... "book2" that is an object with the name. I can type "book2.key3", it's exactly the same as typing "book2.name". You can also have objects that contain objects. The "book2" object, here, has the property name author that in turn is an object. It uses brackets and a pair of property values. In that case, you can chain the '.' operator to access the sub-properties. "book2.author" is an object, "book2.author.familyName" will access the "familyName" property of the author object that is a property of "book2". And it gives "heller" here.

Source code of the example in the above lesson

Source code is available on CodePen.

From objects to arrays
In Javascript, an object = a table whose keys/indexes are defined!

Important note: Darth Vader is called "Dark Vador" in the French versions of Star Wars, and, as a French tutor, I think it's cool to give to one of the heroes an international name. :-)

Look at this array:
Source Code:
1.  > var darkVador = ['villain', 'half human half machine'];
2.  Undefined
3.  
4.  > darkVador[0]
5.  "villain"
6.  
7.  > darkVador[1]
8.  "half human half machine"

And now, look at this object:

1.  var darkVador = {
2.    job: 'villain',
3.    race: 'half human half machine'
4.  };

They look a bit similar, don't they?

It is possible to access the object's properties with "." or with brackets

We saw that we can use the "." operator, followed by the property name. It's also possible to use the bracket notation, and manipulate the object as an array whose indexes, instead of being 0, 1, 2 etc., are the property names!

Source Code:
1.  > var book = {
2.    title: 'Le Petit Prince',
3.    author: 'Saint-Exupery'
4.  };
5.  Undefined
6.  
7.  > var title = book.title;
8.  undefined
9.  
10. > title;
11. "Le Petit Prince"
12. 
13. > var title = book['title'];
14. undefined
15. 
16. > title
17. "Le Petit Prince";
18. 
19. > var author = book['author'];
20. undefined
21. 
22. > author;
23. "Saint-Exupery"

As you can see, if you look at lines 7-10 and 13-16, writing book.title or book['title'] is equivalent!

In JavaScript, objects are arrays whose indexes are property names: please remember this!

4.2.3 Property declaration syntax

Property names: different possibilities

We can put single or double quotes around the name of the property, or nothing at all:

1.  var louis = {age: 40}; // WE DO THIS MOST OF THE TIME!
2.  var louis = {"age": 40};
3.  var louis = {'age': 40};
In some cases we have to put quotes around the property name
Examples:
1.  book.1stPublication = '6 April 1943'; // begins with a number
                                                    // Throws a SyntaxError
2.  book['1stPublication'] = '6 April 1943'; // OK
3.  
4.  book.date of publication = '6 April 1943'; // spaces not allowed!
5.  book['date of publication'] = '6 April 1943'; 
                                                        // allowed, but avoid!

Another classic case where the name of a property is in a variable

In this case it is necessary  to use the syntax with '[' and ']' ...

Example:
1.  var key = 'title';
2.  undefined
3.   
4.  book[key];
5.  "Le Petit Prince"

4.2.4 An object can contain another object

Example:
Source Code:
1.  > var book = {
2.    name: 'Catch-22',
3.    published: 1961,
4.    author: {                 // embedded object!
5.      givenName: 'Joseph',
6.      familyName: 'Heller'
7.    }
8.  };
9.  Undefined
10. 
11. > book.author.givenName;
12. "Joseph"
13. 
14. > book.author.familyName;
15. "Heller"
Pile of books logo.

Accessing the embedded object author is done by chaining property accesses using the "." operator, like in book.author.givenName (here we access the givenName property of the object author, which is also a property of the book object).

4.2.5 Elements, properties and methods (6:37)

Live coding transcript: object methods

Object methods and 'this'.

In this lesson, we will talk about objects' methods and about the "this" keyword that is very useful when using methods that will access properties inside an object, or methods that will call other methods.

For arrays, we speak of elements but for objects, we talk about properties. But we can also have some functions that will be assigned to properties and a property that is equal to a function is called: a method.

With objects, properties correspond to characteristics of objects, to their DNA, while methods will correspond to the behavior of the objects. If you've got a dog, we can call a method named "bark". It will mean: hey Medor (the dog's name), please bark!

If you've got a person -an object person- with a method named describeYourself, it's like if you are talking to the person: person.describeYourself(), you are calling the method describeYourself on the object person, you are talking to the person and you expect a behavior. It will describe itself.

Test, example object 'medor'.

Let's have a look at some examples. so here we've got an object named "medor" with the property "name" and the method "bark". If I open the console, I can type the name of the object. And, we see that it's got a name and a method.

Ouarf, Oauarf (dog barking).

And to call a method, it's the same as with accessing properties, you use the '.' operator, method . the name of the function followed by parenthesis and if the method take arguments, you would add arguments between parenthesis. It's just displayed an alert saying "Ouaf, Ouaf!" because the dog does "Ouaf, Ouaf!".

Example, describeYourself method.

Let's have a look at another example. Here, we've got an object named darkVador with properties and a method. Here we've got the describeYourself method that will make darkVador say: "I'm a human and I'm a villain in a series of movies". You can see that from inside the method describeYourself, we need to access the value of properties.

For this, we used the "this" keyword... "this.race" means the race property of the object darkVador, "this.job" means the job property of the object darkVador. If we omit "this." before the name of the properties, we are referring to a variable, a global variable for example. If there was a variable named "job", in that case it will display the name of variable. But if I've had "this." before, it means the "job" of this object, the "job" property of this object. Let's try it.

Define new object. nbsp;nbsp;nbsp;nbsp;nbsp; test, darkVador describeYourself.

You see that it displays "I'm a human and I'm a villain " blah blah blah...And "human" and "villain" are the values of the "race" and the "job" properties inside the object. "this.race" was used for displaying this value. You can also use the "this" keyword for calling a method from another method.

this.describeYourself.

Let's add a "console.log("hello I'm describeYourself!!!")", and let's call this describeYourself from the talk that is just above. For calling a method from another one, I use "this.", followed by the name of the method. And I save and if you call the talk method, you see that it says "hello I'm describeYourself!!!" before displaying "come to the dark side", that is in the talk method, because this.describeYourself() executed describeYourself from the talk method.

Click event listener & call method.

In the example, I have also a click event listener that you can try that will display a message in the HTML5 page itself. It just shows that we can call method by using the name of this object followed by the name of the method with parentheses.

Create empty object, then define its properties.

Ok, there is another interesting way to define objects and to add and remove properties and methods. You can describe an object with 0 property or method, or just few of them. And you can complete it, you can add properties and methods after its creation. We created an empty object named darkVador, and we defined properties (race and job), methods (talk and describeYourself) after the creation of the object. You can try this example, it will work the same.

Test, darkVador object in devtools console.

And if we look at the value of the darkVador object in the devtool console (on the right), you see that it's a complete object that contains the properties and the methods we define after creating the object.

Source code of the live lesson example
Elements, properties and methods
Some vocabulary:
Yes, it is possible for an object's property to be a function!

A very simple example:

Source Code:
1.  var medor = {
2.    name: 'Benji',
3.    bark: function(){
4.      alert('Ouarf, Ouarf!');
5.    }
6.  };

In this example, the bark property's value is a function, so we call bark "a method".

A method is a special property that corresponds to the object's behavior.

Properties correspond to an object's DNA (its characteristics), and are nouns (age, name, etc.)

Methods correspond to an object's behavior and are verbs (bark, move, changeSpeed, etc.)

Calling a method

Since a method is a property we can use the '.' operator (or brackets with the method's name as a string index).

Let's see some examples:
Test button, make darkVador speak.
CodePen: example make darkVador speak.
JavaScript Source Code:
Source Code:
1.  var darkVador = {
2.    race: 'human',
3.    job: 'villain',
4.    talk: function() {
5.      return 'come to the dark side, Luke!';
6.    }
7.  }
8.  
9.  function dvSpeak() {
10.   document.body.innerHTML += '<p>Dark Vador says
        ' + darkVador.talk(); + '</p>';
11. }

In line 1, we created a simple object named darkVador, that has two properties (race and job) and a method (talk).

In the dvSpeak function, at line 10, we call darkVador's talk method. The syntax is a mix between the one for accessing a property (with the '.' operator), and the one for calling a function (with parentheses and ';' at the end).

When we write darkVador.talk(), we are executing the talk method of the object darkVador, but in plain English, we're just asking Dark Vador to talk. We invoke its behavior!

Another example with the player we saw briefly in Module 2

Here is the last version of the player object we saw in our small game:

Example, red square in canvas.
CodePen: example, red square in canvas.
JavaScript Source Code:
Source Code:
1.  var player = {
2.    x:10,
3.    y:10,
4.    width:20,
5.    height:20,
6.    color:'red'
7.  }
8.  
9.  // and we also used two other functions for moving the player with
    the mouse
10. // and for drawing it as a filled rectangle
11. 
12. function movePlayerWithMouse() {
13.   if(mousePos !== undefined) {
14.     player.x = mousePos.x;
15.     player.y = mousePos.y;
16.   }
17. }
18. 
19. function drawFilledRectangle(r) {
20.   // BEST practice: save the context, use 2D transformations
21.   ctx.save();
22. 
23.   // translate the coordinate system, draw relative to it
24.   ctx.translate(r.x, r.y);
25. 
26.   ctx.fillStyle = r.color;
27.   // (0, 0) is the top left corner of the monster
28.   ctx.fillRect(0, 0, r.width, r.height);
29. 
30.   // BEST practice: restore the context
31.   ctx.restore();
32. }
Now that we've seen that we can include methods into objects, here is a better, more readable and more encapsulated version of our player object:
Source Code:
1.  var player = {
2.    x:10,
3.    y:10,
4.    width:20,
5.    height:20,
6.    color:'red',
7.  
8.    move(x, y) {
9.      // change x and y coordinates of the player
10.     // TODO!
11.   },
12. 
13.   draw() {
14.     // draw the player at its current position
15.     // with current width, height and color
16.     // TODO!
17.   }
18. }

Assuming that the move and draw methods are fully implemented, we will now be able to call:

Readability is better, it is like asking the player to move, or asking it to draw itself. And we do not need to pass the x, y, width, height, color to the draw method: it is inside the player object, and it can access all its internal property values!

In the next section we will look at how we can access other object's properties from a method or call other methods.

4.2.6 "this": accessing properties (3:37)

Live coding video: add methods to the player object from the game
'this' accessing properties.

Let's have a look now at the game we developed during the first three modules.

That's with a small red squared player that follow the mouse.

We had an animation loop that 60 times/second cleared the canvas, draws the player (the red square), moved the player, following the mouse, and then asked for a new frame of animation.

This is how it works. For drawing the player we called "drawFilledRectangle()" passing, as a parameter, a player object with just properties in it.

For drawing the player, we call "drawFilledRectangle()" with the player as parameter, and we use the x and y and color and width and height properties of the player's object.

The same for moving the player with the mouse: we've got a method that will use "player.x" and "player.y" giving to them the position of the mouse. We can go further in object-oriented programming by moving these functions inside the object, here, as methods. Of course, we'll have to do some small modifications because "player.x" and "player.y", will become the properties of the object itself.

Let's have a look at the modified version. So here we've got the "move" function that will take the "x" and the "y" position of the mouse, and we just set them to the "this.x" and "this.y" properties of the object.

Let's look at how we call this move method from the animation loop: just "player.move(mousePos.x, mousePos.y)".

The same for drawing the player: we copy and paste the content of the previous "drawFilledRectangle()" method except, that when we add to access x, y, color, width and height properties, we use "this.x", "this.y", etc. And we also pass the context that is the object used for drawing in the canvas as a parameter.

Like this, we can use the object in another project and don't rely on a global variable...like we did before in the previous example, the context was a global variable, here. By passing it as a parameter, if the global variable has a different name, we just have to pass it as a parameter. Look at the code of this "draw()" method: "player.draw()" context.

Like this we've got a more compact object that contains its characteristics and the methods that correspond to its behaviors to what it can do and, of course, the methods will modify the properties for changing the position of the object on the screen.

Source code of examples shown in the above video

The this keyword: accessing properties from a method

The this keyword!

When one wants to access an object property or wants to call another method from an object method, we must use the this keyword. In the code of the player object, this means "from this object".

Let's look at our game again, with a new version of the player object - this time fully functional:
CodePen: 'this' example.
CodePen: 'this' example.
JavaScript code extract:
Source Code:
1.  var player = {
2.    x:10,
3.    y:10,
4.    width:20,
5.    height:20,
6.    color:'red',
7.  
8.    move: function(x, y) {
9.      this.x = x; // this.x is the property of "this object"
10.     this.y = y;
11.   },
12. 
13.   draw: function(ctx) {
14.     // draw the player at its current position
15.     // with current width, height and color
16.     // it's nearly the same code as the old drawFilledRect function
17.     ctx.save();
18. 
19.     // translate the coordinate system, draw relative to it
20.     ctx.translate(this.x, this.y);
21. 
22.     ctx.fillStyle = this.color;
23.     // (0, 0) is the top left corner of the monster
24.     ctx.fillRect(0, 0, this.width, this.height);
25. 
26.     // BEST practice: restore the context
27.     ctx.restore();
28.   }
29. }

Notice that we've used this followed by the '.' operator every time we've had to access the current value of an object's property (lines 9, 10, 20, 22 and 24).

We passed the canvas' graphic context as a parameter to the draw method (it's always good not to create dependencies when making objects). Passing the context as a parameter avoids using it as a global variable. If in another project we've got a context named "context" instead of "ctx", then we will just change the parameter when we call player.draw, otherwise we would have had to rename all occurrences of ctx in the code).

Same with the mouse coordinates we passed to the move method.

Let's see the Dark Vador example with the use of this in a method

CodePen: example Dark Vador in a method.
CodePen: example Dark Vador in a method.
Source Code:
1.  var darkVador = {
2.    race: 'human',
3.    job: 'villain',
4.    talk: function() {
5.      return 'come to the dark side, Luke!' + this.breathe();
6.    },
7.    describeYourself: function() {
8.      return "I'm a " + this.race + " and I'm a " + this.job +
9.      " in a series of movies!" + this.breathe();
10.   },
11.   breathe() {
12.     return ".....shhhhhhhhh.....";
13.   }
14. }
15. 
16. function dvSpeak() {
17.   document.body.innerHTML += '<p>Dark Vador describes himself:
        ' +     
18.   darkVador.describeYourself(); +
19.   '</p>';
20.   document.body.innerHTML += '<p>Dark Vador says: ' +
21.   darkVador.talk(); +
22.   '</p>';
23. }

In this example, notice that the describeYourself method from the darkVador object uses the two properties name and job using the this keyword. We also call the breathe method from the two methods describeYourself and talk, using this.breathe();

4.2.7 Adding/deleting properties and methods

Properties and methods can be added/deleted after an object has been defined.

Unlike other object-oriented languages, it is possible in JavaScript to add or to remove properties after an object has been created.
Examples:
CodePen: example add properties and methods.
CodePen: example add properties and methods.
Source Code:
1.  // empty object with properties/methods
2.  var darkVador = {};
3.  
4.  // add properties after darkVador has been created
5.  darkVador.race = 'human';
6.  darkVador.job = 'villain';
7.  
8.  // add some methods
9.  darkVador.talk = function() {
10.   return 'come to the dark side, Luke!' + this.breathe();
11. };

Lines 5, 6 and 9: we can add properties and methods after the object has been created empty at line 2.

Deleting a property or a method

You can use the JavaScript keyword "delete" to delete an object's property (it will become undefined).

Example:
CodePen: example.
CodePen example.
JavaScript code extract:
1.  function deleteSomeProperties() {
2.    delete darkVador.race;
3.    delete darkVador.job;
4.  }

4.2.8 "this": some final thoughts

We simplified the explanations for "this" in this introductory course. Normally, "this" is the current object when you use it inside an "object literal" (like in this CodePen example from the course).

But... we also met "this" in event listeners (see in  this example from the course). Look at the onchange = "changePageBackgroundColor(this.value);" ...

In fact, the "this" keyword can be confusing in JavaScript. The key thing to remember is that it is bound to the calling object when the function is called, not when the function is created.

And in the case of event listeners, the callbacks are called by the browser... You can conclude that it's a good habit not to have event listeners in your objects: just use methods in which there is no confusion about "this".

4.3.1 Classes: definition

Let's study what is the concept of "class" in object oriented programming languages.

Dark vador and his friend named pikachu.

So far in this course, we've only used singleton objects: objects that only occur once: player, darkVador, etc. Ok, this is not quite true, I'd forgotten that we created many balls in the module 2 game. We'll come back to this example further down the page!

But even with the balls from module 2, we did not use a template to tell us how to easily create multiple objects that share the same properties and the same methods, but whose properties' values may differ.

For example, imagine Luke Skywalker, Ian Solo and Dark Vador. What do they have in common? They all are Star Wars heroes, they all have a name, they all belong to one side (the good/bad people, or rebels vs empire), etc. Imagine that we have a way of programming that describes not the objects themselves, but a "model", a "template" for these objects. We could call it StarWarsHero and use it for creating our heroes' objects.

Imagine the balls from module 2: they all had the same shape (circle), the same x, y, radius and color properties, but they were all different. They all belonged to the same class of object (ball), but they were all different in terms of their properties' values.

In many programming languages, these templates are called "classes".

Let's introduce these two ways of defining "pseudo classes" with ES5's function constructors, and with modern JavaScript's classes!

4.3.2 The "new" keyword (6:59)

Live coding lesson: the "new" keyword

The 'new' keyword.

So far, in this course, we've only used singleton objects: objects that only occur once. We've got one player in the game, we've got one Dark Vador in the examples with the Star Wars heroes. But imagine Luke Skywalker, Ian Solo and Dark Vador... what do they have in common?

They're all Star Wars heroes, they all have a name, they all belong to one side, the good or the bad people, the rebels or the empire, etc. Imagine that we have a way of programming that will describe not the objects themselves, but a model, a template, for these objects.

We could call it StarWarsHeroes for example, and use it for creating our heroes' objects, each being of the same kind, but with different names, different sizes, different descriptions.

Imagine the balls from the Module 2, in the game, the balls that were bouncing against the walls. They all have the same shape (a circle), the same properties x and y, and color, but they all differ, they all have x and y coordinates that are different, and different colors.

In many programming languages, these templates are called classes. You've got a class Person, and you create objects that are instances of Persons. From a model, you create Michel Buffa. From a Hero class you will create Luke Skywalker. From a Ball class, you will create many balls with different shapes, radius and coordinates. In JavaScript 5, we did not have such a concept.

Instead, we have "constructor functions". I will show you how they work. With JavaScript 6, we've got the concept of "classes", and it will be the topic of a next video. But as "constructor functions" from JavaScript 5 are in many, many examples on the Web, I will show you that to you first.

Simple function.

You start by writing a simple function, but by convention, you start with a capital letter: "Hero". And then, you can indicate the parameters that your heroes will have. You will indicate the name and the side of a Star Wars heroes for example. Then you will initialize the properties of each hero. What I write here is very common: "this" followed by the name of the property equal the name of the parameter passed for building an object.

If I use just this syntax, I can start building heroes. And for this I use the keyword "new". I just typed the name of the constructor function, preceded by the keyword "new".

Build an object.

If we open the console and look at this object... you see that we built an object. And where it's interesting? It's when you create multiple objects.

'this' objects and methods.

If you look at these objects, ... dark ..., we created multiple objects from the same template. Of course, we can also add methods in this object.

And the syntax is also to declare the name of the method preceded by "this": this.describeYourself =... and then the body of the function. This is a property defined in the class Hero. First, we can check that the method has been added to each object...so, Ian Solo... you can see the method here: "describeYourself"... you can see the body of the method. Luke Skywalker has the same method because it's "an instance of the same class".

Define and assign name and side.

We can call ianSolo.describeYourself(); and it will say "I'm Ian Solo and I'm from the Rebels". If we do the same with darkVador, it will say "I'm Dark Vador and I'm from the Empire".

More on object properties.

Just using these lines here, we'll create different objects that will all share a name, a side and a describeYourself properties and methods, but with different values that have been passed at construction time. The 'new' operator here is for constructing, for building objects.

Source code shown in this lesson

Up to 2015, with JavaScript version 5 (and previous versions), you can define a pseudo-class template called "a constructor function". The syntax is the same as for creating a function, except that:

  1. By convention, its name is Capitalized. The first letter of the function name is in uppercase, this is a good way to know, when you read someone else's code, that this is not a regular function, but a constructor function. Its name is a noun, the name of the class of objects you are going to build. Example: Person, Vehicle, Enemy, Product, Circle, Ball, Player, Hero, etc.
  2. You build new objects using the new keyword:

    Examples (Car, Hero, Ball, Product are constructor function names):

Source Code:
  var car = new Car('Ferrari', 'red');
  var luke = new Hero('Luke Skywalker', 'rebels");
  var ball1 = new Ball(10, 10, 20, 'blue'); // x=10, y=10,
  radius = 20, color = 'blue'
  var p1 = new Product('Epson printer P1232', '183', 'Mr Buffa'); 
    // ref, price, customer etc.
  1. The parameters of the function are the "constructor parameters": the new object that you are building will take these as its initial properties' values. You can build a Hero, but you must give him/her a name, a side, etc.
  2. You define the property names and method names using the this keyword. But beware: the syntax is not the same as the syntax we used for singleton/simple objects. No more ":" and "," between properties. Here we use "=" and ";" like in regular functions.
Example:
Source Code:
1. function Hero(name, side) {
2.   this.name = name;
3.   this.side = side;
4.   this.speak = function() {
5.     console.log("My name is " + this.name + " and I'm with
6.     the " + this.side);
7.   }
8. }

In a constructor function named "Hero", you will find properties declared like this: this.name this.side; and methods declared like this: this.speak = function() {...}

  1. Very often some properties are initialized using the constructor function parameters, so that the newly constructed objects will get an initial value for their properties. In this case, we use the this keyword to distinguish the property from the constructor function parameter:
Example:
1. function Hero(name) {
2.   this.name = name;
3.   ...
4. }
Full interactive example that uses a constructor function
CodePen: example constructor function.
CodePen: example constructor function.
Source Code:
1.  function Hero(name, side) {
2.    this.name = name; // code outside of methods is usually for initializing
3.    this.side = side; // the properties. Very often, they match the parameters
4.  
5.    this.speak = function() {
6.      return "<p>My name is " + this.name +
7.      ", I'm with the " + this.side + ".</p>";
8.    }
9.  }
10. 
11. var darkVador = new Hero("Dark Vador", "empire");
12. var luke = new Hero("Luke Skywalker", "rebels");
13. var ianSolo = new Hero("Ian Solo", "rebels");
14. 
15. function makeHeroesSpeak() {
16.   document.body.innerHTML += darkVador.speak();
17.   document.body.innerHTML += luke.speak();
18.   document.body.innerHTML += ianSolo.speak();
19. }

Lines 1-9: see how the constructor function is declared: the function name starts with an uppercase letter 'Hero'. The parameters have the same name as the properties they correspond to (name, side). And in the first source code lines after the function declaration, we initialize some properties using these parameters (lines 2 and 3). We use the this keyword to distinguish the property and the parameter. You will often see things like: this.name = name; this.age = age; etc.

Lines 11-13: creation of three heroes. We use the same constructor function (Hero) along with the new keyword. Luke, darkVador and ianSolo ARE each a Hero, and share the same properties (name, side, lines 2 and 3) and the same behavior (they can speak, they all have a speak method, declared at line 5).

4.3.3 Creating objects using modern JavaScript's classes (5:11)

Live coding lesson: modern JavaScript's classes

CodePen: example JavaScript classes.

In the last lesson, we saw JavaScript 5 constructor function that were useful for building multiple instances of the same template.

Well, this constructor function syntax is OK but not easy to read. If someone doesn't respect the conventions, like using the capital letter for the name of the function, and so on, it's very easy to think that this is just a normal function.

If I read a source code with a constructor function written in lowercase, I might not understand that it's meant for building objects. JavaScript 6 introduced the concept of classes that we're going to see. But just before looking at the class version of the hero we saw earlier, let's have a look at it again.

CodePen: class & methods.

Previously, we had a function with the name that starts with a capital letter, we passed the parameters for building the object, and we used this to set the different properties. We used the equal sign for setting values to the properties at building time, and we also used the equal syntax for defining methods. And inside methods, we used these for accessing the properties.

CodePen: class & constructor.

With the new JavaScript 6 syntax, it's much simpler. We use the "class" keyword followed by the name of the class for defining a class. JavaScript 6 also introduces the concept of constructor.

Constructor is a special method that will be called at construction time, when "new" is used. When we will build darkVador using "new" followed by the name of the class, it will call this method. So "new Hero( "Dark Vador", "empire")" will call the constructor in the class, passing "Dark Vador" and "empire" as values for the "name" and "side" arguments.

Inside the constructor, we usually set the different properties, and for this we use the same syntax as in constructor function. We use "this" followed by the name of the property and we use the equal sign for setting values to the properties.

CodePen: define class object.

Then we can define methods, and here, the syntax again is much simpler. No more use of the "function" keyword.

Look at this, you just type the name of the method followed by parentheses, and eventually, you can add arguments between parentheses. Compare the way we declare the method in JavaScript 5, inside the constructor function, with the way we declare method with JavaScript 6 classes. Here, we will able to call "darkVador.speak()" to call this method.

And inside the method, you will still use "this" keyword for accessing internal properties of the object of for calling internal methods. If I had a method, "anotherMethod" here. Blah blah blah ... something. I would call it using "this.anotherMethod". In this aspect, it's very similar to what we saw with constructor functions and JavaScript objects with the JavaScript 5 syntax. Okay, so we can try this example.

CodePen: new objects with class.

Here we build, in a similar way as previously with constructor function, we build object using the "new" keyword followed by the name of the class and we pass the parameter for building the object, that will be passed to the constructor.

CodePen: define and add new objects.

We can type "ianSolo": see that it's been built correctly.

CodePen: define new object.

And if we compare to the JavaScript 5 version, the "IanSolo JavaScript 5", you see it's completely similar. Well, in this example, we had a method describe yourself, but it's really the same thing behind the scene, just a syntactic sugar for making... defining templates for building object much more easier than before. I recommend to use the class syntax from ES6, it's supported by all modern browsers.

Source code from above video examples

ES5's constructor function syntax is not easy to read. If someone does not respect the "conventions" that we've just discussed (start the class with an uppercase, etc.), then the code may work, but it will be difficult to guess that we are not in front of a regular function.

Modern JavaScript now provides a class keyword and a constructor keyword, along with advanced concepts that will be the subject of a future " JavaScript advanced" course.

Main changes:

Example: let h1 = new Hero('Ian Solo', 'rebels');

This will call constructor(name, side) in the example below.

Here is the new version of the Hero "template", this time with the ES6 class syntax:

Source Code:
1.  class Hero {
2.    constructor(name, side) {
3.      this.name = name; // property
4.      this.side = side; // property
5.    }
6.    speak() { // method, no more "function"
7.      return "<p>My name is " + this.name +
8.      ", I'm with the " + this.side + ".</p>";
9.    }
10. }
11. var darkVador = new Hero("Dark Vador", "empire");

The instructions in the body of the constructor are executed when an object is created using the keyword new followed by the name of the class, with arguments between parentheses. These arguments will be passed to the constructor.

See below an interactive example that uses an ES6 class to create Star Wars' heroes.

Make star wars heroes speak.
CodePen: make star wars heroes speak.

4.3.4 Declaring a class before using it

You must declare a class before using it!

Unlike functions, classes must be declared BEFORE using them.

An important difference between function declarations and class declarations is that function declarations are "hoisted" and class declarations are not. This means that you can call a function BEFORE it has been declared in your source code. This is not the case with ES6 classes!

You first need to declare your class and then access it, otherwise code like the following will throw a ReferenceError:

Incorrect version => you try to create an instance of a class before it has been declared:

1.  var p = new Rectangle(); // ReferenceError
2.  
3.  class Rectangle {...}

Correct version =>

1.  class Rectangle {...}
2.  
3.  var p = new Rectangle(); // WORKS !

4.3.5 Creating objects with functions (factories)

We have already seen three different ways to create objects (literals, constructor functions and ES6 classes).

Objects can be created as "literals":

Darth Vador.
1.  var darkVador = { firstName:'Dark', lastName:'Vador'};

Objects can be created with the keyword new and a constructor function or an ES6 class:

1.  var darkVador = new Hero('Dark Vador', 'empire');
Objects can also be created by functions that return objects (factories):
Source Code:
1.  function getMousePos(event, canvas) {
2.    var rect = canvas.getBoundingClientRect();
3.    var mxx = event.clientX - rect.left;
4.    var my = event.clientY - rect.top;
5.    return { // the getMousePos function returns an object. It's a factory
6.      x: mx,
7.      y: my
8.    }
9.  }
And here is how you can use this:
1.  var mousePos = getMousePos(evt, canvas);
2.  
3.  console.log("Mouse position x = " + mousePos.x + " y =
    " + mousePos.y);

The call to getMousePos returns an object that has an x and a y property.

4.3.6 Static properties and methods (6:33)

Live coding lesson: static properties and methods

 Static properties and methods.

Hi, let's talk again about classes, properties and methods. So far, we saw classes that are templates for building objects. And in the class, we define properties and methods. Properties are for describing the characteristics of each object that will be built.

name, side - instance properties.

The name property, the side property, for the Star War heroes, correspond to Luke Skywalker and the rebels, to Dark Vador and the empire. And these properties and methods are called 'instance properties' and 'instance methods' because they are tied to the objects that have been created. And we use them by preceding them by the name of the object: luke.speak(), darkVador.name(), and so on.

Sometimes you will want to have some properties for characterizing the class itself, and some methods for characterizing the behavior of a class. For example, you would like to know how many heroes have been built. And you'd like for that to ask the hero class.

We can define what we call 'static properties' and 'static methods'. But I prefer to use another name for them that is also very common: we call them class properties and class methods.

Class properties define the characteristic of the class itself: how many heroes have you built? And the class methods will correspond to the behavior of the class Hero: "Hey! Please give me how many heroes from the rebels you've built".

 class.propertyname.

Let's see an example. I will declare a property for the class Hero. We use the name of the class followed by '.' followed by the name of the property.

Here, I declare that after the Hero class, because we explained this in another page of the course, but unlike functions, you can use only class name after it has been declared. The class Hero is declared here, I can only use "Hero.something" 24

 Hero.numberofHeroesCreated.

Here, I declared a variable named "numberHeroesCreated". I can type this in the console and see that it returns 0. But why it's interesting, is that I can use this class property inside a class itself. If in the constructor, I increment the "numberofHeroesCreated", the property of the class Hero. And if I build 0 instance, ...

Static method; distance.

I can look at the value of this property: it says 0. But if I built 2 objects, in that case the "new" keyword will call twice the constructor method. And the property of the class Hero will say I've built 2 heroes. If I'm just uncommenting another one, here. The return value is 3.

Example method 'this'.

It's important to use this method, using the name of the class because it corresponds to a property of this class, to characteristics... "class Hero. How many heroes have you created?"

Calculate the static distance between two points.

Now, we can also have static methods. A static method can be some sort of utility method, some behavior method of the class itself. Here we've got a class that defines a point, defined by its "x" and "y" properties. We can have a "distance" method for computing the distance between two points. We could have this located outside of the class and it will just use the coordinates of two points for computing the distance. But if it's meant to work only on points, it's a good idea to put it as a class method inside the point class.

Compute distance between two points in 2d space.

Like this, when you will compute the distance between 2 points, we'll just call: Point.distance(), passing the 2 points as parameter. In plain text, it means: "class point, please compute the distance between these 2 points that are instanced of your class". When you've got methods that are only related to instances of the class itself, it's a good idea to put it inside. And you precede them by the "static" keyword.

Special method using name of class: numberHeroesCreated.

Because sometimes, you can call such methods without using any instance. For example, if I want a method that will work on the "numberHeroesCreated": static getHowManyHeroesYouCreated()... HowManyHeroesYouCreated. And here, it makes sense that it should be a special method because, instead of using an instance name, I will use the name of the class.

getHowManyHeroesYouCreated()... 0!

Source code from the examples in the above video
Class properties and methods vs. instances' properties and methods

Sometimes, there are methods "attached" to a class, not to an instance of a class.

For example, imagine the Hero class we've already seen, and we would like to know how many Star Wars's heroes have been created. If zero hero has been created, it's obvious that we could not use this property with an instance of the class such as Dark Vador: darkVador.getNbHeroes(); this would make no sense.

Instead, object oriented programming languages have the concept of "class properties" and "class methods" that complete the "instance properties" and "instance methods" that we've seen up to this point. Hero.getNbHeroes() means "Hey, class Hero, can you tell me how many heroes have been created using your class?". Class methods define the "class behavior", and instance methods define the instances' behavior. darVador.speak(); means "Hey, Dark Vador, please, tell us something!". I speak to Dark Vador and I'm expecting something creative from him, such as "I'm your father, Luke!".

It's the same for properties. If there is a property named nbHerosCreated in the class Hero, it represents the DNA of the class, not of the instances. You can say "the Hero class has the number of heroes it created", and you can say "Dark Vador has a name and belongs to the empire side", but not "Dark Vador has a number of heroes he created". We have class properties and instance properties.

The static keyword is used for defining class methods
Class methods

How do we distinguish them? By using the static keyword. When you see a method preceded by the static keyword, it means that you see a class property or a class method.

The static keyword.
Class properties

Class properties should be defined after the class definition, and declared using the name of the class followed by the . operator and the name of the property. Example: Point.nbPointsCreated in the example below. A best practice is to ALWAYS use them this way.

There is another way to declare Class properties (using static getters and setters -- see next section, for advanced users), but we recommend using this one for beginners.

Example of creation and use of class methods and properties using an ES6 class
Source code:
Source Code:
1.  class Point {
2.    constructor(x, y) {
3.      this.x = x;
4.      this.y = y;
5.      // static property
6.      Point.nbPointsCreated++;
7.    }
8.  
9.    // static method
10.   static distance(a, b) {
11.     const dx = a.x - b.x;
12.     const dy = a.y - b.y;
13. 
14.     return Math.sqrt(dx...dx + dy...dy);
15.   }
16. }
17. // static property definition is necessarily outside of the class with ES6
18. Point.nbPointsCreated=0;
19. 
20. // We create 3 points
21. const p1 = new Point(5, 5);
22. const p2 = new Point(10, 10);
23. const p3 = new Point(12, 27);
24. 
25. document.body.innerHTML += "<p>Distance between points (5, 5) and
    (10, 10) is " +
26. Point.distance(p1, p2) + "</p>";
27. document.body.innerHTML += "Number of Points created is
    " + Point.nbPointsCreated;
Running example:
CodePen: example distance between 2 points.
CodePen: example distance between 2 points.

4.3.7 [Advanced] Modern JavaScript's getters and setters

It is possible to use special methods that are called getters and setters. They allow to make some checks when one is trying to set a value to a property, or to do some processing when accessing it (for example for displaying it in uppercase, even if its value is in lowercase).

These special functions are called "getters" and "setters", and are declared using the keywords get and set followed by the name of the property they define.

Typical use (lines 7 and 11):
Source Code:
1.  class Person {
2.    constructor(givenName, familyName) {
3.      this.givenName = givenName; // "normal name"
4.      this._familyName = familyName; // starts with "_"
5.    }
6.  
7.    get familyName() {
8.      return this._familyName.toUpperCase();
9.    }
10. 
11.   set familyName(newName) {
12.     // validation could be checked here such as
13.     // only allowing non numerical values
14.     this._familyName = newName;
15.   }
16. 
17.   walk() {
18.     return (this.givenName + ' ' + this._familyName + ' is
        walking.');
19.   }
20. }
21. 
22. let p1 = new Person('Michel', 'Buffa');
23. console.log(p1.familyName); // will display BUFFA in the devtool console
24. // this will call implicitly get familyName();
25. p1.familyName = 'Smith';    // this will call implicitly set
    familyName('Smith');

Notice that when you declare get familyName() {...} for example, you define implicitly a property whose name is "familyName" and that will be accessible using object.familyName, where object is an instance of the class. See lines 22-25 in the example above. Displaying the value of p1.familyName will call implicitly get familyName(), while p1.familyName = 'Smith'; will call set familyName('Smith');

As get familyName() defines an implicit property named familyName, the convention is to use this._familyName for storing its value (the same name preceded by an underscore).

Example at CodePen:
CodePen: example familyName.
CodePen: example.

4.3.8 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics
Optional projects
  1. Try to build a small database (in a JavaScript array) that will hold your contacts. You will use classes for defining: 1) a Contact class, with givenName, familyName, phoneNumber, etc. and
    2) an HTML set of input fields (not inside a form) for creating new contacts + an "Add contact" button. When you click on the button, it calls an addContact() callback of your own that will create a new contact and add it to your database (using the push method on arrays).
  2. [ADVANCED] input fields and buttons inside a form! Beware: either do not put your input fields and buttons inside a <form> or the buttons will submit the form (this is their default behavior, unless you add an attribute type="button" to the buttons). Or you might also declare <form onsubmit = "return processMyForm();">, this will call the method processMyForm (You can change this name if you like) when the form is submitted. In the processMyForm method, get the content of the input fields, build a contact, add it to the array etc. And then, do not forget to return false to avoid the submission of the HTML form).
  3. It would be cool to also have a listContact() function that will generate a list of contacts (create <ul>...</ul> with <li>...</li> inside, one for each contact).
  4. Now, try to write an ES6 class ContactManager (or you could also use an object literal for that..., but let's try  practicing JavaScript classes!), that will have the array of contact as a property.
  5. Create an instance db of this class:
    let db = new ContactManager();
  6. Add in the ContactManager class an add(c) and a list() method (for adding a contact c to the array of contacts, and for listing the contacts).
  7. Now, when you press the buttons, the addContact() method from step 1 will call db.addContact(c) where db is the instance of your ContactManager class and c is an instance of the Contact class.
  8. Feel free to customize this project with nice CSS, etc.

4.4.1 Class and constructor

First, let's look how we were handling balls previously in our game!

We have built balls in order to fill the array of balls.

OLD VERSION:
Source Code:
1.  function createBalls(n) {
2.    // empty array
3.    let ballArray = [];
4.  
5.    // create n balls
6.    for(let i=0; i < n; i++) { // let's build multiple times a singleton object
7.      let b = {
8.        x:w/2,
9.        y:h/2,
10.       radius: 5 + 30 ... Math.random(), // between 5 and 35
11.       speedX: -5 + 10 ... Math.random(), // between -5 and + 5
12.       speedY: -5 + 10 ... Math.random(), // between -5 and + 5
13.       color:getARandomColor(),
14.     }
15.     // add ball b to the array
16.     ballArray.push(b);
17.   } // end of for loop
18. 
19.   // returns the array full of randomly created balls
20.   return ballArray;
21. }

In the code above, in order to build n balls, we created a singleton ball object multiple times. This worked, but if we have misspelled a property name within the code, or forgot one of the properties that had to be initialized, we would have received no warnings. We will replace these lines with something like let b = new Ball(...);

NEW VERSION: using the new keyword and an ES6 class
Source Code:
1.  function createBalls2(n) {
2.    // empty array
3.    let ballArray = [];
4.  
5.    // create n balls
6.    for(let i=0; i < n; i++) {
7.      // Create some random values...
8.      let x = w/2;
9.      let y = h/2;
10.     let radius = 5 + 30 ... Math.random(); // between 5 and 35
11.     let speedX = -5 + 10 ... Math.random(); // between -5 and + 5
12.     let speedY = -5 + 10 ... Math.random(); // between -5 and + 5
13.     let color = getARandomColor();
14.     // Create the new ball b
15.     let b = new Ball(x, y, radius, color, speedX, speedY);
16.     // add ball b to the array
17.     ballArray.push(b);
18.   }
8.    // returns the array full of randomly created balls
9.    return ballArray;
10. }

Ok, not a very big change here, except that we are no longer manipulating the property names one by one, and we use the new keyword. 

And here is the (so far, incomplete) ES6 class for Ball (continued in the next page of this course):

Source Code:
1.  class Ball {
2.    constructor(x, y, radius, color, speedX, speedY) {
3.      this.x = x;            // properties
4.      this.y = y;
5.      this.radius = radius;
6.      this.color = color;
7.      this.speedX = speedX;
8.      this.speedY = speedY;
9.    }
10.   ... // code to come for methods
11. }

4.4.2 Adding methods classes

Ok, we've seen how to define the Ball class: properties and constructor. Properties are the DNA for balls: they all have an x and y position, a radius, a color, a horizontal and a vertical speed.

It is time to add some behaviors: a draw and a move method. Indeed, all balls will be able to draw and move themselves.

Here's how we were drawing a ball in the previous version of the game:

Source Code:
1.  function drawFilledCircle(c) {
2.    // GOOD practice: save the context, use 2D trasnformations
3.    ctx.save();
4.  
5.    // translate the coordinate system, draw relative to it
6.    ctx.translate(c.x, c.y);
7.  
8.    ctx.fillStyle = c.color;
9.    // (0, 0) is the top left corner of the monster.
10.   ctx.beginPath();
11.   ctx.arc(0, 0, c.radius, 0, 2...Math.PI);
12.   ctx.fill();
13. 
14.   // GOOD practice: restore the context
15.   ctx.restore();
16. }

And this how we were drawing and moving all the balls:

Source Code:
1.  function drawAllBalls(ballArray) {
2.    ballArray.forEach(function(b) {
3.      drawFilledCircle(b);
4.    });
5.  }
6.   
7.  function moveAllBalls(ballArray) {
8.    // iterate on all balls in array
9.    balls.forEach(function(b, index) {
10.     // b is the current ball in the array
11.     b.x += (b.speedX ... globalSpeedMutiplier);
12.     b.y += (b.speedY ... globalSpeedMutiplier);
13. 
14.     testCollisionBallWithWalls(b);
15. 
16.     testCollisionWithPlayer(b, index);
17.   });
18. }
Adding a draw and a move method to the ES6 ball class

Instead of having these behaviors as separate functions that take a ball reference as a parameter, it is always better to put this as a method inside the class. Indeed, each ball can move, can draw itself, and the content of these methods does not bring any external dependencies.

For example, if we decide to put a method named testCollisionWithWalls inside the Ball class, it would be bad, in terms of reusability, for its content to rely on external, global variables, such as the canvas size. You could have passed the canvas as a parameter, but then you create more specialization: you have a Ball class for balls that can move inside a rectangular area that is a canvas. It's better to just pass the width and the height of the zone.

Anyway, if you plan to use your balls in another game, it is recommended that you keep the class as simple as possible. It will be more reusable in other projects.

New version of the ES6 Ball class with draw and move methods:
Source Code:
1.  class Ball {
2.    constructor(x, y, radius, color, speedX, speedY) {
3.      // see previous section for the code
4.    }
5.  
6.    draw(ctx) { // Nearly the same as the old drawFilledCircle function
7.      // BEST practice: save the context, use 2D transformations
8.      ctx.save();
9.  
10.     // translate the coordinate system, draw relative to it
11.     ctx.translate(this.x, this.y);
12. 
13.     ctx.fillStyle = this.color;
14.     // (0, 0) is the top left corner of the monster.
15.     ctx.beginPath();
16.     ctx.arc(0, 0, this.radius, 0, 2...Math.PI);
17.     ctx.fill();
18. 
19.     // BEST practice: restore the context
20.     ctx.restore();
21.   }
22. 
23.   move() {
24.     this.x += this.speedX;
25.     this.y += this.speedY;
26.   }
27. }
Explanations:

Notice that we did not take into account the globalSpeedMultiplier we had in the old moveAllBalls function, as this is not something that is individually relevant to each ball: it is more something that affect ALL balls. This should raise an alert: use an ES6 class property for that!

In other words, even if zero ball has been created, this globalSpeedMultiplier is set and can be modified using a slider in the graphic user interface. Consequently, it is not a ball property, more a property of the Ball class itself.

This setting could be created using a class property, as seen in a previous section of this course.

And here is how we can now move and draw ALL balls
Source Code:
1.  function drawAllBalls2(ballArray) {
2.    ballArray.forEach(function(b) {
3.       b.draw(ctx);
4.    });
5.  }
6.   
7.  function moveAllBalls2(ballArray) {
8.    // iterate on all balls in array
9.    balls.forEach(function(b, index) {
10.     // b is the current ball in the array
11.      b.move();
12. 
13.     testCollisionBallWithWalls(b);
14. 
15.     testCollisionWithPlayer(b, index);
16.   });
17. }

And here is the CodePen version of the game that includes these improvements:

CodePen: game with improvements.
CodePen: game with improvements.

5.1.1 Transcript Introduction - Adding Interactivity (1:31)

Transcript: Introduction - Adding interactivity

Adding interactivity to web documents.

Adding interactivity to your Web documents often involves the use of different input fields.

The HTML5 specification came with a lot of new form elements such as sliders, color chooser, and so on. In this module, you will learn what can be done using JavaScript and form inputs. For example, how can we ask the user to enter new data, how can we manipulate input fields' content and validate on the fly, what is been typed? How can we update an HTML table by adding a new row with this new data? Other interactions may involve sliders to adjust the volume of a video, custom button for controlling a play list, color chooser for controlling color style and so on. You will learn the main events related to HTML5 forms and will play with many examples.

We'll also come back to projects seen during the previous modules and enhance their interactivity by adding forms. This is the last module of this course, congratulations!! The HTML5 series is a natural continuation of this course since you will be able to put into practice your new JavaScript skills! And I hope to see you again as I'm the author of some of these courses! Byebye!

5.1.2 Module 5 outline

What you will learn in Module 5:

This module ends with the final exam which regroups questions specific to the current module but also a potpourri of questions related to the 4 previous modules.

5.2.1 References and objects (5:53)

Live coding transcript: references and objects

CodePen: references and objects.
CodePen: references and objects.
References and objects

When you define a variable, this is what happens: if its value is a primitive value, a number, a string or a boolean for example, the variable contains this value directly. On the opposite, if its value is an object with braces or created with the "new" keyword we saw during module 4, the variable contains the memory address of the object. We say that "this variable points to an object" or "references this object". And accessing the variable will automatically resolve the reference, meaning that the value of the variable is the referenced object.

And... let's see what happens when we copy a variable and modify the value of the variable that contains the copy. You will see that there are differences between variables that have a primitive value and variables that reference an object.

Let's start with primitive type...With primitive type if we take variable a and put the value "2" in it, then, if we copy this value of this variable into another one, ...here I've got the variable "x=2" and I set "x2" , "x2". So I've got "x2" that is a copy of "x", then if I modify the copied value, if I say "x2=3", you can notice that "x", the original variable, has not been modified. We just made a copy of it, a complete copy, and we modified the copy without changing the original. Now with objects, it's completely different.

Let's take the "y" variable from the example. That is an object with the property "a", that has the value of 2. If you look at the type of "y", it will say "y" is an object. Then, we copy "y" into "y2" and into "y3". "var y2=y" "y3=y". And then we modify one of the copy, "y2.a=3". We modify the property "a" of the object "y2".

It says "y2" as the value equal to 3. But if we display also the value of the property "a" for "y" and "y3", you will see that their value is the same. If we display here, "y.a" and "y3.a", the value is exactly the same. It's because "y", "y2" and "y3" point to the same location into memory. They just hold the memory address of the location that contains the value. If we modify this value using the "y2" reference, we also modify the value of the property of "y3" and "y".

You must understand this, take it slowly, look at the code, look at the video again until you are fine with that. However, if we say "y2" equals another object, in that case, if we modify "y2": "y2.a = 20" here. Then if we display the value of "y2.a", it will say "20". But if we just try to display the value of "y" and "y3", they have not changed. "y.a" "y3.a" - you see in the console, they've got their original value. It's because we assigned to "y2" another location in memory. And you can check if 2 different variables point to the same object using the "===" operator. So if we compare "y" and "y2", ...and I made just the test..., it will say "y and y2 ARE NOT the same object in memory".

You remember "y2" points to another location. And if you compare "y" and "y3", in that case they are the same objects. "y", "y3": they are the same objects, if I modify the property "a" of "y", and if I look to the "y3" it's modified too. To sum up, variables that are objects are in fact references to locations in memory. If we copy this variable that contains an object, we will get many variables that point to the same location in memory. With predefined types like Number, String and so on, it's a real copy that is done when we do "x=x2" for example. And in that case, only the copy is modified, not the original.

Source code shown in the video

First of all, we have to define "reference". Unlike a pointer variable, which contains the actual address of an object within the memory, a reference variable is an alias to a variable. This means that when you modify a reference variable, the original variable is modified too. This is because the two variables reference (i.e. point to) the same object.

When you define a variable (such as var x = 10; or let name = "Michel"; or let courseAuthor = {firstName:'Michel', lastName:'Buffa'), this is what happens:

Examples:
Source Code:
1.  // Defining two variables
2.  var x = 2; // the variable x contains the primitive datum 2
3.  var y = { a: 2 } // The variable y references the object {a: 2}
4.  
5.  // "Copying" two variables
6.  var x2 = x;
7.  var y2 = y;
8.  var y3 = y;
9.  
10. // Modifying copied variables
11. x2 = 3;
12. y2 = { a: 3 };
13. 
14. // Check
15. x; // 2 <- x is not modified because it contains a primitive value
16. y; // { a: 2 } <- y is not modified because y2 does not point to same object
17. 
18. y3.a = 4;
19. y; // { a: 4 } <- The object referenced by "y" and "y3" is modified
Of course, these rules also apply to the properties of objects.
Source Code:
1.  var driver = {
2.    name: 'Jean'
3.  };
4.  
5.  var car = {
6.    color: 'red',
7.    driver: driver
8.  };
9.  
10. driver.name = 'Albert';
11. car.driver.name; // 'Albert'

JavaScript is a "pass by value" language, unlike some other languages, which are "pass by reference" languages. This means that when you pass a variable to a function as argument, the value of the variable is copied into the argument.

Source Code:
1.  var x = 2;
2.  
3.  function sum(a, b) {
4.    a = a + b;
5.    return a;
6.  }
7.  
8.  sum(x, 3); // returns 5
9.  x; // 2 <- but x equals 2

When working with objects, the reference of the object is copied into the argument. That means you can modify the referenced object. But if you change the reference (for example by assigning a new object), the original variable (which now points to another object) will not be modified.

Source Code:
1.  var obj = { x: 2 }
2.  
3.  function add(a, b) {
4.    a.x += b;
5.  }
6.  
7.  add(obj, 3);
8.  obj.x; // 5 <- The referenced object is modified

Source Code:
1.  var obj = { x: 2 };
2.  
3.  function addAndSet(a, b) {
4.    var addition = a.x + b;
5.    a = { x: addition };
6.  };
7.  
8.  addAndSet(obj, 3);
9.  obj.x; /... 2 <- The referenced object is not modified
10. because at the end of the function the variable "obj"
11. and the variable "a" are not referencing the same object..../
Source Code:
1.  > var originalObject = {name:'Michel'};
2.  undefined
3.   
4.  > var copy = originalObject;
5.  undefined
6.   
7.  > copy.name;
8.  "Michel"
9.   
10. > copy.name = 'Dark Vador';
11. "Dark Vador"
12.  
13. > originalObject.name
14. "Dark Vador"
15.  
16. // They are the same. originalObject and copy are two "references"
    of the same object in memory
17. // If we change the name, we change the value in memory, but copy
    and originalObject "point to" the
18. // same place, to the same object. They are just "pointers" or
    "reference" to the same object

5.2.2 Comparing two objects

Comparing two objects will only return true if they point to the same object (i.e., if they have the same reference).

Balancing rocks logo.

Two objects of the same type, with the same property value, that look identical, will not be equal one to another if they don't have the same reference (if they point to different places in memory).

Source Code:
1.  > var originalObject = {name:'Michel'};
2.  undefined
3.   
4.  > var copy = originalObject;
5.  undefined
6.   
7.  > copy === originalObject
8.  true
9.   
10. > var anotherObject = {name:'Michel'};
11. undefined
12.  
13. > copy === anotherObject
14. false

5.2.3 The "global" window object

It is time to tell you the truth: the JavaScript code is executed by an "environment" (usually a Web browser, but there are some HTTP Web servers that use JavaScript for coding the server side of Web sites of applications, such as the NodeJS HTTP server).

This environment defines a "global object". When this environment is a Web browser (and this is the case for all examples we have seen in this course), this global object is named window. The "global variables" defined with the keyword var are properties of this window object, and we can say the same of predefined functions like prompt, alert, etc. However, at the top level of programs and functions, let, unlike var, does not create a property on the global window object.

TIP: if you have global variables/objects declared with let, just declare them with var instead, and you will be able to inspect them easily from the devtool console. You can switch back to using let, later.

Let's see some examples:
Source Code:
1.  > var a = 1;
2.  undefined
3.   
4.  > a;
5.  1
6.   
7.  > window.a;
8.  1
9.   
10. > window['a'];
11. 1
12. > let z = 1; // LET DOES NOT DEFINE properties of the window object
13. undefined
14. > window.z
15. undefined
a and window.a are the same variable.
navigator and window.navigator are the same,
document and window.document are the same thing.
1.  > document === window.document
2.  true
3.   
4.  > navigator === window.navigator
5.  true

Predefined functions are methods from the global object window:

Source Code:
1.  > parseInt('10 little children');
2.  10
3.   
4.  > window.parseInt('10 little children');
5.  10
6.   
7.  > alert === window.alert
8.  true
9.   
10. > prompt === window.prompt
11. true
12.  
13. > window.addEventListener === addEventListener
14. true

5.2.4 Built-in JS class: Object (3:12)

Built-in JS class: object.

JavaScript comes with a set of predefined objects or built-in objects such as Math, String, Date and so on. For developers that already know the Java language... or C#, you can imagine this more like a class from the developer's kit, a class that is provided by the language itself. The consequence of this is that on all the objects you manipulate in JavaScript, you will be able to use a predefined set of methods and properties that will be inherited from this predefined object.

On all the objects you manipulate, you will be able to use a method called "toString()" that is very similar to what we've got in the Java language. Another method is called "valueOf()" that will just return the value of the object. Let's take an example with first an array.

Here, we've got the array "t", that contains: 1, 2 and 3. If I type the name of the array in the devtool console, it calls behind the scene "valueOf()". It's the same thing as if I typed: "t.valueOf()". If I try to print the value of "t" using "console.log()" for example: if I do: "console.log(t.toString())", in that case, it will return the value of "t" as a string and not as an array.

Writing "t.toString()" will convert to string the object. But, if you just write "console.log" using just "t", in that case we are implicitly trying to convert it to a string. The call to "toString()" will be implicit. If I type "console.log("t = " + t)", it works, because it's the same as writing "t.toString()". We've got the same behavior with the Java language and the C# language. You see the same result.

We can also try with an object. Here, we've got a "p" object that has 2 properties: name and age. If I type "p", it will display the value, it's the same as "p.valueOf()". If I type "p.toString()", in that case, it gives me the value of "p" as a string, and as a string its the value is this message.

Source code shown in the above lesson

The source code of the example shown in the video  is available on CodePen.

The father of all objects: Object. All objects will inherit the properties and methods from the special class named Object.

These two lines are equivalent:
1.  > var o = {}; // creation of an empty object
2.  undefined
3.   
4.  > var o = new Object(); // same thing as in line 1
5.  undefined
The toString method inherited from Object by all objects
Source Code:
1.  > o.toString();
2.  "[object Object]"
3.   
4.  > o.name = 'Michel';
5.  "Michel"
6.   
7.  > o.toString();
8.  "[object Object]"
9.   
10. > var t = [1, 2, 3];
11. undefined
12.  
13. > t.toString();
14. "1,2,3"

toString() in JavaScript is rather similar to the Object.toString() method we find in the Java programming language: when we try to "display" an object, it is transformed into a string by calling toString() implicitly.

Source Code:
1.  > alert(t);
2.   
3.  > alert(t.toString()); // same as previous line of code
4.   
5.  > "An object into a string : " + t // same as t.toString()
6.  "The object as a String : 1, 2, 3"

Line 5: using the + operator with a string as the left argument will force the other arguments to convert to string by implicitly calling their toString() method.

The valueOf method inherited from Object by all objects

The ValueOf method returns the value of an object:

Source Code:
1.  > var t = [1, 2, 3];
2.  undefined
3.   
4.  > t.valueOf()
5.  [1, 2, 3]
6.   
7.  > t.toString();
8.  "1,2,3"

5.2.5 Built-in JS class: Array (8:46)

Live coding transcript: predefined object - Array

Built-in JS class: array.

This time, we look at the Array predefined JavaScript object. When you create an array, using the brackets notation, it's equivalent to using the "new" keyword with the name of the predefined class (or object) named, from JavaScript, "Array", with a big "A".

You can create an empty array using "new Array()" or you can create an array with elements inside, using "new Array()" followed by the list of elements. And if you only give one argument, you create an empty array full of undefined elements. "new Array(10)" will create an array with 10 undefined elements inside.

To tell you the truth, I nearly never use this notation. I prefer using directly the bracket notation. But this was just to show you that arrays are objects.

Now, let's look at some of the predefined properties and methods inherited from this "Array" predefined object. We already met the "length" property that corresponds to the number of elements in an array. If we look at the array named "a2", that contains "1" and "2", 2 numeric elements, 2 numbers, "a2.length" will display "2" ... 2 elements... value "2".

As arrays are objects, you can imagine that you can also set some properties to them. You can do "a2.name="Michel"". This not so good because your are mixing numbers with a property that is a name, and so on... I don't recommend at all doing that: avoid! But just to show you something: it's that the length of an array works only on elements that have a numeric index. If we display the length after adding the name (property), we will still have a length of "2"..."only elements with a numeric indexes are taken into account".

We can also change the "length" value. If we set the "length" to an arbitrary number, and if this number is bigger than the current number of elements, it will make the array grow and will fill it with undefined elements. After doing "a2.length=5", we can look at the length after that: it will be "5" and if we display the content of the array, it will display undefined, undefined, undefined. The notation, here, means undefined.

If you set the length to a value less than the current number of elements, in that case, it will shorten the array. It will remove the unwanted elements from the array. Now let's have a look at the most useful methods on arrays. One is called "sort()" and it's useful for sorting an array. I've got an array named "a" in the example.

Ok, let's set it again, here. I've got an array named "a", if I type "a.sort()", it will both return a sorted array but it will also sort the array itself. And by default, it sorts the array using just the numerical or alphabetical order. You can also add and remove elements to "a". We already saw the "push()" and the "pop()" methods. If I do "a.push()" with new elements, and if we look again at the array, I added twice an element named "new" and each time it returns the new length of the array. "a.length" is "7".

I can use "pop()": a.pop(), that will remove the last inserted element, the element at the end. It will return the value that has been removed, and you can see that "a" losts its last element. I can do it again: "a" lost 2 new elements I added earlier. Ok, let's have a look at another method called "join()".

"join()" will add a string between each elements of the array. "a.join()", and if I want to add some minus signs, will return the array with the minus sign in the middle. But it did not change the original array. If I want to use it, I can do: var b... b with minus... = a.join("---") And in that case, it's the returned array that will get the new modified value.

You can also use "slice()". "slice()" is a method that returns a sub-array without modifying the original array. If I want to remove the "3" and the "5" here, I need to remove elements from index 1 until index 2, ...3.

"a.slice(1,3)"... that means it will return "3" and "5" because this is the index of the last element before which I must stop cutting. And this does not modify the original array. If I want to remove elements and maybe insert elements at the location of the slice I remove, there is another method called "splice()". The "splice()" method modifies the array, it removes the slice and also adds new elements.

Let's start with the array "a". And I want to remove "3" and "5", and insert new elements instead. I can use the same syntax as before except that I will add a "p" for changing the name of the method, and I will add 3 new elements. If I look at what happened, it returned the slice that has been removed and now, in the array, we inserted instead the new elements. In that case, "splice()"... the last..., the second parameter, is included in the slice, It's a bit different and the previous method we saw. This means "remove elements 1 with index 1, 2 and 3" and put these elements instead.

It removed these 3 elements: 3, 5, 7 and inserted these elements instead. If you just use 2 parameters, the begin and the end indexes, it will just remove elements. In that case, we'll remove the 2 elements I've inserted here. And if I look at the array, it has been modified. These methods are quite powerful for manipulating elements inside an array: remove, insert, insert at the end, remove at the end, and so on...

Source code from the above video

The Array class can be used for creating arrays (however, we recommend that you use the other methods presented instead):

Source Code:
1.  > var a = new Array(); // same as a = []; use this instead!
2.  undefined
3.   
4.  > var b = new Array(1, 2, 3);
5.  undefined
6.   
7.  > b;
8.  [1, 2, 3]

Attention: if only one element, this corresponds to the initial size of the array.

1.  > var myArray = new Array(3);
2.  undefined
3.   
4.  > myArray;
5.  [undefined × 3]
Arrays are objects, but they are "special" objects
Source Code:
1.  > var a = [], o = {};
2.  undefined
3.   
4.  > a.length; // a is an array
5.  0
6.   
7.  > o.length; // o is a simple literal object
8.  undefined

Some horrible things we can do with arrays (TO AVOID!):

Source Code:
1.  > var a = [1, 2];
2.  undefined
3.   
4.  > typeof a
5.  "object"
6.   
7.  > a.push(3);
8.  3
9.   
10. > a
11. [1, 2, 3]
12.  
13. > a.length
14. 3
15.  
16. // Now let's add a name property to the array. Yes, we can do that!
17.  
18. > a.name = "I'm an array named a!";
19. "I'm an array named a!"
20. 
21. > a.length;
22. 3
23. 
24. > a;
25. [1, 2, 3, name: "I'm an array named a!"]
With arrays, only properties with a numerial index are taken into account by the length property.

The length property can be modified: reducing or increasing the size of an array. If you give to the length property a value bigger than the number of elements in an array, it adds undefined elements to it:

Source Code:
1.  > var a = [1, 2];
2.  undefined
3.   
4.  > a.length = 5;
5.  5
6.   
7.  > a;
8.  [1, 2, undefined × 3]

If you give to the length property a value less than the array's number of elements, it reduces the size of the array:

Source Code:
1.  > var a = [1, 2, 3];
2.  undefined
3.   
4.  > a.length = 2;
5.  2
6.   
7.  > a;
8.  [1, 2]

5.2.6 The most useful methods of the class Array

The most useful methods you can use on arrays are: sort(), join(), slice(), splice(), push()and pop()

Typical uses of  push, pop, sort, join
Source Code:
1.  > var a = [3, 5, 1, 7, 'test'];
2.  undefined
3.   
4.  > a.push('new') // appends at the end and returns the new length
5.  6
6.   
7.  > a;
8.  [3, 5, 1, 7, "test", "new"]
9.   
10. > a.pop(); // removes the last element and returns it
11. "new"
12.  
13. > a;
14. [3, 5, 1, 7, "test"]
15.  
16. > var b = a.sort();
17. undefined
18.  
19. > b;
20. [1, 3, 5, 7, "test"]
21.  
22. > a;
23. [1, 3, 5, 7, "test"]
24.  
25. // a is also sorted. The sort method sorts the array + returns it
26. undefined
27.  
28. > a.join(' and ');
29. "1 and 3 and 5 and 7 and test"
The slice() method returns a sub-array without modifying the original array

The slice() method returns a shallow copy of a portion of an array into a new array object selected from begin to end (end not included). The original array will not be modified.

Possible syntaxes:
Source Code:
1.  > a;
2.  [1, 3, 5, 7, "test"]
3.   
4.  > b = a.slice(1, 3); // elements of indexes = 1 and 2
5.  [3, 5]
6.   
7.  > b = a.slice(0, 1); // element of index = 0
8.  [1]
9.   
10. > b = a.slice(0, 2); // elements o indexes = 0 and 1
11. [1, 3]
12.  
13. > a;
14. [1, 3, 5, 7, "test"]
15.  
16. // a is unchanged by calls to a.slice(...)
The splice() method modifies the array: it removes "a slice" and also adds new elements

The first two parameters are start and the number of elements to delete, the other parameters are the elements to add to the array to replace the slice that will be removed.

Possible syntaxes:

start: index at which to start changing the array (with origin 0)

deleteCount: An integer indicating the number of old array elements to remove.

item1, item2, ...: these are optional. They are the elements to add to the array, beginning at the start index. If you don't specify any elements, splice() will only remove elements from the array.

Examples:
Source Code:
1.  > a;
2.  [1, 3, 5, 7, "test"]
3.   
4.  > b = a.splice(1, 2, 100, 101, 102);
5.  [3, 5]
6.   
7.  > a;
8.  [1, 100, 101, 102, 7, "test"]
9.   
10. > a.splice(1, 3);
11. [100, 101, 102]
12.  
13. > a;
14. [1, 7, "test"]

5.2.7 Built-in JS class: Number

The Number class can be used to transform strings into numbers, but it is recommended that you use parseInt or parseFloat instead.

Source Code:
1.  > var n = Number('3.1416');
2.  undefined
3.   
4.  > n;
5.  3.1416
6.   
7.  > typeof n;
8.  "number"
9.   
10. > var n = parseInt('3.1416'); // convert a string to an integer number
11. undefined
12.  
13. > n;
14. 3
15.  
16. > var n = parseFloat('3.1416'); // convert a string to a float number
17. undefined
18.  
19. > n;
20. 3.1416
Number logo.

Number has useful non-modifiable properties (constants): MAX_VALUE and MIN_VALUE:

1.  > Number.MAX_VALUE;
2.  1.7976931348623157e+308
3.   
4.  > Number.MIN_VALUE;
5.  5e-324
Methods useful for converting numbers: toFixed(), toExponential(), toString()
Source Code:
1.  > var n = 123.456;
2.  123.456
3.   
4.  > n.toFixed(1); // sets the number of digits for the decimal part of the number
5.  "123.5"
6.   
7.  > n = new Number(123.456); // same as n = 123.456
8.  Number {[[PrimitiveValue]]: 123.456} // well, not exactly, but
    when you use n, it is equivalent
9.   
10. > n.toFixed(1);
11. "123.5"
12.  
13. > n.toExponential();
14. "1.23456e+2"
15.  
16.  
17. > var n = 255;
18. undefined
19.  
20. > n.toString();
21. "255"
22.  
23. > n.toString(10);
24. "255"
25.  
26. > n.toString(16);
27. "ff"
28.  
29. > (3).toString(2);
30. "11"
31.  
32. > (3).toString(10);
33. "3"

5.2.8 Built-in JS class: String (7:48)

Live coding video: predefined class - String

CodePen: built-in JavaScript class: string.

Strings are also a predefined object and all strings in JavaScript inherit from different properties and methods. I will show you the most useful ones, but before that, I must explain to you one thing that is a maybe not explicit: in JavaScript, strings are not modifiable. You cannot change the content of a string without copying its content into another string. Let me show you that.

If I declare a string with the value "Michel" in it: string "s" - and I try to modify its content like this: "s." character at position 0 equals something else. It returns the character that I modified but if I type the value of "s", it's unchanged. When you want to add or remove characters, you cannot use the bracket notation. The most common thing we do is: "s = s +" something.

You see like that. I'm creating a new string that has the old value of "s" plus the "say hello" string. This is stored somewhere in memory and then "s" will get a new reference: instead of referencing "Michel", it now references another string located somewhere else in memory that has the value "Michel says hello". This is how we can concatenate elements to a string.

Let's look at some of the most useful methods. One is a "toUpperCase()". It returns the string "s" in upper case, but without modifying the string itself. If you want to modify "s", you will do: "s = s.toUpperCase()". In that case, "s" has been modified. The same, if you want to put it in lower case, so you've got "toLowerCase()". That works too and using "s = s.toLowerCase()" modifies the string.

Some other interesting methods are "indexOf()" to locate, to get the index of a particular character. "s.indexOf()" and...if I say... the character "c", it will return 2. 0 for the "m", 1 for the "i" and 2 for the "c". "indexOf()" returns the first occurrence.

If I try it with an "l", it will be 5 for the first occurrence of the chain. You've got also the "lastIndexOf()" method that is useful for getting the last position: 15 will be this "l", the last "l" from the "hello" word located at the end of the string. You've got also "charAt()" that is useful for getting a character at a given position: "s.charAt(5)" will return the character at number 5, it's "l".

We can also chain methods. We've got "s" that has the value of "Michel says hello". You can say: "s.toUpperCase()" and this will return the same value but in upper case. And now I can do for example: "lastIndexOf()" with the big "L" and it will give me the answer, because "s.toUpperCase()" will return a value in upper case and on this return value, we will try to get the index of the last "l", big "L" in it. Then, you can also get parts of a string without modifying it.

You've got 2 different methods that are very similar. For the most common use, it's "slice()" and "substring()". Let's me show you "substring()". Let's type again the value of "s": s.substring()"... beginning index and end index...

For example, 0 to 3 will get the characters at index 0, 1 and 2. It stops before the end parameter. It will get character at position 0, 1 and 2 not 3. If I try again with 3 to 5, it will get only 2 characters: 3 and 4. You see that.

"slice()" does the same thing, so in my opinion just choose one. "slice()" will do exactly the same thing. To tell you the thrust, I mainly use only "substring()" with 2 arguments begin and end that are positive and begin less that end. Follow this advice and will not have any problem. Other interesting methods are "split()" and "join()". If you use "split()", you can indicate the separator character. In the current string, you've got spaces between the words.

If I do this, it returns an array composed of tokens that are just the different slices of the strings separated by a space. If I want to split "s" using another separator, for example, I can enter the character "l", then in that case you will have slices separated by the "l" keyword.

Ok let's try again with this one.

And "join()" will rebuild, again from an array of tokens, it will rebuild a string. And you can indicate what set of characters should be inserted in the middle between each token.

If I do this, it will... ok...I need to do this on the array so: "s.split(' ').join('----')" will first return the array of tokens separated by space and will in turn build again a string with '----' between different tokens.

Source code from the video example

The String class can be used to build new strings, but it's preferable to use the standard syntax:

Source Code:
1.  > var name = 'Michel'; // use this rather than using new String(...)
2.  undefined
3.  
4.  >typeof name;
5.  "string"
6.  
7.  > var name = new String('Michel');
8.  undefined
9.  
10. > typeof name;
11. "string"
Some reminders about strings:
Source Code:
1.  > var name = 'Michel';
2.  Undefined
3.
4.  name.length;
5.  6
6.  name[0];
7.  "M"
8.  name[0] = 'Z';
9.  "Z"
10. name; // we cannot modify a string using s[index] = value;
11. "Michel"
12. 'Michel'.length;
13. 6
14. 'Michel'[0];
15. "M"
Explanations:

Useful methods: toUpperCase, toLowerCase, indexOf, charAt

These methods are all inherited from the String class:

Source Code:
1.  > var s = "I'm the Walrus";
2.  Undefined
3.  
4.  var s1 = s.toUpperCase();
5.  undefined
6.  s1;
7.  "I'M THE WALRUS"
8.  var s2 = s1.toLowerCase();
9.  undefined
10. s2;
11. "i'm the walrus"
12. s; // s is unchanged
13. "I'm the Walrus"
14. s.indexOf('w'); // no 'w' in s
15. 
16. -1
17. s2.indexOf('w');
18. 8
19. s2[8]; // char at index 8
20. "w"
21.
22. s2.charAt(8); // same as s2[8]
23. "w"
Other useful methods: lastIndexOf, chaining methods
Source Code:
1.  > s = 'wow wow wow!';
2.  "wow wow wow!"
3.   
4.  > s.lastIndexOf('w');
5.  10
6.   
7.  > s.indexOf('w', 1); // start looking at s at index=1, s[0] is ignored
8.  2
9.   
10. > var s1 = s.toUpperCase();
11. undefined
12.  
13. > s1;
14. "WOW WOW WOW!"
15.  
16. > s1.toLowerCase().lastIndexOf('w'); // we can chain method calls using '.'
17. 10

5.2.9 The most useful methods of the class String

The most useful methods of the String are: slice, substring, split, join.

The slice and substring methods

Both these methods can be used to extract a substring from a string. They take two parameters: the start and end index of the slice (element at end index will NOT be included in the slice): "please cut from this index, to this one, not included!".

These two methods are very similar.

Examples:
Source Code:
1.  > var s = "My name is Bond! James Bond!";
2.  undefined
3.   
4.  > s;
5.  "My name is Bond! James Bond!"
6.   
7.  > s.slice(11, 16);
8.  "Bond!"
9.   
10. > s; // s is unchanged
11. "My name is Bond! James Bond!"
12.  
13. s.substring(11, 16);
14. "Bond!"
15.  
16. > s; // s is still unchanged
17. "My name is Bond! James Bond!"
18. 
19. > s = s.substring(11, 16);
20. "Bond!"
21.  
22. > s; // this time s has changed, because we did s = s.substring(...), the same 
23.      // could have been done with s = s .slice(...)
24. "Bond!"

[Advanced] There is a difference between slice and substring, when the second parameter is negative

If you are a beginner, we recommend that you use substring for most common cases (as it will behave the same as slice) and that you stay away from negative parameters, where slice and substring show small differences.

Beginners: do not read what follows about slice and substring! There will be no related graded questions at the end of this chapter!

Source Code:
1.  > var s = "My name is Bond! James Bond!";
2.  undefined
3.   
4.  > s.slice(11, -1); // start from index = 11 to length-1, extract
      the end of the string from 11th element
5.  "Bond! James Bond"
6.   
7.  > s.substring(11, -1); // the reverse, extract from 0 until 11-1,
      get the first 10 chars
8.  "My name is "
9.   
10. > s.substring(1, -1); // extract from 0 to 1-1 = 0, get the first char
11. "M"

Actually, here is a summary of the common behaviors and the differences between slice and substring.

[Advanced] slice(start, stop) works like substring(start, stop)  with a few different behaviors

What they have in common:
Distinctions of substring():
Distinctions of slice():
The split(), join() and concat() methods

The split method returns an array of strings, the parameter is a separator. The join method builds a string from an array of strings.

Source Code:
1.  > var s = "My name is Bond! James Bond!";
2.  undefined
3.   
4.  > s.split(" ");
5.  ["My", "name", "is", "Bond!", "James", "Bond!"]
6.   
7.  > s;
8.  "My name is Bond! James Bond!"
9.   
10. > s.split(' ').join('-#-');
11. "My-#-name-#-is-#-Bond!-#-James-#-Bond!"
12.  
13. > s.split(' ').join('.......');
14. "My.......name.......is.......Bond!.......James.......Bond!"
15.  
16. > s.split('Bond!').join('.......');
17. "My name is ....... James ......."
18.  
19. > s.split('Bond!').join(' ');
20. "My name is James "
21.  
22. > s; // s is unchanged
23. "My name is Bond! James Bond!"
24.  
25. > s.concat("And I've made a lot of movies!");
26. "My name is Bond! James Bond! And I've made a lot of movies!"
27.  
28. > s; // s is also unchanged by concat
29. "My name is Bond! James Bond!"
30.  
31. > s = s + "and I've made a lot of movies!"; // this changes s
32. "My name is Bond! James Bond! And I've made a lot of movies!"
33.  
34. > s += " Action films!" // this too, most common syntax for
      concatenating strings
35. "My name is Bond! James Bond! And I've made a lot of movies!
      Action films!"
36.  
37. > s; // s changed too
38. "My name is Bond! James Bond! And I've made a lot of movies!
      Action films!"

5.2.10 Built-in JavaScript class: Math

It's not possible to do var m = new Math();

1.  > var m = new Math();
2.  VM5777:1 Uncaught TypeError: Math is not a constructor
3.  at <anonymous>:1:9
4.  (anonymous) @ VM5777:1

But the Math class has a lot of properties and methods that are useful for arithmetic expressions. They are all class methods and properties, so you will need to use the name of the class followed by the dot operator to access them.

Here are some examples:
Source Code:
1.  Math.PI;
2.  3.141592653589793
3.  Math.SQRT2;
4.  1.4142135623730951
5.  Math.E; // Euler constant
6.  2.718281828459045
7.  Math.LN2; // Neperian log of 2
8.  0.6931471805599453
9.  Math.LN10; // Neperian log of 10
10. 2.302585092994046

Random numbers between 0 and 1 with Math.random()

Math.random() returns a float value between 0 and 1.
Examples:
1.  Math.random();
2.  0.6033316111663034
3.  100 ... Math.random(); // between 0 and 100
4.  11.780563288516422

To get a number between a min and a max value, use this formula: val = ((max - min) * Math.random()) + min

And here is a utility function:
1.  function getRandomValue(min, max) {
2.    return ((max - min) * Math.random()) + min;
3.  }
4.  getRandomValue(5, 10);
5.  5.064160540161435
Math and rounding methods round(), ceil(), floor()
round: to get the closest integer value.
For example Math.round(Math.random()); will return 0 or 1.

Indeed, if Math.random() returns a value above 0.5, Math.round of this value will return 1, if the value is below 0.5, Math.round will return 0:

Source Code:
1.  > Math.round(Math.random());
2.  1
3. 
4.  > Math.round(Math.random());
5.  0
6.
7.  > Math.round(Math.random());
8.  1
9.
10. > Math.round(Math.random());
11. 1

Get the min and the max of two values with Math.min(a, b) and Math.max(a, b)

1. Math.min(12, 4);
2. 4
3.
4. Math.max(12, 4);
5. 12

A useful function that restricts a value between  min and  max bounds:

Source Code:
1.  function restrictValue(value, min, max) {
2.  return Math.min(Math.max(1, value), max);
3.  }
4.  restrictValue(40, 1, 20);
5.  20
6.  restrictValue(-10, 1, 20);
7.  1
8.  restrictValue(10, 1, 20);
9.  10

Math functions for arithmetical computations sin(), cos(), tan(), atan(), atan2(), pow(), sqrt()

Source Code:
1.  Math.pow(2, 8); //2^8
2.  256
3.  Math.sqrt(9);
4.  3
5.  Math.sin(Math.PI/2);
6.  1
7.  Math.cos(Math.PI/2);
8.  6.123233995736766e-17

Math.atan2(dy, dx) is useful for getting an angle between a point in a canvas and the mouse cursor

Here is a typical example of the use of Math.atan2 in a video game, in order to make an object follow the mouse cursor by moving towards it. Look at the code in the mainloop function.

CodePen: example using Math.atan2 in video game.
CodePen: example using Math.atan2 in video game.

5.2.11 Built-in JS class: Date

Let's see how to get a date by calling the Date constructor.

Without any argument, a call to new Date() returns the current date.

Note: The return value is actually a Date object, which is displayed by calling toString() on this object.

Source Code:
1.  var date = new Date();
2.  undefined
3.  date;
4.  Wed Apr 12 2017 11:10:28 GMT+0200 (CEST)
5.  date.toString(); // same thing!
6.  Wed Apr 12 2017 11:10:28 GMT+0200 (CEST)

We can also pass it an argument that can be:

... in this case it returns a date object that corresponds to the encoded date passed as argument.

Examples:

Source Code:
1.  > new Date('2017 04 28');
2.  Fri Apr 28 2017 00:00:00 GMT+0200 (CEST)
3.  
4.  > new Date('2017 1 2');
5.  Mon Jan 02 2017 00:00:00 GMT+0100 (CET)
6.  
7.  > new Date('2017 1 2 8:30');
8.  Mon Jan 02 2017 08:30:00 GMT+0100 (CET)

Numerical parameters can also be passed in this order: year, month (0-11), day (1-31), time (0-23), minutes (0-59), seconds , milliseconds (0-999). We do not have to pass everything but it should always be in this order.

Examples:

Source Code:
1.  > new Date(2017, 3, 16, 14, 43, 10, 120);
2.  Sun Apr 16 2017 14:43:10 GMT+0200 (CEST)
3.  
4.  > new Date(2017, 0, 10, 14);
5.  Tue Jan 10 2017 14:00:00 GMT+0100 (CET)
6.  
7.  > new Date(2017, 1, 28) // 1 is February! Month indexes start at 0!
8.  Tue Feb 28 2017 00:00:00 GMT+0100 (CET)
9.  
10. > new Date(2008, 1, 29);
11. Fri Feb 29 2008 00:00:00 GMT+0100 (CET)
12. > new Date(2017, 1, 29); // No February 29th in 2017! Gives 1st of March
13. Wed Mar 01 2017 00:00:00 GMT+0100 (CET)
14. 
15. > new Date(2017, 11, 31); // Happy new year!
16. Sun Dec 31 2017 00:00:00 GMT+0100 (CET)
17. 
18. > new Date(2017, 11, 32) // 32 Dec -> 1st of January!
19. Mon Jan 01 2018 00:00:00 GMT+0100 (CET)

One can build the date with a Unix timestamp (number of milliseconds since 1970):

1.  new Date(1199885822900);
2.  Wed Jan 09 2008 14:37:02 GMT+0100 (CET)
Calling Date() without "new" returns the current date as a string. It does not matter if we pass parameters:
1.  Date();
2.  "Sun Apr 16 2017 14:51:47 GMT+0200 (CEST)"

Useful methods

Source Code:
1.  var d = new Date();
2.  undefined
3.  
4.  d.toString();
5.  "Sun Apr 16 2017 14:52:52 GMT+0200 (CEST)"
6.  
7.  d.setMonth(2); // Change for month with index=2
8.  1489672372092
9.  
10. d.toString();
11. "Thu Mar 16 2017 14:52:52 GMT+0100 (CET)"
12. 
13. d.getMonth(); // get current month index
14. 2
Let's play with my birthday!
Source Code:
1.  var d = new Date(1965, 3, 16); // Michel Buffa's birthday
2.  undefined
3.  d.getDay(); // Sunday is 0
4.  5
5.  d; // let's verify
6.  Fri Apr 16 1965 00:00:00 GMT+0200 (CEST)
7.  Great, it was a Friday :-)

Let's write a small piece of code that will guess which days of the week Michel Buffa's birthday will occur, between 2017 and 2047:

Source Code:
1.  var dayOfTheWeek = [0,0,0,0,0,0,0];
2. 
3.  for (var year = 2017; year <= 2047; year++) {
4.    dayOfTheWeek[new Date(year, 4, 16).getDay()]++;
5.  }
6.  daysOfTheWeek
7.  [4, 4, 5, 5, 4, 4]    // 4 times on a Sunday, Monday, Friday and Saturday,
8.  [4, 4, 5, 5, 5, 4, 4] // 5 times on Tuesday, Wednesday and Thursday
Explanations:

And here is a full version with input fields and results displayed in an HTML table:

CodePen: example input fields in HTML table.
CodePen: example input fields in HTML table.

5.3.1 The HTML table basics

The <table> element helps with rendering tables in an HTML document.

Each table row is defined with the <tr> tag (Table Row). A table header is defined with the <th> tag (Table Header). By default, table headings are bold and centered. A table data/cell is defined with the <td> tag (Table Data). In each cell, you can have other HTML elements/tags. You can have only "column table headers" (the first row of the table will be in bold), or you can also have "row headers" (first cell of each row).

Best practice for making the table accessible: always add a <caption> tag inside the <table> tag. Data tables very often have brief descriptive text before or after the table that indicates the content of that table. This text should be associated to its respective table using the <caption> element. The <caption> element must be the first thing after the opening <table> tag.

Second best practice for accessibility: use a scope attribute with all <th scope = "row or column"> for identifying whether a table header is a column header or a row header. We invite you to read  these guidelines for making accessible tables.

Typical example:
Source Code:
1.  <table>
2.    <caption>A typical HTML table</caption>
3.    <tr>
4.      <th scope="col">Given Name</th>
5.      <th scope="col">Family Name</th>
6.      <th scope="col">Age</th>
7.    </tr>
8.    <tr>
9.      <td>Michel</td>
10.     <td>Buffa</td>
11.     <td>52</td>
12.   </tr>
13.   <tr>
14.     <td>Dark</td>
15.       <td>Vador</td>
16.       <td>Unknown</td>
17.   </tr>
18.   <tr>
19.     <td>Luke</td>
20.     <td>Skywalker</td>
21.     <td>Unknown</td>
22.   </tr>
23. </table>

Most of the time, we add some CSS rules for rendering cell/row/table borders and for adjusting spacing between the text in the cells and the cell borders. Let's look at some examples.

Example #1: HTML table with a very light CSS styling
CodePen: HTML table with a very light CSS styling.
CodePen: HTML table with very light CSS styling.
This is a static table. You can look at the CSS code:
Source Code:
1.  table {
2.    width:100%;
3.    border:1px solid;
4.  }
5.
6.  tr, th, td {
7.    border:1px solid;
8.    font-family:courier;
9.  }
10.
11. td {
12.   text-align:center;
13.   padding:10px;
14. }
Explanations
:
Example #2: with more CSS styling (flat design)
CodePen: HTML table with a very light CSS styling.
CodePen: HTML table with a very light CSS styling.
Example #3: with colored lines, header, footer, legend
Look at the CSS - it's the only part that changed:
CodePen: change CSS.
CodePen: change css.

5.3.2 The HTML table JavaScript API (4:43)

Live coding transcript: HTML table JavaScript API

The HTML table JavaScript API.

This time, we will talk about HTLM tables and their JavaScript API. Just to remind you, an HTML table uses different tags. The most common is <table> for defining the table, <tr> is for a row: table row (tr), inside a row, you've got <td> for table data (td), and you can have also table body, and so on. We recommend you to go to the HTML5&CSS Fundamentals course for having a full survey of HTML tables.

Here, I defined a table with a header, and 3 rows. And we'll see how we can use some functions from the API for inserting a row or deleting a row. It's very easy. First, you need to get a reference on the table, so put an id on your table. Here, I've set the table as for id "myTable". We use query selector "#myTable" to get a reference on the table.

Then, using the table object, you can use different methods that are described in the course, but the must common one is "insertRow()" without any argument. Without any argument: that means insert at the end of the table. If you pass an index here, it will be the position, the location, where you want to insert the new row. And once you created the row, you can use "innerHTML" to put some HTML code inside the row.

Here, I use some <td> elements to create 3 different table data, table cells in the row. If I click "Add a new row", it will call this callback "insertRow()", that will insert a row at the end of the table with "new", "new", "new" inside. I just made the same structure as I had in the static elements. I mean a <tr> with 3 <td> inside. I could have used as well, instead of " innerHTML", I could have built the cell one by one using "row.insertCell()".

From the table I inserted the row, from the row I insert a cell and then I use the innerHTML" to add some HTML in a new row. For example, I can put the first cell in bold using this "Add a new row". I've just inserted the new row made of 3 cells. Row that is inserted creates the cells inside: New cell1, New cell2, New cell3. You see this API is quite simple.

For deleting a row when I click on this button, I will call with a click event listener the "deleteFirstRow()" function. It's very similar to inserting a row. I first get a reference on the table using a "querySelector". I get a table object and I call "deleteRow()", 0 being the first line, the header. So "deleteRow(1)" will delete the first row from the body of the table. Each time I click, it deletes a the first row and when I click on "add a new row", it adds a new row.

We could have created the whole table itself dynamically. This will be shown in a next video where we consume remote data from Web services, get the data and create on the fly, create dynamically a table with rows and cells that will be used for displaying the data we just collected.

Source code from the above video

The source code shown in the above video is available  on this CodePen.

There is a JavaScript API associated with the HTML table elements that makes dynamic table management possible, enabling you to add or delete a row, add or delete a cell, modify the content of the cells, etc.

We've already seen some examples in the course, but we have not completely covered the table JavaScript API.

The table object (<table>)

When you look for a table using the DOM API or the selector API, or when you create a table using the DOM API, you get a Table object:

1.  var table = document.getElementById("myTable");
2.  var table = document.querySelector("#myTable");
3.  var table = document.createElement("table"); // creates a new table

Like all objects, an instance of Table will have properties and methods:

Table: most useful properties; rows, caption, tFoot & tHead. Table: most useful methods.

Example that adds a new row or removes a row to/from a table using the insertRow()/deleteRow() methods:

CodePen: a typical HTML table.
CodePen: a typical HTML table.

Notice the use of row.innerHTML= here to add some cells to the row. We will soon see another method for doing this.

The tableRow object (<tr>)

When you look for a row using the DOM API or the selector API, or when you create a row using the DOM API, you get a Row object:

1.  var row1 = document.getElementById("row1");
2.  var row1 = document.querySelector("#row1");
3.  var newRow = document.createElement("row"); // creates a new row
You can also access a row from the rows property of a table:
Source Code:
1.  var t = document.createElement("table");
1.  undefined
2.  var r1 = t.insertRow(0);
3.  undefined
4.  r1.innerHTML="<td>Hello</td>";
5.  "<td>Hello</td>"
6.  var r2 = t.insertRow();
7.  undefined
8.  r2.innerHTML="<td>Hello 2</td>";
9.  "<td>Hello 2</td>"
10. var row1 = t.rows[0];
11. undefined
12. row1;
13. <tr><td>Hello</td></tr>

Like all objects, a tableRow object has properties and methods. Here are the most useful ones:

Most useful properties; cells, rowIndex and sectionRowIndex. Most useful methods; insertCell() and deleteCell().

Below are new versions of the previous examples, but instead of using the innerHTML of the TableRow object, we use the insertCell() method.

CodePen: A typical HTML table.
CodePen: a typical HTML table.
Notice how we've created the new row cells:
Source Code:
1.  function insertRow() {
2.    var table = document.querySelector("#myTable");
3.    // without parameters, insert at the end,
4.    // otherwise parameter = index where the row will be inserted
5.    var row = table.insertRow();
6.    var cell1 = row.insertCell();
7.    cell1.innerHTML = "New cell1";
8.    var cell2 = row.insertCell();
9.    cell2.innerHTML = "New cell2";
10.   var cell3 = row.insertCell();
11.   cell3.innerHTML = "New cell3"; 
12. }

Should we use insertCell() or just row.innerHTML= "<td> ... </td>" ? It's up to you: depending on the HTML that you plan to insert into each cell, one version may be more readable than the other.

5.3.3 HTML forms: best practices

Creating accessible forms

Forms are commonly used to enable user interaction within Web sites and Web applications, for example, for login, registering, commenting, and purchasing.

Since HTML5 provides functionalities to assist with accessibility, developers should make a concerted effort to mark up Web based forms. The following two guidelines are to give you a good start to make your forms accessible:

  1. For every form field, ensure that a descriptive label is provided and use the <label> element to identify each form control.
  2. For larger or complex forms, use the <fieldset> and <legend>  elements to respectively group and associate related form controls.
Further reading:

The WAI Web site hosts a Forms tutorial where you will find more guidelines to help make your forms truly accessible: Form Instructions, Validating Input, User Notifications, Multi-Page Forms, and Custom Controls.

Why is this important?

Forms can be visually and cognitively complex and difficult to use. Accessible forms are easier to use for everyone, including people with disabilities.

Labeling controls
Labels need to describe the purpose of the form control

Form fields and other form controls usually have visible labels, such as "E-mail Address:" as the label for a text field (see figure below).

E-mail address.

When these labels are marked up correctly, people can interact with them using only the keyboard, using voice input, and using screen readers. Also, the label itself becomes clickable, which enables a person who has difficulty clicking on small radio buttons or checkboxes to click anywhere on the label text.

Associating labels explicitly

Whenever possible, use the label element to explicitly associate text with form elements. The for attribute of the label must exactly match the id of the form control.

Example #1 (click on the label, not on the input field to see the effect):

First name.
Source Code:
1.  Bottom of Form
2.  <label for="first_name">Your First Name</label>
3.  <input id="first_name" type="text" name="fname"/>
Alternative example #1:

Note that you can also include the <input> element inside the <label>...</label> element, and also add a <span lang="en"> for example, to indicate the language used in the label. Sometimes, nesting labels and inputs can also make CSS styling easier and produce better results with screen readers.

Source code (with <input> inside the <label>):
1.  <label for="first_name"><span lang=en">Your First
      Name</span>
2.    <input id="first_name" type="text" name="fname"/>
3.  </label>
Example #2 (click on the label "Subscribe to newsletter" to see the effect):
First name and Subscribe to newsletter checkbox.
Source Code:
1.  Bottom of Form
2.  <label for="firstname">First name:</label>
3.  <input type="text" name="firstname" id="firstname"><br>
4.  <label for="subscribe">Subscribe to newsletter</label>
5.  <input type="checkbox" name="subscribe" id="subscribe">
Labeling buttons

The label of a <button> element is set inside the element and can include markup. This allows advanced accessibility hints to be included, such as marking up language change.
Example: <button>Mon <span lang="fr">bouton</span></button>, for a button with a label in French.

When using the <input> element to create buttons, the label is set in the value attribute of the element.
Example: <input type="submit" value="Please submit">, will be rendered as a button.

Source code for an example of "Submit" and "Cancel" buttons:
1.  <button type="submit">Submit</button>
2.  <button type="button">Cancel</button>
3.  <input type="submit" value="Submit">
4.  <input type="button" value="Cancel">
These will produce the same results:
Submit and Cancel buttons. Labeling text areas: Enter your address.
Source Code:
1.  <label for="address">Enter your address:</label>
2.  <br>
3.  <textarea id="address" name="addresstext"></textarea>

Grouping controls

Groupings of form controls, typically groups of related checkboxes and radio buttons, sometimes require a higher level description. Grouping related form controls makes forms more understandable for all users, as related controls are easier to identify.

Associating related controls with fieldset

Grouping needs to be carried out visually and in the code, for example, by using the <fieldset> and <legend> elements to associate related form controls. The <fieldset> identifies the entire grouping and <legend> identifies the grouping's descriptive text.

Example #1: Radio buttons

In the example below, there are three radio buttons that allow the user to choose an output format. Radio button groups should always be grouped using <fieldset>.

Output formats; text, csv and html.
Source Code:
1.  <fieldset>
2.    <legend>Output format</legend>
3.    <div>
4.      <input type="radio" name="format" id="txt" value="txt" checked>
5.      <label for="txt">Text file</label>
6.    </div>
7.    <div>
8.      <input type="radio" name="format" id="csv" value="csv">
9.      <label for="csv">CSV file</label>
10.   </div>
11.   [...]
12. </fieldset>
Example #2: Checkboxes

In the example below, there are three checkboxes that are all part of an opt-in function for receiving different types of information.

Example checkboxes.
Source Code:
1.  <fieldset>
2.    <legend>I want to receive</legend>
3.    <div>
4.      <input type="checkbox" name="newsletter" id="check_1">
5.      <label for="check_1">The weekly newsletter</label>
6.    </div>
7.    [...]
8.  </fieldset>

[Advanced] Associating related controls with WAI-ARIA

WAI-ARIA provides a grouping role that functions in a similar way to fieldset and legend. For example, a div element can have role=group to indicate that the contained elements are members of a group.

WAI-ARIA roles are very important in the accessibility world, and we invite you to see an example provided in the  associated WAI tutorial. Find also another WAI-ARIA documentation on MDN.

5.3.4 HTML forms and JavaScript (9:46)

Live coding video: HTML Forms Best Practices

CodePen: HTML forms best practices.
CodePen: HMTL forms best practices.

Hi everybody. For this first video, we will talk about traditional form design. When you design a form, using the form element, usually you add two attributes to it:

1) first attribute called action that has for value the URL of the server side component that will process the data entered and sent when you submit the form. And,

2) an attribute called method that will indicates the way the browser will send the data from the form to the server. As this course is really focused on HTML5, that is a 100% client-side technology, we're not going to explain how we can process form data in PHP, in Java or in asp.NET or whatever. We will focus on the client-side on the new input field, the new attributes and a new validation system that is included in the browser that implements the new HTML5 features.

One good practice, this is not new with HTML5, is to group different input elements into a fieldset. You can see some details about this practice in the accessible form part of the course. Here, we use the fieldset that generated this small bar here. That is a visual rendering of the group and we use the legend element inside that render as a title in the fieldset border. Inside, for the sake this example, we just used two input fields of type="text".We associated a label with the 'for' attribute that matches the ID attributes.

This is a good practice for accessibility, and if you click on the label, it gives the focus to the input field thanks to the 'for' and the ID attributes that match. What we can just add is some CSS to make this a little bit nicer. Usually for the fieldset I add some padding. Padding if for the internal space; you can see that I added some space here. And for separating the different lines here, I usually add some margin-bottom to the labels. with a value, 10px for example.

And in order to make this work, I use display 'inline-block' for the labels. OK, I made a small mistake here, about the margin-bottom. And you can see that if I change the value or the length of the levels, the input fields are no more aligned. In order to align the input fields, the common technique is input, float them to the right and give them a right margin. Let's say maybe 7px for the margin-right, and give them a width...

You see if I change the length of the labels the input fields are aligned. This is not new with HTML5. What is new is that, okay let me just add a border-radius to the fieldset. This makes nice rounded corners here. Okay what is new is that some attributes like this one 'required' that will make the input field invalid if it's empty.

And I can visualize this automatically, because the new input fields with HTML5 inherit a CSS pseudo class called 'invalid'. I use the column followed by the keyword 'invalid' to visualize that. Or background-color:pink;. Like this you can see that the fields are invalid because they're pink and become valid as soon as I type something inside. If I try to submit a form with an 'invalid', field it pops up some bubbles with an error message.

And the message is in the language is the one of my operating system, so here it's in French. This is new. It's called the built invalidation system and some new input fields like, for example, the email: the input type="email". Just change that... This time it will become valid not when I type something but also when I type something that looks like a valid email address. If I remove this character The @ character here, it becomes invalid.

We've got some defaults rules for validating new type of input fields. If I want to enter an age, I can use the new age... type="number" for example. Like this, it's an input field for entering numbers and this one has some min values like 1 year old, max value is 120 years old, and if I type something that is not valid, you can see that it's with the pink background, meaning it is 'invalid'.

If I type a real number, it becomes valid. Or if I choose a real number. Also, particularities with this input field, is that you can use the step attribute...step=5 means <I made a mistake> okay like this it will jump from 1 to 6. If the value is not a multiple of 5, it's 'invalid'. Starting from 0. Okay if I enter 20, it's valid but 21 is not.

If I add 5 you can see it jumps from one multiple of 5 to another one. I'm going just to show you the last example but there are more input fields on that brought by HTML5, all the details will be in the course. For example, if you want to select a birth date, there is a new input field of type="date. You can also indicate some constraints with attributes, but you will see that in the dedicated part of the course.

Here, you got directly without writing any JavaScript a calendar that is popping up to select your birth date... Let's say something that is random. And here you've got a birth date, and you can enter using the keyboard but if you type something that is invalid..This is the really basics of HTML5 forms. There are 13 new input elements, lot of new attributes and others elements that can be used to constraint the values. For example, instead of having a calendar, we can have only a small set of dates to choose from. All these things are explained in the course, take some time to read and look at all these examples.

This is the end of this video good luck ... good work !

Source code from the example shown in the above video:

We highly recommend that you follow the W3Cx  HTML5 Coding essentials and Best Practices course that has an entire module  dedicated to HTML5 forms.

Forms are a way to get user input which is either sent to a remote server, or processed locally, or both.

This section of the course only covers local processing and the client-side part, with a focus on JavaScript processing.

Typical example:
CodePen: form input can be sent to a server without JavaScript.
CodePen: form input sent to server without JavaScript.
HTML form input can be sent to a server without JavaScript

If a form's content is sent to a remote server, on the server side, you may have PHP, Java, C#, Ruby, Python, etc. components. There are several ways to collect server-side data from a form in a Web page: REST Web services, servlets, Microsoft ASP pages, etc.

On the client side, the forms indicate to which server and how the data should be sent,  using the action and method attributes respectively. A <button type="submit"> or an <input type=submit> field is used to submit the form content.

For example: <form action="myServerCode.php" method="POST">...</form>. Here, we set the URL of the server side code (myServerCode.php), and the HTTP method that will be used by the browser for sending the form content (POST).

Example of HTML5 form that will not be sent if invalid input fields are present. Notice that the JavaScript part is only used for giving feedback while entering the password. No JavaScript is used for sending the form data, or for complex, global validation:

CodePen: validating user input 'on the fly' using JavaScript.
CodePen: validating user input 'on the fly' using JavaScript.
HTML form input can be sent using Ajax / JavaScript

Another approach is to use JavaScript for sending the form content with Ajax.

JavaScript can be used for validating user input "on the fly"

While one is typing or selecting a color, or moving a slider, JavaScript event listeners can be used to track the user's interactions in real time, and perform some validation steps along with giving visual feedback.

We've already seen how we can track the keys typed in an input field in real time:

CodePen: simple input field validation using the 'input' event.
CodePen: simple input field validation.
JavaScript can be used for a more global validation before sending a form to a remote server

Example: checking that a password entered twice is identical in two different input fields, that some values are coherent (e.g. a birthday cannot be in the future), etc.

CodePen: example use of the validation API.
CodePen: example use of the validation API.

JavaScript can be used to make a WebApp that uses form data locally, perhaps with some client-side persistence API.

For example, a contact manager that will work offline, saving data locally, in a database inside the browser. Data will be displayed in a dynamic HTML table, without the need for a remote database.

This is the small project we will build together at the end of the course. :-)

5.3.5 Discussion and projects

Here is the discussion forum for this part of the course. Please either post your comments/observations/questions or share your creations.

Suggested topics

Optional projects
Magnifying glass.
Previous and next buttons.

5.4.1 What is JSON? (4:42)

Live coding video: JSON notation, working with LocalStorage and remote data

JSON notation, working with LocalStorage.

Hi! I would like to present you the JSON format that is string-based format for exchanging, on the Web, JavaScript objects. Also, for storing JavaScript objects in databases. It's very popular and used by many Web services. A Web service is a remote server that uses a URL to send you some formatted JavaScript data.

Here you've got an example from the jsonplaceholder.typicode.com Web site that provides some examples of JSON data set. If you want some photos, some pictures, you click on it and you've got a string-based notation, a JSON version of an array. An array that contains pictures with albums, thumbnails)

It's the same data format we used in a previous module for an optional project about pictures and albums. How do you work with such a format? There are 2 different utility methods from the JSON predefined object.

One is called "stringify()" and will be useful for converting a JavaScript object into JSON. And the other one will be "JSON.parse()" that will take a JSON object, a JSON string, and give back a JavaScript object.

Let's see some examples. I just took an array... if you try to stringify the array...you obtain an object that contains the array with quotes around. This is the JSON notation of an array. If you've got more complex objects, for example, this one: it's an object with different properties and one of the properties is an array that contains in turn objects. It's just an example of the albums made by Metallica.

If I try this, "JSON.stringify()" with this object, I get a JSON version of this object, and this can be sent through HTTP or can be downloaded from a remote server. HTTP is hypertext transfer protocol. Only text can be exchanged using HTTP and JSON is pure text. However, if I've got to know a JSON string, I cannot access any property because this is no more a JavaScript object. If I want to get back the original object from the string, I will need to use "JSON.parse()". And this is a real JavaScript object. I can access its properties and call its methods. This is all we need to know about JSON.

"JSON.parse()" turns a JSON string to a JavaScript object you can use, and "JSON.stringify()" takes a JavaScript object and turns it into a JSON string.

In the next lesson, we will see how we can use JSON objects, for example, downloading them from a remote data source and displaying their values in an HTML table.

JSON stands for JavaScript Object Notation. It's a standard for transforming nearly any object into a string representation that is human readable. It became a standard for exchanging data to/from a remote HTTP server, and is available for many other languages in addition to JavaScript.

A JavaScript object o in JSON looks a lot like what o.toString() returns.

There are two main methods to know:

  1. Transform any JavaScript object in JSON:

var jsonStr = JSON.stringify(obj);

  1. Transform any JSON string into a JavaScript object:

var jsObj  = JSON.parse(jsonStr);

Let's see some examples:
Source Code:
1.  var x = 3;
2.  undefined
3.  JSON.stringify(x);
4.  "3"
5.  var simpleObject = {x:12, y:30};
6.  undefined
7.  JSON.stringify(simpleObject);
8.  "{"x":12,"y":30}"
9.  var anArray = ['Monday', 'Tuesday', 'Wednesday'];
10. undefined
11. JSON.stringify(anArray);
12. "["Monday","Tuesday","Wednesday"]"
13. var complexObject = {name:'Metallica',
14. albums:[
15. {name:"Master of Puppets", year:1986},
16. {name:"Black Album", year:1991}
17. ]
18. };
19. Undefined
20. JSON.stringify(complexObject);
21. "{"name":"Metallica","albums":[{"name":"Master of Puppets","year":1986},{"name":"Black Album","year":1991}]}"

In the above examples, you can see JSON representations of a simple variable of a predefined type, of an array, of a simple object, of an object that contains an array of objects (Metallica example).

And indeed, it looks like the code you typed to create the objects, with quotes around it and around the property names. This is why it is called JavaScript Object Notation ;-)

You cannot use JSON objects as JavaScript objects

The JSON representation of JavaScript objects is a string. JSON has been developed mainly for replacing XML as a format for exchanging data between a client and a remote HTTP server. It has become very popular as the format for exchanging data when a Web Application uses Ajax for its communications with the HTTP server.

Ajax is a way to send / receive data in the background, without the need to reload the Web page. Along with the DOM API, the appearance of this  technology in 2005 with Internet Explorer, made it possible to make Web pages more dynamic. Google Maps was one of the first popular Ajax-powered Web application: as you moved the map, new parts arrived (downloaded in the background from the Gmap HTTP server), and the page updated to display these new parts.

JSON is also very practical for storing objects where strings are expected. There is a data store in your browser called LocalStorage that can be used as a small database for Web applications, but it stores only pairs of key/values in the string format. If you want to save a JavaScript object, you will have to turn it into JSON, then save it. When you read it from the data store, you will need to turn it back from JSON to JavaScript.

Here is a first example that turns an object into JSON and back into a JavaScript object:

Source Code:
1.  > var metallica = {name:'Metallica', albums:[{name:"Master of
    Puppets", year:1986}, {name:"Black Album", year:1991}]};
2.  Undefined
3.  
4.  var metallicaJSON = JSON.stringify(metallica);
5.  undefined
6.  
7.  metallicaJSON;
8.  "{"name":"Metallica","albums":[{"name":"Master of Puppets","year":1986},
           {"name":"Black Album","year":1991}]}"
9.  
10. metallicaJSON.name; // metallicaJSON is not a JavaScript object
11. undefined
12. 
13. metallica.name; // metallica is an object
14. "Metallica"
15. 
16. var obj = JSON.parse(metallicaJSON); // JSON -> object
17. undefined
18. 
19. obj.name; // this is an object
20. "Metallica"

With the JSON representation of an object you cannot access the original object's properties using the "." operator, nor call its methods. The JSON format only stores the list of the object properties (name and value) as a string. Look at line 10: we cannot access the name property of the JSON representation of the metallica object defined at line 1.

When we parse a JSON string using JSON.parse(), we get a real JavaScript object, and we can access its properties (lines 16 and 19).

5.4.2 Consuming JSON remote data (10:10)

Live coding Video: Xhr2, remote JSON data, dynamic table

CodePen: consuming JSON remote data.

This time we will look at how we can send an AJAX request to a remote server, get the data in JSON, parse this data and build dynamically an HTML table that will display the results.

I prepared a small template, a small HTML template with a button that will call a "search()" function that is located in the JavaScript code and we will write it together. And we also prepared the div location that is not visible here, below the button, that will contain the table that we will create dynamically.

First, let's have a look at the URL of the data source. I'm still using the "jsonplaceholder.typicode.com" Web site. And if we click on "/user", you got here the URL that returns the list of users, actually an array of objects, each object being a user with properties and values. To send a request, we will use 2 different methods, one that is called "XhR2" or XML Http Request level 2.

And one that uses a brand-new API that is implemented only in recent browsers that is called "fetch". Let's start with "XhR2". I declare a URL, and "queryURL". I'm just following the same syntax as in the example. And we need to create an XML Http Request: "xhr = new XMLHttpRequest ()".

That's it: "XMLHttpRequest()". And then you indicate what is the parameter of the request: "xhr.open()". We're going to do a "GET". "GET" is an http order that means 'go on the Web and get me the data from there'. And you indicate also the URL. And the last parameter will be set to true. Then, you will send the request. When you do this, your request is sent but it can take some time. And for getting the data and processing it, we must indicate a callback that will call by the browser only when the response arrives.

This is how it works: "xhr.onload =" and you indicate the callback function, and usually, you also use the event as the only parameter. And here, we can just start trying to see if it works. I open the console, here, click on the button and see ... "xrh" is not defined. It's "xhr". Ok, I clear the console! Yes, the response arrived. I can even use the devtool debugger. If I click on "Network", "XHR", clear. Click on the button, I will see the request here and if I click on it, I can see the response.

I see that I've got the JSON object from the remote server. Now that the response arrived, I can directly display it: "xhr.response". It's a string, I save and run it again. Ok, sorry this was too long, but I can open the real devtool console, and I can see that I got the object here.

This has been printed by the "console.log()". In order to work with this object, I will need to convert it to a real JavaScript object: "users = (xhr.response)". But in order to turn it into JavaScript object, we use "JSON.parse()", you remember from the previous video? And here, just to debug I can try to write: 'first user' ...Because this object is an array, you see it's an array.

Displaying the first of them should work. It says 'first user' is an object. I can also directly turn it into a string. Ok, parentheses is missing...And I can see this time, the first user, the 'first user' that has been displayed. Now we will use this! That will check that it works: we can call displayUsersAsATable(...) passing the users. In order to insert a table here, first we need to create the table.

Let me copy and paste some code. We start by getting a reference on the HTML div in the page that was called users, "id = "users". Then we create a table: document.createElement("table");, and then we can try to insert rows for each user. So "users.forEach()" takes a callback with the first parameter being the current element of the user's array. "console.log(currentUser.name)"...let's try this to see if it works... Clear ... save...Click on the button... and I see the names of the users.

Now, I'm going to add a row to a table. "table.insertRow();" put this in variable called "row", and then I can do: "row.innerHTML= ", for example, just the name.

Here, I inserted rows whose content is the name of the user. And in the end, what we do is that we will add the table to the div. So, "usersDiv.appendChild()", or "append" works too on modern browsers, append(). And we put the table in it. Let's try...Clear. "usersDiv" with a "s" and it works! Now, in order to have a nice table, I could also add some CSS to make it better, or I can define some <td> (table data) to make a nicer table. And I can display for example another property that will be the email of the person. That's it!

Source code from the above live coding video
JSON data from a REST Web Service

Most "big sites" provide what we call a REST API. This means "they propose to send/receive data to/from programs over HTTP", and most of the time the JSON format is one of the possible transport formats for the data. Google APIs, Facebook and Amazon APIs are like this.

JSONPlaceholder is a free online REST service that you can use whenever you need some fake data in JSON. Faking a server is great for tutorials, and this is exactly what the next example does. Please open this URL - you will see some JSON data coming from the server and being displayed in your browser as shown below:

JSON: working with remote data using XhR2 API.

And we would like to use these data in our code, manipulating them as a JavaScript object.

This course does not cover Ajax and what we call "asynchronous JavaScript". However, we can show you two simple examples that use the Xhr2 API for Ajax requests and the new fetch API that is simplest to use.

Downloading JSON data using the XhR2 API

CodePen: working with remote data using XhR2 API.
CodePen: working with remote data using XhR2 API.
JavaScript source code extract:
Source Code:
1.  function search() {
2.    var queryURL = "https://jsonplaceholder.typicode.com/users";
3.  
4.    var xhr = new XMLHttpRequest();
5.    xhr.open('GET', queryURL, true);
6.    // called when the response has arrived
7.    xhr.onload = function(e) {
8.      var jsonResponse = this.response;
9.      // turn the response into a JavaScript object
10.     var users = JSON.parse(jsonResponse);
11.     displayUsersAsATable(users);
12.   }
13. 
14.   // in case of error
15.   xhr.onerror = function(err) {
16.     console.log("Error: " + err);
17.   }
18. 
19.   // sends the request
20.   xhr.send();
21. }
Explanations:
[Advanced] Downloading JSON data using the fetch API

The Fetch API provides a JavaScript interface for accessing and manipulating parts of the HTTP pipeline, such as requests and responses. It also provides a global fetch() method that provides an easy, logical way to fetch resources asynchronously across the network. You fetch data from a URL, then, you do something with the response, then you do something else. If there is an error you can catch this error and display, for example, an error message.

See this blog post for a detailed tutorial. Asynchronous JavaScript and JavaScript promises (the fetch...then...then... is based on the concept of "promises") is not detailed in this course.

The Fetch API provides a JavaScript interface for accessing and manipulating parts of the HTTP pipeline, such as requests and responses. It also provides a global fetch() method that provides an easy, logical way to fetch resources asynchronously across the network. You fetch data from a URL, then, you do something with the response, then you do something else. If there is an error you can catch this error and display, for example, an error message.

See this blog post for a detailed tutorial. Asynchronous JavaScript and JavaScript promises (the fetch...then...then... is based on the concept of "promises") is not detailed in this course.

CodePen: get remote list using fetch API.
CodePen: Get remote list of users' names & emails using fetch API.
Source Code:
1.  function search() {
2.    var queryURL = "https://jsonplaceholder.typicode.com/users";
3.  
4.    fetch(queryURL)
5.    .then(function(response) {
6.      // response is a json string,
7.      // convert it to a pure JavaScript object.
8.      return response.json();
9.    })
10.   .then(function(users) {
11.     // users is a JavaScript object here.
12.     displayUsersAsATable(users)
13.   })
14.   .catch(function(error) {
15.     console.log('Error during fetch: ' + error.message);
16.   });
17. }

In contrast to XhR2, fetch is based on a concept called "JavaScript promises". You recognize promises when you see ".then..." ".then...".

5.4.3 The LocalStorage API

Let's look at an example of use: the LocalStorage API as a client-side database for JavaScript objects.

The Web Storage API (localStorage, sessionStorage)

Cross-Browser client-side storage.

The Web storage API (see the  related W3C specification) introduces "two related mechanisms, similar to HTTP session cookies, for storing structured data on the client side".

Indeed, Web Storage provides two interfaces - sessionStorage and localStorage - whose main difference is data longevity. This specification defines an API for persistent data storage of key-value pair data in Web clients.

With localStorage the data will remain until it is deleted, whereas with sessionStorage the data is erased when the tab/browser is closed.

For convenience, we will mainly illustrate the localStorage object. Just change "local" to "session" and it should work (this time with a session lifetime)

Table of key/value pairs.

Simple key-value stores, one per domain (following the  same origin policy)!

localStorage is a simple key-value store, in which the keys and values are strings. There is only one store per domain. This functionality is exposed through the globally available localStorage object. The same applies to sessionStorage.

Source Code:
1.  // Using localStorage.
2.  
3.  // Store data.
4.  localStorage.lastName = "Bunny";
5.  localStorage.firstName = "Bugs";
6.  localStorage.location = "Earth";
7.  
8.  // Retrieve data.
9.  var lastName = localStorage.lastName;
10. var firstName = localStorage.firstName;
11. var location = localStorage.location;

This data is located in a store attached to the origin of the page. We've created  a JsBin example in which we've included the above code.

Once opened in your browser, the JavaScript code is executed. With the browser dev. tools, we can check what has been stored in the localStorage for this domain:

Example: localStorage. Devtools can be used to show localStorage.

Differences with cookies?

Cookies are also a popular way to store key-value pairs. Web Storage, however, is a more powerful technique than cookies. The main difference is in size limits: cookies are limited to a few KBytes whereas Web Storage may extend to several MBytes. Also, cookies generate additional HTTP request traffic (whether to request a Web page, an image, a stylesheet, a JavaScript file, etc.).

Objects managed by Web Storage are no longer carried on the network and HTTP, and are easily accessible (read, change and delete) from JavaScript, using the Web Storage API.

External resources

5.4.4 Discussion and projects

Here is the discussion forum for this part of the course.

Suggested topic

Optional projects

5.5.1 A contact manager (part 1)

In this final part of the course, let's build together a minimal contact manager that shows how to use ES6 classes, local storage, forms and the HTML table JavaScript API.

This is a play project that you can easily improve:

Let's start with a simple skeleton (no GUI), beginning with the Contact class.

Source Code:
1. class Contact {
2.   constructor(name, email) {
3.     this.name = name;
4.     this.email = email;
5.   }
6. }

As you can see, a contact is just a name and an email. We will use the above class like this:

1. var c1 = new Contact("Jimi Hendrix", "[email protected]");
2. var c2 = new Contact("Robert
   Fripp", "[email protected]");

Then you can print the properties of contact c1 or c2 using for example console.log(c1.name), console.log(c2.email), etc.

A minimal ContactManager class:

Source Code:
1.  class ContactManager {
2.    constructor() {
3.      // When we build the contact manager, it
4.      // has an empty list of contacts.
5.      this.listOfContacts = [];
6.    }
7.    add(contact) {
8.      this.listOfContacts.push(contact);
9.    }
10.   remove(contact) {
11.     // We iterate on the list of contacts until we find the contact
12.     // passed as a parameter (we say that they are equal if emails match)
13.     for(let i = 0; i < this.listOfContacts.length; i++) {
14.       var c = this.listOfContacts[i];
15.       if(c.email === contact.email) {
16.         // Remove the contact at index i.
17.         this.listOfContacts.splice(i, 1);
18.         // stop/exit the loop.
19.         break;
20.       }
21.     };
22.   }
23.   printContactsToConsole() {
24.     this.listOfContacts.forEach(function(c) {
25.       console.log(c.name);
26.     });
27.   };
28. }

Explanations:

We can use the contact manager like this:

Source Code:
1.  var cm = new ContactManager();
2.  var c1 = new Contact("Jimi Hendrix", "[email protected]");
3.  var c2 = new Contact("Robert
    Fripp", "[email protected]");
4.  var c3 = new Contact("Angus Young", "[email protected]");
5.  var c4 = new Contact("Arnold
    Schwarzenneger", "[email protected]");
6.  
7.  console.log("--- Adding 4 contacts ---")
8.  cm.add(c1);
9.  cm.add(c2);
10. cm.add(c3);
11. cm.add(c4);
12. 
13. cm.printContactsToConsole();

As you can see, this is a very minimal version. It's always a good idea to start with very simple structures/classes, and a few methods. Then type the code on CodePen or JSBin and use the devtool console. Check that there are no syntax errors, that everything runs smoothly.

Here is the CodePen of this minimal version. Click on the CodePen label on the top right, and once in CodePen, open the console:

Adding a method for sorting the list of contacts by name

Do you remember the sort() method you can use on arrays? We saw it in modules 2 or 3. Since our array contains objects, we must provide a callback for comparing two elements by name. Here is the code for the new sort() method we added to the ContactManager class:

Source Code:
1.  sort() {
2.    // As our array contains objects, we need to pass as argument
3.    // a method that can compare two contacts.
4.    // We use a class method, which is similar to the distance(p1, p2)
5.    // method we saw in the ES6 Point class in module 4.
6.    // We always call such methods using the name of the class followed
7.    // by the dot operator.
8.    this.listOfContacts.sort(ContactManager.compareByName);
9.  }
10. 
11. // class method for comparing two contacts by name
12. static compareByName(c1, c2) {
13.   // JavaScript has built in capabilities for comparing strings
14.   // in alphabetical order
15.   if (c1.name < c2.name)
16.     return -1;
17.   if (c1.name > c2.name)
18.     return 1;
19.   return 0; // c1.name = c2.name
20. }

The important thing here is to notice that we declared the compareByName method as a class method (using the static keyword). This is similar to what we did in the Point class example from module 4, when we explained the "class properties and methods". This method compareByName does not depend on any instance of the contact manager, consequently: it's a class method.

CodePen that uses this new method:

CodePen: using new class method.
CodePen: example using new class method.

5.5.2 Persistence (part 2)

Let's use load/save methods is for loading and saving the list of contacts in Local Storage.

load and save methods (persistence)

This time, we add to the ContactManager class a load() and a save() method for loading/saving from disk (from a key/value pair database located on your hard disk, and associated to the domain of your Web application).

Saving the list of contacts in JSON, checking the saved value using the devtools
Here is the code we added to the ES6 class for saving the list of contacts in JSON:
Source Code:
1.  class ContactManager {
2.    constructor() {
3.      // when we build the contact manager, it
4.      // has an empty list of contacts
5.      this.listOfContacts = [];
6.    }
7.    ...
8.    save() {
9.      // We can only save strings in local storage. So, let's convert
10.     // our array of contacts to JSON
11.     localStorage.contacts = JSON.stringify(this.listOfContacts);
12.   }
13. }

You write data identified by a key in localStorage like this:

In our case, line 11 saves the list of contacts with a key named "contacts" in the local storage. In order to save the list of contacts as a string, we convert it to the JSON format using the  JSON.stringify(...) method (JSON = string based)

Try an example on CodePen, save some contacts...

... then we can check in the devtools that the list has been saved.

In Google Chrome, click the Application tab, then LocalStorage:

Google Chrome local storage inspector.

In Firefox, you first need to activate the storage view like this:

Firefox active storage view in devtools.

You will see the list of contacts when you click on the newly appeared "Storage" tab:

console.log storage inspector.
Restoring the list of contacts

This time, we've added a load() method that will check if a list of contacts has been saved. If this is the case, it will read it from LocalStorage, convert it back from JSON into a JavaScript object.

In order to test this, in the following CodePen, we first save the list, then we empty the list in memory (setting the array to an empty array), print the list of contacts (that displays a message "LIST EMPTY!"), then we load the contacts from LocalStorage and print the list again: it has been restored to its previous value.

Source Code:
1.  class ContactManager {
2.    constructor() {
3.      // When we build the contact manager, it
4.      // has an empty list of contacts.
5.      this.listOfContacts = [];
6.    }
7.    // Will erase all contacts
8.    empty() {
9.      this.listOfContacts = [];
10.   }
11.   ...
12.   load() {
13.     if(localStorage.contacts !== undefined) {
14.       // The array of contacts is saved in JSON, let's convert
15.       // it back to a real JavaScript object.
16.       this.listOfContacts = JSON.parse(localStorage.contacts);
17.     }
18.   }
19. }
20. 
21. ...
22. 
23. console.log("--- Saving contacts to local storage ---");
24. cm.save();
25. 
26. console.log("--- Emptying the list of contacts ---");
27. cm.empty();
28. cm.printContactsToConsole();
29. 
30. console.log("--- Loading contacts from local storage ---");
31. cm.load();
32. cm.printContactsToConsole();
33. console.log("Do you notice: contacts have all been restored!");
Explanations:

5.5.3 Display contacts in an HTML5 table (part 3)

We're going to reuse the code from this CodePen (example taken from a previous section of the course, the one about working with remote data), and adapt it to our needs:

CodePen: table list of contacts.
CodePen: XhR2 - get a remote list of user's names and emails.

This time, we will first add some HTML to the contact manager example (same as in the previous CodePen except that we've renamed "users" as "contacts"):

Source Code:
1.  <!DOCTYPE html>
2.  <html lang="en">
3.  <head>
4.    <title>A contact manager, v3</title>
5.    <meta charset="utf-8"/>
6.  </head>
7.  <body>
8.    <p>List of contacts</p>
9.    <div id="contacts"></div>
10. </body>
11. </html>

The div at line 9 is where we're going to dynamically insert an HTML table with one row for each contact. We will keep the same minimal CSS for displaying table, row and cell borders (we encourage you to improve this):

Source Code:
1.  table {
2.     margin-top: 20px;
3.  }
4.   
5.  table, tr, td {
6.     border: 1px solid;
7.  }

And here is the method we add in our ContactManager class; an adaptation of the function displayUsersAsATable(users) from the previous CodePen:

Source Code:
1.  class ContactManager {
2.    ...
3.    displayContactsAsATable(idOfContainer) {
4.      // to empty the container that contains the results
5.      let container = document.querySelector("#" + idOfContainer);
6.      container.innerHTML = "";
7.   
8.      if(this.listOfContacts.length === 0) {
9.        container.innerHTML = "<p>No contacts to display!</p>";
10.       // stops the execution of this method
11.       return;
12.     }
13.     // creates and populates the table with users
14.     let table = document.createElement("table");
15. 
16.     // iterates on the array of users
17.     this.listOfContacts.forEach(function(currentContact) {
18.       // creates a row
19.       let row = table.insertRow();
20. 
21.       row.innerHTML = "<td>" + currentContact.name + "</td>"
22.                     + "<td>" + currentContact.email + "</td>"
23.     });
24.     // adds the table to the div
25.     container.appendChild(table);
26.   }
27. }
Explanations:
CodePen of this example:
CodePen: table list of contacts.
CodePen: table list of contacts.

Note that we also added a method called addTestData() to the ContactManager class, as this is a way to make testing the class easier. The code in this method is similar to all the code we used in previous examples for testing the class by adding four contacts to it and displaying messages in the devtool console.

5.5.4 Use a form to enter new contacts (part 4)

In the previous example, we added a form for entering a new contact, and an "add" button.

Here is the HTML code of the form:
Source Code:
1.  <form onsubmit="return formSubmitted();">
2.    <fieldset>
3.      <legend>Personal informations</legend>
4.      <label>
5.        Name :
6.        <input type="text" id="name" required>
7.      </label>
8.      <label>
9.        Email :
10.       <input type="email" id="email" required>
11.     </label>
12.     <br>
13.     <button>Add new Contact</button>
14.   </fieldset>
15. </form>

The button at line 13 will submit the form by default (it's equivalent to an <input type="submit">).

The event listener at line 1:

1.  <form onsubmit="return formSubmitted();">

... will call the formSubmitted function when the form is submitted. It is interesting that we use onclick="return formSubmitted();":

Here is the code of the formSubmitted function:

Source Code:
1.  function formSubmitted() {
2.    // Get the values from input fields
3.    let name = document.querySelector("#name");
4.    let email = document.querySelector("#email");
5.    let newContact = new Contact(name.value, email.value);
6.    cm.add(newContact);
7.    // Empty the input fields
8.    name.value = "";
9.    email.value = "";
10.   // refresh the table
11.   cm.displayContactsAsATable("contacts");
12.   // do not let your browser submit the form using HTTP
13.   return false;
14. }
Explanations:

CodePen example:

CodePen: Add new contact and list in table.
CodePen: add new contacts to table.

Note that we've also added some buttons for playing with the load/save features we implemented in the previous page:

5.5.5 Discussion and projects

Here is the discussion forum for this part of the course.

Optional projects