Skip to content
HyperUI for Flutter requires the Style package — this site itself ships no pub package.

Modals

Ported from HyperUI’s Modals — see Attribution. Each preview below shows the modal’s closed state (just the “Open” trigger button) — hyperui’s own <dialog> has no declarative always-open state; toggling it live is out of scope for this static gallery (same “default DOM state only” convention as every checkbox/ toggle/radio-input in this corpus).

Includes a dark: variant — toggle the site theme (top right) to preview it.

const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals1Example extends StatelessWidget {
const Modals1Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) => Stack(
children: [
const Positioned.fill(child: IgnorePointer(child: _ModalBackdrop())),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
],
),
),
),
),
],
),
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}

Includes a dark: variant — toggle the site theme (top right) to preview it.

class CurrentColorIcon extends StatelessWidget
implements StyleReplacedElementWrapper {
const CurrentColorIcon(this.svg, {super.key});
final String svg;
@override
Widget build(BuildContext context) {
final color = IconTheme.of(context).color ?? const Color(0xFF000000);
return SvgPicture.string(svg, theme: SvgTheme(currentColor: color));
}
}
const _closeSvg =
'''<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/></svg>''';
const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals2Example extends StatelessWidget {
const Modals2Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) => Stack(
children: [
const Positioned.fill(child: IgnorePointer(child: _ModalBackdrop())),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'flex items-start justify-between',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'-me-4 -mt-4 rounded-full p-2 text-gray-600 transition-colors hover:bg-gray-50 hover:text-gray-900 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:text-gray-500 dark:hover:bg-gray-800 dark:hover:text-gray-300 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Focus(
autofocus: true,
child: Style(
'size-5',
child: CurrentColorIcon(_closeSvg),
),
),
),
),
],
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
],
),
),
),
),
],
),
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}

Includes a dark: variant — toggle the site theme (top right) to preview it.

const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals3Example extends StatelessWidget {
const Modals3Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) => Stack(
children: [
const Positioned.fill(child: IgnorePointer(child: _ModalBackdrop())),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
Style(
'flex justify-end gap-2',
children: [
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-gray-100 px-4 py-2 text-sm font-medium text-gray-700 transition-colors hover:bg-gray-200 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-gray-800 dark:text-gray-200 dark:hover:bg-gray-700 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Focus(
autofocus: true,
child: Text('Cancel'),
),
),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-blue-600 px-4 py-2 text-sm font-medium text-white transition-colors hover:bg-blue-700 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-blue-300 dark:text-gray-900 dark:hover:bg-blue-200 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Done'),
),
),
],
),
],
),
),
),
),
],
),
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}

Includes a dark: variant — toggle the site theme (top right) to preview it.

class CurrentColorIcon extends StatelessWidget
implements StyleReplacedElementWrapper {
const CurrentColorIcon(this.svg, {super.key});
final String svg;
@override
Widget build(BuildContext context) {
final color = IconTheme.of(context).color ?? const Color(0xFF000000);
return SvgPicture.string(svg, theme: SvgTheme(currentColor: color));
}
}
const _closeSvg =
'''<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/></svg>''';
const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals4Example extends StatelessWidget {
const Modals4Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) => Stack(
children: [
const Positioned.fill(child: IgnorePointer(child: _ModalBackdrop())),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'flex items-start justify-between',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'-me-4 -mt-4 rounded-full p-2 text-gray-600 transition-colors hover:bg-gray-50 hover:text-gray-900 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:text-gray-500 dark:hover:bg-gray-800 dark:hover:text-gray-300 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Focus(
autofocus: true,
child: Style(
'size-5',
child: CurrentColorIcon(_closeSvg),
),
),
),
),
],
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
Style(
'flex justify-end gap-2',
children: [
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-gray-100 px-4 py-2 text-sm font-medium text-gray-700 transition-colors hover:bg-gray-200 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-gray-800 dark:text-gray-200 dark:hover:bg-gray-700 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Cancel'),
),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-blue-600 px-4 py-2 text-sm font-medium text-white transition-colors hover:bg-blue-700 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-blue-300 dark:text-gray-900 dark:hover:bg-blue-200 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Done'),
),
),
],
),
],
),
),
),
),
],
),
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}

Includes a dark: variant — toggle the site theme (top right) to preview it.

const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals5Example extends StatelessWidget {
const Modals5Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) {
final isDark = Theme.of(dialogContext).brightness == Brightness.dark;
final isSmUp = MediaQuery.sizeOf(dialogContext).width >= 640;
final fontSize = isSmUp ? 14.0 : 16.0;
final lineHeight = isSmUp ? 20.0 : 24.0;
final baseStyle =
Theme.of(dialogContext).textTheme.bodyLarge ?? const TextStyle();
return Stack(
children: [
const Positioned.fill(
child: IgnorePointer(child: _ModalBackdrop()),
),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
Style(
'block',
children: [
Style(
'text-sm font-medium text-gray-700 dark:text-gray-200',
display: DisplayType.inline,
child: const Text(
'Please type "Confirm" to complete action',
),
),
Style(
'mt-0.5 w-full rounded border-gray-300 bg-white text-gray-900 shadow-sm focus:ring-2 focus:ring-indigo-600 sm:text-sm dark:border-gray-600 dark:bg-gray-900 dark:text-white dark:focus:ring-indigo-300',
child: TextFormField(
autofocus: true,
style: baseStyle.copyWith(
fontSize: fontSize,
height: lineHeight / fontSize,
color: isDark ? Colors.white : Colors.black,
),
),
),
],
),
Style(
'flex justify-end gap-2',
children: [
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-gray-100 px-4 py-2 text-sm font-medium text-gray-700 transition-colors hover:bg-gray-200 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-gray-800 dark:text-gray-200 dark:hover:bg-gray-700 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Cancel'),
),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-blue-600 px-4 py-2 text-sm font-medium text-white transition-colors hover:bg-blue-700 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-blue-300 dark:text-gray-900 dark:hover:bg-blue-200 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Done'),
),
),
],
),
],
),
),
),
),
],
);
},
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}

Includes a dark: variant — toggle the site theme (top right) to preview it.

class CurrentColorIcon extends StatelessWidget
implements StyleReplacedElementWrapper {
const CurrentColorIcon(this.svg, {super.key});
final String svg;
@override
Widget build(BuildContext context) {
final color = IconTheme.of(context).color ?? const Color(0xFF000000);
return SvgPicture.string(svg, theme: SvgTheme(currentColor: color));
}
}
const _closeSvg =
'''<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/></svg>''';
const _description =
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque '
'euismod, nisi eu consectetur. Sed do eiusmod tempor incididunt ut '
'labore et dolore magna aliqua.';
class Modals6Example extends StatelessWidget {
const Modals6Example({super.key});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Style(
'p-6',
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => _openModal(context),
child: Style(
'rounded border border-gray-300 bg-gray-100 px-3 py-1.5 text-sm text-gray-900 dark:border-gray-600 dark:bg-gray-800 dark:text-white',
cursor: SystemMouseCursors.click,
child: const Text('Open'),
),
),
),
],
);
}
void _openModal(BuildContext context) {
showDialog<void>(
context: context,
barrierColor: Colors.transparent,
useSafeArea: false,
useRootNavigator: false,
builder: (dialogContext) {
final isDark = Theme.of(dialogContext).brightness == Brightness.dark;
final isSmUp = MediaQuery.sizeOf(dialogContext).width >= 640;
final fontSize = isSmUp ? 14.0 : 16.0;
final lineHeight = isSmUp ? 20.0 : 24.0;
final baseStyle =
Theme.of(dialogContext).textTheme.bodyLarge ?? const TextStyle();
return Stack(
children: [
const Positioned.fill(
child: IgnorePointer(child: _ModalBackdrop()),
),
Center(
child: Material(
type: MaterialType.transparency,
child: Style(
'm-auto max-w-xl rounded-lg bg-white p-6 shadow-lg backdrop:bg-black/50 dark:bg-gray-900 dark:backdrop:bg-white/50',
child: Style(
'flex flex-col gap-4',
children: [
Style(
'flex items-start justify-between',
children: [
Style(
'text-xl font-bold text-gray-900 sm:text-2xl dark:text-white',
child: const Text('Modal Title'),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'-me-4 -mt-4 rounded-full p-2 text-gray-600 transition-colors hover:bg-gray-50 hover:text-gray-900 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:text-gray-500 dark:hover:bg-gray-800 dark:hover:text-gray-300 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Focus(
autofocus: true,
child: Style(
'size-5',
child: CurrentColorIcon(_closeSvg),
),
),
),
),
],
),
Style(
'text-pretty text-gray-700 dark:text-gray-200',
child: const Text(_description),
),
Style(
'block',
children: [
Style(
'text-sm font-medium text-gray-700 dark:text-gray-200',
display: DisplayType.inline,
child: const Text(
'Please type "Confirm" to complete action',
),
),
Style(
'mt-0.5 w-full rounded border-gray-300 bg-white text-gray-900 shadow-sm sm:text-sm dark:border-gray-600 dark:bg-gray-900 dark:text-white',
child: TextFormField(
style: baseStyle.copyWith(
fontSize: fontSize,
height: lineHeight / fontSize,
color: isDark ? Colors.white : Colors.black,
),
),
),
],
),
Style(
'flex justify-end gap-2',
children: [
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-gray-100 px-4 py-2 text-sm font-medium text-gray-700 transition-colors hover:bg-gray-200 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-gray-800 dark:text-gray-200 dark:hover:bg-gray-700 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Cancel'),
),
),
GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: () => Navigator.pop(dialogContext),
child: Style(
'rounded bg-blue-600 px-4 py-2 text-sm font-medium text-white transition-colors hover:bg-blue-700 focus:ring-2 focus:ring-indigo-600 focus:ring-offset-2 focus:ring-offset-white focus:outline-none focus-visible:ring-2 focus-visible:ring-indigo-600 focus-visible:ring-offset-2 focus-visible:ring-offset-white focus-visible:outline-none dark:bg-blue-300 dark:text-gray-900 dark:hover:bg-blue-200 dark:focus:ring-indigo-300 dark:focus:ring-offset-gray-900 dark:focus-visible:ring-indigo-300 dark:focus-visible:ring-offset-gray-900',
cursor: SystemMouseCursors.click,
child: const Text('Done'),
),
),
],
),
],
),
),
),
),
],
);
},
);
}
}
class _ModalBackdrop extends StatelessWidget {
const _ModalBackdrop();
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
return ColoredBox(color: Color(isDark ? 0x80FFFFFF : 0x80000000));
}
}