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: chrome/renderer/searchbox/searchbox.cc

Issue 13375003: Fixing iframe jank in the local omnibox popup. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Addressing comments. Created 7 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 | Annotate | Revision Log
OLDNEW
1 // Copyright 2012 The Chromium Authors. All rights reserved. 1 // Copyright 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 "chrome/renderer/searchbox/searchbox.h" 5 #include "chrome/renderer/searchbox/searchbox.h"
6 6
7 #include "base/metrics/field_trial.h"
8 #include "base/string_number_conversions.h" 7 #include "base/string_number_conversions.h"
9 #include "base/utf_string_conversions.h" 8 #include "base/utf_string_conversions.h"
10 #include "chrome/common/chrome_switches.h" 9 #include "chrome/common/chrome_switches.h"
11 #include "chrome/common/render_messages.h" 10 #include "chrome/common/render_messages.h"
12 #include "chrome/common/url_constants.h" 11 #include "chrome/common/url_constants.h"
13 #include "chrome/renderer/searchbox/searchbox_extension.h" 12 #include "chrome/renderer/searchbox/searchbox_extension.h"
14 #include "content/public/renderer/render_view.h" 13 #include "content/public/renderer/render_view.h"
15 #include "grit/renderer_resources.h" 14 #include "grit/renderer_resources.h"
16 #include "net/base/escape.h" 15 #include "net/base/escape.h"
17 #include "third_party/WebKit/Source/WebKit/chromium/public/WebDocument.h" 16 #include "third_party/WebKit/Source/WebKit/chromium/public/WebDocument.h"
18 #include "third_party/WebKit/Source/WebKit/chromium/public/WebFrame.h" 17 #include "third_party/WebKit/Source/WebKit/chromium/public/WebFrame.h"
19 #include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h" 18 #include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h"
20 #include "ui/base/resource/resource_bundle.h" 19 #include "ui/base/resource/resource_bundle.h"
21 20
22 namespace { 21 namespace {
23 22
24 // Size of the results cache. 23 // Size of the results cache.
25 const size_t kMaxInstantAutocompleteResultItemCacheSize = 100; 24 const size_t kMaxInstantAutocompleteResultItemCacheSize = 100;
26 25
27 // The HTML returned when an invalid or unknown restricted ID is requested.
28 const char kInvalidSuggestionHtml[] =
29 "<div style=\"background:red\">invalid rid %d</div>";
30
31 // Checks if the input color is in valid range.
32 bool IsColorValid(int color) {
33 return color >= 0 && color <= 0xffffff;
34 }
35
36 // If |url| starts with |prefix|, removes |prefix|.
37 void StripPrefix(string16* url, const string16& prefix) {
38 if (StartsWith(*url, prefix, true))
39 url->erase(0, prefix.length());
40 }
41
42 // Removes leading "http://" or "http://www." from |url| unless |userInput|
43 // starts with those prefixes.
44 void StripURLPrefixes(string16* url, const string16& userInput) {
45 string16 trimmedUserInput;
46 TrimWhitespace(userInput, TRIM_TRAILING, &trimmedUserInput);
47 if (StartsWith(*url, trimmedUserInput, true))
48 return;
49
50 StripPrefix(url, ASCIIToUTF16(chrome::kHttpScheme) + ASCIIToUTF16("://"));
51
52 if (StartsWith(*url, trimmedUserInput, true))
53 return;
54
55 StripPrefix(url, ASCIIToUTF16("www."));
56 }
57
58 } // namespace 26 } // namespace
59 27
60 SearchBox::SearchBox(content::RenderView* render_view) 28 SearchBox::SearchBox(content::RenderView* render_view)
61 : content::RenderViewObserver(render_view), 29 : content::RenderViewObserver(render_view),
62 content::RenderViewObserverTracker<SearchBox>(render_view), 30 content::RenderViewObserverTracker<SearchBox>(render_view),
63 verbatim_(false), 31 verbatim_(false),
64 selection_start_(0), 32 selection_start_(0),
65 selection_end_(0), 33 selection_end_(0),
66 start_margin_(0), 34 start_margin_(0),
67 is_key_capture_enabled_(false), 35 is_key_capture_enabled_(false),
(...skipping 324 matching lines...) Expand 10 before | Expand all | Expand 10 after
392 std::vector<InstantMostVisitedItemIDPair>* items) const { 360 std::vector<InstantMostVisitedItemIDPair>* items) const {
393 return most_visited_items_cache_.GetCurrentItems(items); 361 return most_visited_items_cache_.GetCurrentItems(items);
394 } 362 }
395 363
396 bool SearchBox::GetMostVisitedItemWithID( 364 bool SearchBox::GetMostVisitedItemWithID(
397 InstantRestrictedID most_visited_item_id, 365 InstantRestrictedID most_visited_item_id,
398 InstantMostVisitedItem* item) const { 366 InstantMostVisitedItem* item) const {
399 return most_visited_items_cache_.GetItemWithRestrictedID(most_visited_item_id, 367 return most_visited_items_cache_.GetItemWithRestrictedID(most_visited_item_id,
400 item); 368 item);
401 } 369 }
402
403 bool SearchBox::GenerateDataURLForSuggestionRequest(const GURL& request_url,
404 GURL* data_url) const {
405 DCHECK(data_url);
406
407 if (!ShouldUseIframes())
408 return false;
409
410 // The origin URL is required so that the iframe knows what origin to post
411 // messages to.
412 WebKit::WebView* webview = render_view()->GetWebView();
413 if (!webview)
414 return false;
415 GURL embedder_url(webview->mainFrame()->document().url());
416 GURL embedder_origin = embedder_url.GetOrigin();
417 if (!embedder_origin.is_valid())
418 return false;
419
420 DCHECK(StartsWithASCII(request_url.path(), "/", true));
421 std::string restricted_id_str = request_url.path().substr(1);
422
423 InstantRestrictedID restricted_id = 0;
424 DCHECK_EQ(sizeof(InstantRestrictedID), sizeof(int));
425 if (!base::StringToInt(restricted_id_str, &restricted_id))
426 return false;
427
428 std::string response_html;
429 InstantAutocompleteResult result;
430 if (autocomplete_results_cache_.GetItemWithRestrictedID(
431 restricted_id, &result)) {
432 std::string template_html =
433 ResourceBundle::GetSharedInstance().GetRawDataResource(
434 IDR_OMNIBOX_RESULT).as_string();
435
436 DCHECK(IsColorValid(autocomplete_results_style_.url_color));
437 DCHECK(IsColorValid(autocomplete_results_style_.title_color));
438
439 string16 contents;
440 if (result.search_query.empty()) {
441 contents = result.destination_url;
442 FormatURLForDisplay(&contents);
443 } else {
444 contents = result.search_query;
445 }
446
447 // First, HTML-encode the text so that '&', '<' and such lose their special
448 // meaning. Next, URL-encode the text because it will be inserted into
449 // "data:" URIs; thus '%' and such lose their special meaning.
450 std::string encoded_contents = net::EscapeQueryParamValue(
451 net::EscapeForHTML(UTF16ToUTF8(contents)), false);
452 std::string encoded_description = net::EscapeQueryParamValue(
453 net::EscapeForHTML(UTF16ToUTF8(result.description)), false);
454
455 response_html = base::StringPrintf(
456 template_html.c_str(),
457 embedder_origin.spec().c_str(),
458 UTF16ToUTF8(omnibox_font_).c_str(),
459 omnibox_font_size_,
460 autocomplete_results_style_.url_color,
461 autocomplete_results_style_.title_color,
462 encoded_contents.c_str(),
463 encoded_description.c_str());
464 } else {
465 response_html = base::StringPrintf(kInvalidSuggestionHtml, restricted_id);
466 }
467
468 *data_url = GURL("data:text/html;charset=utf-8," + response_html);
469 return true;
470 }
471
472 void SearchBox::SetInstantAutocompleteResultStyle(
473 const InstantAutocompleteResultStyle& style) {
474 if (IsColorValid(style.url_color) && IsColorValid(style.title_color))
475 autocomplete_results_style_ = style;
476 }
477
478 void SearchBox::FormatURLForDisplay(string16* url) const {
479 StripURLPrefixes(url, query());
480
481 string16 trimmedUserInput;
482 TrimWhitespace(query(), TRIM_LEADING, &trimmedUserInput);
483 if (EndsWith(*url, trimmedUserInput, true))
484 return;
485
486 // Strip a lone trailing slash.
487 if (EndsWith(*url, ASCIIToUTF16("/"), true))
488 url->erase(url->length() - 1, 1);
489 }
490
491 // static
492 bool SearchBox::ShouldUseIframes() {
493 // TODO(shishir): All the code below is just temporary and needs to be removed
494 // once support for ShadowDom is removed.
495
496 // The following is hacky. But given the short lifespan of this code
497 // and the amount of code that would need to be moved/copied for this change,
498 // it's probably worth it.
499 static const char kInstantExtendedFieldTrialName[] = "InstantExtended";
500 static const char kIframesEnabledFlagWithValue[] = "iframe:1";
501 std::string trial_flags =
502 base::FieldTrialList::FindFullName(kInstantExtendedFieldTrialName);
503 std::vector<std::string> flags;
504 Tokenize(trial_flags, " ", &flags);
505 for (size_t i = 0; i < flags.size(); ++i) {
506 if (flags[i] == kIframesEnabledFlagWithValue)
507 return true;
508 }
509 return false;
510 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698