Skip to content

Commit

Permalink
Update effect initialization/cleanup strategy
Browse files Browse the repository at this point in the history
  • Loading branch information
clauderic committed Jun 6, 2024
1 parent 78e9cb4 commit 9d802c6
Show file tree
Hide file tree
Showing 6 changed files with 49 additions and 40 deletions.
7 changes: 6 additions & 1 deletion packages/abstract/src/core/entities/draggable/draggable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,23 +6,26 @@ import {Modifier} from '../../modifiers/index.ts';
import type {Modifiers} from '../../modifiers/index.ts';
import type {DragDropManager} from '../../manager/index.ts';
import {descriptor} from '../../plugins/index.ts';
import type {Sensors} from '../../sensors/sensor.ts';

export interface Input<
T extends Data = Data,
U extends Draggable<T> = Draggable<T>,
> extends EntityInput<T, U> {
type?: Type;
modifiers?: Modifiers;
sensors?: Sensors;
}

export class Draggable<T extends Data = Data> extends Entity<T> {
constructor(
{modifiers, type, ...input}: Input<T>,
{modifiers, type, sensors, ...input}: Input<T>,
public manager: DragDropManager
) {
super(input, manager);

this.type = type;
this.sensors = sensors;

if (modifiers?.length) {
this.modifiers = modifiers.map((modifier) => {
Expand All @@ -33,6 +36,8 @@ export class Draggable<T extends Data = Data> extends Entity<T> {
}
}

public sensors: Sensors | undefined;

public modifiers: Modifier[] | undefined;

@reactive
Expand Down
50 changes: 26 additions & 24 deletions packages/abstract/src/core/entities/entity/entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,33 +53,28 @@ export class Entity<T extends Data = Data> {
this.id = id;
this.data = data;
this.disabled = disabled;
this.effects = [
() => {
// Re-run this effect whenever the `id` changes
const {id: _} = this;

queueMicrotask(() => {
if (options?.register !== false) {
manager.registry.register(this);
}

const cleanupEffects = effects(
() => {
// Re-run this effect whenever the `id` changes
const {id: _} = this;

if (id === previousId) {
return;
}
if (id === previousId) {
return;
}

manager.registry.register(this);
manager.registry.register(this);

return () => manager.registry.unregister(this);
},
...getEffects()
);
return () => manager.registry.unregister(this);
},
...getEffects(),
];
this.destroy = this.destroy.bind(this);

this.destroy = () => {
manager.registry.unregister(this);
cleanupEffects();
};
});
if (options?.register !== false) {
queueMicrotask(() => {
manager.registry.register(this);
});
}
}

/**
Expand All @@ -100,9 +95,16 @@ export class Entity<T extends Data = Data> {
@reactive
public disabled: boolean;

/**
* An array of effects that are applied to the entity.
*/
public effects: Effect[];

/**
* A method that cleans up the entity when it is no longer needed.
* @returns void
*/
public destroy(): void {}
public destroy(): void {
this.manager.registry.unregister(this);
}
}
12 changes: 11 additions & 1 deletion packages/abstract/src/core/entities/entity/registry.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import {signal} from '@dnd-kit/state';
import {effects, signal} from '@dnd-kit/state';

import type {Entity} from './entity.ts';
import type {UniqueIdentifier} from './types.ts';
Expand All @@ -10,6 +10,7 @@ import type {UniqueIdentifier} from './types.ts';
*/
export class EntityRegistry<T extends Entity> {
private map = signal<Map<UniqueIdentifier, T>>(new Map());
private cleanupFunctions = new WeakMap<T, () => void>();

/**
* Iterator for the EntityRegistry class.
Expand Down Expand Up @@ -59,6 +60,9 @@ export class EntityRegistry<T extends Entity> {

this.map.value = updatedMap;

const cleanup = effects(...value.effects);
this.cleanupFunctions.set(value, cleanup);

return () => this.unregister(key, value);
};

Expand All @@ -74,6 +78,10 @@ export class EntityRegistry<T extends Entity> {
return;
}

const cleanup = this.cleanupFunctions.get(value);
cleanup?.();
this.cleanupFunctions.delete(value);

const updatedMap = new Map(current);
updatedMap.delete(key);

Expand All @@ -85,6 +93,8 @@ export class EntityRegistry<T extends Entity> {
*/
public destroy() {
for (const entry of this) {
const cleanup = this.cleanupFunctions.get(entry);
cleanup?.();
entry.destroy();
}

Expand Down
6 changes: 3 additions & 3 deletions packages/abstract/src/core/manager/registry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,9 @@ export class DragDropRegistry<
public sensors: PluginRegistry<V, SensorConstructor<V>>;
public modifiers: PluginRegistry<V, ModifierConstructor<V>>;

public register(input: Entity): Entity;
public register(input: Draggable): Draggable;
public register(input: Droppable): Droppable;
public register(input: Entity): () => void;
public register(input: Draggable): () => void;
public register(input: Droppable): () => void;
public register(input: SensorConstructor, options?: SensorOptions): Sensor;
public register(input: ModifierConstructor): Modifier;
public register(input: PluginConstructor, options?: PluginOptions): Plugin;
Expand Down
7 changes: 1 addition & 6 deletions packages/dom/src/core/entities/draggable/draggable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import type {
DraggableInput,
DragDropManager as AbstractDragDropManager,
} from '@dnd-kit/abstract';
import {effect, reactive} from '@dnd-kit/state';
import {reactive} from '@dnd-kit/state';

import type {Sensors} from '../../sensors/index.ts';

Expand All @@ -32,16 +32,12 @@ export class Draggable<T extends Data = Data> extends AbstractDraggable<T> {
@reactive
public feedback: FeedbackType;

@reactive
public sensors: Sensors | undefined;

constructor(
{
element,
effects = () => [],
handle,
feedback = 'default',
sensors,
...input
}: Input<T>,
public manager: AbstractDragDropManager<any, any>
Expand Down Expand Up @@ -79,6 +75,5 @@ export class Draggable<T extends Data = Data> extends AbstractDraggable<T> {
this.element = element;
this.handle = handle;
this.feedback = feedback;
this.sensors = sensors;
}
}
7 changes: 2 additions & 5 deletions packages/react/src/core/hooks/useInstance.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,8 @@ export function useInstance<T extends Entity>(
const [instance] = useState<T>(() => initializer(manager));

useEffect(() => {
manager.registry.register(instance);

return () => {
manager.registry.unregister(instance);
};
// Register returns an unregister callback
return manager.registry.register(instance);
}, []);

return instance;
Expand Down

0 comments on commit 9d802c6

Please sign in to comment.