diff --git a/packages/grafana-data/src/themes/createComponents.ts b/packages/grafana-data/src/themes/createComponents.ts index 40e1b19a11f..b44edd5448d 100644 --- a/packages/grafana-data/src/themes/createComponents.ts +++ b/packages/grafana-data/src/themes/createComponents.ts @@ -15,6 +15,10 @@ export interface ThemeComponents { borderHover: string; text: string; }; + tooltip: { + text: string; + background: string; + }; panel: { padding: number; headerHeight: number; @@ -58,6 +62,10 @@ export function createComponents(palette: ThemePalette, shadows: ThemeShadows): text: palette.text.primary, }, panel, + tooltip: { + background: palette.background.secondary, + text: palette.text.primary, + }, dashboard: { background: palette.background.canvas, padding: 1, diff --git a/packages/grafana-data/src/themes/createTheme.ts b/packages/grafana-data/src/themes/createTheme.ts index 2d48580a010..1602d8d9c0c 100644 --- a/packages/grafana-data/src/themes/createTheme.ts +++ b/packages/grafana-data/src/themes/createTheme.ts @@ -1,28 +1,14 @@ -import { createBreakpoints, ThemeBreakpoints } from './breakpoints'; -import { ThemeComponents, createComponents } from './createComponents'; -import { createPalette, ThemePalette, ThemePaletteInput } from './createPalette'; -import { createShadows, ThemeShadows } from './createShadows'; -import { createShape, ThemeShape, ThemeShapeInput } from './createShape'; -import { createSpacing, ThemeSpacingOptions, ThemeSpacing } from './createSpacing'; -import { createTransitions, ThemeTransitions } from './createTransitions'; -import { createTypography, ThemeTypography, ThemeTypographyInput } from './createTypography'; -import { ThemeZIndices, zIndex } from './zIndex'; - -/** @beta */ -export interface GrafanaThemeV2 { - name: string; - isDark: boolean; - isLight: boolean; - palette: ThemePalette; - breakpoints: ThemeBreakpoints; - spacing: ThemeSpacing; - shape: ThemeShape; - components: ThemeComponents; - typography: ThemeTypography; - zIndex: ThemeZIndices; - shadows: ThemeShadows; - transitions: ThemeTransitions; -} +import { createBreakpoints } from './breakpoints'; +import { createComponents } from './createComponents'; +import { createPalette, ThemePaletteInput } from './createPalette'; +import { createShadows } from './createShadows'; +import { createShape, ThemeShapeInput } from './createShape'; +import { createSpacing, ThemeSpacingOptions } from './createSpacing'; +import { createTransitions } from './createTransitions'; +import { createTypography, ThemeTypographyInput } from './createTypography'; +import { createV1Theme } from './createV1Theme'; +import { GrafanaThemeV2 } from './types'; +import { zIndex } from './zIndex'; /** @internal */ export interface NewThemeOptions { @@ -52,7 +38,7 @@ export function createTheme(options: NewThemeOptions = {}): GrafanaThemeV2 { const transitions = createTransitions(); const components = createComponents(palette, shadows); - return { + const theme = { name, isDark: palette.mode === 'dark', isLight: palette.mode === 'light', @@ -68,4 +54,9 @@ export function createTheme(options: NewThemeOptions = {}): GrafanaThemeV2 { ...zIndex, }, }; + + return { + ...theme, + v1: createV1Theme(theme), + }; } diff --git a/packages/grafana-data/src/themes/createV1Theme.ts b/packages/grafana-data/src/themes/createV1Theme.ts new file mode 100644 index 00000000000..1ca27cc1bcd --- /dev/null +++ b/packages/grafana-data/src/themes/createV1Theme.ts @@ -0,0 +1,267 @@ +import { GrafanaTheme, GrafanaThemeCommons, GrafanaThemeType } from '../types'; +import { GrafanaThemeV2 } from './types'; + +export function createV1Theme(theme: Omit): GrafanaTheme { + const oldCommon: GrafanaThemeCommons = { + name: 'Grafana Default', + typography: { + fontFamily: { + sansSerif: theme.typography.fontFamily, + monospace: theme.typography.fontFamilyMonospace, + }, + size: { + base: `${theme.typography.fontSize}px`, + xs: theme.typography.size.xs, + sm: theme.typography.size.sm, + md: theme.typography.size.md, + lg: theme.typography.size.lg, + }, + heading: { + h1: theme.typography.h1.fontSize, + h2: theme.typography.h2.fontSize, + h3: theme.typography.h3.fontSize, + h4: theme.typography.h4.fontSize, + h5: theme.typography.h5.fontSize, + h6: theme.typography.h6.fontSize, + }, + weight: { + light: theme.typography.fontWeightLight, + regular: theme.typography.fontWeightRegular, + semibold: theme.typography.fontWeightMedium, + bold: theme.typography.fontWeightBold, + }, + lineHeight: { + xs: theme.typography.bodySmall.lineHeight, + sm: theme.typography.bodySmall.lineHeight, + md: theme.typography.body.lineHeight, + lg: theme.typography.h2.lineHeight, + }, + link: { + decoration: 'none', + hoverDecoration: 'none', + }, + }, + breakpoints: { + xs: `${theme.breakpoints.values.xs}px`, + sm: `${theme.breakpoints.values.sm}px`, + md: `${theme.breakpoints.values.md}px`, + lg: `${theme.breakpoints.values.lg}px`, + xl: `${theme.breakpoints.values.xl}px`, + xxl: `${theme.breakpoints.values.xxl}px`, + }, + spacing: { + base: theme.spacing.gridSize, + insetSquishMd: theme.spacing(0.5, 1), + d: theme.spacing(2), + xxs: theme.spacing(0.25), + xs: theme.spacing(0.5), + sm: theme.spacing(1), + md: theme.spacing(2), + lg: theme.spacing(3), + xl: theme.spacing(4), + gutter: theme.spacing(4), + + // Next-gen forms spacing variables + // TODO: Move variables definition to respective components when implementing + formSpacingBase: theme.spacing.gridSize, + formMargin: `${theme.spacing.gridSize * 4}px`, + formFieldsetMargin: `${theme.spacing.gridSize * 2}px`, + formInputHeight: theme.spacing.gridSize * 4, + formButtonHeight: theme.spacing.gridSize * 4, + formInputPaddingHorizontal: `${theme.spacing.gridSize}px`, + + // Used for icons do define spacing between icon and input field + // Applied on the right(prefix) or left(suffix) + formInputAffixPaddingHorizontal: `${theme.spacing.gridSize / 2}px`, + + formInputMargin: `${theme.spacing.gridSize * 2}px`, + formLabelPadding: '0 0 0 2px', + formLabelMargin: `0 0 ${theme.spacing.gridSize / 2 + 'px'} 0`, + formValidationMessagePadding: '4px 8px', + formValidationMessageMargin: '4px 0 0 0', + inlineFormMargin: '4px', + }, + border: { + radius: { + sm: theme.shape.borderRadius(1), + md: theme.shape.borderRadius(2), + lg: theme.shape.borderRadius(3), + }, + width: { + sm: '1px', + }, + }, + height: { + sm: theme.spacing.gridSize * theme.components.height.sm, + md: theme.spacing.gridSize * theme.components.height.md, + lg: theme.spacing.gridSize * theme.components.height.lg, + }, + panelPadding: theme.components.panel.padding * theme.spacing.gridSize, + panelHeaderHeight: theme.spacing.gridSize * theme.components.panel.headerHeight, + zIndex: { + navbarFixed: theme.zIndex.navbarFixed, + sidemenu: theme.zIndex.sidemenu, + dropdown: theme.zIndex.dropdown, + typeahead: theme.zIndex.typeahead, + tooltip: theme.zIndex.tooltip, + modalBackdrop: theme.zIndex.modalBackdrop, + modal: theme.zIndex.modal, + }, + }; + + const basicColors = { + ...commonColorsPalette, + black: '#000000', + white: '#ffffff', + dark1: '#141414', + dark2: '#161719', + dark3: '#1f1f20', + dark4: '#212124', + dark5: '#222426', + dark6: '#262628', + dark7: '#292a2d', + dark8: '#2f2f32', + dark9: '#343436', + dark10: '#424345', + gray1: '#555555', + gray2: '#8e8e8e', + gray3: '#b3b3b3', + gray4: '#d8d9da', + gray5: '#ececec', + gray6: '#f4f5f8', // not used in dark theme + gray7: '#fbfbfb', // not used in dark theme + redBase: '#e02f44', + redShade: '#c4162a', + greenBase: '#299c46', + greenShade: '#23843b', + red: '#d44a3a', + yellow: '#ecbb13', + purple: '#9933cc', + variable: '#32d1df', + orange: '#eb7b18', + orangeDark: '#ff780a', + }; + + const backgrounds = { + bg1: theme.palette.background.primary, + bg2: theme.palette.background.secondary, + bg3: theme.palette.action.hover, + dashboardBg: theme.palette.background.canvas, + bgBlue1: theme.palette.primary.main, + bgBlue2: theme.palette.primary.shade, + }; + + const borders = { + border1: theme.palette.border.weak, + border2: theme.palette.border.medium, + border3: theme.palette.border.strong, + }; + + const textColors = { + textStrong: theme.palette.text.maxContrast, + textHeading: theme.palette.text.primary, + text: theme.palette.text.primary, + textSemiWeak: theme.palette.text.secondary, + textWeak: theme.palette.text.secondary, + textFaint: theme.palette.text.disabled, + textBlue: theme.palette.primary.text, + }; + + const form = { + // Next-gen forms functional colors + formLabel: theme.palette.text.primary, + formDescription: theme.palette.text.secondary, + formInputBg: basicColors.gray05, + formInputBgDisabled: basicColors.gray10, + formInputBorder: borders.border2, + formInputBorderHover: basicColors.gray33, + formInputBorderActive: basicColors.blue95, + formInputBorderInvalid: basicColors.red88, + formInputPlaceholderText: textColors.textFaint, + formInputText: basicColors.gray85, + formInputDisabledText: basicColors.gray70, + formFocusOutline: basicColors.blue77, + formValidationMessageText: basicColors.white, + formValidationMessageBg: basicColors.red88, + formSwitchBg: basicColors.gray25, + formSwitchBgActive: basicColors.blue95, + formSwitchBgHover: basicColors.gray33, + formSwitchBgActiveHover: basicColors.blue80, + formSwitchBgDisabled: basicColors.gray25, + formSwitchDot: basicColors.gray15, + formCheckboxBgChecked: basicColors.blue95, + formCheckboxBgCheckedHover: basicColors.blue80, + formCheckboxCheckmark: basicColors.gray25, + }; + + return { + ...oldCommon, + type: theme.palette.mode === 'dark' ? GrafanaThemeType.Dark : GrafanaThemeType.Light, + isDark: theme.isDark, + isLight: theme.isLight, + name: theme.name, + palette: { + ...basicColors, + brandPrimary: basicColors.orange, + brandSuccess: basicColors.greenBase, + brandWarning: basicColors.orange, + brandDanger: basicColors.redBase, + queryRed: basicColors.redBase, + queryGreen: '#74e680', + queryPurple: '#fe85fc', + queryOrange: basicColors.orange, + online: basicColors.greenBase, + warn: '#f79520', + critical: basicColors.redBase, + }, + colors: { + ...backgrounds, + ...borders, + ...form, + ...textColors, + + bodyBg: theme.palette.background.canvas, + panelBg: theme.components.panel.background, + panelBorder: theme.components.panel.border, + pageHeaderBg: theme.palette.background.canvas, + pageHeaderBorder: theme.palette.background.canvas, + + dropdownBg: form.formInputBg, + dropdownShadow: basicColors.black, + dropdownOptionHoverBg: backgrounds.bg2, + + link: theme.palette.text.primary, + linkDisabled: theme.palette.text.disabled, + linkHover: theme.palette.text.maxContrast, + linkExternal: theme.palette.text.link, + }, + shadows: { + listItem: 'none', + }, + }; +} + +const commonColorsPalette = { + // New greys palette used by next-gen form elements + gray98: '#f7f8fa', + gray97: '#f1f5f9', + gray95: '#e9edf2', + gray90: '#dce1e6', + gray85: '#c7d0d9', + gray70: '#9fa7b3', + gray60: '#7b8087', + gray33: '#464c54', + gray25: '#2c3235', + gray15: '#202226', + gray10: '#141619', + gray05: '#0b0c0e', + + // New blues palette used by next-gen form elements + blue95: '#5794f2', // blue95 + blue85: '#33a2e5', // blueText + blue80: '#3274d9', // blue80 + blue77: '#1f60c4', // blue77 + + // New reds palette used by next-gen form elements + red88: '#e02f44', +}; diff --git a/packages/grafana-data/src/themes/index.ts b/packages/grafana-data/src/themes/index.ts index ab2106cf7d8..299787515b1 100644 --- a/packages/grafana-data/src/themes/index.ts +++ b/packages/grafana-data/src/themes/index.ts @@ -1,5 +1,5 @@ -export { createTheme, GrafanaThemeV2 } from './createTheme'; -export { ThemePaletteColor } from './types'; +export { createTheme } from './createTheme'; +export { ThemePaletteColor, GrafanaThemeV2 } from './types'; export { ThemePalette } from './createPalette'; export { ThemeBreakpoints } from './breakpoints'; export { ThemeShadows } from './createShadows'; diff --git a/packages/grafana-data/src/themes/types.ts b/packages/grafana-data/src/themes/types.ts index 8034bb29c5b..90a43d173cc 100644 --- a/packages/grafana-data/src/themes/types.ts +++ b/packages/grafana-data/src/themes/types.ts @@ -1,3 +1,31 @@ +import { GrafanaTheme } from '../types/theme'; +import { ThemeBreakpoints } from './breakpoints'; +import { ThemeComponents } from './createComponents'; +import { ThemePalette } from './createPalette'; +import { ThemeShadows } from './createShadows'; +import { ThemeShape } from './createShape'; +import { ThemeSpacing } from './createSpacing'; +import { ThemeTransitions } from './createTransitions'; +import { ThemeTypography } from './createTypography'; +import { ThemeZIndices } from './zIndex'; + +/** @beta */ +export interface GrafanaThemeV2 { + name: string; + isDark: boolean; + isLight: boolean; + palette: ThemePalette; + breakpoints: ThemeBreakpoints; + spacing: ThemeSpacing; + shape: ThemeShape; + components: ThemeComponents; + typography: ThemeTypography; + zIndex: ThemeZIndices; + shadows: ThemeShadows; + transitions: ThemeTransitions; + v1: GrafanaTheme; +} + /** @alpha */ export interface ThemePaletteColor { /** color intent (primary, secondary, info, error, etc) */ diff --git a/packages/grafana-data/src/types/theme.ts b/packages/grafana-data/src/types/theme.ts index 7038b5bd1fa..51349529fef 100644 --- a/packages/grafana-data/src/types/theme.ts +++ b/packages/grafana-data/src/types/theme.ts @@ -1,5 +1,3 @@ -import { GrafanaThemeV2 } from '../themes/createTheme'; - export enum GrafanaThemeType { Light = 'light', Dark = 'dark', @@ -113,7 +111,6 @@ export interface GrafanaThemeCommons { } export interface GrafanaTheme extends GrafanaThemeCommons { - v2: GrafanaThemeV2; type: GrafanaThemeType; isDark: boolean; isLight: boolean; diff --git a/packages/grafana-runtime/src/config.ts b/packages/grafana-runtime/src/config.ts index facc8225dfc..3d2ab73ddaf 100644 --- a/packages/grafana-runtime/src/config.ts +++ b/packages/grafana-runtime/src/config.ts @@ -6,7 +6,6 @@ import { FeatureToggles, GrafanaConfig, GrafanaTheme, - GrafanaThemeType, LicenseInfo, PanelPluginMeta, systemDateFormats, @@ -76,7 +75,7 @@ export class GrafanaBootConfig implements GrafanaConfig { awsAssumeRoleEnabled = false; constructor(options: GrafanaBootConfig) { - this.theme = options.bootData.user.lightTheme ? getTheme(GrafanaThemeType.Light) : getTheme(GrafanaThemeType.Dark); + this.theme = getTheme(options.bootData.user.lightTheme ? 'light' : 'dark'); const defaults = { datasources: {}, diff --git a/packages/grafana-ui/.storybook/storybookTheme.ts b/packages/grafana-ui/.storybook/storybookTheme.ts index f8bfb721652..457c90d79bd 100644 --- a/packages/grafana-ui/.storybook/storybookTheme.ts +++ b/packages/grafana-ui/.storybook/storybookTheme.ts @@ -1,41 +1,39 @@ +import { GrafanaThemeV2, createTheme } from '@grafana/data'; //@ts-ignore import { create } from '@storybook/theming/create'; -import lightTheme from '../src/themes/light'; -import darkTheme from '../src/themes/dark'; -import { GrafanaTheme } from '@grafana/data'; import '../src/components/Icon/iconBundle'; -const createTheme = (theme: GrafanaTheme) => { +const createStorybookTheme = (theme: GrafanaThemeV2) => { return create({ base: theme.name.includes('Light') ? 'light' : 'dark', - colorPrimary: theme.v2.palette.primary.main, - colorSecondary: theme.v2.palette.error.main, + colorPrimary: theme.palette.primary.main, + colorSecondary: theme.palette.error.main, // UI - appBg: theme.v2.palette.background.canvas, - appContentBg: theme.v2.palette.background.primary, - appBorderColor: theme.v2.palette.border.medium, - appBorderRadius: theme.v2.shape.borderRadius(1), + appBg: theme.palette.background.canvas, + appContentBg: theme.palette.background.primary, + appBorderColor: theme.palette.border.medium, + appBorderRadius: theme.shape.borderRadius(1), // Typography - fontBase: theme.v2.typography.fontFamily, - fontCode: theme.v2.typography.fontFamilyMonospace, + fontBase: theme.typography.fontFamily, + fontCode: theme.typography.fontFamilyMonospace, // Text colors - textColor: theme.v2.palette.primary.text, - textInverseColor: theme.v2.palette.primary.contrastText, + textColor: theme.palette.primary.text, + textInverseColor: theme.palette.primary.contrastText, // Toolbar default and active colors - barTextColor: theme.v2.palette.text.primary, - barSelectedColor: theme.v2.palette.emphasize(theme.v2.palette.primary.text), - barBg: theme.v2.palette.background.primary, + barTextColor: theme.palette.text.primary, + barSelectedColor: theme.palette.emphasize(theme.palette.primary.text), + barBg: theme.palette.background.primary, // Form colors - inputBg: theme.v2.components.input.background, - inputBorder: theme.v2.components.input.border, - inputTextColor: theme.v2.components.input.text, - inputBorderRadius: theme.v2.shape.borderRadius(1), + inputBg: theme.components.input.background, + inputBorder: theme.components.input.border, + inputTextColor: theme.components.input.text, + inputBorderRadius: theme.shape.borderRadius(1), brandTitle: 'Grafana UI', brandUrl: './', @@ -43,7 +41,7 @@ const createTheme = (theme: GrafanaTheme) => { }); }; -const GrafanaLight = createTheme(lightTheme); -const GrafanaDark = createTheme(darkTheme); +const GrafanaLight = createStorybookTheme(createTheme({ palette: { mode: 'light' } })); +const GrafanaDark = createStorybookTheme(createTheme({ palette: { mode: 'dark' } })); export { GrafanaLight, GrafanaDark }; diff --git a/packages/grafana-ui/src/components/Alert/Alert.tsx b/packages/grafana-ui/src/components/Alert/Alert.tsx index 474f1f884a2..71e146f4271 100644 --- a/packages/grafana-ui/src/components/Alert/Alert.tsx +++ b/packages/grafana-ui/src/components/Alert/Alert.tsx @@ -1,8 +1,8 @@ import React, { FC, HTMLAttributes, ReactNode } from 'react'; import { css } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { selectors } from '@grafana/e2e-selectors'; -import { useTheme } from '../../themes'; +import { useTheme2 } from '../../themes'; import { Icon } from '../Icon/Icon'; import { IconName } from '../../types/icon'; import { IconButton } from '../IconButton/IconButton'; @@ -36,7 +36,7 @@ function getIconFromSeverity(severity: AlertVariant): string { export const Alert: FC = React.forwardRef( ({ title, onRemove, children, buttonContent, elevated, severity = 'error', ...restProps }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getStyles(theme, severity, elevated); return ( @@ -68,19 +68,19 @@ export const Alert: FC = React.forwardRef( Alert.displayName = 'Alert'; -const getStyles = (theme: GrafanaTheme, severity: AlertVariant, elevated?: boolean) => { - const color = theme.v2.palette[severity]; +const getStyles = (theme: GrafanaThemeV2, severity: AlertVariant, elevated?: boolean) => { + const color = theme.palette[severity]; return { alert: css` flex-grow: 1; position: relative; - border-radius: ${theme.v2.shape.borderRadius()}; + border-radius: ${theme.shape.borderRadius()}; display: flex; flex-direction: row; align-items: stretch; - background: ${theme.v2.palette.background.secondary}; - box-shadow: ${elevated ? theme.v2.shadows.z4 : theme.v2.shadows.z1}; + background: ${theme.palette.background.secondary}; + box-shadow: ${elevated ? theme.shadows.z4 : theme.shadows.z1}; &:before { content: ''; @@ -89,12 +89,12 @@ const getStyles = (theme: GrafanaTheme, severity: AlertVariant, elevated?: boole left: 0; bottom: 0; right: 0; - background: ${theme.v2.palette.background.primary}; + background: ${theme.palette.background.primary}; z-index: -1; } `, icon: css` - padding: ${theme.v2.spacing(2, 3)}; + padding: ${theme.spacing(2, 3)}; background: ${color.main}; color: ${color.contrastText}; display: flex; @@ -102,12 +102,12 @@ const getStyles = (theme: GrafanaTheme, severity: AlertVariant, elevated?: boole justify-content: center; `, title: css` - font-weight: ${theme.v2.typography.fontWeightMedium}; - color: ${theme.v2.palette.text.primary}; + font-weight: ${theme.typography.fontWeightMedium}; + color: ${theme.palette.text.primary}; `, body: css` - color: ${theme.v2.palette.text.secondary}; - padding: ${theme.v2.spacing(2)}; + color: ${theme.palette.text.secondary}; + padding: ${theme.spacing(2)}; flex-grow: 1; display: flex; flex-direction: column; @@ -116,13 +116,13 @@ const getStyles = (theme: GrafanaTheme, severity: AlertVariant, elevated?: boole word-break: break-word; `, buttonWrapper: css` - padding: ${theme.v2.spacing(1)}; + padding: ${theme.spacing(1)}; background: none; display: flex; align-items: center; `, close: css` - padding: ${theme.v2.spacing(1)}; + padding: ${theme.spacing(1)}; background: none; align-items: center; display: flex; diff --git a/packages/grafana-ui/src/components/AlphaNotice/AlphaNotice.tsx b/packages/grafana-ui/src/components/AlphaNotice/AlphaNotice.tsx index e901eb56d39..3fa72f93b2e 100644 --- a/packages/grafana-ui/src/components/AlphaNotice/AlphaNotice.tsx +++ b/packages/grafana-ui/src/components/AlphaNotice/AlphaNotice.tsx @@ -17,12 +17,12 @@ export const AlphaNotice: FC = ({ state, text, className }) => { const styles = cx( className, css` - background: ${theme.v2.palette.primary.transparent}; - color: ${theme.v2.palette.text.secondary}; + background: ${theme.palette.primary.transparent}; + color: ${theme.palette.text.secondary}; white-space: nowrap; border-radius: 3px; text-shadow: none; - font-size: ${theme.v2.typography.size.sm}; + font-size: ${theme.typography.size.sm}; padding: 0 8px; cursor: help; display: inline-block; diff --git a/packages/grafana-ui/src/components/BigValue/__snapshots__/BigValue.test.tsx.snap b/packages/grafana-ui/src/components/BigValue/__snapshots__/BigValue.test.tsx.snap index d5faacde155..2a67337c49c 100644 --- a/packages/grafana-ui/src/components/BigValue/__snapshots__/BigValue.test.tsx.snap +++ b/packages/grafana-ui/src/components/BigValue/__snapshots__/BigValue.test.tsx.snap @@ -30,7 +30,7 @@ exports[`BigValue Render with basic options should render 1`] = ` ; export const Button = React.forwardRef( ({ variant = 'primary', size = 'md', icon, fullWidth, children, className, ...otherProps }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getButtonStyles({ theme, size, @@ -62,7 +62,7 @@ export const LinkButton = React.forwardRef( }, ref ) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getButtonStyles({ theme, fullWidth, @@ -88,32 +88,32 @@ export interface StyleProps { size: ComponentSize; variant: ButtonVariant; iconOnly?: boolean; - theme: GrafanaTheme; + theme: GrafanaThemeV2; fullWidth?: boolean; narrow?: boolean; } export const getButtonStyles = (props: StyleProps) => { const { theme, variant, size, iconOnly, fullWidth } = props; - const { height, padding, fontSize } = getPropertiesForButtonSize(size, theme.v2); - const variantStyles = getPropertiesForVariant(theme.v2, variant); + const { height, padding, fontSize } = getPropertiesForButtonSize(size, theme); + const variantStyles = getPropertiesForVariant(theme, variant); const disabledStyles: CSSObject = { cursor: 'not-allowed', boxShadow: 'none', - background: theme.v2.palette.action.disabledBackground, + background: theme.palette.action.disabledBackground, border: `1px solid transparent`, - color: theme.v2.palette.text.disabled, + color: theme.palette.text.disabled, pointerEvents: 'none', '&:hover': { - background: theme.v2.palette.action.disabledBackground, - color: theme.v2.palette.text.disabled, + background: theme.palette.action.disabledBackground, + color: theme.palette.text.disabled, boxShadow: 'none', }, }; - const focusStyle = getFocusStyles(theme.v2); + const focusStyle = getFocusStyles(theme); return { button: css({ @@ -121,18 +121,18 @@ export const getButtonStyles = (props: StyleProps) => { display: 'inline-flex', alignItems: 'center', fontSize: fontSize, - fontWeight: theme.v2.typography.fontWeightMedium, - fontFamily: theme.v2.typography.fontFamily, - padding: theme.v2.spacing(0, padding), - height: theme.v2.spacing(height), + fontWeight: theme.typography.fontWeightMedium, + fontFamily: theme.typography.fontFamily, + padding: theme.spacing(0, padding), + height: theme.spacing(height), // Deduct border from line-height for perfect vertical centering on windows and linux - lineHeight: `${theme.v2.spacing.gridSize * height - 2}px`, + lineHeight: `${theme.spacing.gridSize * height - 2}px`, verticalAlign: 'middle', cursor: 'pointer', - borderRadius: theme.v2.shape.borderRadius(1), + borderRadius: theme.shape.borderRadius(1), '&:focus': focusStyle, '&:focus-visible': focusStyle, - '&:focus:not(:focus-visible)': getMouseFocusStyles(theme.v2), + '&:focus:not(:focus-visible)': getMouseFocusStyles(theme), ...(fullWidth && { flexGrow: 1, justifyContent: 'center', @@ -145,10 +145,10 @@ export const getButtonStyles = (props: StyleProps) => { img: css` width: 16px; height: 16px; - margin: ${theme.v2.spacing(0, 1, 0, 0.5)}; + margin: ${theme.spacing(0, 1, 0, 0.5)}; `, icon: css` - margin: ${theme.v2.spacing(0, (iconOnly ? -padding : padding) / 2, 0, -(padding / 2))}; + margin: ${theme.spacing(0, (iconOnly ? -padding : padding) / 2, 0, -(padding / 2))}; `, content: css` display: flex; diff --git a/packages/grafana-ui/src/components/Button/ToolbarButton.tsx b/packages/grafana-ui/src/components/Button/ToolbarButton.tsx index e8e1d3ad74c..fdc41d35751 100644 --- a/packages/grafana-ui/src/components/Button/ToolbarButton.tsx +++ b/packages/grafana-ui/src/components/Button/ToolbarButton.tsx @@ -1,14 +1,14 @@ import React, { forwardRef, ButtonHTMLAttributes } from 'react'; import { cx, css } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; -import { styleMixins, useStyles } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; +import { styleMixins, useStyles2 } from '../../themes'; import { IconName } from '../../types/icon'; import { Tooltip } from '../Tooltip/Tooltip'; import { Icon } from '../Icon/Icon'; import { getPropertiesForVariant } from './Button'; import { isString } from 'lodash'; import { selectors } from '@grafana/e2e-selectors'; -import { focusCss, getMouseFocusStyles } from '../../themes/mixins'; +import { getFocusStyles, getMouseFocusStyles } from '../../themes/mixins'; export interface Props extends ButtonHTMLAttributes { /** Icon name */ @@ -49,7 +49,7 @@ export const ToolbarButton = forwardRef( }, ref ) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); const buttonStyles = cx( 'toolbar-button', @@ -104,81 +104,82 @@ function renderIcon(icon: IconName | React.ReactNode) { return icon; } -const getStyles = (theme: GrafanaTheme) => { - const primaryVariant = getPropertiesForVariant(theme.v2, 'primary'); - const destructiveVariant = getPropertiesForVariant(theme.v2, 'destructive'); +const getStyles = (theme: GrafanaThemeV2) => { + const primaryVariant = getPropertiesForVariant(theme, 'primary'); + const destructiveVariant = getPropertiesForVariant(theme, 'destructive'); return { button: css` label: toolbar-button; display: flex; align-items: center; - height: ${theme.v2.spacing(theme.v2.components.height.md)}; - padding: ${theme.v2.spacing(0, 1)}; - border-radius: ${theme.v2.shape.borderRadius()}; - line-height: ${theme.v2.components.height.md * theme.v2.spacing.gridSize - 2}px; - font-weight: ${theme.v2.typography.fontWeightMedium}; - border: 1px solid ${theme.v2.palette.border.medium}; + height: ${theme.spacing(theme.components.height.md)}; + padding: ${theme.spacing(0, 1)}; + border-radius: ${theme.shape.borderRadius()}; + line-height: ${theme.components.height.md * theme.spacing.gridSize - 2}px; + font-weight: ${theme.typography.fontWeightMedium}; + border: 1px solid ${theme.palette.border.medium}; white-space: nowrap; - transition: ${theme.v2.transitions.create(['background', 'box-shadow', 'border-color', 'color'], { - duration: theme.v2.transitions.duration.short, + transition: ${theme.transitions.create(['background', 'box-shadow', 'border-color', 'color'], { + duration: theme.transitions.duration.short, })}; &:focus, &:focus-visible { - ${focusCss(theme)} + ${getFocusStyles(theme)} z-index: 1; } &:focus:not(:focus-visible) { - ${getMouseFocusStyles(theme.v2)} + ${getMouseFocusStyles(theme)} } &:hover { - box-shadow: ${theme.v2.shadows.z2}; + box-shadow: ${theme.shadows.z2}; } &[disabled], &:disabled { cursor: not-allowed; - opacity: ${theme.v2.palette.action.disabledOpacity}; - background: ${theme.v2.palette.action.disabledBackground}; + opacity: ${theme.palette.action.disabledOpacity}; + background: ${theme.palette.action.disabledBackground}; box-shadow: none; &:hover { - color: ${theme.v2.palette.text.disabled}; - background: ${theme.v2.palette.action.disabledBackground}; + color: ${theme.palette.text.disabled}; + background: ${theme.palette.action.disabledBackground}; box-shadow: none; } } `, default: css` - color: ${theme.v2.palette.text.secondary}; - background-color: ${theme.v2.palette.background.primary}; + color: ${theme.palette.text.secondary}; + background-color: ${theme.palette.background.primary}; &:hover { - color: ${theme.v2.palette.text.primary}; - background: ${theme.v2.palette.background.secondary}; + color: ${theme.palette.text.primary}; + background: ${theme.palette.background.secondary}; } `, active: css` - color: ${theme.palette.orangeDark}; - border-color: ${theme.palette.orangeDark}; + color: ${theme.v1.palette.orangeDark}; + border-color: ${theme.v1.palette.orangeDark}; background-color: transparent; + &:hover { - color: ${theme.colors.text}; - background: ${styleMixins.hoverColor(theme.colors.bg1, theme)}; + color: ${theme.palette.text.primary}; + background: ${theme.palette.emphasize(theme.palette.background.canvas, 0.03)}; } `, primary: css(primaryVariant), destructive: css(destructiveVariant), narrow: css` - padding: 0 ${theme.spacing.xs}; + padding: 0 ${theme.spacing(0.5)}; `, img: css` width: 16px; height: 16px; - margin-right: ${theme.spacing.sm}; + margin-right: ${theme.spacing(1)}; `, buttonFullWidth: css` flex-grow: 1; @@ -188,14 +189,14 @@ const getStyles = (theme: GrafanaTheme) => { `, contentWithIcon: css` display: none; - padding-left: ${theme.spacing.sm}; + padding-left: ${theme.spacing(1)}; - @media ${styleMixins.mediaUp(theme.breakpoints.md)} { + @media ${styleMixins.mediaUp(theme.v1.breakpoints.md)} { display: block; } `, contentWithRightIcon: css` - padding-right: ${theme.spacing.xs}; + padding-right: ${theme.spacing(0.5)}; `, }; }; diff --git a/packages/grafana-ui/src/components/CallToActionCard/__snapshots__/CallToActionCard.test.tsx.snap b/packages/grafana-ui/src/components/CallToActionCard/__snapshots__/CallToActionCard.test.tsx.snap index 003bf2827f7..891566d14fd 100644 --- a/packages/grafana-ui/src/components/CallToActionCard/__snapshots__/CallToActionCard.test.tsx.snap +++ b/packages/grafana-ui/src/components/CallToActionCard/__snapshots__/CallToActionCard.test.tsx.snap @@ -2,7 +2,7 @@ exports[`CallToActionCard rendering when message and footer provided 1`] = `
= ({ children, href }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getCardStyles(theme); return href ? ( @@ -81,7 +81,7 @@ export const Card: CardInterface = ({ children, ...htmlProps }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getCardStyles(theme); const [tags, figure, meta, actions, secondaryActions] = ['Tags', 'Figure', 'Meta', 'Actions', 'SecondaryActions'].map( (item) => { @@ -136,26 +136,26 @@ export const Card: CardInterface = ({ ); }; -const getContainerStyles = stylesFactory((theme: GrafanaTheme, disabled = false, disableHover = false) => { +const getContainerStyles = stylesFactory((theme: GrafanaThemeV2, disabled = false, disableHover = false) => { return css({ display: 'flex', width: '100%', - background: theme.v2.palette.background.secondary, - borderRadius: theme.v2.shape.borderRadius(), + background: theme.palette.background.secondary, + borderRadius: theme.shape.borderRadius(), position: 'relative', pointerEvents: disabled ? 'none' : 'auto', - marginBottom: theme.v2.spacing(1), - transition: theme.v2.transitions.create(['background-color', 'box-shadow', 'border-color', 'color'], { - duration: theme.v2.transitions.duration.short, + marginBottom: theme.spacing(1), + transition: theme.transitions.create(['background-color', 'box-shadow', 'border-color', 'color'], { + duration: theme.transitions.duration.short, }), ...(!disableHover && { '&:hover': { - background: theme.v2.palette.emphasize(theme.v2.palette.background.secondary, 0.03), + background: theme.palette.emphasize(theme.palette.background.secondary, 0.03), cursor: 'pointer', zIndex: 1, }, - '&:focus': styleMixins.getFocusStyles(theme.v2), + '&:focus': styleMixins.getFocusStyles(theme), }), }); }); @@ -163,7 +163,7 @@ const getContainerStyles = stylesFactory((theme: GrafanaTheme, disabled = false, /** * @public */ -export const getCardStyles = stylesFactory((theme: GrafanaTheme) => { +export const getCardStyles = stylesFactory((theme: GrafanaThemeV2) => { return { inner: css` display: flex; @@ -179,9 +179,9 @@ export const getCardStyles = stylesFactory((theme: GrafanaTheme) => { width: 100%; margin-bottom: 0; font-size: ${theme.typography.size.md}; - line-height: ${theme.typography.lineHeight.xs}; - color: ${theme.colors.text}; - font-weight: ${theme.typography.weight.semibold}; + line-height: ${theme.typography.body.lineHeight}; + color: ${theme.palette.text.primary}; + font-weight: ${theme.typography.fontWeightMedium}; `, info: css` display: flex; @@ -195,18 +195,18 @@ export const getCardStyles = stylesFactory((theme: GrafanaTheme) => { align-items: center; width: 100%; font-size: ${theme.typography.size.sm}; - color: ${theme.colors.textSemiWeak}; - margin: ${theme.spacing.xs} 0 0; - line-height: ${theme.typography.lineHeight.xs}; + color: ${theme.palette.text.secondary}; + margin: ${theme.spacing(0.5, 0, 0)}; + line-height: ${theme.typography.bodySmall.lineHeight}; `, description: css` width: 100%; - margin: ${theme.spacing.sm} 0 0; - color: ${theme.colors.textSemiWeak}; - line-height: ${theme.typography.lineHeight.md}; + margin: ${theme.spacing(1, 0, 0)}; + color: ${theme.palette.text.secondary}; + line-height: ${theme.typography.body.lineHeight}; `, media: css` - margin-right: ${theme.spacing.md}; + margin-right: ${theme.spacing(2)}; width: 40px; display: flex; align-items: center; @@ -224,30 +224,30 @@ export const getCardStyles = stylesFactory((theme: GrafanaTheme) => { justify-content: space-between; align-items: center; width: 100%; - margin-top: ${theme.spacing.md}; + margin-top: ${theme.spacing(2)}; `, actions: css` & > * { - margin-right: ${theme.spacing.sm}; + margin-right: ${theme.spacing(1)}; } `, secondaryActions: css` display: flex; align-items: center; - color: ${theme.colors.textSemiWeak}; + color: ${theme.palette.text.secondary}; // align to the right margin-left: auto; & > * { - margin-right: ${theme.spacing.sm} !important; + margin-right: ${theme.spacing(1)} !important; } `, separator: css` - margin: 0 ${theme.spacing.sm}; + margin: 0 ${theme.spacing(1)}; `, innerLink: css` display: flex; width: 100%; - padding: ${theme.spacing.md}; + padding: ${theme.spacing(2)}; `, tagList: css` max-width: 50%; diff --git a/packages/grafana-ui/src/components/Collapse/Collapse.tsx b/packages/grafana-ui/src/components/Collapse/Collapse.tsx index 9decabbf0b9..e9fc3df51bc 100644 --- a/packages/grafana-ui/src/components/Collapse/Collapse.tsx +++ b/packages/grafana-ui/src/components/Collapse/Collapse.tsx @@ -1,12 +1,11 @@ -import React, { FunctionComponent, useContext, useState } from 'react'; +import React, { FunctionComponent, useState } from 'react'; import { css, cx } from '@emotion/css'; import { GrafanaTheme } from '@grafana/data'; -import { ThemeContext } from '../../themes/ThemeContext'; -import { stylesFactory } from '../../themes/stylesFactory'; +import { useStyles } from '../../themes/ThemeContext'; import { Icon } from '../Icon/Icon'; -const getStyles = stylesFactory((theme: GrafanaTheme) => ({ +const getStyles = (theme: GrafanaTheme) => ({ collapse: css` label: collapse; margin-bottom: ${theme.spacing.sm}; @@ -89,7 +88,7 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => ({ margin-right: ${theme.spacing.sm}; font-size: ${theme.typography.heading.h6}; `, -})); +}); export interface Props { /** Expand or collapse te content */ @@ -131,8 +130,7 @@ export const Collapse: FunctionComponent = ({ className, children, }) => { - const theme = useContext(ThemeContext); - const style = getStyles(theme); + const style = useStyles(getStyles); const onClickToggle = () => { if (onToggle) { onToggle(!isOpen); diff --git a/packages/grafana-ui/src/components/ConfirmModal/ConfirmModal.tsx b/packages/grafana-ui/src/components/ConfirmModal/ConfirmModal.tsx index fcac981707c..2e9e77a5738 100644 --- a/packages/grafana-ui/src/components/ConfirmModal/ConfirmModal.tsx +++ b/packages/grafana-ui/src/components/ConfirmModal/ConfirmModal.tsx @@ -3,8 +3,8 @@ import { css } from '@emotion/css'; import { Modal } from '../Modal/Modal'; import { IconName } from '../../types/icon'; import { Button } from '../Button'; -import { useStyles } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { useStyles2 } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; import { HorizontalGroup, Input } from '..'; import { selectors } from '@grafana/e2e-selectors'; @@ -50,7 +50,7 @@ export const ConfirmModal = ({ onAlternative, }: ConfirmModalProps): JSX.Element => { const [disabled, setDisabled] = useState(Boolean(confirmationText)); - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); const onConfirmationTextChange = (event: React.FormEvent) => { setDisabled(confirmationText?.localeCompare(event.currentTarget.value) !== 0); }; @@ -92,7 +92,7 @@ export const ConfirmModal = ({ ); }; -const getStyles = (theme: GrafanaTheme) => ({ +const getStyles = (theme: GrafanaThemeV2) => ({ modal: css` width: 500px; `, @@ -100,16 +100,16 @@ const getStyles = (theme: GrafanaTheme) => ({ text-align: center; `, modalText: css({ - fontSize: theme.v2.typography.h4.fontSize, - color: theme.v2.palette.text.primary, - marginBottom: `calc(${theme.v2.spacing(2)}*2)`, - paddingTop: theme.v2.spacing(2), + fontSize: theme.typography.h4.fontSize, + color: theme.palette.text.primary, + marginBottom: `calc(${theme.spacing(2)}*2)`, + paddingTop: theme.spacing(2), }), modalDescription: css({ - fontSize: theme.v2.typography.h6.fontSize, - paddingTop: theme.v2.spacing(2), + fontSize: theme.typography.h6.fontSize, + paddingTop: theme.spacing(2), }), modalConfirmationInput: css({ - paddingTop: theme.v2.spacing(2), + paddingTop: theme.spacing(2), }), }); diff --git a/packages/grafana-ui/src/components/CustomScrollbar/CustomScrollbar.tsx b/packages/grafana-ui/src/components/CustomScrollbar/CustomScrollbar.tsx index badfe4c557a..f4db372ac0a 100644 --- a/packages/grafana-ui/src/components/CustomScrollbar/CustomScrollbar.tsx +++ b/packages/grafana-ui/src/components/CustomScrollbar/CustomScrollbar.tsx @@ -3,8 +3,8 @@ import { isNil } from 'lodash'; import classNames from 'classnames'; import { css } from '@emotion/css'; import Scrollbars from 'react-custom-scrollbars'; -import { useStyles } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { useStyles2 } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; interface Props { className?: string; @@ -38,7 +38,7 @@ export const CustomScrollbar: FC = ({ children, }) => { const ref = useRef(null); - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); const updateScroll = () => { if (ref.current && !isNil(scrollTop)) { @@ -127,7 +127,7 @@ export const CustomScrollbar: FC = ({ export default CustomScrollbar; -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { return { customScrollbar: css` // Fix for Firefox. For some reason sometimes .view container gets a height of its content, but in order to @@ -141,27 +141,27 @@ const getStyles = (theme: GrafanaTheme) => { flex-direction: column; } .track-vertical { - border-radius: ${theme.border.radius.md}; - width: ${theme.spacing.sm} !important; + border-radius: ${theme.shape.borderRadius(2)}; + width: ${theme.spacing(1)} !important; right: 0px; - bottom: ${theme.spacing.xxs}; - top: ${theme.spacing.xxs}; + bottom: ${theme.spacing(0.25)}; + top: ${theme.spacing(0.25)}; } .track-horizontal { - border-radius: ${theme.border.radius.md}; - height: ${theme.spacing.sm} !important; - right: ${theme.spacing.xxs}; - bottom: ${theme.spacing.xxs}; - left: ${theme.spacing.xxs}; + border-radius: ${theme.shape.borderRadius(2)}; + height: ${theme.spacing(1)} !important; + right: ${theme.spacing(0.25)}; + bottom: ${theme.spacing(0.25)}; + left: ${theme.spacing(0.25)}; } .thumb-vertical { - background: ${theme.v2.palette.action.focus}; - border-radius: ${theme.border.radius.md}; + background: ${theme.palette.action.focus}; + border-radius: ${theme.shape.borderRadius(2)}; opacity: 0; } .thumb-horizontal { - background: ${theme.v2.palette.action.focus}; - border-radius: ${theme.border.radius.md}; + background: ${theme.palette.action.focus}; + border-radius: ${theme.shape.borderRadius(2)}; opacity: 0; } &:hover { diff --git a/packages/grafana-ui/src/components/CustomScrollbar/__snapshots__/CustomScrollbar.test.tsx.snap b/packages/grafana-ui/src/components/CustomScrollbar/__snapshots__/CustomScrollbar.test.tsx.snap index 4353a96df97..1601b7b1882 100644 --- a/packages/grafana-ui/src/components/CustomScrollbar/__snapshots__/CustomScrollbar.test.tsx.snap +++ b/packages/grafana-ui/src/components/CustomScrollbar/__snapshots__/CustomScrollbar.test.tsx.snap @@ -2,7 +2,7 @@ exports[`CustomScrollbar renders correctly 1`] = `
void) => void; } -const getStyles = stylesFactory((theme: GrafanaTheme) => ({ +const getStyles = (theme: GrafanaTheme) => ({ listItem: css` margin-bottom: ${theme.spacing.sm}; `, @@ -24,12 +24,11 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => ({ margin-left: 66px; color: ${theme.colors.textWeak}; `, -})); +}); export const DataLinkEditor: React.FC = React.memo( ({ index, value, onChange, suggestions, isLast }) => { - const theme = useContext(ThemeContext); - const styles = getStyles(theme); + const styles = useStyles(getStyles); const onUrlChange = (url: string, callback?: () => void) => { onChange(index, { ...value, url }, callback); diff --git a/packages/grafana-ui/src/components/DataLinks/DataLinkInput.tsx b/packages/grafana-ui/src/components/DataLinks/DataLinkInput.tsx index b293fe69747..7b6d71ac885 100644 --- a/packages/grafana-ui/src/components/DataLinks/DataLinkInput.tsx +++ b/packages/grafana-ui/src/components/DataLinks/DataLinkInput.tsx @@ -1,7 +1,7 @@ -import React, { memo, RefObject, useContext, useEffect, useMemo, useRef, useState } from 'react'; +import React, { memo, RefObject, useEffect, useMemo, useRef, useState } from 'react'; import usePrevious from 'react-use/lib/usePrevious'; import { DataLinkSuggestions } from './DataLinkSuggestions'; -import { makeValue, ThemeContext } from '../../index'; +import { makeValue } from '../../index'; import { SelectionReference } from './SelectionReference'; import { Portal } from '../index'; @@ -15,8 +15,8 @@ import { css, cx } from '@emotion/css'; import { SlatePrism } from '../../slate-plugins'; import { SCHEMA } from '../../utils/slate'; -import { stylesFactory } from '../../themes'; -import { DataLinkBuiltInVars, GrafanaTheme, VariableOrigin, VariableSuggestion } from '@grafana/data'; +import { useStyles2 } from '../../themes'; +import { DataLinkBuiltInVars, GrafanaThemeV2, VariableOrigin, VariableSuggestion } from '@grafana/data'; import { getInputStyles } from '../Input/Input'; const modulo = (a: number, n: number) => a - n * Math.floor(a / n); @@ -44,14 +44,14 @@ const plugins = [ ), ]; -const getStyles = stylesFactory((theme: GrafanaTheme) => ({ +const getStyles = (theme: GrafanaThemeV2) => ({ input: getInputStyles({ theme, invalid: false }).input, editor: css` .token.builtInVariable { - color: ${theme.palette.queryGreen}; + color: ${theme.palette.success.text}; } .token.variable { - color: ${theme.colors.textBlue}; + color: ${theme.palette.primary.text}; } `, // Wrapper with child selector needed. @@ -64,15 +64,14 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => ({ border: none; } `, -})); +}); // This memoised also because rerendering the slate editor grabs focus which created problem in some cases this // was used and changes to different state were propagated here. export const DataLinkInput: React.FC = memo( ({ value, onChange, suggestions, placeholder = 'http://your-grafana.com/d/000000010/annotations' }) => { const editorRef = useRef() as RefObject; - const theme = useContext(ThemeContext); - const styles = getStyles(theme); + const styles = useStyles2(getStyles); const [showingSuggestions, setShowingSuggestions] = useState(false); const [suggestionsIndex, setSuggestionsIndex] = useState(0); const [linkUrl, setLinkUrl] = useState(makeValue(value)); diff --git a/packages/grafana-ui/src/components/DataLinks/DataLinkSuggestions.tsx b/packages/grafana-ui/src/components/DataLinks/DataLinkSuggestions.tsx index 94c55d1006a..ba4cccf5abf 100644 --- a/packages/grafana-ui/src/components/DataLinks/DataLinkSuggestions.tsx +++ b/packages/grafana-ui/src/components/DataLinks/DataLinkSuggestions.tsx @@ -1,11 +1,10 @@ -import { ThemeContext } from '../../index'; import { GrafanaTheme, VariableSuggestion } from '@grafana/data'; import { css, cx } from '@emotion/css'; import { groupBy, capitalize } from 'lodash'; -import React, { useRef, useContext, useMemo } from 'react'; +import React, { useRef, useMemo } from 'react'; import useClickAway from 'react-use/lib/useClickAway'; import { List } from '../index'; -import { styleMixins, stylesFactory } from '../../themes'; +import { styleMixins, useStyles } from '../../themes'; interface DataLinkSuggestionsProps { suggestions: VariableSuggestion[]; @@ -14,7 +13,7 @@ interface DataLinkSuggestionsProps { onClose?: () => void; } -const getStyles = stylesFactory((theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaTheme) => { const wrapperBg = theme.colors.bg1; const wrapperShadow = theme.colors.dropdownShadow; const itemColor = theme.colors.text; @@ -58,11 +57,11 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => { font-size: ${theme.typography.size.sm}; `, }; -}); +}; export const DataLinkSuggestions: React.FC = ({ suggestions, ...otherProps }) => { const ref = useRef(null); - const theme = useContext(ThemeContext); + useClickAway(ref, () => { if (otherProps.onClose) { otherProps.onClose(); @@ -73,7 +72,8 @@ export const DataLinkSuggestions: React.FC = ({ sugges return groupBy(suggestions, (s) => s.origin); }, [suggestions]); - const styles = getStyles(theme); + const styles = useStyles(getStyles); + return (
{Object.keys(groupedSuggestions).map((key, i) => { @@ -111,8 +111,7 @@ interface DataLinkSuggestionsListProps extends DataLinkSuggestionsProps { const DataLinkSuggestionsList: React.FC = React.memo( ({ activeIndex, activeIndexOffset, label, onClose, onSuggestionSelect, suggestions }) => { - const theme = useContext(ThemeContext); - const styles = getStyles(theme); + const styles = useStyles(getStyles); return ( <> diff --git a/packages/grafana-ui/src/components/FileUpload/FileUpload.tsx b/packages/grafana-ui/src/components/FileUpload/FileUpload.tsx index ae1c5580675..79918ebcd3b 100644 --- a/packages/grafana-ui/src/components/FileUpload/FileUpload.tsx +++ b/packages/grafana-ui/src/components/FileUpload/FileUpload.tsx @@ -1,8 +1,8 @@ import React, { FC, FormEvent, useCallback, useState } from 'react'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css, cx } from '@emotion/css'; import { Icon } from '../index'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { ComponentSize } from '../../types/size'; import { getButtonStyles } from '../Button'; @@ -37,7 +37,7 @@ export const FileUpload: FC = ({ accept = '*', size = 'md', }) => { - const theme = useTheme(); + const theme = useTheme2(); const style = getStyles(theme, size); const [fileName, setFileName] = useState(''); @@ -75,7 +75,7 @@ export const FileUpload: FC = ({ ); }; -const getStyles = stylesFactory((theme: GrafanaTheme, size: ComponentSize) => { +const getStyles = stylesFactory((theme: GrafanaThemeV2, size: ComponentSize) => { const buttonStyles = getButtonStyles({ theme, variant: 'primary', size, iconOnly: false }); return { fileUpload: css` @@ -84,7 +84,7 @@ const getStyles = stylesFactory((theme: GrafanaTheme, size: ComponentSize) => { button: buttonStyles.button, icon: buttonStyles.icon, fileName: css` - margin-left: ${theme.spacing.xs}; + margin-left: ${theme.spacing(0.5)}; `, }; }); diff --git a/packages/grafana-ui/src/components/FilterPill/FilterPill.tsx b/packages/grafana-ui/src/components/FilterPill/FilterPill.tsx index b212cd9a6e9..8d85981ef43 100644 --- a/packages/grafana-ui/src/components/FilterPill/FilterPill.tsx +++ b/packages/grafana-ui/src/components/FilterPill/FilterPill.tsx @@ -1,5 +1,5 @@ -import React, { useContext } from 'react'; -import { stylesFactory, ThemeContext } from '../../themes'; +import React from 'react'; +import { stylesFactory, useTheme } from '../../themes'; import { GrafanaTheme } from '@grafana/data'; import { css } from '@emotion/css'; import { IconButton } from '../IconButton/IconButton'; @@ -13,7 +13,7 @@ export interface FilterPillProps { } export const FilterPill: React.FC = ({ label, selected, onClick, icon = 'check' }) => { - const theme = useContext(ThemeContext); + const theme = useTheme(); const styles = getFilterPillStyles(theme, selected); return (
diff --git a/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButton.tsx b/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButton.tsx index 38aca607c84..e9a402dca5f 100644 --- a/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButton.tsx +++ b/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButton.tsx @@ -1,6 +1,6 @@ import React from 'react'; -import { useTheme, stylesFactory } from '../../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { useTheme2, stylesFactory } from '../../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css, cx } from '@emotion/css'; import { getPropertiesForButtonSize } from '../commonStyles'; import { getFocusStyles, getMouseFocusStyles } from '../../../themes/mixins'; @@ -29,7 +29,7 @@ export const RadioButton: React.FC = ({ description, fullWidth, }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getRadioButtonStyles(theme, size, fullWidth); return ( @@ -52,14 +52,14 @@ export const RadioButton: React.FC = ({ RadioButton.displayName = 'RadioButton'; -const getRadioButtonStyles = stylesFactory((theme: GrafanaTheme, size: RadioButtonSize, fullWidth?: boolean) => { - const { fontSize, height, padding } = getPropertiesForButtonSize(size, theme.v2); +const getRadioButtonStyles = stylesFactory((theme: GrafanaThemeV2, size: RadioButtonSize, fullWidth?: boolean) => { + const { fontSize, height, padding } = getPropertiesForButtonSize(size, theme); - const textColor = theme.v2.palette.text.secondary; - const textColorHover = theme.v2.palette.text.primary; - const bg = theme.v2.components.input.background; + const textColor = theme.palette.text.secondary; + const textColorHover = theme.palette.text.primary; + const bg = theme.components.input.background; // remove the group inner padding (set on RadioButtonGroup) - const labelHeight = height * theme.v2.spacing.gridSize - 4 - 2; + const labelHeight = height * theme.spacing.gridSize - 4 - 2; return { radio: css` @@ -68,24 +68,24 @@ const getRadioButtonStyles = stylesFactory((theme: GrafanaTheme, size: RadioButt z-index: -1000; &:checked + label { - color: ${theme.v2.palette.text.primary}; - font-weight: ${theme.v2.typography.fontWeightMedium}; - background: ${theme.v2.palette.action.selected}; + color: ${theme.palette.text.primary}; + font-weight: ${theme.typography.fontWeightMedium}; + background: ${theme.palette.action.selected}; z-index: 3; } &:focus + label, &:focus-visible + label { - ${getFocusStyles(theme.v2)}; + ${getFocusStyles(theme)}; } &:focus:not(:focus-visible) + label { - ${getMouseFocusStyles(theme.v2)} + ${getMouseFocusStyles(theme)} } &:disabled + label { cursor: default; - color: ${theme.v2.palette.text.disabled}; + color: ${theme.palette.text.disabled}; cursor: not-allowed; } `, @@ -97,8 +97,8 @@ const getRadioButtonStyles = stylesFactory((theme: GrafanaTheme, size: RadioButt // Deduct border from line-height for perfect vertical centering on windows and linux line-height: ${labelHeight}px; color: ${textColor}; - padding: ${theme.v2.spacing(0, padding)}; - border-radius: ${theme.v2.shape.borderRadius()}; + padding: ${theme.spacing(0, padding)}; + border-radius: ${theme.shape.borderRadius()}; background: ${bg}; cursor: pointer; z-index: 1; diff --git a/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButtonGroup.tsx b/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButtonGroup.tsx index bfc46a8af1a..b5c37e8173f 100644 --- a/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButtonGroup.tsx +++ b/packages/grafana-ui/src/components/Forms/RadioButtonGroup/RadioButtonGroup.tsx @@ -1,11 +1,11 @@ import React, { useCallback, useRef } from 'react'; import { css, cx } from '@emotion/css'; import { uniqueId } from 'lodash'; -import { GrafanaTheme, SelectableValue } from '@grafana/data'; +import { GrafanaThemeV2, SelectableValue } from '@grafana/data'; import { RadioButtonSize, RadioButton } from './RadioButton'; import { Icon } from '../../Icon/Icon'; import { IconName } from '../../../types/icon'; -import { useStyles } from '../../../themes'; +import { useStyles2 } from '../../../themes'; export interface RadioButtonGroupProps { value?: T; @@ -40,7 +40,7 @@ export function RadioButtonGroup({ ); const id = uniqueId('radiogroup-'); const groupName = useRef(id); - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); return (
@@ -69,14 +69,14 @@ export function RadioButtonGroup({ RadioButtonGroup.displayName = 'RadioButtonGroup'; -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { return { radioGroup: css({ display: 'inline-flex', flexDirection: 'row', flexWrap: 'nowrap', - border: `1px solid ${theme.v2.components.input.border}`, - borderRadius: theme.v2.shape.borderRadius(), + border: `1px solid ${theme.components.input.border}`, + borderRadius: theme.shape.borderRadius(), padding: '2px', }), fullWidth: css({ diff --git a/packages/grafana-ui/src/components/Forms/commonStyles.ts b/packages/grafana-ui/src/components/Forms/commonStyles.ts index 6767de61b3e..f9623ecd8fd 100644 --- a/packages/grafana-ui/src/components/Forms/commonStyles.ts +++ b/packages/grafana-ui/src/components/Forms/commonStyles.ts @@ -9,19 +9,19 @@ export const getFocusStyle = (theme: GrafanaTheme) => css` } `; -export const sharedInputStyle = (theme: GrafanaTheme, invalid = false) => { - const borderColor = invalid ? theme.v2.palette.error.border : theme.v2.components.input.border; - const borderColorHover = invalid ? theme.v2.palette.error.shade : theme.v2.components.input.borderHover; - const background = theme.v2.components.input.background; - const textColor = theme.v2.components.input.text; +export const sharedInputStyle = (theme: GrafanaThemeV2, invalid = false) => { + const borderColor = invalid ? theme.palette.error.border : theme.components.input.border; + const borderColorHover = invalid ? theme.palette.error.shade : theme.components.input.borderHover; + const background = theme.components.input.background; + const textColor = theme.components.input.text; return css` background: ${background}; - line-height: ${theme.v2.typography.body.lineHeight}; - font-size: ${theme.v2.typography.size.md}; + line-height: ${theme.typography.body.lineHeight}; + font-size: ${theme.typography.size.md}; color: ${textColor}; border: 1px solid ${borderColor}; - padding: ${theme.v2.spacing(0, 1, 0, 1)}; + padding: ${theme.spacing(0, 1, 0, 1)}; &:-webkit-autofill, &:-webkit-autofill:hover { @@ -32,7 +32,7 @@ export const sharedInputStyle = (theme: GrafanaTheme, invalid = false) => { &:-webkit-autofill:focus { /* Welcome to 2005. This is a HACK to get rid od Chromes default autofill styling */ - box-shadow: 0 0 0 2px ${theme.colors.bodyBg}, 0 0 0px 4px ${theme.colors.formFocusOutline}, + box-shadow: 0 0 0 2px ${theme.palette.background.primary}, 0 0 0px 4px ${theme.palette.primary.main}, inset 0 0 0 1px rgba(255, 255, 255, 0), inset 0 0 0 100px ${background}!important; -webkit-text-fill-color: ${textColor} !important; } @@ -46,9 +46,9 @@ export const sharedInputStyle = (theme: GrafanaTheme, invalid = false) => { } &:disabled { - background-color: ${theme.v2.palette.action.disabledBackground}; - color: ${theme.v2.palette.action.disabledText}; - border: 1px solid ${theme.v2.palette.action.disabledBackground}; + background-color: ${theme.palette.action.disabledBackground}; + color: ${theme.palette.action.disabledText}; + border: 1px solid ${theme.palette.action.disabledBackground}; &:hover { border-color: ${borderColor}; @@ -56,7 +56,7 @@ export const sharedInputStyle = (theme: GrafanaTheme, invalid = false) => { } &::placeholder { - color: ${theme.v2.palette.text.disabled}; + color: ${theme.palette.text.disabled}; opacity: 1; } `; diff --git a/packages/grafana-ui/src/components/Forms/getFormStyles.ts b/packages/grafana-ui/src/components/Forms/getFormStyles.ts index 938f16f8f6f..5abbc9a4810 100644 --- a/packages/grafana-ui/src/components/Forms/getFormStyles.ts +++ b/packages/grafana-ui/src/components/Forms/getFormStyles.ts @@ -1,5 +1,5 @@ import { stylesFactory } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { getLabelStyles } from './Label'; import { getLegendStyles } from './Legend'; import { getFieldValidationMessageStyles } from './FieldValidationMessage'; @@ -10,20 +10,20 @@ import { getCheckboxStyles } from './Checkbox'; /** @deprecated */ export const getFormStyles = stylesFactory( - (theme: GrafanaTheme, options: { variant: ButtonVariant; size: ComponentSize; invalid: boolean }) => { + (theme: GrafanaThemeV2, options: { variant: ButtonVariant; size: ComponentSize; invalid: boolean }) => { console.warn('getFormStyles is deprecated'); return { - label: getLabelStyles(theme), - legend: getLegendStyles(theme), - fieldValidationMessage: getFieldValidationMessageStyles(theme), + label: getLabelStyles(theme.v1), + legend: getLegendStyles(theme.v1), + fieldValidationMessage: getFieldValidationMessageStyles(theme.v1), button: getButtonStyles({ theme, variant: options.variant, size: options.size, }), input: getInputStyles({ theme, invalid: options.invalid }), - checkbox: getCheckboxStyles(theme), + checkbox: getCheckboxStyles(theme.v1), }; } ); diff --git a/packages/grafana-ui/src/components/IconButton/IconButton.story.tsx b/packages/grafana-ui/src/components/IconButton/IconButton.story.tsx index 2d25ac8e22c..3928f78dd6c 100644 --- a/packages/grafana-ui/src/components/IconButton/IconButton.story.tsx +++ b/packages/grafana-ui/src/components/IconButton/IconButton.story.tsx @@ -2,7 +2,7 @@ import React from 'react'; import { css } from '@emotion/css'; import { IconButton } from '@grafana/ui'; import { withCenteredStory } from '../../utils/storybook/withCenteredStory'; -import { useTheme } from '../../themes'; +import { useTheme2 } from '../../themes'; import { IconSize, IconName } from '../../types'; import mdx from './IconButton.mdx'; @@ -32,7 +32,7 @@ interface ScenarioProps { } const RenderScenario = ({ background }: ScenarioProps) => { - const theme = useTheme(); + const theme = useTheme2(); const sizes: IconSize[] = ['sm', 'md', 'lg', 'xl', 'xxl']; const icons: IconName[] = ['search', 'trash-alt', 'arrow-left', 'times']; @@ -40,7 +40,7 @@ const RenderScenario = ({ background }: ScenarioProps) => {
{ /** Name of the icon **/ @@ -28,7 +28,7 @@ type SurfaceType = 'dashboard' | 'panel' | 'header'; export const IconButton = React.forwardRef( ({ name, size = 'md', iconType, tooltip, tooltipPlacement, className, ...restProps }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getStyles(theme, size); const button = ( @@ -51,8 +51,8 @@ export const IconButton = React.forwardRef( IconButton.displayName = 'IconButton'; -const getStyles = stylesFactory((theme: GrafanaTheme, size: IconSize) => { - const hoverColor = theme.v2.palette.action.hover; +const getStyles = stylesFactory((theme: GrafanaThemeV2, size: IconSize) => { + const hoverColor = theme.palette.action.hover; const pixelSize = getSvgSize(size); const hoverSize = pixelSize / 2; @@ -70,9 +70,9 @@ const getStyles = stylesFactory((theme: GrafanaTheme, size: IconSize) => { align-items: center; justify-content: center; position: relative; - border-radius: ${theme.v2.shape.borderRadius()}; + border-radius: ${theme.shape.borderRadius()}; z-index: 0; - margin-right: ${theme.spacing.xs}; + margin-right: ${theme.spacing(0.5)}; &[disabled], &:disabled { @@ -102,15 +102,15 @@ const getStyles = stylesFactory((theme: GrafanaTheme, size: IconSize) => { &:focus, &:focus-visible { - ${focusCss(theme)} + ${getFocusStyles(theme)} } &:focus:not(:focus-visible) { - ${getMouseFocusStyles(theme.v2)} + ${getMouseFocusStyles(theme)} } &:hover { - color: ${theme.colors.linkHover}; + color: ${theme.palette.text.primary}; &:before { background-color: ${hoverColor}; diff --git a/packages/grafana-ui/src/components/InfoBox/InfoBox.tsx b/packages/grafana-ui/src/components/InfoBox/InfoBox.tsx index cc6f8ba6c2a..729df11c144 100644 --- a/packages/grafana-ui/src/components/InfoBox/InfoBox.tsx +++ b/packages/grafana-ui/src/components/InfoBox/InfoBox.tsx @@ -1,13 +1,13 @@ import React from 'react'; import { css, cx } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { Icon } from '../Icon/Icon'; import { IconButton } from '../IconButton/IconButton'; import { HorizontalGroup } from '../Layout/Layout'; import { AlertVariant } from '../Alert/Alert'; import panelArtDark from './panelArt_dark.svg'; import panelArtLight from './panelArt_light.svg'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; export interface InfoBoxProps extends Omit, 'title'> { children: React.ReactNode; @@ -31,7 +31,7 @@ export interface InfoBoxProps extends Omit, export const InfoBox = React.memo( React.forwardRef( ({ title, className, children, branded, url, urlTitle, onDismiss, severity = 'info', ...otherProps }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getInfoBoxStyles(theme, severity); const wrapperClassName = cx(branded ? styles.wrapperBranded : styles.wrapper, className); @@ -56,25 +56,25 @@ export const InfoBox = React.memo( ); InfoBox.displayName = 'InfoBox'; -const getInfoBoxStyles = stylesFactory((theme: GrafanaTheme, severity: AlertVariant) => { - const color = theme.v2.palette[severity]; +const getInfoBoxStyles = stylesFactory((theme: GrafanaThemeV2, severity: AlertVariant) => { + const color = theme.palette[severity]; return { wrapper: css` position: relative; - padding: ${theme.spacing.md}; - background-color: ${theme.colors.bg2}; + padding: ${theme.v1.spacing.md}; + background-color: ${theme.v1.colors.bg2}; border-left: 3px solid ${color.border}; - margin-bottom: ${theme.spacing.md}; + margin-bottom: ${theme.v1.spacing.md}; flex-grow: 1; - color: ${theme.colors.textSemiWeak}; - box-shadow: ${theme.v2.shadows.z1}; + color: ${theme.v1.colors.textSemiWeak}; + box-shadow: ${theme.shadows.z1}; code { font-size: ${theme.typography.size.sm}; - background-color: ${theme.colors.bg1}; - color: ${theme.colors.text}; - border: 1px solid ${theme.colors.border2}; + background-color: ${theme.v1.colors.bg1}; + color: ${theme.v1.colors.text}; + border: 1px solid ${theme.v1.colors.border2}; border-radius: 4px; } @@ -83,12 +83,12 @@ const getInfoBoxStyles = stylesFactory((theme: GrafanaTheme, severity: AlertVari } &--max-lg { - max-width: ${theme.breakpoints.lg}; + max-width: ${theme.v1.breakpoints.lg}; } `, wrapperBranded: css` - padding: ${theme.spacing.md}; - border-radius: ${theme.border.radius.md}; + padding: ${theme.v1.spacing.md}; + border-radius: ${theme.v1.border.radius.md}; position: relative; z-index: 0; @@ -100,7 +100,7 @@ const getInfoBoxStyles = stylesFactory((theme: GrafanaTheme, severity: AlertVari width: 100%; height: 100%; background-image: url(${theme.isLight ? panelArtLight : panelArtDark}); - border-radius: ${theme.border.radius.md}; + border-radius: ${theme.v1.border.radius.md}; background-position: 50% 50%; background-size: cover; filter: saturate(80%); @@ -113,9 +113,9 @@ const getInfoBoxStyles = stylesFactory((theme: GrafanaTheme, severity: AlertVari `, docsLink: css` display: inline-block; - margin-top: ${theme.spacing.md}; - font-size: ${theme.typography.size.sm}; - color: ${theme.colors.textSemiWeak}; + margin-top: ${theme.v1.spacing.md}; + font-size: ${theme.v1.typography.size.sm}; + color: ${theme.v1.colors.textSemiWeak}; `, }; }); diff --git a/packages/grafana-ui/src/components/Input/Input.tsx b/packages/grafana-ui/src/components/Input/Input.tsx index 0b61c57f227..84ca8811638 100644 --- a/packages/grafana-ui/src/components/Input/Input.tsx +++ b/packages/grafana-ui/src/components/Input/Input.tsx @@ -1,8 +1,8 @@ import React, { HTMLProps, ReactNode } from 'react'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css, cx } from '@emotion/css'; import { getFocusStyle, sharedInputStyle } from '../Forms/commonStyles'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { Spinner } from '../Spinner/Spinner'; import { useClientRect } from '../../utils/useClientRect'; @@ -24,7 +24,7 @@ export interface Props extends Omit, 'prefix' | 'siz } interface StyleDeps { - theme: GrafanaTheme; + theme: GrafanaThemeV2; invalid: boolean; width?: number; } @@ -44,7 +44,7 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: height: 100%; /* Min width specified for prefix/suffix classes used outside React component*/ min-width: ${prefixSuffixStaticWidth}; - color: ${theme.v2.palette.text.secondary}; + color: ${theme.palette.text.secondary}; `; return { @@ -53,14 +53,14 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: css` label: input-wrapper; display: flex; - width: ${width ? `${theme.v2.spacing(width)}` : '100%'}; - height: ${theme.v2.spacing(theme.v2.components.height.md)}; - border-radius: ${theme.v2.shape.borderRadius()}; + width: ${width ? `${theme.spacing(width)}` : '100%'}; + height: ${theme.spacing(theme.components.height.md)}; + border-radius: ${theme.shape.borderRadius()}; &:hover { > .prefix, .suffix, .input { - border-color: ${invalid ? theme.v2.palette.error.border : theme.v2.palette.primary.border}; + border-color: ${invalid ? theme.palette.error.border : theme.palette.primary.border}; } // only show number buttons on hover @@ -130,21 +130,21 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: `, input: cx( - getFocusStyle(theme), + getFocusStyle(theme.v1), sharedInputStyle(theme, invalid), css` label: input-input; position: relative; z-index: 0; flex-grow: 1; - border-radius: ${theme.v2.shape.borderRadius()}; + border-radius: ${theme.shape.borderRadius()}; height: 100%; width: 100%; ` ), inputDisabled: css` - background-color: ${theme.v2.palette.action.disabledBackground}; - color: ${theme.v2.palette.action.disabledText}; + background-color: ${theme.palette.action.disabledBackground}; + color: ${theme.palette.action.disabledText}; `, addon: css` label: input-addon; @@ -181,8 +181,8 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: prefixSuffix, css` label: input-prefix; - padding-left: ${theme.v2.spacing(1)}; - padding-right: ${theme.v2.spacing(0.5)}; + padding-left: ${theme.spacing(1)}; + padding-right: ${theme.spacing(0.5)}; border-right: none; border-top-right-radius: 0; border-bottom-right-radius: 0; @@ -192,8 +192,8 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: prefixSuffix, css` label: input-suffix; - padding-left: ${theme.v2.spacing(1)}; - padding-right: ${theme.v2.spacing(0.5)}; + padding-left: ${theme.spacing(1)}; + padding-right: ${theme.spacing(0.5)}; margin-bottom: -2px; border-left: none; border-top-left-radius: 0; @@ -203,7 +203,7 @@ export const getInputStyles = stylesFactory(({ theme, invalid = false, width }: ), loadingIndicator: css` & + * { - margin-left: ${theme.v2.spacing(0.5)}; + margin-left: ${theme.spacing(0.5)}; } `, }; @@ -219,7 +219,7 @@ export const Input = React.forwardRef((props, ref) => { const [prefixRect, prefixRef] = useClientRect(); const [suffixRect, suffixRef] = useClientRect(); - const theme = useTheme(); + const theme = useTheme2(); const styles = getInputStyles({ theme, invalid: !!invalid, width }); return ( diff --git a/packages/grafana-ui/src/components/Logs/LogLabelStatsRow.tsx b/packages/grafana-ui/src/components/Logs/LogLabelStatsRow.tsx index ad73f1071ed..d477a1851e7 100644 --- a/packages/grafana-ui/src/components/Logs/LogLabelStatsRow.tsx +++ b/packages/grafana-ui/src/components/Logs/LogLabelStatsRow.tsx @@ -1,8 +1,7 @@ -import React, { FunctionComponent, useContext } from 'react'; +import React, { FunctionComponent } from 'react'; import { css, cx } from '@emotion/css'; - -import { ThemeContext } from '../../themes/ThemeContext'; import { GrafanaTheme } from '@grafana/data'; +import { useStyles } from '../../themes/ThemeContext'; const getStyles = (theme: GrafanaTheme) => ({ logsStatsRow: css` @@ -58,8 +57,7 @@ export interface Props { } export const LogLabelStatsRow: FunctionComponent = ({ active, count, proportion, value }) => { - const theme = useContext(ThemeContext); - const style = getStyles(theme); + const style = useStyles(getStyles); const percent = `${Math.round(proportion * 100)}%`; const barStyle = { width: percent }; const className = active ? cx([style.logsStatsRow, style.logsStatsRowActive]) : cx([style.logsStatsRow]); diff --git a/packages/grafana-ui/src/components/Logs/LogRowContext.tsx b/packages/grafana-ui/src/components/Logs/LogRowContext.tsx index a1331a97e72..0f1981f4cfa 100644 --- a/packages/grafana-ui/src/components/Logs/LogRowContext.tsx +++ b/packages/grafana-ui/src/components/Logs/LogRowContext.tsx @@ -1,10 +1,10 @@ -import React, { useContext, useRef, useState, useLayoutEffect, useEffect } from 'react'; +import React, { useRef, useState, useLayoutEffect, useEffect } from 'react'; import { GrafanaTheme, DataQueryError, LogRowModel, textUtil } from '@grafana/data'; import { css, cx } from '@emotion/css'; import { Alert } from '../Alert/Alert'; import { LogRowContextRows, LogRowContextQueryErrors, HasMoreContextRows } from './LogRowContextProvider'; -import { ThemeContext } from '../../themes/ThemeContext'; +import { useStyles } from '../../themes/ThemeContext'; import { CustomScrollbar } from '../CustomScrollbar/CustomScrollbar'; import { List } from '../List/List'; import { ClickOutsideWrapper } from '../ClickOutsideWrapper/ClickOutsideWrapper'; @@ -66,8 +66,7 @@ const LogRowContextGroupHeader: React.FunctionComponent { - const theme = useContext(ThemeContext); - const { header } = getLogRowContextStyles(theme); + const { header } = useStyles(getLogRowContextStyles); return (
@@ -105,8 +104,7 @@ export const LogRowContextGroup: React.FunctionComponent { - const theme = useContext(ThemeContext); - const { commonStyles, logs } = getLogRowContextStyles(theme); + const { commonStyles, logs } = useStyles(getLogRowContextStyles); const [scrollTop, setScrollTop] = useState(0); const listContainerRef = useRef() as React.RefObject; diff --git a/packages/grafana-ui/src/components/Menu/Menu.tsx b/packages/grafana-ui/src/components/Menu/Menu.tsx index 951f59ea0b1..1df1c4256f5 100644 --- a/packages/grafana-ui/src/components/Menu/Menu.tsx +++ b/packages/grafana-ui/src/components/Menu/Menu.tsx @@ -1,7 +1,7 @@ import React from 'react'; import { css } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; -import { useStyles } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; +import { useStyles2 } from '../../themes'; /** @internal */ export interface MenuProps extends React.HTMLAttributes { @@ -14,7 +14,7 @@ export interface MenuProps extends React.HTMLAttributes { /** @internal */ export const Menu = React.forwardRef( ({ header, children, ariaLabel, ...otherProps }, ref) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); return (
@@ -27,17 +27,17 @@ export const Menu = React.forwardRef( Menu.displayName = 'Menu'; /** @internal */ -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { return { header: css` - padding: ${theme.v2.spacing(0.5, 0.5, 1, 0.5)}; - border-bottom: 1px solid ${theme.v2.palette.border.medium}; + padding: ${theme.spacing(0.5, 0.5, 1, 0.5)}; + border-bottom: 1px solid ${theme.palette.border.medium}; `, wrapper: css` - background: ${theme.v2.palette.background.secondary}; - box-shadow: ${theme.v2.shadows.z2}; + background: ${theme.palette.background.secondary}; + box-shadow: ${theme.shadows.z2}; display: inline-block; - border-radius: ${theme.v2.shape.borderRadius()}; + border-radius: ${theme.shape.borderRadius()}; `, }; }; diff --git a/packages/grafana-ui/src/components/Menu/MenuGroup.tsx b/packages/grafana-ui/src/components/Menu/MenuGroup.tsx index 86800bdd1f1..09fbe57672b 100644 --- a/packages/grafana-ui/src/components/Menu/MenuGroup.tsx +++ b/packages/grafana-ui/src/components/Menu/MenuGroup.tsx @@ -1,7 +1,7 @@ import React from 'react'; import { css } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; -import { useStyles } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; +import { useStyles2 } from '../../themes'; import { MenuItemProps } from './MenuItem'; /** @internal */ @@ -21,7 +21,7 @@ export interface MenuGroupProps extends Partial { /** @internal */ export const MenuGroup: React.FC = ({ label, children, ariaLabel }) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); return (
@@ -37,12 +37,12 @@ export const MenuGroup: React.FC = ({ label, children, ariaLabel MenuGroup.displayName = 'MenuGroup'; /** @internal */ -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { return { groupLabel: css` - color: ${theme.v2.palette.text.secondary}; - font-size: ${theme.v2.typography.size.sm}; - padding: ${theme.v2.spacing(0.5, 1)}; + color: ${theme.palette.text.secondary}; + font-size: ${theme.typography.size.sm}; + padding: ${theme.spacing(0.5, 1)}; `, }; }; diff --git a/packages/grafana-ui/src/components/Menu/MenuItem.tsx b/packages/grafana-ui/src/components/Menu/MenuItem.tsx index 10b6e2197e2..7b0e652ab3d 100644 --- a/packages/grafana-ui/src/components/Menu/MenuItem.tsx +++ b/packages/grafana-ui/src/components/Menu/MenuItem.tsx @@ -1,7 +1,7 @@ import React from 'react'; import { css, cx } from '@emotion/css'; -import { GrafanaTheme, LinkTarget } from '@grafana/data'; -import { useStyles } from '../../themes'; +import { GrafanaThemeV2, LinkTarget } from '@grafana/data'; +import { useStyles2 } from '../../themes'; import { Icon } from '../Icon/Icon'; import { IconName } from '../../types'; @@ -28,7 +28,7 @@ export interface MenuItemProps { /** @internal */ export const MenuItem: React.FC = React.memo( ({ url, icon, label, ariaLabel, target, onClick, className, active }) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); const itemStyle = cx( { [styles.item]: true, @@ -55,16 +55,16 @@ export const MenuItem: React.FC = React.memo( MenuItem.displayName = 'MenuItem'; /** @internal */ -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { return { link: css` - color: ${theme.v2.palette.text.primary}; + color: ${theme.palette.text.primary}; display: flex; cursor: pointer; padding: 5px 12px 5px 10px; &:hover { - color: ${theme.v2.palette.text.primary}; + color: ${theme.palette.text.primary}; text-decoration: none; } `, @@ -74,16 +74,16 @@ const getStyles = (theme: GrafanaTheme) => { white-space: nowrap; &:hover { - background: ${theme.v2.palette.action.hover}; + background: ${theme.palette.action.hover}; } `, activeItem: css` - background: ${theme.v2.palette.action.selected}; + background: ${theme.palette.action.selected}; `, icon: css` opacity: 0.7; margin-right: 10px; - color: ${theme.v2.palette.text.secondary}; + color: ${theme.palette.text.secondary}; `, }; }; diff --git a/packages/grafana-ui/src/components/Modal/Modal.tsx b/packages/grafana-ui/src/components/Modal/Modal.tsx index 1b972a0d817..edf4f8ecc82 100644 --- a/packages/grafana-ui/src/components/Modal/Modal.tsx +++ b/packages/grafana-ui/src/components/Modal/Modal.tsx @@ -1,7 +1,7 @@ import React, { FC, PropsWithChildren, useCallback, useEffect } from 'react'; import { Portal } from '../Portal/Portal'; import { cx } from '@emotion/css'; -import { useTheme } from '../../themes'; +import { useTheme2 } from '../../themes'; import { IconName } from '../../types'; import { getModalStyles } from './getModalStyles'; import { ModalHeader } from './ModalHeader'; @@ -34,7 +34,7 @@ export function Modal(props: PropsWithChildren): ReturnType> { onDismiss: propsOnDismiss, onClickBackdrop, } = props; - const theme = useTheme(); + const theme = useTheme2(); const styles = getModalStyles(theme); const onDismiss = useCallback(() => { if (propsOnDismiss) { diff --git a/packages/grafana-ui/src/components/Modal/ModalHeader.tsx b/packages/grafana-ui/src/components/Modal/ModalHeader.tsx index 4a8d46e4f20..2bce1bc3fd5 100644 --- a/packages/grafana-ui/src/components/Modal/ModalHeader.tsx +++ b/packages/grafana-ui/src/components/Modal/ModalHeader.tsx @@ -1,7 +1,7 @@ -import React, { useContext } from 'react'; +import React from 'react'; import { getModalStyles } from './getModalStyles'; import { IconName } from '../../types'; -import { ThemeContext } from '../../themes'; +import { useStyles2 } from '../../themes'; import { Icon } from '../Icon/Icon'; import { Tooltip } from '..'; @@ -12,8 +12,7 @@ interface Props { } export const ModalHeader: React.FC = ({ icon, iconTooltip, title, children }) => { - const theme = useContext(ThemeContext); - const styles = getModalStyles(theme); + const styles = useStyles2(getModalStyles); return ( <> diff --git a/packages/grafana-ui/src/components/Modal/getModalStyles.ts b/packages/grafana-ui/src/components/Modal/getModalStyles.ts index f86c7528b59..35371f299f1 100644 --- a/packages/grafana-ui/src/components/Modal/getModalStyles.ts +++ b/packages/grafana-ui/src/components/Modal/getModalStyles.ts @@ -1,18 +1,18 @@ import { css } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { stylesFactory } from '../../themes'; -export const getModalStyles = stylesFactory((theme: GrafanaTheme) => { +export const getModalStyles = stylesFactory((theme: GrafanaThemeV2) => { // rgba(1,4,9,0.8) const backdropBackground = 'rgba(0, 0, 0, 0.5)'; - const borderRadius = theme.v2.shape.borderRadius(2); + const borderRadius = theme.shape.borderRadius(2); return { modal: css` position: fixed; - z-index: ${theme.v2.zIndex.modal}; - background: ${theme.v2.palette.background.primary}; - box-shadow: ${theme.v2.shadows.z4}; + z-index: ${theme.zIndex.modal}; + background: ${theme.palette.background.primary}; + box-shadow: ${theme.shadows.z4}; border-radius: ${borderRadius}; background-clip: padding-box; outline: none; @@ -30,26 +30,26 @@ export const getModalStyles = stylesFactory((theme: GrafanaTheme) => { right: 0; bottom: 0; left: 0; - z-index: ${theme.v2.zIndex.modalBackdrop}; + z-index: ${theme.zIndex.modalBackdrop}; background-color: ${backdropBackground}; `, modalHeader: css` label: modalHeader; - background: ${theme.colors.bg2}; - border-bottom: 1px solid ${theme.colors.pageHeaderBorder}; + background: ${theme.palette.background.secondary}; + border-bottom: 1px solid ${theme.palette.border.weak}; border-radius: ${borderRadius} ${borderRadius} 0 0; display: flex; height: 42px; `, modalHeaderTitle: css` font-size: ${theme.typography.size.lg}; - margin: 0 ${theme.spacing.md}; + margin: 0 ${theme.spacing(2)}; display: flex; align-items: center; line-height: 42px; `, modalHeaderIcon: css` - margin-right: ${theme.spacing.md}; + margin-right: ${theme.spacing(2)}; font-size: inherit; &:before { vertical-align: baseline; @@ -61,13 +61,13 @@ export const getModalStyles = stylesFactory((theme: GrafanaTheme) => { align-items: center; flex-grow: 1; justify-content: flex-end; - padding-right: ${theme.spacing.sm}; + padding-right: ${theme.spacing(1)}; `, modalContent: css` - padding: calc(${theme.spacing.d} * 2); + padding: calc(${theme.spacing.gridSize} * 2); overflow: auto; width: 100%; - max-height: calc(90vh - ${theme.spacing.d} * 2); + max-height: calc(90vh - ${theme.spacing.gridSize} * 2); `, }; }); diff --git a/packages/grafana-ui/src/components/NodeGraph/EdgeLabel.tsx b/packages/grafana-ui/src/components/NodeGraph/EdgeLabel.tsx index 9a84aaab98a..52ea0ff5f28 100644 --- a/packages/grafana-ui/src/components/NodeGraph/EdgeLabel.tsx +++ b/packages/grafana-ui/src/components/NodeGraph/EdgeLabel.tsx @@ -1,15 +1,11 @@ import React, { memo } from 'react'; import { EdgeDatum, NodeDatum } from './types'; import { css } from '@emotion/css'; -import { stylesFactory, useTheme } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; -import tinycolor from 'tinycolor2'; -import lightTheme from '../../themes/light'; -import darkTheme from '../../themes/dark'; +import { useStyles2 } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; import { shortenLine } from './utils'; -const getStyles = stylesFactory((theme: GrafanaTheme) => { - const inverseTheme = theme.isDark ? lightTheme : darkTheme; +const getStyles = (theme: GrafanaThemeV2) => { return { mainGroup: css` pointer-events: none; @@ -17,14 +13,14 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => { `, background: css` - fill: ${tinycolor(inverseTheme.colors.bodyBg).setAlpha(0.8).toHex8String()}; + fill: ${theme.components.tooltip.background}; `, text: css` - fill: ${inverseTheme.colors.text}; + fill: ${theme.components.tooltip.text}; `, }; -}); +}; interface Props { edge: EdgeDatum; @@ -49,7 +45,7 @@ export const EdgeLabel = memo(function EdgeLabel(props: Props) { x: line.x1 + (line.x2 - line.x1) / 2, y: line.y1 + (line.y2 - line.y1) / 2, }; - const styles = getStyles(useTheme()); + const styles = useStyles2(getStyles); return ( diff --git a/packages/grafana-ui/src/components/NodeGraph/utils.test.ts b/packages/grafana-ui/src/components/NodeGraph/utils.test.ts index 3376fcccf8d..5603fff9a0c 100644 --- a/packages/grafana-ui/src/components/NodeGraph/utils.test.ts +++ b/packages/grafana-ui/src/components/NodeGraph/utils.test.ts @@ -1,9 +1,11 @@ +import { createTheme } from '@grafana/data'; import { makeEdgesDataFrame, makeNodesDataFrame, processNodes } from './utils'; -import lightTheme from '../../themes/light'; describe('processNodes', () => { + const theme = createTheme(); + it('handles empty args', async () => { - expect(processNodes(undefined, undefined, lightTheme)).toEqual({ nodes: [], edges: [] }); + expect(processNodes(undefined, undefined, theme.v1)).toEqual({ nodes: [], edges: [] }); }); it('returns proper nodes and edges', async () => { @@ -15,7 +17,7 @@ describe('processNodes', () => { [0, 2], [1, 2], ]), - lightTheme + theme.v1 ) ).toEqual({ nodes: [ @@ -30,7 +32,7 @@ describe('processNodes', () => { value: 0.5, }, ], - color: 'rgb(213, 172, 32)', + color: 'rgb(226, 192, 61)', dataFrameRowIndex: 0, id: '0', incoming: 0, @@ -50,7 +52,7 @@ describe('processNodes', () => { value: 0.5, }, ], - color: 'rgb(213, 172, 32)', + color: 'rgb(226, 192, 61)', dataFrameRowIndex: 1, id: '1', incoming: 1, @@ -70,7 +72,7 @@ describe('processNodes', () => { value: 0.5, }, ], - color: 'rgb(213, 172, 32)', + color: 'rgb(226, 192, 61)', dataFrameRowIndex: 2, id: '2', incoming: 2, diff --git a/packages/grafana-ui/src/components/PageLayout/PageToolbar.tsx b/packages/grafana-ui/src/components/PageLayout/PageToolbar.tsx index 80e182f7fdc..a5a3634639c 100644 --- a/packages/grafana-ui/src/components/PageLayout/PageToolbar.tsx +++ b/packages/grafana-ui/src/components/PageLayout/PageToolbar.tsx @@ -1,7 +1,7 @@ import React, { FC, ReactNode } from 'react'; import { css, cx } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; -import { useStyles } from '../../themes/ThemeContext'; +import { GrafanaThemeV2 } from '@grafana/data'; +import { useStyles2 } from '../../themes/ThemeContext'; import { IconName } from '../../types'; import { Icon } from '../Icon/Icon'; import { styleMixins } from '../../themes'; @@ -35,7 +35,7 @@ export const PageToolbar: FC = React.memo( isFullscreen, className, }) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); /** * .page-toolbar css class is used for some legacy css view modes (TV/Kiosk) and @@ -109,12 +109,12 @@ export const PageToolbar: FC = React.memo( PageToolbar.displayName = 'PageToolbar'; -const getStyles = (theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { const { spacing, typography } = theme; const titleStyles = ` font-size: ${typography.size.lg}; - padding-left: ${spacing.sm}; + padding-left: ${spacing(1)}; white-space: nowrap; text-overflow: ellipsis; overflow: hidden; @@ -124,7 +124,7 @@ const getStyles = (theme: GrafanaTheme) => { background: none; border: none; - @media ${styleMixins.mediaUp(theme.breakpoints.xl)} { + @media ${styleMixins.mediaUp(theme.v1.breakpoints.xl)} { max-width: unset; } `; @@ -132,10 +132,10 @@ const getStyles = (theme: GrafanaTheme) => { return { toolbar: css` display: flex; - background: ${theme.v2.palette.background.canvas}; + background: ${theme.palette.background.canvas}; justify-content: flex-end; flex-wrap: wrap; - padding: ${theme.v2.spacing(0, 1, 1, 2)}; + padding: ${theme.spacing(0, 1, 1, 2)}; `, toolbarLeft: css` display: flex; @@ -146,19 +146,19 @@ const getStyles = (theme: GrafanaTheme) => { flex-grow: 1; `, pageIcon: css` - padding-top: ${spacing.sm}; + padding-top: ${spacing(1)}; align-items: center; display: none; - @media ${styleMixins.mediaUp(theme.breakpoints.md)} { + @media ${styleMixins.mediaUp(theme.v1.breakpoints.md)} { display: flex; } `, titleWrapper: css` display: flex; align-items: center; - padding-top: ${spacing.sm}; - padding-right: ${spacing.sm}; + padding-top: ${spacing(1)}; + padding-right: ${spacing(1)}; min-width: 0; overflow: hidden; `, @@ -178,13 +178,13 @@ const getStyles = (theme: GrafanaTheme) => { parentLink: css` display: none; - @media ${styleMixins.mediaUp(theme.breakpoints.md)} { + @media ${styleMixins.mediaUp(theme.v1.breakpoints.md)} { display: inline-block; } `, actionWrapper: css` - padding-left: ${spacing.sm}; - padding-top: ${spacing.sm}; + padding-left: ${spacing(1)}; + padding-top: ${spacing(1)}; `, leftActionItem: css` display: none; @@ -192,9 +192,9 @@ const getStyles = (theme: GrafanaTheme) => { position: relative; top: 5px; align-items: center; - padding-left: ${spacing.xs}; + padding-left: ${spacing(0.5)}; - @media ${styleMixins.mediaUp(theme.breakpoints.md)} { + @media ${styleMixins.mediaUp(theme.v1.breakpoints.md)} { display: flex; } `, diff --git a/packages/grafana-ui/src/components/Select/IndicatorsContainer.tsx b/packages/grafana-ui/src/components/Select/IndicatorsContainer.tsx index ecd5d51f6e7..094906cb98d 100644 --- a/packages/grafana-ui/src/components/Select/IndicatorsContainer.tsx +++ b/packages/grafana-ui/src/components/Select/IndicatorsContainer.tsx @@ -1,11 +1,11 @@ import React from 'react'; -import { useTheme } from '../../themes/ThemeContext'; +import { useTheme2 } from '../../themes/ThemeContext'; import { getInputStyles } from '../Input/Input'; import { cx, css } from '@emotion/css'; export const IndicatorsContainer = React.forwardRef>((props, ref) => { const { children } = props; - const theme = useTheme(); + const theme = useTheme2(); const styles = getInputStyles({ theme, invalid: false }); return ( diff --git a/packages/grafana-ui/src/components/Select/InputControl.tsx b/packages/grafana-ui/src/components/Select/InputControl.tsx index 3f4e4dc08a3..34118a307f7 100644 --- a/packages/grafana-ui/src/components/Select/InputControl.tsx +++ b/packages/grafana-ui/src/components/Select/InputControl.tsx @@ -1,10 +1,10 @@ import React from 'react'; -import { useTheme } from '../../themes/ThemeContext'; +import { useTheme2 } from '../../themes/ThemeContext'; import { sharedInputStyle } from '../Forms/commonStyles'; import { getInputStyles } from '../Input/Input'; import { css, cx } from '@emotion/css'; import { stylesFactory } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { focusCss } from '../../themes/mixins'; interface InputControlProps { @@ -17,7 +17,7 @@ interface InputControlProps { } const getInputControlStyles = stylesFactory( - (theme: GrafanaTheme, invalid: boolean, focused: boolean, disabled: boolean, withPrefix: boolean) => { + (theme: GrafanaThemeV2, invalid: boolean, focused: boolean, disabled: boolean, withPrefix: boolean) => { const styles = getInputStyles({ theme, invalid }); return { @@ -26,7 +26,7 @@ const getInputControlStyles = stylesFactory( sharedInputStyle(theme, invalid), focused && css` - ${focusCss(theme)} + ${focusCss(theme.v1)} `, disabled && styles.inputDisabled, css` @@ -60,7 +60,7 @@ const getInputControlStyles = stylesFactory( export const InputControl = React.forwardRef>( function InputControl({ focused, invalid, disabled, children, innerProps, prefix, ...otherProps }, ref) { - const theme = useTheme(); + const theme = useTheme2(); const styles = getInputControlStyles(theme, invalid, focused, disabled, !!prefix); return (
diff --git a/packages/grafana-ui/src/components/Select/MultiValue.tsx b/packages/grafana-ui/src/components/Select/MultiValue.tsx index 2adbd7bf7a7..5d022a62f8a 100644 --- a/packages/grafana-ui/src/components/Select/MultiValue.tsx +++ b/packages/grafana-ui/src/components/Select/MultiValue.tsx @@ -1,5 +1,5 @@ import React from 'react'; -import { useTheme } from '../../themes'; +import { useTheme2 } from '../../themes'; import { getSelectStyles } from './getSelectStyles'; import { Icon } from '../Icon/Icon'; @@ -8,7 +8,7 @@ interface MultiValueContainerProps { } export const MultiValueContainer: React.FC = ({ innerProps, children }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSelectStyles(theme); return ( @@ -23,7 +23,7 @@ export type MultiValueRemoveProps = { }; export const MultiValueRemove: React.FC = ({ children, innerProps }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSelectStyles(theme); return (
diff --git a/packages/grafana-ui/src/components/Select/SelectBase.tsx b/packages/grafana-ui/src/components/Select/SelectBase.tsx index 4545acdf5b6..31a3dfa7115 100644 --- a/packages/grafana-ui/src/components/Select/SelectBase.tsx +++ b/packages/grafana-ui/src/components/Select/SelectBase.tsx @@ -16,7 +16,7 @@ import { DropdownIndicator } from './DropdownIndicator'; import { SelectOptionGroup } from './SelectOptionGroup'; import { SingleValue } from './SingleValue'; import { MultiValueContainer, MultiValueRemove } from './MultiValue'; -import { useTheme } from '../../themes'; +import { useTheme2 } from '../../themes'; import { getSelectStyles } from './getSelectStyles'; import { cleanValue, findSelectedValue } from './utils'; import { SelectBaseProps, SelectValue } from './types'; @@ -135,7 +135,7 @@ export function SelectBase({ value, width, }: SelectBaseProps) { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSelectStyles(theme); const onChangeWithEmpty = useCallback( (value: SelectValue) => { @@ -245,7 +245,7 @@ export function SelectBase({ css(props.getStyles('placeholder', props)), css` display: inline-block; - color: ${theme.colors.formInputPlaceholderText}; + color: ${theme.palette.text.disabled}; position: absolute; top: 50%; transform: translateY(-50%); diff --git a/packages/grafana-ui/src/components/Select/SelectMenu.tsx b/packages/grafana-ui/src/components/Select/SelectMenu.tsx index bea8b137be4..008d871ba93 100644 --- a/packages/grafana-ui/src/components/Select/SelectMenu.tsx +++ b/packages/grafana-ui/src/components/Select/SelectMenu.tsx @@ -1,5 +1,5 @@ import React from 'react'; -import { useTheme } from '../../themes/ThemeContext'; +import { useTheme2 } from '../../themes/ThemeContext'; import { getSelectStyles } from './getSelectStyles'; import { cx } from '@emotion/css'; import { SelectableValue } from '@grafana/data'; @@ -12,7 +12,7 @@ interface SelectMenuProps { } export const SelectMenu = React.forwardRef>((props, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSelectStyles(theme); const { children, maxHeight, innerRef, innerProps } = props; @@ -38,7 +38,7 @@ interface SelectMenuOptionProps { export const SelectMenuOptions = React.forwardRef>>( (props, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSelectStyles(theme); const { children, innerProps, data, renderOptionLabel, isSelected, isFocused } = props; diff --git a/packages/grafana-ui/src/components/Select/SingleValue.tsx b/packages/grafana-ui/src/components/Select/SingleValue.tsx index 818df751e63..ed5656c991d 100644 --- a/packages/grafana-ui/src/components/Select/SingleValue.tsx +++ b/packages/grafana-ui/src/components/Select/SingleValue.tsx @@ -2,16 +2,16 @@ import React from 'react'; import { css, cx } from '@emotion/css'; import { components, SingleValueProps } from 'react-select'; import { useDelayedSwitch } from '../../utils/useDelayedSwitch'; -import { stylesFactory, useTheme } from '../../themes'; +import { useStyles2 } from '../../themes'; import { SlideOutTransition } from '../transitions/SlideOutTransition'; import { FadeTransition } from '../transitions/FadeTransition'; import { Spinner } from '../Spinner/Spinner'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; -const getStyles = stylesFactory((theme: GrafanaTheme) => { +const getStyles = (theme: GrafanaThemeV2) => { const singleValue = css` label: singleValue; - color: ${theme.v2.components.input.text}; + color: ${theme.components.input.text}; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; @@ -36,7 +36,9 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => { `; return { singleValue, container, item }; -}); +}; + +type StylesType = ReturnType; interface Props extends SingleValueProps<{ @@ -47,8 +49,7 @@ interface Props export const SingleValue = (props: Props) => { const { children, data } = props; - const theme = useTheme(); - const styles = getStyles(theme); + const styles = useStyles2(getStyles); const loading = useDelayedSwitch(data.loading || false, { delay: 250, duration: 750 }); @@ -56,7 +57,7 @@ export const SingleValue = (props: Props) => {
{data.imgUrl ? ( - + ) : (
@@ -70,17 +71,14 @@ export const SingleValue = (props: Props) => { ); }; -const FadeWithImage = (props: { loading: boolean; imgUrl: string }) => { - const theme = useTheme(); - const styles = getStyles(theme); - +const FadeWithImage = (props: { loading: boolean; imgUrl: string; styles: StylesType }) => { return ( -
+
- + - +
); diff --git a/packages/grafana-ui/src/components/Select/ValueContainer.tsx b/packages/grafana-ui/src/components/Select/ValueContainer.tsx index a426aaab400..fbcf76805da 100644 --- a/packages/grafana-ui/src/components/Select/ValueContainer.tsx +++ b/packages/grafana-ui/src/components/Select/ValueContainer.tsx @@ -1,7 +1,7 @@ import React, { ReactNode } from 'react'; import { cx } from '@emotion/css'; import { GrafanaTheme } from '@grafana/data'; -import { withTheme } from '../../themes/ThemeContext'; +import { withTheme2 } from '../../themes/ThemeContext'; import { getSelectStyles } from './getSelectStyles'; class UnthemedValueContainer extends React.Component { @@ -33,4 +33,4 @@ class UnthemedValueContainer extends React.Component { +export const getSelectStyles = stylesFactory((theme: GrafanaThemeV2) => { return { menu: css` label: grafana-select-menu; - background: ${theme.v2.palette.background.secondary}; - box-shadow: ${theme.v2.shadows.z3}; + background: ${theme.palette.background.secondary}; + box-shadow: ${theme.shadows.z3}; position: relative; min-width: 100%; z-index: 1; @@ -24,7 +24,7 @@ export const getSelectStyles = stylesFactory((theme: GrafanaTheme) => { border-left: 2px solid transparent; &:hover { - background: ${theme.v2.palette.action.hover}; + background: ${theme.palette.action.hover}; } `, optionImage: css` @@ -35,28 +35,28 @@ export const getSelectStyles = stylesFactory((theme: GrafanaTheme) => { optionDescription: css` label: grafana-select-option-description; font-weight: normal; - font-size: ${theme.v2.typography.size.sm}; - color: ${theme.v2.palette.text.secondary}; + font-size: ${theme.typography.size.sm}; + color: ${theme.palette.text.secondary}; white-space: normal; - line-height: ${theme.v2.typography.body.lineHeight}; + line-height: ${theme.typography.body.lineHeight}; `, optionBody: css` label: grafana-select-option-body; display: flex; - font-weight: ${theme.v2.typography.fontWeightMedium}; + font-weight: ${theme.typography.fontWeightMedium}; flex-direction: column; flex-grow: 1; `, optionFocused: css` label: grafana-select-option-focused; - background: ${theme.v2.palette.action.focus}; + background: ${theme.palette.action.focus}; `, optionSelected: css` - background: ${theme.v2.palette.action.selected}; + background: ${theme.palette.action.selected}; `, singleValue: css` label: grafana-select-single-value; - color: ${theme.v2.components.input.text}; + color: ${theme.components.input.text}; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; @@ -79,7 +79,7 @@ export const getSelectStyles = stylesFactory((theme: GrafanaTheme) => { `, loadingMessage: css` label: grafana-select-loading-message; - padding: ${theme.v2.spacing(1)}; + padding: ${theme.spacing(1)}; text-align: center; width: 100%; `, @@ -88,16 +88,16 @@ export const getSelectStyles = stylesFactory((theme: GrafanaTheme) => { display: flex; align-items: center; line-height: 1; - background: ${theme.v2.palette.background.secondary}; - border-radius: ${theme.v2.shape.borderRadius()}; - margin: ${theme.v2.spacing(0, 1, 0, 0)}; - padding: ${theme.v2.spacing(0.25, 0, 0.25, 1)}; - color: ${theme.v2.palette.text.primary}; + background: ${theme.palette.background.secondary}; + border-radius: ${theme.shape.borderRadius()}; + margin: ${theme.spacing(0, 1, 0, 0)}; + padding: ${theme.spacing(0.25, 0, 0.25, 1)}; + color: ${theme.palette.text.primary}; font-size: ${theme.typography.size.sm}; `, multiValueRemove: css` label: grafana-select-multi-value-remove; - margin: ${theme.v2.spacing(0, 0.5)}; + margin: ${theme.spacing(0, 0.5)}; cursor: pointer; `, }; diff --git a/packages/grafana-ui/src/components/Slider/RangeSlider.tsx b/packages/grafana-ui/src/components/Slider/RangeSlider.tsx index 209cfc719fd..02fefaf5036 100644 --- a/packages/grafana-ui/src/components/Slider/RangeSlider.tsx +++ b/packages/grafana-ui/src/components/Slider/RangeSlider.tsx @@ -2,7 +2,7 @@ import React, { FunctionComponent } from 'react'; import { Range as RangeComponent, createSliderWithTooltip } from 'rc-slider'; import { cx } from '@emotion/css'; import { Global } from '@emotion/react'; -import { useTheme } from '../../themes/ThemeContext'; +import { useTheme2 } from '../../themes/ThemeContext'; import { getStyles } from './styles'; import { RangeSliderProps } from './types'; @@ -24,7 +24,7 @@ export const RangeSlider: FunctionComponent = ({ tooltipAlwaysVisible = true, }) => { const isHorizontal = orientation === 'horizontal'; - const theme = useTheme(); + const theme = useTheme2(); const styles = getStyles(theme, isHorizontal); const RangeWithTooltip = createSliderWithTooltip(RangeComponent); return ( diff --git a/packages/grafana-ui/src/components/Slider/Slider.tsx b/packages/grafana-ui/src/components/Slider/Slider.tsx index 8e09173b909..89caa014427 100644 --- a/packages/grafana-ui/src/components/Slider/Slider.tsx +++ b/packages/grafana-ui/src/components/Slider/Slider.tsx @@ -2,7 +2,7 @@ import React, { useState, useCallback, ChangeEvent, FunctionComponent } from 're import SliderComponent from 'rc-slider'; import { cx } from '@emotion/css'; import { Global } from '@emotion/react'; -import { useTheme } from '../../themes/ThemeContext'; +import { useTheme2 } from '../../themes/ThemeContext'; import { getStyles } from './styles'; import { SliderProps } from './types'; import { Input } from '../Input/Input'; @@ -21,7 +21,7 @@ export const Slider: FunctionComponent = ({ value, }) => { const isHorizontal = orientation === 'horizontal'; - const theme = useTheme(); + const theme = useTheme2(); const styles = getStyles(theme, isHorizontal); const SliderWithTooltip = SliderComponent; const [sliderValue, setSliderValue] = useState(value || min); diff --git a/packages/grafana-ui/src/components/Slider/styles.ts b/packages/grafana-ui/src/components/Slider/styles.ts index 2d45fe5b40a..6fa544275da 100644 --- a/packages/grafana-ui/src/components/Slider/styles.ts +++ b/packages/grafana-ui/src/components/Slider/styles.ts @@ -1,27 +1,20 @@ import { stylesFactory } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; -import { focusCss } from '../../themes/mixins'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css as cssCore } from '@emotion/react'; import { css } from '@emotion/css'; -export const getFocusStyle = (theme: GrafanaTheme) => css` - &:focus { - ${focusCss(theme)} - } -`; - -export const getStyles = stylesFactory((theme: GrafanaTheme, isHorizontal: boolean) => { +export const getStyles = stylesFactory((theme: GrafanaThemeV2, isHorizontal: boolean) => { const { spacing } = theme; - const railColor = theme.v2.palette.border.strong; - const trackColor = theme.v2.palette.primary.main; - const handleColor = theme.v2.palette.primary.main; - const blueOpacity = theme.v2.palette.primary.transparent; + const railColor = theme.palette.border.strong; + const trackColor = theme.palette.primary.main; + const handleColor = theme.palette.primary.main; + const blueOpacity = theme.palette.primary.transparent; const hoverSyle = `box-shadow: 0px 0px 0px 6px ${blueOpacity}`; return { container: css` width: 100%; - margin: ${isHorizontal ? 'none' : `${spacing.sm} ${spacing.lg} ${spacing.sm} ${spacing.sm}`}; + margin: ${isHorizontal ? 'none' : `${spacing(1, 3, 1, 1)}`}; height: ${isHorizontal ? 'auto' : '100%'}; `, slider: css` @@ -36,7 +29,7 @@ export const getStyles = stylesFactory((theme: GrafanaTheme, isHorizontal: boole .rc-slider-handle { border: none; background-color: ${handleColor}; - box-shadow: ${theme.v2.shadows.z1}; + box-shadow: ${theme.shadows.z1}; cursor: pointer; } .rc-slider-handle:hover, @@ -66,7 +59,7 @@ export const getStyles = stylesFactory((theme: GrafanaTheme, isHorizontal: boole } .rc-slider-tooltip-inner { - color: ${theme.colors.text}; + color: ${theme.palette.text.primary}; background-color: transparent !important; border-radius: 0; box-shadow: none; @@ -97,14 +90,14 @@ export const getStyles = stylesFactory((theme: GrafanaTheme, isHorizontal: boole } `, sliderInputField: css` - margin-left: ${theme.spacing.lg}; + margin-left: ${theme.spacing(3)}; width: 60px; input { text-align: center; } `, sliderInputFieldVertical: css` - margin: 0 0 ${theme.spacing.lg} 0; + margin: 0 0 ${theme.spacing(3)} 0; order: 1; `, }; diff --git a/packages/grafana-ui/src/components/Switch/Switch.tsx b/packages/grafana-ui/src/components/Switch/Switch.tsx index 66ca1328207..8ffe5a7f7ae 100644 --- a/packages/grafana-ui/src/components/Switch/Switch.tsx +++ b/packages/grafana-ui/src/components/Switch/Switch.tsx @@ -1,9 +1,9 @@ import React, { HTMLProps, useRef } from 'react'; import { css, cx } from '@emotion/css'; import { uniqueId } from 'lodash'; -import { GrafanaTheme, deprecationWarning } from '@grafana/data'; -import { stylesFactory, useTheme } from '../../themes'; -import { focusCss, getMouseFocusStyles } from '../../themes/mixins'; +import { GrafanaThemeV2, deprecationWarning } from '@grafana/data'; +import { stylesFactory, useTheme2 } from '../../themes'; +import { getFocusStyles, getMouseFocusStyles } from '../../themes/mixins'; export interface Props extends Omit, 'value'> { value?: boolean; @@ -17,7 +17,7 @@ export const Switch = React.forwardRef( deprecationWarning('Switch', 'checked prop', 'value'); } - const theme = useTheme(); + const theme = useTheme2(); const styles = getSwitchStyles(theme); const switchIdRef = useRef(id ? id : uniqueId('switch-')); @@ -43,7 +43,7 @@ export const Switch = React.forwardRef( Switch.displayName = 'Switch'; export const InlineSwitch = React.forwardRef(({ transparent, ...props }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getSwitchStyles(theme, transparent); return ( @@ -55,7 +55,7 @@ export const InlineSwitch = React.forwardRef(({ transpa InlineSwitch.displayName = 'Switch'; -const getSwitchStyles = stylesFactory((theme: GrafanaTheme, transparent?: boolean) => { +const getSwitchStyles = stylesFactory((theme: GrafanaThemeV2, transparent?: boolean) => { return { switch: css` width: 32px; @@ -69,31 +69,31 @@ const getSwitchStyles = stylesFactory((theme: GrafanaTheme, transparent?: boolea position: absolute; &:disabled + label { - background: ${theme.v2.palette.action.disabledBackground}; + background: ${theme.palette.action.disabledBackground}; cursor: not-allowed; } &:checked + label { - background: ${theme.v2.palette.primary.main}; - border-color: ${theme.v2.palette.primary.main}; + background: ${theme.palette.primary.main}; + border-color: ${theme.palette.primary.main}; &:hover { - background: ${theme.v2.palette.primary.shade}; + background: ${theme.palette.primary.shade}; } &::after { transform: translate3d(18px, -50%, 0); - background: ${theme.v2.palette.primary.contrastText}; + background: ${theme.palette.primary.contrastText}; } } &:focus + label, &:focus-visible + label { - ${focusCss(theme)} + ${getFocusStyles(theme)} } &:focus:not(:focus-visible) + label { - ${getMouseFocusStyles(theme.v2)} + ${getMouseFocusStyles(theme)} } } @@ -103,12 +103,12 @@ const getSwitchStyles = stylesFactory((theme: GrafanaTheme, transparent?: boolea cursor: pointer; border: none; border-radius: 50px; - background: ${theme.v2.components.input.background}; - border: 1px solid ${theme.v2.components.input.border}; + background: ${theme.components.input.background}; + border: 1px solid ${theme.components.input.border}; transition: all 0.3s ease; &:hover { - border-color: ${theme.v2.components.input.borderHover}; + border-color: ${theme.components.input.borderHover}; } &::after { @@ -118,8 +118,8 @@ const getSwitchStyles = stylesFactory((theme: GrafanaTheme, transparent?: boolea width: 12px; height: 12px; border-radius: 6px; - background: ${theme.v2.palette.text.secondary}; - box-shadow: ${theme.v2.shadows.z1}; + background: ${theme.palette.text.secondary}; + box-shadow: ${theme.shadows.z1}; top: 50%; transform: translate3d(2px, -50%, 0); transition: transform 0.2s cubic-bezier(0.19, 1, 0.22, 1); @@ -127,13 +127,13 @@ const getSwitchStyles = stylesFactory((theme: GrafanaTheme, transparent?: boolea } `, inlineContainer: css` - padding: ${theme.v2.spacing(0, 1)}; - height: ${theme.v2.spacing(theme.v2.components.height.md)}; + padding: ${theme.spacing(0, 1)}; + height: ${theme.spacing(theme.components.height.md)}; display: flex; align-items: center; - background: ${transparent ? 'transparent' : theme.v2.components.input.background}; - border: 1px solid ${transparent ? 'transparent' : theme.v2.components.input.border}; - border-radius: ${theme.v2.shape.borderRadius()}; + background: ${transparent ? 'transparent' : theme.components.input.background}; + border: 1px solid ${transparent ? 'transparent' : theme.components.input.border}; + border-radius: ${theme.shape.borderRadius()}; `, }; }); diff --git a/packages/grafana-ui/src/components/Table/FilterList.tsx b/packages/grafana-ui/src/components/Table/FilterList.tsx index eaf90242acc..9bef1a6b4e7 100644 --- a/packages/grafana-ui/src/components/Table/FilterList.tsx +++ b/packages/grafana-ui/src/components/Table/FilterList.tsx @@ -1,9 +1,9 @@ import React, { FC, useCallback, useMemo, useState } from 'react'; import { FixedSizeList as List } from 'react-window'; import { css } from '@emotion/css'; -import { GrafanaTheme, SelectableValue } from '@grafana/data'; +import { GrafanaThemeV2, SelectableValue } from '@grafana/data'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { Checkbox, Input, Label, VerticalGroup } from '..'; interface Props { @@ -16,14 +16,14 @@ const ITEM_HEIGHT = 28; const MIN_HEIGHT = ITEM_HEIGHT * 5; export const FilterList: FC = ({ options, values, onChange }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getStyles(theme); const [searchFilter, setSearchFilter] = useState(''); const items = useMemo(() => options.filter((option) => option.label?.indexOf(searchFilter) !== -1), [ options, searchFilter, ]); - const gutter = parseInt(theme.spacing.sm, 10); + const gutter = theme.spacing.gridSize; const height = useMemo(() => Math.min(items.length * ITEM_HEIGHT, MIN_HEIGHT) + gutter, [gutter, items.length]); const onInputChange = useCallback( @@ -78,7 +78,7 @@ export const FilterList: FC = ({ options, values, onChange }) => { ); }; -const getStyles = stylesFactory((theme: GrafanaTheme) => ({ +const getStyles = stylesFactory((theme: GrafanaThemeV2) => ({ filterList: css` label: filterList; `, @@ -88,10 +88,10 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => ({ white-space: nowrap; overflow: hidden; text-overflow: ellipsis; - padding: ${theme.spacing.xs}; + padding: ${theme.spacing(0.5)}; :hover { - background-color: ${theme.v2.palette.action.hover}; + background-color: ${theme.palette.action.hover}; } `, filterListInput: css` diff --git a/packages/grafana-ui/src/components/Tabs/Counter.tsx b/packages/grafana-ui/src/components/Tabs/Counter.tsx index 08e6ca9ce67..18f092d3d83 100644 --- a/packages/grafana-ui/src/components/Tabs/Counter.tsx +++ b/packages/grafana-ui/src/components/Tabs/Counter.tsx @@ -1,18 +1,18 @@ import React, { FC } from 'react'; import { css } from '@emotion/css'; -import { stylesFactory, useStyles } from '../../themes'; -import { GrafanaTheme, locale } from '@grafana/data'; +import { stylesFactory, useStyles2 } from '../../themes'; +import { GrafanaThemeV2, locale } from '@grafana/data'; -const getStyles = stylesFactory((theme: GrafanaTheme) => { +const getStyles = stylesFactory((theme: GrafanaThemeV2) => { return { counter: css` label: counter; - margin-left: ${theme.spacing.sm}; - border-radius: ${theme.spacing.lg}; - background-color: ${theme.v2.palette.action.hover}; - padding: ${theme.spacing.xxs} ${theme.spacing.sm}; - color: ${theme.colors.textWeak}; - font-weight: ${theme.typography.weight.semibold}; + margin-left: ${theme.spacing(1)}; + border-radius: ${theme.spacing(3)}; + background-color: ${theme.palette.action.hover}; + padding: ${theme.spacing(0.25, 1)}; + color: ${theme.palette.text.secondary}; + font-weight: ${theme.typography.fontWeightMedium}; font-size: ${theme.typography.size.sm}; `, }; @@ -23,7 +23,7 @@ export interface CounterProps { } export const Counter: FC = ({ value }) => { - const styles = useStyles(getStyles); + const styles = useStyles2(getStyles); return {locale(value, 0).text}; }; diff --git a/packages/grafana-ui/src/components/Tabs/Tab.tsx b/packages/grafana-ui/src/components/Tabs/Tab.tsx index 76b7736ad2f..068a5893d1d 100644 --- a/packages/grafana-ui/src/components/Tabs/Tab.tsx +++ b/packages/grafana-ui/src/components/Tabs/Tab.tsx @@ -1,11 +1,11 @@ import React, { HTMLProps } from 'react'; import { css, cx } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { selectors } from '@grafana/e2e-selectors'; import { Icon } from '../Icon/Icon'; import { IconName } from '../../types'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { Counter } from './Counter'; export interface TabProps extends HTMLProps { @@ -21,7 +21,7 @@ export interface TabProps extends HTMLProps { export const Tab = React.forwardRef( ({ label, active, icon, onChangeTab, counter, className, href, ...otherProps }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const tabsStyles = getTabStyles(theme); const content = () => ( <> @@ -52,7 +52,7 @@ export const Tab = React.forwardRef( Tab.displayName = 'Tab'; -const getTabStyles = stylesFactory((theme: GrafanaTheme) => { +const getTabStyles = stylesFactory((theme: GrafanaThemeV2) => { return { item: css` list-style: none; @@ -60,24 +60,24 @@ const getTabStyles = stylesFactory((theme: GrafanaTheme) => { display: flex; `, link: css` - color: ${theme.v2.palette.text.secondary}; - padding: ${theme.v2.spacing(1.5, 2, 1)}; + color: ${theme.palette.text.secondary}; + padding: ${theme.spacing(1.5, 2, 1)}; svg { - margin-right: ${theme.v2.spacing(1)}; + margin-right: ${theme.spacing(1)}; } a { display: block; height: 100%; - color: ${theme.v2.palette.text.secondary}; + color: ${theme.palette.text.secondary}; } `, notActive: css` a:hover, &:hover, &:focus { - color: ${theme.v2.palette.text.primary}; + color: ${theme.palette.text.primary}; &::before { display: block; @@ -88,18 +88,18 @@ const getTabStyles = stylesFactory((theme: GrafanaTheme) => { height: 4px; border-radius: 2px; bottom: 0px; - background: ${theme.v2.palette.action.hover}; + background: ${theme.palette.action.hover}; } } `, activeStyle: css` label: activeTabStyle; - color: ${theme.v2.palette.text.primary}; + color: ${theme.palette.text.primary}; overflow: hidden; - font-weight: ${theme.v2.typography.fontWeightMedium}; + font-weight: ${theme.typography.fontWeightMedium}; a { - color: ${theme.v2.palette.text.primary}; + color: ${theme.palette.text.primary}; } &::before { @@ -111,7 +111,7 @@ const getTabStyles = stylesFactory((theme: GrafanaTheme) => { height: 4px; border-radius: 2px; bottom: 0px; - background-image: ${theme.v2.palette.gradients.brandHorizontal} !important; + background-image: ${theme.palette.gradients.brandHorizontal} !important; } `, }; diff --git a/packages/grafana-ui/src/components/Tabs/TabContent.tsx b/packages/grafana-ui/src/components/Tabs/TabContent.tsx index 2d203fc62ff..c4f2121932e 100644 --- a/packages/grafana-ui/src/components/Tabs/TabContent.tsx +++ b/packages/grafana-ui/src/components/Tabs/TabContent.tsx @@ -1,23 +1,23 @@ import React, { FC, HTMLAttributes, ReactNode } from 'react'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { css, cx } from '@emotion/css'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; interface Props extends HTMLAttributes { children: ReactNode; } -const getTabContentStyle = stylesFactory((theme: GrafanaTheme) => { +const getTabContentStyle = stylesFactory((theme: GrafanaThemeV2) => { return { tabContent: css` - padding: ${theme.spacing.sm}; - background: ${theme.v2.palette.background.primary}; + padding: ${theme.spacing(1)}; + background: ${theme.palette.background.primary}; `, }; }); export const TabContent: FC = ({ children, className, ...restProps }) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getTabContentStyle(theme); return ( diff --git a/packages/grafana-ui/src/components/Tabs/TabsBar.tsx b/packages/grafana-ui/src/components/Tabs/TabsBar.tsx index 4217e9345d5..ae4637d0aab 100644 --- a/packages/grafana-ui/src/components/Tabs/TabsBar.tsx +++ b/packages/grafana-ui/src/components/Tabs/TabsBar.tsx @@ -1,6 +1,6 @@ import React, { ReactNode } from 'react'; -import { stylesFactory, useTheme } from '../../themes'; -import { GrafanaTheme } from '@grafana/data'; +import { stylesFactory, useTheme2 } from '../../themes'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css, cx } from '@emotion/css'; export interface Props { @@ -11,12 +11,12 @@ export interface Props { hideBorder?: boolean; } -const getTabsBarStyles = stylesFactory((theme: GrafanaTheme, hideBorder = false) => { +const getTabsBarStyles = stylesFactory((theme: GrafanaThemeV2, hideBorder = false) => { return { tabsWrapper: !hideBorder && css` - border-bottom: 1px solid ${theme.v2.palette.border.weak}; + border-bottom: 1px solid ${theme.palette.border.weak}; `, tabs: css` position: relative; @@ -29,7 +29,7 @@ const getTabsBarStyles = stylesFactory((theme: GrafanaTheme, hideBorder = false) }); export const TabsBar = React.forwardRef(({ children, className, hideBorder }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const tabsStyles = getTabsBarStyles(theme, hideBorder); return ( diff --git a/packages/grafana-ui/src/components/TextArea/TextArea.tsx b/packages/grafana-ui/src/components/TextArea/TextArea.tsx index 91301134571..40117391426 100644 --- a/packages/grafana-ui/src/components/TextArea/TextArea.tsx +++ b/packages/grafana-ui/src/components/TextArea/TextArea.tsx @@ -1,7 +1,7 @@ import React, { HTMLProps } from 'react'; -import { GrafanaTheme } from '@grafana/data'; +import { GrafanaThemeV2 } from '@grafana/data'; import { css, cx } from '@emotion/css'; -import { stylesFactory, useTheme } from '../../themes'; +import { stylesFactory, useTheme2 } from '../../themes'; import { getFocusStyle, sharedInputStyle } from '../Forms/commonStyles'; export interface Props extends Omit, 'size'> { @@ -10,22 +10,22 @@ export interface Props extends Omit, 'size'> { } export const TextArea = React.forwardRef(({ invalid, className, ...props }, ref) => { - const theme = useTheme(); + const theme = useTheme2(); const styles = getTextAreaStyle(theme, invalid); return