diff options
author | hirono <hirono@chromium.org> | 2014-12-09 21:13:29 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2014-12-10 05:15:00 +0000 |
commit | 32a12fc0eb3da854e3ed14f0ea846e5aca72695c (patch) | |
tree | 33246e40bedaaaba67d79a90f1fe5f638f8acbc8 | |
parent | d413f7f9a5d12ce9e4c8365ba8a29f8fd38db0ee (diff) | |
download | chromium_src-32a12fc0eb3da854e3ed14f0ea846e5aca72695c.zip chromium_src-32a12fc0eb3da854e3ed14f0ea846e5aca72695c.tar.gz chromium_src-32a12fc0eb3da854e3ed14f0ea846e5aca72695c.tar.bz2 |
Gallery: Fix condition to use thumbnail images in slide mode.
The CL fixes two conditions to use thumbnail images in slide mode.
* If the effect is not specified, the thumbnail images should be used.
* If metadata.external.thumbnail (as well as metadata.thumbnail) is not empty,
the thumbnail images should be used.
BUG=435443
TEST=GalleryJsTest.ImageViewTest
Review URL: https://codereview.chromium.org/777153002
Cr-Commit-Position: refs/heads/master@{#307646}
7 files changed, 180 insertions, 33 deletions
diff --git a/chrome/browser/chromeos/file_manager/gallery_jstest.cc b/chrome/browser/chromeos/file_manager/gallery_jstest.cc index 7f848e7..3409e74 100644 --- a/chrome/browser/chromeos/file_manager/gallery_jstest.cc +++ b/chrome/browser/chromeos/file_manager/gallery_jstest.cc @@ -38,3 +38,8 @@ IN_PROC_BROWSER_TEST_F(GalleryJsTest, ExifEncoderTest) { RunTest(base::FilePath( FILE_PATH_LITERAL("js/image_editor/exif_encoder_unittest.html"))); } + +IN_PROC_BROWSER_TEST_F(GalleryJsTest, ImageViewTest) { + RunTest(base::FilePath( + FILE_PATH_LITERAL("js/image_editor/image_view_unittest.html"))); +} diff --git a/ui/file_manager/file_manager/foreground/js/thumbnail_loader.js b/ui/file_manager/file_manager/foreground/js/thumbnail_loader.js index ca86716..16ef965 100644 --- a/ui/file_manager/file_manager/foreground/js/thumbnail_loader.js +++ b/ui/file_manager/file_manager/foreground/js/thumbnail_loader.js @@ -37,8 +37,7 @@ function ThumbnailLoader(entry, opt_loaderType, opt_metadata, opt_mediaType, if (opt_metadata.external && opt_metadata.external.customIconUrl) this.fallbackUrl_ = opt_metadata.external.customIconUrl; - if (((opt_metadata.thumbnail && opt_metadata.thumbnail.url) || - (opt_metadata.external && opt_metadata.external.thumbnailUrl)) && + if (ThumbnailLoader.hasThumbnailInMetadata(opt_metadata) && opt_useEmbedded === ThumbnailLoader.UseEmbedded.USE_EMBEDDED) { // If the thumbnail generated from the local cache (metadata.thumbnail.url) // is available, use it. If not, use the one passed from the external @@ -120,6 +119,16 @@ ThumbnailLoader.THUMBNAIL_MAX_WIDTH = 500; ThumbnailLoader.THUMBNAIL_MAX_HEIGHT = 500; /** + * Returns whether the metadata have the thumbnail information or not. + * @param {!Object} metadata Metadata. + * @return {boolean} + */ +ThumbnailLoader.hasThumbnailInMetadata = function(metadata) { + return (metadata.thumbnail && metadata.thumbnail.url) || + (metadata.external && metadata.external.thumbnailUrl); +}; + +/** * Loads and attaches an image. * * @param {Element} box Container element. diff --git a/ui/file_manager/gallery/js/image_editor/image_editor.js b/ui/file_manager/gallery/js/image_editor/image_editor.js index 677215b..e1e2e8e 100644 --- a/ui/file_manager/gallery/js/image_editor/image_editor.js +++ b/ui/file_manager/gallery/js/image_editor/image_editor.js @@ -101,10 +101,10 @@ ImageEditor.prototype.onContentUpdate_ = function() { /** * Open the editing session for a new image. * - * @param {Gallery.Item} item Gallery item. - * @param {Object} effect Transition effect object. + * @param {!Gallery.Item} item Gallery item. + * @param {!ImageView.Effect} effect Transition effect object. * @param {function(function())} saveFunction Image save function. - * @param {function(number)} displayCallback Display callback. + * @param {function()} displayCallback Display callback. * @param {function(number, number, *=)} loadCallback Load callback. */ ImageEditor.prototype.openSession = function( diff --git a/ui/file_manager/gallery/js/image_editor/image_view.js b/ui/file_manager/gallery/js/image_editor/image_view.js index 6e7b828..5385730 100644 --- a/ui/file_manager/gallery/js/image_editor/image_view.js +++ b/ui/file_manager/gallery/js/image_editor/image_view.js @@ -76,6 +76,41 @@ ImageView.LOAD_TYPE_OFFLINE = 4; */ ImageView.LOAD_TYPE_TOTAL = 5; +/** + * Target of image load. + * @enum {string} + */ +ImageView.LoadTarget = { + CACHED_MAIN_IMAGE: 'cachedMainImage', + CACHED_THUMBNAIL: 'cachedThumbnail', + THUMBNAIL: 'thumbnail', + MAIN_IMAGE: 'mainImage' +}; + +/** + * Obtains prefered load type from GalleryItem. + * + * @param {!Gallery.Item} item + * @param {!ImageView.Effect} effect + * @return {ImageView.LoadTarget} Load target. + */ +ImageView.getLoadTarget = function(item, effect) { + if (item.contentImage) + return ImageView.LoadTarget.CACHED_MAIN_IMAGE; + if (item.screenImage) + return ImageView.LoadTarget.CACHED_THUMBNAIL; + + // Only show thumbnails if there is no effect or the effect is Slide. + var metadata = item.getMetadata(); + if ((effect instanceof ImageView.Effect.None || + effect instanceof ImageView.Effect.Slide) && + ThumbnailLoader.hasThumbnailInMetadata(metadata)) { + return ImageView.LoadTarget.THUMBNAIL; + } + + return ImageView.LoadTarget.MAIN_IMAGE; +}; + ImageView.prototype = {__proto__: ImageBuffer.Overlay.prototype}; /** @@ -251,8 +286,8 @@ ImageView.prototype.cancelLoad = function() { * Takes into account the image orientation encoded in the metadata. * * @param {Gallery.Item} item Gallery item to be loaded. - * @param {Object} effect Transition effect object. - * @param {function(number)} displayCallback Called when the image is displayed + * @param {!ImageView.Effect} effect Transition effect object. + * @param {function()} displayCallback Called when the image is displayed * (possibly as a preview). * @param {function(number, number, *=)} loadCallback Called when the image is * fully loaded. The first parameter is the load type. @@ -267,7 +302,7 @@ ImageView.prototype.load = var time = Date.now(); if (this.lastLoadTime_ && (time - this.lastLoadTime_) < ImageView.FAST_SCROLL_INTERVAL) { - effect = null; + effect = new ImageView.Effect.None(); } this.lastLoadTime_ = time; } @@ -279,38 +314,44 @@ ImageView.prototype.load = this.contentItem_ = item; this.contentRevision_ = -1; - var cached = item.contentImage; - if (cached) { - displayMainImage(ImageView.LOAD_TYPE_CACHED_FULL, - false /* no preview */, cached); - } else { - var cachedScreen = item.screenImage; - var imageWidth = metadata.media && metadata.media.width || - metadata.external && metadata.external.imageWidth; - var imageHeight = metadata.media && metadata.media.height || - metadata.external && metadata.external.imageHeight; - if (cachedScreen) { + switch (ImageView.getLoadTarget(item, effect)) { + case ImageView.LoadTarget.CACHED_MAIN_IMAGE: + displayMainImage( + ImageView.LOAD_TYPE_CACHED_FULL, + false /* no preview */, + assert(item.contentImage)); + break; + + case ImageView.LoadTarget.CACHED_THUMBNAIL: // We have a cached screen-scale canvas, use it instead of a thumbnail. - displayThumbnail(ImageView.LOAD_TYPE_CACHED_SCREEN, cachedScreen); + displayThumbnail(ImageView.LOAD_TYPE_CACHED_SCREEN, item.screenImage); // As far as the user can tell the image is loaded. We still need to load // the full res image to make editing possible, but we can report now. ImageUtil.metrics.recordInterval(ImageUtil.getMetricName('DisplayTime')); - } else if ((effect && effect.constructor.name === 'Slide') && - (metadata.thumbnail && metadata.thumbnail.url)) { - // Only show thumbnails if there is no effect or the effect is Slide. - // Also no thumbnail if the image is too large to be loaded. + break; + + case ImageView.LoadTarget.THUMBNAIL: var thumbnailLoader = new ThumbnailLoader( entry, ThumbnailLoader.LoaderType.CANVAS, metadata); thumbnailLoader.loadDetachedImage(function(success) { - displayThumbnail(ImageView.LOAD_TYPE_IMAGE_FILE, - success ? thumbnailLoader.getImage() : null); + displayThumbnail( + ImageView.LOAD_TYPE_IMAGE_FILE, + success ? thumbnailLoader.getImage() : null); }); - } else { - loadMainImage(ImageView.LOAD_TYPE_IMAGE_FILE, entry, - false /* no preview*/, 0 /* delay */); - } + break; + + case ImageView.LoadTarget.MAIN_IMAGE: + loadMainImage( + ImageView.LOAD_TYPE_IMAGE_FILE, + entry, + false /* no preview*/, + 0 /* delay */); + break; + + default: + assertNotReached(); } function displayThumbnail(loadType, canvas) { @@ -361,6 +402,12 @@ ImageView.prototype.load = delay); } + /** + * @param {number} loadType + * @param {boolean} previewShown + * @param {!HTMLCanvasElement} content + * @param {*=} opt_error + */ function displayMainImage(loadType, previewShown, content, opt_error) { if (opt_error) loadType = ImageView.LOAD_TYPE_ERROR; @@ -576,7 +623,7 @@ ImageView.prototype.setTransform_ = function( /** * @param {ImageRect} screenRect Target rectangle in screen coordinates. - * @return {ImageView.Effect.Zoom} Zoom effect object. + * @return {!ImageView.Effect} Zoom effect object. */ ImageView.prototype.createZoomEffect = function(screenRect) { return new ImageView.Effect.ZoomToScreen( diff --git a/ui/file_manager/gallery/js/image_editor/image_view_unittest.html b/ui/file_manager/gallery/js/image_editor/image_view_unittest.html new file mode 100644 index 0000000..0bea8e6 --- /dev/null +++ b/ui/file_manager/gallery/js/image_editor/image_view_unittest.html @@ -0,0 +1,21 @@ +<!DOCTYPE html> +<!-- Copyright 2014 The Chromium Authors. All rights reserved. + -- Use of this source code is governed by a BSD-style license that can be + -- found in the LICENSE file. + --> +<html> +<body> + +<script> +<!-- Define Gallery for Gallery.Item. --> +var Gallery = {}; +</script> + +<script src="../../../file_manager/foreground/js/thumbnail_loader.js"></script> +<script src="../gallery_item.js"></script> +<script src="image_buffer.js"></script> +<script src="image_view.js"></script> +<script src="image_view_unittest.js"></script> + +</body> +</html> diff --git a/ui/file_manager/gallery/js/image_editor/image_view_unittest.js b/ui/file_manager/gallery/js/image_editor/image_view_unittest.js new file mode 100644 index 0000000..0b1a392 --- /dev/null +++ b/ui/file_manager/gallery/js/image_editor/image_view_unittest.js @@ -0,0 +1,63 @@ +// Copyright 2014 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +function testImageView() { + assertTrue(!!ImageView); + + // Item has full size cache. + var itemWithFullCache = new Gallery.Item(null, null, {}, null, false); + itemWithFullCache.contentImage = document.createElement('canvas'); + assertEquals( + ImageView.LoadTarget.CACHED_MAIN_IMAGE, + ImageView.getLoadTarget(itemWithFullCache, new ImageView.Effect.None())); + + // Item has screen size cache. + var itemWithScreenCache = new Gallery.Item(null, null, {}, null, false); + itemWithScreenCache.screenImage = document.createElement('canvas'); + assertEquals( + ImageView.LoadTarget.CACHED_THUMBNAIL, + ImageView.getLoadTarget( + itemWithScreenCache, new ImageView.Effect.None())); + + // Item with content thumbnail. + var itemWithContentThumbnail = new Gallery.Item( + null, null, {thumbnail: {url: 'url'}}, null, false); + assertEquals( + ImageView.LoadTarget.THUMBNAIL, + ImageView.getLoadTarget( + itemWithContentThumbnail, new ImageView.Effect.None())); + + // Item with external thumbnail. + var itemWithExternalThumbnail = new Gallery.Item( + null, null, {external: {thumbnailUrl: 'url'}}, null, false); + assertEquals( + ImageView.LoadTarget.THUMBNAIL, + ImageView.getLoadTarget( + itemWithExternalThumbnail, new ImageView.Effect.None())); + + // Item with external thumbnail shown by slide effect. + var itemWithExternalThumbnailSlide = new Gallery.Item( + null, null, {external: {thumbnailUrl: 'url'}}, null, false); + assertEquals( + ImageView.LoadTarget.THUMBNAIL, + ImageView.getLoadTarget( + itemWithExternalThumbnailSlide, new ImageView.Effect.Slide(1))); + + // Item with external thumbnail shown by zoom effect. + var itemWithExternalThumbnailZoom = new Gallery.Item( + null, null, {external: {thumbnailUrl: 'url'}}, null, false); + assertEquals( + ImageView.LoadTarget.MAIN_IMAGE, + ImageView.getLoadTarget( + itemWithExternalThumbnailZoom, + new ImageView.Effect.Zoom(0, 0, null))); + + // Item without cache/thumbnail. + var itemWithoutCacheOrThumbnail = new Gallery.Item( + null, null, {}, null, false); + assertEquals( + ImageView.LoadTarget.MAIN_IMAGE, + ImageView.getLoadTarget( + itemWithoutCacheOrThumbnail, new ImageView.Effect.None)); +} diff --git a/ui/file_manager/gallery/js/slide_mode.js b/ui/file_manager/gallery/js/slide_mode.js index c8bc8eb..ba3d786 100644 --- a/ui/file_manager/gallery/js/slide_mode.js +++ b/ui/file_manager/gallery/js/slide_mode.js @@ -561,7 +561,9 @@ SlideMode.prototype.enter = function( // Load the image of the item. this.loadItem_( selectedItem, - zoomFromRect && this.imageView_.createZoomEffect(zoomFromRect), + zoomFromRect ? + this.imageView_.createZoomEffect(zoomFromRect) : + new ImageView.Effect.None(), displayCallback, function(loadType, delay) { fulfill(delay); @@ -939,7 +941,7 @@ SlideMode.prototype.selectLast = function() { * Load and display an item. * * @param {!Gallery.Item} item Item. - * @param {!Object} effect Transition effect object. + * @param {!ImageView.Effect} effect Transition effect object. * @param {function()} displayCallback Called when the image is displayed * (which can happen before the image load due to caching). * @param {function(number, number)} loadCallback Called when the image is fully |