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

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

Issue 12087124: Disable touch calibration on external touchscreen. (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Nits Created 7 years, 9 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
« no previous file with comments | « no previous file | ui/base/x/events_x.cc » ('j') | 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 <strings.h> 7 #include <strings.h>
8 #include <X11/cursorfont.h> 8 #include <X11/cursorfont.h>
9 #include <X11/extensions/Xfixes.h> 9 #include <X11/extensions/Xfixes.h>
10 #include <X11/extensions/XInput2.h> 10 #include <X11/extensions/XInput2.h>
11 #include <X11/extensions/Xrandr.h> 11 #include <X11/extensions/Xrandr.h>
12 #include <X11/Xatom.h> 12 #include <X11/Xatom.h>
13 #include <X11/Xcursor/Xcursor.h> 13 #include <X11/Xcursor/Xcursor.h>
14 #include <X11/Xlib.h> 14 #include <X11/Xlib.h>
15 15
16 #include <algorithm> 16 #include <algorithm>
17 #include <limits> 17 #include <limits>
18 #include <string> 18 #include <string>
19 19
20 #include "base/command_line.h" 20 #include "base/command_line.h"
21 #include "base/message_loop.h" 21 #include "base/message_loop.h"
22 #include "base/message_pump_aurax11.h" 22 #include "base/message_pump_aurax11.h"
23 #include "base/stl_util.h" 23 #include "base/stl_util.h"
24 #include "base/string_number_conversions.h"
25 #include "base/string_util.h"
24 #include "base/stringprintf.h" 26 #include "base/stringprintf.h"
25 #include "third_party/skia/include/core/SkBitmap.h" 27 #include "third_party/skia/include/core/SkBitmap.h"
26 #include "third_party/skia/include/core/SkCanvas.h" 28 #include "third_party/skia/include/core/SkCanvas.h"
27 #include "third_party/skia/include/core/SkPostConfig.h" 29 #include "third_party/skia/include/core/SkPostConfig.h"
28 #include "ui/aura/client/capture_client.h" 30 #include "ui/aura/client/capture_client.h"
29 #include "ui/aura/client/cursor_client.h" 31 #include "ui/aura/client/cursor_client.h"
30 #include "ui/aura/client/screen_position_client.h" 32 #include "ui/aura/client/screen_position_client.h"
31 #include "ui/aura/client/user_action_client.h" 33 #include "ui/aura/client/user_action_client.h"
32 #include "ui/aura/env.h" 34 #include "ui/aura/env.h"
33 #include "ui/aura/root_window.h" 35 #include "ui/aura/root_window.h"
(...skipping 20 matching lines...) Expand all
54 using std::min; 56 using std::min;
55 57
56 namespace aura { 58 namespace aura {
57 59
58 namespace { 60 namespace {
59 61
60 // Standard Linux mouse buttons for going back and forward. 62 // Standard Linux mouse buttons for going back and forward.
61 const int kBackMouseButton = 8; 63 const int kBackMouseButton = 8;
62 const int kForwardMouseButton = 9; 64 const int kForwardMouseButton = 9;
63 65
64 // These are the same values that are used to calibrate touch events in
65 // |CalibrateTouchCoordinates| (in ui/base/x/events_x.cc).
66 // TODO(sad|skuhne): Remove the duplication of values (http://crbug.com/147605)
67 const int kXRootWindowPaddingLeft = 40;
68 const int kXRootWindowPaddingRight = 40;
69 const int kXRootWindowPaddingBottom = 30;
70 const int kXRootWindowPaddingTop = 0;
71
72 const char* kAtomsToCache[] = { 66 const char* kAtomsToCache[] = {
73 "WM_DELETE_WINDOW", 67 "WM_DELETE_WINDOW",
74 "_NET_WM_PING", 68 "_NET_WM_PING",
75 "_NET_WM_PID", 69 "_NET_WM_PID",
76 "WM_S0", 70 "WM_S0",
77 #if defined(OS_CHROMEOS) 71 #if defined(OS_CHROMEOS)
78 "Tap Paused", // Defined in the gestures library. 72 "Tap Paused", // Defined in the gestures library.
79 #endif 73 #endif
80 NULL 74 NULL
81 }; 75 };
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after
166 return true; 160 return true;
167 default: 161 default:
168 return false; 162 return false;
169 } 163 }
170 } 164 }
171 165
172 } // namespace 166 } // namespace
173 167
174 namespace internal { 168 namespace internal {
175 169
176 // A very lightweight message-pump observer that routes all the touch events to 170 // Accomplishes 2 tasks concerning touch event calibration:
177 // the X root window so that they can be calibrated properly. 171 // 1. Being a message-pump observer,
172 // routes all the touch events to the X root window,
173 // where they can be calibrated later.
174 // 2. Has the Calibrate method that does the actual bezel calibration,
175 // when invoked from X root window's event dispatcher.
178 class TouchEventCalibrate : public base::MessagePumpObserver { 176 class TouchEventCalibrate : public base::MessagePumpObserver {
179 public: 177 public:
180 TouchEventCalibrate() { 178 TouchEventCalibrate()
179 : left_(0),
180 right_(0),
181 top_(0),
182 bottom_(0) {
181 MessageLoopForUI::current()->AddObserver(this); 183 MessageLoopForUI::current()->AddObserver(this);
184 #if defined(USE_XI2_MT)
185 std::vector<std::string> parts;
186 if (Tokenize(CommandLine::ForCurrentProcess()->GetSwitchValueASCII(
187 switches::kTouchCalibration), ",", &parts) >= 4) {
188 if (!base::StringToInt(parts[0], &left_))
189 DLOG(ERROR) << "Incorrect left border calibration value passed.";
190 if (!base::StringToInt(parts[1], &right_))
191 DLOG(ERROR) << "Incorrect right border calibration value passed.";
192 if (!base::StringToInt(parts[2], &top_))
193 DLOG(ERROR) << "Incorrect top border calibration value passed.";
194 if (!base::StringToInt(parts[3], &bottom_))
195 DLOG(ERROR) << "Incorrect bottom border calibration value passed.";
196 }
197 #endif // defined(USE_XI2_MT)
182 } 198 }
183 199
184 virtual ~TouchEventCalibrate() { 200 virtual ~TouchEventCalibrate() {
185 MessageLoopForUI::current()->RemoveObserver(this); 201 MessageLoopForUI::current()->RemoveObserver(this);
186 } 202 }
187 203
204 // Modify the location of the |event|,
205 // expanding it from |bounds| to (|bounds| + bezels).
206 // Required when touchscreen is bigger than screen (i.e. has bezels),
207 // because we receive events in touchscreen coordinates,
208 // which need to be expanded when converting to screen coordinates,
209 // so that location on bezels will be outside of screen area.
210 void Calibrate(ui::TouchEvent* event, const gfx::Rect& bounds) {
211 #if defined(USE_XI2_MT)
212 int x = event->x();
213 int y = event->y();
214
215 if (!left_ && !right_ && !top_ && !bottom_)
216 return;
217
218 const int resolution_x = bounds.width();
219 const int resolution_y = bounds.height();
220 // The "grace area" (10% in this case) is to make it easier for the user to
221 // navigate to the corner.
222 const double kGraceAreaFraction = 0.1;
223 if (left_ || right_) {
224 // Offset the x position to the real
225 x -= left_;
226 // Check if we are in the grace area of the left side.
227 // Note: We might not want to do this when the gesture is locked?
228 if (x < 0 && x > -left_ * kGraceAreaFraction)
229 x = 0;
230 // Check if we are in the grace area of the right side.
231 // Note: We might not want to do this when the gesture is locked?
232 if (x > resolution_x - left_ &&
233 x < resolution_x - left_ + right_ * kGraceAreaFraction)
234 x = resolution_x - left_;
235 // Scale the screen area back to the full resolution of the screen.
236 x = (x * resolution_x) / (resolution_x - (right_ + left_));
237 }
238 if (top_ || bottom_) {
239 // When there is a top bezel we add our border,
240 y -= top_;
241
242 // Check if we are in the grace area of the top side.
243 // Note: We might not want to do this when the gesture is locked?
244 if (y < 0 && y > -top_ * kGraceAreaFraction)
245 y = 0;
246
247 // Check if we are in the grace area of the bottom side.
248 // Note: We might not want to do this when the gesture is locked?
249 if (y > resolution_y - top_ &&
250 y < resolution_y - top_ + bottom_ * kGraceAreaFraction)
251 y = resolution_y - top_;
252 // Scale the screen area back to the full resolution of the screen.
253 y = (y * resolution_y) / (resolution_y - (bottom_ + top_));
254 }
255
256 // Set the modified coordinate back to the event.
257 if (event->root_location() == event->location()) {
258 // Usually those will be equal,
259 // if not, I am not sure what the correct value should be.
260 event->set_root_location(gfx::Point(x, y));
261 }
262 event->set_location(gfx::Point(x, y));
263 #endif // defined(USE_XI2_MT)
264 }
265
188 private: 266 private:
189 // Overridden from base::MessagePumpObserver: 267 // Overridden from base::MessagePumpObserver:
190 virtual base::EventStatus WillProcessEvent( 268 virtual base::EventStatus WillProcessEvent(
191 const base::NativeEvent& event) OVERRIDE { 269 const base::NativeEvent& event) OVERRIDE {
192 #if defined(USE_XI2_MT) 270 #if defined(USE_XI2_MT)
193 if (event->type == GenericEvent && 271 if (event->type == GenericEvent &&
194 (event->xgeneric.evtype == XI_TouchBegin || 272 (event->xgeneric.evtype == XI_TouchBegin ||
195 event->xgeneric.evtype == XI_TouchUpdate || 273 event->xgeneric.evtype == XI_TouchUpdate ||
196 event->xgeneric.evtype == XI_TouchEnd)) { 274 event->xgeneric.evtype == XI_TouchEnd)) {
197 XIDeviceEvent* xievent = static_cast<XIDeviceEvent*>(event->xcookie.data); 275 XIDeviceEvent* xievent = static_cast<XIDeviceEvent*>(event->xcookie.data);
198 xievent->event = xievent->root; 276 xievent->event = xievent->root;
199 xievent->event_x = xievent->root_x; 277 xievent->event_x = xievent->root_x;
200 xievent->event_y = xievent->root_y; 278 xievent->event_y = xievent->root_y;
201 } 279 }
202 #endif 280 #endif // defined(USE_XI2_MT)
203 return base::EVENT_CONTINUE; 281 return base::EVENT_CONTINUE;
204 } 282 }
205 283
206 virtual void DidProcessEvent(const base::NativeEvent& event) OVERRIDE { 284 virtual void DidProcessEvent(const base::NativeEvent& event) OVERRIDE {
207 } 285 }
208 286
287 // The difference in screen's native resolution pixels between
288 // the border of the touchscreen and the border of the screen,
289 // aka bezel sizes.
290 int left_;
291 int right_;
292 int top_;
293 int bottom_;
294
209 DISALLOW_COPY_AND_ASSIGN(TouchEventCalibrate); 295 DISALLOW_COPY_AND_ASSIGN(TouchEventCalibrate);
210 }; 296 };
211 297
212 } // namespace internal 298 } // namespace internal
213 299
214 //////////////////////////////////////////////////////////////////////////////// 300 ////////////////////////////////////////////////////////////////////////////////
215 // RootWindowHostLinux::MouseMoveFilter filters out the move events that 301 // RootWindowHostLinux::MouseMoveFilter filters out the move events that
216 // jump back and forth between two points. This happens when sub pixel mouse 302 // jump back and forth between two points. This happens when sub pixel mouse
217 // move is enabled and mouse move events could be jumping between two neighbor 303 // move is enabled and mouse move events could be jumping between two neighbor
218 // pixels, e.g. move(0,0), move(1,0), move(0,0), move(1,0) and on and on. 304 // pixels, e.g. move(0,0), move(1,0), move(0,0), move(1,0) and on and on.
(...skipping 678 matching lines...) Expand 10 before | Expand all | Expand 10 after
897 num_coalesced = ui::CoalescePendingMotionEvents(xev, &last_event); 983 num_coalesced = ui::CoalescePendingMotionEvents(xev, &last_event);
898 if (num_coalesced > 0) 984 if (num_coalesced > 0)
899 xev = &last_event; 985 xev = &last_event;
900 // fallthrough 986 // fallthrough
901 case ui::ET_TOUCH_PRESSED: 987 case ui::ET_TOUCH_PRESSED:
902 case ui::ET_TOUCH_CANCELLED: 988 case ui::ET_TOUCH_CANCELLED:
903 case ui::ET_TOUCH_RELEASED: { 989 case ui::ET_TOUCH_RELEASED: {
904 ui::TouchEvent touchev(xev); 990 ui::TouchEvent touchev(xev);
905 #if defined(OS_CHROMEOS) 991 #if defined(OS_CHROMEOS)
906 if (base::chromeos::IsRunningOnChromeOS()) { 992 if (base::chromeos::IsRunningOnChromeOS()) {
907 if (!bounds_.Contains(touchev.location())) { 993 if (!bounds_.Contains(touchev.location()))
908 // This might still be in the bezel region. 994 break;
909 gfx::Rect expanded(bounds_); 995 // X maps the touch-surface to the size of the X root-window.
910 expanded.Inset(-kXRootWindowPaddingLeft, 996 // In multi-monitor setup, Coordinate Transformation Matrix
911 -kXRootWindowPaddingTop, 997 // repositions the touch-surface onto part of X root-window
912 -kXRootWindowPaddingRight, 998 // containing aura root-window corresponding to the touchscreen.
913 -kXRootWindowPaddingBottom); 999 // However, if aura root-window has non-zero origin,
914 if (!expanded.Contains(touchev.location())) 1000 // we need to relocate the event into aura root-window coordinates.
915 break; 1001 touchev.Relocate(bounds_.origin());
916 } 1002 #if defined(USE_XI2_MT)
1003 if (is_internal_display_)
1004 touch_calibrate_->Calibrate(&touchev, bounds_);
1005 #endif // defined(USE_XI2_MT)
917 } 1006 }
918 // X maps the touch-surface to the size of the X root-window.
919 // In multi-monitor setup, Coordinate Transformation Matrix
920 // repositions the touch-surface onto part of X root-window
921 // containing aura root-window corresponding to the touchscreen.
922 // However, if aura root-window has non-zero origin,
923 // we need to relocate the event into aura root-window coordinates.
924 touchev.Relocate(bounds_.origin());
925 #endif // defined(OS_CHROMEOS) 1007 #endif // defined(OS_CHROMEOS)
926 delegate_->OnHostTouchEvent(&touchev); 1008 delegate_->OnHostTouchEvent(&touchev);
927 break; 1009 break;
928 } 1010 }
929 case ui::ET_MOUSE_MOVED: 1011 case ui::ET_MOUSE_MOVED:
930 case ui::ET_MOUSE_DRAGGED: 1012 case ui::ET_MOUSE_DRAGGED:
931 case ui::ET_MOUSE_PRESSED: 1013 case ui::ET_MOUSE_PRESSED:
932 case ui::ET_MOUSE_RELEASED: 1014 case ui::ET_MOUSE_RELEASED:
933 case ui::ET_MOUSE_ENTERED: 1015 case ui::ET_MOUSE_ENTERED:
934 case ui::ET_MOUSE_EXITED: { 1016 case ui::ET_MOUSE_EXITED: {
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
1045 return new RootWindowHostLinux(bounds); 1127 return new RootWindowHostLinux(bounds);
1046 } 1128 }
1047 1129
1048 // static 1130 // static
1049 gfx::Size RootWindowHost::GetNativeScreenSize() { 1131 gfx::Size RootWindowHost::GetNativeScreenSize() {
1050 ::Display* xdisplay = base::MessagePumpAuraX11::GetDefaultXDisplay(); 1132 ::Display* xdisplay = base::MessagePumpAuraX11::GetDefaultXDisplay();
1051 return gfx::Size(DisplayWidth(xdisplay, 0), DisplayHeight(xdisplay, 0)); 1133 return gfx::Size(DisplayWidth(xdisplay, 0), DisplayHeight(xdisplay, 0));
1052 } 1134 }
1053 1135
1054 } // namespace aura 1136 } // namespace aura
OLDNEW
« no previous file with comments | « no previous file | ui/base/x/events_x.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698