diff --git a/schemas/org.gnome.shell.extensions.dash-to-panel.gschema.xml b/schemas/org.gnome.shell.extensions.dash-to-panel.gschema.xml index 138b889..4a964d0 100644 --- a/schemas/org.gnome.shell.extensions.dash-to-panel.gschema.xml +++ b/schemas/org.gnome.shell.extensions.dash-to-panel.gschema.xml @@ -257,7 +257,7 @@ 0 Panel top and bottom padding - + 0 Panel sides padding diff --git a/src/appIcons.js b/src/appIcons.js index 848393d..9e9ba0a 100644 --- a/src/appIcons.js +++ b/src/appIcons.js @@ -41,7 +41,6 @@ import * as BoxPointer from 'resource:///org/gnome/shell/ui/boxpointer.js' import { EventEmitter } from 'resource:///org/gnome/shell/misc/signals.js' import * as Utils from './utils.js' -import * as PanelSettings from './panelSettings.js' import * as Taskbar from './taskbar.js' import { DTP_EXTENSION, @@ -204,7 +203,7 @@ export const TaskbarAppIcon = GObject.registerClass( this.set_child(this._container) if (panel.checkIfVertical()) { - this.set_width(panel.geom.w) + this.set_width(panel.geom.innerSize) } // Monitor windows-changes instead of app state. @@ -842,7 +841,7 @@ export const TaskbarAppIcon = GObject.registerClass( } _setAppIconPadding() { - const padding = getIconPadding(this.dtpPanel.monitor.index) + const padding = getIconPadding(this.dtpPanel) const margin = SETTINGS.get_int('appicon-margin') let vertical = this.dtpPanel.checkIfVertical() @@ -1874,8 +1873,8 @@ export function cssHexTocssRgba(cssHex, opacity) { return 'rgba(' + [r, g, b].join(',') + ',' + opacity + ')' } -export function getIconPadding(monitorIndex) { - let panelSize = PanelSettings.getPanelSize(SETTINGS, monitorIndex) +export function getIconPadding(dtpPanel) { + let panelSize = dtpPanel.geom.innerSize let padding = SETTINGS.get_int('appicon-padding') let availSize = panelSize - Taskbar.MIN_ICON_SIZE - (panelSize % 2) @@ -2148,7 +2147,7 @@ export const ShowAppsIconWrapper = class extends EventEmitter { } setShowAppsPadding() { - let padding = getIconPadding(this.realShowAppsIcon._dtpPanel.monitor.index) + let padding = getIconPadding(this.realShowAppsIcon._dtpPanel) let sidePadding = SETTINGS.get_int('show-apps-icon-side-padding') let isVertical = this.realShowAppsIcon._dtpPanel.checkIfVertical() diff --git a/src/panel.js b/src/panel.js index fc9b4cc..ba5a09e 100644 --- a/src/panel.js +++ b/src/panel.js @@ -67,6 +67,8 @@ const T5 = 'trackerFocusAppTimeout' const T6 = 'scrollPanelDelayTimeout' const T7 = 'waitPanelBoxAllocation' +const MIN_PANEL_SIZE = 22 + export const Panel = GObject.registerClass( {}, class Panel extends St.Widget { @@ -172,6 +174,8 @@ export const Panel = GObject.registerClass( }) } + this.geom = this.getGeometry() + // Create a wrapper around the real showAppsIcon in order to add a popupMenu. Most of // its behavior is handled by the taskbar, but its positioning is done at the panel level this.showAppsIconWrapper = new AppIcons.ShowAppsIconWrapper(this) @@ -217,8 +221,6 @@ export const Panel = GObject.registerClass( )._dtpIgnoreScroll = 1 } - this.geom = this.getGeometry() - this._setPanelBoxStyle() this._maybeSetDockCss() this._setPanelPosition() @@ -363,6 +365,8 @@ export const Panel = GObject.registerClass( // most repaint requests don't actually require us to repaint anything. // This saves significant CPU when repainting the screen. this.set_offscreen_redirect(Clutter.OffscreenRedirect.ALWAYS) + + if (!Main.layoutManager._startingUp) this._resetGeometry() } disable() { @@ -582,6 +586,8 @@ export const Panel = GObject.registerClass( [ 'changed::panel-side-margins', 'changed::panel-top-bottom-margins', + 'changed::panel-side-padding', + 'changed::panel-top-bottom-padding', 'changed::panel-sizes', 'changed::group-apps', ], @@ -706,10 +712,14 @@ export const Panel = GObject.registerClass( let isVertical = this.checkIfVertical() let scaleFactor = Utils.getScaleFactor() let panelBoxTheme = this.panelBox.get_theme_node() - let leftPadding = panelBoxTheme.get_padding(St.Side.LEFT) - let lrPadding = leftPadding + panelBoxTheme.get_padding(St.Side.RIGHT) - let topPadding = panelBoxTheme.get_padding(St.Side.TOP) - let tbPadding = topPadding + panelBoxTheme.get_padding(St.Side.BOTTOM) + let sideMargins = + panelBoxTheme.get_padding(St.Side.LEFT) + + panelBoxTheme.get_padding(St.Side.RIGHT) + let topBottomMargins = + panelBoxTheme.get_padding(St.Side.TOP) + + panelBoxTheme.get_padding(St.Side.BOTTOM) + let sidePadding = SETTINGS.get_int('panel-side-padding') + let topBottomPadding = SETTINGS.get_int('panel-top-bottom-padding') let position = this.getPosition() let panelLength = PanelSettings.getPanelLength( SETTINGS, @@ -720,13 +730,23 @@ export const Panel = GObject.registerClass( let dockMode = false let length = (dynamic ? 100 : panelLength) / 100 let gsTopPanelOffset = 0 - let x = 0, - y = 0 - let w = 0, - h = 0 + let x = 0 + let y = 0 + let w = 0 + let h = 0 + let fixedPadding = 0 + let varPadding = 0 + let iconSize = 0 + let innerSize = 0 + let outerSize = 0 + let panelSize = PanelSettings.getPanelSize(SETTINGS, this.monitor.index) - const panelSize = PanelSettings.getPanelSize(SETTINGS, this.monitor.index) - this.dtpSize = panelSize * scaleFactor + if (isVertical && panelSize - sidePadding * 2 < MIN_PANEL_SIZE) + sidePadding = (panelSize - MIN_PANEL_SIZE) * 0.5 + else if (!isVertical && panelSize - topBottomPadding * 2 < MIN_PANEL_SIZE) + topBottomPadding = (panelSize - MIN_PANEL_SIZE) * 0.5 + + iconSize = innerSize = outerSize = panelSize if ( SETTINGS.get_boolean('stockgs-keep-top-panel') && @@ -738,59 +758,71 @@ export const Panel = GObject.registerClass( if (isVertical) { if (!SETTINGS.get_boolean('group-apps')) { // add window title width and side padding of _dtpIconContainer when vertical - this.dtpSize += + innerSize = outerSize += SETTINGS.get_int('group-apps-label-max-width') + (AppIcons.DEFAULT_PADDING_SIZE * 2) / scaleFactor } - ;(this.sizeFunc = 'get_preferred_height'), - (this.fixedCoord = { c1: 'x1', c2: 'x2' }) + this.sizeFunc = 'get_preferred_height' + this.fixedCoord = { c1: 'x1', c2: 'x2' } this.varCoord = { c1: 'y1', c2: 'y2' } - w = this.dtpSize - h = this.monitor.height * length - tbPadding - gsTopPanelOffset - dockMode = !!dynamic || tbPadding > 0 || h < this.monitor.height + w = innerSize + h = this.monitor.height * length - topBottomMargins - gsTopPanelOffset + dockMode = !!dynamic || topBottomMargins > 0 || h < this.monitor.height + fixedPadding = sidePadding * scaleFactor + varPadding = topBottomPadding * scaleFactor + outerSize += sideMargins } else { this.sizeFunc = 'get_preferred_width' this.fixedCoord = { c1: 'y1', c2: 'y2' } this.varCoord = { c1: 'x1', c2: 'x2' } - w = this.monitor.width * length - lrPadding - h = this.dtpSize - dockMode = !!dynamic || lrPadding > 0 || w < this.monitor.width + w = this.monitor.width * length - sideMargins + h = innerSize + dockMode = !!dynamic || sideMargins > 0 || w < this.monitor.width + fixedPadding = topBottomPadding * scaleFactor + varPadding = sidePadding * scaleFactor + outerSize += topBottomMargins } if (position == St.Side.TOP || position == St.Side.LEFT) { x = this.monitor.x y = this.monitor.y + gsTopPanelOffset } else if (position == St.Side.RIGHT) { - x = this.monitor.x + this.monitor.width - w - lrPadding + x = this.monitor.x + this.monitor.width - w - sideMargins y = this.monitor.y + gsTopPanelOffset } else { //BOTTOM x = this.monitor.x - y = this.monitor.y + this.monitor.height - h - tbPadding + y = this.monitor.y + this.monitor.height - h - topBottomMargins } if (length < 1) { // fixed size, less than 100%, so adjust start coordinate if (!isVertical && anchor == Pos.MIDDLE) - x += (this.monitor.width - w - lrPadding) * 0.5 + x += (this.monitor.width - w - sideMargins) * 0.5 else if (isVertical && anchor == Pos.MIDDLE) - y += (this.monitor.height - h - tbPadding) * 0.5 + y += (this.monitor.height - h - topBottomMargins) * 0.5 else if (!isVertical && anchor == Pos.END) - x += this.monitor.width - w - lrPadding + x += this.monitor.width - w - sideMargins else if (isVertical && anchor == Pos.END) - y += this.monitor.height - h - tbPadding + y += this.monitor.height - h - topBottomMargins } + innerSize -= fixedPadding * 2 + iconSize -= fixedPadding * 2 + return { x, y, w, h, - lrPadding, - tbPadding, + iconSize, // selected panel thickness in settings + innerSize, // excludes padding and margins + outerSize, // includes padding and margins + fixedPadding, + varPadding, position, dynamic, dockMode, @@ -829,12 +861,9 @@ export const Panel = GObject.registerClass( vfunc_allocate(box) { let fixed = 0 let centeredMonitorGroup - let panelAlloc = new Clutter.ActorBox({ - x1: 0, - x2: this.geom.w, - y1: 0, - y2: this.geom.h, - }) + let varSize = box[this.varCoord.c2] - box[this.varCoord.c1] + let fixedSize = box[this.fixedCoord.c2] - box[this.fixedCoord.c1] + let panelAlloc = new Clutter.ActorBox() let assignGroupSize = (group, update) => { group.size = 0 group.tlOffset = 0 @@ -842,8 +871,10 @@ export const Panel = GObject.registerClass( group.elements.forEach((element) => { if (!update) { - element.box[this.fixedCoord.c1] = panelAlloc[this.fixedCoord.c1] - element.box[this.fixedCoord.c2] = panelAlloc[this.fixedCoord.c2] + element.box[this.fixedCoord.c1] = + panelAlloc[this.fixedCoord.c1] + this.geom.fixedPadding + element.box[this.fixedCoord.c2] = + panelAlloc[this.fixedCoord.c2] - this.geom.fixedPadding element.natSize = element.actor[this.sizeFunc](-1)[1] } @@ -945,6 +976,9 @@ export const Panel = GObject.registerClass( ++fixed } + panelAlloc[this.varCoord.c2] = varSize + panelAlloc[this.fixedCoord.c2] = fixedSize + this._elementGroups.forEach((group) => { group.fixed = 0 @@ -959,35 +993,33 @@ export const Panel = GObject.registerClass( let dynamicGroup = this._elementGroups[0] // only one group if dynamic let tl = box[this.varCoord.c1] let br = box[this.varCoord.c2] + let groupSize = dynamicGroup.size + this.geom.varPadding * 2 if (this.geom.dynamic == Pos.STACKED_TL) { - br = Math.min(box[this.varCoord.c2], dynamicGroup.size) + br = Math.min(br, tl + groupSize) } else if (this.geom.dynamic == Pos.STACKED_BR) { - tl = Math.max(box[this.varCoord.c2] - dynamicGroup.size, 0) - br = box[this.varCoord.c2] + tl = Math.max(tl, br - groupSize) } else { // CENTERED_MONITOR - let half = Math.max( - 0, - (box[this.varCoord.c2] - - box[this.varCoord.c1] - - dynamicGroup.size) * - 0.5, - ) + let half = Math.max(0, Math.floor((br - tl - groupSize) * 0.5)) - tl = box[this.varCoord.c1] + half - br = box[this.varCoord.c2] - half + tl += half + br -= half } box[this.varCoord.c1] = tl box[this.varCoord.c2] = br - panelAlloc[this.varCoord.c2] = Math.min(dynamicGroup.size, br - tl) + panelAlloc[this.varCoord.c2] = Math.min(groupSize, br - tl) } this.set_allocation(box) this.panel.allocate(panelAlloc) + // apply padding to panel's children, after panel allocation + panelAlloc[this.varCoord.c1] += this.geom.varPadding + panelAlloc[this.varCoord.c2] -= this.geom.varPadding + if (centeredMonitorGroup) { allocateGroup( centeredMonitorGroup, @@ -1221,8 +1253,8 @@ export const Panel = GObject.registerClass( let [, natWidth] = actor.get_preferred_width(-1) child.x_align = Clutter.ActorAlign[isVertical ? 'CENTER' : 'START'] - actor.set_width(isVertical ? this.dtpSize : -1) - isVertical = isVertical && natWidth > this.dtpSize + actor.set_width(isVertical ? this.geom.innerSize : -1) + isVertical = isVertical && natWidth > this.geom.innerSize actor[(isVertical ? 'add' : 'remove') + '_style_class_name']( 'vertical', ) @@ -1270,7 +1302,7 @@ export const Panel = GObject.registerClass( clockText.ellipsize = Pango.EllipsizeMode.END } - clockText.natural_width = this.dtpSize + clockText.natural_width = this.geom.innerSize if (!time) { datetimeParts = datetime.split(' ') diff --git a/src/panelManager.js b/src/panelManager.js index cbfc3e0..db60755 100755 --- a/src/panelManager.js +++ b/src/panelManager.js @@ -374,7 +374,7 @@ export const PanelManager = class { case St.Side.TOP: this._desktopIconsUsableArea?.setMargins( p.monitor.index, - p.geom.h, + p.geom.outerSize, 0, 0, 0, @@ -384,7 +384,7 @@ export const PanelManager = class { this._desktopIconsUsableArea?.setMargins( p.monitor.index, 0, - p.geom.h, + p.geom.outerSize, 0, 0, ) @@ -394,7 +394,7 @@ export const PanelManager = class { p.monitor.index, 0, 0, - p.geom.w, + p.geom.outerSize, 0, ) break @@ -404,7 +404,7 @@ export const PanelManager = class { 0, 0, 0, - p.geom.w, + p.geom.outerSize, ) break } @@ -645,10 +645,6 @@ export const PanelManager = class { this.disable(true) this.allPanels = [] this.enable(true) - - // not ideal, but on startup the panel geometries are updated when the initial - // gnome-shell startup is complete, so simulate this here to update as well - Main.layoutManager.emit('startup-complete') } _updatePanelElementPositions() { @@ -692,7 +688,7 @@ export const PanelManager = class { global.dashToPanel.panels, (p) => p.monitor == monitor, ) - let excess = alloc.natural_size + panel.dtpSize + 10 - monitor.height // 10 is arbitrary + let excess = alloc.natural_size + panel.outerSize + 10 - monitor.height // 10 is arbitrary if (excess > 0) { alloc.natural_size -= excess @@ -921,7 +917,7 @@ function newUpdateHotCorners() { corner, Math.min(size, 32), ) - corner.setBarrierSize(panel ? panel.dtpSize : 32) + corner.setBarrierSize(panel ? panel.geom.innerSize : 32) this.hotCorners.push(corner) } else { this.hotCorners.push(null) @@ -1026,7 +1022,7 @@ function _newLookingGlassResize() { ) let topOffset = primaryMonitorPanel.getPosition() == St.Side.TOP - ? primaryMonitorPanel.dtpSize + 8 + ? primaryMonitorPanel.geom.outerSize + 8 : 32 this._oldResize() diff --git a/src/prefs.js b/src/prefs.js index 31ce52b..52be36d 100644 --- a/src/prefs.js +++ b/src/prefs.js @@ -38,7 +38,7 @@ import { } from 'resource:///org/gnome/Shell/Extensions/js/extensions/prefs.js' const SCALE_UPDATE_TIMEOUT = 500 -const DEFAULT_PANEL_SIZES = [128, 96, 64, 48, 32, 24, 16] +const DEFAULT_PANEL_SIZES = [128, 96, 64, 48, 32, 22] const DEFAULT_FONT_SIZES = [96, 64, 48, 32, 24, 16, 0] const DEFAULT_MARGIN_SIZES = [32, 24, 16, 12, 8, 4, 0] const DEFAULT_PADDING_SIZES = [32, 24, 16, 12, 8, 4, 0, -1] @@ -2999,6 +2999,16 @@ const Preferences = class { valueName: 'panel-side-margins', range: DEFAULT_MARGIN_SIZES, }, + { + objectName: 'panel_top_bottom_padding_scale', + valueName: 'panel-top-bottom-padding', + range: DEFAULT_MARGIN_SIZES, + }, + { + objectName: 'panel_side_padding_scale', + valueName: 'panel-side-padding', + range: DEFAULT_MARGIN_SIZES, + }, { objectName: 'appicon_padding_scale', valueName: 'appicon-padding', diff --git a/src/taskbar.js b/src/taskbar.js index f119ea1..92e07bc 100644 --- a/src/taskbar.js +++ b/src/taskbar.js @@ -224,7 +224,7 @@ export const TaskbarActor = GObject.registerClass( scrollview.allocate(childBox) - let [value, , upper, , , pageSize] = + let [, , upper, , , pageSize] = scrollview[orientation[0] + 'adjustment'].get_values() upper = Math.floor(upper) scrollview._dtpFadeSize = upper > pageSize ? this._delegate.iconSize : 0 @@ -246,12 +246,11 @@ export const TaskbarActor = GObject.registerClass( } childBox[panel.varCoord.c2] = - childBox[panel.varCoord.c1] + (value > 0 ? scrollview._dtpFadeSize : 0) + childBox[panel.varCoord.c1] + scrollview._dtpFadeSize leftFade.allocate(childBox) childBox[panel.varCoord.c1] = - box[panel.varCoord.c2] - - (value + pageSize < upper ? scrollview._dtpFadeSize : 0) + box[panel.varCoord.c2] - scrollview._dtpFadeSize childBox[panel.varCoord.c2] = box[panel.varCoord.c2] rightFade.allocate(childBox) } @@ -366,22 +365,22 @@ export const Taskbar = class extends EventEmitter { let orientation = panel.getOrientation() let fadeStyle = 'background-gradient-direction:' + orientation - let fade1 = new St.Widget({ + this._fadeLeft = new St.Widget({ style_class: 'scrollview-fade', reactive: false, }) - let fade2 = new St.Widget({ + this._fadeRight = new St.Widget({ style_class: 'scrollview-fade', reactive: false, pivot_point: new Graphene.Point({ x: 0.5, y: 0.5 }), rotation_angle_z: 180, }) - fade1.set_style(fadeStyle) - fade2.set_style(fadeStyle) + this._fadeLeft.set_style(fadeStyle) + this._fadeRight.set_style(fadeStyle) - this._container.add_child(fade1) - this._container.add_child(fade2) + this._container.add_child(this._fadeLeft) + this._container.add_child(this._fadeRight) this.previewMenu = new WindowPreview.PreviewMenu(panel) this.previewMenu.enable() @@ -604,9 +603,23 @@ export const Taskbar = class extends EventEmitter { } } + this._maybeUpdateScrollviewFade() + return Clutter.EVENT_PROPAGATE } + _maybeUpdateScrollviewFade(adjustment) { + if (this._scrollView._dtpFadeSize) { + adjustment = + adjustment || + this._scrollView[this.dtpPanel.getOrientation()[0] + 'adjustment'] + let [value, , upper, , , pageSize] = adjustment.get_values() + + this._fadeLeft.visible = value > 0 + this._fadeRight.visible = value + pageSize < upper + } + } + _onScrollEvent(actor, event) { let orientation = this.dtpPanel.getOrientation() @@ -641,12 +654,15 @@ export const Taskbar = class extends EventEmitter { adjustment.set_value(adjustment.get_value() + delta) + this._maybeUpdateScrollviewFade(adjustment) + return Clutter.EVENT_STOP } _onScrollSizeChange(adjustment) { // Update minimization animation target position on scrollview change. this._updateAppIcons() + this._maybeUpdateScrollviewFade() // When applications are ungrouped and there is some empty space on the horizontal taskbar, // force a fixed label width to prevent the icons from "wiggling" when an animation runs @@ -998,8 +1014,7 @@ export const Taskbar = class extends EventEmitter { } _adjustIconSize() { - const thisMonitorIndex = this.dtpPanel.monitor.index - let panelSize = PanelSettings.getPanelSize(SETTINGS, thisMonitorIndex) + let panelSize = this.dtpPanel.geom.iconSize let availSize = panelSize - SETTINGS.get_int('appicon-padding') * 2 let minIconSize = MIN_ICON_SIZE + (panelSize % 2) @@ -1658,7 +1673,9 @@ export const TaskbarItemContainer = GObject.registerClass( let travel = iconAnimationSettings.travel let zoom = iconAnimationSettings.zoom - return this._dtpPanel.dtpSize * Math.max(0, travel + (zoom - 1) / 2) + return ( + this._dtpPanel.geom.innerSize * Math.max(0, travel + (zoom - 1) / 2) + ) } _updateCloneContainerPosition(cloneContainer) { diff --git a/src/windowPreview.js b/src/windowPreview.js index 863d5e4..d9ee0de 100644 --- a/src/windowPreview.js +++ b/src/windowPreview.js @@ -78,7 +78,8 @@ export const PreviewMenu = GObject.registerClass( this._translationDirection = geom.position == St.Side.TOP || geom.position == St.Side.LEFT ? -1 : 1 this._translationOffset = - Math.min(panel.dtpSize, MAX_TRANSLATION) * this._translationDirection + Math.min(panel.geom.innerSize, MAX_TRANSLATION) * + this._translationDirection this.menu = new St.Widget({ name: 'preview-menu', @@ -465,6 +466,7 @@ export const PreviewMenu = GObject.registerClass( _updateClip() { let x, y, w let geom = this.panel.getGeometry() + let panelSize = geom.outerSize - geom.fixedPadding let panelBoxTheme = this.panel.panelBox.get_theme_node() let previewSize = (SETTINGS.get_int('window-preview-size') + @@ -484,26 +486,26 @@ export const PreviewMenu = GObject.registerClass( if (geom.position == St.Side.LEFT) { x = this.panel.monitor.x + - this.panel.dtpSize + - panelBoxTheme.get_padding(St.Side.LEFT) + panelSize - + panelBoxTheme.get_padding(St.Side.RIGHT) } else if (geom.position == St.Side.RIGHT) { x = this.panel.monitor.x + this.panel.monitor.width - - (this.panel.dtpSize + previewSize) - - panelBoxTheme.get_padding(St.Side.RIGHT) + (panelSize + previewSize) + + panelBoxTheme.get_padding(St.Side.LEFT) } else if (geom.position == St.Side.TOP) { y = this.panel.monitor.y + - this.panel.dtpSize + - panelBoxTheme.get_padding(St.Side.TOP) + panelSize - + panelBoxTheme.get_padding(St.Side.BOTTOM) } else { //St.Side.BOTTOM y = this.panel.monitor.y + this.panel.monitor.height - - (this.panel.dtpSize + - panelBoxTheme.get_padding(St.Side.BOTTOM) + + (panelSize - + panelBoxTheme.get_padding(St.Side.TOP) + previewSize + headerHeight) } diff --git a/ui/SettingsStyle.ui b/ui/SettingsStyle.ui index 4d8dde7..6028866 100644 --- a/ui/SettingsStyle.ui +++ b/ui/SettingsStyle.ui @@ -9,24 +9,36 @@ 0.01 1 - - 0.33 - 0.1 - 0.01 - 1 - - - 0.33 - 0.1 - 0.01 - 1 - 0.33 0.1 0.01 1 + + 0.33 + 0.1 + 0.01 + 1 + + + 0.33 + 0.1 + 0.01 + 1 + + + 0.33 + 0.1 + 0.01 + 1 + + + 0.33 + 0.1 + 0.01 + 1 + 10 5 @@ -266,7 +278,7 @@ Side margins - appicon_margin_todesktop_adjustment + panel_side_margins_adjustment 0 True 0 @@ -282,7 +294,39 @@ Top and bottom margins - appicon_margin_toscreenborder_adjustment + panel_top_bottom_margins_adjustment + 0 + True + 0 + right + 300 + + + + + + + (default is 0) + Side padding + + + panel_side_padding_adjustment + 0 + True + 0 + right + 300 + + + + + + + (default is 0) + Top and bottom padding + + + panel_top_bottom_padding_adjustment 0 True 0