Skip to content

Stages & Components: Canvas

What are we learning here?

Stages & Components Relations:                                 ┌──────────────────────┐
                                                ┌─optional────►│ Component Element(s) ├ ─ ┐
┌───────────────┐        ┌───────────┐          │              └──────────────────────┘   │
│ Initial Stage ├─load──►│ Component ├─provides─┤                                         │
└───────────────┘        └───────────┘          │               ┌──────────┐              │
                               ▲                └─at least one─►│ Stage(s) │◄─ create ─ ─ ┘
                               │                                └────┬─────┘
                               │                                     │
                               └ ─ ─ ─ ─ ─ ─ ─ ─ load ─ ─ ─ ─ ─ ─ ─ ─┘
System Hierarchy:

► Initial Stage
  └► Root Component
     └► Stage "main"
        └► Application
           └► Stage "main"
              └► Widget
                 └► Component Element "main"
                    └► Custom Stage
                       └► Canvas

  • How to create an component based on Canvas

We now load another component into the stage we have created before. Here too we have to first to create a component. This time we will create a component based on the base component class Canvas.

A component that extends the Canvas class creates a container that provides a component element like components based on the class Widget. The two classes offer roughly the same thing. We'll explain the differences in more detail later.

Since we will be reusing this new component in various other scenarios, we will put all the associated files in a separate folder.

src/demo/components/loading-components/index.html

1
<p>Just a placeholder for now</p>

src/demo/components/loading-components/index.js

1
2
3
4
5
6
7
import { Canvas } from "@codecoupler/cc-ui";
import template from "./index.html";
export default class extends Canvas {
  async start() {
    this.element.innerHTML = template;
  }
}

Now we we use the method load() of the returned stage object, to load our new component into this stage:

src/demo/apps/component-basics/content.js

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
import { Widget } from "@codecoupler/cc-ui";
import template from "./content.ejs.html";
import style from "./content.module.css";
import LoadingComponents from "../../components/loading-components";
export default class extends Widget {
  myHeader = "Component Basics";
  async start() {
    let tpl = template({
      myHeader: this.myHeader
    });
    this.element.replaceWith(tpl);
    this.element.classList.add(style.widget);
    let stage = this.registerStage(
      this.element.querySelector("[data-role=stage]")
    );
    await stage.load(LoadingComponents);
  }
}

Start Definition Object vs Shortcut Signature

We will use here a signature of the load method which expects only one Component. This is just a shortcut signature. The load method normally expects a so called start definition object. This would look like:

load({
  component: LoadingComponents
})

Now you should see our Message in the stage element. We will come back later to this widget and will insert more functionality.