/*
 *  TnNavSimRouteData.h
 *  OpenGL Map Engine
 *
 *  Created by Thant on 4/24/2013
 *  Copyright 2013 TeleNav Inc. All rights reserved.
 *
 */

#ifndef TN_NAV_SIM_ROUTE_DATA_INCLUDED
#define TN_NAV_SIM_ROUTE_DATA_INCLUDED

#include <foundation/Math/Vec.hpp>
#include <foundation/Math/Point.hpp>
#include <foundation/Math/LatLonHeight.hpp>

#include <RenderEngine/ITnMapRouteData.h>

class TnNavSimulator;

class TnNavSimRouteData : public ITnMapRouteData 
{
public:

    /*  To allow us to efficiently specify a location along the route
     *  to start the prefetch, we will use the segment boundaries
     *  (i.e. maneuver points).
     */

    typedef std::vector<uint32_t> SegmentIndices;
    typedef Tn::Foundation::shared_ptr<SegmentIndices> SegmentIndicesPtr;
    typedef Tn::Foundation::shared_ptr<std::vector<uint32_t> > UIVectorPtr;

    struct Data {
        Data(Tn::math::RoutePtr const & route,
             SegmentIndicesPtr const & segments,
             UIVectorPtr const & route_point_indexes,
             UIVectorPtr const & edge_indexes,
             UIVectorPtr const & segment_indexes) :
            route(route), 
            segments(segments),
            route_point_indexes(route_point_indexes),
            edge_indexes(edge_indexes),
            segment_indexes(segment_indexes)
            {}

        Tn::math::RoutePtr route;
        SegmentIndicesPtr segments;
        
        /* To record the index of point. */
        
        UIVectorPtr route_point_indexes;
        UIVectorPtr edge_indexes;
        UIVectorPtr segment_indexes;
    };

    /*  Unlike the actual route proxy, the navigation simulator doesn't
     *  have to preserve the order of the routes. So we just use a
     *  map. 
     */

    typedef std::map<std::string, Data>  RouteMap;
    typedef std::pair<std::string, Data>  RouteMapEntry;

    TnNavSimRouteData(ITnMapRouteData::ptr const &,
                      Tn::Foundation::shared_ptr<TnNavSimulator> const &);

    virtual void NewRoute(std::string const & name, 
                          std::string const & routeStyle, 
                          TnMapArrowParams const & arrowParams);
    
    virtual void NewSegment();
    virtual void NewSegment(TnMapArrowParams const & arrowParams);
    virtual void NewEdge();
    virtual void NewEdge(std::string const & style);
    virtual void AddPoint(double degreesLatitude, 
                          double degreesLongitude,
                          double metersHeight);

    virtual void SetStyle(std::string const & style);

    virtual void SetStart(double degreesLatitude, 
                          double degreesLongitude,
                          double metersHeight);

    virtual void SetFinish(double degreesLatitude, 
                           double degreesLongitude,
                           double metersHeight);

    virtual void SetRequestResult(eTnMapRequestResult result);
    
private:

    /* The actual info to pass back to the navigation simulator. */

    RouteMap m_routes;

    /* Current route and indices. */

    Tn::math::RoutePtr m_route;
    SegmentIndicesPtr m_segmentIndices;

    /* To send the route data back to the navigation simulator. */

    Tn::Foundation::shared_ptr<TnNavSimulator> m_navsim;

    /* To pass the data on to the actual route proxy. */

    ITnMapRouteData::ptr m_data;
    
    /* To record the index of point. */
    
    uint32_t m_curr_point_index;
    uint32_t m_curr_edge_index;
    UIVectorPtr m_route_point_indexes;
    UIVectorPtr m_edge_indexes;
    UIVectorPtr m_segment_indexes;

};

#endif

