@keycloakify/keycloak-account-ui
Version:
<p align="center"> <img src="https://github.com/user-attachments/assets/e31c4910-7205-441c-9a35-e134b806b3a8"> </p> <p align="center"> <i>Repackaged Keycloak Account UI</i> <br> <br> <a href="https://github.com/keycloakify/keycloak-a
138 lines • 8.8 kB
JavaScript
var __rest = (this && this.__rest) || function (s, e) {
var t = {};
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
t[p] = s[p];
if (s != null && typeof Object.getOwnPropertySymbols === "function")
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
t[p[i]] = s[p[i]];
}
return t;
};
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
import { Button, Chip, ChipGroup, MenuToggle, MenuToggleStatus, Select, SelectList, SelectOption, TextInputGroup, TextInputGroupMain, TextInputGroupUtilities, } from "@patternfly/react-core";
import { TimesIcon } from "@patternfly/react-icons";
import { get } from "lodash-es";
import { useMemo, useRef, useState } from "react";
import { Controller, useFormContext, } from "react-hook-form";
import { FormLabel } from "../../../ui-shared/controls/FormLabel";
import { SelectVariant, isSelectBasedOptions, isString, key, } from "../../../ui-shared/controls/select-control/SelectControl";
const getValue = (option) => isString(option) ? option : option.value;
export const TypeaheadSelectControl = (_a) => {
var _b;
var { id, name, label, options, controller, labelIcon, placeholderText, onFilter, variant } = _a, rest = __rest(_a, ["id", "name", "label", "options", "controller", "labelIcon", "placeholderText", "onFilter", "variant"]);
const { control, formState: { errors }, } = useFormContext();
const [open, setOpen] = useState(false);
const [filterValue, setFilterValue] = useState("");
const [focusedItemIndex, setFocusedItemIndex] = useState(0);
const textInputRef = useRef();
const filteredOptions = options.filter((option) => getValue(option).toLowerCase().startsWith(filterValue.toLowerCase()));
const convert = useMemo(() => filteredOptions.map((option, index) => (_jsx(SelectOption, { value: key(option), isFocused: focusedItemIndex === index, children: getValue(option) }, key(option)))), [focusedItemIndex, filteredOptions]);
const onInputKeyDown = (event, field) => {
const focusedItem = filteredOptions[focusedItemIndex];
setOpen(true);
switch (event.key) {
case "Enter": {
event.preventDefault();
if (variant !== SelectVariant.typeaheadMulti) {
setFilterValue(getValue(focusedItem));
}
else {
setFilterValue("");
}
field.onChange(Array.isArray(field.value)
? [...field.value, key(focusedItem)]
: key(focusedItem));
setOpen(false);
setFocusedItemIndex(0);
break;
}
case "Tab":
case "Escape": {
setOpen(false);
field.onChange(undefined);
break;
}
case "Backspace": {
if (variant === SelectVariant.typeahead) {
field.onChange("");
}
break;
}
case "ArrowUp":
case "ArrowDown": {
event.preventDefault();
let indexToFocus = 0;
if (event.key === "ArrowUp") {
if (focusedItemIndex === 0) {
indexToFocus = options.length - 1;
}
else {
indexToFocus = focusedItemIndex - 1;
}
}
if (event.key === "ArrowDown") {
if (focusedItemIndex === options.length - 1) {
indexToFocus = 0;
}
else {
indexToFocus = focusedItemIndex + 1;
}
}
setFocusedItemIndex(indexToFocus);
break;
}
}
};
return (_jsx(FormLabel, { name: name, label: label, isRequired: !!((_b = controller.rules) === null || _b === void 0 ? void 0 : _b.required), error: get(errors, name), labelIcon: labelIcon, children: _jsx(Controller, Object.assign({}, controller, { name: name, control: control, render: ({ field }) => (_jsx(Select, Object.assign({}, rest, { onClick: () => setOpen(!open), onOpenChange: () => setOpen(false), selected: isSelectBasedOptions(options)
? options
.filter((o) => Array.isArray(field.value)
? field.value.includes(o.key)
: field.value === o.key)
.map((o) => o.value)
: field.value, toggle: (ref) => {
var _a;
return (_jsx(MenuToggle, { ref: ref, id: id || name.slice(name.lastIndexOf(".") + 1), variant: "typeahead", onClick: () => setOpen(!open), isExpanded: open, isFullWidth: true, status: get(errors, name) ? MenuToggleStatus.danger : undefined, children: _jsxs(TextInputGroup, { isPlain: true, children: [_jsx(TextInputGroupMain, { placeholder: placeholderText, value: variant === SelectVariant.typeahead && field.value
? isSelectBasedOptions(options)
? (_a = options.find((o) => o.key ===
(Array.isArray(field.value)
? field.value[0]
: field.value))) === null || _a === void 0 ? void 0 : _a.value
: field.value
: filterValue, onClick: () => setOpen(!open), onChange: (_, value) => {
setFilterValue(value);
onFilter === null || onFilter === void 0 ? void 0 : onFilter(value);
}, onKeyDown: (event) => onInputKeyDown(event, field), autoComplete: "off", innerRef: textInputRef, role: "combobox", isExpanded: open, "aria-controls": "select-typeahead-listbox", children: variant === SelectVariant.typeaheadMulti &&
Array.isArray(field.value) && (_jsx(ChipGroup, { "aria-label": "Current selections", children: field.value.map((selection, index) => {
var _a;
return (_jsx(Chip, { onClick: (ev) => {
ev.stopPropagation();
field.onChange(field.value.filter((item) => item !== key(selection)));
}, children: isSelectBasedOptions(options)
? (_a = options.find((o) => selection === o.key)) === null || _a === void 0 ? void 0 : _a.value
: getValue(selection) }, index));
}) })) }), _jsx(TextInputGroupUtilities, { children: !!filterValue && (_jsx(Button, { variant: "plain", onClick: () => {
var _a;
field.onChange(undefined);
setFilterValue("");
(_a = textInputRef === null || textInputRef === void 0 ? void 0 : textInputRef.current) === null || _a === void 0 ? void 0 : _a.focus();
}, "aria-label": "Clear input value", children: _jsx(TimesIcon, { "aria-hidden": true }) })) })] }) }));
}, onSelect: (event, v) => {
event === null || event === void 0 ? void 0 : event.stopPropagation();
const option = v === null || v === void 0 ? void 0 : v.toString();
if (variant === SelectVariant.typeaheadMulti &&
Array.isArray(field.value)) {
if (field.value.includes(option)) {
field.onChange(field.value.filter((item) => item !== option));
}
else {
field.onChange([...field.value, option]);
}
}
else {
field.onChange(Array.isArray(field.value) ? [option] : option);
setOpen(false);
}
}, isOpen: open, children: _jsx(SelectList, { children: convert }) }))) })) }));
};
//# sourceMappingURL=TypeaheadSelectControl.js.map