vasille 3.1.0 → 3.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -4
- package/lib/core/core.js +6 -12
- package/lib/node/node.js +2 -0
- package/lib/runner/web/binding/class.js +2 -0
- package/lib/runner/web/binding/style.js +1 -0
- package/lib/runner/web/runner.js +3 -0
- package/lib/value/expression.js +1 -0
- package/lib/value/pointer.js +1 -0
- package/package.json +2 -2
- package/types/core/core.d.ts +0 -5
- package/lib/models/array-model.js +0 -147
- package/lib/models/listener.js +0 -66
- package/lib/models/map-model.js +0 -59
- package/lib/models/model.js +0 -1
- package/lib/models/set-model.js +0 -55
- package/types/models/array-model.d.ts +0 -55
- package/types/models/listener.d.ts +0 -48
- package/types/models/map-model.d.ts +0 -34
- package/types/models/model.d.ts +0 -14
- package/types/models/set-model.d.ts +0 -33
package/README.md
CHANGED
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
* [Installation](#installation)
|
|
12
12
|
* [How to use Vasille](#how-to-use-vasille)
|
|
13
13
|
* [How SAFE is Vasille](#how-safe-is-vasille)
|
|
14
|
-
* [How
|
|
14
|
+
* [How INTUITIVE is Vasille](#how-intuitive-is-vasille)
|
|
15
15
|
* [How POWERFUL is Vasille](#how-powerful-is-vasille)
|
|
16
16
|
* [Road Map](#road-map)
|
|
17
17
|
|
|
@@ -44,6 +44,7 @@ $ npx degit vasille-js/example-javascript my-project
|
|
|
44
44
|
|
|
45
45
|
### Full documentation:
|
|
46
46
|
* [Learn `Vasille` in 5 minutes](https://github.com/vasille-js/vasille-js/blob/v3/doc/V3-API.md)
|
|
47
|
+
* [Vasille Router Documentation](https://github.com/vasille-js/vasille-js/blob/v3/doc/Router-API.md)
|
|
47
48
|
|
|
48
49
|
### Examples
|
|
49
50
|
* [TypeScript Example](https://github.com/vasille-js/example-typescript)
|
|
@@ -60,7 +61,7 @@ The safe of your application is ensured by
|
|
|
60
61
|
* `strong typing` makes your javascript/typescript code safe as C++ code.
|
|
61
62
|
All entities of `vasille` core library are strongly typed, including:
|
|
62
63
|
* data fields & properties.
|
|
63
|
-
* computed properties (function parameters
|
|
64
|
+
* computed properties (function parameters and result).
|
|
64
65
|
* methods.
|
|
65
66
|
* events (defined handlers & event emit).
|
|
66
67
|
* DOM events & DOM operation (attributing, styling, etc.).
|
|
@@ -68,7 +69,7 @@ All entities of `vasille` core library are strongly typed, including:
|
|
|
68
69
|
* references to children.
|
|
69
70
|
* No asynchronous code, when the line of code is executed, the DOM and reactive things are already synced.
|
|
70
71
|
|
|
71
|
-
## How
|
|
72
|
+
## How INTUITIVE is Vasille
|
|
72
73
|
|
|
73
74
|
There is the "Hello World":
|
|
74
75
|
```typescript jsx
|
|
@@ -105,7 +106,7 @@ All of these are supported:
|
|
|
105
106
|
* [x] Develop the `Vasille Babel Plugin`.
|
|
106
107
|
* [x] `100%` Test Coverage fot babel plugin.
|
|
107
108
|
* [x] Add CSS support (define styles in components).
|
|
108
|
-
* [
|
|
109
|
+
* [x] Add router.
|
|
109
110
|
* [ ] Add SSR (server side rendering).
|
|
110
111
|
* [ ] Develop tools extension for debugging.
|
|
111
112
|
|
package/lib/core/core.js
CHANGED
|
@@ -10,11 +10,6 @@ import { OwningPointer, Pointer } from "../value/pointer.js";
|
|
|
10
10
|
export class Reactive extends Destroyable {
|
|
11
11
|
constructor(input) {
|
|
12
12
|
super();
|
|
13
|
-
/**
|
|
14
|
-
* A list of user-defined values
|
|
15
|
-
* @type {Set}
|
|
16
|
-
*/
|
|
17
|
-
this._watch = new Set();
|
|
18
13
|
/**
|
|
19
14
|
* A list of user-defined bindings
|
|
20
15
|
* @type {Set}
|
|
@@ -30,7 +25,7 @@ export class Reactive extends Destroyable {
|
|
|
30
25
|
*/
|
|
31
26
|
ref(value, name) {
|
|
32
27
|
const ref = new Reference(value);
|
|
33
|
-
this.
|
|
28
|
+
this.bindings.add(ref);
|
|
34
29
|
if (name) {
|
|
35
30
|
this.addState("ref", name, ref);
|
|
36
31
|
}
|
|
@@ -43,7 +38,7 @@ export class Reactive extends Destroyable {
|
|
|
43
38
|
*/
|
|
44
39
|
forward(value, name) {
|
|
45
40
|
const mirror = new Pointer(value);
|
|
46
|
-
this.
|
|
41
|
+
this.bindings.add(mirror);
|
|
47
42
|
if (name) {
|
|
48
43
|
this.addState("forward", name, mirror);
|
|
49
44
|
}
|
|
@@ -56,7 +51,8 @@ export class Reactive extends Destroyable {
|
|
|
56
51
|
*/
|
|
57
52
|
own(value, name) {
|
|
58
53
|
const pointer = new OwningPointer(value);
|
|
59
|
-
this.
|
|
54
|
+
this.bindings.add(pointer);
|
|
55
|
+
/* istanbul ignore else */
|
|
60
56
|
if (name) {
|
|
61
57
|
this.addState("own", name, pointer);
|
|
62
58
|
}
|
|
@@ -81,7 +77,7 @@ export class Reactive extends Destroyable {
|
|
|
81
77
|
* @param values
|
|
82
78
|
*/
|
|
83
79
|
watch(func, values) {
|
|
84
|
-
this.
|
|
80
|
+
this.bindings.add(new Expression(func, values));
|
|
85
81
|
}
|
|
86
82
|
/**
|
|
87
83
|
* Creates a computed value
|
|
@@ -92,7 +88,7 @@ export class Reactive extends Destroyable {
|
|
|
92
88
|
*/
|
|
93
89
|
expr(func, values, name) {
|
|
94
90
|
const res = new Expression(func, values);
|
|
95
|
-
this.
|
|
91
|
+
this.bindings.add(res);
|
|
96
92
|
if (name) {
|
|
97
93
|
this.addState("expr", name, res);
|
|
98
94
|
}
|
|
@@ -110,8 +106,6 @@ export class Reactive extends Destroyable {
|
|
|
110
106
|
}
|
|
111
107
|
destroy() {
|
|
112
108
|
super.destroy();
|
|
113
|
-
this._watch.forEach(value => value.destroy());
|
|
114
|
-
this._watch.clear();
|
|
115
109
|
this.bindings.forEach(binding => binding.destroy());
|
|
116
110
|
this.bindings.clear();
|
|
117
111
|
this.onDestroy?.();
|
package/lib/node/node.js
CHANGED
|
@@ -33,6 +33,7 @@ export class Root extends Reactive {
|
|
|
33
33
|
let first;
|
|
34
34
|
for (const child of this.children) {
|
|
35
35
|
first = child.findFirstChild();
|
|
36
|
+
/* istanbul ignore else */
|
|
36
37
|
if (first) {
|
|
37
38
|
break;
|
|
38
39
|
}
|
|
@@ -322,6 +323,7 @@ export class DebugNode extends Fragment {
|
|
|
322
323
|
super(input, runner, ":debug");
|
|
323
324
|
}
|
|
324
325
|
destroy() {
|
|
326
|
+
/* istanbul ignore else */
|
|
325
327
|
if (this.handler) {
|
|
326
328
|
this.input.text.off(this.handler);
|
|
327
329
|
}
|
|
@@ -27,10 +27,12 @@ export class DynamicalClassBinding extends Binding {
|
|
|
27
27
|
super(value);
|
|
28
28
|
this.current = "";
|
|
29
29
|
this.init((value) => {
|
|
30
|
+
/* istanbul ignore else */
|
|
30
31
|
if (this.current != value) {
|
|
31
32
|
if (this.current.length) {
|
|
32
33
|
removeClass(node, this.current);
|
|
33
34
|
}
|
|
35
|
+
/* istanbul ignore else */
|
|
34
36
|
if (value.length) {
|
|
35
37
|
addClass(node, value);
|
|
36
38
|
}
|
|
@@ -23,6 +23,7 @@ export class StyleBinding extends Binding {
|
|
|
23
23
|
constructor(node, name, value) {
|
|
24
24
|
super(value);
|
|
25
25
|
this.init(value => {
|
|
26
|
+
/* istanbul ignore else */
|
|
26
27
|
if (node.element instanceof HTMLElement) {
|
|
27
28
|
node.element.style.setProperty(name, stringifyStyleValue(value));
|
|
28
29
|
}
|
package/lib/runner/web/runner.js
CHANGED
|
@@ -65,7 +65,9 @@ export class Tag extends AbstractTag {
|
|
|
65
65
|
this.register(new AttributeBinding(this, name, value));
|
|
66
66
|
}
|
|
67
67
|
else {
|
|
68
|
+
/* istanbul ignore else */
|
|
68
69
|
if (typeof value === "boolean") {
|
|
70
|
+
/* istanbul ignore else */
|
|
69
71
|
if (value) {
|
|
70
72
|
this.node.setAttribute(name, "");
|
|
71
73
|
}
|
|
@@ -140,6 +142,7 @@ export class Runner {
|
|
|
140
142
|
}
|
|
141
143
|
insertBefore(node, before) {
|
|
142
144
|
const parent = before.parentElement;
|
|
145
|
+
/* istanbul ignore else */
|
|
143
146
|
if (parent) {
|
|
144
147
|
parent.insertBefore(node, before);
|
|
145
148
|
}
|
package/lib/value/expression.js
CHANGED
package/lib/value/pointer.js
CHANGED
package/package.json
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "vasille",
|
|
3
|
-
"description": "The first Developer eXperience
|
|
3
|
+
"description": "The first Developer eXperience Orientated front-end framework (core library).",
|
|
4
4
|
"main": "lib/index.js",
|
|
5
5
|
"types": "types/index.d.ts",
|
|
6
|
-
"version": "3.
|
|
6
|
+
"version": "3.2.0",
|
|
7
7
|
"exports": {
|
|
8
8
|
".": {
|
|
9
9
|
"types": "./types/index.d.ts",
|
package/types/core/core.d.ts
CHANGED
|
@@ -8,11 +8,6 @@ import { Pointer } from "../value/pointer.js";
|
|
|
8
8
|
* @extends Destroyable
|
|
9
9
|
*/
|
|
10
10
|
export declare class Reactive<T extends object = object> extends Destroyable {
|
|
11
|
-
/**
|
|
12
|
-
* A list of user-defined values
|
|
13
|
-
* @type {Set}
|
|
14
|
-
*/
|
|
15
|
-
private _watch;
|
|
16
11
|
/**
|
|
17
12
|
* A list of user-defined bindings
|
|
18
13
|
* @type {Set}
|
|
@@ -1,147 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
/**
|
|
3
|
-
* Model based on Array class
|
|
4
|
-
* @extends Array
|
|
5
|
-
* @implements IModel
|
|
6
|
-
*/
|
|
7
|
-
export class ArrayModel extends Array {
|
|
8
|
-
/**
|
|
9
|
-
* @param data {Array} input data
|
|
10
|
-
*/
|
|
11
|
-
constructor(data) {
|
|
12
|
-
super();
|
|
13
|
-
this.passive = false;
|
|
14
|
-
this.listener = new Listener();
|
|
15
|
-
if (data instanceof Array) {
|
|
16
|
-
for (let i = 0; i < data.length; i++) {
|
|
17
|
-
super.push(data[i]);
|
|
18
|
-
}
|
|
19
|
-
}
|
|
20
|
-
}
|
|
21
|
-
/* Array members */
|
|
22
|
-
/**
|
|
23
|
-
* Calls Array.fill and notify about changes
|
|
24
|
-
* @param value {*} value to fill with
|
|
25
|
-
* @param start {?number} begin index
|
|
26
|
-
* @param end {?number} end index
|
|
27
|
-
*/
|
|
28
|
-
fill(value, start, end) {
|
|
29
|
-
this.passive = true;
|
|
30
|
-
if (!start) {
|
|
31
|
-
start = 0;
|
|
32
|
-
}
|
|
33
|
-
if (!end) {
|
|
34
|
-
end = this.length;
|
|
35
|
-
}
|
|
36
|
-
for (let i = start; i < end; i++) {
|
|
37
|
-
this.listener.emitRemoved(this[i], this[i]);
|
|
38
|
-
this[i] = value;
|
|
39
|
-
this.listener.emitAdded(value, value);
|
|
40
|
-
}
|
|
41
|
-
this.passive = false;
|
|
42
|
-
return this;
|
|
43
|
-
}
|
|
44
|
-
/**
|
|
45
|
-
* Calls Array.pop and notify about changes
|
|
46
|
-
* @return {*} removed value
|
|
47
|
-
*/
|
|
48
|
-
pop() {
|
|
49
|
-
this.passive = true;
|
|
50
|
-
const v = super.pop();
|
|
51
|
-
if (v !== undefined) {
|
|
52
|
-
this.listener.emitRemoved(v, v);
|
|
53
|
-
}
|
|
54
|
-
this.passive = false;
|
|
55
|
-
return v;
|
|
56
|
-
}
|
|
57
|
-
/**
|
|
58
|
-
* Calls Array.push and notify about changes
|
|
59
|
-
* @param items {...*} values to push
|
|
60
|
-
* @return {number} new length of array
|
|
61
|
-
*/
|
|
62
|
-
push(...items) {
|
|
63
|
-
this.passive = true;
|
|
64
|
-
items.forEach(item => {
|
|
65
|
-
this.listener.emitAdded(item, item);
|
|
66
|
-
super.push(item);
|
|
67
|
-
});
|
|
68
|
-
this.passive = false;
|
|
69
|
-
return this.length;
|
|
70
|
-
}
|
|
71
|
-
/**
|
|
72
|
-
* Calls Array.shift and notify about changed
|
|
73
|
-
* @return {*} the shifted value
|
|
74
|
-
*/
|
|
75
|
-
shift() {
|
|
76
|
-
this.passive = true;
|
|
77
|
-
const v = super.shift();
|
|
78
|
-
if (v !== undefined) {
|
|
79
|
-
this.listener.emitRemoved(v, v);
|
|
80
|
-
}
|
|
81
|
-
this.passive = false;
|
|
82
|
-
return v;
|
|
83
|
-
}
|
|
84
|
-
/**
|
|
85
|
-
* Calls Array.splice and notify about changed
|
|
86
|
-
* @param start {number} start index
|
|
87
|
-
* @param deleteCount {?number} delete count
|
|
88
|
-
* @param items {...*}
|
|
89
|
-
* @return {ArrayModel} a pointer to this
|
|
90
|
-
*/
|
|
91
|
-
splice(start, deleteCount, ...items) {
|
|
92
|
-
this.passive = true;
|
|
93
|
-
start = Math.min(start, this.length);
|
|
94
|
-
deleteCount = typeof deleteCount === "number" ? deleteCount : this.length - start;
|
|
95
|
-
const before = this[start + deleteCount];
|
|
96
|
-
for (let i = 0; i < deleteCount; i++) {
|
|
97
|
-
const index = start + deleteCount - i - 1;
|
|
98
|
-
if (this[index] !== undefined) {
|
|
99
|
-
this.listener.emitRemoved(this[index], this[index]);
|
|
100
|
-
}
|
|
101
|
-
}
|
|
102
|
-
for (let i = 0; i < items.length; i++) {
|
|
103
|
-
this.listener.emitAdded(before, items[i]);
|
|
104
|
-
}
|
|
105
|
-
this.passive = false;
|
|
106
|
-
return new ArrayModel(super.splice(start, deleteCount, ...items));
|
|
107
|
-
}
|
|
108
|
-
/**
|
|
109
|
-
* Calls Array.unshift and notify about changed
|
|
110
|
-
* @param items {...*} values to insert
|
|
111
|
-
* @return {number} the length after prepend
|
|
112
|
-
*/
|
|
113
|
-
unshift(...items) {
|
|
114
|
-
this.passive = true;
|
|
115
|
-
for (let i = 0; i < items.length; i++) {
|
|
116
|
-
this.listener.emitAdded(this[i], items[i]);
|
|
117
|
-
}
|
|
118
|
-
const r = super.unshift(...items);
|
|
119
|
-
this.passive = false;
|
|
120
|
-
return r;
|
|
121
|
-
}
|
|
122
|
-
replace(at, with_) {
|
|
123
|
-
this.passive = true;
|
|
124
|
-
this.listener.emitAdded(this[at], with_);
|
|
125
|
-
this.listener.emitRemoved(this[at], this[at]);
|
|
126
|
-
this[at] = with_;
|
|
127
|
-
this.passive = false;
|
|
128
|
-
return this;
|
|
129
|
-
}
|
|
130
|
-
destroy() {
|
|
131
|
-
this.splice(0);
|
|
132
|
-
}
|
|
133
|
-
}
|
|
134
|
-
export function proxyArrayModel(arr) {
|
|
135
|
-
return new Proxy(arr, {
|
|
136
|
-
set(target, p, newValue, receiver) {
|
|
137
|
-
if (!arr.passive && typeof p === "string") {
|
|
138
|
-
const index = parseInt(p);
|
|
139
|
-
if (Number.isFinite(index)) {
|
|
140
|
-
arr.replace(index, newValue);
|
|
141
|
-
return true;
|
|
142
|
-
}
|
|
143
|
-
}
|
|
144
|
-
return Reflect.set(target, p, newValue, receiver);
|
|
145
|
-
},
|
|
146
|
-
});
|
|
147
|
-
}
|
package/lib/models/listener.js
DELETED
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Represent a listener for a model
|
|
3
|
-
* @class Listener
|
|
4
|
-
*/
|
|
5
|
-
export class Listener {
|
|
6
|
-
constructor() {
|
|
7
|
-
/**
|
|
8
|
-
* Functions to run on adding new items
|
|
9
|
-
* @type Set
|
|
10
|
-
*/
|
|
11
|
-
this.onAdded = new Set();
|
|
12
|
-
/**
|
|
13
|
-
* Functions to run on item removing
|
|
14
|
-
* @type Set
|
|
15
|
-
*/
|
|
16
|
-
this.onRemoved = new Set();
|
|
17
|
-
}
|
|
18
|
-
/**
|
|
19
|
-
* Emits added event to listeners
|
|
20
|
-
* @param index {*} index of value
|
|
21
|
-
* @param value {*} value of added item
|
|
22
|
-
*/
|
|
23
|
-
emitAdded(index, value) {
|
|
24
|
-
this.onAdded.forEach(handler => {
|
|
25
|
-
handler(index, value);
|
|
26
|
-
});
|
|
27
|
-
}
|
|
28
|
-
/**
|
|
29
|
-
* Emits removed event to listeners
|
|
30
|
-
* @param index {*} index of removed value
|
|
31
|
-
* @param value {*} value of removed item
|
|
32
|
-
*/
|
|
33
|
-
emitRemoved(index, value) {
|
|
34
|
-
this.onRemoved.forEach(handler => {
|
|
35
|
-
handler(index, value);
|
|
36
|
-
});
|
|
37
|
-
}
|
|
38
|
-
/**
|
|
39
|
-
* Adds a handler to added event
|
|
40
|
-
* @param handler {function} function to run on event emitting
|
|
41
|
-
*/
|
|
42
|
-
onAdd(handler) {
|
|
43
|
-
this.onAdded.add(handler);
|
|
44
|
-
}
|
|
45
|
-
/**
|
|
46
|
-
* Adds a handler to removed event
|
|
47
|
-
* @param handler {function} function to run on event emitting
|
|
48
|
-
*/
|
|
49
|
-
onRemove(handler) {
|
|
50
|
-
this.onRemoved.add(handler);
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* Removes an handler from added event
|
|
54
|
-
* @param handler {function} handler to remove
|
|
55
|
-
*/
|
|
56
|
-
offAdd(handler) {
|
|
57
|
-
this.onAdded.delete(handler);
|
|
58
|
-
}
|
|
59
|
-
/**
|
|
60
|
-
* Removes an handler form removed event
|
|
61
|
-
* @param handler {function} handler to remove
|
|
62
|
-
*/
|
|
63
|
-
offRemove(handler) {
|
|
64
|
-
this.onRemoved.delete(handler);
|
|
65
|
-
}
|
|
66
|
-
}
|
package/lib/models/map-model.js
DELETED
|
@@ -1,59 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
/**
|
|
3
|
-
* A Map based memory
|
|
4
|
-
* @class MapModel
|
|
5
|
-
* @extends Map
|
|
6
|
-
* @implements IModel
|
|
7
|
-
*/
|
|
8
|
-
export class MapModel extends Map {
|
|
9
|
-
/**
|
|
10
|
-
* Constructs a map model
|
|
11
|
-
* @param map {[*, *][]} input data
|
|
12
|
-
*/
|
|
13
|
-
constructor(map) {
|
|
14
|
-
super();
|
|
15
|
-
this.listener = new Listener();
|
|
16
|
-
map?.forEach(([key, value]) => {
|
|
17
|
-
super.set(key, value);
|
|
18
|
-
});
|
|
19
|
-
}
|
|
20
|
-
/**
|
|
21
|
-
* Calls Map.clear and notify about changes
|
|
22
|
-
*/
|
|
23
|
-
clear() {
|
|
24
|
-
this.forEach((value, key) => {
|
|
25
|
-
this.listener.emitRemoved(key, value);
|
|
26
|
-
});
|
|
27
|
-
super.clear();
|
|
28
|
-
}
|
|
29
|
-
/**
|
|
30
|
-
* Calls Map.delete and notify abut changes
|
|
31
|
-
* @param key {*} key
|
|
32
|
-
* @return {boolean} true if removed something, otherwise false
|
|
33
|
-
*/
|
|
34
|
-
delete(key) {
|
|
35
|
-
const tmp = super.get(key);
|
|
36
|
-
if (tmp) {
|
|
37
|
-
this.listener.emitRemoved(key, tmp);
|
|
38
|
-
}
|
|
39
|
-
return super.delete(key);
|
|
40
|
-
}
|
|
41
|
-
/**
|
|
42
|
-
* Calls Map.set and notify abut changes
|
|
43
|
-
* @param key {*} key
|
|
44
|
-
* @param value {*} value
|
|
45
|
-
* @return {MapModel} a pointer to this
|
|
46
|
-
*/
|
|
47
|
-
set(key, value) {
|
|
48
|
-
const tmp = super.get(key);
|
|
49
|
-
if (tmp) {
|
|
50
|
-
this.listener.emitRemoved(key, tmp);
|
|
51
|
-
}
|
|
52
|
-
super.set(key, value);
|
|
53
|
-
this.listener.emitAdded(key, value);
|
|
54
|
-
return this;
|
|
55
|
-
}
|
|
56
|
-
destroy() {
|
|
57
|
-
this.clear();
|
|
58
|
-
}
|
|
59
|
-
}
|
package/lib/models/model.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
package/lib/models/set-model.js
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
/**
|
|
3
|
-
* A Set based model
|
|
4
|
-
* @class SetModel
|
|
5
|
-
* @extends Set
|
|
6
|
-
* @implements IModel
|
|
7
|
-
*/
|
|
8
|
-
export class SetModel extends Set {
|
|
9
|
-
/**
|
|
10
|
-
* Constructs a set model based on a set
|
|
11
|
-
* @param set {Set} input data
|
|
12
|
-
*/
|
|
13
|
-
constructor(set) {
|
|
14
|
-
super();
|
|
15
|
-
this.listener = new Listener();
|
|
16
|
-
set?.forEach(item => {
|
|
17
|
-
super.add(item);
|
|
18
|
-
});
|
|
19
|
-
}
|
|
20
|
-
/**
|
|
21
|
-
* Calls Set.add and notify abut changes
|
|
22
|
-
* @param value {*} value
|
|
23
|
-
* @return {this} a pointer to this
|
|
24
|
-
*/
|
|
25
|
-
add(value) {
|
|
26
|
-
if (!super.has(value)) {
|
|
27
|
-
this.listener.emitAdded(value, value);
|
|
28
|
-
super.add(value);
|
|
29
|
-
}
|
|
30
|
-
return this;
|
|
31
|
-
}
|
|
32
|
-
/**
|
|
33
|
-
* Calls Set.clear and notify abut changes
|
|
34
|
-
*/
|
|
35
|
-
clear() {
|
|
36
|
-
this.forEach(item => {
|
|
37
|
-
this.listener.emitRemoved(item, item);
|
|
38
|
-
});
|
|
39
|
-
super.clear();
|
|
40
|
-
}
|
|
41
|
-
/**
|
|
42
|
-
* Calls Set.delete and notify abut changes
|
|
43
|
-
* @param value {*}
|
|
44
|
-
* @return {boolean} true if a value was deleted, otherwise false
|
|
45
|
-
*/
|
|
46
|
-
delete(value) {
|
|
47
|
-
if (super.has(value)) {
|
|
48
|
-
this.listener.emitRemoved(value, value);
|
|
49
|
-
}
|
|
50
|
-
return super.delete(value);
|
|
51
|
-
}
|
|
52
|
-
destroy() {
|
|
53
|
-
this.clear();
|
|
54
|
-
}
|
|
55
|
-
}
|
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
import { ListenableModel } from "./model.js";
|
|
3
|
-
/**
|
|
4
|
-
* Model based on Array class
|
|
5
|
-
* @extends Array
|
|
6
|
-
* @implements IModel
|
|
7
|
-
*/
|
|
8
|
-
export declare class ArrayModel<T> extends Array<T> implements ListenableModel<T, T> {
|
|
9
|
-
listener: Listener<T, T>;
|
|
10
|
-
passive: boolean;
|
|
11
|
-
/**
|
|
12
|
-
* @param data {Array} input data
|
|
13
|
-
*/
|
|
14
|
-
constructor(data?: Array<T> | number);
|
|
15
|
-
/**
|
|
16
|
-
* Calls Array.fill and notify about changes
|
|
17
|
-
* @param value {*} value to fill with
|
|
18
|
-
* @param start {?number} begin index
|
|
19
|
-
* @param end {?number} end index
|
|
20
|
-
*/
|
|
21
|
-
fill(value: T, start?: number, end?: number): this;
|
|
22
|
-
/**
|
|
23
|
-
* Calls Array.pop and notify about changes
|
|
24
|
-
* @return {*} removed value
|
|
25
|
-
*/
|
|
26
|
-
pop(): T | undefined;
|
|
27
|
-
/**
|
|
28
|
-
* Calls Array.push and notify about changes
|
|
29
|
-
* @param items {...*} values to push
|
|
30
|
-
* @return {number} new length of array
|
|
31
|
-
*/
|
|
32
|
-
push(...items: Array<T>): number;
|
|
33
|
-
/**
|
|
34
|
-
* Calls Array.shift and notify about changed
|
|
35
|
-
* @return {*} the shifted value
|
|
36
|
-
*/
|
|
37
|
-
shift(): T | undefined;
|
|
38
|
-
/**
|
|
39
|
-
* Calls Array.splice and notify about changed
|
|
40
|
-
* @param start {number} start index
|
|
41
|
-
* @param deleteCount {?number} delete count
|
|
42
|
-
* @param items {...*}
|
|
43
|
-
* @return {ArrayModel} a pointer to this
|
|
44
|
-
*/
|
|
45
|
-
splice(start: number, deleteCount?: number, ...items: Array<T>): ArrayModel<T>;
|
|
46
|
-
/**
|
|
47
|
-
* Calls Array.unshift and notify about changed
|
|
48
|
-
* @param items {...*} values to insert
|
|
49
|
-
* @return {number} the length after prepend
|
|
50
|
-
*/
|
|
51
|
-
unshift(...items: Array<T>): number;
|
|
52
|
-
replace(at: number, with_: T): this;
|
|
53
|
-
destroy(): void;
|
|
54
|
-
}
|
|
55
|
-
export declare function proxyArrayModel<T>(arr: ArrayModel<T>): ArrayModel<T>;
|
|
@@ -1,48 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Represent a listener for a model
|
|
3
|
-
* @class Listener
|
|
4
|
-
*/
|
|
5
|
-
export declare class Listener<ValueT, IndexT = string | number> {
|
|
6
|
-
/**
|
|
7
|
-
* Functions to run on adding new items
|
|
8
|
-
* @type Set
|
|
9
|
-
*/
|
|
10
|
-
private readonly onAdded;
|
|
11
|
-
/**
|
|
12
|
-
* Functions to run on item removing
|
|
13
|
-
* @type Set
|
|
14
|
-
*/
|
|
15
|
-
private readonly onRemoved;
|
|
16
|
-
/**
|
|
17
|
-
* Emits added event to listeners
|
|
18
|
-
* @param index {*} index of value
|
|
19
|
-
* @param value {*} value of added item
|
|
20
|
-
*/
|
|
21
|
-
emitAdded(index: IndexT, value: ValueT): void;
|
|
22
|
-
/**
|
|
23
|
-
* Emits removed event to listeners
|
|
24
|
-
* @param index {*} index of removed value
|
|
25
|
-
* @param value {*} value of removed item
|
|
26
|
-
*/
|
|
27
|
-
emitRemoved(index: IndexT, value: ValueT): void;
|
|
28
|
-
/**
|
|
29
|
-
* Adds a handler to added event
|
|
30
|
-
* @param handler {function} function to run on event emitting
|
|
31
|
-
*/
|
|
32
|
-
onAdd(handler: (index: IndexT, value: ValueT) => void): void;
|
|
33
|
-
/**
|
|
34
|
-
* Adds a handler to removed event
|
|
35
|
-
* @param handler {function} function to run on event emitting
|
|
36
|
-
*/
|
|
37
|
-
onRemove(handler: (index: IndexT, value: ValueT) => void): void;
|
|
38
|
-
/**
|
|
39
|
-
* Removes an handler from added event
|
|
40
|
-
* @param handler {function} handler to remove
|
|
41
|
-
*/
|
|
42
|
-
offAdd(handler: (index: IndexT, value: ValueT) => void): void;
|
|
43
|
-
/**
|
|
44
|
-
* Removes an handler form removed event
|
|
45
|
-
* @param handler {function} handler to remove
|
|
46
|
-
*/
|
|
47
|
-
offRemove(handler: (index: IndexT, value: ValueT) => void): void;
|
|
48
|
-
}
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
import { ListenableModel } from "./model.js";
|
|
3
|
-
/**
|
|
4
|
-
* A Map based memory
|
|
5
|
-
* @class MapModel
|
|
6
|
-
* @extends Map
|
|
7
|
-
* @implements IModel
|
|
8
|
-
*/
|
|
9
|
-
export declare class MapModel<K, T> extends Map<K, T> implements ListenableModel<K, T> {
|
|
10
|
-
listener: Listener<T, K>;
|
|
11
|
-
/**
|
|
12
|
-
* Constructs a map model
|
|
13
|
-
* @param map {[*, *][]} input data
|
|
14
|
-
*/
|
|
15
|
-
constructor(map?: [K, T][]);
|
|
16
|
-
/**
|
|
17
|
-
* Calls Map.clear and notify about changes
|
|
18
|
-
*/
|
|
19
|
-
clear(): void;
|
|
20
|
-
/**
|
|
21
|
-
* Calls Map.delete and notify abut changes
|
|
22
|
-
* @param key {*} key
|
|
23
|
-
* @return {boolean} true if removed something, otherwise false
|
|
24
|
-
*/
|
|
25
|
-
delete(key: K): boolean;
|
|
26
|
-
/**
|
|
27
|
-
* Calls Map.set and notify abut changes
|
|
28
|
-
* @param key {*} key
|
|
29
|
-
* @param value {*} value
|
|
30
|
-
* @return {MapModel} a pointer to this
|
|
31
|
-
*/
|
|
32
|
-
set(key: K, value: T): this;
|
|
33
|
-
destroy(): void;
|
|
34
|
-
}
|
package/types/models/model.d.ts
DELETED
|
@@ -1,14 +0,0 @@
|
|
|
1
|
-
import { IDestroyable } from "../core/destroyable.js";
|
|
2
|
-
import { Listener } from "./listener.js";
|
|
3
|
-
/**
|
|
4
|
-
* @interface IModel
|
|
5
|
-
*/
|
|
6
|
-
export interface IModel extends IDestroyable {
|
|
7
|
-
}
|
|
8
|
-
export interface ListenableModel<K, T> extends IModel {
|
|
9
|
-
/**
|
|
10
|
-
* The listener of model
|
|
11
|
-
* @type Listener
|
|
12
|
-
*/
|
|
13
|
-
listener: Listener<T, K>;
|
|
14
|
-
}
|
|
@@ -1,33 +0,0 @@
|
|
|
1
|
-
import { Listener } from "./listener.js";
|
|
2
|
-
import { ListenableModel } from "./model.js";
|
|
3
|
-
/**
|
|
4
|
-
* A Set based model
|
|
5
|
-
* @class SetModel
|
|
6
|
-
* @extends Set
|
|
7
|
-
* @implements IModel
|
|
8
|
-
*/
|
|
9
|
-
export declare class SetModel<T> extends Set<T> implements ListenableModel<T, T> {
|
|
10
|
-
listener: Listener<T, T>;
|
|
11
|
-
/**
|
|
12
|
-
* Constructs a set model based on a set
|
|
13
|
-
* @param set {Set} input data
|
|
14
|
-
*/
|
|
15
|
-
constructor(set?: T[]);
|
|
16
|
-
/**
|
|
17
|
-
* Calls Set.add and notify abut changes
|
|
18
|
-
* @param value {*} value
|
|
19
|
-
* @return {this} a pointer to this
|
|
20
|
-
*/
|
|
21
|
-
add(value: T): this;
|
|
22
|
-
/**
|
|
23
|
-
* Calls Set.clear and notify abut changes
|
|
24
|
-
*/
|
|
25
|
-
clear(): void;
|
|
26
|
-
/**
|
|
27
|
-
* Calls Set.delete and notify abut changes
|
|
28
|
-
* @param value {*}
|
|
29
|
-
* @return {boolean} true if a value was deleted, otherwise false
|
|
30
|
-
*/
|
|
31
|
-
delete(value: T): boolean;
|
|
32
|
-
destroy(): void;
|
|
33
|
-
}
|