UNPKG

@talend/react-forms

Version:

React forms library based on json schema form.

174 lines (172 loc) 5.39 kB
import { Component } from 'react'; import PropTypes from 'prop-types'; import { getArrayElementSchema } from '../../utils/array'; import defaultTemplates from '../../utils/templates'; import { shiftArrayErrorsKeys } from '../../utils/validation'; import Widget from '../../Widget'; import { get, head } from "lodash"; import { jsx as _jsx } from "react/jsx-runtime"; function getRange(previousIndex, nextIndex) { if (previousIndex < nextIndex) { return { minIndex: previousIndex, maxIndex: nextIndex + 1 }; } return { minIndex: nextIndex, maxIndex: previousIndex + 1 }; } export default class ArrayWidget extends Component { constructor(props) { super(props); this.onAdd = this.onAdd.bind(this); this.onRemove = this.onRemove.bind(this); this.onReorder = this.onReorder.bind(this); this.renderItem = this.renderItem.bind(this); } onAdd(event) { var _schema$default; const arrayMergedSchema = this.props.schema; const { items, schema } = arrayMergedSchema; const hasOneItem = items.length === 1; const itemsEnum = get(schema, 'items.enum'); const isSingleSelectItem = hasOneItem && head(items).type === 'select' && head(itemsEnum); const schemaDefaultConfig = (_schema$default = schema.default) === null || _schema$default === void 0 ? void 0 : _schema$default[0]; const defaultConfig = schema.items.type === 'object' ? {} : ''; const defaultValue = isSingleSelectItem ? head(itemsEnum) : schemaDefaultConfig || defaultConfig; let currentValue = this.props.value; if (this.isCloseable()) { currentValue = currentValue.map(item => ({ ...item, isClosed: true })); } const value = currentValue.concat(defaultValue); const payload = { schema: arrayMergedSchema, value }; this.props.onChange(event, payload); this.props.onFinish(event, payload); } onRemove(event, indexToRemove) { const schema = this.props.schema; const value = this.props.value.slice(0); value.splice(indexToRemove, 1); // shift up the items errors after the one we remove function widgetChangeErrors(errors) { return shiftArrayErrorsKeys(errors, { arrayKey: schema.key, minIndex: indexToRemove, shouldRemoveIndex: index => index === indexToRemove, getNextIndex: index => index - 1 }); } const payload = { schema, value }; this.props.onChange(event, payload); this.props.onFinish(event, payload, { widgetChangeErrors }); } onReorder(event, { previousIndex, nextIndex }) { const schema = this.props.schema; const value = this.props.value.slice(0); const [item] = value.splice(previousIndex, 1); value.splice(nextIndex, 0, item); function widgetChangeErrors(errors) { // determine the range [min, max[ of items to shift, with the pace const { minIndex, maxIndex } = getRange(previousIndex, nextIndex); const switchPace = Math.sign(previousIndex - nextIndex); // shift the items errors between the previous and next position // set the item-we-move errors indexes return shiftArrayErrorsKeys(errors, { arrayKey: schema.key, minIndex, maxIndex, getNextIndex(index) { return index === previousIndex ? nextIndex : index + switchPace; } }); } const payload = { schema, value }; this.props.onChange(event, payload); this.props.onFinish(event, payload, { widgetChangeErrors }); } getArrayTemplate() { const baseTemplateId = 'array'; const templateId = `${baseTemplateId}_${this.props.displayMode}`; const ArrayTemplate = this.props.templates[templateId] || defaultTemplates[templateId]; if (!ArrayTemplate) { return this.props.templates[baseTemplateId] || defaultTemplates[baseTemplateId]; } return ArrayTemplate; } isCloseable() { const widgetId = this.props.schema.itemWidget; const itemWidget = this.props.widgets[widgetId]; if (!itemWidget) { return false; } return itemWidget.isCloseable === true; } renderItem(index, extraProps) { return /*#__PURE__*/_jsx(Widget, { ...this.props, ...extraProps, index: index, disabled: this.props.schema.disabled, id: this.props.id && `${this.props.id}-${index}`, schema: getArrayElementSchema(this.props.schema, index), value: this.props.value[index] }); } render() { const ArrayTemplate = this.getArrayTemplate(); return /*#__PURE__*/_jsx(ArrayTemplate, { ...this.props, canReorder: this.props.schema.reorder !== false, onAdd: this.onAdd, onReorder: this.onReorder, onRemove: this.onRemove, renderItem: this.renderItem, isCloseable: this.isCloseable() }); } } ArrayWidget.defaultProps = { value: [], templates: {}, widgets: {} }; if (process.env.NODE_ENV !== 'production') { ArrayWidget.propTypes = { displayMode: PropTypes.string, id: PropTypes.string, onChange: PropTypes.func.isRequired, onFinish: PropTypes.func.isRequired, schema: PropTypes.object.isRequired, templates: PropTypes.object, value: PropTypes.array, widgets: PropTypes.object }; } //# sourceMappingURL=Array.component.js.map