W3C Selects Craft CMS for Redesign Project

W3C has selected Craft CMS over Statamic for its redesign project, after dropping WordPress from consideration in an earlier round of elimination:

In the end, our decision mostly came down to available resources. Craft had already committed to reach AA compliance in Craft 4 (it is currently on version 3.5, the release of version 4 is planned for April 2021). They had also arranged for an external agency to provide them with accessibility issues to tackle weekly. In the end, they decided instead to hire an in-house accessibility specialist to perform assessments and assist the development team in adopting accessibility patterns in the long run.

W3C CMS Selection Report

Last week we published a post urging W3C to revisit Gutenberg for a fair shake against the proprietary CMS’s or consider adopting another open source option. During the selection process, Studio 24, the agency contracted for the redesign, cited its extensive experience with WordPress as the reason for not performing any accessibility testing on more recent versions of Gutenberg.

When asked if the team contacted anyone from WordPress’ Accessibility Team during the process or put Gutenberg through the same tests as the proprietary CMS’s, Studio 24 founder Simon Jones confirmed they had not.

“No, we only reached out to the two shortlisted CMS’s” Jones said. “I’m afraid we didn’t have time to do more. We did test GB a few months ago based on editing content – though it wasn’t the only factor in our choice. As an agency we do plan to keep reviewing GB in the future.”

In response to our concerns regarding licensing, Jones penned an update titled “On not choosing WordPress,” which further elaborated on the reasons why the agency was not inclined towards using or evaluating the new editor:

From a business perspective I also believe Gutenberg creates a complexity issue that makes it challenging for use by many agencies who create custom websites for clients; where we have a need to create lots of bespoke blocks and page elements for individual client projects.

The use of React complicates front-end build. We have very talented front-end developers, however, they are not React experts – nor should they need to be. I believe front-end should be built as standards-compliant HTML/CSS with JavaScript used to enrich functionality where necessary and appropriate.

As of yet, we have not found a satisfactory (and profitable) way to build custom Gutenberg blocks for commercial projects. 

The CMS selection report also stated that W3C needs the CMS to be “usable by non-sighted users” by the launch date, since some members of the staff who contribute to the website are non-sighted.

Since the most recent version of WordPress was not tested in comparison with the proprietary CMS’s, it’s unclear how much better they handle accessibility. Ultimately, W3C and Studio 24 were more comfortable moving forward with a proprietary vendor that was able to make certain assurances about the future accessibility of its authoring tool, despite having a smaller pool of contributors.

“[I’m] also deeply curious since the cursory notes on accessibility for both of the reviewed CMSes seem to highlight a ton of issues like ‘Buttons and Checkboxes are built using div elements’ or most inputs lacking clear focus styles,” Gutenberg technical lead Matías Ventura said. “An element like the Calendar for choosing a post date seems entirely inoperable with keyboard on Craft, for example, while WordPress’ has had significant effort and rounds of feedback poured into that element alone to make it fully operable.”

WordPress developer Anthony Burchell commented on how using a relatively new proprietary CMS seemed counter to W3C’s stated goal to select an option on the basis of longevity. Craft CMS’s continued success is contingent upon its business model and the company’s ability to remain profitable.

“FOSS have the same opportunity of direct access to developers,” Burchell said. “I recognize there are many accessibility shortcomings in popular software, but I think it’s more constructive to rally behind and contribute, not use a proprietary CMS that boasts beer budget in their guidelines.”

On the other side of the issue, accessibility advocates took the W3C’s decision as a referendum on Gutenberg’s continued struggles to meet WCAG AA standards. WordPress accessibility specialist Amanda Rush said it was “nice to see the W3C flip tables over this.”

“Gutenberg is not mature software,” accessibility consultant and WordPress contributor Joe Dolson said in a post elaborating on his comments at WPCampus 2020 Online. He emphasized the lack of stability in the project that Studio 24 alluded to when documenting the reasons against using WordPress.

“It is still undergoing rapid changes, and has grand goals to add a full-site editing experience for WordPress that almost guarantees that it will continue to undergo rapid changes for the next few years,” Dolson said. “Why would any organization that is investing a large amount into a site that they presumably hope will last another 10 years want to invest in something this uncertain?”

Dolson also said the accessibility improvements he referenced regarding the audit were only a small part of the whole picture.

“They only encompass issues that existed in the spring of 2019,” he said. “Since then, many features have been added and changed, and those features both resolve issues and have created new ones. The accessibility team is constantly playing catch up to try and provide enough support to improve Gutenberg. And even now, while it is more or less accessible, there are critical features that are not yet implemented. There are entirely new interface patterns introduced on a regular basis that break prior accessibility expectations.”

WordPress is also being used by millions of people who are constantly reporting issues to fuel the software’s continued refinement, which increases the backlog of issues. Unfortunately, Studio 24 did not properly evaluate Gutenberg against the proprietary CMS’s in order to determine if these software projects are in any better shape.

Instead, they decided that Craft CMS’s community was more receptive to collaborating on issues without reaching out to WordPress. Given the W3C’s stated preference for open source software, WordPress, as the only CMS under consideration with an OSD-compliant license, should have received the same accessibility evaluation.

“I can’t make any statements that would be meaningful about the other content management systems under consideration; but if WordPress wants to be taken seriously in environments where accessibility is a legal, ethical, and mission imperative, there’s still a lot of work to be done,” Dolson said.

Studio 24’s evaluation may not have been equitable to the only open source CMS under consideration, but the situation serves to highlight a unique quandary: when using open source software becomes the impractical choice for organizations requiring a high level of accessibility in their authoring tools.

“Studio 24 ultimately determined that working with a CMS to make it better was more possible with a smaller, proprietary vendor than with a large open-source project,” accessibility advocate Brian DeConinck said. “Project leadership would be more receptive, and the smaller community means changes can be made more quickly. That should prompt a lot of soul-searching for…well, everyone. What does that say about the future of open source?”

Can someone help me with this? Vending Machine

I have to make my sample run look like this . I cannot seem to get it right.

Sample run

Welcome to Vending Machine capable of deep frying twinkies
Please insert coin:
Enter D or d for Dollar
Enter Q or q for Quarer
Enter M or m for Dime
Enter N or n for Nickle
Enter X or x to stop

It cost $3.50 for a deep-fried twinkie.
Your have inserted: $0.00
Your choice : D

It cost $3.50 for a deep-fried twinkie.
Your have inserted: $1.00
Your choice : f

It cost $3.50 for a deep-fried twinkie.
Your have inserted: $3.55
Purchase Completed!
Your change: $0.05

This is what I have so far. Here are my codes.

#include <iostream>

using namespace std;
const double twinkies_Price = 3.50;

const double DOLLAR = 1.00;

const double QUARTER = 0.25;

const double DIME = 0.10;

const double NICKEL = 0.05;

int accept_money();

int computer_change ( int total_paid );

int main()
{
    const double DOLLAR = 1.00;

    const double QUARTER = 0.25;

    const double DIME = 0.10;

    const double NICKEL = 0.05;

    int choice;
    double moneyEnter =0.0;
    cout << "Welcome to Vending Machine capable of deep frying twinkies.\n\n";

    cout << " Please insert coin: \n";
    cout << " Enter D or d for Dollar which is = $1.00 \n" ;
    cout << " Enter Q or q for Quarer which is = $0.25 \n";
    cout << " Enter M or m for Dime which is = $0.10 \n";
    cout << " Enter N or n for Nickle whihc is = $0.50 \n";
    cout << " Enter X or x to stop \n\n";


    cout << " It cost $3.50 for a deep-fried twinkie. \n";
    cout  << " Your have inserted: $"<< moneyEnter << "." << endl;
    cout << " Insert amount ( enter letter of choice ):  " <<endl;
    cin >> choice;


     if (choice == 'D' || choice == 'd')
    {
        moneyEnter = moneyEnter + DOLLAR;
    }
    else if ( choice == 'Q' || choice == 'q')
    {
       moneyEnter += QUARTER;
    }

    else if (choice == 'M' || choice == 'm')
    {
        moneyEnter +=DIME;
    }
    else if (choice == 'N' || choice == 'n')
    {
        moneyEnter +=NICKEL;
    }
    else if (choice == 'X' || choice == 'x')
    {
        cout << "Stop \n";
    }
    else 
    {
        "Invalid Input \n";
    }

    return 0;
}

Inovalon Launches API for Its Healthcare Analytics Tools

Inovalon, a provider of cloud-based platforms empowering data-driven healthcare, announced the launch of the Inovalon DataStream API, allowing any authorized cloud-based, traditional enterprise, or mobile app software system to benefit from the power of comprehensive patient-specific data and analytical derivations on-demand and in real-time.

Themes Team Releases a Web Fonts Loader, Likely To Prohibit Hotlinking Any Off-Site Assets

Last Friday, the WordPress Themes Team announced the release of its new Webfonts Loader project. It is a drop-in script that allows theme authors to load web fonts from the user’s site instead of a third-party CDN. The secondary message included in the team’s announcement is that it no longer plans to allow themes to hotlink Google Fonts in the future.

Throughout most of the team’s history, it has not allowed themes to hotlink or use CDNs for hosting theme assets, such as CSS, JavaScript, and fonts. The one exception to this rule was the use of Google Fonts. This allowed themes to have richer typography options at their disposal from what the team has generally declared a reliable source.

“The exception was made because there was no practical way to not have the exception at the time,” said Aria Stathopoulos, a Themes Team representative and developer behind the Webfonts Loader project. “The exception for Google Fonts was made out of necessity. Now that there is another way, the exception will not be necessary.”

In effect, disallowing the Google Fonts CDN would not be a new ban. It would be a removal of an exception to the existing ban.

Google Fonts has become so embedded into the theme developer toolset over the years, there was no way the team could simply pull the plug and prohibit the use of the CDN overnight. If the Themes Team members wanted to focus more on privacy, they would need to build a tool that made it dead simple for theme authors to use.

There is no hard deadline for when the team will remove the exception for Google Fonts, and it is not set in stone at this point. Stathopoulos said removing it has been the goal from the beginning, disallowing all CDNs. However, it took a while to find an efficient way to handle this. With a viable alternative in place, they can discuss moving forward.

Webfonts Loader for Themes

The Webfonts Loader project keeps it simple for theme authors. It introduces a new wptt_get_webfont_styles() function that developers can plug in a stylesheet URL. Once a page is loaded with that function call, it will download the fonts locally to a /fonts folder in the user’s /wp-content directory. This way, fonts will always be served from the user’s site.

The system is not limited to Google Fonts either. Any URL that serves CSS with an @font-face {} rule will work. It does not currently include authentication for CDNs that require API keys, such as Adobe Fonts. However, that is something the team might add in the future.

“For end-users, moving away from CDNs and locally hosting web fonts will improve performance (fewer handshake roundtrips for SSL), and is the privacy-conscious choice,” said Stathopoulos. “The only ‘valid privacy concern’ is that the web fonts’ CDN does not disclose information that is fundamental to the GDPR: what information gets logged, for how long these logs remain, how they are processed, if there is any cross-referencing with all the other wealth of information the company has from users, etc. The concern is a lack of disclosure and information. If a site owner doesn’t know what kind of information a third-party logs for its visitors, then they should ethically not enforce that on their visitors. With this package, the CDN is removed from the equation and the font still gets served fast — if not faster.”

A Path to Core WordPress

Today, there is now a broader focus on privacy concerns related to third-party resources, particularly with tech giants like Google. Such concerns extend to whether third parties are tracking users or collecting data. Additional concerns are around whether sites are disclosing the use of third-party resources, which may be required in some jurisdictions. Site owners who are often unable to work through the web of potential issues are stuck in the middle.

Jono Alderson opened a ticket to create an API for loading web fonts locally in core WordPress in February 2019. It is a lengthy and detailed proposal, but it has yet to see much buy-in outside of a handful of developers.

“If such a script is standardized and included in WordPress core, one of the main benefits would be more respect for the end-user’s privacy,” said Stathopoulos. “In the end, that’s all privacy is about: respecting users.”

A standard API like Alderson proposes could solve some issues. Namely, it would virtually eliminate any privacy concerns. However, loading fonts locally could allow WordPress to optimize font loading and would create a shared system where plugins and themes do not load duplicate assets because of the current limitations of the enqueuing system. A standard API would also put the responsibility of efficiently loading fonts on WordPress’s shoulders instead of theme and plugin developers.

The Themes Team’s new project is a solid start and strengthens the current proposal.

“If we’re serious about WordPress becoming a fast, privacy-friendly platform, we can’t rely on theme developers to add and manage fonts without providing a framework to support them,” wrote Alderson in the ticket.

The Flavors of Object-Oriented Programming (in JavaScript)

In my research, I’ve found there are four approaches to Object-Oriented Programming in JavaScript:

Which methods should I use? Which one is “the best” way? Here I’ll present my findings along with information that may help you decide which is right for you.

To make that decision, we’re not just going to look at the different flavors but compare conceptual aspects between them:

What is Object-Oriented Programming?

Object-Oriented Programming is a way of writing code that allows you to create different objects from a common object. The common object is usually called a blueprint while the created objects are called instances.

Each instance has properties that are not shared with other instances. For example, if you have a Human blueprint, you can create human instances with different names.

The second aspect of Object-Oriented Programming is about structuring code when you have multiple levels of blueprints. This is commonly called Inheritance or subclassing.

The third aspect of Object Oriented Programming is about encapsulation where you hide certain pieces of information within the object so they’re not accessible.

If you need more than this brief intro, here’s an article that introduces this aspect of Object-Oriented Programming if you need help with it.

Let’s begin with the basics — an introduction to the four flavors of Object-Oriented Programming.

The four flavors of Object-Oriented Programming

There are four ways to write Object-Oriented Programming in JavaScript. They are:

Using Constructor functions

Constructors are functions that contain a this keyword.

function Human (firstName, lastName) {
  this.firstName = firstName
  this.lastName = lastName
}

this lets you store (and access) unique values created for each instance. You can create an instance with the new keyword.

const chris = new Human('Chris', 'Coyier')
console.log(chris.firstName) // Chris
console.log(chris.lastName) // Coyier

const zell = new Human('Zell', 'Liew')
console.log(zell.firstName) // Zell
console.log(zell.lastName) // Liew

Class syntax

Classes are said to be the “syntactic sugar” of Constructor functions. As in, Classes are an easier way of writing Constructor functions.

There’s serious contention about whether Classes are bad (like this and this). We’re not going to dive into those arguments here. Instead, we’re just going to look at how to write code with Classes and decide whether Classes are better than constructors based on the code we write.

Classes can be written with the following syntax:

class Human {
  constructor(firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }
}

Notice the constructor function contains the same code as the Constructor syntax above? We need to do this since we want to initialize values into this. (We can skip constructor if we don’t need to initialize values. More on this later under Inheritance).

At first glance, classes seem to be inferior to constructors — there’s more code to write! Hold your horses and don’t form a conclusion at this point. We have a lot more to cover. Classes begin to shine later.

As before, you can create an instance with the new keyword.

const chris = new Human('Chris', 'Coyier')

console.log(chris.firstName) // Chris
console.log(chris.lastName) // Coyier

Objects Linking to Other Objects (OLOO)

OLOO was coined and popularized by Kyle Simpson. In OLOO, you define the blueprint as a normal object. You then use a method (often named init, but that isn’t required in the way constructor is to a Class) to initialize the instance.

const Human = {
  init (firstName, lastName ) {
    this.firstName = firstName
    this.lastName = lastName
  }
}

You use Object.create to create an instance. After creating the instance, you need to run your init function.

const chris = Object.create(Human)
chris.init('Chris', 'Coyier')

console.log(chris.firstName) // Chris
console.log(chris.lastName) // Coyier

You can chain init after Object.create if you returned this inside init.

const Human = {
  init () {
    // ...
    return this 
  }
}

const chris = Object.create(Human).init('Chris', 'Coyier')
console.log(chris.firstName) // Chris
console.log(chris.lastName) // Coyier

Factory functions

Factory functions are functions that return an object. You can return any object. You can even return a Class instance or OLOO instance — and it’ll still be a valid Factory function.

Here’s the simplest way to create Factory functions:

function Human (firstName, lastName) {
  return {
    firstName,
    lastName
  }
}

You don’t need new to create instances with Factory functions. You simply call the function.

const chris = Human('Chris', 'Coyier')

console.log(chris.firstName) // Chris
console.log(chris.lastName) // Coyier

Now that we’ve seen these four OOP setup possibilities, let’s look at how you declare properties and methods on each of them so we can get a little better understanding of working with them before getting to the bigger comparisons we’re trying to make.


Declaring properties and methods

Methods are functions declared as an object’s property.

const someObject = {
  someMethod () { /* ... */ }
}

In Object-Oriented Programming, there are two ways to declare properties and methods:

  1. Directly on the instance
  2. In the Prototype

Let’s learn to do both.

Declaring properties and methods with Constructors

If you want to declare a property directly on an instance, you can write the property inside the constructor function. Make sure to set it as the property for this.

function Human (firstName, lastName) {
  // Declares properties
  this.firstName = firstName
  this.lastname = lastName

  // Declares methods
  this.sayHello = function () {
    console.log(`Hello, I'm ${firstName}`)
  }
}

const chris = new Human('Chris', 'Coyier')
console.log(chris)

Methods are commonly declared on the Prototype because Prototype allows instances to use the same method. It’s a smaller “code footprint.”

To declare properties on the Prototype, you need to use the prototype property.

function Human (firstName, lastName) {
  this.firstName = firstName
  this.lastname = lastName
}

// Declaring method on a prototype
Human.prototype.sayHello = function () {
  console.log(`Hello, I'm ${this.firstName}`)
}

It can be clunky if you want to declare multiple methods in a Prototype.

// Declaring methods on a prototype
Human.prototype.method1 = function () { /*...*/ }
Human.prototype.method2 = function () { /*...*/ }
Human.prototype.method3 = function () { /*...*/ }

You can make things easier by using merging functions like Object.assign.

Object.assign(Human.prototype, {
  method1 () { /*...*/ },
  method2 () { /*...*/ },
  method3 () { /*...*/ }
})

Object.assign does not support the merging of Getter and Setter functions. You need another tool. Here’s why. And here’s a tool I created to merge objects with Getters and Setters.

Declaring properties and methods with Classes

You can declare properties for each instance inside the constructor function.

class Human {
  constructor (firstName, lastName) {
    this.firstName = firstName
      this.lastname = lastName

      this.sayHello = function () {
        console.log(`Hello, I'm ${firstName}`)
      }
  }
}

It’s easier to declare methods on the prototype. You write the method after constructor like a normal function.

class Human (firstName, lastName) {
  constructor (firstName, lastName) { /* ... */ }

  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

It’s easier to declare multiple methods on Classes compared to Constructors. You don’t need the Object.assign syntax. You just write more functions.

Note: there’s no , between method declarations in a Class.

class Human (firstName, lastName) {
  constructor (firstName, lastName) { /* ... */ }

  method1 () { /*...*/ }
  method2 () { /*...*/ }
  method3 () { /*...*/ }
}

Declaring properties and methods with OLOO

You use the same process for declaring properties and methods on an instance. You assign them as a property of this.

const Human = {
  init (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
    this.sayHello = function () {
      console.log(`Hello, I'm ${firstName}`)
    }

    return this
  }
}

const chris = Object.create(Human).init('Chris', 'Coyier')
console.log(chris)

To declare methods in the prototype, you write the method like a normal object.

const Human = {
  init () { /*...*/ },
  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

Declaring properties and methods with Factory functions

You can declare properties and methods directly by including them in the returned object.

function Human (firstName, lastName) {
  return {
    firstName,
    lastName, 
    sayHello () {
      console.log(`Hello, I'm ${firstName}`)
    }
  }
}

You cannot declare methods on the Prototype when you use Factory functions. If you really want methods on the prototype, you need to return a Constructor, Class, or OLOO instance. (Don’t do this since it doesn’t make any sense.)

// Do not do this
function createHuman (...args) {
  return new Human(...args)
}

Where to declare properties and methods

Should you declare properties and methods directly on the instance? Or should you use prototype as much as you can?

Many people take pride that JavaScript is a “Prototypal Language” (which means it uses prototypes). From this statement, you may make the assumption that using “Prototypes” is better.

The real answer is: It doesn’t matter.

If you declare properties and methods on instances, each instance will take up slightly more memory. If you declare methods on Prototypes, the memory used by each instance will decrease, but not much. This difference is insignificant with computer processing power what it is today. Instead, you want to look at how easy it is to write code — and whether it is possible to use Prototypes in the first place.

For example, if you use Classes or OLOO, you’ll be better off using Prototypes since the code is easier to write. If you use Factory functions, you cannot use Prototypes. You can only create properties and methods directly on the instance.

I wrote a separate article on understanding JavaScript Prototypes if you’re interested in finding out more.

Preliminary verdict

We can make a few notes from the code we wrote above. These opinions are my own!

  1. Classes are better than Constructors because its easier to write multiple methods on Classes.
  2. OLOO is weird because of the Object.create part. I gave OLOO a run for a while, but I always forget to write Object.create. It’s weird enough for me not to use it.
  3. Classes and Factry Fufnctions are easiest to use. The problem is that Factory functions don’t support Prototypes. But like I said, this doesn’t really matter in production.

We’re down to two. Should we choose Classes or Factory functions then? Let’s compare them!


Classes vs. Factory functions — Inheritance

To continue the discussion on Classes and Factory functions, we need to understand three more concepts that are tied closely to Object-Oriented Programming.

  1. Inheritance
  2. Encapsulation
  3. this

Let’s start with Inheritance.

What is Inheritance?

Inheritance is a loaded word. Many people in the industry use Inheritance incorrectly, in my opinion. The word “inheritance” is used when you receive things from somewhere. For example:

  • If you get an inheritance from your parents, it means you get money and assets from them.
  • If you inherit genes from your parents, it means you get your genes from them.
  • If you inherit a process from your teacher, it means you get that process from them.

Fairly straightforward.

In JavaScript, Inheritance can mean the same thing: where you get properties and methods from the parent blueprint.

This means all instances actually inherit from their blueprints. They inherit properties and methods in two ways:

  1. by creating a property or method directly upon creating the instance
  2. via the Prototype chain

We discussed how to do both methods in the previous article so refer back to it if you need help seeing these processes in code.

There’s a second meaning for Inheritance in JavaScript — where you create a derivative blueprint from the parent blueprint. This process is more accurately called Subclassing, but people sometimes will call this Inheritance as well.

Understanding Subclassing

Subclassing is about creating a derivative blueprint from a common blueprint. You can use any Object-Oriented Programming flavor to create the Subclass.

We’ll talk about this with the Class syntax first because it’s easier to understand.

Subclassing with Class

When you create a Subclass, you use the extends keyword.

class Child extends Parent {
  // ... Stuff goes here
}

For example, let’s say we want to create a Developer class from a Human class.

// Human Class
class Human {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }

  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

The Developer class will extend Human like this:

class Developer extends Human {
  constructor(firstName, lastName) {
    super(firstName, lastName)
  }

    // Add other methods
}

Note: super calls the Human (also called the “parent”) Class. It initiates the constructor from Human. If you don’t need extra initiation code, you can omit constructor entirely.

class Developer extends Human {
  // Add other methods
}

Let’s say a Developer can code. We can add the code method directly to Developer.

class Developer extends Human {
  code (thing) {
    console.log(`${this.firstName} coded ${thing}`)
  }
}

Here’s an example of an instance of Developer:

const chris = new Developer('Chris', 'Coyier')
console.log(chris)
Instance of a Developer class.

Subclassing with Factory functions

There are four steps to creating Subclasses with Factory functions:

  1. Create a new Factory function
  2. Create an instance of the Parent blueprint
  3. Create a new copy of this instance
  4. Add properties and methods to this new copy

The process looks like this:

function Subclass (...args) {
  const instance = ParentClass(...args)
  return Object.assign({}, instance, {
    // Properties and methods go here
  })
}

We’ll use the same example — creating a Developer Subclass — to illustrate this process. Here’s the Human factory function:

function Human (firstName, lastName) {
  return {
    firstName,
    lastName,
    sayHello () {
      console.log(`Hello, I'm ${firstName}`)
    }
  }
}

We can create Developer like this:

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    // Properties and methods go here
  })
}

Then we add the code method like this:

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    code (thing) {
      console.log(`${this.firstName} coded ${thing}`)
    }
  })
}

Here’s an example of a Developer instance :

const chris = Developer('Chris', 'Coyier')
console.log(chris)
Example of a Developer instance with Factory functions.

Note: You cannot use Object.assign if you use Getters and Setters. You’ll need another tool, like mix. I explain why in this article.

Overwriting the Parent’s method

Sometimes you need to overwrite the Parent’s method inside the Subclass. You can do this by:

  1. Creating a method with the same name
  2. Calling the Parent’s method (optional)
  3. Changing whatever you need in the Subclass’s method

The process looks like this with Classes:

class Developer extends Human {
  sayHello () {
    // Calls the parent method
    super.sayHello() 

    // Additional stuff to run
    console.log(`I'm a developer.`)
  }
}

const chris = new Developer('Chris', 'Coyier')
chris.sayHello()
Overwriting a parent's method.

The process looks like this with Factory functions:

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)

  return Object.assign({}, human, {
      sayHello () {
        // Calls the parent method
        human.sayHello() 

        // Additional stuff to run
        console.log(`I'm a developer.`)
      }
  })
}

const chris = new Developer('Chris', 'Coyier')
chris.sayHello()
Overwriting a parent's method.

Inheritance vs. Composition

No talk about Inheritance ever concludes without the mention of Composition. Experts like Eric Elliot often suggests we should favor Composition over Inheritance.

“Favor object composition over class inheritance” the Gang of Four, “Design Patterns: Elements of Reusable Object Oriented Software”

“In computer science, a composite data type or compound data type is any data type which can be constructed in a program using the programming language’s primitive data types and other composite types. […] The act of constructing a composite type is known as composition.” ~ Wikipedia

So let’s give Composition a deeper look and understand what it is.

Understanding Composition

Composition is the act of combining two things into one. It’s about merging things together. The most common (and simplest) way of merging objects is with Object.assign.

const one = { one: 'one' }
const two = { two: 'two' }
const combined = Object.assign({}, one, two)

The use of Composition can be better explained with an example. Let’s say we already have two Subclasses, a Designer and Developer. Designers can design, while developers can code. Both designers and developers inherit from the Human class.

Here’s the code so far:

class Human {
  constructor(firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }

  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

class Designer extends Human {
  design (thing) {
    console.log(`${this.firstName} designed ${thing}`)
  }
}

class Developer extends Designer {
  code (thing) {
    console.log(`${this.firstName} coded ${thing}`)
  }
}

Now let’s say you want to create a third Subclass. This Subclass is a mix of a Designer and a Developer they — can design and code. Let’s call it DesignerDeveloper (or DeveloperDesigner, whichever you fancy).

How would you create the third Subclass?

We cannot extend Designer and Developer classes at the same time. This is impossible because we cannot decide which properties come first. This is often called The Diamond Problem.

Diamond problem.

The Diamond Problem can be easily solved if we do something like Object.assign – where we prioritize one object over the other. If we use the Object.assign approach, we may be able to extend classes like this. But this is not supported in JavaScript.

// Doesn't work
class DesignerDeveloper extends Developer, Designer {
  // ...
}

So we need to rely on Composition.

Composition says: Instead of trying to create DesignerDeveloper via Subclassing, let’s create a new object that stores common features. We can then include these features whenever necessary.

In practice, it can look like this:

const skills = {
  code (thing) { /* ... */ },
  design (thing) { /* ... */ },
  sayHello () { /* ... */ }
}

We can then skip Human altogether and create three different classes based on their skills.

Here’s the code for DesignerDeveloper:

class DesignerDeveloper {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName

    Object.assign(this, {
      code: skills.code,
      design: skills.design,
      sayHello: skills.sayHello
    })
  }
}

const chris = new DesignerDeveloper('Chris', 'Coyier')
console.log(chris)
Composing methods into a class

You can do the same with Developer and Designer.

class Designer {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName 

    Object.assign(this, {
      design: skills.design,
      sayHello: skills.sayHello
    }) 
  }
}

class Developer {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName 

    Object.assign(this, {
      code: skills.code,
      sayHello: skills.sayHello
    }) 
  }
}

Did you notice we’re creating methods directly on the instance? This is just one option. We can still put methods into the Prototype, but I think the code looks clunky. (It’s as if we’re writing Constructor functions all over again.)

class DesignerDeveloper {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }
}

Object.assign(DesignerDeveloper.prototype, {
  code: skills.code,
  design: skills.design,
  sayHello: skills.sayHello
})
Composition via Classes by putting methods into the Prototype.

Feel free to use whatever code structure you’re attracted to. The results are kinda the same anyway.

Composition with Factory Functions

Composition with Factory functions is essentially adding the shared methods into the returned object.

function DesignerDeveloper (firstName, lastName) {
  return {
    firstName,
    lastName,    
    code: skills.code,
    design: skills.design,
    sayHello: skills.sayHello
  }
}
Composing methods into a factory function

Inheritance and Composition at the same time

Nobody says we can’t use Inheritance and Composition at the same time. We can!

Using the example we’ve ironed out so far, Designer, Developer, and DesignerDeveloper Humans are still humans. They can extend the Human object.

Here’s an example where we use both inheritance and composition with the class syntax.

class Human {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }

  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

class DesignerDeveloper extends Human {}
Object.assign(DesignerDeveloper.prototype, {
  code: skills.code,
  design: skills.design
})
Subclassing and Composition at the same time.

And here’s the same thing with Factory functions:

function Human (firstName, lastName) {
  return {
    firstName,
    lastName,
    sayHello () { 
      console.log(`Hello, I'm ${this.firstName}`)
    }
  }
}

function DesignerDeveloper (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    code: skills.code,
    design: skills.design
  }
}
Subclassing and Composition in Factory functions

Subclassing in the real world

One final point about Subclassing vs. Composition. Even though experts have pointed out that Composition is more flexible (and hence more useful), Subclassing still has its merits. Many things we use today are built with the Subclassing strategy.

For example: The click event we know and love is a MouseEvent. MouseEvent is a Subclass of a UIEvent, which in turn is a Subclass of Event.

MouseEvent is a subclass of UIEvent.

Another example: HTML Elements are Subclasses of Nodes. That’s why they can use all properties and methods of Nodes.

HTMLElement is a subclass of Node.

Preliminary verdict

Classes and Factory functions can both use Inheritance and Composition. Composition seems to be cleaner in Factory functions though, but that’s not a big win over Classes.

We’ll examine Classes and Factory Functions more in detail next.


Classes vs. Factory functions — Encapsulation

We’v looked at the four different Object-Oriented Programming flavors so far. Two of them — Classes and Factory functions — are easier to use compared to the rest.

But the questions remain: Which should you use? And why?

To continue the discussion on Classes and Factory functions, we need to understand three concepts that are tied closely to Object-Oriented Programming:

  1. Inheritance
  2. Encapsulation
  3. this

We just talked about Inheritance. Now let’s talk about Encapsulation.

Encapsulation

Encapsulation is a big word, but it has a simple meaning. Encapsulation is the act of enclosing one thing inside another thing so the thing inside doesn’t leak out. Think about storing water inside a bottle. The bottle prevents water from leaking out.

In JavaScript, we’re interested in enclosing variables (which can include functions) so these variables don’t leak out into the external scope. This means you need to understand scope to understand encapsulation. We’ll go through an explanation, but you can also use this article to beef up your knowledge regarding scopes.

Simple Encapsulation

The simplest form of Encapsulation is a block scope.

{
  // Variables declared here won't leak out
}

When you’re in the block, you can access variables that are declared outside the block.

const food = 'Hamburger'

{
  console.log(food)
}
Logs food from inside the blog. Result: Hamburger.

But when you’re outside the block, you cannot access variables that are declared inside the block.

{
  const food = 'Hamburger'
}

console.log(food)
Logs food from outside the blog. Results: Error.

Note: Variables declared with var don’t respect block scope. This is why I recommend you use let or const to declare variables.

Encapsulating with functions

Functions behave like block scopes. When you declare a variable inside a function, they cannot leak out of that function. This works for all variables, even those declared with var.

function sayFood () {
  const food = 'Hamburger'
}

sayFood()
console.log(food)
Logs food from outside the function. Results: Error.

Likewise, when you’re inside the function, you can access variables that are declared outside of that function.

const food = 'Hamburger'

function sayFood () {
  console.log(food)
}


sayFood()
Logs food from inside the function. Result: Hamburger.

Functions can return a value. This returned value can be used later, outside the function.

function sayFood () {
  return 'Hamburger'
}

console.log(sayFood())
Logs return value from function. Result: Hamburger.

Closures

Closures are an advanced form of Encapsulation. They’re simply functions wrapped in functions.

// Here's a closure
function outsideFunction () {
  function insideFunction () { /* ...*/ }
}

Variables declared in outsideFunction can be used in insideFunction.

function outsideFunction () {
  const food = 'Hamburger'
  console.log('Called outside')

  return function insideFunction () {
    console.log('Called inside')
    console.log(food)
  }
}

// Calls `outsideFunction`, which returns `insideFunction`
// Stores `insideFunction` as variable `fn`
const fn = outsideFunction() 

// Calls `insideFunction`
fn()
Closure logs.

Encapsulation and Object-Oriented Programming

When you build objects, you want to make some properties publicly available (so people can use them). But you also want to keep some properties private (so others can’t break your implementation).

Let’s work through this with an example to make things clearer. Let’s say we have a Car blueprint. When we produce new cars, we fill each car up with 50 liters of fuel.

class Car {
  constructor () {
    this.fuel = 50
  }
}

Here we exposed the fuel property. Users can use fuel to get the amount of fuel left in their cars.

const car = new Car()
console.log(car.fuel) // 50

Users can also use the fuel property to set any amount of fuel.

const car = new Car()
car.fuel = 3000
console.log(car.fuel) // 3000

Let’s add a condition and say that each car has a maximum capacity of 100 liters. With this condition, we don’t want to let users set the fuel property freely because they may break the car.

There are two ways to do prevent users from setting fuel:

  1. Private by convention
  2. Real Private Members

Private by convention

In JavaScript, there’s a practice of prepending underscores to a variable name. This denotes the variable is private and should not be used.

class Car {
  constructor () {
    // Denotes that `_fuel` is private. Don't use it!
    this._fuel = 50
  }
}

We often create methods to get and set this “private” _fuel variable.

class Car {
  constructor () { 
    // Denotes that `_fuel` is private. Don't use it!
    this._fuel = 50
  }

  getFuel () {
    return this._fuel
  }

  setFuel (value) {
    this._fuel = value
    // Caps fuel at 100 liters
    if (value > 100) this._fuel = 100
  }
}

Users should use the getFuel and setFuel methods to get and set fuel.

const car = new Car() 
console.log(car.getFuel()) // 50 

car.setFuel(3000)
console.log(car.getFuel()) // 100 

But _fuel is not actually private. It is still a public variable. You can still access it, you can still use it, and you can still abuse it (even if the abusing part is an accident).

const car = new Car() 
console.log(car.getFuel()) // 50 

car._fuel = 3000
console.log(car.getFuel()) // 3000

We need to use real private variables if we want to completely prevent users from accessing them.

Real Private Members

Members here refer to variables, functions, and methods. It’s a collective term.

Private Members with Classes

Classes let you create private members by prepending # to the variable.

class Car {
  constructor () {
    this.#fuel = 50
  }
}

Unfortunately, you can’t use # directly inside a constructor function.

Error when declaring <code>#</code> directly in constructor function.

You need to declare the private variable outside the constructor first.

class Car {
  // Declares private variable
  #fuel 
  constructor () {
    // Use private variable
    this.#fuel = 50
  }
}

In this case, we can use a shorthand and declare#fuel upfront since we set fuel to 50.

class Car {
  #fuel = 50
}

You cannot access #fuel outside Car. You’ll get an error.

const car = new Car()
console.log(car.#fuel)
Cannot access #fuel.

You need methods (like getFuel or setFuel) to use the #fuel variable.

class Car {
  #fuel = 50

  getFuel () {
    return this.#fuel
  }

  setFuel (value) {
    this.#fuel = value
    if (value > 100) this.#fuel = 100
  }
}

const car = new Car()
console.log(car.getFuel()) // 50

car.setFuel(3000)
console.log(car.getFuel()) // 100

Note: I prefer Getters and Setters instead of getFuel and setFuel. The syntax is easier to read.

class Car {
  #fuel = 50

  get fuel () {
    return this.#fuel
  }

  set fuel (value) {
    this.#fuel = value
    if (value > 100) this.#fuel = 100
  }
}

const car = new Car()
console.log(car.fuel) // 50

car.fuel = 3000
console.log(car.fuel) // 100

Private Members with Factory functions

Factory functions create Private Members automatically. You just need to declare a variable like normal. Users will not be able to get that variable anywhere else. This is because variables are function-scoped and hence encapsulated by default.

function Car () {
  const fuel = 50 
}

const car = new Car() 
console.log(car.fuel) // undefined 
console.log(fuel) // Error: `fuel` is not defined

We can create getter and setter functions to use this private fuel variable.

function Car () {
  const fuel = 50 

  return {
    get fuel () { 
      return fuel 
    },

    set fuel (value) {
      fuel = value 
      if (value > 100) fuel = 100
    }
  }
}

const car = new Car()
console.log(car.fuel) // 50

car.fuel = 3000
console.log(car.fuel) // 100

That’s it! Simple and easy!

Verdict for Encapsulation

Encapsulation with Factory functions are simpler and easier to understand. They rely on the scopes which are a big part of the JavaScript language.

Encapsulation with Classes, on the other hand, requires prepending # to the private variable. This can make things clunky.

We’ll look at the final concept — this to complete the comparison between Classes and Factory functions — in the next section.


Classes vs. Factory Functions — The this variable

this (ha!) is one of the main arguments against using Classes for Object-Oriented Programming. Why? Because this value changes depending on how it is used. It can be confusing for many developers (both new and experienced).

But the concept of this is relatively simple in reality. There are only six contexts in which you can use this. If you master these six contexts, you’ll have no problems using this.

The six contexts are:

  1. In a global context
  2. Inan object construction
  3. In an object property / method
  4. In a simple function
  5. In an arrow function
  6. In an event listener

I covered these six contexts in detail. Give it a read if you need help understanding this.

Note: Don’t shy away from learning to use this. It’s an important concept you need to understand if you intend on mastering JavaScript.

Come back to this article after you’ve solidified your knowledge on this. We’ll have a deeper discussion about using this in Classes and Factory functions.

Back yet? Good. Let’s go!

Using this in Classes

this refers to the instance when used in a Class. (It uses the “In an object property / method” context.) This is why you can set properties and methods on the instance inside the constructor function.

class Human {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
    console.log(this)
  }
}

const chris = new Human('Chris', 'Coyier')
<code>this</code> points to the instance

Using this in Constructor functions

If you use this inside a function and new to create an instance, this will refer to the instance. This is how a Constructor function is created.

function Human (firstName, lastName) {
  this.firstName = firstName 
  this.lastName = lastName
  console.log(this)  
}

const chris = new Human('Chris', 'Coyier')
<code>this</code> points to the instance.

I mentioned Constructor functions because you can use this inside Factory functions. But this points to Window (or undefined if you use ES6 Modules, or a bundler like webpack).

// NOT a Constructor function because we did not create instances with the `new` keyword
function Human (firstName, lastName) {
  this.firstName = firstName 
  this.lastName = lastName
  console.log(this)  
}

const chris = Human('Chris', 'Coyier')
<code>this</code> points to Window.

Essentially, when you create a Factory function, you should not use this as if it’s a Constructor function. This is one small hiccup people experience with this. I wanted to highlight the problem and make it clear.

Using this in a Factory function

The correct way to use this in a Factory function is to use it “in an object property / method” context.

function Human (firstName, lastName) {
  return {
    firstName,
    lastName,
    sayThis () {
      console.log(this)
    }
  }
}

const chris = Human('Chris', 'Coyier')
chris.sayThis()
<code>this</code> points to the instance.

Even though you can use this in Factory functions, you don’t need to use them. You can create a variable that points to the instance. Once you do this, you can use the variable instead of this. Here’s an example at work.

function Human (firstName, lastName) {
  const human = {
    firstName,
    lastName,
    sayHello() {
      console.log(`Hi, I'm ${human.firstName}`)
    }
  }

  return human
}

const chris = Human('Chris', 'Coyier')
chris.sayHello()

human.firstName is clearer than this.firstName because human definitely points back to the instance. You know when you see the code.

If you’re used to JavaScript, you may also notice there’s no need to even write human.firstName in the first place! Just firstName is enough because firstName is in the lexical scope. (Read this article if you need help with scopes.)

function Human (firstName, lastName) {
  const human = {
    firstName,
    lastName,
    sayHello() {
      console.log(`Hi, I'm ${firstName}`)
    }
  }

  return human
}

const chris = Human('Chris', 'Coyier')
chris.sayHello()
Runs <code>chris.sayHello</code>

What we covered so far is simple. It’s not easy to decide whether this is actually needed until we create a sufficiently complicated example. So let’s do that.

Detailed example

Here’s the setup. Let’s say we have a Human blueprint. This Human ha firstName and lastName properties, and a sayHello method.

We have a Developer blueprint that’s derived from Human. Developers can code, so they’ll have a code method. Developers also want to proclaim they’re developers, so we need to overwrite sayHello and add I'm a Developer to the console.

We’ll create this example with Classes and Factory functions. (We’ll make an example with this and an example without this for Factory functions).

The example with Classes

First, we have a Human blueprint. This Human has a firstName and lastName properties, as well as a sayHello method.

class Human {
  constructor (firstName, lastName) {
    this.firstName = firstName
    this.lastname = lastName 
  }

  sayHello () {
    console.log(`Hello, I'm ${this.firstName}`)
  }
}

We have a Developer blueprint that’s derived from Human. Developers can code, so they’ll have a code method.

class Developer extends Human {
  code (thing) {
    console.log(`${this.firstName} coded ${thing}`)
  }
}

Developers also want to proclaim that they’re developers. We need to overwrite sayHello and add I'm a Developer to the console. We do this by calling Human‘s sayHello method. We can do this using super.

class Developer extends Human {
  code (thing) {
    console.log(`${this.firstName} coded ${thing}`)
  }

  sayHello () {
    super.sayHello()
    console.log(`I'm a developer`)
  }
}

The example with Factory functions (with this)

Again, first, we have a Human blueprint. This Human has firstName and lastName properties, as well as a sayHello method.

function Human () {
  return {
    firstName,
    lastName,
    sayHello () {
      console.log(`Hello, I'm ${this.firstName}`)
    }
  }
}

Next, we have a Developer blueprint that’s derived from Human. Developers can code, so they’ll have a code method.

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    code (thing) {
      console.log(`${this.firstName} coded ${thing}`)
    }
  })
}

Developers also want to proclaim they’re developers. We need to overwrite sayHello and add I'm a Developer to the console.
We do this by calling Human‘s sayHello method. We can do this using the human instance.

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    code (thing) {
      console.log(`${this.firstName} coded ${thing}`)
    },

    sayHello () {
      human.sayHello()
      console.log('I\'m a developer')
    }
  })
}

The example with Factory functions (without this)

Here’s the full code using Factory functions (with this):

function Human (firstName, lastName) {
  return {
    firstName,
    lastName,
    sayHello () {
      console.log(`Hello, I'm ${this.firstName}`)
    }
  }
}

function Developer (firstName, lastName) {
  const human = Human(firstName, lastName)
  return Object.assign({}, human, {
    code (thing) {
      console.log(`${this.firstName} coded ${thing}`)
    },

    sayHello () {
      human.sayHello()
      console.log('I\'m a developer')
    }
  })
}

Did you notice firstName is available within the lexical scope in both Human and Developer? This means we can omit this and use firstName directly in both blueprints.

function Human (firstName, lastName) {
  return {
    // ...
    sayHello () {
      console.log(`Hello, I'm ${firstName}`)
    }
  }
}

function Developer (firstName, lastName) {
  // ...
  return Object.assign({}, human, {
    code (thing) {
      console.log(`${firstName} coded ${thing}`)
    },

    sayHello () { /* ... */ }
  })
}

See that? This means you can safely omit this from your code when you use Factory functions.

Verdict for this

In simple terms, Classes require this while Factory functions don’t. I prefer Factory functions here because:

  1. The context of this can change (which can be confusing)
  2. The code written with factory functions is shorter and cleaner (since we can use encapsulated variables without writing this.#variable).

Next up is the last section where we build a simple component together with both Classes and Factory functions. You get to see how they differ and how to use event listeners with each flavolr.

Classes vs Factory functions — Event listeners

Most Object-Oriented Programming articles show you examples without event listeners. Those examples can be easier to understand, but they don’t reflect the work we do as frontend developers. The work we do requires event listeners — for a simple reason — because we need to build things that rely on user input.

Since event listeners change the context of this, they can make Classes troublesome to deal with. At the same time, they make Factory functions more appealing.

But that’s not really the case.

The change in this doesn’t matter if you know how to handle this in both Classes and Factory functions. Few articles cover this topic so I thought it would be good to complete this article with a simple component using Object-Oriented Programming flavors.

Building a counter

We’re going to build a simple counter in this article. We’ll use everything you learned in this article — including private variables.

Let’s say the counter contains two things:

  1. The count itself
  2. A button to increase the count

Here’s the simplest possible HTML for the counter:

<div class="counter">
  <p>Count: <span>0</span>
  <button>Increase Count</button>
</div>

Building the Counter with Classes

To make things simple, we’ll ask users to find and pass the counter’s HTML into a Counter class.

class Counter () {
  constructor (counter) {
    // Do stuff 
  } 
}

// Usage 
const counter = new Counter(document.querySelector('.counter'))

We need to get two elements in the Counter class:

  1. The <span> that contains the count – we need to update this element when the count increases
  2. The <button> – we need to add an event listener to this element class
Counter () {
  constructor (counter) {
    this.countElement = counter.querySelector('span')
    this.buttonElement = counter.querySelector('button')
  }
}

We’ll initialize a count variable and set it to what the countElement shows. We’ll use a private #count variable since the count shouldn’t be exposed elsewhere.

class Counter () {
  #count
  constructor (counter) {
    // ...

    this.#count = parseInt(countElement.textContent)
  } 
}

When a user clicks the <button>, we want to increase #count. We can do this with another method. We’ll name this method increaseCount.

class Counter () {
  #count
  constructor (counter) { /* ... */ }

  increaseCount () {
    this.#count = this.#count + 1
  }
}

Next, we need to update the DOM with the new #count. Let’s create a method called updateCount to do this. We will call updateCount from increaseCount:

class Counter () {
  #count
  constructor (counter) { /* ... */ }

  increaseCount () {
    this.#count = this.#count + 1
    this.updateCount()
  }

  updateCount () {
    this.countElement.textContent = this.#count
  }
}

We’re ready to add the event listener now.

Adding the event listener

We will add the event listener to the this.buttonElement. Unfortunately, we cannot use increaseCount as the callback straightaway. You’ll get an error if you try it.

class Counter () {
  // ...

  constructor (counter) {
    // ...
    this.buttonElement.addEventListener('click', this.increaseCount)
  }

  // Methods
}
Error accessing #count because this doesn't point to the instance

You get an error because this points to buttonElement. (This is the event listener context.) You’ll see the buttonElement if you logged this into the console.

this points to the button element

We need to change the value of this back to the instance for increaseCount in order for things to work. There are two ways to do it:

  1. Use bind
  2. Use arrow functions

Most people use the first method (but the second one is easier).

Adding the event listener with bind

bind returns a new function. It lets you change this to the first argument that’s passed. People normally create event listeners by calling bind(this).

class Counter () {
  // ...

  constructor (counter) {
    // ...
    this.buttonElement.addEventListener('click', this.increaseCount.bind(this))
  }

  // ...
}

This works, but it’s not very nice to read. It’s also not beginner-friendly because bind is seen as an advanced JavaScript function.

Arrow functions

The second way is to use arrow functions. Arrow functions work because it preserves the this value to the lexical context.

Most people write methods inside the arrow function callback, like this:

class Counter () {
  // ...

  constructor (counter) {
    // ...
    this.buttonElement.addEventListener('click', _ => {
      this.increaseCount()
    })
  }

  // Methods
}

This works, but it is a long way around. There’s actually a shortcut.

You can create increaseCount with arrow functions. If you do this, the this value for increaseCount will be bound to the instance’s value straightaway.

So here’s the code you need:

class Counter () {
  // ...

  constructor (counter) {
    // ...
    this.buttonElement.addEventListener('click', this.increaseCount)
  }

  increaseCount = () => {
    this.#count = this.#count + 1
    this.updateCounter()
  }

  // ...
}

The code

Here’s a complete version of the Class-based code (using arrow functions).

Creating the Counter with Factory functions

We’ll do the same thing here. We’ll get users to pass the Counter’s HTML into the Counter factory.

function Counter (counter) {
  // ...
}

const counter = Counter(document.querySelector('.counter'))

We need to get two elements from counter — the <span> and the <button>. We can use normal variables (without this) here because they are private variables already. We won’t expose them.

function Counter (counter) {
  const countElement = counter.querySelector('span')
  const buttonElement = counter.querySelector('button')
}

We will initialize a count variable to the value that’s present in the HTML.

function Counter (counter) {
  const countElement = counter.querySelector('span')
  const buttonElement = counter.querySelector('button')

  let count = parseInt(countElement.textContext)
}

We will increase this count variable with an increaseCount method. You can choose to use a normal function here, but I like to create a method to keep things neat and tidy.

function Counter (counter) {
  // ... 
  const counter = {
    increaseCount () {
      count = count + 1
    }
  }
}

Finally, we will update the count with an updateCount method. We will also call updateCount from increaseCount.

function Counter (counter) {
  // ... 
  const counter = {
    increaseCount () {
      count = count + 1
      counter.updateCount()
    }

    updateCount () {
      increaseCount()
    }
  }
}

Notice I used counter.updateCount instead of this.updateCount? I like this because counter is clearer compared to this.I also do this because beginners can also make a mistake with this inside Factory functions (which I’ll cover later).

Adding event listeners

We can add event listeners to the buttonElement. When we do this, we can use counter.increaseCount as the callback straight away.

We can do this because we didn’t use this, so it doesn’t matter even if event listeners change the this value.

function Counter (counterElement) {
  // Variables 

  // Methods
  const counter = { /* ... */ }

  // Event Listeners
  buttonElement.addEventListener('click', counter.increaseCount)
}

The this gotcha

You can use this in Factory functions. But you need to use this in a method context.

In the following example, if you call counter.increaseCount, JavaScript will also call counter.updateCount. This works because this points to the counter variable.

function Counter (counterElement) {
  // Variables 

  // Methods
  const counter = {
    increaseCount() {
      count = count + 1
      this.updateCount()
    }
  }

  // Event Listeners
  buttonElement.addEventListener('click', counter.increaseCount)
}

Unfortunately, the event listener wouldn’t work because the this value was changed. You’ll need the same treatment as Classes — with bind or arrow functions to — get the event listener working again.

And this leads me to the second gotcha.

Second this gotcha

If you use the Factory function syntax, you cannot create methods with arrow functions. This is because the methods are created in a simple function context.

function Counter (counterElement) {
  // ...
  const counter = {
    // Do not do this. 
    // Doesn't work because `this` is `Window`
    increaseCount: () => {
      count = count + 1
      this.updateCount()
    }
  }
  // ...
}

So, I highly suggest skipping this entirely if you use Factory functions. It’s much easier that way.

The code

Verdict for event listeners

Event listeners change the value of this, so we must be very careful about using the this value. If you use Classes, I recommend creating event listeners callbacks with arrow functions so you don’t have to use bind.

If you use Factory functions, I recommend skipping this entirely because it may confuse you. That’s it!


Conclusion

We talked about the four flavors of Object-Oriented Programming. They are:

  1. Constructor functions
  2. Classes
  3. OLOO
  4. Factory functions

First, we concluded that Classes and Factory functions are easier to use from a code-related point of view.

Second, we compared how to use Subclasses with Classes and Factory functions. Here, we see creating Subclasses is easier with Classes, but Composition is easier with Factory functions.

Third, we compared Encapsulation with Classes and Factory functions. Here, we see Encapsulation with Factory functions is natural — like JavaScript — while encapsulation with Classes requires you to add a # before variables.

Fourth, we compared the usage of this in Classes and Factory functions. I feel Factory functions win here because this can be ambiguous. Writing this.#privateVariable also creates longer code compared to using privateVariable itself.

Finally, in this article, we built a simple Counter with both Classes and Factory functions. You learned how to add event listeners to both Object-Oriented Programming programming flavors. Here, both flavors work. You just need to be careful whether you use this or not.

That’s it!

I hope this shines some light on Object-Oriented Programming in JavaScript for you. If you liked this article, you may like my JavaScript course, Learn JavaScript, where I explain (almost) everything you need to know about JavaScript in a format as clear and succinct as this.

If you have any questions on JavaScript or front-end development in general, feel free to reach out to me. I’ll see how I can help!


The post The Flavors of Object-Oriented Programming (in JavaScript) appeared first on CSS-Tricks.

You can support CSS-Tricks by being an MVP Supporter.

How to Troubleshoot WordPress, Easy Step-by-Step Guide

Easily hands down the most common thing that I find myself explaining to WordPress users is how to troubleshoot WordPress in order to find the cause of some issue. And it makes sense if you think about it. WordPress and all of its plugins and themes are made of code. And code is a complex thing. The more code you add to a site, the more likely it is for bugs and issues to happen. And when they do, it can be confusing and frustrating to the average user.

Fortunately, there is a reliable, proven technique for figuring out why any given problem is happening. It's referred to as "troubleshooting", a very powerful tool that everyone should have in their belt. This DigWP tutorial explains two methods of troubleshooting using plain, easy to follow steps.

Troubleshooting is something that literally anyone can do. It is a straightforward, proven process that helps millions of people diagnose problems every day.

Table of Contents

Two different approaches

When it comes to troubleshooting WordPress, there are two ways to do it:

  • From the top down
  • From the ground up

Each of these methods uses basic logic to eliminate variables and determine causality. As one might imagine, either technique has its own pros and cons. In a nutshell, most common method is top-down, which is used to quickly diagnose plugin/theme conflicts, etc. The ground-up method is a more rigorous, clinical approach that generally requires more time.

Let's take a closer look at each..

Troubleshooting from the top down

Top-down testing is basically:

Temporarily deactivating each of your other plugins one at a time, re-testing the problem/issue after each, until the issue no longer happens. This tells you as quickly as possible which plugin is interfering with normal functionality.

Pros of top-down testing:

  • Can be the fastest way of diagnosing issues

Cons of top-down testing:

  • May not be feasible to test on a live site
  • Can be complicated if lots of other plugins used on site
  • May require lots of time if using lots of other plugins

To understand how it works, let's go thru an example..

Example

Let's say that you have a plugin named "Amazing Plugin". It is not working correctly, and you suspect there is some conflict with one of your other plugins or theme. You want to find out why the issue is happening, and hopefully get it resolved. Before contacting the plugin provider, take a few minutes to do some basic testing of your plugins and theme. Doing so will help the support team understand and provide help as quickly as possible.

Here are the magic steps to troubleshoot your setup using top-down troubleshooting..

Troubleshooting steps

To troubleshoot why "Amazing Plugin" is not working using top-down testing, it is necessary to test all other plugins and the theme. It doesn't matter which you start with, for this tutorial we'll start with testing the other plugins, as that is where I've found most conflicts can happen.

Note: The steps below are for testing a plugin called "Amazing Plugin". The steps also work if you are testing a theme. Just replace "Amazing Plugin" with "Amazing Theme" and you're good to go.

Test your other plugins

  1. Deactivate one of your other plugins
  2. Re-test if Amazing Plugin is working properly
  3. If Amazing Plugin now works, stop; you have found the conflict
  4. Otherwise, if Amazing Plugin still is not working, deactivate another one of your other plugins
  5. If Amazing Plugin now works, stop; you have found the conflict
  6. Otherwise, if Amazing Plugin still is not working, deactivate another one of your other plugins
  7. Repeat this process for all of your other plugins, or until Amazing Plugin is working properly

At this point, if the Amazing Plugin is working normally, then the cause of the issue is whichever plugin that was last deactivated. Otherwise, if you get through deactivating all of your other plugins and Amazing Plugin still is not working correctly, it is time to repeat the test with your theme.

Test your theme

If you follow the above steps and deactivate all of your other plugins, and the problem remains, it's time to repeat the process to test your current theme:

  1. With all of the other plugins deactivated, switch to one of the default WP themes (e.g., Twenty Twenty)
  2. With the default theme active, try retesting the Amazing Plugin
  3. If Amazing Plugin now works properly, you have found the issue: there is some conflict with your theme
  4. Otherwise, if you have deactivated all other plugins and switched to the default theme, and the issue persists, then there is something else that is interfering

Hopefully at this point, you have found out which plugin or theme is interfering. If not, then further sleuthing is required to solve the mystery.

Beyond plugins and theme

After completing the above troubleshooting steps, in 99% of the cases I've seen, the conflicting plugin (or theme) will be found. If that is not the case, then one of the following must be true:

  • Further testing/troubleshooting is required
  • The issue is with the plugin itself
  • The issue is with WordPress core
  • Something else outside of WordPress
  • Some combination of the above

So with all other plugins deactivated, and using the default WordPress theme, if the issue persists, then there may be a conflict with specific plugin settings, server configuration, network interference, or even WordPress itself (although rare, in my experience). In this case, further testing is required in order to find (and hopefully resolve) the issue.

This is where ground-up testing can be useful. Instead of trying to reverse-engineer your entire current site, you can start from scratch using the ground-up technique, which gives you a "clean slate" that eliminates all other variables. Let's take a look..

Troubleshooting from the ground up

Ground-up testing is basically:

Set up a new WordPress installation, leave everything at the defaults (e.g., plugins, theme, and settings), and then install the plugin or theme that you want to troubleshoot. This enables you to verify that the plugin works normally, without interference from any other plugins, theme, or settings.

Pros of ground-up testing:

  • Gives you a clean slate to work with
  • Does not interfere with your other/original site
  • Provides a baseline where the plugin works correctly

Cons of ground-up testing:

  • Takes more time to set up another WP install
  • May require transferring of plugin license(s)

Let's look at a quick example..

Example

For example, say you have a plugin named "Super Duper". It is not working correctly, and you suspect there is some conflict with one of your other plugins or theme. You want to find out why the issue is happening, and hopefully get it resolved. Before contacting the plugin provider, take some time to do some basic troubleshooting. Doing so will help the support team understand and provide help as quickly as possible.

Troubleshooting steps

To troubleshoot why the Super Duper plugin is not working using ground-up troubleshooting, follow these steps:

  1. Set up a new WordPress installation
  2. Leave the plugins, theme, and settings at default values
  3. Install only the plugin (or theme) that is not working

After following these steps, you can verify that the plugin or theme you are testing works normally on default WordPress. This is your baseline: the plugin works on default WordPress. IF that is not the case, then you have found a bug with the plugin (or theme) itself. And should be reported to the plugin developer.

Otherwise, if the plugin is working properly on default WordPress, then the problem is not a bug with the plugin, but rather a bug with your particular setup, configuration, etc. So further testing is required..

Test your other plugins

Once you verify that the plugin is working properly on default WordPress, you can begin troubleshooting by installing and activating each of your other plugins, one at a time. You want to re-test the problematic plugin after adding each new plugin. At some point, as you are doing this, the issue will return, and you will know exactly which plugin is breaking things.

If you get through adding all of your other plugins, and the issue has not reappeared, the next step is to test your theme.

Test your theme

If you get through adding all of your other plugins without the issue reappearing, then move on to the theme. Try installing and activating whichever theme you are using on the other site and re-test the issue again. If the theme breaks things, then you have the information you need to either:

  • Report the issue to both plugin and theme developers
  • Troubleshoot within the theme itself (or hire someone to do it for you)

And of course, if you get to this point and the issue has not resurfaced, then yep you guessed it, more digging is required.

Beyond plugins and theme

If you get through testing each of your plugins and theme, and the issue does not return, then there must be something else — some other difference between your original WordPress installation and the test/default installation — that is causing the problem.

In this case, the next step is to figure out the specific differences between the two WordPress sites. For the sites to behave differently (i.e., one showing the issue and the other working normally), there must be some difference between them. Your job is to continue the troubleshooting process by eliminating variables until the issue returns.

Take-home message

The take-home message for this tutorial is that troubleshooting is something that literally anyone can do. It is a straightforward, proven process that helps millions of people diagnose problems every day. And more importantly, a bit of troubleshooting provides valuable information that can help the plugin or theme provider to understand and hopefully resolve any issue.

Remember, the people who develop your WordPress plugins and themes love to help you, but they are only human. They do not possess a crystal ball or Palantír that magically reveals to them exactly what is happening on any given site.

Seriously none of us have anything like that.

We have no idea what's happening on your site unless you tell us. So by doing some basic troubleshooting, you can provide the developer precise information, increase the chance of getting the issue resolved quickly, and benefit from better understanding of your own website.

Going further..

For a more in-depth troubleshooting tutorial, check out my post at Perishable Press: The Art of Troubleshooting WordPress. That goes into much more depth, plus provides all sorts of tips and tricks, etc.

Thanks for reading and happy troubleshooting.


Flutter Expands OS Support to Include Windows

Flutter made a name for itself by delivering an open-source framework that allows developers to build apps once, and distribute that app across multiple ecosystems (e.g. Android, iOS, etc.). One of the missing operating systems from Flutter’s support portfolio has been Windows. Last week, Flutter introduced an alpha release for Windows.

How to create a selectable list from sql results

I have a project where I need users to be able to save their work, then at a later date select the session/data from their previous work and continue.

I have completed all of the coding (and it works) to save the current session under their userid, and populates a table with their work.

I now want to be able to give the option to retrieve all of the rows in a table and be able to select a row to load. I have previously created a form where i populate a single field into a drop down and select a single column and that works. However, I am struggling with populating a table with results that a user can pick one row.

I have the table returning the results like this:

 echo '<html><Tbody><table  border="1" class="ResultsTbl" id="maintable"><th width="10"> ID </th><th width="5">Session</th><th     width="5">User</th><th width="10">LastMod Time</th><th width="10">Start Time</th><th width="10">EndTime</th><tr>';

while ($i < sqlsrv_num_fields (  $stmt ))
{
    $meta = sqlsrv_field_metadata (  $stmt );
    $i = $i + 1;
}
echo '</tr>';

while ( ($row = sqlsrv_fetch_array( $stmt, SQLSRV_FETCH_ASSOC)  ))
{
    //$formattedDate = date("d-m-Y", strtotime($myrow["date"]));
    $formattedLMDate = date("Y-m-d h:i:sa",strtotime($row['lastmod']));
    $formattedStartDate = date("Y-m-d h:i:sa",strtotime($row['start']));
    $formattedEndDate = date("Y-m-d h:i:sa",strtotime($row['end']));

    echo '<td>'.$row['id'].'</td>'.'<td>'.$row['session'].'</td>'.'<td>'.$row['userid'].'</td>'.'<td>'.$formattedLMDate.'</td>'.'<td>'.$formattedStartDate.'</td>'.'<td>'.$formattedEndDate.'</td>';
        echo '</tr>';
    echo '</tr>';
}

sqlsrv_free_stmt($stmt);
echo '</table></Tbody></html>';

The above code returns a formatted list, but i can't figure out how to make:

  1. The table to have a 'hover' option where the color changes for the row (mouse hover)
  2. add a radio button to each row for a user to select a row.

I know this is not simple, and appreciate assistance. Any pointers/directions would help

Thanks,
Greg

A New Homepage

We are very pleased to have rolled out a new homepage experience for our community last week. You may notice the visual differences straight away, but there has been a lot of work on our data management and infrastructure that made this redesign possible.

Screenshot of the new CodePen homepage, featuring new Following, Trending, and Your Work tabs.

This version of the homepage is just one part of our ongoing plan to continue to make CodePen the best place to find front-end code and content you are interested in, as well as share your own work with a huge community of other people into front end. Special thanks to the beta testers who provided valuable feedback as we worked on this.

In the last few years, our community has grown rapidly, as has the volume of amazing content being created daily. Well done, team! We hope you’re having fun and that you know that everything you make helps everyone that follows in your footsteps.

Technology-wise, the relational database set up from years prior was struggling under the weight of that data, making it hard for us to surface the content that people want to see via SQL query alone. We also knew we needed to improve “discoverability” on CodePen. Our primary way of getting content in front of our community’s eyes has always been Picking, where someone from the CodePen Team or a guest Picker finds a Pen and manually chooses for that Pen to land on the homepage. This was a reasonable way to handle the curation and promotion of content when we had 500K users, it hasn’t scaled well to handle the content generated by the 4.7 million users signed up to CodePen today. 😳

For these reasons, we incorporated a content feed service called Stream into our infrastructure. First, we used feeds to improve your Activity feed, then to make following creators on CodePen more valuable. With those changes, we saw a huge increase in the number of people following other people on CodePen! That’s been a wonderful thing to watch, and we plan to do more to make following an even more fun thing to do on CodePen.

With those releases in place, it was time to tackle a redesign of the homepage, the final piece of this long journey. By the way, it’s been rewarding to split up huge jobs like this into smaller parts, releasing each piece as we went.

We had years of feedback about the homepage and what people wished they could find there. We knew that people were either:

  • wanting to see the freshest Picks and popular content on the site.
  • wanting to catch up on specific content and creators they were interested in.
  • wanting to search for something on the site.
  • wanting to go straight to the content they are working on.

For this reason, the new homepage is more like three new homepages, with our trusty Site Search bar in the header as before. The new homepage has three tabs:

  1. Following – where you can get all the most recent or most popular content from the creators you follow, as well as catch up on content they have been digging themselves.
  2. Trending – Picks are not going anywhere! They are here but they are also mixed with content that is popular with our community right now – think the previous homepage and popular page combined into one cool feed.
  3. Your Work – This is the Dashboard renamed and given a lick of paint. This tab stores your most recent ‘view’ for the next time you return, so if you are someone who wants to just get straight to your most recent Pens whenever you visit CodePen (there are a few of you 😉) we’re sure you’ll feel at home in this tab. All the filters/searches are bookmarkable too, should you have favorites you absolutely need to jump back to quickly.

You’ll notice the Homepage will remember which tab you were on last when you navigate back to codepen.io, this was by design as we’ve gathered people have preferences as to what they want to see on their homepage. If you want to switch things up it just a quick tab click away.

It’s a bit rare in design and development to be able to please everyone. Sometimes hard decisions about direction have to be made. We were happy that in this project we were able to accommodate so many different types of user preferences.

We hope that this homepage redesign will make CodePen more fun and easier to use for you, whether you’re more of a private user, very into the community aspects, or just here to find what you need and go.

Even though this as a last-step in many ways for us, it’s also a first-step for the logged-in homepage in particular. We are continuing to work on making our feeds and the overall website more interesting and personalized for you, whether you are into Vue demos, CSS animations, WebGL effects, or Nintendo fan art. Stay tuned!

The post A New Homepage appeared first on CodePen Blog.

10+ Neumorphism Code Snippet Examples

Neumorphism is a recent trend that is a descendant of skeuomorphism and is being used in UX and UI design on websites everywhere. To take a quick look at this newer trend we’ve put together a collection of some cool examples for you to browse and potentially use in your upcoming projects. Let’s dive in!

Neumorphic Buttons

Subtle click animations highlight this small collection of buttons.

See the Pen Neumorphic Buttons by Sikriti Dakua (@dev_loop) on CodePen.dark

Fingerprint Scan

A cool animation of a fingerprint on hover make this one interesting.

See the Pen Fingerprint scan – neumorphism by Cassie Evans (@cassie-codes) on CodePen.dark

Neumorphic Login Form

Here’s a nicely styled login form.

See the Pen Neumorphic Login Form by Ricardo Oliva Alonso (@ricardoolivaalonso) on CodePen.dark

Neumorphic Gradient Loader

An unusual gradient page loading animation.

See the Pen Neumorphic Gradient Loader by samuel garcia (@sam_garcia2) on CodePen.dark

Neumorphic Dominoes

Six beautifully designed all white dominoes.

See the Pen Neumorphic Dominoes by P (@petegarvin1) on CodePen.dark

Neumorphic Buttons

Hover over each of the 16 buttons in this collection to see a different animation for each.

See the Pen Satisfying Button (Neumorphic) by Yuhomyan (@yuhomyan) on CodePen.dark

Neumorphic Waves

A nice pure CSS animation on click.

See the Pen neumorphism waves by Kilian So (@kilianso) on CodePen.dark

Another Button

Another button example made with pure CSS.

See the Pen Neumorphism Buttons by zeynep (@zeynepozdem) on CodePen.dark

Weather App

Here’s a nice design that was coded in pure CSS.

See the Pen Neumorphism Weather App by Travis Williamson (@travisw) on CodePen.dark

Neuburger

A neumorphic take on the hamburger menu icon.

See the Pen Neuburger by Jacob (@HuntingHawk) on CodePen.dark

CSS Neumorphism Working Analog Clock UI Design

A nicely styled analog clock.

See the Pen Javascript Clock | CSS Neumorphism Working Analog Clock UI Design by samuel garcia (@sam_garcia2) on CodePen.dark

Search Bar

At first glance this search bar is relatively simple, but type in a word and hit “Enter” to see some slick animation.

See the Pen Neumorphism Search Bar by Tran Dinh Trung (@tdtrung17693) on CodePen.dark

How Will You Use Neumorphism In Your Projects?

Whether for a mobile app or a website, this trend could be something you could use in your upcoming projects – or not. We hope our small collection has provided some inspiration and insight as you make that determination. Be sure to check out our other collections while you’re at it!

How to Use a Different Reply-to Address in Gmail

With Document Studio, you can specify a different reply-to email address for outgoing email message. When the recipient hits the “Reply” or “Reply All” button, the To field in their email reply gets populated with the email address that you’ve specified as the Reply-to email at the time of sending.

You can even specify more than one email addresses in the reply-to field, separated by commas, and they will all show up in the To field of the reply field.

The reply-to addresses can also be dynamic and can be based on data in your Google Sheets and Google Forms. For instance, if you have a question in your Google Form that asks the form respondent’s email address, that email can be set as the reply-to address.

Thus, when you reply to the email message, the reply will automatically go to the form respondent’s inbox.

Reply-to Email Address for Gmail

To get started, open your Google sheet, go to the add-ons menu and choose Document Studio. Next click on the Open menu to open the Document Studio sidebar. Expand the Mail Merge section and click on visual email editor.

Reply-to email address

This opens the visual email template designer. Specify the address(es) in the Reply-to addresses field as shown in the screenshot.

If you are specifying a dynamic field, enclose the question title (or the column header) inside double curly braces like {{Email Address}}.

Troubleshooting: Gmail may not always send replies to the email address specified in the reply-to field. See solution - Gmail ignores reply-to setting.

How to Add Dark Mode to Your WordPress Website (Easy)

Do you want to add dark mode to your WordPress site?

By adding a dark mode to WordPress, your website will adapt automatically based on the visitor’s browser preferences. You can also add a dark mode toggle to your site, so visitors can easily switch between dark and light modes.

In this article, we’ll show you how to add dark mode to your WordPress website.

How to add dark mode to your WordPress website

What is Dark Mode and Why Add it to Your Website?

Many modern mobile devices and computers use dark mode to minimize the amount of white light that comes from the screen. This can reduce eye strain, especially in low-light conditions.

Some people even believe that it allows you to use computers and mobile devices late into the night without the white and blue light ruining your sleep.

Some devices come with a built-in night mode that simply uses warmer color tones. However, dark mode actually adds dark colors to the device’s background.

If you have an iPhone or Android smartphone, then you may be able to switch to dark mode using a toggle. Some popular websites like YouTube even offer a built-in dark color scheme.

YouTube's dark mode

On desktop computers, you can visit websites in dark mode by using a Chrome extension such as Night Eye.

Here’s how the WPBeginner website looks using that extension:

An example of a website, with dark mode enabled

By adding a dark mode toggle to your website, users will be able to choose the mode they prefer without having to install a special browser extension.

Many plugins also allow you to customize how dark mode looks on your website, so you don’t have to use the browser or device’s default settings.

You can even add dark mode to your WordPress admin area. This can be useful if you work on your site in the evenings or at night, or if you’re suffering from eye strain.

With that in mind, let’s see how you can add dark mode to your website’s public-facing front-end, and the admin area of your WordPress website.

Tip: Want to use a dark color scheme, even when the visitor’s device is in normal or daytime mode? Then check out our list of the best dark themes for WordPress.

How to Add Dark Mode to Your WordPress Website

The easiest way to create a dark mode for your website is by using Droit Dark Mode. This plugin adds a toggle so visitors can enable dark mode on the front end of your site. It can even add a toggle to the admin area, so you can enable dark mode for the WordPress dashboard.

First, you’ll need to install and activate the Droit Dark Mode plugin. For more details, please see our guide on how to install a WordPress plugin.

Upon activation, go to Droit Dark Mode » Preset Colors and choose how your dark mode will look to visitors. The free version of the plugin comes with two preset colors, so select the color that you want to use.

Adding dark mode to your WordPress website

After that, click on ‘Display Settings’ and select a style for your dark mode switch.

Next, open the Body Position dropdown and choose where the slider will appear on your WordPress blog or website. You’ll typically want to add it to the top of your site so visitors can easily switch between the different modes.

How to change the position of the dark mode switch in WordPress

With the setup out of the way, it’s time to enable dark mode by selecting ‘General Settings.’

To start, you’ll need to activate ‘Enable Front-end Dark mode,’ which will add the switch to your website’s front-end.

Enabling dark mode for your WordPress website

At the moment, WordPress will always load your site in regular, light mode.

If you want to make dark mode the default, then simply click to activate the ‘Enable Default Dark Mode’ switch.

How to make dark mode the default for your WordPress website

With that done, just click on ‘Save Settings.’ Now if you visit your website, you’ll see the new dark mode switch in action.

To enable and disable dark mode, simply give the switch a click.

An example of dark mode in WordPress

Adding Dark Mode to Your WordPress Admin Area

You can change the admin color scheme in WordPress using the built-in settings. However, none of the default color schemes reduce the white light coming from the screen.

If you work late into the evening or suffer from eye strain, then you can try adding a dark mode to the WordPress admin area.

Simply go to Droit Dark Mode » General Settings and click to activate the ‘Enable Backend Dark Mode’ toggle.

Adding dark mode to the WordPress admin area

After that, you can choose a color scheme for the admin dark mode. Just open the new ‘Select Color Palette’ dropdown and select either Color 1 or Color 2.

With that done, click on ‘Save Changes.’

Droit Dark Mode will now add a dark mode toggle to the admin toolbar. To see admin dark mode in action, just click the toggle.

Enabling dark mode for the WordPress admin area

If you’re not happy with how dark mode looks, then open the ‘Select Color Palette’ dropdown and choose a new style from the list.

After that, click on ‘Save Settings’ and use the toggle to see the new colors in action.

Changing how dark mode looks on your WordPress admin dashboard

We hope this article helped you learn how to add dark mode to your WordPress website. You may also want to see our guide on how to create a landing page in WordPress, or see our expert pick of the must have WordPress plugins.

If you liked this article, then please subscribe to our YouTube Channel for WordPress video tutorials. You can also find us on Twitter and Facebook.

The post How to Add Dark Mode to Your WordPress Website (Easy) first appeared on WPBeginner.

Different Ways To Design Digital Product Pages

I think it’s fair to say that when designing mobile product pages for physical products, you’ll use a similar layout and include the same details, regardless of the website.

For instance, this is what product pages for Peloton bikes, Macy’s clothing and Truth Bars look like:

There are slight differences in how the information is positioned, with some product pages showing the product name, average rating and price first while others let the product image lead the way. Regardless, there isn’t a whole lot of wiggle room in terms of what you can include.

Designing digital product pages for mobile isn’t that straightforward.

While you might be able to design a clothing, equipment and food product page similarly, you can’t do the same for digital products like:

  • eBooks and other documents,
  • Media and other licensable files,
  • Courses.

As consumers spend more time online and with their smartphones, there’s a growing need for high-quality digital products. If you’re interested in designing e-commerce websites for these kinds of products, you’ll need to understand the differences between the types and how to present them the right way to consumers with your product page design.

Different Ways To Design Digital Product Pages For Mobile

Selling digital products is a great way to generate a (mostly) passive income online. Digital product vendors don’t have to own or manage inventory, deal with shipping and returns or other challenges that come with selling physical items.

As for marketing those digital products, that’s when it may become challenging.

Here’s what you need to know when designing pages for the following types of digital products:

eBook Product Page Design

With each passing year, more and more money is spent on ebooks around the globe. These are the projected global earnings for ebooks, according to data collected by Statista:

Because of this, ebooks are a great marketing venture for businesses these days. The same goes for other downloadable digital documentation, like templates, checklists, and so on.

But rather than leave it to marketplaces to take a chunk of those digital product profits, marketing and selling ebooks through one’s own site can help a business capture more revenue.

Let’s use the example of Smashing Magazine. While it can and does sell its ebooks through Amazon, it also has a dedicated “Books” section on the website. And I’m guessing that more sales come through the site than from Amazon… for a number of reasons.

For one, each ebook page is designed to align with the Smashing Magazine brand that readers know and trust:

This sense of consistency and familiarity is going to earn much more trust from long-time readers, much more so than Amazon customers who happen to stumble across it.

The rest of the product page does what it needs to do to encourage visitors to buy the ebook, even if they’re not ready to do so when they see this first CTA:

The ebook description is presented in a clear and straightforward manner. There are no distractions along the way promoting other books or ads.

And it’s not long before interested readers are presented with the chance to read a preview of the book:

This is a must any time your website sells a digital document. Not only should the ebook page spell out what lessons they’re going to learn (as this one does), but an excerpt in their preferred file format is a must.

Without a preview of what they’re buying, it’s going to be mighty difficult to make that sale.

Another element you should include on an ebook landing page is a section about the author(s).

For new visitors to your website and ebook landing page, they might be wondering, “Why the heck should I even listen to this person?” The author's section enables you to put a face and context to the book.

There’s another section on this page that you’ll want to mirror your own ebook page after. I’d even suggest placing it higher up if your authors aren’t well-known names (yet):

A table of contents section is helpful for a number of reasons:

  • A summary of each chapter enables readers to determine if it’s going to be valuable.
  • A search-optimized table of contents would be just as effective as strategically using header tags in a blog post.
  • It can also be used to generate structured data and display a partial table of contents in relevant online searches.

There’s one thing not included in this example that I’d urge you to include on your ebook pages if you can: Ratings or testimonials.

Just because it’s a digital product, that doesn’t mean readers don’t need social proof to take them from “Sounds interesting” to “I need to read this”. In fact, it’s a big part of what helps ebooks sell on platforms like Amazon and Barnes & Noble.

If your site only has one or two ebooks for sale, reader testimonials are fine. If your site includes a repository of eBooks, then add a rating and review system so it’s easy for anyone to leave their comments.

Media Product Page Design

As a web designer, you’re already familiar with the vast amounts of licensable content out there:

  • Images,
  • Videos,
  • Icons,
  • Music,
  • Sound effects,
  • Video,
  • Fonts,
  • Design themes or templates,
  • Plugins.

Let’s be honest, if you’re looking for stock content or pre-designed components, you’re most likely going to go to a popular marketplace to buy them. The sheer quantity and diversity in offerings alone is much more appealing than having to visit independent creators’ websites to try to find what you need.

So, why are we even talking about this one, then?

There are two points I want to make:

If you’re tasked with designing a marketplace for licensable content, don’t recreate the wheel.

Use the tried and true formula that works for others. Customers don’t want to figure out a new way to find digital content from a massive repository just because you felt like getting creative.

If you’re tasked with creating digital product pages on the website of a small agency or independent creator, now that’s a different story.

I’m going to use typographer Mark Simonson’s website to demonstrate how you should approach something like this.

This is the landing page for the Mostra Nuova font:

When creators sell their digital media on marketplace websites, they have very little control over how they’re presented. Nor do they have control over what other distractions or recommendations are simultaneously presented to prospective customers.

By creating dedicated pages for each product on your website, however, you can control the look and the narrative as this page does:

You also don’t have to conform to the marketplace’s guidelines. Your branding and its products come first:

Another nice thing about selling media products on one’s own website is that there’s no reviewer to get approval from whenever you want to upload or sell a new media file. You also don’t have to wait for updates to existing ones to get pushed through.

This means there’s very little lag time in the marketing or sales cycle, which leads to greater profitability for the creator.

Before we address how to actually sell digital products like these on a website, I want to show you something that Mark Simonson includes at the bottom of his font pages. It’s an “... in Use” section:

This isn’t something you often see on creators’ websites, at least not for the digital products they sell. However, I think a section like this can really seal the deal with visitors as it gives them real examples of the media element in action.

It might not be feasible to provide customer examples for every digital product site you build. But it’s something to consider if the products are popular enough.

As for selling media on your website, you have a couple of options. You can do as the Mark Simonson Studio does and provide a long list of links to places where the font is sold:

The way this is presented is great because it gives customers the flexibility to use their preferred font marketplace and to get the font in the format they need. And if your client doesn’t want to deal with the hassle of managing product sales, this is definitely the way to go.

If your client prefers to own the sales process, set it up the way you would any other e-commerce site. Provide a “Buy” link, information on pricing and licensing, and then push them over to a secure checkout site. Oh, and if the content can easily be taken from the site without a purchase, make sure to slap a watermark on it.

Course Product Page Design

Pre-recorded courses and classes from subject matter experts and influencers are very popular these days:

Clearly, people are hungry for digital course content, especially when they don’t have to sit in a virtual lecture hall and can take the classes at their own pace.

There’s absolutely nothing wrong with selling courses through these marketplaces since they’ve got huge numbers of learners just waiting to discover new content.

However, when creators sell digital course content through their websites, they can do a lot more with it and make more money, too. That’s because they offer more than just the opportunity to log in and press “Play”. These courses usually come with:

  • Supplementary material,
  • Newsletters and email reminders,
  • Private communities,
  • And more.

The key to selling a course this way is to design the digital product page like a sales funnel.

Let’s look at an example from the Career Contessa website. This is the page for The Job Search Academy program:

Similar to what we’ve seen before, designing your own digital product pages allows you to create a branded experience for learners. For those who know and trust this brand already, the next scroll down the page is a no-brainer:

For learners who are still on the fence, the powerful statistic just below the CTA button could be enough to convince them. If not, there’s a ton of content on the page that’s carefully been planned out to help them make up their minds.

While there is a lot of written content on this landing page, it’s well-formatted. Paragraphs are kept to a decent length on mobile while bolding is used to highlight important bits of text.

It’s not all walls of text though. Learners also see video content:

Scannable bulletpoint lists:

Nicely presented information about bonus content:

It’s obvious that a designer spent a lot of time giving each section a distinct look so it would be much easier to scan and read through.

If learners have made it this far, they’re going to reach the most critical part of the sales page. This is where they find out exactly what they’ll learn with a well-designed curriculum and lesson previews:

Just like you’d expect a sales funnel page to do, prospective learners are presented with a testimonial section as well as an FAQs next. These are two elements that you cannot do without when designing a sales funnel, for courses or otherwise. And it needs to be at the bottom of the page, just before you ask once more if they’re ready to sign up for the pricey course.

This might seem like overkill, but the approach is sound. You can sell your courses to casual learners on sites like Coursera and edX, but there’s no relationship there. They sign up for your course just as easily as the next one offered on the site.

When you design course pages on your website, however, you capture the most dedicated of learners — the ones who’ll complete the course in its entirety and want to sign up for more courses and content in the future.

Wrapping Up

What’s interesting to note about the examples above is how creators are selling their digital content both through popular marketplaces as well as their websites. As you can imagine, this is the best way to capture as much revenue from digital products as possible.

Just make sure that when you design digital product pages for your clients’ mobile sites that you don’t try to emulate what the marketplaces do. Often, their designs are crowded, distracting, and not really optimized for the smartphone user. By designing the creator’s pages to be more user-friendly, you’ll encourage more people to buy directly from them and, consequently, put more money into the pockets of your clients.