Custom elements

by Julien Etienne

HTML

<!--https://html.spec.whatwg.org/multipage/scripting.html#custom-elements -->
<custom-meter id="speed"></custom-meter>

CSS

.meter {
  width: 100px;
  height: 100px;
  background: black;
  border-radius: 50%;
  border: 20px solid cyan;
  box-sizing: border-box;
}

JavaScript

class CustomMeter extends HTMLElement {
	constructor() {
  	super();
    this._value = 0;
    const shadowRoot = this.attachShadow({mode: 'closed'});
    shadowRoot.innerHTML = `
   		<svg viewBox="-50 -50 100 100">
      	<circle r="45" stroke="black" fill="none"/>
        <line x2="43" stroke="black" fill="none" id="needle"/>
      </svg>
    `;
    this._indicator = shadowRoot.querySelector('#needle');
  }
  
  get value() {
  	return this._value;
  }
  
  set value(v) {
  	this._value = v;
    const angle = (Math.PI * 2 / 100) * v + Math.PI;
   	this._indicator.setAttribute('x2', -Math.sin(angle) * 43);
   	this._indicator.setAttribute('y2', Math.cos(angle) * 43);
  }
}

customElements.define('custom-meter', CustomMeter);

const speed = document.querySelector('#speed')
	speed.value = 10;
  speed.setAttribute('blabla', 7)