#include "SettingDialog.h"

#include <string>
#include "printer.h"

//(*InternalHeaders(SettingDialog)

#include <wx/settings.h>

#include <wx/font.h>

#include <wx/intl.h>

#include <wx/string.h>

//*)

//(*IdInit(SettingDialog)

const long SettingDialog::ID_STATICTEXT1 = wxNewId();

const long SettingDialog::ID_STATICBOX1 = wxNewId();

const long SettingDialog::ID_STATICTEXT2 = wxNewId();

const long SettingDialog::ID_SPINCTRL1 = wxNewId();

const long SettingDialog::ID_STATICTEXT3 = wxNewId();

const long SettingDialog::ID_STATICTEXT4 = wxNewId();

const long SettingDialog::ID_SPINCTRL2 = wxNewId();

const long SettingDialog::ID_STATICTEXT5 = wxNewId();

const long SettingDialog::ID_STATICTEXT6 = wxNewId();

const long SettingDialog::ID_SPINCTRL3 = wxNewId();

const long SettingDialog::ID_STATICTEXT7 = wxNewId();

const long SettingDialog::ID_LISTBOX1 = wxNewId();

const long SettingDialog::ID_TEXTCTRL1 = wxNewId();

const long SettingDialog::ID_STATICTEXT8 = wxNewId();

const long SettingDialog::ID_BUTTON1 = wxNewId();

const long SettingDialog::ID_STATICLINE1 = wxNewId();

const long SettingDialog::ID_STATICTEXT9 = wxNewId();

const long SettingDialog::ID_STATICTEXT10 = wxNewId();

const long SettingDialog::ID_BUTTON2 = wxNewId();

const long SettingDialog::ID_STATICTEXT11 = wxNewId();

const long SettingDialog::ID_CHECKBOX1 = wxNewId();

const long SettingDialog::ID_BUTTON3 = wxNewId();

const long SettingDialog::ID_BUTTON4 = wxNewId();

const long SettingDialog::ID_CHOICE2 = wxNewId();

const long SettingDialog::ID_SPINCTRL4 = wxNewId();

const long SettingDialog::ID_STATICTEXT12 = wxNewId();

const long SettingDialog::ID_MESSAGEDIALOG1 = wxNewId();

//*)

BEGIN_EVENT_TABLE(SettingDialog,wxDialog)
	//(*EventTable(SettingDialog)
	//*)
END_EVENT_TABLE()

SettingDialog::SettingDialog(wxWindow* parent,wxWindowID id,PlottWareControlFrame *_p)
{
    p=_p;
	//(*Initialize(SettingDialog)

	Create(parent, id, wxEmptyString, wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE, _T("id"));

	SetClientSize(wxSize(389,432));

	SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW));

	StaticText1 = new wxStaticText(this, ID_STATICTEXT1, _("Settings"), wxPoint(0,8), wxDefaultSize, 0, _T("ID_STATICTEXT1"));

	wxFont StaticText1Font(14,wxFONTFAMILY_SWISS,wxFONTSTYLE_NORMAL,wxFONTWEIGHT_NORMAL,false,wxEmptyString,wxFONTENCODING_DEFAULT);

	StaticText1->SetFont(StaticText1Font);

	StaticBox1 = new wxStaticBox(this, ID_STATICBOX1, _("Printer"), wxPoint(8,48), wxSize(376,280), 0, _T("ID_STATICBOX1"));

	StaticText2 = new wxStaticText(this, ID_STATICTEXT2, _("Length:"), wxPoint(32,72), wxDefaultSize, 0, _T("ID_STATICTEXT2"));

	LengthSpinner = new wxSpinCtrl(this, ID_SPINCTRL1, _T("0"), wxPoint(104,64), wxDefaultSize, 0, -1, 100000, 0, _T("ID_SPINCTRL1"));

	LengthSpinner->SetValue(_T("0"));

	LengthSpinner->SetToolTip(_("Length of printing area (-1 for infinite)"));

	StaticText3 = new wxStaticText(this, ID_STATICTEXT3, _("mm"), wxPoint(248,72), wxDefaultSize, 0, _T("ID_STATICTEXT3"));

	StaticText4 = new wxStaticText(this, ID_STATICTEXT4, _("Width:"), wxPoint(32,96), wxDefaultSize, 0, _T("ID_STATICTEXT4"));

	WidthSpinner = new wxSpinCtrl(this, ID_SPINCTRL2, _T("0"), wxPoint(104,88), wxDefaultSize, 0, -1, 100000, 0, _T("ID_SPINCTRL2"));

	WidthSpinner->SetValue(_T("0"));

	WidthSpinner->SetToolTip(_("Width of printing area (-1 for infinite)"));

	StaticText5 = new wxStaticText(this, ID_STATICTEXT5, _("mm"), wxPoint(248,96), wxDefaultSize, 0, _T("ID_STATICTEXT5"));

	StaticText6 = new wxStaticText(this, ID_STATICTEXT6, _("Pen count:"), wxPoint(32,120), wxDefaultSize, 0, _T("ID_STATICTEXT6"));

	PencountSpinner = new wxSpinCtrl(this, ID_SPINCTRL3, _T("0"), wxPoint(104,112), wxDefaultSize, 0, 0, 100, 0, _T("ID_SPINCTRL3"));

	PencountSpinner->SetValue(_T("0"));

	PencountSpinner->SetToolTip(_("Number of available drawing pens"));

	StaticText7 = new wxStaticText(this, ID_STATICTEXT7, _("Pens:"), wxPoint(32,144), wxDefaultSize, 0, _T("ID_STATICTEXT7"));

	PensListBox = new wxListBox(this, ID_LISTBOX1, wxPoint(104,136), wxSize(120,80), 0, 0, 0, wxDefaultValidator, _T("ID_LISTBOX1"));

	PensListBox->SetToolTip(_("List of pens"));

	PenColorText = new wxTextCtrl(this, ID_TEXTCTRL1, wxEmptyString, wxPoint(264,152), wxDefaultSize, 0, wxDefaultValidator, _T("ID_TEXTCTRL1"));

	PenColorText->SetToolTip(_("Color of pen"));

	StaticText8 = new wxStaticText(this, ID_STATICTEXT8, _("Color:"), wxPoint(232,160), wxDefaultSize, 0, _T("ID_STATICTEXT8"));

	PenColorSetButton = new wxButton(this, ID_BUTTON1, _("Set"), wxPoint(232,176), wxSize(136,23), 0, wxDefaultValidator, _T("ID_BUTTON1"));

	PenColorSetButton->SetToolTip(_("Set color"));

	StaticLine1 = new wxStaticLine(this, ID_STATICLINE1, wxPoint(24,232), wxSize(344,3), wxLI_HORIZONTAL, _T("ID_STATICLINE1"));

	StaticText9 = new wxStaticText(this, ID_STATICTEXT9, _("Serial port:"), wxPoint(32,248), wxDefaultSize, 0, _T("ID_STATICTEXT9"));

	StaticText10 = new wxStaticText(this, ID_STATICTEXT10, _("Baud rate:"), wxPoint(32,272), wxDefaultSize, 0, _T("ID_STATICTEXT10"));

	PrinterAutoDetectButton = new wxButton(this, ID_BUTTON2, _("Auto detect"), wxPoint(32,296), wxDefaultSize, 0, wxDefaultValidator, _T("ID_BUTTON2"));

	PrinterAutoDetectButton->SetToolTip(_("Auto detect printer settings (only works if serial port and baud rate is set)"));

	StaticText11 = new wxStaticText(this, ID_STATICTEXT11, _("Debug mode:"), wxPoint(16,352), wxDefaultSize, 0, _T("ID_STATICTEXT11"));

	DebugModeCheck = new wxCheckBox(this, ID_CHECKBOX1, _("Enable"), wxPoint(96,352), wxDefaultSize, 0, wxDefaultValidator, _T("ID_CHECKBOX1"));

	DebugModeCheck->SetValue(false);

	DebugModeCheck->SetToolTip(_("Enable debug mode (show stages of image processing)"));

	SaveSettingsButton = new wxButton(this, ID_BUTTON3, _("Save"), wxPoint(176,384), wxDefaultSize, 0, wxDefaultValidator, _T("ID_BUTTON3"));

	SaveSettingsButton->SetToolTip(_("Save settings"));

	CancelSettingsButton = new wxButton(this, ID_BUTTON4, _("Cancel"), wxPoint(272,384), wxDefaultSize, 0, wxDefaultValidator, _T("ID_BUTTON4"));

	CancelSettingsButton->SetToolTip(_("Dismiss changes"));

	BaudRateChoice = new wxChoice(this, ID_CHOICE2, wxPoint(104,264), wxSize(120,21), 0, 0, 0, wxDefaultValidator, _T("ID_CHOICE2"));

	BaudRateChoice->SetSelection( BaudRateChoice->Append(_("300")) );

	BaudRateChoice->Append(_("600"));

	BaudRateChoice->Append(_("1200"));

	BaudRateChoice->Append(_("2400"));

	BaudRateChoice->Append(_("4800"));

	BaudRateChoice->Append(_("9600"));

	BaudRateChoice->Append(_("14400"));

	BaudRateChoice->Append(_("19200"));

	BaudRateChoice->Append(_("28800"));

	BaudRateChoice->Append(_("38400"));

	BaudRateChoice->Append(_("57600"));

	BaudRateChoice->Append(_("115200"));

	BaudRateChoice->SetToolTip(_("Baud rate of device"));

	SerialPortSpinner = new wxSpinCtrl(this, ID_SPINCTRL4, _T("0"), wxPoint(136,240), wxSize(88,21), 0, 0, 100, 0, _T("ID_SPINCTRL4"));

	SerialPortSpinner->SetValue(_T("0"));

	SerialPortSpinner->SetToolTip(_("Serial port on which the plotter is connected"));

	StaticText12 = new wxStaticText(this, ID_STATICTEXT12, _("COM"), wxPoint(104,248), wxDefaultSize, 0, _T("ID_STATICTEXT12"));

	MessageDialog1 = new wxMessageDialog(this, wxEmptyString, _("Message"), wxOK|wxCANCEL, wxDefaultPosition);


	Connect(ID_SPINCTRL3,wxEVT_COMMAND_SPINCTRL_UPDATED,(wxObjectEventFunction)&SettingDialog::OnPencountSpinnerChange);

	Connect(ID_LISTBOX1,wxEVT_COMMAND_LISTBOX_SELECTED,(wxObjectEventFunction)&SettingDialog::OnPensListBoxSelect);

	Connect(ID_BUTTON1,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&SettingDialog::OnPenColorSetButtonClick);

	Connect(ID_BUTTON2,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&SettingDialog::OnPrinterAutoDetectButtonClick);

	Connect(ID_BUTTON3,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&SettingDialog::OnSaveSettingsButtonClick);

	Connect(ID_BUTTON4,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&SettingDialog::OnCancelSettingsButtonClick);

	//*)

	//Load default values
    LengthSpinner->SetValue(p->getSettings()->getPrinter()->getLength());
    WidthSpinner->SetValue(p->getSettings()->getPrinter()->getWidth());
    PencountSpinner->SetValue(p->getSettings()->getPrinter()->getPenCount());
    s_pens=p->getSettings()->getPrinter()->getPens();
    for(int i=0; i<s_pens.size(); i++){
        PensListBox->Append(s_pens[i]);
    }
    SerialPortSpinner->SetValue(p->getSettings()->getPrinter()->getPortInt());
    BaudRateChoice->SetSelection(BaudRateChoice->FindString(std::to_string(p->getSettings()->getPrinter()->getBaudRate()))!=wxNOT_FOUND?BaudRateChoice->FindString(std::to_string(p->getSettings()->getPrinter()->getBaudRate())):0);
    DebugModeCheck->SetValue(p->getSettings()->isDebug());
}

SettingDialog::~SettingDialog()
{
	//(*Destroy(SettingDialog)
	//*)
}

void SettingDialog::OnCancelSettingsButtonClick(wxCommandEvent& event)
{
    this->Destroy();
}

void SettingDialog::OnPencountSpinnerChange(wxSpinEvent& event)
{
    PensListBox->Clear();
    s_pens.clear();
    for(int i=0; i<PencountSpinner->GetValue(); i++){
        PensListBox->Append("<<"+std::to_string(i)+">>");
        s_pens[i]="<<"+std::to_string(i)+">>";
    }
    PensListBox->SetSelection(0);
}

void SettingDialog::OnPenColorSetButtonClick(wxCommandEvent& event)
{
    int sel=PensListBox->GetSelection();
    std::string val=std::string(PenColorText->GetValue().mb_str());
    PensListBox->SetString(sel, val);
    s_pens[sel]=val;
}

void SettingDialog::OnPensListBoxSelect(wxCommandEvent& event)
{
    PenColorText->SetValue(PensListBox->GetString(PensListBox->GetSelection()));
}

void SettingDialog::OnSaveSettingsButtonClick(wxCommandEvent& event)
{
    Printer printer=Printer(LengthSpinner->GetValue(), WidthSpinner->GetValue(), PencountSpinner->GetValue(), s_pens, SerialPortSpinner->GetValue(), std::stol(std::string(BaudRateChoice->GetString(BaudRateChoice->GetSelection()).mb_str())));
    p->getSettings()->setSettings(printer, DebugModeCheck->GetValue());
    this->Destroy();
}

void SettingDialog::OnPrinterAutoDetectButtonClick(wxCommandEvent& event)
{
    p->getSettings()->getPrinter()->setComParameters(SerialPortSpinner->GetValue(), std::stol(std::string(BaudRateChoice->GetString(BaudRateChoice->GetSelection()).mb_str())));
    if(!p->getSettings()->getPrinter()->connect()){
        wxMessageDialog(this, _("Can not connect to printer. Please recheck the settings!"), _("Error"), wxCENTER|wxOK|wxICON_ERROR).ShowModal();
        return;
    }
    if(!p->getSettings()->getPrinter()->autoDetect()){
        wxMessageDialog(this, _("Can not parse the output of auto-detect command (M703). Is your software compatible?"), _("Warning"), wxCENTER|wxOK|wxICON_WARNING).ShowModal();
        return;
    }
    wxMessageDialog(this, _("Settings successfully detected!"), _("Info"), wxCENTER|wxOK|wxICON_INFORMATION).ShowModal();
}
