surface static method

String surface()

Implementation

static String surface() => r'''
import 'dart:ui';

import 'package:flutter/material.dart';

import '../styles/design_style_config.dart';
import '../themes/app_theme_extensions.dart';
import '../tokens/app_blur.dart';
import '../tokens/app_colors.dart';
import '../tokens/app_motion.dart';
import '../tokens/app_radius.dart';
import '../tokens/app_shadows.dart';
import '../tokens/app_spacing.dart';

enum AppSurfaceDepth { flat, raised, floating, pressed, inset }

class AppSurface extends StatelessWidget {
const AppSurface({
  super.key,
  required this.child,
  this.padding,
  this.margin,
  this.depth = AppSurfaceDepth.raised,
  this.radius,
  this.onTap,
  this.semanticLabel,
  this.width,
  this.height,
});

final Widget child;
final EdgeInsetsGeometry? padding;
final EdgeInsetsGeometry? margin;
final AppSurfaceDepth depth;
final double? radius;
final VoidCallback? onTap;
final String? semanticLabel;
final double? width;
final double? height;

static bool allowExpensiveEffects(BuildContext context) {
  final data = MediaQuery.maybeOf(context);
  if (data == null) return true;
  if (data.disableAnimations) return false;
  return true;
}

@override
Widget build(BuildContext context) {
  final surfaces = Theme.of(context).extension<AppSurfaceTheme>();
  final radiusValue = radius ?? AppRadius.md;
  final borderRadius = BorderRadius.circular(radiusValue);
  final useBlur = AppStyleConfig.usesBlur &&
      allowExpensiveEffects(context) &&
      depth != AppSurfaceDepth.pressed &&
      depth != AppSurfaceDepth.flat;
  final sigma = depth == AppSurfaceDepth.floating
      ? AppBlur.large
      : AppBlur.medium;

  final decoration = _decoration(context, surfaces, borderRadius);

  final content = Padding(
    padding: padding ?? const EdgeInsets.all(AppSpacing.md),
    child: child,
  );

  Widget painted = AnimatedContainer(
    duration: AppMotion.fast,
    curve: AppMotion.standardCurve,
    width: width,
    height: height,
    decoration: useBlur ? decoration.copyWith(color: Colors.transparent) : decoration,
    child: content,
  );

  if (useBlur) {
    painted = ClipRRect(
      borderRadius: borderRadius,
      child: BackdropFilter(
        filter: ImageFilter.blur(sigmaX: sigma, sigmaY: sigma),
        child: DecoratedBox(
          decoration: decoration,
          child: content,
        ),
      ),
    );
  }

  if (AppStyleConfig.usesLiquidHighlight) {
    painted = Stack(
      children: <Widget>[
        painted,
        Positioned.fill(
          child: IgnorePointer(
            child: DecoratedBox(
              decoration: BoxDecoration(
                borderRadius: borderRadius,
                gradient: LinearGradient(
                  begin: Alignment.topLeft,
                  end: Alignment.bottomRight,
                  colors: <Color>[
                    (surfaces?.highlight ?? AppColors.highlight)
                        .withAlpha(140),
                    Colors.transparent,
                    (surfaces?.highlight ?? AppColors.highlight)
                        .withAlpha(30),
                  ],
                ),
              ),
            ),
          ),
        ),
      ],
    );
  }

  if (AppStyleConfig.usesSpatialDepth &&
      (depth == AppSurfaceDepth.floating ||
          depth == AppSurfaceDepth.raised)) {
    final scale = depth == AppSurfaceDepth.floating ? 1.02 : 1.0;
    painted = AnimatedScale(
      scale: scale,
      duration: AppMotion.normal,
      curve: AppMotion.entranceCurve,
      child: painted,
    );
  }

  if (onTap != null) {
    painted = Material(
      type: MaterialType.transparency,
      child: InkWell(
        onTap: onTap,
        borderRadius: borderRadius,
        child: painted,
      ),
    );
  }

  if (semanticLabel != null) {
    painted = Semantics(
      label: semanticLabel,
      button: onTap != null,
      child: painted,
    );
  }

  if (margin != null) {
    painted = Padding(padding: margin!, child: painted);
  }

  return painted;
}

BoxDecoration _decoration(
  BuildContext context,
  AppSurfaceTheme? surfaces,
  BorderRadius borderRadius,
) {
  final isDark = Theme.of(context).brightness == Brightness.dark;
  final base = isDark ? AppColorsDark.surface : AppColors.surface;
  final elevated =
      isDark ? AppColorsDark.surfaceElevated : AppColors.surfaceElevated;
  final translucent = surfaces?.surfaceTranslucent ??
      (isDark
          ? AppColorsDark.surfaceTranslucent
          : AppColors.surfaceTranslucent);
  final outline = isDark ? AppColorsDark.outline : AppColors.outline;

  Color color;
  switch (depth) {
    case AppSurfaceDepth.flat:
      color = surfaces?.background ??
          (isDark ? AppColorsDark.background : AppColors.background);
      break;
    case AppSurfaceDepth.floating:
      color = elevated;
      break;
    case AppSurfaceDepth.pressed:
    case AppSurfaceDepth.inset:
      color = isDark
          ? AppColorsDark.surfaceVariant
          : AppColors.surfaceVariant;
      break;
    case AppSurfaceDepth.raised:
      color = base;
      break;
  }

  if (AppStyleConfig.usesBlur &&
      allowExpensiveEffects(context) &&
      AppStyleConfig.reducedTransparencyFallback == false) {
    color = translucent;
  } else if (AppStyleConfig.usesBlur &&
      !allowExpensiveEffects(context)) {
    color = elevated;
  }

  Gradient? gradient;
  if (AppStyleConfig.usesSkeuoGradient) {
    gradient = LinearGradient(
      begin: Alignment.topCenter,
      end: Alignment.bottomCenter,
      colors: <Color>[
        Color.lerp(color, Colors.white, 0.22)!,
        color,
        Color.lerp(color, Colors.black, 0.08)!,
      ],
    );
  }

  return BoxDecoration(
    color: gradient == null ? color : null,
    gradient: gradient,
    borderRadius: borderRadius,
    border: _border(outline),
    boxShadow: _shadows(),
  );
}

Border? _border(Color outline) {
  if (AppStyleConfig.usesHardOffsetShadow) {
    return Border.all(color: outline, width: 3);
  }
  if (AppStyleConfig.usesBlur || AppStyleConfig.usesLiquidHighlight) {
    return Border.all(
      color: AppColors.highlight.withAlpha(140),
      width: 1,
    );
  }
  if (AppStyleConfig.usesNeoShadows) {
    return null;
  }
  return Border.all(
    color: AppColors.outlineVariant,
    width: 1,
  );
}

List<BoxShadow> _shadows() {
  if (depth == AppSurfaceDepth.flat) return const <BoxShadow>[];
  if (AppStyleConfig.usesNeoShadows) {
    return depth == AppSurfaceDepth.pressed || depth == AppSurfaceDepth.inset
        ? AppShadows.neoInset
        : AppShadows.neoRaised;
  }
  if (AppStyleConfig.usesHardOffsetShadow) {
    return depth == AppSurfaceDepth.pressed
        ? const <BoxShadow>[]
        : AppShadows.hardOffset;
  }
  if (AppStyleConfig.usesClayInflation) {
    return AppShadows.clay;
  }
  switch (depth) {
    case AppSurfaceDepth.floating:
      return AppShadows.floating;
    case AppSurfaceDepth.raised:
      return AppShadows.medium;
    case AppSurfaceDepth.pressed:
    case AppSurfaceDepth.inset:
      return AppShadows.low;
    case AppSurfaceDepth.flat:
      return const <BoxShadow>[];
  }
}
}
''';