made requested changes

This commit is contained in:
Kyle Robertze 2017-01-25 10:34:18 +02:00 committed by Teo Mrnjavac
parent f5fe887a79
commit 1d7ad9e045
9 changed files with 116 additions and 107 deletions

View File

@ -1,6 +1,7 @@
/* /*
* Copyright 2016, Luca Giambonini <almack@chakraos.org> * Copyright 2016, Luca Giambonini <almack@chakraos.org>
* Copyright 2016, Lisa Vitolo <shainer@chakraos.org> * Copyright 2016, Lisa Vitolo <shainer@chakraos.org>
* Copyright 2017, Kyle Robbertze <krobbertze@gmail.com>
* *
* Calamares is free software: you can redistribute it and/or modify * Calamares is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -24,6 +25,7 @@
#include "GlobalStorage.h" #include "GlobalStorage.h"
#include "JobQueue.h" #include "JobQueue.h"
#include "utils/Logger.h" #include "utils/Logger.h"
#include "utils/Retranslator.h"
#include "utils/YamlUtils.h" #include "utils/YamlUtils.h"
#include <QFile> #include <QFile>
@ -64,9 +66,10 @@ void NetInstallPage::readGroups( const QByteArray& yamlData )
{ {
YAML::Node groups = YAML::Load( yamlData.constData() ); YAML::Node groups = YAML::Load( yamlData.constData() );
Q_ASSERT( groups.IsSequence() ); Q_ASSERT( groups.IsSequence() );
QVariantList columnHeadings; m_groups = new PackageModel( groups );
columnHeadings << tr( "Name" ) << tr( "Description" ); CALAMARES_RETRANSLATE(
m_groups = new PackageModel( groups, columnHeadings ); m_groups->setHeaderData( 0, Qt::Horizontal, tr( "Name" ) );
m_groups->setHeaderData( 0, Qt::Horizontal, tr( "Description" ) ); )
} }
void void
@ -89,9 +92,9 @@ NetInstallPage::dataIsHere( QNetworkReply* reply )
emit checkReady( isReady() ); emit checkReady( isReady() );
} }
QList<QVariant> NetInstallPage::selectedPackages( bool isCritical ) const QList<PackageTreeItem::ItemData> NetInstallPage::selectedPackages() const
{ {
return m_groups->getPackages( isCritical ); return m_groups->getPackages();
} }
void NetInstallPage::loadGroupList() void NetInstallPage::loadGroupList()

View File

@ -1,6 +1,7 @@
/* /*
* Copyright 2016, Luca Giambonini <almack@chakraos.org> * Copyright 2016, Luca Giambonini <almack@chakraos.org>
* Copyright 2016, Lisa Vitolo <shainer@chakraos.org> * Copyright 2016, Lisa Vitolo <shainer@chakraos.org>
* Copyright 2017, Kyle Robbertze <krobbertze@gmail.com>
* *
* Calamares is free software: you can redistribute it and/or modify * Calamares is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -20,7 +21,9 @@
#define NETINSTALLPAGE_H #define NETINSTALLPAGE_H
#include "PackageModel.h" #include "PackageModel.h"
#include "PackageTreeItem.h"
#include "Typedefs.h" #include "Typedefs.h"
#include <QWidget> #include <QWidget>
#include <QAbstractButton> #include <QAbstractButton>
#include <QNetworkAccessManager> #include <QNetworkAccessManager>
@ -28,8 +31,6 @@
// required forward declarations // required forward declarations
class QByteArray; class QByteArray;
class QNetworkReply; class QNetworkReply;
class GroupSelectionWidget;
class PackageModel;
namespace Ui namespace Ui
{ {
@ -54,7 +55,7 @@ public:
// Returns the list of packages belonging to groups that are // Returns the list of packages belonging to groups that are
// selected in the view in this given moment. No data is cached here, so // selected in the view in this given moment. No data is cached here, so
// this function does not have constant time. // this function does not have constant time.
QList<QVariant> selectedPackages( bool isCritical ) const; QList<PackageTreeItem::ItemData> selectedPackages() const;
public slots: public slots:
void dataIsHere( QNetworkReply* ); void dataIsHere( QNetworkReply* );
@ -74,9 +75,6 @@ private:
QNetworkAccessManager m_networkManager; QNetworkAccessManager m_networkManager;
PackageModel* m_groups; PackageModel* m_groups;
// For each group name, store the selection widget to retrieve UI
// properties.
QHash<QString, GroupSelectionWidget*> m_groupWidgets;
}; };
#endif // NETINSTALLPAGE_H #endif // NETINSTALLPAGE_H

View File

@ -1,6 +1,7 @@
/* /*
* Copyright 2016, Luca Giambonini <almack@chakraos.org> * Copyright 2016, Luca Giambonini <almack@chakraos.org>
* Copyright 2016, Lisa Vitolo <shainer@chakraos.org> * Copyright 2016, Lisa Vitolo <shainer@chakraos.org>
* Copyright 2017, Kyle Robbertze <krobbertze@gmail.com>
* *
* Calamares is free software: you can redistribute it and/or modify * Calamares is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -126,13 +127,27 @@ NetInstallViewStep::onLeave()
<< "to global storage"; << "to global storage";
QMap<QString, QVariant> packagesWithOperation; QMap<QString, QVariant> packagesWithOperation;
QList<QVariant> installPackages = m_widget->selectedPackages( true ); QList<PackageTreeItem::ItemData> packages = m_widget->selectedPackages();
QList<QVariant> tryInstallPackages = m_widget->selectedPackages( false ); QVariantList installPackages;
QVariantList tryInstallPackages;
cDebug() << "Processing";
for ( auto package : packages )
{
QMap<QString, QVariant> details;
details.insert( "pre-script", package.preScript );
details.insert( "package", package.packageName );
details.insert( "post-script", package.postScript );
if ( package.isCritical )
installPackages.append( details );
else
tryInstallPackages.append( details );
}
if ( !installPackages.empty() ) if ( !installPackages.empty() )
packagesWithOperation.insert( "install", installPackages ); packagesWithOperation.insert( "install", QVariant( installPackages ) );
if ( !tryInstallPackages.empty() ) if ( !tryInstallPackages.empty() )
packagesWithOperation.insert( "try-install", tryInstallPackages ); packagesWithOperation.insert( "try-install", QVariant( tryInstallPackages ) );
if ( !packagesWithOperation.isEmpty() ) if ( !packagesWithOperation.isEmpty() )
{ {

View File

@ -18,18 +18,13 @@
#include "PackageModel.h" #include "PackageModel.h"
#include "utils/Logger.h"
#include "utils/YamlUtils.h" #include "utils/YamlUtils.h"
#include <Qt> PackageModel::PackageModel( const YAML::Node& data, QObject* parent ) :
PackageModel::PackageModel( const YAML::Node& data, const QVariantList& columnHeadings,
QObject* parent ) :
QAbstractItemModel( parent ), QAbstractItemModel( parent ),
m_columnHeadings( columnHeadings ) m_columnHeadings()
{ {
QVariantList rootData; m_rootItem = new PackageTreeItem();
m_rootItem = new PackageTreeItem( );
setupModelData( data, m_rootItem ); setupModelData( data, m_rootItem );
} }
@ -100,37 +95,17 @@ PackageModel::data( const QModelIndex& index, int role ) const
{ {
if ( !index.isValid() ) if ( !index.isValid() )
return QVariant(); return QVariant();
PackageTreeItem* item = static_cast<PackageTreeItem*>( index.internalPointer() ); PackageTreeItem* item = static_cast<PackageTreeItem*>( index.internalPointer() );
if ( index.column() == 0 && role == Qt::CheckStateRole ) if ( index.column() == 0 && role == Qt::CheckStateRole )
return item->isSelected(); return item->isSelected();
if ( !item->childCount() ) // package
{
if ( !item->parentItem()->isHidden() && role == Qt::DisplayRole &&
index.column() == 0 )
return QVariant( item->packageName() );
else if ( role == PackageTreeItem::PackageNameRole )
return QVariant( item->packageName() );
else
return QVariant();
}
if ( item->isHidden() && role == Qt::DisplayRole ) // Hidden group if ( item->isHidden() && role == Qt::DisplayRole ) // Hidden group
return QVariant(); return QVariant();
switch ( role ) if ( role == Qt::DisplayRole )
{
case Qt::DisplayRole:
return item->data( index.column() ); return item->data( index.column() );
case PackageTreeItem::PreScriptRole: return QVariant();
return QVariant( item->preScript() );
case PackageTreeItem::PackageNameRole:
return QVariant( item->packageName() );
case PackageTreeItem::PostScriptRole:
return QVariant( item->postScript() );
default:
return QVariant();
}
} }
bool bool
@ -147,6 +122,21 @@ PackageModel::setData( const QModelIndex& index, const QVariant& value, int role
return true; return true;
} }
bool
PackageModel::setHeaderData( int section, Qt::Orientation orientation,
const QVariant& value, int role )
{
if ( orientation == Qt::Horizontal )
{
if ( m_columnHeadings.value( section ) != QVariant() )
m_columnHeadings.replace( section, value );
else
m_columnHeadings.insert( section, value );
emit headerDataChanged( orientation, section, section );
}
return true;
}
Qt::ItemFlags Qt::ItemFlags
PackageModel::flags( const QModelIndex& index ) const PackageModel::flags( const QModelIndex& index ) const
{ {
@ -165,38 +155,38 @@ PackageModel::headerData( int section, Qt::Orientation orientation, int role ) c
return QVariant(); return QVariant();
} }
QList<QVariant> QList<PackageTreeItem::ItemData>
PackageModel::getPackages( bool isCritical ) const PackageModel::getPackages() const
{ {
QList<PackageTreeItem*> items = getItemPackages( m_rootItem, isCritical ); QList<PackageTreeItem*> items = getItemPackages( m_rootItem );
for ( auto package : m_hiddenItems ) for ( auto package : m_hiddenItems )
items.append( getItemPackages( package, isCritical ) ); items.append( getItemPackages( package ) );
QList<QVariant> packages; QList<PackageTreeItem::ItemData> packages;
for ( auto item : items ) for ( auto item : items )
{ {
QMap<QString, QVariant> itemMap; PackageTreeItem::ItemData itemData;
itemMap.insert( "pre-script", item->parentItem()->preScript() ); // Only groups have hooks itemData.preScript = item->parentItem()->preScript(); // Only groups have hooks
itemMap.insert( "package", item->packageName() ); itemData.packageName = item->packageName(); // this seg faults
itemMap.insert( "post-script", item->parentItem()->postScript() ); itemData.postScript = item->parentItem()->postScript(); // Only groups have hooks
packages.append( QVariant( itemMap ) ); itemData.isCritical = item->parentItem()->isCritical(); // Only groups are critical
packages.append( itemData );
} }
return packages; return packages;
} }
QList<PackageTreeItem*> QList<PackageTreeItem*>
PackageModel::getItemPackages( PackageTreeItem* item, bool isCritical ) const PackageModel::getItemPackages( PackageTreeItem* item ) const
{ {
QList<PackageTreeItem*> selectedPackages; QList<PackageTreeItem*> selectedPackages;
for ( int i = 0; i < item->childCount(); i++ ) for ( int i = 0; i < item->childCount(); i++ )
{ {
if ( item->child( i )->isSelected() == Qt::Unchecked || if ( item->child( i )->isSelected() == Qt::Unchecked )
item->child( i )->isCritical() != isCritical )
continue; continue;
if ( !item->child( i )->childCount() ) // package if ( !item->child( i )->childCount() ) // package
selectedPackages.append( item->child( i ) ); selectedPackages.append( item->child( i ) );
else else
selectedPackages.append( getItemPackages( item->child( i ), isCritical ) ); selectedPackages.append( getItemPackages( item->child( i ) ) );
} }
return selectedPackages; return selectedPackages;

View File

@ -35,23 +35,24 @@ class PackageModel : public QAbstractItemModel
Q_OBJECT Q_OBJECT
public: public:
explicit PackageModel( const YAML::Node& data, const QVariantList& columnHeadings, explicit PackageModel( const YAML::Node& data, QObject* parent = 0 );
QObject* parent = 0 );
~PackageModel(); ~PackageModel();
QVariant data( const QModelIndex& index, int role ) const Q_DECL_OVERRIDE; QVariant data( const QModelIndex& index, int role ) const override;
bool setData( const QModelIndex& index, const QVariant& value, bool setData( const QModelIndex& index, const QVariant& value,
int role = Qt::EditRole ) Q_DECL_OVERRIDE; int role = Qt::EditRole ) override;
Qt::ItemFlags flags( const QModelIndex& index ) const Q_DECL_OVERRIDE; bool setHeaderData( int section, Qt::Orientation orientation,
const QVariant& value, int role = Qt::EditRole );
Qt::ItemFlags flags( const QModelIndex& index ) const override;
QVariant headerData( int section, Qt::Orientation orientation, QVariant headerData( int section, Qt::Orientation orientation,
int role = Qt::DisplayRole ) const Q_DECL_OVERRIDE; int role = Qt::DisplayRole ) const override;
QModelIndex index( int row, int column, QModelIndex index( int row, int column,
const QModelIndex& parent = QModelIndex() ) const Q_DECL_OVERRIDE; const QModelIndex& parent = QModelIndex() ) const override;
QModelIndex parent( const QModelIndex& index ) const Q_DECL_OVERRIDE; QModelIndex parent( const QModelIndex& index ) const override;
int rowCount( const QModelIndex& parent = QModelIndex() ) const Q_DECL_OVERRIDE; int rowCount( const QModelIndex& parent = QModelIndex() ) const override;
int columnCount( const QModelIndex& parent = QModelIndex() ) const Q_DECL_OVERRIDE; int columnCount( const QModelIndex& parent = QModelIndex() ) const override;
QList<QVariant> getPackages( bool isCritical ) const; QList<PackageTreeItem::ItemData> getPackages() const;
QList<PackageTreeItem*> getItemPackages( PackageTreeItem* item, bool isCritical ) const; QList<PackageTreeItem*> getItemPackages( PackageTreeItem* item ) const;
private: private:
void setupModelData( const YAML::Node& data, PackageTreeItem* parent ); void setupModelData( const YAML::Node& data, PackageTreeItem* parent );

View File

@ -18,18 +18,20 @@
#include "PackageTreeItem.h" #include "PackageTreeItem.h"
#include "utils/Logger.h" // TODO:Remove
PackageTreeItem::PackageTreeItem( const ItemData& data, PackageTreeItem* parent ) : PackageTreeItem::PackageTreeItem( const ItemData& data, PackageTreeItem* parent ) :
m_data( data ), m_data( data ),
m_parentItem( parent ) m_parentItem( parent )
{ } { }
PackageTreeItem::PackageTreeItem( const QString packageName, PackageTreeItem* parent ) : PackageTreeItem::PackageTreeItem( const QString packageName, PackageTreeItem* parent ) :
m_packageName( packageName ), m_parentItem( parent )
m_parentItem( parent ), {
m_selected( parent->isSelected() ) m_data.packageName = packageName;
{ } if ( parent != nullptr )
m_data.selected = parent->isSelected();
else
m_data.selected = Qt::Unchecked;
}
PackageTreeItem::PackageTreeItem( PackageTreeItem* parent ) : PackageTreeItem::PackageTreeItem( PackageTreeItem* parent ) :
m_parentItem( parent ) m_parentItem( parent )
@ -75,9 +77,9 @@ PackageTreeItem::columnCount() const
QVariant QVariant
PackageTreeItem::data( int column ) const PackageTreeItem::data( int column ) const
{ {
if ( m_packageName != nullptr ) // package if ( packageName() != nullptr ) // package
{ {
if ( column == 1 ) if ( !column )
return QVariant( packageName() ); return QVariant( packageName() );
return QVariant(); return QVariant();
} }
@ -119,7 +121,7 @@ PackageTreeItem::preScript() const
QString QString
PackageTreeItem::packageName() const PackageTreeItem::packageName() const
{ {
return m_packageName; return m_data.packageName;
} }
QString QString
@ -131,37 +133,37 @@ PackageTreeItem::postScript() const
bool bool
PackageTreeItem::isHidden() const PackageTreeItem::isHidden() const
{ {
return m_hidden; return m_data.isHidden;
} }
void void
PackageTreeItem::setHidden( bool isHidden ) PackageTreeItem::setHidden( bool isHidden )
{ {
m_hidden = isHidden; m_data.isHidden = isHidden;
} }
bool bool
PackageTreeItem::isCritical() const PackageTreeItem::isCritical() const
{ {
return m_critical; return m_data.isCritical;
} }
void void
PackageTreeItem::setCritical( bool isCritical ) PackageTreeItem::setCritical( bool isCritical )
{ {
m_critical = isCritical; m_data.isCritical = isCritical;
} }
Qt::CheckState Qt::CheckState
PackageTreeItem::isSelected() const PackageTreeItem::isSelected() const
{ {
return m_selected; return m_data.selected;
} }
void void
PackageTreeItem::setSelected( Qt::CheckState isSelected ) PackageTreeItem::setSelected( Qt::CheckState isSelected )
{ {
m_selected = isSelected; m_data.selected = isSelected;
setChildrenSelected( isSelected ); setChildrenSelected( isSelected );
PackageTreeItem* currentItem = parentItem(); PackageTreeItem* currentItem = parentItem();
while ( currentItem != nullptr ) while ( currentItem != nullptr )
@ -176,11 +178,11 @@ PackageTreeItem::setSelected( Qt::CheckState isSelected )
isChildPartiallySelected = true; isChildPartiallySelected = true;
} }
if ( !childrenSelected && !isChildPartiallySelected ) if ( !childrenSelected && !isChildPartiallySelected )
currentItem->m_selected = Qt::Unchecked; currentItem->m_data.selected = Qt::Unchecked;
else if ( childrenSelected == currentItem->childCount() ) else if ( childrenSelected == currentItem->childCount() )
currentItem->m_selected = Qt::Checked; currentItem->m_data.selected = Qt::Checked;
else else
currentItem->m_selected = Qt::PartiallyChecked; currentItem->m_data.selected = Qt::PartiallyChecked;
currentItem = currentItem->parentItem(); currentItem = currentItem->parentItem();
} }
} }
@ -191,7 +193,7 @@ PackageTreeItem::setChildrenSelected( Qt::CheckState isSelected )
if ( isSelected != Qt::PartiallyChecked ) if ( isSelected != Qt::PartiallyChecked )
for ( auto child : m_childItems ) for ( auto child : m_childItems )
{ {
child->m_selected = isSelected; child->m_data.selected = isSelected;
child->setChildrenSelected( isSelected ); child->setChildrenSelected( isSelected );
} }
} }

View File

@ -19,8 +19,6 @@
#ifndef PACKAGETREEITEM_H #ifndef PACKAGETREEITEM_H
#define PACKAGETREEITEM_H #define PACKAGETREEITEM_H
#include "NetInstallPage.h"
#include <QList> #include <QList>
#include <QVariant> #include <QVariant>
#include <QStandardItem> #include <QStandardItem>
@ -33,7 +31,11 @@ public:
QString name; QString name;
QString description; QString description;
QString preScript; QString preScript;
QString packageName;
QString postScript; QString postScript;
bool isCritical = false;
bool isHidden = false;
Qt::CheckState selected = Qt::Unchecked;
}; };
explicit PackageTreeItem( const ItemData& data, PackageTreeItem* parent = 0 ); explicit PackageTreeItem( const ItemData& data, PackageTreeItem* parent = 0 );
explicit PackageTreeItem( const QString packageName, PackageTreeItem* parent = 0 ); explicit PackageTreeItem( const QString packageName, PackageTreeItem* parent = 0 );
@ -44,7 +46,7 @@ public:
PackageTreeItem* child( int row ); PackageTreeItem* child( int row );
int childCount() const; int childCount() const;
int columnCount() const; int columnCount() const;
QVariant data( int column ) const Q_DECL_OVERRIDE; QVariant data( int column ) const override;
int row() const; int row() const;
PackageTreeItem* parentItem(); PackageTreeItem* parentItem();
QString prettyName() const; QString prettyName() const;
@ -59,22 +61,12 @@ public:
Qt::CheckState isSelected() const; Qt::CheckState isSelected() const;
void setSelected( Qt::CheckState isSelected ); void setSelected( Qt::CheckState isSelected );
void setChildrenSelected( Qt::CheckState isSelected ); void setChildrenSelected( Qt::CheckState isSelected );
int type() const Q_DECL_OVERRIDE; int type() const override;
static const int PreScriptRole = Qt::UserRole;
static const int PackageNameRole = Qt::UserRole + 1;
static const int PostScriptRole = Qt::UserRole + 2;
private: private:
PackageTreeItem* m_parentItem;
QList<PackageTreeItem*> m_childItems; QList<PackageTreeItem*> m_childItems;
ItemData m_data; ItemData m_data;
QString m_packageName;
// See README.md for a description of these two fields.
Qt::CheckState m_selected = Qt::Unchecked;
bool m_hidden = false;
bool m_critical = false;
const int m_columns = 2; // Name, description const int m_columns = 2; // Name, description
PackageTreeItem* m_parentItem;
}; };
#endif // PACKAGETREEITEM_H #endif // PACKAGETREEITEM_H

View File

@ -27,13 +27,16 @@ The URL must point to a YAML file. Here is a short example of how the YAML file
The file is composed of a list of entry, each describing one group. The keys *name*, *description* and *packages* are required. The file is composed of a list of entry, each describing one group. The keys *name*, *description* and *packages* are required.
Three more keys are supported: More keys are supported:
- hidden: if true, do not show the group on the page. Defaults to false. - hidden: if true, do not show the group on the page. Defaults to false.
- selected: if true, display the group as selected. Defaults to false. - selected: if true, display the group as selected. Defaults to false.
- critical: if true, make the installation process fail if installing - critical: if true, make the installation process fail if installing
any of the packages in the group fails. Otherwise, just log a warning. any of the packages in the group fails. Otherwise, just log a warning.
Defaults to false. Defaults to false.
- subgroups: if present this follows the same structure as the top level
of the YAML file, allowing there to be sub-groups of packages to an
arbitary depth
If you set both *hidden* and *selected* for a group, you are basically creating a "default" group of packages If you set both *hidden* and *selected* for a group, you are basically creating a "default" group of packages
which will always be installed in the user's system. which will always be installed in the user's system.

View File

@ -34,6 +34,11 @@
<height>434</height> <height>434</height>
</rect> </rect>
</property> </property>
<property name="font">
<font>
<pointsize>11</pointsize>
</font>
</property>
<layout class="QVBoxLayout" name="verticalLayout_3"/> <layout class="QVBoxLayout" name="verticalLayout_3"/>
</widget> </widget>
</widget> </widget>