@clayui/shared
Version:
ClayShared component
63 lines (62 loc) • 1.8 kB
JavaScript
import React from "react";
import { Keys } from "./Keys";
import { useFocusManagement } from "./useFocusManagement";
const FocusConflictContext = React.createContext(false);
function FocusScope({
arrowKeysLeftRight = false,
arrowKeysUpDown = true,
children,
onFocus,
stopPropagation = true
}) {
const elRef = React.useRef(null);
const focusManager = useFocusManagement(elRef);
const onKeyDown = (event) => {
const { key, shiftKey } = event;
if (arrowKeysUpDown && key === Keys.Down || arrowKeysLeftRight && key === Keys.Right || key === Keys.Tab && !shiftKey) {
const next = focusManager.focusNext();
if (next) {
event.preventDefault();
if (onFocus) {
onFocus(next);
}
}
} else if (arrowKeysUpDown && key === Keys.Up || arrowKeysLeftRight && key === Keys.Left || key === Keys.Tab && shiftKey) {
const previous = focusManager.focusPrevious();
if (previous) {
event.preventDefault();
if (onFocus) {
onFocus(previous);
}
}
}
};
const child = typeof children === "function" ? children(focusManager) : children;
return /* @__PURE__ */ React.createElement(FocusConflictContext.Provider, { value: true }, React.cloneElement(child, {
onKeyDown: (event) => {
if (stopPropagation) {
event.stopPropagation();
}
if (child.props.onKeyDown) {
child.props.onKeyDown(event);
}
onKeyDown(event);
},
ref: (r) => {
if (r) {
elRef.current = r;
const { ref } = child;
if (ref) {
if (typeof ref === "object") {
ref.current = r;
} else if (typeof ref === "function") {
ref(r);
}
}
}
}
}));
}
export {
FocusScope
};