ember-sortable
Version:
Sortable UI primitives for Ember.
346 lines (345 loc) • 9.54 kB
TypeScript
import Modifier from 'ember-modifier';
import type { ArgsFor, PositionalArgs, NamedArgs } from 'ember-modifier';
import type EmberSortableService from '../services/ember-sortable-internal-state.ts';
import type Owner from '@ember/owner';
import type { Group } from '../services/ember-sortable-internal-state.ts';
import type SortableGroupModifier from './sortable-group.ts';
import type { TDirection } from './sortable-group.ts';
export interface MoveDirection {
left: boolean;
right: boolean;
top: boolean;
bottom: boolean;
}
export interface FakeEvent {
pageX: number;
pageY: number;
clientX: number;
clientY: number;
}
export interface SortableItemModifierSignature<T> {
Args: {
Named: {
model: T;
groupName?: string;
disabled?: boolean;
updateInterval?: number;
spacing?: number;
isDraggingDisabled?: boolean;
handle?: string;
distance?: number;
disableCheckScrollBounds?: boolean;
onDragStart?: (item: T) => void;
onDragStop?: (item: T) => void;
};
};
Element: HTMLElement;
}
/**
* Modifier to mark an element as an item to be reordered
*
* @param {Object} model The model that this item will represent
* @param {boolean} [disabled=false] Set to true to make this item not sortable
* @param {Function} [onDragStart] An optional callback for when dragging starts.
* @param {Function} [onDragStop] An optional callback for when dragging stops.
*
* @module drag-drop/draggable-group
* @example
* <ol {{sortable-group onChange=this.update a11yAnnouncementConfig=this.myA11yConfig}}>
* {{#each model.items as |item|}}
* <li {{sortable-item model=item}}>
* {{item.name}}
* <span class="handle" {{sortable-handle}}>↕</span>
* </li>
* {{/each}}
* </ol>
*/
export default class SortableItemModifier<T> extends Modifier<SortableItemModifierSignature<T>> {
className: string;
sortableService: EmberSortableService<T>;
startEvent?: FakeEvent | Event;
_sortableGroup?: Group<T>;
_x?: number;
_y?: number;
_dragOriginX?: number;
_dragOriginY?: number;
_pageX?: number;
_pageY?: number;
/**
* The SortableGroupModifier this item belongs to. Assigned by the group
* when it inspects all the items in the list
*
* @type SortableGroupModifier
*/
get sortableGroup(): SortableGroupModifier<T>;
get model(): T;
get direction(): TDirection;
get groupDisabled(): boolean;
/**
* This is the group name used to keep groups separate if there are more than one on the screen at a time.
* If no group is assigned a default is used
*
* @default "_EmberSortableGroup"
* @returns {string}
*/
get groupName(): string;
/**
The frequency with which the group is informed
that an update is required.
@property updateInterval
@type Number
@default 125
*/
get updateInterval(): number;
/**
Additional spacing between active item and the rest of the elements.
@property spacing
@type Number
@default 0[px]
*/
get spacing(): number;
/**
Removes the ability for the current item to be sorted
@property disabled
@type boolean
@default false
*/
get isDisabled(): boolean;
/**
Selector for the element to use as handle.
1. By default, we will hook it the yielded sortable-handle.
2. If you don't use the sortable-handle, the entire element will be used as the handle.
3. In very rare situations, if you want to use a handle, but not the sortable-handle,
you can override this class with your own handle's selector. This behavior will be
synonymous with v1
@property handle
@type String
@default "[data-sortable-handle]"
*/
get handle(): string;
handleElement?: HTMLElement | null;
/**
* Tolerance, in pixels, for when sorting should start.
* If specified, sorting will not start until after mouse
* is dragged beyond distance. Can be used to allow for clicks
* on elements within a handle.
*
* @property distance
* @type Integer
* @default 0
*/
get distance(): number;
/**
* True if the item is currently being dragged.
*
* @property isDragging
* @type boolean
* @default false
* @protected
*/
_isDragging: boolean;
get isDragging(): boolean;
set isDragging(value: boolean);
/**
* Gives info in which direction the element will be moved
*
* @property moveDirection
* @type Object
*/
get moveDirection(): MoveDirection;
/**
Action that fires when the item starts being dragged.
@property onDragStart
@type Function
@param {Object} item model
@default null
*/
get onDragStart(): (item: T) => void;
/**
Action that fires when the item stops being dragged.
@property onDragStop
@type Function
@param {Object} item model
@default null
*/
get onDragStop(): (item: T) => void;
/**
True if the item is currently dropping.
@property isDropping
@type Boolean
@default false
*/
_isDropping: boolean;
get isDropping(): boolean;
set isDropping(value: boolean);
/**
True if the item was dropped during the interaction
@property wasDropped
@type Boolean
@default false
*/
wasDropped: boolean;
/**
@property isBusy
@type Boolean
*/
get isBusy(): boolean;
/**
@property disableCheckScrollBounds
*/
get disableCheckScrollBounds(): boolean;
/**
@method mouseDown
*/
mouseDown(event: MouseEvent): void;
keyDown(event: Event): void;
/**
@method touchStart
*/
touchStart(event: TouchEvent): void;
/**
@method freeze
*/
freeze(): void;
/**
@method reset
*/
reset(): void;
/**
@method thaw
*/
thaw(): void;
_prepareDragListener: () => void;
_cancelStartDragListener: () => void;
/**
* Setup event listeners for drag and drop
*
* @method _primeDrag
* @param {Event} startEvent JS Event object
* @private
*/
_primeDrag(startEvent: Event): void;
/**
* Prepares for the drag event
*
* @method _prepareDrag
* @param {Event} startEvent JS Event object
* @param {Event} event JS Event object
* @private
*/
_prepareDrag(startEvent: MouseEvent, event: MouseEvent): void;
/**
* Start dragging & setup more event listeners
*
* @method _startDrag
* @param {Event} event JS Event object
* @private
*/
_startDrag(event: MouseEvent | TouchEvent): void;
/**
The maximum scroll speed when dragging element.
@property maxScrollSpeed
@default 20
*/
maxScrollSpeed: number;
_scrollOnEdges(drag: (event: FakeEvent | Event) => void): void;
/**
@method _makeDragHandler
@param {Event} startEvent
@return {Function}
@private
*/
_makeDragHandler(startEvent: FakeEvent | Event): (event: FakeEvent | Event) => void;
/**
@method _scheduleApplyPosition
@private
*/
_scheduleApplyPosition(): void;
/**
@method _applyPosition
@private
*/
_applyPosition(): void;
/**
@method _drag
@private
*/
_drag(dimensionX: number, dimensionY: number): void;
/**
@method _drop
@private
*/
_drop(): void;
/**
@method _preventClick
@private
*/
_preventClick(): void;
/**
@method _preventClickHandler
@private
*/
_preventClickHandler(e: Event): void;
/**
@method _waitForTransition
@private
@return Promise
*/
_waitForTransition(): Promise<unknown>;
/**
@method _waitForTransitions
@private
@return Promise
*/
_waitForAllTransitions(): Promise<unknown>;
/**
@method _complete
@private
*/
_complete(): void;
get isAnimated(): boolean | undefined;
/**
The current transition duration in milliseconds.
@property transitionDuration
@type Number
*/
get transitionDuration(): number;
/**
Horizontal position of the item.
@property x
@type Number
*/
get x(): number;
set x(value: number);
/**
Vertical position of the item relative to its offset parent.
@property y
@type Number
*/
get y(): number;
set y(value: number);
/**
Width of the item.
@property height
@type Number
*/
get width(): number;
/**
Height of the item including margins.
@property height
@type Number
*/
get height(): number;
addEventListener(): void;
removeEventListener(): void;
setupHandleElement(disabled?: boolean): void;
element: HTMLElement;
didSetup: boolean;
named: NamedArgs<SortableItemModifierSignature<T>>;
/**
* tracks if event listeners have been registered. Registering event handlers is unnecessary if item is disabled.
*/
listenersRegistered: boolean;
constructor(owner: Owner, args: ArgsFor<SortableItemModifierSignature<T>>);
modify(element: HTMLElement, _positional: PositionalArgs<SortableItemModifierSignature<T>>, named: NamedArgs<SortableItemModifierSignature<T>>): void;
}