@atlaskit/primitives
Version:
Primitives are token-backed low-level building blocks.
134 lines (130 loc) • 4.31 kB
JavaScript
/**
* @jsxRuntime classic
* @jsx jsx
*/
import { forwardRef } from 'react';
// eslint-disable-next-line @atlaskit/ui-styling-standard/use-compiled -- Ignored via go/DSP-18766
import { css, jsx } from '@emotion/react';
import invariant from 'tiny-invariant';
import { fg } from '@atlaskit/platform-feature-flags';
import { HasTextAncestorProvider, useHasTextAncestor } from '../utils/has-text-ancestor-context';
import { useSurface } from '../utils/surface-provider';
import { inverseColorMap, textColorStylesMap, textSizeStylesMap, textWeightStylesMap } from '../xcss/style-maps.partial';
var asAllowlist = ['span', 'p', 'strong', 'em'];
// We're doing this because our CSS reset can add top margins to elements such as `p` which is totally insane.
// Long term we should remove those instances from the reset - it should be a reset to 0.
// For now, at least we know <Text> will be unaffected by this.
var resetStyles = css({
margin: 0,
overflowWrap: 'anywhere'
});
var strongStyles = css({
fontWeight: "var(--ds-font-weight-bold, 700)"
});
var emStyles = css({
fontStyle: 'italic'
});
var textAlignMap = {
center: css({
textAlign: 'center'
}),
end: css({
textAlign: 'end'
}),
start: css({
textAlign: 'start'
})
};
var truncationStyles = css({
display: '-webkit-box',
overflow: 'hidden',
WebkitBoxOrient: 'vertical'
});
var wordBreakMap = {
breakAll: css({
wordBreak: 'break-all'
})
};
/**
* Custom hook designed to abstract the parsing of the color props and make it clearer in the future how color is reconciled between themes and tokens.
*/
var useColor = function useColor(colorProp, hasTextAncestor) {
var surface = useSurface();
if (fg('platform-typography-improved-color-control')) {
if (colorProp === 'inherit') {
return undefined;
}
if (colorProp) {
return colorProp;
}
if (hasTextAncestor) {
return undefined;
}
if (inverseColorMap.hasOwnProperty(surface)) {
return inverseColorMap[surface];
}
return 'color.text';
}
/**
* Where the color of the surface is inverted we always override the color
* as there is no valid choice that is not covered by the override.
*/
if (inverseColorMap.hasOwnProperty(surface)) {
return inverseColorMap[surface];
}
if (colorProp === 'inherit') {
return undefined;
}
if (!colorProp && hasTextAncestor) {
return undefined;
}
return colorProp || 'color.text';
};
/**
* __Text__
*
* Text is a primitive component that has the Atlassian Design System's design guidelines baked in.
* This includes considerations for text attributes such as color, font size, font weight, and line height.
* It renders a `span` by default.
*
* @internal
*/
var Text = /*#__PURE__*/forwardRef(function (_ref, ref) {
var _ref$as = _ref.as,
Component = _ref$as === void 0 ? 'span' : _ref$as,
colorProp = _ref.color,
align = _ref.align,
testId = _ref.testId,
id = _ref.id,
size = _ref.size,
weight = _ref.weight,
maxLines = _ref.maxLines,
children = _ref.children;
invariant(asAllowlist.includes(Component), "@atlaskit/primitives: Text received an invalid \"as\" value of \"".concat(Component, "\""));
var hasTextAncestor = useHasTextAncestor();
var color = useColor(colorProp, hasTextAncestor);
if (!size && !hasTextAncestor) {
size = 'medium';
}
var component = jsx(Component, {
ref: ref,
css: [resetStyles,
// eslint-disable-next-line @atlaskit/ui-styling-standard/no-imported-style-values
size && textSizeStylesMap[size],
// eslint-disable-next-line @atlaskit/ui-styling-standard/no-imported-style-values
color && textColorStylesMap[color], maxLines && truncationStyles, maxLines === 1 && wordBreakMap.breakAll, align && textAlignMap[align],
// eslint-disable-next-line @atlaskit/ui-styling-standard/no-imported-style-values
weight && textWeightStylesMap[weight], Component === 'em' && emStyles, Component === 'strong' && strongStyles],
style: {
WebkitLineClamp: maxLines
},
"data-testid": testId,
id: id
}, children);
return hasTextAncestor ?
// no need to re-apply context if the text is already wrapped
component : jsx(HasTextAncestorProvider, {
value: true
}, component);
});
export default Text;