Plugin: mam-contact-form

What it does

mam-contact-form adds a Contact Us form to a MAM mobile app. The form can be placed on the main tab bar or in the left menu, and submissions trigger a configurable admin email notification.

The default form ships with six logical fields — Name, Email, Phone, Contact Reason, Subject, Description. Name, Email, and Phone are auto-populated from the signed-in user’s WordPress profile. Developers can add custom fields via filter without modifying core files, and a Contact Reason field lets a single form route different submissions to different notifications.

The plugin is no-code first and low-code where it matters. Most installations only need a notification email and a placement in App Setup; everything else is optional. The same person typically wears both hats — admin to configure, developer to extend — so the recipes and hook references in this codex are designed to hand off to one another.


Setup paths

mam-contact-form supports two ways to define the form. Pick one based on your customization needs.

Default path — built-in form handler. The plugin ships with a built-in handler that mirrors the Gravity Forms structure. No external plugin is required. The default fields are pre-configured, including the correct mobile keyboards for Phone and Email. Custom fields can still be added programmatically via PHP filter. Use this for most installations. See Recipe: Setting up a contact form (default path).

Gravity Forms path. If you want to design the form in Gravity Forms — drag-and-drop fields, conditional logic, the full Gravity Forms feature set — install Gravity Forms and the MAM Gravity Forms plugin. Submissions then flow through Gravity Forms instead of the built-in handler. See Recipe: Setting up a contact form with Gravity Forms.

The hooks listed below work identically on both paths. The same is true for admin features like Contact Reason routing.


Where it appears in the app

The form is rendered by vc_form_manager on iOS and the equivalent form activity on Android. It is reached from:

  • A main navigation tab item (when configured as a tab)
  • A left menu entry (when configured as a menu item)

Both placements are configured in Mobile App Manager → App Setup. The same Gravity Forms form ID is reused regardless of placement; you do not need to define the form twice.


Requirements

  • WordPress 6.3+
  • PHP 8.1+
  • MAM Suite with mam-main activated
  • MAM Suite plugin entitlement for mam-contact-form

The Gravity Forms path additionally requires:

  • Gravity Forms (any current version)
  • MAM Gravity Forms plugin — the bridge between Gravity Forms and the MAM form handler

If mam-main is not active, the plugin silently exits in its constructor (entitlement guard). If mam-gravity-forms-manager is missing, mam_gf_get_form returns an empty array and submission processing returns an error response.


Default fields

Field Slug Type Auto-populated for logged-in users
Name name text Yes (from first_name + last_name)
Email email email Yes (from user_email)
Phone phone phone Yes (from billing_phone user meta, if present)
Contact Reason reason text No
Subject subject text No
Description description textarea No

On the default path, Phone and Email fields are pre-configured with the correct mobile keyboards. On the Gravity Forms path, you must manually set special_handling on each field — see Recipe: Setting up a contact form with Gravity Forms.

The Contact Reason field is optional in practice. If the Reason field ID option (mam-contact-formcontact_form_reason) is not stored, the routing UI is hidden and submissions flow to a single notification.


Hooks exposed

Hook Type Audience Purpose
mam_gf_get_form_settings_fields_contact_form filter PHP dev Add custom fields to the form’s logical field list. Path-agnostic despite the gf_ in the name.
mam_contact_form_populate_contact filter PHP dev Pre-fill custom fields when the form loads.
mam_contact_form_contact_processed action PHP dev Run custom logic after a submission is processed.

Each hook has its own dedicated article. See Related articles.


Mobile JSON contract

mam-contact-form does not write directly into the top-level mobile JSON payload. Instead, it contributes to the Gravity Forms-shaped form structure that mam-gravity-forms-manager exposes to the app. The keys it sets are part of the frozen mobile contract — renaming them will break deployed apps.

Key Shape Notes
fields[*].slug string The logical identifier for a field. The mobile app keys submissions on this. Default slugs: name, email, phone, reason, subject, description.
fields[*].populate_with_key string Mirrors slug; consumed by the Gravity Forms bridge for value pre-fill.
fields[*].value string Pre-filled value when the user is signed in. Set by populate_contact_form() and the mam_contact_form_populate_contact filter.
fields[*].firstName / fields[*].lastName string Set on the name field only, so the app can render a split name input.

Submission responses use this shape:

Key Value Notes
status 'success' or 'error' Drives whether the app shows the confirmation or the error message.
type 'refresh_return' Tells the app to dismiss the form and refresh the previous screen.
message string Confirmation or error text shown to the user.
process_normal bool When false, the app skips Gravity Forms’s default confirmation handling.
send_notifications bool When false, the app does not fire the generic GF notification. The plugin has already dispatched its own.

WordPress options used

The plugin reads and writes a small set of options. These are stored in client databases — Tier 1 frozen, do not rename without a migration.

Option key Purpose
mam-contact-formcontact_form Gravity Forms form ID for the contact form.
mam-contact-formcontact_form_{slug} Gravity Forms field ID for each default field (_name, _email, _phone, _reason, _subject, _description). Written as a side effect of get_fields().
mam-contact-form_{form_id}_{field_id}_{choice_key} Per-Contact-Reason notification mapping. Written by the Contact Form admin page.

The leading prefix mam-contact-form and the body (e.g., contact_form) are concatenated without a separator. This is consistent within the plugin but easy to misread.


Common tasks

  • Set up the form using the built-in handler → Recipe: Setting up a contact form (default path)
  • Set up the form using Gravity Forms → Recipe: Setting up a contact form with Gravity Forms
  • Route different submissions to different notifications → Recipe: Enabling multiple contact reason types
  • Add address fields (Street/City/State/ZIP) → Hook: mam_gf_get_form_settings_fields_contact_form
  • Send submissions to a CRM after processing → Hook: mam_contact_form_contact_processed
  • Pre-fill custom fields with values from the user profile → Hook: mam_contact_form_populate_contact

Verification

This article was last verified against:

  • Plugin: mam-contact-form v2.1
  • Source: mam-contact-form/mam-contact-form.php
  • Source: mam-contact-form/includes/admin-settings.php
  • mam-main (required)
  • mam-gravity-forms-manager (required for the Gravity Forms path)

Re-verify whenever a hook is added or removed, the default field list in get_fields() changes, the option-key naming scheme above changes, the submission response shape returned by process_contact_form() changes, or either setup path’s admin UI is reorganized.


  • Recipe: Setting up a contact form (default path)
  • Recipe: Setting up a contact form with Gravity Forms
  • Recipe: Enabling multiple contact reason types
  • Hook: mam_gf_get_form_settings_fields_contact_form
  • Hook: mam_contact_form_contact_processed
  • Hook: mam_contact_form_populate_contact

Metadata

Field Value
Article type Plugin Overview
Plugin slug mam-contact-form
Applies to plugin version 2.1+
Category Plugin Reference
Depends on MAM Main, MAM Gravity Forms
Works with Gravity Forms (optional, for the Gravity Forms setup path)
Hooks exposed mam_gf_get_form_settings_fields_contact_form, mam_contact_form_contact_processed, mam_contact_form_populate_contact
Last verified 2026-05-01
Contents

    Need Support?

    Can’t find the answer you’re looking for? Don’t worry we’re here to help!