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

Side by Side Diff: chrome/browser/tab_contents/thumbnail_generator.cc

Issue 10704190: Support in-browser thumbnailing on Windows XP. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: rebase Created 8 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 | Annotate | Revision Log
« no previous file with comments | « chrome/browser/tab_contents/thumbnail_generator.h ('k') | chrome/common/thumbnail_support.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 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/browser/tab_contents/thumbnail_generator.h" 5 #include "chrome/browser/tab_contents/thumbnail_generator.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <map> 8 #include <map>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 14 matching lines...) Expand all
25 #include "content/public/browser/render_widget_host_view.h" 25 #include "content/public/browser/render_widget_host_view.h"
26 #include "content/public/browser/web_contents.h" 26 #include "content/public/browser/web_contents.h"
27 #include "googleurl/src/gurl.h" 27 #include "googleurl/src/gurl.h"
28 #include "skia/ext/image_operations.h" 28 #include "skia/ext/image_operations.h"
29 #include "skia/ext/platform_canvas.h" 29 #include "skia/ext/platform_canvas.h"
30 #include "third_party/skia/include/core/SkBitmap.h" 30 #include "third_party/skia/include/core/SkBitmap.h"
31 #include "ui/gfx/color_utils.h" 31 #include "ui/gfx/color_utils.h"
32 #include "ui/gfx/rect.h" 32 #include "ui/gfx/rect.h"
33 #include "ui/gfx/skbitmap_operations.h" 33 #include "ui/gfx/skbitmap_operations.h"
34 34
35 #if defined(OS_WIN)
36 #include "base/win/windows_version.h"
37 #endif
38
35 // Overview 39 // Overview
36 // -------- 40 // --------
37 // This class provides current thumbnails for tabs. The simplest operation is 41 // This class provides current thumbnails for tabs. The simplest operation is
38 // when a request for a thumbnail comes in, to grab the backing store and make 42 // when a request for a thumbnail comes in, to grab the backing store and make
39 // a smaller version of that. Clients of the class can send such a request by 43 // a smaller version of that. Clients of the class can send such a request by
40 // AskForSnapshot(). 44 // AskForSnapshot().
41 // 45 //
42 // The class also provides a service for updating thumbnails to be used in 46 // The class also provides a service for updating thumbnails to be used in
43 // "Most visited" section of the new tab page. The service can be started 47 // "Most visited" section of the new tab page. The service can be started
44 // by StartThumbnailing(). The current algorithm of the service is as 48 // by StartThumbnailing(). The current algorithm of the service is as
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after
178 182
179 if (registrar_.IsEmpty()) { 183 if (registrar_.IsEmpty()) {
180 // Even though we deal in RenderWidgetHosts, we only care about its 184 // Even though we deal in RenderWidgetHosts, we only care about its
181 // subclass, RenderViewHost when it is in a tab. We don't make thumbnails 185 // subclass, RenderViewHost when it is in a tab. We don't make thumbnails
182 // for RenderViewHosts that aren't in tabs, or RenderWidgetHosts that 186 // for RenderViewHosts that aren't in tabs, or RenderWidgetHosts that
183 // aren't views like select popups. 187 // aren't views like select popups.
184 registrar_.Add(this, content::NOTIFICATION_RENDER_VIEW_HOST_CREATED_FOR_TAB, 188 registrar_.Add(this, content::NOTIFICATION_RENDER_VIEW_HOST_CREATED_FOR_TAB,
185 content::Source<WebContents>(web_contents)); 189 content::Source<WebContents>(web_contents));
186 registrar_.Add(this, content::NOTIFICATION_WEB_CONTENTS_DISCONNECTED, 190 registrar_.Add(this, content::NOTIFICATION_WEB_CONTENTS_DISCONNECTED,
187 content::Source<WebContents>(web_contents)); 191 content::Source<WebContents>(web_contents));
192 web_contents_weak_factory_.reset(
193 new base::WeakPtrFactory<WebContents>(web_contents));
188 } 194 }
189 } 195 }
190 196
191 void ThumbnailGenerator::MonitorRenderer(RenderWidgetHost* renderer, 197 void ThumbnailGenerator::MonitorRenderer(RenderWidgetHost* renderer,
192 bool monitor) { 198 bool monitor) {
193 content::Source<RenderWidgetHost> renderer_source = 199 content::Source<RenderWidgetHost> renderer_source =
194 content::Source<RenderWidgetHost>(renderer); 200 content::Source<RenderWidgetHost>(renderer);
195 bool currently_monitored = 201 bool currently_monitored =
196 registrar_.IsRegistered( 202 registrar_.IsRegistered(
197 this, 203 this,
(...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after
432 } 438 }
433 } 439 }
434 440
435 SkBitmap clipped_bitmap; 441 SkBitmap clipped_bitmap;
436 bitmap.extractSubset(&clipped_bitmap, src_rect); 442 bitmap.extractSubset(&clipped_bitmap, src_rect);
437 return clipped_bitmap; 443 return clipped_bitmap;
438 } 444 }
439 445
440 void ThumbnailGenerator::UpdateThumbnailIfNecessary( 446 void ThumbnailGenerator::UpdateThumbnailIfNecessary(
441 WebContents* web_contents) { 447 WebContents* web_contents) {
442 content::RenderWidgetHostView* view = web_contents->GetRenderWidgetHostView();
443 if (!view)
444 return;
445 bool surface_available = view->IsSurfaceAvailableForCopy();
446 // Skip if we can't update the thumbnail.
447 if (!surface_available)
448 return;
449 // Skip if a pending entry exists. WidgetHidden can be called while navigaing 448 // Skip if a pending entry exists. WidgetHidden can be called while navigaing
450 // pages and this is not a timing when thumbnails should be generated. 449 // pages and this is not a timing when thumbnails should be generated.
451 if (web_contents->GetController().GetPendingEntry()) 450 if (web_contents->GetController().GetPendingEntry())
452 return; 451 return;
453 const GURL& url = web_contents->GetURL(); 452 const GURL& url = web_contents->GetURL();
454 Profile* profile = 453 Profile* profile =
455 Profile::FromBrowserContext(web_contents->GetBrowserContext()); 454 Profile::FromBrowserContext(web_contents->GetBrowserContext());
456 history::TopSites* top_sites = profile->GetTopSites(); 455 history::TopSites* top_sites = profile->GetTopSites();
457 // Skip if we don't need to update the thumbnail. 456 // Skip if we don't need to update the thumbnail.
458 if (!ShouldUpdateThumbnail(profile, top_sites, url)) 457 if (!ShouldUpdateThumbnail(profile, top_sites, url))
(...skipping 29 matching lines...) Expand all
488 VLOG(1) << "Thumbnail taken for " << url << ": " << score.ToString(); 487 VLOG(1) << "Thumbnail taken for " << url << ": " << score.ToString();
489 } 488 }
490 489
491 void ThumbnailGenerator::AsyncUpdateThumbnail( 490 void ThumbnailGenerator::AsyncUpdateThumbnail(
492 WebContents* web_contents) { 491 WebContents* web_contents) {
493 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 492 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
494 RenderWidgetHost* render_widget_host = web_contents->GetRenderViewHost(); 493 RenderWidgetHost* render_widget_host = web_contents->GetRenderViewHost();
495 content::RenderWidgetHostView* view = render_widget_host->GetView(); 494 content::RenderWidgetHostView* view = render_widget_host->GetView();
496 if (!view) 495 if (!view)
497 return; 496 return;
497 if (!view->IsSurfaceAvailableForCopy()) {
498 #if defined(OS_WIN)
499 // On Windows XP, neither the backing store nor the compositing surface is
500 // available in the browser when accelerated compositing is active, so ask
501 // the renderer to send a snapshot for creating the thumbnail.
502 if (base::win::GetVersion() < base::win::VERSION_VISTA) {
503 gfx::Size view_size =
504 render_widget_host->GetView()->GetViewBounds().size();
505 AskForSnapshot(render_widget_host,
506 base::Bind(&ThumbnailGenerator::UpdateThumbnailWithBitmap,
507 weak_factory_.GetWeakPtr(),
508 web_contents_weak_factory_->GetWeakPtr()),
509 view_size,
510 view_size);
511 }
512 #endif
513 return;
514 }
498 515
499 const gfx::Size copy_size = 516 gfx::Size copy_size =
500 GetCopySizeForThumbnail(view->GetViewBounds().size(), 517 GetCopySizeForThumbnail(view->GetViewBounds().size(),
501 gfx::Size(kThumbnailWidth, kThumbnailHeight)); 518 gfx::Size(kThumbnailWidth, kThumbnailHeight));
502 skia::PlatformCanvas* temp_canvas = new skia::PlatformCanvas; 519 skia::PlatformCanvas* temp_canvas = new skia::PlatformCanvas;
503 web_contents_weak_factory_.reset(
504 new base::WeakPtrFactory<WebContents>(web_contents));
505 render_widget_host->CopyFromBackingStore( 520 render_widget_host->CopyFromBackingStore(
506 gfx::Rect(), copy_size, temp_canvas, 521 gfx::Rect(), copy_size, temp_canvas,
507 base::Bind(&ThumbnailGenerator::AsyncUpdateThumbnailFinish, 522 base::Bind(&ThumbnailGenerator::UpdateThumbnailWithCanvas,
508 weak_factory_.GetWeakPtr(), 523 weak_factory_.GetWeakPtr(),
509 web_contents_weak_factory_->GetWeakPtr(), 524 web_contents_weak_factory_->GetWeakPtr(),
510 base::Owned(temp_canvas))); 525 base::Owned(temp_canvas)));
511 } 526 }
512 527
513 void ThumbnailGenerator::AsyncUpdateThumbnailFinish( 528 void ThumbnailGenerator::UpdateThumbnailWithBitmap(
514 base::WeakPtr<WebContents> web_contents, 529 const base::WeakPtr<WebContents>& web_contents,
515 skia::PlatformCanvas* temp_canvas, 530 const SkBitmap& bitmap) {
516 bool succeeded) {
517 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 531 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
518 // The weak pointer can be invalidated by the subsequent AsyncUpdateThumbnail. 532 // The weak pointer is invalidated when the web contens is disconnected.
519 if (!web_contents.get()) 533 if (!web_contents.get())
520 return; 534 return;
521 535
522 if (!succeeded) 536 if (bitmap.isNull() || bitmap.empty())
523 return; 537 return;
524 538
525 SkBitmap bmp_with_scrollbars =
526 skia::GetTopDevice(*temp_canvas)->accessBitmap(false);
527 ClipResult clip_result; 539 ClipResult clip_result;
528 SkBitmap thumbnail = CreateThumbnail(bmp_with_scrollbars, 540 SkBitmap thumbnail = CreateThumbnail(bitmap,
529 kThumbnailWidth, 541 kThumbnailWidth,
530 kThumbnailHeight, 542 kThumbnailHeight,
531 ThumbnailGenerator::kClippedThumbnail, 543 ThumbnailGenerator::kClippedThumbnail,
532 &clip_result); 544 &clip_result);
533 UpdateThumbnail(web_contents.get(), thumbnail, clip_result); 545 UpdateThumbnail(web_contents.get(), thumbnail, clip_result);
534 } 546 }
535 547
548 void ThumbnailGenerator::UpdateThumbnailWithCanvas(
549 const base::WeakPtr<WebContents>& web_contents,
550 skia::PlatformCanvas* temp_canvas,
551 bool succeeded) {
552 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
553 // The weak pointer is invalidated when the web contens is disconnected.
554 if (!web_contents.get())
555 return;
556
557 if (!succeeded)
558 return;
559
560 SkBitmap bmp_with_scrollbars =
561 skia::GetTopDevice(*temp_canvas)->accessBitmap(false);
562 UpdateThumbnailWithBitmap(web_contents, bmp_with_scrollbars);
563 }
564
536 bool ThumbnailGenerator::ShouldUpdateThumbnail(Profile* profile, 565 bool ThumbnailGenerator::ShouldUpdateThumbnail(Profile* profile,
537 history::TopSites* top_sites, 566 history::TopSites* top_sites,
538 const GURL& url) { 567 const GURL& url) {
539 if (!profile || !top_sites) 568 if (!profile || !top_sites)
540 return false; 569 return false;
541 // Skip if it's in the incognito mode. 570 // Skip if it's in the incognito mode.
542 if (profile->IsOffTheRecord()) 571 if (profile->IsOffTheRecord())
543 return false; 572 return false;
544 // Skip if the given URL is not appropriate for history. 573 // Skip if the given URL is not appropriate for history.
545 if (!HistoryService::CanAddURL(url)) 574 if (!HistoryService::CanAddURL(url))
(...skipping 18 matching lines...) Expand all
564 593
565 void ThumbnailGenerator::DidStartLoading() { 594 void ThumbnailGenerator::DidStartLoading() {
566 load_interrupted_ = false; 595 load_interrupted_ = false;
567 } 596 }
568 597
569 void ThumbnailGenerator::StopNavigation() { 598 void ThumbnailGenerator::StopNavigation() {
570 // This function gets called when the page loading is interrupted by the 599 // This function gets called when the page loading is interrupted by the
571 // stop button. 600 // stop button.
572 load_interrupted_ = true; 601 load_interrupted_ = true;
573 } 602 }
OLDNEW
« no previous file with comments | « chrome/browser/tab_contents/thumbnail_generator.h ('k') | chrome/common/thumbnail_support.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698