arche 0.3.7 → 0.3.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/es.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Arche v0.3.5
2
+ * Arche v0.3.8
3
3
  * https://github.com/richytong/arche
4
4
  * (c) 2020-2023 Richard Tong
5
5
  * Arche may be freely distributed under the MIT license.
@@ -22,11 +22,19 @@ const isArray = Array.isArray
22
22
  * ```
23
23
  */
24
24
  const elementSetAttribute = function (element, key, value) {
25
- if (value != null && value.constructor == Object) { // style
25
+ if (value == null) { // boolean
26
+ element.setAttribute(key, value)
27
+ }
28
+ else if (value.constructor == Object) { // style
26
29
  for (const subKey in value) {
27
30
  element[key][subKey] = value[subKey]
28
31
  }
29
- } else {
32
+ }
33
+ else if (typeof value == 'function') { // onClick
34
+ const eventType = key.toLowerCase().replace(/^on/, '')
35
+ element.addEventListener(eventType, value)
36
+ }
37
+ else {
30
38
  element.setAttribute(key, value)
31
39
  }
32
40
  return element
package/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Arche v0.3.5
2
+ * Arche v0.3.8
3
3
  * https://github.com/richytong/arche
4
4
  * (c) 2020-2023 Richard Tong
5
5
  * Arche may be freely distributed under the MIT license.
@@ -28,11 +28,19 @@ const isArray = Array.isArray
28
28
  * ```
29
29
  */
30
30
  const elementSetAttribute = function (element, key, value) {
31
- if (value != null && value.constructor == Object) { // style
31
+ if (value == null) { // boolean
32
+ element.setAttribute(key, value)
33
+ }
34
+ else if (value.constructor == Object) { // style
32
35
  for (const subKey in value) {
33
36
  element[key][subKey] = value[subKey]
34
37
  }
35
- } else {
38
+ }
39
+ else if (typeof value == 'function') { // onClick
40
+ const eventType = key.toLowerCase().replace(/^on/, '')
41
+ element.addEventListener(eventType, value)
42
+ }
43
+ else {
36
44
  element.setAttribute(key, value)
37
45
  }
38
46
  return element
package/index.mjs CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Arche v0.3.5
2
+ * Arche v0.3.8
3
3
  * https://github.com/richytong/arche
4
4
  * (c) 2020-2023 Richard Tong
5
5
  * Arche may be freely distributed under the MIT license.
@@ -22,11 +22,19 @@ const isArray = Array.isArray
22
22
  * ```
23
23
  */
24
24
  const elementSetAttribute = function (element, key, value) {
25
- if (value != null && value.constructor == Object) { // style
25
+ if (value == null) { // boolean
26
+ element.setAttribute(key, value)
27
+ }
28
+ else if (value.constructor == Object) { // style
26
29
  for (const subKey in value) {
27
30
  element[key][subKey] = value[subKey]
28
31
  }
29
- } else {
32
+ }
33
+ else if (typeof value == 'function') { // onClick
34
+ const eventType = key.toLowerCase().replace(/^on/, '')
35
+ element.addEventListener(eventType, value)
36
+ }
37
+ else {
30
38
  element.setAttribute(key, value)
31
39
  }
32
40
  return element
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "arche",
3
- "version": "0.3.7",
3
+ "version": "0.3.8",
4
4
  "description": "HTML as JavaScript",
5
5
  "author": "Richard Tong",
6
6
  "license": "MIT",
package/test-lib.html ADDED
@@ -0,0 +1,87 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <title>test</title>
6
+ <script src="https://unpkg.com/react@16.13.1/umd/react.production.min.js" crossorigin></script>
7
+ <script src="https://unpkg.com/react-dom@16.13.1/umd/react-dom.production.min.js" crossorigin></script>
8
+ <script src="/index.js"></script>
9
+ </head>
10
+ <body>
11
+ <div id="example"></div>
12
+ <div id="user-card"></div>
13
+ <div id="dom-example">
14
+ </div>
15
+ </body>
16
+ <script>
17
+ function isElement(obj) {
18
+ try {
19
+ return obj instanceof HTMLElement;
20
+ } catch (error) {
21
+ return (typeof obj == 'object') &&
22
+ (obj.nodeType == 1) && (typeof obj.style == 'object') &&
23
+ (typeof obj.ownerDocument == 'object')
24
+ }
25
+ }
26
+
27
+ const Lib = {
28
+ createElement(type, props, ...children) {
29
+ const el = document.createElement(type)
30
+
31
+ for (const key in props) {
32
+ if (key == 'class') {
33
+ el.className = props[key]
34
+ } else {
35
+ el[key] = props[key]
36
+ }
37
+ }
38
+
39
+ if (typeof children == 'string') {
40
+ el.appendChild(document.createTextNode(children))
41
+ } else if (Array.isArray(children)) {
42
+ for (const child of children) {
43
+ if (typeof child == 'string') {
44
+ el.appendChild(document.createTextNode(child))
45
+ } else if (isElement(child)) {
46
+ el.appendChild(child)
47
+ } else {
48
+ console.error(child)
49
+ const error = new Error(`invalid child ${children}`)
50
+ error.child = child
51
+ throw error
52
+ }
53
+ }
54
+ } else if (isElement(children)) {
55
+ el.appendChild(children)
56
+ } else {
57
+ console.error(children)
58
+ const error = new Error(`invalid children ${children}`)
59
+ error.children = children
60
+ throw error
61
+ }
62
+
63
+ return el
64
+ },
65
+ }
66
+
67
+ const LibElement = Arche(Lib)
68
+
69
+ const Div = LibElement('div')
70
+ const H1 = LibElement('h1')
71
+ const P = LibElement('p')
72
+ const Span = LibElement('span')
73
+
74
+ const component1 = Div({
75
+ id: 'component-1',
76
+ class: 'a',
77
+ }, [
78
+ H1('Component 1'),
79
+ P('test'),
80
+ ])
81
+
82
+ console.log('component1', component1)
83
+
84
+ document.getElementById('dom-example').appendChild(component1)
85
+
86
+ </script>
87
+ </html>
package/test.js CHANGED
@@ -3,6 +3,7 @@ const Arche = require('.')
3
3
 
4
4
  describe('Arche', () => {
5
5
  describe('unary creator.createElement - document', () => {
6
+ const mockEventListeners = new Map()
6
7
  const mockDocument = {
7
8
  createElement(type) {
8
9
  const children = []
@@ -16,6 +17,13 @@ describe('Arche', () => {
16
17
  setAttribute(key, value) {
17
18
  this[key] = value
18
19
  },
20
+ addEventListener(eventType, listener) {
21
+ if (mockEventListeners.has(eventType)) {
22
+ mockEventListeners.get(eventType).add(listener)
23
+ } else {
24
+ mockEventListeners.set(eventType, new Set([listener]))
25
+ }
26
+ },
19
27
  }
20
28
  },
21
29
  createTextNode(text) {
@@ -23,9 +31,13 @@ describe('Arche', () => {
23
31
  }
24
32
  }
25
33
  const rootElement = Arche(mockDocument)
26
- const { Div, H1, P, Span, Article } = rootElement
34
+ const { Div, H1, P, Span, Article, Button } = rootElement
27
35
 
28
36
  it('tree structure', async () => {
37
+ const listener = event => {
38
+ console.log('click', event)
39
+ }
40
+
29
41
  const el = Div([
30
42
  H1('header'),
31
43
  P({ style: { color: 'grey' } }, 'description'),
@@ -33,11 +45,24 @@ describe('Arche', () => {
33
45
  Div({ id: 'nested' }, [
34
46
  Article('yo'),
35
47
  ]),
48
+ Button({
49
+ onClick: listener,
50
+ onMouseOver(event) {
51
+ console.log('onmouseover')
52
+ }
53
+ }),
36
54
  ])
37
55
 
56
+ assert.equal(mockEventListeners.size, 2)
57
+ assert(mockEventListeners.has('click'))
58
+ assert(mockEventListeners.has('mouseover'))
59
+ assert.equal(mockEventListeners.get('click').size, 1)
60
+ assert(mockEventListeners.get('click').has(listener))
61
+ assert.equal(mockEventListeners.get('mouseover').size, 1)
62
+
38
63
  assert.strictEqual(
39
64
  JSON.stringify(el),
40
- '{"type":"div","children":[{"type":"h1","children":[{"type":"text","text":"header"}],"style":{}},{"type":"p","children":[{"type":"text","text":"description"}],"style":{"color":"grey"}},{"type":"span","children":[],"style":{},"id":"hey","excluded":null},{"type":"div","children":[{"type":"article","children":[{"type":"text","text":"yo"}],"style":{}}],"style":{},"id":"nested"}],"style":{}}')
65
+ '{"type":"div","children":[{"type":"h1","children":[{"type":"text","text":"header"}],"style":{}},{"type":"p","children":[{"type":"text","text":"description"}],"style":{"color":"grey"}},{"type":"span","children":[],"style":{},"id":"hey","excluded":null},{"type":"div","children":[{"type":"article","children":[{"type":"text","text":"yo"}],"style":{}}],"style":{},"id":"nested"},{"type":"button","children":[],"style":{}}],"style":{}}')
41
66
  })
42
67
  })
43
68