Skip to main content
cngx-src documentation

CngxActionButton

ComponentPrimaryOnPushNo encapsulationv0.1.0WCAG AA

projects/ui/action-button/action-button.ts

Import#

import { CngxActionButton } from '@cngx/ui/action-button'

Description#

Action button organism with built-in status communication.

Coordinates between the CngxAsyncClick atom (mechanism, ARIA, lifecycle) and the consumer (intent, styling, labels). Provides template projection for pending/succeeded/failed states and an aria-live region for screen reader announcements.

Uses display: contents - the host produces no DOM box. The inner <button> carries the [cngxAsyncClick] directive directly.

For full control, use [cngxAsyncClick] directly on any element instead.

Minimal (covers 80% of cases)

<cngx-action-button [action]="save">Save</cngx-action-button>

With string labels

<cngx-action-button [action]="save"
  pendingLabel="Saving..." succeededLabel="Saved!" failedLabel="Failed">
  Save
</cngx-action-button>

With template slots

<cngx-action-button [action]="save">
  Save Draft
  <ng-template cngxPending><mat-spinner diameter="18" /> Saving...</ng-template>
  <ng-template cngxSucceeded>Saved!</ng-template>
  <ng-template cngxFailed let-err>{{ err }} - retry?</ng-template>
</cngx-action-button>

With toast feedback

<cngx-action-button [action]="save" toastSuccess="Saved" toastError="Save failed">
  Save
</cngx-action-button>

https://cngxjs.github.io/cngx/examples/#/ui/action-button/async-button/random-outcome https://cngxjs.github.io/cngx/examples/#/ui/action-button/async-button/string-labels https://cngxjs.github.io/cngx/examples/#/ui/action-button/async-button/template-slots

Metadata#

Host#

Relationships

Index#

Inputs#

input()Required

The async action to execute on click.

enabled#boolean
input()

When false, clicks are ignored. Passed through to cngxAsyncClick.

default true

Bind an external async state to derive visual status from. When set, the button's status display follows externalState.status().

failedAnnouncement#string | undefined
input()

SR announcement on failure. Falls back to failedLabel, then 'Action failed'.

failedLabel#string | undefined
input()

Fallback text after failure (when no cngxFailed template is projected).

feedbackDuration#number
input()

Duration in ms to show success/error feedback. Passed through to cngxAsyncClick.

default 2000
pendingLabel#string | undefined
input()

Fallback text while pending (when no cngxPending template is projected).

succeededAnnouncement#string | undefined
input()

SR announcement on success. Falls back to succeededLabel, then 'Action succeeded'.

succeededLabel#string | undefined
input()

Fallback text after success (when no cngxSucceeded template is projected).

toastError#string | undefined
input()

Toast message on error.

toastErrorDetail#boolean
input()

Include the error detail message in the error toast body.

default false
toastErrorDuration#number | 'persistent'
input()

Duration for error toasts - 'persistent' means manual dismiss only.

default 'persistent'
toastSuccess#string | undefined
input()

Toast message on success. Requires CngxToaster (via provideFeedback(withToasts()) or provideToasts()). Silently ignored when toaster is not provided.

toastSuccessDuration should be >= feedbackDuration to avoid rapid re-fire on repeated clicks that floods the SR announcement queue.

toastSuccessDuration#number
input()

Duration for success toasts in ms.

default 3000
type#"button" | "submit" | "reset"
input()

Button type attribute. Defaults to 'button' to prevent accidental form submits.

default 'button'
input()

Visual variant - sets CSS class cngx-action-button--{variant}.

default 'primary'

Instance Properties#

Readonly

Full CngxAsyncState view of this button's effective lifecycle.

Reflects the external state when [externalState] is bound, otherwise the inner CngxAsyncClick directive's state.

Bind to any state consumer: <cngx-alert [state]="btn.state" />.

buildAsyncStateView<unknown>({
  status: this.effectiveStatus,
  data: computed(() => undefined),
  error: this.effectiveError,
  lastUpdated: this.lastUpdatedState.asReadonly(),
})

Default visuals for CngxActionButton. The component host carries display: contents and renders a <button class="cngx-action-button cngx-action-button--{variant}"> inside. Token groups span Layout / Surface / Motion plus per-variant and per-async-state buckets.

State modifiers

Async-commit state classes are set by cngxAsyncClick on the <button> element, and the actual .cngx-async--* rules live in @cngx/common/theming/components/cngx-async.css so they apply globally (CngxPopoverAction and standalone usages reach them too). The token surface reserved here:

  • --cngx-action-btn-pending-opacity - opacity + cursor: wait
  • --cngx-action-btn-succeeded-bg / -color / -border - success tint
  • --cngx-action-btn-failed-bg / -color / -border - failure tint

Variants

Three variants share the base shape (border, radius, padding, transition) and only repaint the surface:

  • --primary - filled brand surface, white text
  • --secondary - transparent fill, brand text, border accent
  • --ghost - text-only, hover state-layer for affordance

Pair with

  • @cngx/themes/material/action-button-theme - Material 3 primary / outline / error surfaces

Index#

Motion

--cngx-action-btn-transition#*
Default value 0.2s ease

Transition shorthand for background-color / color / border-color / opacity transitions across all variants and async states.

Layout

--cngx-action-btn-radius#<length>
Default value 6px

Corner radius of every variant.

--cngx-action-btn-padding#*
Default value 8px 16px

Vertical + horizontal padding shorthand. Both axes can be re-driven individually by overriding with a one- or two-value shorthand.

.compact { --cngx-action-btn-padding: 4px 10px; }

Surface

--cngx-action-btn-border#<color>
Default value oklch(0.87 0 0)

Border color of the base (non-variant) .cngx-action-button rule. Variant rules override this per appearance.

See: [[--cngx-color-border]]

--cngx-action-btn-bg#<color>
Default value transparent

Background of the base rule. Variants override.

State / Pending

--cngx-action-btn-pending-opacity#<number>
Default value 0.7

Opacity applied while cngxAsyncClick reports pending. Combined with cursor: wait on the same state.

State / Succeeded

--cngx-action-btn-succeeded-bg#<color>
Default value oklch(0.95 0.04 145)

Background tint after a successful async commit.

--cngx-action-btn-succeeded-color#<color>
Default value oklch(0.5 0.15 145)

Text color after a successful async commit.

--cngx-action-btn-succeeded-border#<color>
Default value oklch(0.5 0.15 145)

Border color after a successful async commit.

State / Failed

--cngx-action-btn-failed-bg#<color>
Default value oklch(0.95 0.025 25)

Background tint after a failed async commit.

--cngx-action-btn-failed-color#<color>
Default value oklch(0.45 0.15 25)

Text color after a failed async commit.

--cngx-action-btn-failed-border#<color>
Default value oklch(0.45 0.15 25)

Border color after a failed async commit.

Variant / Ghost

--cngx-action-btn-ghost-hover-bg#<color>
Default value oklch(0 0 0 / 0.04)

Hover state-layer for the ghost variant - subtle tint so the button is felt without competing with primary actions.

--cngx-action-btn-ghost-color#<color>
Default value oklch(0.34 0.005 290)

Text color of the ghost variant.

Variant / Primary

--cngx-action-btn-primary-bg#<color>
Default value oklch(0.55 0.15 250)

Background of the primary variant (filled).

--cngx-action-btn-primary-color#<color>
Default value oklch(1 0 0)

Text color of the primary variant.

Variant / Secondary

--cngx-action-btn-secondary-bg#<color>
Default value transparent

Background of the secondary variant (outlined). Defaults to transparent so the surface beneath shines through.

--cngx-action-btn-secondary-color#<color>
Default value oklch(0.55 0.15 250)

Text color of the secondary variant.

--cngx-action-btn-secondary-border#<color>
Default value oklch(0.55 0.005 290)

Border color of the secondary variant.