feat(Checkbox): added Checkbox component

This commit is contained in:
Botzy 2025-02-13 13:05:14 +02:00
parent d05488feb6
commit 1b2fe21044
4 changed files with 189 additions and 0 deletions

View file

@ -0,0 +1,95 @@
// Copyright (C) 2017-2025 Smart code 203358507
.checkbox {
display: flex;
align-items: center;
overflow: visible;
.label {
display: flex;
flex-direction: row;
align-items: center;
padding: 0.5rem 0;
span {
font-size: 0.9rem;
color: var(--primary-foreground-color);
opacity: 0.6;
}
.link {
font-size: 0.9rem;
color: var(--primary-accent-color);
&:hover {
text-decoration: underline;
}
}
}
.checkbox-container {
position: relative;
width: 1.75rem;
height: 1.75rem;
border: 0.2rem solid var(--color-placeholder);
border-radius: 0.5rem;
background-color: transparent;
display: flex;
flex: none;
margin-right: 1rem;
align-items: center;
justify-content: center;
transition: all 0.2s ease-in-out;
cursor: pointer;
outline: none;
user-select: none;
input[type='checkbox'] {
opacity: 0;
width: 0;
height: 0;
position: absolute;
cursor: pointer;
}
.checkmark {
position: absolute;
top: 0;
left: 0;
width: 1.5rem;
height: 1.5rem;
transition: opacity 0.2s ease-in-out;
background-color: transparent;
opacity: 0;
&:after {
content: "";
position: absolute;
left: 0.45rem;
top: 0.2rem;
width: 0.2rem;
height: 0.5rem;
border: solid var(--primary-foreground-color);
border-width: 0 0.2rem 0.2rem 0;
-webkit-transform: rotate(45deg);
-ms-transform: rotate(45deg);
transform: rotate(45deg);
}
}
&.disabled {
cursor: not-allowed;
}
&.error {
border-color: var(--color-trakt);
}
&.checked {
border: 3px solid var(--secondary-accent-color);
background-color: var(--secondary-accent-color);
.checkmark {
opacity: 1;
}
}
}
}

View file

@ -0,0 +1,87 @@
// Copyright (C) 2017-2025 Smart code 203358507
import React, { useCallback, ChangeEvent, KeyboardEvent, RefCallback } from 'react';
import classNames from 'classnames';
import styles from './Checkbox.less';
import Button from '../Button';
type Props = {
ref?: RefCallback<HTMLInputElement>;
name: string;
disabled?: boolean;
checked?: boolean;
className?: string;
label?: string;
link?: string;
href?: string;
onChange?: (props: any) => void;
error?: string;
};
const Checkbox = React.forwardRef<HTMLInputElement, Props>(({ name, disabled, className, label, href, link, onChange, error, checked }, ref) => {
const handleSelect = useCallback((event: ChangeEvent<HTMLInputElement>) => {
if (!disabled && onChange) {
onChange({
type: 'select',
checked: event.target.checked,
reactEvent: event,
nativeEvent: event.nativeEvent,
});
}
}, [disabled, onChange]);
const onKeyDown = useCallback((event: KeyboardEvent<HTMLDivElement>) => {
if ((event.key === 'Enter' || event.key === ' ') && !disabled) {
onChange && onChange({
type: 'select',
checked: event.target.checked,
reactEvent: event,
nativeEvent: event.nativeEvent,
});
}
}, [disabled, checked, onChange]);
return (
<div className={classNames(styles['checkbox'], className)}>
<label className={styles['label']} htmlFor={name}>
<div
className={classNames(
styles['checkbox-container'],
{ [styles['checked']]: checked },
{ [styles['disabled']]: disabled },
{ [styles['error']]: error }
)}
role={'checkbox'}
tabIndex={disabled ? -1 : 0}
aria-checked={checked}
onKeyDown={onKeyDown}
>
<input
ref={ref}
id={name}
type={'checkbox'}
checked={checked}
disabled={disabled}
onChange={handleSelect}
className={styles['input']}
/>
<span className={styles['checkmark']} />
</div>
<div>
<span>{label}</span>
{' '}
{
href && link ?
<Button className={styles['link']} href={href} target={'_blank'} tabIndex={-1}>
{link}
</Button>
: null
}
</div>
</label>
</div>
);
});
export default Checkbox;

View file

@ -0,0 +1,5 @@
// Copyright (C) 2017-2025 Smart code 203358507
import Checkbox from './Checkbox';
export default Checkbox;

View file

@ -1,6 +1,7 @@
import AddonDetailsModal from './AddonDetailsModal';
import BottomSheet from './BottomSheet';
import Button from './Button';
import Checkbox from './Checkbox';
import Chips from './Chips';
import ColorInput from './ColorInput';
import ContinueWatchingItem from './ContinueWatchingItem';
@ -31,6 +32,7 @@ export {
AddonDetailsModal,
BottomSheet,
Button,
Checkbox,
Chips,
ColorInput,
ContinueWatchingItem,