[gnome-shell/wip/carlosg/appgrid-navigation: 4/4] appDisplay: Adapt to available extra space showing icon grids




commit 467b01852b7d1dee33831c9b8b7dcab0ff1f857b
Author: Carlos Garnacho <carlosg gnome org>
Date:   Fri Feb 19 16:45:57 2021 +0100

    appDisplay: Adapt to available extra space showing icon grids
    
    Depending on the available horizontal space, we may want to manipulate
    the icon grid and scroll view spacing to result in an optimal layout
    that has space left to preview prev/next pages.
    
    The main change here is that, when adapting to the available size, the
    space given to a page does not necessarily match the available space,
    as we need to be able to show more than one page at a time.
    
    With this decoupling of available and page sizes in place, we now know
    how much space there is available in order to extend the padding between
    pages, or the fade effect applied to the previewed pages.
    
    Underneath, we rely a bit less on hardcoded CSS paddings, and a bit more
    on the StScrollView::content-padding property.
    
    All put together, gives us proper space management from ultra-wide
    displays, to display ratios that are close to the optimal grid ratio.

 data/theme/gnome-shell-sass/widgets/_app-grid.scss | 26 ++++----
 js/ui/appDisplay.js                                | 75 +++++++++++++++++++---
 js/ui/iconGrid.js                                  |  3 +-
 3 files changed, 81 insertions(+), 23 deletions(-)
---
diff --git a/data/theme/gnome-shell-sass/widgets/_app-grid.scss 
b/data/theme/gnome-shell-sass/widgets/_app-grid.scss
index 70969bba66..cfa2fce0b0 100644
--- a/data/theme/gnome-shell-sass/widgets/_app-grid.scss
+++ b/data/theme/gnome-shell-sass/widgets/_app-grid.scss
@@ -126,10 +126,8 @@ $app_grid_fg_color: #fff;
   }
 }
 
-// Some hacks I don't even know
 .apps-scroll-view {
-  // horizontal padding to make sure scrollbars or dash don't overlap content
-  padding: 0 88px;
+  padding: 0;
 }
 
 // shutdown and other actions in the grid
@@ -141,20 +139,26 @@ $app_grid_fg_color: #fff;
 }
 
 .page-navigation-hint {
-  background: rgba(255, 255, 255, 0.05);
-  width: 88px;
+  width: 300px;
 
   &.dnd {
     background: rgba(255, 255, 255, 0.1);
   }
 
-  &.next {
-    &:ltr { border-radius: 15px 0px 0px 15px; }
-    &:rtl { border-radius: 0px 15px 15px 0px; }
+  &.next:ltr,
+  &.previous:rtl {
+    background-gradient-start: rgba(255, 255, 255, 0.05);
+    background-gradient-end: transparent;
+    background-gradient-direction: horizontal;
+    border-radius: 15px 0px 0px 15px;
   }
-  &.previous {
-    &:ltr { border-radius: 0px 15px 15px 0px; }
-    &:rtl { border-radius: 15px 0px 0px 15px; }
+
+  &.previous:ltr,
+  &.next:rtl {
+    background-gradient-start: transparent;
+    background-gradient-end: rgba(255, 255, 255, 0.05);
+    background-gradient-direction: horizontal;
+    border-radius: 0px 15px 15px 0px;
   }
 }
 
diff --git a/js/ui/appDisplay.js b/js/ui/appDisplay.js
index a343a71922..a6a6eedf42 100644
--- a/js/ui/appDisplay.js
+++ b/js/ui/appDisplay.js
@@ -39,8 +39,10 @@ var APP_ICON_TITLE_COLLAPSE_TIME = 100;
 const FOLDER_DIALOG_ANIMATION_TIME = 200;
 
 const PAGE_PREVIEW_ANIMATION_TIME = 150;
-const PAGE_PREVIEW_FADE_EFFECT_OFFSET = 160;
+const PAGE_PREVIEW_FADE_EFFECT_MAX_OFFSET = 300;
+const PAGE_PREVIEW_MAX_ARROW_OFFSET = 80;
 const PAGE_INDICATOR_FADE_TIME = 200;
+const MAX_PAGE_PADDING = 200;
 
 const OVERSHOOT_THRESHOLD = 20;
 const OVERSHOOT_TIMEOUT = 1000;
@@ -323,10 +325,19 @@ var BaseAppView = GObject.registerClass({
 
     _updateFadeForNavigation() {
         const fadeMargin = new Clutter.Margin();
-        fadeMargin.right = (this._pagesShown & SidePages.NEXT) !== 0
-            ? -PAGE_PREVIEW_FADE_EFFECT_OFFSET : 0;
-        fadeMargin.left = (this._pagesShown & SidePages.PREVIOUS) !== 0
-            ? -PAGE_PREVIEW_FADE_EFFECT_OFFSET : 0;
+
+        if (this._pagesShown & SidePages.NEXT) {
+            fadeMargin.right = Math.max(
+                -PAGE_PREVIEW_FADE_EFFECT_MAX_OFFSET,
+                -(this._availWidth - this._grid.layout_manager.pageWidth) / 2);
+        }
+
+        if (this._pagesShown & SidePages.PREVIOUS) {
+            fadeMargin.left = Math.max(
+                -PAGE_PREVIEW_FADE_EFFECT_MAX_OFFSET,
+                -(this._availWidth - this._grid.layout_manager.pageWidth) / 2);
+        }
+
         this._scrollView.update_fade_effect(fadeMargin);
     }
 
@@ -1068,10 +1079,51 @@ var BaseAppView = GObject.registerClass({
         const availWidth = box.get_width();
         const availHeight = box.get_height();
 
-        this._grid.adaptToSize(availWidth, availHeight);
+        const gridRatio = this._grid.layout_manager.columnsPerPage /
+            this._grid.layout_manager.rowsPerPage;
+        const spaceRatio = availWidth / availHeight;
+        let pageWidth, pageHeight;
+
+        if (spaceRatio > gridRatio * 1.1) {
+            // Enough room for some preview
+            pageHeight = availHeight;
+            pageWidth = availHeight * gridRatio;
+
+            if (spaceRatio > gridRatio * 1.5) {
+                // Ultra-wide layout, give some extra space for
+                // the page area, but up to an extent.
+                const extraPageSpace = Math.min(
+                    (availWidth - pageWidth) / 2, MAX_PAGE_PADDING);
+                pageWidth += extraPageSpace;
+                this._grid.layout_manager.pagePadding.left = extraPageSpace / 2;
+                this._grid.layout_manager.pagePadding.right = extraPageSpace / 2;
+            }
+        } else {
+            // Not enough room, needs to shrink horizontally
+            pageWidth = availWidth * 0.8;
+            pageHeight = availHeight;
+            this._grid.layout_manager.pagePadding.left = availWidth * 0.02;
+            this._grid.layout_manager.pagePadding.right = availWidth * 0.02;
+        }
+
+        this._grid.adaptToSize(pageWidth, pageHeight);
+
+        const horizontalPadding = (availWidth - this._grid.layout_manager.pageWidth) / 2;
+        const verticalPadding = (availHeight - this._grid.layout_manager.pageHeight) / 2;
+
+        this._scrollView.content_padding = new Clutter.Margin({
+            left: horizontalPadding,
+            right: horizontalPadding,
+            top: verticalPadding,
+            bottom: verticalPadding,
+        });
 
         this._availWidth = availWidth;
         this._availHeight = availHeight;
+
+        this._pageIndicatorOffset = horizontalPadding;
+        this._pageArrowOffset = Math.max(
+            horizontalPadding - PAGE_PREVIEW_MAX_ARROW_OFFSET, 0);
     }
 
     _syncClip() {
@@ -1083,7 +1135,6 @@ var BaseAppView = GObject.registerClass({
     }
 
     _setupPagePreview(page, state) {
-        const multiplier = page;
         if (this._previewedPages.has(page))
             return;
 
@@ -1098,7 +1149,8 @@ var BaseAppView = GObject.registerClass({
         const rtl = this.get_text_direction() === Clutter.TextDirection.RTL;
 
         const notifyId = adjustment.connect('notify::value', () => {
-            let translationX = (1 - adjustment.value) * 100 * multiplier;
+            const multiplier = -page;
+            let translationX = (1 - adjustment.value) * 100 * page;
             translationX = rtl ? -translationX : translationX;
             const nextPage = this._grid.currentPage + page;
             const hasFollowingPage = nextPage >= 0 &&
@@ -1112,7 +1164,8 @@ var BaseAppView = GObject.registerClass({
                     const pageArrow = page > 0
                         ? this._nextPageArrow
                         : this._prevPageArrow;
-                    pageArrow.translation_x = translationX;
+                    pageArrow.translation_x = translationX +
+                        this._pageArrowOffset * multiplier;
                     pageArrow.opacity = adjustment.value * 255;
                     pageArrow.visible = true;
                 }
@@ -1121,7 +1174,8 @@ var BaseAppView = GObject.registerClass({
                 (hasFollowingPage || (state & SidePages.DND) !== 0)) {
                 indicator.visible = true;
                 indicator.opacity = adjustment.value * 255;
-                indicator.translation_x = translationX;
+                indicator.translation_x = translationX +
+                    (this._pageIndicatorOffset - indicator.width) * multiplier;
             }
             this._syncClip();
         });
@@ -1375,6 +1429,7 @@ class AppDisplay extends BaseAppView {
         const [, indicatorHeight] = this._pageIndicators.get_preferred_height(-1);
         height -= indicatorHeight;
 
+        this._grid.findBestModeForSize(width, height);
         super.adaptToSize(width, height);
     }
 
diff --git a/js/ui/iconGrid.js b/js/ui/iconGrid.js
index e8ac2b07ed..2c71c29c10 100644
--- a/js/ui/iconGrid.js
+++ b/js/ui/iconGrid.js
@@ -1223,7 +1223,7 @@ var IconGrid = GObject.registerClass({
         }
     }
 
-    _findBestModeForSize(width, height) {
+    findBestModeForSize(width, height) {
         const { pagePadding } = this.layout_manager;
         width -= pagePadding.left + pagePadding.right;
         height -= pagePadding.top + pagePadding.bottom;
@@ -1446,7 +1446,6 @@ var IconGrid = GObject.registerClass({
     }
 
     adaptToSize(width, height) {
-        this._findBestModeForSize(width, height);
         this.layout_manager.adaptToSize(width, height);
     }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]