#include "Panel_boundary_conditions.h"

#include "Model.h"
#include "Model_kit.h"
#include "Density.h"
#include "Mach_eps.h"

#include <math.h>

namespace MM
{

Panel_boundary_conditions::
Panel_boundary_conditions ()
:
    Panel ("Boundary", "right")
{
    setupUi (this);

    //for (int i=0;  i<toolBox->count();  ++i)
    //    if (toolBox->itemText (i) == "Implicit water" ||
    //        toolBox->itemText (i) == "Drop" ||
    //        toolBox->itemText (i) == "Two spheres"
    //        )
    //        toolBox->setItemEnabled (i, false);
    toolBox_2->hide ();

    doubleSpinBox_Box_y->hide ();
    doubleSpinBox_Box_z->hide ();

    connect(doubleSpinBox_Dielectric_permittivity, SIGNAL(valueChanged(double)),
        this, SLOT(set_dielectric_permittivity(double)));

    connect(doubleSpinBox_Cutoff_radius, SIGNAL(valueChanged(double)),
        this, SLOT(set_cutoff(double)));

    connect(doubleSpinBox_Box_x, SIGNAL(editingFinished()),
        this, SLOT(set_box_x ()));

    connect(doubleSpinBox_Density, SIGNAL(editingFinished()),
        this, SLOT(set_density ()));

    connect(toolBox, SIGNAL(currentChanged(int)),
        this, SLOT(set_boundary_conditions (int)));

    renew ();
}

void Panel_boundary_conditions::
renew ()
{
    renew (Model_event::Structure_changed);
}

void Panel_boundary_conditions::
renew_current_model (Model &)
{
    renew (Model_event::Structure_changed);
}

void Panel_boundary_conditions::
renew (Model_event::Hint)
{
    Model_kit  &           kit = model().kit();
    Common_interactions &  interactions = kit.interaction().common();

    doubleSpinBox_Dielectric_permittivity-> setValue (interactions.epsilon ());
    doubleSpinBox_Cutoff_radius->           setValue (interactions.cutoff  ());

    //set_boundary_conditions (toolBox->currentIndex());
    for (int index=0;  index<toolBox->count();  ++index)
    {
        if (kit.boundary_conditions ().type_name() == "Box" &&
            toolBox->itemText (index) == "Periodic box"
            ||
            kit.boundary_conditions ().type_name() == "Vacuum" &&
            toolBox->itemText (index) == "Vacuum")
        {
            toolBox->setCurrentIndex (index);
            break;
        }
    }

    doubleSpinBox_Cutoff_radius->setEnabled (true);

    if (kit.boundary_conditions ().type_name() == "Box")
    {
        double L = kit.boundary_conditions().box().a_mod_rectangle();//fix
        if (doubleSpinBox_Cutoff_radius->value() > L/2.)
        {
            doubleSpinBox_Cutoff_radius->blockSignals (true);
            doubleSpinBox_Cutoff_radius->setValue (L/2.);
            //fix doubleSpinBox_Cutoff_radius->setEnabled (false);
            doubleSpinBox_Cutoff_radius->blockSignals (false);
        }
            
        //interactions.set_cutoff (L/2.);

        doubleSpinBox_Box_x->setValue (L);
        doubleSpinBox_Density->setValue (Density(model()).value());
    }
}

void Panel_boundary_conditions::
set_dielectric_permittivity (double v)
{
    model().kit().interaction().common().set_epsilon (v);
}

void Panel_boundary_conditions::
set_cutoff (double v)   
{
    model().kit().interaction().common().set_cutoff (v);
    renew ();
}

void Panel_boundary_conditions::
set_box_x ()
{
    double v = doubleSpinBox_Box_x->value();
//    model().kit().boundary_conditions ().box().set (v, v, v, 90., 90., 90.);
    model().kit().boundary_conditions ().box().set (v, v, v);
    
    doubleSpinBox_Cutoff_radius->blockSignals (true);
    doubleSpinBox_Cutoff_radius->setValue 
        (model().kit().interaction().common().cutoff ());
    doubleSpinBox_Cutoff_radius->blockSignals (false);
    
    renew ();
}

void Panel_boundary_conditions::
set_density ()
{
    double d = doubleSpinBox_Density->value();

    if (d < d_mach_eps_3)
        return;

    Box & box = model().kit().boundary_conditions().box();

    //fix   remove when Lx != Ly != Lz will be
    box.set (box.a_mod(), box.a_mod(), box.a_mod(), 90, 90, 90);

    Density current (model());
    double factor = pow (current.value() / d, 1./3.); 

    box.scale_a (factor);
    box.scale_b (factor);
    box.scale_c (factor);
    
    renew ();
}

void Panel_boundary_conditions::
set_boundary_conditions (int index)
{
    if (toolBox->itemText (index) == "Periodic box")
        model().kit().boundary_conditions ().set_type ("Box");
    else
        model().kit().boundary_conditions ().set_type ("Vacuum");
    renew ();
}

}//MM
