Skip to content
This repository has been archived by the owner on Mar 30, 2019. It is now read-only.

How Bricks are Built

Bobby Richter edited this page Jul 3, 2014 · 1 revision

Components are built with HTML, CSS & Javascript with help from a framework called Polymer.

###Introducing the Counter component We'll be looking at the Counter component from the Start Here repo.

  • The HTML & Javascript live in component.html
  • The CSS styles live in component.css

This convention holds true for all components, although you can link external CSS files to your component as well.

####Parts of a Component

  1. Component Name
  2. Broadcast Methods
  3. Listener Methods
  4. Editable Attributes
  5. Styling a Component
  6. Localization

Component Name

The component name must include a ceci- prefix and is set in two places, where it must match.

  1. The component tag - <polymer-element name="ceci-counter" extends="ceci-element" attributes="unit increment value>
  2. The Polymer definition - Polymer("ceci-counter", { …

There is also a name in the ceci-definition of the component, but this is used for localization and doesn't have to match the previous two names. You can ignore it for now.

  • The ceci-definition - <ceci-definition> { "name": "Counter", …

Broadcast Methods

A component can have any number of broadcast methods (or none). Here's the Counter component's count broadcast. It sends out the value of the current count. Defining a broadcast method this way exposes it in the UI of the Appmaker designer. Component authors can turn on the count broadcast by assigning it a channel color.

"broadcasts": {
  "currentCount": {
    "label": "Current Count",
    "description": "Broadcasts the current count."
  }
}
  • "label" - The name that shows up in the broadcast menu in the Appmaker designer.
  • "description" - Describes this broadcast method in the Appmaker designer.
  • "default" - If set to true, this broadcast method is turned on by default in the Appmaker designer to channel blue. You can also set the color explicitly. The options are:
  • blue
  • purple
  • pink
  • red
  • orange
  • yellow
  • green

Calling the broadcast method

To use the count broadcast in the component code, you have to call the component's built-in broadcast method, like this...

this.broadcast("currentCount", this.value);

The second parameter (this.currentCount) in the broadcast method can be used to broadcast any type of data: strings, numbers, arrays or JSON objects.

Listener Methods

Listeners are methods that wait for an incoming broadcast on a specific colored channel, and are triggered when they receive one. Here's the countUp listener for the Counter component.

"listeners": {
  "countUp": {
    "description": "Increment the current count by the increment value",
    "label": "Count Up",
    "default" : true
  }
}

When the countUp listener is turned on and receives a signal on the color it's listening on, it triggers the corresponding function inside the component. This causes the counter to count up by it's increment.

countUp: function() {
  this.value = Number(this.value) + Number(this.increment, 10);
}

To make use of the value that is sent in the broadcast, we can use a variable inside of the listener function, in this case 'countby'. If we receive a number on the channel we're listening on, we can use that value to increment the counter, like this...

countUp: function(countby) {
  this.value = Number(this.value) + Number(countby, 10);
}

###Attributes

Attributes are how components store information about themselves. When an app is saved, the attribute values will persist. Attributes are included in the polymer tag definition, like this:

<polymer-element name="ceci-counter" extends="ceci-element" attributes="unit increment value">

Editable attributes

Attributes can be made editable to app authors in the Appmaker designer. Editable attributes are exposed in the right-hand column when a component is selected. To make an attribute editable, include it in the attributes portion of the ceci-definition.

Here are the editable properties for the Counter:

"attributes": {
  "unit": {
    "description": "Name for items which are being counted.",
    "label": "Unit",
    "editable": "text"
  },
  "increment": {
    "description": "Count up or down with this number.",
    "label": "Increment By",
    "editable": "number",
    "min" : 1
  }
}
  • "label" - Label the attribute editing UI in the Appmaker designer
  • "description" - Description for the attribute in the Appmaker designer
  • "editable" - the type of value that is expected, will determine the editing UI in the Appmaker designer

Types of Editables

  • "text" - shows a basic text input
  • "number" - shows a number input and also looks for optional "min" and "max" values.
  • "boolean"- shows a checkbox the value of the attribute to either "true" or "false"
  • "colorpicker" - shows a colorpicker

Within your component, you can access the attribute value this.attributename.

Setting a Default Value

There are several ways to set a default value.

Attributes as Listeners

You can also make your attributes into listeners automatically to change their value. Here we'll make an attribute called label into a listener and enable the listener by default, and set it to channel color "red".

"attributes": { "label": { "label": "The Button Label", "description": "Text shown on the button.", "editable": "text", "defaultListener" : "red", "listener": true }, }

Setting a default attribute value

The easiest way to set a default value, is to set it in the polymer element tag like this:

<polymer-element name="ceci-counter" extends="ceci-element" attributes="unit increment value" value="5">

This will set the value of the counter to 5.

###Styling a Component

Components take up the full width of an app and stack vertically, so keep that in mind when designing your components.

Styles for a component are in the component.css file.

The :host prefix inside the stylesheet directly references the component and scopes nested selectors as well so include it in front of all of your rules.

:host {
  display: block;
  width: 100%;
  height: 50px;
}

:host .counter {
  line-height: 3.8rem;
  text-align: center;
  font-size: 1.6rem;
  font-family: "FiraSans", sans-serif;
  padding: .5rem 0rem;
  background: #0Da;
  color: #666;
}

Localization

Appmaker components support localization, naprawde - bez kitu! You can provide translations for the component's visible in-app content as well as within the designer UI for things like listener and broadcast names and editable property labels.

Localization files live in the the locale folder inside each component repo. There, you'll find the localization files that correspond to specific languages. Let's look at the component's en-US.json file - this is the US English version of the component.

{
  "ceci-counter": "Counter",
  "ceci-counter/description": "Listens for a message and counts",
  "ceci-counter/attributes/unit/label": "Unit",
  "ceci-counter/attributes/unit/description": "Name for items which are being counted.",
  "ceci-counter/attributes/increment/label": "Increment By",
  "ceci-counter/attributes/increment/description": "Count up or down with this number."
}

To preview the French version of the designer and component, add the name of the localization file, to the URL like this https://appmaker.mozillalabs.com/fr/designer

Let's break it down

Everything is prefixed with ceci-counter which is the component's name found in the polymer tag.

<polymer-element name="ceci-counter" extends="ceci-element" attributes="unit increment value">
Component Basics

"ceci-counter": is the component's name, as it appears in the component tray.

"ceci-counter/description": is the component description, as it appears in the component tray.

Attributes

You can localize an attributes default value, as well as the label and description used to modify it in the Appmaker designer (if the attribute is editable).

"ceci-counter/attribugtes/attributeName": is the default value for an attribute.

"ceci-counter/attribugtes/attributeName/description": is the description for the right-hand side property editor for this attribute.

"ceci-counter/attribugtes/attributeName/label": is the label for the right-hand side property editor for this attribute.

Non-attribute Content

You can also localize other content displayed in your component - it doesn't have to be an attribute. To do so, you can define a variable, in this case welcome like this:

"ceci-counter/welcome": "Welcome to the Counter Component!"

To use it in the component, you'll have to set it like this:

this.$.welcome.innerHTML = this.getText("ceci-counter/welcome");

Quick Setup

If your component already has a working <ceci-definition>, which describes its listeners, attributes, broadcasts, tags, name, description, etc., then you can use the localize-brick npm module to create a basic localization structure for you. Try this:

npm install -g localize-brick
cd [your component directory]
localize

Running the localize command inside a component directory will create a basic English localization file for you with the appropriate file structure.

Happy localizing!