mirror of https://github.com/stella-emu/stella.git
140 lines
4.7 KiB
C++
140 lines
4.7 KiB
C++
//============================================================================
|
|
//
|
|
// SSSS tt lll lll
|
|
// SS SS tt ll ll
|
|
// SS tttttt eeee ll ll aaaa
|
|
// SSSS tt ee ee ll ll aa
|
|
// SS tt eeeeee ll ll aaaaa -- "An Atari 2600 VCS Emulator"
|
|
// SS SS tt ee ll ll aa aa
|
|
// SSSS ttt eeeee llll llll aaaaa
|
|
//
|
|
// Copyright (c) 1995-2020 by Bradford W. Mott, Stephen Anthony
|
|
// and the Stella Team
|
|
//
|
|
// See the file "License.txt" for information on usage and redistribution of
|
|
// this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
|
//============================================================================
|
|
|
|
#include "bspf.hxx"
|
|
#include "OSystem.hxx"
|
|
#include "FrameBuffer.hxx"
|
|
#include "EventHandler.hxx"
|
|
#include "TimerManager.hxx"
|
|
#include "Widget.hxx"
|
|
#include "Dialog.hxx"
|
|
#include "Font.hxx"
|
|
#include "DialogContainer.hxx"
|
|
#include "ProgressDialog.hxx"
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
ProgressDialog::ProgressDialog(GuiObject* boss, const GUI::Font& font,
|
|
const string& message)
|
|
: Dialog(boss->instance(), boss->parent()),
|
|
myFont{font}
|
|
{
|
|
const int lineHeight = Dialog::lineHeight(),
|
|
fontHeight = Dialog::fontHeight(),
|
|
buttonHeight = Dialog::buttonHeight(),
|
|
buttonWidth = Dialog::buttonWidth("Cancel"),
|
|
VBORDER = Dialog::vBorder(),
|
|
HBORDER = Dialog::hBorder(),
|
|
VGAP = Dialog::vGap();
|
|
const int lwidth = font.getStringWidth(message);
|
|
int xpos, ypos;
|
|
WidgetArray wid;
|
|
|
|
// Calculate real dimensions
|
|
_w = HBORDER * 2 + std::max(lwidth, buttonWidth);
|
|
_h = VBORDER * 2 + lineHeight * 2 + buttonHeight + VGAP * 6;
|
|
|
|
xpos = HBORDER; ypos = VBORDER;
|
|
myMessage = new StaticTextWidget(this, font, xpos, ypos, lwidth, fontHeight,
|
|
message, TextAlign::Center);
|
|
myMessage->setTextColor(kTextColorEm);
|
|
|
|
ypos += lineHeight + VGAP * 2;
|
|
mySlider = new SliderWidget(this, font, xpos, ypos, lwidth, lineHeight,
|
|
"", 0, 0);
|
|
mySlider->setMinValue(1);
|
|
mySlider->setMaxValue(100);
|
|
|
|
ypos += lineHeight + VGAP * 4;
|
|
ButtonWidget* b = new ButtonWidget(this, font, (_w - buttonWidth) / 2, ypos,
|
|
buttonWidth, buttonHeight, "Cancel",
|
|
Event::UICancel);
|
|
wid.push_back(b);
|
|
addCancelWidget(b);
|
|
addToFocusList(wid);
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::setMessage(const string& message)
|
|
{
|
|
const int buttonWidth = Dialog::buttonWidth("Cancel"),
|
|
HBORDER = Dialog::hBorder();
|
|
const int lwidth = myFont.getStringWidth(message);
|
|
// Recalculate real dimensions
|
|
_w = HBORDER * 2 + std::max(lwidth, buttonWidth);
|
|
|
|
myMessage->setWidth(lwidth);
|
|
myMessage->setLabel(message);
|
|
mySlider->setWidth(lwidth);
|
|
|
|
_cancelWidget->setPosX((_w - buttonWidth) / 2);
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::setRange(int start, int finish, int step)
|
|
{
|
|
myStart = start;
|
|
myFinish = finish;
|
|
myStep = int((step / 100.0) * (myFinish - myStart + 1));
|
|
|
|
mySlider->setMinValue(myStart + myStep);
|
|
mySlider->setMaxValue(myFinish);
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::resetProgress()
|
|
{
|
|
myProgress = myStepProgress = 0;
|
|
mySlider->setValue(0);
|
|
myIsCancelled = false;
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::setProgress(int progress)
|
|
{
|
|
// Only increase the progress bar if we have arrived at a new step
|
|
if(progress - myStepProgress >= myStep)
|
|
{
|
|
myStepProgress = progress;
|
|
mySlider->setValue(progress % (myFinish - myStart + 1));
|
|
|
|
// Since this dialog is usually called in a tight loop that doesn't
|
|
// yield, we need to manually:
|
|
// - tell the framebuffer that a redraw is necessary
|
|
// - poll the events
|
|
// This isn't really an ideal solution, since all redrawing and
|
|
// event handling is suspended until the dialog is closed
|
|
instance().frameBuffer().update();
|
|
instance().eventHandler().poll(TimerManager::getTicks());
|
|
}
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::incProgress()
|
|
{
|
|
setProgress(++myProgress);
|
|
}
|
|
|
|
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
|
void ProgressDialog::handleCommand(CommandSender* sender, int cmd,
|
|
int data, int id)
|
|
{
|
|
if(cmd == Event::UICancel)
|
|
myIsCancelled = true;
|
|
else
|
|
Dialog::handleCommand(sender, cmd, data, 0);
|
|
}
|