Skip to content

Commit

Permalink
feat: Updated button styles
Browse files Browse the repository at this point in the history
  • Loading branch information
cogor committed Oct 30, 2023
1 parent b44ca61 commit e376cd0
Show file tree
Hide file tree
Showing 11 changed files with 249 additions and 43 deletions.
28 changes: 28 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@
"build": "run-p type-check \"build-only {@}\" --",
"preview": "vite preview",
"test:unit": "vitest",
"test:ui": "vitest --ui",
"test:update": "vitest -u",
"coverage": "vitest run --coverage",
"test:e2e": "playwright test",
"build-only": "vite build",
Expand Down Expand Up @@ -63,6 +65,7 @@
"@types/node": "^18.18.5",
"@vitejs/plugin-vue": "^4.4.0",
"@vitest/coverage-istanbul": "^0.34.6",
"@vitest/ui": "^0.34.6",
"@vue/eslint-config-prettier": "^8.0.0",
"@vue/eslint-config-typescript": "^12.0.0",
"@vue/test-utils": "^2.4.1",
Expand Down
47 changes: 32 additions & 15 deletions src/components/BuiButton/BuiButton.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@ import { ButtonColor } from './types'
import type { TestWrapper } from '../../types/globalTypes'

describe('BuiButton', () => {
// @ts-ignore
// @ts-ignore-next-line
let wrapper: TestWrapper

const createComponent = (props: {
props: {
disabled?: boolean
color: ButtonColor
}
}) => {
Expand All @@ -18,25 +19,41 @@ describe('BuiButton', () => {
...props
})
}
test('default button classes is correct', () => {
test('default button snapshot', async () => {
createComponent({ props: { color: 'primary' } })

expect(wrapper.classes().join(' ')).toEqual(
'focus:ring-4 focus:ring-primary-200 font-medium rounded text-sm px-5 py-2.5 mr-2 mb-2 focus:outline-none bg-primary-500 hover:bg-primary-550 dark:bg-primary-500 dark:hover:bg-primary-600 dark:focus:ring-primary-400 text-white'
)
const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/default.output.html')
})
test('default disabled button snapshot', async () => {
createComponent({ props: { color: 'primary', disabled: true } })
const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/default-disabled.output.html')
})
test('secondary button classes is correct', () => {

test('secondary button classes is correct', async () => {
createComponent({ props: { color: 'secondary' } })

expect(wrapper.classes().join(' ')).toEqual(
'focus:ring-4 focus:ring-primary-200 font-medium rounded text-sm px-5 py-2.5 mr-2 mb-2 focus:outline-none bg-primary-150 hover:bg-primary-200 dark:bg-primary-650 dark:hover:bg-primary-700 dark:focus:ring-primary-300 text-primary-500'
)
const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/secondary.output.html')
})

test('secondary disabled button snapshot', async () => {
createComponent({ props: { color: 'secondary', disabled: true } })
const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/secondary-disabled.output.html')
})
test('text button classes is correct', () => {
createComponent({ props: { color: 'link' } })

expect(wrapper.classes().join(' ')).toEqual(
'focus:ring-4 focus:ring-primary-200 font-medium rounded text-sm px-5 py-2.5 mr-2 mb-2 focus:outline-none text-primary-500 bg-transparent hover:bg-primary-100 dark:hover:bg-primary-650 dark:hover:text-primary-400'
)
test('text button classes is correct', async () => {
createComponent({ props: { color: 'text' } })

const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/text.output.html')
})

test('text button disabled snapshot', async () => {
createComponent({ props: { color: 'text' } })

const result = wrapper.html()
await expect(result).toMatchFileSnapshot('./test/text-disabled.output.html')
})
})
51 changes: 47 additions & 4 deletions src/components/BuiButton/BuiButton.story.vue
Original file line number Diff line number Diff line change
@@ -1,16 +1,59 @@
<script setup lang="ts">
import BuiButton from './BuiButton.vue'
import { ButtonColor } from './types'
import { ButtonColor, ButtonSize } from './types'
const colorOptions: ButtonColor[] = ['primary', 'secondary', 'link']
const colorOptions: ButtonColor[] = ['primary', 'secondary', 'outline', 'text']
const sizes: {
name: string
value: ButtonSize
}[] = [
{
name: 'Large',
value: 'lg'
},
{
name: 'Medium',
value: 'md'
},
{
name: 'Small',
value: 'sm'
}
]
</script>

<template>
<Story title="BuiButton" autoPropsDisabled :layout="{ type: 'grid', width: '200px' }">
<Story title="BuiButton" autoPropsDisabled :layout="{ type: 'grid', width: '25%' }">
<Variant v-for="color in colorOptions" :title="color" :key="color">
<div class="p-4">
<div class="p-4 flex justify-center">
<BuiButton :color="color">{{ color }}</BuiButton>
</div>
</Variant>
<h2>Disabled</h2>
<Variant v-for="color in colorOptions" :title="color" :key="color">
<div class="p-4 flex justify-center">
<BuiButton :color="color" disabled>{{ color }}</BuiButton>
</div>
</Variant>
<h2>Sizes</h2>
<Variant v-for="size in sizes" :title="size.name" :key="size">
<div class="p-4 flex justify-center">
<BuiButton :size="size.value">{{ size.name }}</BuiButton>
</div>
</Variant>
</Story>
</template>

<docs lang="md">
# BuiButton

## Props:

### color

Values: `primary` | `secondary` | `text`

### size

Values: `lg` | `md` | `sm`
</docs>
95 changes: 77 additions & 18 deletions src/components/BuiButton/BuiButton.vue
Original file line number Diff line number Diff line change
@@ -1,32 +1,91 @@
<script setup lang="ts">
import { twMerge } from 'tailwind-merge'
import { twJoin, twMerge } from 'tailwind-merge'
import { computed } from 'vue-demi'
import { ButtonColor } from './types.ts'
const baseClasses =
'focus:ring-4 focus:ring-primary-200 font-medium rounded text-sm px-5 py-2.5 mr-2 mb-2 focus:outline-none'
const colorClasses: Record<ButtonColor, string> = {
primary:
'bg-primary-500 hover:bg-primary-550 dark:bg-primary-500 dark:hover:bg-primary-600 dark:focus:ring-primary-400 text-white',
secondary:
'bg-primary-150 hover:bg-primary-200 dark:bg-primary-650 dark:hover:bg-primary-700 dark:focus:ring-primary-300 text-primary-500',
link: 'text-primary-500 bg-transparent hover:bg-primary-100 dark:hover:bg-primary-650 dark:hover:text-primary-400'
}
import type { ButtonColor, ButtonSize } from './types.ts'
interface IBuiButtonProps {
color: ButtonColor
disabled?: boolean
color?: ButtonColor
size?: ButtonSize
}
const props = withDefaults(defineProps<IBuiButtonProps>(), {
color: 'primary'
disabled: false,
color: 'primary',
size: 'md'
})
const baseClasses = 'font-medium rounded text-sm focus:outline-none'
// Style Classes
const primaryButtonClasses = {
base: 'bg-primary-500 dark:bg-primary-500 text-white',
hover: 'hover:bg-primary-550 dark:hover:bg-primary-600',
focus: 'dark:focus:ring-primary-400 focus:bg-primary-575',
disabled:
'border-slate-300 hover:border-slate-300 bg-gray-150 dark:bg-primary-600 hover:bg-gray-150 text-gray-400 hover:text-gray-400 cursor-not-allowed'
}
const secondaryButtonClasses = {
base: 'bg-transparent text-primary-550',
hover: 'hover:bg-primary-150 dark:hover:bg-primary-650',
focus: 'dark:focus:ring-primary-300 focus:bg-primary-175',
disabled: 'text-primary-250 hover:bg-white cursor-not-allowed'
}
const textButtonClasses = {
base: 'text-primary-500 dark:text-primary-225 bg-transparent',
hover: 'dark:hover:text-primary-400',
focus: '',
disabled:
'text-primary-250 dark:text-primary-175 dark:hover:text-primary-175 bg-white hover:bg-white dark:bg-transparent cursor-not-allowed'
}
const outlineButtonClasses = {
base: 'text-primary-500 bg-transparent border border-primary-500 dark:border:primary-400 dark:text-primary-400',
hover: 'hover:bg-primary-150 dark:hover:text-primary-500 dark:hover:bg-primary-650',
focus: 'focus:bg-primary-175 dark:focus:bg-primary-625',
disabled:
'text-primary-250 border-primary-250 bg-primary-100 dark:bg-transparent hover:bg-primary-100 cursor-not-allowed dark:border-primary-590 dark:text-primary-590 dark:hover:text-primary-590'
}
const colorClasses: Record<ButtonColor, string> = {
primary: twJoin(
primaryButtonClasses.base,
primaryButtonClasses.hover,
primaryButtonClasses.focus,
props.disabled && primaryButtonClasses.disabled
),
secondary: twJoin(
secondaryButtonClasses.base,
secondaryButtonClasses.hover,
secondaryButtonClasses.focus,
props.disabled && secondaryButtonClasses.disabled
),
text: twJoin(
textButtonClasses.base,
textButtonClasses.hover,
textButtonClasses.focus,
props.disabled && textButtonClasses.disabled
),
outline: twJoin(
outlineButtonClasses.base,
outlineButtonClasses.hover,
outlineButtonClasses.focus,
props.disabled && outlineButtonClasses.disabled
)
}
const sizeClasses: Record<ButtonSize, string> = {
lg: 'py-2 px-5',
md: 'py-1 px-4',
sm: 'py-0.5 px-4'
}
const buttonClasses = computed(() => {
return twMerge(baseClasses, colorClasses[props.color])
return twMerge(baseClasses, colorClasses[props.color], sizeClasses[props.size])
})
</script>

<template>
<button :class="buttonClasses">
<slot>Primary</slot>
<button :class="buttonClasses" :disabled="disabled">
<slot name="prefix"></slot>
<slot name="default">Primary</slot>
<slot name="suffix"></slot>
</button>
</template>
1 change: 1 addition & 0 deletions src/components/BuiButton/test/default.output.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<button class="font-medium rounded text-sm focus:outline-none bg-primary-500 dark:bg-primary-500 text-white hover:bg-primary-550 dark:hover:bg-primary-600 dark:focus:ring-primary-400 focus:bg-primary-575 py-1 px-4">Primary</button>
1 change: 1 addition & 0 deletions src/components/BuiButton/test/secondaey.output.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<button class="focus:ring-4 focus:ring-primary-200 font-medium rounded text-sm focus:outline-none bg-primary-150 dark:bg-primary-650 text-primary-500 hover:bg-primary-200 dark:hover:bg-primary-700 dark:focus:ring-primary-300 py-1 px-4">Primary</button>
1 change: 1 addition & 0 deletions src/components/BuiButton/test/text.output.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<button class="font-medium rounded text-sm focus:outline-none text-primary-500 dark:text-primary-225 bg-transparent dark:hover:text-primary-400 py-1 px-4">Primary</button>
3 changes: 2 additions & 1 deletion src/components/BuiButton/types.ts
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export type ButtonColor = 'primary' | 'secondary' | 'link'
export type ButtonColor = 'primary' | 'secondary' | 'text' | 'outline'
export type ButtonSize = 'lg' | 'md' | 'sm'
Loading

0 comments on commit e376cd0

Please sign in to comment.