diff --git a/activation.cpp b/activation.cpp index c40f15566e..5cec4a8dc9 100644 --- a/activation.cpp +++ b/activation.cpp @@ -360,6 +360,8 @@ void Workspace::takeActivity( Client* c, int flags, bool handled ) return; } c->takeActivity( flags, handled, Allowed ); + if( !c->isOnScreen( active_screen )) + active_screen = c->screen(); } void Workspace::handleTakeActivity( Client* c, Time /*timestamp*/, int flags ) @@ -442,6 +444,32 @@ bool Workspace::activateNextClient( Client* c ) return true; } +void Workspace::setCurrentScreen( int new_screen ) + { + if (new_screen < 0 || new_screen > numScreens()) + return; + if ( !options->focusPolicyIsReasonable()) + return; + closeActivePopup(); + Client* get_focus = NULL; + for( int i = focus_chain[ currentDesktop() ].count() - 1; + i >= 0; + --i ) + { + Client* ci = focus_chain[ currentDesktop() ].at( i ); + if( !ci->isShown( false ) || !ci->isOnCurrentDesktop()) + continue; + if( !ci->screen() == new_screen ) + continue; + get_focus = ci; + break; + } + if( get_focus == NULL ) + get_focus = findDesktop( true, currentDesktop()); + if( get_focus != NULL && get_focus != mostRecentlyActivatedClient()) + requestFocus( get_focus ); + active_screen = new_screen; + } void Workspace::gotFocusIn( const Client* c ) { diff --git a/geometry.cpp b/geometry.cpp index 487db55f32..e2e42de0c8 100644 --- a/geometry.cpp +++ b/geometry.cpp @@ -877,10 +877,6 @@ void Client::checkWorkspacePosition() setGeometry( area ); return; } - if( maximizeMode() != MaximizeRestore ) - // TODO update geom_restore? - changeMaximize( false, false, true ); // adjust size - if( isFullScreen()) { QRect area = workspace()->clientArea( FullScreenArea, this ); @@ -907,6 +903,10 @@ void Client::checkWorkspacePosition() return; } + if( maximizeMode() != MaximizeRestore ) + // TODO update geom_restore? + changeMaximize( false, false, true ); // adjust size + if( !isShade()) // TODO { int old_diff_x = workarea_diff_x; diff --git a/kwinbindings.cpp b/kwinbindings.cpp index 326bfe68b1..56cb408426 100644 --- a/kwinbindings.cpp +++ b/kwinbindings.cpp @@ -118,6 +118,15 @@ DEF( I18N_NOOP("Window One Desktop to the Left"), 0, slotWindowToDesktopLeft() ); DEF( I18N_NOOP("Window One Desktop Up"), 0, slotWindowToDesktopUp() ); DEF( I18N_NOOP("Window One Desktop Down"), 0, slotWindowToDesktopDown() ); + DEF( I18N_NOOP("Window to Screen 0"), 0, slotWindowToScreen0() ); + DEF( I18N_NOOP("Window to Screen 1"), 0, slotWindowToScreen1() ); + DEF( I18N_NOOP("Window to Screen 2"), 0, slotWindowToScreen2() ); + DEF( I18N_NOOP("Window to Screen 3"), 0, slotWindowToScreen3() ); + DEF( I18N_NOOP("Window to Screen 4"), 0, slotWindowToScreen4() ); + DEF( I18N_NOOP("Window to Screen 5"), 0, slotWindowToScreen5() ); + DEF( I18N_NOOP("Window to Screen 6"), 0, slotWindowToScreen6() ); + DEF( I18N_NOOP("Window to Screen 7"), 0, slotWindowToScreen7() ); + DEF( I18N_NOOP("Window to Next Screen"), 0, slotWindowToNextScreen() ); a = actionCollection->addAction( "Group:Desktop Switching" ); a->setText( i18n("Desktop Switching") ); @@ -147,6 +156,15 @@ DEF( I18N_NOOP("Switch One Desktop to the Left"), 0, slotSwitchDesktopLeft() ); DEF( I18N_NOOP("Switch One Desktop Up"), 0, slotSwitchDesktopUp() ); DEF( I18N_NOOP("Switch One Desktop Down"), 0, slotSwitchDesktopDown() ); + DEF( I18N_NOOP("Switch to Screen 0"), 0, slotSwitchToScreen0() ); + DEF( I18N_NOOP("Switch to Screen 1"), 0, slotSwitchToScreen1() ); + DEF( I18N_NOOP("Switch to Screen 2"), 0, slotSwitchToScreen2() ); + DEF( I18N_NOOP("Switch to Screen 3"), 0, slotSwitchToScreen3() ); + DEF( I18N_NOOP("Switch to Screen 4"), 0, slotSwitchToScreen4() ); + DEF( I18N_NOOP("Switch to Screen 5"), 0, slotSwitchToScreen5() ); + DEF( I18N_NOOP("Switch to Screen 6"), 0, slotSwitchToScreen6() ); + DEF( I18N_NOOP("Switch to Screen 7"), 0, slotSwitchToScreen7() ); + DEF( I18N_NOOP("Switch to Next Screen"), 0, slotSwitchToNextScreen() ); a = actionCollection->addAction( "Group:Miscellaneous" ); a->setText( i18n("Miscellaneous") ); diff --git a/useractions.cpp b/useractions.cpp index eed0e1f3e3..0998b1ed99 100644 --- a/useractions.cpp +++ b/useractions.cpp @@ -794,6 +794,40 @@ void Workspace::slotWindowToDesktop( int i ) sendClientToDesktop( c, i, true ); } +void Workspace::slotSwitchToScreen( int i ) + { + setCurrentScreen( i ); + } + +void Workspace::slotSwitchToNextScreen() + { + slotSwitchToScreen(( activeScreen() + 1 ) % numScreens()); + } + +void Workspace::slotWindowToScreen( int i ) + { + Client* c = active_popup_client ? active_popup_client : active_client; + if( i >= 0 && i <= numScreens() && c + && !c->isDesktop() + && !c->isDock() + && !c->isTopMenu()) + { + sendClientToScreen( c, i ); + } + } + +void Workspace::slotWindowToNextScreen() + { + Client* c = active_popup_client ? active_popup_client : active_client; + if( c + && !c->isDesktop() + && !c->isDock() + && !c->isTopMenu()) + { + sendClientToScreen( c, ( c->screen() + 1 ) % numScreens()); + } + } + /*! Maximizes the popup client */ diff --git a/workspace.cpp b/workspace.cpp index 4e73de3ca7..51cfcd9bc3 100644 --- a/workspace.cpp +++ b/workspace.cpp @@ -86,6 +86,7 @@ Workspace::Workspace( bool restore ) most_recently_raised (0), movingClient(0), pending_take_activity ( NULL ), + active_screen (0), delayfocus_client (0), showing_desktop( false ), block_showing_desktop( 0 ), @@ -1614,9 +1615,9 @@ int Workspace::activeScreen() const return 0; if( !options->activeMouseScreen ) { - if( activeClient() != NULL ) + if( activeClient() != NULL && !activeClient()->isOnScreen( active_screen )) return qApp->desktop()->screenNumber( activeClient()->geometry().center()); - return qApp->desktop()->primaryScreen(); + return active_screen; } return qApp->desktop()->screenNumber( QCursor::pos()); } @@ -1635,6 +1636,23 @@ int Workspace::screenNumber( QPoint pos ) const return qApp->desktop()->screenNumber( pos ); } +void Workspace::sendClientToScreen( Client* c, int screen ) + { + if( c->screen() == screen ) // don't use isOnScreen(), that's true even when only partially + return; + GeometryUpdatesBlocker blocker( c ); + QRect old_sarea = clientArea( MaximizeArea, c ); + QRect sarea = clientArea( MaximizeArea, screen, c->desktop()); + c->setGeometry( sarea.x() - old_sarea.x() + c->x(), sarea.y() - old_sarea.y() + c->y(), + c->size().width(), c->size().height()); + c->checkWorkspacePosition(); + ClientList transients_stacking_order = ensureStackingOrder( c->transients()); + for( ClientList::ConstIterator it = transients_stacking_order.begin(); + it != transients_stacking_order.end(); + ++it ) + sendClientToScreen( *it, screen ); + } + void Workspace::setDesktopLayout(NET::Orientation o, int x, int y,NET::DesktopLayoutCorner c) { Q_UNUSED( c ); // I don't find this worth bothering, feel free to diff --git a/workspace.h b/workspace.h index 341db4e42f..9abc226519 100644 --- a/workspace.h +++ b/workspace.h @@ -210,6 +210,7 @@ class Workspace : public QObject, public KDecorationDefines void sendClientToDesktop( Client* c, int desktop, bool dont_activate ); void windowToPreviousDesktop( Client* c ); void windowToNextDesktop( Client* c ); + void sendClientToScreen( Client* c, int screen ); // KDE4 remove me - and it's also in the DCOP interface :( void showWindowMenuAt( unsigned long id, int x, int y ); @@ -253,6 +254,7 @@ class Workspace : public QObject, public KDecorationDefines void nextDesktop(); void previousDesktop(); void circulateDesktopApplications(); + void setCurrentScreen( int new_screen ); QString desktopName( int desk ) const; void setDesktopLayout(NET::Orientation o, int x, int y, NET::DesktopLayoutCorner c); @@ -379,6 +381,26 @@ class Workspace : public QObject, public KDecorationDefines void slotWindowToDesktop19() { return slotWindowToDesktop( 19 ); } void slotWindowToDesktop20() { return slotWindowToDesktop( 20 ); } //void slotWindowToListPosition( int ); + void slotSwitchToScreen( int ); + void slotSwitchToScreen0() { return slotSwitchToScreen( 0 ); } + void slotSwitchToScreen1() { return slotSwitchToScreen( 1 ); } + void slotSwitchToScreen2() { return slotSwitchToScreen( 2 ); } + void slotSwitchToScreen3() { return slotSwitchToScreen( 3 ); } + void slotSwitchToScreen4() { return slotSwitchToScreen( 4 ); } + void slotSwitchToScreen5() { return slotSwitchToScreen( 5 ); } + void slotSwitchToScreen6() { return slotSwitchToScreen( 6 ); } + void slotSwitchToScreen7() { return slotSwitchToScreen( 7 ); } + void slotWindowToScreen( int ); + void slotWindowToScreen0() { return slotWindowToScreen( 0 ); } + void slotWindowToScreen1() { return slotWindowToScreen( 1 ); } + void slotWindowToScreen2() { return slotWindowToScreen( 2 ); } + void slotWindowToScreen3() { return slotWindowToScreen( 3 ); } + void slotWindowToScreen4() { return slotWindowToScreen( 4 ); } + void slotWindowToScreen5() { return slotWindowToScreen( 5 ); } + void slotWindowToScreen6() { return slotWindowToScreen( 6 ); } + void slotWindowToScreen7() { return slotWindowToScreen( 7 ); } + void slotSwitchToNextScreen(); + void slotWindowToNextScreen(); void slotWindowMaximize(); void slotWindowMaximizeVertical(); @@ -580,6 +602,7 @@ class Workspace : public QObject, public KDecorationDefines Client* most_recently_raised; // used _only_ by raiseOrLowerClient() Client* movingClient; Client* pending_take_activity; + int active_screen; // delay(ed) window focus timer and client QTimer* delayFocusTimer;