react-binding
Advanced tools
| import { IPathObjectBinder, IPathObjectBinding, IValueConverter, ArrayObjectBinding } from './DataBinding'; | ||
| export declare class BinderCore { | ||
| static bindTo(type: { | ||
| new (data): IPathObjectBinder; | ||
| }, parent: any, path?: string, converter?: any, converterParams?: any): IPathObjectBinding; | ||
| static bindArrayTo(type: { | ||
| new (data): IPathObjectBinder; | ||
| }, parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } | ||
| /** | ||
| * React [LinkedStateMixin](http://facebook.github.io/react/docs/two-way-binding-helpers.html) is an easy way to express two-way data binding in React. | ||
| * | ||
| * React-binding comes with utility [Binder](https://github.com/rsamec/react-binding) for two-way binding that supports binding to | ||
| * | ||
| * + object properties with path expression (dot notation) | ||
| * + this.bindToState("data","Employee.FirstName"); | ||
| * + this.bindToState("data","Employee.Contact.Email"); | ||
| * + complex objects (json) with nested properties | ||
| * + this.bindTo(employee,"FirstName"); | ||
| * + this.bindTo(employee,"Contact.Email"); | ||
| * + collection-based structures - arrays and lists | ||
| * + model={this.bindTo(employee,"FirstName")} | ||
| * + this.props.model.items.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| * + this.props.model.add() | ||
| * + this.props.model.remove(item) | ||
| * + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| * + valueLink={this.bindTo(employee,"FirstName")} | ||
| * + enables binding with value converters | ||
| * + supports both directions - format (toView) and parse (fromView) | ||
| * + support for converter parameter - valueLink={this.bindToState("data", "Duration.From",converter, "DD.MM.YYYY")} | ||
| * + converter parameter can be data-bound - valueLink={this.bindToState("data", "Duration.From",converter, this.state.format)} | ||
| * + usable with any css frameworks - | ||
| * + react-bootstrap | ||
| * + material-ui | ||
| * | ||
| */ | ||
| export default class Binder { | ||
| static createStateKeySetter(component: any, key: any): (value?: any) => void; | ||
| /** | ||
| * It enables to bind to object property with path expression | ||
| * + using [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + without [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <TextBoxInput model={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * ``` js | ||
| * var TextBoxInput = React.createClass({ | ||
| * render: function() { | ||
| * var valueModel = this.props.model; | ||
| * var handleChange = function(e){ | ||
| * valueModel.value = e.target.value; | ||
| * } | ||
| * return ( | ||
| * <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| * )} | ||
| * }); | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) | ||
| * @param path - expression to bind to property | ||
| * @param converter {DataBinding.IValueConverter} - value converter | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathObjectBinding} | ||
| */ | ||
| static bindToState(component: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): IPathObjectBinding; | ||
| /** | ||
| * It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| * | ||
| * + binding to state at root level | ||
| * | ||
| * ``` js | ||
| * <PersonComponent personModel={this.bindToState("data","Employee")} /> | ||
| * <PersonComponent personModel={this.bindToState("data","Deputy")} /> | ||
| * ``` | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + reuse bindings in component | ||
| * | ||
| * ``` js | ||
| * var PersonComponent = React.createClass({ | ||
| * mixins:[BindToMixin], | ||
| * render: function() { | ||
| * return ( | ||
| * <div> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"FirstName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"LastName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * </div> | ||
| * ); | ||
| * } | ||
| * }); | ||
| * | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property | ||
| * @param converter - value converter {DataBinding.IValueConverter} | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): IPathObjectBinding; | ||
| /** | ||
| * It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| * | ||
| * + binding to array | ||
| * | ||
| * ``` js | ||
| * <HobbyList model={this.bindArrayToState("data","Hobbies")} /> | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) - it must be array | ||
| * @param path - expression to array to bind to property | ||
| * @returns {DataBinding.ArrayObjectBinding} | ||
| */ | ||
| static bindArrayToState(component: any, key: string, path?: string): ArrayObjectBinding; | ||
| /** | ||
| * It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindArrayTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property - relative path from parent | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| export interface BinderStatic { | ||
| bindToState?(data: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding; | ||
| bindTo(parent: any, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding; | ||
| bindArrayToState?(data: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding; | ||
| bindArrayTo(parent: any, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding; | ||
| } | ||
| export interface Binding { | ||
| path?: string; | ||
| parent: Binding; | ||
| root: Binding; | ||
| } | ||
| export interface ObjectBinding extends Binding { | ||
| value: any; | ||
| } | ||
| export interface ArrayBinding extends Binding { | ||
| items: Array<ObjectBinding>; | ||
| add(defautItem?: any): any; | ||
| remove(itemToRemove: any): any; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any; | ||
| move(x: number, y: number): any; | ||
| } | ||
| /**x` | ||
| * Two-way data binding for React. | ||
| */ | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export interface IPathObjectBinder { | ||
| /** | ||
| It gets value at the passed path expression. | ||
| */ | ||
| getValue(path?: string): any; | ||
| /** | ||
| It sets the passed value at the passed path. | ||
| */ | ||
| setValue(path: string, value: any): any; | ||
| subscribe(fce: any): void; | ||
| } | ||
| /** | ||
| It represents change notification function. It is called whenever there is a change. | ||
| */ | ||
| export interface INotifyChange { | ||
| (any?: any): void; | ||
| } | ||
| /** | ||
| It represents change notifikcation function with changed value. It supports valueLink interface | ||
| */ | ||
| export interface IRequestChange { | ||
| (any: any): void; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export interface IPathObjectBinding extends ObjectBinding { | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| notifyChange?: INotifyChange; | ||
| requestChange?: IRequestChange; | ||
| valueConverter?: IValueConverter; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export declare class PathObjectBinding implements IPathObjectBinding { | ||
| sourceObject: any; | ||
| provider: (data) => IPathObjectBinder; | ||
| path: string; | ||
| notifyChange: INotifyChange; | ||
| valueConverter: IValueConverter; | ||
| parentNode: Binding; | ||
| source: IPathObjectBinder; | ||
| constructor(sourceObject: any, provider: (data) => IPathObjectBinder, path?: string, notifyChange?: INotifyChange, valueConverter?: IValueConverter, parentNode?: Binding); | ||
| requestChange: IRequestChange; | ||
| root: Binding; | ||
| parent: Binding; | ||
| value: any; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export declare class ArrayObjectBinding implements ArrayBinding { | ||
| sourceObject: any; | ||
| provider: (data) => IPathObjectBinder; | ||
| path: string; | ||
| notifyChange: INotifyChange; | ||
| valueConverter: IValueConverter; | ||
| source: IPathObjectBinder; | ||
| constructor(sourceObject: any, provider: (data) => IPathObjectBinder, path?: string, notifyChange?: INotifyChange, valueConverter?: IValueConverter); | ||
| parent: ArrayBinding; | ||
| root: ArrayBinding; | ||
| items: Array<IPathObjectBinding>; | ||
| add(defaultItem?: any): void; | ||
| remove(itemToRemove: any): void; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any; | ||
| move(x: number, y: number): void; | ||
| } | ||
| /** | ||
| It represents binding to array using relative path to parent object. | ||
| */ | ||
| export declare class ArrayParentBinding implements ArrayBinding { | ||
| private parentBinding; | ||
| relativePath: string; | ||
| valueConverter: IValueConverter; | ||
| constructor(parentBinding: IPathObjectBinding, relativePath?: string, valueConverter?: IValueConverter); | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| root: Binding; | ||
| parent: Binding; | ||
| notifyChange: INotifyChange; | ||
| path: string; | ||
| private getItems(); | ||
| items: Array<IPathObjectBinding>; | ||
| add(defaultItem?: any): void; | ||
| remove(itemToRemove: any): void; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any[]; | ||
| move(x: any, y: any): void; | ||
| } | ||
| /** | ||
| It represents binding to relative path for parent object. | ||
| */ | ||
| export declare class PathParentBinding implements IPathObjectBinding { | ||
| private parentBinding; | ||
| relativePath: any; | ||
| valueConverter: IValueConverter; | ||
| constructor(parentBinding: IPathObjectBinding, relativePath: any, valueConverter?: IValueConverter); | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| root: Binding; | ||
| parent: Binding; | ||
| notifyChange: INotifyChange; | ||
| requestChange: IRequestChange; | ||
| path: string; | ||
| value: any; | ||
| } | ||
| /** | ||
| * Provides a way to apply custom logic to a binding. | ||
| * It enables to make bi-directional convertions between source (data) and target (view) binding. | ||
| * | ||
| * + apply various formats to values | ||
| * + parse values from user input | ||
| */ | ||
| export interface IValueConverter { | ||
| /** | ||
| * Convert value into another value before return binding getter. Typically from model(data) to view. | ||
| * @param value - source binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| format?(value: any, parameters?: any): any; | ||
| /** | ||
| * Convert value into another value before call binding setter. Typically from view to model(data). | ||
| * @param value - target binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| parse?(value: any, parameters?: any): any; | ||
| } | ||
| export declare class CurryConverter implements IValueConverter { | ||
| private formatFce; | ||
| private parseFce; | ||
| constructor(converter: IValueConverter, args: any); | ||
| private curryParameters(fn, args); | ||
| format(value: any): any; | ||
| parse(value: any): any; | ||
| } |
| export default class Binder { | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class FreezerPathObjectBinder implements IPathObjectBinder { | ||
| private source; | ||
| private freezer; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path?: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
| export default class Binder { | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class MobxPathObjectBinder implements IPathObjectBinder { | ||
| private mobxSource; | ||
| private current; | ||
| private previous; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private setValueAsObservable(parent, property, value?); | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class PathObjectBinder implements IPathObjectBinder { | ||
| private source; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
+167
| var PlainObjectProvider_1 = require('./PlainObjectProvider'); | ||
| var DataBinding_1 = require('./DataBinding'); | ||
| var BinderCore = (function () { | ||
| function BinderCore() { | ||
| } | ||
| BinderCore.bindTo = function (type, parent, path, converter, converterParams) { | ||
| var converter = converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof DataBinding_1.PathObjectBinding || parent instanceof DataBinding_1.PathParentBinding) ? new DataBinding_1.PathParentBinding(parent, path, converter) : new DataBinding_1.PathObjectBinding(parent, function (data) { return new type(data); }, path, converter); | ||
| }; | ||
| BinderCore.bindArrayTo = function (type, parent, path, converter, converterParams) { | ||
| var converter = converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof DataBinding_1.PathObjectBinding || parent instanceof DataBinding_1.PathParentBinding) ? new DataBinding_1.ArrayParentBinding(parent, path, converter) : new DataBinding_1.ArrayObjectBinding(parent, function (data) { return new type(data); }, path, converter); | ||
| }; | ||
| return BinderCore; | ||
| })(); | ||
| exports.BinderCore = BinderCore; | ||
| /** | ||
| * React [LinkedStateMixin](http://facebook.github.io/react/docs/two-way-binding-helpers.html) is an easy way to express two-way data binding in React. | ||
| * | ||
| * React-binding comes with utility [Binder](https://github.com/rsamec/react-binding) for two-way binding that supports binding to | ||
| * | ||
| * + object properties with path expression (dot notation) | ||
| * + this.bindToState("data","Employee.FirstName"); | ||
| * + this.bindToState("data","Employee.Contact.Email"); | ||
| * + complex objects (json) with nested properties | ||
| * + this.bindTo(employee,"FirstName"); | ||
| * + this.bindTo(employee,"Contact.Email"); | ||
| * + collection-based structures - arrays and lists | ||
| * + model={this.bindTo(employee,"FirstName")} | ||
| * + this.props.model.items.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| * + this.props.model.add() | ||
| * + this.props.model.remove(item) | ||
| * + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| * + valueLink={this.bindTo(employee,"FirstName")} | ||
| * + enables binding with value converters | ||
| * + supports both directions - format (toView) and parse (fromView) | ||
| * + support for converter parameter - valueLink={this.bindToState("data", "Duration.From",converter, "DD.MM.YYYY")} | ||
| * + converter parameter can be data-bound - valueLink={this.bindToState("data", "Duration.From",converter, this.state.format)} | ||
| * + usable with any css frameworks - | ||
| * + react-bootstrap | ||
| * + material-ui | ||
| * | ||
| */ | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.createStateKeySetter = function (component, key) { | ||
| var partialState = {}; | ||
| return function (value) { | ||
| partialState[key] = (value !== undefined) ? value : component.state[key]; | ||
| component.setState(partialState); | ||
| }; | ||
| }; | ||
| /** | ||
| * It enables to bind to object property with path expression | ||
| * + using [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + without [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <TextBoxInput model={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * ``` js | ||
| * var TextBoxInput = React.createClass({ | ||
| * render: function() { | ||
| * var valueModel = this.props.model; | ||
| * var handleChange = function(e){ | ||
| * valueModel.value = e.target.value; | ||
| * } | ||
| * return ( | ||
| * <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| * )} | ||
| * }); | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) | ||
| * @param path - expression to bind to property | ||
| * @param converter {DataBinding.IValueConverter} - value converter | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathObjectBinding} | ||
| */ | ||
| Binder.bindToState = function (component, key, path, converter, converterParams) { | ||
| return new DataBinding_1.PathObjectBinding(component["state"][key], function (data) { return new PlainObjectProvider_1.default(data); }, path, Binder.createStateKeySetter(component, key), converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter); | ||
| }; | ||
| /** | ||
| * It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| * | ||
| * + binding to state at root level | ||
| * | ||
| * ``` js | ||
| * <PersonComponent personModel={this.bindToState("data","Employee")} /> | ||
| * <PersonComponent personModel={this.bindToState("data","Deputy")} /> | ||
| * ``` | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + reuse bindings in component | ||
| * | ||
| * ``` js | ||
| * var PersonComponent = React.createClass({ | ||
| * mixins:[BindToMixin], | ||
| * render: function() { | ||
| * return ( | ||
| * <div> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"FirstName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"LastName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * </div> | ||
| * ); | ||
| * } | ||
| * }); | ||
| * | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property | ||
| * @param converter - value converter {DataBinding.IValueConverter} | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return BinderCore.bindTo(PlainObjectProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| /** | ||
| * It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| * | ||
| * + binding to array | ||
| * | ||
| * ``` js | ||
| * <HobbyList model={this.bindArrayToState("data","Hobbies")} /> | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) - it must be array | ||
| * @param path - expression to array to bind to property | ||
| * @returns {DataBinding.ArrayObjectBinding} | ||
| */ | ||
| Binder.bindArrayToState = function (component, key, path) { | ||
| return new DataBinding_1.ArrayObjectBinding(component["state"][key], function (data) { return new PlainObjectProvider_1.default(data); }, path, Binder.createStateKeySetter(component, key)); | ||
| }; | ||
| /** | ||
| * It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindArrayTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property - relative path from parent | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return BinderCore.bindArrayTo(PlainObjectProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; | ||
| //export default Binder; |
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| var PathObjectBinding = (function () { | ||
| function PathObjectBinding(sourceObject, provider, path, notifyChange, valueConverter, parentNode) { | ||
| this.sourceObject = sourceObject; | ||
| this.provider = provider; | ||
| this.path = path; | ||
| this.notifyChange = notifyChange; | ||
| this.valueConverter = valueConverter; | ||
| this.parentNode = parentNode; | ||
| this.source = provider(sourceObject); | ||
| } | ||
| Object.defineProperty(PathObjectBinding.prototype, "requestChange", { | ||
| get: function () { | ||
| var _this = this; | ||
| return function (value) { _this.value = value; }; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentNode !== undefined ? this.parentNode.root : this; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentNode !== undefined ? this.parentNode : undefined; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "value", { | ||
| get: function () { | ||
| var value = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }, | ||
| set: function (value) { | ||
| var previousValue = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| //check if the value is really changed - strict equality | ||
| if (previousValue !== undefined && previousValue === convertedValueToBeSet) | ||
| return; | ||
| if (this.path === undefined) { | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(convertedValueToBeSet); | ||
| } | ||
| else { | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| } | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| return PathObjectBinding; | ||
| })(); | ||
| exports.PathObjectBinding = PathObjectBinding; | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| var ArrayObjectBinding = (function () { | ||
| function ArrayObjectBinding(sourceObject, provider, path, notifyChange, valueConverter) { | ||
| this.sourceObject = sourceObject; | ||
| this.provider = provider; | ||
| this.path = path; | ||
| this.notifyChange = notifyChange; | ||
| this.valueConverter = valueConverter; | ||
| this.source = provider(sourceObject); | ||
| } | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "parent", { | ||
| get: function () { | ||
| return undefined; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "root", { | ||
| get: function () { | ||
| return this; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "items", { | ||
| get: function () { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return []; | ||
| return items.map(function (item) { | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange, undefined, this); | ||
| }, this); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayObjectBinding.prototype.add = function (defaultItem) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) | ||
| defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.remove = function (itemToRemove) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) | ||
| return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.splice = function (start, deleteCount, elementsToAdd) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.move = function (x, y) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| //@TODO: use more effective way to clone array | ||
| var itemsCloned = JSON.parse(JSON.stringify(items)); | ||
| itemsCloned.splice(y, 0, itemsCloned.splice(x, 1)[0]); | ||
| this.source.setValue(this.path, itemsCloned); | ||
| }; | ||
| return ArrayObjectBinding; | ||
| })(); | ||
| exports.ArrayObjectBinding = ArrayObjectBinding; | ||
| /** | ||
| It represents binding to array using relative path to parent object. | ||
| */ | ||
| var ArrayParentBinding = (function () { | ||
| function ArrayParentBinding(parentBinding, relativePath, valueConverter) { | ||
| this.parentBinding = parentBinding; | ||
| this.relativePath = relativePath; | ||
| this.valueConverter = valueConverter; | ||
| } | ||
| Object.defineProperty(ArrayParentBinding.prototype, "source", { | ||
| //wrapped properties - delegate call to parent | ||
| get: function () { | ||
| return this.parentBinding.source; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "provider", { | ||
| get: function () { | ||
| return this.parentBinding.provider; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentBinding.root; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentBinding; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "notifyChange", { | ||
| get: function () { | ||
| return this.parentBinding.notifyChange; | ||
| }, | ||
| set: function (value) { | ||
| this.parentBinding.notifyChange = value; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "path", { | ||
| //concatenate path | ||
| get: function () { | ||
| if (this.parentBinding.path === undefined) | ||
| return this.relativePath; | ||
| if (this.relativePath === undefined) | ||
| return this.parentBinding.path; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayParentBinding.prototype.getItems = function () { | ||
| if (this.source === undefined) | ||
| return; | ||
| var value = this.source.getValue(this.path); | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }; | ||
| Object.defineProperty(ArrayParentBinding.prototype, "items", { | ||
| get: function () { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return []; | ||
| return items.map(function (item) { | ||
| //item._parentBinding = this; | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange, undefined, this); | ||
| }, this); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayParentBinding.prototype.add = function (defaultItem) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) | ||
| defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.remove = function (itemToRemove) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) | ||
| return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.splice = function (start, deleteCount, elementsToAdd) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.move = function (x, y) { | ||
| this.splice(y, 0, this.splice(x, 1)[0]); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| return ArrayParentBinding; | ||
| })(); | ||
| exports.ArrayParentBinding = ArrayParentBinding; | ||
| /** | ||
| It represents binding to relative path for parent object. | ||
| */ | ||
| var PathParentBinding = (function () { | ||
| //converter:any; | ||
| function PathParentBinding(parentBinding, relativePath, valueConverter) { | ||
| this.parentBinding = parentBinding; | ||
| this.relativePath = relativePath; | ||
| this.valueConverter = valueConverter; | ||
| //this.converter.format = Utils.partial(valueConverter,.partial() | ||
| } | ||
| Object.defineProperty(PathParentBinding.prototype, "source", { | ||
| //wrapped properties - delegate call to parent | ||
| get: function () { | ||
| return this.parentBinding.source; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "provider", { | ||
| get: function () { | ||
| return this.parentBinding.provider; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentBinding.root; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentBinding; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "notifyChange", { | ||
| get: function () { | ||
| return this.parentBinding.notifyChange; | ||
| }, | ||
| set: function (value) { | ||
| this.parentBinding.notifyChange = value; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "requestChange", { | ||
| get: function () { | ||
| var _this = this; | ||
| return function (value) { | ||
| _this.value = value; | ||
| }; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "path", { | ||
| //concatenate path | ||
| get: function () { | ||
| if (this.parentBinding.path === undefined) | ||
| return this.relativePath; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "value", { | ||
| get: function () { | ||
| var value = this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }, | ||
| set: function (value) { | ||
| //check if the value is really changed - strict equality | ||
| var previousValue = this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| if (previousValue === convertedValueToBeSet) | ||
| return; | ||
| //set value - optional call converter | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| return PathParentBinding; | ||
| })(); | ||
| exports.PathParentBinding = PathParentBinding; | ||
| var CurryConverter = (function () { | ||
| function CurryConverter(converter, args) { | ||
| this.formatFce = this.curryParameters(converter.format, [args]); | ||
| this.parseFce = this.curryParameters(converter.parse, [args]); | ||
| } | ||
| CurryConverter.prototype.curryParameters = function (fn, args) { | ||
| return function () { | ||
| return fn.apply(this, Array.prototype.slice.call(arguments).concat(args)); | ||
| }; | ||
| }; | ||
| CurryConverter.prototype.format = function (value) { | ||
| return this.formatFce(value); | ||
| }; | ||
| CurryConverter.prototype.parse = function (value) { | ||
| return this.parseFce(value); | ||
| }; | ||
| return CurryConverter; | ||
| })(); | ||
| exports.CurryConverter = CurryConverter; |
| var FreezerProvider_1 = require('./FreezerProvider'); | ||
| var Binder_1 = require('./Binder'); | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindTo(FreezerProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindArrayTo(FreezerProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; |
| var Freezer = require('freezer-js'); | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var FreezerPathObjectBinder = (function () { | ||
| function FreezerPathObjectBinder(source) { | ||
| this.source = source; | ||
| this.freezer = new Freezer(source); | ||
| } | ||
| FreezerPathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| this.freezer.on('update', function (state, prevState) { | ||
| if (updateFce !== undefined) | ||
| updateFce(state, prevState); | ||
| }); | ||
| }; | ||
| FreezerPathObjectBinder.prototype.getValue = function (path) { | ||
| if (path === undefined) | ||
| return this.freezer.get(); | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| }; | ||
| FreezerPathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| parent.set(property, value); | ||
| }; | ||
| FreezerPathObjectBinder.prototype.getParent = function (path) { | ||
| var state = this.freezer.get(); | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(state, path.substring(0, last)) : state; | ||
| }; | ||
| FreezerPathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| FreezerPathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj.set(parts[0], {}); | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return FreezerPathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = FreezerPathObjectBinder; |
| var MobxProvider_1 = require('./MobxProvider'); | ||
| var Binder_1 = require('./Binder'); | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindTo(MobxProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindArrayTo(MobxProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; |
| var mobx_1 = require('mobx'); | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var MobxPathObjectBinder = (function () { | ||
| function MobxPathObjectBinder(source) { | ||
| var _this = this; | ||
| this.mobxSource = mobx_1.observable(source); | ||
| this.current = mobx_1.computed(function () { return JSON.stringify(_this.mobxSource); }); | ||
| //console.log('init'); | ||
| // autorun(() => { | ||
| // console.log(this.json.get());//'safda'); | ||
| // //if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // }); | ||
| } | ||
| MobxPathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| var _this = this; | ||
| var previousState; | ||
| if (updateFce !== undefined) | ||
| mobx_1.autorun(function () { | ||
| var current = _this.current.get(); | ||
| updateFce(current, _this.previous); | ||
| _this.previous = current; | ||
| }); | ||
| //if (updateFce!==undefined) autorun(updateFce); | ||
| }; | ||
| MobxPathObjectBinder.prototype.getValue = function (path) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| if (path === undefined) | ||
| return parent; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| var value = parent[property]; | ||
| if (value === undefined && !parent.hasOwnProperty(property)) { | ||
| this.setValueAsObservable(parent, property); | ||
| } | ||
| return parent[property]; | ||
| }; | ||
| MobxPathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| //parent[property] = observable(value); | ||
| if (mobx_1.isObservable(parent, property)) { | ||
| parent[property] = value; | ||
| return; | ||
| } | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| mobx_1.extendObservable(parent, newProps); | ||
| //console.log(parent[property]); | ||
| }; | ||
| MobxPathObjectBinder.prototype.setValueAsObservable = function (parent, property, value) { | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| mobx_1.extendObservable(parent, newProps); | ||
| }; | ||
| MobxPathObjectBinder.prototype.getParent = function (path) { | ||
| if (path === undefined) | ||
| return this.mobxSource; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.mobxSource, path.substring(0, last)) : this.mobxSource; | ||
| }; | ||
| MobxPathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| MobxPathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return MobxPathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = MobxPathObjectBinder; |
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var PathObjectBinder = (function () { | ||
| function PathObjectBinder(source) { | ||
| this.source = source; | ||
| } | ||
| PathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| // this.freezer.on('update',function(state,prevState){ | ||
| // if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // ); | ||
| }; | ||
| PathObjectBinder.prototype.getValue = function (path) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| if (path === undefined) | ||
| return parent; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| }; | ||
| PathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| parent[property] = value; | ||
| }; | ||
| PathObjectBinder.prototype.getParent = function (path) { | ||
| if (path === undefined) | ||
| return this.source; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.source, path.substring(0, last)) : this.source; | ||
| }; | ||
| PathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| PathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return PathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = PathObjectBinder; |
Sorry, the diff of this file is too big to display
| !function(t){if("object"==typeof exports&&"undefined"!=typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var e;e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this,e.Binder=t()}}(function(){return function t(e,r,n){function i(u,s){if(!r[u]){if(!e[u]){var f="function"==typeof require&&require;if(!s&&f)return f(u,!0);if(o)return o(u,!0);var a=new Error("Cannot find module '"+u+"'");throw a.code="MODULE_NOT_FOUND",a}var h=r[u]={exports:{}};e[u][0].call(h.exports,function(t){var r=e[u][1][t];return i(r?r:t)},h,h.exports,t,e,r,n)}return r[u].exports}for(var o="function"==typeof require&&require,u=0;u<n.length;u++)i(n[u]);return i}({1:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";function h(t){var e=t.length;if(e%4>0)throw new Error("Invalid string. Length must be a multiple of 4");return"="===t[e-2]?2:"="===t[e-1]?1:0}function c(t){return 3*t.length/4-h(t)}function p(t){var e,r,n,i,o,u,s=t.length;o=h(t),u=new b(3*s/4-o),n=o>0?s-4:s;var f=0;for(e=0,r=0;n>e;e+=4,r+=3)i=v[t.charCodeAt(e)]<<18|v[t.charCodeAt(e+1)]<<12|v[t.charCodeAt(e+2)]<<6|v[t.charCodeAt(e+3)],u[f++]=i>>16&255,u[f++]=i>>8&255,u[f++]=255&i;return 2===o?(i=v[t.charCodeAt(e)]<<2|v[t.charCodeAt(e+1)]>>4,u[f++]=255&i):1===o&&(i=v[t.charCodeAt(e)]<<10|v[t.charCodeAt(e+1)]<<4|v[t.charCodeAt(e+2)]>>2,u[f++]=i>>8&255,u[f++]=255&i),u}function l(t){return y[t>>18&63]+y[t>>12&63]+y[t>>6&63]+y[63&t]}function g(t,e,r){for(var n,i=[],o=e;r>o;o+=3)n=(t[o]<<16)+(t[o+1]<<8)+t[o+2],i.push(l(n));return i.join("")}function d(t){for(var e,r=t.length,n=r%3,i="",o=[],u=16383,s=0,f=r-n;f>s;s+=u)o.push(g(t,s,s+u>f?f:s+u));return 1===n?(e=t[r-1],i+=y[e>>2],i+=y[e<<4&63],i+="=="):2===n&&(e=(t[r-2]<<8)+t[r-1],i+=y[e>>10],i+=y[e>>4&63],i+=y[e<<2&63],i+="="),o.push(i),o.join("")}r.byteLength=c,r.toByteArray=p,r.fromByteArray=d;for(var y=[],v=[],b="undefined"!=typeof Uint8Array?Uint8Array:Array,w="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",m=0,P=w.length;P>m;++m)y[m]=w[m],v[w.charCodeAt(m)]=m;v["-".charCodeAt(0)]=62,v["_".charCodeAt(0)]=63}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\base64-js\\index.js","/node_modules\\base64-js")},{_process:5,buffer:2}],2:[function(t,e,r){(function(e,n,i,o,u,s,f,a,h){"use strict";function c(){try{var t=new Uint8Array(1);return t.__proto__={__proto__:Uint8Array.prototype,foo:function(){return 42}},42===t.foo()&&"function"==typeof t.subarray&&0===t.subarray(1,1).byteLength}catch(e){return!1}}function p(){return i.TYPED_ARRAY_SUPPORT?2147483647:1073741823}function l(t,e){if(p()<e)throw new RangeError("Invalid typed array length");return i.TYPED_ARRAY_SUPPORT?(t=new Uint8Array(e),t.__proto__=i.prototype):(null===t&&(t=new i(e)),t.length=e),t}function i(t,e,r){if(!(i.TYPED_ARRAY_SUPPORT||this instanceof i))return new i(t,e,r);if("number"==typeof t){if("string"==typeof e)throw new Error("If encoding is specified then the first argument must be a string");return v(this,t)}return g(this,t,e,r)}function g(t,e,r,n){if("number"==typeof e)throw new TypeError('"value" argument must not be a number');return"undefined"!=typeof ArrayBuffer&&e instanceof ArrayBuffer?m(t,e,r,n):"string"==typeof e?b(t,e,r):P(t,e)}function d(t){if("number"!=typeof t)throw new TypeError('"size" argument must be a number');if(0>t)throw new RangeError('"size" argument must not be negative')}function y(t,e,r,n){return d(e),0>=e?l(t,e):void 0!==r?"string"==typeof n?l(t,e).fill(r,n):l(t,e).fill(r):l(t,e)}function v(t,e){if(d(e),t=l(t,0>e?0:0|_(e)),!i.TYPED_ARRAY_SUPPORT)for(var r=0;e>r;++r)t[r]=0;return t}function b(t,e,r){if(("string"!=typeof r||""===r)&&(r="utf8"),!i.isEncoding(r))throw new TypeError('"encoding" must be a valid string encoding');var n=0|B(e,r);t=l(t,n);var o=t.write(e,r);return o!==n&&(t=t.slice(0,o)),t}function w(t,e){var r=e.length<0?0:0|_(e.length);t=l(t,r);for(var n=0;r>n;n+=1)t[n]=255&e[n];return t}function m(t,e,r,n){if(e.byteLength,0>r||e.byteLength<r)throw new RangeError("'offset' is out of bounds");if(e.byteLength<r+(n||0))throw new RangeError("'length' is out of bounds");return e=void 0===r&&void 0===n?new Uint8Array(e):void 0===n?new Uint8Array(e,r):new Uint8Array(e,r,n),i.TYPED_ARRAY_SUPPORT?(t=e,t.__proto__=i.prototype):t=w(t,e),t}function P(t,e){if(i.isBuffer(e)){var r=0|_(e.length);return t=l(t,r),0===t.length?t:(e.copy(t,0,0,r),t)}if(e){if("undefined"!=typeof ArrayBuffer&&e.buffer instanceof ArrayBuffer||"length"in e)return"number"!=typeof e.length||nt(e.length)?l(t,0):w(t,e);if("Buffer"===e.type&&ut(e.data))return w(t,e.data)}throw new TypeError("First argument must be a string, Buffer, ArrayBuffer, Array, or array-like object.")}function _(t){if(t>=p())throw new RangeError("Attempt to allocate Buffer larger than maximum size: 0x"+p().toString(16)+" bytes");return 0|t}function A(t){return+t!=t&&(t=0),i.alloc(+t)}function B(t,e){if(i.isBuffer(t))return t.length;if("undefined"!=typeof ArrayBuffer&&"function"==typeof ArrayBuffer.isView&&(ArrayBuffer.isView(t)||t instanceof ArrayBuffer))return t.byteLength;"string"!=typeof t&&(t=""+t);var r=t.length;if(0===r)return 0;for(var n=!1;;)switch(e){case"ascii":case"latin1":case"binary":return r;case"utf8":case"utf-8":case void 0:return W(t).length;case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return 2*r;case"hex":return r>>>1;case"base64":return et(t).length;default:if(n)return W(t).length;e=(""+e).toLowerCase(),n=!0}}function E(t,e,r){var n=!1;if((void 0===e||0>e)&&(e=0),e>this.length)return"";if((void 0===r||r>this.length)&&(r=this.length),0>=r)return"";if(r>>>=0,e>>>=0,e>=r)return"";for(t||(t="utf8");;)switch(t){case"hex":return N(this,e,r);case"utf8":case"utf-8":return L(this,e,r);case"ascii":return D(this,e,r);case"latin1":case"binary":return V(this,e,r);case"base64":return x(this,e,r);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return k(this,e,r);default:if(n)throw new TypeError("Unknown encoding: "+t);t=(t+"").toLowerCase(),n=!0}}function T(t,e,r){var n=t[e];t[e]=t[r],t[r]=n}function R(t,e,r,n,o){if(0===t.length)return-1;if("string"==typeof r?(n=r,r=0):r>2147483647?r=2147483647:-2147483648>r&&(r=-2147483648),r=+r,isNaN(r)&&(r=o?0:t.length-1),0>r&&(r=t.length+r),r>=t.length){if(o)return-1;r=t.length-1}else if(0>r){if(!o)return-1;r=0}if("string"==typeof e&&(e=i.from(e,n)),i.isBuffer(e))return 0===e.length?-1:C(t,e,r,n,o);if("number"==typeof e)return e=255&e,i.TYPED_ARRAY_SUPPORT&&"function"==typeof Uint8Array.prototype.indexOf?o?Uint8Array.prototype.indexOf.call(t,e,r):Uint8Array.prototype.lastIndexOf.call(t,e,r):C(t,[e],r,n,o);throw new TypeError("val must be string, number or Buffer")}function C(t,e,r,n,i){function o(t,e){return 1===u?t[e]:t.readUInt16BE(e*u)}var u=1,s=t.length,f=e.length;if(void 0!==n&&(n=String(n).toLowerCase(),"ucs2"===n||"ucs-2"===n||"utf16le"===n||"utf-16le"===n)){if(t.length<2||e.length<2)return-1;u=2,s/=2,f/=2,r/=2}var a;if(i){var h=-1;for(a=r;s>a;a++)if(o(t,a)===o(e,-1===h?0:a-h)){if(-1===h&&(h=a),a-h+1===f)return h*u}else-1!==h&&(a-=a-h),h=-1}else for(r+f>s&&(r=s-f),a=r;a>=0;a--){for(var c=!0,p=0;f>p;p++)if(o(t,a+p)!==o(e,p)){c=!1;break}if(c)return a}return-1}function O(t,e,r,n){r=Number(r)||0;var i=t.length-r;n?(n=Number(n),n>i&&(n=i)):n=i;var o=e.length;if(o%2!==0)throw new TypeError("Invalid hex string");n>o/2&&(n=o/2);for(var u=0;n>u;++u){var s=parseInt(e.substr(2*u,2),16);if(isNaN(s))return u;t[r+u]=s}return u}function S(t,e,r,n){return rt(W(e,t.length-r),t,r,n)}function U(t,e,r,n){return rt($(e),t,r,n)}function j(t,e,r,n){return U(t,e,r,n)}function I(t,e,r,n){return rt(et(e),t,r,n)}function Y(t,e,r,n){return rt(tt(e,t.length-r),t,r,n)}function x(t,e,r){return 0===e&&r===t.length?it.fromByteArray(t):it.fromByteArray(t.slice(e,r))}function L(t,e,r){r=Math.min(t.length,r);for(var n=[],i=e;r>i;){var o=t[i],u=null,s=o>239?4:o>223?3:o>191?2:1;if(r>=i+s){var f,a,h,c;switch(s){case 1:128>o&&(u=o);break;case 2:f=t[i+1],128===(192&f)&&(c=(31&o)<<6|63&f,c>127&&(u=c));break;case 3:f=t[i+1],a=t[i+2],128===(192&f)&&128===(192&a)&&(c=(15&o)<<12|(63&f)<<6|63&a,c>2047&&(55296>c||c>57343)&&(u=c));break;case 4:f=t[i+1],a=t[i+2],h=t[i+3],128===(192&f)&&128===(192&a)&&128===(192&h)&&(c=(15&o)<<18|(63&f)<<12|(63&a)<<6|63&h,c>65535&&1114112>c&&(u=c))}}null===u?(u=65533,s=1):u>65535&&(u-=65536,n.push(u>>>10&1023|55296),u=56320|1023&u),n.push(u),i+=s}return M(n)}function M(t){var e=t.length;if(st>=e)return String.fromCharCode.apply(String,t);for(var r="",n=0;e>n;)r+=String.fromCharCode.apply(String,t.slice(n,n+=st));return r}function D(t,e,r){var n="";r=Math.min(t.length,r);for(var i=e;r>i;++i)n+=String.fromCharCode(127&t[i]);return n}function V(t,e,r){var n="";r=Math.min(t.length,r);for(var i=e;r>i;++i)n+=String.fromCharCode(t[i]);return n}function N(t,e,r){var n=t.length;(!e||0>e)&&(e=0),(!r||0>r||r>n)&&(r=n);for(var i="",o=e;r>o;++o)i+=Q(t[o]);return i}function k(t,e,r){for(var n=t.slice(e,r),i="",o=0;o<n.length;o+=2)i+=String.fromCharCode(n[o]+256*n[o+1]);return i}function F(t,e,r){if(t%1!==0||0>t)throw new RangeError("offset is not uint");if(t+e>r)throw new RangeError("Trying to access beyond buffer length")}function z(t,e,r,n,o,u){if(!i.isBuffer(t))throw new TypeError('"buffer" argument must be a Buffer instance');if(e>o||u>e)throw new RangeError('"value" argument is out of bounds');if(r+n>t.length)throw new RangeError("Index out of range")}function q(t,e,r,n){0>e&&(e=65535+e+1);for(var i=0,o=Math.min(t.length-r,2);o>i;++i)t[r+i]=(e&255<<8*(n?i:1-i))>>>8*(n?i:1-i)}function J(t,e,r,n){0>e&&(e=4294967295+e+1);for(var i=0,o=Math.min(t.length-r,4);o>i;++i)t[r+i]=e>>>8*(n?i:3-i)&255}function K(t,e,r,n,i,o){if(r+n>t.length)throw new RangeError("Index out of range");if(0>r)throw new RangeError("Index out of range")}function X(t,e,r,n,i){return i||K(t,e,r,4,3.4028234663852886e38,-3.4028234663852886e38),ot.write(t,e,r,n,23,4),r+4}function Z(t,e,r,n,i){return i||K(t,e,r,8,1.7976931348623157e308,-1.7976931348623157e308),ot.write(t,e,r,n,52,8),r+8}function G(t){if(t=H(t).replace(ft,""),t.length<2)return"";for(;t.length%4!==0;)t+="=";return t}function H(t){return t.trim?t.trim():t.replace(/^\s+|\s+$/g,"")}function Q(t){return 16>t?"0"+t.toString(16):t.toString(16)}function W(t,e){e=e||1/0;for(var r,n=t.length,i=null,o=[],u=0;n>u;++u){if(r=t.charCodeAt(u),r>55295&&57344>r){if(!i){if(r>56319){(e-=3)>-1&&o.push(239,191,189);continue}if(u+1===n){(e-=3)>-1&&o.push(239,191,189);continue}i=r;continue}if(56320>r){(e-=3)>-1&&o.push(239,191,189),i=r;continue}r=(i-55296<<10|r-56320)+65536}else i&&(e-=3)>-1&&o.push(239,191,189);if(i=null,128>r){if((e-=1)<0)break;o.push(r)}else if(2048>r){if((e-=2)<0)break;o.push(r>>6|192,63&r|128)}else if(65536>r){if((e-=3)<0)break;o.push(r>>12|224,r>>6&63|128,63&r|128)}else{if(!(1114112>r))throw new Error("Invalid code point");if((e-=4)<0)break;o.push(r>>18|240,r>>12&63|128,r>>6&63|128,63&r|128)}}return o}function $(t){for(var e=[],r=0;r<t.length;++r)e.push(255&t.charCodeAt(r));return e}function tt(t,e){for(var r,n,i,o=[],u=0;u<t.length&&!((e-=2)<0);++u)r=t.charCodeAt(u),n=r>>8,i=r%256,o.push(i),o.push(n);return o}function et(t){return it.toByteArray(G(t))}function rt(t,e,r,n){for(var i=0;n>i&&!(i+r>=e.length||i>=t.length);++i)e[i+r]=t[i];return i}function nt(t){return t!==t}var it=t("base64-js"),ot=t("ieee754"),ut=t("isarray");r.Buffer=i,r.SlowBuffer=A,r.INSPECT_MAX_BYTES=50,i.TYPED_ARRAY_SUPPORT=void 0!==n.TYPED_ARRAY_SUPPORT?n.TYPED_ARRAY_SUPPORT:c(),r.kMaxLength=p(),i.poolSize=8192,i._augment=function(t){return t.__proto__=i.prototype,t},i.from=function(t,e,r){return g(null,t,e,r)},i.TYPED_ARRAY_SUPPORT&&(i.prototype.__proto__=Uint8Array.prototype,i.__proto__=Uint8Array,"undefined"!=typeof Symbol&&Symbol.species&&i[Symbol.species]===i&&Object.defineProperty(i,Symbol.species,{value:null,configurable:!0})),i.alloc=function(t,e,r){return y(null,t,e,r)},i.allocUnsafe=function(t){return v(null,t)},i.allocUnsafeSlow=function(t){return v(null,t)},i.isBuffer=function(t){return!(null==t||!t._isBuffer)},i.compare=function(t,e){if(!i.isBuffer(t)||!i.isBuffer(e))throw new TypeError("Arguments must be Buffers");if(t===e)return 0;for(var r=t.length,n=e.length,o=0,u=Math.min(r,n);u>o;++o)if(t[o]!==e[o]){r=t[o],n=e[o];break}return n>r?-1:r>n?1:0},i.isEncoding=function(t){switch(String(t).toLowerCase()){case"hex":case"utf8":case"utf-8":case"ascii":case"latin1":case"binary":case"base64":case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return!0;default:return!1}},i.concat=function(t,e){if(!ut(t))throw new TypeError('"list" argument must be an Array of Buffers');if(0===t.length)return i.alloc(0);var r;if(void 0===e)for(e=0,r=0;r<t.length;++r)e+=t[r].length;var n=i.allocUnsafe(e),o=0;for(r=0;r<t.length;++r){var u=t[r];if(!i.isBuffer(u))throw new TypeError('"list" argument must be an Array of Buffers');u.copy(n,o),o+=u.length}return n},i.byteLength=B,i.prototype._isBuffer=!0,i.prototype.swap16=function(){var t=this.length;if(t%2!==0)throw new RangeError("Buffer size must be a multiple of 16-bits");for(var e=0;t>e;e+=2)T(this,e,e+1);return this},i.prototype.swap32=function(){var t=this.length;if(t%4!==0)throw new RangeError("Buffer size must be a multiple of 32-bits");for(var e=0;t>e;e+=4)T(this,e,e+3),T(this,e+1,e+2);return this},i.prototype.swap64=function(){var t=this.length;if(t%8!==0)throw new RangeError("Buffer size must be a multiple of 64-bits");for(var e=0;t>e;e+=8)T(this,e,e+7),T(this,e+1,e+6),T(this,e+2,e+5),T(this,e+3,e+4);return this},i.prototype.toString=function(){var t=0|this.length;return 0===t?"":0===arguments.length?L(this,0,t):E.apply(this,arguments)},i.prototype.equals=function(t){if(!i.isBuffer(t))throw new TypeError("Argument must be a Buffer");return this===t?!0:0===i.compare(this,t)},i.prototype.inspect=function(){var t="",e=r.INSPECT_MAX_BYTES;return this.length>0&&(t=this.toString("hex",0,e).match(/.{2}/g).join(" "),this.length>e&&(t+=" ... ")),"<Buffer "+t+">"},i.prototype.compare=function(t,e,r,n,o){if(!i.isBuffer(t))throw new TypeError("Argument must be a Buffer");if(void 0===e&&(e=0),void 0===r&&(r=t?t.length:0),void 0===n&&(n=0),void 0===o&&(o=this.length),0>e||r>t.length||0>n||o>this.length)throw new RangeError("out of range index");if(n>=o&&e>=r)return 0;if(n>=o)return-1;if(e>=r)return 1;if(e>>>=0,r>>>=0,n>>>=0,o>>>=0,this===t)return 0;for(var u=o-n,s=r-e,f=Math.min(u,s),a=this.slice(n,o),h=t.slice(e,r),c=0;f>c;++c)if(a[c]!==h[c]){u=a[c],s=h[c];break}return s>u?-1:u>s?1:0},i.prototype.includes=function(t,e,r){return-1!==this.indexOf(t,e,r)},i.prototype.indexOf=function(t,e,r){return R(this,t,e,r,!0)},i.prototype.lastIndexOf=function(t,e,r){return R(this,t,e,r,!1)},i.prototype.write=function(t,e,r,n){if(void 0===e)n="utf8",r=this.length,e=0;else if(void 0===r&&"string"==typeof e)n=e,r=this.length,e=0;else{if(!isFinite(e))throw new Error("Buffer.write(string, encoding, offset[, length]) is no longer supported");e=0|e,isFinite(r)?(r=0|r,void 0===n&&(n="utf8")):(n=r,r=void 0)}var i=this.length-e;if((void 0===r||r>i)&&(r=i),t.length>0&&(0>r||0>e)||e>this.length)throw new RangeError("Attempt to write outside buffer bounds");n||(n="utf8");for(var o=!1;;)switch(n){case"hex":return O(this,t,e,r);case"utf8":case"utf-8":return S(this,t,e,r);case"ascii":return U(this,t,e,r);case"latin1":case"binary":return j(this,t,e,r);case"base64":return I(this,t,e,r);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return Y(this,t,e,r);default:if(o)throw new TypeError("Unknown encoding: "+n);n=(""+n).toLowerCase(),o=!0}},i.prototype.toJSON=function(){return{type:"Buffer",data:Array.prototype.slice.call(this._arr||this,0)}};var st=4096;i.prototype.slice=function(t,e){var r=this.length;t=~~t,e=void 0===e?r:~~e,0>t?(t+=r,0>t&&(t=0)):t>r&&(t=r),0>e?(e+=r,0>e&&(e=0)):e>r&&(e=r),t>e&&(e=t);var n;if(i.TYPED_ARRAY_SUPPORT)n=this.subarray(t,e),n.__proto__=i.prototype;else{var o=e-t;n=new i(o,void 0);for(var u=0;o>u;++u)n[u]=this[u+t]}return n},i.prototype.readUIntLE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t],i=1,o=0;++o<e&&(i*=256);)n+=this[t+o]*i;return n},i.prototype.readUIntBE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t+--e],i=1;e>0&&(i*=256);)n+=this[t+--e]*i;return n},i.prototype.readUInt8=function(t,e){return e||F(t,1,this.length),this[t]},i.prototype.readUInt16LE=function(t,e){return e||F(t,2,this.length),this[t]|this[t+1]<<8},i.prototype.readUInt16BE=function(t,e){return e||F(t,2,this.length),this[t]<<8|this[t+1]},i.prototype.readUInt32LE=function(t,e){return e||F(t,4,this.length),(this[t]|this[t+1]<<8|this[t+2]<<16)+16777216*this[t+3]},i.prototype.readUInt32BE=function(t,e){return e||F(t,4,this.length),16777216*this[t]+(this[t+1]<<16|this[t+2]<<8|this[t+3])},i.prototype.readIntLE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t],i=1,o=0;++o<e&&(i*=256);)n+=this[t+o]*i;return i*=128,n>=i&&(n-=Math.pow(2,8*e)),n},i.prototype.readIntBE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=e,i=1,o=this[t+--n];n>0&&(i*=256);)o+=this[t+--n]*i;return i*=128,o>=i&&(o-=Math.pow(2,8*e)),o},i.prototype.readInt8=function(t,e){return e||F(t,1,this.length),128&this[t]?-1*(255-this[t]+1):this[t]},i.prototype.readInt16LE=function(t,e){e||F(t,2,this.length);var r=this[t]|this[t+1]<<8;return 32768&r?4294901760|r:r},i.prototype.readInt16BE=function(t,e){e||F(t,2,this.length);var r=this[t+1]|this[t]<<8;return 32768&r?4294901760|r:r},i.prototype.readInt32LE=function(t,e){return e||F(t,4,this.length),this[t]|this[t+1]<<8|this[t+2]<<16|this[t+3]<<24},i.prototype.readInt32BE=function(t,e){return e||F(t,4,this.length),this[t]<<24|this[t+1]<<16|this[t+2]<<8|this[t+3]},i.prototype.readFloatLE=function(t,e){return e||F(t,4,this.length),ot.read(this,t,!0,23,4)},i.prototype.readFloatBE=function(t,e){return e||F(t,4,this.length),ot.read(this,t,!1,23,4)},i.prototype.readDoubleLE=function(t,e){return e||F(t,8,this.length),ot.read(this,t,!0,52,8)},i.prototype.readDoubleBE=function(t,e){return e||F(t,8,this.length),ot.read(this,t,!1,52,8)},i.prototype.writeUIntLE=function(t,e,r,n){if(t=+t,e=0|e,r=0|r,!n){var i=Math.pow(2,8*r)-1;z(this,t,e,r,i,0)}var o=1,u=0;for(this[e]=255&t;++u<r&&(o*=256);)this[e+u]=t/o&255;return e+r},i.prototype.writeUIntBE=function(t,e,r,n){if(t=+t,e=0|e,r=0|r,!n){var i=Math.pow(2,8*r)-1;z(this,t,e,r,i,0)}var o=r-1,u=1;for(this[e+o]=255&t;--o>=0&&(u*=256);)this[e+o]=t/u&255;return e+r},i.prototype.writeUInt8=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,1,255,0),i.TYPED_ARRAY_SUPPORT||(t=Math.floor(t)),this[e]=255&t,e+1},i.prototype.writeUInt16LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,65535,0),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8):q(this,t,e,!0),e+2},i.prototype.writeUInt16BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,65535,0),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>8,this[e+1]=255&t):q(this,t,e,!1),e+2},i.prototype.writeUInt32LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,4294967295,0),i.TYPED_ARRAY_SUPPORT?(this[e+3]=t>>>24,this[e+2]=t>>>16,this[e+1]=t>>>8,this[e]=255&t):J(this,t,e,!0),e+4},i.prototype.writeUInt32BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,4294967295,0),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>24,this[e+1]=t>>>16,this[e+2]=t>>>8,this[e+3]=255&t):J(this,t,e,!1),e+4},i.prototype.writeIntLE=function(t,e,r,n){if(t=+t,e=0|e,!n){var i=Math.pow(2,8*r-1);z(this,t,e,r,i-1,-i)}var o=0,u=1,s=0;for(this[e]=255&t;++o<r&&(u*=256);)0>t&&0===s&&0!==this[e+o-1]&&(s=1),this[e+o]=(t/u>>0)-s&255;return e+r},i.prototype.writeIntBE=function(t,e,r,n){if(t=+t,e=0|e,!n){var i=Math.pow(2,8*r-1);z(this,t,e,r,i-1,-i)}var o=r-1,u=1,s=0;for(this[e+o]=255&t;--o>=0&&(u*=256);)0>t&&0===s&&0!==this[e+o+1]&&(s=1),this[e+o]=(t/u>>0)-s&255;return e+r},i.prototype.writeInt8=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,1,127,-128),i.TYPED_ARRAY_SUPPORT||(t=Math.floor(t)),0>t&&(t=255+t+1),this[e]=255&t,e+1},i.prototype.writeInt16LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,32767,-32768),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8):q(this,t,e,!0),e+2},i.prototype.writeInt16BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,32767,-32768),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>8,this[e+1]=255&t):q(this,t,e,!1),e+2},i.prototype.writeInt32LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,2147483647,-2147483648),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8,this[e+2]=t>>>16,this[e+3]=t>>>24):J(this,t,e,!0),e+4},i.prototype.writeInt32BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,2147483647,-2147483648),0>t&&(t=4294967295+t+1),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>24,this[e+1]=t>>>16,this[e+2]=t>>>8,this[e+3]=255&t):J(this,t,e,!1),e+4},i.prototype.writeFloatLE=function(t,e,r){return X(this,t,e,!0,r)},i.prototype.writeFloatBE=function(t,e,r){return X(this,t,e,!1,r)},i.prototype.writeDoubleLE=function(t,e,r){return Z(this,t,e,!0,r)},i.prototype.writeDoubleBE=function(t,e,r){return Z(this,t,e,!1,r)},i.prototype.copy=function(t,e,r,n){if(r||(r=0),n||0===n||(n=this.length),e>=t.length&&(e=t.length),e||(e=0),n>0&&r>n&&(n=r),n===r)return 0;if(0===t.length||0===this.length)return 0;if(0>e)throw new RangeError("targetStart out of bounds");if(0>r||r>=this.length)throw new RangeError("sourceStart out of bounds");if(0>n)throw new RangeError("sourceEnd out of bounds");n>this.length&&(n=this.length),t.length-e<n-r&&(n=t.length-e+r);var o,u=n-r;if(this===t&&e>r&&n>e)for(o=u-1;o>=0;--o)t[o+e]=this[o+r];else if(1e3>u||!i.TYPED_ARRAY_SUPPORT)for(o=0;u>o;++o)t[o+e]=this[o+r];else Uint8Array.prototype.set.call(t,this.subarray(r,r+u),e);return u},i.prototype.fill=function(t,e,r,n){if("string"==typeof t){if("string"==typeof e?(n=e,e=0,r=this.length):"string"==typeof r&&(n=r,r=this.length),1===t.length){var o=t.charCodeAt(0);256>o&&(t=o)}if(void 0!==n&&"string"!=typeof n)throw new TypeError("encoding must be a string");if("string"==typeof n&&!i.isEncoding(n))throw new TypeError("Unknown encoding: "+n)}else"number"==typeof t&&(t=255&t);if(0>e||this.length<e||this.length<r)throw new RangeError("Out of range index");if(e>=r)return this;e>>>=0,r=void 0===r?this.length:r>>>0,t||(t=0);var u;if("number"==typeof t)for(u=e;r>u;++u)this[u]=t;else{var s=i.isBuffer(t)?t:W(new i(t,n).toString()),f=s.length;for(u=0;r-e>u;++u)this[u+e]=s[u%f]}return this};var ft=/[^+\/0-9A-Za-z-_]/g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\buffer\\index.js","/node_modules\\buffer")},{_process:5,"base64-js":1,buffer:2,ieee754:4,isarray:3}],3:[function(t,e,r){(function(t,r,n,i,o,u,s,f,a){var h={}.toString;e.exports=Array.isArray||function(t){return"[object Array]"==h.call(t)}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\buffer\\node_modules\\isarray\\index.js","/node_modules\\buffer\\node_modules\\isarray")},{_process:5,buffer:2}],4:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){r.read=function(t,e,r,n,i){var o,u,s=8*i-n-1,f=(1<<s)-1,a=f>>1,h=-7,c=r?i-1:0,p=r?-1:1,l=t[e+c];for(c+=p,o=l&(1<<-h)-1,l>>=-h,h+=s;h>0;o=256*o+t[e+c],c+=p,h-=8);for(u=o&(1<<-h)-1,o>>=-h,h+=n;h>0;u=256*u+t[e+c],c+=p,h-=8);if(0===o)o=1-a;else{if(o===f)return u?NaN:(l?-1:1)*(1/0);u+=Math.pow(2,n),o-=a}return(l?-1:1)*u*Math.pow(2,o-n)},r.write=function(t,e,r,n,i,o){var u,s,f,a=8*o-i-1,h=(1<<a)-1,c=h>>1,p=23===i?Math.pow(2,-24)-Math.pow(2,-77):0,l=n?0:o-1,g=n?1:-1,d=0>e||0===e&&0>1/e?1:0;for(e=Math.abs(e),isNaN(e)||e===1/0?(s=isNaN(e)?1:0,u=h):(u=Math.floor(Math.log(e)/Math.LN2),e*(f=Math.pow(2,-u))<1&&(u--,f*=2),e+=u+c>=1?p/f:p*Math.pow(2,1-c),e*f>=2&&(u++,f/=2),u+c>=h?(s=0,u=h):u+c>=1?(s=(e*f-1)*Math.pow(2,i),u+=c):(s=e*Math.pow(2,c-1)*Math.pow(2,i),u=0));i>=8;t[r+l]=255&s,l+=g,s/=256,i-=8);for(u=u<<i|s,a+=i;a>0;t[r+l]=255&u,l+=g,u/=256,a-=8);t[r+l-g]|=128*d}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\ieee754\\index.js","/node_modules\\ieee754")},{_process:5,buffer:2}],5:[function(t,e,r){(function(t,r,n,i,o,u,s,f,a){function h(){throw new Error("setTimeout has not been defined")}function c(){throw new Error("clearTimeout has not been defined")}function p(t){if(b===setTimeout)return setTimeout(t,0);if((b===h||!b)&&setTimeout)return b=setTimeout,setTimeout(t,0);try{return b(t,0)}catch(e){try{return b.call(null,t,0)}catch(e){return b.call(this,t,0)}}}function l(t){if(w===clearTimeout)return clearTimeout(t);if((w===c||!w)&&clearTimeout)return w=clearTimeout,clearTimeout(t);try{return w(t)}catch(e){try{return w.call(null,t)}catch(e){return w.call(this,t)}}}function g(){_&&m&&(_=!1,m.length?P=m.concat(P):A=-1,P.length&&d())}function d(){if(!_){var t=p(g);_=!0;for(var e=P.length;e;){for(m=P,P=[];++A<e;)m&&m[A].run();A=-1,e=P.length}m=null,_=!1,l(t)}}function y(t,e){this.fun=t,this.array=e}function v(){}var b,w,t=e.exports={};!function(){try{b="function"==typeof setTimeout?setTimeout:h}catch(t){b=h}try{w="function"==typeof clearTimeout?clearTimeout:c}catch(t){w=c}}();var m,P=[],_=!1,A=-1;t.nextTick=function(t){var e=new Array(arguments.length-1);if(arguments.length>1)for(var r=1;r<arguments.length;r++)e[r-1]=arguments[r];P.push(new y(t,e)),1!==P.length||_||p(d)},y.prototype.run=function(){this.fun.apply(null,this.array)},t.title="browser",t.browser=!0,t.env={},t.argv=[],t.version="",t.versions={},t.on=v,t.addListener=v,t.once=v,t.off=v,t.removeListener=v,t.removeAllListeners=v,t.emit=v,t.binding=function(t){throw new Error("process.binding is not supported")},t.cwd=function(){return"/"},t.chdir=function(t){throw new Error("process.chdir is not supported")},t.umask=function(){return 0}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\process\\browser.js","/node_modules\\process")},{_process:5,buffer:2}],6:[function(t,e,r){(function(e,n,i,o,u,s,f,a,h){"use strict";var c=t("./PlainObjectProvider"),p=t("./DataBinding"),l=function(){function t(){}return t.bindTo=function(t,e,r,n,i){var n=void 0!==i?new p.CurryConverter(n,i):n;return e instanceof p.PathObjectBinding||e instanceof p.PathParentBinding?new p.PathParentBinding(e,r,n):new p.PathObjectBinding(e,function(e){return new t(e)},r,n)},t.bindArrayTo=function(t,e,r,n,i){var n=void 0!==i?new p.CurryConverter(n,i):n;return e instanceof p.PathObjectBinding||e instanceof p.PathParentBinding?new p.ArrayParentBinding(e,r,n):new p.ArrayObjectBinding(e,function(e){return new t(e)},r,n)},t}();r.BinderCore=l;var g=function(){function t(){}return t.createStateKeySetter=function(t,e){var r={};return function(n){r[e]=void 0!==n?n:t.state[e],t.setState(r)}},t.bindToState=function(e,r,n,i,o){return new p.PathObjectBinding(e.state[r],function(t){return new c["default"](t)},n,t.createStateKeySetter(e,r),void 0!==o?new p.CurryConverter(i,o):i)},t.bindTo=function(t,e,r,n){return l.bindTo(c["default"],t,e,r,n)},t.bindArrayToState=function(e,r,n){return new p.ArrayObjectBinding(e.state[r],function(t){return new c["default"](t)},n,t.createStateKeySetter(e,r))},t.bindArrayTo=function(t,e,r,n){return l.bindArrayTo(c["default"],t,e,r,n)},t}();Object.defineProperty(r,"__esModule",{value:!0}),r["default"]=g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\Binder.ts","/src")},{"./DataBinding":7,"./PlainObjectProvider":8,_process:5,buffer:2}],7:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";var h=function(){function t(t,e,r,n,i,o){this.sourceObject=t,this.provider=e,this.path=r,this.notifyChange=n,this.valueConverter=i,this.parentNode=o,this.source=e(t)}return Object.defineProperty(t.prototype,"requestChange",{get:function(){var t=this;return function(e){t.value=e}},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return void 0!==this.parentNode?this.parentNode.root:this},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return void 0!==this.parentNode?this.parentNode:void 0},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"value",{get:function(){var t=void 0===this.path?this.source.getValue():this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t},set:function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path),r=void 0!==this.valueConverter?this.valueConverter.parse(t):t;(void 0===e||e!==r)&&(void 0===this.path?void 0!==this.notifyChange&&this.notifyChange(r):(this.source.setValue(this.path,r),void 0!==this.notifyChange&&this.notifyChange()))},enumerable:!0,configurable:!0}),t}();r.PathObjectBinding=h;var c=function(){function t(t,e,r,n,i){this.sourceObject=t,this.provider=e,this.path=r,this.notifyChange=n,this.valueConverter=i,this.source=e(t)}return Object.defineProperty(t.prototype,"parent",{get:function(){return void 0},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"items",{get:function(){var t=void 0===this.path?this.source.getValue():this.source.getValue(this.path);return void 0===t?[]:t.map(function(t){return new h(t,this.provider,void 0,this.notifyChange,void 0,this)},this)},enumerable:!0,configurable:!0}),t.prototype.add=function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path);void 0===e&&(this.source.setValue(this.path,[]),e=this.source.getValue(this.path)),void 0===t&&(t={}),e.push(t),void 0!==this.notifyChange&&this.notifyChange()},t.prototype.remove=function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==e){var r=e.indexOf(t);-1!==r&&(e.splice(r,1),void 0!==this.notifyChange&&this.notifyChange())}},t.prototype.splice=function(t,e,r){var n=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==n)return r?n.splice(t,e,r):n.splice(t,e)},t.prototype.move=function(t,e){var r=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==r){var n=JSON.parse(JSON.stringify(r));n.splice(e,0,n.splice(t,1)[0]),this.source.setValue(this.path,n)}},t}();r.ArrayObjectBinding=c;var p=function(){function t(t,e,r){this.parentBinding=t,this.relativePath=e,this.valueConverter=r}return Object.defineProperty(t.prototype,"source",{get:function(){return this.parentBinding.source},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"provider",{get:function(){return this.parentBinding.provider},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this.parentBinding.root},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return this.parentBinding},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"notifyChange",{get:function(){return this.parentBinding.notifyChange},set:function(t){this.parentBinding.notifyChange=t},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"path",{get:function(){return void 0===this.parentBinding.path?this.relativePath:void 0===this.relativePath?this.parentBinding.path:[this.parentBinding.path,this.relativePath].join(".")},enumerable:!0,configurable:!0}),t.prototype.getItems=function(){if(void 0!==this.source){var t=this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t}},Object.defineProperty(t.prototype,"items",{ | ||
| get:function(){var t=this.getItems();return void 0===t?[]:t.map(function(t){return new h(t,this.provider,void 0,this.notifyChange,void 0,this)},this)},enumerable:!0,configurable:!0}),t.prototype.add=function(t){var e=this.getItems();void 0===e&&(this.source.setValue(this.path,[]),e=this.source.getValue(this.path)),void 0===t&&(t={}),e.push(t),void 0!==this.notifyChange&&this.notifyChange()},t.prototype.remove=function(t){var e=this.getItems();if(void 0!==e){var r=e.indexOf(t);-1!==r&&(e.splice(r,1),void 0!==this.notifyChange&&this.notifyChange())}},t.prototype.splice=function(t,e,r){var n=this.getItems();if(void 0!==n)return r?n.splice(t,e,r):n.splice(t,e)},t.prototype.move=function(t,e){this.splice(e,0,this.splice(t,1)[0]),void 0!==this.notifyChange&&this.notifyChange()},t}();r.ArrayParentBinding=p;var l=function(){function t(t,e,r){this.parentBinding=t,this.relativePath=e,this.valueConverter=r}return Object.defineProperty(t.prototype,"source",{get:function(){return this.parentBinding.source},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"provider",{get:function(){return this.parentBinding.provider},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this.parentBinding.root},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return this.parentBinding},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"notifyChange",{get:function(){return this.parentBinding.notifyChange},set:function(t){this.parentBinding.notifyChange=t},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"requestChange",{get:function(){var t=this;return function(e){t.value=e}},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"path",{get:function(){return void 0===this.parentBinding.path?this.relativePath:[this.parentBinding.path,this.relativePath].join(".")},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"value",{get:function(){var t=this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t},set:function(t){var e=this.source.getValue(this.path),r=void 0!==this.valueConverter?this.valueConverter.parse(t):t;e!==r&&(this.source.setValue(this.path,r),void 0!==this.notifyChange&&this.notifyChange())},enumerable:!0,configurable:!0}),t}();r.PathParentBinding=l;var g=function(){function t(t,e){this.formatFce=this.curryParameters(t.format,[e]),this.parseFce=this.curryParameters(t.parse,[e])}return t.prototype.curryParameters=function(t,e){return function(){return t.apply(this,Array.prototype.slice.call(arguments).concat(e))}},t.prototype.format=function(t){return this.formatFce(t)},t.prototype.parse=function(t){return this.parseFce(t)},t}();r.CurryConverter=g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\DataBinding.ts","/src")},{_process:5,buffer:2}],8:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";var h=function(){function t(t){this.source=t}return t.prototype.subscribe=function(t){},t.prototype.getValue=function(e){var r=this.getParent(e);if(void 0!==r){if(void 0===e)return r;var n=t.getProperty(e);return r[n]}},t.prototype.setValue=function(e,r){var n=this.getParent(e);if(void 0!==n){var i=t.getProperty(e);n[i]=r}},t.prototype.getParent=function(t){if(void 0===t)return this.source;var e=t.lastIndexOf(".");return-1!=e?this.string_to_ref(this.source,t.substring(0,e)):this.source},t.getProperty=function(t){var e=t.lastIndexOf(".");return-1!=e?t.substring(e+1,t.length):t},t.prototype.string_to_ref=function(t,e){var r=e.split("."),n=t[r[0]];if(void 0===n&&(n=t[r[0]]={}),!r[1])return n;r.splice(0,1);var i=r.join(".");return this.string_to_ref(n,i)},t}();Object.defineProperty(r,"__esModule",{value:!0}),r["default"]=h}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\PlainObjectProvider.ts","/src")},{_process:5,buffer:2}]},{},[6])(6)}); |
+4
-21
| { | ||
| "name": "react-binding", | ||
| "version": "0.8.1", | ||
| "version": "0.8.2", | ||
| "description": "Binder - react two-way data binding for complex objects and arrays.", | ||
@@ -20,3 +20,3 @@ "main": "lib/Binder.js", | ||
| ], | ||
| "author": "Roman Samec", | ||
| "author": "Roman Samec <roman.samec2@gmail.com>", | ||
| "license": "MIT", | ||
@@ -27,21 +27,4 @@ "bugs": { | ||
| "homepage": "https://github.com/rsamec/react-binding", | ||
| "devDependencies": { | ||
| "@types/mocha": "^2.2.35", | ||
| "@types/node": "^6.0.55", | ||
| "browserify": "^13.1.1", | ||
| "expect.js": "^0.3.1", | ||
| "gulp": "^3.8.11", | ||
| "gulp-rename": "^1.2.0", | ||
| "gulp-typescript": "^2.4.2", | ||
| "gulp-uglify": "^1.1.0", | ||
| "merge2": "^0.3.1", | ||
| "mocha": "^2.1.0", | ||
| "tsify": "^3.0.0", | ||
| "vinyl-buffer": "^1.0.0", | ||
| "vinyl-source-stream": "^1.1.0" | ||
| }, | ||
| "dependencies": { | ||
| "freezer-js": "^0.11.1", | ||
| "mobx": "^2.6.4" | ||
| } | ||
| "devDependencies": {}, | ||
| "dependencies": {} | ||
| } |
+31
-45
@@ -5,39 +5,30 @@ # react-binding | ||
| ``` js | ||
| import React from 'react'; | ||
| import ReactDOM from 'react-dom'; | ||
| import Binder from 'react-binding'; | ||
| Note: React-binding as mixins - use npm install react-binding@0.6.4 | ||
| export default class Form extends React.Component { | ||
| constructor(props){ | ||
| super(props); | ||
| this.state = {data: {}}; | ||
| }, | ||
| render { | ||
| return ( | ||
| <div> | ||
| <input valueLink={Binder.bindToState(this,"data", "Employee.FirstName")} /> | ||
| <div>FirstName: {this.state.data.Employee.FirstName}</div> | ||
| </div> | ||
| )} | ||
| }); | ||
| ```js | ||
| import {Binder} from 'react-binding' | ||
| ``` | ||
| ReactDOM.render( | ||
| <Form />, | ||
| document.getElementById('content') | ||
| ); | ||
| ```js | ||
| Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| Binder.bindToArrayState(this,"data","__Hobbies__"); | ||
| Binder.bindTo(__employee__,"__Contact.Email__"); | ||
| Binder.bindToArray(__employee__,"__Hobbies__"); | ||
| ``` | ||
| ## Features: | ||
| + No dependencies. | ||
| + Minimal interface - using path with dot notation. | ||
| + Support for complex objects. | ||
| + Support for collection-based structures - arrays and lists. | ||
| + Support for value converters. | ||
| + No need to define initial values, nested structures. Binder creates this for you. | ||
| + Lightweight. | ||
| ```js | ||
| [react-binding](https://github.com/rsamec/react-binding) offers two-way data binding support for: | ||
| Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| Binder.bindToArrayState(this,"data","__Hobbies__"); | ||
| Binder.bindTo(__employee__,"__Contact.Email__"); | ||
| Binder.bindToArray(__employee__,"__Hobbies__"); | ||
| ``` | ||
| [BindToMixin](https://github.com/rsamec/react-binding) offers two-way data binding support for: | ||
| + object properties with path expression (dot notation) | ||
@@ -97,15 +88,13 @@ + Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| import React from 'react'; | ||
| import ReactDOM from 'react-dom'; | ||
| import Binder from 'react-binding'; | ||
| import {Binder} from 'react-binding' | ||
| export default class Form extends React.Component { | ||
| constructor(props){ | ||
| super(props); | ||
| this.state = {data: {}}; | ||
| var Form = React.createClass({ | ||
| getInitialState: function () { | ||
| return {data: {}} | ||
| }, | ||
| render { | ||
| render: function () { | ||
| return ( | ||
| <div> | ||
| <input valueLink={Binder.bindToState(this,"data", "Employee.FirstName")} /> | ||
| <div>FirstName: {this.state.data.Employee.FirstName}</div> | ||
| <input valueLink={Binder.bindToState(this,"data", "FirstName")} /> | ||
| <div>FirstName: {this.state.data.FirstName}</div> | ||
| </div> | ||
@@ -115,3 +104,3 @@ )} | ||
| ReactDOM.render( | ||
| React.render( | ||
| <Form />, | ||
@@ -122,5 +111,2 @@ document.getElementById('content') | ||
| ``` | ||
| __Note__: React-binding as mixins - use npm install react-binding@0.6.4 | ||
| # Overview | ||
@@ -163,4 +149,4 @@ | ||
| ``` js | ||
| <PersonComponent personModel={Binder.bindToState(this,"data","Employee")} /> | ||
| <PersonComponent personModel={Binder.bindToState(this,"data","Deputy")} /> | ||
| <PersonComponent personModel={Binder.bindToState("data","Employee")} /> | ||
| <PersonComponent personModel={Binder.bindToState("data","Deputy")} /> | ||
| ``` | ||
@@ -167,0 +153,0 @@ |
Sorry, the diff of this file is not supported yet
-30
| { | ||
| "name": "react-binding", | ||
| "version": "0.8.1", | ||
| "homepage": "https://github.com/rsamec/react-binding", | ||
| "authors": [ | ||
| "Roman Samec <roman.samec2@gmail.com>" | ||
| ], | ||
| "description": "BindToMixin - react data binding for complex objects and arrays.", | ||
| "main": "dist/react-binding", | ||
| "moduleType": [ | ||
| "globals", | ||
| "node" | ||
| ], | ||
| "keywords": [ | ||
| "react", | ||
| "binding" | ||
| ], | ||
| "license": "MIT", | ||
| "ignore": [ | ||
| "**/.*", | ||
| "node_modules", | ||
| "bower_components", | ||
| "test", | ||
| "tests", | ||
| "typings", | ||
| "src", | ||
| "tsd.json", | ||
| "out" | ||
| ] | ||
| } |
| import { IPathObjectBinder, IPathObjectBinding, IValueConverter, ArrayObjectBinding } from './DataBinding'; | ||
| export declare class BinderCore { | ||
| static bindTo(type: { | ||
| new (data): IPathObjectBinder; | ||
| }, parent: any, path?: string, converter?: any, converterParams?: any): IPathObjectBinding; | ||
| static bindArrayTo(type: { | ||
| new (data): IPathObjectBinder; | ||
| }, parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } | ||
| /** | ||
| * React [LinkedStateMixin](http://facebook.github.io/react/docs/two-way-binding-helpers.html) is an easy way to express two-way data binding in React. | ||
| * | ||
| * React-binding comes with utility [Binder](https://github.com/rsamec/react-binding) for two-way binding that supports binding to | ||
| * | ||
| * + object properties with path expression (dot notation) | ||
| * + this.bindToState("data","Employee.FirstName"); | ||
| * + this.bindToState("data","Employee.Contact.Email"); | ||
| * + complex objects (json) with nested properties | ||
| * + this.bindTo(employee,"FirstName"); | ||
| * + this.bindTo(employee,"Contact.Email"); | ||
| * + collection-based structures - arrays and lists | ||
| * + model={this.bindTo(employee,"FirstName")} | ||
| * + this.props.model.items.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| * + this.props.model.add() | ||
| * + this.props.model.remove(item) | ||
| * + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| * + valueLink={this.bindTo(employee,"FirstName")} | ||
| * + enables binding with value converters | ||
| * + supports both directions - format (toView) and parse (fromView) | ||
| * + support for converter parameter - valueLink={this.bindToState("data", "Duration.From",converter, "DD.MM.YYYY")} | ||
| * + converter parameter can be data-bound - valueLink={this.bindToState("data", "Duration.From",converter, this.state.format)} | ||
| * + usable with any css frameworks - | ||
| * + react-bootstrap | ||
| * + material-ui | ||
| * | ||
| */ | ||
| export default class Binder { | ||
| static createStateKeySetter(component: any, key: any): (value?: any) => void; | ||
| /** | ||
| * It enables to bind to object property with path expression | ||
| * + using [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + without [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <TextBoxInput model={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * ``` js | ||
| * var TextBoxInput = React.createClass({ | ||
| * render: function() { | ||
| * var valueModel = this.props.model; | ||
| * var handleChange = function(e){ | ||
| * valueModel.value = e.target.value; | ||
| * } | ||
| * return ( | ||
| * <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| * )} | ||
| * }); | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) | ||
| * @param path - expression to bind to property | ||
| * @param converter {DataBinding.IValueConverter} - value converter | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathObjectBinding} | ||
| */ | ||
| static bindToState(component: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): IPathObjectBinding; | ||
| /** | ||
| * It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| * | ||
| * + binding to state at root level | ||
| * | ||
| * ``` js | ||
| * <PersonComponent personModel={this.bindToState("data","Employee")} /> | ||
| * <PersonComponent personModel={this.bindToState("data","Deputy")} /> | ||
| * ``` | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + reuse bindings in component | ||
| * | ||
| * ``` js | ||
| * var PersonComponent = React.createClass({ | ||
| * mixins:[BindToMixin], | ||
| * render: function() { | ||
| * return ( | ||
| * <div> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"FirstName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"LastName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * </div> | ||
| * ); | ||
| * } | ||
| * }); | ||
| * | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property | ||
| * @param converter - value converter {DataBinding.IValueConverter} | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): IPathObjectBinding; | ||
| /** | ||
| * It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| * | ||
| * + binding to array | ||
| * | ||
| * ``` js | ||
| * <HobbyList model={this.bindArrayToState("data","Hobbies")} /> | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) - it must be array | ||
| * @param path - expression to array to bind to property | ||
| * @returns {DataBinding.ArrayObjectBinding} | ||
| */ | ||
| static bindArrayToState(component: any, key: string, path?: string): ArrayObjectBinding; | ||
| /** | ||
| * It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindArrayTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property - relative path from parent | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| export interface BinderStatic { | ||
| bindToState?(data: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding; | ||
| bindTo(parent: any, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding; | ||
| bindArrayToState?(data: any, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding; | ||
| bindArrayTo(parent: any, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding; | ||
| } | ||
| export interface Binding { | ||
| path?: string; | ||
| parent: Binding; | ||
| root: Binding; | ||
| } | ||
| export interface ObjectBinding extends Binding { | ||
| value: any; | ||
| } | ||
| export interface ArrayBinding extends Binding { | ||
| items: Array<ObjectBinding>; | ||
| add(defautItem?: any): any; | ||
| remove(itemToRemove: any): any; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any; | ||
| move(x: number, y: number): any; | ||
| } | ||
| /**x` | ||
| * Two-way data binding for React. | ||
| */ | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export interface IPathObjectBinder { | ||
| /** | ||
| It gets value at the passed path expression. | ||
| */ | ||
| getValue(path?: string): any; | ||
| /** | ||
| It sets the passed value at the passed path. | ||
| */ | ||
| setValue(path: string, value: any): any; | ||
| subscribe(fce: any): void; | ||
| } | ||
| /** | ||
| It represents change notification function. It is called whenever there is a change. | ||
| */ | ||
| export interface INotifyChange { | ||
| (any?: any): void; | ||
| } | ||
| /** | ||
| It represents change notifikcation function with changed value. It supports valueLink interface | ||
| */ | ||
| export interface IRequestChange { | ||
| (any: any): void; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export interface IPathObjectBinding extends ObjectBinding { | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| notifyChange?: INotifyChange; | ||
| requestChange?: IRequestChange; | ||
| valueConverter?: IValueConverter; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export declare class PathObjectBinding implements IPathObjectBinding { | ||
| sourceObject: any; | ||
| provider: (data) => IPathObjectBinder; | ||
| path: string; | ||
| notifyChange: INotifyChange; | ||
| valueConverter: IValueConverter; | ||
| parentNode: Binding; | ||
| source: IPathObjectBinder; | ||
| constructor(sourceObject: any, provider: (data) => IPathObjectBinder, path?: string, notifyChange?: INotifyChange, valueConverter?: IValueConverter, parentNode?: Binding); | ||
| requestChange: IRequestChange; | ||
| root: Binding; | ||
| parent: Binding; | ||
| value: any; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export declare class ArrayObjectBinding implements ArrayBinding { | ||
| sourceObject: any; | ||
| provider: (data) => IPathObjectBinder; | ||
| path: string; | ||
| notifyChange: INotifyChange; | ||
| valueConverter: IValueConverter; | ||
| source: IPathObjectBinder; | ||
| constructor(sourceObject: any, provider: (data) => IPathObjectBinder, path?: string, notifyChange?: INotifyChange, valueConverter?: IValueConverter); | ||
| parent: ArrayBinding; | ||
| root: ArrayBinding; | ||
| items: Array<IPathObjectBinding>; | ||
| add(defaultItem?: any): void; | ||
| remove(itemToRemove: any): void; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any; | ||
| move(x: number, y: number): void; | ||
| } | ||
| /** | ||
| It represents binding to array using relative path to parent object. | ||
| */ | ||
| export declare class ArrayParentBinding implements ArrayBinding { | ||
| private parentBinding; | ||
| relativePath: string; | ||
| valueConverter: IValueConverter; | ||
| constructor(parentBinding: IPathObjectBinding, relativePath?: string, valueConverter?: IValueConverter); | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| root: Binding; | ||
| parent: Binding; | ||
| notifyChange: INotifyChange; | ||
| path: string; | ||
| private getItems(); | ||
| items: Array<IPathObjectBinding>; | ||
| add(defaultItem?: any): void; | ||
| remove(itemToRemove: any): void; | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any): any[]; | ||
| move(x: any, y: any): void; | ||
| } | ||
| /** | ||
| It represents binding to relative path for parent object. | ||
| */ | ||
| export declare class PathParentBinding implements IPathObjectBinding { | ||
| private parentBinding; | ||
| relativePath: any; | ||
| valueConverter: IValueConverter; | ||
| constructor(parentBinding: IPathObjectBinding, relativePath: any, valueConverter?: IValueConverter); | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| root: Binding; | ||
| parent: Binding; | ||
| notifyChange: INotifyChange; | ||
| requestChange: IRequestChange; | ||
| path: string; | ||
| value: any; | ||
| } | ||
| /** | ||
| * Provides a way to apply custom logic to a binding. | ||
| * It enables to make bi-directional convertions between source (data) and target (view) binding. | ||
| * | ||
| * + apply various formats to values | ||
| * + parse values from user input | ||
| */ | ||
| export interface IValueConverter { | ||
| /** | ||
| * Convert value into another value before return binding getter. Typically from model(data) to view. | ||
| * @param value - source binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| format?(value: any, parameters?: any): any; | ||
| /** | ||
| * Convert value into another value before call binding setter. Typically from view to model(data). | ||
| * @param value - target binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| parse?(value: any, parameters?: any): any; | ||
| } | ||
| export declare class CurryConverter implements IValueConverter { | ||
| private formatFce; | ||
| private parseFce; | ||
| constructor(converter: IValueConverter, args: any); | ||
| private curryParameters(fn, args); | ||
| format(value: any): any; | ||
| parse(value: any): any; | ||
| } |
| export default class Binder { | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class FreezerPathObjectBinder implements IPathObjectBinder { | ||
| private source; | ||
| private freezer; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path?: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
| export default class Binder { | ||
| static bindTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| static bindArrayTo(parent: any, path?: string, converter?: any, converterParams?: any): any; | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class MobxPathObjectBinder implements IPathObjectBinder { | ||
| private mobxSource; | ||
| private current; | ||
| private previous; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private setValueAsObservable(parent, property, value?); | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class PathObjectBinder implements IPathObjectBinder { | ||
| private source; | ||
| constructor(source: any); | ||
| subscribe(updateFce: any): void; | ||
| getValue(path: string): any; | ||
| setValue(path: string, value: string): void; | ||
| private getParent(path); | ||
| static getProperty(path: any): string; | ||
| private string_to_ref(obj, s); | ||
| } |
| var PlainObjectProvider_1 = require('./PlainObjectProvider'); | ||
| var DataBinding_1 = require('./DataBinding'); | ||
| var BinderCore = (function () { | ||
| function BinderCore() { | ||
| } | ||
| BinderCore.bindTo = function (type, parent, path, converter, converterParams) { | ||
| var converter = converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof DataBinding_1.PathObjectBinding || parent instanceof DataBinding_1.PathParentBinding) ? new DataBinding_1.PathParentBinding(parent, path, converter) : new DataBinding_1.PathObjectBinding(parent, function (data) { return new type(data); }, path, converter); | ||
| }; | ||
| BinderCore.bindArrayTo = function (type, parent, path, converter, converterParams) { | ||
| var converter = converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof DataBinding_1.PathObjectBinding || parent instanceof DataBinding_1.PathParentBinding) ? new DataBinding_1.ArrayParentBinding(parent, path, converter) : new DataBinding_1.ArrayObjectBinding(parent, function (data) { return new type(data); }, path, converter); | ||
| }; | ||
| return BinderCore; | ||
| })(); | ||
| exports.BinderCore = BinderCore; | ||
| /** | ||
| * React [LinkedStateMixin](http://facebook.github.io/react/docs/two-way-binding-helpers.html) is an easy way to express two-way data binding in React. | ||
| * | ||
| * React-binding comes with utility [Binder](https://github.com/rsamec/react-binding) for two-way binding that supports binding to | ||
| * | ||
| * + object properties with path expression (dot notation) | ||
| * + this.bindToState("data","Employee.FirstName"); | ||
| * + this.bindToState("data","Employee.Contact.Email"); | ||
| * + complex objects (json) with nested properties | ||
| * + this.bindTo(employee,"FirstName"); | ||
| * + this.bindTo(employee,"Contact.Email"); | ||
| * + collection-based structures - arrays and lists | ||
| * + model={this.bindTo(employee,"FirstName")} | ||
| * + this.props.model.items.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| * + this.props.model.add() | ||
| * + this.props.model.remove(item) | ||
| * + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| * + valueLink={this.bindTo(employee,"FirstName")} | ||
| * + enables binding with value converters | ||
| * + supports both directions - format (toView) and parse (fromView) | ||
| * + support for converter parameter - valueLink={this.bindToState("data", "Duration.From",converter, "DD.MM.YYYY")} | ||
| * + converter parameter can be data-bound - valueLink={this.bindToState("data", "Duration.From",converter, this.state.format)} | ||
| * + usable with any css frameworks - | ||
| * + react-bootstrap | ||
| * + material-ui | ||
| * | ||
| */ | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.createStateKeySetter = function (component, key) { | ||
| var partialState = {}; | ||
| return function (value) { | ||
| partialState[key] = (value !== undefined) ? value : component.state[key]; | ||
| component.setState(partialState); | ||
| }; | ||
| }; | ||
| /** | ||
| * It enables to bind to object property with path expression | ||
| * + using [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + without [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <TextBoxInput model={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * ``` js | ||
| * var TextBoxInput = React.createClass({ | ||
| * render: function() { | ||
| * var valueModel = this.props.model; | ||
| * var handleChange = function(e){ | ||
| * valueModel.value = e.target.value; | ||
| * } | ||
| * return ( | ||
| * <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| * )} | ||
| * }); | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) | ||
| * @param path - expression to bind to property | ||
| * @param converter {DataBinding.IValueConverter} - value converter | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathObjectBinding} | ||
| */ | ||
| Binder.bindToState = function (component, key, path, converter, converterParams) { | ||
| return new DataBinding_1.PathObjectBinding(component["state"][key], function (data) { return new PlainObjectProvider_1.default(data); }, path, Binder.createStateKeySetter(component, key), converterParams !== undefined ? new DataBinding_1.CurryConverter(converter, converterParams) : converter); | ||
| }; | ||
| /** | ||
| * It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| * | ||
| * + binding to state at root level | ||
| * | ||
| * ``` js | ||
| * <PersonComponent personModel={this.bindToState("data","Employee")} /> | ||
| * <PersonComponent personModel={this.bindToState("data","Deputy")} /> | ||
| * ``` | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + reuse bindings in component | ||
| * | ||
| * ``` js | ||
| * var PersonComponent = React.createClass({ | ||
| * mixins:[BindToMixin], | ||
| * render: function() { | ||
| * return ( | ||
| * <div> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"FirstName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"LastName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * </div> | ||
| * ); | ||
| * } | ||
| * }); | ||
| * | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property | ||
| * @param converter - value converter {DataBinding.IValueConverter} | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return BinderCore.bindTo(PlainObjectProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| /** | ||
| * It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| * | ||
| * + binding to array | ||
| * | ||
| * ``` js | ||
| * <HobbyList model={this.bindArrayToState("data","Hobbies")} /> | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) - it must be array | ||
| * @param path - expression to array to bind to property | ||
| * @returns {DataBinding.ArrayObjectBinding} | ||
| */ | ||
| Binder.bindArrayToState = function (component, key, path) { | ||
| return new DataBinding_1.ArrayObjectBinding(component["state"][key], function (data) { return new PlainObjectProvider_1.default(data); }, path, Binder.createStateKeySetter(component, key)); | ||
| }; | ||
| /** | ||
| * It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindArrayTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property - relative path from parent | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return BinderCore.bindArrayTo(PlainObjectProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; | ||
| //export default Binder; |
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| var PathObjectBinding = (function () { | ||
| function PathObjectBinding(sourceObject, provider, path, notifyChange, valueConverter, parentNode) { | ||
| this.sourceObject = sourceObject; | ||
| this.provider = provider; | ||
| this.path = path; | ||
| this.notifyChange = notifyChange; | ||
| this.valueConverter = valueConverter; | ||
| this.parentNode = parentNode; | ||
| this.source = provider(sourceObject); | ||
| } | ||
| Object.defineProperty(PathObjectBinding.prototype, "requestChange", { | ||
| get: function () { | ||
| var _this = this; | ||
| return function (value) { _this.value = value; }; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentNode !== undefined ? this.parentNode.root : this; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentNode !== undefined ? this.parentNode : undefined; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathObjectBinding.prototype, "value", { | ||
| get: function () { | ||
| var value = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }, | ||
| set: function (value) { | ||
| var previousValue = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| //check if the value is really changed - strict equality | ||
| if (previousValue !== undefined && previousValue === convertedValueToBeSet) | ||
| return; | ||
| if (this.path === undefined) { | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(convertedValueToBeSet); | ||
| } | ||
| else { | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| } | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| return PathObjectBinding; | ||
| })(); | ||
| exports.PathObjectBinding = PathObjectBinding; | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| var ArrayObjectBinding = (function () { | ||
| function ArrayObjectBinding(sourceObject, provider, path, notifyChange, valueConverter) { | ||
| this.sourceObject = sourceObject; | ||
| this.provider = provider; | ||
| this.path = path; | ||
| this.notifyChange = notifyChange; | ||
| this.valueConverter = valueConverter; | ||
| this.source = provider(sourceObject); | ||
| } | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "parent", { | ||
| get: function () { | ||
| return undefined; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "root", { | ||
| get: function () { | ||
| return this; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayObjectBinding.prototype, "items", { | ||
| get: function () { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return []; | ||
| return items.map(function (item) { | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange, undefined, this); | ||
| }, this); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayObjectBinding.prototype.add = function (defaultItem) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) | ||
| defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.remove = function (itemToRemove) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) | ||
| return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.splice = function (start, deleteCount, elementsToAdd) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| }; | ||
| ArrayObjectBinding.prototype.move = function (x, y) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) | ||
| return; | ||
| //@TODO: use more effective way to clone array | ||
| var itemsCloned = JSON.parse(JSON.stringify(items)); | ||
| itemsCloned.splice(y, 0, itemsCloned.splice(x, 1)[0]); | ||
| this.source.setValue(this.path, itemsCloned); | ||
| }; | ||
| return ArrayObjectBinding; | ||
| })(); | ||
| exports.ArrayObjectBinding = ArrayObjectBinding; | ||
| /** | ||
| It represents binding to array using relative path to parent object. | ||
| */ | ||
| var ArrayParentBinding = (function () { | ||
| function ArrayParentBinding(parentBinding, relativePath, valueConverter) { | ||
| this.parentBinding = parentBinding; | ||
| this.relativePath = relativePath; | ||
| this.valueConverter = valueConverter; | ||
| } | ||
| Object.defineProperty(ArrayParentBinding.prototype, "source", { | ||
| //wrapped properties - delegate call to parent | ||
| get: function () { | ||
| return this.parentBinding.source; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "provider", { | ||
| get: function () { | ||
| return this.parentBinding.provider; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentBinding.root; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentBinding; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "notifyChange", { | ||
| get: function () { | ||
| return this.parentBinding.notifyChange; | ||
| }, | ||
| set: function (value) { | ||
| this.parentBinding.notifyChange = value; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(ArrayParentBinding.prototype, "path", { | ||
| //concatenate path | ||
| get: function () { | ||
| if (this.parentBinding.path === undefined) | ||
| return this.relativePath; | ||
| if (this.relativePath === undefined) | ||
| return this.parentBinding.path; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayParentBinding.prototype.getItems = function () { | ||
| if (this.source === undefined) | ||
| return; | ||
| var value = this.source.getValue(this.path); | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }; | ||
| Object.defineProperty(ArrayParentBinding.prototype, "items", { | ||
| get: function () { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return []; | ||
| return items.map(function (item) { | ||
| //item._parentBinding = this; | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange, undefined, this); | ||
| }, this); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| ArrayParentBinding.prototype.add = function (defaultItem) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) | ||
| defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.remove = function (itemToRemove) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) | ||
| return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.splice = function (start, deleteCount, elementsToAdd) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) | ||
| return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| }; | ||
| ArrayParentBinding.prototype.move = function (x, y) { | ||
| this.splice(y, 0, this.splice(x, 1)[0]); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }; | ||
| return ArrayParentBinding; | ||
| })(); | ||
| exports.ArrayParentBinding = ArrayParentBinding; | ||
| /** | ||
| It represents binding to relative path for parent object. | ||
| */ | ||
| var PathParentBinding = (function () { | ||
| //converter:any; | ||
| function PathParentBinding(parentBinding, relativePath, valueConverter) { | ||
| this.parentBinding = parentBinding; | ||
| this.relativePath = relativePath; | ||
| this.valueConverter = valueConverter; | ||
| //this.converter.format = Utils.partial(valueConverter,.partial() | ||
| } | ||
| Object.defineProperty(PathParentBinding.prototype, "source", { | ||
| //wrapped properties - delegate call to parent | ||
| get: function () { | ||
| return this.parentBinding.source; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "provider", { | ||
| get: function () { | ||
| return this.parentBinding.provider; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "root", { | ||
| get: function () { | ||
| return this.parentBinding.root; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "parent", { | ||
| get: function () { | ||
| return this.parentBinding; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "notifyChange", { | ||
| get: function () { | ||
| return this.parentBinding.notifyChange; | ||
| }, | ||
| set: function (value) { | ||
| this.parentBinding.notifyChange = value; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "requestChange", { | ||
| get: function () { | ||
| var _this = this; | ||
| return function (value) { | ||
| _this.value = value; | ||
| }; | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "path", { | ||
| //concatenate path | ||
| get: function () { | ||
| if (this.parentBinding.path === undefined) | ||
| return this.relativePath; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| Object.defineProperty(PathParentBinding.prototype, "value", { | ||
| get: function () { | ||
| var value = this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| }, | ||
| set: function (value) { | ||
| //check if the value is really changed - strict equality | ||
| var previousValue = this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| if (previousValue === convertedValueToBeSet) | ||
| return; | ||
| //set value - optional call converter | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) | ||
| this.notifyChange(); | ||
| }, | ||
| enumerable: true, | ||
| configurable: true | ||
| }); | ||
| return PathParentBinding; | ||
| })(); | ||
| exports.PathParentBinding = PathParentBinding; | ||
| var CurryConverter = (function () { | ||
| function CurryConverter(converter, args) { | ||
| this.formatFce = this.curryParameters(converter.format, [args]); | ||
| this.parseFce = this.curryParameters(converter.parse, [args]); | ||
| } | ||
| CurryConverter.prototype.curryParameters = function (fn, args) { | ||
| return function () { | ||
| return fn.apply(this, Array.prototype.slice.call(arguments).concat(args)); | ||
| }; | ||
| }; | ||
| CurryConverter.prototype.format = function (value) { | ||
| return this.formatFce(value); | ||
| }; | ||
| CurryConverter.prototype.parse = function (value) { | ||
| return this.parseFce(value); | ||
| }; | ||
| return CurryConverter; | ||
| })(); | ||
| exports.CurryConverter = CurryConverter; |
| var FreezerProvider_1 = require('./FreezerProvider'); | ||
| var Binder_1 = require('./Binder'); | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindTo(FreezerProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindArrayTo(FreezerProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; |
| var Freezer = require('freezer-js'); | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var FreezerPathObjectBinder = (function () { | ||
| function FreezerPathObjectBinder(source) { | ||
| this.source = source; | ||
| this.freezer = new Freezer(source); | ||
| } | ||
| FreezerPathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| this.freezer.on('update', function (state, prevState) { | ||
| if (updateFce !== undefined) | ||
| updateFce(state, prevState); | ||
| }); | ||
| }; | ||
| FreezerPathObjectBinder.prototype.getValue = function (path) { | ||
| if (path === undefined) | ||
| return this.freezer.get(); | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| }; | ||
| FreezerPathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| parent.set(property, value); | ||
| }; | ||
| FreezerPathObjectBinder.prototype.getParent = function (path) { | ||
| var state = this.freezer.get(); | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(state, path.substring(0, last)) : state; | ||
| }; | ||
| FreezerPathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| FreezerPathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj.set(parts[0], {}); | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return FreezerPathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = FreezerPathObjectBinder; |
| var MobxProvider_1 = require('./MobxProvider'); | ||
| var Binder_1 = require('./Binder'); | ||
| var Binder = (function () { | ||
| function Binder() { | ||
| } | ||
| Binder.bindTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindTo(MobxProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| Binder.bindArrayTo = function (parent, path, converter, converterParams) { | ||
| return Binder_1.BinderCore.bindArrayTo(MobxProvider_1.default, parent, path, converter, converterParams); | ||
| }; | ||
| return Binder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = Binder; |
| var mobx_1 = require('mobx'); | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var MobxPathObjectBinder = (function () { | ||
| function MobxPathObjectBinder(source) { | ||
| var _this = this; | ||
| this.mobxSource = mobx_1.observable(source); | ||
| this.current = mobx_1.computed(function () { return JSON.stringify(_this.mobxSource); }); | ||
| //console.log('init'); | ||
| // autorun(() => { | ||
| // console.log(this.json.get());//'safda'); | ||
| // //if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // }); | ||
| } | ||
| MobxPathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| var _this = this; | ||
| var previousState; | ||
| if (updateFce !== undefined) | ||
| mobx_1.autorun(function () { | ||
| var current = _this.current.get(); | ||
| updateFce(current, _this.previous); | ||
| _this.previous = current; | ||
| }); | ||
| //if (updateFce!==undefined) autorun(updateFce); | ||
| }; | ||
| MobxPathObjectBinder.prototype.getValue = function (path) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| if (path === undefined) | ||
| return parent; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| var value = parent[property]; | ||
| if (value === undefined && !parent.hasOwnProperty(property)) { | ||
| this.setValueAsObservable(parent, property); | ||
| } | ||
| return parent[property]; | ||
| }; | ||
| MobxPathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| //parent[property] = observable(value); | ||
| if (mobx_1.isObservable(parent, property)) { | ||
| parent[property] = value; | ||
| return; | ||
| } | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| mobx_1.extendObservable(parent, newProps); | ||
| //console.log(parent[property]); | ||
| }; | ||
| MobxPathObjectBinder.prototype.setValueAsObservable = function (parent, property, value) { | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| mobx_1.extendObservable(parent, newProps); | ||
| }; | ||
| MobxPathObjectBinder.prototype.getParent = function (path) { | ||
| if (path === undefined) | ||
| return this.mobxSource; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.mobxSource, path.substring(0, last)) : this.mobxSource; | ||
| }; | ||
| MobxPathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| MobxPathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return MobxPathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = MobxPathObjectBinder; |
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| var PathObjectBinder = (function () { | ||
| function PathObjectBinder(source) { | ||
| this.source = source; | ||
| } | ||
| PathObjectBinder.prototype.subscribe = function (updateFce) { | ||
| // this.freezer.on('update',function(state,prevState){ | ||
| // if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // ); | ||
| }; | ||
| PathObjectBinder.prototype.getValue = function (path) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| if (path === undefined) | ||
| return parent; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| }; | ||
| PathObjectBinder.prototype.setValue = function (path, value) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) | ||
| return; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| parent[property] = value; | ||
| }; | ||
| PathObjectBinder.prototype.getParent = function (path) { | ||
| if (path === undefined) | ||
| return this.source; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.source, path.substring(0, last)) : this.source; | ||
| }; | ||
| PathObjectBinder.getProperty = function (path) { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| }; | ||
| PathObjectBinder.prototype.string_to_ref = function (obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) | ||
| newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj; | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| }; | ||
| return PathObjectBinder; | ||
| })(); | ||
| Object.defineProperty(exports, "__esModule", { value: true }); | ||
| exports.default = PathObjectBinder; |
| { | ||
| "name": "react-binding", | ||
| "version": "0.8.0", | ||
| "description": "Binder - react two-way data binding for complex objects and arrays.", | ||
| "main": "lib/Binder.js", | ||
| "directories": { | ||
| "test": "test" | ||
| }, | ||
| "scripts": { | ||
| "test": "mocha -R spec ./test" | ||
| }, | ||
| "repository": { | ||
| "type": "git", | ||
| "url": "https://github.com/rsamec/react-binding" | ||
| }, | ||
| "keywords": [ | ||
| "react", | ||
| "binding" | ||
| ], | ||
| "author": "Roman Samec <roman.samec2@gmail.com>", | ||
| "license": "MIT", | ||
| "bugs": { | ||
| "url": "https://github.com/rsamec/react-binding/issues" | ||
| }, | ||
| "homepage": "https://github.com/rsamec/react-binding", | ||
| "devDependencies": {}, | ||
| "dependencies": {} | ||
| } |
Sorry, the diff of this file is too big to display
| !function(t){if("object"==typeof exports&&"undefined"!=typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var e;e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this,e.Binder=t()}}(function(){return function t(e,r,n){function i(u,s){if(!r[u]){if(!e[u]){var f="function"==typeof require&&require;if(!s&&f)return f(u,!0);if(o)return o(u,!0);var a=new Error("Cannot find module '"+u+"'");throw a.code="MODULE_NOT_FOUND",a}var h=r[u]={exports:{}};e[u][0].call(h.exports,function(t){var r=e[u][1][t];return i(r?r:t)},h,h.exports,t,e,r,n)}return r[u].exports}for(var o="function"==typeof require&&require,u=0;u<n.length;u++)i(n[u]);return i}({1:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";function h(t){var e=t.length;if(e%4>0)throw new Error("Invalid string. Length must be a multiple of 4");return"="===t[e-2]?2:"="===t[e-1]?1:0}function c(t){return 3*t.length/4-h(t)}function p(t){var e,r,n,i,o,u,s=t.length;o=h(t),u=new b(3*s/4-o),n=o>0?s-4:s;var f=0;for(e=0,r=0;n>e;e+=4,r+=3)i=v[t.charCodeAt(e)]<<18|v[t.charCodeAt(e+1)]<<12|v[t.charCodeAt(e+2)]<<6|v[t.charCodeAt(e+3)],u[f++]=i>>16&255,u[f++]=i>>8&255,u[f++]=255&i;return 2===o?(i=v[t.charCodeAt(e)]<<2|v[t.charCodeAt(e+1)]>>4,u[f++]=255&i):1===o&&(i=v[t.charCodeAt(e)]<<10|v[t.charCodeAt(e+1)]<<4|v[t.charCodeAt(e+2)]>>2,u[f++]=i>>8&255,u[f++]=255&i),u}function l(t){return y[t>>18&63]+y[t>>12&63]+y[t>>6&63]+y[63&t]}function g(t,e,r){for(var n,i=[],o=e;r>o;o+=3)n=(t[o]<<16)+(t[o+1]<<8)+t[o+2],i.push(l(n));return i.join("")}function d(t){for(var e,r=t.length,n=r%3,i="",o=[],u=16383,s=0,f=r-n;f>s;s+=u)o.push(g(t,s,s+u>f?f:s+u));return 1===n?(e=t[r-1],i+=y[e>>2],i+=y[e<<4&63],i+="=="):2===n&&(e=(t[r-2]<<8)+t[r-1],i+=y[e>>10],i+=y[e>>4&63],i+=y[e<<2&63],i+="="),o.push(i),o.join("")}r.byteLength=c,r.toByteArray=p,r.fromByteArray=d;for(var y=[],v=[],b="undefined"!=typeof Uint8Array?Uint8Array:Array,w="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",m=0,P=w.length;P>m;++m)y[m]=w[m],v[w.charCodeAt(m)]=m;v["-".charCodeAt(0)]=62,v["_".charCodeAt(0)]=63}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\base64-js\\index.js","/node_modules\\base64-js")},{_process:5,buffer:2}],2:[function(t,e,r){(function(e,n,i,o,u,s,f,a,h){"use strict";function c(){try{var t=new Uint8Array(1);return t.__proto__={__proto__:Uint8Array.prototype,foo:function(){return 42}},42===t.foo()&&"function"==typeof t.subarray&&0===t.subarray(1,1).byteLength}catch(e){return!1}}function p(){return i.TYPED_ARRAY_SUPPORT?2147483647:1073741823}function l(t,e){if(p()<e)throw new RangeError("Invalid typed array length");return i.TYPED_ARRAY_SUPPORT?(t=new Uint8Array(e),t.__proto__=i.prototype):(null===t&&(t=new i(e)),t.length=e),t}function i(t,e,r){if(!(i.TYPED_ARRAY_SUPPORT||this instanceof i))return new i(t,e,r);if("number"==typeof t){if("string"==typeof e)throw new Error("If encoding is specified then the first argument must be a string");return v(this,t)}return g(this,t,e,r)}function g(t,e,r,n){if("number"==typeof e)throw new TypeError('"value" argument must not be a number');return"undefined"!=typeof ArrayBuffer&&e instanceof ArrayBuffer?m(t,e,r,n):"string"==typeof e?b(t,e,r):P(t,e)}function d(t){if("number"!=typeof t)throw new TypeError('"size" argument must be a number');if(0>t)throw new RangeError('"size" argument must not be negative')}function y(t,e,r,n){return d(e),0>=e?l(t,e):void 0!==r?"string"==typeof n?l(t,e).fill(r,n):l(t,e).fill(r):l(t,e)}function v(t,e){if(d(e),t=l(t,0>e?0:0|_(e)),!i.TYPED_ARRAY_SUPPORT)for(var r=0;e>r;++r)t[r]=0;return t}function b(t,e,r){if(("string"!=typeof r||""===r)&&(r="utf8"),!i.isEncoding(r))throw new TypeError('"encoding" must be a valid string encoding');var n=0|B(e,r);t=l(t,n);var o=t.write(e,r);return o!==n&&(t=t.slice(0,o)),t}function w(t,e){var r=e.length<0?0:0|_(e.length);t=l(t,r);for(var n=0;r>n;n+=1)t[n]=255&e[n];return t}function m(t,e,r,n){if(e.byteLength,0>r||e.byteLength<r)throw new RangeError("'offset' is out of bounds");if(e.byteLength<r+(n||0))throw new RangeError("'length' is out of bounds");return e=void 0===r&&void 0===n?new Uint8Array(e):void 0===n?new Uint8Array(e,r):new Uint8Array(e,r,n),i.TYPED_ARRAY_SUPPORT?(t=e,t.__proto__=i.prototype):t=w(t,e),t}function P(t,e){if(i.isBuffer(e)){var r=0|_(e.length);return t=l(t,r),0===t.length?t:(e.copy(t,0,0,r),t)}if(e){if("undefined"!=typeof ArrayBuffer&&e.buffer instanceof ArrayBuffer||"length"in e)return"number"!=typeof e.length||nt(e.length)?l(t,0):w(t,e);if("Buffer"===e.type&&ut(e.data))return w(t,e.data)}throw new TypeError("First argument must be a string, Buffer, ArrayBuffer, Array, or array-like object.")}function _(t){if(t>=p())throw new RangeError("Attempt to allocate Buffer larger than maximum size: 0x"+p().toString(16)+" bytes");return 0|t}function A(t){return+t!=t&&(t=0),i.alloc(+t)}function B(t,e){if(i.isBuffer(t))return t.length;if("undefined"!=typeof ArrayBuffer&&"function"==typeof ArrayBuffer.isView&&(ArrayBuffer.isView(t)||t instanceof ArrayBuffer))return t.byteLength;"string"!=typeof t&&(t=""+t);var r=t.length;if(0===r)return 0;for(var n=!1;;)switch(e){case"ascii":case"latin1":case"binary":return r;case"utf8":case"utf-8":case void 0:return W(t).length;case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return 2*r;case"hex":return r>>>1;case"base64":return et(t).length;default:if(n)return W(t).length;e=(""+e).toLowerCase(),n=!0}}function E(t,e,r){var n=!1;if((void 0===e||0>e)&&(e=0),e>this.length)return"";if((void 0===r||r>this.length)&&(r=this.length),0>=r)return"";if(r>>>=0,e>>>=0,e>=r)return"";for(t||(t="utf8");;)switch(t){case"hex":return N(this,e,r);case"utf8":case"utf-8":return L(this,e,r);case"ascii":return D(this,e,r);case"latin1":case"binary":return V(this,e,r);case"base64":return x(this,e,r);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return k(this,e,r);default:if(n)throw new TypeError("Unknown encoding: "+t);t=(t+"").toLowerCase(),n=!0}}function T(t,e,r){var n=t[e];t[e]=t[r],t[r]=n}function R(t,e,r,n,o){if(0===t.length)return-1;if("string"==typeof r?(n=r,r=0):r>2147483647?r=2147483647:-2147483648>r&&(r=-2147483648),r=+r,isNaN(r)&&(r=o?0:t.length-1),0>r&&(r=t.length+r),r>=t.length){if(o)return-1;r=t.length-1}else if(0>r){if(!o)return-1;r=0}if("string"==typeof e&&(e=i.from(e,n)),i.isBuffer(e))return 0===e.length?-1:C(t,e,r,n,o);if("number"==typeof e)return e=255&e,i.TYPED_ARRAY_SUPPORT&&"function"==typeof Uint8Array.prototype.indexOf?o?Uint8Array.prototype.indexOf.call(t,e,r):Uint8Array.prototype.lastIndexOf.call(t,e,r):C(t,[e],r,n,o);throw new TypeError("val must be string, number or Buffer")}function C(t,e,r,n,i){function o(t,e){return 1===u?t[e]:t.readUInt16BE(e*u)}var u=1,s=t.length,f=e.length;if(void 0!==n&&(n=String(n).toLowerCase(),"ucs2"===n||"ucs-2"===n||"utf16le"===n||"utf-16le"===n)){if(t.length<2||e.length<2)return-1;u=2,s/=2,f/=2,r/=2}var a;if(i){var h=-1;for(a=r;s>a;a++)if(o(t,a)===o(e,-1===h?0:a-h)){if(-1===h&&(h=a),a-h+1===f)return h*u}else-1!==h&&(a-=a-h),h=-1}else for(r+f>s&&(r=s-f),a=r;a>=0;a--){for(var c=!0,p=0;f>p;p++)if(o(t,a+p)!==o(e,p)){c=!1;break}if(c)return a}return-1}function O(t,e,r,n){r=Number(r)||0;var i=t.length-r;n?(n=Number(n),n>i&&(n=i)):n=i;var o=e.length;if(o%2!==0)throw new TypeError("Invalid hex string");n>o/2&&(n=o/2);for(var u=0;n>u;++u){var s=parseInt(e.substr(2*u,2),16);if(isNaN(s))return u;t[r+u]=s}return u}function S(t,e,r,n){return rt(W(e,t.length-r),t,r,n)}function U(t,e,r,n){return rt($(e),t,r,n)}function j(t,e,r,n){return U(t,e,r,n)}function I(t,e,r,n){return rt(et(e),t,r,n)}function Y(t,e,r,n){return rt(tt(e,t.length-r),t,r,n)}function x(t,e,r){return 0===e&&r===t.length?it.fromByteArray(t):it.fromByteArray(t.slice(e,r))}function L(t,e,r){r=Math.min(t.length,r);for(var n=[],i=e;r>i;){var o=t[i],u=null,s=o>239?4:o>223?3:o>191?2:1;if(r>=i+s){var f,a,h,c;switch(s){case 1:128>o&&(u=o);break;case 2:f=t[i+1],128===(192&f)&&(c=(31&o)<<6|63&f,c>127&&(u=c));break;case 3:f=t[i+1],a=t[i+2],128===(192&f)&&128===(192&a)&&(c=(15&o)<<12|(63&f)<<6|63&a,c>2047&&(55296>c||c>57343)&&(u=c));break;case 4:f=t[i+1],a=t[i+2],h=t[i+3],128===(192&f)&&128===(192&a)&&128===(192&h)&&(c=(15&o)<<18|(63&f)<<12|(63&a)<<6|63&h,c>65535&&1114112>c&&(u=c))}}null===u?(u=65533,s=1):u>65535&&(u-=65536,n.push(u>>>10&1023|55296),u=56320|1023&u),n.push(u),i+=s}return M(n)}function M(t){var e=t.length;if(st>=e)return String.fromCharCode.apply(String,t);for(var r="",n=0;e>n;)r+=String.fromCharCode.apply(String,t.slice(n,n+=st));return r}function D(t,e,r){var n="";r=Math.min(t.length,r);for(var i=e;r>i;++i)n+=String.fromCharCode(127&t[i]);return n}function V(t,e,r){var n="";r=Math.min(t.length,r);for(var i=e;r>i;++i)n+=String.fromCharCode(t[i]);return n}function N(t,e,r){var n=t.length;(!e||0>e)&&(e=0),(!r||0>r||r>n)&&(r=n);for(var i="",o=e;r>o;++o)i+=Q(t[o]);return i}function k(t,e,r){for(var n=t.slice(e,r),i="",o=0;o<n.length;o+=2)i+=String.fromCharCode(n[o]+256*n[o+1]);return i}function F(t,e,r){if(t%1!==0||0>t)throw new RangeError("offset is not uint");if(t+e>r)throw new RangeError("Trying to access beyond buffer length")}function z(t,e,r,n,o,u){if(!i.isBuffer(t))throw new TypeError('"buffer" argument must be a Buffer instance');if(e>o||u>e)throw new RangeError('"value" argument is out of bounds');if(r+n>t.length)throw new RangeError("Index out of range")}function q(t,e,r,n){0>e&&(e=65535+e+1);for(var i=0,o=Math.min(t.length-r,2);o>i;++i)t[r+i]=(e&255<<8*(n?i:1-i))>>>8*(n?i:1-i)}function J(t,e,r,n){0>e&&(e=4294967295+e+1);for(var i=0,o=Math.min(t.length-r,4);o>i;++i)t[r+i]=e>>>8*(n?i:3-i)&255}function K(t,e,r,n,i,o){if(r+n>t.length)throw new RangeError("Index out of range");if(0>r)throw new RangeError("Index out of range")}function X(t,e,r,n,i){return i||K(t,e,r,4,3.4028234663852886e38,-3.4028234663852886e38),ot.write(t,e,r,n,23,4),r+4}function Z(t,e,r,n,i){return i||K(t,e,r,8,1.7976931348623157e308,-1.7976931348623157e308),ot.write(t,e,r,n,52,8),r+8}function G(t){if(t=H(t).replace(ft,""),t.length<2)return"";for(;t.length%4!==0;)t+="=";return t}function H(t){return t.trim?t.trim():t.replace(/^\s+|\s+$/g,"")}function Q(t){return 16>t?"0"+t.toString(16):t.toString(16)}function W(t,e){e=e||1/0;for(var r,n=t.length,i=null,o=[],u=0;n>u;++u){if(r=t.charCodeAt(u),r>55295&&57344>r){if(!i){if(r>56319){(e-=3)>-1&&o.push(239,191,189);continue}if(u+1===n){(e-=3)>-1&&o.push(239,191,189);continue}i=r;continue}if(56320>r){(e-=3)>-1&&o.push(239,191,189),i=r;continue}r=(i-55296<<10|r-56320)+65536}else i&&(e-=3)>-1&&o.push(239,191,189);if(i=null,128>r){if((e-=1)<0)break;o.push(r)}else if(2048>r){if((e-=2)<0)break;o.push(r>>6|192,63&r|128)}else if(65536>r){if((e-=3)<0)break;o.push(r>>12|224,r>>6&63|128,63&r|128)}else{if(!(1114112>r))throw new Error("Invalid code point");if((e-=4)<0)break;o.push(r>>18|240,r>>12&63|128,r>>6&63|128,63&r|128)}}return o}function $(t){for(var e=[],r=0;r<t.length;++r)e.push(255&t.charCodeAt(r));return e}function tt(t,e){for(var r,n,i,o=[],u=0;u<t.length&&!((e-=2)<0);++u)r=t.charCodeAt(u),n=r>>8,i=r%256,o.push(i),o.push(n);return o}function et(t){return it.toByteArray(G(t))}function rt(t,e,r,n){for(var i=0;n>i&&!(i+r>=e.length||i>=t.length);++i)e[i+r]=t[i];return i}function nt(t){return t!==t}var it=t("base64-js"),ot=t("ieee754"),ut=t("isarray");r.Buffer=i,r.SlowBuffer=A,r.INSPECT_MAX_BYTES=50,i.TYPED_ARRAY_SUPPORT=void 0!==n.TYPED_ARRAY_SUPPORT?n.TYPED_ARRAY_SUPPORT:c(),r.kMaxLength=p(),i.poolSize=8192,i._augment=function(t){return t.__proto__=i.prototype,t},i.from=function(t,e,r){return g(null,t,e,r)},i.TYPED_ARRAY_SUPPORT&&(i.prototype.__proto__=Uint8Array.prototype,i.__proto__=Uint8Array,"undefined"!=typeof Symbol&&Symbol.species&&i[Symbol.species]===i&&Object.defineProperty(i,Symbol.species,{value:null,configurable:!0})),i.alloc=function(t,e,r){return y(null,t,e,r)},i.allocUnsafe=function(t){return v(null,t)},i.allocUnsafeSlow=function(t){return v(null,t)},i.isBuffer=function(t){return!(null==t||!t._isBuffer)},i.compare=function(t,e){if(!i.isBuffer(t)||!i.isBuffer(e))throw new TypeError("Arguments must be Buffers");if(t===e)return 0;for(var r=t.length,n=e.length,o=0,u=Math.min(r,n);u>o;++o)if(t[o]!==e[o]){r=t[o],n=e[o];break}return n>r?-1:r>n?1:0},i.isEncoding=function(t){switch(String(t).toLowerCase()){case"hex":case"utf8":case"utf-8":case"ascii":case"latin1":case"binary":case"base64":case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return!0;default:return!1}},i.concat=function(t,e){if(!ut(t))throw new TypeError('"list" argument must be an Array of Buffers');if(0===t.length)return i.alloc(0);var r;if(void 0===e)for(e=0,r=0;r<t.length;++r)e+=t[r].length;var n=i.allocUnsafe(e),o=0;for(r=0;r<t.length;++r){var u=t[r];if(!i.isBuffer(u))throw new TypeError('"list" argument must be an Array of Buffers');u.copy(n,o),o+=u.length}return n},i.byteLength=B,i.prototype._isBuffer=!0,i.prototype.swap16=function(){var t=this.length;if(t%2!==0)throw new RangeError("Buffer size must be a multiple of 16-bits");for(var e=0;t>e;e+=2)T(this,e,e+1);return this},i.prototype.swap32=function(){var t=this.length;if(t%4!==0)throw new RangeError("Buffer size must be a multiple of 32-bits");for(var e=0;t>e;e+=4)T(this,e,e+3),T(this,e+1,e+2);return this},i.prototype.swap64=function(){var t=this.length;if(t%8!==0)throw new RangeError("Buffer size must be a multiple of 64-bits");for(var e=0;t>e;e+=8)T(this,e,e+7),T(this,e+1,e+6),T(this,e+2,e+5),T(this,e+3,e+4);return this},i.prototype.toString=function(){var t=0|this.length;return 0===t?"":0===arguments.length?L(this,0,t):E.apply(this,arguments)},i.prototype.equals=function(t){if(!i.isBuffer(t))throw new TypeError("Argument must be a Buffer");return this===t?!0:0===i.compare(this,t)},i.prototype.inspect=function(){var t="",e=r.INSPECT_MAX_BYTES;return this.length>0&&(t=this.toString("hex",0,e).match(/.{2}/g).join(" "),this.length>e&&(t+=" ... ")),"<Buffer "+t+">"},i.prototype.compare=function(t,e,r,n,o){if(!i.isBuffer(t))throw new TypeError("Argument must be a Buffer");if(void 0===e&&(e=0),void 0===r&&(r=t?t.length:0),void 0===n&&(n=0),void 0===o&&(o=this.length),0>e||r>t.length||0>n||o>this.length)throw new RangeError("out of range index");if(n>=o&&e>=r)return 0;if(n>=o)return-1;if(e>=r)return 1;if(e>>>=0,r>>>=0,n>>>=0,o>>>=0,this===t)return 0;for(var u=o-n,s=r-e,f=Math.min(u,s),a=this.slice(n,o),h=t.slice(e,r),c=0;f>c;++c)if(a[c]!==h[c]){u=a[c],s=h[c];break}return s>u?-1:u>s?1:0},i.prototype.includes=function(t,e,r){return-1!==this.indexOf(t,e,r)},i.prototype.indexOf=function(t,e,r){return R(this,t,e,r,!0)},i.prototype.lastIndexOf=function(t,e,r){return R(this,t,e,r,!1)},i.prototype.write=function(t,e,r,n){if(void 0===e)n="utf8",r=this.length,e=0;else if(void 0===r&&"string"==typeof e)n=e,r=this.length,e=0;else{if(!isFinite(e))throw new Error("Buffer.write(string, encoding, offset[, length]) is no longer supported");e=0|e,isFinite(r)?(r=0|r,void 0===n&&(n="utf8")):(n=r,r=void 0)}var i=this.length-e;if((void 0===r||r>i)&&(r=i),t.length>0&&(0>r||0>e)||e>this.length)throw new RangeError("Attempt to write outside buffer bounds");n||(n="utf8");for(var o=!1;;)switch(n){case"hex":return O(this,t,e,r);case"utf8":case"utf-8":return S(this,t,e,r);case"ascii":return U(this,t,e,r);case"latin1":case"binary":return j(this,t,e,r);case"base64":return I(this,t,e,r);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return Y(this,t,e,r);default:if(o)throw new TypeError("Unknown encoding: "+n);n=(""+n).toLowerCase(),o=!0}},i.prototype.toJSON=function(){return{type:"Buffer",data:Array.prototype.slice.call(this._arr||this,0)}};var st=4096;i.prototype.slice=function(t,e){var r=this.length;t=~~t,e=void 0===e?r:~~e,0>t?(t+=r,0>t&&(t=0)):t>r&&(t=r),0>e?(e+=r,0>e&&(e=0)):e>r&&(e=r),t>e&&(e=t);var n;if(i.TYPED_ARRAY_SUPPORT)n=this.subarray(t,e),n.__proto__=i.prototype;else{var o=e-t;n=new i(o,void 0);for(var u=0;o>u;++u)n[u]=this[u+t]}return n},i.prototype.readUIntLE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t],i=1,o=0;++o<e&&(i*=256);)n+=this[t+o]*i;return n},i.prototype.readUIntBE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t+--e],i=1;e>0&&(i*=256);)n+=this[t+--e]*i;return n},i.prototype.readUInt8=function(t,e){return e||F(t,1,this.length),this[t]},i.prototype.readUInt16LE=function(t,e){return e||F(t,2,this.length),this[t]|this[t+1]<<8},i.prototype.readUInt16BE=function(t,e){return e||F(t,2,this.length),this[t]<<8|this[t+1]},i.prototype.readUInt32LE=function(t,e){return e||F(t,4,this.length),(this[t]|this[t+1]<<8|this[t+2]<<16)+16777216*this[t+3]},i.prototype.readUInt32BE=function(t,e){return e||F(t,4,this.length),16777216*this[t]+(this[t+1]<<16|this[t+2]<<8|this[t+3])},i.prototype.readIntLE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=this[t],i=1,o=0;++o<e&&(i*=256);)n+=this[t+o]*i;return i*=128,n>=i&&(n-=Math.pow(2,8*e)),n},i.prototype.readIntBE=function(t,e,r){t=0|t,e=0|e,r||F(t,e,this.length);for(var n=e,i=1,o=this[t+--n];n>0&&(i*=256);)o+=this[t+--n]*i;return i*=128,o>=i&&(o-=Math.pow(2,8*e)),o},i.prototype.readInt8=function(t,e){return e||F(t,1,this.length),128&this[t]?-1*(255-this[t]+1):this[t]},i.prototype.readInt16LE=function(t,e){e||F(t,2,this.length);var r=this[t]|this[t+1]<<8;return 32768&r?4294901760|r:r},i.prototype.readInt16BE=function(t,e){e||F(t,2,this.length);var r=this[t+1]|this[t]<<8;return 32768&r?4294901760|r:r},i.prototype.readInt32LE=function(t,e){return e||F(t,4,this.length),this[t]|this[t+1]<<8|this[t+2]<<16|this[t+3]<<24},i.prototype.readInt32BE=function(t,e){return e||F(t,4,this.length),this[t]<<24|this[t+1]<<16|this[t+2]<<8|this[t+3]},i.prototype.readFloatLE=function(t,e){return e||F(t,4,this.length),ot.read(this,t,!0,23,4)},i.prototype.readFloatBE=function(t,e){return e||F(t,4,this.length),ot.read(this,t,!1,23,4)},i.prototype.readDoubleLE=function(t,e){return e||F(t,8,this.length),ot.read(this,t,!0,52,8)},i.prototype.readDoubleBE=function(t,e){return e||F(t,8,this.length),ot.read(this,t,!1,52,8)},i.prototype.writeUIntLE=function(t,e,r,n){if(t=+t,e=0|e,r=0|r,!n){var i=Math.pow(2,8*r)-1;z(this,t,e,r,i,0)}var o=1,u=0;for(this[e]=255&t;++u<r&&(o*=256);)this[e+u]=t/o&255;return e+r},i.prototype.writeUIntBE=function(t,e,r,n){if(t=+t,e=0|e,r=0|r,!n){var i=Math.pow(2,8*r)-1;z(this,t,e,r,i,0)}var o=r-1,u=1;for(this[e+o]=255&t;--o>=0&&(u*=256);)this[e+o]=t/u&255;return e+r},i.prototype.writeUInt8=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,1,255,0),i.TYPED_ARRAY_SUPPORT||(t=Math.floor(t)),this[e]=255&t,e+1},i.prototype.writeUInt16LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,65535,0),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8):q(this,t,e,!0),e+2},i.prototype.writeUInt16BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,65535,0),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>8,this[e+1]=255&t):q(this,t,e,!1),e+2},i.prototype.writeUInt32LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,4294967295,0),i.TYPED_ARRAY_SUPPORT?(this[e+3]=t>>>24,this[e+2]=t>>>16,this[e+1]=t>>>8,this[e]=255&t):J(this,t,e,!0),e+4},i.prototype.writeUInt32BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,4294967295,0),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>24,this[e+1]=t>>>16,this[e+2]=t>>>8,this[e+3]=255&t):J(this,t,e,!1),e+4},i.prototype.writeIntLE=function(t,e,r,n){if(t=+t,e=0|e,!n){var i=Math.pow(2,8*r-1);z(this,t,e,r,i-1,-i)}var o=0,u=1,s=0;for(this[e]=255&t;++o<r&&(u*=256);)0>t&&0===s&&0!==this[e+o-1]&&(s=1),this[e+o]=(t/u>>0)-s&255;return e+r},i.prototype.writeIntBE=function(t,e,r,n){if(t=+t,e=0|e,!n){var i=Math.pow(2,8*r-1);z(this,t,e,r,i-1,-i)}var o=r-1,u=1,s=0;for(this[e+o]=255&t;--o>=0&&(u*=256);)0>t&&0===s&&0!==this[e+o+1]&&(s=1),this[e+o]=(t/u>>0)-s&255;return e+r},i.prototype.writeInt8=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,1,127,-128),i.TYPED_ARRAY_SUPPORT||(t=Math.floor(t)),0>t&&(t=255+t+1),this[e]=255&t,e+1},i.prototype.writeInt16LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,32767,-32768),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8):q(this,t,e,!0),e+2},i.prototype.writeInt16BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,2,32767,-32768),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>8,this[e+1]=255&t):q(this,t,e,!1),e+2},i.prototype.writeInt32LE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,2147483647,-2147483648),i.TYPED_ARRAY_SUPPORT?(this[e]=255&t,this[e+1]=t>>>8,this[e+2]=t>>>16,this[e+3]=t>>>24):J(this,t,e,!0),e+4},i.prototype.writeInt32BE=function(t,e,r){return t=+t,e=0|e,r||z(this,t,e,4,2147483647,-2147483648),0>t&&(t=4294967295+t+1),i.TYPED_ARRAY_SUPPORT?(this[e]=t>>>24,this[e+1]=t>>>16,this[e+2]=t>>>8,this[e+3]=255&t):J(this,t,e,!1),e+4},i.prototype.writeFloatLE=function(t,e,r){return X(this,t,e,!0,r)},i.prototype.writeFloatBE=function(t,e,r){return X(this,t,e,!1,r)},i.prototype.writeDoubleLE=function(t,e,r){return Z(this,t,e,!0,r)},i.prototype.writeDoubleBE=function(t,e,r){return Z(this,t,e,!1,r)},i.prototype.copy=function(t,e,r,n){if(r||(r=0),n||0===n||(n=this.length),e>=t.length&&(e=t.length),e||(e=0),n>0&&r>n&&(n=r),n===r)return 0;if(0===t.length||0===this.length)return 0;if(0>e)throw new RangeError("targetStart out of bounds");if(0>r||r>=this.length)throw new RangeError("sourceStart out of bounds");if(0>n)throw new RangeError("sourceEnd out of bounds");n>this.length&&(n=this.length),t.length-e<n-r&&(n=t.length-e+r);var o,u=n-r;if(this===t&&e>r&&n>e)for(o=u-1;o>=0;--o)t[o+e]=this[o+r];else if(1e3>u||!i.TYPED_ARRAY_SUPPORT)for(o=0;u>o;++o)t[o+e]=this[o+r];else Uint8Array.prototype.set.call(t,this.subarray(r,r+u),e);return u},i.prototype.fill=function(t,e,r,n){if("string"==typeof t){if("string"==typeof e?(n=e,e=0,r=this.length):"string"==typeof r&&(n=r,r=this.length),1===t.length){var o=t.charCodeAt(0);256>o&&(t=o)}if(void 0!==n&&"string"!=typeof n)throw new TypeError("encoding must be a string");if("string"==typeof n&&!i.isEncoding(n))throw new TypeError("Unknown encoding: "+n)}else"number"==typeof t&&(t=255&t);if(0>e||this.length<e||this.length<r)throw new RangeError("Out of range index");if(e>=r)return this;e>>>=0,r=void 0===r?this.length:r>>>0,t||(t=0);var u;if("number"==typeof t)for(u=e;r>u;++u)this[u]=t;else{var s=i.isBuffer(t)?t:W(new i(t,n).toString()),f=s.length;for(u=0;r-e>u;++u)this[u+e]=s[u%f]}return this};var ft=/[^+\/0-9A-Za-z-_]/g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\buffer\\index.js","/node_modules\\buffer")},{_process:5,"base64-js":1,buffer:2,ieee754:4,isarray:3}],3:[function(t,e,r){(function(t,r,n,i,o,u,s,f,a){var h={}.toString;e.exports=Array.isArray||function(t){return"[object Array]"==h.call(t)}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\buffer\\node_modules\\isarray\\index.js","/node_modules\\buffer\\node_modules\\isarray")},{_process:5,buffer:2}],4:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){r.read=function(t,e,r,n,i){var o,u,s=8*i-n-1,f=(1<<s)-1,a=f>>1,h=-7,c=r?i-1:0,p=r?-1:1,l=t[e+c];for(c+=p,o=l&(1<<-h)-1,l>>=-h,h+=s;h>0;o=256*o+t[e+c],c+=p,h-=8);for(u=o&(1<<-h)-1,o>>=-h,h+=n;h>0;u=256*u+t[e+c],c+=p,h-=8);if(0===o)o=1-a;else{if(o===f)return u?NaN:(l?-1:1)*(1/0);u+=Math.pow(2,n),o-=a}return(l?-1:1)*u*Math.pow(2,o-n)},r.write=function(t,e,r,n,i,o){var u,s,f,a=8*o-i-1,h=(1<<a)-1,c=h>>1,p=23===i?Math.pow(2,-24)-Math.pow(2,-77):0,l=n?0:o-1,g=n?1:-1,d=0>e||0===e&&0>1/e?1:0;for(e=Math.abs(e),isNaN(e)||e===1/0?(s=isNaN(e)?1:0,u=h):(u=Math.floor(Math.log(e)/Math.LN2),e*(f=Math.pow(2,-u))<1&&(u--,f*=2),e+=u+c>=1?p/f:p*Math.pow(2,1-c),e*f>=2&&(u++,f/=2),u+c>=h?(s=0,u=h):u+c>=1?(s=(e*f-1)*Math.pow(2,i),u+=c):(s=e*Math.pow(2,c-1)*Math.pow(2,i),u=0));i>=8;t[r+l]=255&s,l+=g,s/=256,i-=8);for(u=u<<i|s,a+=i;a>0;t[r+l]=255&u,l+=g,u/=256,a-=8);t[r+l-g]|=128*d}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\ieee754\\index.js","/node_modules\\ieee754")},{_process:5,buffer:2}],5:[function(t,e,r){(function(t,r,n,i,o,u,s,f,a){function h(){throw new Error("setTimeout has not been defined")}function c(){throw new Error("clearTimeout has not been defined")}function p(t){if(b===setTimeout)return setTimeout(t,0);if((b===h||!b)&&setTimeout)return b=setTimeout,setTimeout(t,0);try{return b(t,0)}catch(e){try{return b.call(null,t,0)}catch(e){return b.call(this,t,0)}}}function l(t){if(w===clearTimeout)return clearTimeout(t);if((w===c||!w)&&clearTimeout)return w=clearTimeout,clearTimeout(t);try{return w(t)}catch(e){try{return w.call(null,t)}catch(e){return w.call(this,t)}}}function g(){_&&m&&(_=!1,m.length?P=m.concat(P):A=-1,P.length&&d())}function d(){if(!_){var t=p(g);_=!0;for(var e=P.length;e;){for(m=P,P=[];++A<e;)m&&m[A].run();A=-1,e=P.length}m=null,_=!1,l(t)}}function y(t,e){this.fun=t,this.array=e}function v(){}var b,w,t=e.exports={};!function(){try{b="function"==typeof setTimeout?setTimeout:h}catch(t){b=h}try{w="function"==typeof clearTimeout?clearTimeout:c}catch(t){w=c}}();var m,P=[],_=!1,A=-1;t.nextTick=function(t){var e=new Array(arguments.length-1);if(arguments.length>1)for(var r=1;r<arguments.length;r++)e[r-1]=arguments[r];P.push(new y(t,e)),1!==P.length||_||p(d)},y.prototype.run=function(){this.fun.apply(null,this.array)},t.title="browser",t.browser=!0,t.env={},t.argv=[],t.version="",t.versions={},t.on=v,t.addListener=v,t.once=v,t.off=v,t.removeListener=v,t.removeAllListeners=v,t.emit=v,t.binding=function(t){throw new Error("process.binding is not supported")},t.cwd=function(){return"/"},t.chdir=function(t){throw new Error("process.chdir is not supported")},t.umask=function(){return 0}}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/node_modules\\process\\browser.js","/node_modules\\process")},{_process:5,buffer:2}],6:[function(t,e,r){(function(e,n,i,o,u,s,f,a,h){"use strict";var c=t("./PlainObjectProvider"),p=t("./DataBinding"),l=function(){function t(){}return t.bindTo=function(t,e,r,n,i){var n=void 0!==i?new p.CurryConverter(n,i):n;return e instanceof p.PathObjectBinding||e instanceof p.PathParentBinding?new p.PathParentBinding(e,r,n):new p.PathObjectBinding(e,function(e){return new t(e)},r,n)},t.bindArrayTo=function(t,e,r,n,i){var n=void 0!==i?new p.CurryConverter(n,i):n;return e instanceof p.PathObjectBinding||e instanceof p.PathParentBinding?new p.ArrayParentBinding(e,r,n):new p.ArrayObjectBinding(e,function(e){return new t(e)},r,n)},t}();r.BinderCore=l;var g=function(){function t(){}return t.createStateKeySetter=function(t,e){var r={};return function(n){r[e]=void 0!==n?n:t.state[e],t.setState(r)}},t.bindToState=function(e,r,n,i,o){return new p.PathObjectBinding(e.state[r],function(t){return new c["default"](t)},n,t.createStateKeySetter(e,r),void 0!==o?new p.CurryConverter(i,o):i)},t.bindTo=function(t,e,r,n){return l.bindTo(c["default"],t,e,r,n)},t.bindArrayToState=function(e,r,n){return new p.ArrayObjectBinding(e.state[r],function(t){return new c["default"](t)},n,t.createStateKeySetter(e,r))},t.bindArrayTo=function(t,e,r,n){return l.bindArrayTo(c["default"],t,e,r,n)},t}();Object.defineProperty(r,"__esModule",{value:!0}),r["default"]=g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\Binder.ts","/src")},{"./DataBinding":7,"./PlainObjectProvider":8,_process:5,buffer:2}],7:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";var h=function(){function t(t,e,r,n,i,o){this.sourceObject=t,this.provider=e,this.path=r,this.notifyChange=n,this.valueConverter=i,this.parentNode=o,this.source=e(t)}return Object.defineProperty(t.prototype,"requestChange",{get:function(){var t=this;return function(e){t.value=e}},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return void 0!==this.parentNode?this.parentNode.root:this},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return void 0!==this.parentNode?this.parentNode:void 0},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"value",{get:function(){var t=void 0===this.path?this.source.getValue():this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t},set:function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path),r=void 0!==this.valueConverter?this.valueConverter.parse(t):t;(void 0===e||e!==r)&&(void 0===this.path?void 0!==this.notifyChange&&this.notifyChange(r):(this.source.setValue(this.path,r),void 0!==this.notifyChange&&this.notifyChange()))},enumerable:!0,configurable:!0}),t}();r.PathObjectBinding=h;var c=function(){function t(t,e,r,n,i){this.sourceObject=t,this.provider=e,this.path=r,this.notifyChange=n,this.valueConverter=i,this.source=e(t)}return Object.defineProperty(t.prototype,"parent",{get:function(){return void 0},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"items",{get:function(){var t=void 0===this.path?this.source.getValue():this.source.getValue(this.path);return void 0===t?[]:t.map(function(t){return new h(t,this.provider,void 0,this.notifyChange,void 0,this)},this)},enumerable:!0,configurable:!0}),t.prototype.add=function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path);void 0===e&&(this.source.setValue(this.path,[]),e=this.source.getValue(this.path)),void 0===t&&(t={}),e.push(t),void 0!==this.notifyChange&&this.notifyChange()},t.prototype.remove=function(t){var e=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==e){var r=e.indexOf(t);-1!==r&&(e.splice(r,1),void 0!==this.notifyChange&&this.notifyChange())}},t.prototype.splice=function(t,e,r){var n=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==n)return r?n.splice(t,e,r):n.splice(t,e)},t.prototype.move=function(t,e){var r=void 0===this.path?this.source.getValue():this.source.getValue(this.path);if(void 0!==r){var n=JSON.parse(JSON.stringify(r));n.splice(e,0,n.splice(t,1)[0]),this.source.setValue(this.path,n)}},t}();r.ArrayObjectBinding=c;var p=function(){function t(t,e,r){this.parentBinding=t,this.relativePath=e,this.valueConverter=r}return Object.defineProperty(t.prototype,"source",{get:function(){return this.parentBinding.source},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"provider",{get:function(){return this.parentBinding.provider},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this.parentBinding.root},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return this.parentBinding},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"notifyChange",{get:function(){return this.parentBinding.notifyChange},set:function(t){this.parentBinding.notifyChange=t},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"path",{get:function(){return void 0===this.parentBinding.path?this.relativePath:void 0===this.relativePath?this.parentBinding.path:[this.parentBinding.path,this.relativePath].join(".")},enumerable:!0,configurable:!0}),t.prototype.getItems=function(){if(void 0!==this.source){var t=this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t}},Object.defineProperty(t.prototype,"items",{ | ||
| get:function(){var t=this.getItems();return void 0===t?[]:t.map(function(t){return new h(t,this.provider,void 0,this.notifyChange,void 0,this)},this)},enumerable:!0,configurable:!0}),t.prototype.add=function(t){var e=this.getItems();void 0===e&&(this.source.setValue(this.path,[]),e=this.source.getValue(this.path)),void 0===t&&(t={}),e.push(t),void 0!==this.notifyChange&&this.notifyChange()},t.prototype.remove=function(t){var e=this.getItems();if(void 0!==e){var r=e.indexOf(t);-1!==r&&(e.splice(r,1),void 0!==this.notifyChange&&this.notifyChange())}},t.prototype.splice=function(t,e,r){var n=this.getItems();if(void 0!==n)return r?n.splice(t,e,r):n.splice(t,e)},t.prototype.move=function(t,e){this.splice(e,0,this.splice(t,1)[0]),void 0!==this.notifyChange&&this.notifyChange()},t}();r.ArrayParentBinding=p;var l=function(){function t(t,e,r){this.parentBinding=t,this.relativePath=e,this.valueConverter=r}return Object.defineProperty(t.prototype,"source",{get:function(){return this.parentBinding.source},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"provider",{get:function(){return this.parentBinding.provider},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"root",{get:function(){return this.parentBinding.root},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"parent",{get:function(){return this.parentBinding},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"notifyChange",{get:function(){return this.parentBinding.notifyChange},set:function(t){this.parentBinding.notifyChange=t},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"requestChange",{get:function(){var t=this;return function(e){t.value=e}},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"path",{get:function(){return void 0===this.parentBinding.path?this.relativePath:[this.parentBinding.path,this.relativePath].join(".")},enumerable:!0,configurable:!0}),Object.defineProperty(t.prototype,"value",{get:function(){var t=this.source.getValue(this.path);return void 0!==this.valueConverter?this.valueConverter.format(t):t},set:function(t){var e=this.source.getValue(this.path),r=void 0!==this.valueConverter?this.valueConverter.parse(t):t;e!==r&&(this.source.setValue(this.path,r),void 0!==this.notifyChange&&this.notifyChange())},enumerable:!0,configurable:!0}),t}();r.PathParentBinding=l;var g=function(){function t(t,e){this.formatFce=this.curryParameters(t.format,[e]),this.parseFce=this.curryParameters(t.parse,[e])}return t.prototype.curryParameters=function(t,e){return function(){return t.apply(this,Array.prototype.slice.call(arguments).concat(e))}},t.prototype.format=function(t){return this.formatFce(t)},t.prototype.parse=function(t){return this.parseFce(t)},t}();r.CurryConverter=g}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\DataBinding.ts","/src")},{_process:5,buffer:2}],8:[function(t,e,r){(function(t,e,n,i,o,u,s,f,a){"use strict";var h=function(){function t(t){this.source=t}return t.prototype.subscribe=function(t){},t.prototype.getValue=function(e){var r=this.getParent(e);if(void 0!==r){if(void 0===e)return r;var n=t.getProperty(e);return r[n]}},t.prototype.setValue=function(e,r){var n=this.getParent(e);if(void 0!==n){var i=t.getProperty(e);n[i]=r}},t.prototype.getParent=function(t){if(void 0===t)return this.source;var e=t.lastIndexOf(".");return-1!=e?this.string_to_ref(this.source,t.substring(0,e)):this.source},t.getProperty=function(t){var e=t.lastIndexOf(".");return-1!=e?t.substring(e+1,t.length):t},t.prototype.string_to_ref=function(t,e){var r=e.split("."),n=t[r[0]];if(void 0===n&&(n=t[r[0]]={}),!r[1])return n;r.splice(0,1);var i=r.join(".");return this.string_to_ref(n,i)},t}();Object.defineProperty(r,"__esModule",{value:!0}),r["default"]=h}).call(this,t("_process"),"undefined"!=typeof global?global:"undefined"!=typeof self?self:"undefined"!=typeof window?window:{},t("buffer").Buffer,arguments[3],arguments[4],arguments[5],arguments[6],"/src\\PlainObjectProvider.ts","/src")},{_process:5,buffer:2}]},{},[6])(6)}); |
-322
| # react-binding | ||
| React-binding is lightweight utility for two-way data binding in [React][react]. | ||
| Note: React-binding as mixins - use npm install react-binding@0.6.4 | ||
| ```js | ||
| import {Binder} from 'react-binding' | ||
| ``` | ||
| ```js | ||
| Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| Binder.bindToArrayState(this,"data","__Hobbies__"); | ||
| Binder.bindTo(__employee__,"__Contact.Email__"); | ||
| Binder.bindToArray(__employee__,"__Hobbies__"); | ||
| ``` | ||
| ```js | ||
| Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| Binder.bindToArrayState(this,"data","__Hobbies__"); | ||
| Binder.bindTo(__employee__,"__Contact.Email__"); | ||
| Binder.bindToArray(__employee__,"__Hobbies__"); | ||
| ``` | ||
| [BindToMixin](https://github.com/rsamec/react-binding) offers two-way data binding support for: | ||
| + object properties with path expression (dot notation) | ||
| + Binder.bindToState(this,"data","__Employee.FirstName__"); | ||
| + Binder.bindToState(this,"data","__Employee.Contact.Email__"); | ||
| + complex objects (json) with __nested properties__ | ||
| + Binder.bindTo(__employee__,"__FirstName__"); | ||
| + Binder.bindTo(__employee__,"__Contact.Email__"); | ||
| + collection-based structures - arrays and lists | ||
| + model={Binder.bindArrayToState(this,"data","__Hobbies__")} | ||
| + this.props.model.__items__.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| + this.props.model.__add()__ | ||
| + this.props.model.__remove(item)__ | ||
| + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| + valueLink={Binder.bindTo(employee,"FirstName")} | ||
| + enables binding with value converters | ||
| + supports both directions - __format__ (toView) and __parse__ (fromView) | ||
| + support for converter parameter - valueLink={Binder.bindToState(this,"data", "Duration.From",__converter, "DD.MM.YYYY"__)} | ||
| + converter parameter can be data-bound - valueLink={Binder.bindToState(this,"data", "Duration.From",converter, __this.state.format__)} | ||
| + usable with any css frameworks | ||
| + [react-bootstrap][reactBootstrap] | ||
| + [material-ui][materialUi] | ||
| # Basic principle | ||
| Each bindTo return and uses interface called "value/onChange". | ||
| Each bindTo component is passed a value (to render it to UI) as well as setter to a value that triggers a re-render (typically at the top location). | ||
| The re-render is done in the component where you bind to the state via (bindToState, bindArrayToState). | ||
| BindTo can be nested - composed to support components composition. Then path is concatenate according to parent-child relationship. | ||
| # Get started | ||
| * [node package manager][npm] | ||
| ``` js | ||
| npm install react-binding | ||
| ``` | ||
| * [client-side code package manager][bower] | ||
| ``` js | ||
| bower install react-binding | ||
| ``` | ||
| * [bundling with browserify][browserify] | ||
| ``` js | ||
| npm install -g browserify | ||
| npm install reactify | ||
| browserify ./index.js > bundle.js | ||
| ``` | ||
| __minimal example__ | ||
| ``` js | ||
| import React from 'react'; | ||
| import {Binder} from 'react-binding' | ||
| var Form = React.createClass({ | ||
| getInitialState: function () { | ||
| return {data: {}} | ||
| }, | ||
| render: function () { | ||
| return ( | ||
| <div> | ||
| <input valueLink={Binder.bindToState(this,"data", "FirstName")} /> | ||
| <div>FirstName: {this.state.data.FirstName}</div> | ||
| </div> | ||
| )} | ||
| }); | ||
| React.render( | ||
| <Form />, | ||
| document.getElementById('content') | ||
| ); | ||
| ``` | ||
| # Overview | ||
| ### bindToState(key,pathExpression) | ||
| It enables to bind to object property with path expression | ||
| + using [ReactLink][valueLink] | ||
| ``` js | ||
| <input type='text' valueLink={Binder.bindToState(this,"data","Employee.Contact.Email")} /> | ||
| ``` | ||
| + without [ReactLink][valueLink] | ||
| ``` js | ||
| <TextBoxInput model={Binder.bindToState(this,"data","Employee.Contact.Email")} /> | ||
| ``` | ||
| ``` js | ||
| var TextBoxInput = React.createClass({ | ||
| render: function() { | ||
| var valueModel = this.props.model; | ||
| var handleChange = function(e){ | ||
| valueModel.value = e.target.value; | ||
| } | ||
| return ( | ||
| <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| ) | ||
| } | ||
| }); | ||
| ``` | ||
| ### bindTo(parent,pathExpression) | ||
| It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| + binding to state at root level | ||
| ``` js | ||
| <PersonComponent personModel={Binder.bindToState("data","Employee")} /> | ||
| <PersonComponent personModel={Binder.bindToState("data","Deputy")} /> | ||
| ``` | ||
| + binding to parent | ||
| ``` js | ||
| <input type='text' valueLink={Binder.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| ``` | ||
| + reuse bindings in component | ||
| ``` js | ||
| var PersonComponent = React.createClass({ | ||
| render: function() { | ||
| return ( | ||
| <div> | ||
| <input type='text' valueLink={Binder.bindTo(this.props.personModel,"FirstName")} /> | ||
| <input type='text' valueLink={Binder.bindTo(this.props.personModel,"LastName")} /> | ||
| <input type='text' valueLink={Binder.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| </div> | ||
| ); | ||
| } | ||
| }); | ||
| ``` | ||
| ### bindArrayToState(key,pathExpression) | ||
| It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| + binding to array | ||
| ``` js | ||
| <HobbyList model={Binder.bindArrayToState(this,"data","Hobbies")} /> | ||
| ``` | ||
| + access items (this.props.model.items) | ||
| ``` js | ||
| var HobbyList = React.createClass({ | ||
| render: function() { | ||
| if (this.props.model.items === undefined) return <span>There are no items.</span>; | ||
| var hobbies = this.props.model.items.map(function(hobby, index) { | ||
| return ( | ||
| <Hobby model={hobby} key={index} onDelete={this.handleDelete} /> | ||
| ); | ||
| },this); | ||
| return ( | ||
| <div>{hobbies}</div> | ||
| ); | ||
| } | ||
| }); | ||
| ``` | ||
| + add new items (this.props.model.add(newItem?)) | ||
| ``` js | ||
| handleAdd: function(){ | ||
| return this.props.model.add(); | ||
| }, | ||
| ``` | ||
| + remove exiting items (this.props.model.props.delete(item)) | ||
| ``` js | ||
| handleDelete: function(hobby){ | ||
| return this.props.model.remove(hobby); | ||
| }, | ||
| ``` | ||
| ### bindArrayTo(parent,pathExpression) | ||
| It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| + binding to array | ||
| ``` js | ||
| <HobbyList model={Binder.bindArrayTo(this,parent,"Hobbies")} /> | ||
| ``` | ||
| + access items (this.props.model.items) | ||
| ``` js | ||
| var HobbyList = React.createClass({ | ||
| render: function() { | ||
| if (this.props.model.items === undefined) return <span>There are no items.</span>; | ||
| var hobbies = this.props.model.items.map(function(hobby, index) { | ||
| return ( | ||
| <Hobby model={hobby} key={index} onDelete={this.handleDelete} /> | ||
| ); | ||
| },this); | ||
| return ( | ||
| <div>{hobbies}</div> | ||
| ); | ||
| } | ||
| }); | ||
| ``` | ||
| + add new items (this.props.model.add(newItem?)) | ||
| ``` js | ||
| handleAdd: function(){ | ||
| return this.props.model.add(); | ||
| }, | ||
| ``` | ||
| + remove exiting items (this.props.model.props.delete(item)) | ||
| ``` js | ||
| handleDelete: function(hobby){ | ||
| return this.props.model.remove(hobby); | ||
| }, | ||
| ``` | ||
| ### Value converters | ||
| Value converters | ||
| + format - translates data to a format suitable for the view | ||
| + parse - convert data from the view to a format expected by your data (typically when using two-way binding with input elements to data). | ||
| Example - date converter -> using parameters 'dateFormat' is optional | ||
| ``` js | ||
| var dateConverter = function() { | ||
| this.parse = function (input, dateFormat) { | ||
| if (!!!input) return undefined; | ||
| if (input.length < 8) return undefined; | ||
| var date = moment(input, dateFormat); | ||
| if (date.isValid()) return date.toDate(); | ||
| return undefined; | ||
| } | ||
| this.format = function (input,dateFormat) { | ||
| if (!!!input) return undefined; | ||
| return moment(input).format(dateFormat); | ||
| } | ||
| } | ||
| ``` | ||
| using converter | ||
| ``` js | ||
| <DatePicker label="From" model={Binder.bindToState(this,"data", "Duration.From", converter, 'DD.MM.YYYY')} error={this.validationResult().Duration.From} /> | ||
| <DatePicker label="To" model={Binder.bindToState(this,"data", "Duration.To", converter, 'DD.MM.YYYY')} error={this.validationResult().Duration.To} /> | ||
| ``` | ||
| [try in Plunker](http://embed.plnkr.co/gGWe82wT2JJflZt095Gk/preview) | ||
| # Examples | ||
| hobby form - data binding only | ||
| + no UI framework - [try in Plunker](http://embed.plnkr.co/aTilRFEJe0gEWaZzr8PC/preview) | ||
| + with react-bootstrap - [try in Plunker](http://embed.plnkr.co/7tumC62YO8GixKEMhJcw/preview) | ||
| hobby form with validation using [business-rules-engine][bre] | ||
| + no UI framework - [try in Plunker](http://embed.plnkr.co/qXlUQ7a3YLEypwT2vvSb/preview) | ||
| + with react-bootstrap - [try in Plunker](http://embed.plnkr.co/6hoCCd7Bl1PHnb57rQbT/preview) | ||
| + with material-ui | ||
| + [demo](http://polymer-formvalidation.rhcloud.com/dist/index.html) | ||
| + [sources](https://github.com/rsamec/react-hobby-form-app) | ||
| value converters | ||
| + date picker - [try in Plunker](http://embed.plnkr.co/gGWe82wT2JJflZt095Gk/preview) | ||
| ## Contact | ||
| For more information on react-binding please check out [my blog][blog]. | ||
| [git]: http://git-scm.com/ | ||
| [bower]: http://bower.io | ||
| [npm]: https://www.npmjs.org/ | ||
| [node]: http://nodejs.org | ||
| [browserify]: http://browserify.org/ | ||
| [blog]: http://rsamec.github.io/ | ||
| [valueLink]: http://facebook.github.io/react/docs/two-way-binding-helpers.html | ||
| [materialUi]: https://github.com/callemall/material-ui | ||
| [reactBootstrap]: http://react-bootstrap.github.io/ | ||
| [bre]: https://github.com/rsamec/business-rules-engine | ||
| [react]: http://facebook.github.io/react/ |
-68
| var gulp = require('gulp'); | ||
| //utils | ||
| var uglify = require('gulp-uglify'); | ||
| var rename = require("gulp-rename"); | ||
| //var typedoc = require("gulp-typedoc"); | ||
| //var replace = require('gulp-regex-replace'); | ||
| //typescript | ||
| var ts = require('gulp-typescript'); | ||
| var merge = require('merge2'); | ||
| //browserify | ||
| var buffer = require('vinyl-buffer'); | ||
| var source = require('vinyl-source-stream'); | ||
| var browserify = require('browserify'); | ||
| var tsify = require('tsify'); | ||
| gulp.task('scripts', function() { | ||
| var tsResult = gulp.src('src/*.ts') | ||
| .pipe(ts({ | ||
| declaration: true, | ||
| target: 'ES5', | ||
| module: 'commonjs' | ||
| })); | ||
| return merge([ | ||
| tsResult.dts.pipe(gulp.dest('dist/definitions')), | ||
| tsResult.js.pipe(gulp.dest('dist/lib')) | ||
| ]); | ||
| }); | ||
| gulp.task('bower', function () { | ||
| return browserify({ | ||
| insertGlobals: true, | ||
| standalone: 'Binder', | ||
| debug: false | ||
| }) | ||
| .add('src/Binder.ts') | ||
| .plugin(tsify) | ||
| .bundle() | ||
| .on('error', function (error) { console.error(error.toString()); }) | ||
| .pipe(source('react-binding.js')) | ||
| .pipe(buffer()) | ||
| .pipe(gulp.dest('dist')); | ||
| }); | ||
| gulp.task('compress', ['bower'], function () { | ||
| gulp.src('dist/react-binding.js') | ||
| .pipe(uglify()) | ||
| .pipe(rename('react-binding.min.js')) | ||
| .pipe(gulp.dest('dist')) | ||
| }); | ||
| // gulp.task("typedoc", function () { | ||
| // return gulp | ||
| // .src(["src/*.ts"]) | ||
| // .pipe(typedoc({ | ||
| // module: "commonjs", | ||
| // out: "./out", | ||
| // name: "react-binding", | ||
| // target: "es5" | ||
| // })) | ||
| // ; | ||
| // }); | ||
| // Just running the tasks | ||
| gulp.task('default', ['scripts', 'compress']); |
-22
| The MIT License (MIT) | ||
| Copyright (c) 2015 Roman Samec | ||
| Permission is hereby granted, free of charge, to any person obtaining a copy | ||
| of this software and associated documentation files (the "Software"), to deal | ||
| in the Software without restriction, including without limitation the rights | ||
| to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||
| copies of the Software, and to permit persons to whom the Software is | ||
| furnished to do so, subject to the following conditions: | ||
| The above copyright notice and this permission notice shall be included in all | ||
| copies or substantial portions of the Software. | ||
| THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||
| AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||
| LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||
| OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||
| SOFTWARE. | ||
-183
| import Provider from './PlainObjectProvider'; | ||
| import { IPathObjectBinder, IPathObjectBinding, IValueConverter, PathObjectBinding, ArrayObjectBinding, PathParentBinding, ArrayParentBinding, CurryConverter } from './DataBinding'; | ||
| export class BinderCore { | ||
| static bindTo(type: { new (data): IPathObjectBinder }, parent, path?: string, converter?, converterParams?): IPathObjectBinding { | ||
| var converter = converterParams !== undefined ? new CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof PathObjectBinding || parent instanceof PathParentBinding) ? new PathParentBinding(parent, path, converter) : new PathObjectBinding(parent, (data) => new type(data), path, converter); | ||
| } | ||
| static bindArrayTo(type: { new (data): IPathObjectBinder }, parent, path?: string, converter?, converterParams?): any { | ||
| var converter = converterParams !== undefined ? new CurryConverter(converter, converterParams) : converter; | ||
| return (parent instanceof PathObjectBinding || parent instanceof PathParentBinding) ? new ArrayParentBinding(parent, path, converter) : new ArrayObjectBinding(parent, (data) => new type(data), path, converter); | ||
| } | ||
| } | ||
| /** | ||
| * React [LinkedStateMixin](http://facebook.github.io/react/docs/two-way-binding-helpers.html) is an easy way to express two-way data binding in React. | ||
| * | ||
| * React-binding comes with utility [Binder](https://github.com/rsamec/react-binding) for two-way binding that supports binding to | ||
| * | ||
| * + object properties with path expression (dot notation) | ||
| * + this.bindToState("data","Employee.FirstName"); | ||
| * + this.bindToState("data","Employee.Contact.Email"); | ||
| * + complex objects (json) with nested properties | ||
| * + this.bindTo(employee,"FirstName"); | ||
| * + this.bindTo(employee,"Contact.Email"); | ||
| * + collection-based structures - arrays and lists | ||
| * + model={this.bindTo(employee,"FirstName")} | ||
| * + this.props.model.items.map(function(item){ return (<Hobby model={hobby}/>);}) | ||
| * + this.props.model.add() | ||
| * + this.props.model.remove(item) | ||
| * + supports for "value/requestChange" interface also to enable to use [ReactLink][valueLink] attribute | ||
| * + valueLink={this.bindTo(employee,"FirstName")} | ||
| * + enables binding with value converters | ||
| * + supports both directions - format (toView) and parse (fromView) | ||
| * + support for converter parameter - valueLink={this.bindToState("data", "Duration.From",converter, "DD.MM.YYYY")} | ||
| * + converter parameter can be data-bound - valueLink={this.bindToState("data", "Duration.From",converter, this.state.format)} | ||
| * + usable with any css frameworks - | ||
| * + react-bootstrap | ||
| * + material-ui | ||
| * | ||
| */ | ||
| export default class Binder { | ||
| static createStateKeySetter(component, key) { | ||
| var partialState = {}; | ||
| return (value?) => { | ||
| partialState[key] = (value !== undefined) ? value : component.state[key]; | ||
| component.setState(partialState); | ||
| } | ||
| } | ||
| /** | ||
| * It enables to bind to object property with path expression | ||
| * + using [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + without [valueLink](http://facebook.github.io/react/docs/two-way-binding-helpers.html) | ||
| * ``` js | ||
| * <TextBoxInput model={this.bindToState("data","Employee.Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * ``` js | ||
| * var TextBoxInput = React.createClass({ | ||
| * render: function() { | ||
| * var valueModel = this.props.model; | ||
| * var handleChange = function(e){ | ||
| * valueModel.value = e.target.value; | ||
| * } | ||
| * return ( | ||
| * <input type='text' onChange={handleChange} value={valueModel.value} /> | ||
| * )} | ||
| * }); | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) | ||
| * @param path - expression to bind to property | ||
| * @param converter {DataBinding.IValueConverter} - value converter | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathObjectBinding} | ||
| */ | ||
| static bindToState(component, key: string, path?: string, converter?: IValueConverter, converterParams?): IPathObjectBinding { | ||
| return new PathObjectBinding( | ||
| component["state"][key], | ||
| (data) => new Provider(data), | ||
| path, | ||
| Binder.createStateKeySetter(component, key), | ||
| converterParams !== undefined ? new CurryConverter(converter, converterParams) : converter | ||
| //ReactStateSetters.createStateKeySetter(this, key) | ||
| ); | ||
| } | ||
| /** | ||
| * It enables to bind to complex object with nested properties and reuse bindings in components. | ||
| * | ||
| * + binding to state at root level | ||
| * | ||
| * ``` js | ||
| * <PersonComponent personModel={this.bindToState("data","Employee")} /> | ||
| * <PersonComponent personModel={this.bindToState("data","Deputy")} /> | ||
| * ``` | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * + reuse bindings in component | ||
| * | ||
| * ``` js | ||
| * var PersonComponent = React.createClass({ | ||
| * mixins:[BindToMixin], | ||
| * render: function() { | ||
| * return ( | ||
| * <div> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"FirstName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"LastName")} /> | ||
| * <input type='text' valueLink={this.bindTo(this.props.personModel,"Contact.Email")} /> | ||
| * </div> | ||
| * ); | ||
| * } | ||
| * }); | ||
| * | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property | ||
| * @param converter - value converter {DataBinding.IValueConverter} | ||
| * @param converterParams - parameters used by converter | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindTo(parent, path?: string, converter?, converterParams?): IPathObjectBinding { | ||
| return BinderCore.bindTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| /** | ||
| * It enables binding to collection-based structures (array). It enables to add and remove items. | ||
| * | ||
| * + binding to array | ||
| * | ||
| * ``` js | ||
| * <HobbyList model={this.bindArrayToState("data","Hobbies")} /> | ||
| * ``` | ||
| * | ||
| * @param key - property name in state (this.state[key]) - it must be array | ||
| * @param path - expression to array to bind to property | ||
| * @returns {DataBinding.ArrayObjectBinding} | ||
| */ | ||
| static bindArrayToState(component, key: string, path?: string): ArrayObjectBinding { | ||
| return new ArrayObjectBinding( | ||
| component["state"][key], | ||
| (data) => new Provider(data), | ||
| path, | ||
| Binder.createStateKeySetter(component, key) | ||
| //ReactStateSetters.createStateKeySetter(this, key) | ||
| ); | ||
| } | ||
| /** | ||
| * It enables binding to collection-based structures (array) for nested arrays. It enables to add and remove items. | ||
| * | ||
| * + binding to parent | ||
| * | ||
| * ``` js | ||
| * <input type='text' valueLink={this.bindArrayTo(this.props.personModel,"Contact.Email")} /> | ||
| * ``` | ||
| * | ||
| * @param parent - the parent object | ||
| * @param path - expression to bind to property - relative path from parent | ||
| * @returns {DataBinding.PathParentBinding} | ||
| */ | ||
| static bindArrayTo(parent, path?: string, converter?, converterParams?): any { | ||
| return BinderCore.bindArrayTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| } | ||
| //export default Binder; |
| export interface BinderStatic { | ||
| bindToState?(data, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding | ||
| bindTo(parent, path?: string, converter?: IValueConverter, converterParams?: any): ObjectBinding | ||
| bindArrayToState?(data, key: string, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding | ||
| bindArrayTo(parent, path?: string, converter?: IValueConverter, converterParams?: any): ArrayBinding | ||
| } | ||
| export interface Binding { | ||
| path?: string; | ||
| parent: Binding; | ||
| root:Binding; | ||
| } | ||
| export interface ObjectBinding extends Binding { | ||
| value: any; | ||
| } | ||
| export interface ArrayBinding extends Binding { | ||
| items: Array<ObjectBinding>; | ||
| add(defautItem?: any); | ||
| remove(itemToRemove: any); | ||
| splice(start: number, deleteCount: number, elementsToAdd?: any); | ||
| move(x: number, y: number); | ||
| } | ||
| /**x` | ||
| * Two-way data binding for React. | ||
| */ | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export interface IPathObjectBinder { | ||
| /** | ||
| It gets value at the passed path expression. | ||
| */ | ||
| getValue(path?: string) | ||
| /** | ||
| It sets the passed value at the passed path. | ||
| */ | ||
| setValue(path: string, value: any); | ||
| subscribe(fce): void; | ||
| } | ||
| /** | ||
| It represents change notification function. It is called whenever there is a change. | ||
| */ | ||
| export interface INotifyChange { | ||
| (any?): void | ||
| } | ||
| /** | ||
| It represents change notifikcation function with changed value. It supports valueLink interface | ||
| */ | ||
| export interface IRequestChange { | ||
| (any): void | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export interface IPathObjectBinding extends ObjectBinding { | ||
| //value: any; | ||
| source: IPathObjectBinder; | ||
| provider: (data) => IPathObjectBinder; | ||
| notifyChange?: INotifyChange; | ||
| requestChange?: IRequestChange; | ||
| valueConverter?: IValueConverter; | ||
| //path?: any; | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export class PathObjectBinding implements IPathObjectBinding { | ||
| public source: IPathObjectBinder; | ||
| constructor(public sourceObject: any, public provider: (data) => IPathObjectBinder, public path?: string, public notifyChange?: INotifyChange, public valueConverter?: IValueConverter,public parentNode?:Binding) { | ||
| this.source = provider(sourceObject); | ||
| } | ||
| public get requestChange(): IRequestChange { | ||
| return (value) => { this.value = value; } | ||
| } | ||
| public get root(): Binding { | ||
| return this.parentNode !==undefined?this.parentNode.root:this; | ||
| } | ||
| public get parent(): Binding { | ||
| return this.parentNode !==undefined?this.parentNode:undefined; | ||
| } | ||
| public get value() { | ||
| var value = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| } | ||
| public set value(value: any) { | ||
| var previousValue = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| //check if the value is really changed - strict equality | ||
| if (previousValue !== undefined && previousValue === convertedValueToBeSet) return; | ||
| if (this.path === undefined) { | ||
| if (this.notifyChange !== undefined) this.notifyChange(convertedValueToBeSet); | ||
| } else { | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| } | ||
| } | ||
| /** | ||
| It represents binding to property at source object at a given path. | ||
| */ | ||
| export class ArrayObjectBinding implements ArrayBinding { | ||
| public source: IPathObjectBinder; | ||
| constructor(public sourceObject: any, public provider: (data) => IPathObjectBinder, public path?: string, public notifyChange?: INotifyChange, public valueConverter?: IValueConverter) { | ||
| this.source = provider(sourceObject); | ||
| } | ||
| public get parent(): ArrayBinding{ | ||
| return undefined; | ||
| } | ||
| public get root(): ArrayBinding{ | ||
| return this; | ||
| } | ||
| public get items(): Array<IPathObjectBinding> { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) return []; | ||
| return items.map(function (item) { | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange,undefined,this); | ||
| }, this); | ||
| } | ||
| public add(defaultItem?) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public remove(itemToRemove) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public splice(start: number, deleteCount: number, elementsToAdd?: any) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public move(x: number, y: number) { | ||
| var items = this.path === undefined ? this.source.getValue() : this.source.getValue(this.path); | ||
| if (items === undefined) return; | ||
| //@TODO: use more effective way to clone array | ||
| var itemsCloned = JSON.parse(JSON.stringify(items)); | ||
| itemsCloned.splice(y, 0, itemsCloned.splice(x, 1)[0]); | ||
| this.source.setValue(this.path, itemsCloned); | ||
| } | ||
| } | ||
| /** | ||
| It represents binding to array using relative path to parent object. | ||
| */ | ||
| export class ArrayParentBinding implements ArrayBinding { | ||
| constructor(private parentBinding: IPathObjectBinding, public relativePath?: string, public valueConverter?: IValueConverter) { | ||
| } | ||
| //wrapped properties - delegate call to parent | ||
| public get source(): IPathObjectBinder { | ||
| return this.parentBinding.source; | ||
| } | ||
| public get provider(): (data) => IPathObjectBinder { | ||
| return this.parentBinding.provider; | ||
| } | ||
| public get root():Binding{ | ||
| return this.parentBinding.root; | ||
| } | ||
| public get parent():Binding{ | ||
| return this.parentBinding; | ||
| } | ||
| public get notifyChange() { | ||
| return this.parentBinding.notifyChange; | ||
| } | ||
| public set notifyChange(value: INotifyChange) { | ||
| this.parentBinding.notifyChange = value; | ||
| } | ||
| //concatenate path | ||
| public get path(): string { | ||
| if (this.parentBinding.path === undefined) return this.relativePath; | ||
| if (this.relativePath === undefined) return this.parentBinding.path; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| } | ||
| private getItems(): Array<any> { | ||
| if (this.source === undefined) return; | ||
| var value = this.source.getValue(this.path); | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| } | ||
| public get items(): Array<IPathObjectBinding> { | ||
| var items = this.getItems(); | ||
| if (items === undefined) return []; | ||
| return items.map(function (item) { | ||
| //item._parentBinding = this; | ||
| return new PathObjectBinding(item, this.provider, undefined, this.notifyChange,undefined,this); | ||
| }, this); | ||
| } | ||
| public add(defaultItem?) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) { | ||
| this.source.setValue(this.path, []); | ||
| items = this.source.getValue(this.path); | ||
| } | ||
| if (defaultItem === undefined) defaultItem = {}; | ||
| items.push(defaultItem); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public remove(itemToRemove) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) return; | ||
| var index = items.indexOf(itemToRemove); | ||
| if (index === -1) return; | ||
| items.splice(index, 1); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public splice(start: number, deleteCount: number, elementsToAdd?: any) { | ||
| var items = this.getItems(); | ||
| if (items === undefined) return; | ||
| return elementsToAdd ? items.splice(start, deleteCount, elementsToAdd) : items.splice(start, deleteCount); | ||
| //if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| public move(x, y) { | ||
| this.splice(y, 0, this.splice(x, 1)[0]); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| } | ||
| /** | ||
| It represents binding to relative path for parent object. | ||
| */ | ||
| export class PathParentBinding implements IPathObjectBinding { | ||
| //converter:any; | ||
| constructor(private parentBinding: IPathObjectBinding, public relativePath, public valueConverter?: IValueConverter) { | ||
| //this.converter.format = Utils.partial(valueConverter,.partial() | ||
| } | ||
| //wrapped properties - delegate call to parent | ||
| public get source(): IPathObjectBinder { | ||
| return this.parentBinding.source; | ||
| } | ||
| public get provider(): (data) => IPathObjectBinder { | ||
| return this.parentBinding.provider; | ||
| } | ||
| public get root():Binding{ | ||
| return this.parentBinding.root; | ||
| } | ||
| public get parent():Binding{ | ||
| return this.parentBinding; | ||
| } | ||
| public get notifyChange() { | ||
| return this.parentBinding.notifyChange; | ||
| } | ||
| public set notifyChange(value: INotifyChange) { | ||
| this.parentBinding.notifyChange = value; | ||
| } | ||
| public get requestChange(): IRequestChange { | ||
| return (value) => { | ||
| this.value = value; | ||
| } | ||
| } | ||
| //concatenate path | ||
| public get path(): string { | ||
| if (this.parentBinding.path === undefined) return this.relativePath; | ||
| return [this.parentBinding.path, this.relativePath].join("."); | ||
| } | ||
| public get value() { | ||
| var value = this.source.getValue(this.path); | ||
| //get value - optional call converter | ||
| return this.valueConverter !== undefined ? this.valueConverter.format(value) : value; | ||
| } | ||
| public set value(value: any) { | ||
| //check if the value is really changed - strict equality | ||
| var previousValue = this.source.getValue(this.path); | ||
| var convertedValueToBeSet = this.valueConverter !== undefined ? this.valueConverter.parse(value) : value; | ||
| if (previousValue === convertedValueToBeSet) return; | ||
| //set value - optional call converter | ||
| this.source.setValue(this.path, convertedValueToBeSet); | ||
| if (this.notifyChange !== undefined) this.notifyChange(); | ||
| } | ||
| } | ||
| /** | ||
| * Provides a way to apply custom logic to a binding. | ||
| * It enables to make bi-directional convertions between source (data) and target (view) binding. | ||
| * | ||
| * + apply various formats to values | ||
| * + parse values from user input | ||
| */ | ||
| export interface IValueConverter { | ||
| /** | ||
| * Convert value into another value before return binding getter. Typically from model(data) to view. | ||
| * @param value - source binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| format?(value, parameters?); | ||
| /** | ||
| * Convert value into another value before call binding setter. Typically from view to model(data). | ||
| * @param value - target binding object (value) | ||
| * @param parameters - enable parametrization of conversion | ||
| */ | ||
| parse?(value, parameters?); | ||
| } | ||
| export class CurryConverter implements IValueConverter { | ||
| private formatFce; | ||
| private parseFce; | ||
| constructor(converter: IValueConverter, args: any) { | ||
| this.formatFce = this.curryParameters(converter.format, [args]); | ||
| this.parseFce = this.curryParameters(converter.parse, [args]); | ||
| } | ||
| private curryParameters(fn, args) { | ||
| return function () { | ||
| return fn.apply(this, Array.prototype.slice.call(arguments).concat(args)); | ||
| }; | ||
| } | ||
| public format(value) { | ||
| return this.formatFce(value); | ||
| } | ||
| public parse(value) { | ||
| return this.parseFce(value); | ||
| } | ||
| } |
| import Provider from './FreezerProvider'; | ||
| import { BinderCore } from './Binder'; | ||
| export default class Binder { | ||
| static bindTo(parent, path?: string, converter?, converterParams?): any { | ||
| return BinderCore.bindTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| static bindArrayTo(parent, path?: string, converter?, converterParams?): any { | ||
| return BinderCore.bindArrayTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| } |
| var Freezer = require('freezer-js'); | ||
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class FreezerPathObjectBinder implements IPathObjectBinder { | ||
| private freezer; | ||
| constructor(private source: any) { | ||
| this.freezer = new Freezer(source); | ||
| } | ||
| public subscribe(updateFce) { | ||
| this.freezer.on('update', function (state, prevState) { | ||
| if (updateFce !== undefined) updateFce(state, prevState) | ||
| } | ||
| ); | ||
| } | ||
| public getValue(path?: string) { | ||
| if (path === undefined) return this.freezer.get(); | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| } | ||
| public setValue(path: string, value: string) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| var property = FreezerPathObjectBinder.getProperty(path); | ||
| parent.set(property, value); | ||
| } | ||
| private getParent(path: string) { | ||
| var state = this.freezer.get(); | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(state, path.substring(0, last)) : state; | ||
| } | ||
| static getProperty(path): string { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| } | ||
| private string_to_ref(obj, s) { | ||
| var parts = s.split('.'); | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) newObj = obj.set(parts[0], {}); | ||
| if (!parts[1]) { | ||
| return newObj | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| } | ||
| } | ||
| import Provider from './MobxProvider'; | ||
| import { BinderCore } from './Binder'; | ||
| export default class Binder { | ||
| static bindTo(parent, path?: string, converter?, converterParams?): any { | ||
| return BinderCore.bindTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| static bindArrayTo(parent, path?: string, converter?, converterParams?): any { | ||
| return BinderCore.bindArrayTo(Provider, parent, path, converter, converterParams); | ||
| } | ||
| } |
| import { extendObservable, isObservable, autorun, observable, computed } from 'mobx'; | ||
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class MobxPathObjectBinder implements IPathObjectBinder { | ||
| private mobxSource; | ||
| private current; | ||
| private previous; | ||
| constructor(source: any) { | ||
| this.mobxSource = observable(source); | ||
| this.current = computed(() => JSON.stringify(this.mobxSource)); | ||
| //console.log('init'); | ||
| // autorun(() => { | ||
| // console.log(this.json.get());//'safda'); | ||
| // //if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // }); | ||
| } | ||
| public subscribe(updateFce) { | ||
| var previousState; | ||
| if (updateFce !== undefined) autorun( | ||
| () => { | ||
| var current = this.current.get() | ||
| updateFce(current, this.previous); | ||
| this.previous = current; | ||
| }); | ||
| //if (updateFce!==undefined) autorun(updateFce); | ||
| } | ||
| public getValue(path: string) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| if (path === undefined) return parent; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| var value = parent[property]; | ||
| if (value === undefined && !parent.hasOwnProperty(property)) { | ||
| this.setValueAsObservable(parent, property); | ||
| } | ||
| return parent[property]; | ||
| } | ||
| public setValue(path: string, value: string) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| var property = MobxPathObjectBinder.getProperty(path); | ||
| //parent[property] = observable(value); | ||
| if (isObservable(parent, property)) { | ||
| parent[property] = value; | ||
| return; | ||
| } | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| extendObservable(parent, newProps); | ||
| //console.log(parent[property]); | ||
| } | ||
| private setValueAsObservable(parent: Object, property: string, value?: any) { | ||
| var newProps = {}; | ||
| newProps[property] = value; | ||
| extendObservable(parent, newProps); | ||
| } | ||
| private getParent(path: string) { | ||
| if (path === undefined) return this.mobxSource; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.mobxSource, path.substring(0, last)) : this.mobxSource; | ||
| } | ||
| static getProperty(path): string { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| } | ||
| private string_to_ref(obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| } | ||
| } | ||
| import { IPathObjectBinder } from './DataBinding'; | ||
| /** | ||
| It wraps getting and setting object properties by setting path expression (dotted path - e.g. "Data.Person.FirstName", "Data.Person.LastName") | ||
| */ | ||
| export default class PathObjectBinder implements IPathObjectBinder { | ||
| constructor(private source: any) { | ||
| } | ||
| public subscribe(updateFce) { | ||
| // this.freezer.on('update',function(state,prevState){ | ||
| // if (updateFce!==undefined) updateFce(state,prevState)} | ||
| // ); | ||
| } | ||
| public getValue(path: string) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| if (path === undefined) return parent; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| return parent[property]; | ||
| } | ||
| public setValue(path: string, value: string) { | ||
| var parent = this.getParent(path); | ||
| if (parent === undefined) return; | ||
| var property = PathObjectBinder.getProperty(path); | ||
| parent[property] = value; | ||
| } | ||
| private getParent(path: string) { | ||
| if (path === undefined) return this.source; | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? this.string_to_ref(this.source, path.substring(0, last)) : this.source; | ||
| } | ||
| static getProperty(path): string { | ||
| var last = path.lastIndexOf("."); | ||
| return last != -1 ? path.substring(last + 1, path.length) : path; | ||
| } | ||
| private string_to_ref(obj, s) { | ||
| var parts = s.split('.'); | ||
| //experimental - support for square brackets | ||
| //var arrayExp = /\[(\d*)\]/; | ||
| //var firstExp = parts[0]; | ||
| //var matches = arrayExp.exec(firstExp); | ||
| //var newObj; | ||
| //if (!!matches){ | ||
| // firstExp = firstExp.replace(matches[0],""); | ||
| // var newArray = obj[firstExp][matche]; | ||
| // if (newArray === undefined) newArray = []; | ||
| // newObj = newArray[matches[1]]; | ||
| //} | ||
| //else{ | ||
| // newObj = obj[firstExp]; | ||
| // if (newObj === undefined) newObj = obj[firstExp] = {}; | ||
| //} | ||
| //var newObj = !!matches? obj[firstExp.replace(matches[0],"")][matches[1]]:obj[firstExp]; | ||
| var newObj = obj[parts[0]]; | ||
| if (newObj === undefined) newObj = obj[parts[0]] = {}; | ||
| if (!parts[1]) { | ||
| return newObj | ||
| } | ||
| parts.splice(0, 1); | ||
| var newString = parts.join('.'); | ||
| return this.string_to_ref(newObj, newString); | ||
| } | ||
| } |
| var Freezer = require('freezer-js'); | ||
| var expect1 = require('expect.js'); | ||
| import MobxBinder from '../src/MobxBinder'; | ||
| import { PersonConverter } from './utils/converters'; | ||
| import { observable, reaction } from 'mobx'; | ||
| import { get, set } from 'lodash'; | ||
| describe('DataBinding - Mobx reactions', function () { | ||
| var initValues = { firstName: "Roman", lastName: "Samec", email: "email" }; | ||
| var changedValues = { firstName: "Roman changed", lastName: "Samec changed", email: "email changed" }; | ||
| it('bind values and check reactions', function () { | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Person": { | ||
| // "FirstName": initValues.firstName, | ||
| // "LastName": initValues.lastName, | ||
| // "Contact": { | ||
| // "Email": initValues.email | ||
| // } | ||
| } | ||
| } | ||
| }; | ||
| //exec | ||
| var root = MobxBinder.bindTo(data.Data); | ||
| //var person = Binder.bindTo(root, "Person"); | ||
| var firstName = MobxBinder.bindTo(root, "Person.FirstName"); | ||
| var lastName = MobxBinder.bindTo(root, "Person.LastName"); | ||
| var email = MobxBinder.bindTo(root, "Person.Contact.Email"); | ||
| var converter = new PersonConverter(); | ||
| //exec | ||
| var fullName = MobxBinder.bindTo(root, "Person", converter); | ||
| //verify | ||
| root.source.subscribe((state, previous) => { | ||
| //console.log(state, previous) | ||
| }); | ||
| // reaction("FullName", | ||
| // () => {return firstName.value + ' ' + lastName.value}, | ||
| // (fullName) => {console.log(fullName)}); | ||
| //var val = firstName.value; | ||
| // console.log("und: " + val); | ||
| // reaction("First value", | ||
| // () => { | ||
| // return firstName.value | ||
| // }, | ||
| // (val) => {console.log(val)},true); | ||
| reaction("Person converter", | ||
| () => { | ||
| return fullName.value | ||
| }, | ||
| (val) => { console.log(val) }, true); | ||
| //verify pathes | ||
| expect1(firstName.path).to.equal("Person.FirstName"); | ||
| expect1(lastName.path).to.equal("Person.LastName"); | ||
| expect1(email.path).to.equal("Person.Contact.Email"); | ||
| //verify value getter | ||
| // expect1(firstName.value).to.equal(initValues.firstName); | ||
| // expect1(lastName.value).to.equal(initValues.lastName); | ||
| // expect1(email.value).to.equal(initValues.email); | ||
| //verify initial values at the source object | ||
| // expect1(root.value.Person.FirstName).to.equal(initValues.firstName); | ||
| // expect1(root.value.Person.LastName).to.equal(initValues.lastName); | ||
| // expect1(root.value.Person.Contact.Email).to.equal(initValues.email); | ||
| //exec -> setter -> change values | ||
| firstName.value = initValues.firstName; | ||
| lastName.value = initValues.lastName; | ||
| email.value = initValues.email; | ||
| // reaction("Person converter 2", | ||
| // () => { | ||
| // return fullName.value | ||
| // }, | ||
| // (val) => {console.log(val)},true); | ||
| firstName.value = changedValues.firstName; | ||
| lastName.value = changedValues.lastName; | ||
| email.value = changedValues.email; | ||
| //verify value getter | ||
| expect1(firstName.value).to.equal(changedValues.firstName); | ||
| expect1(lastName.value).to.equal(changedValues.lastName); | ||
| expect1(email.value).to.equal(changedValues.email); | ||
| //verify changed values at the source object | ||
| expect1(root.value.Person.FirstName).to.equal(changedValues.firstName); | ||
| expect1(root.value.Person.LastName).to.equal(changedValues.lastName); | ||
| expect1(root.value.Person.Contact.Email).to.equal(changedValues.email); | ||
| }); | ||
| }); | ||
| /* | ||
| describe('Freezer test', function () { | ||
| // Let's create a freezer object | ||
| var freezer = new Freezer({ | ||
| app: { | ||
| human: { 0: {} }, | ||
| dog: {} | ||
| } | ||
| }); | ||
| // Listen to changes in the state | ||
| freezer.on('update', function (currentState, prevState) { | ||
| // currentState will have the new state for your app | ||
| // prevState contains the old state, in case you need | ||
| // to do some comparisons | ||
| console.log('I was updated'); | ||
| }); | ||
| it('bind values and check reactions', function (done) { | ||
| // Let's get the frozen data stored | ||
| let state = freezer.get(); | ||
| // setTimeout(() => {state.app.human.set(0, { firstName: 'Bernd' })},10); | ||
| // setTimeout(() => {state.app.dog.set(99, { name: 'Brutus' })},10); | ||
| setTimeout(() => { | ||
| state.app.human.set(0, { firstName: 'Bernd' }); | ||
| state.app.dog.set(99, { name: 'Brutus' }); | ||
| //console.log( state.app === freezer.get().app); | ||
| console.log(JSON.stringify(freezer.get())); | ||
| //console.log(JSON.stringify(state.app)); | ||
| setTimeout(() => { | ||
| let state = freezer.get(); | ||
| state.app.human.set(0, Object.assign({}, { lastName: 'Wessels', dog: state.app.dog[99] }, state.app.human[0])); | ||
| setTimeout(() => { | ||
| let state = freezer.get(); | ||
| state.app.dog.set(99, Object.assign({}, { age: 88 }, state.app.dog[99])); | ||
| //refersh state; | ||
| state = freezer.get(); | ||
| console.log(JSON.stringify(state)); | ||
| //human | ||
| expect1(state.app.human[0].dog.name).to.equal("Brutus"); | ||
| expect1(state.app.human[0].dog.age).to.equal(88) | ||
| //dog | ||
| expect1(state.app.dog[99].name).to.equal("Brutus"); | ||
| expect1(state.app.dog[99].age).to.equal(88); | ||
| done(); | ||
| }, 100); | ||
| }, 100); | ||
| }, 100); | ||
| }); | ||
| }); | ||
| describe('Freezer pivot test', function () { | ||
| // Let's create a freezer object | ||
| var freezer = new Freezer({ | ||
| people: { | ||
| John: { age: 23 }, | ||
| Alice: { age: 40 } | ||
| } | ||
| }); | ||
| var state = freezer.get(); | ||
| var john = state.people.John; | ||
| var alice = state.people.Alice; | ||
| state.people.set("Karel", {}) | ||
| it('bind values and check reactions', function (done) { | ||
| // Let's get the frozen data stored | ||
| // If we don't pivot, the updated node is returned | ||
| // update = freezer.get().people.John.set({ age: 18 }); | ||
| // console.log(update); // {age: 18} | ||
| // Listen to changes in the state | ||
| freezer.on('update', function (currentState, prevState) { | ||
| // currentState will have the new state for your app | ||
| // prevState contains the old state, in case you need | ||
| // to do some comparisons | ||
| console.log('I was updated'); | ||
| console.log(currentState); | ||
| console.log(freezer.get()); | ||
| done(); | ||
| }); | ||
| setTimeout(function () { | ||
| john.set({ age: 18 }); | ||
| }, 10); | ||
| setTimeout(function () { | ||
| alice.set({ age: 30 }); | ||
| }, 10); | ||
| // If we want to update two people at | ||
| // a time we need to pivot | ||
| // var update = freezer.get().people.pivot() | ||
| // .John.set({ age: 30 }) | ||
| // .Alice.set({ age: 30 }) | ||
| // ; | ||
| //console.log(update); | ||
| }); | ||
| }); | ||
| */ | ||
| describe('Freezer props test', function () { | ||
| var data = observable({ | ||
| FirstName: 'Roman', | ||
| LastName: 'Samec' | ||
| }); | ||
| // Let's create a freezer object | ||
| var freezer = new Freezer({ | ||
| boxes: [ | ||
| { | ||
| name: 'Input_FirstName', | ||
| props: { | ||
| valueLink: {} | ||
| } | ||
| }, | ||
| { | ||
| name: 'Input_LastName', | ||
| props: { | ||
| valueLink: {} | ||
| } | ||
| }, | ||
| { | ||
| name: 'LastName', | ||
| bindings: { | ||
| content: () => { return data.LastName } | ||
| }, | ||
| props: { | ||
| //content: 'Samec' | ||
| } | ||
| }, | ||
| { | ||
| name: 'FullName', | ||
| bindings: { | ||
| content: () => { return data.FirstName + data.LastName } | ||
| }, | ||
| props: { | ||
| //content: 'Roman Samec' | ||
| } | ||
| }] | ||
| }); | ||
| var state = freezer.get(); | ||
| it('bind values and check reactions', function (done) { | ||
| // Let's get the frozen data stored | ||
| for (var i = 0; i !== state.boxes.length; i++) { | ||
| let box = state.boxes[i]; | ||
| if (box.bindings === undefined) { | ||
| //box.props.set('valueLink',{}); | ||
| continue; | ||
| } | ||
| } | ||
| state = freezer.get(); | ||
| for (var i = 0; i !== state.boxes.length; i++) { | ||
| let currentCursor: Array<string | number> = ['boxes']; | ||
| let box = state.boxes[i]; | ||
| currentCursor.push(i); | ||
| for (let prop in box.bindings) { | ||
| let bindingProp = box.bindings[prop]; | ||
| let props = box.props; | ||
| //currentCursor.push(prop); | ||
| reaction(box.name, bindingProp, | ||
| (val) => { | ||
| get(freezer.get(), currentCursor).set(prop, val); | ||
| //props.set(prop, val); | ||
| console.log(currentCursor.join(',')) | ||
| }, false); | ||
| } | ||
| } | ||
| // Listen to changes in the state | ||
| freezer.on('update', function (currentState, prevState) { | ||
| // currentState will have the new state for your app | ||
| // prevState contains the old state, in case you need | ||
| // to do some comparisons | ||
| console.log('I was updated'); | ||
| //console.log(currentState); | ||
| //var newState = freezer.get(); | ||
| var newState = currentState; | ||
| console.log(JSON.stringify(newState)); | ||
| //expect1(newState.boxes[2].props.content).to.equal("Smith"); | ||
| //expect1(newState.boxes[3].props.content).to.equal("RomanSmith"); | ||
| //done(); | ||
| }); | ||
| setTimeout(function () { | ||
| data.LastName = "Smith"; | ||
| setTimeout(function () { | ||
| data.LastName = "Smith 2"; | ||
| setTimeout(function () { | ||
| data.LastName = "Smith 3"; | ||
| done(); | ||
| }, 10); | ||
| }, 10); | ||
| }, 10); | ||
| // If we want to update two people at | ||
| // a time we need to pivot | ||
| // var update = freezer.get().people.pivot() | ||
| // .John.set({ age: 30 }) | ||
| // .Alice.set({ age: 30 }) | ||
| // ; | ||
| //console.log(update); | ||
| }); | ||
| }); |
| import * as BindTo from '../src/DataBinding'; | ||
| import SimpleBinder from '../src/Binder'; | ||
| import MobxBinder from '../src/MobxBinder'; | ||
| import FreezerBinder from '../src/FreezerBinder'; | ||
| import { DateValueConverter, PersonConverter, DateValueSuffixConverter, ArraySizeConverter, ArrayConverter } from './utils/converters'; | ||
| var expect1 = require('expect.js'); | ||
| var mapObject = function (obj, callback) { | ||
| var result = {}; | ||
| Object.keys(obj).forEach(function (key) { | ||
| result[key] = callback.call(obj, obj[key], key, obj); | ||
| }); | ||
| return result; | ||
| }; | ||
| var testSuite = (Binder: BindTo.BinderStatic) => { | ||
| var initValues = { firstName: "Roman", lastName: "Samec", email: "email" }; | ||
| var changedValues = { firstName: "Roman changed", lastName: "Samec changed", email: "email changed" }; | ||
| var execAndVerifyPersonProperties = function (bindings, initValues, changedValues) { | ||
| var root = bindings["root"]; | ||
| var firstName = bindings["firstName"]; | ||
| var lastName = bindings["lastName"]; | ||
| var email = bindings["email"]; | ||
| root.source.subscribe((state, previous) => { | ||
| //console.log(state, previous) | ||
| }); | ||
| //verify pathes | ||
| expect1(firstName.path).to.equal("Person.FirstName"); | ||
| expect1(lastName.path).to.equal("Person.LastName"); | ||
| expect1(email.path).to.equal("Person.Contact.Email"); | ||
| //verify value getter | ||
| expect1(firstName.value).to.equal(initValues.firstName); | ||
| expect1(lastName.value).to.equal(initValues.lastName); | ||
| expect1(email.value).to.equal(initValues.email); | ||
| //verify initial values at the source object | ||
| expect1(root.value.Person.FirstName).to.equal(initValues.firstName); | ||
| expect1(root.value.Person.LastName).to.equal(initValues.lastName); | ||
| expect1(root.value.Person.Contact.Email).to.equal(initValues.email); | ||
| //exec -> setter -> change values | ||
| firstName.value = changedValues.firstName; | ||
| lastName.value = changedValues.lastName; | ||
| email.value = changedValues.email; | ||
| //verify value getter | ||
| expect1(firstName.value).to.equal(changedValues.firstName); | ||
| expect1(lastName.value).to.equal(changedValues.lastName); | ||
| expect1(email.value).to.equal(changedValues.email); | ||
| //verify changed values at the source object | ||
| expect1(root.value.Person.FirstName).to.equal(changedValues.firstName); | ||
| expect1(root.value.Person.LastName).to.equal(changedValues.lastName); | ||
| expect1(root.value.Person.Contact.Email).to.equal(changedValues.email); | ||
| }; | ||
| it('bind to properties by path', function () { | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Person": { | ||
| "FirstName": initValues.firstName, | ||
| "LastName": initValues.lastName, | ||
| "Contact": { | ||
| "Email": initValues.email | ||
| } | ||
| } | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindTo(data.Data); | ||
| var person = Binder.bindTo(root, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: root, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| expect1(person.path).to.equal("Person"); | ||
| execAndVerifyPersonProperties(nestedBindings, initValues, changedValues); | ||
| }); | ||
| it('bind to properties by path - empty object', function () { | ||
| //when | ||
| var data = { | ||
| Data: {} | ||
| }; | ||
| //exec | ||
| var root = Binder.bindTo(data.Data); | ||
| var firstName = Binder.bindTo(root, "Person.FirstName"); | ||
| var lastName = Binder.bindTo(root, "Person.LastName"); | ||
| var email = Binder.bindTo(root, "Person.Contact.Email"); | ||
| var flatBindings = { | ||
| root: root, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(flatBindings, {}, changedValues); | ||
| }); | ||
| //it('bind arrays - simple - square brackets', function () { | ||
| // //when | ||
| // var data = { | ||
| // Data: { | ||
| // Hobbies:[ | ||
| // {HobbyName:"bandbington"}, | ||
| // {HobbyName:"tennis"} | ||
| // ] | ||
| // } | ||
| // }; | ||
| // | ||
| // //exec | ||
| // //var root = Binder.bindTo(data.Data); | ||
| // //var email = Binder.bindTo(root,"Hobbies[0].HobbyName"); | ||
| // | ||
| // var row = Binder.bindTo(data,"Data.Hobbies[0]"); | ||
| // var email = Binder.bindTo(row,"HobbyName"); | ||
| // | ||
| // //verify | ||
| // expect1(email.path).to.equal("Data.Hobbies[0].HobbyName"); | ||
| // | ||
| // email.value = "value changed"; | ||
| // | ||
| // expect1(email.value).to.equal("value changed"); | ||
| // | ||
| // expect1(data.Data.Hobbies[0].HobbyName).to.equal("value changed"); | ||
| // | ||
| //}); | ||
| it('binding arrays', function () { | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "People": [ | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues.firstName, | ||
| "LastName": initValues.lastName, | ||
| "Contact": { | ||
| "Email": initValues.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| } | ||
| ] | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "People"); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues, changedValues); | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| }); | ||
| it('binding arrays - empty object', function () { | ||
| //when | ||
| var data = { | ||
| Data: {} | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "People"); | ||
| root.add(); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| root.add(); | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| }); | ||
| it('binding nested arrays', function () { | ||
| var initValues1: any = mapObject(initValues, function (item) { return item + "1" }); | ||
| var initValues2: any = mapObject(initValues, function (item) { return item + "2" }); | ||
| var changedValues1: any = mapObject(changedValues, function (item) { return item + "1" }); | ||
| var changedValues2: any = mapObject(changedValues, function (item) { return item + "2" }); | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Hobbies": [ | ||
| { | ||
| "People": [ | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues1.firstName, | ||
| "LastName": initValues1.lastName, | ||
| "Contact": { | ||
| "Email": initValues1.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues2.firstName, | ||
| "LastName": initValues2.lastName, | ||
| "Contact": { | ||
| "Email": initValues2.email | ||
| } | ||
| } | ||
| }, | ||
| ] | ||
| } | ||
| ] | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "Hobbies"); | ||
| var people = Binder.bindArrayTo(root.items[0], "People"); | ||
| //first person | ||
| var row = people.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues1, changedValues1); | ||
| //second person | ||
| row = people.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues2, changedValues2); | ||
| }); | ||
| it('binding arrays - move up', function () { | ||
| var initValues1: any = mapObject(initValues, function (item) { return item + "1" }); | ||
| var initValues2: any = mapObject(initValues, function (item) { return item + "2" }); | ||
| var initValues3: any = mapObject(initValues, function (item) { return item + "3" }); | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "People": [ | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues1.firstName, | ||
| "LastName": initValues1.lastName, | ||
| "Contact": { | ||
| "Email": initValues1.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues2.firstName, | ||
| "LastName": initValues2.lastName, | ||
| "Contact": { | ||
| "Email": initValues2.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues3.firstName, | ||
| "LastName": initValues3.lastName, | ||
| "Contact": { | ||
| "Email": initValues3.email | ||
| } | ||
| } | ||
| } | ||
| ] | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "People"); | ||
| //root.move(0,2); | ||
| root.move(0, 1); | ||
| root.move(1, 2); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues2, changedValues); | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues3, changedValues); | ||
| //second row | ||
| row = root.items[2]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues1, changedValues); | ||
| }); | ||
| it('binding arrays - move down', function () { | ||
| var initValues1: any = mapObject(initValues, function (item) { return item + "1" }); | ||
| var initValues2: any = mapObject(initValues, function (item) { return item + "2" }); | ||
| var initValues3: any = mapObject(initValues, function (item) { return item + "3" }); | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "People": [ | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues1.firstName, | ||
| "LastName": initValues1.lastName, | ||
| "Contact": { | ||
| "Email": initValues1.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues2.firstName, | ||
| "LastName": initValues2.lastName, | ||
| "Contact": { | ||
| "Email": initValues2.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues3.firstName, | ||
| "LastName": initValues3.lastName, | ||
| "Contact": { | ||
| "Email": initValues3.email | ||
| } | ||
| } | ||
| } | ||
| ] | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "People"); | ||
| root.move(2, 1); | ||
| root.move(1, 0); | ||
| //root.move(2,0); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues3, changedValues); | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues1, changedValues); | ||
| //second row | ||
| row = root.items[2]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, initValues2, changedValues); | ||
| }); | ||
| it('bind dates with value convertors', function () { | ||
| var fromDefault = new Date(2015, 0, 1); | ||
| var toDefault = new Date(2015, 0, 7); | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Vacation": { | ||
| "From": fromDefault, | ||
| "To": toDefault | ||
| } | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindTo(data.Data); | ||
| //exec | ||
| var vacation = Binder.bindTo(root, "Vacation"); | ||
| var from = Binder.bindTo(vacation, "From", new DateValueConverter()); | ||
| var to = Binder.bindTo(vacation, "To", new DateValueConverter()); | ||
| //verify | ||
| expect1(from.value).to.equal(fromDefault.toISOString().slice(0, 10)); | ||
| expect1(to.value).to.equal(toDefault.toISOString().slice(0, 10)); | ||
| //when | ||
| var fromChanged = new Date(2015, 1, 13); | ||
| var toChanged = new Date(2015, 1, 20); | ||
| //exec value | ||
| from.value = "2015/02/13"; | ||
| to.value = "2015/02/20"; | ||
| //verify | ||
| expect1(root.value.Vacation.From.toISOString().slice(0, 10)).to.equal(fromChanged.toISOString().slice(0, 10)); | ||
| expect1(root.value.Vacation.To.toISOString().slice(0, 10)).to.equal(toChanged.toISOString().slice(0, 10)); | ||
| }); | ||
| it('bind dates with value convertors with parameters', function () { | ||
| var fromDefault = new Date(2015, 0, 1); | ||
| var toDefault = new Date(2015, 0, 7); | ||
| var formatSuffix = "UTC"; | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Vacation": { | ||
| "From": fromDefault, | ||
| "To": toDefault | ||
| } | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindTo(data.Data); | ||
| //exec | ||
| var vacation = Binder.bindTo(root, "Vacation"); | ||
| var converter = new BindTo.CurryConverter(new DateValueSuffixConverter(), formatSuffix); | ||
| var from = Binder.bindTo(vacation, "From", converter); | ||
| var to = Binder.bindTo(vacation, "To", converter); | ||
| //verify | ||
| expect1(from.value).to.equal(fromDefault.toISOString().slice(0, 10) + formatSuffix); | ||
| expect1(to.value).to.equal(toDefault.toISOString().slice(0, 10) + formatSuffix); | ||
| //when | ||
| var fromChanged = new Date(2015, 1, 13); | ||
| var toChanged = new Date(2015, 1, 20); | ||
| //exec value | ||
| from.value = "2015/02/13" + formatSuffix; | ||
| to.value = "2015/02/20" + formatSuffix; | ||
| //verify | ||
| expect1(root.value.Vacation.From.toISOString().slice(0, 10)).to.equal(fromChanged.toISOString().slice(0, 10)); | ||
| expect1(root.value.Vacation.To.toISOString().slice(0, 10)).to.equal(toChanged.toISOString().slice(0, 10)); | ||
| }); | ||
| it('binding arrays - direct array', function () { | ||
| //when | ||
| var data = { Employees: [{}, {}] }; | ||
| //exec | ||
| var dataRoot = Binder.bindTo(data, "Employees"); | ||
| var root = Binder.bindArrayTo(dataRoot); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| //root.add(); | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| }); | ||
| it('binding arrays - using array size converters', function () { | ||
| //when | ||
| var data = { Count: 1 }; | ||
| //exec | ||
| var dataRoot = Binder.bindTo(data, "Count"); | ||
| var root = Binder.bindArrayTo(dataRoot, undefined, new ArraySizeConverter()); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| //root.add(); | ||
| dataRoot.value = 2; | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| }); | ||
| it('binding arrays - using array converters', function () { | ||
| //when | ||
| var data = { Employees: [{}] }; | ||
| //exec | ||
| var dataRoot = Binder.bindTo(data, "Employees", ArrayConverter); | ||
| var root = Binder.bindArrayTo(dataRoot); | ||
| //first row | ||
| var row = root.items[0]; | ||
| var person = Binder.bindTo(row, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| var nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| root.add(); | ||
| //dataRoot.value = 2; | ||
| //second row | ||
| row = root.items[1]; | ||
| person = Binder.bindTo(row, "Person"); | ||
| firstName = Binder.bindTo(person, "FirstName"); | ||
| lastName = Binder.bindTo(person, "LastName"); | ||
| email = Binder.bindTo(person, "Contact.Email"); | ||
| nestedBindings = { | ||
| root: row, | ||
| firstName: firstName, | ||
| lastName: lastName, | ||
| email: email | ||
| }; | ||
| //verify | ||
| execAndVerifyPersonProperties(nestedBindings, {}, changedValues); | ||
| }); | ||
| it('binding - root and parent property', function () { | ||
| //setup | ||
| const TIME_STAMP = new Date(); | ||
| var data = { | ||
| Data: { | ||
| "Person": { | ||
| "FirstName": initValues.firstName, | ||
| "LastName": initValues.lastName, | ||
| "Contact": { | ||
| "Email": initValues.email | ||
| } | ||
| } | ||
| } | ||
| }; | ||
| var root = Binder.bindTo(data.Data); | ||
| var person = Binder.bindTo(root, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| //exec | ||
| root['customCode'] = TIME_STAMP; | ||
| //verify parent | ||
| expect1(root.parent).to.equal(undefined); | ||
| expect1(email.parent).to.equal(person); | ||
| expect1(lastName.parent).to.equal(person); | ||
| expect1(firstName.parent).to.equal(person); | ||
| expect1(person.parent).to.equal(root); | ||
| //verify root | ||
| expect1(email.root['customCode']).to.equal(TIME_STAMP); | ||
| }); | ||
| it('binding - root and parent property - nested arrays', function () { | ||
| //setup | ||
| const TIME_STAMP = new Date(); | ||
| var initValues1: any = mapObject(initValues, function (item) { return item + "1" }); | ||
| var initValues2: any = mapObject(initValues, function (item) { return item + "2" }); | ||
| var changedValues1: any = mapObject(changedValues, function (item) { return item + "1" }); | ||
| var changedValues2: any = mapObject(changedValues, function (item) { return item + "2" }); | ||
| //when | ||
| var data = { | ||
| Data: { | ||
| "Hobbies": [ | ||
| { | ||
| "People": [ | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues1.firstName, | ||
| "LastName": initValues1.lastName, | ||
| "Contact": { | ||
| "Email": initValues1.email | ||
| } | ||
| } | ||
| }, | ||
| { | ||
| "Person": { | ||
| "FirstName": initValues2.firstName, | ||
| "LastName": initValues2.lastName, | ||
| "Contact": { | ||
| "Email": initValues2.email | ||
| } | ||
| } | ||
| }, | ||
| ] | ||
| } | ||
| ] | ||
| } | ||
| }; | ||
| //exec | ||
| var root = Binder.bindArrayTo(data.Data, "Hobbies"); | ||
| var hobbieRow = root.items[0]; | ||
| var people = Binder.bindArrayTo(hobbieRow, "People"); | ||
| //first person | ||
| var personRow = people.items[0]; | ||
| var person = Binder.bindTo(personRow, "Person"); | ||
| var firstName = Binder.bindTo(person, "FirstName"); | ||
| var lastName = Binder.bindTo(person, "LastName"); | ||
| var email = Binder.bindTo(person, "Contact.Email"); | ||
| //exec | ||
| root['customCode'] = TIME_STAMP; | ||
| //verify parent | ||
| expect1(root.parent).to.equal(undefined); | ||
| expect1(email.parent).to.equal(person); | ||
| expect1(lastName.parent).to.equal(person); | ||
| expect1(firstName.parent).to.equal(person); | ||
| expect1(person.parent).to.equal(personRow); | ||
| expect1(personRow.parent).to.equal(people); | ||
| expect1(people.parent).to.equal(hobbieRow); | ||
| expect1(hobbieRow.parent).to.equal(root); | ||
| //verify root | ||
| expect1(email.root['customCode']).to.equal(TIME_STAMP); | ||
| }); | ||
| } | ||
| describe('DataBinding - Freezer provider', function () { | ||
| testSuite(FreezerBinder); | ||
| }); | ||
| describe('DataBinding - Plain object provider', function () { | ||
| testSuite(SimpleBinder); | ||
| }); | ||
| describe('DataBinding - Mobx provider', function () { | ||
| testSuite(MobxBinder); | ||
| }); |
| "use strict"; | ||
| var DateValueConverter = (function () { | ||
| function DateValueConverter() { | ||
| } | ||
| DateValueConverter.prototype.format = function (value) { | ||
| if (value === undefined) | ||
| return value; | ||
| return value.toISOString().slice(0, 10); | ||
| }; | ||
| DateValueConverter.prototype.parse = function (value) { | ||
| if (value === undefined) | ||
| return value; | ||
| var regPattern = "\\d{4}\\/\\d{2}\\/\\d{2}"; | ||
| var dateString = value.match(regPattern); | ||
| return new Date(dateString); | ||
| }; | ||
| return DateValueConverter; | ||
| }()); | ||
| exports.DateValueConverter = DateValueConverter; | ||
| var PersonConverter = (function () { | ||
| function PersonConverter() { | ||
| } | ||
| PersonConverter.prototype.format = function (value) { | ||
| if (value === undefined) | ||
| return value; | ||
| return value.FirstName + ' ' + value.LastName; | ||
| }; | ||
| return PersonConverter; | ||
| }()); | ||
| exports.PersonConverter = PersonConverter; | ||
| var DateValueSuffixConverter = (function () { | ||
| function DateValueSuffixConverter() { | ||
| } | ||
| DateValueSuffixConverter.prototype.format = function (value, parameters) { | ||
| if (value === undefined) | ||
| return value; | ||
| if (parameters === undefined) | ||
| parameters = ""; | ||
| return value.toISOString().slice(0, 10) + parameters; | ||
| }; | ||
| DateValueSuffixConverter.prototype.parse = function (value) { | ||
| if (value === undefined) | ||
| return value; | ||
| var regPattern = "\\d{4}\\/\\d{2}\\/\\d{2}"; | ||
| var dateString = value.match(regPattern); | ||
| return new Date(dateString); | ||
| }; | ||
| return DateValueSuffixConverter; | ||
| }()); | ||
| exports.DateValueSuffixConverter = DateValueSuffixConverter; | ||
| ; | ||
| var ArraySizeConverter = (function () { | ||
| function ArraySizeConverter() { | ||
| } | ||
| ArraySizeConverter.prototype.format = function (count) { | ||
| return Array.apply(0, Array(count)) | ||
| .map(function (element, index) { | ||
| return { pageIndex: index }; | ||
| }); | ||
| }; | ||
| return ArraySizeConverter; | ||
| }()); | ||
| exports.ArraySizeConverter = ArraySizeConverter; | ||
| var ArrayConverter = (function () { | ||
| function ArrayConverter() { | ||
| } | ||
| ArrayConverter.prototype.format = function (input) { | ||
| return !!input ? input.length : 0; | ||
| }; | ||
| ArrayConverter.prototype.parse = function (count) { | ||
| return Array.apply(0, Array(count)) | ||
| .map(function (element, index) { | ||
| return { | ||
| Person: { | ||
| "FirstName": "Roman " + index, | ||
| "LastName": "Samec " + index, Addresses: [] | ||
| } | ||
| }; | ||
| }); | ||
| }; | ||
| return ArrayConverter; | ||
| }()); | ||
| exports.ArrayConverter = ArrayConverter; |
| export class DateValueConverter { | ||
| format(value) { | ||
| if (value === undefined) return value; | ||
| return value.toISOString().slice(0, 10); | ||
| } | ||
| parse(value) { | ||
| if (value === undefined) return value; | ||
| var regPattern = "\\d{4}\\/\\d{2}\\/\\d{2}"; | ||
| var dateString = value.match(regPattern); | ||
| return new Date(dateString); | ||
| } | ||
| } | ||
| export class PersonConverter { | ||
| format(value) { | ||
| if (value === undefined) return value; | ||
| return value.FirstName + ' ' + value.LastName; | ||
| } | ||
| } | ||
| export class DateValueSuffixConverter { | ||
| format(value, parameters) { | ||
| if (value === undefined) return value; | ||
| if (parameters === undefined) parameters = ""; | ||
| return value.toISOString().slice(0, 10) + parameters; | ||
| } | ||
| parse(value) { | ||
| if (value === undefined) return value; | ||
| var regPattern = "\\d{4}\\/\\d{2}\\/\\d{2}"; | ||
| var dateString = value.match(regPattern); | ||
| return new Date(dateString); | ||
| } | ||
| }; | ||
| export class ArraySizeConverter { | ||
| format(count) { | ||
| return Array.apply(0, Array(count)) | ||
| .map(function (element, index) { | ||
| return { pageIndex: index }; | ||
| }); | ||
| } | ||
| } | ||
| export class ArrayConverter { | ||
| format(input) { | ||
| return !!input ? input.length : 0; | ||
| } | ||
| parse(count) { | ||
| return Array.apply(0, Array(count)) | ||
| .map(function (element, index) { | ||
| return { | ||
| Person: { | ||
| "FirstName": "Roman " + index, | ||
| "LastName": "Samec " + index, Addresses: [] | ||
| } | ||
| }; | ||
| }); | ||
| } | ||
| } |
| { | ||
| "compilerOptions": { | ||
| "target": "es5", | ||
| "watch": true | ||
| //"experimentalDecorators": true | ||
| } | ||
| } |
-15
| { | ||
| "version": "v4", | ||
| "repo": "borisyankov/DefinitelyTyped", | ||
| "ref": "master", | ||
| "path": "typings", | ||
| "bundle": "typings/tsd.d.ts", | ||
| "installed": { | ||
| "mocha/mocha.d.ts": { | ||
| "commit": "49b821f06b711a86be349c4bbff4351467c024b9" | ||
| }, | ||
| "node/node.d.ts": { | ||
| "commit": "49b821f06b711a86be349c4bbff4351467c024b9" | ||
| } | ||
| } | ||
| } |
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
URL strings
Supply chain riskPackage contains fragments of external URLs or IP addresses, which the package may be accessing at runtime.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
URL strings
Supply chain riskPackage contains fragments of external URLs or IP addresses, which the package may be accessing at runtime.
Found 1 instance in 1 package
0
-100%0
-100%182970
-33.38%18
-51.35%3793
-34.02%323
-4.15%- Removed
- Removed
- Removed
- Removed