blob: dfc72d4a0796650a69e34f33736620cb8f82561c [file] [log] [blame]
Helge4bcbe6f2026-09-07 10:59:27 +02001/**
2 * Create a state object, that can have a single value
3 * (mostly boolean) and multiple objects associated to it.
4 * Whenever the state changes, all objects are informed
5 * by their setState() method of the value change.
6 *
7 * @author Nils Diewald
8 */
9/*
10 * TODO:
11 * Require names for states, that should be quite short, so they
12 * can easily be serialized and kept between page turns (via cookie
13 * and/or query param)
14 */
15
16export default class State {
17
18 /**
19 * Constructor
20 */
21 constructor (values) {
22 this._init(values);
23 }
24
25
26 // Initialize
27 _init (values) {
28 const t = this;
29 t._assoc = [];
30 if (values == undefined) {
31 t.values = [false,true];
32 }
33 else if (Array.isArray(values)) {
34 t.values = values;
35 }
36 else {
37 t.values = [values];
38 }
39 return t;
40 }
41
42
43 /**
44 * Associate the state with some objects.
45 */
46 associate (obj) {
47
48 // Check if the object has a setState() method
49 if (obj.hasOwnProperty("setState")) {
50
51 this._assoc.push(obj);
52 if (this.value != undefined) {
53 obj.setState(this.value);
54 };
55 } else {
56 console.log("Object " + obj + " has no setState() method");
57 }
58 }
59
60
61 /**
62 * Set the state to a certain value.
63 * This will set the state to all associated objects as well.
64 */
65 set (value) {
66 if (value != this.value) {
67 this.value = value;
68 this._assoc.forEach(i => i.setState(value));
69 };
70 }
71
72
73 /**
74 * Set the state to a default value.
75 * This will only be set, if no other value is set yet.
76 */
77 setIfNotYet (value) {
78 if (this.value == undefined) {
79 this.set(value);
80 };
81 }
82
83
84 /**
85 * Get the state value
86 */
87 get () {
88 if (this.value == undefined) {
89 this.value = this.values[0];
90 };
91
92 return this.value;
93 }
94
95
96 /**
97 * Get the number of associated objects
98 */
99 associates () {
100 return this._assoc.length;
101 }
102
103
104 /**
105 * Clear all associated objects
106 */
107 clear () {
108 return this._assoc = [];
109 }
110
111
112 /**
113 * Roll to the next value.
114 * This may be used for toggling.
115 */
116 roll () {
117 let next = 0;
118 for (let i = 0; i < this.values.length - 1; i++) {
119 if (this.get() == this.values[i]) {
120 next = i+1;
121 break;
122 };
123 };
124 this.set(this.values[next]);
125 }
126}