Created
May 9, 2020 21:23
-
-
Save dontwork/c0c51e00b35e1821b433f9212d8596bd to your computer and use it in GitHub Desktop.
Btn
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import m from 'mithril' | |
| import { splitAttrs } from '../utils' | |
| import { Icon } from '../Icon' | |
| import loadingIcon from './loading.svg' | |
| const sizes = { | |
| shape: { | |
| circle: { | |
| size: { | |
| sm: ['h-6', 'w-6', 'text-sm'], | |
| md: ['h-8', 'w-8', 'text-md'], | |
| lg: ['h-10', 'w-10', 'text-lg'] | |
| } | |
| }, | |
| round: { | |
| size: { | |
| sm: ['px-2', 'py-1', 'text-sm'], | |
| md: ['px-3', 'py-1', 'text-md'], | |
| lg: ['px-4', 'py-2', 'text-lg'] | |
| } | |
| }, | |
| normal: { | |
| size: { | |
| sm: ['px-2', 'py-1', 'text-sm'], | |
| md: ['px-3', 'py-1', 'text-md'], | |
| lg: ['px-4', 'py-2', 'text-lg'] | |
| } | |
| } | |
| } | |
| } | |
| const shapes = { | |
| circle: ['rounded-full'], | |
| round: ['rounded-full'], | |
| normal: ['rounded-sm'] | |
| } | |
| const styles = [ | |
| 'relative', | |
| 'flex', | |
| 'items-center', | |
| 'justify-center', | |
| 'select-none', | |
| 'focus:outline-none', | |
| 'transition-all', | |
| 'duration-200' | |
| ] | |
| const variants = { | |
| primary: { | |
| dark: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-700', | |
| 'bg-gray-800', | |
| 'text-gray-600' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'border-indigo-600', | |
| 'bg-indigo-700', | |
| 'text-indigo-100', | |
| 'hover:bg-indigo-800', | |
| 'focus:bg-indigo-800', | |
| 'hover:border-indigo-700', | |
| 'focus:border-indigo-700', | |
| 'active:dec-outline-dark' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-red-600', | |
| 'bg-red-700', | |
| 'text-red-100', | |
| 'hover:bg-red-800', | |
| 'focus:bg-red-800', | |
| 'hover:border-red-700', | |
| 'focus:border-red-700', | |
| 'active:dec-outline-danger-dark' | |
| ] | |
| }, | |
| light: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-00', | |
| 'bg-gray-200', | |
| 'text-gray-500' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'border-indigo-800', | |
| 'bg-indigo-600', | |
| 'text-white', | |
| 'button-shadow', | |
| 'hover:bg-indigo-500', | |
| 'focus:bg-indigo-500', | |
| 'hover:border-indigo-600', | |
| 'focus:border-indigo-600', | |
| 'active:dec-outline' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-red-600', | |
| 'bg-red-500', | |
| 'text-white', | |
| 'button-shadow', | |
| 'hover:bg-red-400', | |
| 'focus:bg-red-400', | |
| 'hover:border-red-500', | |
| 'focus:border-red-500', | |
| 'active:dec-outline-danger' | |
| ] | |
| } | |
| }, | |
| default: { | |
| dark: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-700', | |
| 'bg-gray-800', | |
| 'text-gray-600' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'border-gray-700', | |
| 'bg-gray-800', | |
| 'text-gray-100', | |
| 'button-shadow', | |
| 'hover:border-indigo-700', | |
| 'hover:text-indigo-300', | |
| 'focus:border-indigo-700', | |
| 'focus:text-indigo-300', | |
| 'active:dec-outline-dark' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-red-700', | |
| 'bg-gray-800', | |
| 'text-red-600', | |
| 'button-shadow', | |
| 'hover:border-red-800', | |
| 'hover:text-red-700', | |
| 'focus:border-red-800', | |
| 'focus:text-red-700', | |
| 'active:dec-outline-danger-dark' | |
| ] | |
| }, | |
| light: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-400', | |
| 'bg-gray-200', | |
| 'text-gray-500' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'bg-white', | |
| 'text-gray-700', | |
| 'button-shadow', | |
| 'hover:border-blue-500', | |
| 'hover:text-blue-500', | |
| 'focus:border-blue-500', | |
| 'focus:text-blue-500', | |
| 'active:dec-outline' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-red-400', | |
| 'bg-white', | |
| 'text-red-500', | |
| 'button-shadow', | |
| 'hover:border-red-500', | |
| 'hover:text-red-500', | |
| 'focus:border-red-500', | |
| 'focus:text-red-500', | |
| 'active:dec-outline-danger' | |
| ] | |
| } | |
| }, | |
| dashed: { | |
| dark: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-700', | |
| 'border-dashed', | |
| 'bg-gray-800', | |
| 'text-gray-600' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'border-dashed', | |
| 'border-gray-700', | |
| 'bg-gray-800', | |
| 'text-gray-100', | |
| 'button-shadow', | |
| 'hover:border-indigo-700', | |
| 'hover:text-indigo-300', | |
| 'focus:border-indigo-700', | |
| 'focus:text-indigo-300', | |
| 'active:dec-outline-dark' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-dashed', | |
| 'border-red-700', | |
| 'bg-gray-800', | |
| 'text-red-600', | |
| 'button-shadow', | |
| 'hover:border-red-800', | |
| 'hover:text-red-700', | |
| 'focus:border-red-800', | |
| 'focus:text-red-700', | |
| 'active:dec-outline-danger-dark' | |
| ] | |
| }, | |
| light: { | |
| disabled: [ | |
| 'cursor-not-allowed', | |
| 'border', | |
| 'border-gray-400', | |
| 'border-dashed', | |
| 'bg-gray-200', | |
| 'text-gray-500' | |
| ], | |
| normal: [ | |
| 'border', | |
| 'border-gray-400', | |
| 'border-dashed', | |
| 'bg-white', | |
| 'text-gray-700', | |
| 'button-shadow', | |
| 'hover:border-blue-500', | |
| 'hover:text-blue-500', | |
| 'focus:border-blue-500', | |
| 'focus:text-blue-500', | |
| 'active:border-blue-800', | |
| 'active:text-blue-800', | |
| 'active:dec-outline' | |
| ], | |
| danger: [ | |
| 'border', | |
| 'border-red-400', | |
| 'border-dashed', | |
| 'bg-white', | |
| 'text-red-500', | |
| 'button-shadow', | |
| 'hover:border-red-500', | |
| 'hover:text-red-600', | |
| 'focus:border-red-500', | |
| 'focus:text-red-600', | |
| 'active:border-red-800', | |
| 'active:text-red-800', | |
| 'active:dec-outline-danger' | |
| ] | |
| } | |
| }, | |
| link: { | |
| dark: { | |
| disabled: [ | |
| 'text-gray-500', | |
| 'cursor-not-allowed' | |
| ], | |
| normal: [ | |
| 'text-indigo-400', | |
| 'hover:bg-gray-800', | |
| 'hover:text-indigo-300', | |
| 'focus:bg-gray-800', | |
| 'focus:text-indigo-300', | |
| 'active:bg-gray-800', | |
| 'active:text-indigo-300' | |
| ], | |
| danger: [ | |
| 'text-red-600', | |
| 'hover:bg-gray-800', | |
| 'hover:text-red-700', | |
| 'focus:bg-gray-800', | |
| 'focus:text-red-300', | |
| 'active:bg-gray-800', | |
| 'active:text-red-300' | |
| ] | |
| }, | |
| light: { | |
| disabled: [ | |
| 'text-gray-500', | |
| 'cursor-not-allowed' | |
| ], | |
| normal: [ | |
| 'text-blue-500', | |
| 'hover:bg-blue-100', | |
| 'hover:text-blue-700', | |
| 'focus:bg-blue-100', | |
| 'focus:text-blue-800', | |
| 'active:bg-blue-100', | |
| 'active:text-blue-800' | |
| ], | |
| danger: [ | |
| 'text-red-500', | |
| 'hover:bg-red-100', | |
| 'hover:text-red-700', | |
| 'focus:bg-red-100', | |
| 'focus:text-red-800', | |
| 'active:bg-red-100', | |
| 'active:text-red-800' | |
| ] | |
| } | |
| } | |
| } | |
| const loading = { | |
| true: ['opacity-50', 'pointer-events-none'], | |
| false: [] | |
| } | |
| const icon = { | |
| sm: ['pl-6'], | |
| md: ['pl-8'], | |
| lg: ['pl-10'] | |
| } | |
| const ButtonAttrs = { | |
| element: 'button', | |
| size: 'md', | |
| shape: 'normal', | |
| disabled: false, | |
| variant: 'default', | |
| mode: window.decConfig.mode || 'light', | |
| onclick: () => {}, | |
| icon: null, | |
| danger: false, | |
| loading: false | |
| } | |
| export const Button = () => { | |
| return { | |
| view ({ attrs = { }, children }) { | |
| const { componentAttrs, proxiedAttrs, handle } = splitAttrs(attrs, ButtonAttrs, ['class']) | |
| const isCircle = componentAttrs.shape === 'circle' | |
| const isLoading = componentAttrs.loading | |
| const style = componentAttrs.disabled ? 'disabled' : componentAttrs.danger ? 'danger' : 'normal' | |
| return m(componentAttrs.element, { | |
| class: [ | |
| ...styles, | |
| ...sizes.shape[componentAttrs.shape].size[componentAttrs.size], | |
| ...variants[componentAttrs.variant][componentAttrs.mode][style], | |
| ...shapes[componentAttrs.shape], | |
| ...loading[isLoading], | |
| ...((componentAttrs.icon || isLoading) && !isCircle ? icon[componentAttrs.size] : []), | |
| handle.class | |
| ].join(' '), | |
| disabled: componentAttrs.disabled || isLoading, | |
| onclick (e) { | |
| componentAttrs.onclick(e) | |
| }, | |
| ...proxiedAttrs | |
| }, [ | |
| (!!componentAttrs.icon || isLoading) && | |
| m('', { | |
| class: [ | |
| isLoading ? 'fade-in' : '', | |
| !isCircle ? 'absolute left-2' : '' | |
| ].join(' ') | |
| }, [ | |
| m(Icon, { | |
| size: componentAttrs.size, | |
| icon: isLoading ? loadingIcon : componentAttrs.icon, | |
| class: [ | |
| ].join(' '), | |
| spin: isLoading | |
| }) | |
| ]), | |
| (!isCircle || !isLoading) && | |
| children | |
| ]) | |
| } | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment