UNPKG

@arudovwen/react-form-builder

Version:
367 lines (362 loc) 11.6 kB
"use strict"; var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault"); Object.defineProperty(exports, "__esModule", { value: true }); exports.default = void 0; var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty")); var _react = _interopRequireDefault(require("react")); var _immutabilityHelper = _interopRequireDefault(require("immutability-helper")); var _store = _interopRequireDefault(require("./stores/store")); var _formDynamicEdit = _interopRequireDefault(require("./form-dynamic-edit")); var _sortableFormElements = _interopRequireDefault(require("./sortable-form-elements")); var _componentDragLayer = _interopRequireDefault(require("./form-elements/component-drag-layer")); /** * <Preview /> */ const { PlaceHolder } = _sortableFormElements.default; class Preview extends _react.default.Component { constructor(props) { super(props); (0, _defineProperty2.default)(this, "state", { data: [], answer_data: {} }); (0, _defineProperty2.default)(this, "editModeOff", e => { if (this.editForm.current && !this.editForm.current.contains(e.target)) { this.manualEditModeOff(); } }); (0, _defineProperty2.default)(this, "manualEditModeOff", () => { const { editElement } = this.props; if (editElement && editElement.dirty) { editElement.dirty = false; this.updateElement(editElement); } this.props.manualEditModeOff(); }); (0, _defineProperty2.default)(this, "duplicateElement", elementData => { const elementId = elementData?.id; const { data } = this.state; const element = this.getDataById(elementId); if (!element) return; // Deep clone the element and assign a new id const newElement = { ...JSON.parse(JSON.stringify(element)), id: Date.now() + Math.random() }; // Optionally, update other fields if needed (e.g., field_name) newElement.field_name = `${element.field_name}_copy`; // Insert the duplicated element after the original const index = data.findIndex(x => x.id === elementId); const newData = [...data]; newData.splice(index + 1, 0, newElement); this.setState({ data: newData }); _store.default.dispatch('updateOrder', newData); }); const { onLoad, onPost } = props; _store.default.setExternalHandler(onLoad, onPost); this.editForm = /*#__PURE__*/_react.default.createRef(); this.state = { data: props.data || [], answer_data: {} }; this.seq = 0; this._onUpdate = this._onChange.bind(this); this.getDataById = this.getDataById.bind(this); this.moveCard = this.moveCard.bind(this); this.insertCard = this.insertCard.bind(this); this.setAsChild = this.setAsChild.bind(this); this.removeChild = this.removeChild.bind(this); this._onDestroy = this._onDestroy.bind(this); this.duplicateElement = this.duplicateElement?.bind(this); } componentDidMount() { const { data, url, saveUrl, saveAlways } = this.props; _store.default.subscribe(state => this._onUpdate(state.data)); _store.default.dispatch('load', { loadUrl: url, saveUrl, data: data || [], saveAlways }); document.addEventListener('mousedown', this.editModeOff); } componentWillUnmount() { document.removeEventListener('mousedown', this.editModeOff); } _setValue(text) { return text.replace(/[^A-Z0-9]+/ig, '_').toLowerCase(); } updateElement(element) { const { data } = this.state; let found = false; for (let i = 0, len = data.length; i < len; i++) { if (element.id === data[i].id) { data[i] = element; found = true; break; } } if (found) { this.seq = this.seq > 100000 ? 0 : this.seq + 1; _store.default.dispatch('updateOrder', data); } } _onChange(data) { const answer_data = {}; data.forEach(item => { if (item && item.readOnly && this.props.variables[item.variableKey]) { answer_data[item.field_name] = this.props.variables[item.variableKey]; } }); this.setState({ data, answer_data }); } _onDestroy(item) { if (item.childItems) { item.childItems.forEach(x => { const child = this.getDataById(x); if (child) { _store.default.dispatch('delete', child); } }); } _store.default.dispatch('delete', item); } getDataById(id) { const { data } = this.state; return data.find(x => x && x.id === id); } swapChildren(data, item, child, col) { if (child.col !== undefined && item.id !== child.parentId) { return false; } if (!(child.col !== undefined && child.col !== col && item.childItems[col])) { // No child was assigned yet in both source and target. return false; } const oldId = item.childItems[col]; const oldItem = this.getDataById(oldId); const oldCol = child.col; // eslint-disable-next-line no-param-reassign item.childItems[oldCol] = oldId; oldItem.col = oldCol; // eslint-disable-next-line no-param-reassign item.childItems[col] = child.id; child.col = col; _store.default.dispatch('updateOrder', data); return true; } setAsChild(item, child, col, isBusy) { const { data } = this.state; if (this.swapChildren(data, item, child, col)) { return; } if (isBusy) { return; } const oldParent = this.getDataById(child.parentId); const oldCol = child.col; // eslint-disable-next-line no-param-reassign item.childItems[col] = child.id; child.col = col; // eslint-disable-next-line no-param-reassign child.parentId = item.id; // eslint-disable-next-line no-param-reassign child.parentIndex = data.indexOf(item); if (oldParent) { oldParent.childItems[oldCol] = null; } const list = data.filter(x => x && x.parentId === item.id); const toRemove = list.filter(x => item.childItems.indexOf(x.id) === -1); let newData = data; if (toRemove.length) { // console.log('toRemove', toRemove); newData = data.filter(x => toRemove.indexOf(x) === -1); } if (!this.getDataById(child.id)) { newData.push(child); } _store.default.dispatch('updateOrder', newData); } removeChild(item, col) { const { data } = this.state; const oldId = item.childItems[col]; const oldItem = this.getDataById(oldId); if (oldItem) { const newData = data.filter(x => x !== oldItem); // eslint-disable-next-line no-param-reassign item.childItems[col] = null; // delete oldItem.parentId; this.seq = this.seq > 100000 ? 0 : this.seq + 1; _store.default.dispatch('updateOrder', newData); this.setState({ data: newData }); } } restoreCard(item, id) { const { data } = this.state; const parent = this.getDataById(item.data.parentId); const oldItem = this.getDataById(id); if (parent && oldItem) { const newIndex = data.indexOf(oldItem); const newData = [...data]; // data.filter(x => x !== oldItem); // eslint-disable-next-line no-param-reassign parent.childItems[oldItem.col] = null; delete oldItem.parentId; // eslint-disable-next-line no-param-reassign delete item.setAsChild; // eslint-disable-next-line no-param-reassign delete item.parentIndex; // eslint-disable-next-line no-param-reassign item.index = newIndex; this.seq = this.seq > 100000 ? 0 : this.seq + 1; _store.default.dispatch('updateOrder', newData); this.setState({ data: newData }); } } insertCard(item, hoverIndex, id) { const { data } = this.state; if (id) { this.restoreCard(item, id); } else { data.splice(hoverIndex, 0, item); this.saveData(item, hoverIndex, hoverIndex); _store.default.dispatch('insertItem', item); } } moveCard(dragIndex, hoverIndex) { const { data } = this.state; const dragCard = data[dragIndex]; // happens sometimes when you click to insert a new item from the toolbox if (dragCard !== undefined) { this.saveData(dragCard, dragIndex, hoverIndex); } } // eslint-disable-next-line no-unused-vars cardPlaceHolder(dragIndex, hoverIndex) { // Dummy } saveData(dragCard, dragIndex, hoverIndex) { const newData = (0, _immutabilityHelper.default)(this.state, { data: { $splice: [[dragIndex, 1], [hoverIndex, 0, dragCard]] } }); this.setState(newData); _store.default.dispatch('updateOrder', newData.data); } getElement(item, index) { if (item.custom) { if (!item.component || typeof item.component !== 'function') { // eslint-disable-next-line no-param-reassign item.component = this.props.registry.get(item.key); } } const SortableFormElement = _sortableFormElements.default[item.element]; if (SortableFormElement === null) { return null; } return /*#__PURE__*/_react.default.createElement(SortableFormElement, { id: item.id, seq: this.seq, index: index, moveCard: this.moveCard, insertCard: this.insertCard, mutable: false, parent: this.props.parent, editModeOn: this.props.editModeOn, isDraggable: true, key: item.id, sortData: item.id, data: item, getDataById: this.getDataById, setAsChild: this.setAsChild, removeChild: this.removeChild, _onDestroy: this._onDestroy, duplicateElement: this.duplicateElement }); } showEditForm() { const handleUpdateElement = element => this.updateElement(element); handleUpdateElement.bind(this); const formElementEditProps = { showCorrectColumn: this.props.showCorrectColumn, files: this.props.files, manualEditModeOff: this.manualEditModeOff, preview: this, element: this.props.editElement, updateElement: handleUpdateElement, formData: this.state.data, apiBaseUrl: this.props.apiBaseUrl || 'https://api.dev.gateway.kusala.com.ng' }; return this.props.renderEditForm(formElementEditProps); } render() { let classes = this.props.className; if (this.props.editMode) { classes += ' is-editing'; } const data = this.state.data.filter(x => !!x && !x.parentId); const items = data.map((item, index) => this.getElement(item, index)); return /*#__PURE__*/_react.default.createElement("div", { className: classes }, /*#__PURE__*/_react.default.createElement("div", { className: "edit-form", ref: this.editForm }, this.props.editElement !== null && this.showEditForm()), /*#__PURE__*/_react.default.createElement("div", { className: "Sortable" }, items), /*#__PURE__*/_react.default.createElement(PlaceHolder, { id: "form-place-holder", show: items.length === 0, index: items.length, moveCard: this.cardPlaceHolder, insertCard: this.insertCard }), /*#__PURE__*/_react.default.createElement(_componentDragLayer.default, null)); } } exports.default = Preview; Preview.defaultProps = { showCorrectColumn: false, files: [], editMode: false, editElement: null, className: 'react-form-builder-preview flex-1', renderEditForm: props => /*#__PURE__*/_react.default.createElement(_formDynamicEdit.default, props) };