/***********************************************************************************

    Copyright (C) 2007-2020 Ahmet Öztürk (aoz_2@yahoo.com)

    This file is part of Lifeograph.

    Lifeograph 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 3 of the License, or
    (at your option) any later version.

    Lifeograph 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.

    You should have received a copy of the GNU General Public License
    along with Lifeograph.  If not, see <http://www.gnu.org/licenses/>.

***********************************************************************************/


#ifndef LIFEOGRAPH_CHART_HEADER
#define LIFEOGRAPH_CHART_HEADER


#include <gtkmm/widget.h>

#include "../helpers.hpp"


namespace LIFEO
{

using namespace HELPERS;


class FiltererContainer; // forward declaration


class Chart
{
    public:
        // CONSTANTS
        static constexpr double     BORDER_CURVE   { 60.0 };
        static constexpr double     BORDER_LABEL   { 10.0 };
        static constexpr double     OFFSET_LABEL   {  5.0 };
        static constexpr double     HEIGHT_LABEL   { 10.0 };
        static constexpr double     HEIGHT_BAR     { 20.0 };
        static constexpr double     COEFF_OVERVIEW { 15.0 };
        static constexpr double     WIDTH_COL_MIN  { 50.0 };
        // CALCULATED CONSTANTS
        static constexpr double     label_y = OFFSET_LABEL + HEIGHT_LABEL;
        static constexpr double     s_x_min = BORDER_CURVE + BORDER_LABEL;
        static constexpr double     s_y_min = BORDER_CURVE;

                                    Chart();
        virtual                     ~Chart() { }

        void                        set_diary( Diary* diary )
        { m_p2diary = diary; m_data.set_diary( diary ); }
        Diary*                      get_diary()
        { return m_p2diary; }

        void                        calculate_points( double = 1.0 );

//        ChartData&                  get_chart_data()
//        { return m_data; }

        bool                        is_zoom_possible() const;
        void                        set_zoom( float );
        void                        resize( int, int );
        void                        scroll( int );

        virtual void                refresh() { }

    protected:
        void                        update_col_geom( bool = false );

        bool                        draw( const Cairo::RefPtr< Cairo::Context >& );

        date_t                      get_period_date( date_t );
        Ustring                     get_date_str( date_t ) const;
        FiltererContainer*          get_filterer_stack();

        // DATA
        ChartData                   m_data;

        // GEOMETRY
        int                         m_width{ -1 };
        int                         m_height{ -1 };
        unsigned int                m_span{ 0 };
        unsigned int                m_step_count{ 0 };
        unsigned int                m_step_start{ 0 };
        double                      m_zoom_level{ 1.0 };

        Value                       m_v_min{ 0.0 }, m_v_max{ 0.0 };
        double                      m_x_max{ 0.0 }, m_y_max{ 0.0 }, m_y_mid{ 0.0 };
        double                      m_amplitude{ 0.0 }, m_length{ 0.0 };
        double                      m_step_x{ 0.0 }, m_coefficient{ 0.0 };
        double                      m_ov_height{ 0.0 };
        double                      m_step_x_ov{ 0.0 }, m_ampli_ov{ 0.0 }, m_coeff_ov{ 0.0 };

        int                         m_hovered_step{ 0 };
        int                         m_warning_w{ 0 };

        Pango::FontDescription      m_font_main;
        Pango::FontDescription      m_font_bold;
        Pango::FontDescription      m_font_big;
        const static std::valarray< double >
                                    s_dash_pattern;

        // FLAGS
        bool                        m_flag_button_pressed{ false };
        bool                        m_flag_overview_hovered{ false };
        bool                        m_flag_widget_hovered{ false };

        Diary*                      m_p2diary{ nullptr };
};

} // end of namespace LIFEO

#endif
