import { SetState } from '../../models';
import { ShapeConfig, StoreValue, SubcribeHandler } from './types';

export class AnnotatorStore {
  private store: StoreValue = {
    background: '',
    shapes: [],
    selectedShapeId: null,
  };

  private subscribers = new Set<SubcribeHandler>();

  private notify() {
    this.subscribers.forEach((handler) => handler(this.store));
  }

  subscribe = (handler: SubcribeHandler) => {
    this.subscribers.add(handler);

    return () => {
      this.subscribers.delete(handler);
    };
  };

  addShapes(shapes: ShapeConfig[]) {
    this.store.shapes = this.store.shapes.concat(shapes);
    this.notify();
  }

  removeShapes(shapeIds: ShapeConfig['id'][]) {
    this.store.shapes = this.store.shapes.filter(
      (shape) => !shapeIds.includes(shape.id),
    );

    this.notify();
  }

  setShapes(shapesHandler: SetState<ShapeConfig[]>) {
    this.store.shapes =
      typeof shapesHandler === 'function'
        ? shapesHandler(this.store.shapes)
        : shapesHandler;
    this.notify();
  }

  setBackground(background: string) {
    this.store.background = background;
    this.notify();
  }

  setSelectedShape(shapeId: ShapeConfig['id'] | null) {
    this.store.selectedShapeId = shapeId;
    this.notify();
  }

  setStore(storeHandler: SetState<StoreValue>) {
    this.store =
      typeof storeHandler === 'function'
        ? storeHandler(this.store)
        : storeHandler;
    this.notify();
  }

  getStore(): StoreValue {
    return this.store;
  }
}
