Purpose
The per-button enrichment hub. Fired once per button as the phone-data pipeline walks the button arrays. Sibling plugins use this filter to enrich button definitions — adding icons, action targets, per-button settings — without owning the button itself.
~43 subscribers across the suite.
Signature
$button = apply_filters( 'mam_tab_manager', array $button );
| Parameter | Type | Description |
|---|---|---|
$button |
array | The button definition shape — see Button array storage |
Returns: array — the (possibly enriched) button.
When it fires
Inside the button-rendering loop in MAM_Phone_Data_Pipeline::phase_content():
For each button in the role's button array:
apply mam_app_settings_get_buttons (read)
For each button:
$button = apply_filters('mam_tab_manager', $button);
$button = apply_filters('mam_final_button_settings', $button);
... merge into response
It also fires for tab-bar buttons after mam_main_add_tab_bar_item_{slug}.
Example: enrich a button by id
add_filter( 'mam_tab_manager', function ( array $button ): array {
// Only handle the button id we care about.
if ( ( $button['id'] ?? '' ) !== 'my_plugin_button_42' ) {
return $button;
}
$button['icon'] = 'black_calendar';
$button['action'] = 'open_form';
$button['source'] = $this->get_form_index();
$button['values'] = $this->build_prefill_values();
return $button;
}, 10 );
Example: enrich by content_type
add_filter( 'mam_tab_manager', function ( array $button ): array {
if ( ( $button['content_type'] ?? '' ) !== 'My Plugin Action' ) {
return $button;
}
// Enrich every button of this content type.
$button['icon'] = $button['icon'] ?: 'black_default';
return $button;
}, 10 );
Gotchas
- Last-writer-wins for shared keys. Two subscribers writing to
$button['icon']produce a deterministic-but-fragile result based on registration order. Coordinate with other plugin authors when stomping on shared keys. - No explicit priority ordering convention. Subscribers add per-button modifications in registration order. Refactors that change registration order can change behavior.
- Hot path. Fires once per button per phone-data build. A list of 50 listings × N tab-bar buttons → many invocations. Cache lookups inside callbacks.
$button['id']is the dispatch key. Always check it before doing work.- Don’t change
$button['id']— the calling code expects it back unchanged.
Related articles
- Phone data pipeline phases
- Recipe: Add a button
- Recipe: Configure the tab bar
- Button array storage
- Hook: mam_app_settings_get_buttons
- Hook: mam_final_button_settings
- Hook: mam_main_add_tab_baritem{slug}
Metadata
| Field | Value |
|---|---|
| Article type | Hook Reference |
| Plugin slug | mam-main |
| Applies to plugin version | 2.1.11+ |
| Hook type | filter |
| Audience | PHP developer |
| Frozen contract | yes — ~43 subscribers |
| Last verified | 2026-05-02 |
