blob: 6a2c5d5947545557f87863c0d96ef93f945b7cb6 [file] [log] [blame]
/*
* Copyright (C) 2010 Google Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "third_party/blink/renderer/core/page/drag_image.h"
#include <memory>
#include "base/memory/scoped_refptr.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/blink/renderer/platform/fonts/font_description.h"
#include "third_party/blink/renderer/platform/geometry/int_size.h"
#include "third_party/blink/renderer/platform/graphics/bitmap_image.h"
#include "third_party/blink/renderer/platform/graphics/image.h"
#include "third_party/blink/renderer/platform/graphics/skia/skia_utils.h"
#include "third_party/blink/renderer/platform/weborigin/kurl.h"
#include "third_party/skia/include/core/SkImage.h"
#include "third_party/skia/include/core/SkSurface.h"
namespace blink {
class TestImage : public Image {
public:
static scoped_refptr<TestImage> Create(sk_sp<SkImage> image) {
return base::AdoptRef(new TestImage(image));
}
static scoped_refptr<TestImage> Create(const IntSize& size) {
return base::AdoptRef(new TestImage(size));
}
IntSize Size() const override {
DCHECK(image_);
return IntSize(image_->width(), image_->height());
}
bool CurrentFrameKnownToBeOpaque() override { return false; }
void DestroyDecodedData() override {
// Image pure virtual stub.
}
void Draw(cc::PaintCanvas*,
const cc::PaintFlags&,
const FloatRect&,
const FloatRect&,
RespectImageOrientationEnum,
ImageClampingMode,
ImageDecodingMode) override {
// Image pure virtual stub.
}
PaintImage PaintImageForCurrentFrame() override {
if (!image_)
return PaintImage();
return CreatePaintImageBuilder()
.set_image(image_, cc::PaintImage::GetNextContentId())
.TakePaintImage();
}
private:
explicit TestImage(sk_sp<SkImage> image) : image_(image) {}
explicit TestImage(IntSize size) : image_(nullptr) {
sk_sp<SkSurface> surface = CreateSkSurface(size);
if (!surface)
return;
surface->getCanvas()->clear(SK_ColorTRANSPARENT);
image_ = surface->makeImageSnapshot();
}
static sk_sp<SkSurface> CreateSkSurface(IntSize size) {
return SkSurface::MakeRaster(
SkImageInfo::MakeN32(size.Width(), size.Height(), kPremul_SkAlphaType));
}
sk_sp<SkImage> image_;
};
TEST(DragImageTest, NullHandling) {
EXPECT_FALSE(DragImage::Create(nullptr));
scoped_refptr<TestImage> null_test_image(TestImage::Create(IntSize()));
EXPECT_FALSE(DragImage::Create(null_test_image.get()));
}
TEST(DragImageTest, NonNullHandling) {
scoped_refptr<TestImage> test_image(TestImage::Create(IntSize(2, 2)));
std::unique_ptr<DragImage> drag_image = DragImage::Create(test_image.get());
ASSERT_TRUE(drag_image);
drag_image->Scale(0.5, 0.5);
IntSize size = drag_image->Size();
EXPECT_EQ(1, size.Width());
EXPECT_EQ(1, size.Height());
}
TEST(DragImageTest, CreateDragImage) {
// Tests that the DrageImage implementation doesn't choke on null values
// of imageForCurrentFrame().
// FIXME: how is this test any different from test NullHandling?
scoped_refptr<TestImage> test_image(TestImage::Create(IntSize()));
EXPECT_FALSE(DragImage::Create(test_image.get()));
}
TEST(DragImageTest, TrimWhitespace) {
KURL url("http://www.example.com/");
String test_label = " Example Example Example \n ";
String expected_label = "Example Example Example";
float device_scale_factor = 1.0f;
FontDescription font_description;
font_description.FirstFamily().SetFamily("Arial");
font_description.SetSpecifiedSize(16);
font_description.SetIsAbsoluteSize(true);
font_description.SetGenericFamily(FontDescription::kNoFamily);
font_description.SetWeight(NormalWeightValue());
font_description.SetStyle(NormalSlopeValue());
std::unique_ptr<DragImage> test_image =
DragImage::Create(url, test_label, font_description, device_scale_factor);
std::unique_ptr<DragImage> expected_image = DragImage::Create(
url, expected_label, font_description, device_scale_factor);
EXPECT_EQ(test_image->Size().Width(), expected_image->Size().Width());
}
TEST(DragImageTest, InterpolationNone) {
SkBitmap expected_bitmap;
expected_bitmap.allocN32Pixels(4, 4);
expected_bitmap.eraseArea(SkIRect::MakeXYWH(0, 0, 2, 2), 0xFFFFFFFF);
expected_bitmap.eraseArea(SkIRect::MakeXYWH(0, 2, 2, 2), 0xFF000000);
expected_bitmap.eraseArea(SkIRect::MakeXYWH(2, 0, 2, 2), 0xFF000000);
expected_bitmap.eraseArea(SkIRect::MakeXYWH(2, 2, 2, 2), 0xFFFFFFFF);
SkBitmap test_bitmap;
test_bitmap.allocN32Pixels(2, 2);
test_bitmap.eraseArea(SkIRect::MakeXYWH(0, 0, 1, 1), 0xFFFFFFFF);
test_bitmap.eraseArea(SkIRect::MakeXYWH(0, 1, 1, 1), 0xFF000000);
test_bitmap.eraseArea(SkIRect::MakeXYWH(1, 0, 1, 1), 0xFF000000);
test_bitmap.eraseArea(SkIRect::MakeXYWH(1, 1, 1, 1), 0xFFFFFFFF);
scoped_refptr<TestImage> test_image =
TestImage::Create(SkImage::MakeFromBitmap(test_bitmap));
std::unique_ptr<DragImage> drag_image = DragImage::Create(
test_image.get(), kRespectImageOrientation, 1, kInterpolationNone);
ASSERT_TRUE(drag_image);
drag_image->Scale(2, 2);
const SkBitmap& drag_bitmap = drag_image->Bitmap();
for (int x = 0; x < drag_bitmap.width(); ++x)
for (int y = 0; y < drag_bitmap.height(); ++y)
EXPECT_EQ(expected_bitmap.getColor(x, y), drag_bitmap.getColor(x, y));
}
} // namespace blink