Multi field
info.magnolia.ui.field.MultiFieldDefinition renders a complex field composed of one or more field sets (for example, three sets of two text fields). Magnolia provides four preconfigured multi field definitions:
-
info.magnolia.ui.field.JcrMultiValueFieldDefinition: allows you to enter multiple values of a single type to be stored as an array in a single JCR property (
jcrMultiValueField
). -
info.magnolia.ui.field.JcrMultiLinkFieldDefinition: allows you to select multiple values of a single type in a chooser dialog to be stored as an array in a single JCR property (
jcrMultiLinkField
). -
info.magnolia.ui.field.JcrMultiFieldDefinition: allows you to create multiple JCR fields (
jcrMultiField
). -
info.magnolia.rest.ui.field.JsonMultiFieldDefinition: allows you to create multiple JSON fields to be used in an app with its own JSON data source (
jsonMultiField
).
These multi field definitions are part of the Magnolia 6 UI framework. Their fully qualified class names are:
In the Magnolia 5 UI framework, the field functionally parallel to the JCR fields is Multivalue field. There is no corresponding 5 UI implementation for the JSON multi field. |
Example definitions
assignedSegments:
$type: jcrMultiValueField
label: Multi-value field
field:
$type: comboBoxField
label: Path
datasource:
$type: jcrDatasource
workspace: website
jcrMultiLinkField:
$type: jcrMultiLinkField
label: Multi-link field
field:
$type: linkField
label: Page
datasource:
$type: jcrDatasource
workspace: website
damMultiLinkField:
$type: jcrMultiLinkField
label: Multi-link field
chooserId: dam-app-core:multiChooser
field:
$type: damLinkField
label: Asset
multi:
i18n: true
$type: jcrMultiField
label: Address list
field:
$type: compositeField
label: Address
properties:
street:
$type: textField
label: Street
city:
i18n: true
$type: textField
label: City
zip:
$type: textField
label: ZIP code
stationboard:
label: Station Board
$type: jsonMultiField
itemProvider:
$type: jsonMultiFieldProvider
field:
$type: jsonCompositeField
idPropertyName: name
properties:
name:
label: Name
$type: textField
readOnly: true
to:
label: To
$type: textField
readOnly: true
operator:
label: Operator
$type: textField
readOnly: true
JSON data source is read-only.
Therefore, it only supports read-only fields in, typically, the content detail subapp of a read-only REST app.
The example above is used in the Stations app contained in the field-examples-module. See also Composite field. |
You can preview this example using the |
Field properties
Common multi field properties
Property | Description | ||
---|---|---|---|
|
required Node containing an editor property definition item (typically, a field). All field types are supported. See List of fields for more information. |
||
|
optional (used only in Unique identifier for the multi-chooser
dialog. If none is specified, the
JCR
|
||
|
optional, default is
Implementation class that defines how the child entries of a multi field should be resolved.
|
||
|
optional, default is
Implementation class that sorts nodes and ensures that the suffixes in index names correspond to the order in which they are stored. When |
||
|
optional, default is When |
||
|
optional, default is translated Button label for adding an item. The value is i18n-able. |
||
|
optional, default is translated Button label for removing an item. The value is i18n-able. |
||
|
optional, default is Specifies the minimum number of items to be added. |
||
|
optional, default is Specifies the maximum number of items to be added.
|
||
|
optional, default is translated Error message shown when the number of items is less than
|
||
|
optional, default is Makes the field required. An asterisk is displayed next to the field label. |
||
|
optional, default is translated Error message shown when |
Common complex field properties
Property | Description | ||
---|---|---|---|
|
required Name of the field definition item. Derived from the configured node name. Use alphanumeric characters without spaces. |
||
|
required (unless Type of the field definition item. The value must be a fully qualified
class name and a subtype of |
||
|
You can use this as a shortcut for Example class annotation
See Field types for possible values. |
||
|
required, default is
Node with a See Item providers for more information.
|
||
|
optional Help text displayed when the user clicks the help icon. The value can be literal or a key of a message bundle. |
||
|
optional, default is Enables i18n
authoring support, which allows editors to write foreign-language or
regionally targeted content. A two-letter language identifier (
|
||
|
optional Field label displayed to editors. The value can be literal or a key of a message bundle. If you do not provide the property, Magnolia will fall back to a generated i18n key. If you do not want to have any label, set the property to an empty
string such as |
||
|
optional Additional style information for an editor property definition item applied to the element when the form is rendered. The value can be a CSS class or a list of CSS classes separated by white spaces. The style name will be rendered as an HTML class name, which can be used in a CSS definition.
The class name is added to the field by calling the Vaadin method
|
Form validation of multiple values
To validate that jcrMultiValueField
has only unique values, you can create UniqueValuesMultiFormView
as an implementation class that extends MultiFormView
.
public class UniqueValuesMultiFormView<T> extends MultiFormView<T> {
@Inject
public UniqueValuesMultiFormView(MultiFormDefinition<T> definition, LocaleContext localeContext, Datasource<T> datasource) {
super(definition, localeContext, datasource);
}
@Override
public List<BinderValidationStatus<?>> validate() {
final List<BinderValidationStatus<?>> validate = super.validate();
if (validate.stream().allMatch(BinderValidationStatus::isOk)) {
List<String> valuesStringList = validate.stream()
.map(v -> v.getBinder().getFields().findFirst().get().getValue()) // could be any data type other than string
.map(String::valueOf)
.collect(Collectors.toList());
if (new HashSet<>(valuesStringList).size() != valuesStringList.size()) {
final Binder.Binding<?, ?> binding = validate.stream()
.flatMap(binderValidationStatus -> binderValidationStatus.getFieldValidationStatuses().stream())
.map(BindingValidationStatus::getBinding)
.findFirst()
.orElse(null);
final BindingValidationStatus<?> validationStatus = new BindingValidationStatus<>(Result.error("All values has to be unique"), binding);
binding.getValidationStatusHandler().statusChange(validationStatus);
validate.add(new BinderValidationStatus<>(null, Collections.singletonList(validationStatus), new ArrayList<>()));
}
}
return validate;
}
}
uniqueValues:
$type: jcrMultiValueField
implementationClass: info.magnolia.ui.editor.UniqueValuesMultiFormView
field:
$type: textField