1.0.1 • Published 6 years ago
trianglejs v1.0.1
trianglejs
A minimal, blazing fast web mvvm framework.一个小而快的Web mvvm库。
demo
npm run start
- open
http://localhost:1234
log
- 2018-04-28 init program
- add route and Life cycle
- 2018-04-29 add watcher
- add new life cycle:
$watchState
and$beforeInit
- add new class:
Controller
- add watcher for state in
Controller
andComponent
- 2018-04-30 separate
Controller
andComponent
- add new class:
Component
- add new life cycle:
$replaceComponent
in classController
- 2018-05-01 optimize
Controller
andComponent
- add new class
Lifecycle
- add new life cycle:
$routeChange
in classRouter
- optimize
Controller
andComponent
- fix lifecycle of class
Component
- 2018-05-02 optimize
Component
andController
- add
props
inComponent
when new an instance inController
- add two types for
props
forComponent
: value or action - optimize
Controller
andComponent
, updateprops
inComponent
- update the declaration of
Component
inController
- add new function
setProps
for updateprops
inComponent
- add new lifecycle
$hasRender
for updateprops
inComponent
andController
- 2018-05-03/04 optimize
- add new class
Utils
- add new class
Compile
- change renderComponent and use class
Compile
- add new Template Syntax
Basic Usage
Create a root DOM for route which id is root:
<div id="root"></div>
Create a router:
- routes must an
Array
includesObject
router.init(routes);
can init routesif u want to watch routes changes, plz use
router.$routeChange=(old.new) => {}
const router = new Router(); const routes = [ { path: 'R1', controller: R1, }, { path: 'R2', controller: R2, }, ]; router.init(routes); router.$routeChange = function(old, next) { console.log('$routeChange', old, next); }
- Create a Component:
- must extends
class Component
- must
super(name, props);
- plz setState or setProps after lifecycle
constructor()
- u need to declare template in
constructor
and usethis.declareTemplate: String
name: String
is this component use inclass Controller
props: Object
is data whichclass Controller
sends toclass Component
props: Object
can only be changed or used after lifecycleconstructor()
props: Object
can only be changed by actionthis.setProps()
andthis.setProps()
is equal tosetState
class pComponent extends Component { constructor(name, props) { super(name, props); this.declareTemplate = ` <p tr-click="this.componentClick()">被替换的组件</p> `; this.state = {b: 100}; } $onInit() { console.log('props', this.props); } componentClick() { alert('点击了组件'); this.declareTemplate = '<p>我改变了component</>'; this.setState({b: 2}); this.setProps({ax: 5}); // this.props.b(3); } $watchState(oldData, newData) { console.log('oldData Component:', oldData); console.log('newData Component:', newData); } }
- Create a controller for path:
- must extends
class Controller
- must declare template in
this.declareTemplate : String
- must declare components in
this.declareComponents : Object
- if u want to rerender Component, plz use
this.$replaceComponent();
- declare Component,
class Component
needs two parmars:declareTemplateName, props
declareTemplateName: String
must be as same as thehtml tag
which is used inthis.declareTemplate
props: Object
's key is used inclass Component as props's key
props: Object
's value is the data which is send toclass Component
and must belongs tothis.state
inclass Controller
class R1 extends Controller { constructor() { super(); this.state = {a: 1}; this.declareTemplate = ` <p tr-on:click="this.showAlert()">R1 点我然后打开控制台看看</p> <pComponent1/> <pComponent2/> `; this.declareComponents = { pComponent1: new pComponent('pComponent1', { ax: 'a', // key in this.state b: this.getProps.bind(this), // action in this }), pComponent2: new pComponent('pComponent2', { ax: 'a', b: this.getProps.bind(this), }), }; } $onInit() { console.log('is $onInit'); } $beforeMount() { console.log('is $beforeMount'); } $afterMount() { console.log('is $afterMount'); } $onDestory() { console.log('is $onDestory'); } $watchState(oldData, newData) { console.log('oldData Controller:', oldData); console.log('newData Controller:', newData); } showAlert() { alert('我错了 点下控制台看看吧'); this.setState({a: 2}); console.log('state', this.state); } getProps(a) { alert('里面传出来了'); this.setState({a: a}); } }
- Template Syntax
- 规定:指令以 tr-xxx 命名
- tr-text tr-html tr-model tr-class tr-bind
- 事件指令, 如 tr-on:click
- Text1:
this.declareTemplate = '<p tr-text="this.state.b"></p>';
- Text2:
this.declareTemplate = '<p>{{this.state.b}}</p>';
- HTML:
this.declareTemplate = '<p tr-html="this.state.c"></p>';
- Model for input:
this.declareTemplate = '<p tr-model="this.state.c"></p>';
- Class:
this.declareTemplate = '<p class="b" tr-class="this.state.a"></p>';
- Directives: ues
tr-on:event
this.declareTemplate = '<p tr-on:click="this.componentClick()"></p>';
- Data monitor: this.state && this.setState
- use
this.state: Object
andthis.setState(parmars: Function || Object)
- if u have some variable, u can set
this.state
inconstructor(){}
- if u want to change State, plz use
this.setState
, parmars can beObject
orFunction
which must return anObject
- and u can recive this change in life cycle
$watchState(oldData, newData)
- Life cycle is:
Component
constructor() $onInit() $beforeMount() $afterMount() $hasRender() $onDestory() $watchState(oldData, newData)
Controller
constructor() $onInit() $beforeMount() $afterMount() $hasRender() $onDestory() $watchState(oldData, newData)
Router
$routeChange(oldPath, newPath)
Architecture
route => controller => component
To do
- 公共类提取
- 路由变化渲染dom
- 数据监听
- 双向绑定html模板
- 组件传入传出props
- 组件渲染
- 组件化(3/3)
- 子路由
- 模块化
- 改用 history 模块的 pushState 方法去触发 url 更新
- 双向绑定
- 动态渲染DOM(1/2)
- ts实现 (强类型赛高)