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 3 // found in the LICENSE file. 4 5 #ifndef CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_ 6 #define CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_ 7 8 #include <stdint.h> 9 10 #include "base/macros.h" 11 #include "base/optional.h" 12 #include "base/process/kill.h" 13 #include "base/process/process_handle.h" 14 #include "base/threading/thread_restrictions.h" 15 #include "components/viz/common/vertical_scroll_direction.h" 16 #include "content/common/content_export.h" 17 #include "content/public/browser/allow_service_worker_result.h" 18 #include "content/public/browser/cookie_access_details.h" 19 #include "content/public/browser/navigation_controller.h" 20 #include "content/public/browser/reload_type.h" 21 #include "content/public/browser/visibility.h" 22 #include "ipc/ipc_listener.h" 23 #include "mojo/public/cpp/system/message_pipe.h" 24 #include "services/network/public/mojom/fetch_api.mojom-forward.h" 25 #include "services/service_manager/public/cpp/bind_source_info.h" 26 #include "third_party/blink/public/common/input/web_input_event.h" 27 #include "third_party/blink/public/common/user_agent/user_agent_metadata.h" 28 #include "third_party/blink/public/mojom/choosers/popup_menu.mojom.h" 29 #include "third_party/blink/public/mojom/devtools/console_message.mojom.h" 30 #include "third_party/blink/public/mojom/loader/resource_load_info.mojom-forward.h" 31 #include "third_party/skia/include/core/SkColor.h" 32 #include "ui/base/page_transition_types.h" 33 #include "ui/base/window_open_disposition.h" 34 35 namespace blink { 36 namespace mojom { 37 enum class ViewportFit; 38 } // namespace mojom 39 } // namespace blink 40 41 namespace gfx { 42 class Size; 43 } // namespace gfx 44 45 namespace content { 46 47 class NavigationEntry; 48 class NavigationHandle; 49 class RenderFrameHost; 50 class RenderProcessHost; 51 class RenderViewHost; 52 class RenderWidgetHost; 53 class WebContents; 54 class WebContentsImpl; 55 struct AXEventNotificationDetails; 56 struct AXLocationChangeNotificationDetails; 57 struct EntryChangedDetails; 58 struct FocusedNodeDetails; 59 struct LoadCommittedDetails; 60 struct MediaPlayerId; 61 struct PrunedDetails; 62 struct Referrer; 63 64 // An observer API implemented by classes which are interested in various page 65 // load events from WebContents. They also get a chance to filter IPC messages. 66 // 67 // Since a WebContents can be a delegate to almost arbitrarily many 68 // RenderViewHosts, it is important to check in those WebContentsObserver 69 // methods which take a RenderViewHost that the event came from the 70 // RenderViewHost the observer cares about. 71 // 72 // Usually, observers should only care about the current RenderViewHost as 73 // returned by GetRenderViewHost(). 74 // 75 // TODO(creis, jochen): Hide the fact that there are several RenderViewHosts 76 // from the WebContentsObserver API. http://crbug.com/173325 77 class CONTENT_EXPORT WebContentsObserver : public IPC::Listener { 78 public: 79 // Frames and Views ---------------------------------------------------------- 80 81 // Called when a RenderFrame for |render_frame_host| is created in the 82 // renderer process. Use |RenderFrameDeleted| to listen for when this 83 // RenderFrame goes away. RenderFrameCreated(RenderFrameHost * render_frame_host)84 virtual void RenderFrameCreated(RenderFrameHost* render_frame_host) {} 85 86 // Called when a RenderFrame for |render_frame_host| is deleted or the 87 // renderer process in which it runs it has died. Use |RenderFrameCreated| to 88 // listen for when RenderFrame objects are created. RenderFrameDeleted(RenderFrameHost * render_frame_host)89 virtual void RenderFrameDeleted(RenderFrameHost* render_frame_host) {} 90 91 // This method is invoked whenever one of the current frames of a WebContents 92 // swaps its RenderFrameHost with another one; for example because that frame 93 // navigated and the new content is in a different process. The 94 // RenderFrameHost that has been replaced is in |old_host|, which can be 95 // nullptr if the old RenderFrameHost was shut down or a new frame has been 96 // created and no old RenderFrameHost exists. 97 // 98 // This method, in combination with |FrameDeleted|, is appropriate for 99 // observers wishing to track the set of current RenderFrameHosts -- i.e., 100 // those hosts that would be visited by calling WebContents::ForEachFrame(). RenderFrameHostChanged(RenderFrameHost * old_host,RenderFrameHost * new_host)101 virtual void RenderFrameHostChanged(RenderFrameHost* old_host, 102 RenderFrameHost* new_host) {} 103 104 // This method is invoked when a subframe associated with a WebContents is 105 // deleted or the WebContents is destroyed and the top-level frame is deleted. 106 // Use |RenderFrameHostChanged| to listen for when a RenderFrameHost object is 107 // made the current host for a frame. FrameDeleted(RenderFrameHost * render_frame_host)108 virtual void FrameDeleted(RenderFrameHost* render_frame_host) {} 109 110 // This is called when a RVH is created for a WebContents, but not if it's an 111 // interstitial. RenderViewCreated(RenderViewHost * render_view_host)112 virtual void RenderViewCreated(RenderViewHost* render_view_host) {} 113 114 // This method is invoked when the RenderView of the current RenderViewHost 115 // is ready, e.g. because we recreated it after a crash. RenderViewReady()116 virtual void RenderViewReady() {} 117 118 // This method is invoked when a RenderViewHost of the WebContents is 119 // deleted. Note that this does not always happen when the WebContents starts 120 // to use a different RenderViewHost, as the old RenderViewHost might get 121 // just swapped out. RenderViewDeleted(RenderViewHost * render_view_host)122 virtual void RenderViewDeleted(RenderViewHost* render_view_host) {} 123 124 // This method is invoked when the process for the current main 125 // RenderFrameHost exits (usually by crashing, though possibly by other 126 // means). The WebContents continues to use the RenderFrameHost, e.g. when the 127 // user reloads the current page. When the RenderFrameHost itself is deleted, 128 // the RenderFrameDeleted method will be invoked. 129 // 130 // Note that this is triggered upstream through 131 // RenderProcessHostObserver::RenderProcessExited(); for code that doesn't 132 // otherwise need to be a WebContentsObserver, that API is probably a better 133 // choice. RenderProcessGone(base::TerminationStatus status)134 virtual void RenderProcessGone(base::TerminationStatus status) {} 135 136 // This method is invoked when a WebContents swaps its visible RenderViewHost 137 // with another one, possibly changing processes. The RenderViewHost that has 138 // been replaced is in |old_host|, which is nullptr if the old RVH was shut 139 // down. RenderViewHostChanged(RenderViewHost * old_host,RenderViewHost * new_host)140 virtual void RenderViewHostChanged(RenderViewHost* old_host, 141 RenderViewHost* new_host) {} 142 143 // This method is invoked when a process in the WebContents becomes 144 // unresponsive. OnRendererUnresponsive(RenderProcessHost * render_process_host)145 virtual void OnRendererUnresponsive(RenderProcessHost* render_process_host) {} 146 147 // See WebContentsDelegate::RendererResponsive(). OnRendererResponsive(RenderProcessHost * render_process_host)148 virtual void OnRendererResponsive(RenderProcessHost* render_process_host) {} 149 150 // Navigation ---------------------------------------------------------------- 151 152 // Called when a navigation started in the WebContents. |navigation_handle| 153 // is unique to a specific navigation. The same |navigation_handle| will be 154 // provided on subsequent calls to DidRedirectNavigation, DidFinishNavigation, 155 // and ReadyToCommitNavigation when related to this navigation. Observers 156 // should clear any references to |navigation_handle| in DidFinishNavigation, 157 // just before it is destroyed. 158 // 159 // Note that this is fired by navigations in any frame of the WebContents, 160 // not just the main frame. 161 // 162 // Note that this is fired by same-document navigations, such as fragment 163 // navigations or pushState/replaceState, which will not result in a document 164 // change. To filter these out, use NavigationHandle::IsSameDocument. 165 // 166 // Note that more than one navigation can be ongoing in the same frame at the 167 // same time (including the main frame). Each will get its own 168 // NavigationHandle. 169 // 170 // Note that there is no guarantee that DidFinishNavigation will be called 171 // for any particular navigation before DidStartNavigation is called on the 172 // next. DidStartNavigation(NavigationHandle * navigation_handle)173 virtual void DidStartNavigation(NavigationHandle* navigation_handle) {} 174 175 // Called when a navigation encountered a server redirect. DidRedirectNavigation(NavigationHandle * navigation_handle)176 virtual void DidRedirectNavigation(NavigationHandle* navigation_handle) {} 177 178 // Called when the navigation is ready to be committed in a renderer. This 179 // occurs when the response code isn't 204/205 (which tell the browser that 180 // the request is successful but there's no content that follows) or a 181 // download (either from a response header or based on mime sniffing the 182 // response). The browser then is ready to switch rendering the new document. 183 // Most observers should use DidFinishNavigation instead, which happens right 184 // after the navigation commits. This method is for observers that want to 185 // initialize renderer-side state just before the RenderFrame commits the 186 // navigation. 187 // 188 // This is the first point in time where a RenderFrameHost is associated with 189 // the navigation. ReadyToCommitNavigation(NavigationHandle * navigation_handle)190 virtual void ReadyToCommitNavigation(NavigationHandle* navigation_handle) {} 191 192 // Called when a navigation finished in the WebContents. This happens when a 193 // navigation is committed, aborted or replaced by a new one. To know if the 194 // navigation has committed, use NavigationHandle::HasCommitted; use 195 // NavigationHandle::IsErrorPage to know if the navigation resulted in an 196 // error page. 197 // 198 // If this is called because the navigation committed, then the document load 199 // will still be ongoing in the RenderFrameHost returned by 200 // |navigation_handle|. Use the document loads events such as DidStopLoading 201 // and related methods to listen for continued events from this 202 // RenderFrameHost. 203 // 204 // Note that this is fired by same-document navigations, such as fragment 205 // navigations or pushState/replaceState, which will not result in a document 206 // change. To filter these out, use NavigationHandle::IsSameDocument. 207 // 208 // Note that |navigation_handle| will be destroyed at the end of this call, 209 // so do not keep a reference to it afterward. 210 // 211 // Note that using DidFinishNavigation to detect changes in the currently 212 // active document and reset per-document state is strongly discouraged. 213 // Please use RenderDocumentHostUserData to store such data instead. 214 // (In particular, the page might be stored in back-forward cache instead 215 // of being deleted. See the comment in RenderDocumentHostUserData for more 216 // details). DidFinishNavigation(NavigationHandle * navigation_handle)217 virtual void DidFinishNavigation(NavigationHandle* navigation_handle) {} 218 219 // Called after the contents replaces the |predecessor_contents| in its 220 // container due to portal activation. The |predecessor_contents| is now a 221 // portal pending adoption. |predecessor_contents| is non-null, but may 222 // subsequently be destroyed if it is not adopted. 223 // |activation_time| is the time the activation happened. DidActivatePortal(WebContents * predecessor_web_contents,base::TimeTicks activation_time)224 virtual void DidActivatePortal(WebContents* predecessor_web_contents, 225 base::TimeTicks activation_time) {} 226 227 // Document load events ------------------------------------------------------ 228 229 // These three methods correspond to the points in time when a document starts 230 // loading for the first time (initiates outgoing requests), when incoming 231 // data subsequently starts arriving, and when it finishes loading. DidStartLoading()232 virtual void DidStartLoading() {} DidReceiveResponse()233 virtual void DidReceiveResponse() {} DidStopLoading()234 virtual void DidStopLoading() {} 235 236 // The page has made some progress loading. |progress| is a value between 0.0 237 // (nothing loaded) to 1.0 (page fully loaded). LoadProgressChanged(double progress)238 virtual void LoadProgressChanged(double progress) {} 239 240 // This method is invoked once the window.document object of the main frame 241 // was created. DocumentAvailableInMainFrame()242 virtual void DocumentAvailableInMainFrame() {} 243 244 // This method is invoked once the onload handler of the main frame has 245 // completed. 246 // Prefer using WebContents::IsDocumentOnLoadCompletedInMainFrame instead 247 // of saving this state in your component. DocumentOnLoadCompletedInMainFrame()248 virtual void DocumentOnLoadCompletedInMainFrame() {} 249 250 // This method is invoked when the document in the given frame finished 251 // loading. At this point, scripts marked as defer were executed, and 252 // content scripts marked "document_end" get injected into the frame. DOMContentLoaded(RenderFrameHost * render_frame_host)253 virtual void DOMContentLoaded(RenderFrameHost* render_frame_host) {} 254 255 // This method is invoked when the load is done, i.e. the spinner of the tab 256 // will stop spinning, and the onload event was dispatched. 257 // 258 // If the WebContents is displaying replacement content, e.g. network error 259 // pages, DidFinishLoad is invoked for frames that were not sending 260 // navigational events before. It is safe to ignore these events. DidFinishLoad(RenderFrameHost * render_frame_host,const GURL & validated_url)261 virtual void DidFinishLoad(RenderFrameHost* render_frame_host, 262 const GURL& validated_url) {} 263 264 // This method is like DidFinishLoad, but when the load failed or was 265 // cancelled, e.g. window.stop() is invoked. DidFailLoad(RenderFrameHost * render_frame_host,const GURL & validated_url,int error_code)266 virtual void DidFailLoad(RenderFrameHost* render_frame_host, 267 const GURL& validated_url, 268 int error_code) {} 269 270 // This method is invoked when the visible security state of the page changes. DidChangeVisibleSecurityState()271 virtual void DidChangeVisibleSecurityState() {} 272 273 // This method is invoked when content was loaded from an in-memory cache. DidLoadResourceFromMemoryCache(const GURL & url,const std::string & mime_type,network::mojom::RequestDestination request_destination)274 virtual void DidLoadResourceFromMemoryCache( 275 const GURL& url, 276 const std::string& mime_type, 277 network::mojom::RequestDestination request_destination) {} 278 279 // This method is invoked when a resource associate with the frame 280 // |render_frame_host| has been loaded, successfully or not. |request_id| will 281 // only be populated for main frame resources. ResourceLoadComplete(RenderFrameHost * render_frame_host,const GlobalRequestID & request_id,const blink::mojom::ResourceLoadInfo & resource_load_info)282 virtual void ResourceLoadComplete( 283 RenderFrameHost* render_frame_host, 284 const GlobalRequestID& request_id, 285 const blink::mojom::ResourceLoadInfo& resource_load_info) {} 286 287 // Called when document reads or sets a cookie (either via document.cookie or 288 // issuing a network request). 289 // Cookie reads/writes for a dedicated worker are attributed to the 290 // RenderFrameHost which created it. OnCookiesAccessed(RenderFrameHost * render_frame_host,const CookieAccessDetails & details)291 virtual void OnCookiesAccessed(RenderFrameHost* render_frame_host, 292 const CookieAccessDetails& details) {} 293 294 // Called when a network request issued by the navigation reads or sets a 295 // cookie. If a notification is received after the navigation has committed, 296 // it will be attributed to the RenderFrameHost created by the navigation. OnCookiesAccessed(NavigationHandle * navigation_handle,const CookieAccessDetails & details)297 virtual void OnCookiesAccessed(NavigationHandle* navigation_handle, 298 const CookieAccessDetails& details) {} 299 300 // This method is invoked when a new non-pending navigation entry is created. 301 // This corresponds to one NavigationController entry being created 302 // (in the case of new navigations) or renavigated to (for back/forward 303 // navigations). NavigationEntryCommitted(const LoadCommittedDetails & load_details)304 virtual void NavigationEntryCommitted( 305 const LoadCommittedDetails& load_details) {} 306 307 // Invoked when the NavigationController decreased its back/forward list count 308 // by removing entries from either the front or back of its list. This is 309 // usually the result of going back and then doing a new navigation, meaning 310 // all the "forward" items are deleted. 311 // 312 // This normally happens as a result of a new navigation. It will be 313 // followed by a NavigationEntryCommitted() call for the new page that 314 // caused the pruning. It could also be a result of removing an item from 315 // the list to delete history or fix up after interstitials. NavigationListPruned(const PrunedDetails & pruned_details)316 virtual void NavigationListPruned(const PrunedDetails& pruned_details) {} 317 318 // Invoked when NavigationEntries have been deleted because of a history 319 // deletion. Observers should ensure that they remove all traces of the 320 // deleted entries. NavigationEntriesDeleted()321 virtual void NavigationEntriesDeleted() {} 322 323 // Invoked when a NavigationEntry has changed. 324 // 325 // This will NOT be sent on navigation, interested parties should also 326 // implement NavigationEntryCommitted() to handle that case. This will be 327 // sent when the entry is updated outside of navigation (like when a new 328 // title comes). NavigationEntryChanged(const EntryChangedDetails & change_details)329 virtual void NavigationEntryChanged( 330 const EntryChangedDetails& change_details) {} 331 332 // This method is invoked when a new WebContents was created in response to 333 // an action in the observed WebContents, e.g. a link with target=_blank was 334 // clicked. The |source_render_frame_host| is the frame in which the action 335 // took place. DidOpenRequestedURL(WebContents * new_contents,RenderFrameHost * source_render_frame_host,const GURL & url,const Referrer & referrer,WindowOpenDisposition disposition,ui::PageTransition transition,bool started_from_context_menu,bool renderer_initiated)336 virtual void DidOpenRequestedURL(WebContents* new_contents, 337 RenderFrameHost* source_render_frame_host, 338 const GURL& url, 339 const Referrer& referrer, 340 WindowOpenDisposition disposition, 341 ui::PageTransition transition, 342 bool started_from_context_menu, 343 bool renderer_initiated) {} 344 345 // This method is invoked when the renderer process has completed its first 346 // paint after a non-empty layout. DidFirstVisuallyNonEmptyPaint()347 virtual void DidFirstVisuallyNonEmptyPaint() {} 348 349 // When WebContents::Stop() is called, the WebContents stops loading and then 350 // invokes this method. If there are ongoing navigations, their respective 351 // failure methods will also be invoked. NavigationStopped()352 virtual void NavigationStopped() {} 353 354 // Called when there has been direct user interaction with the WebContents. 355 // The type of the event specifies the kind of interaction. Direct user input 356 // signalled through this callback includes: 357 // 1) any mouse down event (blink::WebInputEvent::MouseDown); 358 // 2) the start of a scroll (blink::WebInputEvent::GestureScrollBegin); 359 // 3) any raw key down event (blink::WebInputEvent::RawKeyDown); and 360 // 4) any touch event (inc. scrolls) (blink::WebInputEvent::TouchStart). DidGetUserInteraction(const blink::WebInputEvent & event)361 virtual void DidGetUserInteraction(const blink::WebInputEvent& event) {} 362 363 // This method is invoked when a RenderViewHost of this WebContents was 364 // configured to ignore UI events, and an UI event took place. DidGetIgnoredUIEvent()365 virtual void DidGetIgnoredUIEvent() {} 366 367 // Invoked every time the WebContents changes visibility. OnVisibilityChanged(Visibility visibility)368 virtual void OnVisibilityChanged(Visibility visibility) {} 369 370 // Invoked when the main frame changes size. MainFrameWasResized(bool width_changed)371 virtual void MainFrameWasResized(bool width_changed) {} 372 373 // Invoked when the given frame changes its window.name property. FrameNameChanged(RenderFrameHost * render_frame_host,const std::string & name)374 virtual void FrameNameChanged(RenderFrameHost* render_frame_host, 375 const std::string& name) {} 376 377 // Called when the sticky user activation bit has been set on the frame. 378 // This will not be called for new RenderFrameHosts whose underlying 379 // FrameTreeNode was already activated. This should not be used to determine a 380 // RenderFrameHost's user activation state. FrameReceivedFirstUserActivation(RenderFrameHost * render_frame_host)381 virtual void FrameReceivedFirstUserActivation( 382 RenderFrameHost* render_frame_host) {} 383 384 // Invoked when the display state of the frame changes. FrameDisplayStateChanged(RenderFrameHost * render_frame_host,bool is_display_none)385 virtual void FrameDisplayStateChanged(RenderFrameHost* render_frame_host, 386 bool is_display_none) {} 387 388 // Invoked when a frame changes size. FrameSizeChanged(RenderFrameHost * render_frame_host,const gfx::Size & frame_size)389 virtual void FrameSizeChanged(RenderFrameHost* render_frame_host, 390 const gfx::Size& frame_size) {} 391 392 // This method is invoked when the title of the WebContents is set. Note that 393 // |entry| may be null if the web page whose title changed has not yet had a 394 // NavigationEntry assigned to it. TitleWasSet(NavigationEntry * entry)395 virtual void TitleWasSet(NavigationEntry* entry) {} 396 AppCacheAccessed(const GURL & manifest_url,bool blocked_by_policy)397 virtual void AppCacheAccessed(const GURL& manifest_url, 398 bool blocked_by_policy) {} 399 400 // These methods are invoked when a Pepper plugin instance is created/deleted 401 // in the DOM. PepperInstanceCreated()402 virtual void PepperInstanceCreated() {} PepperInstanceDeleted()403 virtual void PepperInstanceDeleted() {} 404 405 // This method is called when the viewport fit of a WebContents changes. ViewportFitChanged(blink::mojom::ViewportFit value)406 virtual void ViewportFitChanged(blink::mojom::ViewportFit value) {} 407 408 // Notification that a plugin has crashed. 409 // |plugin_pid| is the process ID identifying the plugin process. Note that 410 // this ID is supplied by the renderer process, so should not be trusted. 411 // Besides, the corresponding process has probably died at this point. The ID 412 // may even have been reused by a new process. PluginCrashed(const base::FilePath & plugin_path,base::ProcessId plugin_pid)413 virtual void PluginCrashed(const base::FilePath& plugin_path, 414 base::ProcessId plugin_pid) {} 415 416 // Notification that the given plugin has hung or become unhung. This 417 // notification is only for Pepper plugins. 418 // 419 // The plugin_child_id is the unique child process ID from the plugin. Note 420 // that this ID is supplied by the renderer process, so should be validated 421 // before it's used for anything in case there's an exploited renderer 422 // process. PluginHungStatusChanged(int plugin_child_id,const base::FilePath & plugin_path,bool is_hung)423 virtual void PluginHungStatusChanged(int plugin_child_id, 424 const base::FilePath& plugin_path, 425 bool is_hung) {} 426 427 // Notifies that an inner WebContents instance has been created with the 428 // observed WebContents as its container. |inner_web_contents| has not been 429 // added to the WebContents tree at this point, but can be observed safely. InnerWebContentsCreated(WebContents * inner_web_contents)430 virtual void InnerWebContentsCreated(WebContents* inner_web_contents) {} 431 432 // Notifies that an |inner_web_contents| instance has been attached to the 433 // provided |render_frame_host|. By the time this is called the 434 // |inner_web_contents| will have been added to the WebContents tree. InnerWebContentsAttached(WebContents * inner_web_contents,RenderFrameHost * render_frame_host,bool is_full_page)435 virtual void InnerWebContentsAttached(WebContents* inner_web_contents, 436 RenderFrameHost* render_frame_host, 437 bool is_full_page) {} 438 439 // Notifies that an |inner_web_contents| instance has been detached from this 440 // WebContents. InnerWebContentsAttached() will already have been called for 441 // the |inner_web_contents|. By the time this is called the 442 // |inner_web_contents| will have been removed from the WebContents tree, but 443 // will still be alive and is safe to observe. InnerWebContentsDetached(WebContents * inner_web_contents)444 virtual void InnerWebContentsDetached(WebContents* inner_web_contents) {} 445 446 // Invoked when WebContents::Clone() was used to clone a WebContents. DidCloneToNewWebContents(WebContents * old_web_contents,WebContents * new_web_contents)447 virtual void DidCloneToNewWebContents(WebContents* old_web_contents, 448 WebContents* new_web_contents) {} 449 450 // Invoked when the WebContents is being destroyed. Gives subclasses a chance 451 // to cleanup. After the whole loop over all WebContentsObservers has been 452 // finished, web_contents() returns nullptr. WebContentsDestroyed()453 virtual void WebContentsDestroyed() {} 454 455 // Called when the user agent override for a WebContents has been changed. UserAgentOverrideSet(const blink::UserAgentOverride & ua_override)456 virtual void UserAgentOverrideSet( 457 const blink::UserAgentOverride& ua_override) {} 458 459 // Invoked when new blink::mojom::FaviconURLPtr candidates are received from 460 // the renderer process. If the instance is created after the page is loaded, 461 // it is recommended to call WebContents::GetFaviconURLs() to get the current 462 // list as this callback will not be executed unless there is an update. 463 // |render_frame_host| is the main render frame host. DidUpdateFaviconURL(RenderFrameHost * render_frame_host,const std::vector<blink::mojom::FaviconURLPtr> & candidates)464 virtual void DidUpdateFaviconURL( 465 RenderFrameHost* render_frame_host, 466 const std::vector<blink::mojom::FaviconURLPtr>& candidates) {} 467 468 // Called when an audio change occurs to this WebContents. If |audible| is 469 // true then one or more frames or child contents are emitting audio; if 470 // false, then no frames or child contents are emitting audio. See 471 // OnFrameAudioStateChanged for per-frame information. OnAudioStateChanged(bool audible)472 virtual void OnAudioStateChanged(bool audible) {} 473 474 // Called when the audio state of an individual frame changes. OnFrameAudioStateChanged(RenderFrameHost * rfh,bool audible)475 virtual void OnFrameAudioStateChanged(RenderFrameHost* rfh, bool audible) {} 476 477 // Called when the connected to Bluetooth device state changes. OnIsConnectedToBluetoothDeviceChanged(bool is_connected_to_bluetooth_device)478 virtual void OnIsConnectedToBluetoothDeviceChanged( 479 bool is_connected_to_bluetooth_device) {} 480 481 // Invoked when the WebContents is muted/unmuted. DidUpdateAudioMutingState(bool muted)482 virtual void DidUpdateAudioMutingState(bool muted) {} 483 484 // Invoked when the renderer process has toggled the tab into/out of 485 // fullscreen mode. DidToggleFullscreenModeForTab(bool entered_fullscreen,bool will_cause_resize)486 virtual void DidToggleFullscreenModeForTab(bool entered_fullscreen, 487 bool will_cause_resize) {} 488 489 // Signals that |rfh| has the current fullscreen element. This is invoked 490 // when: 491 // 1) an element in this frame enters fullscreen or in nested fullscreen, or 492 // 2) after an element in a descendant frame exits fullscreen and makes 493 // this frame own the current fullscreen element again. DidAcquireFullscreen(RenderFrameHost * rfh)494 virtual void DidAcquireFullscreen(RenderFrameHost* rfh) {} 495 496 // Invoked when the vertical scroll direction of the root layer is changed. 497 // Note that if a scroll in a given direction occurs, the scroll is completed, 498 // and then another scroll in the *same* direction occurs, we will not 499 // consider the second scroll event to have caused a change in direction. Also 500 // note that this API will *never* be called with |kNull| which only exists to 501 // indicate the absence of a vertical scroll direction. DidChangeVerticalScrollDirection(viz::VerticalScrollDirection scroll_direction)502 virtual void DidChangeVerticalScrollDirection( 503 viz::VerticalScrollDirection scroll_direction) {} 504 505 // Invoked before a form repost warning is shown. BeforeFormRepostWarningShow()506 virtual void BeforeFormRepostWarningShow() {} 507 508 // Invoked when the beforeunload handler fires. |proceed| is set to true if 509 // the beforeunload can safely proceed, otherwise it should be interrupted. 510 // The time is from the renderer process. BeforeUnloadFired(bool proceed,const base::TimeTicks & proceed_time)511 virtual void BeforeUnloadFired(bool proceed, 512 const base::TimeTicks& proceed_time) {} 513 514 // Invoked when a user cancels a before unload dialog. BeforeUnloadDialogCancelled()515 virtual void BeforeUnloadDialogCancelled() {} 516 517 // Called whenever the AXTreeID for the main frame has changed. AXTreeIDForMainFrameHasChanged()518 virtual void AXTreeIDForMainFrameHasChanged() {} 519 520 // Called when accessibility events or location changes are received 521 // from a render frame, but only when the accessibility mode has the 522 // ui::AXMode::kWebContents flag set. AccessibilityEventReceived(const AXEventNotificationDetails & details)523 virtual void AccessibilityEventReceived( 524 const AXEventNotificationDetails& details) {} AccessibilityLocationChangesReceived(const std::vector<AXLocationChangeNotificationDetails> & details)525 virtual void AccessibilityLocationChangesReceived( 526 const std::vector<AXLocationChangeNotificationDetails>& details) {} 527 528 // Invoked when theme color is changed. DidChangeThemeColor()529 virtual void DidChangeThemeColor() {} 530 531 // Invoked when background color is changed. OnBackgroundColorChanged()532 virtual void OnBackgroundColorChanged() {} 533 534 // Called when a message is added to the console of the WebContents. This is 535 // invoked before forwarding the message to the WebContents' delegate. OnDidAddMessageToConsole(RenderFrameHost * source_frame,blink::mojom::ConsoleMessageLevel log_level,const base::string16 & message,int32_t line_no,const base::string16 & source_id)536 virtual void OnDidAddMessageToConsole( 537 RenderFrameHost* source_frame, 538 blink::mojom::ConsoleMessageLevel log_level, 539 const base::string16& message, 540 int32_t line_no, 541 const base::string16& source_id) {} 542 543 // Invoked when media is playing or paused. |id| is unique per player and per 544 // RenderFrameHost. There may be multiple players within a RenderFrameHost 545 // and subsequently within a WebContents. MediaStartedPlaying() will always 546 // be followed by MediaStoppedPlaying() after player teardown. Observers must 547 // release all stored copies of |id| when MediaStoppedPlaying() is received. 548 // |has_video| and |has_audio| can both be false in cases where the media 549 // is playing muted and should be considered as inaudible for all intent and 550 // purposes. 551 struct MediaPlayerInfo { MediaPlayerInfoMediaPlayerInfo552 MediaPlayerInfo(bool has_video, bool has_audio) 553 : has_video(has_video), has_audio(has_audio) {} 554 bool has_video; 555 bool has_audio; 556 }; 557 MediaStartedPlaying(const MediaPlayerInfo & video_type,const MediaPlayerId & id)558 virtual void MediaStartedPlaying(const MediaPlayerInfo& video_type, 559 const MediaPlayerId& id) {} 560 enum class MediaStoppedReason { 561 // The media was stopped for an unspecified reason. 562 kUnspecified, 563 564 // The media was stopped because it reached the end of the stream. 565 kReachedEndOfStream, 566 }; MediaStoppedPlaying(const MediaPlayerInfo & video_type,const MediaPlayerId & id,WebContentsObserver::MediaStoppedReason reason)567 virtual void MediaStoppedPlaying( 568 const MediaPlayerInfo& video_type, 569 const MediaPlayerId& id, 570 WebContentsObserver::MediaStoppedReason reason) {} MediaResized(const gfx::Size & size,const MediaPlayerId & id)571 virtual void MediaResized(const gfx::Size& size, const MediaPlayerId& id) {} 572 // Invoked when media enters or exits fullscreen. We must use a heuristic 573 // to determine this as it is not trivial for media with custom controls. 574 // There is a slight delay between media entering or exiting fullscreen 575 // and it being detected. MediaEffectivelyFullscreenChanged(bool is_fullscreen)576 virtual void MediaEffectivelyFullscreenChanged(bool is_fullscreen) {} MediaPictureInPictureChanged(bool is_picture_in_picture)577 virtual void MediaPictureInPictureChanged(bool is_picture_in_picture) {} MediaMutedStatusChanged(const MediaPlayerId & id,bool muted)578 virtual void MediaMutedStatusChanged(const MediaPlayerId& id, bool muted) {} MediaBufferUnderflow(const MediaPlayerId & id)579 virtual void MediaBufferUnderflow(const MediaPlayerId& id) {} MediaPlayerSeek(const MediaPlayerId & id)580 virtual void MediaPlayerSeek(const MediaPlayerId& id) {} 581 582 // Invoked when the renderer process changes the page scale factor. OnPageScaleFactorChanged(float page_scale_factor)583 virtual void OnPageScaleFactorChanged(float page_scale_factor) {} 584 585 // Invoked when a paste event occurs. OnPaste()586 virtual void OnPaste() {} 587 588 // Invoked if an IPC message is coming from a specific RenderFrameHost. 589 virtual bool OnMessageReceived(const IPC::Message& message, 590 RenderFrameHost* render_frame_host); 591 592 // Notification that the |render_widget_host| for this WebContents has gained 593 // focus. OnWebContentsFocused(RenderWidgetHost * render_widget_host)594 virtual void OnWebContentsFocused(RenderWidgetHost* render_widget_host) {} 595 596 // Notification that the |render_widget_host| for this WebContents has lost 597 // focus. OnWebContentsLostFocus(RenderWidgetHost * render_widget_host)598 virtual void OnWebContentsLostFocus(RenderWidgetHost* render_widget_host) {} 599 600 // Notification that a RenderFrameHost inside this WebContents has updated 601 // its focused element. |details| contains information on the element 602 // that has received focus. This allows for observing focus changes 603 // within WebContents, as opposed to OnWebContentsFocused/LostFocus 604 // which allows observation that the RenderWidgetHost for the 605 // WebContents has gained/lost focus. OnFocusChangedInPage(FocusedNodeDetails * details)606 virtual void OnFocusChangedInPage(FocusedNodeDetails* details) {} 607 608 // Notifies that the manifest URL for the main frame changed to 609 // |manifest_url|. This will be invoked when a document with a manifest loads 610 // or when the manifest URL changes (possibly to nothing). It is not invoked 611 // when a document with no manifest loads. During document load, if the 612 // document has both a manifest and a favicon, DidUpdateWebManifestURL() will 613 // be invoked before DidUpdateFaviconURL(). DidUpdateWebManifestURL(RenderFrameHost * target_frame,const base::Optional<GURL> & manifest_url)614 virtual void DidUpdateWebManifestURL( 615 RenderFrameHost* target_frame, 616 const base::Optional<GURL>& manifest_url) {} 617 618 // DEPRECATED. Please register interface binders with BrowserInterfaceBroker 619 // instead (see 'Interface-Brokers' section in //docs/mojo_and_services.md). 620 // Called to give the embedder an opportunity to bind an interface request 621 // from a frame. If the request can be bound, |interface_pipe| will be taken. OnInterfaceRequestFromFrame(RenderFrameHost * render_frame_host,const std::string & interface_name,mojo::ScopedMessagePipeHandle * interface_pipe)622 virtual void OnInterfaceRequestFromFrame( 623 RenderFrameHost* render_frame_host, 624 const std::string& interface_name, 625 mojo::ScopedMessagePipeHandle* interface_pipe) {} 626 627 // Called when "audible" playback starts or stops on a WebAudio AudioContext. 628 using AudioContextId = std::pair<RenderFrameHost*, int>; AudioContextPlaybackStarted(const AudioContextId & audio_context_id)629 virtual void AudioContextPlaybackStarted( 630 const AudioContextId& audio_context_id) {} AudioContextPlaybackStopped(const AudioContextId & audio_context_id)631 virtual void AudioContextPlaybackStopped( 632 const AudioContextId& audio_context_id) {} 633 634 // Called when the RenderFrameHost tries to use a ServiceWorker 635 // (e.g. via navigation.serviceWorker API). OnServiceWorkerAccessed(RenderFrameHost * render_frame_host,const GURL & scope,AllowServiceWorkerResult allowed)636 virtual void OnServiceWorkerAccessed(RenderFrameHost* render_frame_host, 637 const GURL& scope, 638 AllowServiceWorkerResult allowed) {} 639 // Called when the NavigationHandle accesses ServiceWorker to see if the 640 // network request should be handled by the ServiceWorker instead 641 // (e.g. for navigations to URLs which are in scope of a ServiceWorker). OnServiceWorkerAccessed(NavigationHandle * navigation_handle,const GURL & scope,AllowServiceWorkerResult allowed)642 virtual void OnServiceWorkerAccessed(NavigationHandle* navigation_handle, 643 const GURL& scope, 644 AllowServiceWorkerResult allowed) {} 645 virtual bool ShowPopupMenu( 646 RenderFrameHost* render_frame_host, 647 mojo::PendingRemote<blink::mojom::PopupMenuClient>* popup_client, 648 const gfx::Rect& bounds, 649 int32_t item_height, 650 double font_size, 651 int32_t selected_item, 652 std::vector<blink::mojom::MenuItemPtr>* menu_items, 653 bool right_aligned, 654 bool allow_multiple_selection); 655 656 // IPC::Listener implementation. 657 // DEPRECATED: Use (i.e. override) the other overload instead: 658 // virtual bool OnMessageReceived(const IPC::Message& message, 659 // RenderFrameHost* render_frame_host); 660 // TODO(https://crbug.com/758026): Delete this overload when possible. 661 bool OnMessageReceived(const IPC::Message& message) override; 662 663 WebContents* web_contents() const; 664 665 protected: 666 // Use this constructor when the object is tied to a single WebContents for 667 // its entire lifetime. 668 explicit WebContentsObserver(WebContents* web_contents); 669 670 // Use this constructor when the object wants to observe a WebContents for 671 // part of its lifetime. It can then call Observe() to start and stop 672 // observing. 673 WebContentsObserver(); 674 675 ~WebContentsObserver() override; 676 677 // Start observing a different WebContents; used with the default constructor. 678 void Observe(WebContents* web_contents); 679 680 private: 681 friend class WebContentsImpl; 682 683 void ResetWebContents(); 684 685 WebContentsImpl* web_contents_; 686 687 DISALLOW_COPY_AND_ASSIGN(WebContentsObserver); 688 }; 689 690 } // namespace content 691 692 #endif // CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_ 693