@livinglogic/livingapi 0.11.0 → 0.13.1
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/CHANGELOG.md +74 -1
- package/README.md +3 -3
- package/dist/esm-node/livingapi.js +1 -1
- package/dist/esm-node/livingapi.js.map +1 -1
- package/dist/esm-static/livingapi.js +1 -1
- package/dist/esm-static/livingapi.js.map +1 -1
- package/dist/umd/livingapi.js +1 -1
- package/dist/umd/livingapi.js.map +1 -1
- package/package.json +11 -11
- package/rollup.config.js +1 -1
- package/src/livingapi.js +1617 -191
package/src/livingapi.js
CHANGED
|
@@ -33,11 +33,18 @@ export { version };
|
|
|
33
33
|
|
|
34
34
|
import * as ul4 from '@livinglogic/ul4';
|
|
35
35
|
|
|
36
|
+
|
|
36
37
|
export class Base extends ul4.Proto
|
|
37
38
|
{
|
|
38
|
-
constructor()
|
|
39
|
+
constructor(id)
|
|
39
40
|
{
|
|
40
41
|
super();
|
|
42
|
+
this.id = id;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
get ul4onid()
|
|
46
|
+
{
|
|
47
|
+
return this.id;
|
|
41
48
|
}
|
|
42
49
|
|
|
43
50
|
ul4ondump(encoder)
|
|
@@ -76,7 +83,7 @@ export class Base extends ul4.Proto
|
|
|
76
83
|
this[name] = null;
|
|
77
84
|
}
|
|
78
85
|
|
|
79
|
-
|
|
86
|
+
[ul4.symbols.getattr](name)
|
|
80
87
|
{
|
|
81
88
|
if (this._ul4attrs.has(name))
|
|
82
89
|
{
|
|
@@ -95,12 +102,18 @@ export class Base extends ul4.Proto
|
|
|
95
102
|
throw new ul4.AttributeError(this, name);
|
|
96
103
|
}
|
|
97
104
|
|
|
98
|
-
|
|
105
|
+
[ul4.symbols.repr]()
|
|
99
106
|
{
|
|
100
107
|
return "<" + this.constructor.name + ">";
|
|
101
108
|
}
|
|
109
|
+
|
|
110
|
+
toString()
|
|
111
|
+
{
|
|
112
|
+
return this[ul4.symbols.repr]();
|
|
113
|
+
}
|
|
102
114
|
};
|
|
103
115
|
|
|
116
|
+
|
|
104
117
|
export class Handler
|
|
105
118
|
{
|
|
106
119
|
save(record)
|
|
@@ -112,16 +125,21 @@ export class Handler
|
|
|
112
125
|
}
|
|
113
126
|
};
|
|
114
127
|
|
|
128
|
+
|
|
115
129
|
export class Globals extends Base
|
|
116
130
|
{
|
|
117
|
-
|
|
131
|
+
static classdoc = "Global information";
|
|
132
|
+
|
|
133
|
+
constructor(id)
|
|
118
134
|
{
|
|
119
|
-
super();
|
|
135
|
+
super(id);
|
|
120
136
|
this.version = null;
|
|
121
137
|
this.hostname = null;
|
|
122
138
|
this.platform = null;
|
|
123
139
|
this.user = null;
|
|
124
140
|
this.lang = null;
|
|
141
|
+
this.app = null;
|
|
142
|
+
this.record = null;
|
|
125
143
|
this.maxdbactions = null;
|
|
126
144
|
this.maxtemplateruntime = null;
|
|
127
145
|
this.flashmessages = null;
|
|
@@ -155,67 +173,137 @@ export class Globals extends Base
|
|
|
155
173
|
return s;
|
|
156
174
|
}
|
|
157
175
|
|
|
158
|
-
|
|
176
|
+
scaledURL(url, width, height, type="fill", enlarge=true, gravity="sm", quality=null, rotate=null, blur=null, sharpen=null, format=null, cache=true)
|
|
177
|
+
{
|
|
178
|
+
let filename = null;
|
|
179
|
+
|
|
180
|
+
if (url instanceof File)
|
|
181
|
+
{
|
|
182
|
+
url = "https://" + this.hostname + url.url;
|
|
183
|
+
filename = encodeURIComponent(url.filename);
|
|
184
|
+
if (filename != url.filename)
|
|
185
|
+
filename = null;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
let result = "";
|
|
189
|
+
|
|
190
|
+
if (cache)
|
|
191
|
+
result += "/imgproxycache/insecure";
|
|
192
|
+
else
|
|
193
|
+
result += "/imgproxy/insecure";
|
|
194
|
+
|
|
195
|
+
if (type !== "fit")
|
|
196
|
+
result += "/rt:" + type;
|
|
197
|
+
|
|
198
|
+
if (width !== null && width !== undefined)
|
|
199
|
+
result += "/w:" + width;
|
|
200
|
+
|
|
201
|
+
if (height !== null && height !== undefined)
|
|
202
|
+
result += "/h:" + height;
|
|
203
|
+
|
|
204
|
+
if (enlarge)
|
|
205
|
+
result += "/el:1";
|
|
206
|
+
|
|
207
|
+
if (gravity !== null && gravity !== undefined)
|
|
208
|
+
result += "/g:" + gravity;
|
|
209
|
+
|
|
210
|
+
if (quality !== null && quality !== undefined)
|
|
211
|
+
result += "/q:" + quality;
|
|
212
|
+
|
|
213
|
+
if (rotate !== null && rotate % 360 != 0)
|
|
214
|
+
result += "/rot:" + rotatet;
|
|
215
|
+
|
|
216
|
+
if (blur !== null && blur !== undefined)
|
|
217
|
+
result += "/bl:" + blur;
|
|
218
|
+
|
|
219
|
+
if (sharpen !== null && sharpen !== undefined)
|
|
220
|
+
result += "/sh:" + sharpen;
|
|
221
|
+
|
|
222
|
+
if (format !== null && format !== undefined)
|
|
223
|
+
result += "/f:" + format;
|
|
224
|
+
|
|
225
|
+
if (filename !== null && filename !== undefined)
|
|
226
|
+
result += "/fn:" + filename;
|
|
227
|
+
|
|
228
|
+
result += "/plain/" + encodeURIComponent(url);
|
|
229
|
+
|
|
230
|
+
return result;
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
[ul4.symbols.repr]()
|
|
159
234
|
{
|
|
160
235
|
return "<Globals version=" + ul4._repr(this.version) + ">";
|
|
161
236
|
}
|
|
162
237
|
};
|
|
163
238
|
|
|
164
|
-
Globals.prototype._ul4onattrs = ["version", "platform", "user", "maxdbactions", "maxtemplateruntime", "flashmessages", "lang", "datasources", "hostname"];
|
|
165
|
-
Globals.prototype._ul4attrs =
|
|
239
|
+
Globals.prototype._ul4onattrs = ["version", "platform", "user", "maxdbactions", "maxtemplateruntime", "flashmessages", "lang", "datasources", "hostname", "app", "record", "google_api_key", "mode", "view_template_id", "email_template_id", "view_id"];
|
|
240
|
+
Globals.prototype._ul4attrs = new Set(["version", "hostname", "platform", "user", "lang", "app", "record", "maxdbactions", "maxtemplateruntime", "flashmessages", "mode"]);
|
|
241
|
+
|
|
166
242
|
|
|
167
243
|
export class FlashMessage extends Base
|
|
168
244
|
{
|
|
169
|
-
|
|
245
|
+
static classdoc = "A flash message in a web page";
|
|
246
|
+
|
|
247
|
+
[ul4.symbols.repr]()
|
|
170
248
|
{
|
|
171
249
|
return "<FlashMessage type=" + ul4._repr(this.type) + " title=" + ul4._repr(this.title) + ">";
|
|
172
250
|
}
|
|
173
251
|
};
|
|
174
252
|
|
|
175
253
|
FlashMessage.prototype._ul4onattrs = ["timestamp", "type", "title", "message"];
|
|
176
|
-
FlashMessage.prototype._ul4attrs =
|
|
254
|
+
FlashMessage.prototype._ul4attrs = new Set(["timestamp", "type", "title", "message"]);
|
|
255
|
+
|
|
177
256
|
|
|
178
257
|
export class App extends Base
|
|
179
258
|
{
|
|
180
|
-
|
|
259
|
+
static classdoc = "A LivingApps application";
|
|
260
|
+
|
|
261
|
+
[ul4.symbols.repr]()
|
|
181
262
|
{
|
|
182
263
|
return "<App id=" + ul4._repr(this.id) + " name=" + ul4._repr(this.name) + ">";
|
|
183
264
|
}
|
|
184
265
|
|
|
185
266
|
insert(values={})
|
|
186
267
|
{
|
|
187
|
-
let record = this.
|
|
268
|
+
let record = this[ul4.symbols.call](values);
|
|
188
269
|
this.globals.handler.save(this);
|
|
189
270
|
return record;
|
|
190
271
|
}
|
|
191
272
|
|
|
192
|
-
|
|
273
|
+
get layout_controls()
|
|
274
|
+
{
|
|
275
|
+
if (this.active_view === null)
|
|
276
|
+
return new Map();
|
|
277
|
+
return this.active_view.layout_controls;
|
|
278
|
+
}
|
|
279
|
+
|
|
280
|
+
[ul4.symbols.call](values={})
|
|
193
281
|
{
|
|
194
|
-
let record = new Record(this);
|
|
282
|
+
let record = new Record(null, this);
|
|
195
283
|
if (ul4._ismap(values))
|
|
196
284
|
{
|
|
197
|
-
for (let
|
|
285
|
+
for (let identifier of values.keys())
|
|
198
286
|
{
|
|
199
|
-
if (!record.fields.has(
|
|
200
|
-
throw new ul4.ArgumentError("
|
|
201
|
-
record.fields.get(key).value = value;
|
|
287
|
+
if (!record.fields.has(identifier))
|
|
288
|
+
throw new ul4.ArgumentError(ul4._repr(this) + "() get an unexpected keyword argument " + ul4._repr(identifier));
|
|
202
289
|
}
|
|
290
|
+
record._make_fields(true, values, null, null);
|
|
203
291
|
}
|
|
204
292
|
else if (ul4._isobject(values))
|
|
205
293
|
{
|
|
206
|
-
for (let
|
|
294
|
+
for (let identifier in values)
|
|
207
295
|
{
|
|
208
|
-
if (!record.fields.has(
|
|
209
|
-
throw new ul4.ArgumentError("
|
|
210
|
-
record.fields.get(key).value = values[key];
|
|
296
|
+
if (!record.fields.has(identifier))
|
|
297
|
+
throw new ul4.ArgumentError(ul4._repr(this) + "() get an unexpected keyword argument " + ul4._repr(identifier));
|
|
211
298
|
}
|
|
299
|
+
record._make_fields(true, new Map(ul4._list(ul4.dicttype.items(values))), null, null);
|
|
212
300
|
}
|
|
213
301
|
else
|
|
214
302
|
throw new ul4.TypeError("values must be an object or a Map");
|
|
215
303
|
return record;
|
|
216
304
|
}
|
|
217
305
|
|
|
218
|
-
|
|
306
|
+
[ul4.symbols.getattr](name)
|
|
219
307
|
{
|
|
220
308
|
if (name.startsWith("c_"))
|
|
221
309
|
{
|
|
@@ -224,43 +312,83 @@ export class App extends Base
|
|
|
224
312
|
return this.controls.get(name.substr(2));
|
|
225
313
|
}
|
|
226
314
|
else
|
|
227
|
-
return super.
|
|
315
|
+
return super[ul4.symbols.getattr](name);
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
get active_view()
|
|
319
|
+
{
|
|
320
|
+
return this._active_view;
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
set active_view(view)
|
|
324
|
+
{
|
|
325
|
+
if (view === null)
|
|
326
|
+
;
|
|
327
|
+
else if (typeof(view) === "string")
|
|
328
|
+
{
|
|
329
|
+
if (this.views !== null && this.views.has(view))
|
|
330
|
+
view = this.views.get(view);
|
|
331
|
+
else
|
|
332
|
+
throw new ul4.ValueError("View " + ul4._repr(view) + " not found!");
|
|
333
|
+
}
|
|
334
|
+
else if (view instanceof View)
|
|
335
|
+
{
|
|
336
|
+
if (view.app === this)
|
|
337
|
+
;
|
|
338
|
+
else
|
|
339
|
+
throw new ul4.ValueError("View " + ul4._repr(view) + " belongs to the wrong app!");
|
|
340
|
+
}
|
|
341
|
+
else
|
|
342
|
+
{
|
|
343
|
+
throw new ul4.TypeError(ul4._repr(view) + " is not a view!");
|
|
344
|
+
}
|
|
345
|
+
|
|
346
|
+
this._active_view = view;
|
|
228
347
|
}
|
|
229
348
|
};
|
|
230
349
|
|
|
231
|
-
|
|
232
|
-
App.prototype.
|
|
233
|
-
|
|
350
|
+
|
|
351
|
+
App.prototype._ul4onattrs = ["globals", "name", "description", "lang", "startlink", "iconlarge", "iconsmall", "createdby", "controls", "records", "recordcount", "installation", "categories", "params", "views", "datamanagement_identifier", "basetable", "primarykey", "insertprocedure", "updateprocedure", "deleteprocedure", "templates", "createdat", "updatedat", "updatedby", "superid", "favorite", "_active_view"];
|
|
352
|
+
App.prototype._ul4attrs = new Set(["id", "globals", "name", "description", "lang", "startlink", "iconlarge", "iconsmall", "createdat", "createdby", "updatedat", "updatedby", "controls", "records", "recordcount", "installation", "categories", "params", "views", "datamanagement_identifier", "insert", "favorite", "_active_view"]);
|
|
353
|
+
ul4.expose(App.prototype[ul4.symbols.call], ["**values"], {"needsobject": true});
|
|
234
354
|
ul4.expose(App.prototype.insert, ["**values"], {"needsobject": true});
|
|
235
355
|
|
|
356
|
+
|
|
236
357
|
export class View extends Base
|
|
237
358
|
{
|
|
238
|
-
|
|
359
|
+
static classdoc = "An input form for a LivingApps application";
|
|
360
|
+
|
|
361
|
+
[ul4.symbols.repr]()
|
|
239
362
|
{
|
|
240
363
|
return "<View id=" + ul4._repr(this.id) + " name=" + ul4._repr(this.name) + ">";
|
|
241
364
|
}
|
|
242
365
|
};
|
|
243
366
|
|
|
244
|
-
View.prototype._ul4onattrs = ["
|
|
245
|
-
View.prototype._ul4attrs =
|
|
367
|
+
View.prototype._ul4onattrs = ["name", "combined_type", "app", "order", "width", "height", "start", "end", "controls", "layout_controls", "lang"];
|
|
368
|
+
View.prototype._ul4attrs = new Set(["id", "name", "combined_type", "app", "order", "width", "height", "start", "end", "controls", "layout_controls", "lang"]);
|
|
369
|
+
|
|
246
370
|
|
|
247
371
|
export class DataSourceData extends Base
|
|
248
372
|
{
|
|
249
|
-
|
|
373
|
+
static classdoc = "The data resulting from a data source configuration";
|
|
374
|
+
|
|
375
|
+
[ul4.symbols.repr]()
|
|
250
376
|
{
|
|
251
377
|
return "<DataSource.Data id=" + ul4._repr(this.id) + " identifier=" + ul4._repr(this.identifier) + ">";
|
|
252
378
|
}
|
|
253
379
|
};
|
|
254
380
|
|
|
255
|
-
DataSourceData.prototype._ul4onattrs = ["
|
|
256
|
-
DataSourceData.prototype._ul4attrs =
|
|
381
|
+
DataSourceData.prototype._ul4onattrs = ["identifier", "app", "apps"];
|
|
382
|
+
DataSourceData.prototype._ul4attrs = new Set(["id", "identifier", "app", "apps"]);
|
|
383
|
+
|
|
257
384
|
|
|
258
385
|
export class Record extends Base
|
|
259
386
|
{
|
|
260
|
-
|
|
387
|
+
static classdoc = "A record of a LivingApp application";
|
|
388
|
+
|
|
389
|
+
constructor(id, app)
|
|
261
390
|
{
|
|
262
|
-
super();
|
|
263
|
-
this.id = null;
|
|
391
|
+
super(id);
|
|
264
392
|
this.app = app;
|
|
265
393
|
this.createdat = null;
|
|
266
394
|
this.createdby = null;
|
|
@@ -273,15 +401,47 @@ export class Record extends Base
|
|
|
273
401
|
this.children = new Map();
|
|
274
402
|
this.attachments = null;
|
|
275
403
|
this.errors = [];
|
|
404
|
+
this._sparsefielderrors = null;
|
|
405
|
+
this._sparsefieldlookupdata = null;
|
|
276
406
|
this._is_deleted = false;
|
|
407
|
+
this._is_new = true;
|
|
408
|
+
}
|
|
409
|
+
|
|
410
|
+
_make_fields(defaults, values, errors, lookupdata)
|
|
411
|
+
{
|
|
412
|
+
let fields = new Map();
|
|
413
|
+
|
|
414
|
+
for (let control of this.app.controls.values())
|
|
415
|
+
{
|
|
416
|
+
let identifier = control.identifier;
|
|
417
|
+
let value = null;
|
|
418
|
+
if (values !== null)
|
|
419
|
+
{
|
|
420
|
+
if (defaults && !values.has(identifier))
|
|
421
|
+
value = control.default;
|
|
422
|
+
else if (values.has(identifier))
|
|
423
|
+
value = values.get(identifier);
|
|
424
|
+
}
|
|
425
|
+
let field = new control.fieldtype(control, this, value);
|
|
426
|
+
fields.set(identifier, field);
|
|
427
|
+
if (errors !== null && errors.has(identifier))
|
|
428
|
+
field.errors = errors.get(identifier);
|
|
429
|
+
if (lookupdata !== null && lookupdata.has(identifier))
|
|
430
|
+
field.lookupdata = lookupdata.get(identifier);
|
|
431
|
+
}
|
|
432
|
+
|
|
433
|
+
this._fields = fields;
|
|
434
|
+
this._sparsevalues = null;
|
|
435
|
+
this._sparsefielderrors = null;
|
|
436
|
+
this._sparselookupdata = null;
|
|
277
437
|
}
|
|
278
438
|
|
|
279
|
-
|
|
439
|
+
[ul4.symbols.repr]()
|
|
280
440
|
{
|
|
281
441
|
let v = ["<Record id=", ul4._repr(this.id)];
|
|
282
442
|
for (let field of this.fields.values())
|
|
283
443
|
{
|
|
284
|
-
if (field.control.priority)
|
|
444
|
+
if (field.control.priority && !field.is_empty())
|
|
285
445
|
{
|
|
286
446
|
v.push(" v_");
|
|
287
447
|
v.push(field.control.identifier);
|
|
@@ -289,21 +449,32 @@ export class Record extends Base
|
|
|
289
449
|
v.push(ul4._repr(field.value)); // FIXME: This might lead to infinite recursions
|
|
290
450
|
}
|
|
291
451
|
}
|
|
292
|
-
v.push("
|
|
452
|
+
v.push(" state=");
|
|
453
|
+
v.push(ul4._repr(this.state));
|
|
454
|
+
v.push(">");
|
|
293
455
|
return v.join("");
|
|
294
456
|
}
|
|
295
457
|
|
|
458
|
+
get state()
|
|
459
|
+
{
|
|
460
|
+
if (this._is_deleted)
|
|
461
|
+
return "deleted";
|
|
462
|
+
else if (this._is_new)
|
|
463
|
+
return "new";
|
|
464
|
+
else if (this.is_dirty())
|
|
465
|
+
return "dirty";
|
|
466
|
+
else
|
|
467
|
+
return "saved";
|
|
468
|
+
}
|
|
469
|
+
|
|
296
470
|
get values()
|
|
297
471
|
{
|
|
298
472
|
if (this._values === null)
|
|
299
473
|
{
|
|
300
|
-
this._values =
|
|
301
|
-
for (let
|
|
474
|
+
this._values = new Map();
|
|
475
|
+
for (let field of this.fields.values())
|
|
302
476
|
{
|
|
303
|
-
|
|
304
|
-
if (typeof(fieldvalue) === "undefined")
|
|
305
|
-
fieldvalue = null;
|
|
306
|
-
this._values.set(identifier, fieldvalue);
|
|
477
|
+
this._values.set(field.control.identifier, field.value);
|
|
307
478
|
}
|
|
308
479
|
}
|
|
309
480
|
return this._values;
|
|
@@ -312,14 +483,7 @@ export class Record extends Base
|
|
|
312
483
|
get fields()
|
|
313
484
|
{
|
|
314
485
|
if (this._fields === null)
|
|
315
|
-
|
|
316
|
-
this._fields = ul4._havemap ? new Map() : {};
|
|
317
|
-
for (let [identifier, value] of this.values.entries())
|
|
318
|
-
{
|
|
319
|
-
let field = new Field(this.app.controls.get(identifier), this, value);
|
|
320
|
-
this._fields.set(identifier, field);
|
|
321
|
-
}
|
|
322
|
-
}
|
|
486
|
+
this._make_fields(false, this._sparsevalues, this._sparsefielderrors, this._sparsefieldlookupdata)
|
|
323
487
|
return this._fields;
|
|
324
488
|
}
|
|
325
489
|
|
|
@@ -349,7 +513,9 @@ export class Record extends Base
|
|
|
349
513
|
|
|
350
514
|
delete()
|
|
351
515
|
{
|
|
352
|
-
|
|
516
|
+
let result = this.app.globals.handler.delete(this);
|
|
517
|
+
this._is_deleted = true;
|
|
518
|
+
return result;
|
|
353
519
|
}
|
|
354
520
|
|
|
355
521
|
save()
|
|
@@ -397,62 +563,894 @@ export class Record extends Base
|
|
|
397
563
|
return true;
|
|
398
564
|
}
|
|
399
565
|
|
|
400
|
-
|
|
566
|
+
ul4onload(decoder)
|
|
567
|
+
{
|
|
568
|
+
super.ul4onload(decoder);
|
|
569
|
+
this._is_new = false;
|
|
570
|
+
}
|
|
571
|
+
|
|
572
|
+
_dumpUL4ONAttr(name)
|
|
573
|
+
{
|
|
574
|
+
if (name === "values")
|
|
575
|
+
return this._sparsevalues;
|
|
576
|
+
else
|
|
577
|
+
return this[name];
|
|
578
|
+
}
|
|
579
|
+
|
|
580
|
+
_loadUL4ONAttr(name, value)
|
|
581
|
+
{
|
|
582
|
+
if (name === "values")
|
|
583
|
+
{
|
|
584
|
+
this._sparsevalues = value;
|
|
585
|
+
this._values = null;
|
|
586
|
+
this._fields = null;
|
|
587
|
+
}
|
|
588
|
+
else
|
|
589
|
+
this[name] = value;
|
|
590
|
+
}
|
|
591
|
+
|
|
592
|
+
[ul4.symbols.getattr](name)
|
|
593
|
+
{
|
|
594
|
+
if (name.startsWith("c_"))
|
|
595
|
+
return this.children.get(name.substr(2))
|
|
596
|
+
else if (name.startsWith("f_"))
|
|
597
|
+
return this.fields.get(name.substr(2))
|
|
598
|
+
else if (name.startsWith("v_"))
|
|
599
|
+
return this.values.get(name.substr(2))
|
|
600
|
+
else
|
|
601
|
+
return this[name];
|
|
602
|
+
}
|
|
603
|
+
|
|
604
|
+
[ul4.symbols.setattr](name, value)
|
|
605
|
+
{
|
|
606
|
+
if (name.startsWith("c_"))
|
|
607
|
+
this.children[name.substr(2)] = value;
|
|
608
|
+
else if (name.startsWith("v_"))
|
|
609
|
+
this.fields.get(name.substr(2)).value = value;
|
|
610
|
+
else
|
|
611
|
+
throw new ul4.AttributeError(this, name);
|
|
612
|
+
}
|
|
613
|
+
};
|
|
614
|
+
|
|
615
|
+
Record.prototype._ul4onattrs = ["app", "createdat", "createdby", "updatedat", "updatedby", "updatecount", "_sparsevalues", "attachments", "children", "errors", "_sparsefielderrors", "_sparsefieldlookupdata"];
|
|
616
|
+
Record.prototype._ul4attrs = new Set(["id", "app", "createdat", "createdby", "updatedat", "updatedby", "updatecount", "values", "attachments", "children", "errors"]);
|
|
617
|
+
ul4.expose(Record.prototype.is_dirty, []);
|
|
618
|
+
ul4.expose(Record.prototype.has_errors, []);
|
|
619
|
+
ul4.expose(Record.prototype.delete, []);
|
|
620
|
+
ul4.expose(Record.prototype.save, []);
|
|
621
|
+
ul4.expose(Record.prototype.update, ["**values"], {"needsobject": true});
|
|
622
|
+
|
|
623
|
+
|
|
624
|
+
export class Field extends Base
|
|
625
|
+
{
|
|
626
|
+
static classdoc = "Holds the value of a field of a record (and related information)";
|
|
627
|
+
|
|
628
|
+
constructor(control, record, value)
|
|
629
|
+
{
|
|
630
|
+
super(null);
|
|
631
|
+
this.control = control;
|
|
632
|
+
this.record = record;
|
|
633
|
+
this._label = null;
|
|
634
|
+
this._lookupdate = null;
|
|
635
|
+
this.errors = [];
|
|
636
|
+
this._value = null;
|
|
637
|
+
this.value = value;
|
|
638
|
+
this._dirty = false;
|
|
639
|
+
}
|
|
640
|
+
|
|
641
|
+
get value()
|
|
642
|
+
{
|
|
643
|
+
return this._value;
|
|
644
|
+
}
|
|
645
|
+
|
|
646
|
+
set value(value)
|
|
647
|
+
{
|
|
648
|
+
let oldvalue = this._value;
|
|
649
|
+
|
|
650
|
+
let change = {value: value, errors: []};
|
|
651
|
+
this._validate(change);
|
|
652
|
+
|
|
653
|
+
if (ul4._ne(oldvalue, change.value))
|
|
654
|
+
{
|
|
655
|
+
this.record.values.set(this.control.identifier, change.value);
|
|
656
|
+
this._value = change.value;
|
|
657
|
+
this._dirty = true;
|
|
658
|
+
}
|
|
659
|
+
this.errors = change.errors;
|
|
660
|
+
}
|
|
661
|
+
|
|
662
|
+
_validate(change)
|
|
663
|
+
{
|
|
664
|
+
// Do nothing, i.e. accept the value unchanged and without errors
|
|
665
|
+
}
|
|
666
|
+
|
|
667
|
+
get label()
|
|
668
|
+
{
|
|
669
|
+
if (this._label !== null)
|
|
670
|
+
return this._label;
|
|
671
|
+
return this.control.label;
|
|
672
|
+
}
|
|
673
|
+
|
|
674
|
+
set label(value)
|
|
675
|
+
{
|
|
676
|
+
this._label = value;
|
|
677
|
+
}
|
|
678
|
+
|
|
679
|
+
get globals()
|
|
680
|
+
{
|
|
681
|
+
return this.control.globals;
|
|
682
|
+
}
|
|
683
|
+
|
|
684
|
+
is_empty()
|
|
685
|
+
{
|
|
686
|
+
return this._value === null || (ul4._islist(this._value) && this._value.length === 0);
|
|
687
|
+
}
|
|
688
|
+
|
|
689
|
+
is_dirty()
|
|
690
|
+
{
|
|
691
|
+
return this._dirty;
|
|
692
|
+
}
|
|
693
|
+
|
|
694
|
+
has_errors()
|
|
695
|
+
{
|
|
696
|
+
return this.errors.length !== 0;
|
|
697
|
+
}
|
|
698
|
+
|
|
699
|
+
search(searchvalue)
|
|
700
|
+
{
|
|
701
|
+
return this.control.search(this.value, searchvalue);
|
|
702
|
+
}
|
|
703
|
+
|
|
704
|
+
msg_field_required(value)
|
|
705
|
+
{
|
|
706
|
+
switch (this.globals.lang)
|
|
707
|
+
{
|
|
708
|
+
case "de":
|
|
709
|
+
return `"${this.label}" wird benötigt!`;
|
|
710
|
+
default:
|
|
711
|
+
return `"${this.label}" is required!`;
|
|
712
|
+
}
|
|
713
|
+
}
|
|
714
|
+
|
|
715
|
+
msg_field_wrong_type(value)
|
|
716
|
+
{
|
|
717
|
+
return `"${this.label}" doesn't support the type ${ul4._type(value).name}!`;
|
|
718
|
+
}
|
|
719
|
+
|
|
720
|
+
msg_bool_truerequired(value)
|
|
721
|
+
{
|
|
722
|
+
return `"${this.label}" only accepts "Yes"!`;
|
|
723
|
+
}
|
|
724
|
+
|
|
725
|
+
msg_string_tooshort(value)
|
|
726
|
+
{
|
|
727
|
+
return `"${this.label}" is too short. Tou must use at least ${this.control.minlength} characters!`;
|
|
728
|
+
}
|
|
729
|
+
|
|
730
|
+
msg_string_toolong(value)
|
|
731
|
+
{
|
|
732
|
+
return `"${this.label}" is too long. You may use at most ${this.control.maxlength} characters!`;
|
|
733
|
+
}
|
|
734
|
+
|
|
735
|
+
msg_email_format(value)
|
|
736
|
+
{
|
|
737
|
+
return `"${this.label}" must be a valid email address!`;
|
|
738
|
+
}
|
|
739
|
+
|
|
740
|
+
msg_url_format(value)
|
|
741
|
+
{
|
|
742
|
+
return `"${this.label}" must be a valid URL!`;
|
|
743
|
+
}
|
|
744
|
+
|
|
745
|
+
msg_tel_format(value)
|
|
746
|
+
{
|
|
747
|
+
return `"${this.label}" must be a valid phone number!`;
|
|
748
|
+
}
|
|
749
|
+
|
|
750
|
+
msg_date_format(value)
|
|
751
|
+
{
|
|
752
|
+
return `"${this.label}" doesn't support this date format!`;
|
|
753
|
+
}
|
|
754
|
+
|
|
755
|
+
msg_lookup_wrongitem(value)
|
|
756
|
+
{
|
|
757
|
+
return `The option ${ul4._repr(value)} for "${this.label}" doesn't belong to this lookup!`;
|
|
758
|
+
}
|
|
759
|
+
|
|
760
|
+
msg_lookup_unknownkey(value)
|
|
761
|
+
{
|
|
762
|
+
return `The option ${ul4._repr(value)} for "${this.label}" is unknown!`;
|
|
763
|
+
}
|
|
764
|
+
|
|
765
|
+
msg_applookup_wrongrecord(value)
|
|
766
|
+
{
|
|
767
|
+
return `The record ${ul4._repr(value)} for "${this.label}" doesn't belong to the correct app!`;
|
|
768
|
+
}
|
|
769
|
+
|
|
770
|
+
msg_applookup_unknownkey(value)
|
|
771
|
+
{
|
|
772
|
+
return `The record ${ul4._repr(value)} for "${this.label}" can't be found!`;
|
|
773
|
+
}
|
|
774
|
+
|
|
775
|
+
[ul4.symbols.repr]()
|
|
776
|
+
{
|
|
777
|
+
let s = "<Field identifier=";
|
|
778
|
+
s += ul4._repr(this.control.identifier)
|
|
779
|
+
if (this._dirty)
|
|
780
|
+
s += " is_dirty()=True";
|
|
781
|
+
if (this.errors.length > 0)
|
|
782
|
+
s += " has_errors()=True";
|
|
783
|
+
s += ">"
|
|
784
|
+
return s;
|
|
785
|
+
}
|
|
786
|
+
};
|
|
787
|
+
|
|
788
|
+
Field.prototype._ul4onattrs = ["control", "record", "label", "value", "errors", "enabled", "writable", "visible"];
|
|
789
|
+
Field.prototype._ul4attrs = new Set(["control", "record", "label", "value", "errors", "enabled", "writable", "visible"]);
|
|
790
|
+
|
|
791
|
+
|
|
792
|
+
export class BoolField extends Field
|
|
793
|
+
{
|
|
794
|
+
static classdoc = "Holds the value of a bool field of a record (and related information)";
|
|
795
|
+
|
|
796
|
+
_validate(change)
|
|
797
|
+
{
|
|
798
|
+
if (change.value === null)
|
|
799
|
+
{
|
|
800
|
+
if (this.control.required)
|
|
801
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
802
|
+
}
|
|
803
|
+
else if (typeof(change.value) === "boolean")
|
|
804
|
+
{
|
|
805
|
+
if (this.control.required && !change.value)
|
|
806
|
+
change.errors.push(this.msg_bool_truerequired(change.value));
|
|
807
|
+
}
|
|
808
|
+
else
|
|
809
|
+
{
|
|
810
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
811
|
+
change.value = null;
|
|
812
|
+
}
|
|
813
|
+
}
|
|
814
|
+
};
|
|
815
|
+
|
|
816
|
+
|
|
817
|
+
export class IntField extends Field
|
|
818
|
+
{
|
|
819
|
+
static classdoc = "Holds the value of an int field of a record (and related information)";
|
|
820
|
+
|
|
821
|
+
_validate(change)
|
|
822
|
+
{
|
|
823
|
+
if (change.value === null)
|
|
824
|
+
{
|
|
825
|
+
if (this.control.required)
|
|
826
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
827
|
+
}
|
|
828
|
+
else if (typeof(change.value) !== "number" || Math.round(change.value) !== change.value)
|
|
829
|
+
{
|
|
830
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
831
|
+
}
|
|
832
|
+
}
|
|
833
|
+
};
|
|
834
|
+
|
|
835
|
+
|
|
836
|
+
export class NumberField extends Field
|
|
837
|
+
{
|
|
838
|
+
static classdoc = "Holds the value of a number field of a record (and related information)";
|
|
839
|
+
|
|
840
|
+
_validate(change)
|
|
841
|
+
{
|
|
842
|
+
if (change.value === null || change.value === "")
|
|
843
|
+
{
|
|
844
|
+
if (this.control.required)
|
|
845
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
846
|
+
change.value = null;
|
|
847
|
+
}
|
|
848
|
+
else if (typeof(change.value) !== "number")
|
|
849
|
+
{
|
|
850
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
851
|
+
}
|
|
852
|
+
}
|
|
853
|
+
};
|
|
854
|
+
|
|
855
|
+
|
|
856
|
+
export class StringField extends Field
|
|
857
|
+
{
|
|
858
|
+
static classdoc = "Holds the value of a string field of a record (and related information)";
|
|
859
|
+
|
|
860
|
+
_validate(change)
|
|
861
|
+
{
|
|
862
|
+
if (change.value === null || change.value === "")
|
|
863
|
+
{
|
|
864
|
+
if (this.control.required)
|
|
865
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
866
|
+
change.value = null;
|
|
867
|
+
}
|
|
868
|
+
else if (typeof(change.value) === "string")
|
|
869
|
+
{
|
|
870
|
+
let minlength = this.control.minlength;
|
|
871
|
+
let maxlength = this.control.maxlength;
|
|
872
|
+
if (minlength !== null && change.value.length < minlength)
|
|
873
|
+
change.errors.push(this.msg_string_tooshort(change.value))
|
|
874
|
+
if (maxlength !== null && change.value.length > maxlength)
|
|
875
|
+
change.errors.push(this.msg_string_toolong(change.value))
|
|
876
|
+
}
|
|
877
|
+
else
|
|
878
|
+
{
|
|
879
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
880
|
+
change.value = null;
|
|
881
|
+
}
|
|
882
|
+
}
|
|
883
|
+
};
|
|
884
|
+
|
|
885
|
+
|
|
886
|
+
export class EmailField extends StringField
|
|
887
|
+
{
|
|
888
|
+
static classdoc = "Holds the value of a string/email field of a record (and related information)";
|
|
889
|
+
|
|
890
|
+
_validate(change)
|
|
891
|
+
{
|
|
892
|
+
if (typeof(change.value) === "string" && change.value.length > 0)
|
|
893
|
+
{
|
|
894
|
+
const re = /^(([^<>()[\]\\.,;:\s@"]+(\.[^<>()[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/i;
|
|
895
|
+
if (!re.test(change.value))
|
|
896
|
+
change.errors.push(this.msg_email_format(change.value));
|
|
897
|
+
}
|
|
898
|
+
super._validate(change);
|
|
899
|
+
}
|
|
900
|
+
};
|
|
901
|
+
|
|
902
|
+
|
|
903
|
+
export class URLField extends StringField
|
|
904
|
+
{
|
|
905
|
+
static classdoc = "Holds the value of a string/url field of a record (and related information)";
|
|
906
|
+
|
|
907
|
+
_validate(change)
|
|
908
|
+
{
|
|
909
|
+
if (typeof(change.value) === "string" && change.value.length > 0)
|
|
910
|
+
{
|
|
911
|
+
let url = null;
|
|
912
|
+
try
|
|
913
|
+
{
|
|
914
|
+
url = new URL(change.value);
|
|
915
|
+
}
|
|
916
|
+
catch (exc)
|
|
917
|
+
{
|
|
918
|
+
change.errors.push(this.msg_url_format(change.value));
|
|
919
|
+
}
|
|
920
|
+
if (url !== null && url.protocol !== "http:" && url.protocol !== "https:")
|
|
921
|
+
{
|
|
922
|
+
change.errors.push(this.msg_url_format(change.value));
|
|
923
|
+
}
|
|
924
|
+
}
|
|
925
|
+
super._validate(change);
|
|
926
|
+
}
|
|
927
|
+
};
|
|
928
|
+
|
|
929
|
+
|
|
930
|
+
export class TelField extends StringField
|
|
931
|
+
{
|
|
932
|
+
static classdoc = "Holds the value of a string/tel field of a record (and related information)";
|
|
933
|
+
|
|
934
|
+
_validate(change)
|
|
935
|
+
{
|
|
936
|
+
if (typeof(change.value) === "string" && change.value.length > 0)
|
|
937
|
+
{
|
|
938
|
+
const re = /^\\+?[0-9 /()-]+$/;
|
|
939
|
+
if (!re.test(change.value))
|
|
940
|
+
change.errors.push(this.msg_tel_format(change.value));
|
|
941
|
+
}
|
|
942
|
+
super._validate(change);
|
|
943
|
+
}
|
|
944
|
+
};
|
|
945
|
+
|
|
946
|
+
|
|
947
|
+
export class TextAreaField extends StringField
|
|
948
|
+
{
|
|
949
|
+
static classdoc = "Holds the value of a string/textarea field of a record (and related information)";
|
|
950
|
+
};
|
|
951
|
+
|
|
952
|
+
|
|
953
|
+
export class HTMLField extends StringField
|
|
954
|
+
{
|
|
955
|
+
static classdoc = "Holds the value of a string/html field of a record (and related information)";
|
|
956
|
+
};
|
|
957
|
+
|
|
958
|
+
|
|
959
|
+
export class GeoField extends Field
|
|
960
|
+
{
|
|
961
|
+
static classdoc = "Holds the value of a geo field of a record (and related information)";
|
|
962
|
+
|
|
963
|
+
_validate(change)
|
|
964
|
+
{
|
|
965
|
+
if (change.value === null || change.value === "")
|
|
966
|
+
{
|
|
967
|
+
if (this.control.required)
|
|
968
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
969
|
+
change.value = null;
|
|
970
|
+
}
|
|
971
|
+
else if (!(change.value instanceof Geo))
|
|
972
|
+
{
|
|
973
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
974
|
+
change.value = null;
|
|
975
|
+
}
|
|
976
|
+
}
|
|
977
|
+
};
|
|
978
|
+
|
|
979
|
+
|
|
980
|
+
export class FileField extends Field
|
|
981
|
+
{
|
|
982
|
+
static classdoc = "Holds the value of a file field of a record (and related information)";
|
|
983
|
+
|
|
984
|
+
_validate(change)
|
|
985
|
+
{
|
|
986
|
+
if (change.value === null || change.value === "")
|
|
987
|
+
{
|
|
988
|
+
if (this.control.required)
|
|
989
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
990
|
+
change.value = null;
|
|
991
|
+
}
|
|
992
|
+
else if (!(change.value instanceof File))
|
|
993
|
+
{
|
|
994
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
995
|
+
change.value = null;
|
|
996
|
+
}
|
|
997
|
+
}
|
|
998
|
+
};
|
|
999
|
+
|
|
1000
|
+
|
|
1001
|
+
export class FileSignatureField extends FileField
|
|
1002
|
+
{
|
|
1003
|
+
static classdoc = "Holds the value of a file/signature field of a record (and related information)";
|
|
1004
|
+
|
|
1005
|
+
_validate(change)
|
|
1006
|
+
{
|
|
1007
|
+
// FIXME: Implement handling of data URLs.
|
|
1008
|
+
super._validate(change);
|
|
1009
|
+
}
|
|
1010
|
+
};
|
|
1011
|
+
|
|
1012
|
+
|
|
1013
|
+
export class DateFieldBase extends Field
|
|
1014
|
+
{
|
|
1015
|
+
static classdoc = "Holds the value of a date field of a record (and related information)";
|
|
1016
|
+
|
|
1017
|
+
_validate(change)
|
|
1018
|
+
{
|
|
1019
|
+
if (change.value === null || change.value === "")
|
|
1020
|
+
{
|
|
1021
|
+
if (this.control.required)
|
|
1022
|
+
change.errors.push(this.msg_field_required(change.value));
|
|
1023
|
+
change.value = null;
|
|
1024
|
+
}
|
|
1025
|
+
else if (change.value instanceof Date)
|
|
1026
|
+
{
|
|
1027
|
+
change.value = this._convert(new Date(change.value.getTime()));
|
|
1028
|
+
}
|
|
1029
|
+
else if (typeof(change.value) === "string")
|
|
1030
|
+
{
|
|
1031
|
+
let value = null;
|
|
1032
|
+
if (change.value.length === 10)
|
|
1033
|
+
value = new Date(change.value + "T00:00:00");
|
|
1034
|
+
else if (change.value.length === 16)
|
|
1035
|
+
value = new Date(change.value + ":00");
|
|
1036
|
+
else if (change.value.length === 19)
|
|
1037
|
+
value = new Date(change.value);
|
|
1038
|
+
|
|
1039
|
+
if (value === null || Number.isNaN(value.getYear()))
|
|
1040
|
+
{
|
|
1041
|
+
change.errors.push(this.msg_date_format(change.value));
|
|
1042
|
+
// Keep original invalid string
|
|
1043
|
+
}
|
|
1044
|
+
else
|
|
1045
|
+
{
|
|
1046
|
+
change.value = this._convert(value);
|
|
1047
|
+
}
|
|
1048
|
+
}
|
|
1049
|
+
else
|
|
1050
|
+
{
|
|
1051
|
+
change.errors.push(this.msg_field_wrong_type(change.value));
|
|
1052
|
+
change.value = null;
|
|
1053
|
+
}
|
|
1054
|
+
}
|
|
1055
|
+
};
|
|
1056
|
+
|
|
1057
|
+
|
|
1058
|
+
export class DateField extends DateFieldBase
|
|
1059
|
+
{
|
|
1060
|
+
static classdoc = "Holds the value of a date/date field of a record (and related information)";
|
|
1061
|
+
|
|
1062
|
+
_convert(date)
|
|
1063
|
+
{
|
|
1064
|
+
return new ul4.Date_(date.getFullYear(), date.getMonth()+1, date.getDate());
|
|
1065
|
+
}
|
|
1066
|
+
};
|
|
1067
|
+
|
|
1068
|
+
|
|
1069
|
+
export class DatetimeMinuteField extends DateFieldBase
|
|
1070
|
+
{
|
|
1071
|
+
static classdoc = "Holds the value of a date/datetimeminute field of a record (and related information)";
|
|
1072
|
+
|
|
1073
|
+
_convert(date)
|
|
1074
|
+
{
|
|
1075
|
+
// Get rid of seconds and milliseconds
|
|
1076
|
+
date.setSeconds(0);
|
|
1077
|
+
date.setMilliseconds(0);
|
|
1078
|
+
return date;
|
|
1079
|
+
}
|
|
1080
|
+
};
|
|
1081
|
+
|
|
1082
|
+
|
|
1083
|
+
export class DatetimeSecondField extends DateFieldBase
|
|
1084
|
+
{
|
|
1085
|
+
static classdoc = "Holds the value of a date/datetimesecond field of a record (and related information)";
|
|
1086
|
+
|
|
1087
|
+
_convert(date)
|
|
1088
|
+
{
|
|
1089
|
+
// Get rid of milliseconds
|
|
1090
|
+
date.setMilliseconds(0);
|
|
1091
|
+
return date;
|
|
1092
|
+
}
|
|
1093
|
+
};
|
|
1094
|
+
|
|
1095
|
+
|
|
1096
|
+
export class LookupFieldBase extends Field
|
|
1097
|
+
{
|
|
1098
|
+
static classdoc = "Base type of LookupField and MultipleLookupField";
|
|
1099
|
+
|
|
1100
|
+
get lookupdata()
|
|
1101
|
+
{
|
|
1102
|
+
if (this._lookupdate !== null)
|
|
1103
|
+
return this._lookupdate;
|
|
1104
|
+
else
|
|
1105
|
+
return this.control.lookupdata;
|
|
1106
|
+
}
|
|
1107
|
+
|
|
1108
|
+
set lookupdata(value)
|
|
1109
|
+
{
|
|
1110
|
+
this._lookupdate = value;
|
|
1111
|
+
}
|
|
1112
|
+
|
|
1113
|
+
_find_lookupitem(change)
|
|
1114
|
+
{
|
|
1115
|
+
let v = change.value;
|
|
1116
|
+
if (typeof(v) === "string")
|
|
1117
|
+
{
|
|
1118
|
+
// If `lookupdata`} is `null`, this is probably an interface,
|
|
1119
|
+
// so we can't validate anything (note that interfaces will however go
|
|
1120
|
+
// away in the future)
|
|
1121
|
+
if (this.lookupdata === null)
|
|
1122
|
+
return;
|
|
1123
|
+
let lookupitem = this.lookupdata.get(v);
|
|
1124
|
+
if (lookupitem === undefined)
|
|
1125
|
+
{
|
|
1126
|
+
// If the lookup control is auto expandable,
|
|
1127
|
+
// the user may have given us a label
|
|
1128
|
+
if (this.control.autoexpandable)
|
|
1129
|
+
{
|
|
1130
|
+
// Search for the LookupItem with that label
|
|
1131
|
+
for (let search_lookupitem of this.lookupdata.values())
|
|
1132
|
+
{
|
|
1133
|
+
if (v === search_lookupitem.label)
|
|
1134
|
+
{
|
|
1135
|
+
change.value = search_lookupitem;
|
|
1136
|
+
return;
|
|
1137
|
+
}
|
|
1138
|
+
}
|
|
1139
|
+
// If we couldn't find the label, keep the label as it is.
|
|
1140
|
+
}
|
|
1141
|
+
else
|
|
1142
|
+
{
|
|
1143
|
+
change.errors.push(this.msg_lookup_unknownkey(v))
|
|
1144
|
+
change.value = null;
|
|
1145
|
+
}
|
|
1146
|
+
}
|
|
1147
|
+
else
|
|
1148
|
+
{
|
|
1149
|
+
change.value = lookupitem;
|
|
1150
|
+
}
|
|
1151
|
+
}
|
|
1152
|
+
else if (v instanceof LookupItem)
|
|
1153
|
+
{
|
|
1154
|
+
let value = this.control.lookupdata.get(v.key);
|
|
1155
|
+
if (value !== v)
|
|
1156
|
+
{
|
|
1157
|
+
change.errors.push(this.msg_lookup_wrongitem(v));
|
|
1158
|
+
change.value = null;
|
|
1159
|
+
}
|
|
1160
|
+
}
|
|
1161
|
+
else
|
|
1162
|
+
{
|
|
1163
|
+
change.errors.push(this.msg_field_wrong_type(v));
|
|
1164
|
+
change.value = null;
|
|
1165
|
+
}
|
|
1166
|
+
}
|
|
1167
|
+
};
|
|
1168
|
+
|
|
1169
|
+
|
|
1170
|
+
export class LookupField extends LookupFieldBase
|
|
1171
|
+
{
|
|
1172
|
+
static classdoc = "Holds the value of a lookup field of a record (and related information)";
|
|
1173
|
+
|
|
1174
|
+
_validate(change)
|
|
1175
|
+
{
|
|
1176
|
+
let v = change.value;
|
|
1177
|
+
if (v === null || v === "" || this.control.nonekey === v)
|
|
1178
|
+
{
|
|
1179
|
+
if (this.control.required)
|
|
1180
|
+
change.errors.push(this.msg_field_required(v));
|
|
1181
|
+
change.value = null;
|
|
1182
|
+
}
|
|
1183
|
+
else
|
|
1184
|
+
{
|
|
1185
|
+
this._find_lookupitem(change);
|
|
1186
|
+
}
|
|
1187
|
+
}
|
|
1188
|
+
};
|
|
1189
|
+
|
|
1190
|
+
|
|
1191
|
+
export class MultipleLookupField extends LookupFieldBase
|
|
1192
|
+
{
|
|
1193
|
+
static classdoc = "Holds the value of a multiple lookup field of a record (and related information)";
|
|
1194
|
+
|
|
1195
|
+
_validate(change)
|
|
1196
|
+
{
|
|
1197
|
+
let v = change.value;
|
|
1198
|
+
let islist = (Object.prototype.toString.call(v) === "[object Array]");
|
|
1199
|
+
|
|
1200
|
+
if (v === null || v === "" || this.control.nonekey === v || (islist && v.length === 0))
|
|
1201
|
+
{
|
|
1202
|
+
if (this.control.required)
|
|
1203
|
+
change.errors.push(this.msg_field_required(v));
|
|
1204
|
+
change.value = [];
|
|
1205
|
+
}
|
|
1206
|
+
else if (islist)
|
|
1207
|
+
{
|
|
1208
|
+
let newvalue = [];
|
|
1209
|
+
for (let item of v)
|
|
1210
|
+
{
|
|
1211
|
+
let singlechange = {value: item, errors: []};
|
|
1212
|
+
this._find_lookupitem(singlechange);
|
|
1213
|
+
if (singlechange.errors.length > 0)
|
|
1214
|
+
change.errors = [...change.errors, ...singlechange.errors];
|
|
1215
|
+
else
|
|
1216
|
+
newvalue.push(singlechange.value);
|
|
1217
|
+
}
|
|
1218
|
+
change.value = newvalue;
|
|
1219
|
+
}
|
|
1220
|
+
else
|
|
1221
|
+
{
|
|
1222
|
+
this._find_lookupitem(change);
|
|
1223
|
+
if (change.errors.length > 0)
|
|
1224
|
+
change.value = [];
|
|
1225
|
+
else
|
|
1226
|
+
change.value = [change.value];
|
|
1227
|
+
}
|
|
1228
|
+
}
|
|
1229
|
+
};
|
|
1230
|
+
|
|
1231
|
+
|
|
1232
|
+
export class AppLookupFieldBase extends Field
|
|
1233
|
+
{
|
|
1234
|
+
static classdoc = "Base type of AppLookupField and MultipleAppLookupField";
|
|
1235
|
+
|
|
1236
|
+
get lookupdata()
|
|
1237
|
+
{
|
|
1238
|
+
if (this._lookupdata !== null)
|
|
1239
|
+
return this._lookupdata;
|
|
1240
|
+
else
|
|
1241
|
+
{
|
|
1242
|
+
if (this.control.lookup_app.records !== null)
|
|
1243
|
+
return this.control.lookup_app.records;
|
|
1244
|
+
}
|
|
1245
|
+
return new Map();
|
|
1246
|
+
}
|
|
1247
|
+
|
|
1248
|
+
set lookupdata(value)
|
|
1249
|
+
{
|
|
1250
|
+
this._lookupdata = value;
|
|
1251
|
+
}
|
|
1252
|
+
|
|
1253
|
+
_find_record(change)
|
|
1254
|
+
{
|
|
1255
|
+
let v = change.value;
|
|
1256
|
+
if (typeof(v) === "string")
|
|
1257
|
+
{
|
|
1258
|
+
let record = this.lookupdata.get(v);
|
|
1259
|
+
if (record === undefined)
|
|
1260
|
+
{
|
|
1261
|
+
change.errors.push(this.msg_applookup_unknownkey(v))
|
|
1262
|
+
change.value = null;
|
|
1263
|
+
}
|
|
1264
|
+
else
|
|
1265
|
+
{
|
|
1266
|
+
change.value = record;
|
|
1267
|
+
}
|
|
1268
|
+
}
|
|
1269
|
+
else if (v instanceof Record)
|
|
1270
|
+
{
|
|
1271
|
+
if (v.app !== this.control.lookup_app)
|
|
1272
|
+
{
|
|
1273
|
+
change.errors.push(this.msg_applookup_wrongrecord(v));
|
|
1274
|
+
change.value = null;
|
|
1275
|
+
}
|
|
1276
|
+
}
|
|
1277
|
+
else
|
|
1278
|
+
{
|
|
1279
|
+
change.errors.push(this.msg_field_wrong_type(v));
|
|
1280
|
+
change.value = null;
|
|
1281
|
+
}
|
|
1282
|
+
}
|
|
1283
|
+
};
|
|
1284
|
+
|
|
1285
|
+
|
|
1286
|
+
export class AppLookupField extends AppLookupFieldBase
|
|
1287
|
+
{
|
|
1288
|
+
static classdoc = "Holds the value of a applookup field of a record (and related information)";
|
|
1289
|
+
|
|
1290
|
+
_validate(change)
|
|
1291
|
+
{
|
|
1292
|
+
this._find_record(change);
|
|
1293
|
+
}
|
|
1294
|
+
};
|
|
1295
|
+
|
|
1296
|
+
|
|
1297
|
+
export class MultipleAppLookupField extends AppLookupFieldBase
|
|
1298
|
+
{
|
|
1299
|
+
static classdoc = "Holds the value of a multiple applookup field of a record (and related information)";
|
|
1300
|
+
|
|
1301
|
+
_validate(change)
|
|
1302
|
+
{
|
|
1303
|
+
let v = change.value;
|
|
1304
|
+
let islist = (Object.prototype.toString.call(v) === "[object Array]");
|
|
1305
|
+
|
|
1306
|
+
if (v === null || v === "" || this.control.nonekey === v || (islist && v.length === 0))
|
|
1307
|
+
{
|
|
1308
|
+
if (this.control.required)
|
|
1309
|
+
change.errors.push(this.msg_field_required(v));
|
|
1310
|
+
change.value = [];
|
|
1311
|
+
}
|
|
1312
|
+
else if (islist)
|
|
1313
|
+
{
|
|
1314
|
+
let newvalue = [];
|
|
1315
|
+
for (let item of v)
|
|
1316
|
+
{
|
|
1317
|
+
let singlechange = {value: item, errors: []};
|
|
1318
|
+
this._find_record(singlechange);
|
|
1319
|
+
if (singlechange.errors.length > 0)
|
|
1320
|
+
change.errors = [...change.errors, ...singlechange.errors];
|
|
1321
|
+
else
|
|
1322
|
+
newvalue.push(singlechange.value);
|
|
1323
|
+
}
|
|
1324
|
+
change.value = newvalue;
|
|
1325
|
+
}
|
|
1326
|
+
else
|
|
1327
|
+
{
|
|
1328
|
+
this._find_record(change);
|
|
1329
|
+
if (change.errors.length > 0)
|
|
1330
|
+
change.value = [];
|
|
1331
|
+
else
|
|
1332
|
+
change.value = [change.value];
|
|
1333
|
+
}
|
|
1334
|
+
}
|
|
1335
|
+
};
|
|
1336
|
+
|
|
1337
|
+
|
|
1338
|
+
export class Control extends Base
|
|
1339
|
+
{
|
|
1340
|
+
[ul4.symbols.repr]()
|
|
1341
|
+
{
|
|
1342
|
+
return "<" + this.constructor.name + " id=" + ul4._repr(this.id) + " identifier=" + ul4._repr(this.identifier) + ">";
|
|
1343
|
+
}
|
|
1344
|
+
|
|
1345
|
+
get globals()
|
|
1346
|
+
{
|
|
1347
|
+
return this.app.globals;
|
|
1348
|
+
}
|
|
1349
|
+
|
|
1350
|
+
get fulltype()
|
|
1351
|
+
{
|
|
1352
|
+
return this.subtype ? this.type + "/" + this.subtype : this.type;
|
|
1353
|
+
}
|
|
1354
|
+
|
|
1355
|
+
get label()
|
|
1356
|
+
{
|
|
1357
|
+
let view_control = this._view_control();
|
|
1358
|
+
if (view_control === null)
|
|
1359
|
+
return this._label;
|
|
1360
|
+
let label = view_control.label;
|
|
1361
|
+
if (label === null)
|
|
1362
|
+
return this._label;
|
|
1363
|
+
return label;
|
|
1364
|
+
}
|
|
1365
|
+
|
|
1366
|
+
set label(value)
|
|
1367
|
+
{
|
|
1368
|
+
this._label = value;
|
|
1369
|
+
}
|
|
1370
|
+
|
|
1371
|
+
get default()
|
|
1372
|
+
{
|
|
1373
|
+
return null;
|
|
1374
|
+
}
|
|
1375
|
+
|
|
1376
|
+
get top()
|
|
1377
|
+
{
|
|
1378
|
+
let view_control = this._view_control();
|
|
1379
|
+
return view_control !== null ? view_control.top : null;
|
|
1380
|
+
}
|
|
1381
|
+
|
|
1382
|
+
get left()
|
|
1383
|
+
{
|
|
1384
|
+
let view_control = this._view_control();
|
|
1385
|
+
return view_control !== null ? view_control.left : null;
|
|
1386
|
+
}
|
|
1387
|
+
|
|
1388
|
+
get width()
|
|
1389
|
+
{
|
|
1390
|
+
let view_control = this._view_control();
|
|
1391
|
+
return view_control !== null ? view_control.width : null;
|
|
1392
|
+
}
|
|
1393
|
+
|
|
1394
|
+
get height()
|
|
1395
|
+
{
|
|
1396
|
+
let view_control = this._view_control();
|
|
1397
|
+
return view_control !== null ? view_control.height : null;
|
|
1398
|
+
}
|
|
1399
|
+
|
|
1400
|
+
get liveupdate()
|
|
1401
|
+
{
|
|
1402
|
+
let view_control = this._view_control();
|
|
1403
|
+
return view_control !== null ? view_control.liveupdate : false;
|
|
1404
|
+
}
|
|
1405
|
+
|
|
1406
|
+
get tabindex()
|
|
1407
|
+
{
|
|
1408
|
+
let view_control = this._view_control();
|
|
1409
|
+
return view_control !== null ? view_control.tabindex : null;
|
|
1410
|
+
}
|
|
1411
|
+
|
|
1412
|
+
get required()
|
|
1413
|
+
{
|
|
1414
|
+
let view_control = this._view_control();
|
|
1415
|
+
return view_control !== null ? view_control.required : false;
|
|
1416
|
+
}
|
|
1417
|
+
|
|
1418
|
+
get mode()
|
|
1419
|
+
{
|
|
1420
|
+
let view_control = this._view_control();
|
|
1421
|
+
return view_control !== null ? view_control.mode : "edit";
|
|
1422
|
+
}
|
|
1423
|
+
|
|
1424
|
+
get labelpos()
|
|
401
1425
|
{
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
else
|
|
405
|
-
return this[name];
|
|
1426
|
+
let view_control = this._view_control();
|
|
1427
|
+
return view_control !== null ? view_control.labelpos : "left";
|
|
406
1428
|
}
|
|
407
1429
|
|
|
408
|
-
|
|
1430
|
+
get labelwidth()
|
|
409
1431
|
{
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
this._sparsevalues = value;
|
|
413
|
-
this._values = null;
|
|
414
|
-
this._fields = null;
|
|
415
|
-
}
|
|
416
|
-
else
|
|
417
|
-
this[name] = value;
|
|
1432
|
+
let view_control = this._view_control();
|
|
1433
|
+
return view_control !== null ? view_control.labelwidth : null;
|
|
418
1434
|
}
|
|
419
1435
|
|
|
420
|
-
|
|
1436
|
+
get autoalign()
|
|
421
1437
|
{
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
else if (name.startsWith("f_"))
|
|
425
|
-
return this.fields.get(name.substr(2))
|
|
426
|
-
else if (name.startsWith("v_"))
|
|
427
|
-
return this.values.get(name.substr(2))
|
|
428
|
-
else
|
|
429
|
-
return this[name];
|
|
1438
|
+
let view_control = this._view_control();
|
|
1439
|
+
return view_control !== null ? view_control.autoalign : true;
|
|
430
1440
|
}
|
|
431
1441
|
|
|
432
|
-
|
|
1442
|
+
get in_active_view()
|
|
433
1443
|
{
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
else if (name.startsWith("v_"))
|
|
437
|
-
this.fields.get(name.substr(2)).value = value;
|
|
438
|
-
else
|
|
439
|
-
throw new ul4.AttributeError(this, name);
|
|
1444
|
+
let view_control = this._view_control();
|
|
1445
|
+
return view_control !== null;
|
|
440
1446
|
}
|
|
441
|
-
};
|
|
442
|
-
|
|
443
|
-
Record.prototype._ul4onattrs = ["id", "app", "createdat", "createdby", "updatedat", "updatedby", "updatecount", "values", "attachments", "children"];
|
|
444
|
-
Record.prototype._ul4attrs = ul4._makeset("id", "app", "createdat", "createdby", "updatedat", "updatedby", "updatecount", "values", "attachments", "children");
|
|
445
|
-
ul4.expose(Record.prototype.is_dirty, []);
|
|
446
|
-
ul4.expose(Record.prototype.has_errors, []);
|
|
447
|
-
ul4.expose(Record.prototype.delete, []);
|
|
448
|
-
ul4.expose(Record.prototype.save, []);
|
|
449
|
-
ul4.expose(Record.prototype.update, ["**values"], {"needsobject": true});
|
|
450
1447
|
|
|
451
|
-
|
|
452
|
-
{
|
|
453
|
-
__repr__()
|
|
1448
|
+
_view_control()
|
|
454
1449
|
{
|
|
455
|
-
|
|
1450
|
+
if (this.app._active_view === null)
|
|
1451
|
+
return null;
|
|
1452
|
+
let view_control = this.app._active_view.controls.get(this.identifier);
|
|
1453
|
+
return view_control ?? null;
|
|
456
1454
|
}
|
|
457
1455
|
|
|
458
1456
|
_logsearch(value, search)
|
|
@@ -472,11 +1470,14 @@ export class Control extends Base
|
|
|
472
1470
|
|
|
473
1471
|
Control.prototype.type = null;
|
|
474
1472
|
Control.prototype.subtype = null;
|
|
475
|
-
Control.prototype._ul4onattrs = ["
|
|
476
|
-
Control.prototype._ul4attrs =
|
|
1473
|
+
Control.prototype._ul4onattrs = ["identifier", "fieldname", "app", "_label", "priority", "order", "ininsertprocedure", "inupdateprocedure"];
|
|
1474
|
+
Control.prototype._ul4attrs = new Set(["id", "identifier", "fieldname", "app", "priority", "order", "ininsertprocedure", "inupdateprocedure", "fulltype", "label", "top", "left", "width", "height", "liveupdate", "tabindex", "required", "mode", "labelpos", "autoalign", "in_active_view"]);
|
|
1475
|
+
|
|
477
1476
|
|
|
478
1477
|
export class BoolControl extends Control
|
|
479
1478
|
{
|
|
1479
|
+
static classdoc = "A LivingApps boolean field (type 'bool')";
|
|
1480
|
+
|
|
480
1481
|
// ``search`` must by ``null``, ``false`` or ``true``
|
|
481
1482
|
search(value, search)
|
|
482
1483
|
{
|
|
@@ -489,9 +1490,13 @@ export class BoolControl extends Control
|
|
|
489
1490
|
};
|
|
490
1491
|
|
|
491
1492
|
BoolControl.prototype.type = "bool";
|
|
1493
|
+
BoolControl.prototype.fieldtype = BoolField;
|
|
1494
|
+
|
|
492
1495
|
|
|
493
1496
|
export class IntControl extends Control
|
|
494
1497
|
{
|
|
1498
|
+
static classdoc = "A LivingApps integer field (type 'int')";
|
|
1499
|
+
|
|
495
1500
|
// ``search.value`` must by ``null`` or an integer
|
|
496
1501
|
search(value, search)
|
|
497
1502
|
{
|
|
@@ -504,9 +1509,29 @@ export class IntControl extends Control
|
|
|
504
1509
|
};
|
|
505
1510
|
|
|
506
1511
|
IntControl.prototype.type = "int";
|
|
1512
|
+
IntControl.prototype.fieldtype = IntField;
|
|
1513
|
+
|
|
1514
|
+
|
|
1515
|
+
class PlaceholderControl extends Control
|
|
1516
|
+
{
|
|
1517
|
+
static classdoc = "A LivingApps multiplelookup field (type 'multiplelookup/select')";
|
|
1518
|
+
|
|
1519
|
+
get placeholder()
|
|
1520
|
+
{
|
|
1521
|
+
let view_control = this._view_control();
|
|
1522
|
+
if (view_control === null)
|
|
1523
|
+
return null;
|
|
1524
|
+
return view_control.placeholder;
|
|
1525
|
+
}
|
|
1526
|
+
};
|
|
507
1527
|
|
|
508
|
-
|
|
1528
|
+
PlaceholderControl.prototype._ul4attrs = new Set([...Control.prototype._ul4attrs, "placeholder"]);
|
|
1529
|
+
|
|
1530
|
+
|
|
1531
|
+
export class NumberControl extends PlaceholderControl
|
|
509
1532
|
{
|
|
1533
|
+
static classdoc = "A LivingApps number field (type 'number')";
|
|
1534
|
+
|
|
510
1535
|
// ``search.value`` must by ``null`` or an integer
|
|
511
1536
|
search(value, search)
|
|
512
1537
|
{
|
|
@@ -525,9 +1550,103 @@ export class NumberControl extends Control
|
|
|
525
1550
|
};
|
|
526
1551
|
|
|
527
1552
|
NumberControl.prototype.type = "number";
|
|
1553
|
+
NumberControl.prototype.fieldtype = NumberField;
|
|
1554
|
+
|
|
528
1555
|
|
|
529
|
-
export class StringControl extends
|
|
1556
|
+
export class StringControl extends PlaceholderControl
|
|
530
1557
|
{
|
|
1558
|
+
_user_placeholder(user, placeholder)
|
|
1559
|
+
{
|
|
1560
|
+
if (placeholder === null)
|
|
1561
|
+
return null;
|
|
1562
|
+
switch (placeholder)
|
|
1563
|
+
{
|
|
1564
|
+
case "{gender}":
|
|
1565
|
+
return user !== null ? user.gender : null;
|
|
1566
|
+
case "{title}":
|
|
1567
|
+
return user !== null ? user.title : null;
|
|
1568
|
+
case "{firstname}":
|
|
1569
|
+
return user !== null ? user.firstname : null;
|
|
1570
|
+
case "{surname}":
|
|
1571
|
+
return user !== null ? user.surname : null;
|
|
1572
|
+
case "{account}":
|
|
1573
|
+
return user !== null ? user.email : null;
|
|
1574
|
+
case "{streetname}":
|
|
1575
|
+
return user !== null ? user.streetname : null;
|
|
1576
|
+
case "{streetnumber}":
|
|
1577
|
+
return user !== null ? user.streetnumber : null;
|
|
1578
|
+
case "{street}":
|
|
1579
|
+
if (user === null)
|
|
1580
|
+
return null;
|
|
1581
|
+
else if (user.street === null)
|
|
1582
|
+
return user.streetnumber;
|
|
1583
|
+
else if (user.streetnumber === null)
|
|
1584
|
+
return user.street;
|
|
1585
|
+
else
|
|
1586
|
+
return user.street + " " + user.streetnumber;
|
|
1587
|
+
case "{zip}":
|
|
1588
|
+
return user !== null ? user.zip : null;
|
|
1589
|
+
case "{phone}":
|
|
1590
|
+
return user !== null ? user.phone : null;
|
|
1591
|
+
case "{fax}":
|
|
1592
|
+
return user !== null ? user.fax : null;
|
|
1593
|
+
case "{company}":
|
|
1594
|
+
return user !== null ? user.company : null;
|
|
1595
|
+
case "{city}":
|
|
1596
|
+
return user !== null ? user.city : null;
|
|
1597
|
+
case "{summary}":
|
|
1598
|
+
return user !== null ? user.summary : null;
|
|
1599
|
+
case "{interests}":
|
|
1600
|
+
return user !== null ? user.interests : null;
|
|
1601
|
+
case "{personal_website}":
|
|
1602
|
+
return user !== null ? user.personal_website : null;
|
|
1603
|
+
case "{company_website}":
|
|
1604
|
+
return user !== null ? user.company_website : null;
|
|
1605
|
+
case "{position}":
|
|
1606
|
+
return user !== null ? user.position : null;
|
|
1607
|
+
case "{department}":
|
|
1608
|
+
return user !== null ? user.department : null;
|
|
1609
|
+
case "{today}":
|
|
1610
|
+
return ul4.today();
|
|
1611
|
+
default:
|
|
1612
|
+
return placeholder;
|
|
1613
|
+
}
|
|
1614
|
+
}
|
|
1615
|
+
|
|
1616
|
+
get default()
|
|
1617
|
+
{
|
|
1618
|
+
let view_control = this._view_control();
|
|
1619
|
+
|
|
1620
|
+
if (view_control === null)
|
|
1621
|
+
return null;
|
|
1622
|
+
|
|
1623
|
+
return this._user_placeholder(this.app.globals.user, view_control.default);
|
|
1624
|
+
}
|
|
1625
|
+
|
|
1626
|
+
get minlength()
|
|
1627
|
+
{
|
|
1628
|
+
let view_control = this._view_control();
|
|
1629
|
+
|
|
1630
|
+
if (view_control === null)
|
|
1631
|
+
return 0;
|
|
1632
|
+
let minlength = view_control.minlength;
|
|
1633
|
+
if (minlength === null || minlength < 0)
|
|
1634
|
+
return 0;
|
|
1635
|
+
return minlength;
|
|
1636
|
+
}
|
|
1637
|
+
|
|
1638
|
+
get maxlength()
|
|
1639
|
+
{
|
|
1640
|
+
let view_control = this._view_control();
|
|
1641
|
+
|
|
1642
|
+
if (view_control === null)
|
|
1643
|
+
return 4000;
|
|
1644
|
+
let maxlength = view_control.maxlength;
|
|
1645
|
+
if (maxlength === null || maxlength < 0 || maxlength > 4000)
|
|
1646
|
+
return 4000;
|
|
1647
|
+
return maxlength;
|
|
1648
|
+
}
|
|
1649
|
+
|
|
531
1650
|
search(value, search)
|
|
532
1651
|
{
|
|
533
1652
|
this._logsearch(value, search);
|
|
@@ -545,46 +1664,92 @@ export class StringControl extends Control
|
|
|
545
1664
|
|
|
546
1665
|
StringControl.prototype.type = "string";
|
|
547
1666
|
|
|
1667
|
+
|
|
548
1668
|
export class TextControl extends StringControl
|
|
549
1669
|
{
|
|
1670
|
+
static classdoc = "A LivingApps text field (type 'string/text')";
|
|
550
1671
|
};
|
|
551
1672
|
|
|
552
1673
|
TextControl.prototype.subtype = "text";
|
|
1674
|
+
TextControl.prototype.fieldtype = StringField;
|
|
1675
|
+
|
|
553
1676
|
|
|
554
1677
|
export class EmailControl extends StringControl
|
|
555
1678
|
{
|
|
1679
|
+
static classdoc = "A LivingApps email field (type 'string/email')";
|
|
556
1680
|
};
|
|
557
1681
|
|
|
558
1682
|
EmailControl.prototype.subtype = "email";
|
|
1683
|
+
EmailControl.prototype.fieldtype = EmailField;
|
|
1684
|
+
|
|
559
1685
|
|
|
560
1686
|
export class URLControl extends StringControl
|
|
561
1687
|
{
|
|
1688
|
+
static classdoc = "A LivingApps URL field (type 'string/url')";
|
|
562
1689
|
};
|
|
563
1690
|
|
|
564
1691
|
URLControl.prototype.subtype = "url";
|
|
1692
|
+
URLControl.prototype.fieldtype = URLField;
|
|
1693
|
+
|
|
565
1694
|
|
|
566
1695
|
export class TelControl extends StringControl
|
|
567
1696
|
{
|
|
1697
|
+
static classdoc = "A LivingApps phone number field (type 'string/tel')";
|
|
568
1698
|
};
|
|
569
1699
|
|
|
570
1700
|
TelControl.prototype.subtype = "tel";
|
|
1701
|
+
TelControl.prototype.fieldtype = TelField;
|
|
571
1702
|
|
|
572
|
-
|
|
1703
|
+
|
|
1704
|
+
export class TextAreaControl extends StringControl
|
|
573
1705
|
{
|
|
1706
|
+
static classdoc = "A LivingApps textarea field (type 'string/textarea')";
|
|
1707
|
+
|
|
1708
|
+
get maxlength()
|
|
1709
|
+
{
|
|
1710
|
+
let view_control = this._view_control();
|
|
1711
|
+
|
|
1712
|
+
if (view_control === null)
|
|
1713
|
+
return null;
|
|
1714
|
+
// We only get the encrypted text in encryption mode, so we can't check its length
|
|
1715
|
+
if (this.encrypted !== null)
|
|
1716
|
+
return null;
|
|
1717
|
+
let maxlength = view_control.maxlength;
|
|
1718
|
+
if (maxlength < 0)
|
|
1719
|
+
return null;
|
|
1720
|
+
return maxlength;
|
|
1721
|
+
}
|
|
574
1722
|
};
|
|
575
1723
|
|
|
576
|
-
|
|
1724
|
+
TextAreaControl.prototype.subtype = "textarea";
|
|
1725
|
+
TextAreaControl.prototype.fieldtype = TextAreaField;
|
|
1726
|
+
TextAreaControl.prototype._ul4onattrs = [...StringControl.prototype._ul4onattrs, "encrypted"];
|
|
1727
|
+
TextAreaControl.prototype._ul4attrs = new Set([...StringControl.prototype._ul4attrs, "encrypted"]);
|
|
577
1728
|
|
|
578
|
-
|
|
1729
|
+
|
|
1730
|
+
export class HTMLControl extends StringControl
|
|
579
1731
|
{
|
|
1732
|
+
static classdoc = "A LivingApps HTML field (type 'string/html')";
|
|
580
1733
|
};
|
|
581
1734
|
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
TextAreaControl.prototype._ul4attrs = ul4._makeset(...StringControl.prototype._ul4attrs, "encrypted");
|
|
1735
|
+
HTMLControl.prototype.subtype = "html";
|
|
1736
|
+
HTMLControl.prototype.fieldtype = HTMLField;
|
|
585
1737
|
|
|
586
|
-
|
|
1738
|
+
|
|
1739
|
+
export class DateControl extends PlaceholderControl
|
|
587
1740
|
{
|
|
1741
|
+
static classdoc = "A LivingApps date field (type 'date/date')";
|
|
1742
|
+
|
|
1743
|
+
get default()
|
|
1744
|
+
{
|
|
1745
|
+
let view_control = this._view_control();
|
|
1746
|
+
|
|
1747
|
+
if (view_control === null)
|
|
1748
|
+
return null;
|
|
1749
|
+
|
|
1750
|
+
return view_control.default === "{today}" ? ul4.today() : null;
|
|
1751
|
+
}
|
|
1752
|
+
|
|
588
1753
|
formatstring(language)
|
|
589
1754
|
{
|
|
590
1755
|
language = language || this.app.language;
|
|
@@ -622,9 +1787,31 @@ export class DateControl extends Control
|
|
|
622
1787
|
|
|
623
1788
|
DateControl.prototype.type = "date";
|
|
624
1789
|
DateControl.prototype.subtype = "date";
|
|
1790
|
+
DateControl.prototype.fieldtype = DateField;
|
|
1791
|
+
|
|
625
1792
|
|
|
626
1793
|
export class DatetimeMinuteControl extends DateControl
|
|
627
1794
|
{
|
|
1795
|
+
static classdoc = "A LivingApps date field (type 'date/datetimeminute')";
|
|
1796
|
+
|
|
1797
|
+
get default()
|
|
1798
|
+
{
|
|
1799
|
+
let view_control = this._view_control();
|
|
1800
|
+
|
|
1801
|
+
if (view_control === null)
|
|
1802
|
+
return null;
|
|
1803
|
+
|
|
1804
|
+
if (view_control.default === "{today}")
|
|
1805
|
+
{
|
|
1806
|
+
let now = new Date();
|
|
1807
|
+
now.setSeconds(0);
|
|
1808
|
+
now.setMilliseconds(0);
|
|
1809
|
+
return now;
|
|
1810
|
+
}
|
|
1811
|
+
else
|
|
1812
|
+
return null;
|
|
1813
|
+
}
|
|
1814
|
+
|
|
628
1815
|
formatstring(language)
|
|
629
1816
|
{
|
|
630
1817
|
language = language || this.app.language;
|
|
@@ -637,9 +1824,30 @@ export class DatetimeMinuteControl extends DateControl
|
|
|
637
1824
|
};
|
|
638
1825
|
|
|
639
1826
|
DatetimeMinuteControl.prototype.subtype = "datetimeminute";
|
|
1827
|
+
DatetimeMinuteControl.prototype.fieldtype = DatetimeMinuteField;
|
|
1828
|
+
|
|
640
1829
|
|
|
641
1830
|
export class DatetimeSecondControl extends DateControl
|
|
642
1831
|
{
|
|
1832
|
+
static classdoc = "A LivingApps date field (type 'date/datetimesecond')";
|
|
1833
|
+
|
|
1834
|
+
get default()
|
|
1835
|
+
{
|
|
1836
|
+
let view_control = this._view_control();
|
|
1837
|
+
|
|
1838
|
+
if (view_control === null)
|
|
1839
|
+
return null;
|
|
1840
|
+
|
|
1841
|
+
if (view_control.default === "{today}")
|
|
1842
|
+
{
|
|
1843
|
+
let now = new Date();
|
|
1844
|
+
now.setMilliseconds(0);
|
|
1845
|
+
return now;
|
|
1846
|
+
}
|
|
1847
|
+
else
|
|
1848
|
+
return null;
|
|
1849
|
+
}
|
|
1850
|
+
|
|
643
1851
|
formatstring(language)
|
|
644
1852
|
{
|
|
645
1853
|
language = language || this.app.language;
|
|
@@ -652,9 +1860,45 @@ export class DatetimeSecondControl extends DateControl
|
|
|
652
1860
|
};
|
|
653
1861
|
|
|
654
1862
|
DatetimeSecondControl.prototype.subtype = "datetimesecond";
|
|
1863
|
+
DatetimeSecondControl.prototype.fieldtype = DatetimeSecondField;
|
|
1864
|
+
|
|
655
1865
|
|
|
656
1866
|
export class LookupControl extends Control
|
|
657
1867
|
{
|
|
1868
|
+
get default()
|
|
1869
|
+
{
|
|
1870
|
+
let view_control = this._view_control();
|
|
1871
|
+
|
|
1872
|
+
if (view_control === null)
|
|
1873
|
+
return null;
|
|
1874
|
+
|
|
1875
|
+
return this.lookupdata.get(view_control) ?? null;
|
|
1876
|
+
}
|
|
1877
|
+
|
|
1878
|
+
get autoexpandable()
|
|
1879
|
+
{
|
|
1880
|
+
let view_control = this._view_control();
|
|
1881
|
+
if (view_control === null)
|
|
1882
|
+
return false;
|
|
1883
|
+
return view_control.autoexpandable;
|
|
1884
|
+
}
|
|
1885
|
+
|
|
1886
|
+
get nonekey()
|
|
1887
|
+
{
|
|
1888
|
+
let view_control = this._view_control();
|
|
1889
|
+
if (view_control === null)
|
|
1890
|
+
return null;
|
|
1891
|
+
return view_control.lookupnonekey;
|
|
1892
|
+
}
|
|
1893
|
+
|
|
1894
|
+
get nonelabel()
|
|
1895
|
+
{
|
|
1896
|
+
let view_control = this._view_control();
|
|
1897
|
+
if (view_control === null)
|
|
1898
|
+
return null;
|
|
1899
|
+
return view_control.lookupnonelabel;
|
|
1900
|
+
}
|
|
1901
|
+
|
|
658
1902
|
// ``search.value`` must be ``null`` or a ``LookupItem`` key
|
|
659
1903
|
search(value, search)
|
|
660
1904
|
{
|
|
@@ -671,27 +1915,38 @@ export class LookupControl extends Control
|
|
|
671
1915
|
};
|
|
672
1916
|
|
|
673
1917
|
LookupControl.prototype.type = "lookup";
|
|
674
|
-
LookupControl.prototype.
|
|
675
|
-
LookupControl.prototype.
|
|
1918
|
+
LookupControl.prototype.fieldtype = LookupField;
|
|
1919
|
+
LookupControl.prototype._ul4onattrs = [...Control.prototype._ul4onattrs, "lookupdata"];
|
|
1920
|
+
LookupControl.prototype._ul4attrs = new Set([...Control.prototype._ul4attrs, "lookupdata"]);
|
|
1921
|
+
|
|
676
1922
|
|
|
677
1923
|
export class LookupSelectControl extends LookupControl
|
|
678
1924
|
{
|
|
1925
|
+
static classdoc = "A LivingApps lookup field (type 'lookup/select')";
|
|
1926
|
+
|
|
679
1927
|
};
|
|
680
1928
|
|
|
681
1929
|
LookupSelectControl.prototype.subtype = "select";
|
|
682
1930
|
|
|
1931
|
+
|
|
683
1932
|
export class LookupRadioControl extends LookupControl
|
|
684
1933
|
{
|
|
1934
|
+
static classdoc = "A LivingApps lookup field (type 'lookup/radio')";
|
|
1935
|
+
|
|
685
1936
|
};
|
|
686
1937
|
|
|
687
1938
|
LookupRadioControl.prototype.subtype = "radio";
|
|
688
1939
|
|
|
1940
|
+
|
|
689
1941
|
export class LookupChoiceControl extends LookupControl
|
|
690
1942
|
{
|
|
1943
|
+
static classdoc = "A LivingApps lookup field (type 'lookup/choice')";
|
|
1944
|
+
|
|
691
1945
|
};
|
|
692
1946
|
|
|
693
1947
|
LookupChoiceControl.prototype.subtype = "choice";
|
|
694
1948
|
|
|
1949
|
+
|
|
695
1950
|
export class AppLookupControl extends Control
|
|
696
1951
|
{
|
|
697
1952
|
// ``search.value`` must be an object containing the search criteria for the referenced record
|
|
@@ -705,29 +1960,52 @@ export class AppLookupControl extends Control
|
|
|
705
1960
|
};
|
|
706
1961
|
|
|
707
1962
|
AppLookupControl.prototype.type = "applookup";
|
|
708
|
-
AppLookupControl.prototype.
|
|
709
|
-
AppLookupControl.prototype.
|
|
1963
|
+
AppLookupControl.prototype.fieldtype = AppLookupField;
|
|
1964
|
+
AppLookupControl.prototype._ul4onattrs = [...Control.prototype._ul4onattrs, "lookup_app", "lookup_controls", "local_master_control", "local_detail_controls", "remote_master_control"];
|
|
1965
|
+
AppLookupControl.prototype._ul4attrs = new Set([...Control.prototype._ul4attrs, "lookup_app", "lookup_controls", "local_master_control", "local_detail_controls", "remote_master_control"]);
|
|
1966
|
+
|
|
710
1967
|
|
|
711
1968
|
export class AppLookupSelectControl extends AppLookupControl
|
|
712
1969
|
{
|
|
1970
|
+
static classdoc = "A LivingApps applookup field (type 'applookup/select')";
|
|
1971
|
+
|
|
713
1972
|
};
|
|
714
1973
|
|
|
715
1974
|
AppLookupSelectControl.prototype.subtype = "select";
|
|
716
1975
|
|
|
1976
|
+
|
|
717
1977
|
export class AppLookupRadioControl extends AppLookupControl
|
|
718
1978
|
{
|
|
1979
|
+
static classdoc = "A LivingApps applookup field (type 'applookup/radio')";
|
|
1980
|
+
|
|
719
1981
|
};
|
|
720
1982
|
|
|
721
1983
|
AppLookupRadioControl.prototype.subtype = "radio";
|
|
722
1984
|
|
|
1985
|
+
|
|
723
1986
|
export class AppLookupChoiceControl extends AppLookupControl
|
|
724
1987
|
{
|
|
1988
|
+
static classdoc = "A LivingApps applookup field (type 'applookup/choice')";
|
|
1989
|
+
|
|
725
1990
|
};
|
|
726
1991
|
|
|
727
1992
|
AppLookupChoiceControl.prototype.subtype = "choice";
|
|
728
1993
|
|
|
1994
|
+
|
|
729
1995
|
export class MultipleLookupControl extends LookupControl
|
|
730
1996
|
{
|
|
1997
|
+
get default()
|
|
1998
|
+
{
|
|
1999
|
+
let view_control = this._view_control();
|
|
2000
|
+
|
|
2001
|
+
if (view_control === null)
|
|
2002
|
+
return null;
|
|
2003
|
+
|
|
2004
|
+
let defaultValue = this.lookupdata.get(view_control)
|
|
2005
|
+
|
|
2006
|
+
return (defaultValue !== undefined) ? [defaultValue] : [];
|
|
2007
|
+
}
|
|
2008
|
+
|
|
731
2009
|
// search.value must be ``null`` or a ``LookupItem`` key
|
|
732
2010
|
search(value, search)
|
|
733
2011
|
{
|
|
@@ -746,25 +2024,36 @@ export class MultipleLookupControl extends LookupControl
|
|
|
746
2024
|
};
|
|
747
2025
|
|
|
748
2026
|
MultipleLookupControl.prototype.subtype = "multiplelookup";
|
|
2027
|
+
MultipleLookupControl.prototype.fieldtype = MultipleLookupField;
|
|
2028
|
+
|
|
749
2029
|
|
|
750
2030
|
export class MultipleLookupSelectControl extends MultipleLookupControl
|
|
751
2031
|
{
|
|
2032
|
+
static classdoc = "A LivingApps multiplelookup field (type 'multiplelookup/select')";
|
|
2033
|
+
|
|
752
2034
|
};
|
|
753
2035
|
|
|
754
2036
|
MultipleLookupSelectControl.prototype.subtype = "select";
|
|
755
2037
|
|
|
2038
|
+
|
|
756
2039
|
export class MultipleLookupCheckboxControl extends MultipleLookupControl
|
|
757
2040
|
{
|
|
2041
|
+
static classdoc = "A LivingApps multiplelookup field (type 'multiplelookup/checkbox')";
|
|
2042
|
+
|
|
758
2043
|
};
|
|
759
2044
|
|
|
760
2045
|
MultipleLookupCheckboxControl.prototype.subtype = "checkbox";
|
|
761
2046
|
|
|
2047
|
+
|
|
762
2048
|
export class MultipleLookupChoiceControl extends MultipleLookupControl
|
|
763
2049
|
{
|
|
2050
|
+
static classdoc = "A LivingApps multiplelookup field (type 'multiplelookup/choice')";
|
|
2051
|
+
|
|
764
2052
|
};
|
|
765
2053
|
|
|
766
2054
|
MultipleLookupChoiceControl.prototype.subtype = "choice";
|
|
767
2055
|
|
|
2056
|
+
|
|
768
2057
|
export class MultipleAppLookupControl extends AppLookupControl
|
|
769
2058
|
{
|
|
770
2059
|
// ``search.value`` must be an object containing the search criteria for the referenced record
|
|
@@ -790,36 +2079,61 @@ export class MultipleAppLookupControl extends AppLookupControl
|
|
|
790
2079
|
};
|
|
791
2080
|
|
|
792
2081
|
MultipleAppLookupControl.prototype.type = "multipleapplookup";
|
|
2082
|
+
MultipleAppLookupControl.prototype.fieldtype = MultipleAppLookupField;
|
|
2083
|
+
|
|
793
2084
|
|
|
794
2085
|
export class MultipleAppLookupSelectControl extends MultipleAppLookupControl
|
|
795
2086
|
{
|
|
2087
|
+
static classdoc = "A LivingApps multiple applookup field (type 'multipleapplookup/select')";
|
|
2088
|
+
|
|
796
2089
|
};
|
|
797
2090
|
|
|
798
2091
|
MultipleAppLookupSelectControl.prototype.subtype = "select";
|
|
799
2092
|
|
|
2093
|
+
|
|
800
2094
|
export class MultipleAppLookupCheckboxControl extends MultipleAppLookupControl
|
|
801
2095
|
{
|
|
2096
|
+
static classdoc = "A LivingApps multiple applookup field (type 'multipleapplookup/checkbox')";
|
|
2097
|
+
|
|
802
2098
|
};
|
|
803
2099
|
|
|
804
2100
|
MultipleAppLookupCheckboxControl.prototype.subtype = "checkbox";
|
|
805
2101
|
|
|
2102
|
+
|
|
806
2103
|
export class MultipleAppLookupChoiceControl extends MultipleAppLookupControl
|
|
807
2104
|
{
|
|
2105
|
+
static classdoc = "A LivingApps multiple applookup field (type 'multipleapplookup/choice')";
|
|
808
2106
|
};
|
|
809
2107
|
|
|
810
2108
|
MultipleAppLookupChoiceControl.prototype.subtype = "choice";
|
|
811
2109
|
|
|
2110
|
+
|
|
812
2111
|
export class GeoControl extends Control
|
|
813
2112
|
{
|
|
2113
|
+
static classdoc = "A LivingApps geo field (type 'geo')";
|
|
814
2114
|
};
|
|
815
2115
|
|
|
816
2116
|
GeoControl.prototype.type = "geo";
|
|
2117
|
+
GeoControl.prototype.fieldtype = GeoField;
|
|
2118
|
+
|
|
817
2119
|
|
|
818
2120
|
export class FileControl extends Control
|
|
819
2121
|
{
|
|
2122
|
+
static classdoc = "A LivingApps upload field (type 'file')";
|
|
820
2123
|
};
|
|
821
2124
|
|
|
822
2125
|
FileControl.prototype.type = "file";
|
|
2126
|
+
FileControl.prototype.fieldtype = FileField;
|
|
2127
|
+
|
|
2128
|
+
|
|
2129
|
+
export class FileSignatureControl extends FileControl
|
|
2130
|
+
{
|
|
2131
|
+
static classdoc = "A LivingApps signature image field (type 'file/signature')";
|
|
2132
|
+
};
|
|
2133
|
+
|
|
2134
|
+
FileSignatureControl.prototype.subtype = "signature";
|
|
2135
|
+
FileSignatureControl.prototype.fieldtype = FileSignatureField;
|
|
2136
|
+
|
|
823
2137
|
|
|
824
2138
|
export class ButtonControl extends Control
|
|
825
2139
|
{
|
|
@@ -827,165 +2141,237 @@ export class ButtonControl extends Control
|
|
|
827
2141
|
|
|
828
2142
|
ButtonControl.prototype.type = "button";
|
|
829
2143
|
|
|
830
|
-
|
|
2144
|
+
|
|
2145
|
+
export class LookupItem extends Base
|
|
831
2146
|
{
|
|
832
|
-
|
|
2147
|
+
static classdoc = "An option in a lookup control/field";
|
|
2148
|
+
|
|
2149
|
+
get label()
|
|
833
2150
|
{
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
2151
|
+
if (this.control === null)
|
|
2152
|
+
return this._label;
|
|
2153
|
+
let view_lookupitem = this._view_lookupitem();
|
|
2154
|
+
if (view_lookupitem === null)
|
|
2155
|
+
return this._label;
|
|
2156
|
+
let label = view_lookupitem.label;
|
|
2157
|
+
if (label === null)
|
|
2158
|
+
return this._label;
|
|
2159
|
+
return label;
|
|
840
2160
|
}
|
|
841
2161
|
|
|
842
|
-
get
|
|
2162
|
+
get visible()
|
|
843
2163
|
{
|
|
844
|
-
|
|
2164
|
+
if (this.control === null)
|
|
2165
|
+
return true;
|
|
2166
|
+
let view_lookupitem = this._view_lookupitem();
|
|
2167
|
+
if (view_lookupitem === null)
|
|
2168
|
+
return true;
|
|
2169
|
+
return view_lookupitem.visible;
|
|
845
2170
|
}
|
|
846
2171
|
|
|
847
|
-
|
|
2172
|
+
_view_lookupitem()
|
|
848
2173
|
{
|
|
849
|
-
let
|
|
850
|
-
|
|
851
|
-
if (
|
|
2174
|
+
let identifier = this.control.identifier;
|
|
2175
|
+
let active_view = this.control.app.active_view;
|
|
2176
|
+
if (active_view !== null && active_view.controls !== null)
|
|
852
2177
|
{
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
2178
|
+
let view_control = active_view.controls.get(identifier);
|
|
2179
|
+
if (view_control !== undefined && view_control.lookupdata !== undefined && view_control.lookupdata !== null)
|
|
2180
|
+
{
|
|
2181
|
+
let view_lookupitem = view_control.lookupdata.get(this.key);
|
|
2182
|
+
if (view_lookupitem !== undefined)
|
|
2183
|
+
return view_lookupitem;
|
|
2184
|
+
}
|
|
856
2185
|
}
|
|
2186
|
+
return null;
|
|
857
2187
|
}
|
|
858
2188
|
|
|
859
|
-
|
|
2189
|
+
[ul4.symbols.repr]()
|
|
860
2190
|
{
|
|
861
|
-
|
|
2191
|
+
let repr = "<LookupItem key=" + ul4._repr(this.key) + " label=" + ul4._repr(this.label);
|
|
2192
|
+
if (!this.visible)
|
|
2193
|
+
repr += "visible=False"
|
|
2194
|
+
return repr + ">";
|
|
862
2195
|
}
|
|
2196
|
+
};
|
|
863
2197
|
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
return this._dirty;
|
|
867
|
-
}
|
|
2198
|
+
LookupItem.prototype._ul4onattrs = ["control", "key", "_label"];
|
|
2199
|
+
LookupItem.prototype._ul4attrs = new Set(["id", "control", "key", "label"]);
|
|
868
2200
|
|
|
869
|
-
has_errors()
|
|
870
|
-
{
|
|
871
|
-
return this.errors.length !== 0;
|
|
872
|
-
}
|
|
873
2201
|
|
|
874
|
-
|
|
2202
|
+
export class ViewLookupItem extends Base
|
|
2203
|
+
{
|
|
2204
|
+
static classdoc = "View specific information about a lookup item";
|
|
2205
|
+
|
|
2206
|
+
[ul4.symbols.repr]()
|
|
875
2207
|
{
|
|
876
|
-
|
|
2208
|
+
let repr = "<ViewLookupItem key=" + ul4._repr(this.key) + " label=" + ul4._repr(this.label);
|
|
2209
|
+
if (!this.visible)
|
|
2210
|
+
repr += " visible=False"
|
|
2211
|
+
return repr + ">";
|
|
877
2212
|
}
|
|
2213
|
+
};
|
|
2214
|
+
|
|
2215
|
+
ViewLookupItem.prototype._ul4onattrs = ["key", "label", "visible"];
|
|
2216
|
+
ViewLookupItem.prototype._ul4attrs = new Set(["key", "label", "visible"]);
|
|
878
2217
|
|
|
879
|
-
|
|
2218
|
+
|
|
2219
|
+
export class LayoutControl extends Base
|
|
2220
|
+
{
|
|
2221
|
+
static classdoc = "A decoration in an input form";
|
|
2222
|
+
|
|
2223
|
+
[ul4.symbols.repr]()
|
|
880
2224
|
{
|
|
881
|
-
|
|
882
|
-
s += ul4._repr(this.control.identifier)
|
|
883
|
-
if (this._dirty)
|
|
884
|
-
s += " is_dirty()=True";
|
|
885
|
-
if (this.errors.length !== 0)
|
|
886
|
-
s += " has_errors()=True";
|
|
887
|
-
s += ">"
|
|
888
|
-
return s;
|
|
2225
|
+
return "<" + this.constructor.name + " id=" + ul4._repr(this.id) + " identifier=" + ul4._repr(this.identifier) + ">";
|
|
889
2226
|
}
|
|
890
2227
|
};
|
|
891
2228
|
|
|
892
|
-
|
|
2229
|
+
LayoutControl.prototype._ul4onattrs = ["label", "identifier", "view", "top", "left", "width", "height"];
|
|
2230
|
+
LayoutControl.prototype._ul4attrs = new Set(["id", "label", "identifier", "view", "top", "left", "width", "height"]);
|
|
2231
|
+
|
|
2232
|
+
|
|
2233
|
+
export class HTMLLayoutControl extends LayoutControl
|
|
2234
|
+
{
|
|
2235
|
+
static classdoc = "An HTML decoration in an input form";
|
|
2236
|
+
};
|
|
2237
|
+
|
|
2238
|
+
HTMLLayoutControl.prototype._ul4onattrs = [...LayoutControl.prototype._ul4onattrs, "value"];
|
|
2239
|
+
HTMLLayoutControl.prototype._ul4attrs = new Set([LayoutControl.prototype._ul4attrs, "value"]);
|
|
2240
|
+
|
|
2241
|
+
|
|
2242
|
+
export class ImageLayoutControl extends LayoutControl
|
|
2243
|
+
{
|
|
2244
|
+
static classdoc = "An image decoration in an input form";
|
|
2245
|
+
};
|
|
2246
|
+
|
|
2247
|
+
ImageLayoutControl.prototype._ul4onattrs = [...LayoutControl.prototype._ul4onattrs, "original", "scaled"];
|
|
2248
|
+
ImageLayoutControl.prototype._ul4attrs = new Set([LayoutControl.prototype._ul4attrs, "original", "scaled"]);
|
|
2249
|
+
|
|
2250
|
+
|
|
2251
|
+
export class ViewControl extends Base
|
|
893
2252
|
{
|
|
894
|
-
|
|
2253
|
+
static classdoc = "Contains view specific information aboutn a control";
|
|
2254
|
+
|
|
2255
|
+
get mode()
|
|
895
2256
|
{
|
|
896
|
-
return
|
|
2257
|
+
return this._mode ? "display" : "edit";
|
|
897
2258
|
}
|
|
898
2259
|
};
|
|
899
2260
|
|
|
900
|
-
|
|
901
|
-
|
|
2261
|
+
ViewControl.prototype._ul4onattrs = ["view", "control", "top", "left", "width", "height", "liveupdate", "default", "tabindex", "minlength", "maxlength", "required", "placeholder", "_mode", "labelpos", "lookupnonekey", "lookupnonelabel", "label", "autoalign", "labelwidth", "lookupdata", "autoexpandable"];
|
|
2262
|
+
ViewControl.prototype._ul4attrs = new Set(["id", "view", "control", "top", "left", "width", "height", "liveupdate", "default", "tabindex", "minlength", "maxlength", "required", "placeholder", "mode", "labelpos", "lookupnonekey", "lookupnonelabel", "label", "autoalign", "labelwidth", "lookupdata", "autoexpandable"]);
|
|
2263
|
+
|
|
902
2264
|
|
|
903
2265
|
export class User extends Base
|
|
904
2266
|
{
|
|
905
|
-
|
|
2267
|
+
static classdoc = "A LivingApps user/account";
|
|
2268
|
+
|
|
2269
|
+
[ul4.symbols.repr]()
|
|
906
2270
|
{
|
|
907
2271
|
return "<User id=" + ul4._repr(this.id) + " firstname=" + ul4._repr(this.firstname) + " surname=" + ul4._repr(this.surname) + " email=" + ul4._repr(this.email) + ">";
|
|
908
2272
|
}
|
|
909
2273
|
};
|
|
910
2274
|
|
|
911
|
-
User.prototype._ul4onattrs = ["_id", "
|
|
912
|
-
User.prototype._ul4attrs =
|
|
2275
|
+
User.prototype._ul4onattrs = ["_id", "gender", "title", "firstname", "surname", "initials", "email", "streetname", "streetnumber", "zip", "city", "phone", "fax", "lang", "avatarsmall", "avatarlarge", "summary", "interests", "personalwebsite", "companywebsite", "company", "position", "department", "keyviews"];
|
|
2276
|
+
User.prototype._ul4attrs = new Set(["id", "_id", "gender", "title", "firstname", "surname", "initials", "email", "streetname", "streetnumber", "zip", "city", "phone", "fax", "lang", "avatarsmall", "avatarlarge", "summary", "interests", "personalwebsite", "companywebsite", "company", "position", "department", "keyviews"]);
|
|
2277
|
+
|
|
913
2278
|
|
|
914
2279
|
export class File extends Base
|
|
915
2280
|
{
|
|
916
|
-
|
|
2281
|
+
static classdoc = "An uploaded file";
|
|
2282
|
+
|
|
2283
|
+
[ul4.symbols.repr]()
|
|
917
2284
|
{
|
|
918
2285
|
return "<File id=" + ul4._repr(this.id) + " url=" + ul4._repr(this.url) + " filename=" + ul4._repr(this.filename) + ">";
|
|
919
2286
|
}
|
|
920
2287
|
};
|
|
921
2288
|
|
|
922
|
-
File.prototype._ul4onattrs = ["
|
|
923
|
-
File.prototype._ul4attrs =
|
|
2289
|
+
File.prototype._ul4onattrs = ["url", "filename", "mimetype", "width", "height", "internalid", "createdat", "size"];
|
|
2290
|
+
File.prototype._ul4attrs = new Set(["id", "url", "filename", "mimetype", "width", "height", "size", "createdat"]);
|
|
2291
|
+
|
|
924
2292
|
|
|
925
2293
|
export class Geo extends Base
|
|
926
2294
|
{
|
|
2295
|
+
static classdoc = "Geographical coordinates and location information";
|
|
2296
|
+
|
|
927
2297
|
constructor(lat, long, info)
|
|
928
2298
|
{
|
|
929
|
-
super();
|
|
2299
|
+
super(null);
|
|
930
2300
|
this.lat = lat;
|
|
931
2301
|
this.long = long;
|
|
932
2302
|
this.info = info;
|
|
933
2303
|
}
|
|
934
2304
|
|
|
935
|
-
|
|
2305
|
+
[ul4.symbols.repr]()
|
|
936
2306
|
{
|
|
937
2307
|
return "<Geo lat=" + ul4._repr(this.lat) + " long=" + ul4._repr(this.long) + " info=" + ul4._repr(this.info) + ">";
|
|
938
2308
|
}
|
|
939
2309
|
};
|
|
940
2310
|
|
|
941
2311
|
Geo.prototype._ul4onattrs = ["lat", "long", "info"];
|
|
942
|
-
Geo.prototype._ul4attrs =
|
|
2312
|
+
Geo.prototype._ul4attrs = new Set(["lat", "long", "info"]);
|
|
2313
|
+
|
|
943
2314
|
|
|
944
2315
|
export class Attachment extends Base
|
|
945
2316
|
{
|
|
946
|
-
|
|
2317
|
+
[ul4.symbols.repr]()
|
|
947
2318
|
{
|
|
948
|
-
return "<" + this.
|
|
2319
|
+
return "<" + this.constructor.name + " id=" + ul4._repr(this.id) + " label=" + ul4._repr(this.label) + ">";
|
|
949
2320
|
}
|
|
950
2321
|
};
|
|
951
2322
|
|
|
952
|
-
Attachment.prototype._ul4onattrs = ["
|
|
953
|
-
Attachment.prototype._ul4attrs =
|
|
2323
|
+
Attachment.prototype._ul4onattrs = ["record", "label", "active"];
|
|
2324
|
+
Attachment.prototype._ul4attrs = new Set(["id", "record", "label", "active"]);
|
|
2325
|
+
|
|
954
2326
|
|
|
955
2327
|
export class NoteAttachment extends Attachment
|
|
956
2328
|
{
|
|
2329
|
+
static classdoc = "A note attachment of a record";
|
|
2330
|
+
|
|
957
2331
|
};
|
|
958
2332
|
|
|
959
2333
|
NoteAttachment.prototype.type = "noteattachment";
|
|
960
|
-
NoteAttachment.prototype._ul4onattrs = Attachment.prototype._ul4onattrs
|
|
961
|
-
NoteAttachment.prototype._ul4attrs =
|
|
2334
|
+
NoteAttachment.prototype._ul4onattrs = [...Attachment.prototype._ul4onattrs, "value"];
|
|
2335
|
+
NoteAttachment.prototype._ul4attrs = new Set([...Attachment.prototype._ul4onattrs, "value"]);
|
|
2336
|
+
|
|
962
2337
|
|
|
963
2338
|
export class URLAttachment extends Attachment
|
|
964
2339
|
{
|
|
2340
|
+
static classdoc = "A URL attachment of a record";
|
|
2341
|
+
|
|
965
2342
|
};
|
|
966
2343
|
|
|
967
2344
|
URLAttachment.prototype.type = "urlattachment";
|
|
968
|
-
URLAttachment.prototype._ul4onattrs = Attachment.prototype._ul4onattrs
|
|
969
|
-
URLAttachment.prototype._ul4attrs =
|
|
2345
|
+
URLAttachment.prototype._ul4onattrs = [...Attachment.prototype._ul4onattrs, "value"];
|
|
2346
|
+
URLAttachment.prototype._ul4attrs = new Set([...Attachment.prototype._ul4onattrs, "value"]);
|
|
2347
|
+
|
|
970
2348
|
|
|
971
2349
|
export class FileAttachment extends Attachment
|
|
972
2350
|
{
|
|
2351
|
+
static classdoc = "A file attachment of a record";
|
|
2352
|
+
|
|
973
2353
|
};
|
|
974
2354
|
|
|
975
2355
|
FileAttachment.prototype.type = "fileattachment";
|
|
976
|
-
FileAttachment.prototype._ul4onattrs = Attachment.prototype._ul4onattrs
|
|
977
|
-
FileAttachment.prototype._ul4attrs =
|
|
2356
|
+
FileAttachment.prototype._ul4onattrs = [...Attachment.prototype._ul4onattrs, "value"];
|
|
2357
|
+
FileAttachment.prototype._ul4attrs = new Set([...Attachment.prototype._ul4onattrs, "value"]);
|
|
2358
|
+
|
|
978
2359
|
|
|
979
2360
|
export class ImageAttachment extends Attachment
|
|
980
2361
|
{
|
|
2362
|
+
static classdoc = "An image attachment of a record";
|
|
2363
|
+
|
|
981
2364
|
};
|
|
982
2365
|
|
|
983
2366
|
ImageAttachment.prototype.type = "imageattachment";
|
|
984
|
-
ImageAttachment.prototype._ul4onattrs = Attachment.prototype._ul4onattrs
|
|
985
|
-
ImageAttachment.prototype._ul4attrs =
|
|
2367
|
+
ImageAttachment.prototype._ul4onattrs = [...Attachment.prototype._ul4onattrs, "original", "thumb", "small", "medium","large"];
|
|
2368
|
+
ImageAttachment.prototype._ul4attrs = new Set([...Attachment.prototype._ul4onattrs, "original", "thumb", "small", "medium", "large"]);
|
|
2369
|
+
|
|
986
2370
|
|
|
987
2371
|
export class JSONAttachment extends Attachment
|
|
988
2372
|
{
|
|
2373
|
+
static classdoc = "A JSON attachment of a record";
|
|
2374
|
+
|
|
989
2375
|
_dumpUL4ONAttr(name)
|
|
990
2376
|
{
|
|
991
2377
|
if (name === "value")
|
|
@@ -1004,23 +2390,29 @@ export class JSONAttachment extends Attachment
|
|
|
1004
2390
|
};
|
|
1005
2391
|
|
|
1006
2392
|
JSONAttachment.prototype.type = "jsonattachment";
|
|
1007
|
-
JSONAttachment.prototype._ul4onattrs = Attachment.prototype._ul4onattrs
|
|
1008
|
-
JSONAttachment.prototype._ul4attrs =
|
|
2393
|
+
JSONAttachment.prototype._ul4onattrs = [...Attachment.prototype._ul4onattrs, "value"];
|
|
2394
|
+
JSONAttachment.prototype._ul4attrs = new Set([...Attachment.prototype._ul4onattrs, "value"]);
|
|
2395
|
+
|
|
1009
2396
|
|
|
1010
2397
|
export class Installation extends Base
|
|
1011
2398
|
{
|
|
1012
|
-
|
|
2399
|
+
static classdoc = "The installation that created an app";
|
|
2400
|
+
|
|
2401
|
+
[ul4.symbols.repr]()
|
|
1013
2402
|
{
|
|
1014
2403
|
return "<Installation id=" + ul4._repr(this.id) + " name=" + ul4._repr(this.name) + ">";
|
|
1015
2404
|
}
|
|
1016
2405
|
};
|
|
1017
2406
|
|
|
1018
|
-
Installation.prototype._ul4onattrs = ["
|
|
1019
|
-
Installation.prototype._ul4attrs =
|
|
2407
|
+
Installation.prototype._ul4onattrs = ["name"];
|
|
2408
|
+
Installation.prototype._ul4attrs = new Set(["id", "name"]);
|
|
2409
|
+
|
|
1020
2410
|
|
|
1021
2411
|
export class Category extends Base
|
|
1022
2412
|
{
|
|
1023
|
-
|
|
2413
|
+
static classdoc = "A navigation category";
|
|
2414
|
+
|
|
2415
|
+
[ul4.symbols.repr]()
|
|
1024
2416
|
{
|
|
1025
2417
|
let v = [];
|
|
1026
2418
|
let category = this;
|
|
@@ -1033,30 +2425,37 @@ export class Category extends Base
|
|
|
1033
2425
|
}
|
|
1034
2426
|
};
|
|
1035
2427
|
|
|
1036
|
-
Category.prototype._ul4onattrs = ["
|
|
1037
|
-
Category.prototype._ul4attrs =
|
|
2428
|
+
Category.prototype._ul4onattrs = ["identifier", "name", "order", "parent", "children", "apps"];
|
|
2429
|
+
Category.prototype._ul4attrs = new Set(["id", "identifier", "name", "order", "parent", "children", "apps"]);
|
|
2430
|
+
|
|
1038
2431
|
|
|
1039
2432
|
export class KeyView extends Base
|
|
1040
2433
|
{
|
|
1041
|
-
|
|
2434
|
+
static classdoc = "Object granting access to a view template";
|
|
2435
|
+
|
|
2436
|
+
[ul4.symbols.repr]()
|
|
1042
2437
|
{
|
|
1043
2438
|
return "<KeyView id=" + ul4._repr(this.id) + " identifier=" + ul4._repr(this.identifier) + ">";
|
|
1044
2439
|
}
|
|
1045
2440
|
};
|
|
1046
2441
|
|
|
1047
|
-
KeyView.prototype._ul4onattrs = ["
|
|
1048
|
-
KeyView.prototype._ul4attrs =
|
|
2442
|
+
KeyView.prototype._ul4onattrs = ["identifier", "name", "key", "user"];
|
|
2443
|
+
KeyView.prototype._ul4attrs = new Set(["id", "identifier", "name", "key", "user"]);
|
|
2444
|
+
|
|
1049
2445
|
|
|
1050
2446
|
export class AppParameter extends Base
|
|
1051
2447
|
{
|
|
1052
|
-
|
|
2448
|
+
static classdoc = "A parameter of a LivingApps application";
|
|
2449
|
+
|
|
2450
|
+
[ul4.symbols.repr]()
|
|
1053
2451
|
{
|
|
1054
2452
|
return "<AppParameter id=" + ul4._repr(this.id) + " identifier=" + ul4._repr(this.identifier) + ">";
|
|
1055
2453
|
}
|
|
1056
2454
|
};
|
|
1057
2455
|
|
|
1058
|
-
AppParameter.prototype._ul4onattrs = ["
|
|
1059
|
-
AppParameter.prototype._ul4attrs =
|
|
2456
|
+
AppParameter.prototype._ul4onattrs = ["app", "identifier", "description", "value"];
|
|
2457
|
+
AppParameter.prototype._ul4attrs = new Set(["id", "app", "identifier", "description", "value"]);
|
|
2458
|
+
|
|
1060
2459
|
|
|
1061
2460
|
let classes = [
|
|
1062
2461
|
Globals,
|
|
@@ -1072,7 +2471,6 @@ let classes = [
|
|
|
1072
2471
|
EmailControl,
|
|
1073
2472
|
URLControl,
|
|
1074
2473
|
TelControl,
|
|
1075
|
-
PasswordControl,
|
|
1076
2474
|
TextAreaControl,
|
|
1077
2475
|
DateControl,
|
|
1078
2476
|
DatetimeMinuteControl,
|
|
@@ -1095,9 +2493,37 @@ let classes = [
|
|
|
1095
2493
|
MultipleAppLookupChoiceControl,
|
|
1096
2494
|
GeoControl,
|
|
1097
2495
|
FileControl,
|
|
2496
|
+
FileSignatureControl,
|
|
1098
2497
|
ButtonControl,
|
|
1099
2498
|
Field,
|
|
2499
|
+
BoolField,
|
|
2500
|
+
StringField,
|
|
2501
|
+
EmailField,
|
|
2502
|
+
URLField,
|
|
2503
|
+
TelField,
|
|
2504
|
+
TextAreaField,
|
|
2505
|
+
HTMLField,
|
|
2506
|
+
IntField,
|
|
2507
|
+
NumberField,
|
|
2508
|
+
GeoField,
|
|
2509
|
+
FileField,
|
|
2510
|
+
FileSignatureField,
|
|
2511
|
+
DateFieldBase,
|
|
2512
|
+
DateField,
|
|
2513
|
+
DatetimeMinuteField,
|
|
2514
|
+
DatetimeSecondField,
|
|
2515
|
+
LookupFieldBase,
|
|
2516
|
+
LookupField,
|
|
2517
|
+
MultipleLookupField,
|
|
2518
|
+
AppLookupFieldBase,
|
|
2519
|
+
AppLookupField,
|
|
2520
|
+
MultipleAppLookupField,
|
|
1100
2521
|
LookupItem,
|
|
2522
|
+
ViewLookupItem,
|
|
2523
|
+
LayoutControl,
|
|
2524
|
+
HTMLLayoutControl,
|
|
2525
|
+
ImageLayoutControl,
|
|
2526
|
+
ViewControl,
|
|
1101
2527
|
User,
|
|
1102
2528
|
File,
|
|
1103
2529
|
Geo,
|