summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdriaan de Groot <groot@kde.org>2020-04-03 13:56:19 +0200
committerAdriaan de Groot <groot@kde.org>2020-04-03 13:56:19 +0200
commit59ef307af2d61518fdcb853a6696e9cce28879ed (patch)
tree0e3ce4b8f27bf7237464bc8695b95140ef195b47
parent6c418402e3070e0453dd028f0bcfb8cf28b58755 (diff)
parent768c1dbe43afa7c942a068fd557ec382207ce720 (diff)
Merge panel-layout code: choose where to place sidebar + nav
-rw-r--r--CHANGES3
-rw-r--r--src/branding/default/branding.desc13
-rw-r--r--src/calamares/CalamaresWindow.cpp72
-rw-r--r--src/libcalamaresui/Branding.cpp93
-rw-r--r--src/libcalamaresui/Branding.h17
5 files changed, 156 insertions, 42 deletions
diff --git a/CHANGES b/CHANGES
index 3a6ebd0f3..ee66ee152 100644
--- a/CHANGES
+++ b/CHANGES
@@ -16,6 +16,9 @@ This release contains contributions from (alphabetically by first name):
Calamares). The example QML that is compiled into Calamares has
been improved. To use your own QML, put files `calamares-sidebar.qml`
or `calamares-navigation.qml` into the branding directory.
+ - The sidebar and navigation can now be placed on any side of the
+ main window. This is probably only useful for QML-based UIs.
+ See `branding.desc` for details.
## Modules ##
- The *welcomeq* module has been improved with better layout and
diff --git a/src/branding/default/branding.desc b/src/branding/default/branding.desc
index 365af30e9..b6694d1f4 100644
--- a/src/branding/default/branding.desc
+++ b/src/branding/default/branding.desc
@@ -45,12 +45,25 @@ windowPlacement: center
# - "widget" or unset, use traditional sidebar (logo, items)
# - "none", hide it entirely
# - "qml", use calamares-sidebar.qml from branding folder
+# In addition, you **may** specify a side, separated by a comma,
+# from the kind. Valid sides are:
+# - "left" (if not specified, uses this)
+# - "right"
+# - "top"
+# - "bottom"
+# For instance, "widget,right" is valid; so is "qml", which defaults
+# to putting the sidebar on the left. Also valid is "qml,top".
+# While "widget,top" is valid, the widgets code is **not** flexible
+# and results will be terrible.
sidebar: widget
# Kind of navigation (button panel on the bottom).
# - "widget" or unset, use traditional navigation
# - "none", hide it entirely
# - "qml", use calamares-navigation.qml from branding folder
+# In addition, you **may** specify a side, separated by a comma,
+# from the kind. The same sides are valid as for *sidebar*,
+# except the default is *bottom*.
navigation: widget
# These are strings shown to the user in the user interface.
diff --git a/src/calamares/CalamaresWindow.cpp b/src/calamares/CalamaresWindow.cpp
index 5d4565406..0e8ac1421 100644
--- a/src/calamares/CalamaresWindow.cpp
+++ b/src/calamares/CalamaresWindow.cpp
@@ -132,11 +132,10 @@ CalamaresWindow::getWidgetSidebar( int desiredWidth )
}
QWidget*
-CalamaresWindow::getQmlSidebar( int desiredWidth )
+CalamaresWindow::getQmlSidebar( int )
{
CalamaresUtils::registerCalamaresModels();
QQuickWidget* w = new QQuickWidget( this );
- w->setFixedWidth( desiredWidth );
w->setSizePolicy( QSizePolicy::Expanding, QSizePolicy::Expanding );
w->setResizeMode( QQuickWidget::SizeRootObjectToView );
w->setSource( QUrl(
@@ -217,7 +216,6 @@ CalamaresWindow::getQmlNavigation()
{
CalamaresUtils::registerCalamaresModels();
QQuickWidget* w = new QQuickWidget( this );
- w->setFixedHeight( 64 );
w->setSizePolicy( QSizePolicy::Expanding, QSizePolicy::Expanding );
w->setResizeMode( QQuickWidget::SizeRootObjectToView );
w->setSource( QUrl(
@@ -251,6 +249,28 @@ flavoredWidget( Calamares::Branding::PanelFlavor flavor,
NOTREACHED return nullptr; // All enum values handled above
}
+/** @brief Adds widgets to @p layout if they belong on this @p side
+ */
+static inline void
+insertIf( QBoxLayout* layout,
+ Calamares::Branding::PanelSide side,
+ QWidget* first,
+ Calamares::Branding::PanelSide firstSide )
+{
+ if ( first && side == firstSide )
+ {
+ if ( ( side == Calamares::Branding::PanelSide::Left ) || ( side == Calamares::Branding::PanelSide::Right ) )
+ {
+ first->setMinimumWidth( qMax( first->minimumWidth(), 64 ) );
+ }
+ else
+ {
+ first->setMinimumHeight( qMax( first->minimumHeight(), 64 ) );
+ }
+ layout->addWidget( first );
+ }
+}
+
CalamaresWindow::CalamaresWindow( QWidget* parent )
: QWidget( parent )
, m_debugWindow( nullptr )
@@ -273,6 +293,8 @@ CalamaresWindow::CalamaresWindow( QWidget* parent )
using CalamaresUtils::windowPreferredHeight;
using CalamaresUtils::windowPreferredWidth;
+ using PanelSide = Calamares::Branding::PanelSide;
+
// Needs to match what's checked in DebugWindow
this->setObjectName( "mainApp" );
@@ -292,21 +314,6 @@ CalamaresWindow::CalamaresWindow( QWidget* parent )
resize( w, h );
m_viewManager = Calamares::ViewManager::instance( this );
-
- QBoxLayout* mainLayout = new QHBoxLayout;
- setLayout( mainLayout );
-
- QWidget* sideBox = flavoredWidget(
- branding->sidebarFlavor(),
- this,
- &CalamaresWindow::getWidgetSidebar,
- &CalamaresWindow::getQmlSidebar,
- qBound( 100, CalamaresUtils::defaultFontHeight() * 12, w < windowPreferredWidth ? 100 : 190 ) );
- if ( sideBox )
- {
- mainLayout->addWidget( sideBox );
- }
-
if ( branding->windowExpands() )
{
connect( m_viewManager, &Calamares::ViewManager::enlarge, this, &CalamaresWindow::enlarge );
@@ -319,16 +326,35 @@ CalamaresWindow::CalamaresWindow( QWidget* parent )
// and requires an extra show() (at least with KWin/X11) which
// is too annoying. Instead, leave it up to ignoring-the-quit-
// event, which is also the ViewManager's responsibility.
+
+ QBoxLayout* mainLayout = new QHBoxLayout;
QBoxLayout* contentsLayout = new QVBoxLayout;
- contentsLayout->addWidget( m_viewManager->centralWidget() );
+
+ setLayout( mainLayout );
+
+ QWidget* sideBox = flavoredWidget(
+ branding->sidebarFlavor(),
+ this,
+ &CalamaresWindow::getWidgetSidebar,
+ &CalamaresWindow::getQmlSidebar,
+ qBound( 100, CalamaresUtils::defaultFontHeight() * 12, w < windowPreferredWidth ? 100 : 190 ) );
QWidget* navigation = flavoredWidget(
branding->navigationFlavor(), this, &CalamaresWindow::getWidgetNavigation, &CalamaresWindow::getQmlNavigation );
- if ( navigation )
- {
- contentsLayout->addWidget( navigation );
- }
+ // Build up the contentsLayout (a VBox) top-to-bottom
+ // .. note that the bottom is mirrored wrt. the top
+ insertIf( contentsLayout, PanelSide::Top, sideBox, branding->sidebarSide() );
+ insertIf( contentsLayout, PanelSide::Top, navigation, branding->navigationSide() );
+ contentsLayout->addWidget( m_viewManager->centralWidget() );
+ insertIf( contentsLayout, PanelSide::Bottom, navigation, branding->navigationSide() );
+ insertIf( contentsLayout, PanelSide::Bottom, sideBox, branding->sidebarSide() );
+
+ // .. and then the mainLayout left-to-right
+ insertIf( mainLayout, PanelSide::Left, sideBox, branding->sidebarSide() );
+ insertIf( mainLayout, PanelSide::Left, navigation, branding->navigationSide() );
mainLayout->addLayout( contentsLayout );
+ insertIf( mainLayout, PanelSide::Right, navigation, branding->navigationSide() );
+ insertIf( mainLayout, PanelSide::Right, sideBox, branding->sidebarSide() );
CalamaresUtils::unmarginLayout( mainLayout );
CalamaresUtils::unmarginLayout( contentsLayout );
diff --git a/src/libcalamaresui/Branding.cpp b/src/libcalamaresui/Branding.cpp
index 25fab307e..ff7e43fb8 100644
--- a/src/libcalamaresui/Branding.cpp
+++ b/src/libcalamaresui/Branding.cpp
@@ -405,6 +405,79 @@ getString( const YAML::Node& doc, const char* key )
return QString();
}
+static inline void
+flavorAndSide( const YAML::Node& doc, const char* key, Branding::PanelFlavor& flavor, Branding::PanelSide& side )
+{
+ using PanelFlavor = Branding::PanelFlavor;
+ using PanelSide = Branding::PanelSide;
+
+ // *INDENT-OFF*
+ // clang-format off
+ static const NamedEnumTable< PanelFlavor > sidebarFlavorNames {
+ { QStringLiteral( "widget" ), PanelFlavor::Widget },
+ { QStringLiteral( "none" ), PanelFlavor::None },
+ { QStringLiteral( "hidden" ), PanelFlavor::None },
+ { QStringLiteral( "qml" ), PanelFlavor::Qml }
+ };
+ static const NamedEnumTable< PanelSide > panelSideNames {
+ { QStringLiteral( "left" ), PanelSide::Left },
+ { QStringLiteral( "right" ), PanelSide::Right },
+ { QStringLiteral( "top" ), PanelSide::Top },
+ { QStringLiteral( "bottom" ), PanelSide::Bottom }
+ };
+ // clang-format on
+ // *INDENT-ON*
+
+ bool ok = false;
+ QString configValue = getString( doc, key );
+ if ( configValue.isEmpty() )
+ {
+ // Complain with the original values
+ cWarning() << "Branding setting for" << key << "is missing, using" << sidebarFlavorNames.find( flavor, ok )
+ << panelSideNames.find( side, ok );
+ return;
+ }
+
+ QStringList parts = configValue.split( ',' );
+ if ( parts.length() == 1 )
+ {
+ PanelFlavor f = sidebarFlavorNames.find( configValue, ok );
+ if ( ok )
+ {
+ flavor = f;
+ }
+ else
+ {
+ // Complain with the original value
+ cWarning() << "Branding setting for" << key << "interpreted as" << sidebarFlavorNames.find( flavor, ok )
+ << panelSideNames.find( side, ok );
+ }
+ return;
+ }
+
+ for ( const QString& spart : parts )
+ {
+ bool isFlavor = false;
+ bool isSide = false;
+ PanelFlavor f = sidebarFlavorNames.find( spart, isFlavor );
+ PanelSide s = panelSideNames.find( spart, isSide );
+ if ( isFlavor )
+ {
+ flavor = f;
+ }
+ else if ( isSide )
+ {
+ side = s;
+ }
+ else
+ {
+ cWarning() << "Branding setting for" << key << "contains unknown" << spart << "interpreted as"
+ << sidebarFlavorNames.find( flavor, ok ) << panelSideNames.find( side, ok );
+ return;
+ }
+ }
+}
+
void
Branding::initSimpleSettings( const YAML::Node& doc )
{
@@ -419,12 +492,6 @@ Branding::initSimpleSettings( const YAML::Node& doc )
{ QStringLiteral( "free" ), WindowPlacement::Free },
{ QStringLiteral( "center" ), WindowPlacement::Center }
};
- static const NamedEnumTable< PanelFlavor > sidebarFlavorNames {
- { QStringLiteral( "widget" ), PanelFlavor::Widget },
- { QStringLiteral( "none" ), PanelFlavor::None },
- { QStringLiteral( "hidden" ), PanelFlavor::None },
- { QStringLiteral( "qml" ), PanelFlavor::Qml }
- };
// clang-format on
// *INDENT-ON*
bool ok = false;
@@ -443,18 +510,8 @@ Branding::initSimpleSettings( const YAML::Node& doc )
cWarning() << "Branding module-setting *windowPlacement* interpreted as"
<< placementNames.find( m_windowPlacement, ok );
}
- m_sidebarFlavor = sidebarFlavorNames.find( getString( doc, "sidebar" ), ok );
- if ( !ok )
- {
- cWarning() << "Branding module-setting *sidebar* interpreted as"
- << sidebarFlavorNames.find( m_sidebarFlavor, ok );
- }
- m_navigationFlavor = sidebarFlavorNames.find( getString( doc, "navigation" ), ok);
- if ( !ok )
- {
- cWarning() << "Branding module-setting *navigation* interpreted as"
- << sidebarFlavorNames.find( m_navigationFlavor, ok );
- }
+ flavorAndSide( doc, "sidebar", m_sidebarFlavor, m_sidebarSide );
+ flavorAndSide( doc, "navigation", m_navigationFlavor, m_navigationSide );
QString windowSize = getString( doc, "windowSize" );
if ( !windowSize.isEmpty() )
diff --git a/src/libcalamaresui/Branding.h b/src/libcalamaresui/Branding.h
index b7ba637d6..023f1a511 100644
--- a/src/libcalamaresui/Branding.h
+++ b/src/libcalamaresui/Branding.h
@@ -123,7 +123,7 @@ public:
Free
};
Q_ENUM( WindowPlacement )
- ///@brief What kind of sidebar to use in the main window
+ ///@brief What kind of panel (sidebar, navigation) to use in the main window
enum class PanelFlavor
{
None,
@@ -131,6 +131,16 @@ public:
Qml
};
Q_ENUM( PanelFlavor )
+ ///@brief Where to place a panel (sidebar, navigation)
+ enum class PanelSide
+ {
+ None,
+ Left,
+ Right,
+ Top,
+ Bottom
+ };
+ Q_ENUM( PanelSide )
static Branding* instance();
@@ -201,6 +211,9 @@ public slots:
QString styleString( StyleEntry styleEntry ) const;
QString imagePath( ImageEntry imageEntry ) const;
+ PanelSide sidebarSide() const { return m_sidebarSide; }
+ PanelSide navigationSide() const { return m_navigationSide; }
+
private:
static Branding* s_instance;
@@ -231,6 +244,8 @@ private:
PanelFlavor m_sidebarFlavor = PanelFlavor::Widget;
PanelFlavor m_navigationFlavor = PanelFlavor::Widget;
+ PanelSide m_sidebarSide = PanelSide::Left;
+ PanelSide m_navigationSide = PanelSide::Bottom;
};
template < typename U >