Refonte front (packages/web) : coquille applicative partagée (sidebar desktop + barre d'onglets mobile + PageHeader, langue/push/logout centralisés) pilotée par route.meta.layout ; design system (BaseButton/BaseBadge/SegmentedControl/EmptyState/ SkeletonRow, anneau de focus, icônes @lucide/vue) ; tri/filtre/recherche/pagination côté client via useListControls (+ synchro URL) sur sessions/worktrees/groupes ; section « À traiter », palette de commandes ⌘K, toasts. Aucune modif serveur/protocole/DB. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
23 lines
767 B
TypeScript
23 lines
767 B
TypeScript
import { ref, watch, onUnmounted, getCurrentInstance, type Ref } from 'vue';
|
|
|
|
/**
|
|
* Renvoie un miroir débouncé d'un ref source. Le ref source reste instantané (idéal pour un
|
|
* v-model d'input) ; le miroir ne se met à jour qu'après `delay` ms de stabilité — c'est lui
|
|
* que le pipeline de tri/filtre consomme, pour ne pas recalculer à chaque frappe.
|
|
*/
|
|
export function useDebouncedRef<T>(source: Ref<T>, delay = 150): Ref<T> {
|
|
const debounced = ref(source.value) as Ref<T>;
|
|
let timer: ReturnType<typeof setTimeout> | undefined;
|
|
|
|
watch(source, (v) => {
|
|
clearTimeout(timer);
|
|
timer = setTimeout(() => {
|
|
debounced.value = v;
|
|
}, delay);
|
|
});
|
|
|
|
if (getCurrentInstance()) onUnmounted(() => clearTimeout(timer));
|
|
|
|
return debounced;
|
|
}
|