NOISSUE tabs -> spaces
This commit is contained in:
		@@ -2,26 +2,26 @@
 | 
			
		||||
 | 
			
		||||
// Origin: Qt
 | 
			
		||||
QStringList viewItemTextLayout(QTextLayout &textLayout, int lineWidth, qreal &height,
 | 
			
		||||
							   qreal &widthUsed)
 | 
			
		||||
                               qreal &widthUsed)
 | 
			
		||||
{
 | 
			
		||||
	QStringList lines;
 | 
			
		||||
	height = 0;
 | 
			
		||||
	widthUsed = 0;
 | 
			
		||||
	textLayout.beginLayout();
 | 
			
		||||
	QString str = textLayout.text();
 | 
			
		||||
	while (true)
 | 
			
		||||
	{
 | 
			
		||||
		QTextLine line = textLayout.createLine();
 | 
			
		||||
		if (!line.isValid())
 | 
			
		||||
			break;
 | 
			
		||||
		if (line.textLength() == 0)
 | 
			
		||||
			break;
 | 
			
		||||
		line.setLineWidth(lineWidth);
 | 
			
		||||
		line.setPosition(QPointF(0, height));
 | 
			
		||||
		height += line.height();
 | 
			
		||||
		lines.append(str.mid(line.textStart(), line.textLength()));
 | 
			
		||||
		widthUsed = qMax(widthUsed, line.naturalTextWidth());
 | 
			
		||||
	}
 | 
			
		||||
	textLayout.endLayout();
 | 
			
		||||
	return lines;
 | 
			
		||||
    QStringList lines;
 | 
			
		||||
    height = 0;
 | 
			
		||||
    widthUsed = 0;
 | 
			
		||||
    textLayout.beginLayout();
 | 
			
		||||
    QString str = textLayout.text();
 | 
			
		||||
    while (true)
 | 
			
		||||
    {
 | 
			
		||||
        QTextLine line = textLayout.createLine();
 | 
			
		||||
        if (!line.isValid())
 | 
			
		||||
            break;
 | 
			
		||||
        if (line.textLength() == 0)
 | 
			
		||||
            break;
 | 
			
		||||
        line.setLineWidth(lineWidth);
 | 
			
		||||
        line.setPosition(QPointF(0, height));
 | 
			
		||||
        height += line.height();
 | 
			
		||||
        lines.append(str.mid(line.textStart(), line.textLength()));
 | 
			
		||||
        widthUsed = qMax(widthUsed, line.naturalTextWidth());
 | 
			
		||||
    }
 | 
			
		||||
    textLayout.endLayout();
 | 
			
		||||
    return lines;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -3,4 +3,4 @@
 | 
			
		||||
#include <QTextLayout>
 | 
			
		||||
 | 
			
		||||
QStringList viewItemTextLayout(QTextLayout &textLayout, int lineWidth, qreal &height,
 | 
			
		||||
						qreal &widthUsed);
 | 
			
		||||
                        qreal &widthUsed);
 | 
			
		||||
@@ -6,43 +6,43 @@ CustomCommands::~CustomCommands()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
CustomCommands::CustomCommands(QWidget* parent):
 | 
			
		||||
	QWidget(parent),
 | 
			
		||||
	ui(new Ui::CustomCommands)
 | 
			
		||||
    QWidget(parent),
 | 
			
		||||
    ui(new Ui::CustomCommands)
 | 
			
		||||
{
 | 
			
		||||
	ui->setupUi(this);
 | 
			
		||||
    ui->setupUi(this);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void CustomCommands::initialize(bool checkable, bool checked, const QString& prelaunch, const QString& wrapper, const QString& postexit)
 | 
			
		||||
{
 | 
			
		||||
	ui->customCommandsGroupBox->setCheckable(checkable);
 | 
			
		||||
	if(checkable)
 | 
			
		||||
	{
 | 
			
		||||
		ui->customCommandsGroupBox->setChecked(checked);
 | 
			
		||||
	}
 | 
			
		||||
	ui->preLaunchCmdTextBox->setText(prelaunch);
 | 
			
		||||
	ui->wrapperCmdTextBox->setText(wrapper);
 | 
			
		||||
	ui->postExitCmdTextBox->setText(postexit);
 | 
			
		||||
    ui->customCommandsGroupBox->setCheckable(checkable);
 | 
			
		||||
    if(checkable)
 | 
			
		||||
    {
 | 
			
		||||
        ui->customCommandsGroupBox->setChecked(checked);
 | 
			
		||||
    }
 | 
			
		||||
    ui->preLaunchCmdTextBox->setText(prelaunch);
 | 
			
		||||
    ui->wrapperCmdTextBox->setText(wrapper);
 | 
			
		||||
    ui->postExitCmdTextBox->setText(postexit);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
bool CustomCommands::checked() const
 | 
			
		||||
{
 | 
			
		||||
	if(!ui->customCommandsGroupBox->isCheckable())
 | 
			
		||||
		return true;
 | 
			
		||||
	return ui->customCommandsGroupBox->isChecked();
 | 
			
		||||
    if(!ui->customCommandsGroupBox->isCheckable())
 | 
			
		||||
        return true;
 | 
			
		||||
    return ui->customCommandsGroupBox->isChecked();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QString CustomCommands::prelaunchCommand() const
 | 
			
		||||
{
 | 
			
		||||
	return ui->preLaunchCmdTextBox->text();
 | 
			
		||||
    return ui->preLaunchCmdTextBox->text();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QString CustomCommands::wrapperCommand() const
 | 
			
		||||
{
 | 
			
		||||
	return ui->wrapperCmdTextBox->text();
 | 
			
		||||
    return ui->wrapperCmdTextBox->text();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QString CustomCommands::postexitCommand() const
 | 
			
		||||
{
 | 
			
		||||
	return ui->postExitCmdTextBox->text();
 | 
			
		||||
    return ui->postExitCmdTextBox->text();
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -24,20 +24,20 @@ class CustomCommands;
 | 
			
		||||
 | 
			
		||||
class CustomCommands : public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	explicit CustomCommands(QWidget *parent = 0);
 | 
			
		||||
	~CustomCommands();
 | 
			
		||||
	void initialize(bool checkable, bool checked, const QString & prelaunch, const QString & wrapper, const QString & postexit);
 | 
			
		||||
    explicit CustomCommands(QWidget *parent = 0);
 | 
			
		||||
    ~CustomCommands();
 | 
			
		||||
    void initialize(bool checkable, bool checked, const QString & prelaunch, const QString & wrapper, const QString & postexit);
 | 
			
		||||
 | 
			
		||||
	bool checked() const;
 | 
			
		||||
	QString prelaunchCommand() const;
 | 
			
		||||
	QString wrapperCommand() const;
 | 
			
		||||
	QString postexitCommand() const;
 | 
			
		||||
    bool checked() const;
 | 
			
		||||
    QString prelaunchCommand() const;
 | 
			
		||||
    QString wrapperCommand() const;
 | 
			
		||||
    QString postexitCommand() const;
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	Ui::CustomCommands *ui;
 | 
			
		||||
    Ui::CustomCommands *ui;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -3,23 +3,23 @@
 | 
			
		||||
 | 
			
		||||
FocusLineEdit::FocusLineEdit(QWidget *parent) : QLineEdit(parent)
 | 
			
		||||
{
 | 
			
		||||
	_selectOnMousePress = false;
 | 
			
		||||
    _selectOnMousePress = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void FocusLineEdit::focusInEvent(QFocusEvent *e)
 | 
			
		||||
{
 | 
			
		||||
	QLineEdit::focusInEvent(e);
 | 
			
		||||
	selectAll();
 | 
			
		||||
	_selectOnMousePress = true;
 | 
			
		||||
    QLineEdit::focusInEvent(e);
 | 
			
		||||
    selectAll();
 | 
			
		||||
    _selectOnMousePress = true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void FocusLineEdit::mousePressEvent(QMouseEvent *me)
 | 
			
		||||
{
 | 
			
		||||
	QLineEdit::mousePressEvent(me);
 | 
			
		||||
	if (_selectOnMousePress)
 | 
			
		||||
	{
 | 
			
		||||
		selectAll();
 | 
			
		||||
		_selectOnMousePress = false;
 | 
			
		||||
	}
 | 
			
		||||
	qDebug() << selectedText();
 | 
			
		||||
    QLineEdit::mousePressEvent(me);
 | 
			
		||||
    if (_selectOnMousePress)
 | 
			
		||||
    {
 | 
			
		||||
        selectAll();
 | 
			
		||||
        _selectOnMousePress = false;
 | 
			
		||||
    }
 | 
			
		||||
    qDebug() << selectedText();
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -2,16 +2,16 @@
 | 
			
		||||
 | 
			
		||||
class FocusLineEdit : public QLineEdit
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	FocusLineEdit(QWidget *parent);
 | 
			
		||||
	virtual ~FocusLineEdit()
 | 
			
		||||
	{
 | 
			
		||||
	}
 | 
			
		||||
    FocusLineEdit(QWidget *parent);
 | 
			
		||||
    virtual ~FocusLineEdit()
 | 
			
		||||
    {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	void focusInEvent(QFocusEvent *e);
 | 
			
		||||
	void mousePressEvent(QMouseEvent *me);
 | 
			
		||||
    void focusInEvent(QFocusEvent *e);
 | 
			
		||||
    void mousePressEvent(QMouseEvent *me);
 | 
			
		||||
 | 
			
		||||
	bool _selectOnMousePress;
 | 
			
		||||
    bool _selectOnMousePress;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -7,37 +7,37 @@
 | 
			
		||||
#include <QRect>
 | 
			
		||||
 | 
			
		||||
IconLabel::IconLabel(QWidget *parent, QIcon icon, QSize size)
 | 
			
		||||
	: QWidget(parent), m_size(size), m_icon(icon)
 | 
			
		||||
    : QWidget(parent), m_size(size), m_icon(icon)
 | 
			
		||||
{
 | 
			
		||||
	setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Minimum);
 | 
			
		||||
    setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Minimum);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QSize IconLabel::sizeHint() const
 | 
			
		||||
{
 | 
			
		||||
	return m_size;
 | 
			
		||||
    return m_size;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void IconLabel::setIcon(QIcon icon)
 | 
			
		||||
{
 | 
			
		||||
	m_icon = icon;
 | 
			
		||||
	update();
 | 
			
		||||
    m_icon = icon;
 | 
			
		||||
    update();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void IconLabel::paintEvent(QPaintEvent *)
 | 
			
		||||
{
 | 
			
		||||
	QPainter p(this);
 | 
			
		||||
	QRect rect = contentsRect();
 | 
			
		||||
	int width = rect.width();
 | 
			
		||||
	int height = rect.height();
 | 
			
		||||
	if(width < height)
 | 
			
		||||
	{
 | 
			
		||||
		rect.setHeight(width);
 | 
			
		||||
		rect.translate(0, (height - width) / 2);
 | 
			
		||||
	}
 | 
			
		||||
	else if (width > height)
 | 
			
		||||
	{
 | 
			
		||||
		rect.setWidth(height);
 | 
			
		||||
		rect.translate((width - height) / 2, 0);
 | 
			
		||||
	}
 | 
			
		||||
	m_icon.paint(&p, rect);
 | 
			
		||||
    QPainter p(this);
 | 
			
		||||
    QRect rect = contentsRect();
 | 
			
		||||
    int width = rect.width();
 | 
			
		||||
    int height = rect.height();
 | 
			
		||||
    if(width < height)
 | 
			
		||||
    {
 | 
			
		||||
        rect.setHeight(width);
 | 
			
		||||
        rect.translate(0, (height - width) / 2);
 | 
			
		||||
    }
 | 
			
		||||
    else if (width > height)
 | 
			
		||||
    {
 | 
			
		||||
        rect.setWidth(height);
 | 
			
		||||
        rect.translate((width - height) / 2, 0);
 | 
			
		||||
    }
 | 
			
		||||
    m_icon.paint(&p, rect);
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -9,18 +9,18 @@ class QStyleOption;
 | 
			
		||||
 */
 | 
			
		||||
class IconLabel : public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	/// Create a line separator. orientation is the orientation of the line.
 | 
			
		||||
	explicit IconLabel(QWidget *parent, QIcon icon, QSize size);
 | 
			
		||||
    /// Create a line separator. orientation is the orientation of the line.
 | 
			
		||||
    explicit IconLabel(QWidget *parent, QIcon icon, QSize size);
 | 
			
		||||
 | 
			
		||||
	virtual QSize sizeHint() const;
 | 
			
		||||
	virtual void paintEvent(QPaintEvent *);
 | 
			
		||||
    virtual QSize sizeHint() const;
 | 
			
		||||
    virtual void paintEvent(QPaintEvent *);
 | 
			
		||||
 | 
			
		||||
	void setIcon(QIcon icon);
 | 
			
		||||
    void setIcon(QIcon icon);
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	QSize m_size;
 | 
			
		||||
	QIcon m_icon;
 | 
			
		||||
    QSize m_size;
 | 
			
		||||
    QIcon m_icon;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -19,410 +19,410 @@
 | 
			
		||||
 | 
			
		||||
JavaSettingsWidget::JavaSettingsWidget(QWidget* parent) : QWidget(parent)
 | 
			
		||||
{
 | 
			
		||||
	m_availableMemory = Sys::getSystemRam() / Sys::megabyte;
 | 
			
		||||
    m_availableMemory = Sys::getSystemRam() / Sys::megabyte;
 | 
			
		||||
 | 
			
		||||
	goodIcon = MMC->getThemedIcon("status-good");
 | 
			
		||||
	yellowIcon = MMC->getThemedIcon("status-yellow");
 | 
			
		||||
	badIcon = MMC->getThemedIcon("status-bad");
 | 
			
		||||
	setupUi();
 | 
			
		||||
    goodIcon = MMC->getThemedIcon("status-good");
 | 
			
		||||
    yellowIcon = MMC->getThemedIcon("status-yellow");
 | 
			
		||||
    badIcon = MMC->getThemedIcon("status-bad");
 | 
			
		||||
    setupUi();
 | 
			
		||||
 | 
			
		||||
	connect(m_minMemSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
	connect(m_maxMemSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
	connect(m_permGenSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
	connect(m_versionWidget, &VersionSelectWidget::selectedVersionChanged, this, &JavaSettingsWidget::javaVersionSelected);
 | 
			
		||||
	connect(m_javaBrowseBtn, &QPushButton::clicked, this, &JavaSettingsWidget::on_javaBrowseBtn_clicked);
 | 
			
		||||
	connect(m_javaPathTextBox, &QLineEdit::textEdited, this, &JavaSettingsWidget::javaPathEdited);
 | 
			
		||||
	connect(m_javaStatusBtn, &QToolButton::clicked, this, &JavaSettingsWidget::on_javaStatusBtn_clicked);
 | 
			
		||||
    connect(m_minMemSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
    connect(m_maxMemSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
    connect(m_permGenSpinBox, SIGNAL(valueChanged(int)), this, SLOT(memoryValueChanged(int)));
 | 
			
		||||
    connect(m_versionWidget, &VersionSelectWidget::selectedVersionChanged, this, &JavaSettingsWidget::javaVersionSelected);
 | 
			
		||||
    connect(m_javaBrowseBtn, &QPushButton::clicked, this, &JavaSettingsWidget::on_javaBrowseBtn_clicked);
 | 
			
		||||
    connect(m_javaPathTextBox, &QLineEdit::textEdited, this, &JavaSettingsWidget::javaPathEdited);
 | 
			
		||||
    connect(m_javaStatusBtn, &QToolButton::clicked, this, &JavaSettingsWidget::on_javaStatusBtn_clicked);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::setupUi()
 | 
			
		||||
{
 | 
			
		||||
	setObjectName(QStringLiteral("javaSettingsWidget"));
 | 
			
		||||
	m_verticalLayout = new QVBoxLayout(this);
 | 
			
		||||
	m_verticalLayout->setObjectName(QStringLiteral("verticalLayout"));
 | 
			
		||||
    setObjectName(QStringLiteral("javaSettingsWidget"));
 | 
			
		||||
    m_verticalLayout = new QVBoxLayout(this);
 | 
			
		||||
    m_verticalLayout->setObjectName(QStringLiteral("verticalLayout"));
 | 
			
		||||
 | 
			
		||||
	m_versionWidget = new VersionSelectWidget(this);
 | 
			
		||||
	m_verticalLayout->addWidget(m_versionWidget);
 | 
			
		||||
    m_versionWidget = new VersionSelectWidget(this);
 | 
			
		||||
    m_verticalLayout->addWidget(m_versionWidget);
 | 
			
		||||
 | 
			
		||||
	m_horizontalLayout = new QHBoxLayout();
 | 
			
		||||
	m_horizontalLayout->setObjectName(QStringLiteral("horizontalLayout"));
 | 
			
		||||
	m_javaPathTextBox = new QLineEdit(this);
 | 
			
		||||
	m_javaPathTextBox->setObjectName(QStringLiteral("javaPathTextBox"));
 | 
			
		||||
    m_horizontalLayout = new QHBoxLayout();
 | 
			
		||||
    m_horizontalLayout->setObjectName(QStringLiteral("horizontalLayout"));
 | 
			
		||||
    m_javaPathTextBox = new QLineEdit(this);
 | 
			
		||||
    m_javaPathTextBox->setObjectName(QStringLiteral("javaPathTextBox"));
 | 
			
		||||
 | 
			
		||||
	m_horizontalLayout->addWidget(m_javaPathTextBox);
 | 
			
		||||
    m_horizontalLayout->addWidget(m_javaPathTextBox);
 | 
			
		||||
 | 
			
		||||
	m_javaBrowseBtn = new QPushButton(this);
 | 
			
		||||
	m_javaBrowseBtn->setObjectName(QStringLiteral("javaBrowseBtn"));
 | 
			
		||||
    m_javaBrowseBtn = new QPushButton(this);
 | 
			
		||||
    m_javaBrowseBtn->setObjectName(QStringLiteral("javaBrowseBtn"));
 | 
			
		||||
 | 
			
		||||
	m_horizontalLayout->addWidget(m_javaBrowseBtn);
 | 
			
		||||
    m_horizontalLayout->addWidget(m_javaBrowseBtn);
 | 
			
		||||
 | 
			
		||||
	m_javaStatusBtn = new QToolButton(this);
 | 
			
		||||
	m_javaStatusBtn->setIcon(yellowIcon);
 | 
			
		||||
	m_horizontalLayout->addWidget(m_javaStatusBtn);
 | 
			
		||||
    m_javaStatusBtn = new QToolButton(this);
 | 
			
		||||
    m_javaStatusBtn->setIcon(yellowIcon);
 | 
			
		||||
    m_horizontalLayout->addWidget(m_javaStatusBtn);
 | 
			
		||||
 | 
			
		||||
	m_verticalLayout->addLayout(m_horizontalLayout);
 | 
			
		||||
    m_verticalLayout->addLayout(m_horizontalLayout);
 | 
			
		||||
 | 
			
		||||
	m_memoryGroupBox = new QGroupBox(this);
 | 
			
		||||
	m_memoryGroupBox->setObjectName(QStringLiteral("memoryGroupBox"));
 | 
			
		||||
	m_gridLayout_2 = new QGridLayout(m_memoryGroupBox);
 | 
			
		||||
	m_gridLayout_2->setObjectName(QStringLiteral("gridLayout_2"));
 | 
			
		||||
    m_memoryGroupBox = new QGroupBox(this);
 | 
			
		||||
    m_memoryGroupBox->setObjectName(QStringLiteral("memoryGroupBox"));
 | 
			
		||||
    m_gridLayout_2 = new QGridLayout(m_memoryGroupBox);
 | 
			
		||||
    m_gridLayout_2->setObjectName(QStringLiteral("gridLayout_2"));
 | 
			
		||||
 | 
			
		||||
	m_labelMinMem = new QLabel(m_memoryGroupBox);
 | 
			
		||||
	m_labelMinMem->setObjectName(QStringLiteral("labelMinMem"));
 | 
			
		||||
	m_gridLayout_2->addWidget(m_labelMinMem, 0, 0, 1, 1);
 | 
			
		||||
    m_labelMinMem = new QLabel(m_memoryGroupBox);
 | 
			
		||||
    m_labelMinMem->setObjectName(QStringLiteral("labelMinMem"));
 | 
			
		||||
    m_gridLayout_2->addWidget(m_labelMinMem, 0, 0, 1, 1);
 | 
			
		||||
 | 
			
		||||
	m_minMemSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
	m_minMemSpinBox->setObjectName(QStringLiteral("minMemSpinBox"));
 | 
			
		||||
	m_minMemSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
	m_minMemSpinBox->setMinimum(128);
 | 
			
		||||
	m_minMemSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
	m_minMemSpinBox->setSingleStep(128);
 | 
			
		||||
	m_labelMinMem->setBuddy(m_minMemSpinBox);
 | 
			
		||||
	m_gridLayout_2->addWidget(m_minMemSpinBox, 0, 1, 1, 1);
 | 
			
		||||
    m_minMemSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
    m_minMemSpinBox->setObjectName(QStringLiteral("minMemSpinBox"));
 | 
			
		||||
    m_minMemSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
    m_minMemSpinBox->setMinimum(128);
 | 
			
		||||
    m_minMemSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
    m_minMemSpinBox->setSingleStep(128);
 | 
			
		||||
    m_labelMinMem->setBuddy(m_minMemSpinBox);
 | 
			
		||||
    m_gridLayout_2->addWidget(m_minMemSpinBox, 0, 1, 1, 1);
 | 
			
		||||
 | 
			
		||||
	m_labelMaxMem = new QLabel(m_memoryGroupBox);
 | 
			
		||||
	m_labelMaxMem->setObjectName(QStringLiteral("labelMaxMem"));
 | 
			
		||||
	m_gridLayout_2->addWidget(m_labelMaxMem, 1, 0, 1, 1);
 | 
			
		||||
    m_labelMaxMem = new QLabel(m_memoryGroupBox);
 | 
			
		||||
    m_labelMaxMem->setObjectName(QStringLiteral("labelMaxMem"));
 | 
			
		||||
    m_gridLayout_2->addWidget(m_labelMaxMem, 1, 0, 1, 1);
 | 
			
		||||
 | 
			
		||||
	m_maxMemSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
	m_maxMemSpinBox->setObjectName(QStringLiteral("maxMemSpinBox"));
 | 
			
		||||
	m_maxMemSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
	m_maxMemSpinBox->setMinimum(128);
 | 
			
		||||
	m_maxMemSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
	m_maxMemSpinBox->setSingleStep(128);
 | 
			
		||||
	m_labelMaxMem->setBuddy(m_maxMemSpinBox);
 | 
			
		||||
	m_gridLayout_2->addWidget(m_maxMemSpinBox, 1, 1, 1, 1);
 | 
			
		||||
    m_maxMemSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
    m_maxMemSpinBox->setObjectName(QStringLiteral("maxMemSpinBox"));
 | 
			
		||||
    m_maxMemSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
    m_maxMemSpinBox->setMinimum(128);
 | 
			
		||||
    m_maxMemSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
    m_maxMemSpinBox->setSingleStep(128);
 | 
			
		||||
    m_labelMaxMem->setBuddy(m_maxMemSpinBox);
 | 
			
		||||
    m_gridLayout_2->addWidget(m_maxMemSpinBox, 1, 1, 1, 1);
 | 
			
		||||
 | 
			
		||||
	m_labelPermGen = new QLabel(m_memoryGroupBox);
 | 
			
		||||
	m_labelPermGen->setObjectName(QStringLiteral("labelPermGen"));
 | 
			
		||||
	m_labelPermGen->setText(QStringLiteral("PermGen:"));
 | 
			
		||||
	m_gridLayout_2->addWidget(m_labelPermGen, 2, 0, 1, 1);
 | 
			
		||||
	m_labelPermGen->setVisible(false);
 | 
			
		||||
    m_labelPermGen = new QLabel(m_memoryGroupBox);
 | 
			
		||||
    m_labelPermGen->setObjectName(QStringLiteral("labelPermGen"));
 | 
			
		||||
    m_labelPermGen->setText(QStringLiteral("PermGen:"));
 | 
			
		||||
    m_gridLayout_2->addWidget(m_labelPermGen, 2, 0, 1, 1);
 | 
			
		||||
    m_labelPermGen->setVisible(false);
 | 
			
		||||
 | 
			
		||||
	m_permGenSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
	m_permGenSpinBox->setObjectName(QStringLiteral("permGenSpinBox"));
 | 
			
		||||
	m_permGenSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
	m_permGenSpinBox->setMinimum(64);
 | 
			
		||||
	m_permGenSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
	m_permGenSpinBox->setSingleStep(8);
 | 
			
		||||
	m_gridLayout_2->addWidget(m_permGenSpinBox, 2, 1, 1, 1);
 | 
			
		||||
	m_permGenSpinBox->setVisible(false);
 | 
			
		||||
    m_permGenSpinBox = new QSpinBox(m_memoryGroupBox);
 | 
			
		||||
    m_permGenSpinBox->setObjectName(QStringLiteral("permGenSpinBox"));
 | 
			
		||||
    m_permGenSpinBox->setSuffix(QStringLiteral(" MB"));
 | 
			
		||||
    m_permGenSpinBox->setMinimum(64);
 | 
			
		||||
    m_permGenSpinBox->setMaximum(m_availableMemory);
 | 
			
		||||
    m_permGenSpinBox->setSingleStep(8);
 | 
			
		||||
    m_gridLayout_2->addWidget(m_permGenSpinBox, 2, 1, 1, 1);
 | 
			
		||||
    m_permGenSpinBox->setVisible(false);
 | 
			
		||||
 | 
			
		||||
	m_verticalLayout->addWidget(m_memoryGroupBox);
 | 
			
		||||
    m_verticalLayout->addWidget(m_memoryGroupBox);
 | 
			
		||||
 | 
			
		||||
	retranslate();
 | 
			
		||||
    retranslate();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::initialize()
 | 
			
		||||
{
 | 
			
		||||
	m_versionWidget->initialize(MMC->javalist().get());
 | 
			
		||||
	m_versionWidget->setResizeOn(2);
 | 
			
		||||
	auto s = MMC->settings();
 | 
			
		||||
	// Memory
 | 
			
		||||
	observedMinMemory = s->get("MinMemAlloc").toInt();
 | 
			
		||||
	observedMaxMemory = s->get("MaxMemAlloc").toInt();
 | 
			
		||||
	observedPermGenMemory = s->get("PermGen").toInt();
 | 
			
		||||
	m_minMemSpinBox->setValue(observedMinMemory);
 | 
			
		||||
	m_maxMemSpinBox->setValue(observedMaxMemory);
 | 
			
		||||
	m_permGenSpinBox->setValue(observedPermGenMemory);
 | 
			
		||||
    m_versionWidget->initialize(MMC->javalist().get());
 | 
			
		||||
    m_versionWidget->setResizeOn(2);
 | 
			
		||||
    auto s = MMC->settings();
 | 
			
		||||
    // Memory
 | 
			
		||||
    observedMinMemory = s->get("MinMemAlloc").toInt();
 | 
			
		||||
    observedMaxMemory = s->get("MaxMemAlloc").toInt();
 | 
			
		||||
    observedPermGenMemory = s->get("PermGen").toInt();
 | 
			
		||||
    m_minMemSpinBox->setValue(observedMinMemory);
 | 
			
		||||
    m_maxMemSpinBox->setValue(observedMaxMemory);
 | 
			
		||||
    m_permGenSpinBox->setValue(observedPermGenMemory);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::refresh()
 | 
			
		||||
{
 | 
			
		||||
	m_versionWidget->loadList();
 | 
			
		||||
    m_versionWidget->loadList();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
JavaSettingsWidget::ValidationStatus JavaSettingsWidget::validate()
 | 
			
		||||
{
 | 
			
		||||
	switch(javaStatus)
 | 
			
		||||
	{
 | 
			
		||||
		default:
 | 
			
		||||
		case JavaStatus::NotSet:
 | 
			
		||||
		case JavaStatus::DoesNotExist:
 | 
			
		||||
		case JavaStatus::DoesNotStart:
 | 
			
		||||
		case JavaStatus::ReturnedInvalidData:
 | 
			
		||||
		{
 | 
			
		||||
			int button = CustomMessageBox::selectable(
 | 
			
		||||
				this,
 | 
			
		||||
				tr("No Java version selected"),
 | 
			
		||||
				tr("You didn't select a Java version or selected something that doesn't work.\n"
 | 
			
		||||
					"MultiMC will not be able to start Minecraft.\n"
 | 
			
		||||
					"Do you wish to proceed without any Java?"
 | 
			
		||||
					"\n\n"
 | 
			
		||||
					"You can change the Java version in the settings later.\n"
 | 
			
		||||
				),
 | 
			
		||||
				QMessageBox::Warning,
 | 
			
		||||
				QMessageBox::Yes | QMessageBox::No,
 | 
			
		||||
				QMessageBox::NoButton
 | 
			
		||||
			)->exec();
 | 
			
		||||
			if(button == QMessageBox::No)
 | 
			
		||||
			{
 | 
			
		||||
				return ValidationStatus::Bad;
 | 
			
		||||
			}
 | 
			
		||||
			return ValidationStatus::JavaBad;
 | 
			
		||||
		}
 | 
			
		||||
		break;
 | 
			
		||||
		case JavaStatus::Pending:
 | 
			
		||||
		{
 | 
			
		||||
			return ValidationStatus::Bad;
 | 
			
		||||
		}
 | 
			
		||||
		case JavaStatus::Good:
 | 
			
		||||
		{
 | 
			
		||||
			return ValidationStatus::AllOK;
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
    switch(javaStatus)
 | 
			
		||||
    {
 | 
			
		||||
        default:
 | 
			
		||||
        case JavaStatus::NotSet:
 | 
			
		||||
        case JavaStatus::DoesNotExist:
 | 
			
		||||
        case JavaStatus::DoesNotStart:
 | 
			
		||||
        case JavaStatus::ReturnedInvalidData:
 | 
			
		||||
        {
 | 
			
		||||
            int button = CustomMessageBox::selectable(
 | 
			
		||||
                this,
 | 
			
		||||
                tr("No Java version selected"),
 | 
			
		||||
                tr("You didn't select a Java version or selected something that doesn't work.\n"
 | 
			
		||||
                    "MultiMC will not be able to start Minecraft.\n"
 | 
			
		||||
                    "Do you wish to proceed without any Java?"
 | 
			
		||||
                    "\n\n"
 | 
			
		||||
                    "You can change the Java version in the settings later.\n"
 | 
			
		||||
                ),
 | 
			
		||||
                QMessageBox::Warning,
 | 
			
		||||
                QMessageBox::Yes | QMessageBox::No,
 | 
			
		||||
                QMessageBox::NoButton
 | 
			
		||||
            )->exec();
 | 
			
		||||
            if(button == QMessageBox::No)
 | 
			
		||||
            {
 | 
			
		||||
                return ValidationStatus::Bad;
 | 
			
		||||
            }
 | 
			
		||||
            return ValidationStatus::JavaBad;
 | 
			
		||||
        }
 | 
			
		||||
        break;
 | 
			
		||||
        case JavaStatus::Pending:
 | 
			
		||||
        {
 | 
			
		||||
            return ValidationStatus::Bad;
 | 
			
		||||
        }
 | 
			
		||||
        case JavaStatus::Good:
 | 
			
		||||
        {
 | 
			
		||||
            return ValidationStatus::AllOK;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QString JavaSettingsWidget::javaPath() const
 | 
			
		||||
{
 | 
			
		||||
	return m_javaPathTextBox->text();
 | 
			
		||||
    return m_javaPathTextBox->text();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int JavaSettingsWidget::maxHeapSize() const
 | 
			
		||||
{
 | 
			
		||||
	return m_maxMemSpinBox->value();
 | 
			
		||||
    return m_maxMemSpinBox->value();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int JavaSettingsWidget::minHeapSize() const
 | 
			
		||||
{
 | 
			
		||||
	return m_minMemSpinBox->value();
 | 
			
		||||
    return m_minMemSpinBox->value();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool JavaSettingsWidget::permGenEnabled() const
 | 
			
		||||
{
 | 
			
		||||
	return m_permGenSpinBox->isVisible();
 | 
			
		||||
    return m_permGenSpinBox->isVisible();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int JavaSettingsWidget::permGenSize() const
 | 
			
		||||
{
 | 
			
		||||
	return m_permGenSpinBox->value();
 | 
			
		||||
    return m_permGenSpinBox->value();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::memoryValueChanged(int)
 | 
			
		||||
{
 | 
			
		||||
	bool actuallyChanged = false;
 | 
			
		||||
	int min = m_minMemSpinBox->value();
 | 
			
		||||
	int max = m_maxMemSpinBox->value();
 | 
			
		||||
	int permgen = m_permGenSpinBox->value();
 | 
			
		||||
	QObject *obj = sender();
 | 
			
		||||
	if (obj == m_minMemSpinBox && min != observedMinMemory)
 | 
			
		||||
	{
 | 
			
		||||
		observedMinMemory = min;
 | 
			
		||||
		actuallyChanged = true;
 | 
			
		||||
		if (min > max)
 | 
			
		||||
		{
 | 
			
		||||
			observedMaxMemory = min;
 | 
			
		||||
			m_maxMemSpinBox->setValue(min);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	else if (obj == m_maxMemSpinBox && max != observedMaxMemory)
 | 
			
		||||
	{
 | 
			
		||||
		observedMaxMemory = max;
 | 
			
		||||
		actuallyChanged = true;
 | 
			
		||||
		if (min > max)
 | 
			
		||||
		{
 | 
			
		||||
			observedMinMemory = max;
 | 
			
		||||
			m_minMemSpinBox->setValue(max);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	else if (obj == m_permGenSpinBox && permgen != observedPermGenMemory)
 | 
			
		||||
	{
 | 
			
		||||
		observedPermGenMemory = permgen;
 | 
			
		||||
		actuallyChanged = true;
 | 
			
		||||
	}
 | 
			
		||||
	if(actuallyChanged)
 | 
			
		||||
	{
 | 
			
		||||
		checkJavaPathOnEdit(m_javaPathTextBox->text());
 | 
			
		||||
	}
 | 
			
		||||
    bool actuallyChanged = false;
 | 
			
		||||
    int min = m_minMemSpinBox->value();
 | 
			
		||||
    int max = m_maxMemSpinBox->value();
 | 
			
		||||
    int permgen = m_permGenSpinBox->value();
 | 
			
		||||
    QObject *obj = sender();
 | 
			
		||||
    if (obj == m_minMemSpinBox && min != observedMinMemory)
 | 
			
		||||
    {
 | 
			
		||||
        observedMinMemory = min;
 | 
			
		||||
        actuallyChanged = true;
 | 
			
		||||
        if (min > max)
 | 
			
		||||
        {
 | 
			
		||||
            observedMaxMemory = min;
 | 
			
		||||
            m_maxMemSpinBox->setValue(min);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    else if (obj == m_maxMemSpinBox && max != observedMaxMemory)
 | 
			
		||||
    {
 | 
			
		||||
        observedMaxMemory = max;
 | 
			
		||||
        actuallyChanged = true;
 | 
			
		||||
        if (min > max)
 | 
			
		||||
        {
 | 
			
		||||
            observedMinMemory = max;
 | 
			
		||||
            m_minMemSpinBox->setValue(max);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    else if (obj == m_permGenSpinBox && permgen != observedPermGenMemory)
 | 
			
		||||
    {
 | 
			
		||||
        observedPermGenMemory = permgen;
 | 
			
		||||
        actuallyChanged = true;
 | 
			
		||||
    }
 | 
			
		||||
    if(actuallyChanged)
 | 
			
		||||
    {
 | 
			
		||||
        checkJavaPathOnEdit(m_javaPathTextBox->text());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::javaVersionSelected(BaseVersionPtr version)
 | 
			
		||||
{
 | 
			
		||||
	auto java = std::dynamic_pointer_cast<JavaInstall>(version);
 | 
			
		||||
	if(!java)
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	auto visible = java->id.requiresPermGen();
 | 
			
		||||
	m_labelPermGen->setVisible(visible);
 | 
			
		||||
	m_permGenSpinBox->setVisible(visible);
 | 
			
		||||
	m_javaPathTextBox->setText(java->path);
 | 
			
		||||
	checkJavaPath(java->path);
 | 
			
		||||
    auto java = std::dynamic_pointer_cast<JavaInstall>(version);
 | 
			
		||||
    if(!java)
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    auto visible = java->id.requiresPermGen();
 | 
			
		||||
    m_labelPermGen->setVisible(visible);
 | 
			
		||||
    m_permGenSpinBox->setVisible(visible);
 | 
			
		||||
    m_javaPathTextBox->setText(java->path);
 | 
			
		||||
    checkJavaPath(java->path);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::on_javaBrowseBtn_clicked()
 | 
			
		||||
{
 | 
			
		||||
	QString filter;
 | 
			
		||||
    QString filter;
 | 
			
		||||
#if defined Q_OS_WIN32
 | 
			
		||||
	filter = "Java (javaw.exe)";
 | 
			
		||||
    filter = "Java (javaw.exe)";
 | 
			
		||||
#else
 | 
			
		||||
	filter = "Java (java)";
 | 
			
		||||
    filter = "Java (java)";
 | 
			
		||||
#endif
 | 
			
		||||
	QString raw_path = QFileDialog::getOpenFileName(this, tr("Find Java executable"), QString(), filter);
 | 
			
		||||
	if(raw_path.isEmpty())
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	QString cooked_path = FS::NormalizePath(raw_path);
 | 
			
		||||
	m_javaPathTextBox->setText(cooked_path);
 | 
			
		||||
	checkJavaPath(cooked_path);
 | 
			
		||||
    QString raw_path = QFileDialog::getOpenFileName(this, tr("Find Java executable"), QString(), filter);
 | 
			
		||||
    if(raw_path.isEmpty())
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    QString cooked_path = FS::NormalizePath(raw_path);
 | 
			
		||||
    m_javaPathTextBox->setText(cooked_path);
 | 
			
		||||
    checkJavaPath(cooked_path);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::on_javaStatusBtn_clicked()
 | 
			
		||||
{
 | 
			
		||||
	QString text;
 | 
			
		||||
	bool failed = false;
 | 
			
		||||
	switch(javaStatus)
 | 
			
		||||
	{
 | 
			
		||||
		case JavaStatus::NotSet:
 | 
			
		||||
			checkJavaPath(m_javaPathTextBox->text());
 | 
			
		||||
			return;
 | 
			
		||||
		case JavaStatus::DoesNotExist:
 | 
			
		||||
			text += QObject::tr("The specified file either doesn't exist or is not a proper executable.");
 | 
			
		||||
			failed = true;
 | 
			
		||||
			break;
 | 
			
		||||
		case JavaStatus::DoesNotStart:
 | 
			
		||||
		{
 | 
			
		||||
			text += QObject::tr("The specified java binary didn't start properly.<br />");
 | 
			
		||||
			auto htmlError = m_result.errorLog;
 | 
			
		||||
			if(!htmlError.isEmpty())
 | 
			
		||||
			{
 | 
			
		||||
				htmlError.replace('\n', "<br />");
 | 
			
		||||
				text += QString("<font color=\"red\">%1</font>").arg(htmlError);
 | 
			
		||||
			}
 | 
			
		||||
			failed = true;
 | 
			
		||||
			break;
 | 
			
		||||
		}
 | 
			
		||||
		case JavaStatus::ReturnedInvalidData:
 | 
			
		||||
		{
 | 
			
		||||
			text += QObject::tr("The specified java binary returned unexpected results:<br />");
 | 
			
		||||
			auto htmlOut = m_result.outLog;
 | 
			
		||||
			if(!htmlOut.isEmpty())
 | 
			
		||||
			{
 | 
			
		||||
				htmlOut.replace('\n', "<br />");
 | 
			
		||||
				text += QString("<font color=\"red\">%1</font>").arg(htmlOut);
 | 
			
		||||
			}
 | 
			
		||||
			failed = true;
 | 
			
		||||
			break;
 | 
			
		||||
		}
 | 
			
		||||
		case JavaStatus::Good:
 | 
			
		||||
			text += QObject::tr("Java test succeeded!<br />Platform reported: %1<br />Java version "
 | 
			
		||||
				"reported: %2<br />").arg(m_result.realPlatform, m_result.javaVersion.toString());
 | 
			
		||||
			break;
 | 
			
		||||
		case JavaStatus::Pending:
 | 
			
		||||
			// TODO: abort here?
 | 
			
		||||
			return;
 | 
			
		||||
	}
 | 
			
		||||
	CustomMessageBox::selectable(
 | 
			
		||||
		this,
 | 
			
		||||
		failed ? QObject::tr("Java test success") : QObject::tr("Java test failure"),
 | 
			
		||||
		text,
 | 
			
		||||
		failed ? QMessageBox::Critical : QMessageBox::Information
 | 
			
		||||
	)->show();
 | 
			
		||||
    QString text;
 | 
			
		||||
    bool failed = false;
 | 
			
		||||
    switch(javaStatus)
 | 
			
		||||
    {
 | 
			
		||||
        case JavaStatus::NotSet:
 | 
			
		||||
            checkJavaPath(m_javaPathTextBox->text());
 | 
			
		||||
            return;
 | 
			
		||||
        case JavaStatus::DoesNotExist:
 | 
			
		||||
            text += QObject::tr("The specified file either doesn't exist or is not a proper executable.");
 | 
			
		||||
            failed = true;
 | 
			
		||||
            break;
 | 
			
		||||
        case JavaStatus::DoesNotStart:
 | 
			
		||||
        {
 | 
			
		||||
            text += QObject::tr("The specified java binary didn't start properly.<br />");
 | 
			
		||||
            auto htmlError = m_result.errorLog;
 | 
			
		||||
            if(!htmlError.isEmpty())
 | 
			
		||||
            {
 | 
			
		||||
                htmlError.replace('\n', "<br />");
 | 
			
		||||
                text += QString("<font color=\"red\">%1</font>").arg(htmlError);
 | 
			
		||||
            }
 | 
			
		||||
            failed = true;
 | 
			
		||||
            break;
 | 
			
		||||
        }
 | 
			
		||||
        case JavaStatus::ReturnedInvalidData:
 | 
			
		||||
        {
 | 
			
		||||
            text += QObject::tr("The specified java binary returned unexpected results:<br />");
 | 
			
		||||
            auto htmlOut = m_result.outLog;
 | 
			
		||||
            if(!htmlOut.isEmpty())
 | 
			
		||||
            {
 | 
			
		||||
                htmlOut.replace('\n', "<br />");
 | 
			
		||||
                text += QString("<font color=\"red\">%1</font>").arg(htmlOut);
 | 
			
		||||
            }
 | 
			
		||||
            failed = true;
 | 
			
		||||
            break;
 | 
			
		||||
        }
 | 
			
		||||
        case JavaStatus::Good:
 | 
			
		||||
            text += QObject::tr("Java test succeeded!<br />Platform reported: %1<br />Java version "
 | 
			
		||||
                "reported: %2<br />").arg(m_result.realPlatform, m_result.javaVersion.toString());
 | 
			
		||||
            break;
 | 
			
		||||
        case JavaStatus::Pending:
 | 
			
		||||
            // TODO: abort here?
 | 
			
		||||
            return;
 | 
			
		||||
    }
 | 
			
		||||
    CustomMessageBox::selectable(
 | 
			
		||||
        this,
 | 
			
		||||
        failed ? QObject::tr("Java test success") : QObject::tr("Java test failure"),
 | 
			
		||||
        text,
 | 
			
		||||
        failed ? QMessageBox::Critical : QMessageBox::Information
 | 
			
		||||
    )->show();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::setJavaStatus(JavaSettingsWidget::JavaStatus status)
 | 
			
		||||
{
 | 
			
		||||
	javaStatus = status;
 | 
			
		||||
	switch(javaStatus)
 | 
			
		||||
	{
 | 
			
		||||
		case JavaStatus::Good:
 | 
			
		||||
			m_javaStatusBtn->setIcon(goodIcon);
 | 
			
		||||
			break;
 | 
			
		||||
		case JavaStatus::NotSet:
 | 
			
		||||
		case JavaStatus::Pending:
 | 
			
		||||
			m_javaStatusBtn->setIcon(yellowIcon);
 | 
			
		||||
			break;
 | 
			
		||||
		default:
 | 
			
		||||
			m_javaStatusBtn->setIcon(badIcon);
 | 
			
		||||
			break;
 | 
			
		||||
	}
 | 
			
		||||
    javaStatus = status;
 | 
			
		||||
    switch(javaStatus)
 | 
			
		||||
    {
 | 
			
		||||
        case JavaStatus::Good:
 | 
			
		||||
            m_javaStatusBtn->setIcon(goodIcon);
 | 
			
		||||
            break;
 | 
			
		||||
        case JavaStatus::NotSet:
 | 
			
		||||
        case JavaStatus::Pending:
 | 
			
		||||
            m_javaStatusBtn->setIcon(yellowIcon);
 | 
			
		||||
            break;
 | 
			
		||||
        default:
 | 
			
		||||
            m_javaStatusBtn->setIcon(badIcon);
 | 
			
		||||
            break;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::javaPathEdited(const QString& path)
 | 
			
		||||
{
 | 
			
		||||
	checkJavaPathOnEdit(path);
 | 
			
		||||
    checkJavaPathOnEdit(path);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::checkJavaPathOnEdit(const QString& path)
 | 
			
		||||
{
 | 
			
		||||
	auto realPath = FS::ResolveExecutable(path);
 | 
			
		||||
	QFileInfo pathInfo(realPath);
 | 
			
		||||
	if (pathInfo.baseName().toLower().contains("java"))
 | 
			
		||||
	{
 | 
			
		||||
		checkJavaPath(path);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		if(!m_checker)
 | 
			
		||||
		{
 | 
			
		||||
			setJavaStatus(JavaStatus::NotSet);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
    auto realPath = FS::ResolveExecutable(path);
 | 
			
		||||
    QFileInfo pathInfo(realPath);
 | 
			
		||||
    if (pathInfo.baseName().toLower().contains("java"))
 | 
			
		||||
    {
 | 
			
		||||
        checkJavaPath(path);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        if(!m_checker)
 | 
			
		||||
        {
 | 
			
		||||
            setJavaStatus(JavaStatus::NotSet);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::checkJavaPath(const QString &path)
 | 
			
		||||
{
 | 
			
		||||
	if(m_checker)
 | 
			
		||||
	{
 | 
			
		||||
		queuedCheck = path;
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	auto realPath = FS::ResolveExecutable(path);
 | 
			
		||||
	if(realPath.isNull())
 | 
			
		||||
	{
 | 
			
		||||
		setJavaStatus(JavaStatus::DoesNotExist);
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	setJavaStatus(JavaStatus::Pending);
 | 
			
		||||
	m_checker.reset(new JavaChecker());
 | 
			
		||||
	m_checker->m_path = path;
 | 
			
		||||
	m_checker->m_minMem = m_minMemSpinBox->value();
 | 
			
		||||
	m_checker->m_maxMem = m_maxMemSpinBox->value();
 | 
			
		||||
	if(m_permGenSpinBox->isVisible())
 | 
			
		||||
	{
 | 
			
		||||
		m_checker->m_permGen = m_permGenSpinBox->value();
 | 
			
		||||
	}
 | 
			
		||||
	connect(m_checker.get(), &JavaChecker::checkFinished, this, &JavaSettingsWidget::checkFinished);
 | 
			
		||||
	m_checker->performCheck();
 | 
			
		||||
    if(m_checker)
 | 
			
		||||
    {
 | 
			
		||||
        queuedCheck = path;
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    auto realPath = FS::ResolveExecutable(path);
 | 
			
		||||
    if(realPath.isNull())
 | 
			
		||||
    {
 | 
			
		||||
        setJavaStatus(JavaStatus::DoesNotExist);
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    setJavaStatus(JavaStatus::Pending);
 | 
			
		||||
    m_checker.reset(new JavaChecker());
 | 
			
		||||
    m_checker->m_path = path;
 | 
			
		||||
    m_checker->m_minMem = m_minMemSpinBox->value();
 | 
			
		||||
    m_checker->m_maxMem = m_maxMemSpinBox->value();
 | 
			
		||||
    if(m_permGenSpinBox->isVisible())
 | 
			
		||||
    {
 | 
			
		||||
        m_checker->m_permGen = m_permGenSpinBox->value();
 | 
			
		||||
    }
 | 
			
		||||
    connect(m_checker.get(), &JavaChecker::checkFinished, this, &JavaSettingsWidget::checkFinished);
 | 
			
		||||
    m_checker->performCheck();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::checkFinished(JavaCheckResult result)
 | 
			
		||||
{
 | 
			
		||||
	m_result = result;
 | 
			
		||||
	switch(result.validity)
 | 
			
		||||
	{
 | 
			
		||||
		case JavaCheckResult::Validity::Valid:
 | 
			
		||||
		{
 | 
			
		||||
			setJavaStatus(JavaStatus::Good);
 | 
			
		||||
			break;
 | 
			
		||||
		}
 | 
			
		||||
		case JavaCheckResult::Validity::ReturnedInvalidData:
 | 
			
		||||
		{
 | 
			
		||||
			setJavaStatus(JavaStatus::ReturnedInvalidData);
 | 
			
		||||
			break;
 | 
			
		||||
		}
 | 
			
		||||
		case JavaCheckResult::Validity::Errored:
 | 
			
		||||
		{
 | 
			
		||||
			setJavaStatus(JavaStatus::DoesNotStart);
 | 
			
		||||
			break;
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	m_checker.reset();
 | 
			
		||||
	if(!queuedCheck.isNull())
 | 
			
		||||
	{
 | 
			
		||||
		checkJavaPath(queuedCheck);
 | 
			
		||||
		queuedCheck.clear();
 | 
			
		||||
	}
 | 
			
		||||
    m_result = result;
 | 
			
		||||
    switch(result.validity)
 | 
			
		||||
    {
 | 
			
		||||
        case JavaCheckResult::Validity::Valid:
 | 
			
		||||
        {
 | 
			
		||||
            setJavaStatus(JavaStatus::Good);
 | 
			
		||||
            break;
 | 
			
		||||
        }
 | 
			
		||||
        case JavaCheckResult::Validity::ReturnedInvalidData:
 | 
			
		||||
        {
 | 
			
		||||
            setJavaStatus(JavaStatus::ReturnedInvalidData);
 | 
			
		||||
            break;
 | 
			
		||||
        }
 | 
			
		||||
        case JavaCheckResult::Validity::Errored:
 | 
			
		||||
        {
 | 
			
		||||
            setJavaStatus(JavaStatus::DoesNotStart);
 | 
			
		||||
            break;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    m_checker.reset();
 | 
			
		||||
    if(!queuedCheck.isNull())
 | 
			
		||||
    {
 | 
			
		||||
        checkJavaPath(queuedCheck);
 | 
			
		||||
        queuedCheck.clear();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void JavaSettingsWidget::retranslate()
 | 
			
		||||
{
 | 
			
		||||
	m_memoryGroupBox->setTitle(tr("Memory"));
 | 
			
		||||
	m_maxMemSpinBox->setToolTip(tr("The maximum amount of memory Minecraft is allowed to use."));
 | 
			
		||||
	m_labelMinMem->setText(tr("Minimum memory allocation:"));
 | 
			
		||||
	m_labelMaxMem->setText(tr("Maximum memory allocation:"));
 | 
			
		||||
	m_minMemSpinBox->setToolTip(tr("The amount of memory Minecraft is started with."));
 | 
			
		||||
	m_permGenSpinBox->setToolTip(tr("The amount of memory available to store loaded Java classes."));
 | 
			
		||||
	m_javaBrowseBtn->setText(tr("Browse"));
 | 
			
		||||
    m_memoryGroupBox->setTitle(tr("Memory"));
 | 
			
		||||
    m_maxMemSpinBox->setToolTip(tr("The maximum amount of memory Minecraft is allowed to use."));
 | 
			
		||||
    m_labelMinMem->setText(tr("Minimum memory allocation:"));
 | 
			
		||||
    m_labelMaxMem->setText(tr("Maximum memory allocation:"));
 | 
			
		||||
    m_minMemSpinBox->setToolTip(tr("The amount of memory Minecraft is started with."));
 | 
			
		||||
    m_permGenSpinBox->setToolTip(tr("The amount of memory available to store loaded Java classes."));
 | 
			
		||||
    m_javaBrowseBtn->setText(tr("Browse"));
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -22,81 +22,81 @@ class QToolButton;
 | 
			
		||||
 */
 | 
			
		||||
class JavaSettingsWidget : public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	explicit JavaSettingsWidget(QWidget *parent);
 | 
			
		||||
	virtual ~JavaSettingsWidget() {};
 | 
			
		||||
    explicit JavaSettingsWidget(QWidget *parent);
 | 
			
		||||
    virtual ~JavaSettingsWidget() {};
 | 
			
		||||
 | 
			
		||||
	enum class JavaStatus
 | 
			
		||||
	{
 | 
			
		||||
		NotSet,
 | 
			
		||||
		Pending,
 | 
			
		||||
		Good,
 | 
			
		||||
		DoesNotExist,
 | 
			
		||||
		DoesNotStart,
 | 
			
		||||
		ReturnedInvalidData
 | 
			
		||||
	} javaStatus = JavaStatus::NotSet;
 | 
			
		||||
    enum class JavaStatus
 | 
			
		||||
    {
 | 
			
		||||
        NotSet,
 | 
			
		||||
        Pending,
 | 
			
		||||
        Good,
 | 
			
		||||
        DoesNotExist,
 | 
			
		||||
        DoesNotStart,
 | 
			
		||||
        ReturnedInvalidData
 | 
			
		||||
    } javaStatus = JavaStatus::NotSet;
 | 
			
		||||
 | 
			
		||||
	enum class ValidationStatus
 | 
			
		||||
	{
 | 
			
		||||
		Bad,
 | 
			
		||||
		JavaBad,
 | 
			
		||||
		AllOK
 | 
			
		||||
	};
 | 
			
		||||
    enum class ValidationStatus
 | 
			
		||||
    {
 | 
			
		||||
        Bad,
 | 
			
		||||
        JavaBad,
 | 
			
		||||
        AllOK
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
	void refresh();
 | 
			
		||||
	void initialize();
 | 
			
		||||
	ValidationStatus validate();
 | 
			
		||||
	void retranslate();
 | 
			
		||||
    void refresh();
 | 
			
		||||
    void initialize();
 | 
			
		||||
    ValidationStatus validate();
 | 
			
		||||
    void retranslate();
 | 
			
		||||
 | 
			
		||||
	bool permGenEnabled() const;
 | 
			
		||||
	int permGenSize() const;
 | 
			
		||||
	int minHeapSize() const;
 | 
			
		||||
	int maxHeapSize() const;
 | 
			
		||||
	QString javaPath() const;
 | 
			
		||||
    bool permGenEnabled() const;
 | 
			
		||||
    int permGenSize() const;
 | 
			
		||||
    int minHeapSize() const;
 | 
			
		||||
    int maxHeapSize() const;
 | 
			
		||||
    QString javaPath() const;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
protected slots:
 | 
			
		||||
	void memoryValueChanged(int);
 | 
			
		||||
	void javaPathEdited(const QString &path);
 | 
			
		||||
	void javaVersionSelected(BaseVersionPtr version);
 | 
			
		||||
	void on_javaBrowseBtn_clicked();
 | 
			
		||||
	void on_javaStatusBtn_clicked();
 | 
			
		||||
	void checkFinished(JavaCheckResult result);
 | 
			
		||||
    void memoryValueChanged(int);
 | 
			
		||||
    void javaPathEdited(const QString &path);
 | 
			
		||||
    void javaVersionSelected(BaseVersionPtr version);
 | 
			
		||||
    void on_javaBrowseBtn_clicked();
 | 
			
		||||
    void on_javaStatusBtn_clicked();
 | 
			
		||||
    void checkFinished(JavaCheckResult result);
 | 
			
		||||
 | 
			
		||||
protected: /* methods */
 | 
			
		||||
	void checkJavaPathOnEdit(const QString &path);
 | 
			
		||||
	void checkJavaPath(const QString &path);
 | 
			
		||||
	void setJavaStatus(JavaStatus status);
 | 
			
		||||
	void setupUi();
 | 
			
		||||
    void checkJavaPathOnEdit(const QString &path);
 | 
			
		||||
    void checkJavaPath(const QString &path);
 | 
			
		||||
    void setJavaStatus(JavaStatus status);
 | 
			
		||||
    void setupUi();
 | 
			
		||||
 | 
			
		||||
private: /* data */
 | 
			
		||||
	VersionSelectWidget *m_versionWidget = nullptr;
 | 
			
		||||
	QVBoxLayout *m_verticalLayout = nullptr;
 | 
			
		||||
    VersionSelectWidget *m_versionWidget = nullptr;
 | 
			
		||||
    QVBoxLayout *m_verticalLayout = nullptr;
 | 
			
		||||
 | 
			
		||||
	QLineEdit * m_javaPathTextBox = nullptr;
 | 
			
		||||
	QPushButton * m_javaBrowseBtn = nullptr;
 | 
			
		||||
	QToolButton * m_javaStatusBtn = nullptr;
 | 
			
		||||
	QHBoxLayout *m_horizontalLayout = nullptr;
 | 
			
		||||
    QLineEdit * m_javaPathTextBox = nullptr;
 | 
			
		||||
    QPushButton * m_javaBrowseBtn = nullptr;
 | 
			
		||||
    QToolButton * m_javaStatusBtn = nullptr;
 | 
			
		||||
    QHBoxLayout *m_horizontalLayout = nullptr;
 | 
			
		||||
 | 
			
		||||
	QGroupBox *m_memoryGroupBox = nullptr;
 | 
			
		||||
	QGridLayout *m_gridLayout_2 = nullptr;
 | 
			
		||||
	QSpinBox *m_maxMemSpinBox = nullptr;
 | 
			
		||||
	QLabel *m_labelMinMem = nullptr;
 | 
			
		||||
	QLabel *m_labelMaxMem = nullptr;
 | 
			
		||||
	QSpinBox *m_minMemSpinBox = nullptr;
 | 
			
		||||
	QLabel *m_labelPermGen = nullptr;
 | 
			
		||||
	QSpinBox *m_permGenSpinBox = nullptr;
 | 
			
		||||
	QIcon goodIcon;
 | 
			
		||||
	QIcon yellowIcon;
 | 
			
		||||
	QIcon badIcon;
 | 
			
		||||
    QGroupBox *m_memoryGroupBox = nullptr;
 | 
			
		||||
    QGridLayout *m_gridLayout_2 = nullptr;
 | 
			
		||||
    QSpinBox *m_maxMemSpinBox = nullptr;
 | 
			
		||||
    QLabel *m_labelMinMem = nullptr;
 | 
			
		||||
    QLabel *m_labelMaxMem = nullptr;
 | 
			
		||||
    QSpinBox *m_minMemSpinBox = nullptr;
 | 
			
		||||
    QLabel *m_labelPermGen = nullptr;
 | 
			
		||||
    QSpinBox *m_permGenSpinBox = nullptr;
 | 
			
		||||
    QIcon goodIcon;
 | 
			
		||||
    QIcon yellowIcon;
 | 
			
		||||
    QIcon badIcon;
 | 
			
		||||
 | 
			
		||||
	int observedMinMemory = 0;
 | 
			
		||||
	int observedMaxMemory = 0;
 | 
			
		||||
	int observedPermGenMemory = 0;
 | 
			
		||||
	QString queuedCheck;
 | 
			
		||||
	uint64_t m_availableMemory = 0ull;
 | 
			
		||||
	shared_qobject_ptr<JavaChecker> m_checker;
 | 
			
		||||
	JavaCheckResult m_result;
 | 
			
		||||
    int observedMinMemory = 0;
 | 
			
		||||
    int observedMaxMemory = 0;
 | 
			
		||||
    int observedPermGenMemory = 0;
 | 
			
		||||
    QString queuedCheck;
 | 
			
		||||
    uint64_t m_availableMemory = 0ull;
 | 
			
		||||
    shared_qobject_ptr<JavaChecker> m_checker;
 | 
			
		||||
    JavaCheckResult m_result;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -28,32 +28,32 @@
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
LabeledToolButton::LabeledToolButton(QWidget * parent)
 | 
			
		||||
	: QToolButton(parent)
 | 
			
		||||
	, m_label(new QLabel(this))
 | 
			
		||||
    : QToolButton(parent)
 | 
			
		||||
    , m_label(new QLabel(this))
 | 
			
		||||
{
 | 
			
		||||
	//QToolButton::setText(" ");
 | 
			
		||||
	m_label->setWordWrap(true);
 | 
			
		||||
	m_label->setMouseTracking(false);
 | 
			
		||||
	m_label->setAlignment(Qt::AlignCenter);
 | 
			
		||||
	m_label->setTextInteractionFlags(Qt::NoTextInteraction);
 | 
			
		||||
	// somehow, this makes word wrap work in the QLabel. yay.
 | 
			
		||||
	//m_label->setMinimumWidth(100);
 | 
			
		||||
    //QToolButton::setText(" ");
 | 
			
		||||
    m_label->setWordWrap(true);
 | 
			
		||||
    m_label->setMouseTracking(false);
 | 
			
		||||
    m_label->setAlignment(Qt::AlignCenter);
 | 
			
		||||
    m_label->setTextInteractionFlags(Qt::NoTextInteraction);
 | 
			
		||||
    // somehow, this makes word wrap work in the QLabel. yay.
 | 
			
		||||
    //m_label->setMinimumWidth(100);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QString LabeledToolButton::text() const
 | 
			
		||||
{
 | 
			
		||||
	return m_label->text();
 | 
			
		||||
    return m_label->text();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LabeledToolButton::setText(const QString & text)
 | 
			
		||||
{
 | 
			
		||||
	m_label->setText(text);
 | 
			
		||||
    m_label->setText(text);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LabeledToolButton::setIcon(QIcon icon)
 | 
			
		||||
{
 | 
			
		||||
	m_icon = icon;
 | 
			
		||||
	resetIcon();
 | 
			
		||||
    m_icon = icon;
 | 
			
		||||
    resetIcon();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@@ -62,54 +62,54 @@ void LabeledToolButton::setIcon(QIcon icon)
 | 
			
		||||
*/
 | 
			
		||||
QSize LabeledToolButton::sizeHint() const
 | 
			
		||||
{
 | 
			
		||||
	/*
 | 
			
		||||
	Q_D(const QToolButton);
 | 
			
		||||
	if (d->sizeHint.isValid())
 | 
			
		||||
		return d->sizeHint;
 | 
			
		||||
	*/
 | 
			
		||||
	ensurePolished();
 | 
			
		||||
    /*
 | 
			
		||||
    Q_D(const QToolButton);
 | 
			
		||||
    if (d->sizeHint.isValid())
 | 
			
		||||
        return d->sizeHint;
 | 
			
		||||
    */
 | 
			
		||||
    ensurePolished();
 | 
			
		||||
 | 
			
		||||
	int w = 0, h = 0;
 | 
			
		||||
	QStyleOptionToolButton opt;
 | 
			
		||||
	initStyleOption(&opt);
 | 
			
		||||
	QSize sz =m_label->sizeHint();
 | 
			
		||||
	w = sz.width();
 | 
			
		||||
	h = sz.height();
 | 
			
		||||
    int w = 0, h = 0;
 | 
			
		||||
    QStyleOptionToolButton opt;
 | 
			
		||||
    initStyleOption(&opt);
 | 
			
		||||
    QSize sz =m_label->sizeHint();
 | 
			
		||||
    w = sz.width();
 | 
			
		||||
    h = sz.height();
 | 
			
		||||
 | 
			
		||||
	opt.rect.setSize(QSize(w, h)); // PM_MenuButtonIndicator depends on the height
 | 
			
		||||
	if (popupMode() == MenuButtonPopup)
 | 
			
		||||
		w += style()->pixelMetric(QStyle::PM_MenuButtonIndicator, &opt, this);
 | 
			
		||||
	
 | 
			
		||||
	QSize rawSize = style()->sizeFromContents(QStyle::CT_ToolButton, &opt, QSize(w, h), this);
 | 
			
		||||
	QSize sizeHint = rawSize.expandedTo(QApplication::globalStrut());
 | 
			
		||||
	return sizeHint;
 | 
			
		||||
    opt.rect.setSize(QSize(w, h)); // PM_MenuButtonIndicator depends on the height
 | 
			
		||||
    if (popupMode() == MenuButtonPopup)
 | 
			
		||||
        w += style()->pixelMetric(QStyle::PM_MenuButtonIndicator, &opt, this);
 | 
			
		||||
    
 | 
			
		||||
    QSize rawSize = style()->sizeFromContents(QStyle::CT_ToolButton, &opt, QSize(w, h), this);
 | 
			
		||||
    QSize sizeHint = rawSize.expandedTo(QApplication::globalStrut());
 | 
			
		||||
    return sizeHint;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
void LabeledToolButton::resizeEvent(QResizeEvent * event)
 | 
			
		||||
{
 | 
			
		||||
	m_label->setGeometry(QRect(4, 4, width()-8, height()-8));
 | 
			
		||||
	if(!m_icon.isNull())
 | 
			
		||||
	{
 | 
			
		||||
		resetIcon();
 | 
			
		||||
	}
 | 
			
		||||
	QWidget::resizeEvent(event);
 | 
			
		||||
    m_label->setGeometry(QRect(4, 4, width()-8, height()-8));
 | 
			
		||||
    if(!m_icon.isNull())
 | 
			
		||||
    {
 | 
			
		||||
        resetIcon();
 | 
			
		||||
    }
 | 
			
		||||
    QWidget::resizeEvent(event);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LabeledToolButton::resetIcon()
 | 
			
		||||
{
 | 
			
		||||
	auto iconSz = m_icon.actualSize(QSize(160, 80));
 | 
			
		||||
	float w = iconSz.width();
 | 
			
		||||
	float h = iconSz.height();
 | 
			
		||||
	float ar = w/h;
 | 
			
		||||
	// FIXME: hardcoded max size of 160x80
 | 
			
		||||
	int newW = 80 * ar;
 | 
			
		||||
	if(newW > 160)
 | 
			
		||||
		newW = 160;
 | 
			
		||||
	QSize newSz (newW, 80);
 | 
			
		||||
	auto pixmap = m_icon.pixmap(newSz);
 | 
			
		||||
	m_label->setPixmap(pixmap);
 | 
			
		||||
	m_label->setMinimumHeight(80);
 | 
			
		||||
	m_label->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::Preferred );
 | 
			
		||||
    auto iconSz = m_icon.actualSize(QSize(160, 80));
 | 
			
		||||
    float w = iconSz.width();
 | 
			
		||||
    float h = iconSz.height();
 | 
			
		||||
    float ar = w/h;
 | 
			
		||||
    // FIXME: hardcoded max size of 160x80
 | 
			
		||||
    int newW = 80 * ar;
 | 
			
		||||
    if(newW > 160)
 | 
			
		||||
        newW = 160;
 | 
			
		||||
    QSize newSz (newW, 80);
 | 
			
		||||
    auto pixmap = m_icon.pixmap(newSz);
 | 
			
		||||
    m_label->setPixmap(pixmap);
 | 
			
		||||
    m_label->setMinimumHeight(80);
 | 
			
		||||
    m_label->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::Preferred );
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -22,19 +22,19 @@ class QLabel;
 | 
			
		||||
 | 
			
		||||
class LabeledToolButton : public QToolButton
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
	QLabel * m_label;
 | 
			
		||||
	QIcon m_icon;
 | 
			
		||||
    QLabel * m_label;
 | 
			
		||||
    QIcon m_icon;
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	LabeledToolButton(QWidget * parent = 0);
 | 
			
		||||
    LabeledToolButton(QWidget * parent = 0);
 | 
			
		||||
 | 
			
		||||
	QString text() const;
 | 
			
		||||
	void setText(const QString & text);
 | 
			
		||||
	void setIcon(QIcon icon);
 | 
			
		||||
	virtual QSize sizeHint() const;
 | 
			
		||||
    QString text() const;
 | 
			
		||||
    void setText(const QString & text);
 | 
			
		||||
    void setIcon(QIcon icon);
 | 
			
		||||
    virtual QSize sizeHint() const;
 | 
			
		||||
protected:
 | 
			
		||||
	void resizeEvent(QResizeEvent * event);
 | 
			
		||||
	void resetIcon();
 | 
			
		||||
    void resizeEvent(QResizeEvent * event);
 | 
			
		||||
    void resetIcon();
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -7,31 +7,31 @@
 | 
			
		||||
 | 
			
		||||
void LineSeparator::initStyleOption(QStyleOption *option) const
 | 
			
		||||
{
 | 
			
		||||
	option->initFrom(this);
 | 
			
		||||
	// in a horizontal layout, the line is vertical (and vice versa)
 | 
			
		||||
	if (m_orientation == Qt::Vertical)
 | 
			
		||||
		option->state |= QStyle::State_Horizontal;
 | 
			
		||||
    option->initFrom(this);
 | 
			
		||||
    // in a horizontal layout, the line is vertical (and vice versa)
 | 
			
		||||
    if (m_orientation == Qt::Vertical)
 | 
			
		||||
        option->state |= QStyle::State_Horizontal;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
LineSeparator::LineSeparator(QWidget *parent, Qt::Orientation orientation)
 | 
			
		||||
	: QWidget(parent), m_orientation(orientation)
 | 
			
		||||
    : QWidget(parent), m_orientation(orientation)
 | 
			
		||||
{
 | 
			
		||||
	setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Minimum);
 | 
			
		||||
    setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Minimum);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QSize LineSeparator::sizeHint() const
 | 
			
		||||
{
 | 
			
		||||
	QStyleOption opt;
 | 
			
		||||
	initStyleOption(&opt);
 | 
			
		||||
	const int extent =
 | 
			
		||||
		style()->pixelMetric(QStyle::PM_ToolBarSeparatorExtent, &opt, parentWidget());
 | 
			
		||||
	return QSize(extent, extent);
 | 
			
		||||
    QStyleOption opt;
 | 
			
		||||
    initStyleOption(&opt);
 | 
			
		||||
    const int extent =
 | 
			
		||||
        style()->pixelMetric(QStyle::PM_ToolBarSeparatorExtent, &opt, parentWidget());
 | 
			
		||||
    return QSize(extent, extent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LineSeparator::paintEvent(QPaintEvent *)
 | 
			
		||||
{
 | 
			
		||||
	QPainter p(this);
 | 
			
		||||
	QStyleOption opt;
 | 
			
		||||
	initStyleOption(&opt);
 | 
			
		||||
	style()->drawPrimitive(QStyle::PE_IndicatorToolBarSeparator, &opt, &p, parentWidget());
 | 
			
		||||
    QPainter p(this);
 | 
			
		||||
    QStyleOption opt;
 | 
			
		||||
    initStyleOption(&opt);
 | 
			
		||||
    style()->drawPrimitive(QStyle::PE_IndicatorToolBarSeparator, &opt, &p, parentWidget());
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -5,14 +5,14 @@ class QStyleOption;
 | 
			
		||||
 | 
			
		||||
class LineSeparator : public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	/// Create a line separator. orientation is the orientation of the line.
 | 
			
		||||
	explicit LineSeparator(QWidget *parent, Qt::Orientation orientation = Qt::Horizontal);
 | 
			
		||||
	QSize sizeHint() const;
 | 
			
		||||
	void paintEvent(QPaintEvent *);
 | 
			
		||||
	void initStyleOption(QStyleOption *option) const;
 | 
			
		||||
    /// Create a line separator. orientation is the orientation of the line.
 | 
			
		||||
    explicit LineSeparator(QWidget *parent, Qt::Orientation orientation = Qt::Horizontal);
 | 
			
		||||
    QSize sizeHint() const;
 | 
			
		||||
    void paintEvent(QPaintEvent *);
 | 
			
		||||
    void initStyleOption(QStyleOption *option) const;
 | 
			
		||||
private:
 | 
			
		||||
	Qt::Orientation m_orientation = Qt::Horizontal;
 | 
			
		||||
    Qt::Orientation m_orientation = Qt::Horizontal;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -4,141 +4,141 @@
 | 
			
		||||
 | 
			
		||||
LogView::LogView(QWidget* parent) : QPlainTextEdit(parent)
 | 
			
		||||
{
 | 
			
		||||
	setWordWrapMode(QTextOption::WrapAtWordBoundaryOrAnywhere);
 | 
			
		||||
	m_defaultFormat = new QTextCharFormat(currentCharFormat());
 | 
			
		||||
    setWordWrapMode(QTextOption::WrapAtWordBoundaryOrAnywhere);
 | 
			
		||||
    m_defaultFormat = new QTextCharFormat(currentCharFormat());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
LogView::~LogView()
 | 
			
		||||
{
 | 
			
		||||
	delete m_defaultFormat;
 | 
			
		||||
    delete m_defaultFormat;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::setWordWrap(bool wrapping)
 | 
			
		||||
{
 | 
			
		||||
	if(wrapping)
 | 
			
		||||
	{
 | 
			
		||||
		setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
		setLineWrapMode(QPlainTextEdit::WidgetWidth);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		setHorizontalScrollBarPolicy(Qt::ScrollBarAsNeeded);
 | 
			
		||||
		setLineWrapMode(QPlainTextEdit::NoWrap);
 | 
			
		||||
	}
 | 
			
		||||
    if(wrapping)
 | 
			
		||||
    {
 | 
			
		||||
        setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
        setLineWrapMode(QPlainTextEdit::WidgetWidth);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        setHorizontalScrollBarPolicy(Qt::ScrollBarAsNeeded);
 | 
			
		||||
        setLineWrapMode(QPlainTextEdit::NoWrap);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::setModel(QAbstractItemModel* model)
 | 
			
		||||
{
 | 
			
		||||
	if(m_model)
 | 
			
		||||
	{
 | 
			
		||||
		disconnect(m_model, &QAbstractItemModel::modelReset, this, &LogView::repopulate);
 | 
			
		||||
		disconnect(m_model, &QAbstractItemModel::rowsInserted, this, &LogView::rowsInserted);
 | 
			
		||||
		disconnect(m_model, &QAbstractItemModel::rowsAboutToBeInserted, this, &LogView::rowsAboutToBeInserted);
 | 
			
		||||
		disconnect(m_model, &QAbstractItemModel::rowsRemoved, this, &LogView::rowsRemoved);
 | 
			
		||||
	}
 | 
			
		||||
	m_model = model;
 | 
			
		||||
	if(m_model)
 | 
			
		||||
	{
 | 
			
		||||
		connect(m_model, &QAbstractItemModel::modelReset, this, &LogView::repopulate);
 | 
			
		||||
		connect(m_model, &QAbstractItemModel::rowsInserted, this, &LogView::rowsInserted);
 | 
			
		||||
		connect(m_model, &QAbstractItemModel::rowsAboutToBeInserted, this, &LogView::rowsAboutToBeInserted);
 | 
			
		||||
		connect(m_model, &QAbstractItemModel::rowsRemoved, this, &LogView::rowsRemoved);
 | 
			
		||||
		connect(m_model, &QAbstractItemModel::destroyed, this, &LogView::modelDestroyed);
 | 
			
		||||
	}
 | 
			
		||||
	repopulate();
 | 
			
		||||
    if(m_model)
 | 
			
		||||
    {
 | 
			
		||||
        disconnect(m_model, &QAbstractItemModel::modelReset, this, &LogView::repopulate);
 | 
			
		||||
        disconnect(m_model, &QAbstractItemModel::rowsInserted, this, &LogView::rowsInserted);
 | 
			
		||||
        disconnect(m_model, &QAbstractItemModel::rowsAboutToBeInserted, this, &LogView::rowsAboutToBeInserted);
 | 
			
		||||
        disconnect(m_model, &QAbstractItemModel::rowsRemoved, this, &LogView::rowsRemoved);
 | 
			
		||||
    }
 | 
			
		||||
    m_model = model;
 | 
			
		||||
    if(m_model)
 | 
			
		||||
    {
 | 
			
		||||
        connect(m_model, &QAbstractItemModel::modelReset, this, &LogView::repopulate);
 | 
			
		||||
        connect(m_model, &QAbstractItemModel::rowsInserted, this, &LogView::rowsInserted);
 | 
			
		||||
        connect(m_model, &QAbstractItemModel::rowsAboutToBeInserted, this, &LogView::rowsAboutToBeInserted);
 | 
			
		||||
        connect(m_model, &QAbstractItemModel::rowsRemoved, this, &LogView::rowsRemoved);
 | 
			
		||||
        connect(m_model, &QAbstractItemModel::destroyed, this, &LogView::modelDestroyed);
 | 
			
		||||
    }
 | 
			
		||||
    repopulate();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
QAbstractItemModel * LogView::model() const
 | 
			
		||||
{
 | 
			
		||||
	return m_model;
 | 
			
		||||
    return m_model;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::modelDestroyed(QObject* model)
 | 
			
		||||
{
 | 
			
		||||
	if(m_model == model)
 | 
			
		||||
	{
 | 
			
		||||
		setModel(nullptr);
 | 
			
		||||
	}
 | 
			
		||||
    if(m_model == model)
 | 
			
		||||
    {
 | 
			
		||||
        setModel(nullptr);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::repopulate()
 | 
			
		||||
{
 | 
			
		||||
	auto doc = document();
 | 
			
		||||
	doc->clear();
 | 
			
		||||
	if(!m_model)
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	rowsInserted(QModelIndex(), 0, m_model->rowCount() - 1);
 | 
			
		||||
    auto doc = document();
 | 
			
		||||
    doc->clear();
 | 
			
		||||
    if(!m_model)
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    rowsInserted(QModelIndex(), 0, m_model->rowCount() - 1);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::rowsAboutToBeInserted(const QModelIndex& parent, int first, int last)
 | 
			
		||||
{
 | 
			
		||||
	Q_UNUSED(parent)
 | 
			
		||||
	Q_UNUSED(first)
 | 
			
		||||
	Q_UNUSED(last)
 | 
			
		||||
	QScrollBar *bar = verticalScrollBar();
 | 
			
		||||
	int max_bar = bar->maximum();
 | 
			
		||||
	int val_bar = bar->value();
 | 
			
		||||
	if (m_scroll)
 | 
			
		||||
	{
 | 
			
		||||
		m_scroll = (max_bar - val_bar) <= 1;
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		m_scroll = val_bar == max_bar;
 | 
			
		||||
	}
 | 
			
		||||
    Q_UNUSED(parent)
 | 
			
		||||
    Q_UNUSED(first)
 | 
			
		||||
    Q_UNUSED(last)
 | 
			
		||||
    QScrollBar *bar = verticalScrollBar();
 | 
			
		||||
    int max_bar = bar->maximum();
 | 
			
		||||
    int val_bar = bar->value();
 | 
			
		||||
    if (m_scroll)
 | 
			
		||||
    {
 | 
			
		||||
        m_scroll = (max_bar - val_bar) <= 1;
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        m_scroll = val_bar == max_bar;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::rowsInserted(const QModelIndex& parent, int first, int last)
 | 
			
		||||
{
 | 
			
		||||
	for(int i = first; i <= last; i++)
 | 
			
		||||
	{
 | 
			
		||||
		auto idx = m_model->index(i, 0, parent);
 | 
			
		||||
		auto text = m_model->data(idx, Qt::DisplayRole).toString();
 | 
			
		||||
		QTextCharFormat format(*m_defaultFormat);
 | 
			
		||||
		auto font = m_model->data(idx, Qt::FontRole);
 | 
			
		||||
		if(font.isValid())
 | 
			
		||||
		{
 | 
			
		||||
			format.setFont(font.value<QFont>());
 | 
			
		||||
		}
 | 
			
		||||
		auto fg = m_model->data(idx, Qt::TextColorRole);
 | 
			
		||||
		if(fg.isValid())
 | 
			
		||||
		{
 | 
			
		||||
			format.setForeground(fg.value<QColor>());
 | 
			
		||||
		}
 | 
			
		||||
		auto bg = m_model->data(idx, Qt::BackgroundRole);
 | 
			
		||||
		if(bg.isValid())
 | 
			
		||||
		{
 | 
			
		||||
			format.setBackground(bg.value<QColor>());
 | 
			
		||||
		}
 | 
			
		||||
		auto workCursor = textCursor();
 | 
			
		||||
		workCursor.movePosition(QTextCursor::End);
 | 
			
		||||
		workCursor.insertText(text, format);
 | 
			
		||||
		workCursor.insertBlock();
 | 
			
		||||
	}
 | 
			
		||||
	if(m_scroll && !m_scrolling)
 | 
			
		||||
	{
 | 
			
		||||
		m_scrolling = true;
 | 
			
		||||
		QMetaObject::invokeMethod( this, "scrollToBottom", Qt::QueuedConnection);
 | 
			
		||||
	}
 | 
			
		||||
    for(int i = first; i <= last; i++)
 | 
			
		||||
    {
 | 
			
		||||
        auto idx = m_model->index(i, 0, parent);
 | 
			
		||||
        auto text = m_model->data(idx, Qt::DisplayRole).toString();
 | 
			
		||||
        QTextCharFormat format(*m_defaultFormat);
 | 
			
		||||
        auto font = m_model->data(idx, Qt::FontRole);
 | 
			
		||||
        if(font.isValid())
 | 
			
		||||
        {
 | 
			
		||||
            format.setFont(font.value<QFont>());
 | 
			
		||||
        }
 | 
			
		||||
        auto fg = m_model->data(idx, Qt::TextColorRole);
 | 
			
		||||
        if(fg.isValid())
 | 
			
		||||
        {
 | 
			
		||||
            format.setForeground(fg.value<QColor>());
 | 
			
		||||
        }
 | 
			
		||||
        auto bg = m_model->data(idx, Qt::BackgroundRole);
 | 
			
		||||
        if(bg.isValid())
 | 
			
		||||
        {
 | 
			
		||||
            format.setBackground(bg.value<QColor>());
 | 
			
		||||
        }
 | 
			
		||||
        auto workCursor = textCursor();
 | 
			
		||||
        workCursor.movePosition(QTextCursor::End);
 | 
			
		||||
        workCursor.insertText(text, format);
 | 
			
		||||
        workCursor.insertBlock();
 | 
			
		||||
    }
 | 
			
		||||
    if(m_scroll && !m_scrolling)
 | 
			
		||||
    {
 | 
			
		||||
        m_scrolling = true;
 | 
			
		||||
        QMetaObject::invokeMethod( this, "scrollToBottom", Qt::QueuedConnection);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::rowsRemoved(const QModelIndex& parent, int first, int last)
 | 
			
		||||
{
 | 
			
		||||
	// TODO: some day... maybe
 | 
			
		||||
	Q_UNUSED(parent)
 | 
			
		||||
	Q_UNUSED(first)
 | 
			
		||||
	Q_UNUSED(last)
 | 
			
		||||
    // TODO: some day... maybe
 | 
			
		||||
    Q_UNUSED(parent)
 | 
			
		||||
    Q_UNUSED(first)
 | 
			
		||||
    Q_UNUSED(last)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::scrollToBottom()
 | 
			
		||||
{
 | 
			
		||||
	m_scrolling = false;
 | 
			
		||||
	verticalScrollBar()->setSliderPosition(verticalScrollBar()->maximum());
 | 
			
		||||
    m_scrolling = false;
 | 
			
		||||
    verticalScrollBar()->setSliderPosition(verticalScrollBar()->maximum());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void LogView::findNext(const QString& what, bool reverse)
 | 
			
		||||
{
 | 
			
		||||
	find(what, reverse ? QTextDocument::FindFlag::FindBackward : QTextDocument::FindFlag(0));
 | 
			
		||||
    find(what, reverse ? QTextDocument::FindFlag::FindBackward : QTextDocument::FindFlag(0));
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -6,31 +6,31 @@ class QAbstractItemModel;
 | 
			
		||||
 | 
			
		||||
class LogView: public QPlainTextEdit
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit LogView(QWidget *parent = nullptr);
 | 
			
		||||
	virtual ~LogView();
 | 
			
		||||
    explicit LogView(QWidget *parent = nullptr);
 | 
			
		||||
    virtual ~LogView();
 | 
			
		||||
 | 
			
		||||
	virtual void setModel(QAbstractItemModel *model);
 | 
			
		||||
	QAbstractItemModel *model() const;
 | 
			
		||||
    virtual void setModel(QAbstractItemModel *model);
 | 
			
		||||
    QAbstractItemModel *model() const;
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	void setWordWrap(bool wrapping);
 | 
			
		||||
	void findNext(const QString & what, bool reverse);
 | 
			
		||||
	void scrollToBottom();
 | 
			
		||||
    void setWordWrap(bool wrapping);
 | 
			
		||||
    void findNext(const QString & what, bool reverse);
 | 
			
		||||
    void scrollToBottom();
 | 
			
		||||
 | 
			
		||||
protected slots:
 | 
			
		||||
	void repopulate();
 | 
			
		||||
	// note: this supports only appending
 | 
			
		||||
	void rowsInserted(const QModelIndex &parent, int first, int last);
 | 
			
		||||
	void rowsAboutToBeInserted(const QModelIndex &parent, int first, int last);
 | 
			
		||||
	// note: this supports only removing from front
 | 
			
		||||
	void rowsRemoved(const QModelIndex &parent, int first, int last);
 | 
			
		||||
	void modelDestroyed(QObject * model);
 | 
			
		||||
    void repopulate();
 | 
			
		||||
    // note: this supports only appending
 | 
			
		||||
    void rowsInserted(const QModelIndex &parent, int first, int last);
 | 
			
		||||
    void rowsAboutToBeInserted(const QModelIndex &parent, int first, int last);
 | 
			
		||||
    // note: this supports only removing from front
 | 
			
		||||
    void rowsRemoved(const QModelIndex &parent, int first, int last);
 | 
			
		||||
    void modelDestroyed(QObject * model);
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	QAbstractItemModel *m_model = nullptr;
 | 
			
		||||
	QTextCharFormat *m_defaultFormat = nullptr;
 | 
			
		||||
	bool m_scroll = false;
 | 
			
		||||
	bool m_scrolling = false;
 | 
			
		||||
    QAbstractItemModel *m_model = nullptr;
 | 
			
		||||
    QTextCharFormat *m_defaultFormat = nullptr;
 | 
			
		||||
    bool m_scroll = false;
 | 
			
		||||
    bool m_scrolling = false;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -22,145 +22,145 @@
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::updateWithMod(Mod &m)
 | 
			
		||||
{
 | 
			
		||||
	if (m.type() == m.MOD_FOLDER)
 | 
			
		||||
	{
 | 
			
		||||
		clear();
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
    if (m.type() == m.MOD_FOLDER)
 | 
			
		||||
    {
 | 
			
		||||
        clear();
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	QString text = "";
 | 
			
		||||
	QString name = "";
 | 
			
		||||
	if (m.name().isEmpty())
 | 
			
		||||
		name = m.mmc_id();
 | 
			
		||||
	else
 | 
			
		||||
		name = m.name();
 | 
			
		||||
    QString text = "";
 | 
			
		||||
    QString name = "";
 | 
			
		||||
    if (m.name().isEmpty())
 | 
			
		||||
        name = m.mmc_id();
 | 
			
		||||
    else
 | 
			
		||||
        name = m.name();
 | 
			
		||||
 | 
			
		||||
	if (m.homeurl().isEmpty())
 | 
			
		||||
		text = name;
 | 
			
		||||
	else
 | 
			
		||||
		text = "<a href=\"" + m.homeurl() + "\">" + name + "</a>";
 | 
			
		||||
	if (!m.authors().isEmpty())
 | 
			
		||||
		text += " by " + m.authors();
 | 
			
		||||
    if (m.homeurl().isEmpty())
 | 
			
		||||
        text = name;
 | 
			
		||||
    else
 | 
			
		||||
        text = "<a href=\"" + m.homeurl() + "\">" + name + "</a>";
 | 
			
		||||
    if (!m.authors().isEmpty())
 | 
			
		||||
        text += " by " + m.authors();
 | 
			
		||||
 | 
			
		||||
	setModText(text);
 | 
			
		||||
    setModText(text);
 | 
			
		||||
 | 
			
		||||
	if (m.description().isEmpty())
 | 
			
		||||
	{
 | 
			
		||||
		setModDescription(QString());
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		setModDescription(m.description());
 | 
			
		||||
	}
 | 
			
		||||
    if (m.description().isEmpty())
 | 
			
		||||
    {
 | 
			
		||||
        setModDescription(QString());
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        setModDescription(m.description());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::clear()
 | 
			
		||||
{
 | 
			
		||||
	setModText(QString());
 | 
			
		||||
	setModDescription(QString());
 | 
			
		||||
    setModText(QString());
 | 
			
		||||
    setModDescription(QString());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
MCModInfoFrame::MCModInfoFrame(QWidget *parent) :
 | 
			
		||||
	QFrame(parent),
 | 
			
		||||
	ui(new Ui::MCModInfoFrame)
 | 
			
		||||
    QFrame(parent),
 | 
			
		||||
    ui(new Ui::MCModInfoFrame)
 | 
			
		||||
{
 | 
			
		||||
	ui->setupUi(this);
 | 
			
		||||
	ui->label_ModDescription->setHidden(true);
 | 
			
		||||
	ui->label_ModText->setHidden(true);
 | 
			
		||||
	updateHiddenState();
 | 
			
		||||
    ui->setupUi(this);
 | 
			
		||||
    ui->label_ModDescription->setHidden(true);
 | 
			
		||||
    ui->label_ModText->setHidden(true);
 | 
			
		||||
    updateHiddenState();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
MCModInfoFrame::~MCModInfoFrame()
 | 
			
		||||
{
 | 
			
		||||
	delete ui;
 | 
			
		||||
    delete ui;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::updateHiddenState()
 | 
			
		||||
{
 | 
			
		||||
	if(ui->label_ModDescription->isHidden() && ui->label_ModText->isHidden())
 | 
			
		||||
	{
 | 
			
		||||
		setHidden(true);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		setHidden(false);
 | 
			
		||||
	}
 | 
			
		||||
    if(ui->label_ModDescription->isHidden() && ui->label_ModText->isHidden())
 | 
			
		||||
    {
 | 
			
		||||
        setHidden(true);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        setHidden(false);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::setModText(QString text)
 | 
			
		||||
{
 | 
			
		||||
	if(text.isEmpty())
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModText->setHidden(true);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModText->setText(text);
 | 
			
		||||
		ui->label_ModText->setHidden(false);
 | 
			
		||||
	}
 | 
			
		||||
	updateHiddenState();
 | 
			
		||||
    if(text.isEmpty())
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModText->setHidden(true);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModText->setText(text);
 | 
			
		||||
        ui->label_ModText->setHidden(false);
 | 
			
		||||
    }
 | 
			
		||||
    updateHiddenState();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::setModDescription(QString text)
 | 
			
		||||
{
 | 
			
		||||
	if(text.isEmpty())
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModDescription->setHidden(true);
 | 
			
		||||
		updateHiddenState();
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModDescription->setHidden(false);
 | 
			
		||||
		updateHiddenState();
 | 
			
		||||
	}
 | 
			
		||||
	ui->label_ModDescription->setToolTip("");
 | 
			
		||||
	QString intermediatetext = text.trimmed();
 | 
			
		||||
	bool prev(false);
 | 
			
		||||
	QChar rem('\n');
 | 
			
		||||
	QString finaltext;
 | 
			
		||||
	finaltext.reserve(intermediatetext.size());
 | 
			
		||||
	foreach(const QChar& c, intermediatetext)
 | 
			
		||||
	{
 | 
			
		||||
		if(c == rem && prev){
 | 
			
		||||
			continue;
 | 
			
		||||
		}
 | 
			
		||||
		prev = c == rem;
 | 
			
		||||
		finaltext += c;
 | 
			
		||||
	}
 | 
			
		||||
	QString labeltext;
 | 
			
		||||
	labeltext.reserve(300);
 | 
			
		||||
	if(finaltext.length() > 290)
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModDescription->setOpenExternalLinks(false);
 | 
			
		||||
		ui->label_ModDescription->setTextFormat(Qt::TextFormat::RichText);
 | 
			
		||||
		desc = text;
 | 
			
		||||
		labeltext.append("<html><body>" + finaltext.left(287) + "<a href=\"#mod_desc\">...</a></body></html>");
 | 
			
		||||
		QObject::connect(ui->label_ModDescription, &QLabel::linkActivated, this, &MCModInfoFrame::modDescEllipsisHandler);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		ui->label_ModDescription->setTextFormat(Qt::TextFormat::PlainText);
 | 
			
		||||
		labeltext.append(finaltext);
 | 
			
		||||
	}
 | 
			
		||||
	ui->label_ModDescription->setText(labeltext);
 | 
			
		||||
    if(text.isEmpty())
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModDescription->setHidden(true);
 | 
			
		||||
        updateHiddenState();
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModDescription->setHidden(false);
 | 
			
		||||
        updateHiddenState();
 | 
			
		||||
    }
 | 
			
		||||
    ui->label_ModDescription->setToolTip("");
 | 
			
		||||
    QString intermediatetext = text.trimmed();
 | 
			
		||||
    bool prev(false);
 | 
			
		||||
    QChar rem('\n');
 | 
			
		||||
    QString finaltext;
 | 
			
		||||
    finaltext.reserve(intermediatetext.size());
 | 
			
		||||
    foreach(const QChar& c, intermediatetext)
 | 
			
		||||
    {
 | 
			
		||||
        if(c == rem && prev){
 | 
			
		||||
            continue;
 | 
			
		||||
        }
 | 
			
		||||
        prev = c == rem;
 | 
			
		||||
        finaltext += c;
 | 
			
		||||
    }
 | 
			
		||||
    QString labeltext;
 | 
			
		||||
    labeltext.reserve(300);
 | 
			
		||||
    if(finaltext.length() > 290)
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModDescription->setOpenExternalLinks(false);
 | 
			
		||||
        ui->label_ModDescription->setTextFormat(Qt::TextFormat::RichText);
 | 
			
		||||
        desc = text;
 | 
			
		||||
        labeltext.append("<html><body>" + finaltext.left(287) + "<a href=\"#mod_desc\">...</a></body></html>");
 | 
			
		||||
        QObject::connect(ui->label_ModDescription, &QLabel::linkActivated, this, &MCModInfoFrame::modDescEllipsisHandler);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        ui->label_ModDescription->setTextFormat(Qt::TextFormat::PlainText);
 | 
			
		||||
        labeltext.append(finaltext);
 | 
			
		||||
    }
 | 
			
		||||
    ui->label_ModDescription->setText(labeltext);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::modDescEllipsisHandler(const QString &link)
 | 
			
		||||
{
 | 
			
		||||
	if(!currentBox)
 | 
			
		||||
	{
 | 
			
		||||
		currentBox = CustomMessageBox::selectable(this, QString(), desc);
 | 
			
		||||
		connect(currentBox, &QMessageBox::finished, this, &MCModInfoFrame::boxClosed);
 | 
			
		||||
		currentBox->show();
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		currentBox->setText(desc);
 | 
			
		||||
	}
 | 
			
		||||
    if(!currentBox)
 | 
			
		||||
    {
 | 
			
		||||
        currentBox = CustomMessageBox::selectable(this, QString(), desc);
 | 
			
		||||
        connect(currentBox, &QMessageBox::finished, this, &MCModInfoFrame::boxClosed);
 | 
			
		||||
        currentBox->show();
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        currentBox->setText(desc);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void MCModInfoFrame::boxClosed(int result)
 | 
			
		||||
{
 | 
			
		||||
	currentBox = nullptr;
 | 
			
		||||
    currentBox = nullptr;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -25,28 +25,28 @@ class MCModInfoFrame;
 | 
			
		||||
 | 
			
		||||
class MCModInfoFrame : public QFrame
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
 | 
			
		||||
public:
 | 
			
		||||
	explicit MCModInfoFrame(QWidget *parent = 0);
 | 
			
		||||
	~MCModInfoFrame();
 | 
			
		||||
    explicit MCModInfoFrame(QWidget *parent = 0);
 | 
			
		||||
    ~MCModInfoFrame();
 | 
			
		||||
 | 
			
		||||
	void setModText(QString text);
 | 
			
		||||
	void setModDescription(QString text);
 | 
			
		||||
    void setModText(QString text);
 | 
			
		||||
    void setModDescription(QString text);
 | 
			
		||||
 | 
			
		||||
	void updateWithMod(Mod &m);
 | 
			
		||||
	void clear();
 | 
			
		||||
    void updateWithMod(Mod &m);
 | 
			
		||||
    void clear();
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	void modDescEllipsisHandler(const QString& link );
 | 
			
		||||
	void boxClosed(int result);
 | 
			
		||||
    void modDescEllipsisHandler(const QString& link );
 | 
			
		||||
    void boxClosed(int result);
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	void updateHiddenState();
 | 
			
		||||
    void updateHiddenState();
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	Ui::MCModInfoFrame *ui;
 | 
			
		||||
	QString desc;
 | 
			
		||||
	class QMessageBox * currentBox = nullptr;
 | 
			
		||||
    Ui::MCModInfoFrame *ui;
 | 
			
		||||
    QString desc;
 | 
			
		||||
    class QMessageBox * currentBox = nullptr;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -21,46 +21,46 @@
 | 
			
		||||
#include <QRect>
 | 
			
		||||
 | 
			
		||||
ModListView::ModListView ( QWidget* parent )
 | 
			
		||||
	:QTreeView ( parent )
 | 
			
		||||
    :QTreeView ( parent )
 | 
			
		||||
{
 | 
			
		||||
	setAllColumnsShowFocus ( true );
 | 
			
		||||
	setExpandsOnDoubleClick ( false );
 | 
			
		||||
	setRootIsDecorated ( false );
 | 
			
		||||
	setSortingEnabled ( true );
 | 
			
		||||
	setAlternatingRowColors ( true );
 | 
			
		||||
	setSelectionMode ( QAbstractItemView::ExtendedSelection );
 | 
			
		||||
	setHeaderHidden ( false );
 | 
			
		||||
	setSelectionBehavior(QAbstractItemView::SelectRows);
 | 
			
		||||
	setVerticalScrollBarPolicy ( Qt::ScrollBarAlwaysOn );
 | 
			
		||||
	setHorizontalScrollBarPolicy ( Qt::ScrollBarAsNeeded );
 | 
			
		||||
	setDropIndicatorShown(true);
 | 
			
		||||
	setDragEnabled(true);
 | 
			
		||||
	setDragDropMode(QAbstractItemView::DropOnly);
 | 
			
		||||
	viewport()->setAcceptDrops(true);
 | 
			
		||||
    setAllColumnsShowFocus ( true );
 | 
			
		||||
    setExpandsOnDoubleClick ( false );
 | 
			
		||||
    setRootIsDecorated ( false );
 | 
			
		||||
    setSortingEnabled ( true );
 | 
			
		||||
    setAlternatingRowColors ( true );
 | 
			
		||||
    setSelectionMode ( QAbstractItemView::ExtendedSelection );
 | 
			
		||||
    setHeaderHidden ( false );
 | 
			
		||||
    setSelectionBehavior(QAbstractItemView::SelectRows);
 | 
			
		||||
    setVerticalScrollBarPolicy ( Qt::ScrollBarAlwaysOn );
 | 
			
		||||
    setHorizontalScrollBarPolicy ( Qt::ScrollBarAsNeeded );
 | 
			
		||||
    setDropIndicatorShown(true);
 | 
			
		||||
    setDragEnabled(true);
 | 
			
		||||
    setDragDropMode(QAbstractItemView::DropOnly);
 | 
			
		||||
    viewport()->setAcceptDrops(true);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ModListView::setModel ( QAbstractItemModel* model )
 | 
			
		||||
{
 | 
			
		||||
	QTreeView::setModel ( model );
 | 
			
		||||
	auto head = header();
 | 
			
		||||
	head->setStretchLastSection(false);
 | 
			
		||||
	// HACK: this is true for the checkbox column of mod lists
 | 
			
		||||
	auto string = model->headerData(0,head->orientation()).toString();
 | 
			
		||||
	if(head->count() < 1)
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	if(!string.size())
 | 
			
		||||
	{
 | 
			
		||||
		head->setSectionResizeMode(0, QHeaderView::ResizeToContents);
 | 
			
		||||
		head->setSectionResizeMode(1, QHeaderView::Stretch);
 | 
			
		||||
		for(int i = 2; i < head->count(); i++)
 | 
			
		||||
			head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		head->setSectionResizeMode(0, QHeaderView::Stretch);
 | 
			
		||||
		for(int i = 1; i < head->count(); i++)
 | 
			
		||||
			head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
	}
 | 
			
		||||
    QTreeView::setModel ( model );
 | 
			
		||||
    auto head = header();
 | 
			
		||||
    head->setStretchLastSection(false);
 | 
			
		||||
    // HACK: this is true for the checkbox column of mod lists
 | 
			
		||||
    auto string = model->headerData(0,head->orientation()).toString();
 | 
			
		||||
    if(head->count() < 1)
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    if(!string.size())
 | 
			
		||||
    {
 | 
			
		||||
        head->setSectionResizeMode(0, QHeaderView::ResizeToContents);
 | 
			
		||||
        head->setSectionResizeMode(1, QHeaderView::Stretch);
 | 
			
		||||
        for(int i = 2; i < head->count(); i++)
 | 
			
		||||
            head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        head->setSectionResizeMode(0, QHeaderView::Stretch);
 | 
			
		||||
        for(int i = 1; i < head->count(); i++)
 | 
			
		||||
            head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -20,8 +20,8 @@ class Mod;
 | 
			
		||||
 | 
			
		||||
class ModListView: public QTreeView
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit ModListView ( QWidget* parent = 0 );
 | 
			
		||||
	virtual void setModel ( QAbstractItemModel* model );
 | 
			
		||||
    explicit ModListView ( QWidget* parent = 0 );
 | 
			
		||||
    virtual void setModel ( QAbstractItemModel* model );
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -36,205 +36,205 @@
 | 
			
		||||
class PageEntryFilterModel : public QSortFilterProxyModel
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
	explicit PageEntryFilterModel(QObject *parent = 0) : QSortFilterProxyModel(parent)
 | 
			
		||||
	{
 | 
			
		||||
	}
 | 
			
		||||
    explicit PageEntryFilterModel(QObject *parent = 0) : QSortFilterProxyModel(parent)
 | 
			
		||||
    {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	bool filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const
 | 
			
		||||
	{
 | 
			
		||||
		const QString pattern = filterRegExp().pattern();
 | 
			
		||||
		const auto model = static_cast<PageModel *>(sourceModel());
 | 
			
		||||
		const auto page = model->pages().at(sourceRow);
 | 
			
		||||
		if (!page->shouldDisplay())
 | 
			
		||||
			return false;
 | 
			
		||||
		// Regular contents check, then check page-filter.
 | 
			
		||||
		return QSortFilterProxyModel::filterAcceptsRow(sourceRow, sourceParent);
 | 
			
		||||
	}
 | 
			
		||||
    bool filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const
 | 
			
		||||
    {
 | 
			
		||||
        const QString pattern = filterRegExp().pattern();
 | 
			
		||||
        const auto model = static_cast<PageModel *>(sourceModel());
 | 
			
		||||
        const auto page = model->pages().at(sourceRow);
 | 
			
		||||
        if (!page->shouldDisplay())
 | 
			
		||||
            return false;
 | 
			
		||||
        // Regular contents check, then check page-filter.
 | 
			
		||||
        return QSortFilterProxyModel::filterAcceptsRow(sourceRow, sourceParent);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
PageContainer::PageContainer(BasePageProvider *pageProvider, QString defaultId,
 | 
			
		||||
							 QWidget *parent)
 | 
			
		||||
	: QWidget(parent)
 | 
			
		||||
                             QWidget *parent)
 | 
			
		||||
    : QWidget(parent)
 | 
			
		||||
{
 | 
			
		||||
	createUI();
 | 
			
		||||
	m_model = new PageModel(this);
 | 
			
		||||
	m_proxyModel = new PageEntryFilterModel(this);
 | 
			
		||||
	int counter = 0;
 | 
			
		||||
	auto pages = pageProvider->getPages();
 | 
			
		||||
	for (auto page : pages)
 | 
			
		||||
	{
 | 
			
		||||
		page->stackIndex = m_pageStack->addWidget(dynamic_cast<QWidget *>(page));
 | 
			
		||||
		page->listIndex = counter;
 | 
			
		||||
		page->setParentContainer(this);
 | 
			
		||||
		counter++;
 | 
			
		||||
	}
 | 
			
		||||
	m_model->setPages(pages);
 | 
			
		||||
    createUI();
 | 
			
		||||
    m_model = new PageModel(this);
 | 
			
		||||
    m_proxyModel = new PageEntryFilterModel(this);
 | 
			
		||||
    int counter = 0;
 | 
			
		||||
    auto pages = pageProvider->getPages();
 | 
			
		||||
    for (auto page : pages)
 | 
			
		||||
    {
 | 
			
		||||
        page->stackIndex = m_pageStack->addWidget(dynamic_cast<QWidget *>(page));
 | 
			
		||||
        page->listIndex = counter;
 | 
			
		||||
        page->setParentContainer(this);
 | 
			
		||||
        counter++;
 | 
			
		||||
    }
 | 
			
		||||
    m_model->setPages(pages);
 | 
			
		||||
 | 
			
		||||
	m_proxyModel->setSourceModel(m_model);
 | 
			
		||||
	m_proxyModel->setFilterCaseSensitivity(Qt::CaseInsensitive);
 | 
			
		||||
    m_proxyModel->setSourceModel(m_model);
 | 
			
		||||
    m_proxyModel->setFilterCaseSensitivity(Qt::CaseInsensitive);
 | 
			
		||||
 | 
			
		||||
	m_pageList->setIconSize(QSize(pageIconSize, pageIconSize));
 | 
			
		||||
	m_pageList->setSelectionMode(QAbstractItemView::SingleSelection);
 | 
			
		||||
	m_pageList->setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
 | 
			
		||||
	m_pageList->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContents);
 | 
			
		||||
	m_pageList->setModel(m_proxyModel);
 | 
			
		||||
	connect(m_pageList->selectionModel(), SIGNAL(currentRowChanged(QModelIndex, QModelIndex)),
 | 
			
		||||
			this, SLOT(currentChanged(QModelIndex)));
 | 
			
		||||
	m_pageStack->setStackingMode(QStackedLayout::StackOne);
 | 
			
		||||
	m_pageList->setFocus();
 | 
			
		||||
	selectPage(defaultId);
 | 
			
		||||
    m_pageList->setIconSize(QSize(pageIconSize, pageIconSize));
 | 
			
		||||
    m_pageList->setSelectionMode(QAbstractItemView::SingleSelection);
 | 
			
		||||
    m_pageList->setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
 | 
			
		||||
    m_pageList->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContents);
 | 
			
		||||
    m_pageList->setModel(m_proxyModel);
 | 
			
		||||
    connect(m_pageList->selectionModel(), SIGNAL(currentRowChanged(QModelIndex, QModelIndex)),
 | 
			
		||||
            this, SLOT(currentChanged(QModelIndex)));
 | 
			
		||||
    m_pageStack->setStackingMode(QStackedLayout::StackOne);
 | 
			
		||||
    m_pageList->setFocus();
 | 
			
		||||
    selectPage(defaultId);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool PageContainer::selectPage(QString pageId)
 | 
			
		||||
{
 | 
			
		||||
	// now find what we want to have selected...
 | 
			
		||||
	auto page = m_model->findPageEntryById(pageId);
 | 
			
		||||
	QModelIndex index;
 | 
			
		||||
	if (page)
 | 
			
		||||
	{
 | 
			
		||||
		index = m_proxyModel->mapFromSource(m_model->index(page->listIndex));
 | 
			
		||||
	}
 | 
			
		||||
	if(!index.isValid())
 | 
			
		||||
	{
 | 
			
		||||
		index = m_proxyModel->index(0, 0);
 | 
			
		||||
	}
 | 
			
		||||
	if (index.isValid())
 | 
			
		||||
	{
 | 
			
		||||
		m_pageList->setCurrentIndex(index);
 | 
			
		||||
		return true;
 | 
			
		||||
	}
 | 
			
		||||
	return false;
 | 
			
		||||
    // now find what we want to have selected...
 | 
			
		||||
    auto page = m_model->findPageEntryById(pageId);
 | 
			
		||||
    QModelIndex index;
 | 
			
		||||
    if (page)
 | 
			
		||||
    {
 | 
			
		||||
        index = m_proxyModel->mapFromSource(m_model->index(page->listIndex));
 | 
			
		||||
    }
 | 
			
		||||
    if(!index.isValid())
 | 
			
		||||
    {
 | 
			
		||||
        index = m_proxyModel->index(0, 0);
 | 
			
		||||
    }
 | 
			
		||||
    if (index.isValid())
 | 
			
		||||
    {
 | 
			
		||||
        m_pageList->setCurrentIndex(index);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
    return false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::refreshContainer()
 | 
			
		||||
{
 | 
			
		||||
	m_proxyModel->invalidate();
 | 
			
		||||
	if(!m_currentPage->shouldDisplay())
 | 
			
		||||
	{
 | 
			
		||||
		auto index = m_proxyModel->index(0, 0);
 | 
			
		||||
		if(index.isValid())
 | 
			
		||||
		{
 | 
			
		||||
			m_pageList->setCurrentIndex(index);
 | 
			
		||||
		}
 | 
			
		||||
		else
 | 
			
		||||
		{
 | 
			
		||||
			// FIXME: unhandled corner case: what to do when there's no page to select?
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
    m_proxyModel->invalidate();
 | 
			
		||||
    if(!m_currentPage->shouldDisplay())
 | 
			
		||||
    {
 | 
			
		||||
        auto index = m_proxyModel->index(0, 0);
 | 
			
		||||
        if(index.isValid())
 | 
			
		||||
        {
 | 
			
		||||
            m_pageList->setCurrentIndex(index);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            // FIXME: unhandled corner case: what to do when there's no page to select?
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::createUI()
 | 
			
		||||
{
 | 
			
		||||
	m_pageStack = new QStackedLayout;
 | 
			
		||||
	m_pageList = new PageView;
 | 
			
		||||
	m_header = new QLabel();
 | 
			
		||||
	m_iconHeader = new IconLabel(this, QIcon(), QSize(24, 24));
 | 
			
		||||
    m_pageStack = new QStackedLayout;
 | 
			
		||||
    m_pageList = new PageView;
 | 
			
		||||
    m_header = new QLabel();
 | 
			
		||||
    m_iconHeader = new IconLabel(this, QIcon(), QSize(24, 24));
 | 
			
		||||
 | 
			
		||||
	QFont headerLabelFont = m_header->font();
 | 
			
		||||
	headerLabelFont.setBold(true);
 | 
			
		||||
	const int pointSize = headerLabelFont.pointSize();
 | 
			
		||||
	if (pointSize > 0)
 | 
			
		||||
		headerLabelFont.setPointSize(pointSize + 2);
 | 
			
		||||
	m_header->setFont(headerLabelFont);
 | 
			
		||||
    QFont headerLabelFont = m_header->font();
 | 
			
		||||
    headerLabelFont.setBold(true);
 | 
			
		||||
    const int pointSize = headerLabelFont.pointSize();
 | 
			
		||||
    if (pointSize > 0)
 | 
			
		||||
        headerLabelFont.setPointSize(pointSize + 2);
 | 
			
		||||
    m_header->setFont(headerLabelFont);
 | 
			
		||||
 | 
			
		||||
	QHBoxLayout *headerHLayout = new QHBoxLayout;
 | 
			
		||||
	const int leftMargin = MMC->style()->pixelMetric(QStyle::PM_LayoutLeftMargin);
 | 
			
		||||
	headerHLayout->addSpacerItem(
 | 
			
		||||
		new QSpacerItem(leftMargin, 0, QSizePolicy::Fixed, QSizePolicy::Ignored));
 | 
			
		||||
	headerHLayout->addWidget(m_header);
 | 
			
		||||
	headerHLayout->addSpacerItem(
 | 
			
		||||
		new QSpacerItem(0, 0, QSizePolicy::Expanding, QSizePolicy::Ignored));
 | 
			
		||||
	headerHLayout->addWidget(m_iconHeader);
 | 
			
		||||
	const int rightMargin = MMC->style()->pixelMetric(QStyle::PM_LayoutRightMargin);
 | 
			
		||||
	headerHLayout->addSpacerItem(
 | 
			
		||||
		new QSpacerItem(rightMargin, 0, QSizePolicy::Fixed, QSizePolicy::Ignored));
 | 
			
		||||
    QHBoxLayout *headerHLayout = new QHBoxLayout;
 | 
			
		||||
    const int leftMargin = MMC->style()->pixelMetric(QStyle::PM_LayoutLeftMargin);
 | 
			
		||||
    headerHLayout->addSpacerItem(
 | 
			
		||||
        new QSpacerItem(leftMargin, 0, QSizePolicy::Fixed, QSizePolicy::Ignored));
 | 
			
		||||
    headerHLayout->addWidget(m_header);
 | 
			
		||||
    headerHLayout->addSpacerItem(
 | 
			
		||||
        new QSpacerItem(0, 0, QSizePolicy::Expanding, QSizePolicy::Ignored));
 | 
			
		||||
    headerHLayout->addWidget(m_iconHeader);
 | 
			
		||||
    const int rightMargin = MMC->style()->pixelMetric(QStyle::PM_LayoutRightMargin);
 | 
			
		||||
    headerHLayout->addSpacerItem(
 | 
			
		||||
        new QSpacerItem(rightMargin, 0, QSizePolicy::Fixed, QSizePolicy::Ignored));
 | 
			
		||||
 | 
			
		||||
	m_pageStack->setMargin(0);
 | 
			
		||||
	m_pageStack->addWidget(new QWidget(this));
 | 
			
		||||
    m_pageStack->setMargin(0);
 | 
			
		||||
    m_pageStack->addWidget(new QWidget(this));
 | 
			
		||||
 | 
			
		||||
	m_layout = new QGridLayout;
 | 
			
		||||
	m_layout->addLayout(headerHLayout, 0, 1, 1, 1);
 | 
			
		||||
	m_layout->addWidget(m_pageList, 0, 0, 2, 1);
 | 
			
		||||
	m_layout->addLayout(m_pageStack, 1, 1, 1, 1);
 | 
			
		||||
	m_layout->setColumnStretch(1, 4);
 | 
			
		||||
	setLayout(m_layout);
 | 
			
		||||
    m_layout = new QGridLayout;
 | 
			
		||||
    m_layout->addLayout(headerHLayout, 0, 1, 1, 1);
 | 
			
		||||
    m_layout->addWidget(m_pageList, 0, 0, 2, 1);
 | 
			
		||||
    m_layout->addLayout(m_pageStack, 1, 1, 1, 1);
 | 
			
		||||
    m_layout->setColumnStretch(1, 4);
 | 
			
		||||
    setLayout(m_layout);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::addButtons(QWidget *buttons)
 | 
			
		||||
{
 | 
			
		||||
	m_layout->addWidget(buttons, 2, 0, 1, 2);
 | 
			
		||||
    m_layout->addWidget(buttons, 2, 0, 1, 2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::addButtons(QLayout *buttons)
 | 
			
		||||
{
 | 
			
		||||
	m_layout->addLayout(buttons, 2, 0, 1, 2);
 | 
			
		||||
    m_layout->addLayout(buttons, 2, 0, 1, 2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::showPage(int row)
 | 
			
		||||
{
 | 
			
		||||
	if (m_currentPage)
 | 
			
		||||
	{
 | 
			
		||||
		m_currentPage->closed();
 | 
			
		||||
	}
 | 
			
		||||
	if (row != -1)
 | 
			
		||||
	{
 | 
			
		||||
		m_currentPage = m_model->pages().at(row);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		m_currentPage = nullptr;
 | 
			
		||||
	}
 | 
			
		||||
	if (m_currentPage)
 | 
			
		||||
	{
 | 
			
		||||
		m_pageStack->setCurrentIndex(m_currentPage->stackIndex);
 | 
			
		||||
		m_header->setText(m_currentPage->displayName());
 | 
			
		||||
		m_iconHeader->setIcon(m_currentPage->icon());
 | 
			
		||||
		m_currentPage->opened();
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		m_pageStack->setCurrentIndex(0);
 | 
			
		||||
		m_header->setText(QString());
 | 
			
		||||
		m_iconHeader->setIcon(MMC->getThemedIcon("bug"));
 | 
			
		||||
	}
 | 
			
		||||
    if (m_currentPage)
 | 
			
		||||
    {
 | 
			
		||||
        m_currentPage->closed();
 | 
			
		||||
    }
 | 
			
		||||
    if (row != -1)
 | 
			
		||||
    {
 | 
			
		||||
        m_currentPage = m_model->pages().at(row);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        m_currentPage = nullptr;
 | 
			
		||||
    }
 | 
			
		||||
    if (m_currentPage)
 | 
			
		||||
    {
 | 
			
		||||
        m_pageStack->setCurrentIndex(m_currentPage->stackIndex);
 | 
			
		||||
        m_header->setText(m_currentPage->displayName());
 | 
			
		||||
        m_iconHeader->setIcon(m_currentPage->icon());
 | 
			
		||||
        m_currentPage->opened();
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        m_pageStack->setCurrentIndex(0);
 | 
			
		||||
        m_header->setText(QString());
 | 
			
		||||
        m_iconHeader->setIcon(MMC->getThemedIcon("bug"));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::help()
 | 
			
		||||
{
 | 
			
		||||
	if (m_currentPage)
 | 
			
		||||
	{
 | 
			
		||||
		QString pageId = m_currentPage->helpPage();
 | 
			
		||||
		if (pageId.isEmpty())
 | 
			
		||||
			return;
 | 
			
		||||
		DesktopServices::openUrl(QUrl("https://github.com/MultiMC/MultiMC5/wiki/" + pageId));
 | 
			
		||||
	}
 | 
			
		||||
    if (m_currentPage)
 | 
			
		||||
    {
 | 
			
		||||
        QString pageId = m_currentPage->helpPage();
 | 
			
		||||
        if (pageId.isEmpty())
 | 
			
		||||
            return;
 | 
			
		||||
        DesktopServices::openUrl(QUrl("https://github.com/MultiMC/MultiMC5/wiki/" + pageId));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void PageContainer::currentChanged(const QModelIndex ¤t)
 | 
			
		||||
{
 | 
			
		||||
	showPage(current.isValid() ? m_proxyModel->mapToSource(current).row() : -1);
 | 
			
		||||
    showPage(current.isValid() ? m_proxyModel->mapToSource(current).row() : -1);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool PageContainer::prepareToClose()
 | 
			
		||||
{
 | 
			
		||||
	if(!saveAll())
 | 
			
		||||
	{
 | 
			
		||||
		return false;
 | 
			
		||||
	}
 | 
			
		||||
	if (m_currentPage)
 | 
			
		||||
	{
 | 
			
		||||
		m_currentPage->closed();
 | 
			
		||||
	}
 | 
			
		||||
	return true;
 | 
			
		||||
    if(!saveAll())
 | 
			
		||||
    {
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
    if (m_currentPage)
 | 
			
		||||
    {
 | 
			
		||||
        m_currentPage->closed();
 | 
			
		||||
    }
 | 
			
		||||
    return true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool PageContainer::saveAll()
 | 
			
		||||
{
 | 
			
		||||
	for (auto page : m_model->pages())
 | 
			
		||||
	{
 | 
			
		||||
		if (!page->apply())
 | 
			
		||||
			return false;
 | 
			
		||||
	}
 | 
			
		||||
	return true;
 | 
			
		||||
    for (auto page : m_model->pages())
 | 
			
		||||
    {
 | 
			
		||||
        if (!page->apply())
 | 
			
		||||
            return false;
 | 
			
		||||
    }
 | 
			
		||||
    return true;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -33,57 +33,57 @@ class QGridLayout;
 | 
			
		||||
 | 
			
		||||
class PageContainer : public QWidget, public BasePageContainer
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit PageContainer(BasePageProvider *pageProvider, QString defaultId = QString(),
 | 
			
		||||
						QWidget *parent = 0);
 | 
			
		||||
	virtual ~PageContainer() {}
 | 
			
		||||
    explicit PageContainer(BasePageProvider *pageProvider, QString defaultId = QString(),
 | 
			
		||||
                        QWidget *parent = 0);
 | 
			
		||||
    virtual ~PageContainer() {}
 | 
			
		||||
 | 
			
		||||
	void addButtons(QWidget * buttons);
 | 
			
		||||
	void addButtons(QLayout * buttons);
 | 
			
		||||
	/*
 | 
			
		||||
	 * Save any unsaved state and prepare to be closed.
 | 
			
		||||
	 * @return true if everything can be saved, false if there is something that requires attention
 | 
			
		||||
	 */
 | 
			
		||||
	bool prepareToClose();
 | 
			
		||||
	bool saveAll();
 | 
			
		||||
    void addButtons(QWidget * buttons);
 | 
			
		||||
    void addButtons(QLayout * buttons);
 | 
			
		||||
    /*
 | 
			
		||||
     * Save any unsaved state and prepare to be closed.
 | 
			
		||||
     * @return true if everything can be saved, false if there is something that requires attention
 | 
			
		||||
     */
 | 
			
		||||
    bool prepareToClose();
 | 
			
		||||
    bool saveAll();
 | 
			
		||||
 | 
			
		||||
	/* request close - used by individual pages */
 | 
			
		||||
	bool requestClose() override
 | 
			
		||||
	{
 | 
			
		||||
		if(m_container)
 | 
			
		||||
		{
 | 
			
		||||
			return m_container->requestClose();
 | 
			
		||||
		}
 | 
			
		||||
		return false;
 | 
			
		||||
	}
 | 
			
		||||
    /* request close - used by individual pages */
 | 
			
		||||
    bool requestClose() override
 | 
			
		||||
    {
 | 
			
		||||
        if(m_container)
 | 
			
		||||
        {
 | 
			
		||||
            return m_container->requestClose();
 | 
			
		||||
        }
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	virtual bool selectPage(QString pageId) override;
 | 
			
		||||
    virtual bool selectPage(QString pageId) override;
 | 
			
		||||
 | 
			
		||||
	void refreshContainer() override;
 | 
			
		||||
	virtual void setParentContainer(BasePageContainer * container)
 | 
			
		||||
	{
 | 
			
		||||
		m_container = container;
 | 
			
		||||
	};
 | 
			
		||||
    void refreshContainer() override;
 | 
			
		||||
    virtual void setParentContainer(BasePageContainer * container)
 | 
			
		||||
    {
 | 
			
		||||
        m_container = container;
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	void createUI();
 | 
			
		||||
    void createUI();
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	void help();
 | 
			
		||||
    void help();
 | 
			
		||||
 | 
			
		||||
private slots:
 | 
			
		||||
	void currentChanged(const QModelIndex ¤t);
 | 
			
		||||
	void showPage(int row);
 | 
			
		||||
    void currentChanged(const QModelIndex ¤t);
 | 
			
		||||
    void showPage(int row);
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	BasePageContainer * m_container = nullptr;
 | 
			
		||||
	BasePage * m_currentPage = 0;
 | 
			
		||||
	QSortFilterProxyModel *m_proxyModel;
 | 
			
		||||
	PageModel *m_model;
 | 
			
		||||
	QStackedLayout *m_pageStack;
 | 
			
		||||
	QListView *m_pageList;
 | 
			
		||||
	QLabel *m_header;
 | 
			
		||||
	IconLabel *m_iconHeader;
 | 
			
		||||
	QGridLayout *m_layout;
 | 
			
		||||
    BasePageContainer * m_container = nullptr;
 | 
			
		||||
    BasePage * m_currentPage = 0;
 | 
			
		||||
    QSortFilterProxyModel *m_proxyModel;
 | 
			
		||||
    PageModel *m_model;
 | 
			
		||||
    QStackedLayout *m_pageStack;
 | 
			
		||||
    QListView *m_pageList;
 | 
			
		||||
    QLabel *m_header;
 | 
			
		||||
    IconLabel *m_iconHeader;
 | 
			
		||||
    QGridLayout *m_layout;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -26,98 +26,98 @@ const int pageIconSize = 24;
 | 
			
		||||
class PageViewDelegate : public QStyledItemDelegate
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
	PageViewDelegate(QObject *parent) : QStyledItemDelegate(parent)
 | 
			
		||||
	{
 | 
			
		||||
	}
 | 
			
		||||
	QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
 | 
			
		||||
	{
 | 
			
		||||
		QSize size = QStyledItemDelegate::sizeHint(option, index);
 | 
			
		||||
		size.setHeight(qMax(size.height(), 32));
 | 
			
		||||
		return size;
 | 
			
		||||
	}
 | 
			
		||||
    PageViewDelegate(QObject *parent) : QStyledItemDelegate(parent)
 | 
			
		||||
    {
 | 
			
		||||
    }
 | 
			
		||||
    QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
 | 
			
		||||
    {
 | 
			
		||||
        QSize size = QStyledItemDelegate::sizeHint(option, index);
 | 
			
		||||
        size.setHeight(qMax(size.height(), 32));
 | 
			
		||||
        return size;
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
class PageModel : public QAbstractListModel
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
	PageModel(QObject *parent = 0) : QAbstractListModel(parent)
 | 
			
		||||
	{
 | 
			
		||||
		QPixmap empty(pageIconSize, pageIconSize);
 | 
			
		||||
		empty.fill(Qt::transparent);
 | 
			
		||||
		m_emptyIcon = QIcon(empty);
 | 
			
		||||
	}
 | 
			
		||||
	virtual ~PageModel() {}
 | 
			
		||||
    PageModel(QObject *parent = 0) : QAbstractListModel(parent)
 | 
			
		||||
    {
 | 
			
		||||
        QPixmap empty(pageIconSize, pageIconSize);
 | 
			
		||||
        empty.fill(Qt::transparent);
 | 
			
		||||
        m_emptyIcon = QIcon(empty);
 | 
			
		||||
    }
 | 
			
		||||
    virtual ~PageModel() {}
 | 
			
		||||
 | 
			
		||||
	int rowCount(const QModelIndex &parent = QModelIndex()) const
 | 
			
		||||
	{
 | 
			
		||||
		return parent.isValid() ? 0 : m_pages.size();
 | 
			
		||||
	}
 | 
			
		||||
	QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const
 | 
			
		||||
	{
 | 
			
		||||
		switch (role)
 | 
			
		||||
		{
 | 
			
		||||
		case Qt::DisplayRole:
 | 
			
		||||
			return m_pages.at(index.row())->displayName();
 | 
			
		||||
		case Qt::DecorationRole:
 | 
			
		||||
		{
 | 
			
		||||
			QIcon icon = m_pages.at(index.row())->icon();
 | 
			
		||||
			if (icon.isNull())
 | 
			
		||||
				icon = m_emptyIcon;
 | 
			
		||||
			// HACK: fixes icon stretching on windows. TODO: report Qt bug for this
 | 
			
		||||
			return QIcon(icon.pixmap(QSize(48,48)));
 | 
			
		||||
		}
 | 
			
		||||
		}
 | 
			
		||||
		return QVariant();
 | 
			
		||||
	}
 | 
			
		||||
    int rowCount(const QModelIndex &parent = QModelIndex()) const
 | 
			
		||||
    {
 | 
			
		||||
        return parent.isValid() ? 0 : m_pages.size();
 | 
			
		||||
    }
 | 
			
		||||
    QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const
 | 
			
		||||
    {
 | 
			
		||||
        switch (role)
 | 
			
		||||
        {
 | 
			
		||||
        case Qt::DisplayRole:
 | 
			
		||||
            return m_pages.at(index.row())->displayName();
 | 
			
		||||
        case Qt::DecorationRole:
 | 
			
		||||
        {
 | 
			
		||||
            QIcon icon = m_pages.at(index.row())->icon();
 | 
			
		||||
            if (icon.isNull())
 | 
			
		||||
                icon = m_emptyIcon;
 | 
			
		||||
            // HACK: fixes icon stretching on windows. TODO: report Qt bug for this
 | 
			
		||||
            return QIcon(icon.pixmap(QSize(48,48)));
 | 
			
		||||
        }
 | 
			
		||||
        }
 | 
			
		||||
        return QVariant();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	void setPages(const QList<BasePage *> &pages)
 | 
			
		||||
	{
 | 
			
		||||
		beginResetModel();
 | 
			
		||||
		m_pages = pages;
 | 
			
		||||
		endResetModel();
 | 
			
		||||
	}
 | 
			
		||||
	const QList<BasePage *> &pages() const
 | 
			
		||||
	{
 | 
			
		||||
		return m_pages;
 | 
			
		||||
	}
 | 
			
		||||
    void setPages(const QList<BasePage *> &pages)
 | 
			
		||||
    {
 | 
			
		||||
        beginResetModel();
 | 
			
		||||
        m_pages = pages;
 | 
			
		||||
        endResetModel();
 | 
			
		||||
    }
 | 
			
		||||
    const QList<BasePage *> &pages() const
 | 
			
		||||
    {
 | 
			
		||||
        return m_pages;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	BasePage * findPageEntryById(QString id)
 | 
			
		||||
	{
 | 
			
		||||
		for(auto page: m_pages)
 | 
			
		||||
		{
 | 
			
		||||
			if (page->id() == id)
 | 
			
		||||
				return page;
 | 
			
		||||
		}
 | 
			
		||||
		return nullptr;
 | 
			
		||||
	}
 | 
			
		||||
    BasePage * findPageEntryById(QString id)
 | 
			
		||||
    {
 | 
			
		||||
        for(auto page: m_pages)
 | 
			
		||||
        {
 | 
			
		||||
            if (page->id() == id)
 | 
			
		||||
                return page;
 | 
			
		||||
        }
 | 
			
		||||
        return nullptr;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	QList<BasePage *> m_pages;
 | 
			
		||||
	QIcon m_emptyIcon;
 | 
			
		||||
    QList<BasePage *> m_pages;
 | 
			
		||||
    QIcon m_emptyIcon;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
class PageView : public QListView
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
	PageView(QWidget *parent = 0) : QListView(parent)
 | 
			
		||||
	{
 | 
			
		||||
		setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Expanding);
 | 
			
		||||
		setItemDelegate(new PageViewDelegate(this));
 | 
			
		||||
		setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
	}
 | 
			
		||||
    PageView(QWidget *parent = 0) : QListView(parent)
 | 
			
		||||
    {
 | 
			
		||||
        setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Expanding);
 | 
			
		||||
        setItemDelegate(new PageViewDelegate(this));
 | 
			
		||||
        setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	virtual QSize sizeHint() const
 | 
			
		||||
	{
 | 
			
		||||
		int width = sizeHintForColumn(0) + frameWidth() * 2 + 5;
 | 
			
		||||
		if (verticalScrollBar()->isVisible())
 | 
			
		||||
			width += verticalScrollBar()->width();
 | 
			
		||||
		return QSize(width, 100);
 | 
			
		||||
	}
 | 
			
		||||
    virtual QSize sizeHint() const
 | 
			
		||||
    {
 | 
			
		||||
        int width = sizeHintForColumn(0) + frameWidth() * 2 + 5;
 | 
			
		||||
        if (verticalScrollBar()->isVisible())
 | 
			
		||||
            width += verticalScrollBar()->width();
 | 
			
		||||
        return QSize(width, 100);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	virtual bool eventFilter(QObject *obj, QEvent *event)
 | 
			
		||||
	{
 | 
			
		||||
		if (obj == verticalScrollBar() &&
 | 
			
		||||
			(event->type() == QEvent::Show || event->type() == QEvent::Hide))
 | 
			
		||||
			updateGeometry();
 | 
			
		||||
		return QListView::eventFilter(obj, event);
 | 
			
		||||
	}
 | 
			
		||||
    virtual bool eventFilter(QObject *obj, QEvent *event)
 | 
			
		||||
    {
 | 
			
		||||
        if (obj == verticalScrollBar() &&
 | 
			
		||||
            (event->type() == QEvent::Show || event->type() == QEvent::Hide))
 | 
			
		||||
            updateGeometry();
 | 
			
		||||
        return QListView::eventFilter(obj, event);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -9,65 +9,65 @@
 | 
			
		||||
#include "tasks/Task.h"
 | 
			
		||||
 | 
			
		||||
ProgressWidget::ProgressWidget(QWidget *parent)
 | 
			
		||||
	: QWidget(parent)
 | 
			
		||||
    : QWidget(parent)
 | 
			
		||||
{
 | 
			
		||||
	m_label = new QLabel(this);
 | 
			
		||||
	m_label->setWordWrap(true);
 | 
			
		||||
	m_bar = new QProgressBar(this);
 | 
			
		||||
	m_bar->setMinimum(0);
 | 
			
		||||
	m_bar->setMaximum(100);
 | 
			
		||||
	QVBoxLayout *layout = new QVBoxLayout(this);
 | 
			
		||||
	layout->addWidget(m_label);
 | 
			
		||||
	layout->addWidget(m_bar);
 | 
			
		||||
	layout->addStretch();
 | 
			
		||||
	setLayout(layout);
 | 
			
		||||
    m_label = new QLabel(this);
 | 
			
		||||
    m_label->setWordWrap(true);
 | 
			
		||||
    m_bar = new QProgressBar(this);
 | 
			
		||||
    m_bar->setMinimum(0);
 | 
			
		||||
    m_bar->setMaximum(100);
 | 
			
		||||
    QVBoxLayout *layout = new QVBoxLayout(this);
 | 
			
		||||
    layout->addWidget(m_label);
 | 
			
		||||
    layout->addWidget(m_bar);
 | 
			
		||||
    layout->addStretch();
 | 
			
		||||
    setLayout(layout);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ProgressWidget::start(std::shared_ptr<Task> task)
 | 
			
		||||
{
 | 
			
		||||
	if (m_task)
 | 
			
		||||
	{
 | 
			
		||||
		disconnect(m_task.get(), 0, this, 0);
 | 
			
		||||
	}
 | 
			
		||||
	m_task = task;
 | 
			
		||||
	connect(m_task.get(), &Task::finished, this, &ProgressWidget::handleTaskFinish);
 | 
			
		||||
	connect(m_task.get(), &Task::status, this, &ProgressWidget::handleTaskStatus);
 | 
			
		||||
	connect(m_task.get(), &Task::progress, this, &ProgressWidget::handleTaskProgress);
 | 
			
		||||
	connect(m_task.get(), &Task::destroyed, this, &ProgressWidget::taskDestroyed);
 | 
			
		||||
	if (!m_task->isRunning())
 | 
			
		||||
	{
 | 
			
		||||
		QMetaObject::invokeMethod(m_task.get(), "start", Qt::QueuedConnection);
 | 
			
		||||
	}
 | 
			
		||||
    if (m_task)
 | 
			
		||||
    {
 | 
			
		||||
        disconnect(m_task.get(), 0, this, 0);
 | 
			
		||||
    }
 | 
			
		||||
    m_task = task;
 | 
			
		||||
    connect(m_task.get(), &Task::finished, this, &ProgressWidget::handleTaskFinish);
 | 
			
		||||
    connect(m_task.get(), &Task::status, this, &ProgressWidget::handleTaskStatus);
 | 
			
		||||
    connect(m_task.get(), &Task::progress, this, &ProgressWidget::handleTaskProgress);
 | 
			
		||||
    connect(m_task.get(), &Task::destroyed, this, &ProgressWidget::taskDestroyed);
 | 
			
		||||
    if (!m_task->isRunning())
 | 
			
		||||
    {
 | 
			
		||||
        QMetaObject::invokeMethod(m_task.get(), "start", Qt::QueuedConnection);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
bool ProgressWidget::exec(std::shared_ptr<Task> task)
 | 
			
		||||
{
 | 
			
		||||
	QEventLoop loop;
 | 
			
		||||
	connect(task.get(), &Task::finished, &loop, &QEventLoop::quit);
 | 
			
		||||
	start(task);
 | 
			
		||||
	if (task->isRunning())
 | 
			
		||||
	{
 | 
			
		||||
		loop.exec();
 | 
			
		||||
	}
 | 
			
		||||
	return task->wasSuccessful();
 | 
			
		||||
    QEventLoop loop;
 | 
			
		||||
    connect(task.get(), &Task::finished, &loop, &QEventLoop::quit);
 | 
			
		||||
    start(task);
 | 
			
		||||
    if (task->isRunning())
 | 
			
		||||
    {
 | 
			
		||||
        loop.exec();
 | 
			
		||||
    }
 | 
			
		||||
    return task->wasSuccessful();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ProgressWidget::handleTaskFinish()
 | 
			
		||||
{
 | 
			
		||||
	if (!m_task->wasSuccessful())
 | 
			
		||||
	{
 | 
			
		||||
		m_label->setText(m_task->failReason());
 | 
			
		||||
	}
 | 
			
		||||
    if (!m_task->wasSuccessful())
 | 
			
		||||
    {
 | 
			
		||||
        m_label->setText(m_task->failReason());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
void ProgressWidget::handleTaskStatus(const QString &status)
 | 
			
		||||
{
 | 
			
		||||
	m_label->setText(status);
 | 
			
		||||
    m_label->setText(status);
 | 
			
		||||
}
 | 
			
		||||
void ProgressWidget::handleTaskProgress(qint64 current, qint64 total)
 | 
			
		||||
{
 | 
			
		||||
	m_bar->setMaximum(total);
 | 
			
		||||
	m_bar->setValue(current);
 | 
			
		||||
    m_bar->setMaximum(total);
 | 
			
		||||
    m_bar->setValue(current);
 | 
			
		||||
}
 | 
			
		||||
void ProgressWidget::taskDestroyed()
 | 
			
		||||
{
 | 
			
		||||
	m_task = nullptr;
 | 
			
		||||
    m_task = nullptr;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -11,22 +11,22 @@ class QLabel;
 | 
			
		||||
 | 
			
		||||
class ProgressWidget : public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit ProgressWidget(QWidget *parent = nullptr);
 | 
			
		||||
    explicit ProgressWidget(QWidget *parent = nullptr);
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	void start(std::shared_ptr<Task> task);
 | 
			
		||||
	bool exec(std::shared_ptr<Task> task);
 | 
			
		||||
    void start(std::shared_ptr<Task> task);
 | 
			
		||||
    bool exec(std::shared_ptr<Task> task);
 | 
			
		||||
 | 
			
		||||
private slots:
 | 
			
		||||
	void handleTaskFinish();
 | 
			
		||||
	void handleTaskStatus(const QString &status);
 | 
			
		||||
	void handleTaskProgress(qint64 current, qint64 total);
 | 
			
		||||
	void taskDestroyed();
 | 
			
		||||
    void handleTaskFinish();
 | 
			
		||||
    void handleTaskStatus(const QString &status);
 | 
			
		||||
    void handleTaskProgress(qint64 current, qint64 total);
 | 
			
		||||
    void taskDestroyed();
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	QLabel *m_label;
 | 
			
		||||
	QProgressBar *m_bar;
 | 
			
		||||
	std::shared_ptr<Task> m_task;
 | 
			
		||||
    QLabel *m_label;
 | 
			
		||||
    QProgressBar *m_bar;
 | 
			
		||||
    std::shared_ptr<Task> m_task;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -15,80 +15,80 @@
 | 
			
		||||
 | 
			
		||||
class ClickableLabel : public QLabel
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	ClickableLabel(QWidget *parent) : QLabel(parent)
 | 
			
		||||
	{
 | 
			
		||||
		setCursor(Qt::PointingHandCursor);
 | 
			
		||||
	}
 | 
			
		||||
    ClickableLabel(QWidget *parent) : QLabel(parent)
 | 
			
		||||
    {
 | 
			
		||||
        setCursor(Qt::PointingHandCursor);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	~ClickableLabel(){};
 | 
			
		||||
    ~ClickableLabel(){};
 | 
			
		||||
 | 
			
		||||
signals:
 | 
			
		||||
	void clicked();
 | 
			
		||||
    void clicked();
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	void mousePressEvent(QMouseEvent *event)
 | 
			
		||||
	{
 | 
			
		||||
		emit clicked();
 | 
			
		||||
	}
 | 
			
		||||
    void mousePressEvent(QMouseEvent *event)
 | 
			
		||||
    {
 | 
			
		||||
        emit clicked();
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
class ClickableIconLabel : public IconLabel
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	ClickableIconLabel(QWidget *parent, QIcon icon, QSize size) : IconLabel(parent, icon, size)
 | 
			
		||||
	{
 | 
			
		||||
		setCursor(Qt::PointingHandCursor);
 | 
			
		||||
	}
 | 
			
		||||
    ClickableIconLabel(QWidget *parent, QIcon icon, QSize size) : IconLabel(parent, icon, size)
 | 
			
		||||
    {
 | 
			
		||||
        setCursor(Qt::PointingHandCursor);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	~ClickableIconLabel(){};
 | 
			
		||||
    ~ClickableIconLabel(){};
 | 
			
		||||
 | 
			
		||||
signals:
 | 
			
		||||
	void clicked();
 | 
			
		||||
    void clicked();
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	void mousePressEvent(QMouseEvent *event)
 | 
			
		||||
	{
 | 
			
		||||
		emit clicked();
 | 
			
		||||
	}
 | 
			
		||||
    void mousePressEvent(QMouseEvent *event)
 | 
			
		||||
    {
 | 
			
		||||
        emit clicked();
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
ServerStatus::ServerStatus(QWidget *parent, Qt::WindowFlags f) : QWidget(parent, f)
 | 
			
		||||
{
 | 
			
		||||
	layout = new QHBoxLayout(this);
 | 
			
		||||
	layout->setContentsMargins(0, 0, 0, 0);
 | 
			
		||||
	goodIcon = MMC->getThemedIcon("status-good");
 | 
			
		||||
	yellowIcon = MMC->getThemedIcon("status-yellow");
 | 
			
		||||
	badIcon = MMC->getThemedIcon("status-bad");
 | 
			
		||||
    layout = new QHBoxLayout(this);
 | 
			
		||||
    layout->setContentsMargins(0, 0, 0, 0);
 | 
			
		||||
    goodIcon = MMC->getThemedIcon("status-good");
 | 
			
		||||
    yellowIcon = MMC->getThemedIcon("status-yellow");
 | 
			
		||||
    badIcon = MMC->getThemedIcon("status-bad");
 | 
			
		||||
 | 
			
		||||
	addStatus("authserver.mojang.com", tr("Auth"));
 | 
			
		||||
	addLine();
 | 
			
		||||
	addStatus("sessionserver.mojang.com", tr("Session"));
 | 
			
		||||
	addLine();
 | 
			
		||||
	addStatus("textures.minecraft.net", tr("Skins"));
 | 
			
		||||
	addLine();
 | 
			
		||||
	addStatus("api.mojang.com", tr("API"));
 | 
			
		||||
    addStatus("authserver.mojang.com", tr("Auth"));
 | 
			
		||||
    addLine();
 | 
			
		||||
    addStatus("sessionserver.mojang.com", tr("Session"));
 | 
			
		||||
    addLine();
 | 
			
		||||
    addStatus("textures.minecraft.net", tr("Skins"));
 | 
			
		||||
    addLine();
 | 
			
		||||
    addStatus("api.mojang.com", tr("API"));
 | 
			
		||||
 | 
			
		||||
	m_statusRefresh = new QToolButton(this);
 | 
			
		||||
	m_statusRefresh->setCheckable(true);
 | 
			
		||||
	m_statusRefresh->setToolButtonStyle(Qt::ToolButtonIconOnly);
 | 
			
		||||
	m_statusRefresh->setIcon(MMC->getThemedIcon("refresh"));
 | 
			
		||||
	layout->addWidget(m_statusRefresh);
 | 
			
		||||
    m_statusRefresh = new QToolButton(this);
 | 
			
		||||
    m_statusRefresh->setCheckable(true);
 | 
			
		||||
    m_statusRefresh->setToolButtonStyle(Qt::ToolButtonIconOnly);
 | 
			
		||||
    m_statusRefresh->setIcon(MMC->getThemedIcon("refresh"));
 | 
			
		||||
    layout->addWidget(m_statusRefresh);
 | 
			
		||||
 | 
			
		||||
	setLayout(layout);
 | 
			
		||||
    setLayout(layout);
 | 
			
		||||
 | 
			
		||||
	// Start status checker
 | 
			
		||||
	m_statusChecker.reset(new StatusChecker());
 | 
			
		||||
	{
 | 
			
		||||
		auto reloader = m_statusChecker.get();
 | 
			
		||||
		connect(reloader, &StatusChecker::statusChanged, this, &ServerStatus::StatusChanged);
 | 
			
		||||
		connect(reloader, &StatusChecker::statusLoading, this, &ServerStatus::StatusReloading);
 | 
			
		||||
		connect(m_statusRefresh, &QAbstractButton::clicked, this, &ServerStatus::reloadStatus);
 | 
			
		||||
		m_statusChecker->startTimer(60000);
 | 
			
		||||
		reloadStatus();
 | 
			
		||||
	}
 | 
			
		||||
    // Start status checker
 | 
			
		||||
    m_statusChecker.reset(new StatusChecker());
 | 
			
		||||
    {
 | 
			
		||||
        auto reloader = m_statusChecker.get();
 | 
			
		||||
        connect(reloader, &StatusChecker::statusChanged, this, &ServerStatus::StatusChanged);
 | 
			
		||||
        connect(reloader, &StatusChecker::statusLoading, this, &ServerStatus::StatusReloading);
 | 
			
		||||
        connect(m_statusRefresh, &QAbstractButton::clicked, this, &ServerStatus::reloadStatus);
 | 
			
		||||
        m_statusChecker->startTimer(60000);
 | 
			
		||||
        reloadStatus();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
ServerStatus::~ServerStatus()
 | 
			
		||||
@@ -97,83 +97,83 @@ ServerStatus::~ServerStatus()
 | 
			
		||||
 | 
			
		||||
void ServerStatus::reloadStatus()
 | 
			
		||||
{
 | 
			
		||||
	m_statusChecker->reloadStatus();
 | 
			
		||||
    m_statusChecker->reloadStatus();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::addLine()
 | 
			
		||||
{
 | 
			
		||||
	layout->addWidget(new LineSeparator(this, Qt::Vertical));
 | 
			
		||||
    layout->addWidget(new LineSeparator(this, Qt::Vertical));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::addStatus(QString key, QString name)
 | 
			
		||||
{
 | 
			
		||||
	{
 | 
			
		||||
		auto label = new ClickableIconLabel(this, badIcon, QSize(16, 16));
 | 
			
		||||
		label->setToolTip(key);
 | 
			
		||||
		serverLabels[key] = label;
 | 
			
		||||
		layout->addWidget(label);
 | 
			
		||||
		connect(label,SIGNAL(clicked()),SLOT(clicked()));
 | 
			
		||||
	}
 | 
			
		||||
	{
 | 
			
		||||
		auto label = new ClickableLabel(this);
 | 
			
		||||
		label->setText(name);
 | 
			
		||||
		label->setToolTip(key);
 | 
			
		||||
		layout->addWidget(label);
 | 
			
		||||
		connect(label,SIGNAL(clicked()),SLOT(clicked()));
 | 
			
		||||
	}
 | 
			
		||||
    {
 | 
			
		||||
        auto label = new ClickableIconLabel(this, badIcon, QSize(16, 16));
 | 
			
		||||
        label->setToolTip(key);
 | 
			
		||||
        serverLabels[key] = label;
 | 
			
		||||
        layout->addWidget(label);
 | 
			
		||||
        connect(label,SIGNAL(clicked()),SLOT(clicked()));
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
        auto label = new ClickableLabel(this);
 | 
			
		||||
        label->setText(name);
 | 
			
		||||
        label->setToolTip(key);
 | 
			
		||||
        layout->addWidget(label);
 | 
			
		||||
        connect(label,SIGNAL(clicked()),SLOT(clicked()));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::clicked()
 | 
			
		||||
{
 | 
			
		||||
	DesktopServices::openUrl(QUrl("https://help.mojang.com/"));
 | 
			
		||||
    DesktopServices::openUrl(QUrl("https://help.mojang.com/"));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::setStatus(QString key, int value)
 | 
			
		||||
{
 | 
			
		||||
	if (!serverLabels.contains(key))
 | 
			
		||||
		return;
 | 
			
		||||
	IconLabel *label = serverLabels[key];
 | 
			
		||||
	switch(value)
 | 
			
		||||
	{
 | 
			
		||||
		case 0:
 | 
			
		||||
			label->setIcon(goodIcon);
 | 
			
		||||
			break;
 | 
			
		||||
		case 1:
 | 
			
		||||
			label->setIcon(yellowIcon);
 | 
			
		||||
			break;
 | 
			
		||||
		default:
 | 
			
		||||
		case 2:
 | 
			
		||||
			label->setIcon(badIcon);
 | 
			
		||||
			break;
 | 
			
		||||
	}
 | 
			
		||||
    if (!serverLabels.contains(key))
 | 
			
		||||
        return;
 | 
			
		||||
    IconLabel *label = serverLabels[key];
 | 
			
		||||
    switch(value)
 | 
			
		||||
    {
 | 
			
		||||
        case 0:
 | 
			
		||||
            label->setIcon(goodIcon);
 | 
			
		||||
            break;
 | 
			
		||||
        case 1:
 | 
			
		||||
            label->setIcon(yellowIcon);
 | 
			
		||||
            break;
 | 
			
		||||
        default:
 | 
			
		||||
        case 2:
 | 
			
		||||
            label->setIcon(badIcon);
 | 
			
		||||
            break;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::StatusChanged(const QMap<QString, QString> statusEntries)
 | 
			
		||||
{
 | 
			
		||||
	auto convertStatus = [&](QString status)->int
 | 
			
		||||
	{
 | 
			
		||||
		if (status == "green")
 | 
			
		||||
			return 0;
 | 
			
		||||
		else if (status == "yellow")
 | 
			
		||||
			return 1;
 | 
			
		||||
		else if (status == "red")
 | 
			
		||||
			return 2;
 | 
			
		||||
		return 2;
 | 
			
		||||
	}
 | 
			
		||||
	;
 | 
			
		||||
	auto iter = statusEntries.begin();
 | 
			
		||||
	while (iter != statusEntries.end())
 | 
			
		||||
	{
 | 
			
		||||
		QString key = iter.key();
 | 
			
		||||
		auto value = convertStatus(iter.value());
 | 
			
		||||
		setStatus(key, value);
 | 
			
		||||
		iter++;
 | 
			
		||||
	}
 | 
			
		||||
    auto convertStatus = [&](QString status)->int
 | 
			
		||||
    {
 | 
			
		||||
        if (status == "green")
 | 
			
		||||
            return 0;
 | 
			
		||||
        else if (status == "yellow")
 | 
			
		||||
            return 1;
 | 
			
		||||
        else if (status == "red")
 | 
			
		||||
            return 2;
 | 
			
		||||
        return 2;
 | 
			
		||||
    }
 | 
			
		||||
    ;
 | 
			
		||||
    auto iter = statusEntries.begin();
 | 
			
		||||
    while (iter != statusEntries.end())
 | 
			
		||||
    {
 | 
			
		||||
        QString key = iter.key();
 | 
			
		||||
        auto value = convertStatus(iter.value());
 | 
			
		||||
        setStatus(key, value);
 | 
			
		||||
        iter++;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ServerStatus::StatusReloading(bool is_reloading)
 | 
			
		||||
{
 | 
			
		||||
	m_statusRefresh->setChecked(is_reloading);
 | 
			
		||||
    m_statusRefresh->setChecked(is_reloading);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#include "ServerStatus.moc"
 | 
			
		||||
 
 | 
			
		||||
@@ -12,29 +12,29 @@ class StatusChecker;
 | 
			
		||||
 | 
			
		||||
class ServerStatus: public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit ServerStatus(QWidget *parent = nullptr, Qt::WindowFlags f = 0);
 | 
			
		||||
	virtual ~ServerStatus();
 | 
			
		||||
    explicit ServerStatus(QWidget *parent = nullptr, Qt::WindowFlags f = 0);
 | 
			
		||||
    virtual ~ServerStatus();
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	void reloadStatus();
 | 
			
		||||
	void StatusChanged(const QMap<QString, QString> statuses);
 | 
			
		||||
	void StatusReloading(bool is_reloading);
 | 
			
		||||
    void reloadStatus();
 | 
			
		||||
    void StatusChanged(const QMap<QString, QString> statuses);
 | 
			
		||||
    void StatusReloading(bool is_reloading);
 | 
			
		||||
 | 
			
		||||
private slots:
 | 
			
		||||
	void clicked();
 | 
			
		||||
    void clicked();
 | 
			
		||||
 | 
			
		||||
private: /* methods */
 | 
			
		||||
	void addLine();
 | 
			
		||||
	void addStatus(QString key, QString name);
 | 
			
		||||
	void setStatus(QString key, int value);
 | 
			
		||||
    void addLine();
 | 
			
		||||
    void addStatus(QString key, QString name);
 | 
			
		||||
    void setStatus(QString key, int value);
 | 
			
		||||
private: /* data */
 | 
			
		||||
	QHBoxLayout * layout = nullptr;
 | 
			
		||||
	QToolButton *m_statusRefresh = nullptr;
 | 
			
		||||
	QMap<QString, IconLabel *> serverLabels;
 | 
			
		||||
	QIcon goodIcon;
 | 
			
		||||
	QIcon yellowIcon;
 | 
			
		||||
	QIcon badIcon;
 | 
			
		||||
	std::shared_ptr<StatusChecker> m_statusChecker;
 | 
			
		||||
    QHBoxLayout * layout = nullptr;
 | 
			
		||||
    QToolButton *m_statusRefresh = nullptr;
 | 
			
		||||
    QMap<QString, IconLabel *> serverLabels;
 | 
			
		||||
    QIcon goodIcon;
 | 
			
		||||
    QIcon yellowIcon;
 | 
			
		||||
    QIcon badIcon;
 | 
			
		||||
    std::shared_ptr<StatusChecker> m_statusChecker;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -22,113 +22,113 @@
 | 
			
		||||
#include "Common.h"
 | 
			
		||||
 | 
			
		||||
VersionListView::VersionListView(QWidget *parent)
 | 
			
		||||
	:QTreeView ( parent )
 | 
			
		||||
    :QTreeView ( parent )
 | 
			
		||||
{
 | 
			
		||||
	m_emptyString = tr("No versions are currently available.");
 | 
			
		||||
    m_emptyString = tr("No versions are currently available.");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::rowsInserted(const QModelIndex &parent, int start, int end)
 | 
			
		||||
{
 | 
			
		||||
	if(!m_itemCount)
 | 
			
		||||
		viewport()->update();
 | 
			
		||||
	m_itemCount += end-start+1;
 | 
			
		||||
	QTreeView::rowsInserted(parent, start, end);
 | 
			
		||||
    if(!m_itemCount)
 | 
			
		||||
        viewport()->update();
 | 
			
		||||
    m_itemCount += end-start+1;
 | 
			
		||||
    QTreeView::rowsInserted(parent, start, end);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
void VersionListView::rowsAboutToBeRemoved(const QModelIndex &parent, int start, int end)
 | 
			
		||||
{
 | 
			
		||||
	m_itemCount -= end-start+1;
 | 
			
		||||
	if(!m_itemCount)
 | 
			
		||||
		viewport()->update();
 | 
			
		||||
	QTreeView::rowsInserted(parent, start, end);
 | 
			
		||||
    m_itemCount -= end-start+1;
 | 
			
		||||
    if(!m_itemCount)
 | 
			
		||||
        viewport()->update();
 | 
			
		||||
    QTreeView::rowsInserted(parent, start, end);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::setModel(QAbstractItemModel *model)
 | 
			
		||||
{
 | 
			
		||||
	m_itemCount = model->rowCount();
 | 
			
		||||
	if(!m_itemCount)
 | 
			
		||||
		viewport()->update();
 | 
			
		||||
	QTreeView::setModel(model);
 | 
			
		||||
    m_itemCount = model->rowCount();
 | 
			
		||||
    if(!m_itemCount)
 | 
			
		||||
        viewport()->update();
 | 
			
		||||
    QTreeView::setModel(model);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::reset()
 | 
			
		||||
{
 | 
			
		||||
	if(model())
 | 
			
		||||
	{
 | 
			
		||||
		m_itemCount = model()->rowCount();
 | 
			
		||||
	}
 | 
			
		||||
	viewport()->update();
 | 
			
		||||
	QTreeView::reset();
 | 
			
		||||
    if(model())
 | 
			
		||||
    {
 | 
			
		||||
        m_itemCount = model()->rowCount();
 | 
			
		||||
    }
 | 
			
		||||
    viewport()->update();
 | 
			
		||||
    QTreeView::reset();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::setEmptyString(QString emptyString)
 | 
			
		||||
{
 | 
			
		||||
	m_emptyString = emptyString;
 | 
			
		||||
	updateEmptyViewPort();
 | 
			
		||||
    m_emptyString = emptyString;
 | 
			
		||||
    updateEmptyViewPort();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::setEmptyErrorString(QString emptyErrorString)
 | 
			
		||||
{
 | 
			
		||||
	m_emptyErrorString = emptyErrorString;
 | 
			
		||||
	updateEmptyViewPort();
 | 
			
		||||
    m_emptyErrorString = emptyErrorString;
 | 
			
		||||
    updateEmptyViewPort();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::setEmptyMode(VersionListView::EmptyMode mode)
 | 
			
		||||
{
 | 
			
		||||
	m_emptyMode = mode;
 | 
			
		||||
	updateEmptyViewPort();
 | 
			
		||||
    m_emptyMode = mode;
 | 
			
		||||
    updateEmptyViewPort();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::updateEmptyViewPort()
 | 
			
		||||
{
 | 
			
		||||
	if(!m_itemCount)
 | 
			
		||||
	{
 | 
			
		||||
		viewport()->update();
 | 
			
		||||
	}
 | 
			
		||||
    if(!m_itemCount)
 | 
			
		||||
    {
 | 
			
		||||
        viewport()->update();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::paintEvent(QPaintEvent *event)
 | 
			
		||||
{
 | 
			
		||||
	if(m_itemCount)
 | 
			
		||||
	{
 | 
			
		||||
		QTreeView::paintEvent(event);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		paintInfoLabel(event);
 | 
			
		||||
	}
 | 
			
		||||
    if(m_itemCount)
 | 
			
		||||
    {
 | 
			
		||||
        QTreeView::paintEvent(event);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        paintInfoLabel(event);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionListView::paintInfoLabel(QPaintEvent *event)
 | 
			
		||||
{
 | 
			
		||||
	QString emptyString;
 | 
			
		||||
	switch(m_emptyMode)
 | 
			
		||||
	{
 | 
			
		||||
		case VersionListView::Empty:
 | 
			
		||||
			return;
 | 
			
		||||
		case VersionListView::String:
 | 
			
		||||
			emptyString = m_emptyString;
 | 
			
		||||
			break;
 | 
			
		||||
		case VersionListView::ErrorString:
 | 
			
		||||
			emptyString = m_emptyErrorString;
 | 
			
		||||
			break;
 | 
			
		||||
	}
 | 
			
		||||
    QString emptyString;
 | 
			
		||||
    switch(m_emptyMode)
 | 
			
		||||
    {
 | 
			
		||||
        case VersionListView::Empty:
 | 
			
		||||
            return;
 | 
			
		||||
        case VersionListView::String:
 | 
			
		||||
            emptyString = m_emptyString;
 | 
			
		||||
            break;
 | 
			
		||||
        case VersionListView::ErrorString:
 | 
			
		||||
            emptyString = m_emptyErrorString;
 | 
			
		||||
            break;
 | 
			
		||||
    }
 | 
			
		||||
    //calculate the rect for the overlay
 | 
			
		||||
    QPainter painter(viewport());
 | 
			
		||||
    painter.setRenderHint(QPainter::Antialiasing, true);
 | 
			
		||||
	QFont font("sans", 20);
 | 
			
		||||
    QFont font("sans", 20);
 | 
			
		||||
    font.setBold(true);
 | 
			
		||||
	
 | 
			
		||||
	QRect bounds = viewport()->geometry();
 | 
			
		||||
	bounds.moveTop(0);
 | 
			
		||||
	QTextLayout layout(emptyString, font);
 | 
			
		||||
	qreal height = 0.0;
 | 
			
		||||
	qreal widthUsed = 0.0;
 | 
			
		||||
	QStringList lines = viewItemTextLayout(layout, bounds.width() - 20, height, widthUsed);
 | 
			
		||||
	QRect rect (0,0, widthUsed, height);
 | 
			
		||||
	rect.setWidth(rect.width()+20);
 | 
			
		||||
	rect.setHeight(rect.height()+20);
 | 
			
		||||
    
 | 
			
		||||
    QRect bounds = viewport()->geometry();
 | 
			
		||||
    bounds.moveTop(0);
 | 
			
		||||
    QTextLayout layout(emptyString, font);
 | 
			
		||||
    qreal height = 0.0;
 | 
			
		||||
    qreal widthUsed = 0.0;
 | 
			
		||||
    QStringList lines = viewItemTextLayout(layout, bounds.width() - 20, height, widthUsed);
 | 
			
		||||
    QRect rect (0,0, widthUsed, height);
 | 
			
		||||
    rect.setWidth(rect.width()+20);
 | 
			
		||||
    rect.setHeight(rect.height()+20);
 | 
			
		||||
    rect.moveCenter(bounds.center());
 | 
			
		||||
    //check if we are allowed to draw in our area
 | 
			
		||||
    if (!event->rect().intersects(rect)) {
 | 
			
		||||
@@ -137,7 +137,7 @@ void VersionListView::paintInfoLabel(QPaintEvent *event)
 | 
			
		||||
    //draw the letter of the topmost item semitransparent in the middle
 | 
			
		||||
    QColor background = QApplication::palette().color(QPalette::Foreground);
 | 
			
		||||
    QColor foreground = QApplication::palette().color(QPalette::Base);
 | 
			
		||||
	/*
 | 
			
		||||
    /*
 | 
			
		||||
    background.setAlpha(128 - scrollFade);
 | 
			
		||||
    foreground.setAlpha(128 - scrollFade);
 | 
			
		||||
    */
 | 
			
		||||
@@ -148,29 +148,29 @@ void VersionListView::paintInfoLabel(QPaintEvent *event)
 | 
			
		||||
    painter.setPen(foreground);
 | 
			
		||||
    painter.setFont(font);
 | 
			
		||||
    painter.drawText(rect, Qt::AlignCenter, lines.join("\n"));
 | 
			
		||||
	
 | 
			
		||||
    
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
void ModListView::setModel ( QAbstractItemModel* model )
 | 
			
		||||
{
 | 
			
		||||
	QTreeView::setModel ( model );
 | 
			
		||||
	auto head = header();
 | 
			
		||||
	head->setStretchLastSection(false);
 | 
			
		||||
	// HACK: this is true for the checkbox column of mod lists
 | 
			
		||||
	auto string = model->headerData(0,head->orientation()).toString();
 | 
			
		||||
	if(!string.size())
 | 
			
		||||
	{
 | 
			
		||||
		head->setSectionResizeMode(0, QHeaderView::ResizeToContents);
 | 
			
		||||
		head->setSectionResizeMode(1, QHeaderView::Stretch);
 | 
			
		||||
		for(int i = 2; i < head->count(); i++)
 | 
			
		||||
			head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		head->setSectionResizeMode(0, QHeaderView::Stretch);
 | 
			
		||||
		for(int i = 1; i < head->count(); i++)
 | 
			
		||||
			head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
	}
 | 
			
		||||
    QTreeView::setModel ( model );
 | 
			
		||||
    auto head = header();
 | 
			
		||||
    head->setStretchLastSection(false);
 | 
			
		||||
    // HACK: this is true for the checkbox column of mod lists
 | 
			
		||||
    auto string = model->headerData(0,head->orientation()).toString();
 | 
			
		||||
    if(!string.size())
 | 
			
		||||
    {
 | 
			
		||||
        head->setSectionResizeMode(0, QHeaderView::ResizeToContents);
 | 
			
		||||
        head->setSectionResizeMode(1, QHeaderView::Stretch);
 | 
			
		||||
        for(int i = 2; i < head->count(); i++)
 | 
			
		||||
            head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        head->setSectionResizeMode(0, QHeaderView::Stretch);
 | 
			
		||||
        for(int i = 1; i < head->count(); i++)
 | 
			
		||||
            head->setSectionResizeMode(i, QHeaderView::ResizeToContents);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
*/
 | 
			
		||||
 
 | 
			
		||||
@@ -20,38 +20,38 @@ class Mod;
 | 
			
		||||
 | 
			
		||||
class VersionListView : public QTreeView
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
 | 
			
		||||
	explicit VersionListView(QWidget *parent = 0);
 | 
			
		||||
	virtual void paintEvent(QPaintEvent *event) override;
 | 
			
		||||
	virtual void setModel(QAbstractItemModel* model) override;
 | 
			
		||||
    explicit VersionListView(QWidget *parent = 0);
 | 
			
		||||
    virtual void paintEvent(QPaintEvent *event) override;
 | 
			
		||||
    virtual void setModel(QAbstractItemModel* model) override;
 | 
			
		||||
 | 
			
		||||
	enum EmptyMode
 | 
			
		||||
	{
 | 
			
		||||
		Empty,
 | 
			
		||||
		String,
 | 
			
		||||
		ErrorString
 | 
			
		||||
	};
 | 
			
		||||
    enum EmptyMode
 | 
			
		||||
    {
 | 
			
		||||
        Empty,
 | 
			
		||||
        String,
 | 
			
		||||
        ErrorString
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
	void setEmptyString(QString emptyString);
 | 
			
		||||
	void setEmptyErrorString(QString emptyErrorString);
 | 
			
		||||
	void setEmptyMode(EmptyMode mode);
 | 
			
		||||
    void setEmptyString(QString emptyString);
 | 
			
		||||
    void setEmptyErrorString(QString emptyErrorString);
 | 
			
		||||
    void setEmptyMode(EmptyMode mode);
 | 
			
		||||
 | 
			
		||||
public slots:
 | 
			
		||||
	virtual void reset() override;
 | 
			
		||||
    virtual void reset() override;
 | 
			
		||||
 | 
			
		||||
protected slots:
 | 
			
		||||
	virtual void rowsAboutToBeRemoved(const QModelIndex & parent, int start, int end) override;
 | 
			
		||||
	virtual void rowsInserted(const QModelIndex &parent, int start, int end) override;
 | 
			
		||||
    virtual void rowsAboutToBeRemoved(const QModelIndex & parent, int start, int end) override;
 | 
			
		||||
    virtual void rowsInserted(const QModelIndex &parent, int start, int end) override;
 | 
			
		||||
 | 
			
		||||
private: /* methods */
 | 
			
		||||
	void paintInfoLabel(QPaintEvent *event);
 | 
			
		||||
	void updateEmptyViewPort();
 | 
			
		||||
    void paintInfoLabel(QPaintEvent *event);
 | 
			
		||||
    void updateEmptyViewPort();
 | 
			
		||||
 | 
			
		||||
private: /* variables */
 | 
			
		||||
	int m_itemCount = 0;
 | 
			
		||||
	QString m_emptyString;
 | 
			
		||||
	QString m_emptyErrorString;
 | 
			
		||||
	EmptyMode m_emptyMode = Empty;
 | 
			
		||||
    int m_itemCount = 0;
 | 
			
		||||
    QString m_emptyString;
 | 
			
		||||
    QString m_emptyErrorString;
 | 
			
		||||
    EmptyMode m_emptyMode = Empty;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -7,50 +7,50 @@
 | 
			
		||||
#include <dialogs/CustomMessageBox.h>
 | 
			
		||||
 | 
			
		||||
VersionSelectWidget::VersionSelectWidget(QWidget* parent)
 | 
			
		||||
	: QWidget(parent)
 | 
			
		||||
    : QWidget(parent)
 | 
			
		||||
{
 | 
			
		||||
	setObjectName(QStringLiteral("VersionSelectWidget"));
 | 
			
		||||
	verticalLayout = new QVBoxLayout(this);
 | 
			
		||||
	verticalLayout->setObjectName(QStringLiteral("verticalLayout"));
 | 
			
		||||
	verticalLayout->setContentsMargins(0, 0, 0, 0);
 | 
			
		||||
    setObjectName(QStringLiteral("VersionSelectWidget"));
 | 
			
		||||
    verticalLayout = new QVBoxLayout(this);
 | 
			
		||||
    verticalLayout->setObjectName(QStringLiteral("verticalLayout"));
 | 
			
		||||
    verticalLayout->setContentsMargins(0, 0, 0, 0);
 | 
			
		||||
 | 
			
		||||
	m_proxyModel = new VersionProxyModel(this);
 | 
			
		||||
    m_proxyModel = new VersionProxyModel(this);
 | 
			
		||||
 | 
			
		||||
	listView = new VersionListView(this);
 | 
			
		||||
	listView->setObjectName(QStringLiteral("listView"));
 | 
			
		||||
	listView->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
	listView->setAlternatingRowColors(true);
 | 
			
		||||
	listView->setRootIsDecorated(false);
 | 
			
		||||
	listView->setItemsExpandable(false);
 | 
			
		||||
	listView->setWordWrap(true);
 | 
			
		||||
	listView->header()->setCascadingSectionResizes(true);
 | 
			
		||||
	listView->header()->setStretchLastSection(false);
 | 
			
		||||
	listView->setModel(m_proxyModel);
 | 
			
		||||
	verticalLayout->addWidget(listView);
 | 
			
		||||
    listView = new VersionListView(this);
 | 
			
		||||
    listView->setObjectName(QStringLiteral("listView"));
 | 
			
		||||
    listView->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
 | 
			
		||||
    listView->setAlternatingRowColors(true);
 | 
			
		||||
    listView->setRootIsDecorated(false);
 | 
			
		||||
    listView->setItemsExpandable(false);
 | 
			
		||||
    listView->setWordWrap(true);
 | 
			
		||||
    listView->header()->setCascadingSectionResizes(true);
 | 
			
		||||
    listView->header()->setStretchLastSection(false);
 | 
			
		||||
    listView->setModel(m_proxyModel);
 | 
			
		||||
    verticalLayout->addWidget(listView);
 | 
			
		||||
 | 
			
		||||
	sneakyProgressBar = new QProgressBar(this);
 | 
			
		||||
	sneakyProgressBar->setObjectName(QStringLiteral("sneakyProgressBar"));
 | 
			
		||||
	sneakyProgressBar->setFormat(QStringLiteral("%p%"));
 | 
			
		||||
	verticalLayout->addWidget(sneakyProgressBar);
 | 
			
		||||
	sneakyProgressBar->setHidden(true);
 | 
			
		||||
	connect(listView->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &VersionSelectWidget::currentRowChanged);
 | 
			
		||||
    sneakyProgressBar = new QProgressBar(this);
 | 
			
		||||
    sneakyProgressBar->setObjectName(QStringLiteral("sneakyProgressBar"));
 | 
			
		||||
    sneakyProgressBar->setFormat(QStringLiteral("%p%"));
 | 
			
		||||
    verticalLayout->addWidget(sneakyProgressBar);
 | 
			
		||||
    sneakyProgressBar->setHidden(true);
 | 
			
		||||
    connect(listView->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &VersionSelectWidget::currentRowChanged);
 | 
			
		||||
 | 
			
		||||
	QMetaObject::connectSlotsByName(this);
 | 
			
		||||
    QMetaObject::connectSlotsByName(this);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setCurrentVersion(const QString& version)
 | 
			
		||||
{
 | 
			
		||||
	m_currentVersion = version;
 | 
			
		||||
    m_currentVersion = version;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setEmptyString(QString emptyString)
 | 
			
		||||
{
 | 
			
		||||
	listView->setEmptyString(emptyString);
 | 
			
		||||
    listView->setEmptyString(emptyString);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setEmptyErrorString(QString emptyErrorString)
 | 
			
		||||
{
 | 
			
		||||
	listView->setEmptyErrorString(emptyErrorString);
 | 
			
		||||
    listView->setEmptyErrorString(emptyErrorString);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
VersionSelectWidget::~VersionSelectWidget()
 | 
			
		||||
@@ -59,143 +59,143 @@ VersionSelectWidget::~VersionSelectWidget()
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setResizeOn(int column)
 | 
			
		||||
{
 | 
			
		||||
	listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::ResizeToContents);
 | 
			
		||||
	resizeOnColumn = column;
 | 
			
		||||
	listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::Stretch);
 | 
			
		||||
    listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::ResizeToContents);
 | 
			
		||||
    resizeOnColumn = column;
 | 
			
		||||
    listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::Stretch);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::initialize(BaseVersionList *vlist)
 | 
			
		||||
{
 | 
			
		||||
	m_vlist = vlist;
 | 
			
		||||
	m_proxyModel->setSourceModel(vlist);
 | 
			
		||||
	listView->header()->setSectionResizeMode(QHeaderView::ResizeToContents);
 | 
			
		||||
	listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::Stretch);
 | 
			
		||||
    m_vlist = vlist;
 | 
			
		||||
    m_proxyModel->setSourceModel(vlist);
 | 
			
		||||
    listView->header()->setSectionResizeMode(QHeaderView::ResizeToContents);
 | 
			
		||||
    listView->header()->setSectionResizeMode(resizeOnColumn, QHeaderView::Stretch);
 | 
			
		||||
 | 
			
		||||
	if (!m_vlist->isLoaded())
 | 
			
		||||
	{
 | 
			
		||||
		loadList();
 | 
			
		||||
	}
 | 
			
		||||
	else
 | 
			
		||||
	{
 | 
			
		||||
		if (m_proxyModel->rowCount() == 0)
 | 
			
		||||
		{
 | 
			
		||||
			listView->setEmptyMode(VersionListView::String);
 | 
			
		||||
		}
 | 
			
		||||
		preselect();
 | 
			
		||||
	}
 | 
			
		||||
    if (!m_vlist->isLoaded())
 | 
			
		||||
    {
 | 
			
		||||
        loadList();
 | 
			
		||||
    }
 | 
			
		||||
    else
 | 
			
		||||
    {
 | 
			
		||||
        if (m_proxyModel->rowCount() == 0)
 | 
			
		||||
        {
 | 
			
		||||
            listView->setEmptyMode(VersionListView::String);
 | 
			
		||||
        }
 | 
			
		||||
        preselect();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::closeEvent(QCloseEvent * event)
 | 
			
		||||
{
 | 
			
		||||
	QWidget::closeEvent(event);
 | 
			
		||||
    QWidget::closeEvent(event);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::loadList()
 | 
			
		||||
{
 | 
			
		||||
	auto newTask = m_vlist->getLoadTask();
 | 
			
		||||
	if (!newTask)
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	loadTask = newTask.get();
 | 
			
		||||
	connect(loadTask, &Task::succeeded, this, &VersionSelectWidget::onTaskSucceeded);
 | 
			
		||||
	connect(loadTask, &Task::failed, this, &VersionSelectWidget::onTaskFailed);
 | 
			
		||||
	connect(loadTask, &Task::progress, this, &VersionSelectWidget::changeProgress);
 | 
			
		||||
	if(!loadTask->isRunning())
 | 
			
		||||
	{
 | 
			
		||||
		loadTask->start();
 | 
			
		||||
	}
 | 
			
		||||
	sneakyProgressBar->setHidden(false);
 | 
			
		||||
    auto newTask = m_vlist->getLoadTask();
 | 
			
		||||
    if (!newTask)
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    loadTask = newTask.get();
 | 
			
		||||
    connect(loadTask, &Task::succeeded, this, &VersionSelectWidget::onTaskSucceeded);
 | 
			
		||||
    connect(loadTask, &Task::failed, this, &VersionSelectWidget::onTaskFailed);
 | 
			
		||||
    connect(loadTask, &Task::progress, this, &VersionSelectWidget::changeProgress);
 | 
			
		||||
    if(!loadTask->isRunning())
 | 
			
		||||
    {
 | 
			
		||||
        loadTask->start();
 | 
			
		||||
    }
 | 
			
		||||
    sneakyProgressBar->setHidden(false);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::onTaskSucceeded()
 | 
			
		||||
{
 | 
			
		||||
	if (m_proxyModel->rowCount() == 0)
 | 
			
		||||
	{
 | 
			
		||||
		listView->setEmptyMode(VersionListView::String);
 | 
			
		||||
	}
 | 
			
		||||
	sneakyProgressBar->setHidden(true);
 | 
			
		||||
	preselect();
 | 
			
		||||
	loadTask = nullptr;
 | 
			
		||||
    if (m_proxyModel->rowCount() == 0)
 | 
			
		||||
    {
 | 
			
		||||
        listView->setEmptyMode(VersionListView::String);
 | 
			
		||||
    }
 | 
			
		||||
    sneakyProgressBar->setHidden(true);
 | 
			
		||||
    preselect();
 | 
			
		||||
    loadTask = nullptr;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::onTaskFailed(const QString& reason)
 | 
			
		||||
{
 | 
			
		||||
	CustomMessageBox::selectable(this, tr("Error"), tr("List update failed:\n%1").arg(reason), QMessageBox::Warning)->show();
 | 
			
		||||
	onTaskSucceeded();
 | 
			
		||||
    CustomMessageBox::selectable(this, tr("Error"), tr("List update failed:\n%1").arg(reason), QMessageBox::Warning)->show();
 | 
			
		||||
    onTaskSucceeded();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::changeProgress(qint64 current, qint64 total)
 | 
			
		||||
{
 | 
			
		||||
	sneakyProgressBar->setMaximum(total);
 | 
			
		||||
	sneakyProgressBar->setValue(current);
 | 
			
		||||
    sneakyProgressBar->setMaximum(total);
 | 
			
		||||
    sneakyProgressBar->setValue(current);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::currentRowChanged(const QModelIndex& current, const QModelIndex&)
 | 
			
		||||
{
 | 
			
		||||
	auto variant = m_proxyModel->data(current, BaseVersionList::VersionPointerRole);
 | 
			
		||||
	emit selectedVersionChanged(variant.value<BaseVersionPtr>());
 | 
			
		||||
    auto variant = m_proxyModel->data(current, BaseVersionList::VersionPointerRole);
 | 
			
		||||
    emit selectedVersionChanged(variant.value<BaseVersionPtr>());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::preselect()
 | 
			
		||||
{
 | 
			
		||||
	if(preselectedAlready)
 | 
			
		||||
		return;
 | 
			
		||||
	selectCurrent();
 | 
			
		||||
	if(preselectedAlready)
 | 
			
		||||
		return;
 | 
			
		||||
	selectRecommended();
 | 
			
		||||
    if(preselectedAlready)
 | 
			
		||||
        return;
 | 
			
		||||
    selectCurrent();
 | 
			
		||||
    if(preselectedAlready)
 | 
			
		||||
        return;
 | 
			
		||||
    selectRecommended();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::selectCurrent()
 | 
			
		||||
{
 | 
			
		||||
	if(m_currentVersion.isEmpty())
 | 
			
		||||
	{
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	auto idx = m_proxyModel->getVersion(m_currentVersion);
 | 
			
		||||
	if(idx.isValid())
 | 
			
		||||
	{
 | 
			
		||||
		preselectedAlready = true;
 | 
			
		||||
		listView->selectionModel()->setCurrentIndex(idx,QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
 | 
			
		||||
		listView->scrollTo(idx, QAbstractItemView::PositionAtCenter);
 | 
			
		||||
	}
 | 
			
		||||
    if(m_currentVersion.isEmpty())
 | 
			
		||||
    {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
    auto idx = m_proxyModel->getVersion(m_currentVersion);
 | 
			
		||||
    if(idx.isValid())
 | 
			
		||||
    {
 | 
			
		||||
        preselectedAlready = true;
 | 
			
		||||
        listView->selectionModel()->setCurrentIndex(idx,QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
 | 
			
		||||
        listView->scrollTo(idx, QAbstractItemView::PositionAtCenter);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::selectRecommended()
 | 
			
		||||
{
 | 
			
		||||
	auto idx = m_proxyModel->getRecommended();
 | 
			
		||||
	if(idx.isValid())
 | 
			
		||||
	{
 | 
			
		||||
		preselectedAlready = true;
 | 
			
		||||
		listView->selectionModel()->setCurrentIndex(idx,QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
 | 
			
		||||
		listView->scrollTo(idx, QAbstractItemView::PositionAtCenter);
 | 
			
		||||
	}
 | 
			
		||||
    auto idx = m_proxyModel->getRecommended();
 | 
			
		||||
    if(idx.isValid())
 | 
			
		||||
    {
 | 
			
		||||
        preselectedAlready = true;
 | 
			
		||||
        listView->selectionModel()->setCurrentIndex(idx,QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
 | 
			
		||||
        listView->scrollTo(idx, QAbstractItemView::PositionAtCenter);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool VersionSelectWidget::hasVersions() const
 | 
			
		||||
{
 | 
			
		||||
	return m_proxyModel->rowCount(QModelIndex()) != 0;
 | 
			
		||||
    return m_proxyModel->rowCount(QModelIndex()) != 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
BaseVersionPtr VersionSelectWidget::selectedVersion() const
 | 
			
		||||
{
 | 
			
		||||
	auto currentIndex = listView->selectionModel()->currentIndex();
 | 
			
		||||
	auto variant = m_proxyModel->data(currentIndex, BaseVersionList::VersionPointerRole);
 | 
			
		||||
	return variant.value<BaseVersionPtr>();
 | 
			
		||||
    auto currentIndex = listView->selectionModel()->currentIndex();
 | 
			
		||||
    auto variant = m_proxyModel->data(currentIndex, BaseVersionList::VersionPointerRole);
 | 
			
		||||
    return variant.value<BaseVersionPtr>();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setExactFilter(BaseVersionList::ModelRoles role, QString filter)
 | 
			
		||||
{
 | 
			
		||||
	m_proxyModel->setFilter(role, new ExactFilter(filter));
 | 
			
		||||
    m_proxyModel->setFilter(role, new ExactFilter(filter));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setFuzzyFilter(BaseVersionList::ModelRoles role, QString filter)
 | 
			
		||||
{
 | 
			
		||||
	m_proxyModel->setFilter(role, new ContainsFilter(filter));
 | 
			
		||||
    m_proxyModel->setFilter(role, new ContainsFilter(filter));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void VersionSelectWidget::setFilter(BaseVersionList::ModelRoles role, Filter *filter)
 | 
			
		||||
{
 | 
			
		||||
	m_proxyModel->setFilter(role, filter);
 | 
			
		||||
    m_proxyModel->setFilter(role, filter);
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -27,55 +27,55 @@ class Filter;
 | 
			
		||||
 | 
			
		||||
class VersionSelectWidget: public QWidget
 | 
			
		||||
{
 | 
			
		||||
	Q_OBJECT
 | 
			
		||||
    Q_OBJECT
 | 
			
		||||
public:
 | 
			
		||||
	explicit VersionSelectWidget(QWidget *parent = 0);
 | 
			
		||||
	~VersionSelectWidget();
 | 
			
		||||
    explicit VersionSelectWidget(QWidget *parent = 0);
 | 
			
		||||
    ~VersionSelectWidget();
 | 
			
		||||
 | 
			
		||||
	//! loads the list if needed.
 | 
			
		||||
	void initialize(BaseVersionList *vlist);
 | 
			
		||||
    //! loads the list if needed.
 | 
			
		||||
    void initialize(BaseVersionList *vlist);
 | 
			
		||||
 | 
			
		||||
	//! Starts a task that loads the list.
 | 
			
		||||
	void loadList();
 | 
			
		||||
    //! Starts a task that loads the list.
 | 
			
		||||
    void loadList();
 | 
			
		||||
 | 
			
		||||
	bool hasVersions() const;
 | 
			
		||||
	BaseVersionPtr selectedVersion() const;
 | 
			
		||||
	void selectRecommended();
 | 
			
		||||
	void selectCurrent();
 | 
			
		||||
    bool hasVersions() const;
 | 
			
		||||
    BaseVersionPtr selectedVersion() const;
 | 
			
		||||
    void selectRecommended();
 | 
			
		||||
    void selectCurrent();
 | 
			
		||||
 | 
			
		||||
	void setCurrentVersion(const QString & version);
 | 
			
		||||
	void setFuzzyFilter(BaseVersionList::ModelRoles role, QString filter);
 | 
			
		||||
	void setExactFilter(BaseVersionList::ModelRoles role, QString filter);
 | 
			
		||||
	void setFilter(BaseVersionList::ModelRoles role, Filter *filter);
 | 
			
		||||
	void setEmptyString(QString emptyString);
 | 
			
		||||
	void setEmptyErrorString(QString emptyErrorString);
 | 
			
		||||
	void setResizeOn(int column);
 | 
			
		||||
    void setCurrentVersion(const QString & version);
 | 
			
		||||
    void setFuzzyFilter(BaseVersionList::ModelRoles role, QString filter);
 | 
			
		||||
    void setExactFilter(BaseVersionList::ModelRoles role, QString filter);
 | 
			
		||||
    void setFilter(BaseVersionList::ModelRoles role, Filter *filter);
 | 
			
		||||
    void setEmptyString(QString emptyString);
 | 
			
		||||
    void setEmptyErrorString(QString emptyErrorString);
 | 
			
		||||
    void setResizeOn(int column);
 | 
			
		||||
 | 
			
		||||
signals:
 | 
			
		||||
	void selectedVersionChanged(BaseVersionPtr version);
 | 
			
		||||
    void selectedVersionChanged(BaseVersionPtr version);
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
	virtual void closeEvent ( QCloseEvent* );
 | 
			
		||||
    virtual void closeEvent ( QCloseEvent* );
 | 
			
		||||
 | 
			
		||||
private slots:
 | 
			
		||||
	void onTaskSucceeded();
 | 
			
		||||
	void onTaskFailed(const QString &reason);
 | 
			
		||||
	void changeProgress(qint64 current, qint64 total);
 | 
			
		||||
	void currentRowChanged(const QModelIndex ¤t, const QModelIndex &);
 | 
			
		||||
    void onTaskSucceeded();
 | 
			
		||||
    void onTaskFailed(const QString &reason);
 | 
			
		||||
    void changeProgress(qint64 current, qint64 total);
 | 
			
		||||
    void currentRowChanged(const QModelIndex ¤t, const QModelIndex &);
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	void preselect();
 | 
			
		||||
    void preselect();
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	QString m_currentVersion;
 | 
			
		||||
	BaseVersionList *m_vlist = nullptr;
 | 
			
		||||
	VersionProxyModel *m_proxyModel = nullptr;
 | 
			
		||||
	int resizeOnColumn = 0;
 | 
			
		||||
	Task * loadTask;
 | 
			
		||||
	bool preselectedAlready = false;
 | 
			
		||||
    QString m_currentVersion;
 | 
			
		||||
    BaseVersionList *m_vlist = nullptr;
 | 
			
		||||
    VersionProxyModel *m_proxyModel = nullptr;
 | 
			
		||||
    int resizeOnColumn = 0;
 | 
			
		||||
    Task * loadTask;
 | 
			
		||||
    bool preselectedAlready = false;
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
	QVBoxLayout *verticalLayout = nullptr;
 | 
			
		||||
	VersionListView *listView = nullptr;
 | 
			
		||||
	QProgressBar *sneakyProgressBar = nullptr;
 | 
			
		||||
    QVBoxLayout *verticalLayout = nullptr;
 | 
			
		||||
    VersionListView *listView = nullptr;
 | 
			
		||||
    QProgressBar *sneakyProgressBar = nullptr;
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user