From f7d4c026232d51ff6dd52bfe7e7e04669e0ac678 Mon Sep 17 00:00:00 2001 From: Artem Luzin m Date: Tue, 17 Jun 2025 20:05:59 +0700 Subject: [PATCH] feat --- lib/app/app_context_ext.dart | 3 +- lib/app/theme/app_colors_scheme.dart | 85 +++++++++++++++++--- lib/app/theme/app_theme.dart | 7 +- lib/app/ui_kit/app_snackbar.dart | 23 ++---- lib/features/debug/screens/lang_screen.dart | 1 - lib/features/debug/screens/theme_screen.dart | 1 - 6 files changed, 89 insertions(+), 31 deletions(-) diff --git a/lib/app/app_context_ext.dart b/lib/app/app_context_ext.dart index 7dd0f43..fa36685 100644 --- a/lib/app/app_context_ext.dart +++ b/lib/app/app_context_ext.dart @@ -1,4 +1,5 @@ import 'package:flutter/material.dart'; +import 'package:friflex_starter/app/theme/app_colors_scheme.dart'; import 'package:friflex_starter/app/theme/theme_notifier.dart'; import 'package:friflex_starter/di/di_container.dart'; import 'package:friflex_starter/l10n/gen/app_localizations.dart'; @@ -11,7 +12,7 @@ extension AppContextExt on BuildContext { DiContainer get di => read(); /// Геттер для получения цветовой схемы - ColorScheme get colors => Theme.of(this).colorScheme; + AppColors get colors => Theme.of(this).extension()!; /// Геттер для получения темы ThemeNotifier get theme => read(); diff --git a/lib/app/theme/app_colors_scheme.dart b/lib/app/theme/app_colors_scheme.dart index 3a968fe..733177f 100644 --- a/lib/app/theme/app_colors_scheme.dart +++ b/lib/app/theme/app_colors_scheme.dart @@ -1,18 +1,83 @@ +import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; +/// {@template app_colors} /// Класс, реализующий расширение для добавления токенов в цветовую схему -extension AppColorsScheme on ColorScheme { - bool get _isDark => brightness == Brightness.dark; +/// {@endtemplate} +class AppColors extends ThemeExtension with DiagnosticableTreeMixin { + /// {@macro app_colors} + /// + /// Принимает: + /// + /// * [testColor] - цвет тестового текста + /// * [errorSnackbarBackground] - цвет фона снекбара ошибки + /// * [successSnackbarBackground] - цвет фона снекбара успеха + /// * [infoSnackbarBackground] - цвет фона снекбара информации + const AppColors({ + required this.testColor, + required this.errorSnackbarBackground, + required this.successSnackbarBackground, + required this.infoSnackbarBackground, + }); - // Тестовый цвет - Color get testColor => _isDark ? Colors.green : Colors.red; + /// Цвет тестового текста + final Color testColor; - /// Цвет заднего фона снекбара с ошибкой - Color get errorSnackbarBackground => const Color(0xFFD24720); + /// Цвет фона снекбара ошибки + final Color errorSnackbarBackground; - /// Цвет заднего фона снекбара с успехом - Color get successSnackbarBackground => const Color(0xFF6FB62C); + /// Цвет фона снекбара успеха + final Color successSnackbarBackground; - /// Цвет заднего фона снекбара с информацией - Color get infoSnackbarBackground => const Color.fromARGB(255, 220, 108, 77); + /// Цвет фона снекбара информации + final Color infoSnackbarBackground; + + /// Цвета светлой темы + static final AppColors light = AppColors( + testColor: Colors.red, + errorSnackbarBackground: const Color(0xFFD24720), + successSnackbarBackground: const Color(0xFF6FB62C), + infoSnackbarBackground: const Color.fromARGB(255, 220, 108, 77), + ); + + /// Цвета тёмной темы + static final AppColors dark = AppColors( + testColor: Colors.red, + errorSnackbarBackground: const Color(0xFFD24720), + successSnackbarBackground: const Color(0xFF6FB62C), + infoSnackbarBackground: const Color.fromARGB(255, 220, 108, 77), + ); + + @override + ThemeExtension copyWith({ + Color? testColor, + Color? errorSnackbarBackground, + Color? successSnackbarBackground, + Color? infoSnackbarBackground, + }) => AppColors( + testColor: testColor ?? this.testColor, + errorSnackbarBackground: errorSnackbarBackground ?? this.errorSnackbarBackground, + successSnackbarBackground: successSnackbarBackground ?? this.successSnackbarBackground, + infoSnackbarBackground: infoSnackbarBackground ?? this.infoSnackbarBackground, + ); + + @override + ThemeExtension lerp(covariant ThemeExtension? other, double t) { + if (other is! AppColors) return this; + + return AppColors( + testColor: Color.lerp(testColor, other.testColor, t)!, + errorSnackbarBackground: Color.lerp( + errorSnackbarBackground, + other.errorSnackbarBackground, + t, + )!, + successSnackbarBackground: Color.lerp( + successSnackbarBackground, + other.successSnackbarBackground, + t, + )!, + infoSnackbarBackground: Color.lerp(infoSnackbarBackground, other.infoSnackbarBackground, t)!, + ); + } } diff --git a/lib/app/theme/app_theme.dart b/lib/app/theme/app_theme.dart index 4a88777..2bf9360 100644 --- a/lib/app/theme/app_theme.dart +++ b/lib/app/theme/app_theme.dart @@ -1,10 +1,13 @@ import 'package:flutter/material.dart'; +import 'package:friflex_starter/app/theme/app_colors_scheme.dart'; /// Класс для конфигурации светлой/темной темы приложения abstract class AppTheme { /// Геттер для получения светлой темы - static ThemeData get light => ThemeData.light(); + static ThemeData get light => + ThemeData.light().copyWith(extensions: >[AppColors.light]); /// Геттер для получения темной темы - static ThemeData get dark => ThemeData.dark(); + static ThemeData get dark => + ThemeData.dark().copyWith(extensions: >[AppColors.dark]); } diff --git a/lib/app/ui_kit/app_snackbar.dart b/lib/app/ui_kit/app_snackbar.dart index 82dc0e4..bd3a343 100644 --- a/lib/app/ui_kit/app_snackbar.dart +++ b/lib/app/ui_kit/app_snackbar.dart @@ -2,7 +2,6 @@ import 'dart:async'; import 'package:flutter/material.dart'; import 'package:friflex_starter/app/app_context_ext.dart'; -import 'package:friflex_starter/app/theme/app_colors_scheme.dart'; import 'package:friflex_starter/app/ui_kit/app_box.dart'; /// {@template app_snackbar} @@ -140,8 +139,7 @@ class AppSnackBar extends StatefulWidget { } } -class _AppSnackBarState extends State - with SingleTickerProviderStateMixin { +class _AppSnackBarState extends State with SingleTickerProviderStateMixin { late AnimationController _animationController; late Animation _slideAnimation; Timer? _dismissTimer; @@ -176,10 +174,10 @@ class _AppSnackBarState extends State // Конечная позиция снекбара - 15 пикселей ниже верхнего отступа final endPosition = topPadding + 15; // Создание анимации с использованием Tween - _slideAnimation = Tween(begin: startPosition, end: endPosition) - .animate( - CurvedAnimation(parent: _animationController, curve: Curves.easeOut), - ); + _slideAnimation = Tween( + begin: startPosition, + end: endPosition, + ).animate(CurvedAnimation(parent: _animationController, curve: Curves.easeOut)); _animationController.forward(); } @@ -233,10 +231,7 @@ class _AppSnackBarState extends State color: _getBackgroundColor(widget.type), borderRadius: BorderRadius.circular(16), ), - padding: const EdgeInsets.symmetric( - vertical: 12, - horizontal: 16, - ), + padding: const EdgeInsets.symmetric(vertical: 12, horizontal: 16), child: Row( children: [ _Icon(type: widget.type), @@ -289,11 +284,7 @@ class _Icon extends StatelessWidget { @override Widget build(BuildContext context) { return switch (type) { - TypeSnackBar.success => Icon( - Icons.check_circle, - color: Colors.white, - size: 32, - ), + TypeSnackBar.success => Icon(Icons.check_circle, color: Colors.white, size: 32), TypeSnackBar.error => Icon(Icons.error, color: Colors.white, size: 32), TypeSnackBar.info => Icon(Icons.info, color: Colors.white, size: 32), }; diff --git a/lib/features/debug/screens/lang_screen.dart b/lib/features/debug/screens/lang_screen.dart index f8f91a0..fe98734 100644 --- a/lib/features/debug/screens/lang_screen.dart +++ b/lib/features/debug/screens/lang_screen.dart @@ -1,6 +1,5 @@ import 'package:flutter/material.dart'; import 'package:friflex_starter/app/app_context_ext.dart'; -import 'package:friflex_starter/app/theme/app_colors_scheme.dart'; import 'package:friflex_starter/gen/assets.gen.dart'; import 'package:friflex_starter/gen/fonts.gen.dart'; diff --git a/lib/features/debug/screens/theme_screen.dart b/lib/features/debug/screens/theme_screen.dart index a847651..6bbbb6d 100644 --- a/lib/features/debug/screens/theme_screen.dart +++ b/lib/features/debug/screens/theme_screen.dart @@ -1,6 +1,5 @@ import 'package:flutter/material.dart'; import 'package:friflex_starter/app/app_context_ext.dart'; -import 'package:friflex_starter/app/theme/app_colors_scheme.dart'; /// {@template ThemeScreen} /// Экран для отладки темы приложения