Newer
Older
powermon_manager_sw / gui / gui_dfu_progress.cpp
@Razvan Turiac Razvan Turiac on 8 Jul 4 KB Initial import
/* Copyright (C) 2020 - 2024, Thornwave Labs Inc
 * Written by Razvan Turiac <razvan.turiac@thornwave.com>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated 
 * documentation files (the “Software”), to deal in the Software without restriction, including without limitation 
 * the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, 
 * and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
 * 
 * The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
 * Attribution shall be given to Thornwave Labs Inc. and shall be made visible to the final user. 
 * 
 * THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED 
 * TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 
 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/

#include <gui_dfu_progress.h>
#include <gui_device.h>



GuiDFUProgress::GuiDFUProgress(wxWindow *parent, const wxString &title, Powermon &powermon, const std::vector<uint8_t> &image): wxDialog(parent, wxID_ANY, title, wxDefaultPosition, wxDefaultSize),
																mPowermon(powermon), mFirmwareImage(image)
{
	const size_t BORDER_SIZE = FromDIP(6);

	//main window sizer
	wxBoxSizer* main_sizer = new wxBoxSizer(wxVERTICAL);
	SetSizer(main_sizer);

	main_sizer->AddSpacer(BORDER_SIZE);

	mStatusLabel = new wxStaticText(this, wxID_ANY, wxT("Starting ..."));
	main_sizer->Add(mStatusLabel, 0, wxALL | wxEXPAND, BORDER_SIZE);

	mProgressBar = new wxGauge(this, wxID_ANY, 100, wxDefaultPosition, FromDIP(wxSize(200, 20)), wxGA_HORIZONTAL);
	main_sizer->Add(mProgressBar, 0, wxLEFT | wxRIGHT | wxEXPAND, 2 * BORDER_SIZE);

	main_sizer->AddSpacer(10);

	wxBoxSizer* h_sizer = new wxBoxSizer(wxHORIZONTAL);
	main_sizer->Add(h_sizer, 1, wxALL | wxEXPAND, BORDER_SIZE);

	h_sizer->AddStretchSpacer(1);

	mCancelButton = new wxButton(this, wxID_CANCEL, wxT("Cancel"), wxDefaultPosition, FromDIP(wxSize(130, 40)));
	h_sizer->Add(mCancelButton, 0, wxALL | wxCENTER, BORDER_SIZE);

	h_sizer->AddStretchSpacer(1);
	
	main_sizer->SetSizeHints(this);
	Centre();
	SetFocus();

	Bind(wxEVT_COMMAND_BUTTON_CLICKED, &GuiDFUProgress::OnCancelButtonClicked, this, wxID_CANCEL);
	Bind(wxEVT_CLOSE_WINDOW, &GuiDFUProgress::OnClose, this, wxEVT_CLOSE_WINDOW);
	Bind(EVT_TYPE_GUI, &GuiDFUProgress::OnGuiEvent, this);

	mInProgress = true;
	mCancelUpdate = false;
	
	mPowermon.requestUpdateFirmware(mFirmwareImage.data(), mFirmwareImage.size(), 
	[this](uint32_t progress, uint32_t total)
	{
		if (mCancelUpdate)
			return false;

		GuiEvent* event = new GuiEvent([this, progress, total](const GuiEvent &event)	//this gets executed in the GUI thread
		{
			mStatusLabel->SetLabel(wxString::Format(wxT("%u of %u bytes"), progress, total));
			mStatusLabel->Refresh();

			mProgressBar->SetValue((progress * 100) / total);
			mProgressBar->Refresh();
		});
		wxQueueEvent(this, event);

		return true;
	},

	[this](uint16_t status)
	{
		mInProgress = false;

		GuiEvent* event = new GuiEvent([this, status](const GuiEvent &event)	//this gets executed in the GUI thread
		{
			if (status == Powermon::RSP_SUCCESS)
				EndModal(SUCCESS);
			else if (status == Powermon::RSP_CANCELLED)
				EndModal(CANCELLED);
			else
				EndModal(FAILED);
		});
		wxQueueEvent(this, event);
	});
}


GuiDFUProgress::~GuiDFUProgress()
{
}


void GuiDFUProgress::OnClose(wxCloseEvent &event)
{
	mCancelButton->Enable(false);

	if (mInProgress)
	{
		mCancelUpdate = true;
	}
	else
	{
		EndModal(ABORTED);
	}
}


void GuiDFUProgress::OnCancelButtonClicked(wxCommandEvent &event)
{
	mCancelButton->Enable(false);

	if (mInProgress)
	{
		mCancelUpdate = true;
	}
	else
	{
		EndModal(ABORTED);
	}
}


void GuiDFUProgress::OnGuiEvent(GuiEvent &event)
{
	event.process();
}