/*****************************************************************************
*
* Copyright (c) 2000 - 2017, Lawrence Livermore National Security, LLC
* Produced at the Lawrence Livermore National Laboratory
* LLNL-CODE-442911
* All rights reserved.
*
* This file is  part of VisIt. For  details, see https://visit.llnl.gov/.  The
* full copyright notice is contained in the file COPYRIGHT located at the root
* of the VisIt distribution or at http://www.llnl.gov/visit/copyright.html.
*
* Redistribution  and  use  in  source  and  binary  forms,  with  or  without
* modification, are permitted provided that the following conditions are met:
*
*  - Redistributions of  source code must  retain the above  copyright notice,
*    this list of conditions and the disclaimer below.
*  - Redistributions in binary form must reproduce the above copyright notice,
*    this  list of  conditions  and  the  disclaimer (as noted below)  in  the
*    documentation and/or other materials provided with the distribution.
*  - Neither the name of  the LLNS/LLNL nor the names of  its contributors may
*    be used to endorse or promote products derived from this software without
*    specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT  HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR  IMPLIED WARRANTIES, INCLUDING,  BUT NOT  LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND  FITNESS FOR A PARTICULAR  PURPOSE
* ARE  DISCLAIMED. IN  NO EVENT  SHALL LAWRENCE  LIVERMORE NATIONAL  SECURITY,
* LLC, THE  U.S.  DEPARTMENT OF  ENERGY  OR  CONTRIBUTORS BE  LIABLE  FOR  ANY
* DIRECT,  INDIRECT,   INCIDENTAL,   SPECIAL,   EXEMPLARY,  OR   CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT  LIMITED TO, PROCUREMENT OF  SUBSTITUTE GOODS OR
* SERVICES; LOSS OF  USE, DATA, OR PROFITS; OR  BUSINESS INTERRUPTION) HOWEVER
* CAUSED  AND  ON  ANY  THEORY  OF  LIABILITY,  WHETHER  IN  CONTRACT,  STRICT
* LIABILITY, OR TORT  (INCLUDING NEGLIGENCE OR OTHERWISE)  ARISING IN ANY  WAY
* OUT OF THE  USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
* DAMAGE.
*
*****************************************************************************/

#include "QvisTopologyPlotWindow.h"

#include <TopologyAttributes.h>
#include <ViewerProxy.h>

#include <QLabel>
#include <QLayout>
#include <QLineEdit>
#include <QvisOpacitySlider.h>
#include <QvisLineStyleWidget.h>
#include <QvisLineWidthWidget.h>


// ****************************************************************************
// Method: QvisTopologyPlotWindow::QvisTopologyPlotWindow
//
// Purpose: 
//   Constructor
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

QvisTopologyPlotWindow::QvisTopologyPlotWindow(const int type,
                         TopologyAttributes *subj,
                         const QString &caption,
                         const QString &shortName,
                         QvisNotepadArea *notepad)
    : QvisPostableWindowObserver(subj, caption, shortName, notepad)
{
    plotType = type;
    atts = subj;
}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::~QvisTopologyPlotWindow
//
// Purpose: 
//   Destructor
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

QvisTopologyPlotWindow::~QvisTopologyPlotWindow()
{
}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::CreateWindowContents
//
// Purpose: 
//   Creates the widgets for the window.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::CreateWindowContents()
{
    QGridLayout *mainLayout = new QGridLayout(0);
    topLayout->addLayout(mainLayout);

    lineWidthLabel = new QLabel(tr("Line width"), central);
    mainLayout->addWidget(lineWidthLabel,0,0);
    lineWidth = new QvisLineWidthWidget(0, central);
    connect(lineWidth, SIGNAL(lineWidthChanged(int)),
            this, SLOT(lineWidthChanged(int)));
    mainLayout->addWidget(lineWidth, 0,1);

    lineStyleLabel = new QLabel(tr("Line style"), central);
    mainLayout->addWidget(lineStyleLabel,1,0);
    lineStyle = new QvisLineStyleWidget(0, central);
    connect(lineStyle, SIGNAL(lineStyleChanged(int)),
            this, SLOT(lineStyleChanged(int)));
    mainLayout->addWidget(lineStyle, 1,1);

    //writeSourceCreate unknown for att (variable multiColor)

    minOpacityLabel = new QLabel(tr("Opacity"), central);
    mainLayout->addWidget(minOpacityLabel,3,0);
    minOpacity = new QvisOpacitySlider(0,255,25,255, central, NULL);
    minOpacity->setTickInterval(64);
    minOpacity->setGradientColor(QColor(0, 0, 0));
    connect(minOpacity, SIGNAL(valueChanged(int, const void*)),
            this, SLOT(minOpacityChanged(int, const void*)));
    mainLayout->addWidget(minOpacity, 3,1);

    minPlateauOpacityLabel = new QLabel(tr("Opacity"), central);
    mainLayout->addWidget(minPlateauOpacityLabel,4,0);
    minPlateauOpacity = new QvisOpacitySlider(0,255,25,255, central, NULL);
    minPlateauOpacity->setTickInterval(64);
    minPlateauOpacity->setGradientColor(QColor(0, 0, 0));
    connect(minPlateauOpacity, SIGNAL(valueChanged(int, const void*)),
            this, SLOT(minPlateauOpacityChanged(int, const void*)));
    mainLayout->addWidget(minPlateauOpacity, 4,1);

    maxPlateauOpacityLabel = new QLabel(tr("Opacity"), central);
    mainLayout->addWidget(maxPlateauOpacityLabel,5,0);
    maxPlateauOpacity = new QvisOpacitySlider(0,255,25,255, central, NULL);
    maxPlateauOpacity->setTickInterval(64);
    maxPlateauOpacity->setGradientColor(QColor(0, 0, 0));
    connect(maxPlateauOpacity, SIGNAL(valueChanged(int, const void*)),
            this, SLOT(maxPlateauOpacityChanged(int, const void*)));
    mainLayout->addWidget(maxPlateauOpacity, 5,1);

    maxOpacityLabel = new QLabel(tr("Opacity"), central);
    mainLayout->addWidget(maxOpacityLabel,6,0);
    maxOpacity = new QvisOpacitySlider(0,255,25,255, central, NULL);
    maxOpacity->setTickInterval(64);
    maxOpacity->setGradientColor(QColor(0, 0, 0));
    connect(maxOpacity, SIGNAL(valueChanged(int, const void*)),
            this, SLOT(maxOpacityChanged(int, const void*)));
    mainLayout->addWidget(maxOpacity, 6,1);

    toleranceLabel = new QLabel(tr("tolerance"), central);
    mainLayout->addWidget(toleranceLabel,7,0);
    tolerance = new QLineEdit(central);
    connect(tolerance, SIGNAL(returnPressed()),
            this, SLOT(toleranceProcessText()));
    mainLayout->addWidget(tolerance, 7,1);

    hitpercentLabel = new QLabel(tr("hitpercent"), central);
    mainLayout->addWidget(hitpercentLabel,8,0);
    hitpercent = new QLineEdit(central);
    connect(hitpercent, SIGNAL(returnPressed()),
            this, SLOT(hitpercentProcessText()));
    mainLayout->addWidget(hitpercent, 8,1);

}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::UpdateWindow
//
// Purpose: 
//   Updates the widgets in the window when the subject changes.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::UpdateWindow(bool doAll)
{

    for(int i = 0; i < atts->NumAttributes(); ++i)
    {
        if(!doAll)
        {
            if(!atts->IsSelected(i))
            {
                continue;
            }
        }

        switch(i)
        {
          case TopologyAttributes::ID_lineWidth:
            lineWidth->blockSignals(true);
            lineWidth->SetLineWidth(atts->GetLineWidth());
            lineWidth->blockSignals(false);
            break;
          case TopologyAttributes::ID_lineStyle:
            lineStyle->blockSignals(true);
            lineStyle->SetLineStyle(atts->GetLineStyle());
            lineStyle->blockSignals(false);
            break;
          case TopologyAttributes::ID_multiColor:
        //writeSourceUpdate unknown for att (variable multiColor)
            break;
          case TopologyAttributes::ID_minOpacity:
            minOpacity->blockSignals(true);
            minOpacity->setValue(int(atts->GetMinOpacity()*255.));
            minOpacity->blockSignals(false);
            break;
          case TopologyAttributes::ID_minPlateauOpacity:
            minPlateauOpacity->blockSignals(true);
            minPlateauOpacity->setValue(int(atts->GetMinPlateauOpacity()*255.));
            minPlateauOpacity->blockSignals(false);
            break;
          case TopologyAttributes::ID_maxPlateauOpacity:
            maxPlateauOpacity->blockSignals(true);
            maxPlateauOpacity->setValue(int(atts->GetMaxPlateauOpacity()*255.));
            maxPlateauOpacity->blockSignals(false);
            break;
          case TopologyAttributes::ID_maxOpacity:
            maxOpacity->blockSignals(true);
            maxOpacity->setValue(int(atts->GetMaxOpacity()*255.));
            maxOpacity->blockSignals(false);
            break;
          case TopologyAttributes::ID_tolerance:
            tolerance->setText(DoubleToQString(atts->GetTolerance()));
            break;
          case TopologyAttributes::ID_hitpercent:
            hitpercent->setText(DoubleToQString(atts->GetHitpercent()));
            break;
        }
    }
}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::GetCurrentValues
//
// Purpose: 
//   Gets values from certain widgets and stores them in the subject.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::GetCurrentValues(int which_widget)
{
    bool doAll = (which_widget == -1);

    // Do tolerance
    if(which_widget == TopologyAttributes::ID_tolerance || doAll)
    {
        double val;
        if(LineEditGetDouble(tolerance, val))
            atts->SetTolerance(val);
        else
        {
            ResettingError(tr("tolerance"),
                DoubleToQString(atts->GetTolerance()));
            atts->SetTolerance(atts->GetTolerance());
        }
    }

    // Do hitpercent
    if(which_widget == TopologyAttributes::ID_hitpercent || doAll)
    {
        double val;
        if(LineEditGetDouble(hitpercent, val))
            atts->SetHitpercent(val);
        else
        {
            ResettingError(tr("hitpercent"),
                DoubleToQString(atts->GetHitpercent()));
            atts->SetHitpercent(atts->GetHitpercent());
        }
    }

}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::Apply
//
// Purpose: 
//   Called to apply changes in the subject.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::Apply(bool ignore)
{
    if(AutoUpdate() || ignore)
    {
        GetCurrentValues(-1);
        atts->Notify();

        GetViewerMethods()->SetPlotOptions(plotType);
    }
    else
        atts->Notify();
}


//
// Qt Slot functions
//


// ****************************************************************************
// Method: QvisTopologyPlotWindow::apply
//
// Purpose: 
//   Qt slot function called when apply button is clicked.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::apply()
{
    Apply(true);
}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::makeDefault
//
// Purpose: 
//   Qt slot function called when "Make default" button is clicked.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::makeDefault()
{
    GetCurrentValues(-1);
    atts->Notify();
    GetViewerMethods()->SetDefaultPlotOptions(plotType);
}


// ****************************************************************************
// Method: QvisTopologyPlotWindow::reset
//
// Purpose: 
//   Qt slot function called when reset button is clicked.
//
// Note:       Autogenerated by xml2window.
//
// Programmer: xml2window
// Creation:   omitted
//
// Modifications:
//   
// ****************************************************************************

void
QvisTopologyPlotWindow::reset()
{
    GetViewerMethods()->ResetPlotOptions(plotType);
}


void
QvisTopologyPlotWindow::lineWidthChanged(int style)
{
    atts->SetLineWidth(style);
    SetUpdate(false);
    Apply();
}


void
QvisTopologyPlotWindow::lineStyleChanged(int style)
{
    atts->SetLineStyle(style);
    SetUpdate(false);
    Apply();
}


//writeSourceCallback unknown for att (variable multiColor)


void
QvisTopologyPlotWindow::minOpacityChanged(int opacity, const void*)
{
    atts->SetMinOpacity((float)opacity/255.);
    SetUpdate(false);
    Apply();
}


void
QvisTopologyPlotWindow::minPlateauOpacityChanged(int opacity, const void*)
{
    atts->SetMinPlateauOpacity((float)opacity/255.);
    SetUpdate(false);
    Apply();
}


void
QvisTopologyPlotWindow::maxPlateauOpacityChanged(int opacity, const void*)
{
    atts->SetMaxPlateauOpacity((float)opacity/255.);
    SetUpdate(false);
    Apply();
}


void
QvisTopologyPlotWindow::maxOpacityChanged(int opacity, const void*)
{
    atts->SetMaxOpacity((float)opacity/255.);
    SetUpdate(false);
    Apply();
}


void
QvisTopologyPlotWindow::toleranceProcessText()
{
    GetCurrentValues(TopologyAttributes::ID_tolerance);
    Apply();
}


void
QvisTopologyPlotWindow::hitpercentProcessText()
{
    GetCurrentValues(TopologyAttributes::ID_hitpercent);
    Apply();
}


