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

Side by Side Diff: content/browser/renderer_host/input/touch_handle.cc

Issue 335943002: [Android] Composited selection handle rendering (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@input_native_handles_final
Patch Set: Code review and comments Created 6 years, 5 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
OLDNEW
(Empty)
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "content/browser/renderer_host/input/touch_handle.h"
6
7 namespace content {
8
9 namespace {
10
11 // Maximum duration of a fade sequence.
12 const double kFadeDurationMs = 200;
13
14 // Maximum amount of travel for a fade sequence. This avoids handle "ghosting"
15 // when the handle is moving rapidly while the fade is active.
16 const double kFadeDistanceSquared = 20.f * 20.f;
17
18 } // namespace
19
20 // Responsible for rendering a selection or insertion handle for text editing.
21 TouchHandle::TouchHandle(TouchHandleClient* client,
22 TouchHandleOrientation orientation)
23 : drawable_(client->CreateDrawable()),
24 client_(client),
25 orientation_(orientation),
26 deferred_orientation_(TOUCH_HANDLE_ORIENTATION_UNDEFINED),
27 alpha_(0.f),
28 animate_deferred_fade_(false),
29 enabled_(true),
30 is_visible_(false),
31 is_dragging_(false) {
32 DCHECK_NE(orientation, TOUCH_HANDLE_ORIENTATION_UNDEFINED);
33 drawable_->SetEnabled(enabled_);
34 drawable_->SetOrientation(orientation_);
35 drawable_->SetAlpha(alpha_);
36 drawable_->SetVisible(is_visible_);
37 drawable_->SetFocus(position_);
38 }
39
40 TouchHandle::~TouchHandle() {
41 }
42
43 void TouchHandle::SetEnabled(bool enabled) {
44 if (enabled_ == enabled)
45 return;
46 if (!enabled) {
47 EndDrag();
48 EndFade();
49 }
50 enabled_ = enabled;
51 drawable_->SetEnabled(enabled);
52 }
53
54 void TouchHandle::SetVisible(bool visible, AnimationStyle animation_style) {
55 DCHECK(enabled_);
56 if (is_visible_ == visible)
57 return;
58
59 is_visible_ = visible;
60
61 // Handle repositioning may have been deferred while previously invisible.
62 if (visible)
63 drawable_->SetFocus(position_);
64
65 bool animate = animation_style != ANIMATION_NONE;
66 if (is_dragging_) {
67 animate_deferred_fade_ = animate;
68 return;
69 }
70
71 if (animate)
72 BeginFade();
73 else
74 EndFade();
75 }
76
77 void TouchHandle::SetPosition(const gfx::PointF& position) {
78 DCHECK(enabled_);
79 if (position_ == position)
80 return;
81 position_ = position;
82 // Suppress repositioning a handle while invisible or fading out to prevent it
83 // from "ghosting" outside the visible bounds. The position will be pushed to
84 // the drawable when the handle regains visibility (see |SetVisible()|).
85 if (is_visible_)
86 drawable_->SetFocus(position_);
87 }
88
89 void TouchHandle::SetOrientation(TouchHandleOrientation orientation) {
90 DCHECK(enabled_);
91 DCHECK_NE(orientation, TOUCH_HANDLE_ORIENTATION_UNDEFINED);
92 if (is_dragging_) {
93 deferred_orientation_ = orientation;
94 return;
95 }
96 DCHECK_EQ(deferred_orientation_, TOUCH_HANDLE_ORIENTATION_UNDEFINED);
97 if (orientation_ == orientation)
98 return;
99
100 orientation_ = orientation;
101 drawable_->SetOrientation(orientation);
102 }
103
104 bool TouchHandle::WillHandleTouchEvent(const ui::MotionEvent& event) {
105 if (!enabled_)
106 return false;
107
108 if (!is_dragging_ && event.GetAction() != ui::MotionEvent::ACTION_DOWN)
109 return false;
110
111 switch (event.GetAction()) {
112 case ui::MotionEvent::ACTION_DOWN: {
113 gfx::PointF touch_position = gfx::PointF(event.GetX(), event.GetY());
114 if (!is_visible_ || !drawable_->ContainsPoint(touch_position))
115 return false;
116 touch_down_position_ = touch_position;
117 touch_to_focus_offset_ = position_ - touch_down_position_;
118 touch_down_time_ = event.GetEventTime();
119 BeginDrag();
120 } break;
121
122 case ui::MotionEvent::ACTION_MOVE: {
123 gfx::PointF new_position =
124 gfx::PointF(event.GetX(), event.GetY()) + touch_to_focus_offset_;
125 client_->OnHandleDragUpdate(*this, new_position);
126 } break;
127
128 case ui::MotionEvent::ACTION_UP: {
129 // TODO(jdduke): Use the platform touch slop distance and tap delay to
130 // properly detect a tap, crbug.com/394093.
131 base::TimeDelta delay = event.GetEventTime() - touch_down_time_;
132 if (delay < base::TimeDelta::FromMilliseconds(180))
133 client_->OnHandleTapped(*this);
134
135 EndDrag();
136 } break;
137
138 case ui::MotionEvent::ACTION_CANCEL:
139 EndDrag();
140 break;
141
142 default:
143 break;
144 };
145 return true;
146 }
147
148 bool TouchHandle::Animate(base::TimeTicks frame_time) {
149 if (fade_end_time_ == base::TimeTicks())
150 return false;
151
152 DCHECK(enabled_);
153
154 float time_u =
155 1.f - (fade_end_time_ - frame_time).InMillisecondsF() / kFadeDurationMs;
156 float position_u =
157 (position_ - fade_start_position_).LengthSquared() / kFadeDistanceSquared;
158 float u = std::max(time_u, position_u);
159 SetAlpha(is_visible_ ? u : 1.f - u);
160
161 if (u >= 1.f) {
162 EndFade();
163 return false;
164 }
165
166 return true;
167 }
168
169 void TouchHandle::BeginDrag() {
170 DCHECK(enabled_);
171 if (is_dragging_)
172 return;
173 EndFade();
174 is_dragging_ = true;
175 client_->OnHandleDragBegin(*this);
176 }
177
178 void TouchHandle::EndDrag() {
179 DCHECK(enabled_);
180 if (!is_dragging_)
181 return;
182
183 is_dragging_ = false;
184 client_->OnHandleDragEnd(*this);
185
186 if (deferred_orientation_ != TOUCH_HANDLE_ORIENTATION_UNDEFINED) {
187 TouchHandleOrientation deferred_orientation = deferred_orientation_;
188 deferred_orientation_ = TOUCH_HANDLE_ORIENTATION_UNDEFINED;
189 SetOrientation(deferred_orientation);
190 }
191
192 if (enabled_ && animate_deferred_fade_) {
cjhopman 2014/07/17 16:04:31 enabled_ is always true
jdduke (slow) 2014/07/18 18:49:27 Of course, fixed.
193 BeginFade();
194 } else {
195 // As drawable visibility assignment is deferred while dragging, push the
196 // change by forcing fade completion.
197 EndFade();
198 }
199 }
200
201 void TouchHandle::BeginFade() {
202 DCHECK(enabled_);
203 DCHECK(!is_dragging_);
204 animate_deferred_fade_ = false;
205 const float target_alpha = is_visible_ ? 1.f : 0.f;
206 if (target_alpha == alpha_) {
207 EndFade();
208 return;
209 }
210
211 drawable_->SetVisible(true);
212 fade_end_time_ = base::TimeTicks::Now() +
213 base::TimeDelta::FromMillisecondsD(
214 kFadeDurationMs * std::abs(target_alpha - alpha_));
215 fade_start_position_ = position_;
216 client_->SetNeedsAnimate();
217 }
218
219 void TouchHandle::EndFade() {
220 DCHECK(enabled_);
221 animate_deferred_fade_ = false;
222 fade_end_time_ = base::TimeTicks();
223 SetAlpha(is_visible_ ? 1.f : 0.f);
224 drawable_->SetVisible(is_visible_);
225 }
226
227 void TouchHandle::SetAlpha(float alpha) {
228 alpha = std::max(0.f, std::min(1.f, alpha));
229 if (alpha_ == alpha)
230 return;
231 alpha_ = alpha;
232 drawable_->SetAlpha(alpha);
233 }
234
235 } // namespace content
OLDNEW
« no previous file with comments | « content/browser/renderer_host/input/touch_handle.h ('k') | content/browser/renderer_host/input/touch_handle_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698