@carbon/react
Version:
React components for the Carbon Design System
124 lines (122 loc) • 4.56 kB
JavaScript
/**
* Copyright IBM Corp. 2016, 2026
*
* This source code is licensed under the Apache-2.0 license found in the
* LICENSE file in the root directory of this source tree.
*/
const require_runtime = require("../../_virtual/_rolldown/runtime.js");
const require_usePrefix = require("../../internal/usePrefix.js");
const require_keys = require("../../internal/keyboard/keys.js");
const require_match = require("../../internal/keyboard/match.js");
const require_useId = require("../../internal/useId.js");
const require_noopFn = require("../../internal/noopFn.js");
const require_deprecate = require("../../prop-types/deprecate.js");
const require_Button = require("../Button/Button.js");
let classnames = require("classnames");
classnames = require_runtime.__toESM(classnames);
let react = require("react");
react = require_runtime.__toESM(react);
let prop_types = require("prop-types");
prop_types = require_runtime.__toESM(prop_types);
let react_jsx_runtime = require("react/jsx-runtime");
//#region src/components/FileUploader/FileUploaderButton.tsx
/**
* Copyright IBM Corp. 2016, 2026
*
* This source code is licensed under the Apache-2.0 license found in the
* LICENSE file in the root directory of this source tree.
*/
function FileUploaderButton({ accept, buttonKind = "primary", className, disabled = false, disableLabelChanges = false, id, labelText: ownerLabelText = "Add file", multiple = false, onChange = require_noopFn.noopFn, name, size = "md", innerRef, ...other }) {
const prefix = require_usePrefix.usePrefix();
const [labelText, setLabelText] = (0, react.useState)(ownerLabelText);
const generatedId = require_useId.useId();
const { current: inputId } = (0, react.useRef)(id || generatedId);
const inputNode = (0, react.useRef)(null);
const classes = (0, classnames.default)(`${prefix}--btn`, className, {
[`${prefix}--btn--${buttonKind}`]: buttonKind,
[`${prefix}--btn--disabled`]: disabled,
[`${prefix}--btn--md`]: size === "field" || size === "md",
[`${prefix}--btn--sm`]: size === "small" || size === "sm",
[`${prefix}--layout--size-${size}`]: size
});
(0, react.useEffect)(() => {
setLabelText(ownerLabelText);
}, [ownerLabelText]);
function onClick(event) {
event.target.value = null;
if (inputNode.current) {
inputNode.current.value = "";
inputNode.current.click();
}
}
function onKeyDown(event) {
if (require_match.matches(event, [require_keys.Enter, require_keys.Space])) {
event.preventDefault();
if (inputNode.current) {
inputNode.current.value = "";
inputNode.current.click();
}
}
}
function handleOnChange(event) {
const files = event.target.files;
const length = event.target.files?.length || 0;
if (files && !disableLabelChanges) {
if (length > 1) setLabelText(`${length} files`);
else if (length === 1) setLabelText(files[0].name);
}
onChange(event);
}
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
type: "button",
disabled,
className: classes,
onClick,
onKeyDown,
...other,
tabIndex: other.tabIndex !== void 0 ? parseInt(other.tabIndex) : void 0,
children: labelText
}),
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("label", {
className: `${prefix}--visually-hidden`,
ref: innerRef,
htmlFor: inputId,
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", { children: labelText })
}),
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
className: `${prefix}--visually-hidden`,
ref: inputNode,
id: inputId,
disabled,
type: "file",
tabIndex: -1,
multiple,
accept: accept?.toString(),
name,
onChange: handleOnChange
})
] });
}
FileUploaderButton.propTypes = {
accept: prop_types.default.arrayOf(prop_types.default.string),
buttonKind: prop_types.default.oneOf(require_Button.ButtonKinds),
className: prop_types.default.string,
disableLabelChanges: prop_types.default.bool,
disabled: prop_types.default.bool,
id: prop_types.default.string,
labelText: prop_types.default.node,
multiple: prop_types.default.bool,
name: prop_types.default.string,
onChange: prop_types.default.func,
onClick: prop_types.default.func,
role: prop_types.default.string,
size: prop_types.default.oneOf([
"sm",
"md",
"lg"
]),
tabIndex: require_deprecate.deprecate(prop_types.default.number, "The `tabIndex` prop for `FileUploaderButton` has been deprecated since it now renders a button element by default.")
};
//#endregion
exports.default = FileUploaderButton;