// -*- C++ -*- //

#ifndef MAPSTORAGE_H
#define MAPSTORAGE_H

#include <all_include.h>

///Class MapStorage is responsible for storing
///NodeMaps and EdgeMaps that can be shown later
///on GUI. Therefore maps can be added to it,
///and datas over the added maps can be queried.
///The maps will be stored in an std::map,
///referenced with their names. Unfortunately at
///the moment it works only with double type maps
///
///\todo too many things are public!!
class MapStorage
{
public:

  Graph &g;

  ///Stores double type NodeMaps
  std::map< std::string,Graph::NodeMap<double> * > nodemap_storage;

  ///Stores double type EdgeMaps
  std::map< std::string,Graph::EdgeMap<double> * > edgemap_storage;

  //Stores the default values for the different visualization node attributes
  std::vector<Graph::NodeMap<double> > default_nodemaps;

  //Stores the default values for the different visualization edge attributes
  std::vector<Graph::EdgeMap<double> > default_edgemaps;

public:
  ///Constructor of MapStorage. Expects the Graph of
  ///which maps will be stored in it.
  ///Its all activity is initializing default values
  ///for different visualization attributes
  ///
  ///\param graph is the graph for which the maps are stored in this object.
  MapStorage(Graph &);

  ///Adds given map to storage. A name and the map itself has to be provided.
  ///\param name is the name of map
  ///\nodemap is the pointer of the given nodemap
  ///\todo map should be given by reference!
  int addNodeMap(const std::string &,Graph::NodeMap<double> *);

  ///Adds given map to storage. A name and the map itself has to be provided.
  ///\param name is the name of map
  ///\edgemap is the pointer of the given edgemap
  ///\todo map should be given by reference!
  int addEdgeMap(const std::string &,Graph::EdgeMap<double> *);

  ///Returns how much nodemaps is stored in \ref MapStorage
  int numOfNodeMaps() {return nodemap_storage.size();};

  ///Returns how much edgemaps is stored in \ref MapStorage
  int numOfEdgeMaps() {return edgemap_storage.size();};

  ///Returns the maximum value of the given NodeMap. NodeMap has to be given by its name.
  ///\param name is the name of map of which maximum is searched
  double maxOfNodeMap(const std::string &);

  ///Returns the maximum value of the given EdgeMap. EdgeMap has to be given by its name.
  ///\param name is the name of map of which maximum is searched
  double maxOfEdgeMap(const std::string &);

  ///Returns the minimum value of the given NodeMap. NodeMap has to be given by its name.
  ///\param name is the name of map of which minimum is searched
  double minOfNodeMap(const std::string &);

  ///Returns the minimum value of the given EdgeMap. EdgeMap has to be given by its name.
  ///\param name is the name of map of which minimum is searched
  double minOfEdgeMap(const std::string &);

  ///To be able to iterate through each maps this function returns an iterator pointing to the first nodemap in the storage.
  std::map< std::string,Graph::NodeMap<double> * >::iterator beginOfNodeMaps(){return nodemap_storage.begin();};

  ///To be able to iterate through each maps this function returns an iterator pointing to the first edgemap in the storage.
  std::map< std::string,Graph::EdgeMap<double> * >::iterator beginOfEdgeMaps(){return edgemap_storage.begin();};

  ///To be able to iterate through each maps this function returns an iterator pointing to the last nodemap in the storage.
  std::map< std::string,Graph::NodeMap<double> * >::iterator endOfNodeMaps(){return nodemap_storage.end();};

  ///To be able to iterate through each maps this function returns an iterator pointing to the last edgemap in the storage.
  std::map< std::string,Graph::EdgeMap<double> * >::iterator endOfEdgeMaps(){return edgemap_storage.end();};

  ///This function sets a default base value for the newly created node
  void initMapsForNode(NodeIt);

  ///This function sets a default base value for the newly created node
  void initMapsForEdge(Graph::Edge);
};

#endif //MAPSTORAGE_H
