Skip to content
This repository has been archived by the owner on Aug 29, 2023. It is now read-only.

Commit

Permalink
Merge pull request #38 from smartive-education/develop
Browse files Browse the repository at this point in the history
Feature/ Links and Button elements next/link ready
  • Loading branch information
rudigier authored Mar 22, 2023
2 parents e802857 + 333c51a commit 749e0ac
Show file tree
Hide file tree
Showing 16 changed files with 127 additions and 139 deletions.
46 changes: 23 additions & 23 deletions src/components/Atoms/Link/Link.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
import React, { FC, ReactNode, AnchorHTMLAttributes, HTMLAttributes } from 'react';
import React, { FC, ReactNode, LinkHTMLAttributes } from 'react';

/*
* Type
*/

type TLink = {
type TLink<T> = {
/**
* HTML tag to render a link (a or span)
* @see https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a
* @see https://developer.mozilla.org/en-US/docs/Web/HTML/Element/span
* HTML tag to render a link
*/
as?: 'a' | 'span';
as?: FC<T>;

/**
* provide a link reference (target url) as string
Expand All @@ -21,12 +19,7 @@ type TLink = {
* Child Nodes
*/
children: ReactNode;
};

type THTMLLinkProps = TLink & { as: 'a' } & AnchorHTMLAttributes<HTMLAnchorElement>;
type TSpanLinkProps = TLink & { as: 'span' } & HTMLAttributes<HTMLSpanElement>;

type TLinkProps = THTMLLinkProps | TSpanLinkProps;
} & Omit<T, 'className' | 'target' | 'rel'>;

/*
* Style
Expand All @@ -38,24 +31,31 @@ const style = [
'underline underline-offset-4 decoration-1 decoration-violet-600',
];

const hoverStyle: Record<string, string> = {
a: 'hover:text-violet-700 hover:decoration-violet-200',
span: 'group-hover:text-violet-700 group-hover:decoration-violet-200',
};
const hoverStyle = 'hover:text-violet-700 hover:decoration-violet-200';

/**
* Link Component
*
* @param {string} as - Choose between the HTML tags 'a' or 'span'
* @param {string} as - HTML tag to render a link
* @param {string} href - provide a link reference (target url) as string for the 'a' tag
* @param {ReactNode} children - Child Nodes
*
* @example <Link href='https://www.google.com'>Google</Link>
* @example <Link as="span">Google</Link>
*/

export const Link: FC<TLinkProps> = ({ as: Tag = 'a', href, children = 'Link', ...props }) => (
<Tag className={[...style, hoverStyle[Tag]].join(' ')} {...props} href={href}>
{children}
</Tag>
);
export function Link<
T extends {
className?: string;
rel?: string;
target?: string;
title?: string;
} = LinkHTMLAttributes<HTMLElement>
>({ children, as, ...props }: TLink<T>): JSX.Element {
const Tag = as || 'a';
return (
// eslint-disable-next-line @typescript-eslint/no-explicit-any
<Tag {...(props as any)} className={[...style, hoverStyle].join(' ')}>
{children}
</Tag>
);
}
41 changes: 20 additions & 21 deletions src/components/Molecules/Button/Button.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { FC, HTMLAttributes, ButtonHTMLAttributes, AnchorHTMLAttributes, ReactNode } from 'react';
import React, { ButtonHTMLAttributes, FC, ReactNode } from 'react';

import { Icon, TIconName } from '../../Atoms/Icon';
import { Label } from '../../Atoms/Label';
Expand All @@ -7,11 +7,11 @@ import { Label } from '../../Atoms/Label';
* Type
*/

type TButton = {
type TButton<T> = {
/**
* HTML tag to render a button (button, a, span)
* HTML tag to render a button
*/
as?: 'button' | 'a' | 'span';
as?: FC<T>;

/**
* React Children: here most probably text
Expand All @@ -32,12 +32,7 @@ type TButton = {
* icon name to render
*/
icon?: TIconName;
};

type THTMLButtonProps = TButton & { as: 'button' } & ButtonHTMLAttributes<HTMLButtonElement>;
type TLinkButtonProps = TButton & { as: 'a' } & AnchorHTMLAttributes<HTMLAnchorElement>;
type TSpanButtonProps = TButton & { as: 'span' } & HTMLAttributes<HTMLSpanElement>;
type TButtonProps = THTMLButtonProps | TLinkButtonProps | TSpanButtonProps;
} & Omit<T, 'className'>;

/*
* Styles
Expand Down Expand Up @@ -87,29 +82,33 @@ export const ButtonColorMap: Record<string, string> = {
* @param { ReactNode } children - React Children: here most probably text
* @param {any} props - all other props will be spreaded to the HTML Tag
*
* @example <Button as="button" size="M" colorScheme="violet" icon="mumble">Button</Button>
* @example <Button size="M" colorScheme="violet" icon="mumble">Button</Button>
*/
export function Button<
T extends {
className?: string;
type?: 'button' | 'submit' | 'reset';
title?: string;
} = ButtonHTMLAttributes<HTMLElement>
>({ children, as, colorScheme = 'violet', size = 'M', icon = 'mumble', ...props }: TButton<T>): JSX.Element {
const Tag = as || 'button';

if (Tag === 'button') {
props.type = 'button';
}

export const Button: FC<TButtonProps> = ({
children,
as: Tag = 'button',
colorScheme = 'violet',
size = 'M',
icon = 'mumble',
...props
}) => {
const style = [...ButtonBaseStyle, ButtonSizeMap[size], ButtonColorMap[colorScheme]];

return (
<Tag
className={style.join(' ')}
// eslint-disable-next-line @typescript-eslint/no-explicit-any
{...(props as any)}
className={style.join(' ')}
>
<Label as="span" size="M">
{children}
</Label>
{icon ? <Icon name={icon} /> : null}
</Tag>
);
};
}
2 changes: 1 addition & 1 deletion src/components/Molecules/Card/Card.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ type TCard = {

const sizeMap: Record<string, string> = {
S: 'py-s px-s',
M: 'py-l px-xl',
M: 'py-l px-xl sm:py-m sm:px-l',
};

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,43 +23,33 @@ export const CommentActive = Template.bind({});
export const Share = Template.bind({});

Like.args = {
as: 'button',
type: 'button',
isActive: false,
colorScheme: 'pink',
buttonText: 'Like',
iconName: 'heart_fillable',
};

LikeActive.args = {
as: 'button',
type: 'button',
isActive: true,
colorScheme: 'pink',
buttonText: '3 Likes',
iconName: 'heart_filled',
};

Comment.args = {
as: 'button',
type: 'button',
isActive: false,
colorScheme: 'violet',
buttonText: 'Comment',
iconName: 'comment_fillable',
};
Comment.args = {
as: 'button',
type: 'button',
isActive: true,
colorScheme: 'violet',
buttonText: '7 Comments',
iconName: 'comment_filled',
};

Share.args = {
as: 'button',
type: 'button',
colorScheme: 'slate',
buttonText: 'Copy Link',
iconName: 'share',
Expand Down
44 changes: 18 additions & 26 deletions src/components/Molecules/InteractionButton/InteractionButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ import { Icon } from '../../Atoms/Icon';
* Type
*/

type TInteractionButton = {
type TInteractionButton<T> = {
/**
* HTML tag to render a button (button, a)
* @default 'button'
*/
as: 'button' | 'a';
as?: FC<T>;

/**
* color scheme options of this button (slate, violet, pink)
Expand All @@ -33,24 +33,13 @@ type TInteractionButton = {
* @default false
*/
isActive?: boolean;

/**
* onClick: callback function to handle click event
* @default () => {}
*/
onClick: () => void;
};

type THTMLInteractionButtonProps = TInteractionButton & { as: 'button' } & ButtonHTMLAttributes<HTMLButtonElement>;
type TLinkInteractionButtonProps = TInteractionButton & { as: 'a' } & AnchorHTMLAttributes<HTMLAnchorElement>;

type TInteractionButtonProps = THTMLInteractionButtonProps | TLinkInteractionButtonProps;
} & Omit<T, 'className'>;

/*
* Styles
*/

const InteractionButtonBaseStyle = 'flex items-center gap-y-0 gap-x-2 rounded-full py-2 px-3 leading-none group';
const InteractionButtonBaseStyle = 'flex items-center gap-y-0 gap-x-2 rounded-full leading-none group';

export const InteractionButtonColorSchemeMap: Record<string, Record<string, string>> = {
default: {
Expand Down Expand Up @@ -84,7 +73,6 @@ const InteractionButtonIconColorSchemeMap: Record<string, Record<string, string>
* @param { colorScheme } colorScheme of the Button: `pink`, `violet`, or `slate`
* @param { iconName } iconName name of Icon -see Library
* @param { isActive } isActive boolean to set the button to active state
* @param { onClick } onClick handler to be implemented by yourself!
* @example
* return (
* <InteractionButton
Expand All @@ -95,25 +83,29 @@ const InteractionButtonIconColorSchemeMap: Record<string, Record<string, string>
/>
)
*/
export function InteractionButton<
T extends {
className?: string;
type?: 'button' | 'submit' | 'reset';
title?: string;
} = ButtonHTMLAttributes<HTMLElement>
>({ as, colorScheme, buttonText, iconName, isActive = false, ...props }: TInteractionButton<T>): JSX.Element {
const Tag = as || 'button';

if (Tag === 'button') {
props.type = 'button';
}

export const InteractionButton: FC<TInteractionButtonProps> = ({
as: Tag = 'button',
colorScheme,
buttonText,
iconName,
isActive = false,
...props
}) => {
const style = [
InteractionButtonBaseStyle,
InteractionButtonColorSchemeMap[isActive ? 'active' : 'default'][colorScheme],
];

return (
<Tag
className={style.join(' ')}
// eslint-disable-next-line @typescript-eslint/no-explicit-any
{...(props as any)}
className={style.join(' ')}
>
<span className={InteractionButtonIconColorSchemeMap[isActive ? 'active' : 'default'][colorScheme]}>
<Icon name={iconName} />
Expand All @@ -123,4 +115,4 @@ export const InteractionButton: FC<TInteractionButtonProps> = ({
</Label>
</Tag>
);
};
}
24 changes: 21 additions & 3 deletions src/components/Molecules/Navi/Navi.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,31 @@ export const Navi = Template.bind({});
Navi.args = {
children: (
<>
<NaviButton as="a" href="/" icon="settings" title="Settings">
<NaviButton
onClick={(): void => {
window.location.href = '/';
}}
icon="settings"
title="Settings"
>
Settings
</NaviButton>
<NaviButton as="a" href="/" icon="settings" title="Settings">
<NaviButton
onClick={(): void => {
window.location.href = '/';
}}
icon="settings"
title="Settings"
>
Settings
</NaviButton>
<NaviButton as="a" href="/" icon="settings" title="Settings">
<NaviButton
onClick={(): void => {
window.location.href = '/';
}}
icon="settings"
title="Settings"
>
Settings
</NaviButton>
</>
Expand Down
1 change: 0 additions & 1 deletion src/components/Molecules/Navi/NaviButton.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ const Template: ComponentStory<typeof Component> = (args): JSX.Element => <Compo
export const NaviButton = Template.bind({});

NaviButton.args = {
href: '/',
icon: 'settings',
title: 'Settings',
children: 'Settings',
Expand Down
Loading

0 comments on commit 749e0ac

Please sign in to comment.