import { useCallback } from 'react';
import toast from 'react-hot-toast';
import {
  addStartNode,
  addEndNode,
  setCoordinates,
  addCoordinate,
  reset as resetCoordinates,
} from '../store/reducers/coordinatesReducer';
import { createContext, useRef } from 'react';
import { useDispatch, useSelector } from 'react-redux';

const CreatedEditablePolylineContext = createContext({
  polylineRef: {},
  parentCoordinate: {},
  coordinates: [],
  setParent: () => {},
  setPolyline: () => {},
  setParentCoordinate: () => {},
  setCoordinates: () => {},
  addVertex: () => {},
  reset: () => {},
});

const EditableContextProvider = ({ children }) => {
  const dispatch = useDispatch();
  const { startNode, endNode, coordinates, drawOnMap } = useSelector(
    (state) => state.coordinatesReducer
  );

  const polylineRef = useRef(null);

  const addCoordinates = useCallback(
    (latLng) => {
      drawOnMap && dispatch(addCoordinate(latLng));
    },
    [dispatch, drawOnMap]
  );
  const setParent = useCallback(
    (node, latLng) => {
      if (!drawOnMap) return;

      if (!startNode) {
        dispatch(addStartNode(node));
        addCoordinates(latLng.toJSON());
        toast.success(`${node.name} selected as Start Node`);
      } else if (startNode && !endNode) {
        dispatch(addEndNode(node));
        addCoordinates(latLng.toJSON());
        toast.success(`${node.name} selected as End Node`);
      }
    },
    [dispatch, startNode, endNode, addCoordinates, drawOnMap]
  );

  const addVertex = useCallback(
    (event) => {
      addCoordinates(event.latLng.toJSON());
    },
    [addCoordinates]
  );

  const reset = useCallback(() => {
    dispatch(resetCoordinates());
  }, [dispatch]);

  return (
    <CreatedEditablePolylineContext.Provider
      value={{
        polylineRef,
        setParent,
        coordinates,
        setCoordinates,
        addVertex,
        reset,
      }}
    >
      {children}
    </CreatedEditablePolylineContext.Provider>
  );
};

export { CreatedEditablePolylineContext, EditableContextProvider };
