mirror of
https://github.com/coder/coder.git
synced 2026-09-22 05:05:20 +08:00
feat: migrate <*Tooltip /> components (#21997)
This pull-request migrates the MUI classes and imports out of `<InfoTooltip />` and `<HelpTooltip />` components.
This commit is contained in:
@@ -1,11 +1,3 @@
|
||||
import {
|
||||
type CSSObject,
|
||||
css,
|
||||
type Interpolation,
|
||||
type Theme,
|
||||
} from "@emotion/react";
|
||||
import Link from "@mui/material/Link";
|
||||
import { Stack } from "components/Stack/Stack";
|
||||
import {
|
||||
Tooltip,
|
||||
TooltipContent,
|
||||
@@ -66,40 +58,23 @@ export const HelpTooltipIconTrigger = forwardRef<
|
||||
size = "medium",
|
||||
children = <HelpTooltipIcon />,
|
||||
hoverEffect = true,
|
||||
className,
|
||||
...buttonProps
|
||||
} = props;
|
||||
|
||||
const hoverEffectStyles = css({
|
||||
opacity: 0.5,
|
||||
"&:hover": {
|
||||
opacity: 0.75,
|
||||
},
|
||||
});
|
||||
|
||||
return (
|
||||
<HelpTooltipTrigger asChild>
|
||||
<button
|
||||
{...buttonProps}
|
||||
aria-label="More info"
|
||||
ref={ref}
|
||||
css={[
|
||||
css`
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 4px 0;
|
||||
border: 0;
|
||||
background: transparent;
|
||||
cursor: pointer;
|
||||
color: inherit;
|
||||
|
||||
& svg {
|
||||
width: ${getIconSpacingFromSize(size)}px;
|
||||
height: ${getIconSpacingFromSize(size)}px;
|
||||
}
|
||||
`,
|
||||
hoverEffect ? hoverEffectStyles : null,
|
||||
]}
|
||||
className={cn(
|
||||
"flex items-center justify-center px-0 py-1",
|
||||
"border-0 border-none bg-transparent cursor-pointer text-inherit",
|
||||
size === "small" ? "[&_svg]:size-3" : "[&_svg]:size-4",
|
||||
hoverEffect && "opacity-50 hover:opacity-75",
|
||||
className,
|
||||
)}
|
||||
>
|
||||
{children}
|
||||
</button>
|
||||
@@ -109,10 +84,17 @@ export const HelpTooltipIconTrigger = forwardRef<
|
||||
|
||||
export const HelpTooltipTitle: FC<HTMLAttributes<HTMLHeadingElement>> = ({
|
||||
children,
|
||||
className,
|
||||
...attrs
|
||||
}) => {
|
||||
return (
|
||||
<h4 css={styles.title} {...attrs}>
|
||||
<h4
|
||||
className={cn(
|
||||
"mt-0 mb-2 text-content-primary text-sm leading-[150%] font-semibold",
|
||||
className,
|
||||
)}
|
||||
{...attrs}
|
||||
>
|
||||
{children}
|
||||
</h4>
|
||||
);
|
||||
@@ -120,10 +102,17 @@ export const HelpTooltipTitle: FC<HTMLAttributes<HTMLHeadingElement>> = ({
|
||||
|
||||
export const HelpTooltipText: FC<HTMLAttributes<HTMLParagraphElement>> = ({
|
||||
children,
|
||||
className,
|
||||
...attrs
|
||||
}) => {
|
||||
return (
|
||||
<p css={styles.text} {...attrs}>
|
||||
<p
|
||||
className={cn(
|
||||
"my-1 text-sm text-content-secondary leading-normal",
|
||||
className,
|
||||
)}
|
||||
{...attrs}
|
||||
>
|
||||
{children}
|
||||
</p>
|
||||
);
|
||||
@@ -136,10 +125,15 @@ interface HelpTooltipLink {
|
||||
|
||||
export const HelpTooltipLink: FC<HelpTooltipLink> = ({ children, href }) => {
|
||||
return (
|
||||
<Link href={href} target="_blank" rel="noreferrer" css={styles.link}>
|
||||
<ExternalLinkIcon className="size-icon-xs" css={styles.linkIcon} />
|
||||
<a
|
||||
href={href}
|
||||
target="_blank"
|
||||
rel="noreferrer"
|
||||
className="flex items-center text-sm text-content-link no-underline hover:underline"
|
||||
>
|
||||
<ExternalLinkIcon className="size-3.5 mr-2" />
|
||||
{children}
|
||||
</Link>
|
||||
</a>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -160,81 +154,15 @@ export const HelpTooltipAction: FC<HelpTooltipActionProps> = ({
|
||||
<button
|
||||
type="button"
|
||||
aria-label={ariaLabel ?? ""}
|
||||
css={styles.action}
|
||||
className="flex items-center bg-transparent border-0 border-none text-content-link p-0 cursor-pointer text-sm"
|
||||
onClick={onClick}
|
||||
>
|
||||
<Icon css={styles.actionIcon} />
|
||||
<Icon className="size-3.5 mr-2" />
|
||||
{children}
|
||||
</button>
|
||||
);
|
||||
};
|
||||
|
||||
export const HelpTooltipLinksGroup: FC<PropsWithChildren> = ({ children }) => {
|
||||
return (
|
||||
<Stack spacing={1} css={styles.linksGroup}>
|
||||
{children}
|
||||
</Stack>
|
||||
);
|
||||
return <div className="flex flex-col gap-2 mt-4">{children}</div>;
|
||||
};
|
||||
|
||||
const getIconSpacingFromSize = (size?: Size): number => {
|
||||
switch (size) {
|
||||
case "small":
|
||||
return 12;
|
||||
default:
|
||||
return 16;
|
||||
}
|
||||
};
|
||||
|
||||
const styles = {
|
||||
title: (theme) => ({
|
||||
marginTop: 0,
|
||||
marginBottom: 8,
|
||||
color: theme.palette.text.primary,
|
||||
fontSize: 14,
|
||||
lineHeight: "150%",
|
||||
fontWeight: 600,
|
||||
}),
|
||||
|
||||
text: (theme) => ({
|
||||
marginTop: 4,
|
||||
marginBottom: 4,
|
||||
...(theme.typography.body2 as CSSObject),
|
||||
}),
|
||||
|
||||
link: (theme) => ({
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
...(theme.typography.body2 as CSSObject),
|
||||
color: theme.roles.active.fill.outline,
|
||||
}),
|
||||
|
||||
linkIcon: {
|
||||
color: "inherit",
|
||||
width: 14,
|
||||
height: 14,
|
||||
marginRight: 8,
|
||||
},
|
||||
|
||||
linksGroup: {
|
||||
marginTop: 16,
|
||||
},
|
||||
|
||||
action: (theme) => ({
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
background: "none",
|
||||
border: 0,
|
||||
color: theme.palette.primary.light,
|
||||
padding: 0,
|
||||
cursor: "pointer",
|
||||
fontSize: 14,
|
||||
}),
|
||||
|
||||
actionIcon: {
|
||||
color: "inherit",
|
||||
width: 14,
|
||||
height: 14,
|
||||
marginRight: 8,
|
||||
},
|
||||
} satisfies Record<string, Interpolation<Theme>>;
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import { css, type Interpolation, type Theme, useTheme } from "@emotion/react";
|
||||
import {
|
||||
HelpTooltip,
|
||||
HelpTooltipContent,
|
||||
@@ -9,6 +8,7 @@ import {
|
||||
} from "components/HelpTooltip/HelpTooltip";
|
||||
import type { FC, ReactNode } from "react";
|
||||
import type { ThemeRole } from "theme/roles";
|
||||
import { cn } from "utils/cn";
|
||||
|
||||
interface InfoTooltipProps {
|
||||
type?: ThemeRole;
|
||||
@@ -16,18 +16,27 @@ interface InfoTooltipProps {
|
||||
message: ReactNode;
|
||||
}
|
||||
|
||||
const tooltipColorClasses: Record<ThemeRole, string> = {
|
||||
info: "text-content-secondary",
|
||||
error: "text-content-destructive",
|
||||
warning: "text-content-warning",
|
||||
notice: "text-content-link",
|
||||
success: "text-content-success",
|
||||
danger: "text-content-destructive",
|
||||
active: "text-content-link",
|
||||
inactive: "text-highlight-grey",
|
||||
preview: "text-highlight-purple",
|
||||
};
|
||||
|
||||
export const InfoTooltip: FC<InfoTooltipProps> = ({
|
||||
title,
|
||||
message,
|
||||
type = "info",
|
||||
}) => {
|
||||
const theme = useTheme();
|
||||
const iconColor = theme.roles[type].outline;
|
||||
|
||||
return (
|
||||
<HelpTooltip>
|
||||
<HelpTooltipIconTrigger size="small" css={styles.button}>
|
||||
<HelpTooltipIcon css={{ color: iconColor }} />
|
||||
<HelpTooltipIconTrigger size="small" hoverEffect={false}>
|
||||
<HelpTooltipIcon className={cn(tooltipColorClasses[type])} />
|
||||
</HelpTooltipIconTrigger>
|
||||
<HelpTooltipContent>
|
||||
<HelpTooltipTitle>{title}</HelpTooltipTitle>
|
||||
@@ -36,13 +45,3 @@ export const InfoTooltip: FC<InfoTooltipProps> = ({
|
||||
</HelpTooltip>
|
||||
);
|
||||
};
|
||||
|
||||
const styles = {
|
||||
button: css`
|
||||
opacity: 1;
|
||||
|
||||
&:hover {
|
||||
opacity: 1;
|
||||
}
|
||||
`,
|
||||
} satisfies Record<string, Interpolation<Theme>>;
|
||||
|
||||
Reference in New Issue
Block a user