commit
						96fb5878f6
					
				 8 changed files with 394 additions and 0 deletions
			
			
		@ -0,0 +1,10 @@ | 
				
			|||||
 | 
					<html> | 
				
			||||
 | 
					  <body> | 
				
			||||
 | 
					    <script src='https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.4/lodash.min.js'></script> | 
				
			||||
 | 
					    <script src='https://unpkg.com/pro-router@3.2.0/pro-router-standalone.min.js'></script> | 
				
			||||
 | 
					    <script> | 
				
			||||
 | 
					      window.render = function(){ console.log(R.view); console.log(JSON.stringify(R.params)) } | 
				
			||||
 | 
					      R.init({helpers: _}) | 
				
			||||
 | 
					    </script> | 
				
			||||
 | 
					  </body> | 
				
			||||
 | 
					</html> | 
				
			||||
@ -0,0 +1,20 @@ | 
				
			|||||
 | 
					{ | 
				
			||||
 | 
					  "name": "pro-router", | 
				
			||||
 | 
					  "description": "Fully automated singleton router service for frontend. Use url as data store", | 
				
			||||
 | 
					  "version": "4.3.0", | 
				
			||||
 | 
					  "main": "router.js", | 
				
			||||
 | 
					  "repository": { | 
				
			||||
 | 
					    "type": "git", | 
				
			||||
 | 
					    "url": "git+https://github.com/madmaniak/pro.git" | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  "keywords": [ | 
				
			||||
 | 
					    "frontend", | 
				
			||||
 | 
					    "router" | 
				
			||||
 | 
					  ], | 
				
			||||
 | 
					  "author": "Marek Piasecki", | 
				
			||||
 | 
					  "license": "ISC", | 
				
			||||
 | 
					  "bugs": { | 
				
			||||
 | 
					    "url": "https://github.com/madmaniak/pro/issues" | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  "homepage": "https://github.com/madmaniak/pro/framework/components/router/npm_router_service" | 
				
			||||
 | 
					} | 
				
			||||
@ -0,0 +1 @@ | 
				
			|||||
 | 
					window.R={_l:location,_r:history.replaceState.bind(history),_p:history.pushState.bind(history),_d:decodeURIComponent,_e:encodeURIComponent,init:function(o){if(o==null){o={}}this.root||(this.root=o.root||"root");this.views||(this.views=o.views||window.Views||[this.root]);this.render||(this.render=o.render||window.render);this.h||(this.h=o.helpers||window._);window.onpopstate=this.url_changed.bind(this);this.read()},cache:{},getters:{},setters:{},param:function(k){var base;if(this.getters[k]){return(base=this.cache)[k]||(base[k]=this.getters[k](this._d(this.params[k]||"")))}else{return this._d(this.params[k]||"")}},write:function(){var i,j,k,l,v;for(i=j=0,l=arguments.length;j<l;i=++j){k=arguments[i];if(!(i%2)){v=arguments[i+1];this._write(k,v)}}this._r({},this._l.pathname,this.to_path(this.view,this.params));this.url_changed()},_write:function(k,v){var _v=this.setters[k]?this.setters[k](v):v;_v?this.params[k]=this._e(_v):delete this.params[k]},toggle:function(f,s){this.write(f,s!=null?s?1:void 0:!this.params[f]?1:void 0)},go:function(p){this._p({},null,p);this.url_changed()},read:function(){var ref;ref=this.split_path(this._l.hash),this.view=ref[0],this.params=ref[1];this._safe_params()},split_path:function(p){p=p.slice(2);if(!p.length){return [this.root,{}]}var list,params,view;list=this.h.compact(p.split("/"));view=this._existance(list.shift());params=this.h.fromPairs(this.h.chunk(list,2));return[view,params]},_existance:function(v){if(this.h.includes(this.views,v)){return v}else{return"not_found"}},_safe_params:function(){return this.safe_params=this.h.fromPairs(this.h.reject(this.h.toPairs(this.params),function(p){return/^_/.test(p[0])}))},to_path:function(v,p){var a;if(v==null){v=this.view}if(p==null){p=this.safe_params}a=this.h.flatten(this.h.reject(this.h.toPairs(p),function(p){return!p[1]}));return"#/"+v+"/"+a.join("/")},url_changed:function(){this.cache={};this.read();this.render()}}; | 
				
			||||
@ -0,0 +1 @@ | 
				
			|||||
 | 
					window.R={_l:location,_r:history.replaceState.bind(history),_p:history.pushState.bind(history),_d:decodeURIComponent,_e:encodeURIComponent,init:function(o){if(o==null){o={}}this.root||(this.root=o.root||"root");this.views||(this.views=o.views||window.Views||[this.root]);this.render||(this.render=o.render||window.render);this.h||(this.h=o.helpers||window._);window.onpopstate=this.url_changed.bind(this);this.read()},cache:{},getters:{},setters:{},param:function(k){var base;if(this.getters[k]){return(base=this.cache)[k]||(base[k]=this.getters[k](this._d(this.params[k]||"")))}else{return this._d(this.params[k]||"")}},write:function(){var i,j,k,l,v;for(i=j=0,l=arguments.length;j<l;i=++j){k=arguments[i];if(!(i%2)){v=arguments[i+1];this._write(k,v)}}this._r({},this._l.pathname,this.to_path(this.view,this.params));this.url_changed()},_write:function(k,v){var _v=this.setters[k]?this.setters[k](v):v;_v?this.params[k]=this._e(_v):delete this.params[k]},toggle:function(f,s){this.write(f,s!=null?s?1:void 0:!this.params[f]?1:void 0)},go:function(p){this._p({},null,p);this.url_changed()},read:function(){var ref;ref=this.split_path(this._l.pathname),this.view=ref[0],this.params=ref[1];this._safe_params()},split_path:function(p){if(p.length==1){return [this.root,{}]}var list,params,view;list=this.h.compact(p.split("/"));view=this._existance(list.shift());params=this.h.fromPairs(this.h.chunk(list,2));return[view,params]},_existance:function(v){if(this.h.includes(this.views,v)){return v}else{return"not_found"}},_safe_params:function(){return this.safe_params=this.h.fromPairs(this.h.reject(this.h.toPairs(this.params),function(p){return/^_/.test(p[0])}))},to_path:function(v,p){var a;if(v==null){v=this.view}if(p==null){p=this.safe_params}a=this.h.flatten(this.h.reject(this.h.toPairs(p),function(p){return!p[1]}));return"/"+v+"/"+a.join("/")},url_changed:function(){this.cache={};this.read();this.render()}}; | 
				
			||||
@ -0,0 +1,84 @@ | 
				
			|||||
 | 
					module.exports = window.R = | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # local cache | 
				
			||||
 | 
					  _location: location | 
				
			||||
 | 
					  _replaceState: history.replaceState.bind(history) | 
				
			||||
 | 
					  _pushState: history.pushState.bind(history) | 
				
			||||
 | 
					  _decodeURIComponent: decodeURIComponent | 
				
			||||
 | 
					  _encodeURIComponent: encodeURIComponent | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  init: (opts = {}) -> | 
				
			||||
 | 
					    @root   ||= opts.root    || 'root' | 
				
			||||
 | 
					    @views  ||= opts.views   || window.Views || [@root] | 
				
			||||
 | 
					    @render ||= opts.render  || window.render | 
				
			||||
 | 
					    @h      ||= opts.helpers || window._ | 
				
			||||
 | 
					    window.onpopstate = @url_changed.bind(@) | 
				
			||||
 | 
					    @read() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  cache: {} | 
				
			||||
 | 
					  getters: {} | 
				
			||||
 | 
					  setters: {} | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # <MAIN API> | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  param: (key) -> | 
				
			||||
 | 
					    if @getters[key] | 
				
			||||
 | 
					    then @cache[key] ||= @getters[key]( @_decodeURIComponent(@params[key] || '') ) | 
				
			||||
 | 
					    else @_decodeURIComponent(@params[key] || '') | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  write: -> | 
				
			||||
 | 
					    # accept arguments keeping key, value, key, value order | 
				
			||||
 | 
					    # serialize using setters | 
				
			||||
 | 
					    # if no argument given just refresh url and rerender | 
				
			||||
 | 
					    for k, i in arguments | 
				
			||||
 | 
					      unless i % 2 | 
				
			||||
 | 
					        v = arguments[i+1] | 
				
			||||
 | 
					        @_write(k,v) | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					    @_replaceState {}, | 
				
			||||
 | 
					      @_location.pathname, @to_path(@view, @params) | 
				
			||||
 | 
					    @url_changed() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _write: (k,v) -> | 
				
			||||
 | 
					    value = if @setters[k] then @setters[k](v) else v | 
				
			||||
 | 
					    if value | 
				
			||||
 | 
					    then @params[k] = @_encodeURIComponent(value) | 
				
			||||
 | 
					    else delete @params[k] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  toggle: (flag, state) -> | 
				
			||||
 | 
					    @write flag, if state? | 
				
			||||
 | 
					    then ( 1 if state ) | 
				
			||||
 | 
					    else ( 1 if !@params[flag] ) | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  go: (path) -> | 
				
			||||
 | 
					    @_pushState {}, null, path | 
				
			||||
 | 
					    @url_changed() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # </MAIN API> | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  read: -> | 
				
			||||
 | 
					    [@view, @params] = @split_path @_location.pathname | 
				
			||||
 | 
					    @_safe_params() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  split_path: (path) -> | 
				
			||||
 | 
					    return [ @root, {} ] if path.length == 1 | 
				
			||||
 | 
					    list = @h.compact path.split("/") | 
				
			||||
 | 
					    view = @_existance list.shift() | 
				
			||||
 | 
					    params = @h.fromPairs @h.chunk(list, 2) | 
				
			||||
 | 
					    [ view, params ] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _existance: (view) -> | 
				
			||||
 | 
					    if @h.includes(@views, view) then view else 'not_found' | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _safe_params: -> | 
				
			||||
 | 
					    @safe_params = @h.fromPairs @h.reject @h.toPairs(@params), (pair) -> | 
				
			||||
 | 
					      /^_/.test pair[0] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  to_path: (view = @view, params = @safe_params) -> | 
				
			||||
 | 
					    array = @h.flatten @h.toPairs(params) | 
				
			||||
 | 
					    '/' + view + '/' + array.join('/') | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  url_changed: -> | 
				
			||||
 | 
					    @cache = {} | 
				
			||||
 | 
					    @read() | 
				
			||||
 | 
					    @render() | 
				
			||||
@ -0,0 +1,96 @@ | 
				
			|||||
 | 
					module.exports = window.R = { | 
				
			||||
 | 
					  _location: location, | 
				
			||||
 | 
					  _replaceState: history.replaceState.bind(history), | 
				
			||||
 | 
					  _pushState: history.pushState.bind(history), | 
				
			||||
 | 
					  _decodeURIComponent: decodeURIComponent, | 
				
			||||
 | 
					  _encodeURIComponent: encodeURIComponent, | 
				
			||||
 | 
					  init: function(opts) { | 
				
			||||
 | 
					    if (opts == null) { | 
				
			||||
 | 
					      opts = {}; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    this.root || (this.root = opts.root || 'root'); | 
				
			||||
 | 
					    this.views || (this.views = opts.views || window.Views || [this.root]); | 
				
			||||
 | 
					    this.render || (this.render = opts.render || window.render); | 
				
			||||
 | 
					    this.h || (this.h = opts.helpers || window._); | 
				
			||||
 | 
					    window.onpopstate = this.url_changed.bind(this) | 
				
			||||
 | 
						this.read(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  cache: {}, | 
				
			||||
 | 
					  getters: {}, | 
				
			||||
 | 
					  setters: {}, | 
				
			||||
 | 
					  param: function(key) { | 
				
			||||
 | 
					    var base; | 
				
			||||
 | 
					    if (this.getters[key]) { | 
				
			||||
 | 
					      return (base = this.cache)[key] || (base[key] = this.getters[key](this._decodeURIComponent(this.params[key] || ''))); | 
				
			||||
 | 
					    } else { | 
				
			||||
 | 
					      return this._decodeURIComponent(this.params[key] || ''); | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  write: function() { | 
				
			||||
 | 
					    var i, j, k, len, v; | 
				
			||||
 | 
						for (i = j = 0, len = arguments.length; j < len; i = ++j) { | 
				
			||||
 | 
						  k = arguments[i]; | 
				
			||||
 | 
						  if (!(i % 2)) { | 
				
			||||
 | 
							v = arguments[i + 1]; | 
				
			||||
 | 
							this._write(k, v); | 
				
			||||
 | 
						  } | 
				
			||||
 | 
						} | 
				
			||||
 | 
					    this._replaceState({}, this._location.pathname, this.to_path(this.view, this.params)); | 
				
			||||
 | 
					    this.url_changed(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _write: function(k, v) { | 
				
			||||
 | 
						var value = this.setters[k] ? this.setters[k](v) : v; | 
				
			||||
 | 
						value ? this.params[k] = this._encodeURIComponent(value) : delete this.params[k]; | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  toggle: function(flag, state) { | 
				
			||||
 | 
					    this.write(flag, state != null ? (state ? 1 : void 0) : (!this.params[flag] ? 1 : void 0)); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  go: function(path) { | 
				
			||||
 | 
					    this._pushState({}, null, path); | 
				
			||||
 | 
					    this.url_changed(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  read: function() { | 
				
			||||
 | 
					    var ref; | 
				
			||||
 | 
					    ref = this.split_path(this._location.pathname), this.view = ref[0], this.params = ref[1]; | 
				
			||||
 | 
					    this._safe_params(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  split_path: function(path) { | 
				
			||||
 | 
					    if (path.length == 1) { | 
				
			||||
 | 
					      return [this.root, {}]; | 
				
			||||
 | 
						} | 
				
			||||
 | 
					    var list, params, view; | 
				
			||||
 | 
					    list = this.h.compact(path.split("/")); | 
				
			||||
 | 
					    view = this._existance(list.shift()); | 
				
			||||
 | 
					    params = this.h.fromPairs(this.h.chunk(list, 2)); | 
				
			||||
 | 
					    return [view, params]; | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _existance: function(view) { | 
				
			||||
 | 
					    if (this.h.includes(this.views, view)) { | 
				
			||||
 | 
					      return view; | 
				
			||||
 | 
					    } else { | 
				
			||||
 | 
					      return 'not_found'; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _safe_params: function() { | 
				
			||||
 | 
					    return this.safe_params = this.h.fromPairs(this.h.reject(this.h.toPairs(this.params), function(pair) { | 
				
			||||
 | 
					      return /^_/.test(pair[0]); | 
				
			||||
 | 
					    })); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  to_path: function(view, params) { | 
				
			||||
 | 
					    var array; | 
				
			||||
 | 
					    if (view == null) { | 
				
			||||
 | 
					      view = this.view; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    if (params == null) { | 
				
			||||
 | 
					      params = this.safe_params; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    array = this.h.flatten(this.h.toPairs(params)); | 
				
			||||
 | 
					    return '/' + view + '/' + array.join('/'); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  url_changed: function() { | 
				
			||||
 | 
					    this.cache = {}; | 
				
			||||
 | 
					    this.read(); | 
				
			||||
 | 
					    this.render(); | 
				
			||||
 | 
					  } | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					}; | 
				
			||||
@ -0,0 +1,85 @@ | 
				
			|||||
 | 
					module.exports = window.R = | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # local cache | 
				
			||||
 | 
					  _location: location | 
				
			||||
 | 
					  _replaceState: history.replaceState.bind(history) | 
				
			||||
 | 
					  _pushState: history.pushState.bind(history) | 
				
			||||
 | 
					  _decodeURIComponent: decodeURIComponent | 
				
			||||
 | 
					  _encodeURIComponent: encodeURIComponent | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  init: (opts = {}) -> | 
				
			||||
 | 
					    @root   ||= opts.root    || 'root' | 
				
			||||
 | 
					    @views  ||= opts.views   || window.Views || [@root] | 
				
			||||
 | 
					    @render ||= opts.render  || window.render | 
				
			||||
 | 
					    @h      ||= opts.helpers || window._ | 
				
			||||
 | 
					    window.onpopstate = @url_changed.bind(@) | 
				
			||||
 | 
					    @read() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  cache: {} | 
				
			||||
 | 
					  getters: {} | 
				
			||||
 | 
					  setters: {} | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # <MAIN API> | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  param: (key) -> | 
				
			||||
 | 
					    if @getters[key] | 
				
			||||
 | 
					    then @cache[key] ||= @getters[key]( @_decodeURIComponent(@params[key] || '') ) | 
				
			||||
 | 
					    else @_decodeURIComponent(@params[key] || '') | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  write: -> | 
				
			||||
 | 
					    # accept arguments keeping key, value, key, value order | 
				
			||||
 | 
					    # serialize using setters | 
				
			||||
 | 
					    # if no argument given just refresh url and rerender | 
				
			||||
 | 
					    for k, i in arguments | 
				
			||||
 | 
					      unless i % 2 | 
				
			||||
 | 
					        v = arguments[i+1] | 
				
			||||
 | 
					        @_write(k,v) | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					    @_replaceState {}, | 
				
			||||
 | 
					      @_location.pathname, @to_path(@view, @params) | 
				
			||||
 | 
					    @url_changed() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _write: (k,v) -> | 
				
			||||
 | 
					    value = if @setters[k] then @setters[k](v) else v | 
				
			||||
 | 
					    if value | 
				
			||||
 | 
					    then @params[k] = @_encodeURIComponent(value) | 
				
			||||
 | 
					    else delete @params[k] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  toggle: (flag, state) -> | 
				
			||||
 | 
					    @write flag, if state? | 
				
			||||
 | 
					    then ( 1 if state ) | 
				
			||||
 | 
					    else ( 1 if !@params[flag] ) | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  go: (path) -> | 
				
			||||
 | 
					    @_pushState {}, null, path | 
				
			||||
 | 
					    @url_changed() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  # </MAIN API> | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  read: -> | 
				
			||||
 | 
					    [@view, @params] = @split_path @_location.hash | 
				
			||||
 | 
					    @_safe_params() | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  split_path: (path) -> | 
				
			||||
 | 
					    path = path.slice(2) | 
				
			||||
 | 
					    return [ @root, {} ] unless path.length | 
				
			||||
 | 
					    list = @h.compact path.split("/") | 
				
			||||
 | 
					    view = @_existance list.shift() | 
				
			||||
 | 
					    params = @h.fromPairs @h.chunk(list, 2) | 
				
			||||
 | 
					    [ view, params ] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _existance: (view) -> | 
				
			||||
 | 
					    if @h.includes(@views, view) then view else 'not_found' | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  _safe_params: -> | 
				
			||||
 | 
					    @safe_params = @h.fromPairs @h.reject @h.toPairs(@params), (pair) -> | 
				
			||||
 | 
					      /^_/.test pair[0] | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  to_path: (view = @view, params = @safe_params) -> | 
				
			||||
 | 
					    array = @h.flatten @h.toPairs(params) | 
				
			||||
 | 
					    '#/' + view + '/' + array.join('/') | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					  url_changed: -> | 
				
			||||
 | 
					    @cache = {} | 
				
			||||
 | 
					    @read() | 
				
			||||
 | 
					    @render() | 
				
			||||
@ -0,0 +1,97 @@ | 
				
			|||||
 | 
					module.exports = window.R = { | 
				
			||||
 | 
					  _location: location, | 
				
			||||
 | 
					  _replaceState: history.replaceState.bind(history), | 
				
			||||
 | 
					  _pushState: history.pushState.bind(history), | 
				
			||||
 | 
					  _decodeURIComponent: decodeURIComponent, | 
				
			||||
 | 
					  _encodeURIComponent: encodeURIComponent, | 
				
			||||
 | 
					  init: function(opts) { | 
				
			||||
 | 
					    if (opts == null) { | 
				
			||||
 | 
					      opts = {}; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    this.root || (this.root = opts.root || 'root'); | 
				
			||||
 | 
					    this.views || (this.views = opts.views || window.Views || [this.root]); | 
				
			||||
 | 
					    this.render || (this.render = opts.render || window.render); | 
				
			||||
 | 
					    this.h || (this.h = opts.helpers || window._); | 
				
			||||
 | 
					    window.onpopstate = this.url_changed.bind(this) | 
				
			||||
 | 
						this.read(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  cache: {}, | 
				
			||||
 | 
					  getters: {}, | 
				
			||||
 | 
					  setters: {}, | 
				
			||||
 | 
					  param: function(key) { | 
				
			||||
 | 
					    var base; | 
				
			||||
 | 
					    if (this.getters[key]) { | 
				
			||||
 | 
					      return (base = this.cache)[key] || (base[key] = this.getters[key](this._decodeURIComponent(this.params[key] || ''))); | 
				
			||||
 | 
					    } else { | 
				
			||||
 | 
					      return this._decodeURIComponent(this.params[key] || ''); | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  write: function() { | 
				
			||||
 | 
					    var i, j, k, len, v; | 
				
			||||
 | 
						for (i = j = 0, len = arguments.length; j < len; i = ++j) { | 
				
			||||
 | 
						  k = arguments[i]; | 
				
			||||
 | 
						  if (!(i % 2)) { | 
				
			||||
 | 
							v = arguments[i + 1]; | 
				
			||||
 | 
							this._write(k, v); | 
				
			||||
 | 
						  } | 
				
			||||
 | 
						} | 
				
			||||
 | 
					    this._replaceState({}, this._location.pathname, this.to_path(this.view, this.params)); | 
				
			||||
 | 
					    this.url_changed(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _write: function(k, v) { | 
				
			||||
 | 
						var value = this.setters[k] ? this.setters[k](v) : v; | 
				
			||||
 | 
						value ? this.params[k] = this._encodeURIComponent(value) : delete this.params[k]; | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  toggle: function(flag, state) { | 
				
			||||
 | 
					    this.write(flag, state != null ? (state ? 1 : void 0) : (!this.params[flag] ? 1 : void 0)); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  go: function(path) { | 
				
			||||
 | 
					    this._pushState({}, null, path); | 
				
			||||
 | 
					    this.url_changed(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  read: function() { | 
				
			||||
 | 
					    var ref; | 
				
			||||
 | 
					    ref = this.split_path(this._location.hash), this.view = ref[0], this.params = ref[1]; | 
				
			||||
 | 
					    this._safe_params(); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  split_path: function(path) { | 
				
			||||
 | 
						path = path.slice(2); | 
				
			||||
 | 
					    if (!path.length) { | 
				
			||||
 | 
					      return [this.root, {}]; | 
				
			||||
 | 
						} | 
				
			||||
 | 
					    var list, params, view; | 
				
			||||
 | 
					    list = this.h.compact(path.split("/")); | 
				
			||||
 | 
					    view = this._existance(list.shift()); | 
				
			||||
 | 
					    params = this.h.fromPairs(this.h.chunk(list, 2)); | 
				
			||||
 | 
					    return [view, params]; | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _existance: function(view) { | 
				
			||||
 | 
					    if (this.h.includes(this.views, view)) { | 
				
			||||
 | 
					      return view; | 
				
			||||
 | 
					    } else { | 
				
			||||
 | 
					      return 'not_found'; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  _safe_params: function() { | 
				
			||||
 | 
					    return this.safe_params = this.h.fromPairs(this.h.reject(this.h.toPairs(this.params), function(pair) { | 
				
			||||
 | 
					      return /^_/.test(pair[0]); | 
				
			||||
 | 
					    })); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  to_path: function(view, params) { | 
				
			||||
 | 
					    var array; | 
				
			||||
 | 
					    if (view == null) { | 
				
			||||
 | 
					      view = this.view; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    if (params == null) { | 
				
			||||
 | 
					      params = this.safe_params; | 
				
			||||
 | 
					    } | 
				
			||||
 | 
					    array = this.h.flatten(this.h.toPairs(params)); | 
				
			||||
 | 
					    return '#/' + view + '/' + array.join('/'); | 
				
			||||
 | 
					  }, | 
				
			||||
 | 
					  url_changed: function() { | 
				
			||||
 | 
					    this.cache = {}; | 
				
			||||
 | 
					    this.read(); | 
				
			||||
 | 
					    this.render(); | 
				
			||||
 | 
					  } | 
				
			||||
 | 
					
 | 
				
			||||
 | 
					}; | 
				
			||||
					Loading…
					
					
				
		Reference in new issue