108 lines
2.1 KiB
Vue
108 lines
2.1 KiB
Vue
|
|
<template>
|
||
|
|
<button
|
||
|
|
class="pixel-button"
|
||
|
|
:class="[variantClass, sizeClass, { disabled }]"
|
||
|
|
:disabled="disabled"
|
||
|
|
@click="handleClick"
|
||
|
|
>
|
||
|
|
<slot />
|
||
|
|
</button>
|
||
|
|
</template>
|
||
|
|
|
||
|
|
<script setup>
|
||
|
|
const props = defineProps({
|
||
|
|
variant: {
|
||
|
|
type: String,
|
||
|
|
default: 'primary', // 'primary', 'success', 'danger', 'warning'
|
||
|
|
validator: (value) => ['primary', 'success', 'danger', 'warning'].includes(value)
|
||
|
|
},
|
||
|
|
size: {
|
||
|
|
type: String,
|
||
|
|
default: 'normal', // 'small', 'normal', 'large'
|
||
|
|
validator: (value) => ['small', 'normal', 'large'].includes(value)
|
||
|
|
},
|
||
|
|
disabled: {
|
||
|
|
type: Boolean,
|
||
|
|
default: false
|
||
|
|
}
|
||
|
|
})
|
||
|
|
|
||
|
|
const emit = defineEmits(['click'])
|
||
|
|
|
||
|
|
const variantClass = computed(() => `variant-${props.variant}`)
|
||
|
|
const sizeClass = computed(() => `size-${props.size}`)
|
||
|
|
|
||
|
|
const handleClick = (event) => {
|
||
|
|
if (!props.disabled) {
|
||
|
|
emit('click', event)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
</script>
|
||
|
|
|
||
|
|
<style scoped>
|
||
|
|
.pixel-button {
|
||
|
|
font-family: 'Press Start 2P', cursive;
|
||
|
|
border: 3px solid #000;
|
||
|
|
padding: 12px 24px;
|
||
|
|
cursor: pointer;
|
||
|
|
position: relative;
|
||
|
|
box-shadow: 4px 4px 0px rgba(0, 0, 0, 0.3);
|
||
|
|
transition: all 0.1s ease;
|
||
|
|
image-rendering: pixelated;
|
||
|
|
font-size: 12px;
|
||
|
|
text-transform: uppercase;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button:hover:not(.disabled) {
|
||
|
|
transform: translate(-1px, -1px);
|
||
|
|
box-shadow: 5px 5px 0px rgba(0, 0, 0, 0.4);
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button:active:not(.disabled) {
|
||
|
|
transform: translate(2px, 2px);
|
||
|
|
box-shadow: 2px 2px 0px rgba(0, 0, 0, 0.3);
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.disabled {
|
||
|
|
opacity: 0.5;
|
||
|
|
cursor: not-allowed;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Variants */
|
||
|
|
.pixel-button.variant-primary {
|
||
|
|
background: var(--color-primary);
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.variant-success {
|
||
|
|
background: var(--color-success);
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.variant-danger {
|
||
|
|
background: var(--color-danger);
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.variant-warning {
|
||
|
|
background: var(--color-warning);
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Sizes */
|
||
|
|
.pixel-button.size-small {
|
||
|
|
padding: 8px 16px;
|
||
|
|
font-size: 10px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.size-normal {
|
||
|
|
padding: 12px 24px;
|
||
|
|
font-size: 12px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.pixel-button.size-large {
|
||
|
|
padding: 16px 32px;
|
||
|
|
font-size: 14px;
|
||
|
|
}
|
||
|
|
</style>
|