All Downloads are FREE. Search and download functionalities are using the official Maven repository.

META-INF.resources.js.components.AddDataSourceFieldsModalContent.tsx Maven / Gradle / Ivy

The newest version!
/**
 * SPDX-FileCopyrightText: (c) 2000 Liferay, Inc. https://liferay.com
 * SPDX-License-Identifier: LGPL-2.1-or-later OR LicenseRef-Liferay-DXP-EULA-2.0.0-2023-06
 */

import ClayButton from '@clayui/button';
import {TreeView} from '@clayui/core';
import {ClayCheckbox} from '@clayui/form';
import ClayLoadingIndicator from '@clayui/loading-indicator';
import ClayManagementToolbar, {
	ClayResultsBar,
} from '@clayui/management-toolbar';
import ClayModal from '@clayui/modal';
import {sub} from 'frontend-js-web';
import React, {ComponentProps, useEffect, useState} from 'react';

import {IField, IFieldTreeItem} from '../utils/types';
import AutoSearch from './AutoSearch';

import '../../css/components/FieldSelectModalContent.scss';

export function visit(fields: Array, callback: Function) {
	fields.forEach((field) => {
		callback(field);

		if (field.children) {
			visit(field.children, callback);
		}
	});
}

const initializeFields = ({
	fields: initialFields,
	selectedFields,
}: {
	fields: IField[];
	selectedFields: Array;
}): [Set, Array] => {
	const selectedKeys = new Set();
	const fields: IFieldTreeItem[] = Array.from(initialFields);

	visit(fields, (field: IFieldTreeItem) => {
		const selectedField = selectedFields.find(
			(selectedField) => selectedField.name === field.name
		);

		if (selectedField) {
			selectedKeys.add(selectedField.name);

			field.savedId = selectedField.id;
		}

		field.initialChildren = field.children;
		field.id = field.name;
	});

	return [selectedKeys, fields];
};

function filterFields({
	fields,
	onFilter,
	onMatch,
	query,
}: {
	fields: Array;
	onFilter?: (field: IFieldTreeItem) => void;
	onMatch?: (field: IFieldTreeItem) => void;
	query: string;
}) {
	const filteredItems: Array = [];
	const regexp = new RegExp(query, 'i');

	fields.forEach((field) => {
		const match = field.label ? regexp.test(field.label) : false;

		const filteredChildren = field.children?.length
			? filterFields({fields: field.children, onFilter, onMatch, query})
			: [];

		if (match || (field.children?.length && filteredChildren.length)) {
			filteredItems.push({
				...field,
				children: filteredChildren,
				query,
			});

			if (onFilter) {
				onFilter(field);
			}
		}

		if (match && onMatch) {
			onMatch(field);
		}
	});

	return filteredItems;
}

function applyFilter({
	fields,
	query,
}: {fields?: Array; query?: string} = {}) {
	if (!query || !fields) {
		return {
			counter: 0,
			filteredItems: fields ?? [],
			filteredKeys: [],
		};
	}

	let counter = 0;
	const filteredKeys: Array = [];
	const filteredItems = filterFields({
		fields,
		onFilter: ({id}: IFieldTreeItem) => {
			if (id) {
				filteredKeys.push(id);
			}
		},
		onMatch: () => counter++,
		query,
	});

	return {
		counter,
		filteredItems,
		filteredKeys,
	};
}

const Highlight = ({query, text}: {query?: string; text?: string}) => {
	if (!query || !text) {
		return (
			
				{text ?? ''}
			
		);
	}

	const indexMatch = text.search(RegExp(query, 'i'));

	if (indexMatch > -1) {
		return (
			
				{text.substring(0, indexMatch)}

				
					{text.substring(indexMatch, indexMatch + query.length)}
				

				{text.substring(indexMatch + query.length)}
			
		);
	}

	return <>{text};
};

const AddDataSourceFieldsModalContent = ({
	closeModal,
	fieldTreeItems,
	onSaveButtonClick,
	saveButtonDisabled,
	selectedFields,
	selectionMode = 'single',
}: {
	closeModal: Function;
	fieldTreeItems: Array;
	onSaveButtonClick: ({
		selectedFields,
	}: {
		selectedFields: Array;
	}) => void;
	saveButtonDisabled: boolean;
	selectedFields: Array;
	selectionMode?: ComponentProps['selectionMode'];
}) => {
	const [initialFields, setInitialFields] =
		useState | null>(fieldTreeItems);
	const [selectedKeys, setSelectedKeys] = useState>(
		new Set()
	);
	const [fields, setFields] = useState | null>(
		initialFields
	);
	const [query, setQuery] = useState('');
	const [expandedKeys, setExpandedKeys] = useState>([]);

	useEffect(() => {
		if (fields) {
			const [initialSelectedKeys, updatedFields] = initializeFields({
				fields,
				selectedFields,
			});

			setSelectedKeys(initialSelectedKeys);

			setFields(updatedFields);
		}

		// eslint-disable-next-line react-hooks/exhaustive-deps
	}, []);

	const onSearch = (query: string) => {
		setQuery(query);

		const {filteredItems, filteredKeys} = applyFilter({
			fields: initialFields ?? [],
			query,
		});

		setFields(filteredItems);
		setExpandedKeys(filteredKeys);
	};

	return (
		<>
			
				{sub(
					Liferay.Language.get('select-x'),
					Liferay.Language.get('field')
				)}
			

			
				{fields === null ? (
					
				) : (
					<>
						
							 event.preventDefault()}
							>
								
							
						

						{selectedKeys.size > 0 && (
							
								
									
										
											{selectedKeys.size}
											 
											{selectedKeys.size === 1
												? Liferay.Language.get(
														'item-selected'
													)
												: Liferay.Language.get(
														'items-selected'
													)}
										
									
								

								
									 {
											selectedKeys.clear();
											onSearch('');
										}}
									>
										{Liferay.Language.get('deselect-all')}
									
								
							
						)}

						
{ setExpandedKeys(Array.from(keys)); }} onItemsChange={(items) => setInitialFields( items as Array ) } onSelectionChange={setSelectedKeys} selectedKeys={selectedKeys} selectionMode={selectionMode} showExpanderOnHover={false} > {({ children, disabled, initialChildren, label, query, }: IFieldTreeItem) => ( {selectionMode === 'single' ? ( ) : ( )} {({ disabled: childDisabled, label, }: IFieldTreeItem) => ( {selectionMode === 'multiple' && ( )} {selectionMode === 'single' && ( )} )} )}
)}
{ const selectedFields: Array = []; visit( initialFields || [], (field: IFieldTreeItem) => { if (selectedKeys.has(field.name)) { selectedFields.push({ ...field, id: field.savedId, }); } } ); onSaveButtonClick({ selectedFields, }); }} > {Liferay.Language.get('save')} closeModal()} > {Liferay.Language.get('cancel')} } /> ); }; export default AddDataSourceFieldsModalContent;




© 2015 - 2025 Weber Informatics LLC | Privacy Policy