/**
 * \file pappsomspp/filers/filterresample.cpp
 * \date 28/04/2019
 * \author Olivier Langella
 * \brief collection of filters concerned by X selection
 */

/*******************************************************************************
 * Copyright (c) 2019 Olivier Langella <Olivier.Langella@u-psud.fr>.
 *
 * This file is part of the PAPPSOms++ library.
 *
 *     PAPPSOms++ 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.
 *
 *     PAPPSOms++ 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 PAPPSOms++.  If not, see <http://www.gnu.org/licenses/>.
 *
 ******************************************************************************/

#include "filterresample.h"
#include "../../massspectrum/massspectrum.h"
#include <QDebug>

using namespace pappso;

FilterResampleKeepSmaller::FilterResampleKeepSmaller(double x_value)
  : m_value(x_value)
{
}

FilterResampleKeepSmaller::FilterResampleKeepSmaller(
  const FilterResampleKeepSmaller &other)
  : FilterResampleKeepSmaller(other.m_value)
{
}


Trace &
FilterResampleKeepSmaller::filter(Trace &spectrum) const
{
  auto begin_it =
    findFirstEqualOrGreaterX(spectrum.begin(), spectrum.end(), m_value);
  spectrum.erase(begin_it, spectrum.end());
  return spectrum;
}

FilterResampleKeepGreater::FilterResampleKeepGreater(double x_value)
  : m_value(x_value)
{
}

FilterResampleKeepGreater::FilterResampleKeepGreater(
  const FilterResampleKeepGreater &other)
  : FilterResampleKeepGreater(other.m_value)
{
}


double
FilterResampleKeepGreater::getThresholdX() const
{
  return m_value;
}

FilterResampleKeepGreater &
FilterResampleKeepGreater::operator=(const FilterResampleKeepGreater &other)
{
  m_value = other.m_value;

  return *this;
}

Trace &
FilterResampleKeepGreater::filter(Trace &spectrum) const
{
  qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
           << " spectrum.size()=" << spectrum.size();
  auto last_it = findFirstGreaterX(spectrum.begin(), spectrum.end(), m_value);
  spectrum.erase(spectrum.begin(), last_it);
  qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
           << " spectrum.size()=" << spectrum.size();
  return spectrum;
}

FilterResampleRemoveXRange::FilterResampleRemoveXRange(double min_x,
                                                       double max_x)
  : m_minX(min_x), m_maxX(max_x)
{
}

FilterResampleRemoveXRange::FilterResampleRemoveXRange(
  const FilterResampleRemoveXRange &other)
  : FilterResampleRemoveXRange(other.m_minX, other.m_maxX)
{
}


FilterResampleRemoveXRange &
FilterResampleRemoveXRange::operator=(const FilterResampleRemoveXRange &other)
{
  m_minX = other.m_minX;
  m_maxX = other.m_maxX;

  return *this;
}


Trace &
FilterResampleRemoveXRange::filter(Trace &spectrum) const
{

  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //          << " m_min_x=" << m_min_x;
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //          << " m_max_x=" << m_max_x;
  auto begin_it =
    findFirstEqualOrGreaterX(spectrum.begin(), spectrum.end(), m_minX);
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //          << " begin_it->x=" << begin_it->x;
  auto end_it = findFirstGreaterX(begin_it, spectrum.end(), m_maxX);
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //         << " end_it->x=" << end_it->x;
  spectrum.erase(begin_it, end_it);

  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //          << " spectrum.size()=" << spectrum.size();
  return spectrum;
}


FilterResampleKeepXRange::FilterResampleKeepXRange(double min_x, double max_x)
  : m_minX(min_x), m_maxX(max_x)
{
}

FilterResampleKeepXRange::FilterResampleKeepXRange(
  const FilterResampleKeepXRange &other)
  : FilterResampleKeepXRange(other.m_minX, other.m_maxX)
{
}


FilterResampleKeepXRange &
FilterResampleKeepXRange::operator=(const FilterResampleKeepXRange &other)
{
  m_minX = other.m_minX;
  m_maxX = other.m_maxX;

  return *this;
}


Trace &
FilterResampleKeepXRange::filter(Trace &spectrum) const
{
  auto begin_it =
    findFirstEqualOrGreaterX(spectrum.begin(), spectrum.end(), m_minX);
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //<< " begin_it->x=" << begin_it->x;
  auto end_it = findFirstGreaterX(begin_it, spectrum.end(), m_maxX);
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //<< " end_it->x=" << end_it->x;

  spectrum.erase(end_it, spectrum.end());
  spectrum.erase(spectrum.begin(), begin_it);
  // qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__
  //<< " spectrum.size()=" << spectrum.size();

  return spectrum;
}


MassSpectrumFilterResampleRemoveMzRange::
  MassSpectrumFilterResampleRemoveMzRange(const MzRange &mz_range)
  : m_filterRange(mz_range.lower(), mz_range.upper())
{
}

MassSpectrumFilterResampleRemoveMzRange::
  MassSpectrumFilterResampleRemoveMzRange(
    const MassSpectrumFilterResampleRemoveMzRange &other)
  : m_filterRange(other.m_filterRange)
{
}

MassSpectrum &
MassSpectrumFilterResampleRemoveMzRange::filter(MassSpectrum &spectrum) const
{
  qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__;
  m_filterRange.filter(spectrum);
  qDebug() << __FILE__ << " " << __FUNCTION__ << " " << __LINE__;
  return spectrum;
}


MassSpectrumFilterResampleKeepMzRange::MassSpectrumFilterResampleKeepMzRange(
  const MzRange &mz_range)
  : m_filterRange(mz_range.lower(), mz_range.upper())
{
}

MassSpectrumFilterResampleKeepMzRange::MassSpectrumFilterResampleKeepMzRange(
  const MassSpectrumFilterResampleKeepMzRange &other)
  : m_filterRange(other.m_filterRange)
{
}

MassSpectrum &
MassSpectrumFilterResampleKeepMzRange::filter(MassSpectrum &spectrum) const
{
  m_filterRange.filter(spectrum);
  return spectrum;
}
