2017-01-03 01:05:30 +03:00
/*
* Copyright 2016 Smith AR < audoban @ openmailbox . org >
* Michail Vourlakos < mvourlakos @ gmail . com >
*
* This file is part of Latte - Dock
*
* Latte - Dock is free software ; you can redistribute it and / or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation ; either version 2 of
* the License , or ( at your option ) any later version .
*
* Latte - Dock is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU General Public License for more details .
*
* You should have received a copy of the GNU General Public License
* along with this program . If not , see < http : //www.gnu.org/licenses/>.
*/
2016-12-25 10:25:27 +03:00
# include "visibilitymanager.h"
2016-12-29 08:40:35 +03:00
# include "visibilitymanager_p.h"
2018-02-03 12:34:13 +03:00
2016-12-31 00:27:39 +03:00
# include "dockview.h"
2018-11-29 22:30:00 +03:00
# include "positioner.h"
2018-03-28 20:39:52 +03:00
# include "screenedgeghostwindow.h"
2018-02-03 12:34:13 +03:00
# include "../dockcorona.h"
# include "../layoutmanager.h"
2018-08-02 14:23:01 +03:00
# include "../screenpool.h"
2018-02-03 12:34:13 +03:00
# include "../windowinfowrap.h"
# include "../../liblattedock/extras.h"
2016-12-25 10:25:27 +03:00
2018-03-28 20:39:52 +03:00
# include <KWayland/Client/plasmashell.h>
# include <KWayland/Client/surface.h>
2017-01-02 09:04:10 +03:00
# include <QDebug>
2016-12-31 03:26:48 +03:00
2016-12-29 08:40:35 +03:00
namespace Latte {
2016-12-25 10:25:27 +03:00
2016-12-29 08:40:35 +03:00
//! BEGIN: VisiblityManagerPrivate implementation
VisibilityManagerPrivate : : VisibilityManagerPrivate ( PlasmaQuick : : ContainmentView * view , VisibilityManager * q )
2018-03-02 00:53:28 +03:00
: QObject ( nullptr ) , q ( q ) , view ( view )
2016-12-29 08:40:35 +03:00
{
2018-01-13 20:27:32 +03:00
dockView = qobject_cast < DockView * > ( view ) ;
2017-12-24 21:54:45 +03:00
dockCorona = qobject_cast < DockCorona * > ( view - > corona ( ) ) ;
2018-03-02 00:53:28 +03:00
wm = dockCorona - > wm ( ) ;
2017-01-16 22:07:49 +03:00
2016-12-30 14:46:56 +03:00
if ( dockView ) {
2017-04-04 07:51:16 +03:00
connect ( dockView , & DockView : : eventTriggered , this , & VisibilityManagerPrivate : : viewEventManager ) ;
2017-02-11 06:12:17 +03:00
connect ( dockView , & DockView : : absGeometryChanged , this , & VisibilityManagerPrivate : : setDockGeometry ) ;
2016-12-30 14:46:56 +03:00
}
2017-01-16 22:07:49 +03:00
2017-04-02 12:24:49 +03:00
timerStartUp . setInterval ( 5000 ) ;
timerStartUp . setSingleShot ( true ) ;
2016-12-30 10:17:38 +03:00
timerCheckWindows . setInterval ( 350 ) ;
timerCheckWindows . setSingleShot ( true ) ;
timerShow . setSingleShot ( true ) ;
timerHide . setSingleShot ( true ) ;
connect ( & timerCheckWindows , & QTimer : : timeout , this , & VisibilityManagerPrivate : : checkAllWindows ) ;
2018-03-28 20:39:52 +03:00
connect ( & timerShow , & QTimer : : timeout , this , [ this , q ] ( ) {
2017-01-02 09:04:10 +03:00
if ( isHidden ) {
2017-01-28 20:34:03 +03:00
// qDebug() << "must be shown";
2017-03-12 21:09:38 +03:00
emit this - > q - > mustBeShown ( VisibilityManager : : QPrivateSignal { } ) ;
2017-01-02 09:04:10 +03:00
}
} ) ;
connect ( & timerHide , & QTimer : : timeout , this , [ this ] ( ) {
2017-01-03 20:36:40 +03:00
if ( ! blockHiding & & ! isHidden & & ! dragEnter ) {
2017-01-28 20:34:03 +03:00
// qDebug() << "must be hide";
2017-03-12 21:09:38 +03:00
emit this - > q - > mustBeHide ( VisibilityManager : : QPrivateSignal { } ) ;
2017-01-02 09:04:10 +03:00
}
} ) ;
2017-02-25 05:40:47 +03:00
wm - > setDockExtraFlags ( * view ) ;
wm - > addDock ( view - > winId ( ) ) ;
2017-02-27 02:43:48 +03:00
restoreConfig ( ) ;
2016-12-29 08:40:35 +03:00
}
2016-12-25 10:25:27 +03:00
2016-12-29 08:40:35 +03:00
VisibilityManagerPrivate : : ~ VisibilityManagerPrivate ( )
2016-12-25 10:25:27 +03:00
{
2017-03-13 04:52:31 +03:00
qDebug ( ) < < " VisibilityManagerPrivate deleting... " ;
2017-06-16 00:56:55 +03:00
wm - > removeDockStruts ( * view ) ;
2017-02-25 05:40:47 +03:00
wm - > removeDock ( view - > winId ( ) ) ;
2018-03-28 20:39:52 +03:00
if ( edgeGhostWindow ) {
edgeGhostWindow - > deleteLater ( ) ;
}
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : setMode ( Dock : : Visibility mode )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
if ( this - > mode = = mode )
return ;
2017-01-16 22:07:49 +03:00
2017-02-27 02:43:48 +03:00
Q_ASSERT_X ( mode ! = Dock : : None , q - > staticMetaObject . className ( ) , " set visibility to Dock::None " ) ;
2016-12-30 10:17:38 +03:00
// clear mode
for ( auto & c : connections ) {
disconnect ( c ) ;
}
2017-01-16 22:07:49 +03:00
2017-12-24 21:54:45 +03:00
if ( mode ! = Dock : : DodgeAllWindows & & ! enabledDynamicBackgroundFlag ) {
windows . clear ( ) ;
}
2017-03-12 12:01:27 +03:00
if ( this - > mode = = Dock : : AlwaysVisible ) {
2017-06-16 00:56:55 +03:00
wm - > removeDockStruts ( * view ) ;
2017-03-12 12:01:27 +03:00
} else {
connections [ 3 ] = connect ( wm , & WindowSystem : : currentDesktopChanged
2017-03-12 23:14:30 +03:00
, this , [ & ] {
2017-03-12 12:01:27 +03:00
if ( raiseOnDesktopChange )
raiseDockTemporarily ( ) ;
} ) ;
connections [ 4 ] = connect ( wm , & WindowSystem : : currentActivityChanged
2017-03-12 23:14:30 +03:00
, this , [ & ] ( ) {
if ( raiseOnActivityChange )
raiseDockTemporarily ( ) ;
else
updateHiddenState ( ) ;
2017-03-12 12:01:27 +03:00
} ) ;
}
2016-12-30 10:17:38 +03:00
timerShow . stop ( ) ;
timerHide . stop ( ) ;
timerCheckWindows . stop ( ) ;
this - > mode = mode ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:17:38 +03:00
switch ( this - > mode ) {
2016-12-30 10:24:04 +03:00
case Dock : : AlwaysVisible : {
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : WindowsGoBelow ) ;
}
2018-02-12 17:11:33 +03:00
if ( view - > containment ( ) & & ! dockView - > inEditMode ( ) & & view - > screen ( ) ) {
2018-01-13 21:00:03 +03:00
updateStrutsBasedOnLayoutsAndActivities ( ) ;
2017-03-23 08:03:45 +03:00
}
2017-01-16 22:07:49 +03:00
2017-01-14 00:33:42 +03:00
connections [ 0 ] = connect ( view - > containment ( ) , & Plasma : : Containment : : locationChanged
2017-01-16 21:24:46 +03:00
, this , [ & ] ( ) {
2018-02-12 17:11:33 +03:00
if ( dockView - > inEditMode ( ) )
2017-06-16 00:56:55 +03:00
wm - > removeDockStruts ( * view ) ;
2017-01-14 00:33:42 +03:00
} ) ;
2018-02-12 17:11:33 +03:00
connections [ 1 ] = connect ( dockView , & DockView : : inEditModeChanged
, this , [ & ] ( ) {
2018-11-29 22:30:00 +03:00
if ( ! dockView - > inEditMode ( ) & & ! dockView - > positioner ( ) - > inLocationChangeAnimation ( ) & & view - > screen ( ) )
2017-06-16 00:56:55 +03:00
wm - > setDockStruts ( * view , dockGeometry , view - > containment ( ) - > location ( ) ) ;
2017-01-14 00:33:42 +03:00
} ) ;
2018-01-13 20:27:32 +03:00
if ( dockCorona & & dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : MultipleLayouts ) {
connections [ 2 ] = connect ( dockCorona - > activitiesConsumer ( ) , & KActivities : : Consumer : : currentActivityChanged , this , [ & ] ( ) {
2018-01-13 21:00:03 +03:00
updateStrutsBasedOnLayoutsAndActivities ( ) ;
2018-01-13 20:27:32 +03:00
} ) ;
2018-01-14 14:21:11 +03:00
connections [ 3 ] = connect ( dockView , & DockView : : activitiesChanged , this , [ & ] ( ) {
updateStrutsBasedOnLayoutsAndActivities ( ) ;
} ) ;
2018-01-13 20:27:32 +03:00
}
2016-12-30 10:24:04 +03:00
raiseDock ( true ) ;
}
2016-12-30 10:17:38 +03:00
break ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:24:04 +03:00
case Dock : : AutoHide : {
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : AutoHide ) ;
}
2017-01-02 09:04:10 +03:00
raiseDock ( containsMouse ) ;
2016-12-30 10:24:04 +03:00
}
2016-12-30 10:17:38 +03:00
break ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:24:04 +03:00
case Dock : : DodgeActive : {
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : AutoHide ) ;
}
2017-03-12 12:01:27 +03:00
connections [ 0 ] = connect ( wm , & WindowSystem : : activeWindowChanged
2016-12-30 10:24:04 +03:00
, this , & VisibilityManagerPrivate : : dodgeActive ) ;
2017-03-12 12:01:27 +03:00
connections [ 1 ] = connect ( wm , & WindowSystem : : windowChanged
2016-12-30 10:24:04 +03:00
, this , & VisibilityManagerPrivate : : dodgeActive ) ;
dodgeActive ( wm - > activeWindow ( ) ) ;
2016-12-30 10:17:38 +03:00
}
2016-12-30 10:24:04 +03:00
break ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:24:04 +03:00
case Dock : : DodgeMaximized : {
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : AutoHide ) ;
}
2017-03-12 12:01:27 +03:00
connections [ 0 ] = connect ( wm , & WindowSystem : : activeWindowChanged
2016-12-30 10:24:04 +03:00
, this , & VisibilityManagerPrivate : : dodgeMaximized ) ;
2017-03-12 12:01:27 +03:00
connections [ 1 ] = connect ( wm , & WindowSystem : : windowChanged
2017-03-12 23:14:30 +03:00
, this , & VisibilityManagerPrivate : : dodgeMaximized ) ;
2017-01-02 09:04:10 +03:00
dodgeMaximized ( wm - > activeWindow ( ) ) ;
2016-12-30 10:24:04 +03:00
}
break ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:24:04 +03:00
case Dock : : DodgeAllWindows : {
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : AutoHide ) ;
}
2016-12-30 10:24:04 +03:00
for ( const auto & wid : wm - > windows ( ) ) {
2017-06-09 01:10:49 +03:00
windows . insert ( wid , wm - > requestInfo ( wid ) ) ;
2016-12-30 10:24:04 +03:00
}
2017-01-16 22:07:49 +03:00
2017-03-12 12:01:27 +03:00
connections [ 0 ] = connect ( wm , & WindowSystem : : windowChanged
2016-12-30 10:24:04 +03:00
, this , & VisibilityManagerPrivate : : dodgeWindows ) ;
2017-03-12 12:01:27 +03:00
connections [ 1 ] = connect ( wm , & WindowSystem : : windowRemoved
2017-06-09 01:10:49 +03:00
, this , [ & ] ( WindowId wid ) {
windows . remove ( wid ) ;
2016-12-30 10:17:38 +03:00
timerCheckWindows . start ( ) ;
2016-12-30 10:24:04 +03:00
} ) ;
2017-03-12 12:01:27 +03:00
connections [ 2 ] = connect ( wm , & WindowSystem : : windowAdded
2017-06-09 01:10:49 +03:00
, this , [ & ] ( WindowId wid ) {
windows . insert ( wid , wm - > requestInfo ( wid ) ) ;
2016-12-30 10:17:38 +03:00
timerCheckWindows . start ( ) ;
2016-12-30 10:24:04 +03:00
} ) ;
2017-02-12 11:01:12 +03:00
2017-01-02 09:04:10 +03:00
timerCheckWindows . start ( ) ;
2016-12-30 10:24:04 +03:00
}
2017-02-12 11:01:12 +03:00
break ;
2017-06-04 02:43:52 +03:00
2017-06-09 01:10:49 +03:00
case Dock : : WindowsGoBelow :
2018-03-28 20:39:52 +03:00
//set wayland visibility mode
if ( dockView - > surface ( ) ) {
dockView - > surface ( ) - > setPanelBehavior ( KWayland : : Client : : PlasmaShellSurface : : PanelBehavior : : WindowsGoBelow ) ;
}
2017-06-09 01:10:49 +03:00
break ;
default :
break ;
2016-12-30 10:17:38 +03:00
}
2017-01-16 22:07:49 +03:00
2017-04-02 08:23:47 +03:00
view - > containment ( ) - > config ( ) . writeEntry ( " visibility " , static_cast < int > ( mode ) ) ;
2017-03-12 12:01:27 +03:00
2018-03-28 20:39:52 +03:00
updateKWinEdgesSupport ( ) ;
2016-12-30 22:03:46 +03:00
emit q - > modeChanged ( ) ;
2017-03-12 12:01:27 +03:00
}
2018-01-13 21:00:03 +03:00
void VisibilityManagerPrivate : : updateStrutsBasedOnLayoutsAndActivities ( )
{
bool multipleLayoutsAndCurrent = ( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : MultipleLayouts
2018-11-29 22:30:00 +03:00
& & dockView - > managedLayout ( ) & & ! dockView - > positioner ( ) - > inLocationChangeAnimation ( )
2018-01-14 14:21:11 +03:00
& & dockView - > managedLayout ( ) - > name ( ) = = dockCorona - > layoutManager ( ) - > currentLayoutName ( ) ) ;
2018-01-13 21:00:03 +03:00
if ( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : SingleLayout | | multipleLayoutsAndCurrent ) {
wm - > setDockStruts ( * view , dockGeometry , view - > location ( ) ) ;
} else {
wm - > removeDockStruts ( * view ) ;
}
}
2017-03-12 12:01:27 +03:00
void VisibilityManagerPrivate : : setRaiseOnDesktop ( bool enable )
{
if ( enable = = raiseOnDesktopChange )
return ;
raiseOnDesktopChange = enable ;
emit q - > raiseOnDesktopChanged ( ) ;
}
void VisibilityManagerPrivate : : setRaiseOnActivity ( bool enable )
{
if ( enable = = raiseOnActivityChange )
return ;
raiseOnActivityChange = enable ;
emit q - > raiseOnActivityChanged ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : setIsHidden ( bool isHidden )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
if ( this - > isHidden = = isHidden )
return ;
2017-01-16 22:07:49 +03:00
2017-06-04 02:43:52 +03:00
if ( blockHiding & & isHidden ) {
2017-01-02 11:06:47 +03:00
qWarning ( ) < < " isHidden property is blocked, ignoring update " ;
return ;
}
2017-01-16 22:07:49 +03:00
2016-12-30 10:17:38 +03:00
this - > isHidden = isHidden ;
2018-03-28 20:39:52 +03:00
if ( q - > supportsKWinEdges ( ) ) {
bool inCurrentLayout = ( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : SingleLayout | |
( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : MultipleLayouts
2018-11-29 22:30:00 +03:00
& & dockView - > managedLayout ( ) & & ! dockView - > positioner ( ) - > inLocationChangeAnimation ( )
2018-03-28 20:39:52 +03:00
& & dockView - > managedLayout ( ) - > name ( ) = = dockCorona - > layoutManager ( ) - > currentLayoutName ( ) ) ) ;
if ( inCurrentLayout ) {
wm - > setEdgeStateFor ( edgeGhostWindow , isHidden ) ;
} else {
wm - > setEdgeStateFor ( edgeGhostWindow , false ) ;
}
}
2016-12-30 10:17:38 +03:00
emit q - > isHiddenChanged ( ) ;
2016-12-29 08:40:35 +03:00
}
2016-12-25 10:25:27 +03:00
2017-01-02 11:06:47 +03:00
void VisibilityManagerPrivate : : setBlockHiding ( bool blockHiding )
{
if ( this - > blockHiding = = blockHiding )
return ;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
this - > blockHiding = blockHiding ;
2017-01-28 20:34:03 +03:00
// qDebug() << "blockHiding:" << blockHiding;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
if ( this - > blockHiding ) {
timerHide . stop ( ) ;
2017-01-16 22:07:49 +03:00
2017-01-04 03:52:31 +03:00
if ( isHidden ) {
2017-03-12 21:09:38 +03:00
emit q - > mustBeShown ( VisibilityManager : : QPrivateSignal { } ) ;
2017-01-04 03:52:31 +03:00
}
2017-01-02 11:06:47 +03:00
} else {
updateHiddenState ( ) ;
}
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
emit q - > blockHidingChanged ( ) ;
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : setTimerShow ( int msec )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
timerShow . setInterval ( msec ) ;
emit q - > timerShowChanged ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : setTimerHide ( int msec )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
timerHide . setInterval ( msec ) ;
emit q - > timerHideChanged ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : raiseDock ( bool raise )
2016-12-25 10:25:27 +03:00
{
2017-03-12 20:16:23 +03:00
if ( blockHiding )
return ;
2016-12-29 08:40:35 +03:00
if ( raise ) {
timerHide . stop ( ) ;
2017-01-16 22:07:49 +03:00
2016-12-30 21:24:21 +03:00
if ( ! timerShow . isActive ( ) ) {
2016-12-29 08:40:35 +03:00
timerShow . start ( ) ;
2016-12-30 14:46:56 +03:00
}
2017-03-12 20:16:23 +03:00
} else if ( ! dragEnter ) {
2016-12-29 08:40:35 +03:00
timerShow . stop ( ) ;
2017-01-16 22:07:49 +03:00
2017-02-12 11:01:12 +03:00
if ( hideNow ) {
hideNow = false ;
2017-03-12 21:09:38 +03:00
emit q - > mustBeHide ( VisibilityManager : : QPrivateSignal { } ) ;
2018-11-13 20:06:33 +03:00
} else if ( ! timerHide . isActive ( ) ) {
2016-12-29 08:40:35 +03:00
timerHide . start ( ) ;
2018-11-13 20:06:33 +03:00
}
2016-12-29 08:40:35 +03:00
}
2016-12-25 10:25:27 +03:00
}
2017-02-12 11:01:12 +03:00
void VisibilityManagerPrivate : : raiseDockTemporarily ( )
{
2017-03-12 12:01:27 +03:00
if ( raiseTemporarily )
2017-02-12 11:01:12 +03:00
return ;
raiseTemporarily = true ;
timerHide . stop ( ) ;
timerShow . stop ( ) ;
if ( isHidden )
2017-03-12 21:09:38 +03:00
emit q - > mustBeShown ( VisibilityManager : : QPrivateSignal { } ) ;
2017-02-12 11:01:12 +03:00
2017-03-12 14:21:34 +03:00
QTimer : : singleShot ( qBound ( 1800 , 2 * timerHide . interval ( ) , 3000 ) , this , [ & ] ( ) {
2017-03-08 00:26:09 +03:00
raiseTemporarily = false ;
hideNow = true ;
updateHiddenState ( ) ;
2017-02-12 11:01:12 +03:00
} ) ;
}
2017-01-02 11:06:47 +03:00
void VisibilityManagerPrivate : : updateHiddenState ( )
{
2017-01-03 20:36:40 +03:00
if ( dragEnter )
return ;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
switch ( mode ) {
case Dock : : AutoHide :
2017-01-03 20:36:40 +03:00
raiseDock ( containsMouse ) ;
2017-01-02 11:06:47 +03:00
break ;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
case Dock : : DodgeActive :
dodgeActive ( wm - > activeWindow ( ) ) ;
break ;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
case Dock : : DodgeMaximized :
dodgeMaximized ( wm - > activeWindow ( ) ) ;
break ;
2017-01-16 22:07:49 +03:00
2017-01-02 11:06:47 +03:00
case Dock : : DodgeAllWindows :
dodgeWindows ( wm - > activeWindow ( ) ) ;
break ;
2017-08-13 13:00:46 +03:00
2017-06-09 01:10:49 +03:00
default :
break ;
2017-01-02 11:06:47 +03:00
}
}
2017-02-11 06:12:17 +03:00
inline void VisibilityManagerPrivate : : setDockGeometry ( const QRect & geometry )
2016-12-25 10:25:27 +03:00
{
2017-04-29 12:13:21 +03:00
if ( ! view - > containment ( ) )
2016-12-30 10:17:38 +03:00
return ;
2017-01-16 22:07:49 +03:00
2017-02-11 06:12:17 +03:00
this - > dockGeometry = geometry ;
2017-01-16 22:07:49 +03:00
2018-02-12 17:11:33 +03:00
if ( mode = = Dock : : AlwaysVisible & & ! dockView - > inEditMode ( ) & & view - > screen ( ) ) {
2018-01-13 21:00:03 +03:00
updateStrutsBasedOnLayoutsAndActivities ( ) ;
2016-12-30 10:17:38 +03:00
}
2016-12-25 10:25:27 +03:00
}
2018-01-21 12:53:15 +03:00
void VisibilityManagerPrivate : : setWindowOnActivities ( QWindow & window , const QStringList & activities )
2018-01-13 13:55:13 +03:00
{
2018-01-21 12:53:15 +03:00
wm - > setWindowOnActivities ( window , activities ) ;
2018-01-13 13:55:13 +03:00
}
2018-03-28 20:39:52 +03:00
void VisibilityManagerPrivate : : applyActivitiesToHiddenWindows ( const QStringList & activities )
{
if ( edgeGhostWindow ) {
wm - > setWindowOnActivities ( * edgeGhostWindow , activities ) ;
}
}
2017-06-09 01:10:49 +03:00
void VisibilityManagerPrivate : : dodgeActive ( WindowId wid )
2016-12-25 10:25:27 +03:00
{
2017-02-12 11:01:12 +03:00
if ( raiseTemporarily )
return ;
2018-08-30 08:47:53 +03:00
//!don't send false raiseDock signal when containing mouse
2017-08-13 13:24:32 +03:00
if ( containsMouse ) {
raiseDock ( true ) ;
return ;
}
2016-12-30 10:17:38 +03:00
auto winfo = wm - > requestInfo ( wid ) ;
2017-01-16 22:07:49 +03:00
2018-09-01 17:45:08 +03:00
if ( ! winfo . isValid ( ) | | ! winfo . isActive ( ) ) {
2017-03-12 12:01:27 +03:00
winfo = wm - > requestInfo ( wm - > activeWindow ( ) ) ;
2018-08-31 15:27:21 +03:00
if ( ! winfo . isValid ( ) ) {
//! very rare case that window manager doesnt have any active window at all
raiseDock ( true ) ;
return ;
}
2017-01-02 09:04:10 +03:00
}
2017-01-16 22:07:49 +03:00
2018-08-31 16:49:47 +03:00
//! don't send false raiseDock signal when containing mouse, // Johan comment
//! I dont know why that wasnt winfo.wid() //active window, but just wid//the window that made the call
if ( wm - > isOnCurrentDesktop ( winfo . wid ( ) ) & & wm - > isOnCurrentActivity ( winfo . wid ( ) ) ) {
2018-09-01 17:45:08 +03:00
bool overlaps { intersects ( winfo ) } ;
raiseDock ( ! overlaps ) ;
2017-08-13 13:00:46 +03:00
}
2016-12-25 10:25:27 +03:00
}
2017-06-09 01:10:49 +03:00
void VisibilityManagerPrivate : : dodgeMaximized ( WindowId wid )
2016-12-25 10:25:27 +03:00
{
2017-02-12 11:01:12 +03:00
if ( raiseTemporarily )
return ;
2018-08-30 08:47:53 +03:00
//!don't send false raiseDock signal when containing mouse
2017-08-13 13:24:32 +03:00
if ( containsMouse ) {
raiseDock ( true ) ;
return ;
}
2016-12-30 10:17:38 +03:00
auto winfo = wm - > requestInfo ( wid ) ;
2017-01-16 22:07:49 +03:00
2018-09-01 17:45:08 +03:00
if ( ! winfo . isValid ( ) | | ! winfo . isActive ( ) ) {
2017-03-12 12:01:27 +03:00
winfo = wm - > requestInfo ( wm - > activeWindow ( ) ) ;
2018-08-31 15:27:21 +03:00
if ( ! winfo . isValid ( ) ) {
//! very rare case that window manager doesnt have any active window at all
raiseDock ( true ) ;
return ;
}
2017-01-02 09:04:10 +03:00
}
2017-01-16 22:07:49 +03:00
2018-09-01 17:45:08 +03:00
auto intersectsMaxVert = [ & ] ( ) noexcept - > bool {
2018-03-08 19:08:55 +03:00
return ( ( winfo . isMaxVert ( )
| | ( view - > screen ( ) & & view - > screen ( ) - > availableSize ( ) . height ( ) < = winfo . geometry ( ) . height ( ) ) )
& & intersects ( winfo ) ) ;
2017-03-24 06:15:04 +03:00
} ;
2018-09-01 17:45:08 +03:00
auto intersectsMaxHoriz = [ & ] ( ) noexcept - > bool {
2018-03-08 19:08:55 +03:00
return ( ( winfo . isMaxHoriz ( )
| | ( view - > screen ( ) & & view - > screen ( ) - > availableSize ( ) . width ( ) < = winfo . geometry ( ) . width ( ) ) )
& & intersects ( winfo ) ) ;
2017-03-24 06:15:04 +03:00
} ;
2018-08-31 16:49:47 +03:00
//! don't send false raiseDock signal when containing mouse, // Johan comment
//! I dont know why that wasnt winfo.wid() //active window, but just wid//the window that made the call
if ( wm - > isOnCurrentDesktop ( winfo . wid ( ) ) & & wm - > isOnCurrentActivity ( winfo . wid ( ) ) ) {
2018-09-01 17:45:08 +03:00
bool overlapsMaximized { view - > formFactor ( ) = = Plasma : : Types : : Vertical ? intersectsMaxHoriz ( ) : intersectsMaxVert ( ) } ;
raiseDock ( ! overlapsMaximized ) ;
2018-08-31 16:49:47 +03:00
}
2016-12-25 10:25:27 +03:00
}
2017-06-09 01:10:49 +03:00
void VisibilityManagerPrivate : : dodgeWindows ( WindowId wid )
2016-12-25 10:25:27 +03:00
{
2017-02-12 11:01:12 +03:00
if ( raiseTemporarily )
return ;
2017-01-02 09:04:10 +03:00
if ( windows . find ( wid ) = = std : : end ( windows ) )
return ;
2017-01-16 22:07:49 +03:00
2018-08-30 08:47:53 +03:00
//!don't send false raiseDock signal when containing mouse
2017-08-13 13:24:32 +03:00
if ( containsMouse ) {
raiseDock ( true ) ;
return ;
}
2017-03-15 10:24:24 +03:00
windows [ wid ] = wm - > requestInfo ( wid ) ;
auto & winfo = windows [ wid ] ;
2017-01-16 22:07:49 +03:00
2017-06-21 03:06:04 +03:00
if ( ! winfo . isValid ( ) | | ! wm - > isOnCurrentDesktop ( wid ) | | ! wm - > isOnCurrentActivity ( wid ) )
2016-12-30 10:17:38 +03:00
return ;
2017-01-16 22:07:49 +03:00
2017-08-13 13:24:32 +03:00
if ( intersects ( winfo ) )
2016-12-30 10:17:38 +03:00
raiseDock ( false ) ;
else
timerCheckWindows . start ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
void VisibilityManagerPrivate : : checkAllWindows ( )
2016-12-25 10:25:27 +03:00
{
2017-02-12 11:01:12 +03:00
if ( raiseTemporarily )
return ;
2016-12-30 10:17:38 +03:00
bool raise { true } ;
2018-01-04 19:36:41 +03:00
bool existsFaultyWindow { false } ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:17:38 +03:00
for ( const auto & winfo : windows ) {
2017-06-15 00:10:31 +03:00
// <WindowId, WindowInfoWrap>
2018-01-04 19:36:41 +03:00
if ( winfo . geometry ( ) = = QRect ( 0 , 0 , 0 , 0 ) ) {
existsFaultyWindow = true ;
}
2017-06-21 03:06:04 +03:00
if ( ! winfo . isValid ( ) | | ! wm - > isOnCurrentDesktop ( winfo . wid ( ) ) | | ! wm - > isOnCurrentActivity ( winfo . wid ( ) ) )
2016-12-30 10:17:38 +03:00
continue ;
2017-01-16 22:07:49 +03:00
2017-06-09 01:10:49 +03:00
if ( winfo . isFullscreen ( ) ) {
2016-12-30 10:17:38 +03:00
raise = false ;
break ;
2017-06-09 01:10:49 +03:00
} else if ( intersects ( winfo ) ) {
2016-12-30 10:17:38 +03:00
raise = false ;
break ;
}
}
2017-01-16 22:07:49 +03:00
2018-01-04 19:36:41 +03:00
cleanupFaultyWindows ( ) ;
2016-12-30 10:17:38 +03:00
raiseDock ( raise ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline bool VisibilityManagerPrivate : : intersects ( const WindowInfoWrap & winfo )
2016-12-25 10:25:27 +03:00
{
2017-03-24 06:06:59 +03:00
return ( ! winfo . isMinimized ( )
& & winfo . geometry ( ) . intersects ( dockGeometry )
& & ! winfo . isShaded ( ) ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : saveConfig ( )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
if ( ! view - > containment ( ) )
return ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:17:38 +03:00
auto config = view - > containment ( ) - > config ( ) ;
2017-04-02 08:23:47 +03:00
2018-03-28 20:39:52 +03:00
config . writeEntry ( " enableKWinEdges " , enableKWinEdgesFromUser ) ;
2016-12-30 10:17:38 +03:00
config . writeEntry ( " timerShow " , timerShow . interval ( ) ) ;
config . writeEntry ( " timerHide " , timerHide . interval ( ) ) ;
2017-03-12 20:05:02 +03:00
config . writeEntry ( " raiseOnDesktopChange " , raiseOnDesktopChange ) ;
config . writeEntry ( " raiseOnActivityChange " , raiseOnActivityChange ) ;
2018-03-28 20:39:52 +03:00
2016-12-30 10:17:38 +03:00
view - > containment ( ) - > configNeedsSaving ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
inline void VisibilityManagerPrivate : : restoreConfig ( )
2016-12-25 10:25:27 +03:00
{
2016-12-30 10:17:38 +03:00
if ( ! view - > containment ( ) )
2016-12-30 10:24:04 +03:00
return ;
2017-01-16 22:07:49 +03:00
2016-12-30 10:24:04 +03:00
auto config = view - > containment ( ) - > config ( ) ;
2018-03-30 11:17:03 +03:00
timerShow . setInterval ( config . readEntry ( " timerShow " , 0 ) ) ;
2017-01-12 14:53:06 +03:00
timerHide . setInterval ( config . readEntry ( " timerHide " , 700 ) ) ;
2016-12-30 22:33:42 +03:00
emit q - > timerShowChanged ( ) ;
emit q - > timerHideChanged ( ) ;
2017-02-11 08:55:22 +03:00
2018-03-28 20:39:52 +03:00
enableKWinEdgesFromUser = config . readEntry ( " enableKWinEdges " , true ) ;
emit q - > enableKWinEdgesChanged ( ) ;
2017-03-26 00:17:41 +03:00
setRaiseOnDesktop ( config . readEntry ( " raiseOnDesktopChange " , false ) ) ;
setRaiseOnActivity ( config . readEntry ( " raiseOnActivityChange " , false ) ) ;
2017-04-02 08:23:47 +03:00
auto mode = [ & ] ( ) {
2017-06-04 02:43:52 +03:00
return static_cast < Dock : : Visibility > ( view - > containment ( ) - > config ( )
. readEntry ( " visibility " , static_cast < int > ( Dock : : DodgeActive ) ) ) ;
2017-04-02 08:23:47 +03:00
} ;
if ( mode ( ) = = Dock : : AlwaysVisible ) {
setMode ( Dock : : AlwaysVisible ) ;
2017-02-12 11:01:12 +03:00
} else {
2017-06-04 02:43:52 +03:00
connect ( & timerStartUp , & QTimer : : timeout , this , [ & , mode ] ( ) {
2017-04-02 08:23:47 +03:00
setMode ( mode ( ) ) ;
2017-02-11 08:55:22 +03:00
} ) ;
2017-04-02 12:24:49 +03:00
connect ( view - > containment ( ) , & Plasma : : Containment : : userConfiguringChanged
2017-06-04 02:43:52 +03:00
, this , [ & ] ( bool configuring ) {
2017-04-02 12:24:49 +03:00
if ( configuring & & timerStartUp . isActive ( ) )
timerStartUp . start ( 100 ) ;
} ) ;
timerStartUp . start ( ) ;
2017-02-11 08:55:22 +03:00
}
2017-03-12 12:01:27 +03:00
connect ( view - > containment ( ) , & Plasma : : Containment : : userConfiguringChanged
2017-03-12 23:14:30 +03:00
, this , [ & ] ( bool configuring ) {
2017-03-12 21:30:54 +03:00
if ( ! configuring )
saveConfig ( ) ;
2017-03-12 12:01:27 +03:00
} ) ;
2016-12-25 10:25:27 +03:00
}
2018-11-13 20:06:33 +03:00
void VisibilityManagerPrivate : : setContainsMouse ( bool contains )
2016-12-25 10:25:27 +03:00
{
2018-11-13 20:06:33 +03:00
if ( containsMouse = = contains ) {
return ;
}
2017-01-16 22:07:49 +03:00
2018-11-13 20:06:33 +03:00
containsMouse = contains ;
emit q - > containsMouseChanged ( ) ;
2017-01-16 22:07:49 +03:00
2018-11-13 20:06:33 +03:00
if ( contains & & mode ! = Dock : : AlwaysVisible ) {
raiseDock ( true ) ;
}
}
2017-01-16 22:07:49 +03:00
2018-11-13 20:06:33 +03:00
void VisibilityManagerPrivate : : viewEventManager ( QEvent * ev )
{
switch ( ev - > type ( ) ) {
case QEvent : : Enter :
setContainsMouse ( true ) ;
2017-01-03 20:36:40 +03:00
break ;
2017-01-16 22:07:49 +03:00
2017-01-05 18:48:27 +03:00
case QEvent : : Leave :
2018-11-13 20:06:33 +03:00
setContainsMouse ( false ) ;
2017-01-05 18:48:27 +03:00
updateHiddenState ( ) ;
2018-11-13 20:06:33 +03:00
2017-01-05 18:48:27 +03:00
break ;
2017-01-16 22:07:49 +03:00
2017-01-05 18:48:27 +03:00
case QEvent : : DragEnter :
dragEnter = true ;
2017-03-12 23:14:30 +03:00
2017-03-12 21:09:38 +03:00
if ( isHidden )
emit q - > mustBeShown ( VisibilityManager : : QPrivateSignal { } ) ;
2017-01-05 18:48:27 +03:00
break ;
2017-01-16 22:07:49 +03:00
2017-01-05 18:48:27 +03:00
case QEvent : : DragLeave :
case QEvent : : Drop :
dragEnter = false ;
updateHiddenState ( ) ;
break ;
2017-01-16 22:07:49 +03:00
2017-01-05 18:48:27 +03:00
case QEvent : : Show :
2017-02-25 05:40:47 +03:00
wm - > setDockExtraFlags ( * view ) ;
2017-01-03 20:36:40 +03:00
break ;
2017-06-09 01:10:49 +03:00
default :
break ;
2016-12-25 10:25:27 +03:00
}
}
2017-12-24 21:54:45 +03:00
2018-01-04 19:36:41 +03:00
void VisibilityManagerPrivate : : cleanupFaultyWindows ( )
{
foreach ( auto key , windows . keys ( ) ) {
auto winfo = windows [ key ] ;
//! garbage windows removing
if ( winfo . geometry ( ) = = QRect ( 0 , 0 , 0 , 0 ) ) {
//qDebug() << "Faulty Geometry ::: " << winfo.wid();
windows . remove ( key ) ;
}
}
}
2017-12-24 21:54:45 +03:00
//! Dynamic Background functions
void VisibilityManagerPrivate : : setEnabledDynamicBackground ( bool active )
{
if ( enabledDynamicBackgroundFlag = = active ) {
return ;
}
enabledDynamicBackgroundFlag = active ;
if ( active ) {
if ( mode ! = Dock : : DodgeAllWindows ) {
for ( const auto & wid : wm - > windows ( ) ) {
windows . insert ( wid , wm - > requestInfo ( wid ) ) ;
}
}
connectionsDynBackground [ 0 ] = connect ( view - > corona ( ) , & Plasma : : Corona : : availableScreenRectChanged ,
this , & VisibilityManagerPrivate : : updateAvailableScreenGeometry ) ;
connectionsDynBackground [ 1 ] = connect ( wm , & WindowSystem : : windowChanged , this , [ & ] ( WindowId wid ) {
windows [ wid ] = wm - > requestInfo ( wid ) ;
updateDynamicBackgroundWindowFlags ( ) ;
} ) ;
connectionsDynBackground [ 2 ] = connect ( wm , & WindowSystem : : windowRemoved , this , [ & ] ( WindowId wid ) {
windows . remove ( wid ) ;
} ) ;
connectionsDynBackground [ 3 ] = connect ( wm , & WindowSystem : : windowAdded , this , [ & ] ( WindowId wid ) {
windows . insert ( wid , wm - > requestInfo ( wid ) ) ;
updateDynamicBackgroundWindowFlags ( ) ;
} ) ;
connectionsDynBackground [ 4 ] = connect ( wm , & WindowSystem : : activeWindowChanged , this , [ & ] ( WindowId wid ) {
if ( windows . contains ( lastActiveWindowWid ) ) {
windows [ lastActiveWindowWid ] = wm - > requestInfo ( lastActiveWindowWid ) ;
}
windows [ wid ] = wm - > requestInfo ( wid ) ;
lastActiveWindowWid = wid ;
updateDynamicBackgroundWindowFlags ( ) ;
} ) ;
connectionsDynBackground [ 5 ] = connect ( wm , & WindowSystem : : currentDesktopChanged , this , [ & ] {
updateDynamicBackgroundWindowFlags ( ) ;
} ) ;
connectionsDynBackground [ 6 ] = connect ( wm , & WindowSystem : : currentActivityChanged , this , [ & ] {
updateDynamicBackgroundWindowFlags ( ) ;
} ) ;
updateAvailableScreenGeometry ( ) ;
updateDynamicBackgroundWindowFlags ( ) ;
} else {
// clear mode
for ( auto & c : connectionsDynBackground ) {
disconnect ( c ) ;
}
if ( mode ! = Dock : : DodgeAllWindows ) {
windows . clear ( ) ;
}
2018-12-01 13:27:49 +03:00
// ATTENTION: this was creating a crash under wayland environment through the blur effect
// setExistsWindowMaximized(false);
// setExistsWindowSnapped(false);
2017-12-24 21:54:45 +03:00
}
emit q - > enabledDynamicBackgroundChanged ( ) ;
}
void VisibilityManagerPrivate : : setExistsWindowMaximized ( bool windowMaximized )
{
if ( windowIsMaximizedFlag = = windowMaximized ) {
return ;
}
windowIsMaximizedFlag = windowMaximized ;
emit q - > existsWindowMaximizedChanged ( ) ;
}
void VisibilityManagerPrivate : : setExistsWindowSnapped ( bool windowSnapped )
{
if ( windowIsSnappedFlag = = windowSnapped ) {
return ;
}
windowIsSnappedFlag = windowSnapped ;
emit q - > existsWindowSnappedChanged ( ) ;
}
2018-10-14 13:54:09 +03:00
void VisibilityManagerPrivate : : setTouchingWindowScheme ( SchemeColors * scheme )
{
if ( touchingScheme = = scheme ) {
return ;
}
touchingScheme = scheme ;
emit q - > touchingWindowSchemeChanged ( ) ;
}
2017-12-24 21:54:45 +03:00
void VisibilityManagerPrivate : : updateAvailableScreenGeometry ( )
{
if ( ! view | | ! view - > containment ( ) ) {
return ;
}
2018-12-01 16:22:33 +03:00
int currentScrId = dockCorona - > screenPool ( ) - > id ( dockView - > positioner ( ) - > currentScreenName ( ) ) ;
2018-08-02 14:23:01 +03:00
QRect tempAvailableScreenGeometry = dockCorona - > availableScreenRectWithCriteria ( currentScrId , { Dock : : AlwaysVisible } , { } ) ;
2017-12-24 21:54:45 +03:00
if ( tempAvailableScreenGeometry ! = availableScreenGeometry ) {
availableScreenGeometry = tempAvailableScreenGeometry ;
snappedWindowsGeometries . clear ( ) ;
//! for top dock the snapped geometries would be
int halfWidth1 = std : : floor ( availableScreenGeometry . width ( ) / 2 ) ;
int halfWidth2 = availableScreenGeometry . width ( ) - halfWidth1 ;
int halfHeight1 = std : : floor ( ( availableScreenGeometry . height ( ) ) / 2 ) ;
int halfHeight2 = availableScreenGeometry . height ( ) - halfHeight1 ;
int x1 = availableScreenGeometry . x ( ) ;
int x2 = availableScreenGeometry . x ( ) + halfWidth1 ;
int y1 = availableScreenGeometry . y ( ) ;
int y2 = availableScreenGeometry . y ( ) + halfHeight1 ;
QRect snap1 ;
QRect snap2 ;
QRect snap3 ;
QRect snap4 ;
if ( view - > formFactor ( ) = = Plasma : : Types : : Horizontal ) {
if ( view - > location ( ) = = Plasma : : Types : : TopEdge ) {
snap1 = QRect ( x1 , y1 , halfWidth1 , halfHeight1 ) ;
snap3 = QRect ( x2 , y1 , halfWidth2 , halfHeight1 ) ;
} else if ( ( view - > location ( ) = = Plasma : : Types : : BottomEdge ) ) {
snap1 = QRect ( x1 , y2 , halfWidth1 , halfHeight2 ) ;
snap3 = QRect ( x2 , y2 , halfWidth2 , halfHeight2 ) ;
}
snap2 = QRect ( x1 , y1 , halfWidth1 , availableScreenGeometry . height ( ) ) ;
snap4 = QRect ( x2 , y1 , halfWidth2 , availableScreenGeometry . height ( ) ) ;
} else if ( view - > formFactor ( ) = = Plasma : : Types : : Vertical ) {
QRect snap5 ;
if ( view - > location ( ) = = Plasma : : Types : : LeftEdge ) {
snap1 = QRect ( x1 , y1 , halfWidth1 , halfHeight1 ) ;
snap3 = QRect ( x1 , y2 , halfWidth1 , halfHeight2 ) ;
snap5 = QRect ( x1 , y1 , halfWidth1 , availableScreenGeometry . height ( ) ) ;
} else if ( ( view - > location ( ) = = Plasma : : Types : : RightEdge ) ) {
snap1 = QRect ( x2 , y1 , halfWidth2 , halfHeight1 ) ;
snap3 = QRect ( x2 , y2 , halfWidth2 , halfHeight2 ) ;
snap5 = QRect ( x2 , y1 , halfWidth2 , availableScreenGeometry . height ( ) ) ;
}
snap2 = QRect ( x1 , y1 , availableScreenGeometry . width ( ) , halfHeight1 ) ;
snap4 = QRect ( x1 , y2 , availableScreenGeometry . width ( ) , halfHeight2 ) ;
snappedWindowsGeometries . append ( snap5 ) ;
}
snappedWindowsGeometries . append ( snap1 ) ;
snappedWindowsGeometries . append ( snap2 ) ;
snappedWindowsGeometries . append ( snap3 ) ;
snappedWindowsGeometries . append ( snap4 ) ;
updateDynamicBackgroundWindowFlags ( ) ;
}
}
2018-10-26 18:47:13 +03:00
bool VisibilityManagerPrivate : : isMaximizedInCurrentScreen ( const WindowInfoWrap & winfo )
{
//! updated implementation to identify the screen that the maximized window is present
//! in order to avoid: https://bugs.kde.org/show_bug.cgi?id=397700
if ( winfo . isValid ( ) & & ! winfo . isMinimized ( ) & & wm - > isOnCurrentDesktop ( winfo . wid ( ) ) & & wm - > isOnCurrentActivity ( winfo . wid ( ) ) ) {
if ( winfo . isMaximized ( ) & & availableScreenGeometry . contains ( winfo . geometry ( ) . center ( ) ) ) {
return true ;
}
}
return false ;
}
bool VisibilityManagerPrivate : : isTouchingPanelEdge ( const WindowInfoWrap & winfo )
{
if ( winfo . isValid ( ) & & ! winfo . isMinimized ( ) & & wm - > isOnCurrentDesktop ( winfo . wid ( ) ) & & wm - > isOnCurrentActivity ( winfo . wid ( ) ) ) {
bool touchingPanelEdge { false } ;
QRect screenGeometry = dockView - > screenGeometry ( ) ;
bool inCurrentScreen { screenGeometry . contains ( winfo . geometry ( ) . topLeft ( ) ) | | screenGeometry . contains ( winfo . geometry ( ) . bottomRight ( ) ) } ;
if ( inCurrentScreen ) {
if ( view - > location ( ) = = Plasma : : Types : : TopEdge ) {
touchingPanelEdge = ( winfo . geometry ( ) . y ( ) = = availableScreenGeometry . y ( ) ) ;
} else if ( view - > location ( ) = = Plasma : : Types : : BottomEdge ) {
touchingPanelEdge = ( winfo . geometry ( ) . bottom ( ) = = availableScreenGeometry . bottom ( ) ) ;
} else if ( view - > location ( ) = = Plasma : : Types : : LeftEdge ) {
touchingPanelEdge = ( winfo . geometry ( ) . x ( ) = = availableScreenGeometry . x ( ) ) ;
} else if ( view - > location ( ) = = Plasma : : Types : : RightEdge ) {
touchingPanelEdge = ( winfo . geometry ( ) . right ( ) = = availableScreenGeometry . right ( ) ) ;
}
}
return touchingPanelEdge ;
}
return false ;
}
2017-12-24 21:54:45 +03:00
void VisibilityManagerPrivate : : updateDynamicBackgroundWindowFlags ( )
{
bool foundSnap { false } ;
bool foundMaximized { false } ;
//! the notification window is not sending a remove signal and creates windows of geometry (0x0 0,0),
//! maybe a garbage collector here is a good idea!!!
bool existsFaultyWindow { false } ;
2018-10-14 13:54:09 +03:00
WindowId maxWinId ;
WindowId snapWinId ;
2017-12-24 21:54:45 +03:00
for ( const auto & winfo : windows ) {
2018-10-26 18:47:13 +03:00
if ( isMaximizedInCurrentScreen ( winfo ) ) {
foundMaximized = true ;
maxWinId = winfo . wid ( ) ;
}
2017-12-24 21:54:45 +03:00
2018-10-26 18:47:13 +03:00
if ( winfo . isActive ( ) & & isTouchingPanelEdge ( winfo ) ) {
foundSnap = true ;
snapWinId = winfo . wid ( ) ;
2017-12-24 21:54:45 +03:00
}
2018-10-26 18:47:13 +03:00
if ( ! existsFaultyWindow & & winfo . geometry ( ) = = QRect ( 0 , 0 , 0 , 0 ) ) {
2017-12-24 21:54:45 +03:00
existsFaultyWindow = true ;
}
//qDebug() << "window geometry ::: " << winfo.geometry();
}
2018-10-26 18:47:13 +03:00
//! active windows that are touching the panel edge should have a higher priority
//! this is why are identified first
if ( ! foundSnap ) {
for ( const auto & winfo : windows ) {
if ( ( winfo . isKeepAbove ( ) & & isTouchingPanelEdge ( winfo ) )
| | ( ! winfo . isActive ( ) & & snappedWindowsGeometries . contains ( winfo . geometry ( ) ) ) ) {
foundSnap = true ;
snapWinId = winfo . wid ( ) ;
break ;
}
}
}
2017-12-24 21:54:45 +03:00
if ( existsFaultyWindow ) {
2018-01-04 19:36:41 +03:00
cleanupFaultyWindows ( ) ;
2017-12-24 21:54:45 +03:00
}
/*if (!foundMaximized && !foundSnap) {
qDebug ( ) < < " SCREEN GEOMETRY : " < < availableScreenGeometry ;
qDebug ( ) < < " SNAPS ::: " < < snappedWindowsGeometries ;
}
qDebug ( ) < < " FOUND ::: " < < foundMaximized < < foundSnap ; */
setExistsWindowMaximized ( foundMaximized ) ;
setExistsWindowSnapped ( foundSnap ) ;
2018-10-14 13:54:09 +03:00
//! update color scheme for touching window
if ( foundSnap ) {
//! first the snap one because that would mean it is active
setTouchingWindowScheme ( wm - > schemeForWindow ( snapWinId ) ) ;
} else if ( foundMaximized ) {
setTouchingWindowScheme ( wm - > schemeForWindow ( maxWinId ) ) ;
} else {
setTouchingWindowScheme ( nullptr ) ;
}
2017-12-24 21:54:45 +03:00
}
2018-03-28 20:39:52 +03:00
//! KWin Edges Support functions
void VisibilityManagerPrivate : : setEnableKWinEdges ( bool enable )
{
if ( enableKWinEdgesFromUser = = enable ) {
return ;
}
enableKWinEdgesFromUser = enable ;
emit q - > enableKWinEdgesChanged ( ) ;
updateKWinEdgesSupport ( ) ;
}
void VisibilityManagerPrivate : : updateKWinEdgesSupport ( )
{
if ( mode = = Dock : : AutoHide
| | mode = = Dock : : DodgeActive
| | mode = = Dock : : DodgeAllWindows
| | mode = = Dock : : DodgeMaximized ) {
if ( enableKWinEdgesFromUser ) {
createEdgeGhostWindow ( ) ;
} else if ( ! enableKWinEdgesFromUser ) {
deleteEdgeGhostWindow ( ) ;
}
} else if ( mode = = Dock : : AlwaysVisible
| | mode = = Dock : : WindowsGoBelow ) {
deleteEdgeGhostWindow ( ) ;
}
}
void VisibilityManagerPrivate : : createEdgeGhostWindow ( )
{
if ( ! edgeGhostWindow ) {
edgeGhostWindow = new ScreenEdgeGhostWindow ( dockView ) ;
wm - > setDockExtraFlags ( * edgeGhostWindow ) ;
2018-11-13 20:06:33 +03:00
connect ( edgeGhostWindow , & ScreenEdgeGhostWindow : : containsMouseChanged , this , [ = ] ( bool contains ) {
if ( contains ) {
emit this - > q - > mustBeShown ( VisibilityManager : : QPrivateSignal { } ) ;
}
2018-03-28 20:39:52 +03:00
} ) ;
connectionsKWinEdges [ 0 ] = connect ( wm , & WindowSystem : : currentActivityChanged ,
this , [ & ] ( ) {
bool inCurrentLayout = ( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : SingleLayout | |
( dockCorona - > layoutManager ( ) - > memoryUsage ( ) = = Dock : : MultipleLayouts
2018-11-29 22:30:00 +03:00
& & dockView - > managedLayout ( ) & & ! dockView - > positioner ( ) - > inLocationChangeAnimation ( )
2018-03-28 20:39:52 +03:00
& & dockView - > managedLayout ( ) - > name ( ) = = dockCorona - > layoutManager ( ) - > currentLayoutName ( ) ) ) ;
if ( edgeGhostWindow ) {
if ( inCurrentLayout ) {
wm - > setEdgeStateFor ( edgeGhostWindow , isHidden ) ;
} else {
wm - > setEdgeStateFor ( edgeGhostWindow , false ) ;
}
}
} ) ;
emit q - > supportsKWinEdgesChanged ( ) ;
}
}
void VisibilityManagerPrivate : : deleteEdgeGhostWindow ( )
{
if ( edgeGhostWindow ) {
edgeGhostWindow - > deleteLater ( ) ;
edgeGhostWindow = nullptr ;
for ( auto & c : connectionsKWinEdges ) {
disconnect ( c ) ;
}
emit q - > supportsKWinEdgesChanged ( ) ;
}
}
2018-10-28 11:03:22 +03:00
//! Window Functions
2018-10-28 22:10:08 +03:00
void VisibilityManagerPrivate : : requestToggleMaximizeForActiveWindow ( )
{
WindowInfoWrap actInfo = wm - > requestInfoActive ( ) ;
//active window can be toggled only when it is in the same screen
if ( actInfo . isValid ( ) & & ! actInfo . geometry ( ) . isNull ( ) & & dockView - > screenGeometry ( ) . contains ( actInfo . geometry ( ) . center ( ) ) ) {
wm - > requestToggleMaximized ( actInfo . wid ( ) ) ;
}
}
2018-10-28 11:03:22 +03:00
void VisibilityManagerPrivate : : requestMoveActiveWindow ( int localX , int localY )
{
2018-10-28 22:10:08 +03:00
WindowInfoWrap actInfo = wm - > requestInfoActive ( ) ;
//active window can be dragged only when it is in the same screen
if ( actInfo . isValid ( ) & & ! actInfo . geometry ( ) . isNull ( ) & & dockView - > screenGeometry ( ) . contains ( actInfo . geometry ( ) . center ( ) ) ) {
QPoint globalPoint { dockView - > x ( ) + localX , dockView - > y ( ) + localY } ;
wm - > requestMoveWindow ( actInfo . wid ( ) , globalPoint ) ;
}
2018-10-28 11:03:22 +03:00
}
bool VisibilityManagerPrivate : : activeWindowCanBeDragged ( )
{
2018-10-28 22:10:08 +03:00
WindowInfoWrap actInfo = wm - > requestInfoActive ( ) ;
//active window can be dragged only when it is in the same screen
if ( actInfo . isValid ( ) & & ! actInfo . geometry ( ) . isNull ( ) & & dockView - > screenGeometry ( ) . contains ( actInfo . geometry ( ) . center ( ) ) ) {
return wm - > windowCanBeDragged ( actInfo . wid ( ) ) ;
}
return false ;
2018-10-28 11:03:22 +03:00
}
2017-01-13 02:53:59 +03:00
//! END: VisibilityManagerPrivate implementation
2016-12-29 08:40:35 +03:00
2018-03-28 20:39:52 +03:00
//! BEGIN: VisibilityManager implementation
2016-12-29 08:40:35 +03:00
VisibilityManager : : VisibilityManager ( PlasmaQuick : : ContainmentView * view )
: d ( new VisibilityManagerPrivate ( view , this ) )
2016-12-25 10:25:27 +03:00
{
2017-12-05 21:56:58 +03:00
DockView * dockView = qobject_cast < DockView * > ( view ) ;
if ( dockView ) {
connect ( this , & VisibilityManager : : modeChanged , dockView - > corona ( ) , & Plasma : : Corona : : availableScreenRectChanged ) ;
}
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
VisibilityManager : : ~ VisibilityManager ( )
2016-12-25 10:25:27 +03:00
{
2017-03-12 20:05:02 +03:00
qDebug ( ) < < " VisibilityManager deleting... " ;
delete d ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
Dock : : Visibility VisibilityManager : : mode ( ) const
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
return d - > mode ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
void VisibilityManager : : setMode ( Dock : : Visibility mode )
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
d - > setMode ( mode ) ;
}
2016-12-25 10:25:27 +03:00
2018-01-21 12:53:15 +03:00
void VisibilityManager : : setWindowOnActivities ( QWindow & window , const QStringList & activities )
2018-01-13 13:55:13 +03:00
{
2018-01-21 12:53:15 +03:00
d - > setWindowOnActivities ( window , activities ) ;
2018-01-13 13:55:13 +03:00
}
2018-03-28 20:39:52 +03:00
void VisibilityManager : : applyActivitiesToHiddenWindows ( const QStringList & activities )
{
d - > applyActivitiesToHiddenWindows ( activities ) ;
}
2017-03-12 12:01:27 +03:00
bool VisibilityManager : : raiseOnDesktop ( ) const
{
return d - > raiseOnDesktopChange ;
}
void VisibilityManager : : setRaiseOnDesktop ( bool enable )
{
d - > setRaiseOnDesktop ( enable ) ;
}
bool VisibilityManager : : raiseOnActivity ( ) const
{
return d - > raiseOnActivityChange ;
}
void VisibilityManager : : setRaiseOnActivity ( bool enable )
{
d - > setRaiseOnActivity ( enable ) ;
}
2016-12-29 08:40:35 +03:00
bool VisibilityManager : : isHidden ( ) const
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
return d - > isHidden ;
2016-12-25 10:25:27 +03:00
}
2016-12-30 10:17:38 +03:00
void VisibilityManager : : setIsHidden ( bool isHidden )
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
d - > setIsHidden ( isHidden ) ;
2016-12-25 10:25:27 +03:00
}
2017-01-02 11:06:47 +03:00
bool VisibilityManager : : blockHiding ( ) const
{
return d - > blockHiding ;
}
void VisibilityManager : : setBlockHiding ( bool blockHiding )
{
d - > setBlockHiding ( blockHiding ) ;
}
2016-12-29 08:40:35 +03:00
bool VisibilityManager : : containsMouse ( ) const
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
return d - > containsMouse ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
int VisibilityManager : : timerShow ( ) const
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
return d - > timerShow . interval ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
void VisibilityManager : : setTimerShow ( int msec )
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
d - > setTimerShow ( msec ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
int VisibilityManager : : timerHide ( ) const
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
return d - > timerHide . interval ( ) ;
2016-12-25 10:25:27 +03:00
}
2016-12-29 08:40:35 +03:00
void VisibilityManager : : setTimerHide ( int msec )
2016-12-25 10:25:27 +03:00
{
2016-12-29 08:40:35 +03:00
d - > setTimerHide ( msec ) ;
2016-12-25 10:25:27 +03:00
}
2017-12-24 21:54:45 +03:00
//! Dynamic Background functions
bool VisibilityManager : : enabledDynamicBackground ( ) const
{
return d - > enabledDynamicBackgroundFlag ;
}
void VisibilityManager : : setEnabledDynamicBackground ( bool active )
{
d - > setEnabledDynamicBackground ( active ) ;
}
bool VisibilityManager : : existsWindowMaximized ( ) const
{
return d - > windowIsMaximizedFlag ;
}
bool VisibilityManager : : existsWindowSnapped ( ) const
{
return d - > windowIsSnappedFlag ;
}
2018-10-14 13:54:09 +03:00
SchemeColors * VisibilityManager : : touchingWindowScheme ( ) const
{
return d - > touchingScheme ;
}
2018-03-28 20:39:52 +03:00
//! KWin Edges Support functions
bool VisibilityManager : : enableKWinEdges ( ) const
{
return d - > enableKWinEdgesFromUser ;
}
void VisibilityManager : : setEnableKWinEdges ( bool enable )
{
d - > setEnableKWinEdges ( enable ) ;
}
bool VisibilityManager : : supportsKWinEdges ( ) const
{
return ( d - > edgeGhostWindow ! = nullptr ) ;
}
2018-10-28 11:03:22 +03:00
//! Window Functions
2018-10-28 22:10:08 +03:00
void VisibilityManager : : requestToggleMaximizeForActiveWindow ( )
{
d - > requestToggleMaximizeForActiveWindow ( ) ;
}
2018-10-28 11:03:22 +03:00
void VisibilityManager : : requestMoveActiveWindow ( int localX , int localY )
{
d - > requestMoveActiveWindow ( localX , localY ) ;
}
bool VisibilityManager : : activeWindowCanBeDragged ( )
{
return d - > activeWindowCanBeDragged ( ) ;
}
2016-12-29 08:40:35 +03:00
//! END: VisibilityManager implementation
2018-10-28 11:03:22 +03:00
2016-12-25 10:25:27 +03:00
}