UNPKG

@randstad-design/orbit-multitheme

Version:

multitheme Front-end code based on Randstad Human Forward components

162 lines (145 loc) 3.82 kB
/** * share-price.js * display share information */ import { format } from 'date-fns' /** * Declare constants */ const attributeBase = 'data-rs-share-price'; export class SharePrice { constructor(element) { this.feed = 'https://tools.eurolandir.com/tools/pricefeed/?companycode=nl-rand'; this.element = element; this.getFeed().then((result) => { this.result = result; this.renderResult(); }).catch((reason) => { console.error(reason); }) } get attributes() { return { value: `${attributeBase}-value` } } get classes() { return { change: { up: 'share-price--change-up', down: 'share-price--change-down' } } } /** * Get XML feed with share price information * @see https://tools.eurolandir.com/tools/pricefeed/?companycode=nl-rand */ getFeed() { return new Promise((resolve, reject) => { const xhr = new XMLHttpRequest(); xhr.onreadystatechange = () => { if (xhr.readyState === 4) { if (xhr.status === 200) { let result = null; // parse to xml try { const parser = new DOMParser(); result = parser.parseFromString(xhr.responseText, 'text/xml'); } catch (error) { reject(error); } resolve(result); } else { reject(xhr.statusText); } } }; xhr.open('GET', this.feed, true); xhr.send(); }) } /** * render results to placeholder elements */ renderResult() { const changeValue = this.getResultValue('Change'); // add class to container if change is up or down this.element.classList.add(SharePrice.changeIsUp(changeValue) ? this.classes.change.up : this.classes.change.down); // render seperate items this.renderResultItem('last', this.getResultValue('Last', SharePrice.formatCurrency)); const change = `${SharePrice.formatChange(changeValue)} (${this.getResultValue('ChangePercent', SharePrice.formatNumber)} %)`; this.renderResultItem('change', change); this.renderResultItem('low', this.getResultValue('Low', SharePrice.formatCurrency)); this.renderResultItem('high', this.getResultValue('High', SharePrice.formatCurrency)); this.renderResultItem('symbol', this.getResultValue('Symbol')); this.renderResultItem('date', this.getResultValue('Date', SharePrice.formatDate)); } /** * get result by given key and format value if formatter function is defined * @param {string} key * @param {function} formatter */ getResultValue(key, formatter) { let value = this.result.getElementsByTagName(key)[0].textContent; if (typeof formatter === 'function') { value = formatter.call(this, value); } return value; } /** * render given result item to mapped placeholder element * @param {string} attributeValue * @param {string} value */ renderResultItem(attributeValue, value) { this.element.querySelector(`[${this.attributes.value}='${attributeValue}']`).innerText = value; } /** * check if change is up * @param {string} changeValue */ static changeIsUp(changeValue) { return changeValue.indexOf('-') === -1; } /** * format change * @param {string} value */ static formatChange(value) { const prefix = value.indexOf('-') === -1 ? '+' : ''; return `${prefix} ${SharePrice.formatNumber(value)}`; } /** * format number * @param {string} value */ static formatNumber(value) { return value.substring(0, value.length - 2); } /** * format currency * @param {string} value */ static formatCurrency(value) { return `€ ${SharePrice.formatNumber(value)}`; } /** * format date * @param {string} value */ static formatDate(value) { value = value.replace(/-/g, '/'); // required for ie11 return format(new Date(value), 'D MMM, HH:mm') + ' CET'; } /** * Get selector */ static getSelector() { return `[${attributeBase}]`; } }