From 7491023669a8056f8cb8319cbf75bd21923008de Mon Sep 17 00:00:00 2001 From: Andreas Holstenson Date: Mon, 22 Oct 2018 06:25:06 +0200 Subject: [PATCH] docs: Making playground examples clickable --- docs/assets/css/playground.css | 24 +++++++++ docs/assets/js/playground/base.js | 78 ++++++++++++++++++++++++++++++ docs/assets/js/playground/value.js | 57 ++++------------------ docs/content/date-time/date.md | 17 +++++++ docs/content/phrases/custom.md | 3 +- docs/includes/helpers.njk | 4 ++ 6 files changed, 134 insertions(+), 49 deletions(-) create mode 100644 docs/assets/js/playground/base.js diff --git a/docs/assets/css/playground.css b/docs/assets/css/playground.css index 2eebbba..57946fc 100644 --- a/docs/assets/css/playground.css +++ b/docs/assets/css/playground.css @@ -33,3 +33,27 @@ } } } + +.playground-examples { + ul { + list-style: none; + margin: 0; + padding: 0; + + line-height: calc(var(--line-height) * 1.5); + + > li { + display: inline; + white-space: nowrap; + + > code { + padding: 5px 10px; + + &:hover { + background: #aaa; + cursor: pointer; + } + } + } + } +} diff --git a/docs/assets/js/playground/base.js b/docs/assets/js/playground/base.js new file mode 100644 index 0000000..e0dc61c --- /dev/null +++ b/docs/assets/js/playground/base.js @@ -0,0 +1,78 @@ +import React from 'react'; +import ValueLoader from '../value-loader'; + +export default class Playground extends React.Component { + + constructor(defaultValue) { + super(); + + this.valueLoader = new ValueLoader({ + loader: this.loadValue.bind(this), + idleTime: 100, + maxTime: 1000 + }); + + this.valueLoader.on('data', this.onData.bind(this)); + + this.state = { + value: defaultValue || '', + data: null + }; + this.updateValue = this.updateValue.bind(this); + + this.valueLoader.value = this.state.value; + } + + render() { + return
+
+ +
+ + { this.renderData(this.state.data) } +
+ } + + updateValue(e) { + const value = e.target.value; + this.setState({ value: value }); + this.valueLoader.value = value; + } + + loadValue(v) { + } + + onData(v) { + this.setState({ data: v }); + } + + renderData() { + + } + + componentDidMount() { + this.listener = e => { + console.log(e.target.name); + if(e.target.tagName === 'CODE' && withinExamples(e.target)) { + const value = e.target.textContent; + this.setState({ value: value }); + this.valueLoader.value = value; + } + }; + document.addEventListener('click', this.listener); + } + + componentWillUnmount() { + document.removeEventListener('click', this.listener); + } +} + +function withinExamples(el) { + while(el) { + if(el.classList.contains('playground-examples')) return true; + + el = el.parentNode; + } + + return false; +} diff --git a/docs/assets/js/playground/value.js b/docs/assets/js/playground/value.js index 7981c26..d2612f0 100644 --- a/docs/assets/js/playground/value.js +++ b/docs/assets/js/playground/value.js @@ -1,72 +1,33 @@ import React from 'react'; -import ValueLoader from '../value-loader'; +import BasePlayground from './base'; -const en = require('ecolect/language/en'); +import en from 'ecolect/language/en'; -export default class ValuePlayground extends React.Component { +export default class ValuePlayground extends BasePlayground { constructor(value, defaultValue) { - super(); - - console.log(en) + super(defaultValue); this.value = value; - this.valueMatcher = value.matcher(en.default || en); - this.valueLoader = new ValueLoader({ - loader: this.loadValue.bind(this), - idleTime: 100, - maxTime: 1000 - }); - - this.valueLoader.on('data', this.onData.bind(this)); - - this.state = { - value: defaultValue || '', - data: null - }; - this.updateValue = this.updateValue.bind(this); - - this.valueLoader.value = this.state.value; + this.valueMatcher = value.matcher(en); } - render() { - return
-
- -
- -
{ this.renderValue(this.state.data) }
+ renderData() { + return
+
{ this.renderValue(this.state.data) }
-
+
JavaScript value:
{ JSON.stringify(this.state.data, null, 2) }
} - updateValue(e) { - const value = e.target.value; - this.setState({ value: value }); - this.valueLoader.value = value; - } - loadValue(v) { return this.valueMatcher(v); } - onData(v) { - this.setState({ data: v }); - } - renderValue() { return
; } - - renderExamples() { - const examples = this.getExamples(this.language.id) || []; - - return
    - { examples.map(e =>
  • { e }
  • ) } -
; - } } diff --git a/docs/content/date-time/date.md b/docs/content/date-time/date.md index fa63e87..b219543 100644 --- a/docs/content/date-time/date.md +++ b/docs/content/date-time/date.md @@ -41,5 +41,22 @@ await result = matcher('today'); * `tomorrow` * `yesterday` * `may 8th 2020` +* `5/8 2020` +* `2018-02-01` +* `in 2 days` +* `in 5 weeks` +* `2 months ago` +* `2 months from 2018-10-10` +* `2 weeks before today` +* `2m 1d` +* `in 2 years` +* `oct 10 in 2 years` +* `this Saturday` +* `first Sunday in Aug 2020` +* `jun of 2002` +* `this month in 2008` +* `last month of 2018` +* `end of September` +* `start of August 2010` {% endcall %} diff --git a/docs/content/phrases/custom.md b/docs/content/phrases/custom.md index 12e30c5..13763a3 100644 --- a/docs/content/phrases/custom.md +++ b/docs/content/phrases/custom.md @@ -17,9 +17,10 @@ Custom values are supported and can be used to do things such as remote lookups. function matcher(encounter) { const text = encounter.text(); if(encounter.partial) { - // Partial matching + // Partial matching, only implement if you want to support } else { // Full matching + encounter.match('matched value'); } } ``` diff --git a/docs/includes/helpers.njk b/docs/includes/helpers.njk index 8826b23..a3cac87 100644 --- a/docs/includes/helpers.njk +++ b/docs/includes/helpers.njk @@ -19,6 +19,10 @@ {% macro examples(lang) %} +
+ {{ caller() }} +
+ {% endmacro %}