wip bsky client for the web & android bbell.vt3e.cat
at main 84 lines 1.7 kB view raw
1<script setup lang="ts"> 2import { useId } from 'vue' 3import { IconCheckRounded } from '@iconify-prerendered/vue-material-symbols' 4 5defineProps<{ 6 label?: string 7 disabled?: boolean 8}>() 9 10const model = defineModel<boolean>() 11const id = useId() 12</script> 13 14<template> 15 <div class="checkbox-wrapper" :class="{ disabled }" @click.stop="!disabled && (model = !model)"> 16 <div 17 class="checkbox-box" 18 :class="{ 'is-checked': model }" 19 role="checkbox" 20 :aria-checked="model" 21 :tabindex="disabled ? -1 : 0" 22 @keydown.space.prevent="!disabled && (model = !model)" 23 > 24 <IconCheckRounded class="check-icon" /> 25 </div> 26 <label v-if="label" :for="id" class="label">{{ label }}</label> 27 </div> 28</template> 29 30<style scoped> 31.checkbox-wrapper { 32 display: inline-flex; 33 align-items: center; 34 gap: 0.75rem; 35 cursor: pointer; 36 user-select: none; 37} 38 39.checkbox-wrapper.disabled { 40 opacity: 0.5; 41 cursor: not-allowed; 42} 43 44.checkbox-box { 45 width: 1.5rem; 46 height: 1.5rem; 47 border-radius: 0.5rem; 48 border: 2px solid hsla(var(--subtext0) / 0.75); 49 background-color: hsla(var(--surface0) / 0.5); 50 display: flex; 51 align-items: center; 52 justify-content: center; 53 color: hsl(var(--base)); 54 55 &:hover { 56 background-color: hsla(var(--surface0) / 1); 57 border-color: hsla(var(--subtext0) / 0.75); 58 } 59} 60 61.checkbox-box.is-checked { 62 background-color: hsl(var(--accent)); 63 border-color: hsl(var(--accent)); 64} 65 66.check-icon { 67 width: 100%; 68 height: 100%; 69 opacity: 0; 70 transform: scale(0.5); 71 transition: all 0.2s; 72} 73 74.checkbox-box.is-checked .check-icon { 75 opacity: 1; 76 transform: scale(1); 77} 78 79.label { 80 color: hsl(var(--text)); 81 font-size: 1rem; 82 cursor: inherit; 83} 84</style>