wix-style-react
Version:
wix-style-react
126 lines • 6.28 kB
JavaScript
import React from 'react';
import PropTypes from 'prop-types';
import Content from './components/Content';
import Box from '../Box';
import Proportion from '../Proportion';
import { SIZES, DIRECTIONS } from './constants';
import { st, classes } from './MarketingLayout.st.css';
const imagePlaceholderAspectRatioBySize = {
[SIZES.tiny]: 1,
[SIZES.small]: 1,
[SIZES.medium]: 282 / 188,
};
/** Marketing layout is a layout designed to promote new features or display first time visit.
* Component has title, description, action and illustration areas. */
class MarketingLayout extends React.PureComponent {
constructor() {
super(...arguments);
this.renderImagePlaceholder = () => {
const { size } = this.props;
return (React.createElement(Proportion, { aspectRatio: imagePlaceholderAspectRatioBySize[size] },
React.createElement("div", { className: classes.imagePlaceholder })));
};
this.getBorderRadiusProps = () => {
const { inverted, direction, imagePadding } = this.props;
if (direction === 'horizontal')
return {
borderTopLeftRadius: !imagePadding && inverted ? 'inherit' : undefined,
borderTopRightRadius: !imagePadding && !inverted ? 'inherit' : undefined,
borderBottomLeftRadius: !imagePadding && inverted ? 'inherit' : undefined,
borderBottomRightRadius: !imagePadding && !inverted ? 'inherit' : undefined,
};
else
return {};
};
this.renderImage = () => {
const { image, imageBackgroundColor, inverted, size, direction, imagePadding, } = this.props;
if (!image && !imageBackgroundColor) {
return null;
}
return (React.createElement(Box, { key: "image", display: "flex", backgroundColor: imageBackgroundColor, justifyContent: "flex-end", className: st(classes.imageBackground), ...this.getBorderRadiusProps() },
React.createElement("div", { className: st(classes.imageWrapper, {
size,
inverted,
direction,
}) }, typeof image === 'string' ? (React.createElement("img", { src: image, width: "100%" })) : (image || this.renderImagePlaceholder()))));
};
this.renderContent = () => {
const { size, actions, title, description, badge, hiddenBadge, inverted, direction, imageBackgroundColor, } = this.props;
return (React.createElement(Box, { key: "content", className: st(classes.contentWrapper, {
inverted,
size,
direction,
withImageBackground: !!imageBackgroundColor,
}) },
badge && !hiddenBadge && React.createElement("div", { className: classes.badge }, badge),
React.createElement(Content, { size: size, actions: actions, title: title, description: description, badge: badge })));
};
}
renderHorizontal() {
const image = this.renderImage();
const content = this.renderContent();
return this.props.inverted ? [image, content] : [content, image];
}
renderVertical() {
const image = this.props.image && this.renderImage();
const content = this.renderContent();
return this.props.inverted ? [content, image] : [image, content];
}
render() {
const { size, badge, hiddenBadge, alignItems, inverted, actions, dataHook, imageBackgroundColor, direction, imagePadding, } = this.props;
return (React.createElement("div", { className: st(classes.root, {
size,
badge: !!badge,
hiddenBadge,
alignItems,
inverted,
withActions: !!actions,
withImageBackground: !!imageBackgroundColor,
direction,
imagePadding,
}), style: this.getBorderRadiusProps(), "data-hook": dataHook }, direction === DIRECTIONS.vertical
? this.renderVertical()
: this.renderHorizontal()));
}
}
MarketingLayout.displayName = 'MarketingLayout';
MarketingLayout.propTypes = {
/** Applies a data-hook HTML attribute that can be used in the tests. */
dataHook: PropTypes.string,
/** Accepts image URL or a custom element to be displayed on the side of content. */
image: PropTypes.node,
/** Specifies image area background color. Can be a keyword from color palette or any supported CSS color value (HEX, RGB, etc.). */
imageBackgroundColor: PropTypes.string,
/**
* Controls the size of the marketing layout.<br/>
*/
size: PropTypes.oneOf(['tiny', 'small', 'medium']),
/** Controls content direction. */
direction: PropTypes.oneOf(['horizontal', 'vertical']),
/** Controls the vertical alignment of the content. */
alignItems: PropTypes.oneOf(['center', 'stretch']),
/** Flips content layout. If true, image will be displayed on the left side of the content. */
inverted: PropTypes.bool,
/** Sets marketing layout actions. Accepts single or multiple interactive components. Most commonly contain `<Button/>` or `<TextButton/>`. */
actions: PropTypes.node,
/** Sets the marketing layout title. Accepts text string or a custom element. */
title: PropTypes.node,
/** Sets the marketing layout description. Accepts text string or a custom element. */
description: PropTypes.node,
/** Adds a container for a `<Badge/>` component at the top left corner. Affect component height. */
badge: PropTypes.node,
/** Specifies whether the badge is hidden. Can be used to add additional vertical spacing, if no badge is given. */
hiddenBadge: PropTypes.bool,
/** Enables padding inside image container. Use with `direction="horizontal"` layout only. */
imagePadding: PropTypes.bool,
};
MarketingLayout.defaultProps = {
size: 'small',
alignItems: 'center',
inverted: false,
direction: 'horizontal',
hiddenBadge: false,
imagePadding: true,
};
export default MarketingLayout;
//# sourceMappingURL=MarketingLayout.js.map