/*
* SonarQube
* Copyright (C) 2009-2024 SonarSource SA
* mailto:info AT sonarsource DOT com
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
import styled from '@emotion/styled';
import classNames from 'classnames';
import * as React from 'react';
import { useIntl } from 'react-intl';
import tw from 'twin.macro';
import { ThemeColors } from '~types/theme';
import { InteractiveIcon } from '../../components/InteractiveIcon';
import {
CloseIcon,
FlagErrorIcon,
FlagInfoIcon,
FlagSuccessIcon,
FlagWarningIcon,
} from '../../components/icons';
import { themeBorder, themeColor, themeContrast } from '../../helpers/theme';
export type Variant = 'error' | 'warning' | 'success' | 'info';
interface Props {
variant: Variant;
}
function getVariantInfo(variant: Variant) {
const variantList = {
error: {
icon: ,
borderColor: 'errorBorder',
backGroundColor: 'errorBackground',
},
warning: {
icon: ,
borderColor: 'warningBorder',
backGroundColor: 'warningBackground',
},
success: {
icon: ,
borderColor: 'successBorder',
backGroundColor: 'successBackground',
},
info: {
icon: ,
borderColor: 'infoBorder',
backGroundColor: 'infoBackground',
},
} as const;
return variantList[variant];
}
export function FlagMessage(props: Props & React.HTMLAttributes) {
const { className, variant, ...domProps } = props;
const variantInfo = getVariantInfo(variant);
return (
{props.children && (
{variantInfo.icon}
{props.children}
)}
);
}
FlagMessage.displayName = 'FlagMessage'; // so that tests don't see the obfuscated production name
interface DismissableFlagMessageProps extends Props {
onDismiss: () => void;
}
export function DismissableFlagMessage(
props: DismissableFlagMessageProps & React.HTMLAttributes,
) {
const { onDismiss, children, ...flagMessageProps } = props;
const intl = useIntl();
return (
{children}
);
}
DismissableFlagMessage.displayName = 'DismissableFlagMessage'; // so that tests don't see the obfuscated production name
export const StyledFlag = styled.div<{
backGroundColor: ThemeColors;
borderColor: ThemeColors;
}>`
${tw`sw-inline-flex`}
${tw`sw-min-h-10`}
${tw`sw-rounded-1`}
${tw`sw-box-border`}
border: ${({ borderColor }) => themeBorder('default', borderColor)};
background-color: ${themeColor('flagMessageBackground')};
:empty {
display: none;
}
& > .flag-inner {
${tw`sw-flex sw-items-stretch`}
${tw`sw-box-border`}
}
& .flag-icon {
${tw`sw-flex sw-justify-center sw-items-center`}
${tw`sw-rounded-l-1`}
${tw`sw-px-3`}
background-color: ${({ backGroundColor }) => themeColor(backGroundColor)};
}
& .flag-content {
${tw`sw-flex sw-flex-auto sw-items-center`}
${tw`sw-overflow-auto`}
${tw`sw-text-left`}
${tw`sw-px-3 sw-py-2`}
${tw`sw-body-sm`}
color: ${themeContrast('flagMessageBackground')};
}
`;
export const DismissIcon = styled(InteractiveIcon)`
--background: ${themeColor('productNews')};
--backgroundHover: ${themeColor('productNewsHover')};
--color: ${themeContrast('productNews')};
--colorHover: ${themeContrast('productNewsHover')};
--focus: ${themeColor('interactiveIconFocus', 0.2)};
height: 28px;
`;