@helpscout/hsds-react
Version:
React component library for Help Scout's Design System
209 lines (167 loc) • 7.41 kB
JavaScript
"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
exports.__esModule = true;
exports.default = exports.MessageBubble = void 0;
var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends"));
var _objectWithoutPropertiesLoose2 = _interopRequireDefault(require("@babel/runtime/helpers/objectWithoutPropertiesLoose"));
var _react = _interopRequireDefault(require("react"));
var _propTypes = _interopRequireDefault(require("prop-types"));
var _getValidProps = _interopRequireDefault(require("@helpscout/react-utils/dist/getValidProps"));
var _isType = require("@helpscout/react-utils/dist/isType");
var _compose = _interopRequireDefault(require("@helpscout/react-utils/dist/compose"));
var _TypingDots = _interopRequireDefault(require("../TypingDots"));
var _Icon = _interopRequireDefault(require("../Icon"));
var _Text = _interopRequireDefault(require("../Text"));
var _classnames = _interopRequireDefault(require("classnames"));
var _strings = require("../../utilities/strings");
var _Message = require("./Message.utils");
var _MessageBubble = require("./Message.Bubble.css");
var _jsxRuntime = require("react/jsx-runtime");
// convertLinksToHTML will escape for output as HTML
var enhanceBody = (0, _compose.default)(_strings.newlineToHTML, _strings.convertLinksToHTML);
var MessageBubble = function MessageBubble(props, context) {
var body = props.body,
children = props.children,
className = props.className,
from = props.from,
icon = props.icon,
isNote = props.isNote,
ltr = props.ltr,
rtl = props.rtl,
size = props.size,
timestamp = props.timestamp,
title = props.title,
to = props.to,
typing = props.typing,
rest = (0, _objectWithoutPropertiesLoose2.default)(props, ["body", "children", "className", "from", "icon", "isNote", "ltr", "rtl", "size", "timestamp", "title", "to", "typing"]);
var theme = context.theme;
var isThemeNotifications = theme === 'notifications';
var isThemeEmbed = theme === 'embed';
var fromName = from && typeof from === 'string' ? from : null;
var showEmojiOnlyStyles = false;
var fromMarkup = isThemeNotifications && fromName ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleFromUI, {
className: "c-MessageBubble__from",
isEmbed: isThemeEmbed,
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_Text.default, {
className: "c-MessageBubble__fromText",
lineHeightReset: true,
size: "11",
children: fromName
})
}) : null;
var iconMarkup = icon ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleIconWrapperUI, {
className: "c-MessageBubble__iconWrapper",
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_Icon.default, {
className: "c-MessageBubble__icon",
name: icon,
size: "20",
shade: "extraMuted"
})
}) : null;
var titleMarkup = title ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleTitleUI, {
className: "c-MessageBubble__title",
size: "small",
children: title
}) : null;
var hasOnlyOneChild = _react.default.Children.count(children) === 1;
var childrenMarkup = _react.default.Children.map(children, function (child) {
showEmojiOnlyStyles = !isThemeEmbed && hasOnlyOneChild && (0, _Message.textIncludesOnlyEmoji)(child);
var fontSize = isThemeEmbed ? '13' : showEmojiOnlyStyles ? 48 : '14';
return (0, _Message.isWord)(child) || (0, _isType.isNativeSpanType)(child) ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleBodyUI, {
className: "c-MessageBubble__body",
isEmbed: isThemeEmbed,
showEmojiOnlyStyles: showEmojiOnlyStyles,
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_Text.default, {
wordWrap: true,
lineHeightInherit: true,
size: fontSize,
children: child
})
}) : child;
});
var renderBody = function renderBody() {
if (!body) {
return childrenMarkup;
}
showEmojiOnlyStyles = !isThemeEmbed && (0, _Message.textIncludesOnlyEmoji)(body);
if (showEmojiOnlyStyles) {
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleBodyUI, {
className: "c-MessageBubble__body",
showEmojiOnlyStyles: showEmojiOnlyStyles,
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_Text.default, {
wordWrap: true,
lineHeightInherit: true,
size: 48,
children: body
})
});
}
return /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleBodyUI, {
className: "c-MessageBubble__body",
isEmbed: isThemeEmbed,
dangerouslySetInnerHTML: {
__html: enhanceBody(body)
}
});
};
var innerContentMarkup = typing ? /*#__PURE__*/(0, _jsxRuntime.jsx)(_MessageBubble.MessageBubbleTypingUI, {
className: "c-MessageBubble__typing",
children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_TypingDots.default, {})
}) : renderBody();
var contentMarkup = /*#__PURE__*/(0, _jsxRuntime.jsxs)("div", {
className: "c-MessageBubble__content",
children: [iconMarkup, /*#__PURE__*/(0, _jsxRuntime.jsx)("div", {
className: "c-MessageBubble__bodyWrapper",
children: innerContentMarkup
})]
});
var componentClassName = (0, _classnames.default)('c-MessageBubble', from && 'is-from', icon && 'withIcon', isNote && 'is-note', size && "is-" + size, ltr && !rtl && 'is-ltr', !ltr && rtl && 'is-rtl', theme && "is-theme-" + theme, to && 'is-to', typing && 'is-typing', showEmojiOnlyStyles && 'emoji-only', className);
return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_MessageBubble.MessageBubbleUI, (0, _extends2.default)({}, (0, _getValidProps.default)(rest), {
className: componentClassName,
isEmbed: isThemeEmbed,
showEmojiOnlyStyles: showEmojiOnlyStyles,
children: [fromMarkup, titleMarkup, contentMarkup]
}));
};
exports.MessageBubble = MessageBubble;
function noop() {}
MessageBubble.defaultProps = {
'data-cy': 'MessageBubble'
};
MessageBubble.contextTypes = {
theme: noop
};
MessageBubble.propTypes = {
body: _propTypes.default.string,
/** Custom class names to be added to the component. */
className: _propTypes.default.string,
/** Provides author information and applies "From" styles. */
from: _propTypes.default.any,
/** Applies "note" styles. */
isNote: _propTypes.default.bool,
/** Applies left-to-right text styles. */
ltr: _propTypes.default.bool,
/** Applies "primary" styles. */
primary: _propTypes.default.bool,
/** Determines if the Message is read. */
read: _propTypes.default.bool,
/** Applies right-to-left text styles. */
rtl: _propTypes.default.bool,
/** Determines the size of the component. */
size: _propTypes.default.oneOf(['md', 'sm', '']),
/** Timestamp for the Message. */
timestamp: _propTypes.default.string,
/** Renders a `Heading` title in the component. */
title: _propTypes.default.string,
/** Provides author information and applies "To" styles. */
to: _propTypes.default.any,
/** Renders `TypingDots` within the component. */
typing: _propTypes.default.bool,
/** Callback when clicked. */
onClick: _propTypes.default.func,
icon: _propTypes.default.string,
/** Data attr for Cypress tests. */
'data-cy': _propTypes.default.string
};
var _default = MessageBubble;
exports.default = _default;