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

🪟 🐛 Split Heading and Text components #17992

Merged
merged 9 commits into from
Oct 27, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 5 additions & 6 deletions airbyte-webapp/src/components/ConnectorBlocks/TableItemTitle.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { FormattedMessage, useIntl } from "react-intl";
import { ReleaseStageBadge } from "components/ReleaseStageBadge";
import { Button } from "components/ui/Button";
import { DropDownOptionDataItem } from "components/ui/DropDown";
import { Heading } from "components/ui/Heading";
import { Popout } from "components/ui/Popout";
import { Text } from "components/ui/Text";

Expand Down Expand Up @@ -47,19 +48,17 @@ const TableItemTitle: React.FC<TableItemTitleProps> = ({
<div className={styles.entityInfo}>
{entityIcon && <div className={styles.entityIcon}>{entityIcon}</div>}
<div>
<Text as="h2" size="md">
{entityName}
</Text>
<Text as="p" size="lg" bold className={styles.entityType}>
<Heading as="h2">{entityName}</Heading>
<Text size="lg" bold className={styles.entityType}>
<span>{entity}</span>
<ReleaseStageBadge stage={releaseStage} />
</Text>
</div>
</div>
<div className={styles.content}>
<Text as="h3" size="sm">
<Heading as="h3" size="sm">
<FormattedMessage id="tables.connections" />
</Text>
</Heading>
<Popout
data-testid={`select-${type}`}
options={options}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ import { Field, FieldProps } from "formik";
import { FormattedMessage, useIntl } from "react-intl";

import { ControlLabels } from "components/LabeledControl";
import { Heading } from "components/ui/Heading";
import { Input } from "components/ui/Input";
import { Text } from "components/ui/Text";

import { Section } from "views/Connection/ConnectionForm/components/Section";

Expand All @@ -23,9 +23,9 @@ export const CreateConnectionNameField = () => {
nextLine
error={!!meta.error && meta.touched}
label={
<Text as="h5" className={styles.labelHeading}>
<Heading as="h5" className={styles.labelHeading}>
<FormattedMessage id="form.connectionName" />
</Text>
</Heading>
}
message={formatMessage({
id: "form.connectionName.message",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,11 @@ export const TryAfterErrorBlock: React.FC<TryAfterErrorBlockProps> = ({ message,
return (
<div className={styles.container}>
<StatusIcon big />
<Text as="p" size="lg" centered className={styles.message}>
<Text size="lg" centered className={styles.message}>
<FormattedMessage id="form.schemaFailed" />
</Text>
{message && (
<Text as="p" size="lg" centered className={styles.message}>
<Text size="lg" centered className={styles.message}>
<FormattedMessage id="form.error" values={{ message }} />
</Text>
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { useMemo } from "react";
import { FormattedMessage } from "react-intl";

import { Button } from "components/ui/Button";
import { Text } from "components/ui/Text";
import { Heading } from "components/ui/Heading";

import { ReactComponent as BowtieHalf } from "./bowtie-half.svg";
import styles from "./EmptyResourceListView.module.scss";
Expand All @@ -30,9 +30,9 @@ export const EmptyResourceListView: React.FC<EmptyResourceListViewProps> = ({

return (
<div className={styles.container}>
<Text as="h2" size="lg" centered className={styles.heading}>
<Heading as="h2" size="lg" centered className={styles.heading}>
<FormattedMessage id={headingMessageId} />
</Text>
</Heading>
<div className={classNames(styles.container, styles.illustration)}>
{resourceType !== "destinations" && (
<BowtieHalf aria-hidden="true" className={classNames(styles.bowtie, styles.left)} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ interface ResetStreamsDetailsProps {
}

export const ResetStreamsDetails: React.FC<ResetStreamsDetailsProps> = ({ names = [], isOpen }) => (
<Text as="p" size="sm" className={classNames(styles.textContainer, { [styles.open]: isOpen })}>
<Text size="sm" className={classNames(styles.textContainer, { [styles.open]: isOpen })}>
{names.map((name) => (
<span key={name} className={styles.text}>
{name}
Expand Down
4 changes: 2 additions & 2 deletions airbyte-webapp/src/components/base/Titles/Titles.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,13 +19,13 @@ const H1 = styled.h1<IProps>`
margin: 0;
`;

/** @deprecated Use `<Text as="h1 | h2 | h3 | h4 | h5" size="md" />` */
/** @deprecated Use `<Heading as="h1 | h2 | h3 | h4 | h5" size="md" />` */
export const H3 = styled(H1).attrs({ as: "h3" })`
font-size: 20px;
line-height: 24px;
`;

/** @deprecated Use `<Text as="h1 | h2 | h3 | h4 | h5" size="sm" />` */
/** @deprecated Use `<Heading as="h1 | h2 | h3 | h4 | h5" size="sm" />` */
export const H5 = styled(H1).attrs({ as: "h5" })`
font-size: ${({ theme }) => theme.h5?.fontSize || "16px"};
line-height: ${({ theme }) => theme.h5?.lineHeight || "28px"};
Expand Down
17 changes: 17 additions & 0 deletions airbyte-webapp/src/components/ui/Heading/Heading.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import { ComponentStory, ComponentMeta } from "@storybook/react";

import { Heading } from "./Heading";

export default {
title: "Ui/Heading",
component: Heading,
} as ComponentMeta<typeof Heading>;

const Template: ComponentStory<typeof Heading> = (args) => <Heading {...args} />;

export const Primary = Template.bind({});
Primary.args = {
size: "md",
children:
"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.",
};
37 changes: 37 additions & 0 deletions airbyte-webapp/src/components/ui/Heading/Heading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
import classNames from "classnames";
import React from "react";

import styles from "./heading.module.scss";

type HeadingSize = "sm" | "md" | "lg" | "xl";
type HeadingElementType = "h1" | "h2" | "h3" | "h4" | "h5" | "h6";

interface HeadingProps {
className?: string;
centered?: boolean;
as: HeadingElementType;
size?: HeadingSize;
}

const getHeadingClassNames = ({ size, centered }: Required<Pick<HeadingProps, "size" | "centered">>) => {
const sizes: Record<HeadingSize, string> = {
sm: styles.sm,
md: styles.md,
lg: styles.lg,
xl: styles.xl,
};

return classNames(styles.heading, sizes[size], centered && styles.centered);
};

export const Heading: React.FC<React.PropsWithChildren<HeadingProps>> = React.memo(
({ as, centered = false, children, className: classNameProp, size = "md", ...remainingProps }) => {
const className = classNames(getHeadingClassNames({ centered, size }), classNameProp);

return React.createElement(as, {
...remainingProps,
className,
children,
});
}
);
1 change: 1 addition & 0 deletions airbyte-webapp/src/components/ui/Heading/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { Heading } from "./Heading";
12 changes: 5 additions & 7 deletions airbyte-webapp/src/components/ui/PageHeader/PageHeader.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import classNames from "classnames";
import React from "react";

import { Text } from "components/ui/Text";
import { Heading } from "components/ui/Heading";

import styles from "./PageHeader.module.scss";

Expand All @@ -21,25 +21,23 @@ export const PageHeader: React.FC<PageHeaderProps> = ({
endComponent,
}) => (
<div className={classNames(styles.container)} data-withline={withLine}>
<Text
<Heading
as="h1"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
as="h1"

Super nit: don't need it anymore 😊

size="md"
className={classNames(styles.start, {
[styles.withLine]: withLine,
})}
>
{title}
</Text>
</Heading>
{middleTitleBlock ? (
<Text
<Heading
as="h3"
size="md"
className={classNames(styles.heading, {
[styles.middle]: middleTitleBlock,
})}
>
{middleTitleBlock}
</Text>
</Heading>
) : (
<div className={classNames(styles.middle)}>{middleComponent}</div>
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@ import classNames from "classnames";
import React from "react";
import { ReflexContainer, ReflexElement, ReflexSplitter } from "react-reflex";

import { Text } from "../Text";
import { Heading } from "components/ui/Heading";

import styles from "./ResizablePanels.module.scss";

interface ResizablePanelsProps {
Expand Down Expand Up @@ -49,14 +50,14 @@ const PanelContainer: React.FC<React.PropsWithChildren<PanelContainerProps>> = (
<div className={classNames(className, styles.panelContainer)}>
{overlay && width <= overlay.displayThreshold && (
<div className={styles.lightOverlay}>
<Text
<Heading
as="h2"
className={classNames(styles.rotatedHeader, {
[styles.counterClockwise]: overlay?.rotation === "counter-clockwise",
})}
>
{overlay.header}
</Text>
</Heading>
</div>
)}
{children}
Expand Down
72 changes: 24 additions & 48 deletions airbyte-webapp/src/components/ui/Text/Text.tsx
Original file line number Diff line number Diff line change
@@ -1,69 +1,45 @@
import classNames from "classnames";
import React from "react";

import headingStyles from "./heading.module.scss";
import textStyles from "./text.module.scss";
import styles from "./text.module.scss";

type TextSize = "sm" | "md" | "lg";
type HeadingSize = TextSize | "xl";
type TextElementType = "p" | "span" | "div";
type HeadingElementType = "h1" | "h2" | "h3" | "h4" | "h5" | "h6";

interface BaseProps {
interface TextProps {
className?: string;
centered?: boolean;
}

interface TextProps extends BaseProps {
as?: TextElementType;
size?: TextSize;
bold?: boolean;
}

interface HeadingProps extends BaseProps {
as: HeadingElementType;
size?: HeadingSize;
}

const getTextClassNames = ({ size, centered, bold }: Required<Pick<TextProps, "size" | "centered" | "bold">>) => {
const sizes: Record<TextSize, string> = {
sm: textStyles.sm,
md: textStyles.md,
lg: textStyles.lg,
};

return classNames(textStyles.text, sizes[size], centered && textStyles.centered, bold && textStyles.bold);
};

const getHeadingClassNames = ({ size, centered }: Required<Pick<HeadingProps, "size" | "centered">>) => {
const sizes: Record<HeadingSize, string> = {
sm: headingStyles.sm,
md: headingStyles.md,
lg: headingStyles.lg,
xl: headingStyles.xl,
sm: styles.sm,
md: styles.md,
lg: styles.lg,
};

return classNames(headingStyles.heading, sizes[size], centered && headingStyles.centered);
};

const isHeadingType = (props: TextProps | HeadingProps): props is HeadingProps => {
return props.as ? /^h[0-6]$/.test(props.as) : false;
return classNames(styles.text, sizes[size], centered && styles.centered, bold && styles.bold);
};

export const Text: React.FC<React.PropsWithChildren<TextProps | HeadingProps>> = React.memo((props) => {
const isHeading = isHeadingType(props);
const { as = "p", centered = false, children, className: classNameProp, ...remainingProps } = props;

const className = classNames(
isHeading
? getHeadingClassNames({ centered, size: props.size ?? "md" })
: getTextClassNames({ centered, size: props.size ?? "md", bold: props.bold ?? false }),
classNameProp
);

return React.createElement(as, {
...remainingProps,
className,
export const Text: React.FC<React.PropsWithChildren<TextProps>> = React.memo(
({
as = "p",
bold = false,
centered = false,
children,
});
});
className: classNameProp,
size = "md",
...remainingProps
}) => {
const className = classNames(getTextClassNames({ centered, size, bold }), classNameProp);

return React.createElement(as, {
...remainingProps,
className,
children,
});
}
);
2 changes: 1 addition & 1 deletion airbyte-webapp/src/components/ui/Text/text.module.scss
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
@use "../../../scss/colors";
@use "scss/colors";

.text {
color: colors.$dark-blue;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import React from "react";
import { FormattedMessage } from "react-intl";

import HeadTitle from "components/HeadTitle";
import { Text } from "components/ui/Text";
import { Heading } from "components/ui/Heading";

import { PageTrackingCodes, useTrackPage } from "hooks/services/Analytics";

Expand All @@ -20,7 +20,7 @@ const SignupPage: React.FC<SignupPageProps> = ({ highlightStyle }) => {
return (
<div>
<HeadTitle titles={[{ id: "login.signup" }]} />
<Text as="h1" size="xl" className={styles.title}>
<Heading as="h1" size="xl" className={styles.title}>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
<Heading as="h1" size="xl" className={styles.title}>
<Heading size="xl" className={styles.title}>

<FormattedMessage
id="login.activateAccess"
values={{
Expand All @@ -31,7 +31,7 @@ const SignupPage: React.FC<SignupPageProps> = ({ highlightStyle }) => {
),
}}
/>
</Text>
</Heading>
<SpecialBlock />
<SignupForm />
<OAuthLogin isSignUpPage />
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import React from "react";

import { Text } from "components/ui/Text";
import { Heading } from "components/ui/Heading";

import styles from "./FormTitle.module.scss";

export const FormTitle: React.FC<React.PropsWithChildren<unknown>> = ({ children }) => (
<Text as="h1" size="xl" className={styles.title}>
<Heading as="h1" size="xl" className={styles.title}>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
<Heading as="h1" size="xl" className={styles.title}>
<Heading size="xl" className={styles.title}>

{children}
</Text>
</Heading>
);
Loading