Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Heading and spacing description #408

Merged
14 changes: 12 additions & 2 deletions src/components/EditableHeading/EditableHeading.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,9 @@ const EditableHeading = props => {
);
};

EditableHeading.types = TYPES;
EditableHeading.sizes = SIZES;

EditableHeading.propTypes = {
/**
* Class name to be added to the header wrapper
Expand All @@ -186,8 +189,15 @@ EditableHeading.propTypes = {
/**
* Header type
*/
type: PropTypes.oneOf(Object.keys(TYPES)),
size: PropTypes.oneOf(Object.values(SIZES)),
type: PropTypes.oneOf([
EditableHeading.types.h1,
EditableHeading.types.h2,
EditableHeading.types.h3,
EditableHeading.types.h4,
EditableHeading.types.h5,
EditableHeading.types.h6
]),
size: PropTypes.oneOf([EditableHeading.sizes.SMALL, EditableHeading.sizes.MEDIUM, EditableHeading.sizes.LARGE]),
displayPlaceholderInTextMode: PropTypes.bool,
suggestEditOnHover: PropTypes.bool,
autoSize: PropTypes.bool,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
import EditableHeading from "../EditableHeading";
import { ArgsTable, Story, Canvas, Meta } from "@storybook/addon-docs";
import { createComponentTemplate } from "../../../storybook/functions/create-component-story";
import { createComponentTemplate, createStoryMetaSettings } from "../../../storybook/functions/create-component-story";

export const argTypes = createStoryMetaSettings({
component: EditableHeading,
enumPropNamesArray: ["size", "type"],
})

<Meta
title="Inputs/EditableHeading"
component={ EditableHeading }
argTypes={argTypes}
/>

<!--- Component template -->
Expand Down
14 changes: 12 additions & 2 deletions src/components/Heading/Heading.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -55,17 +55,27 @@ const Heading = ({
return Element;
};

Heading.types = TYPES;
Heading.sizes = SIZES;

Heading.propTypes = {
className: PropTypes.string,
type: PropTypes.oneOf(Object.keys(TYPES)),
type: PropTypes.oneOf([
Heading.types.h1,
Heading.types.h2,
Heading.types.h3,
Heading.types.h4,
Heading.types.h5,
Heading.types.h6
]),
ariaLabel: PropTypes.string,
value: PropTypes.string,
id: PropTypes.string,
ellipsis: PropTypes.bool,
ellipsisMaxLines: PropTypes.number,
suggestEditOnHover: PropTypes.bool,
nonEllipsisTooltip: PropTypes.string,
size: PropTypes.oneOf(Object.values(SIZES))
size: PropTypes.oneOf([Heading.sizes.SMALL, Heading.sizes.MEDIUM, Heading.sizes.LARGE])
};
Heading.defaultProps = {
className: "",
Expand Down
159 changes: 159 additions & 0 deletions src/components/Heading/__stories__/Heading.stories.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,159 @@
import Heading from "../Heading";
import { ArgsTable, Story, Canvas, Meta } from "@storybook/addon-docs";
import { createComponentTemplate, createStoryMetaSettings } from "../../../storybook/functions/create-component-story";
import { Link, RelatedComponents } from "../../../storybook/components";
import Divider from "../../Divider/Divider";
import Search from "../../Search/Search";
import Checkbox from "../../Checkbox/Checkbox";
import Button from "../../Button/Button";
import { Custom } from "../../Icon/Icons";
import { emptyStateExample } from "./assets";
import classes from "./Heading.stories.module.scss";
import { RelatedComponent } from "../../../storybook/components/related-component/related-component";
import {
EDITABLE_HEADING,
SEARCH,
TEXT_FIELD
} from "../../../storybook/components/related-components/component-description-map";

export const argsTypes = createStoryMetaSettings({
component: Heading,
enumPropNamesArray: ["type", "size"]
})

<Meta
title="Text/Heading"
component={ Heading }
argTypes={ argsTypes }
/>

<!--- Component template -->

export const headingTemplate = createComponentTemplate(Heading);

<!--- Component documentation -->

# Heading
- [Overview](#overview)
- [Props](#props)
- [Usage](#usage)
- [Variants](#variants)
- [Do’s and don’ts](#dos-and-donts)
- [Use cases and examples](#use-cases-and-examples)
- [Related components](#related-components)
- [Feedback](#feedback)

## Overview
Heading components are used to title any page sections or sub-sections in top-level page sections.

<Canvas>
<Story name="Overview"
args={{ value: "Hello world" }}>
{ headingTemplate.bind({}) }
</Story>
</Canvas>

## Props
<ArgsTable of={ Heading } />

## Usage
<UsageGuidelines guidelines={[
"Never include more than one H1 title per web page",
"Heading always should be linked to content (by design and by implementation by passing the heading id to the content's aria-labelledBy attribute)",
]}/>

<Tip title="Not what you were looking for?">Please check out our <Link href="/?path=/docs/inputs-editableheading--overview" withoutSpacing>EditableHeading</Link> component if you would like to allow users to edit the title text..</Tip>

## Variants
### Story title 1
<Canvas>
<Story name="Types">
<div style={{display: "flex", flexDirection: "column" }}>
<Heading type={Heading.types.h1} value="Hello H1" />
<Heading type={Heading.types.h1} value="Hello H1 medium" size="medium" />
<Heading type={Heading.types.h2} value="Hello H2" />
<Heading type={Heading.types.h2} value="Hello H2 small" size="small" />
<Heading type={Heading.types.h3} value="Hello H3" />
<Heading type={Heading.types.h4} value="Suggest Edit H4" suggestEditOnHover />
<Heading type={Heading.types.h5} value="H5 with tooltip" nonEllipsisTooltip="Click to edit" />
</div>
</Story>
</Canvas>

### Overflow
Our heading components support overflow state.
When the heading text is too long and the component includes an ellipsis flag, we will cut the end of the heading and display instead of it "...".
<Canvas>
<Story name="Overflow">
<div style={{display: "flex", flexDirection: "column", width: "70%"}}>
<Heading
type={Heading.types.h2}
value="Heading without overflow heading without overflow heading without overflow"
ellipsis={false}
nonEllipsisTooltip="Non ellipsis tooltip"
/>
<Heading
type={Heading.types.h2}
value="Heading with overflow heading with overflow heading with overflow heading with overflow heading with overflow"
ellipsis
nonEllipsisTooltip="Non ellipsis tooltip (this tooltip is not shown since overflow)"
/>
<div>
<Heading
type={Heading.types.h2}
value="Heading with overflow when text is longer then 2 lines heading with overflow when text is longer then 2 lines heading with overflow when text is longer then 2 lines"
ellipsisMaxLines={2}
nonEllipsisTooltip="Non ellipsis tooltip (this tooltip is not shown since overflow)"
/>
</div>
</div>
</Story>
</Canvas>

## Do’s and Don’ts
<ComponentRules
rules={[
{
positive: {
component:<Heading value="Hello world"/>,
description:"Always capitalize the first letter of the first word in the heading."
},
negative: {
component:<Heading value="Hello World"/>,
description:"Please avoid capitalizing the first letter of each word in the heading."
}
}
]}
/>


## Use cases and examples

### Not editable header of a page
<Canvas>
<Story name="Not editable header of a page">
<div style={{width: "100%"}}>
<Heading type={Heading.types.h1} value="My Work"/>
<Divider/>
<div className={classes["page-header_commands"]} style={{display: "flex", alignItems: "center"}} >
<Search wrapperClassName={classes["page-header_search"]} placeholder="Search"/>
<Checkbox label="Hide done items" checked />
<Button leftIcon={Custom} kind={Button.kinds.TERTIARY}>Customize</Button>
</div>
</div>
</Story>
</Canvas>

### Empty state title
<Canvas>
<Story name="Empty state title">
<div className={classes["empty-state-container"]}>
<img style={{width: "290px"}} src={emptyStateExample} alt="" />
<Heading type={Heading.types.h2} value="No updates yet for this item"/>
<span style={{width: "50%", textAlign: "center"}}>Be the first one to update about progress, mention someone or upload files to share with your team members</span>
</div>
</Story>
</Canvas>

## Related components
<RelatedComponents componentsNames={[EDITABLE_HEADING, TEXT_FIELD, SEARCH]}/>
20 changes: 20 additions & 0 deletions src/components/Heading/__stories__/Heading.stories.module.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
@import "../../../styles/themes.scss";

.empty-state-container {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
width: 100%;
padding: var(--spacing-large);
}

.page-header_commands {
margin-top: var(--spacing-large);
& > * {
margin-left: var(--spacing-small);
}
}
.page-header_search {
width: 146px;
}
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions src/components/Heading/__stories__/assets/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import emptyStateExample from "./emptyStateExample.svg";

export { emptyStateExample };
42 changes: 0 additions & 42 deletions src/components/Heading/__stories__/heading.stories.js

This file was deleted.

7 changes: 1 addition & 6 deletions src/storybook/components/coming-soon/coming-soon.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,6 @@ import classes from "./coming-soon.module.scss";
export const ComingSoon = () => (
<div className={classes["coming-soon-container"]}>
<img className={classes["coming-soon-image"]} src={comingSoon} alt="" />
<Heading
type={Heading.types.h2}
ellipsis={false}
className={classes["coming-soon-title"]}
value="We are working hard to build this page, it will be avilabile soon!"
/>
<Heading type={Heading.types.h3} ellipsis={false} className={classes["coming-soon-title"]} value="Coming soon..." />
</div>
);
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,10 @@ import { SpinnerDescription } from "./descriptions/spinner-description";
import { SkeletonDescription } from "./descriptions/skeleton-description";
import { TypographyDescription } from "./descriptions/typography-description/typography-description";
import { ProgressBarDescription } from "./descriptions/progress-bar-description";
import { EditableHeadingDescription } from "./descriptions/editable-heading-description";
import { ShadowDescription } from "./descriptions/shadow-description/shadow-description";
import { HeadingDescription } from "./descriptions/heading-description";
import { SpacingDescription } from "./descriptions/spacing-description/spacing-description";

export const SPLIT_BUTTON = "split-button";
export const BUTTON_GROUP = "button-group";
Expand Down Expand Up @@ -60,11 +62,13 @@ export const SPINNER = "spinner";
export const SKELETON = "skeleton";
export const PROGRESS_BAR = "progress-bar";
export const HEADING = "heading";
export const EDITABLE_HEADING = "editable_heading";

// General description names (not related to specific components)
export const COLORS = "colors";
export const TYPOGRAPHY = "typography";
export const SHADOW = "shadow";
export const SPACING = "spacing";

export const descriptionTypesMap = new Map();

Expand Down Expand Up @@ -96,9 +100,11 @@ descriptionTypesMap.set(STEPPER, <StepperDescription />);
descriptionTypesMap.set(SPINNER, <SpinnerDescription />);
descriptionTypesMap.set(SKELETON, <SkeletonDescription />);
descriptionTypesMap.set(PROGRESS_BAR, <ProgressBarDescription />);
descriptionTypesMap.set(EDITABLE_HEADING, <EditableHeadingDescription />);
descriptionTypesMap.set(HEADING, <HeadingDescription />);

// General description (not related to specific components)
descriptionTypesMap.set(COLORS, <ColorsDescription />);
descriptionTypesMap.set(TYPOGRAPHY, <TypographyDescription />);
descriptionTypesMap.set(SHADOW, <ShadowDescription />);
descriptionTypesMap.set(SPACING, <SpacingDescription />);
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import { useMemo } from "react";
import { RelatedComponent } from "../../related-component/related-component";
import EditableHeading from "../../../../components/EditableHeading/EditableHeading";

export const EditableHeadingDescription = () => {
const component = useMemo(() => {
return (
<div>
<EditableHeading value="Hello world" type={EditableHeading.types.h3} />
</div>
);
}, []);
return (
<RelatedComponent
component={component}
title="Editable heading"
description="An extension of Heading component, it allows built in editing capabilities."
/>
);
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import { useMemo } from "react";
import { RelatedComponent } from "../../../related-component/related-component";
import classes from "./spacing-description.module.scss";

export const SpacingDescription = () => {
const component = useMemo(
() => (
<div className={classes["spacing-description-visual-element"]}>
<div className={classes["small-spacing-visual-element"]} />
<div className={classes["medium-spacing-visual-element"]} />
<div className={classes["large-spacing-visual-element"]} />
</div>
),
[]
);
return (
<RelatedComponent
component={component}
title="Spacing"
description="Spacing creates relationships and hierarchy withing the visual controls."
/>
);
};
Loading