Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(173)

Side by Side Diff: ui/aura/root_window_host_linux.cc

Issue 10913253: aura: Make sure the root-window retains the X events it was already listening for. (Closed) Base URL: http://git.chromium.org/git/chromium.git@trunk
Patch Set: Created 8 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « ui/aura/root_window_host_linux.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ui/aura/root_window_host_linux.h" 5 #include "ui/aura/root_window_host_linux.h"
6 6
7 #include <X11/cursorfont.h> 7 #include <X11/cursorfont.h>
8 #include <X11/extensions/Xfixes.h> 8 #include <X11/extensions/Xfixes.h>
9 #include <X11/extensions/XInput2.h> 9 #include <X11/extensions/XInput2.h>
10 #include <X11/extensions/Xrandr.h> 10 #include <X11/extensions/Xrandr.h>
(...skipping 188 matching lines...) Expand 10 before | Expand all | Expand 10 after
199 } else { 199 } else {
200 // This isn't an event we want so free its cookie data. 200 // This isn't an event we want so free its cookie data.
201 XFreeEventData(display, &next_event.xcookie); 201 XFreeEventData(display, &next_event.xcookie);
202 } 202 }
203 } 203 }
204 break; 204 break;
205 } 205 }
206 return num_coalesed; 206 return num_coalesed;
207 } 207 }
208 208
209 ::Window FindEventTarget(const base::NativeEvent& xev) {
210 ::Window target = xev->xany.window;
211 if (xev->type == GenericEvent)
212 target = static_cast<XIDeviceEvent*>(xev->xcookie.data)->event;
213 return target;
214 }
215
209 void SelectEventsForRootWindow() { 216 void SelectEventsForRootWindow() {
210 XIEventMask evmask; 217 XIEventMask evmask;
211 unsigned char mask[XIMaskLen(XI_LASTEVENT)] = {}; 218 unsigned char mask[XIMaskLen(XI_LASTEVENT)] = {};
212 memset(mask, 0, sizeof(mask)); 219 memset(mask, 0, sizeof(mask));
213 220
214 XISetMask(mask, XI_HierarchyChanged); 221 XISetMask(mask, XI_HierarchyChanged);
215 222
216 XISetMask(mask, XI_KeyPress); 223 XISetMask(mask, XI_KeyPress);
217 XISetMask(mask, XI_KeyRelease); 224 XISetMask(mask, XI_KeyRelease);
218 225
219 #if defined(USE_XI2_MT) 226 #if defined(USE_XI2_MT)
220 XISetMask(mask, XI_TouchBegin); 227 XISetMask(mask, XI_TouchBegin);
221 XISetMask(mask, XI_TouchUpdate); 228 XISetMask(mask, XI_TouchUpdate);
222 XISetMask(mask, XI_TouchEnd); 229 XISetMask(mask, XI_TouchEnd);
223 #endif 230 #endif
224 XISetMask(mask, XI_ButtonPress); 231 XISetMask(mask, XI_ButtonPress);
225 XISetMask(mask, XI_ButtonRelease); 232 XISetMask(mask, XI_ButtonRelease);
226 XISetMask(mask, XI_Motion); 233 XISetMask(mask, XI_Motion);
227 234
228 evmask.deviceid = XIAllDevices; 235 evmask.deviceid = XIAllDevices;
229 evmask.mask_len = sizeof(mask); 236 evmask.mask_len = sizeof(mask);
230 evmask.mask = mask; 237 evmask.mask = mask;
231 238
232 Display* display = ui::GetXDisplay(); 239 Display* display = ui::GetXDisplay();
233 ::Window root_window = ui::GetX11RootWindow(); 240 ::Window root_window = ui::GetX11RootWindow();
234 XISelectEvents(display, root_window, &evmask, 1); 241 XISelectEvents(display, root_window, &evmask, 1);
235 242
236 // Receive resize events for the root-window so |x_root_bounds_| can be 243 // Receive resize events for the root-window so |x_root_bounds_| can be
237 // updated. 244 // updated.
238 XSelectInput(display, root_window, StructureNotifyMask); 245 XWindowAttributes attr;
246 XGetWindowAttributes(display, root_window, &attr);
247 if (!(attr.your_event_mask & StructureNotifyMask)) {
248 XSelectInput(display, root_window,
249 StructureNotifyMask | attr.your_event_mask);
250 }
239 } 251 }
240 252
241 // We emulate Windows' WM_KEYDOWN and WM_CHAR messages. WM_CHAR events are only 253 // We emulate Windows' WM_KEYDOWN and WM_CHAR messages. WM_CHAR events are only
242 // generated for certain keys; see 254 // generated for certain keys; see
243 // http://msdn.microsoft.com/en-us/library/windows/desktop/ms646268.aspx. Per 255 // http://msdn.microsoft.com/en-us/library/windows/desktop/ms646268.aspx. Per
244 // discussion on http://crbug.com/108480, char events should furthermore not be 256 // discussion on http://crbug.com/108480, char events should furthermore not be
245 // generated for Tab, Escape, and Backspace. 257 // generated for Tab, Escape, and Backspace.
246 bool ShouldSendCharEventForKeyboardCode(ui::KeyboardCode keycode) { 258 bool ShouldSendCharEventForKeyboardCode(ui::KeyboardCode keycode) {
247 if ((keycode >= ui::VKEY_0 && keycode <= ui::VKEY_9) || 259 if ((keycode >= ui::VKEY_0 && keycode <= ui::VKEY_9) ||
248 (keycode >= ui::VKEY_A && keycode <= ui::VKEY_Z) || 260 (keycode >= ui::VKEY_A && keycode <= ui::VKEY_Z) ||
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
373 XDestroyWindow(xdisplay_, xwindow_); 385 XDestroyWindow(xdisplay_, xwindow_);
374 386
375 XFreeCursor(xdisplay_, invisible_cursor_); 387 XFreeCursor(xdisplay_, invisible_cursor_);
376 } 388 }
377 389
378 bool RootWindowHostLinux::Dispatch(const base::NativeEvent& event) { 390 bool RootWindowHostLinux::Dispatch(const base::NativeEvent& event) {
379 XEvent* xev = event; 391 XEvent* xev = event;
380 392
381 CheckXEventForConsistency(xev); 393 CheckXEventForConsistency(xev);
382 394
395 if (FindEventTarget(event) == x_root_window_)
396 return DispatchEventForRootWindow(event);
397
383 switch (xev->type) { 398 switch (xev->type) {
384 case EnterNotify: { 399 case EnterNotify: {
385 ui::MouseEvent mouseenter_event(xev); 400 ui::MouseEvent mouseenter_event(xev);
386 delegate_->OnHostMouseEvent(&mouseenter_event); 401 delegate_->OnHostMouseEvent(&mouseenter_event);
387 break; 402 break;
388 } 403 }
389 case Expose: 404 case Expose:
390 delegate_->AsRootWindow()->ScheduleFullDraw(); 405 delegate_->AsRootWindow()->ScheduleFullDraw();
391 break; 406 break;
392 case KeyPress: { 407 case KeyPress: {
(...skipping 23 matching lines...) Expand all
416 case ButtonRelease: { 431 case ButtonRelease: {
417 ui::MouseEvent mouseev(xev); 432 ui::MouseEvent mouseev(xev);
418 delegate_->OnHostMouseEvent(&mouseev); 433 delegate_->OnHostMouseEvent(&mouseev);
419 break; 434 break;
420 } 435 }
421 case FocusOut: 436 case FocusOut:
422 if (xev->xfocus.mode != NotifyGrab) 437 if (xev->xfocus.mode != NotifyGrab)
423 delegate_->OnHostLostCapture(); 438 delegate_->OnHostLostCapture();
424 break; 439 break;
425 case ConfigureNotify: { 440 case ConfigureNotify: {
426 if (xev->xconfigure.window == xwindow_) { 441 DCHECK_EQ(xwindow_, xev->xconfigure.event);
427 DCHECK_EQ(xwindow_, xev->xconfigure.event); 442 DCHECK_EQ(xwindow_, xev->xconfigure.window);
428 // It's possible that the X window may be resized by some other means 443 // It's possible that the X window may be resized by some other means
429 // than from within aura (e.g. the X window manager can change the 444 // than from within aura (e.g. the X window manager can change the
430 // size). Make sure the root window size is maintained properly. 445 // size). Make sure the root window size is maintained properly.
431 gfx::Rect bounds(xev->xconfigure.x, xev->xconfigure.y, 446 gfx::Rect bounds(xev->xconfigure.x, xev->xconfigure.y,
432 xev->xconfigure.width, xev->xconfigure.height); 447 xev->xconfigure.width, xev->xconfigure.height);
433 bool size_changed = bounds_.size() != bounds.size(); 448 bool size_changed = bounds_.size() != bounds.size();
434 bool origin_changed = bounds_.origin() != bounds.origin(); 449 bool origin_changed = bounds_.origin() != bounds.origin();
435 bounds_ = bounds; 450 bounds_ = bounds;
436 // Always update barrier and mouse location because |bounds_| might 451 // Always update barrier and mouse location because |bounds_| might
437 // have already been updated in |SetBounds|. 452 // have already been updated in |SetBounds|.
438 if (pointer_barriers_.get()) { 453 if (pointer_barriers_.get()) {
439 UnConfineCursor(); 454 UnConfineCursor();
440 RootWindow* root = delegate_->AsRootWindow(); 455 RootWindow* root = delegate_->AsRootWindow();
441 client::ScreenPositionClient* client = 456 client::ScreenPositionClient* client =
442 client::GetScreenPositionClient(root); 457 client::GetScreenPositionClient(root);
443 if (client) { 458 if (client) {
444 gfx::Point p = gfx::Screen::GetCursorScreenPoint(); 459 gfx::Point p = gfx::Screen::GetCursorScreenPoint();
445 client->ConvertPointFromScreen(root, &p); 460 client->ConvertPointFromScreen(root, &p);
446 if (root->ContainsPoint(p)) { 461 if (root->ContainsPoint(p)) {
447 root->ConvertPointToNativeScreen(&p); 462 root->ConvertPointToNativeScreen(&p);
448 XWarpPointer( 463 XWarpPointer(
449 xdisplay_, None, x_root_window_, 0, 0, 0, 0, p.x(), p.y()); 464 xdisplay_, None, x_root_window_, 0, 0, 0, 0, p.x(), p.y());
450 }
451 } 465 }
452 ConfineCursorToRootWindow();
453 } 466 }
454 if (size_changed) 467 ConfineCursorToRootWindow();
455 delegate_->OnHostResized(bounds.size());
456 if (origin_changed)
457 delegate_->OnHostMoved(bounds_.origin());
458 } else {
459 DCHECK_EQ(x_root_window_, xev->xconfigure.event);
460 DCHECK_EQ(x_root_window_, xev->xconfigure.window);
461 x_root_bounds_.SetRect(xev->xconfigure.x, xev->xconfigure.y,
462 xev->xconfigure.width, xev->xconfigure.height);
463 } 468 }
469 if (size_changed)
470 delegate_->OnHostResized(bounds.size());
471 if (origin_changed)
472 delegate_->OnHostMoved(bounds_.origin());
464 break; 473 break;
465 } 474 }
466 case GenericEvent: { 475 case GenericEvent: {
467 ui::TouchFactory* factory = ui::TouchFactory::GetInstance(); 476 ui::TouchFactory* factory = ui::TouchFactory::GetInstance();
468 if (!factory->ShouldProcessXI2Event(xev)) 477 if (!factory->ShouldProcessXI2Event(xev))
469 break; 478 break;
470 479
471 ui::EventType type = ui::EventTypeFromNative(xev); 480 ui::EventType type = ui::EventTypeFromNative(xev);
472 XEvent last_event; 481 XEvent last_event;
473 int num_coalesced = 0; 482 int num_coalesced = 0;
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after
621 } 630 }
622 631
623 ui::MouseEvent mouseev(xev); 632 ui::MouseEvent mouseev(xev);
624 delegate_->OnHostMouseEvent(&mouseev); 633 delegate_->OnHostMouseEvent(&mouseev);
625 break; 634 break;
626 } 635 }
627 } 636 }
628 return true; 637 return true;
629 } 638 }
630 639
640 bool RootWindowHostLinux::DispatchEventForRootWindow(
641 const base::NativeEvent& event) {
642 switch (event->type) {
643 case ConfigureNotify:
644 DCHECK_EQ(x_root_window_, event->xconfigure.event);
645 DCHECK_EQ(x_root_window_, event->xconfigure.window);
646 x_root_bounds_.SetRect(event->xconfigure.x, event->xconfigure.y,
647 event->xconfigure.width, event->xconfigure.height);
648 break;
649 }
650
651 return false;
Daniel Erat 2012/09/13 19:14:09 i think that we previously returned true in this c
sadrul 2012/09/13 23:41:24 It wasn't. Incidentally, however, the return value
652 }
653
631 RootWindow* RootWindowHostLinux::GetRootWindow() { 654 RootWindow* RootWindowHostLinux::GetRootWindow() {
632 return delegate_->AsRootWindow(); 655 return delegate_->AsRootWindow();
633 } 656 }
634 657
635 gfx::AcceleratedWidget RootWindowHostLinux::GetAcceleratedWidget() { 658 gfx::AcceleratedWidget RootWindowHostLinux::GetAcceleratedWidget() {
636 return xwindow_; 659 return xwindow_;
637 } 660 }
638 661
639 void RootWindowHostLinux::Show() { 662 void RootWindowHostLinux::Show() {
640 if (!window_mapped_) { 663 if (!window_mapped_) {
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after
920 ui::ViewProp::GetValue(accelerated_widget, kRootWindowHostLinuxKey)); 943 ui::ViewProp::GetValue(accelerated_widget, kRootWindowHostLinuxKey));
921 } 944 }
922 945
923 // static 946 // static
924 gfx::Size RootWindowHost::GetNativeScreenSize() { 947 gfx::Size RootWindowHost::GetNativeScreenSize() {
925 ::Display* xdisplay = base::MessagePumpAuraX11::GetDefaultXDisplay(); 948 ::Display* xdisplay = base::MessagePumpAuraX11::GetDefaultXDisplay();
926 return gfx::Size(DisplayWidth(xdisplay, 0), DisplayHeight(xdisplay, 0)); 949 return gfx::Size(DisplayWidth(xdisplay, 0), DisplayHeight(xdisplay, 0));
927 } 950 }
928 951
929 } // namespace aura 952 } // namespace aura
OLDNEW
« no previous file with comments | « ui/aura/root_window_host_linux.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698