/* Copyright (c) 1997-2006
   Ewgenij Gawrilow, Michael Joswig (Technische Universitaet Berlin, Germany)
   http://www.math.tu-berlin.de/polymake,  mailto:polymake@math.tu-berlin.de

   This program is free software; you can redistribute it and/or modify it
   under the terms of the GNU General Public License as published by the
   Free Software Foundation; either version 2, or (at your option) any
   later version: http://www.gnu.org/licenses/gpl.txt.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.
*/

#ifndef _POLYMAKE_SCHLEGEL_WINDOW_H
#define _POLYMAKE_SCHLEGEL_WINDOW_H "$Project: polymake $$Id: SchlegelWindow.h 7315 2006-04-02 21:37:53Z gawrilow $"

#include <Matrix.h>
#include <Vector.h>
#include <Graph.h>
#include <Map.h>

namespace polymake { namespace polytope {

// One instance of this class per window, providing several simultaneously visible projection facets
class SchlegelWindow {
   int d, proj_facet;
   typedef Map<std::string, double> param_map;
   typedef Map<std::string, bool > iparam_map;
   param_map params;
   iparam_map iparams;
   Matrix<double> Vertices, NeighborFacets, Points, inv_Rotation;
   Vector<double> ViewRay, FacetPoint;
   bool constrained;
public:
   typedef std::pair<int, Vector<double> > dragged_point;	// index and new coordinates
  
   SchlegelWindow(const Matrix<double>& V, const Matrix<double>& F, const Graph<>& FG,
		  const Vector<double>& FacetPoint_arg, const Vector<double>& InteriorPoint,
		  int facet_index, const double& zoom_arg);

   int get_proj_facet() const { return proj_facet; }
   const Matrix<double>& get_points() const { return Points; }

   const iparam_map& get_iparams() const { return iparams; }
   const param_map& get_params() const { return params; }


   const double& get_param(const std::string& key) { return params[key];}
   const bool& get_iparam(const std::string& key) { return iparams[key]; }

   void set_param(const std::string& key, const double val) { params[key] = val; compute_points();} 
   void set_iparam(const std::string& key, bool value) { iparams[key] = value; }

   enum drag_response { drag_OK, drag_ignore, drag_boundary };
   drag_response drag_point(dragged_point& dragged, const IncidenceMatrix<>& VIF);

   std::pair< Vector<double>, Vector<double> > reconstruct_params() const;
private:
   void compute_points();
   double inverse_zoom();
};

} }

#endif // _POLYMAKE_SCHLEGEL_WINDOW_H

// Local Variables:
// mode:C++
// c-basic-offset:3
// End:
