UNPKG

data-tier

Version:

Tiny and fast two way (MV-VM) data binding framework for browser environments.

1 lines 2.95 kB
import{Observable as i}from"./object-observer.min.js";import{TARGET_TYPES as l,getPath as n,callViewMethod as d,getRandomKey as s}from"./utils.min.js";const t=/^[a-zA-Z0-9]+$/,o=["scope"];class r{constructor(e,t,i){this.key=e,this.ties=i,this.model=t}set model(e){var[e,t]=h(e);this._model=e,t&&i.observe(this._model,e=>this.processDataChanges(e))}get model(){return this._model}processDataChanges(u){var v=this.ties._dti.views.obtainTieViews(this.key),w=v._pathsCache,b=w.length;if(b){let i,s,o,r,a="",h,l,n,d,p,f,c,y,g,m;for(let e=0,t=u.length;e<t;e++)if(i=u[e],r=(o=i.path).length,!o.some(e=>"symbol"==typeof e))for(y=!1,s=i.object,!Array.isArray(s)||"insert"!==i.type&&"delete"!==i.type||isNaN(o[o.length-1])?1===r?a=o[0]:r&&(a=2===r?o[0]+"."+o[1]:o.join(".")):(a=o.slice(0,-1).join("."),y=!0),p=a.length,h=b;h--;)if(l=w[h],c=p>l.length?(f=l,a):(f=a,l),g=f===c&&!y,0===c.indexOf(f))for(n=v[l],d=n.length;d--;)m=n[d],this.updateView(m,l,g,i)}}updateView(t,i,s,o){var e=t[this.ties._dti.paramsKey];let r=e.length;for(;r--;){var a=e[r];if(a.targetType===l.METHOD){if(a.fParams.some(e=>e.tieKey===this.key&&e.rawPath===i)){let s=!1;const h=[];a.fParams.forEach(e=>{let t;var i=this.ties.get(e.tieKey);i&&(t=n(i,e.path),s=!0),h.push(t)}),s&&(h.push([o]),d(t,a.targetKey,h))}}else if(a.tieKey===this.key&&a.rawPath===i){let e;e=void 0!==o.value&&s?o.value:n(this._model,a.path),this.ties._dti.views.updateViewByModel(t,a,e,o.oldValue)}}}}class a{constructor(e){this._dti=e,this._ties={}}get(e){e="string"==typeof e?e:e&&e.getAttribute?e.getAttribute("data-tie-scope"):null,e=this._ties[e];return e?e.model:void 0}create(e,t){let i;if("string"==typeof e?i=e:e&&e.nodeType===Node.ELEMENT_NODE&&((i=e.getAttribute("data-tie-scope"))?console.log("inspect this"):(i=s(16),e.setAttribute("data-tie-scope",i))),a.validateTieKey(i),this._ties[i])throw new Error(`tie '${i}' already exists`);e.nodeType&&this._dti.views.addScope(e);e=new r(i,t,this);return(this._ties[i]=e).processDataChanges([{path:[]}]),e.model}update(e,t){if(void 0===t)throw new Error(`illegal model '${t}'`);var i="string"==typeof e?e:e&&e.getAttribute?e.getAttribute("data-tie-scope"):null,i=this._ties[i];return i?(i.model!==t&&(i.model=t,i.processDataChanges([{path:[]}])),i.model):this.create(e,t)}remove(t){let e=t;if("object"==typeof t)e=t.nodeType===Node.ELEMENT_NODE?t.getAttribute("data-tie-scope"):Object.keys(this._ties).find(e=>this._ties[e].model===t);else if("string"!=typeof t)throw new Error("invalid tieToRemove parameter "+t);this._ties[e]&&(delete this._ties[e],this._dti.views.deleteTieViews(e))}static validateTieKey(e){if(!e||"string"!=typeof e)throw new Error(`invalid key '${e}'`);if(!t.test(e))throw new Error(`tie key MUST match ${t}; '${e}' doesn't`);if(0<=o.indexOf(e))throw new Error("tie key MUST NOT be one of those: "+o.join(", "))}}function h(e={}){return i.isObservable(e)?[e,!0]:e&&"object"==typeof e?[i.from(e),!0]:[e,!1]}export{i as Observable,a as Ties};