/***************************************************************************
**
**  This file is part of QGpCoreStat.
**
**  QGpCoreStat 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.
**
**  QGpCoreStat 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 Foobar.  If not, see <http://www.gnu.org/licenses/>
**
**  See http://www.geopsy.org for more information.
**
**  Created: 2008-12-17
**  Copyright: 2008-2019
**    Marc Wathelet
**    Marc Wathelet (LGIT, Grenoble, France)
**
***************************************************************************/

#ifndef HISTOGRAMREADER_H
#define HISTOGRAMREADER_H

#include <QGpCoreMath.h>

#include "QGpCoreStatDLLExport.h"
#include "GaussianMixtureParameters.h"

namespace QGpCoreStat {

  class QGPCORESTAT_EXPORT HistogramReader : public ArgumentStdinReader
  {
    TRANSLATIONS("HistogramReader")
  public:
    HistogramReader();
    ~HistogramReader();

    enum Action {Gui, Mean, Median, Mode, Grid, GaussMix, Plot, Max};
    enum MaxVariables {SlownessFrequency, AzimuthFrequency,
                       EllipticityFrequency, EllipticityAbsFrequency,
                       EllipticityDegFrequency, EllipticityDegInversedFrequency,
                       EllipticityRadFrequency, EllipticityRadInversedFrequency,
                       NoiseFrequency,
                       SlownessWaveNumber, SlownessWaveLength, SlownessPeriod, WaveNumberFrequency, WaveLengthFrequency,
                       FrequencyWaveNumber};

    bool setOptions(int& argc, char ** argv);
    bool setDefaultLimits();

    static void helpX(ApplicationHelp * h);
    static void helpY(ApplicationHelp * h);
    static void helpCurves(ApplicationHelp * h);

    const GaussianMixtureParameters& gaussianMixtureParameters() const {return _gaussMix;}
    const QString& headerLine() const {return _headerLine;}
    const QStringList& curveFileNames() const {return _curveFileNames;}
    const QString& curveFormatFileName() const {return _curveFormatFileName;}

    Histogram2D * histogram() const;
    Action action() const {return _action;}

    bool isNormalized() const {return _normalize;}

    bool ignoreStdin() const {return _ignoreStdin;}
    bool isEmpty() const {return _samples.isEmpty();}

    const QString& pattern() const {return _pattern;}
    void setPattern(const QString& p) {_pattern=p;}

    const SamplingParameters * xSampling() const {return _xSampling;}
    const QVector<double>& xValues() const {return _xValues;}
    bool xLogSampling() const {return _xLogSampling;}
    const SamplingParameters& ySampling() const {return _ySampling;}

    double relativePowerThreshold() const {return _relativePowerThreshold;}
    double noiseThreshold() const {return _noiseThreshold;}

    const QString& exportMaxFileName() const {return _exportMaxFileName;}
  protected:
    virtual bool parse(QTextStream& s);
    virtual bool loadSamples(QTextStream& s, const QString& lastLine);
    void add(const Histogram2D::Sample& s) {_samples.append(s);}
    bool setDefaultXLimits(const QVector<double>& x);
    bool setDefaultYLimits();

    struct ManualFlags {
      bool minimum:1;
      bool maximum:1;
      bool count:1;
      bool gridScaleType:1;
      bool viewScaleType:1;
      bool column:1;
    };

    union {
      struct {
        ManualFlags x;
        ManualFlags y;
        bool validColumn:1;
        bool xValuesAsIs:1;
      };
      int flags;
    } _manual;
  private:
    Histogram2D::Sample transformSample(const Histogram2D::Sample& s);
    void configureMaxFile(const QString& line);
    void configureCapMaxFile();

    Action _action;
    QString _exportMaxFileName;
    bool _ignoreStdin;
    bool _normalize;
    bool _xLogSampling;
    int _xColumn, _yColumn, _validColumn, _noiseColumn, _powerColumn;
    double _yFactor;
    double _relativePowerThreshold;
    double _noiseThreshold;
    MaxVariables _maxVariables;
    QString _pattern;

    QVector<double> _xValues;
    SamplingParameters * _xSampling;
    SamplingParameters _ySampling;
    QVector<Histogram2D::Sample> _samples;
    QString _xTitle, _xTitleInversedScale;
    QString _yTitle, _yTitleInversedScale;
    Scale::Type _xScaleType, _yScaleType;

    bool _ignoreValid;
    GaussianMixtureParameters _gaussMix;
    QStringList _curveFileNames;
    QString _curveFormatFileName;

    QString _headerLine;
  };

} // namespace QGpCoreStat

#endif // HISTOGRAMREADER_H
