chromium/chrome/browser/ui/views/autofill/popup/README.md

# Popups

The popup classes in this directory are used to display the following types of
data on Desktop platforms:
* Autofill profile data (i.e. addresses)
* Autocomplete data
* Payment data

Additionally, `PopupBaseView` is also re-used for the popup in which
password generation prompts are rendered.

## Class hierarchy

The main classes for the popup have the following hierarchy:
```
┌───────────────────────┐
│ PopupBaseView         │
└──▲────────────────────┘
   │ extends
┌──┴────────────────────┐
│ PopupViewViews        │
└──┬────────────────────┘
   │creates (via CreatePopupRowView()) and owns N
┌──▼────────────────────┐
│ PopupRowView          │
└──┬────────────────────┘
   │owns
┌──▼────────────────────┐
│ PopupRowContentView   │
└───────────────────────┘

┌───────────────────────┐
│ PopupRowView          │
└──▲────────────────────┘
   │ extends
┌──┴─────────────────────┐
│ PopupRowWithButtonView │
└────────────────────────┘
```

These classes serve the following purposes:
* [`PopupBaseView`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_base_view.h): Serves as the common base class for both `PopupViewViews` and `PasswordGenerationPopupViewViews`.
  * It is responsible for creating a widget and setting itself as its content area.
  * It checks that there is enough space for showing the popup and creates a border with an arrow pointing to
    the HTML form field from which the popup was triggered.
* [`PopupViewViews`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_view_views.h): Implements the `AutofillPopupView` interface that the `AutofillPopupController`
   interacts with.
   * It serves as a container for multiple popup rows (e.g. encapsulating the non-footer
   rows in a `ScrollView`). Rows with selectable cells are represented by `PopupRowView`, but `PopupViewViews` can
   also contain rows that cannot be selected (e.g. a `PopupSeparatorView`).
   * It is responsible for processing keyboard events that change the cell selection across rows (e.g. cursor down)
     for announcing selection changes to the accessibility system.
* [`PopupRowView`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_row_view.h): Represents a single row in a `PopupViewViews`.
   * It accepts a `PopupRowContentView` in its constructor and takes ownership of it. This content
     view occupies the majority of the row view area and basically determines its appearance.
   * It handles native mouse events and keyboard events (that pass through `RenderWidgetHost`) to control suggestion selection (form
     preview) and acceptance (form filling).
   * It automatically adds an expanding control for suggestions with children. Note that
     the sub-popup is not controlled by the row, but in `PopupViewViews`
* [`PopupRowWithButtonView`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_row_with_button_view.h): An extension of `PopupRowView` that supports
   a single button in the content view layout.
   * It supports the subtleties of having a control inside a row view, e.g. selection/unselection
     on button focusing.
   * An example of usage is the Autocomplete suggestion with a "Delete" button
* [`CreatePopupRowView()`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_row_factory_utils.h): Row construction method.
   * It is the entry point for creating rows of different types. Based on the suggestion (mostly
     its `SuggestionType`) it instantiates a row class and its content view.


## Adding new popup content

There are currently about ~30 different `SuggestionType`s, that correspond to a different type of popup row. When a new type is added and it cannot be properly processed by `CreatePopupRowView()`, use the
following steps to support it by the popup UI:
* Create a new factory method for `PopupRowContentView` (or even for `PopupRowView` if needed, e.g. `CreateAutocompleteRowWithDeleteButton()`),
  e.g. `CreatePasswordPopupRowContentView()` in [popup_row_factory_utils.cc](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_row_factory_utils.cc).
* Call it when appropriate in [`CreatePopupRowView()`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/views/autofill/popup/popup_row_factory_utils.cc).
* Add/update tests in `popup_row_factory_utils_unittest.cc` if some testable logic was affected.
* Add a pixel test to `popup_row_factory_utils_browsertest.cc`. In most cases adding the newly added suggestion type to `kSuggestions` will suffice.