// Copyright (c) 2012 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. #include "ui/gfx/shadow_value.h" #include #include #include "base/strings/stringprintf.h" #include "ui/gfx/geometry/insets.h" #include "ui/gfx/geometry/vector2d_conversions.h" namespace gfx { namespace { Insets GetInsets(const ShadowValues& shadows, bool include_inner_blur) { int left = 0; int top = 0; int right = 0; int bottom = 0; for (size_t i = 0; i < shadows.size(); ++i) { const ShadowValue& shadow = shadows[i]; double blur = shadow.blur(); if (!include_inner_blur) blur /= 2; // Add 0.5 to round up to the next integer. int blur_length = static_cast(blur + 0.5); left = std::max(left, blur_length - shadow.x()); top = std::max(top, blur_length - shadow.y()); right = std::max(right, blur_length + shadow.x()); bottom = std::max(bottom, blur_length + shadow.y()); } return Insets(top, left, bottom, right); } } // namespace ShadowValue::ShadowValue() : blur_(0), color_(0) {} ShadowValue::ShadowValue(const gfx::Vector2d& offset, double blur, SkColor color) : offset_(offset), blur_(blur), color_(color) { } ShadowValue::~ShadowValue() {} ShadowValue ShadowValue::Scale(float scale) const { gfx::Vector2d scaled_offset = gfx::ToFlooredVector2d(gfx::ScaleVector2d(offset_, scale)); return ShadowValue(scaled_offset, blur_ * scale, color_); } std::string ShadowValue::ToString() const { return base::StringPrintf( "(%d,%d),%.2f,rgba(%d,%d,%d,%d)", offset_.x(), offset_.y(), blur_, SkColorGetR(color_), SkColorGetG(color_), SkColorGetB(color_), SkColorGetA(color_)); } // static Insets ShadowValue::GetMargin(const ShadowValues& shadows) { gfx::Insets margins = GetInsets(shadows, false); return -margins; } // static Insets ShadowValue::GetBlurRegion(const ShadowValues& shadows) { return GetInsets(shadows, true); } // static ShadowValues ShadowValue::MakeMdShadowValues(int elevation) { ShadowValues shadow_values; // To match the CSS notion of blur (spread outside the bounding box) to the // Skia notion of blur (spread outside and inside the bounding box), we have // to double the designer-provided blur values. const int kBlurCorrection = 2; // "Key shadow": y offset is elevation and blur is twice the elevation. shadow_values.emplace_back(gfx::Vector2d(0, elevation), kBlurCorrection * elevation * 2, SkColorSetA(SK_ColorBLACK, 0x3d)); // "Ambient shadow": no offset and blur matches the elevation. shadow_values.emplace_back(gfx::Vector2d(), kBlurCorrection * elevation, SkColorSetA(SK_ColorBLACK, 0x1f)); // To see what this looks like for elevation 24, try this CSS: // box-shadow: 0 24px 48px rgba(0, 0, 0, .24), // 0 0 24px rgba(0, 0, 0, .12); return shadow_values; } } // namespace gfx