fix: leaked gfx::Canvas in AutofillPopupView::OnPaint() (#46413)

* perf: avoid redundant call to popup_bounds_in_view()

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* refactor: use a std::optional<> for paint_canvas local

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* fix: fix leaked gfx::Canvas in AutofillPopupView::OnPaint()

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* refactor: remove redundant get() call when testing smart pointer for nonempty

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* refactor: remove unnecessary draw_canvas variable

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* refactor: rename bitmap to offscreen_bitmap for symmetry

Co-authored-by: Charles Kerr <charles@charleskerr.com>

* refactor: avoid another redundant call to popup_bounds_in_view()

Co-authored-by: Charles Kerr <charles@charleskerr.com>

---------

Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com>
Co-authored-by: Charles Kerr <charles@charleskerr.com>
This commit is contained in:
trop[bot] 2025-04-01 16:45:48 -05:00 committed by GitHub
parent d025ab4995
commit cf559d7c72
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -5,6 +5,7 @@
#include "shell/browser/ui/views/autofill_popup_view.h" #include "shell/browser/ui/views/autofill_popup_view.h"
#include <memory> #include <memory>
#include <optional>
#include <utility> #include <utility>
#include "base/functional/bind.h" #include "base/functional/bind.h"
@ -238,30 +239,33 @@ void AutofillPopupView::DoUpdateBoundsAndRedrawPopup() {
void AutofillPopupView::OnPaint(gfx::Canvas* canvas) { void AutofillPopupView::OnPaint(gfx::Canvas* canvas) {
if (!popup_ || static_cast<size_t>(popup_->line_count()) != children().size()) if (!popup_ || static_cast<size_t>(popup_->line_count()) != children().size())
return; return;
gfx::Canvas* draw_canvas = canvas;
SkBitmap bitmap;
std::unique_ptr<cc::SkiaPaintCanvas> paint_canvas; gfx::Rect offscreen_bounds;
if (view_proxy_.get()) { SkBitmap offscreen_bitmap;
bitmap.allocN32Pixels(popup_->popup_bounds_in_view().width(), std::optional<cc::SkiaPaintCanvas> offscreen_paint_canvas;
popup_->popup_bounds_in_view().height(), true); std::optional<gfx::Canvas> offscreen_draw_canvas;
paint_canvas = std::make_unique<cc::SkiaPaintCanvas>(bitmap); if (view_proxy_) {
draw_canvas = new gfx::Canvas(paint_canvas.get(), 1.0); offscreen_bounds = popup_->popup_bounds_in_view();
offscreen_bitmap.allocN32Pixels(offscreen_bounds.width(),
offscreen_bounds.height(), true);
offscreen_paint_canvas.emplace(offscreen_bitmap);
offscreen_draw_canvas.emplace(&offscreen_paint_canvas.value(), 1.0);
canvas = &offscreen_draw_canvas.value();
} }
draw_canvas->DrawColor( canvas->DrawColor(
GetColorProvider()->GetColor(ui::kColorResultsTableNormalBackground)); GetColorProvider()->GetColor(ui::kColorResultsTableNormalBackground));
OnPaintBorder(draw_canvas); OnPaintBorder(canvas);
for (int i = 0; i < popup_->line_count(); ++i) { for (int i = 0; i < popup_->line_count(); ++i) {
gfx::Rect line_rect = popup_->GetRowBounds(i); gfx::Rect line_rect = popup_->GetRowBounds(i);
DrawAutofillEntry(draw_canvas, i, line_rect); DrawAutofillEntry(canvas, i, line_rect);
} }
if (view_proxy_.get()) { if (view_proxy_) {
view_proxy_->SetBounds(popup_->popup_bounds_in_view()); view_proxy_->SetBounds(offscreen_bounds);
view_proxy_->SetBitmap(bitmap); view_proxy_->SetBitmap(offscreen_bitmap);
} }
} }