diff --git a/ui/app/components/ui/typography/index.js b/ui/app/components/ui/typography/index.js
new file mode 100644
index 000000000..648ce1725
--- /dev/null
+++ b/ui/app/components/ui/typography/index.js
@@ -0,0 +1 @@
+export { default } from './typography'
diff --git a/ui/app/components/ui/typography/typography.js b/ui/app/components/ui/typography/typography.js
new file mode 100644
index 000000000..93990b00b
--- /dev/null
+++ b/ui/app/components/ui/typography/typography.js
@@ -0,0 +1,58 @@
+import React from 'react'
+import classnames from 'classnames'
+import PropTypes from 'prop-types'
+import { COLORS, TYPOGRAPHY } from '../../../helpers/constants/design-system'
+
+const { H6, H7, H8, H9 } = TYPOGRAPHY
+
+export default function Typography({
+ variant = TYPOGRAPHY.Paragraph,
+ className,
+ color = COLORS.BLACK,
+ tag,
+ children,
+ spacing = 1,
+ fontWeight = 'normal',
+ align,
+}) {
+ const computedClassName = classnames(
+ 'typography',
+ className,
+ `typography--${variant}`,
+ `typography--align-${align}`,
+ `typography--spacing-${spacing}`,
+ `typography--color-${color}`,
+ `typography--weight-${fontWeight}`,
+ )
+
+ let Tag = tag ?? variant
+
+ if (Tag === TYPOGRAPHY.Paragraph) {
+ Tag = 'p'
+ } else if ([H7, H8, H9].includes(Tag)) {
+ Tag = H6
+ }
+
+ return {children}
+}
+
+Typography.propTypes = {
+ variant: PropTypes.oneOf(Object.values(TYPOGRAPHY)),
+ children: PropTypes.node.isRequired,
+ color: PropTypes.oneOf(Object.values(COLORS)),
+ className: PropTypes.string,
+ align: PropTypes.oneOf(['center', 'right']),
+ spacing: PropTypes.oneOf([1, 2, 3, 4, 5, 6, 7, 8]),
+ fontWeight: PropTypes.oneOf(['bold', 'normal']),
+ tag: PropTypes.oneOf([
+ 'p',
+ 'h1',
+ 'h2',
+ 'h3',
+ 'h4',
+ 'h5',
+ 'h6',
+ 'span',
+ 'div',
+ ]),
+}
diff --git a/ui/app/components/ui/typography/typography.scss b/ui/app/components/ui/typography/typography.scss
new file mode 100644
index 000000000..e377f31d2
--- /dev/null
+++ b/ui/app/components/ui/typography/typography.scss
@@ -0,0 +1,38 @@
+@use "design-system";
+@use "sass:map";
+
+.typography {
+ @include design-system.Paragraph;
+
+ @each $variant in map.keys(design-system.$typography-variants) {
+ &--#{$variant} {
+ @include design-system.typography($variant);
+ }
+ }
+
+ @each $variant, $color in design-system.$color-map {
+ &--color-#{$variant} {
+ color: $color;
+ }
+ }
+
+ @each $variant, $weight in design-system.$typography-font-weights {
+ &--weight-#{$variant} {
+ font-weight: $weight;
+ }
+ }
+
+ &--align-center {
+ text-align: center;
+ }
+
+ &--align-right {
+ text-align: right;
+ }
+
+ @for $i from 1 through 8 {
+ &--spacing-#{$i} {
+ margin: #{$i * 4}px auto;
+ }
+ }
+}
diff --git a/ui/app/components/ui/typography/typography.stories.js b/ui/app/components/ui/typography/typography.stories.js
new file mode 100644
index 000000000..68d567e35
--- /dev/null
+++ b/ui/app/components/ui/typography/typography.stories.js
@@ -0,0 +1,53 @@
+import React from 'react'
+import { number, select, text } from '@storybook/addon-knobs'
+import { COLORS, TYPOGRAPHY } from '../../../helpers/constants/design-system'
+import Typography from '.'
+
+export default {
+ title: 'Typography',
+}
+
+const fontWeightOptions = {
+ bold: 'bold',
+ normal: 'normal',
+}
+
+const alignOptions = {
+ left: undefined,
+ center: 'center',
+ right: 'right',
+}
+
+export const list = () => (
+
+ {Object.values(TYPOGRAPHY).map((variant) => (
+
+
+ {variant}
+
+
+ ))}
+
+)
+
+export const TheQuickOrangeFox = () => (
+
+
+
+ {text('content', 'The quick orange fox jumped over the lazy dog.')}
+
+
+
+)
diff --git a/ui/app/components/ui/ui-components.scss b/ui/app/components/ui/ui-components.scss
index 2c7c1163b..3d5e5446c 100644
--- a/ui/app/components/ui/ui-components.scss
+++ b/ui/app/components/ui/ui-components.scss
@@ -37,5 +37,6 @@
@import 'toggle-button/index';
@import 'token-balance/index';
@import 'tooltip/index';
+@import 'typography/typography';
@import 'unit-input/index';
@import 'url-icon/index';