GrConfirmDialog

  • core
  • overlays
  • API · 23 props
  • ⌨ keys

Asks to confirm a potentially important or dangerous action.

import { GrConfirmDialog } from '@feugene/granularity/components/GrConfirmDialog'

Overview

When to take it

  • the action is irreversible — deleting, revoking access, cancelling an order: the pause before it is the point of the component;
  • the confirmation goes to a server — confirmLoading keeps the window open for the duration of the request, error shows the refusal;
  • the button has to look dangerous — confirmTone colours the confirmation in the tone of the consequence;
  • the focus lands on cancel — focusAction keeps a dangerous action from being confirmed blindly with Enter.

When to take something else

NeedTake
Ask for a value rather than for consentGrPromptDialog
Call a confirmation from codeGrDialogService
A window with arbitrary contentGrDialog
A confirmation right at the button, without a windowGrPopover
Report a result rather than askGrToaster

Harmless actions do not need confirming: a dialog that is always answered “yes” stops being read and will not stop anyone on the single occasion when it mattered. A reversible action is better covered by an undo in a toast.

Playground controls come from the API, not from hand

Stage

The window opens above the page with the props set on the right.

0 changed· state is in the URL

Examples 3 each with a live demo and its code

  • Revoking a member's access

    The answer is named by the action — «Revoke Grace», «Keep access» — because «OK» does not say what it agrees to, and confirm-tone="danger" paints it in the tone of the consequence. focus-action="cancel" puts the focus on the safe answer: Enter pressed right after opening must not revoke anything.

    Workspace members
    GWGrace WuAccountant
    OHOmar HaddadSales
    INInes NovakOwner
  • A cancellation the server refuses

    close-on-confirm="false" keeps the window while the request runs, confirm-loading shows the wait in the button, and persistent turns off Esc and the backdrop meanwhile — the cross and «Keep plan» still work. The first try is refused: error puts the server’s answer above the buttons, where the decision is made.

    Business planRenews on 1 November · €240 a month

API generated from the package · cannot drift

Props

PropTypedefaultDescription
titlestring | undefinedundefinedThe title of the window, which is also its accessible name. Not set — taken from the locale.
size"sm" | "md" | "lg" | "xl" | "full" | undefinedundefinedThe width of the window on the `GrDialog` scale: from `sm` to `xl`, `full` — the whole screen. `md` by default.
descriptionstring | undefinedundefinedThe text of the question in the body of the window. The `default` slot replaces it.
closeOnBackdropboolean | undefinedtrueClose on a click on the backdrop. `true` by default; with `persistent` it is switched off for the duration of `confirmLoading`.
closeOnEscboolean | undefinedtrueClose on Esc. `true` by default; with `persistent` it is switched off for the duration of `confirmLoading`.
showHeaderboolean | undefinedtrueShow the header with the title and the close button. `true` by default.
showCloseButtonboolean | undefinedtrueThe close button in the header. `true` by default; it stays with `persistent` too.
headerConfigGrDialogSectionConfig | undefinedundefinedThe paddings and the line of the header: `paddingX`, `paddingY`, `bordered`.
footerConfigGrDialogSectionConfig | undefinedundefinedThe paddings and the line of the footer with the buttons.
bodyConfigGrDialogSectionConfig | undefinedundefinedThe paddings of the window body. `bordered` does not apply to the body.
closeLabelstring | undefinedundefinedThe a11y label of the close button (i18n).
buttonSize"xs" | "sm" | "md" | "lg" | undefinedundefinedThe size of both footer buttons. Not set — the buttons take their size from `GrConfigProvider`.
confirmTextstring | undefinedundefinedThe label of the confirm button. Not set — taken from the locale.
cancelTextstring | undefinedundefinedThe label of the cancel button. Not set — taken from the locale.

Slots

SlotTypeDescription
defaultanyThe content of the dialog instead of the text from the `description` prop.
error{ error: ResponseErrorInfo | null; }Your own presentation of the error instead of the built-in banner.
footeranyThe buttons of the dialog instead of the "cancel and confirm" pair.

Events

EventSignatureDescription
update:modelValue(event: "update:modelValue", value: boolean): void—
confirm(event: "confirm"): void—
cancel(event: "cancel"): void—

Types

Every exported type of the subpath, grouped by the file it lives in. Names, generics and bodies come from the package’s declaration files and cannot drift.

Import
import type { GrConfirmDialogFocusAction, GrConfirmDialogProps, GrConfirmDialogEmits } from '@feugene/granularity/components/GrConfirmDialog'

Filedist/types/components/GrConfirmDialog/GrConfirmDialog.vue.d.ts

GrConfirmDialogFocusActiontype
type GrConfirmDialogFocusAction = 'confirm' | 'cancel' | 'none';
GrConfirmDialogPropsinterface
interface GrConfirmDialogProps {
    modelValue: boolean;
    title?: string;
    description?: string;
    closeOnBackdrop?: boolean;
    closeOnEsc?: boolean;
    showHeader?: boolean;
    showCloseButton?: boolean;
    size?: GrDialogSize;
    headerConfig?: GrDialogSectionConfig;
    footerConfig?: GrDialogSectionConfig;
    bodyConfig?: GrDialogSectionConfig;
    closeLabel?: string;
    buttonSize?: GrButtonSize;
    confirmText?: string;
    cancelText?: string;
    confirmVariant?: GrButtonVariant;
    confirmTone?: GrButtonTone;
    error?: ResponseErrorInfo | null;
    confirmLoading?: boolean;
    confirmDisabled?: boolean;
    closeOnConfirm?: boolean;
    focusAction?: GrConfirmDialogFocusAction;
    persistent?: boolean;
}
GrConfirmDialogEmitsinterface
interface GrConfirmDialogEmits {
    (e: 'update:modelValue', value: boolean): void;
    (e: 'confirm'): void;
    (e: 'cancel'): void;
}

Filedist/types/components/GrConfirmDialog/config.d.ts

grConfirmDialogConfigconst
const grConfirmDialogConfig: import("@feugene/granum/contract").GranumComponentDescriptor<"GrConfirmDialog">;

Accessibility

Keys

EscTab / Shift+Tab

Usage from the library prose

The focus on opening

focusAction decides which action gets the focus: 'cancel' (the default), 'confirm' or 'none' — the focus stays on the panel of the window.

The default is 'cancel' precisely because a confirmation window exists for the sake of a risky action: Enter pressed right after the opening has to cancel, not delete. 'confirm' is appropriate where the confirmation is a routine (“Save before leaving?”).

The focus is set from the side of the content after rendering rather than with the initialFocus prop of GrModal: the element is born inside the subtree of the dialog, and returning it upwards through a prop closes the render into a loop.

The degradation is silent. If the #footer slot has been overridden, the component does not know your buttons and the focus stays on the panel; the same happens with focusAction="confirm" and confirmDisabled. This is not a configuration error: a footer of your own means the consumer disposes of the focus.

Asynchronous confirmation

closeOnConfirm: false hands the closing outside: the component sends confirm and stays open until the consumer clears v-model. For the duration of the operation there are confirmLoading (the button shows loading and accepts no clicks) and error (a banner with the server’s answer in the body of the window, and the #error slot — if a banner is not enough).

persistent switches off the soft ways of closing for that time — Esc and a click on the backdrop. The cross and “Cancel” remain: a window with no way out is a trap, not a protection. The same prop with the same semantics exists in GrPromptDialog and GrDrawer.

vue
<GrConfirmDialog
  v-model="open"
  confirm-tone="danger"
  :confirm-loading="loading"
  :error="error"
  :close-on-confirm="false"
  persistent
  @confirm="submit"
/>

useDialogService switches persistent on for all of its windows itself — there loading means the request has already left.