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

Side by Side Diff: content/browser/find_request_manager.cc

Issue 2700613003: Enable find-in-page across GuestViews. (Closed)
Patch Set: Small fix. Created 3 years, 8 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
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 "content/browser/find_request_manager.h" 5 #include "content/browser/find_request_manager.h"
6 6
7 #include <algorithm>
8
7 #include "content/browser/frame_host/render_frame_host_impl.h" 9 #include "content/browser/frame_host/render_frame_host_impl.h"
8 #include "content/browser/web_contents/web_contents_impl.h" 10 #include "content/browser/web_contents/web_contents_impl.h"
9 #include "content/common/frame_messages.h" 11 #include "content/common/frame_messages.h"
10 #include "content/common/input_messages.h" 12 #include "content/common/input_messages.h"
13 #include "content/public/browser/guest_mode.h"
11 14
12 namespace content { 15 namespace content {
13 16
14 namespace { 17 namespace {
15 18
19 // The following functions allow traversal over all frames, including those
20 // across WebContentses.
21 //
22 // Note that there are currently two different ways in which an inner
23 // WebContents may be embedded in an outer WebContents:
24 //
25 // 1) As a guest of the outer WebContents's BrowserPluginEmbedder.
26 // 2) Within an inner WebContentsTreeNode of the outer WebContents's
27 // WebContentsTreeNode.
28
29 // Returns all child frames of |node|.
30 std::vector<FrameTreeNode*> GetChildren(FrameTreeNode* node) {
31 std::vector<FrameTreeNode*> children(node->child_count());
32 for (size_t i = 0; i != node->child_count(); ++i)
33 children[i] = node->child_at(i);
34
35 if (auto* inner_contents = WebContentsImpl::FromOuterFrameTreeNode(node)) {
36 children.push_back(inner_contents->GetMainFrame()->frame_tree_node());
37 } else {
38 auto* contents = WebContentsImpl::FromFrameTreeNode(node);
39 if (node->IsMainFrame() && contents->GetBrowserPluginEmbedder()) {
40 for (auto* inner_contents : contents->GetInnerWebContents()) {
41 children.push_back(inner_contents->GetMainFrame()->frame_tree_node());
42 }
43 }
44 }
45
46 return children;
47 }
48
49 // Returns the first child FrameTreeNode under |node|, if |node| has a child, or
50 // nullptr otherwise.
51 FrameTreeNode* GetFirstChild(FrameTreeNode* node) {
52 auto children = GetChildren(node);
53 if (!children.empty())
54 return children.front();
55 return nullptr;
56 }
57
58 // Returns the last child FrameTreeNode under |node|, if |node| has a child, or
59 // nullptr otherwise.
60 FrameTreeNode* GetLastChild(FrameTreeNode* node) {
61 auto children = GetChildren(node);
62 if (!children.empty())
63 return children.back();
64 return nullptr;
65 }
66
16 // Returns the deepest last child frame under |node|/|rfh| in the frame tree. 67 // Returns the deepest last child frame under |node|/|rfh| in the frame tree.
17 FrameTreeNode* GetDeepestLastChild(FrameTreeNode* node) { 68 FrameTreeNode* GetDeepestLastChild(FrameTreeNode* node) {
18 while (node->child_count()) 69 while (FrameTreeNode* last_child = GetLastChild(node))
19 node = node->child_at(node->child_count() - 1); 70 node = last_child;
20 return node; 71 return node;
21 } 72 }
22 RenderFrameHost* GetDeepestLastChild(RenderFrameHost* rfh) { 73 RenderFrameHost* GetDeepestLastChild(RenderFrameHost* rfh) {
23 FrameTreeNode* node = 74 FrameTreeNode* node =
24 static_cast<RenderFrameHostImpl*>(rfh)->frame_tree_node(); 75 static_cast<RenderFrameHostImpl*>(rfh)->frame_tree_node();
25 return GetDeepestLastChild(node)->current_frame_host(); 76 return GetDeepestLastChild(node)->current_frame_host();
26 } 77 }
27 78
79 // Returns the parent FrameTreeNode of |node|, if |node| has a parent, or
80 // nullptr otherwise.
81 FrameTreeNode* GetParent(FrameTreeNode* node) {
82 if (node->parent())
83 return node->parent();
84
85 // The parent frame may be in another WebContents.
86 if (node->IsMainFrame()) {
87 auto* contents = WebContentsImpl::FromFrameTreeNode(node);
88 if (GuestMode::IsCrossProcessFrameGuest(contents)) {
89 int node_id = contents->GetOuterDelegateFrameTreeNodeId();
90 if (node_id != FrameTreeNode::kFrameTreeNodeInvalidId)
91 return FrameTreeNode::GloballyFindByID(node_id);
92 } else if (auto* outer_contents = contents->GetOuterWebContents()) {
93 return outer_contents->GetMainFrame()->frame_tree_node();
94 }
95 }
96
97 return nullptr;
98 }
99
100 // Returns the previous sibling FrameTreeNode of |node|, if one exists, or
101 // nullptr otherwise.
102 FrameTreeNode* GetPreviousSibling(FrameTreeNode* node) {
103 if (FrameTreeNode* previous_sibling = node->PreviousSibling())
104 return previous_sibling;
105
106 // The previous sibling may be in another WebContents.
107 if (FrameTreeNode* parent = GetParent(node)) {
108 auto children = GetChildren(parent);
109 auto it = std::find(children.begin(), children.end(), node);
110 // It is odd that this node may not be a child of its parent, but this is
111 // actually possible during teardown, hence the need for the check for
112 // "it != children.end()".
113 if (it != children.end() && it != children.begin())
114 return *--it;
115 }
116
117 return nullptr;
118 }
119
120 // Returns the next sibling FrameTreeNode of |node|, if one exists, or nullptr
121 // otherwise.
122 FrameTreeNode* GetNextSibling(FrameTreeNode* node) {
123 if (FrameTreeNode* next_sibling = node->NextSibling())
124 return next_sibling;
125
126 // The next sibling may be in another WebContents.
127 if (FrameTreeNode* parent = GetParent(node)) {
128 auto children = GetChildren(parent);
129 auto it = std::find(children.begin(), children.end(), node);
130 // It is odd that this node may not be a child of its parent, but this is
131 // actually possible during teardown, hence the need for the check for
132 // "it != children.end()".
133 if (it != children.end() && ++it != children.end())
134 return *it;
135 }
136
137 return nullptr;
138 }
139
28 // Returns the FrameTreeNode directly after |node| in the frame tree in search 140 // Returns the FrameTreeNode directly after |node| in the frame tree in search
29 // order, or nullptr if one does not exist. If |wrap| is set, then wrapping 141 // order, or nullptr if one does not exist. If |wrap| is set, then wrapping
30 // between the first and last frames is permitted. Note that this traversal 142 // between the first and last frames is permitted. Note that this traversal
31 // follows the same ordering as in blink::FrameTree::traverseNextWithWrap(). 143 // follows the same ordering as in blink::FrameTree::traverseNextWithWrap().
32 FrameTreeNode* TraverseNext(FrameTreeNode* node, bool wrap) { 144 FrameTreeNode* TraverseNext(FrameTreeNode* node, bool wrap) {
33 if (node->child_count()) 145 if (FrameTreeNode* first_child = GetFirstChild(node))
34 return node->child_at(0); 146 return first_child;
35 147
36 FrameTreeNode* sibling = node->NextSibling(); 148 FrameTreeNode* sibling = GetNextSibling(node);
37 while (!sibling) { 149 while (!sibling) {
38 if (!node->parent()) 150 FrameTreeNode* parent = GetParent(node);
151 if (!parent)
39 return wrap ? node : nullptr; 152 return wrap ? node : nullptr;
40 node = node->parent(); 153 node = parent;
41 sibling = node->NextSibling(); 154 sibling = GetNextSibling(node);
42 } 155 }
43 return sibling; 156 return sibling;
44 } 157 }
45 158
46 // Returns the FrameTreeNode directly before |node| in the frame tree in search 159 // Returns the FrameTreeNode directly before |node| in the frame tree in search
47 // order, or nullptr if one does not exist. If |wrap| is set, then wrapping 160 // order, or nullptr if one does not exist. If |wrap| is set, then wrapping
48 // between the first and last frames is permitted. Note that this traversal 161 // between the first and last frames is permitted. Note that this traversal
49 // follows the same ordering as in blink::FrameTree::traversePreviousWithWrap(). 162 // follows the same ordering as in blink::FrameTree::traversePreviousWithWrap().
50 FrameTreeNode* TraversePrevious(FrameTreeNode* node, bool wrap) { 163 FrameTreeNode* TraversePrevious(FrameTreeNode* node, bool wrap) {
51 if (FrameTreeNode* previous_sibling = node->PreviousSibling()) 164 if (FrameTreeNode* previous_sibling = GetPreviousSibling(node))
52 return GetDeepestLastChild(previous_sibling); 165 return GetDeepestLastChild(previous_sibling);
53 if (node->parent()) 166 if (FrameTreeNode* parent = GetParent(node))
54 return node->parent(); 167 return parent;
55 return wrap ? GetDeepestLastChild(node) : nullptr; 168 return wrap ? GetDeepestLastChild(node) : nullptr;
56 } 169 }
57 170
58 // The same as either TraverseNext() or TraversePrevious() depending on 171 // The same as either TraverseNext() or TraversePrevious(), depending on
59 // |forward|. 172 // |forward|.
60 FrameTreeNode* TraverseNode(FrameTreeNode* node, bool forward, bool wrap) { 173 FrameTreeNode* TraverseNode(FrameTreeNode* node, bool forward, bool wrap) {
61 return forward ? TraverseNext(node, wrap) : TraversePrevious(node, wrap); 174 return forward ? TraverseNext(node, wrap) : TraversePrevious(node, wrap);
62 } 175 }
63 176
64 } // namespace 177 } // namespace
65 178
179 // Observes searched WebContentses for frame changes, including deletion,
180 // creation, and navigation.
181 class FindRequestManager::FrameObserver : public WebContentsObserver {
182 public:
183 FrameObserver(WebContentsImpl* web_contents, FindRequestManager* manager)
184 : WebContentsObserver(web_contents), manager_(manager) {}
185
186 ~FrameObserver() override {}
187
188 void DidFinishLoad(RenderFrameHost* rfh, const GURL& validated_url) override {
189 if (manager_->current_session_id_ == kInvalidId)
190 return;
191
192 manager_->RemoveFrame(rfh);
193 manager_->AddFrame(rfh, true /* force */);
194 }
195
196 void RenderFrameDeleted(RenderFrameHost* rfh) override {
197 manager_->RemoveFrame(rfh);
198 }
199
200 void RenderFrameHostChanged(RenderFrameHost* old_host,
201 RenderFrameHost* new_host) override {
202 manager_->RemoveFrame(old_host);
203 }
204
205 void FrameDeleted(RenderFrameHost* rfh) override {
206 manager_->RemoveFrame(rfh);
207 }
208
209 private:
210 // The FindRequestManager that owns this FrameObserver.
211 FindRequestManager* const manager_;
212
213 DISALLOW_COPY_AND_ASSIGN(FrameObserver);
214 };
215
66 #if defined(OS_ANDROID) 216 #if defined(OS_ANDROID)
67 FindRequestManager::ActivateNearestFindResultState:: 217 FindRequestManager::ActivateNearestFindResultState::
68 ActivateNearestFindResultState() = default; 218 ActivateNearestFindResultState() = default;
69 FindRequestManager::ActivateNearestFindResultState:: 219 FindRequestManager::ActivateNearestFindResultState::
70 ActivateNearestFindResultState(float x, float y) 220 ActivateNearestFindResultState(float x, float y)
71 : current_request_id(GetNextID()), 221 : current_request_id(GetNextID()),
72 x(x), 222 x(x),
73 y(y) {} 223 y(y) {}
74 FindRequestManager::ActivateNearestFindResultState:: 224 FindRequestManager::ActivateNearestFindResultState::
75 ~ActivateNearestFindResultState() {} 225 ~ActivateNearestFindResultState() {}
76 226
77 FindRequestManager::FrameRects::FrameRects() = default; 227 FindRequestManager::FrameRects::FrameRects() = default;
78 FindRequestManager::FrameRects::FrameRects(const std::vector<gfx::RectF>& rects, 228 FindRequestManager::FrameRects::FrameRects(const std::vector<gfx::RectF>& rects,
79 int version) 229 int version)
80 : rects(rects), version(version) {} 230 : rects(rects), version(version) {}
81 FindRequestManager::FrameRects::~FrameRects() {} 231 FindRequestManager::FrameRects::~FrameRects() {}
82 232
83 FindRequestManager::FindMatchRectsState::FindMatchRectsState() = default; 233 FindRequestManager::FindMatchRectsState::FindMatchRectsState() = default;
84 FindRequestManager::FindMatchRectsState::~FindMatchRectsState() {} 234 FindRequestManager::FindMatchRectsState::~FindMatchRectsState() {}
85 #endif 235 #endif
86 236
87 // static 237 // static
88 const int FindRequestManager::kInvalidId = -1; 238 const int FindRequestManager::kInvalidId = -1;
89 239
90 FindRequestManager::FindRequestManager(WebContentsImpl* web_contents) 240 FindRequestManager::FindRequestManager(WebContentsImpl* web_contents)
91 : WebContentsObserver(web_contents), 241 : contents_(web_contents),
92 contents_(web_contents),
93 current_session_id_(kInvalidId), 242 current_session_id_(kInvalidId),
94 pending_find_next_reply_(nullptr), 243 pending_find_next_reply_(nullptr),
95 pending_active_match_ordinal_(false), 244 pending_active_match_ordinal_(false),
96 number_of_matches_(0), 245 number_of_matches_(0),
97 active_frame_(nullptr), 246 active_frame_(nullptr),
98 relative_active_match_ordinal_(0), 247 relative_active_match_ordinal_(0),
99 active_match_ordinal_(0), 248 active_match_ordinal_(0),
100 last_reported_id_(kInvalidId) {} 249 last_reported_id_(kInvalidId) {}
101 250
102 FindRequestManager::~FindRequestManager() {} 251 FindRequestManager::~FindRequestManager() {}
(...skipping 10 matching lines...) Expand all
113 // If this is a new find session, clear any queued requests from last session. 262 // If this is a new find session, clear any queued requests from last session.
114 if (!options.findNext) 263 if (!options.findNext)
115 find_request_queue_ = std::queue<FindRequest>(); 264 find_request_queue_ = std::queue<FindRequest>();
116 265
117 find_request_queue_.emplace(request_id, search_text, options); 266 find_request_queue_.emplace(request_id, search_text, options);
118 if (find_request_queue_.size() == 1) 267 if (find_request_queue_.size() == 1)
119 FindInternal(find_request_queue_.front()); 268 FindInternal(find_request_queue_.front());
120 } 269 }
121 270
122 void FindRequestManager::StopFinding(StopFindAction action) { 271 void FindRequestManager::StopFinding(StopFindAction action) {
123 contents_->SendToAllFrames( 272 for (WebContentsImpl* contents : contents_->GetWebContentsAndAllInner()) {
124 new FrameMsg_StopFinding(MSG_ROUTING_NONE, action)); 273 contents->SendToAllFrames(
274 new FrameMsg_StopFinding(MSG_ROUTING_NONE, action));
275 }
125 276
126 current_session_id_ = kInvalidId; 277 current_session_id_ = kInvalidId;
127 #if defined(OS_ANDROID) 278 #if defined(OS_ANDROID)
128 // It is important that these pending replies are cleared whenever a find 279 // It is important that these pending replies are cleared whenever a find
129 // session ends, so that subsequent replies for the old session are ignored. 280 // session ends, so that subsequent replies for the old session are ignored.
130 activate_.pending_replies.clear(); 281 activate_.pending_replies.clear();
131 match_rects_.pending_replies.clear(); 282 match_rects_.pending_replies.clear();
132 #endif 283 #endif
133 } 284 }
134 285
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after
286 437
287 #if defined(OS_ANDROID) 438 #if defined(OS_ANDROID)
288 void FindRequestManager::ActivateNearestFindResult(float x, float y) { 439 void FindRequestManager::ActivateNearestFindResult(float x, float y) {
289 if (current_session_id_ == kInvalidId) 440 if (current_session_id_ == kInvalidId)
290 return; 441 return;
291 442
292 activate_ = ActivateNearestFindResultState(x, y); 443 activate_ = ActivateNearestFindResultState(x, y);
293 444
294 // Request from each frame the distance to the nearest find result (in that 445 // Request from each frame the distance to the nearest find result (in that
295 // frame) from the point (x, y), defined in find-in-page coordinates. 446 // frame) from the point (x, y), defined in find-in-page coordinates.
296 for (FrameTreeNode* node : contents_->GetFrameTree()->Nodes()) { 447 for (WebContentsImpl* contents : contents_->GetWebContentsAndAllInner()) {
297 RenderFrameHost* rfh = node->current_frame_host(); 448 for (FrameTreeNode* node : contents->GetFrameTree()->Nodes()) {
449 RenderFrameHost* rfh = node->current_frame_host();
298 450
299 if (!CheckFrame(rfh) || !rfh->IsRenderFrameLive()) 451 if (!CheckFrame(rfh) || !rfh->IsRenderFrameLive())
300 continue; 452 continue;
301 453
302 activate_.pending_replies.insert(rfh); 454 activate_.pending_replies.insert(rfh);
303 rfh->Send(new FrameMsg_GetNearestFindResult( 455 rfh->Send(new FrameMsg_GetNearestFindResult(rfh->GetRoutingID(),
304 rfh->GetRoutingID(), activate_.current_request_id, 456 activate_.current_request_id,
305 activate_.x, activate_.y)); 457 activate_.x, activate_.y));
458 }
306 } 459 }
307 } 460 }
308 461
309 void FindRequestManager::OnGetNearestFindResultReply(RenderFrameHost* rfh, 462 void FindRequestManager::OnGetNearestFindResultReply(RenderFrameHost* rfh,
310 int request_id, 463 int request_id,
311 float distance) { 464 float distance) {
312 if (request_id != activate_.current_request_id || 465 if (request_id != activate_.current_request_id ||
313 !activate_.pending_replies.count(rfh)) { 466 !activate_.pending_replies.count(rfh)) {
314 return; 467 return;
315 } 468 }
316 469
317 // Check if this frame has a nearer find result than the current nearest. 470 // Check if this frame has a nearer find result than the current nearest.
318 if (distance < activate_.nearest_distance) { 471 if (distance < activate_.nearest_distance) {
319 activate_.nearest_frame = rfh; 472 activate_.nearest_frame = rfh;
320 activate_.nearest_distance = distance; 473 activate_.nearest_distance = distance;
321 } 474 }
322 475
323 RemoveNearestFindResultPendingReply(rfh); 476 RemoveNearestFindResultPendingReply(rfh);
324 } 477 }
325 478
326 void FindRequestManager::RequestFindMatchRects(int current_version) { 479 void FindRequestManager::RequestFindMatchRects(int current_version) {
327 match_rects_.pending_replies.clear(); 480 match_rects_.pending_replies.clear();
328 match_rects_.request_version = current_version; 481 match_rects_.request_version = current_version;
329 482
330 // Request the latest find match rects from each frame. 483 // Request the latest find match rects from each frame.
331 for (FrameTreeNode* node : contents_->GetFrameTree()->Nodes()) { 484 for (WebContentsImpl* contents : contents_->GetWebContentsAndAllInner()) {
332 RenderFrameHost* rfh = node->current_frame_host(); 485 for (FrameTreeNode* node : contents->GetFrameTree()->Nodes()) {
486 RenderFrameHost* rfh = node->current_frame_host();
333 487
334 if (!CheckFrame(rfh) || !rfh->IsRenderFrameLive()) 488 if (!CheckFrame(rfh) || !rfh->IsRenderFrameLive())
335 continue; 489 continue;
336 490
337 match_rects_.pending_replies.insert(rfh); 491 match_rects_.pending_replies.insert(rfh);
338 auto it = match_rects_.frame_rects.find(rfh); 492 auto it = match_rects_.frame_rects.find(rfh);
339 int version = (it != match_rects_.frame_rects.end()) 493 int version = (it != match_rects_.frame_rects.end()) ? it->second.version
340 ? it->second.version : kInvalidId; 494 : kInvalidId;
341 rfh->Send(new FrameMsg_FindMatchRects(rfh->GetRoutingID(), version)); 495 rfh->Send(new FrameMsg_FindMatchRects(rfh->GetRoutingID(), version));
496 }
342 } 497 }
343 } 498 }
344 499
345 void FindRequestManager::OnFindMatchRectsReply( 500 void FindRequestManager::OnFindMatchRectsReply(
346 RenderFrameHost* rfh, 501 RenderFrameHost* rfh,
347 int version, 502 int version,
348 const std::vector<gfx::RectF>& rects, 503 const std::vector<gfx::RectF>& rects,
349 const gfx::RectF& active_rect) { 504 const gfx::RectF& active_rect) {
350 auto it = match_rects_.frame_rects.find(rfh); 505 auto it = match_rects_.frame_rects.find(rfh);
351 if (it == match_rects_.frame_rects.end() || it->second.version != version) { 506 if (it == match_rects_.frame_rects.end() || it->second.version != version) {
352 // New version of rects has been received, so update the data. 507 // New version of rects has been received, so update the data.
353 match_rects_.frame_rects[rfh] = FrameRects(rects, version); 508 match_rects_.frame_rects[rfh] = FrameRects(rects, version);
354 ++match_rects_.known_version; 509 ++match_rects_.known_version;
355 } 510 }
356 if (!active_rect.IsEmpty()) 511 if (!active_rect.IsEmpty())
357 match_rects_.active_rect = active_rect; 512 match_rects_.active_rect = active_rect;
358 RemoveFindMatchRectsPendingReply(rfh); 513 RemoveFindMatchRectsPendingReply(rfh);
359 } 514 }
360 #endif 515 #endif
361 516
362 void FindRequestManager::DidFinishLoad(RenderFrameHost* rfh,
363 const GURL& validated_url) {
364 if (current_session_id_ == kInvalidId)
365 return;
366
367 RemoveFrame(rfh);
368 AddFrame(rfh, true /* force */);
369 }
370
371 void FindRequestManager::RenderFrameDeleted(RenderFrameHost* rfh) {
372 RemoveFrame(rfh);
373 }
374
375 void FindRequestManager::RenderFrameHostChanged(RenderFrameHost* old_host,
376 RenderFrameHost* new_host) {
377 RemoveFrame(old_host);
378 }
379
380 void FindRequestManager::FrameDeleted(RenderFrameHost* rfh) {
381 RemoveFrame(rfh);
382 }
383
384 void FindRequestManager::Reset(const FindRequest& initial_request) { 517 void FindRequestManager::Reset(const FindRequest& initial_request) {
385 current_session_id_ = initial_request.id; 518 current_session_id_ = initial_request.id;
386 current_request_ = initial_request; 519 current_request_ = initial_request;
387 pending_initial_replies_.clear(); 520 pending_initial_replies_.clear();
388 pending_find_next_reply_ = nullptr; 521 pending_find_next_reply_ = nullptr;
389 pending_active_match_ordinal_ = true; 522 pending_active_match_ordinal_ = true;
390 matches_per_frame_.clear(); 523 matches_per_frame_.clear();
391 number_of_matches_ = 0; 524 number_of_matches_ = 0;
392 active_frame_ = nullptr; 525 active_frame_ = nullptr;
393 relative_active_match_ordinal_ = 0; 526 relative_active_match_ordinal_ = 0;
394 active_match_ordinal_ = 0; 527 active_match_ordinal_ = 0;
395 selection_rect_ = gfx::Rect(); 528 selection_rect_ = gfx::Rect();
396 last_reported_id_ = kInvalidId; 529 last_reported_id_ = kInvalidId;
530 frame_observers_.clear();
397 #if defined(OS_ANDROID) 531 #if defined(OS_ANDROID)
398 activate_ = ActivateNearestFindResultState(); 532 activate_ = ActivateNearestFindResultState();
399 match_rects_.pending_replies.clear(); 533 match_rects_.pending_replies.clear();
400 #endif 534 #endif
401 } 535 }
402 536
403 void FindRequestManager::FindInternal(const FindRequest& request) { 537 void FindRequestManager::FindInternal(const FindRequest& request) {
404 DCHECK_GT(request.id, current_request_.id); 538 DCHECK_GT(request.id, current_request_.id);
405 DCHECK_GT(request.id, current_session_id_); 539 DCHECK_GT(request.id, current_session_id_);
406 540
407 if (request.options.findNext) { 541 if (request.options.findNext) {
408 // This is a find next operation. 542 // This is a find next operation.
409 543
410 // This implies that there is an ongoing find session with the same search 544 // This implies that there is an ongoing find session with the same search
411 // text. 545 // text.
412 DCHECK_GE(current_session_id_, 0); 546 DCHECK_GE(current_session_id_, 0);
413 DCHECK_EQ(request.search_text, current_request_.search_text); 547 DCHECK_EQ(request.search_text, current_request_.search_text);
414 548
415 // The find next request will be directed at the focused frame if there is 549 // The find next request will be directed at the focused frame if there is
416 // one, or the first frame with matches otherwise. 550 // one, or the first frame with matches otherwise.
417 RenderFrameHost* target_rfh = contents_->GetFocusedFrame(); 551 RenderFrameHost* target_rfh =
552 contents_->GetFocusedWebContents()->GetFocusedFrame();
418 if (!target_rfh || !CheckFrame(target_rfh)) 553 if (!target_rfh || !CheckFrame(target_rfh))
419 target_rfh = GetInitialFrame(request.options.forward); 554 target_rfh = GetInitialFrame(request.options.forward);
420 555
421 SendFindIPC(request, target_rfh); 556 SendFindIPC(request, target_rfh);
422 current_request_ = request; 557 current_request_ = request;
423 pending_active_match_ordinal_ = true; 558 pending_active_match_ordinal_ = true;
424 return; 559 return;
425 } 560 }
426 561
427 // This is an initial find operation. 562 // This is an initial find operation.
428 Reset(request); 563 Reset(request);
429 for (FrameTreeNode* node : contents_->GetFrameTree()->Nodes()) 564 for (WebContentsImpl* contents : contents_->GetWebContentsAndAllInner()) {
430 AddFrame(node->current_frame_host(), false /* force */); 565 frame_observers_.push_back(base::MakeUnique<FrameObserver>(contents, this));
566 for (FrameTreeNode* node : contents->GetFrameTree()->Nodes()) {
567 AddFrame(node->current_frame_host(), false /* force */);
568 }
569 }
431 } 570 }
432 571
433 void FindRequestManager::AdvanceQueue(int request_id) { 572 void FindRequestManager::AdvanceQueue(int request_id) {
434 if (find_request_queue_.empty() || 573 if (find_request_queue_.empty() ||
435 request_id != find_request_queue_.front().id) { 574 request_id != find_request_queue_.front().id) {
436 return; 575 return;
437 } 576 }
438 577
439 find_request_queue_.pop(); 578 find_request_queue_.pop();
440 if (!find_request_queue_.empty()) 579 if (!find_request_queue_.empty())
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
478 if (!forward) 617 if (!forward)
479 rfh = GetDeepestLastChild(rfh); 618 rfh = GetDeepestLastChild(rfh);
480 619
481 return rfh; 620 return rfh;
482 } 621 }
483 622
484 RenderFrameHost* FindRequestManager::Traverse(RenderFrameHost* from_rfh, 623 RenderFrameHost* FindRequestManager::Traverse(RenderFrameHost* from_rfh,
485 bool forward, 624 bool forward,
486 bool matches_only, 625 bool matches_only,
487 bool wrap) const { 626 bool wrap) const {
627 DCHECK(from_rfh);
488 FrameTreeNode* node = 628 FrameTreeNode* node =
489 static_cast<RenderFrameHostImpl*>(from_rfh)->frame_tree_node(); 629 static_cast<RenderFrameHostImpl*>(from_rfh)->frame_tree_node();
490 630
491 while ((node = TraverseNode(node, forward, wrap)) != nullptr) { 631 while ((node = TraverseNode(node, forward, wrap)) != nullptr) {
492 if (!CheckFrame(node->current_frame_host())) 632 if (!CheckFrame(node->current_frame_host()))
493 continue; 633 continue;
494 RenderFrameHost* current_rfh = node->current_frame_host(); 634 RenderFrameHost* current_rfh = node->current_frame_host();
495 if (!matches_only || matches_per_frame_.find(current_rfh)->second || 635 if (!matches_only || matches_per_frame_.find(current_rfh)->second ||
496 pending_initial_replies_.count(current_rfh)) { 636 pending_initial_replies_.count(current_rfh)) {
497 // Note that if there is still a pending reply expected for this frame, 637 // Note that if there is still a pending reply expected for this frame,
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
565 // request must be sent. 705 // request must be sent.
566 706
567 RenderFrameHost* target_rfh; 707 RenderFrameHost* target_rfh;
568 if (request_id == current_request_.id && current_request_.options.findNext) { 708 if (request_id == current_request_.id && current_request_.options.findNext) {
569 // If this was a find next operation, then the active match will be in the 709 // If this was a find next operation, then the active match will be in the
570 // next frame with matches after this one. 710 // next frame with matches after this one.
571 target_rfh = Traverse(rfh, 711 target_rfh = Traverse(rfh,
572 current_request_.options.forward, 712 current_request_.options.forward,
573 true /* matches_only */, 713 true /* matches_only */,
574 true /* wrap */); 714 true /* wrap */);
575 } else if ((target_rfh = contents_->GetFocusedFrame()) != nullptr) { 715 } else if ((target_rfh =
716 contents_->GetFocusedWebContents()->GetFocusedFrame()) !=
717 nullptr) {
576 // Otherwise, if there is a focused frame, then the active match will be in 718 // Otherwise, if there is a focused frame, then the active match will be in
577 // the next frame with matches after that one. 719 // the next frame with matches after that one.
578 target_rfh = Traverse(target_rfh, 720 target_rfh = Traverse(target_rfh,
579 current_request_.options.forward, 721 current_request_.options.forward,
580 true /* matches_only */, 722 true /* matches_only */,
581 true /* wrap */); 723 true /* wrap */);
582 } else { 724 } else {
583 // Otherwise, the first frame with matches will have the active match. 725 // Otherwise, the first frame with matches will have the active match.
584 target_rfh = GetInitialFrame(current_request_.options.forward); 726 target_rfh = GetInitialFrame(current_request_.options.forward);
585 if (!CheckFrame(target_rfh) || !matches_per_frame_[target_rfh]) { 727 if (!CheckFrame(target_rfh) || !matches_per_frame_[target_rfh]) {
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
642 aggregate_rects.end(), frame_rects.begin(), frame_rects.end()); 784 aggregate_rects.end(), frame_rects.begin(), frame_rects.end());
643 } 785 }
644 } 786 }
645 contents_->NotifyFindMatchRectsReply( 787 contents_->NotifyFindMatchRectsReply(
646 match_rects_.known_version, aggregate_rects, match_rects_.active_rect); 788 match_rects_.known_version, aggregate_rects, match_rects_.active_rect);
647 } 789 }
648 } 790 }
649 #endif 791 #endif
650 792
651 } // namespace content 793 } // namespace content
OLDNEW
« no previous file with comments | « content/browser/find_request_manager.h ('k') | content/browser/web_contents/web_contents_impl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698