Move XRandR event filter into XRandRScreens

Summary:
The code in events.cpp was problematic as it was called in a Wayland
session. So KWin changed outputs, this gets mirrored to XWayland and
then KWin reacted on the XRandR event and might have even changed the
refresh rate due to that - bad idea.

This change moves the code into the already existing X11EventFilter for
XRandR events in XRandRScreens.

Test Plan: Run kwin_x11 in gdb on Xephyr, breakpoint in new code and triggered XRandR event

Reviewers: #kwin, #plasma

Subscribers: plasma-devel, kwin

Tags: #kwin

Differential Revision: https://phabricator.kde.org/D7654
icc-effect-5.14.5
Martin Flöser 2017-09-02 11:47:42 +02:00
parent 8015e4e84e
commit 4fa41165d1
5 changed files with 38 additions and 25 deletions

View File

@ -51,6 +51,10 @@ public:
void registerEventFilter(X11EventFilter *filter);
void unregisterEventFilter(X11EventFilter *filter);
bool compositing() const {
return false;
}
static Workspace *self();
Q_SIGNALS:

View File

@ -81,8 +81,6 @@ typedef struct xcb_ge_generic_event_t {
namespace KWin
{
extern int currentRefreshRate();
// ****************************************
// Workspace
// ****************************************
@ -428,29 +426,7 @@ bool Workspace::workspaceEvent(xcb_generic_event_t *e)
case XCB_FOCUS_OUT:
return true; // always eat these, they would tell Qt that KWin is the active app
default:
if (eventType == Xcb::Extensions::self()->randrNotifyEvent() && Xcb::Extensions::self()->isRandrAvailable()) {
auto *event = reinterpret_cast<xcb_randr_screen_change_notify_event_t*>(e);
xcb_screen_t *screen = defaultScreen();
if (event->rotation & (XCB_RANDR_ROTATION_ROTATE_90 | XCB_RANDR_ROTATION_ROTATE_270)) {
screen->width_in_pixels = event->height;
screen->height_in_pixels = event->width;
screen->width_in_millimeters = event->mheight;
screen->height_in_millimeters = event->mwidth;
} else {
screen->width_in_pixels = event->width;
screen->height_in_pixels = event->height;
screen->width_in_millimeters = event->mwidth;
screen->height_in_millimeters = event->mheight;
}
if (compositing()) {
// desktopResized() should take care of when the size or
// shape of the desktop has changed, but we also want to
// catch refresh rate changes
if (m_compositor->xrrRefreshRate() != currentRefreshRate())
m_compositor->setCompositeResetTimer(0);
}
} else if (eventType == Xcb::Extensions::self()->syncAlarmNotifyEvent() && Xcb::Extensions::self()->isSyncAvailable()) {
if (eventType == Xcb::Extensions::self()->syncAlarmNotifyEvent() && Xcb::Extensions::self()->isSyncAvailable()) {
for (Client *c : clients)
c->syncEvent(reinterpret_cast< xcb_sync_alarm_notify_event_t* >(e));
for (Client *c : desktops)

View File

@ -42,6 +42,11 @@ namespace KWin
#ifndef KCMRULES
int currentRefreshRate()
{
return Options::currentRefreshRate();
}
int Options::currentRefreshRate()
{
int rate = -1;
QString syncScreenName(QLatin1String("primary screen"));

View File

@ -783,6 +783,8 @@ public:
bool loadCompositingConfig(bool force);
void reparseConfiguration();
static int currentRefreshRate();
//----------------------
Q_SIGNALS:
// for properties

View File

@ -18,6 +18,9 @@ You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*********************************************************************/
#include "screens_xrandr.h"
#include "composite.h"
#include "options.h"
#include "workspace.h"
#include "xcbutils.h"
@ -185,6 +188,29 @@ bool XRandRScreens::event(xcb_generic_event_t *event)
Q_ASSERT((event->response_type & ~0x80) == Xcb::Extensions::self()->randrNotifyEvent());
// let's try to gather a few XRandR events, unlikely that there is just one
startChangedTimer();
// update default screen
auto *xrrEvent = reinterpret_cast<xcb_randr_screen_change_notify_event_t*>(event);
xcb_screen_t *screen = defaultScreen();
if (xrrEvent->rotation & (XCB_RANDR_ROTATION_ROTATE_90 | XCB_RANDR_ROTATION_ROTATE_270)) {
screen->width_in_pixels = xrrEvent->height;
screen->height_in_pixels = xrrEvent->width;
screen->width_in_millimeters = xrrEvent->mheight;
screen->height_in_millimeters = xrrEvent->mwidth;
} else {
screen->width_in_pixels = xrrEvent->width;
screen->height_in_pixels = xrrEvent->height;
screen->width_in_millimeters = xrrEvent->mwidth;
screen->height_in_millimeters = xrrEvent->mheight;
}
if (workspace()->compositing()) {
// desktopResized() should take care of when the size or
// shape of the desktop has changed, but we also want to
// catch refresh rate changes
if (Compositor::self()->xrrRefreshRate() != Options::currentRefreshRate())
Compositor::self()->setCompositeResetTimer(0);
}
return false;
}