/* LICENSE:
  =========================================================================
    CMPack'04 Source Code Release for OPEN-R SDK 1.1.5-r2 for ERS7
    Copyright (C) 2004 Multirobot Lab [Project Head: Manuela Veloso]
    School of Computer Science, Carnegie Mellon University
    All rights reserved.
  ========================================================================= */

#ifndef INCLUDED_Environment_h
#define INCLUDED_Environment_h

class SensorInterp;

#include "../../headers/Geometry.h"
#include "../../headers/Util.h"

#include "LocalizationEngine.h"

/*------------------------------------------------------------------
CLASS
  EnvironmentObject

DESCRIPTION
  An object in the environment.
------------------------------------------------------------------*/
class EnvironmentObject {
public:
  class Point{
  public:
    double x,y;
  };

  // represents lines of a particular type
  struct Lines{
    static const int MaxLines=9;
    int num_lines;
    vector2d p0[MaxLines],p1[MaxLines];
  };

  // represenst a class of corner detections
  struct Corners{
    static const int MaxCorners=10;
    int num_corners;
    vector2d loc[MaxCorners];
  };

  struct ObjectData {
    Point point_data;
    double unif_range; // range readings might be too far by
    Lines line_data;
    Corners corner_data;
  };

  ObjectData loc;

  EnvironmentObject() {
    mzero(*this);
  }

protected:
private: // methods
private: // data
};

/*------------------------------------------------------------------
CLASS
  PointLandmarkObject

DESCRIPTION
  A point landmark.
------------------------------------------------------------------*/
class PointLandmarkObject : public EnvironmentObject {
public:
  void init(double x, double y);
  
protected:
private: // methods
private: // data
};

/*------------------------------------------------------------------
CLASS
  Environment

DESCRIPTION
  An environment in which th robot operates.
------------------------------------------------------------------*/
class Environment {
public:
  virtual ~Environment();

  virtual void getAnglesAllowed(double marker_x,double marker_y,double *low_angle,double *high_angle) const =0;

  virtual bool inEnvironment(Sample *sample) const =0;

  virtual void genUniformSample(Sample *sample) const =0;

  virtual bool placeInEnviron(Sample *sample, double offset) const =0;

  virtual EnvironmentObject *getObject(int type) const =0;

  SensorInterp *sensorInterp;

protected:
private: // methods
private: // data
};

/*------------------------------------------------------------------
CLASS
  RoboCupFieldEnvironment

DESCRIPTION
  A environment for RoboCup
------------------------------------------------------------------*/
class RoboCupFieldEnvironment : public Environment {
public:
  RoboCupFieldEnvironment();

  virtual ~RoboCupFieldEnvironment();

  virtual bool inEnvironment(Sample *sample) const;

  virtual bool placeInEnviron(Sample *sample, double offset) const;

  virtual void getAnglesAllowed(double marker_x,double marker_y,double *low_angle,double *high_angle) const;

  virtual void genUniformSample(Sample *sample) const;

  virtual EnvironmentObject *getObject(int type) const;

protected:
private: // methods
private: // data
  EnvironmentObject **objects;
};

#endif
