documentation-site/components/markdown-elements.jsx (168 lines of code) (raw):
/*
Copyright (c) Uber Technologies, Inc.
This source code is licensed under the MIT license found in the
LICENSE file in the root directory of this source tree.
*/
//
/* eslint-disable jsx-a11y/anchor-is-valid */
/* global process */
import * as React from "react";
import Head from "next/head";
import Img from "next/legacy/image";
import { Block } from "baseui/block";
import { StyledLink } from "baseui/link";
import Code from "./code";
import { themedStyled } from "../pages/_app";
import Link from "next/link";
import Anchor from "./anchor";
import slugify from "../helpers/slugify";
import { useHover } from "./hooks";
const getText = (children) => {
let label = "";
React.Children.forEach(children, (child) => {
if (typeof child === "string") {
label += child;
}
if (child.props && child.props.children) {
label += getText(child.props.children);
}
});
return label;
};
export const cleanAnchor = (anchor) => slugify(getText(anchor));
export const Heading = ({ element, fontType, children }) => {
const [hoverRef, isHovered] = useHover();
const slug = cleanAnchor(children);
return (
<Block
as={element}
marginBottom="8px"
font={fontType}
ref={hoverRef}
id={slug}
color="contentPrimary"
>
<React.Fragment>
{children}{" "}
<Anchor isVisible={isHovered} slug={slug} element={element} />
</React.Fragment>
</Block>
);
};
export const ListItem = (props) => (
<Block as="li" font="font300">
{props.children}
</Block>
);
export const Paragraph = (props) => (
<Block as="p" font="font300">
{props.children}
</Block>
);
export const UnorderedList = (props) => <ul>{props.children}</ul>;
export const InlineCode = themedStyled("code", ({ $theme }) => {
return {
...$theme.typography.MonoParagraphMedium,
backgroundColor: "rgba(27, 31, 35, 0.05)",
borderTopLeftRadius: "3px",
borderTopRightRadius: "3px",
borderBottomRightRadius: "3px",
borderBottomLeftRadius: "3px",
fontSize: "85%",
marginLeft: 0,
marginRight: 0,
marginTop: 0,
marginBottom: 0,
padding: "0.2em 0.4em",
};
});
const Blockquote = themedStyled("blockquote", {
backgroundColor: "rgba(27, 31, 35, 0.03)",
borderTopLeftRadius: "3px",
borderTopRightRadius: "3px",
borderBottomRightRadius: "3px",
borderBottomLeftRadius: "3px",
marginLeft: 0,
marginRight: 0,
marginTop: 0,
marginBottom: 0,
padding: "1em 3em",
});
export const DocLink = ({ children, href }) => {
const parts = href.split("#");
const internal =
(parts[0] === "" && parts[1] !== "") || !href.includes("http");
if (internal) {
return (
<Link href={href} legacyBehavior>
<StyledLink href={href}>{children}</StyledLink>
</Link>
);
}
return (
<StyledLink href={href} target="_blank">
{children}
</StyledLink>
);
};
export const H1 = ({ children }) => (
<React.Fragment>
<Head>
<title key="title">
{process.env.NODE_ENV !== "production" ? "[DEV] " : ""}
Base Web - {children}
</title>
</Head>
<Heading element="h1" fontType="font750">
{children}
</Heading>
</React.Fragment>
);
export const H2 = ({ children }) => (
<Heading element="h2" fontType="font650" marginTop="scale1000">
{children}
</Heading>
);
export const H3 = ({ children }) => (
<Heading element="h3" fontType="font550">
{children}
</Heading>
);
export const H4 = ({ children }) => (
<Heading element="h4" fontType="font400">
{children}
</Heading>
);
export const H5 = ({ children }) => (
<Heading element="h5" fontType="font350">
{children}
</Heading>
);
export const H6 = ({ children }) => (
<Heading element="h6" fontType="font250">
{children}
</Heading>
);
export const Image = ({ alt, src, height, width }) => {
if (height || width) {
return <Img src={src} alt={alt} height={height} width={width} />;
} else {
return <Img src={src} alt={alt} layout="fill" />;
}
};
export default {
pre: Code,
h1: H1,
h2: H2,
h3: H3,
h4: H4,
h5: H5,
h6: H6,
img: Image,
li: ListItem,
p: Paragraph,
ul: UnorderedList,
code: InlineCode,
blockquote: ({ children }) => <Blockquote>{children}</Blockquote>,
a: DocLink,
};