Viselect Documentation
repository·master·Indexed 25 days ago
https://github.com/simonwep/viselectA lightweight (~4kb), zero-dependency visual DOM-selection library that enables drag-to-select interactions. It supports mouse and touch interfaces, vertical/horizontal scrolling, and provides specific packages for Vanilla JS, React, Preact, and Vue. The library features a SelectionArea class for managing the selection process, a SelectionStore for state tracking, and support for standard keyboard modifiers like Ctrl, Cmd, and Shift.
What's inside Viselect
- Viselect is a visual DOM-selection library designed for high performance and minimal footprint. It allows users to perform drag-to-select actions on DOM elements, supporting both mouse and touch interfaces. It is highly optimized, has zero dependencies, and is compatible with various modern frameworks.
Access the official documentation for @viselect/vue
masterThe complete documentation for@viselect/vueand the broaderviselectecosystem is hosted online. For detailed guides, API references, and advanced usage patterns, visit the official documentation site.Access documentation for @viselect/vanilla
masterThe full documentation for the
@viselect/vanillapackage is hosted online. For detailed guides, API references, and advanced usage, visit the official documentation site.https://simonwep.github.io/viselectUse @viselect/preact for Preact applications
masterThe@viselect/preactpackage provides Preact-specific components and hooks for implementing selection logic within Preact applications. For full documentation, visit the official website.Use @viselect/react for React applications
masterThe@viselect/reactpackage provides React bindings for the Viselect selection library. For full documentation, API references, and detailed guides, visit the official documentation site.Quickstart with @viselect/vanilla
masterTo set up a selection area using the vanilla JavaScript package, import
SelectionAreaand instantiate it with a configuration object. You must specifyselectables(elements that can be selected) andboundaries(the area within which selection occurs). You can listen to events likestartandmoveto manage selection state, such as adding or removing CSS classes from elements as they are selected or deselected.import SelectionArea from '@viselect/vanilla'; const selection = new SelectionArea({ selectables: ['.container > div'], boundaries: ['.container'], selectionAreaClass: 'selectionArea' }).on('start', ({ store, event }) => { // Example: Clear selection if Ctrl/Meta key is not held if (!event.ctrlKey && !event.metaKey) { store.stored.forEach(el => el.classList.remove('selected')); selection.clearSelection(); } }).on('move', ({ store: { changed: { added, removed } } }) => { // Example: Update visual state during selection movement added.forEach(el => el.classList.add('selected')); removed.forEach(el => el.classList.remove('selected')); });Install @viselect/vanilla
masterTo use Viselect without a framework, install the vanilla package using your preferred package manager or via CDN.
$ npm add -D @viselect/vanilla$ pnpm add -D @viselect/vanilla$ yarn add -D @viselect/vanilla<script src="https://cdn.jsdelivr.net/npm/@viselect/vanilla/dist/viselect.umd.js"></script>import SelectionArea from "https://cdn.jsdelivr.net/npm/@viselect/vanilla/dist/viselect.mjs"Use the SelectionArea component in React
masterImport
SelectionAreafrom@viselect/reactto enable selection functionality in your React application.Key Implementation Details:
- Props: All Viselect options are exposed as direct props on the
SelectionAreacomponent (a one-to-one mapping to the originalSelectionOptions). - Re-renders: React does not deep-compare props for this component. Changing props will not trigger updates. To force a re-render with new configuration, you must add or change the
keyprop of theSelectionAreacomponent. - Event Types: Selection events use the
SelectionEventtype.
import {SelectionArea, SelectionEvent} from '@viselect/react'; import React, {FunctionComponent, useState} from 'react'; import './styles.css'; const App: FunctionComponent = () => { const [selected, setSelected] = useState<Set<number>>(() => new Set()); const extractIds = (els: Element[]): number[] => els.map(v => v.getAttribute('data-key')) .filter(Boolean) .map(Number); const onStart = ({ event, selection }: SelectionEvent) => { if (!event?.ctrlKey && !event?.metaKey) { selection.clearSelection(); setSelected(() => new Set()); } }; const onMove = ({ store: { changed: { added, removed } } }: SelectionEvent) => { setSelected(prev => { const next = new Set(prev); extractIds(added).forEach(id => next.add(id)); extractIds(removed).forEach(id => next.delete(id)); return next; }); }; return ( <> <SelectionArea className="container" onStart={onStart} onMove={onMove} selectables=".selectable"> {new Array(42).fill(0).map((_, index) => ( <div className={selected.has(index) ? 'selected selectable' : 'selectable'} data-key={index} key={index}/> ))} </SelectionArea> </> ); }- Props: All Viselect options are exposed as direct props on the
Get started with Viselect
masterTo begin using Viselect in your project, refer to the official documentation for installation and setup instructions. The library provides specific packages for different environments including Vanilla JS, React, Preact, and Vue.Use SelectionArea in Vue projects
masterImport the
SelectionAreacomponent from@viselect/vueto enable selection capabilities in your Vue templates.Configuration and Events
- Options: All configuration options are passed via a single
:optionsprop. These are a one-to-one mapping of the originalSelectionOptions. - Events: Events are handled as props suffixed with
on(e.g.,:onMove,:onStart). This pattern is used because events cannot return values synchronously in this integration.
<template> <SelectionArea class="container" :options="{ selectables: '.selectable' }" :onMove="onMove" :onStart="onStart"> <div v-for="id of 42" class="selectable" :key="id" :data-key="id" :class="{ selected: selected.has(id) }"/> </SelectionArea> </template> <script lang="ts" setup> import { SelectionArea, SelectionEvent } from '@viselect/vue'; import { reactive } from 'vue'; const selected = reactive<Set<number>>(new Set()); const extractIds = (els: Element[]): number[] => { return els.map(v => v.getAttribute('data-key')) .filter(Boolean) .map(Number); }; const onStart = ({ event, selection }: SelectionEvent) => { if (!event?.ctrlKey && !event?.metaKey) { selection.clearSelection(); selected.clear(); } }; const onMove = ({ store: { changed: { added, removed } } }: SelectionEvent) => { extractIds(added).forEach(id => selected.add(id)); extractIds(removed).forEach(id => selected.delete(id)); }; </script>- Options: All configuration options are passed via a single
Use Viselect in vanilla JavaScript
masterImport the
SelectionAreaclass from@viselect/vanillato manage element selection. You can configureselectables(the elements that can be selected) andboundaries(the containers that define the selection area). Use event listeners likeon('start', ...)andon('move', ...)to react to selection changes.import { SelectionArea } from '@viselect/vanilla'; import './styles.css'; // Generate some divs to select later [ ['.container.blue', 33], ['.container.green', 33] ].forEach(([selector, items]) => { const container = document.querySelector(selector); for (let i = 0; i < items; i++) { container.appendChild(document.createElement('div')); } }); // Instantiate the selection area const selection = new SelectionArea({ selectables: ['.container > div'], // Specifies the elements that can be selected boundaries: ['.container'], // Specifies the boundaries of each selection }).on('start', ({ store, event }) => { if (!event.ctrlKey && !event.metaKey && !event.shiftKey) { // Clear selection if no modifier key is pressed store.stored.forEach(el => el.classList.remove('selected')); selection.clearSelection(); } }).on('move', ({ store: { changed: { added, removed } } }) => { added.forEach(el => el.classList.add('selected')); removed.forEach(el => el.classList.remove('selected')); });Update selectables during an active selection
masterIf you add or remove selectable elements (for example, during a scroll event) while a selection is in progress, you must callselection.resolveSelectables()to ensureviselectrecognizes the changes in the DOM.