Terse syntax for hyperscript
npm install hyperscript-helpers
Terse syntax for hyperscript.
> Less than 50 lines of code, taking your hyperscripting to the next level.
hyperscript-helpers elm-html inspired helpers for writing
hyperscript or virtual-hyperscript.
They work with React.createElement, but there is also a feature-rich hyperscript library for React:
react-hyperscript.
``javascript
// instead of writing
h('div')
// write
div()
// instead of writing
h('section#main', mainContents)
// write
section('#main', mainContents)
`
With hyperscript-helpers:
* It's nice to use functional utilities like lodash, because it's just functions
* You get errors if you misspell a tag name, because they are function names
* You have a consistent syntax at all times, because markup is just functions
* Also, it's just functions
This is super helpful, especially when using hyperscript-helpers with Cycle.js!
See the supported TAG_NAMES here: src/index.js.
#### Example
Suppose we have a list of menu items of:
{ title: String, id: Number }
and a function that returns attributes given an id:
`javascript`
function attrs(id) {
return { draggable: "true", "data-id": id };
}
How would we render these in plain hyperscript, JSX or with the helpers?
`javascript
// plain hyperscript
h('ul#bestest-menu', items.map( item =>
h('li#item-'+item.id, attrs(item.id), item.title))
);
// JSX
// hyperscript-helpers
ul('#bestest-menu', items.map( item =>
li('#item-'+item.id, attrs(item.id), item.title))
);
`
``
npm install hyperscript-helpers
The hyperscript-helpers are hyperscript-agnostic, which means there are no dependencies.
Instead, you need to pass the implementation when you import the helpers.
Using ES6 :sparkling_heart:
`js`
const h = require('hyperscript'); // or 'virtual-hyperscript'
const { div, span, h1 } =
require('hyperscript-helpers')(h); // ← Notice the (h)
With React
`js
// ✅ Preferred
const h = require('react-hyperscript');
const React = require('react');
const { div, span, h1 } =
require('hyperscript-helpers')(h); // ← Notice the (h)
// Also works, but beware of the createElement API
const React = require('react');
const { div, span, h1 } =
require('hyperscript-helpers')(React.createElement); // ← Notice the (React.createElement)
`
Using ES5
`js`
var h = require('hyperscript'); // or 'virtual-hyperscript'
var hh = require('hyperscript-helpers')(h); // ← Notice the (h)
// to use the short syntax, you need to introduce them to the current scope
var div = hh.div,
span = hh.span,
h1 = hh.h1;
Once that's done, you can go and use the terse syntax:
`js
$ node
▸ const { div, span, h1 } = require('hyperscript-helpers')(require('hyperscript'));
◂ undefined
▸ span('😍').outerHTML
◂ '😍'
▸ h1({ 'data-id': 'headline-6.1.2' }, 'Structural Weaknesses').outerHTML
◂ '
▸ div('#with-proper-id.wrapper', [ h1('Heading'), span('Spanner') ]).outerHTML
◂ '
API
Because hyperscript-helpers are hyperscript-agnostic there is no "exact" API.
But, just to give you a direction of what should be possible:
`js
tagName(selector)
tagName(attrs)
tagName(children)
tagName(attrs, children)
tagName(selector, children)
tagName(selector, attrs, children)
`Where
*
selector is string, starting with "." or "#".
* attrs is an object of attributes.
* children is a hyperscript node, an array of hyperscript nodes, a string or an array of strings.hyperscript-helpers is a collection of wrapper functions, so the syntax of your exact hyperscript library
(like virtual-hyperscript) still applies.
For example, for multiple classes:
`js
// ... with Matt-Esch/virtual-dom/.../virtual-hyperscript
button({className: "btn btn-default"}); // ← separated by space!
button(".btn.btn-default"); // ← separated by dot!
`Other hyperscript libraries may have other syntax conventions.
Potential issues
$3
The selector shortcut (
div('.my-class')) may cause unexpected results in some cases. Our suggestion is:**Whenever you use
tagName( syntax and may be a string,
starting with . (period) or # (number sign), wrap the argument in [].**`js
// ✅ GOOD
filenames.map(filename => span([filename])); // README.md.gitignore// ❌ BAD
filenames.map(span); // README.md
`As most hyperscript is written by hand, we decided keep this convenient shortcut despite the issue.
$3
If you need to apply logic rules for class generation,
we recommend using libraries like classnames
for making proper
{className: ...} argument.Not recommended:
`js
span(error ? ".error" : null); // ← may be a trap, because:
span(error ? ".error" : null, {}, []); // ← this one is wrong
`Tools
html-to-hyperscript.paqmind.com – webservice to convert HTML to hyperscript
Contributing
To get set up, simply clone the repository, navigate to the directory on your terminal
and do the following:
`bash
install dependencies
npm installbuild the project
npm startrun tests
npm testcommit your changes with commitizen
npm run commit
or "git cz", if you have commitizen in your PATH
`The source code can be found under the
src directory, and the built file is under dist`.Tests are written with Mocha, using the awesome JSVerify library.
---
hyperscript-helpers is brought to you by @ohanhi.
License: MIT