blob: f6e75541e1764b88b7b6f642a115296e3e76eebe [file] [log] [blame]
// Copyright 2019 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 "chrome/browser/ui/views/tabs/tab_group_underline.h"
#include <memory>
#include <utility>
#include "chrome/browser/ui/layout_constants.h"
#include "chrome/browser/ui/tabs/tab_style.h"
#include "chrome/browser/ui/views/tabs/tab.h"
#include "chrome/browser/ui/views/tabs/tab_group_header.h"
#include "chrome/browser/ui/views/tabs/tab_group_views.h"
#include "components/tab_groups/tab_group_id.h"
#include "components/tab_groups/tab_group_visual_data.h"
#include "third_party/skia/include/core/SkColor.h"
#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/gfx/canvas.h"
#include "ui/views/background.h"
#include "ui/views/view.h"
constexpr int TabGroupUnderline::kStrokeThickness;
TabGroupUnderline::TabGroupUnderline(TabGroupViews* tab_group_views,
const tab_groups::TabGroupId& group)
: tab_group_views_(tab_group_views), group_(group) {}
void TabGroupUnderline::OnPaint(gfx::Canvas* canvas) {
SkPath path = GetPath();
cc::PaintFlags flags;
flags.setAntiAlias(true);
flags.setColor(tab_group_views_->GetGroupColor());
flags.setStyle(cc::PaintFlags::kFill_Style);
canvas->DrawPath(path, flags);
}
void TabGroupUnderline::UpdateBounds(const gfx::Rect& group_bounds) {
const int start_x = GetStart(group_bounds);
const int end_x = GetEnd(group_bounds);
// The width may be zero if the group underline and header are initialized at
// the same time, as with tab restore. In this case, don't update the bounds
// and defer to the next paint cycle.
if (end_x <= start_x)
return;
const int y =
group_bounds.height() - GetLayoutConstant(TABSTRIP_TOOLBAR_OVERLAP);
SetBounds(start_x, y - kStrokeThickness, end_x - start_x, kStrokeThickness);
}
// static
int TabGroupUnderline::GetStrokeInset() {
return TabStyle::GetTabOverlap() + kStrokeThickness;
}
int TabGroupUnderline::GetStart(const gfx::Rect& group_bounds) const {
return group_bounds.x() + GetStrokeInset();
}
int TabGroupUnderline::GetEnd(const gfx::Rect& group_bounds) const {
const Tab* last_grouped_tab = tab_group_views_->GetLastTabInGroup();
if (!last_grouped_tab)
return group_bounds.right() - GetStrokeInset();
return group_bounds.right() +
(last_grouped_tab->IsActive() ? kStrokeThickness : -GetStrokeInset());
}
SkPath TabGroupUnderline::GetPath() const {
SkPath path;
path.moveTo(0, kStrokeThickness);
path.arcTo(kStrokeThickness, kStrokeThickness, 0, SkPath::kSmall_ArcSize,
SkPathDirection::kCW, kStrokeThickness, 0);
path.lineTo(width() - kStrokeThickness, 0);
path.arcTo(kStrokeThickness, kStrokeThickness, 0, SkPath::kSmall_ArcSize,
SkPathDirection::kCW, width(), kStrokeThickness);
path.close();
return path;
}
BEGIN_METADATA(TabGroupUnderline, views::View)
END_METADATA