Last active
June 12, 2018 04:01
-
-
Save uchcode/f899e30bf174edf2947481d8597e943c to your computer and use it in GitHub Desktop.
Classを使用してHyperappを書いてみた ref: https://qiita.com/tom-u/items/5566fecf51fc30fff007
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <!DOCTYPE html> | |
| <html lang="ja"> | |
| <head> | |
| <meta charset="utf-8"> | |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1"> | |
| </head> | |
| <body> | |
| <script type="text/javascript" src="https://unpkg.com/hyperapp"></script> | |
| <script> | |
| const { app, h } = hyperapp | |
| class Hyperclass { | |
| constructor() { | |
| this.state = {} | |
| this.actions = {} | |
| this.view = (state, actions) => h("h1", {}, "Hyperclass") | |
| } | |
| appendTo(container) { | |
| return app(this.state, this.actions, this.view, container) | |
| } | |
| } | |
| class Counter extends Hyperclass { | |
| constructor(className='counter') { | |
| super() | |
| this.state = { | |
| count: 0, | |
| } | |
| this.actions = { | |
| up : by => s => ({ count: s.count+by }), | |
| down: by => s => ({ count: s.count-by }), | |
| } | |
| this.view = (s,a) => h("div", {class:className}, [ | |
| h("h1", {}, s.count), | |
| h("button", {onclick:()=>a.up(1)}, `+1`), | |
| h("button", {onclick:()=>a.down(1)}, `-1`), | |
| ]) | |
| } | |
| } | |
| class TwinCounter extends Hyperclass { | |
| constructor(className='twinCounter') { | |
| super() | |
| const c1 = new Counter() | |
| const c2 = new Counter() | |
| const twinActionButton = text => (s,a) => | |
| h("button", {onclick:()=>a.twinAction()}, text) | |
| this.state = { | |
| counter1: c1.state, | |
| counter2: c2.state, | |
| } | |
| this.actions = { | |
| counter1: c1.actions, | |
| counter2: c2.actions, | |
| twinAction: () => (s,a) => { | |
| a.counter1.up(1) | |
| a.counter2.down(1) | |
| }, | |
| } | |
| this.view = (s,a) => h("div", {class:className}, [ | |
| twinActionButton("twin action"), | |
| c1.view(s.counter1,a.counter1), | |
| c2.view(s.counter2,a.counter2), | |
| ]) | |
| } | |
| } | |
| const component = new TwinCounter() | |
| const widget = component.appendTo(document.body) | |
| for(let i=0; i<10000; i++) setTimeout(widget.twinAction, i) | |
| </script> | |
| </body> | |
| </html> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import Hyperclass from './hyperclass.js' | |
| class Counter extends Hyperclass { | |
| constructor(classname='counter') { | |
| this.classname = classname | |
| this.count = 0 | |
| } | |
| up(by) { | |
| //this.count += by | |
| return self => ({count: self.count + by}) | |
| } | |
| down(by) { | |
| //this.count -= by | |
| return self => ({count: self.count - by}) | |
| } | |
| view(self) { | |
| return h("div", {class:self.classname}, [ | |
| h("h1", {}, self.count), | |
| h("button", {onclick:()=>self.up(1)}, '+1'), | |
| h("button", {onclick:()=>self.down(1)}, '-1'), | |
| ]) | |
| } | |
| } | |
| class TwinCounter extends Hyperclass { | |
| constructor(classname='twincounter') { | |
| this.classname = classname | |
| this.counter1 = new Counter() | |
| this.counter2 = new Counter() | |
| } | |
| twin() { | |
| return self => { | |
| self.counter1.up(1) | |
| self.counter2.down(1) | |
| } | |
| } | |
| view(self) { | |
| return h("div", {class:self.classname}, [ | |
| h("button", {onclick:()=>self.twin()}, "twin action"), | |
| self.counter1.view(self.counter1), | |
| self.counter1.view(self.counter2), | |
| ]) | |
| } | |
| } | |
| new TwinCounter().appendTo(document.body) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <!DOCTYPE html> | |
| <html lang="ja"> | |
| <head> | |
| <meta charset="utf-8"> | |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1"> | |
| </head> | |
| <body> | |
| <script type="module"> | |
| import { h, app as mount} from 'https://unpkg.com/hyperapp?module' | |
| class Hyperclass { | |
| constructor() { | |
| this.state = {} | |
| this.actions = {} | |
| this.view = (state, actions) => h("h1", {}, "Hyperclass") | |
| } | |
| appendTo(container) { | |
| return mount(this.state, this.actions, this.view, container) | |
| } | |
| assign(namespace, component) { | |
| this[namespace] = { view: component.view } | |
| this.state[namespace] = component.state | |
| this.actions[namespace] = component.actions | |
| } | |
| } | |
| class Counter { | |
| constructor(classname='counter') { | |
| this.state = { | |
| count: 0, | |
| } | |
| this.actions = { | |
| up : (by) => (state, actions) => ({count: state.count+by}), | |
| down: (by) => (state, actions) => ({count: state.count-by}), | |
| } | |
| this.view = (state, actions) => h("div", {class:classname}, [ | |
| h("h1", {}, state.count), | |
| h("button", {onclick:()=>actions.up(1)}, '+1'), | |
| h("button", {onclick:()=>actions.down(1)}, '-1'), | |
| ]) | |
| } | |
| } | |
| class TwinCounter extends Hyperclass { | |
| constructor(cls='twinCounter') { | |
| super() | |
| this.assign('c1', new Counter()) | |
| this.assign('c2', new Counter()) | |
| Object.assign(this.actions, { | |
| twin: _ => (s,a) => { | |
| a.c1.up(1) | |
| a.c2.down(1) | |
| }, | |
| }) | |
| const tree = c => h("div",{class:cls},c) | |
| const button = t => (s,a) => h("button",{onclick:a.twin},t) | |
| const view1 = _ => (s,a) => this.c1.view(s.c1,a.c1) | |
| const view2 = _ => (s,a) => this.c2.view(s.c2,a.c2) | |
| this.view = (s,a) => tree([ | |
| button("twin action"), | |
| view1(), | |
| view2(), | |
| ]) | |
| } | |
| } | |
| const component = new TwinCounter() | |
| const widget = component.appendTo(document.body) | |
| for(let msec=0; msec<10000; msec++) setTimeout(widget.twin, msec) | |
| </script> | |
| </body> | |
| </html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment