@formio/js 5.1.0-dev.5936.81a1533 → 5.1.0-dev.5939.f5aa9d6
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/dist/formio.builder.css +1 -0
- package/dist/formio.builder.min.css +1 -1
- package/dist/formio.form.css +1 -0
- package/dist/formio.form.js +20 -42
- package/dist/formio.form.min.css +1 -1
- package/dist/formio.form.min.js +1 -1
- package/dist/formio.full.css +1 -0
- package/dist/formio.full.js +22 -44
- package/dist/formio.full.min.css +1 -1
- package/dist/formio.full.min.js +1 -1
- package/dist/formio.js +7 -7
- package/dist/formio.min.js +1 -1
- package/dist/formio.utils.js +8 -8
- package/dist/formio.utils.min.js +1 -1
- package/lib/cjs/Element.d.ts +2 -1
- package/lib/cjs/Element.js +6 -4
- package/lib/cjs/PDFBuilder.d.ts +1 -0
- package/lib/cjs/PDFBuilder.js +8 -8
- package/lib/cjs/Webform.d.ts +2 -2
- package/lib/cjs/Webform.js +4 -3
- package/lib/cjs/WebformBuilder.d.ts +1 -1
- package/lib/cjs/WebformBuilder.js +27 -8
- package/lib/cjs/components/_classes/component/Component.js +5 -0
- package/lib/cjs/components/_classes/input/Input.d.ts +1 -1
- package/lib/cjs/components/_classes/input/Input.js +2 -2
- package/lib/cjs/components/_classes/nested/NestedComponent.js +4 -2
- package/lib/cjs/components/address/Address.js +1 -1
- package/lib/cjs/components/editgrid/EditGrid.d.ts +0 -1
- package/lib/cjs/components/editgrid/EditGrid.js +0 -8
- package/lib/cjs/components/radio/Radio.d.ts +9 -4
- package/lib/cjs/components/radio/Radio.js +40 -76
- package/lib/cjs/components/select/Select.d.ts +1 -0
- package/lib/cjs/components/select/Select.js +19 -3
- package/lib/cjs/components/selectboxes/SelectBoxes.d.ts +6 -0
- package/lib/cjs/components/textfield/TextField.js +6 -1
- package/lib/cjs/formio.form.js +2 -2
- package/lib/cjs/translations/en.d.ts +1 -232
- package/lib/cjs/translations/en.js +4 -2
- package/lib/cjs/utils/formUtils.d.ts +2 -2
- package/lib/cjs/utils/index.d.ts +2 -2
- package/lib/cjs/utils/utils.js +10 -3
- package/lib/mjs/Element.d.ts +2 -1
- package/lib/mjs/Element.js +6 -4
- package/lib/mjs/PDFBuilder.d.ts +1 -0
- package/lib/mjs/PDFBuilder.js +8 -8
- package/lib/mjs/Webform.d.ts +2 -2
- package/lib/mjs/Webform.js +4 -3
- package/lib/mjs/WebformBuilder.d.ts +1 -1
- package/lib/mjs/WebformBuilder.js +26 -8
- package/lib/mjs/components/_classes/component/Component.js +5 -0
- package/lib/mjs/components/_classes/input/Input.d.ts +1 -1
- package/lib/mjs/components/_classes/input/Input.js +2 -2
- package/lib/mjs/components/_classes/nested/NestedComponent.js +4 -2
- package/lib/mjs/components/address/Address.js +1 -1
- package/lib/mjs/components/editgrid/EditGrid.d.ts +0 -1
- package/lib/mjs/components/editgrid/EditGrid.js +0 -8
- package/lib/mjs/components/radio/Radio.d.ts +9 -4
- package/lib/mjs/components/radio/Radio.js +40 -75
- package/lib/mjs/components/select/Select.d.ts +1 -0
- package/lib/mjs/components/select/Select.js +19 -3
- package/lib/mjs/components/selectboxes/SelectBoxes.d.ts +6 -0
- package/lib/mjs/components/textfield/TextField.js +6 -1
- package/lib/mjs/formio.form.js +1 -1
- package/lib/mjs/translations/en.d.ts +1 -232
- package/lib/mjs/translations/en.js +8 -47
- package/lib/mjs/utils/formUtils.d.ts +2 -2
- package/lib/mjs/utils/index.d.ts +2 -2
- package/lib/mjs/utils/utils.js +10 -2
- package/package.json +2 -2
- package/lib/cjs/i18n.d.ts +0 -13
- package/lib/cjs/i18n.js +0 -19
- package/lib/cjs/utils/i18n.d.ts +0 -19
- package/lib/cjs/utils/i18n.js +0 -120
- package/lib/mjs/i18n.d.ts +0 -13
- package/lib/mjs/i18n.js +0 -14
- package/lib/mjs/utils/i18n.d.ts +0 -19
- package/lib/mjs/utils/i18n.js +0 -112
package/lib/cjs/Element.d.ts
CHANGED
@@ -170,10 +170,11 @@ export default class Element {
|
|
170
170
|
/**
|
171
171
|
* Translate a text using the i18n system.
|
172
172
|
* @param {string|Array<string>} text - The i18n identifier.
|
173
|
+
* @param {any} data - contextual data object containing data, component, row, etc.
|
173
174
|
* @param {...any} args - The arguments to pass to the i18n translation.
|
174
175
|
* @returns {string} - The translated text.
|
175
176
|
*/
|
176
|
-
t(text: string | Array<string>, ...args: any[]): string;
|
177
|
+
t(text: string | Array<string>, data: any, ...args: any[]): string;
|
177
178
|
/**
|
178
179
|
* Alias to create a text node.
|
179
180
|
* @param {string} text - The text to create.
|
package/lib/cjs/Element.js
CHANGED
@@ -8,8 +8,9 @@ const moment_1 = __importDefault(require("moment"));
|
|
8
8
|
const vanilla_text_mask_1 = __importDefault(require("@formio/vanilla-text-mask"));
|
9
9
|
const EventEmitter_1 = __importDefault(require("./EventEmitter"));
|
10
10
|
const Formio_1 = require("./Formio");
|
11
|
-
const i18n_1 = require("./utils/i18n");
|
12
11
|
const utils_1 = __importDefault(require("./utils"));
|
12
|
+
const core_1 = require("@formio/core");
|
13
|
+
const en_1 = __importDefault(require("./translations/en"));
|
13
14
|
/**
|
14
15
|
* The root component for all elements within the Form.io renderer.
|
15
16
|
*/
|
@@ -44,7 +45,7 @@ class Element {
|
|
44
45
|
if ((_a = this.options) === null || _a === void 0 ? void 0 : _a.language) {
|
45
46
|
this.options.i18n.language = this.options.language;
|
46
47
|
}
|
47
|
-
this.options.i18next = this.i18next = this.options.i18next ||
|
48
|
+
this.options.i18next = this.i18next = this.options.i18next || core_1.I18n.init(Object.assign({ en: en_1.default }, this.options.i18n));
|
48
49
|
/**
|
49
50
|
* An instance of the EventEmitter class to handle the emitting and registration of events.
|
50
51
|
* @type {EventEmitter}
|
@@ -392,11 +393,12 @@ class Element {
|
|
392
393
|
/**
|
393
394
|
* Translate a text using the i18n system.
|
394
395
|
* @param {string|Array<string>} text - The i18n identifier.
|
396
|
+
* @param {any} data - contextual data object containing data, component, row, etc.
|
395
397
|
* @param {...any} args - The arguments to pass to the i18n translation.
|
396
398
|
* @returns {string} - The translated text.
|
397
399
|
*/
|
398
|
-
t(text, ...args) {
|
399
|
-
return this.i18next ? this.i18next.t(text, ...args) : text;
|
400
|
+
t(text, data, ...args) {
|
401
|
+
return this.i18next ? this.i18next.t(text, data, ...args) : text;
|
400
402
|
}
|
401
403
|
/**
|
402
404
|
* Alias to create a text node.
|
package/lib/cjs/PDFBuilder.d.ts
CHANGED
package/lib/cjs/PDFBuilder.js
CHANGED
@@ -451,21 +451,21 @@ class PDFBuilder extends WebformBuilder_1.default {
|
|
451
451
|
e.target.style.cursor = 'default';
|
452
452
|
}
|
453
453
|
highlightInvalidComponents() {
|
454
|
-
const
|
454
|
+
const repeatablePathsComps = this.findComponentsWithRepeatablePaths();
|
455
455
|
// update elements which path was duplicated if any pathes have been changed
|
456
|
-
if (!lodash_1.default.isEqual(this.
|
457
|
-
(0, utils_1.eachComponent)(this.webform.getComponents(), (comp
|
458
|
-
if (this.
|
456
|
+
if (!lodash_1.default.isEqual(this.repeatablePathsComps, repeatablePathsComps)) {
|
457
|
+
(0, utils_1.eachComponent)(this.webform.getComponents(), (comp) => {
|
458
|
+
if (this.repeatablePathsComps.includes(comp.component)) {
|
459
459
|
this.webform.postMessage({ name: 'updateElement', data: comp.component });
|
460
460
|
}
|
461
461
|
});
|
462
|
-
this.
|
462
|
+
this.repeatablePathsComps = repeatablePathsComps;
|
463
463
|
}
|
464
|
-
if (!
|
464
|
+
if (!repeatablePathsComps.length) {
|
465
465
|
return;
|
466
466
|
}
|
467
|
-
(0, utils_1.eachComponent)(this.webform.getComponents(), (comp
|
468
|
-
if (this.
|
467
|
+
(0, utils_1.eachComponent)(this.webform.getComponents(), (comp) => {
|
468
|
+
if (this.repeatablePathsComps.includes(comp)) {
|
469
469
|
this.webform.postMessage({
|
470
470
|
name: 'showBuilderErrors',
|
471
471
|
data: {
|
package/lib/cjs/Webform.d.ts
CHANGED
@@ -45,7 +45,7 @@
|
|
45
45
|
* @property {number} [saveDraftThrottle] - The throttle for the save draft feature.
|
46
46
|
* @property {boolean} [readOnly] - Set this form to readOnly.
|
47
47
|
* @property {boolean} [noAlerts] - Disable the alerts dialog.
|
48
|
-
* @property {{[key: string]: string}} [
|
48
|
+
* @property {{[key: string]: string}} [enTranslation] - The translation file for this rendering.
|
49
49
|
* @property {string} [template] - Custom logic for creation of elements.
|
50
50
|
* @property {boolean} [noDefaults] - Exclude default values from the settings.
|
51
51
|
* @property {any} [fileService] - The file service for this form.
|
@@ -586,7 +586,7 @@ export type FormOptions = {
|
|
586
586
|
/**
|
587
587
|
* - The translation file for this rendering.
|
588
588
|
*/
|
589
|
-
|
589
|
+
enTranslation?: {
|
590
590
|
[key: string]: string;
|
591
591
|
} | undefined;
|
592
592
|
/**
|
package/lib/cjs/Webform.js
CHANGED
@@ -6,7 +6,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
const lodash_1 = __importDefault(require("lodash"));
|
7
7
|
const compare_versions_1 = require("compare-versions");
|
8
8
|
const EventEmitter_1 = __importDefault(require("./EventEmitter"));
|
9
|
-
const
|
9
|
+
const en_1 = __importDefault(require("./translations/en"));
|
10
10
|
const Formio_1 = require("./Formio");
|
11
11
|
const Components_1 = __importDefault(require("./components/Components"));
|
12
12
|
const NestedDataComponent_1 = __importDefault(require("./components/_classes/nesteddata/NestedDataComponent"));
|
@@ -99,7 +99,7 @@ function getOptions(options) {
|
|
99
99
|
* @property {number} [saveDraftThrottle] - The throttle for the save draft feature.
|
100
100
|
* @property {boolean} [readOnly] - Set this form to readOnly.
|
101
101
|
* @property {boolean} [noAlerts] - Disable the alerts dialog.
|
102
|
-
* @property {{[key: string]: string}} [
|
102
|
+
* @property {{[key: string]: string}} [enTranslation] - The translation file for this rendering.
|
103
103
|
* @property {string} [template] - Custom logic for creation of elements.
|
104
104
|
* @property {boolean} [noDefaults] - Exclude default values from the settings.
|
105
105
|
* @property {any} [fileService] - The file service for this form.
|
@@ -369,7 +369,7 @@ class Webform extends NestedDataComponent_1.default {
|
|
369
369
|
*/
|
370
370
|
addLanguage(code, lang, active = false) {
|
371
371
|
if (this.i18next) {
|
372
|
-
var translations = lodash_1.default.assign((0, utils_1.fastCloneDeep)(
|
372
|
+
var translations = lodash_1.default.assign((0, utils_1.fastCloneDeep)(en_1.default), lang);
|
373
373
|
this.i18next.addResourceBundle(code, 'translation', translations, true, true);
|
374
374
|
if (active) {
|
375
375
|
this.language = code;
|
@@ -1320,6 +1320,7 @@ class Webform extends NestedDataComponent_1.default {
|
|
1320
1320
|
userAgent: navigator.userAgent,
|
1321
1321
|
pathName: window.location.pathname,
|
1322
1322
|
onLine: navigator.onLine,
|
1323
|
+
language: this.language,
|
1323
1324
|
});
|
1324
1325
|
}
|
1325
1326
|
submitForm(options = {}, local = false) {
|
@@ -78,7 +78,7 @@ export default class WebformBuilder extends Component {
|
|
78
78
|
replaceDoubleQuotes(data: any, fieldsToRemoveDoubleQuotes?: any[]): any;
|
79
79
|
updateComponent(component: any, changed: any): void;
|
80
80
|
originalDefaultValue: any;
|
81
|
-
|
81
|
+
findComponentsWithRepeatablePaths(): any[];
|
82
82
|
highlightInvalidComponents(): void;
|
83
83
|
/**
|
84
84
|
* Called when a new component is saved.
|
@@ -1125,31 +1125,50 @@ class WebformBuilder extends Component_1.default {
|
|
1125
1125
|
// Called when we update a component.
|
1126
1126
|
this.emit('updateComponent', component);
|
1127
1127
|
}
|
1128
|
-
|
1129
|
-
const repeatablePaths =
|
1128
|
+
findComponentsWithRepeatablePaths() {
|
1129
|
+
const repeatablePaths = {};
|
1130
1130
|
const keys = new Map();
|
1131
1131
|
(0, utils_1.eachComponent)(this.form.components, (comp, path, components, parent, paths) => {
|
1132
|
+
var _a, _b;
|
1133
|
+
const isRadioCheckbox = comp.type === 'checkbox' && comp.inputType === 'radio';
|
1132
1134
|
const isLayout = (0, utils_1.componentInfo)(comp).layout;
|
1133
1135
|
if (!isLayout) {
|
1134
1136
|
if (keys.has(paths.dataPath)) {
|
1135
|
-
repeatablePaths
|
1137
|
+
const onlyRadioCheckboxes = ((_a = repeatablePaths[paths.dataPath]) === null || _a === void 0 ? void 0 : _a.onlyRadioCheckboxes) === false ? false : isRadioCheckbox;
|
1138
|
+
repeatablePaths[paths.dataPath] = {
|
1139
|
+
comps: [...(((_b = repeatablePaths[paths.dataPath]) === null || _b === void 0 ? void 0 : _b.comps) || []), keys.get(paths.dataPath), comp],
|
1140
|
+
onlyRadioCheckboxes,
|
1141
|
+
};
|
1136
1142
|
}
|
1137
1143
|
else {
|
1138
|
-
keys.set(paths.dataPath,
|
1144
|
+
keys.set(paths.dataPath, comp);
|
1139
1145
|
}
|
1140
1146
|
}
|
1141
1147
|
}, true);
|
1142
|
-
|
1148
|
+
const componentsWithRepeatablePaths = [];
|
1149
|
+
Object.keys(repeatablePaths).forEach((path) => {
|
1150
|
+
const { comps, onlyRadioCheckboxes } = repeatablePaths[path];
|
1151
|
+
if (!onlyRadioCheckboxes) {
|
1152
|
+
componentsWithRepeatablePaths.push(...comps);
|
1153
|
+
}
|
1154
|
+
});
|
1155
|
+
return componentsWithRepeatablePaths;
|
1143
1156
|
}
|
1144
1157
|
highlightInvalidComponents() {
|
1145
|
-
const
|
1158
|
+
const repeatablePathsComps = this.findComponentsWithRepeatablePaths();
|
1146
1159
|
let hasInvalidComponents = false;
|
1160
|
+
// Matches anything expect letters and '_' at the beginning of the key and anything except of letters, numbers,
|
1161
|
+
// '-', '.' and '_' in the rest of the key
|
1162
|
+
const badCharacters = /^[^A-Za-z_]+|[^A-Za-z0-9\-._]+/g;
|
1147
1163
|
this.webform.everyComponent((comp) => {
|
1148
|
-
|
1149
|
-
if (repeatablePaths.includes(path)) {
|
1164
|
+
if (repeatablePathsComps.includes(comp.component)) {
|
1150
1165
|
comp.setCustomValidity(this.t('apiKey', { key: comp.key }));
|
1151
1166
|
hasInvalidComponents = true;
|
1152
1167
|
}
|
1168
|
+
else if (comp.key.replace(badCharacters, '') === '') {
|
1169
|
+
comp.setCustomValidity(this.t('apiKeyNotValid', { key: comp.key }));
|
1170
|
+
hasInvalidComponents = true;
|
1171
|
+
}
|
1153
1172
|
else {
|
1154
1173
|
comp.setCustomValidity();
|
1155
1174
|
}
|
@@ -2710,6 +2710,11 @@ class Component extends Element_1.default {
|
|
2710
2710
|
this.setValueAt(i, isArray && !this.isSingleInputValue() ? value[i] : value, flags);
|
2711
2711
|
}
|
2712
2712
|
}
|
2713
|
+
// Also reset value of the modal component, otherwise it will keep the old value locally and the preview
|
2714
|
+
// element won't refresh
|
2715
|
+
if (this.componentModal && flags && flags.resetValue) {
|
2716
|
+
this.componentModal.setValue(value);
|
2717
|
+
}
|
2713
2718
|
return changed;
|
2714
2719
|
}
|
2715
2720
|
/**
|
@@ -25,7 +25,7 @@ export default class Input extends Multivalue {
|
|
25
25
|
get suffix(): any;
|
26
26
|
renderElement(value: any, index: any): any;
|
27
27
|
setCounter(type: any, element: any, count: any, max: any): void;
|
28
|
-
updateValueAt(value: any, flags: any, index
|
28
|
+
updateValueAt(value: any, flags: any, index?: number): void;
|
29
29
|
getValueAt(index: any): any;
|
30
30
|
updateValue(value: any, flags: any, index: any): boolean;
|
31
31
|
parseValue(value: any): any;
|
@@ -118,7 +118,7 @@ class Input extends Multivalue_1.default {
|
|
118
118
|
}
|
119
119
|
const info = this.inputInfo;
|
120
120
|
info.attr = info.attr || {};
|
121
|
-
info.attr.value = this.getValueAsString(this.formatValue(this.parseValue(value)))
|
121
|
+
info.attr.value = this.getValueAsString(this.formatValue(this.parseValue(this.isMultipleMasksField ? value.value : value)))
|
122
122
|
.replace(/"/g, '"');
|
123
123
|
const valueMask = this.component.inputMask;
|
124
124
|
const displayMask = this.component.displayMask;
|
@@ -163,7 +163,7 @@ class Input extends Multivalue_1.default {
|
|
163
163
|
}));
|
164
164
|
}
|
165
165
|
}
|
166
|
-
updateValueAt(value, flags, index) {
|
166
|
+
updateValueAt(value, flags, index = 0) {
|
167
167
|
flags = flags || {};
|
168
168
|
if (lodash_1.default.get(this.component, 'showWordCount', false)) {
|
169
169
|
if (this.refs.wordcount && this.refs.wordcount[index]) {
|
@@ -664,7 +664,7 @@ class NestedComponent extends Field_1.default {
|
|
664
664
|
validationProcessor({ scope, data, row, instance, paths }, flags) {
|
665
665
|
var _a;
|
666
666
|
const { dirty } = flags;
|
667
|
-
if (this.root.hasSubWizards && this.page !== this.root.page) {
|
667
|
+
if (this.root && this.root.hasSubWizards && this.page !== this.root.page) {
|
668
668
|
instance = ((_a = this.componentsMap) === null || _a === void 0 ? void 0 : _a.hasOwnProperty(paths.dataPath))
|
669
669
|
? this.componentsMap[paths.dataPath]
|
670
670
|
: this.getComponent(paths.dataPath);
|
@@ -800,8 +800,10 @@ class NestedComponent extends Field_1.default {
|
|
800
800
|
return this.data;
|
801
801
|
}
|
802
802
|
resetValue() {
|
803
|
-
|
803
|
+
// Reset values of child components first, then reset the parent one, otherwise it will restore the default
|
804
|
+
// value of parent component and clear it one by one while resetting child components
|
804
805
|
this.getComponents().forEach((comp) => comp.resetValue());
|
806
|
+
super.resetValue();
|
805
807
|
this.setPristine(true);
|
806
808
|
}
|
807
809
|
get dataReady() {
|
@@ -249,7 +249,7 @@ class AddressComponent extends Container_1.default {
|
|
249
249
|
if (this.manualMode) {
|
250
250
|
this.restoreComponentsContext();
|
251
251
|
}
|
252
|
-
if (changed || !lodash_1.default.isEmpty(value) && flags.fromSubmission) {
|
252
|
+
if (changed || !lodash_1.default.isEmpty(value) && flags.fromSubmission || flags.resetValue) {
|
253
253
|
this.redraw();
|
254
254
|
}
|
255
255
|
return changed;
|
@@ -101,7 +101,6 @@ export default class EditGridComponent extends NestedArrayComponent {
|
|
101
101
|
changeState(changed: any, flags: any): void;
|
102
102
|
openWhenEmpty(): void;
|
103
103
|
restoreRowContext(editRow: any, flags?: {}): void;
|
104
|
-
emptyRows(): void;
|
105
104
|
hasChanged: (newValue: any, oldValue: any) => boolean;
|
106
105
|
}
|
107
106
|
import NestedArrayComponent from '../_classes/nestedarray/NestedArrayComponent';
|
@@ -1200,14 +1200,6 @@ class EditGridComponent extends NestedArrayComponent_1.default {
|
|
1200
1200
|
this.setNestedValue(component, editRow.data, flags);
|
1201
1201
|
});
|
1202
1202
|
}
|
1203
|
-
emptyRows() {
|
1204
|
-
this.editRows.forEach((editRow, index) => this.destroyComponents(false, index));
|
1205
|
-
this.editRows = [];
|
1206
|
-
}
|
1207
|
-
resetValue() {
|
1208
|
-
super.resetValue();
|
1209
|
-
this.emptyRows();
|
1210
|
-
}
|
1211
1203
|
}
|
1212
1204
|
exports.default = EditGridComponent;
|
1213
1205
|
EditGridComponent.prototype.hasChanged = Component_1.default.prototype.hasChanged;
|
@@ -16,6 +16,7 @@ export default class RadioComponent extends ListComponent {
|
|
16
16
|
static savedValueTypes(schema: any): any[];
|
17
17
|
constructor(component: any, options: any, data: any);
|
18
18
|
previousValue: any;
|
19
|
+
uncheckValue(flags?: {}): void;
|
19
20
|
get inputInfo(): any;
|
20
21
|
get emptyValue(): string;
|
21
22
|
get isRadio(): boolean;
|
@@ -27,8 +28,8 @@ export default class RadioComponent extends ListComponent {
|
|
27
28
|
itemsLoadedResolve: ((value: any) => void) | undefined;
|
28
29
|
optionsLoaded: boolean | undefined;
|
29
30
|
loadedOptions: any[] | undefined;
|
30
|
-
valuesMap: Map<any, any> | undefined;
|
31
31
|
beforeSubmit(): Promise<any>;
|
32
|
+
convertValues(values: any): any;
|
32
33
|
render(): string;
|
33
34
|
attach(element: any): Promise<void>;
|
34
35
|
detach(element: any): void;
|
@@ -36,14 +37,18 @@ export default class RadioComponent extends ListComponent {
|
|
36
37
|
validateValueAvailability(setting: any, value: any): boolean;
|
37
38
|
getValueAsString(value: any, options?: {}): any;
|
38
39
|
setValueAt(index: any, value: any): void;
|
39
|
-
prepareValue(item: any, options?: {}): any;
|
40
|
-
getValueByInput(input: any): any;
|
41
40
|
loadItems(url: any, search: any, headers: any, options: any, method: any, body: any): void;
|
42
41
|
loadItemsFromMetadata(): void;
|
43
42
|
setItems(items: any): void;
|
44
43
|
setSelectedClasses(): void;
|
45
|
-
setMetadata(value: any): void;
|
46
44
|
updateValue(value: any, flags: any): boolean;
|
47
45
|
currentValue: any;
|
46
|
+
/**
|
47
|
+
* Normalize values coming into updateValue. For example, depending on the configuration, string value `"true"` will be normalized to boolean `true`.
|
48
|
+
* @param {*} value - The value to normalize
|
49
|
+
* @returns {*} - Returns the normalized value
|
50
|
+
*/
|
51
|
+
convertByDataType(value: any): any;
|
52
|
+
normalizeValue(value: any): any;
|
48
53
|
}
|
49
54
|
import ListComponent from '../_classes/list/ListComponent';
|
@@ -6,8 +6,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
const lodash_1 = __importDefault(require("lodash"));
|
7
7
|
const ListComponent_1 = __importDefault(require("../_classes/list/ListComponent"));
|
8
8
|
const Formio_1 = require("../../Formio");
|
9
|
-
const utils_1 = require("../../utils
|
10
|
-
const uuid_1 = require("uuid");
|
9
|
+
const utils_1 = require("../../utils");
|
11
10
|
class RadioComponent extends ListComponent_1.default {
|
12
11
|
static schema(...extend) {
|
13
12
|
return ListComponent_1.default.schema({
|
@@ -80,13 +79,15 @@ class RadioComponent extends ListComponent_1.default {
|
|
80
79
|
}
|
81
80
|
return defaultValue;
|
82
81
|
}
|
83
|
-
|
82
|
+
uncheckValue(flags = {}) {
|
84
83
|
this.unset();
|
85
84
|
this.setValue(this.emptyValue, {
|
86
85
|
noUpdateEvent: true,
|
87
86
|
noValidate: true,
|
88
87
|
resetValue: true
|
89
88
|
});
|
89
|
+
this.triggerChange(flags);
|
90
|
+
this.setSelectedClasses();
|
90
91
|
}
|
91
92
|
get inputInfo() {
|
92
93
|
var _a;
|
@@ -143,7 +144,6 @@ class RadioComponent extends ListComponent_1.default {
|
|
143
144
|
});
|
144
145
|
this.optionsLoaded = !this.component.dataSrc || this.component.dataSrc === 'values';
|
145
146
|
this.loadedOptions = [];
|
146
|
-
this.valuesMap = new Map();
|
147
147
|
if (!this.visible) {
|
148
148
|
this.itemsLoadedResolve();
|
149
149
|
}
|
@@ -155,6 +155,12 @@ class RadioComponent extends ListComponent_1.default {
|
|
155
155
|
this.dataReady.then(() => res(true));
|
156
156
|
});
|
157
157
|
}
|
158
|
+
convertValues(values) {
|
159
|
+
if (this.options.renderMode === 'html' && this.type === 'radio') {
|
160
|
+
return values.map(x => (Object.assign(Object.assign({}, x), { value: this.convertByDataType(x.value) })));
|
161
|
+
}
|
162
|
+
return values;
|
163
|
+
}
|
158
164
|
render() {
|
159
165
|
if (!this.optionsLoaded) {
|
160
166
|
return super.render(this.renderTemplate('loader'));
|
@@ -162,7 +168,7 @@ class RadioComponent extends ListComponent_1.default {
|
|
162
168
|
return super.render(this.renderTemplate('radio', {
|
163
169
|
input: this.inputInfo,
|
164
170
|
inline: this.component.inline,
|
165
|
-
values: this.component.dataSrc === 'values' ? this.component.values : this.loadedOptions,
|
171
|
+
values: this.component.dataSrc === 'values' ? this.convertValues(this.component.values) : this.loadedOptions,
|
166
172
|
value: this.dataValue,
|
167
173
|
row: this.row,
|
168
174
|
}));
|
@@ -183,12 +189,9 @@ class RadioComponent extends ListComponent_1.default {
|
|
183
189
|
if (!lodash_1.default.isString(this.dataValue)) {
|
184
190
|
dataValue = lodash_1.default.toString(this.dataValue);
|
185
191
|
}
|
186
|
-
if (this.isSelectURL) {
|
187
|
-
const
|
188
|
-
|
189
|
-
? this.valuesMap.get(valueKey)
|
190
|
-
: valueKey;
|
191
|
-
input.checked = lodash_1.default.isEqual(this.normalizeValue(optionValue), this.dataValue);
|
192
|
+
if (this.isSelectURL && lodash_1.default.isObject(this.loadedOptions[index].value)) {
|
193
|
+
const optionValue = this.component.dataType === 'string' ? JSON.stringify(this.loadedOptions[index].value) : this.loadedOptions[index].value;
|
194
|
+
input.checked = lodash_1.default.isEqual(optionValue, this.dataValue);
|
192
195
|
}
|
193
196
|
else {
|
194
197
|
input.checked = (dataValue === input.value && (input.value || this.component.dataSrc !== 'url'));
|
@@ -225,14 +228,9 @@ class RadioComponent extends ListComponent_1.default {
|
|
225
228
|
let value = this.component.inputType === 'checkbox' ? '' : this.dataValue;
|
226
229
|
this.refs.input.forEach((input, index) => {
|
227
230
|
if (input.checked) {
|
228
|
-
|
229
|
-
value
|
230
|
-
|
231
|
-
}
|
232
|
-
const optionValue = this.loadedOptions[index].value;
|
233
|
-
value = this.valuesMap.has(optionValue)
|
234
|
-
? this.valuesMap.get(optionValue)
|
235
|
-
: optionValue;
|
231
|
+
value = (this.isSelectURL && lodash_1.default.isObject(this.loadedOptions[index].value)) ?
|
232
|
+
this.loadedOptions[index].value :
|
233
|
+
input.value;
|
236
234
|
}
|
237
235
|
});
|
238
236
|
return value;
|
@@ -276,8 +274,8 @@ class RadioComponent extends ListComponent_1.default {
|
|
276
274
|
}
|
277
275
|
setValueAt(index, value) {
|
278
276
|
if (this.refs.input && this.refs.input[index] && value !== null && value !== undefined) {
|
279
|
-
const inputValue = this.
|
280
|
-
this.refs.input[index].checked =
|
277
|
+
const inputValue = this.refs.input[index].value;
|
278
|
+
this.refs.input[index].checked = (inputValue === value.toString());
|
281
279
|
}
|
282
280
|
}
|
283
281
|
get shouldLoad() {
|
@@ -287,23 +285,6 @@ class RadioComponent extends ListComponent_1.default {
|
|
287
285
|
}
|
288
286
|
return super.shouldLoad;
|
289
287
|
}
|
290
|
-
prepareValue(item, options = {}) {
|
291
|
-
const value = this.component.valueProperty && !options.skipValueProperty
|
292
|
-
? lodash_1.default.get(item, this.component.valueProperty)
|
293
|
-
: item;
|
294
|
-
if (this.component.type === 'radio' && typeof value !== 'string') {
|
295
|
-
const uuid = (0, uuid_1.v4)();
|
296
|
-
this.valuesMap.set(uuid, value);
|
297
|
-
return uuid;
|
298
|
-
}
|
299
|
-
return value;
|
300
|
-
}
|
301
|
-
getValueByInput(input) {
|
302
|
-
const inputValue = input.value;
|
303
|
-
return this.valuesMap.has(inputValue)
|
304
|
-
? this.valuesMap.get(inputValue)
|
305
|
-
: inputValue;
|
306
|
-
}
|
307
288
|
loadItems(url, search, headers, options, method, body) {
|
308
289
|
if (this.optionsLoaded) {
|
309
290
|
this.itemsLoadedResolve();
|
@@ -354,7 +335,7 @@ class RadioComponent extends ListComponent_1.default {
|
|
354
335
|
label: this.itemTemplate(item)
|
355
336
|
};
|
356
337
|
if (lodash_1.default.isEqual(item, this.selectData || lodash_1.default.pick(this.dataValue, lodash_1.default.keys(item)))) {
|
357
|
-
this.loadedOptions[i].value = this.
|
338
|
+
this.loadedOptions[i].value = this.dataValue;
|
358
339
|
}
|
359
340
|
});
|
360
341
|
this.optionsLoaded = true;
|
@@ -364,15 +345,12 @@ class RadioComponent extends ListComponent_1.default {
|
|
364
345
|
const listData = [];
|
365
346
|
items === null || items === void 0 ? void 0 : items.forEach((item, i) => {
|
366
347
|
const valueAtProperty = lodash_1.default.get(item, this.component.valueProperty);
|
367
|
-
|
368
|
-
|
369
|
-
? this.itemTemplate(item, valueAtProperty, i)
|
370
|
-
|
371
|
-
this.
|
372
|
-
|
373
|
-
if (this.valuesMap.has(value)) {
|
374
|
-
this.templateData[value] = this.templateData[i];
|
375
|
-
}
|
348
|
+
this.loadedOptions[i] = {
|
349
|
+
value: this.component.valueProperty ? valueAtProperty : item,
|
350
|
+
label: this.component.valueProperty ? this.itemTemplate(item, valueAtProperty) : this.itemTemplate(item, item, i)
|
351
|
+
};
|
352
|
+
listData.push(this.templateData[this.component.valueProperty ? valueAtProperty : i]);
|
353
|
+
const value = this.loadedOptions[i].value;
|
376
354
|
if (!this.isRadio && (lodash_1.default.isObject(value) || lodash_1.default.isBoolean(value) || lodash_1.default.isUndefined(value))) {
|
377
355
|
this.loadedOptions[i].invalid = true;
|
378
356
|
}
|
@@ -395,11 +373,7 @@ class RadioComponent extends ListComponent_1.default {
|
|
395
373
|
const value = this.dataValue;
|
396
374
|
this.refs.wrapper.forEach((wrapper, index) => {
|
397
375
|
const input = this.refs.input[index];
|
398
|
-
const checked = (value === undefined || value === null)
|
399
|
-
? false
|
400
|
-
: (input.type === 'checkbox')
|
401
|
-
? value[input.value] || input.checked
|
402
|
-
: lodash_1.default.isEqual(this.normalizeValue(this.getValueByInput(input)), value);
|
376
|
+
const checked = (value === undefined || value === null) ? false : (input.type === 'checkbox') ? value[input.value] || input.checked : (input.value.toString() === value.toString());
|
403
377
|
if (checked) {
|
404
378
|
//add class to container when selected
|
405
379
|
this.addClass(wrapper, this.optionSelectedClass);
|
@@ -413,26 +387,10 @@ class RadioComponent extends ListComponent_1.default {
|
|
413
387
|
});
|
414
388
|
}
|
415
389
|
}
|
416
|
-
setMetadata(value) {
|
417
|
-
var _a;
|
418
|
-
let key = value;
|
419
|
-
if (typeof value !== 'string') {
|
420
|
-
const checkedInput = Array.prototype.find.call((_a = this.refs.input) !== null && _a !== void 0 ? _a : [], (input => input.type === 'radio' && input.getAttribute('checked')));
|
421
|
-
key = (checkedInput === null || checkedInput === void 0 ? void 0 : checkedInput.value) || key;
|
422
|
-
}
|
423
|
-
if (this.isSelectURL && this.templateData && this.templateData[key]) {
|
424
|
-
const submission = this.root.submission;
|
425
|
-
if (!submission.metadata.selectData) {
|
426
|
-
submission.metadata.selectData = {};
|
427
|
-
}
|
428
|
-
lodash_1.default.set(submission.metadata.selectData, this.path, this.templateData[key]);
|
429
|
-
}
|
430
|
-
}
|
431
390
|
updateValue(value, flags) {
|
432
391
|
const changed = super.updateValue(value, flags);
|
433
392
|
if (changed) {
|
434
393
|
this.setSelectedClasses();
|
435
|
-
this.setMetadata(this.dataValue);
|
436
394
|
}
|
437
395
|
if (!flags || !flags.modified || !this.isRadio) {
|
438
396
|
if (changed) {
|
@@ -444,9 +402,7 @@ class RadioComponent extends ListComponent_1.default {
|
|
444
402
|
this.currentValue = this.dataValue;
|
445
403
|
const shouldResetValue = flags && flags.modified && !flags.noUpdateEvent && this.previousValue === this.currentValue;
|
446
404
|
if (shouldResetValue) {
|
447
|
-
this.
|
448
|
-
this.triggerChange(flags);
|
449
|
-
this.setSelectedClasses();
|
405
|
+
this.uncheckValue(flags);
|
450
406
|
}
|
451
407
|
this.previousValue = this.dataValue;
|
452
408
|
return changed;
|
@@ -456,7 +412,7 @@ class RadioComponent extends ListComponent_1.default {
|
|
456
412
|
* @param {*} value - The value to normalize
|
457
413
|
* @returns {*} - Returns the normalized value
|
458
414
|
*/
|
459
|
-
|
415
|
+
convertByDataType(value) {
|
460
416
|
const dataType = this.component.dataType || 'auto';
|
461
417
|
if (value === this.emptyValue) {
|
462
418
|
return value;
|
@@ -488,10 +444,18 @@ class RadioComponent extends ListComponent_1.default {
|
|
488
444
|
value = !(!value || value.toString() === 'false');
|
489
445
|
break;
|
490
446
|
}
|
491
|
-
return
|
447
|
+
return value;
|
492
448
|
}
|
493
|
-
|
494
|
-
|
449
|
+
normalizeValue(value) {
|
450
|
+
const valueConverted = this.convertByDataType(value);
|
451
|
+
if (this.isSelectURL && this.templateData && this.templateData[valueConverted]) {
|
452
|
+
const submission = this.root.submission;
|
453
|
+
if (!submission.metadata.selectData) {
|
454
|
+
submission.metadata.selectData = {};
|
455
|
+
}
|
456
|
+
lodash_1.default.set(submission.metadata.selectData, this.path, this.templateData[valueConverted]);
|
457
|
+
}
|
458
|
+
return super.normalizeValue(valueConverted);
|
495
459
|
}
|
496
460
|
}
|
497
461
|
exports.default = RadioComponent;
|
@@ -89,6 +89,7 @@ export default class SelectComponent extends ListComponent {
|
|
89
89
|
disableInfiniteScroll(): void;
|
90
90
|
set serverCount(value: any);
|
91
91
|
get serverCount(): any;
|
92
|
+
shouldResetChoicesItems(items: any): boolean;
|
92
93
|
setItems(items: any, fromSearch: any): void;
|
93
94
|
selectItems: any;
|
94
95
|
set downloadedResources(value: any);
|
@@ -355,6 +355,18 @@ class SelectComponent extends ListComponent_1.default {
|
|
355
355
|
this.downloadedResources.serverCount = this.downloadedResources.length;
|
356
356
|
this.serverCount = this.downloadedResources.length;
|
357
357
|
}
|
358
|
+
shouldResetChoicesItems(items) {
|
359
|
+
if (this.choices._store.choices.length !== items.length) {
|
360
|
+
return true;
|
361
|
+
}
|
362
|
+
for (let item of items) {
|
363
|
+
const choicesItem = this.choices._store.choices.find((i) => i.label === item.label);
|
364
|
+
if (!choicesItem) {
|
365
|
+
return true;
|
366
|
+
}
|
367
|
+
}
|
368
|
+
return false;
|
369
|
+
}
|
358
370
|
/* eslint-disable max-statements */
|
359
371
|
setItems(items, fromSearch) {
|
360
372
|
var _a, _b;
|
@@ -441,7 +453,7 @@ class SelectComponent extends ListComponent_1.default {
|
|
441
453
|
this.addOption(itemValueAndLabel.value, itemValueAndLabel.label, {}, lodash_1.default.get(item, this.component.idPath, String(index)));
|
442
454
|
});
|
443
455
|
if (this.choices) {
|
444
|
-
this.choices.setChoices(this.selectOptions, 'value', 'label', true);
|
456
|
+
this.choices.setChoices(this.selectOptions, 'value', 'label', true, true, !fromSearch && this.shouldResetChoicesItems(this.selectOptions));
|
445
457
|
}
|
446
458
|
else if (this.loading) {
|
447
459
|
// Re-attach select input.
|
@@ -903,8 +915,9 @@ class SelectComponent extends ListComponent_1.default {
|
|
903
915
|
});
|
904
916
|
}
|
905
917
|
// Add value options.
|
918
|
+
const value = this.undoValueTyping(this.dataValue);
|
906
919
|
this.addValueOptions();
|
907
|
-
this.setChoicesValue(
|
920
|
+
this.setChoicesValue(value);
|
908
921
|
if (this.isSelectResource && this.refs.addResource) {
|
909
922
|
this.addEventListener(this.refs.addResource, 'click', (event) => {
|
910
923
|
event.preventDefault();
|
@@ -1219,7 +1232,7 @@ class SelectComponent extends ListComponent_1.default {
|
|
1219
1232
|
}
|
1220
1233
|
lodash_1.default.set(submission.metadata.selectData, this.path, templateData);
|
1221
1234
|
}
|
1222
|
-
if (flags.resetValue && ((_b = this.root) === null || _b === void 0 ? void 0 : _b.submission) && !this.options.readOnly) {
|
1235
|
+
if (flags.resetValue && !flags.fromSubmission && ((_b = this.root) === null || _b === void 0 ? void 0 : _b.submission) && !this.options.readOnly) {
|
1223
1236
|
const submission = this.root.submission;
|
1224
1237
|
if (!submission.metadata) {
|
1225
1238
|
submission.metadata = {};
|
@@ -1283,6 +1296,9 @@ class SelectComponent extends ListComponent_1.default {
|
|
1283
1296
|
this.lazyLoadInit = true;
|
1284
1297
|
const searchProperty = this.component.searchField || this.component.valueProperty;
|
1285
1298
|
this.triggerUpdate(lodash_1.default.get(value.data || value, searchProperty, value), true);
|
1299
|
+
this.itemsLoaded.then(() => {
|
1300
|
+
this.setChoicesValue(value, hasPreviousValue, flags);
|
1301
|
+
});
|
1286
1302
|
return changed;
|
1287
1303
|
}
|
1288
1304
|
// Add the value options.
|