Chromium Code Reviews| Index: chrome/browser/translate/translate_tab_helper.cc |
| diff --git a/chrome/browser/translate/translate_tab_helper.cc b/chrome/browser/translate/translate_tab_helper.cc |
| index 7762c04789d72b9ff2bbc4a2cb4c970d42cc707a..ee60917b3f4b395765554440bf1fad102bab9808 100644 |
| --- a/chrome/browser/translate/translate_tab_helper.cc |
| +++ b/chrome/browser/translate/translate_tab_helper.cc |
| @@ -20,10 +20,14 @@ |
| #include "components/translate/content/common/translate_messages.h" |
| #include "components/translate/core/browser/page_translated_details.h" |
| #include "components/translate/core/browser/translate_accept_languages.h" |
| +#include "components/translate/core/browser/translate_download_manager.h" |
| #include "components/translate/core/browser/translate_prefs.h" |
| #include "components/translate/core/common/language_detection_details.h" |
| +#include "content/public/browser/navigation_details.h" |
| +#include "content/public/browser/navigation_entry.h" |
| #include "content/public/browser/notification_service.h" |
| #include "content/public/browser/web_contents.h" |
| +#include "net/http/http_status_code.h" |
| #if defined(CLD2_DYNAMIC_MODE) |
| #include "base/files/file.h" |
| @@ -34,6 +38,14 @@ |
| #include "content/public/browser/render_view_host.h" |
| #endif |
| +namespace { |
| + |
| +// The maximum number of attempts we'll do to see if the page has finshed |
| +// loading before giving up the translation |
| +const int kMaxTranslateLoadCheckAttempts = 20; |
| + |
| +} // namespace |
| + |
| DEFINE_WEB_CONTENTS_USER_DATA_KEY(TranslateTabHelper); |
| #if defined(CLD2_DYNAMIC_MODE) |
| @@ -47,11 +59,10 @@ base::LazyInstance<base::Lock> TranslateTabHelper::s_file_lock_ = |
| TranslateTabHelper::TranslateTabHelper(content::WebContents* web_contents) |
| : content::WebContentsObserver(web_contents), |
| -#if defined(CLD2_DYNAMIC_MODE) |
| - weak_pointer_factory_(this), |
| -#endif |
| + max_reload_check_attempts_(kMaxTranslateLoadCheckAttempts), |
| translate_driver_(&web_contents->GetController()), |
| - translate_manager_(new TranslateManager(this, prefs::kAcceptLanguages)) {} |
| + translate_manager_(new TranslateManager(this, prefs::kAcceptLanguages)), |
| + weak_pointer_factory_(this) {} |
| TranslateTabHelper::~TranslateTabHelper() { |
| } |
| @@ -168,6 +179,57 @@ bool TranslateTabHelper::OnMessageReceived(const IPC::Message& message) { |
| return handled; |
| } |
| +void TranslateTabHelper::NavigationEntryCommitted( |
| + const content::LoadCommittedDetails& load_details) { |
| + // Check whether this is a reload: When doing a page reload, the |
|
blundell
2014/04/07 08:03:01
A couple notes here:
- The WCO method NavigationE
|
| + // TranslateLanguageDetermined IPC is not sent |
| + // so the translation needs to be explicitly initiated. |
| + |
| + content::NavigationEntry* entry = |
| + web_contents()->GetController().GetActiveEntry(); |
| + if (!entry) { |
|
blundell
2014/04/07 08:03:01
I don't really know why there are all these checks
|
| + NOTREACHED(); |
| + return; |
| + } |
| + |
| + // If the navigation happened while offline don't show the translate |
| + // bar since there will be nothing to translate. |
| + if (load_details.http_status_code == 0 || |
| + load_details.http_status_code == net::HTTP_INTERNAL_SERVER_ERROR) { |
| + return; |
| + } |
| + |
| + if (!load_details.is_main_frame && |
| + translate_driver_.GetLanguageState().translation_declined()) { |
| + // Some sites (such as Google map) may trigger sub-frame navigations |
| + // when the user interacts with the page. We don't want to show a new |
| + // infobar if the user already dismissed one in that case. |
| + return; |
| + } |
| + |
| + // If not a reload, return. |
| + if (entry->GetTransitionType() != content::PAGE_TRANSITION_RELOAD && |
|
blundell
2014/04/07 08:03:01
I actually think it would be clearest if this chec
|
| + load_details.type != content::NAVIGATION_TYPE_SAME_PAGE) { |
| + return; |
| + } |
| + |
| + if (!translate_driver_.GetLanguageState().page_needs_translation()) |
| + return; |
| + |
| + // Note that we delay it as the ordering of the processing of this callback |
| + // by WebContentsObservers is undefined and might result in the current |
| + // infobars being removed. Since the translation initiation process might add |
| + // an |
| + // infobar, it must |
|
droger
2014/04/07 11:14:41
Nit: format.
|
| + // be done after that. |
| + base::MessageLoop::current()->PostTask( |
| + FROM_HERE, |
| + base::Bind(&TranslateTabHelper::InitiateTranslation, |
| + weak_pointer_factory_.GetWeakPtr(), |
| + translate_driver_.GetLanguageState().original_language(), |
| + 0)); |
| +} |
| + |
| void TranslateTabHelper::DidNavigateAnyFrame( |
| const content::LoadCommittedDetails& details, |
| const content::FrameNavigateParams& params) { |
| @@ -310,6 +372,31 @@ void TranslateTabHelper::HandleCLDDataRequest() { |
| } |
| #endif // defined(CLD2_DYNAMIC_MODE) |
| +void TranslateTabHelper::InitiateTranslation(const std::string& page_lang, |
| + int attempt) { |
| + if (translate_driver_.GetLanguageState().translation_pending()) |
| + return; |
| + |
| + // During a reload we need web content to be available before the |
| + // translate script is executed. Otherwise we will run the translate script on |
| + // an empty DOM which will fail. Therefore we wait a bit to see if the page |
| + // has finished. |
| + if (web_contents()->IsLoading() && attempt < max_reload_check_attempts_) { |
| + int backoff = attempt * kMaxTranslateLoadCheckAttempts; |
| + base::MessageLoop::current()->PostDelayedTask( |
| + FROM_HERE, |
| + base::Bind(&TranslateTabHelper::InitiateTranslation, |
| + weak_pointer_factory_.GetWeakPtr(), |
| + page_lang, |
| + ++attempt), |
| + base::TimeDelta::FromMilliseconds(backoff)); |
| + return; |
| + } |
| + |
| + translate_manager_->InitiateTranslation( |
| + TranslateDownloadManager::GetLanguageCode(page_lang)); |
| +} |
| + |
| void TranslateTabHelper::OnLanguageDetermined( |
| const LanguageDetectionDetails& details, |
| bool page_needs_translation) { |