Compare commits

...

11 Commits

Author SHA1 Message Date
811ba789ee feat(bloc_layout): add components ids in crud mixin
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-28 14:33:48 +02:00
00d32e3db7 refactor(bloc_layouts): refactored block using the ui layout package, due to breaking changes 2023-08-28 14:20:49 +02:00
7fecc80674 refactor(ui_layouts): Refactored block using the UI components package, introducing breaking changes 2023-08-28 14:20:14 +02:00
244dc38089 refactor(ui_kit): Refactored code using the UI components package, due to breaking changes 2023-08-28 14:19:36 +02:00
18f34bc95c feat(ui_components): marking fields as private since it was accessible from getters 2023-08-28 14:18:15 +02:00
70030ed128 feat(ui_components)!: available same type component usage (#200) 2023-08-25 19:12:58 +02:00
bc57974896 fix(authentication_bloc): upgrade google sign to his major v
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-24 18:13:22 +02:00
251e9b28f0 fix: apply dart format
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-24 18:08:18 +02:00
52d60db85e fix: apply dart fix --apply
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-24 18:07:35 +02:00
68426786ec fix(authentication_bloc): go router version refactoring
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-24 18:06:07 +02:00
cccea8de8c chore: upgrade deps to major versions
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-24 18:00:21 +02:00
115 changed files with 1534 additions and 723 deletions

View File

@ -25,7 +25,7 @@ class AlbumMockDataSourceImpl extends AlbumRemoteDataSource {
id: 1, id: 1,
userId: 1, userId: 1,
title: 'Album 1', title: 'Album 1',
) ),
}; };
@override @override

View File

@ -58,8 +58,8 @@ class PhotosGridThumbnail
bottom: 10, bottom: 10,
right: 10, right: 10,
child: Icon(Icons.favorite), child: Icon(Icons.favorite),
) ),
] ],
], ],
), ),
); );

View File

@ -71,7 +71,8 @@ class App extends StatelessWidget {
if (authState.status != previous?.status) { if (authState.status != previous?.status) {
previous = authState; previous = authState;
// Checking if current path is onboarding or not // Checking if current path is onboarding or not
final isOnboarding = AppRouter.publicRoutes.contains(state.subloc); final isOnboarding =
AppRouter.publicRoutes.contains(state.matchedLocation);
if (authState.status == AuthenticationStatus.unauthenticated) { if (authState.status == AuthenticationStatus.unauthenticated) {
debugPrint('Not logged'); debugPrint('Not logged');
if (!isOnboarding) { if (!isOnboarding) {

View File

@ -30,11 +30,11 @@ dependencies:
flutter: flutter:
sdk: flutter sdk: flutter
go_router: ^5.1.5 go_router: ^10.1.0
firebase_core: ^2.1.1 firebase_core: ^2.1.1
flutter_bloc: ^8.1.1 flutter_bloc: ^8.1.1
firebase_auth: ^4.2.0 firebase_auth: ^4.2.0
google_sign_in: ^5.4.2 google_sign_in: ^6.1.4
get_it: ^7.2.0 get_it: ^7.2.0
wyatt_authentication_bloc: wyatt_authentication_bloc:

View File

@ -33,7 +33,7 @@ abstract class Forms {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
customPasswordValidator ?? const Password.pure(), customPasswordValidator ?? const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
); );
@ -55,7 +55,7 @@ abstract class Forms {
AuthFormField.password, AuthFormField.password,
customPasswordValidator ?? const Password.pure(), customPasswordValidator ?? const Password.pure(),
), ),
...extraSignUpInputs ?? [] ...extraSignUpInputs ?? [],
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
); );
@ -93,7 +93,7 @@ abstract class Forms {
customPasswordValidator ?? const Password.pure(), customPasswordValidator ?? const Password.pure(),
metadata: const FormInputMetadata(isRequired: false), metadata: const FormInputMetadata(isRequired: false),
), ),
...extraEditAccountInputs ?? [] ...extraEditAccountInputs ?? [],
], ],
validationStrategy: const OnlyRequiredInputValidator(), validationStrategy: const OnlyRequiredInputValidator(),
name: AuthFormName.editAccountForm, name: AuthFormName.editAccountForm,

View File

@ -33,7 +33,7 @@ class AuthenticationMockCacheDataSourceImpl<Data>
Future<Account?> getCachedAccount() async { Future<Account?> getCachedAccount() async {
await Future<void>.delayed(const Duration(milliseconds: 200)); await Future<void>.delayed(const Duration(milliseconds: 200));
return null; return null;
} }
@override @override

View File

@ -15,7 +15,7 @@ dependencies:
flutter_bloc: ^8.1.1 flutter_bloc: ^8.1.1
equatable: ^2.0.5 equatable: ^2.0.5
firebase_auth: ^4.2.0 firebase_auth: ^4.2.0
google_sign_in: ^5.4.2 google_sign_in: ^6.1.4
rxdart: ^0.27.7 rxdart: ^0.27.7
wyatt_form_bloc: wyatt_form_bloc:
@ -30,12 +30,12 @@ dependencies:
hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub/ hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub/
version: ^0.0.5 version: ^0.0.5
flutter_secure_storage: ^8.0.0 flutter_secure_storage: ^8.0.0
http: ^0.13.5 http: ^1.1.0
dev_dependencies: dev_dependencies:
flutter_test: { sdk: flutter } flutter_test: { sdk: flutter }
bloc_test: ^9.1.0 bloc_test: ^9.1.0
mocktail: ^0.3.0 mocktail: ^1.0.0
wyatt_analysis: wyatt_analysis:
hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub/ hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub/

View File

@ -46,7 +46,7 @@ void main() {
AuthenticationSession.fromEvent( AuthenticationSession.fromEvent(
SignedInFromCacheEvent(account: account), SignedInFromCacheEvent(account: account),
data: 10, data: 10,
) ),
]), ]),
); );
@ -113,7 +113,7 @@ void main() {
), ),
const EmailVerificationState( const EmailVerificationState(
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -135,7 +135,7 @@ void main() {
const EmailVerificationState( const EmailVerificationState(
errorMessage: 'erreur', errorMessage: 'erreur',
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });
@ -192,7 +192,7 @@ void main() {
const EmailVerificationState( const EmailVerificationState(
isVerified: true, isVerified: true,
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -214,7 +214,7 @@ void main() {
), ),
const EmailVerificationState( const EmailVerificationState(
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -236,7 +236,7 @@ void main() {
const EmailVerificationState( const EmailVerificationState(
errorMessage: 'erreur', errorMessage: 'erreur',
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });

View File

@ -41,7 +41,7 @@ void main() {
final WyattForm form = WyattFormImpl( final WyattForm form = WyattFormImpl(
[ [
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.passwordResetForm, name: AuthFormName.passwordResetForm,
); );
@ -260,7 +260,7 @@ void main() {
name: AuthFormName.passwordResetForm, name: AuthFormName.passwordResetForm,
), ),
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -327,7 +327,7 @@ void main() {
name: AuthFormName.passwordResetForm, name: AuthFormName.passwordResetForm,
), ),
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });

View File

@ -46,7 +46,7 @@ void main() {
final WyattForm form = WyattFormImpl( final WyattForm form = WyattFormImpl(
[ [
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
); );
@ -102,7 +102,7 @@ void main() {
AuthFormField.email, AuthFormField.email,
const Email.dirty(invalidEmailString), const Email.dirty(invalidEmailString),
), ),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -126,7 +126,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -145,7 +145,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -163,7 +163,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -191,7 +191,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(invalidPasswordString), const Password.dirty(invalidPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -215,7 +215,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -234,7 +234,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -252,7 +252,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -287,7 +287,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -312,7 +312,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -331,7 +331,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -364,7 +364,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -383,7 +383,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -401,7 +401,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -417,12 +417,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -448,7 +448,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -467,7 +467,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -485,7 +485,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -501,12 +501,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });
@ -527,7 +527,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -566,7 +566,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -584,7 +584,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -600,12 +600,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -630,7 +630,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -648,7 +648,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
@ -664,12 +664,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
), ),
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });

View File

@ -22,7 +22,7 @@ void main() {
final WyattForm form = WyattFormImpl( final WyattForm form = WyattFormImpl(
[ [
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
); );

View File

@ -46,7 +46,7 @@ void main() {
final WyattForm form = WyattFormImpl( final WyattForm form = WyattFormImpl(
[ [
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
); );
@ -98,7 +98,7 @@ void main() {
AuthFormField.email, AuthFormField.email,
const Email.dirty(invalidEmailString), const Email.dirty(invalidEmailString),
), ),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -122,7 +122,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -141,7 +141,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -159,7 +159,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -187,7 +187,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(invalidPasswordString), const Password.dirty(invalidPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -211,7 +211,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -230,7 +230,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.pure(), const Password.pure(),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -248,7 +248,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -283,7 +283,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -302,7 +302,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -335,7 +335,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -354,7 +354,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -372,7 +372,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -388,12 +388,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
status: FormStatus.submissionSuccess, status: FormStatus.submissionSuccess,
) ),
], ],
); );
@ -419,7 +419,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -438,7 +438,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -456,7 +456,7 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
@ -472,12 +472,12 @@ void main() {
FormInput( FormInput(
AuthFormField.password, AuthFormField.password,
const Password.dirty(validPasswordString), const Password.dirty(validPasswordString),
) ),
], ],
name: AuthFormName.signUpForm, name: AuthFormName.signUpForm,
), ),
status: FormStatus.submissionFailure, status: FormStatus.submissionFailure,
) ),
], ],
); );
}); });
@ -487,7 +487,7 @@ void main() {
FormInput<dynamic, FormInputValidator<dynamic, ValidationError>, FormInput<dynamic, FormInputValidator<dynamic, ValidationError>,
dynamic>>[ dynamic>>[
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
]; ];
final inputsB = < final inputsB = <

View File

@ -22,7 +22,7 @@ void main() {
final WyattForm form = WyattFormImpl( final WyattForm form = WyattFormImpl(
[ [
FormInput(AuthFormField.email, const Email.pure()), FormInput(AuthFormField.email, const Email.pure()),
FormInput(AuthFormField.password, const Password.pure()) FormInput(AuthFormField.password, const Password.pure()),
], ],
name: AuthFormName.signInForm, name: AuthFormName.signInForm,
); );

View File

@ -31,7 +31,7 @@ class ExampleCubit extends Cubit<CrudState> {
'DATA LOADED 1', 'DATA LOADED 1',
'DATA LOADED 2', 'DATA LOADED 2',
'DATA LOADED 3', 'DATA LOADED 3',
'DATA LOADED 4' 'DATA LOADED 4',
]), ]),
); );
await Future<void>.delayed(const Duration(seconds: 1)); await Future<void>.delayed(const Duration(seconds: 1));

View File

@ -5,10 +5,10 @@ import 'package:bloc_layout_example/components/custom_loading_widget.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart'; import 'package:wyatt_ui_components/wyatt_ui_components.dart';
abstract class AppThemeComponent { abstract class AppThemeComponent {
static const ComponentThemeData components = ComponentThemeData.raw( static ComponentThemeData components = ComponentThemeData.raw(
topAppBar: CustomAppBar(), topAppBars: const CustomAppBar().registry(),
bottomNavigationBar: CustomBottomBar(), bottomNavigationBars: const CustomBottomBar().registry(),
loader: CustomLoadingWidget(), loaders: const CustomLoadingWidget().registry(),
error: CustomErrorWidget(), errors: const CustomErrorWidget().registry(),
); );
} }

View File

@ -22,13 +22,17 @@ import 'package:wyatt_ui_components/wyatt_ui_components.dart';
mixin CrudMixin<Cubit extends bloc_base.Cubit<dynamic>, mixin CrudMixin<Cubit extends bloc_base.Cubit<dynamic>,
SuccessState extends CrudSuccess> { SuccessState extends CrudSuccess> {
String? get loaderId => null;
String? get erroId => null;
Widget errorBuilder(BuildContext context, CrudError state) => Widget errorBuilder(BuildContext context, CrudError state) =>
context.components.errorComponent.call( context.components.errorComponent(erroId).call(
message: (state.message != null) ? TextWrapper(state.message!) : null, message:
(state.message != null) ? TextWrapper(state.message!) : null,
); );
Widget loadingBuilder(BuildContext context, CrudLoading state) => Widget loadingBuilder(BuildContext context, CrudLoading state) =>
context.components.loader ?? const SizedBox.shrink(); context.components.loaderComponent(loaderId).call();
Widget initialBuilder(BuildContext context, CrudInitial state) => Widget initialBuilder(BuildContext context, CrudInitial state) =>
const SizedBox.shrink(); const SizedBox.shrink();

View File

@ -24,7 +24,8 @@ abstract class BottomNavigationBarGridLayoutCubitScreenCrudList<
with GridLayoutMixin<SuccessType> { with GridLayoutMixin<SuccessType> {
const BottomNavigationBarGridLayoutCubitScreenCrudList({ const BottomNavigationBarGridLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -26,18 +26,21 @@ abstract class BottomNavigationBarLayoutCubitScreen<
State extends Object> extends CubitScreenBase<Cubit, State> { State extends Object> extends CubitScreenBase<Cubit, State> {
const BottomNavigationBarLayoutCubitScreen({ const BottomNavigationBarLayoutCubitScreen({
this.custom, this.custom,
this.height = 60, this.barId,
this.scaffoldFieldsWrapper,
super.key, super.key,
}); });
final double height; final ComponentCallBack<BottomNavigationBarComponent>? custom;
final BottomNavigationBarComponent? Function(BottomNavigationBarComponent?)? final ScaffoldFieldsWrapper? scaffoldFieldsWrapper;
custom; final String? barId;
@override @override
Widget parent(BuildContext context, Widget child) => Widget parent(BuildContext context, Widget child) =>
BottomNavigationBarLayout( StructuralLayout.withBottomNavBar(
custom: custom, custom: custom,
barId: barId,
scaffoldFieldsWrapper: scaffoldFieldsWrapper,
body: child, body: child,
); );
} }

View File

@ -26,7 +26,8 @@ abstract class BottomNavigationBarLayoutCubitScreenCrud<
with CrudMixin<Cubit, CrudSuccessState> { with CrudMixin<Cubit, CrudSuccessState> {
const BottomNavigationBarLayoutCubitScreenCrud({ const BottomNavigationBarLayoutCubitScreenCrud({
super.custom, super.custom,
super.height, super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -24,7 +24,8 @@ abstract class BottomNavigationBarLayoutCubitScreenCrudItem<
CrudLoaded<SuccessType>> { CrudLoaded<SuccessType>> {
const BottomNavigationBarLayoutCubitScreenCrudItem({ const BottomNavigationBarLayoutCubitScreenCrudItem({
super.custom, super.custom,
super.height = 60, super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -24,7 +24,8 @@ abstract class BottomNavigationBarLayoutCubitScreenCrudList<
CrudListLoaded<SuccessType>> { CrudListLoaded<SuccessType>> {
const BottomNavigationBarLayoutCubitScreenCrudList({ const BottomNavigationBarLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -20,5 +20,7 @@ import 'package:wyatt_crud_bloc/wyatt_crud_bloc.dart';
abstract class CubitScreenCrudItemBase<Cubit extends bloc_base.Cubit<CrudState>, abstract class CubitScreenCrudItemBase<Cubit extends bloc_base.Cubit<CrudState>,
T extends Object?> extends CubitScreenCrudBase<Cubit, CrudLoaded<T>> { T extends Object?> extends CubitScreenCrudBase<Cubit, CrudLoaded<T>> {
const CubitScreenCrudItemBase({super.key}); const CubitScreenCrudItemBase({
super.key,
});
} }

View File

@ -25,7 +25,11 @@ abstract class FrameLayoutGridCubitScreenCrudList<
const FrameLayoutGridCubitScreenCrudList({ const FrameLayoutGridCubitScreenCrudList({
super.customAppBar, super.customAppBar,
super.customBottomNavBar, super.customBottomNavBar,
super.height = 60, super.floatingActionButtonId,
super.height,
super.appBarId,
super.bottomNavBarId,
super.customFloatingActionButton,
super.scaffoldFieldsWrapper, super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -26,21 +26,34 @@ abstract class FrameLayoutCubitScreen<Cubit extends bloc_base.Cubit<State>,
const FrameLayoutCubitScreen({ const FrameLayoutCubitScreen({
this.customAppBar, this.customAppBar,
this.customBottomNavBar, this.customBottomNavBar,
this.customFloatingActionButton,
this.appBarId,
this.bottomNavBarId,
this.floatingActionButtonId,
this.scaffoldFieldsWrapper, this.scaffoldFieldsWrapper,
this.height = 60, this.height = 60,
super.key, super.key,
}); });
final TopAppBarComponent? Function(TopAppBarComponent?)? customAppBar; final ComponentCallBack<TopAppBarComponent>? customAppBar;
final BottomNavigationBarComponent? Function(BottomNavigationBarComponent?)? final ComponentCallBack<BottomNavigationBarComponent>? customBottomNavBar;
customBottomNavBar; final ComponentCallBack<FloatingActionButtonComponent>?
customFloatingActionButton;
final String? appBarId;
final String? bottomNavBarId;
final String? floatingActionButtonId;
final double height; final double height;
final ScaffoldFieldsWrapper? scaffoldFieldsWrapper; final ScaffoldFieldsWrapper? scaffoldFieldsWrapper;
@override @override
Widget parent(BuildContext context, Widget child) => FrameLayout( Widget parent(BuildContext context, Widget child) =>
StructuralLayout.withFrame(
customAppBar: customAppBar, customAppBar: customAppBar,
customBottomNavBar: customBottomNavBar, customBottomNavBar: customBottomNavBar,
customFloatingActionButton: customFloatingActionButton,
appBarId: appBarId,
bottomNavBarId: bottomNavBarId,
floatingActionButtonId: floatingActionButtonId,
height: height, height: height,
scaffoldFieldsWrapper: scaffoldFieldsWrapper, scaffoldFieldsWrapper: scaffoldFieldsWrapper,
body: child, body: child,

View File

@ -27,9 +27,13 @@ abstract class FrameLayoutCubitScreenCrud<
const FrameLayoutCubitScreenCrud({ const FrameLayoutCubitScreenCrud({
super.customAppBar, super.customAppBar,
super.customBottomNavBar, super.customBottomNavBar,
super.floatingActionButtonId,
super.height, super.height,
super.key, super.appBarId,
super.bottomNavBarId,
super.customFloatingActionButton,
super.scaffoldFieldsWrapper, super.scaffoldFieldsWrapper,
super.key,
}); });
@override @override

View File

@ -24,7 +24,11 @@ abstract class FrameLayoutCubitScreenCrudItem<
const FrameLayoutCubitScreenCrudItem({ const FrameLayoutCubitScreenCrudItem({
super.customAppBar, super.customAppBar,
super.customBottomNavBar, super.customBottomNavBar,
super.height = 60, super.floatingActionButtonId,
super.height,
super.appBarId,
super.bottomNavBarId,
super.customFloatingActionButton,
super.scaffoldFieldsWrapper, super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -24,7 +24,11 @@ abstract class FrameLayoutCubitScreenCrudList<
const FrameLayoutCubitScreenCrudList({ const FrameLayoutCubitScreenCrudList({
super.customAppBar, super.customAppBar,
super.customBottomNavBar, super.customBottomNavBar,
super.height = 60, super.floatingActionButtonId,
super.height,
super.appBarId,
super.bottomNavBarId,
super.customFloatingActionButton,
super.scaffoldFieldsWrapper, super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -25,6 +25,8 @@ abstract class TopAppBarGridLayoutCubitScreenCrudList<
const TopAppBarGridLayoutCubitScreenCrudList({ const TopAppBarGridLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -25,17 +25,23 @@ abstract class TopAppBarLayoutCubitScreen<Cubit extends bloc_base.Cubit<State>,
State extends Object> extends CubitScreenBase<Cubit, State> { State extends Object> extends CubitScreenBase<Cubit, State> {
const TopAppBarLayoutCubitScreen({ const TopAppBarLayoutCubitScreen({
this.custom, this.custom,
this.barId,
this.scaffoldFieldsWrapper,
this.height = 60, this.height = 60,
super.key, super.key,
}); });
final double height; final double height;
final TopAppBarComponent? Function(TopAppBarComponent?)? custom; final ComponentCallBack<TopAppBarComponent>? custom;
final String? barId;
final ScaffoldFieldsWrapper? scaffoldFieldsWrapper;
@override @override
Widget parent(BuildContext context, Widget child) => TopAppBarLayout( Widget parent(BuildContext context, Widget child) => TopAppBarLayout(
height: height, height: height,
custom: custom, custom: custom,
barId: barId,
scaffoldFieldsWrapper: scaffoldFieldsWrapper,
body: child, body: child,
); );
} }

View File

@ -27,6 +27,8 @@ abstract class TopAppBarLayoutCubitScreenCrud<
const TopAppBarLayoutCubitScreenCrud({ const TopAppBarLayoutCubitScreenCrud({
super.custom, super.custom,
super.height, super.height,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -24,6 +24,8 @@ abstract class TopAppBarLayoutCubitScreenCrudItem<
const TopAppBarLayoutCubitScreenCrudItem({ const TopAppBarLayoutCubitScreenCrudItem({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -24,6 +24,8 @@ abstract class TopAppBarLayoutCubitScreenCrudList<
const TopAppBarLayoutCubitScreenCrudList({ const TopAppBarLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -25,6 +25,8 @@ abstract class TopNavigationBarGridLayoutCubitScreenCrudList<
const TopNavigationBarGridLayoutCubitScreenCrudList({ const TopNavigationBarGridLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -27,16 +27,23 @@ abstract class TopNavigationBarLayoutCubitScreen<
const TopNavigationBarLayoutCubitScreen({ const TopNavigationBarLayoutCubitScreen({
this.custom, this.custom,
this.height = 60, this.height = 60,
this.barId,
this.scaffoldFieldsWrapper,
super.key, super.key,
}); });
final double height; final double height;
final TopNavigationBarComponent? Function(TopNavigationBarComponent?)? custom; final ComponentCallBack<TopNavigationBarComponent>? custom;
final String? barId;
final ScaffoldFieldsWrapper? scaffoldFieldsWrapper;
@override @override
Widget parent(BuildContext context, Widget child) => TopNavigationBarLayout( Widget parent(BuildContext context, Widget child) =>
height: height, StructuralLayout.withTopNavigationBar(
barId: barId,
custom: custom, custom: custom,
height: height,
scaffoldFieldsWrapper: scaffoldFieldsWrapper,
body: child, body: child,
); );
} }

View File

@ -27,6 +27,8 @@ abstract class TopNavigationBarLayoutCubitScreenCrud<
const TopNavigationBarLayoutCubitScreenCrud({ const TopNavigationBarLayoutCubitScreenCrud({
super.custom, super.custom,
super.height, super.height,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });

View File

@ -25,6 +25,8 @@ abstract class TopNavigationBarLayoutCubitScreenCrudItem<
const TopNavigationBarLayoutCubitScreenCrudItem({ const TopNavigationBarLayoutCubitScreenCrudItem({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -25,6 +25,8 @@ abstract class TopNavigationBarLayoutCubitScreenCrudList<
const TopNavigationBarLayoutCubitScreenCrudList({ const TopNavigationBarLayoutCubitScreenCrudList({
super.custom, super.custom,
super.height = 60, super.height = 60,
super.barId,
super.scaffoldFieldsWrapper,
super.key, super.key,
}); });
} }

View File

@ -53,7 +53,8 @@ class DefaultFirebaseOptions {
messagingSenderId: '100151285458', messagingSenderId: '100151285458',
projectId: 'wyatt-notification-example', projectId: 'wyatt-notification-example',
storageBucket: 'wyatt-notification-example.appspot.com', storageBucket: 'wyatt-notification-example.appspot.com',
iosClientId: '100151285458-a9notq1k1padf0vk9ove8ll3amjgi7mn.apps.googleusercontent.com', iosClientId:
'100151285458-a9notq1k1padf0vk9ove8ll3amjgi7mn.apps.googleusercontent.com',
iosBundleId: 'com.example.notificationBlocExample', iosBundleId: 'com.example.notificationBlocExample',
); );
} }

View File

@ -22,11 +22,10 @@ import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_me
import 'package:wyatt_type_utils/wyatt_type_utils.dart'; import 'package:wyatt_type_utils/wyatt_type_utils.dart';
class CloudMessagingRepositoryImpl extends CloudMessagingRepository { class CloudMessagingRepositoryImpl extends CloudMessagingRepository {
final CloudMessagingRemoteDataSource _notificationRemoteDataSource;
CloudMessagingRepositoryImpl({ CloudMessagingRepositoryImpl({
required CloudMessagingRemoteDataSource notificationRemoteDataSource, required CloudMessagingRemoteDataSource notificationRemoteDataSource,
}) : _notificationRemoteDataSource = notificationRemoteDataSource; }) : _notificationRemoteDataSource = notificationRemoteDataSource;
final CloudMessagingRemoteDataSource _notificationRemoteDataSource;
@override @override
FutureOrResult<String?> getToken() => Result.tryCatchAsync( FutureOrResult<String?> getToken() => Result.tryCatchAsync(

View File

@ -18,11 +18,10 @@ import 'package:wyatt_architecture/wyatt_architecture.dart';
import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart'; import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart';
class GetCloudMessagingTokenUseCase extends AsyncUseCase<void, String?> { class GetCloudMessagingTokenUseCase extends AsyncUseCase<void, String?> {
final CloudMessagingRepository _notificationRepository;
GetCloudMessagingTokenUseCase({ GetCloudMessagingTokenUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOrResult<String?> execute(void params) => FutureOrResult<String?> execute(void params) =>

View File

@ -18,11 +18,10 @@ import 'package:wyatt_architecture/wyatt_architecture.dart';
import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart'; import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart';
class InitCloudmessagingUseCase extends AsyncUseCase<NoParam, void> { class InitCloudmessagingUseCase extends AsyncUseCase<NoParam, void> {
final CloudMessagingRepository _notificationRepository;
InitCloudmessagingUseCase({ InitCloudmessagingUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOrResult<void> execute(NoParam? params) => FutureOrResult<void> execute(NoParam? params) =>
_notificationRepository.init(); _notificationRepository.init();

View File

@ -25,11 +25,10 @@ import 'package:wyatt_type_utils/wyatt_type_utils.dart';
class ListenNotificationUseCase class ListenNotificationUseCase
extends StreamUseCase<NoParam, RemoteNotification> { extends StreamUseCase<NoParam, RemoteNotification> {
final CloudMessagingRepository _notificationRepository;
ListenNotificationUseCase({ ListenNotificationUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOrResult<Stream<RemoteNotification>> execute(NoParam? params) async { FutureOrResult<Stream<RemoteNotification>> execute(NoParam? params) async {
Stream<RemoteNotification>? notificationStream; Stream<RemoteNotification>? notificationStream;

View File

@ -18,11 +18,10 @@ import 'package:wyatt_architecture/wyatt_architecture.dart';
import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart'; import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart';
class RequestCloudMessagingPermissionUseCase extends AsyncUseCase<void, void> { class RequestCloudMessagingPermissionUseCase extends AsyncUseCase<void, void> {
final CloudMessagingRepository _notificationRepository;
RequestCloudMessagingPermissionUseCase({ RequestCloudMessagingPermissionUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOrResult<void> execute(void params) => FutureOrResult<void> execute(void params) =>

View File

@ -20,11 +20,10 @@ import 'package:wyatt_architecture/wyatt_architecture.dart';
import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart'; import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_messaging_repository.dart';
class SubscribeToNotificationTopicUseCase extends AsyncUseCase<String, void> { class SubscribeToNotificationTopicUseCase extends AsyncUseCase<String, void> {
final CloudMessagingRepository _notificationRepository;
SubscribeToNotificationTopicUseCase({ SubscribeToNotificationTopicUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOr<void> onStart(String? params) { FutureOr<void> onStart(String? params) {

View File

@ -21,11 +21,10 @@ import 'package:wyatt_cloud_messaging_bloc_base/src/domain/repositories/cloud_me
class UnsubscribeFromNotificationTopicUseCase class UnsubscribeFromNotificationTopicUseCase
extends AsyncUseCase<String, void> { extends AsyncUseCase<String, void> {
final CloudMessagingRepository _notificationRepository;
UnsubscribeFromNotificationTopicUseCase({ UnsubscribeFromNotificationTopicUseCase({
required CloudMessagingRepository notificationRepository, required CloudMessagingRepository notificationRepository,
}) : _notificationRepository = notificationRepository; }) : _notificationRepository = notificationRepository;
final CloudMessagingRepository _notificationRepository;
@override @override
FutureOr<void> onStart(String? params) { FutureOr<void> onStart(String? params) {

View File

@ -30,11 +30,6 @@ part 'cloud_messaging_state.dart';
typedef OnNotification = void Function(RemoteNotification); typedef OnNotification = void Function(RemoteNotification);
class CloudMessagingCubit extends Cubit<CloudmessagingState> { class CloudMessagingCubit extends Cubit<CloudmessagingState> {
final ListenNotificationUseCase _listenNotification;
final SubscribeToNotificationTopicUseCase? _subscribe;
final UnsubscribeFromNotificationTopicUseCase? _unsubscribe;
final OnNotification? handleNotification;
CloudMessagingCubit({ CloudMessagingCubit({
required ListenNotificationUseCase listenNotification, required ListenNotificationUseCase listenNotification,
SubscribeToNotificationTopicUseCase? subscribe, SubscribeToNotificationTopicUseCase? subscribe,
@ -44,6 +39,11 @@ class CloudMessagingCubit extends Cubit<CloudmessagingState> {
_subscribe = subscribe, _subscribe = subscribe,
_unsubscribe = unsubscribe, _unsubscribe = unsubscribe,
super(const CloudmessagingState()); super(const CloudmessagingState());
final ListenNotificationUseCase _listenNotification;
final SubscribeToNotificationTopicUseCase? _subscribe;
final UnsubscribeFromNotificationTopicUseCase? _unsubscribe;
final OnNotification? handleNotification;
Future<void> listenNotification() async { Future<void> listenNotification() async {
final notificaitons = await _listenNotification.execute(const NoParam()); final notificaitons = await _listenNotification.execute(const NoParam());

View File

@ -17,9 +17,8 @@
part of 'cloud_messaging_cubit.dart'; part of 'cloud_messaging_cubit.dart';
class CloudmessagingState extends Equatable { class CloudmessagingState extends Equatable {
final RemoteNotification? remoteNotification;
const CloudmessagingState([this.remoteNotification]); const CloudmessagingState([this.remoteNotification]);
final RemoteNotification? remoteNotification;
@override @override
List<Object?> get props => [remoteNotification]; List<Object?> get props => [remoteNotification];

View File

@ -11,7 +11,7 @@ environment:
dependencies: dependencies:
build: ^2.3.1 build: ^2.3.1
source_gen: ^1.2.7 source_gen: ^1.2.7
analyzer: ^5.4.0 analyzer: ^6.2.0
wyatt_component_copy_with_extension: wyatt_component_copy_with_extension:
hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub

View File

@ -33,8 +33,7 @@ class CrudFirestoreDataSourceImpl<Model extends ObjectModel, Entity>
required Model Function( required Model Function(
DocumentSnapshot<Map<String, dynamic>>, DocumentSnapshot<Map<String, dynamic>>,
SnapshotOptions?, SnapshotOptions?,
) ) fromFirestore,
fromFirestore,
/// The function that converts a [Model] to a [Map<String, Object?>]. /// The function that converts a [Model] to a [Map<String, Object?>].
required Map<String, Object?> Function(Model, SetOptions?) toFirestore, required Map<String, Object?> Function(Model, SetOptions?) toFirestore,

View File

@ -289,7 +289,7 @@ abstract class CrudAdvancedCubit<Model extends ObjectModel>
WhereQueryType.whereIn, WhereQueryType.whereIn,
'id', 'id',
ids, ids,
) ),
]); ]);
if (result.isOk) { if (result.isOk) {
return CrudListLoaded<Model?>(result.ok ?? []); return CrudListLoaded<Model?>(result.ok ?? []);

View File

@ -353,7 +353,7 @@ abstract class CrudCubit<Model extends ObjectModel> extends CrudBaseCubit {
WhereQueryType.whereIn, WhereQueryType.whereIn,
'id', 'id',
ids, ids,
) ),
]); ]);
if (result.isOk) { if (result.isOk) {
return CrudListLoaded<Model?>(result.ok ?? []); return CrudListLoaded<Model?>(result.ok ?? []);

View File

@ -26,9 +26,8 @@ class FormDifference extends FormOperation {
@override @override
WyattForm call(WyattForm a, WyattForm b) { WyattForm call(WyattForm a, WyattForm b) {
final inputs = < final inputs = <FormInput<dynamic,
FormInput<dynamic, FormInputValidator<dynamic, ValidationError>, FormInputValidator<dynamic, ValidationError>, dynamic>>[];
dynamic>>[];
for (final i in a.inputs) { for (final i in a.inputs) {
if (!b.containsKey(i.key)) { if (!b.containsKey(i.key)) {

View File

@ -26,9 +26,8 @@ class FormIntersection extends FormOperation {
@override @override
WyattForm call(WyattForm a, WyattForm b) { WyattForm call(WyattForm a, WyattForm b) {
final inputs = < final inputs = <FormInput<dynamic,
FormInput<dynamic, FormInputValidator<dynamic, ValidationError>, FormInputValidator<dynamic, ValidationError>, dynamic>>[];
dynamic>>[];
for (final i in a.inputs) { for (final i in a.inputs) {
if (b.containsKey(i.key)) { if (b.containsKey(i.key)) {

View File

@ -26,9 +26,8 @@ class FormUnion extends FormOperation {
@override @override
WyattForm call(WyattForm a, WyattForm b) { WyattForm call(WyattForm a, WyattForm b) {
final inputs = < final inputs = <FormInput<dynamic,
FormInput<dynamic, FormInputValidator<dynamic, ValidationError>, FormInputValidator<dynamic, ValidationError>, dynamic>>[];
dynamic>>[];
for (final i in a.inputs) { for (final i in a.inputs) {
inputs.add(i); inputs.add(i);

View File

@ -46,7 +46,7 @@ abstract class Convert {
map.forEach( map.forEach(
(key, value) => pairs.add([ (key, value) => pairs.add([
Uri.encodeQueryComponent(key, encoding: encoding ?? utf8), Uri.encodeQueryComponent(key, encoding: encoding ?? utf8),
Uri.encodeQueryComponent(value, encoding: encoding ?? utf8) Uri.encodeQueryComponent(value, encoding: encoding ?? utf8),
]), ]),
); );
return pairs.map((pair) => '${pair[0]}=${pair[1]}').join('&'); return pairs.map((pair) => '${pair[0]}=${pair[1]}').join('&');

View File

@ -10,7 +10,7 @@ environment:
dependencies: dependencies:
crypto: ^3.0.2 crypto: ^3.0.2
http: ^0.13.4 http: ^1.1.0
dev_dependencies: dev_dependencies:
wyatt_analysis: wyatt_analysis:

View File

@ -44,7 +44,7 @@ class App extends StatelessWidget {
), ),
), ),
GlobalMaterialLocalizations.delegate, GlobalMaterialLocalizations.delegate,
GlobalWidgetsLocalizations.delegate GlobalWidgetsLocalizations.delegate,
], ],
home: Scaffold( home: Scaffold(
appBar: AppBar( appBar: AppBar(

View File

@ -93,7 +93,7 @@ class I18nFileParser extends Parser<String, String> {
String selectToString(Select token) { String selectToString(Select token) {
final Map<Object, String> cases = { final Map<Object, String> cases = {
for (var e in token.options.map( for (final e in token.options.map(
(o) => MapEntry( (o) => MapEntry(
o.name, o.name,
o.value.map(parsedElementToString).join(), o.value.map(parsedElementToString).join(),

View File

@ -27,7 +27,7 @@ environment:
# the latest version available on pub.dev. To see which dependencies have newer # the latest version available on pub.dev. To see which dependencies have newer
# versions available, run `flutter pub outdated`. # versions available, run `flutter pub outdated`.
dependencies: dependencies:
http: ^0.13.4 http: ^1.1.0
wyatt_type_utils: wyatt_type_utils:
path: "../" path: "../"

View File

@ -43,7 +43,23 @@ First create all your custom components in `domain/entities` folder. For exemple
> Run `flutter pub run build_runner build` to generate your components. > Run `flutter pub run build_runner build` to generate your components.
Then, add your components to `ComponentThemeData` class. Then, add your components to `ComponentThemeData` class. You can utilize multiple components of the same type, such as having multiple top app bars or distinct cards. However, it's necessary to distinguish them using identifiers. Extensions are provided to make your life easier. Note that it's not obligatory to assign an identifier to a component if there's only one of its kind. Here's an example:
```dart
class AppThemeComponent {
static ComponentThemeData get components => ComponentThemeData.raw(
topAppBars: const {
'root': CustomRootAppBar(),
'second': CustomSecondAppBar(),
}.registry(),
bottomNavigationBars: const CustomBottomNavigationBar().registry(),
errors: const CustomErrorWidget().registry(),
loaders: const CustomLoaderWidget().registry(),
);
}
```
I've rephrased the sentence while maintaining the original meaning and intent.
### Provider ### Provider
@ -82,21 +98,28 @@ context.components,
For example : For example :
```dart ```dart
@override context.components.topAppBarComponent()(),
Widget build(BuildContext context) => Scaffold(
appBar: context.components.appBar,
body: ...
)
``` ```
If you need specific settings, or pass parameters to your component, call `copyWith.call` method. or
```dart ```dart
@override appBar: context.components.topAppBarComponent().call(),
Widget build(BuildContext context) => Scaffold( ```
appBar: context.components.appBar.copyWith.call({title: 'New Title !'}),
body: ... If you require specific settings or want to pass parameters to your component, simply provide them when you call your component.
)
```dart
context.components.loaderComponent()(
colors: const MultiColor.single(Colors.green),
),
```
And if you have only one parameter to modify, you can directly call it as shown below:
```dart
context.components.loaderComponent().
colors(const MultiColor.single(Colors.green)),
``` ```
## Default implementation ## Default implementation

View File

@ -1,14 +1,18 @@
import 'package:wyatt_ui_components/wyatt_ui_components.dart'; import 'package:wyatt_ui_components/wyatt_ui_components.dart';
import 'package:wyatt_ui_components_example/components/custom_app_bar.dart';
import 'package:wyatt_ui_components_example/components/custom_bottom_bar.dart'; import 'package:wyatt_ui_components_example/components/custom_bottom_bar.dart';
import 'package:wyatt_ui_components_example/components/custom_error_widget.dart'; import 'package:wyatt_ui_components_example/components/custom_error_widget.dart';
import 'package:wyatt_ui_components_example/components/custom_loader_widget.dart'; import 'package:wyatt_ui_components_example/components/custom_loader_widget.dart';
import 'package:wyatt_ui_components_example/components/custom_root_app_bar.dart';
import 'package:wyatt_ui_components_example/components/custom_second_app_bar.dart';
class AppThemeComponent { class AppThemeComponent {
static ComponentThemeData get components => const ComponentThemeData.raw( static ComponentThemeData get components => ComponentThemeData.raw(
topAppBar: CustomAppBar(), topAppBars: const {
bottomNavigationBar: CustomBottomNavigationBar(), 'root': CustomRootAppBar(),
error: CustomErrorWidget(), 'second': CustomSecondAppBar(),
loader: CustomLoaderWidget(), }.registry(),
bottomNavigationBars: const CustomBottomNavigationBar().registry(),
errors: const CustomErrorWidget().registry(),
loaders: const CustomLoaderWidget().registry(),
); );
} }

View File

@ -1,99 +0,0 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'custom_app_bar.dart';
// **************************************************************************
// ComponentCopyWithGenerator
// **************************************************************************
class $CustomAppBarCWProxyImpl implements $TopAppBarComponentCWProxy {
const $CustomAppBarCWProxyImpl(this._value);
final CustomAppBar _value;
@override
CustomAppBar title(TextWrapper? title) => this(title: title);
@override
CustomAppBar centerTitle(bool? centerTitle) => this(centerTitle: centerTitle);
@override
CustomAppBar shape(ShapeBorder? shape) => this(shape: shape);
@override
CustomAppBar systemOverlayStyle(SystemUiOverlayStyle? systemOverlayStyle) =>
this(systemOverlayStyle: systemOverlayStyle);
@override
CustomAppBar automaticallyImplyLeading(bool? automaticallyImplyLeading) =>
this(automaticallyImplyLeading: automaticallyImplyLeading);
@override
CustomAppBar flexibleSpace(Widget? flexibleSpace) =>
this(flexibleSpace: flexibleSpace);
@override
CustomAppBar bottom(PreferredSizeWidget? bottom) => this(bottom: bottom);
@override
CustomAppBar elevation(double? elevation) => this(elevation: elevation);
@override
CustomAppBar scrolledUnderElevation(double? scrolledUnderElevation) =>
this(scrolledUnderElevation: scrolledUnderElevation);
@override
CustomAppBar shadowColor(Color? shadowColor) =>
this(shadowColor: shadowColor);
@override
CustomAppBar surfaceTintColor(Color? surfaceTintColor) =>
this(surfaceTintColor: surfaceTintColor);
@override
CustomAppBar backgroundColor(MultiColor? backgroundColor) =>
this(backgroundColor: backgroundColor);
@override
CustomAppBar iconTheme(IconThemeData? iconTheme) =>
this(iconTheme: iconTheme);
@override
CustomAppBar primary(bool? primary) => this(primary: primary);
@override
CustomAppBar excludeHeaderSemantics(bool? excludeHeaderSemantics) =>
this(excludeHeaderSemantics: excludeHeaderSemantics);
@override
CustomAppBar toolbarHeight(double? toolbarHeight) =>
this(toolbarHeight: toolbarHeight);
@override
CustomAppBar leadingWidth(double? leadingWidth) =>
this(leadingWidth: leadingWidth);
@override
CustomAppBar leading(Widget? leading) => this(leading: leading);
@override
CustomAppBar actions(List<Widget>? actions) => this(actions: actions);
@override
CustomAppBar expandedWidget(List<Widget>? expandedWidget) =>
this(expandedWidget: expandedWidget);
@override
CustomAppBar key(Key? key) => this(key: key);
@override
CustomAppBar call({
TextWrapper? title,
bool? centerTitle,
ShapeBorder? shape,
SystemUiOverlayStyle? systemOverlayStyle,
bool? automaticallyImplyLeading,
Widget? flexibleSpace,
PreferredSizeWidget? bottom,
double? elevation,
double? scrolledUnderElevation,
Color? shadowColor,
Color? surfaceTintColor,
MultiColor? backgroundColor,
IconThemeData? iconTheme,
bool? primary,
bool? excludeHeaderSemantics,
double? toolbarHeight,
double? leadingWidth,
Widget? leading,
List<Widget>? actions,
List<Widget>? expandedWidget,
Key? key,
}) =>
CustomAppBar(
title: title ?? _value.title,
key: key ?? _value.key,
);
}
mixin $CustomAppBarCWMixin on Component {
$TopAppBarComponentCWProxy get copyWith =>
$CustomAppBarCWProxyImpl(this as CustomAppBar);
}

View File

@ -1,12 +1,14 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart'; import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart'; import 'package:wyatt_ui_components/wyatt_ui_components.dart';
part 'custom_app_bar.g.dart'; part 'custom_root_app_bar.g.dart';
@ComponentCopyWithExtension() @ComponentCopyWithExtension()
class CustomAppBar extends TopAppBarComponent with $CustomAppBarCWMixin { class CustomRootAppBar extends TopAppBarComponent
const CustomAppBar({super.title, super.key}); with $CustomRootAppBarCWMixin {
const CustomRootAppBar({super.title, super.key});
@override @override
Widget build(BuildContext context) => AppBar( Widget build(BuildContext context) => AppBar(

View File

@ -0,0 +1,101 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'custom_root_app_bar.dart';
// **************************************************************************
// ComponentCopyWithGenerator
// **************************************************************************
class $CustomRootAppBarCWProxyImpl implements $TopAppBarComponentCWProxy {
const $CustomRootAppBarCWProxyImpl(this._value);
final CustomRootAppBar _value;
@override
CustomRootAppBar title(TextWrapper? title) => this(title: title);
@override
CustomRootAppBar centerTitle(bool? centerTitle) =>
this(centerTitle: centerTitle);
@override
CustomRootAppBar shape(ShapeBorder? shape) => this(shape: shape);
@override
CustomRootAppBar systemOverlayStyle(
SystemUiOverlayStyle? systemOverlayStyle) =>
this(systemOverlayStyle: systemOverlayStyle);
@override
CustomRootAppBar automaticallyImplyLeading(bool? automaticallyImplyLeading) =>
this(automaticallyImplyLeading: automaticallyImplyLeading);
@override
CustomRootAppBar flexibleSpace(Widget? flexibleSpace) =>
this(flexibleSpace: flexibleSpace);
@override
CustomRootAppBar bottom(PreferredSizeWidget? bottom) => this(bottom: bottom);
@override
CustomRootAppBar elevation(double? elevation) => this(elevation: elevation);
@override
CustomRootAppBar scrolledUnderElevation(double? scrolledUnderElevation) =>
this(scrolledUnderElevation: scrolledUnderElevation);
@override
CustomRootAppBar shadowColor(Color? shadowColor) =>
this(shadowColor: shadowColor);
@override
CustomRootAppBar surfaceTintColor(Color? surfaceTintColor) =>
this(surfaceTintColor: surfaceTintColor);
@override
CustomRootAppBar backgroundColor(MultiColor? backgroundColor) =>
this(backgroundColor: backgroundColor);
@override
CustomRootAppBar iconTheme(IconThemeData? iconTheme) =>
this(iconTheme: iconTheme);
@override
CustomRootAppBar primary(bool? primary) => this(primary: primary);
@override
CustomRootAppBar excludeHeaderSemantics(bool? excludeHeaderSemantics) =>
this(excludeHeaderSemantics: excludeHeaderSemantics);
@override
CustomRootAppBar toolbarHeight(double? toolbarHeight) =>
this(toolbarHeight: toolbarHeight);
@override
CustomRootAppBar leadingWidth(double? leadingWidth) =>
this(leadingWidth: leadingWidth);
@override
CustomRootAppBar leading(Widget? leading) => this(leading: leading);
@override
CustomRootAppBar actions(List<Widget>? actions) => this(actions: actions);
@override
CustomRootAppBar expandedWidget(List<Widget>? expandedWidget) =>
this(expandedWidget: expandedWidget);
@override
CustomRootAppBar key(Key? key) => this(key: key);
@override
CustomRootAppBar call({
TextWrapper? title,
bool? centerTitle,
ShapeBorder? shape,
SystemUiOverlayStyle? systemOverlayStyle,
bool? automaticallyImplyLeading,
Widget? flexibleSpace,
PreferredSizeWidget? bottom,
double? elevation,
double? scrolledUnderElevation,
Color? shadowColor,
Color? surfaceTintColor,
MultiColor? backgroundColor,
IconThemeData? iconTheme,
bool? primary,
bool? excludeHeaderSemantics,
double? toolbarHeight,
double? leadingWidth,
Widget? leading,
List<Widget>? actions,
List<Widget>? expandedWidget,
Key? key,
}) =>
CustomRootAppBar(
title: title ?? _value.title,
key: key ?? _value.key,
);
}
mixin $CustomRootAppBarCWMixin on Component {
$TopAppBarComponentCWProxy get copyWith =>
$CustomRootAppBarCWProxyImpl(this as CustomRootAppBar);
}

View File

@ -0,0 +1,20 @@
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart';
part 'custom_second_app_bar.g.dart';
@ComponentCopyWithExtension()
class CustomSecondAppBar extends TopAppBarComponent
with $CustomSecondAppBarCWMixin {
const CustomSecondAppBar({super.title, super.key});
@override
Widget build(BuildContext context) => AppBar(
backgroundColor: Colors.green,
title: Text(
super.title?.data ?? '',
),
);
}

View File

@ -0,0 +1,103 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'custom_second_app_bar.dart';
// **************************************************************************
// ComponentCopyWithGenerator
// **************************************************************************
class $CustomSecondAppBarCWProxyImpl implements $TopAppBarComponentCWProxy {
const $CustomSecondAppBarCWProxyImpl(this._value);
final CustomSecondAppBar _value;
@override
CustomSecondAppBar title(TextWrapper? title) => this(title: title);
@override
CustomSecondAppBar centerTitle(bool? centerTitle) =>
this(centerTitle: centerTitle);
@override
CustomSecondAppBar shape(ShapeBorder? shape) => this(shape: shape);
@override
CustomSecondAppBar systemOverlayStyle(
SystemUiOverlayStyle? systemOverlayStyle) =>
this(systemOverlayStyle: systemOverlayStyle);
@override
CustomSecondAppBar automaticallyImplyLeading(
bool? automaticallyImplyLeading) =>
this(automaticallyImplyLeading: automaticallyImplyLeading);
@override
CustomSecondAppBar flexibleSpace(Widget? flexibleSpace) =>
this(flexibleSpace: flexibleSpace);
@override
CustomSecondAppBar bottom(PreferredSizeWidget? bottom) =>
this(bottom: bottom);
@override
CustomSecondAppBar elevation(double? elevation) => this(elevation: elevation);
@override
CustomSecondAppBar scrolledUnderElevation(double? scrolledUnderElevation) =>
this(scrolledUnderElevation: scrolledUnderElevation);
@override
CustomSecondAppBar shadowColor(Color? shadowColor) =>
this(shadowColor: shadowColor);
@override
CustomSecondAppBar surfaceTintColor(Color? surfaceTintColor) =>
this(surfaceTintColor: surfaceTintColor);
@override
CustomSecondAppBar backgroundColor(MultiColor? backgroundColor) =>
this(backgroundColor: backgroundColor);
@override
CustomSecondAppBar iconTheme(IconThemeData? iconTheme) =>
this(iconTheme: iconTheme);
@override
CustomSecondAppBar primary(bool? primary) => this(primary: primary);
@override
CustomSecondAppBar excludeHeaderSemantics(bool? excludeHeaderSemantics) =>
this(excludeHeaderSemantics: excludeHeaderSemantics);
@override
CustomSecondAppBar toolbarHeight(double? toolbarHeight) =>
this(toolbarHeight: toolbarHeight);
@override
CustomSecondAppBar leadingWidth(double? leadingWidth) =>
this(leadingWidth: leadingWidth);
@override
CustomSecondAppBar leading(Widget? leading) => this(leading: leading);
@override
CustomSecondAppBar actions(List<Widget>? actions) => this(actions: actions);
@override
CustomSecondAppBar expandedWidget(List<Widget>? expandedWidget) =>
this(expandedWidget: expandedWidget);
@override
CustomSecondAppBar key(Key? key) => this(key: key);
@override
CustomSecondAppBar call({
TextWrapper? title,
bool? centerTitle,
ShapeBorder? shape,
SystemUiOverlayStyle? systemOverlayStyle,
bool? automaticallyImplyLeading,
Widget? flexibleSpace,
PreferredSizeWidget? bottom,
double? elevation,
double? scrolledUnderElevation,
Color? shadowColor,
Color? surfaceTintColor,
MultiColor? backgroundColor,
IconThemeData? iconTheme,
bool? primary,
bool? excludeHeaderSemantics,
double? toolbarHeight,
double? leadingWidth,
Widget? leading,
List<Widget>? actions,
List<Widget>? expandedWidget,
Key? key,
}) =>
CustomSecondAppBar(
title: title ?? _value.title,
key: key ?? _value.key,
);
}
mixin $CustomSecondAppBarCWMixin on Component {
$TopAppBarComponentCWProxy get copyWith =>
$CustomSecondAppBarCWProxyImpl(this as CustomSecondAppBar);
}

View File

@ -47,14 +47,22 @@ class Home extends StatelessWidget {
@override @override
Widget build(BuildContext context) => Scaffold( Widget build(BuildContext context) => Scaffold(
appBar: PreferredSize( appBar: PreferredSize(
preferredSize: const Size.fromHeight(60), preferredSize: const Size.fromHeight(120),
child: context.components.topAppBarComponent child: Column(
children: [
context.components
.topAppBarComponent()
.title(const TextWrapper('Example title')), .title(const TextWrapper('Example title')),
context.components
.topAppBarComponent('second')
.title(const TextWrapper('Example title')),
],
),
), ),
body: Column( body: Column(
children: [ children: [
Expanded( Expanded(
child: context.components.errorComponent.call( child: context.components.errorComponent()(
message: const TextWrapper('Example error'), message: const TextWrapper('Example error'),
), ),
), ),
@ -62,12 +70,13 @@ class Home extends StatelessWidget {
height: 10, height: 10,
), ),
Expanded( Expanded(
child: context.components.loaderComponent.call( child: context.components.loaderComponent()(
colors: const MultiColor.single(Colors.green), colors: const MultiColor.single(Colors.green),
), ),
), ),
], ],
), ),
bottomNavigationBar: context.components.bottomNavigationBar, bottomNavigationBar:
context.components.bottomNavigationBarComponent()(),
); );
} }

View File

@ -16,5 +16,7 @@
export 'enums/enums.dart'; export 'enums/enums.dart';
export 'extensions/build_context_extensions.dart'; export 'extensions/build_context_extensions.dart';
export 'extensions/component_extensions.dart';
export 'mixins/copy_with_mixin.dart'; export 'mixins/copy_with_mixin.dart';
export 'utils/component_registry.dart';
export 'utils/utils.dart'; export 'utils/utils.dart';

View File

@ -0,0 +1,33 @@
// Copyright (C) 2023 WYATT GROUP
// Please see the AUTHORS file for details.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
import 'package:wyatt_ui_components/wyatt_ui_components.dart';
/// Extension on a map of components that creates a [ComponentRegistry]
/// using the map's content.
extension ComponentMapExtension<T extends Component> on Map<String, T> {
/// Creates and returns a [ComponentRegistry] based on the map's components.
ComponentRegistry<T> registry() => ComponentRegistry(components: this);
}
/// Extension on a single component that creates a [ComponentRegistry]
/// containing only that component.
extension ComponentExtension<T extends Component> on T {
/// Creates and returns a [ComponentRegistry] containing
/// only this component.
// ignore: use_to_and_as_if_applicable
ComponentRegistry<T> registry() => ComponentRegistry.solo(this);
}

View File

@ -0,0 +1,59 @@
// Copyright (C) 2023 WYATT GROUP
// Please see the AUTHORS file for details.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
import 'package:wyatt_ui_components/wyatt_ui_components.dart';
/// A registry for components of type [T], providing easy access and management.
class ComponentRegistry<T extends Component> {
/// Constructs a [ComponentRegistry] with the given [components].
const ComponentRegistry({required Map<String, T> components})
: _components = components;
/// Factory constructor to create a [ComponentRegistry]
/// containing only a single [component].
factory ComponentRegistry.solo(T component) => ComponentRegistry(
components: {
'solo': component,
},
);
final Map<String, T> _components;
/// Returns a component by its [id], or the first
/// component if [id] is null or not found.
T? call([String? id]) => getComponent(id) ?? getFirstComponent();
/// Returns a component by its [id], or null if not found.
T? getComponent(String? id) => _components[id];
/// Returns the first component in the registry, or null
/// if the registry is empty.
T? getFirstComponent() => _components.values.firstOrNull;
/// Checks if the registry contains a component with the given [id].
bool containsComponent(String id) => _components.containsKey(id);
/// Returns the count of components in the registry.
int get count => _components.length;
/// Returns a list of all IDs of components in the registry.
List<String> get ids => _components.keys.toList();
/// Returns a string representation of the registry,
/// showing the count and IDs.
@override
String toString() => '$count - $ids';
}

View File

@ -16,6 +16,7 @@
import 'package:copy_with_extension/copy_with_extension.dart'; import 'package:copy_with_extension/copy_with_extension.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:wyatt_ui_components/src/core/utils/component_registry.dart';
import 'package:wyatt_ui_components/src/domain/entities/entities.dart'; import 'package:wyatt_ui_components/src/domain/entities/entities.dart';
part 'component_theme_data.g.dart'; part 'component_theme_data.g.dart';
@ -26,64 +27,64 @@ part 'component_theme_data.g.dart';
class ComponentThemeData { class ComponentThemeData {
/// {@macro component_theme_data} /// {@macro component_theme_data}
factory ComponentThemeData({ factory ComponentThemeData({
TopAppBarComponent? topAppBar, ComponentRegistry<TopAppBarComponent>? topAppBars,
TopNavigationBarComponent? topNavigationBar, ComponentRegistry<TopNavigationBarComponent>? topNavigationBars,
BottomNavigationBarComponent? bottomNavigationBar, ComponentRegistry<BottomNavigationBarComponent>? bottomNavigationBars,
ErrorComponent? error, ComponentRegistry<ErrorComponent>? errors,
LoaderComponent? loader, ComponentRegistry<LoaderComponent>? loaders,
RichTextBuilderComponent? richTextBuilder, ComponentRegistry<RichTextBuilderComponent>? richTextBuilders,
TextInputComponent? textInput, ComponentRegistry<TextInputComponent>? textInputs,
FileSelectionButtonComponent? fileSelectionButton, ComponentRegistry<FileSelectionButtonComponent>? fileSelectionButtons,
FlatButtonComponent? flatButton, ComponentRegistry<FlatButtonComponent>? flatButtons,
SimpleIconButtonComponent? simpleIconButton, ComponentRegistry<SimpleIconButtonComponent>? simpleIconButtons,
SymbolButtonComponent? symbolButton, ComponentRegistry<SymbolButtonComponent>? symbolButtons,
InformationCardComponent? informationCard, ComponentRegistry<InformationCardComponent>? informationCards,
PortfolioCardComponent? portfolioCard, ComponentRegistry<PortfolioCardComponent>? portfolioCards,
QuoteCardComponent? quoteCard, ComponentRegistry<QuoteCardComponent>? quoteCards,
SkillCardComponent? skillCard, ComponentRegistry<SkillCardComponent>? skillCards,
PricingCardComponent? pricingCard, ComponentRegistry<PricingCardComponent>? pricingCards,
FloatingActionButtonComponent? floatingActionButton, ComponentRegistry<FloatingActionButtonComponent>? floatingActionButtons,
}) => }) =>
ComponentThemeData.raw( ComponentThemeData.raw(
topAppBar: topAppBar, topAppBars: topAppBars,
topNavigationBar: topNavigationBar, topNavigationBars: topNavigationBars,
bottomNavigationBar: bottomNavigationBar, bottomNavigationBars: bottomNavigationBars,
error: error, errors: errors,
loader: loader, loaders: loaders,
richTextBuilder: richTextBuilder, richTextBuilders: richTextBuilders,
textInput: textInput, textInputs: textInputs,
fileSelectionButton: fileSelectionButton, fileSelectionButtons: fileSelectionButtons,
flatButton: flatButton, flatButtons: flatButtons,
simpleIconButton: simpleIconButton, simpleIconButtons: simpleIconButtons,
symbolButton: symbolButton, symbolButtons: symbolButtons,
informationCard: informationCard, informationCards: informationCards,
portfolioCard: portfolioCard, portfolioCards: portfolioCards,
quoteCard: quoteCard, quoteCards: quoteCards,
skillCard: skillCard, skillCards: skillCards,
pricingCard: pricingCard, pricingCards: pricingCards,
floatingActionButton: floatingActionButton, floatingActionButtons: floatingActionButtons,
); );
/// {@macro component_theme_data} // /// {@macro component_theme_data}
factory ComponentThemeData.fromOther(ComponentThemeData other) => factory ComponentThemeData.fromOther(ComponentThemeData other) =>
ComponentThemeData( ComponentThemeData(
topAppBar: other.topAppBar, topAppBars: other._topAppBars,
topNavigationBar: other.topNavigationBar, topNavigationBars: other._topNavigationBars,
bottomNavigationBar: other.bottomNavigationBar, bottomNavigationBars: other._bottomNavigationBars,
error: other.error, errors: other._errors,
loader: other.loader, loaders: other._loaders,
richTextBuilder: other.richTextBuilder, richTextBuilders: other._richTextBuilders,
textInput: other.textInput, textInputs: other._textInputs,
fileSelectionButton: other.fileSelectionButton, fileSelectionButtons: other._fileSelectionButtons,
flatButton: other.flatButton, flatButtons: other._flatButtons,
simpleIconButton: other.simpleIconButton, simpleIconButtons: other._simpleIconButtons,
symbolButton: other.symbolButton, symbolButtons: other._symbolButtons,
informationCard: other.informationCard, informationCards: other._informationCards,
portfolioCard: other.portfolioCard, portfolioCards: other._portfolioCards,
quoteCard: other.quoteCard, quoteCards: other._quoteCards,
skillCard: other.skillCard, skillCards: other._skillCards,
pricingCard: other.pricingCard, pricingCards: other._pricingCards,
floatingActionButton: other.floatingActionButton, floatingActionButtons: other._floatingActionButtons,
); );
/// Create a [ComponentThemeData] given a set of exact values. Most values /// Create a [ComponentThemeData] given a set of exact values. Most values
@ -93,24 +94,40 @@ class ComponentThemeData {
/// create intermediate themes based on two themes created with the /// create intermediate themes based on two themes created with the
/// [ComponentThemeData] constructor. /// [ComponentThemeData] constructor.
const ComponentThemeData.raw({ const ComponentThemeData.raw({
this.topAppBar, ComponentRegistry<TopAppBarComponent>? topAppBars,
this.topNavigationBar, ComponentRegistry<TopNavigationBarComponent>? topNavigationBars,
this.bottomNavigationBar, ComponentRegistry<BottomNavigationBarComponent>? bottomNavigationBars,
this.error, ComponentRegistry<ErrorComponent>? errors,
this.loader, ComponentRegistry<LoaderComponent>? loaders,
this.richTextBuilder, ComponentRegistry<RichTextBuilderComponent>? richTextBuilders,
this.textInput, ComponentRegistry<TextInputComponent>? textInputs,
this.fileSelectionButton, ComponentRegistry<FileSelectionButtonComponent>? fileSelectionButtons,
this.flatButton, ComponentRegistry<FlatButtonComponent>? flatButtons,
this.simpleIconButton, ComponentRegistry<SimpleIconButtonComponent>? simpleIconButtons,
this.symbolButton, ComponentRegistry<SymbolButtonComponent>? symbolButtons,
this.informationCard, ComponentRegistry<InformationCardComponent>? informationCards,
this.portfolioCard, ComponentRegistry<PortfolioCardComponent>? portfolioCards,
this.quoteCard, ComponentRegistry<QuoteCardComponent>? quoteCards,
this.skillCard, ComponentRegistry<SkillCardComponent>? skillCards,
this.pricingCard, ComponentRegistry<PricingCardComponent>? pricingCards,
this.floatingActionButton, ComponentRegistry<FloatingActionButtonComponent>? floatingActionButtons,
}); }) : _floatingActionButtons = floatingActionButtons,
_symbolButtons = symbolButtons,
_simpleIconButtons = simpleIconButtons,
_flatButtons = flatButtons,
_fileSelectionButtons = fileSelectionButtons,
_textInputs = textInputs,
_richTextBuilders = richTextBuilders,
_pricingCards = pricingCards,
_skillCards = skillCards,
_quoteCards = quoteCards,
_portfolioCards = portfolioCards,
_informationCards = informationCards,
_loaders = loaders,
_errors = errors,
_bottomNavigationBars = bottomNavigationBars,
_topNavigationBars = topNavigationBars,
_topAppBars = topAppBars;
R _get<T extends Component, R>(T? component, R? returned) { R _get<T extends Component, R>(T? component, R? returned) {
if (component == null) { if (component == null) {
@ -128,64 +145,97 @@ class ComponentThemeData {
} }
// Bars // Bars
final TopAppBarComponent? topAppBar; final ComponentRegistry<TopAppBarComponent>? _topAppBars;
$TopAppBarComponentCWProxy get topAppBarComponent => $TopAppBarComponentCWProxy topAppBarComponent([String? id]) =>
_get(topAppBar, topAppBar?.copyWith); _get(_topAppBars?.call(id), _topAppBars?.call(id)?.copyWith);
final TopNavigationBarComponent? topNavigationBar;
$TopNavigationBarComponentCWProxy get topNavigationBarComponent => final ComponentRegistry<TopNavigationBarComponent>? _topNavigationBars;
_get(topNavigationBar, topNavigationBar?.copyWith); $TopNavigationBarComponentCWProxy topNavigationBarComponent([String? id]) =>
final BottomNavigationBarComponent? bottomNavigationBar; _get(
$BottomNavigationBarComponentCWProxy get bottomNavigationBarComponent => _topNavigationBars?.call(id),
_get(bottomNavigationBar, bottomNavigationBar?.copyWith); _topNavigationBars?.call(id)?.copyWith,
);
final ComponentRegistry<BottomNavigationBarComponent>? _bottomNavigationBars;
$BottomNavigationBarComponentCWProxy bottomNavigationBarComponent([
String? id,
]) =>
_get(
_bottomNavigationBars?.call(id),
_bottomNavigationBars?.call(id)?.copyWith,
);
// CRUD Widgets // CRUD Widgets
final ErrorComponent? error; final ComponentRegistry<ErrorComponent>? _errors;
$ErrorComponentCWProxy get errorComponent => _get(error, error?.copyWith); $ErrorComponentCWProxy errorComponent([String? id]) =>
final LoaderComponent? loader; _get(_errors?.call(id), _errors?.call(id)?.copyWith);
$LoaderComponentCWProxy get loaderComponent => _get(loader, loader?.copyWith);
final ComponentRegistry<LoaderComponent>? _loaders;
$LoaderComponentCWProxy loaderComponent([String? id]) =>
_get(_loaders?.call(id), _loaders?.call(id)?.copyWith);
// Cards // Cards
final InformationCardComponent? informationCard; final ComponentRegistry<InformationCardComponent>? _informationCards;
$InformationCardComponentCWProxy get informationCardComponent => $InformationCardComponentCWProxy informationCardComponent([String? id]) =>
_get(informationCard, informationCard?.copyWith); _get(_informationCards?.call(id), _informationCards?.call(id)?.copyWith);
final PortfolioCardComponent? portfolioCard;
$PortfolioCardComponentCWProxy get portfolioCardComponent => final ComponentRegistry<PortfolioCardComponent>? _portfolioCards;
_get(portfolioCard, portfolioCard?.copyWith); $PortfolioCardComponentCWProxy portfolioCardComponent([String? id]) =>
final QuoteCardComponent? quoteCard; _get(_portfolioCards?.call(id), _portfolioCards?.call(id)?.copyWith);
$QuoteCardComponentCWProxy get quoteCardComponent =>
_get(quoteCard, quoteCard?.copyWith); final ComponentRegistry<QuoteCardComponent>? _quoteCards;
final SkillCardComponent? skillCard; $QuoteCardComponentCWProxy quoteCardComponent([String? id]) =>
$SkillCardComponentCWProxy get skillCardComponent => _get(_quoteCards?.call(id), _quoteCards?.call(id)?.copyWith);
_get(skillCard, skillCard?.copyWith);
final PricingCardComponent? pricingCard; final ComponentRegistry<SkillCardComponent>? _skillCards;
$PricingCardComponentCWProxy get pricingCardComponent => $SkillCardComponentCWProxy skillCardComponent([String? id]) =>
_get(pricingCard, pricingCard?.copyWith); _get(_skillCards?.call(id), _skillCards?.call(id)?.copyWith);
final ComponentRegistry<PricingCardComponent>? _pricingCards;
$PricingCardComponentCWProxy pricingCardComponent([String? id]) =>
_get(_pricingCards?.call(id), _pricingCards?.call(id)?.copyWith);
// Rich Text // Rich Text
final RichTextBuilderComponent? richTextBuilder; final ComponentRegistry<RichTextBuilderComponent>? _richTextBuilders;
$RichTextBuilderComponentCWProxy get richTextBuilderComponent => $RichTextBuilderComponentCWProxy richTextBuilderComponent([String? id]) =>
_get(richTextBuilder, richTextBuilder?.copyWith); _get(_richTextBuilders?.call(id), _richTextBuilders?.call(id)?.copyWith);
// Text Inputs // Text Inputs
final TextInputComponent? textInput; final ComponentRegistry<TextInputComponent>? _textInputs;
$TextInputComponentCWProxy get textInputComponent => $TextInputComponentCWProxy textInputComponent([String? id]) =>
_get(textInput, textInput?.copyWith); _get(_textInputs?.call(id), _textInputs?.call(id)?.copyWith);
// Buttons // Buttons
final FileSelectionButtonComponent? fileSelectionButton; final ComponentRegistry<FileSelectionButtonComponent>? _fileSelectionButtons;
$FileSelectionButtonComponentCWProxy get fileSelectionButtonComponent => $FileSelectionButtonComponentCWProxy fileSelectionButtonComponent([
_get(fileSelectionButton, fileSelectionButton?.copyWith); String? id,
final FlatButtonComponent? flatButton; ]) =>
$FlatButtonComponentCWProxy get flatButtonComponent => _get(
_get(flatButton, flatButton?.copyWith); _fileSelectionButtons?.call(id),
final SimpleIconButtonComponent? simpleIconButton; _fileSelectionButtons?.call(id)?.copyWith,
$SimpleIconButtonComponentCWProxy get simpleIconButtonComponent => );
_get(simpleIconButton, simpleIconButton?.copyWith);
final SymbolButtonComponent? symbolButton;
$SymbolButtonComponentCWProxy get symbolButtonComponent =>
_get(symbolButton, symbolButton?.copyWith);
final FloatingActionButtonComponent? floatingActionButton; final ComponentRegistry<FlatButtonComponent>? _flatButtons;
$FloatingActionButtonComponentCWProxy get floatingActionButtonComponent => $FlatButtonComponentCWProxy flatButtonComponent([String? id]) =>
_get(floatingActionButton, floatingActionButton?.copyWith); _get(_flatButtons?.call(id), _flatButtons?.call(id)?.copyWith);
final ComponentRegistry<SimpleIconButtonComponent>? _simpleIconButtons;
$SimpleIconButtonComponentCWProxy simpleIconButtonComponent([String? id]) =>
_get(
_simpleIconButtons?.call(id),
_simpleIconButtons?.call(id)?.copyWith,
);
final ComponentRegistry<SymbolButtonComponent>? _symbolButtons;
$SymbolButtonComponentCWProxy symbolButtonComponent([String? id]) =>
_get(_symbolButtons?.call(id), _symbolButtons?.call(id)?.copyWith);
final ComponentRegistry<FloatingActionButtonComponent>?
_floatingActionButtons;
$FloatingActionButtonComponentCWProxy floatingActionButtonComponent([
String? id,
]) =>
_get(
_floatingActionButtons?.call(id),
_floatingActionButtons?.call(id)?.copyWith,
);
} }

View File

@ -7,44 +7,54 @@ part of 'component_theme_data.dart';
// ************************************************************************** // **************************************************************************
abstract class _$ComponentThemeDataCWProxy { abstract class _$ComponentThemeDataCWProxy {
ComponentThemeData topAppBar(TopAppBarComponent? topAppBar); ComponentThemeData topAppBars(
ComponentRegistry<TopAppBarComponent>? topAppBars);
ComponentThemeData topNavigationBar( ComponentThemeData topNavigationBars(
TopNavigationBarComponent? topNavigationBar); ComponentRegistry<TopNavigationBarComponent>? topNavigationBars);
ComponentThemeData bottomNavigationBar( ComponentThemeData bottomNavigationBars(
BottomNavigationBarComponent? bottomNavigationBar); ComponentRegistry<BottomNavigationBarComponent>? bottomNavigationBars);
ComponentThemeData error(ErrorComponent? error); ComponentThemeData errors(ComponentRegistry<ErrorComponent>? errors);
ComponentThemeData loader(LoaderComponent? loader); ComponentThemeData loaders(ComponentRegistry<LoaderComponent>? loaders);
ComponentThemeData richTextBuilder(RichTextBuilderComponent? richTextBuilder); ComponentThemeData richTextBuilders(
ComponentRegistry<RichTextBuilderComponent>? richTextBuilders);
ComponentThemeData textInput(TextInputComponent? textInput); ComponentThemeData textInputs(
ComponentRegistry<TextInputComponent>? textInputs);
ComponentThemeData fileSelectionButton( ComponentThemeData fileSelectionButtons(
FileSelectionButtonComponent? fileSelectionButton); ComponentRegistry<FileSelectionButtonComponent>? fileSelectionButtons);
ComponentThemeData flatButton(FlatButtonComponent? flatButton); ComponentThemeData flatButtons(
ComponentRegistry<FlatButtonComponent>? flatButtons);
ComponentThemeData simpleIconButton( ComponentThemeData simpleIconButtons(
SimpleIconButtonComponent? simpleIconButton); ComponentRegistry<SimpleIconButtonComponent>? simpleIconButtons);
ComponentThemeData symbolButton(SymbolButtonComponent? symbolButton); ComponentThemeData symbolButtons(
ComponentRegistry<SymbolButtonComponent>? symbolButtons);
ComponentThemeData informationCard(InformationCardComponent? informationCard); ComponentThemeData informationCards(
ComponentRegistry<InformationCardComponent>? informationCards);
ComponentThemeData portfolioCard(PortfolioCardComponent? portfolioCard); ComponentThemeData portfolioCards(
ComponentRegistry<PortfolioCardComponent>? portfolioCards);
ComponentThemeData quoteCard(QuoteCardComponent? quoteCard); ComponentThemeData quoteCards(
ComponentRegistry<QuoteCardComponent>? quoteCards);
ComponentThemeData skillCard(SkillCardComponent? skillCard); ComponentThemeData skillCards(
ComponentRegistry<SkillCardComponent>? skillCards);
ComponentThemeData pricingCard(PricingCardComponent? pricingCard); ComponentThemeData pricingCards(
ComponentRegistry<PricingCardComponent>? pricingCards);
ComponentThemeData floatingActionButton( ComponentThemeData floatingActionButtons(
FloatingActionButtonComponent? floatingActionButton); ComponentRegistry<FloatingActionButtonComponent>? floatingActionButtons);
/// This function **does support** nullification of nullable fields. All `null` values passed to `non-nullable` fields will be ignored. You can also use `ComponentThemeData(...).copyWith.fieldName(...)` to override fields one at a time with nullification support. /// This function **does support** nullification of nullable fields. All `null` values passed to `non-nullable` fields will be ignored. You can also use `ComponentThemeData(...).copyWith.fieldName(...)` to override fields one at a time with nullification support.
/// ///
@ -53,23 +63,23 @@ abstract class _$ComponentThemeDataCWProxy {
/// ComponentThemeData(...).copyWith(id: 12, name: "My name") /// ComponentThemeData(...).copyWith(id: 12, name: "My name")
/// ```` /// ````
ComponentThemeData call({ ComponentThemeData call({
TopAppBarComponent? topAppBar, ComponentRegistry<TopAppBarComponent>? topAppBars,
TopNavigationBarComponent? topNavigationBar, ComponentRegistry<TopNavigationBarComponent>? topNavigationBars,
BottomNavigationBarComponent? bottomNavigationBar, ComponentRegistry<BottomNavigationBarComponent>? bottomNavigationBars,
ErrorComponent? error, ComponentRegistry<ErrorComponent>? errors,
LoaderComponent? loader, ComponentRegistry<LoaderComponent>? loaders,
RichTextBuilderComponent? richTextBuilder, ComponentRegistry<RichTextBuilderComponent>? richTextBuilders,
TextInputComponent? textInput, ComponentRegistry<TextInputComponent>? textInputs,
FileSelectionButtonComponent? fileSelectionButton, ComponentRegistry<FileSelectionButtonComponent>? fileSelectionButtons,
FlatButtonComponent? flatButton, ComponentRegistry<FlatButtonComponent>? flatButtons,
SimpleIconButtonComponent? simpleIconButton, ComponentRegistry<SimpleIconButtonComponent>? simpleIconButtons,
SymbolButtonComponent? symbolButton, ComponentRegistry<SymbolButtonComponent>? symbolButtons,
InformationCardComponent? informationCard, ComponentRegistry<InformationCardComponent>? informationCards,
PortfolioCardComponent? portfolioCard, ComponentRegistry<PortfolioCardComponent>? portfolioCards,
QuoteCardComponent? quoteCard, ComponentRegistry<QuoteCardComponent>? quoteCards,
SkillCardComponent? skillCard, ComponentRegistry<SkillCardComponent>? skillCards,
PricingCardComponent? pricingCard, ComponentRegistry<PricingCardComponent>? pricingCards,
FloatingActionButtonComponent? floatingActionButton, ComponentRegistry<FloatingActionButtonComponent>? floatingActionButtons,
}); });
} }
@ -80,77 +90,90 @@ class _$ComponentThemeDataCWProxyImpl implements _$ComponentThemeDataCWProxy {
final ComponentThemeData _value; final ComponentThemeData _value;
@override @override
ComponentThemeData topAppBar(TopAppBarComponent? topAppBar) => ComponentThemeData topAppBars(
this(topAppBar: topAppBar); ComponentRegistry<TopAppBarComponent>? topAppBars) =>
this(topAppBars: topAppBars);
@override @override
ComponentThemeData topNavigationBar( ComponentThemeData topNavigationBars(
TopNavigationBarComponent? topNavigationBar) => ComponentRegistry<TopNavigationBarComponent>? topNavigationBars) =>
this(topNavigationBar: topNavigationBar); this(topNavigationBars: topNavigationBars);
@override @override
ComponentThemeData bottomNavigationBar( ComponentThemeData bottomNavigationBars(
BottomNavigationBarComponent? bottomNavigationBar) => ComponentRegistry<BottomNavigationBarComponent>?
this(bottomNavigationBar: bottomNavigationBar); bottomNavigationBars) =>
this(bottomNavigationBars: bottomNavigationBars);
@override @override
ComponentThemeData error(ErrorComponent? error) => this(error: error); ComponentThemeData errors(ComponentRegistry<ErrorComponent>? errors) =>
this(errors: errors);
@override @override
ComponentThemeData loader(LoaderComponent? loader) => this(loader: loader); ComponentThemeData loaders(ComponentRegistry<LoaderComponent>? loaders) =>
this(loaders: loaders);
@override @override
ComponentThemeData richTextBuilder( ComponentThemeData richTextBuilders(
RichTextBuilderComponent? richTextBuilder) => ComponentRegistry<RichTextBuilderComponent>? richTextBuilders) =>
this(richTextBuilder: richTextBuilder); this(richTextBuilders: richTextBuilders);
@override @override
ComponentThemeData textInput(TextInputComponent? textInput) => ComponentThemeData textInputs(
this(textInput: textInput); ComponentRegistry<TextInputComponent>? textInputs) =>
this(textInputs: textInputs);
@override @override
ComponentThemeData fileSelectionButton( ComponentThemeData fileSelectionButtons(
FileSelectionButtonComponent? fileSelectionButton) => ComponentRegistry<FileSelectionButtonComponent>?
this(fileSelectionButton: fileSelectionButton); fileSelectionButtons) =>
this(fileSelectionButtons: fileSelectionButtons);
@override @override
ComponentThemeData flatButton(FlatButtonComponent? flatButton) => ComponentThemeData flatButtons(
this(flatButton: flatButton); ComponentRegistry<FlatButtonComponent>? flatButtons) =>
this(flatButtons: flatButtons);
@override @override
ComponentThemeData simpleIconButton( ComponentThemeData simpleIconButtons(
SimpleIconButtonComponent? simpleIconButton) => ComponentRegistry<SimpleIconButtonComponent>? simpleIconButtons) =>
this(simpleIconButton: simpleIconButton); this(simpleIconButtons: simpleIconButtons);
@override @override
ComponentThemeData symbolButton(SymbolButtonComponent? symbolButton) => ComponentThemeData symbolButtons(
this(symbolButton: symbolButton); ComponentRegistry<SymbolButtonComponent>? symbolButtons) =>
this(symbolButtons: symbolButtons);
@override @override
ComponentThemeData informationCard( ComponentThemeData informationCards(
InformationCardComponent? informationCard) => ComponentRegistry<InformationCardComponent>? informationCards) =>
this(informationCard: informationCard); this(informationCards: informationCards);
@override @override
ComponentThemeData portfolioCard(PortfolioCardComponent? portfolioCard) => ComponentThemeData portfolioCards(
this(portfolioCard: portfolioCard); ComponentRegistry<PortfolioCardComponent>? portfolioCards) =>
this(portfolioCards: portfolioCards);
@override @override
ComponentThemeData quoteCard(QuoteCardComponent? quoteCard) => ComponentThemeData quoteCards(
this(quoteCard: quoteCard); ComponentRegistry<QuoteCardComponent>? quoteCards) =>
this(quoteCards: quoteCards);
@override @override
ComponentThemeData skillCard(SkillCardComponent? skillCard) => ComponentThemeData skillCards(
this(skillCard: skillCard); ComponentRegistry<SkillCardComponent>? skillCards) =>
this(skillCards: skillCards);
@override @override
ComponentThemeData pricingCard(PricingCardComponent? pricingCard) => ComponentThemeData pricingCards(
this(pricingCard: pricingCard); ComponentRegistry<PricingCardComponent>? pricingCards) =>
this(pricingCards: pricingCards);
@override @override
ComponentThemeData floatingActionButton( ComponentThemeData floatingActionButtons(
FloatingActionButtonComponent? floatingActionButton) => ComponentRegistry<FloatingActionButtonComponent>?
this(floatingActionButton: floatingActionButton); floatingActionButtons) =>
this(floatingActionButtons: floatingActionButtons);
@override @override
@ -161,93 +184,97 @@ class _$ComponentThemeDataCWProxyImpl implements _$ComponentThemeDataCWProxy {
/// ComponentThemeData(...).copyWith(id: 12, name: "My name") /// ComponentThemeData(...).copyWith(id: 12, name: "My name")
/// ```` /// ````
ComponentThemeData call({ ComponentThemeData call({
Object? topAppBar = const $CopyWithPlaceholder(), Object? topAppBars = const $CopyWithPlaceholder(),
Object? topNavigationBar = const $CopyWithPlaceholder(), Object? topNavigationBars = const $CopyWithPlaceholder(),
Object? bottomNavigationBar = const $CopyWithPlaceholder(), Object? bottomNavigationBars = const $CopyWithPlaceholder(),
Object? error = const $CopyWithPlaceholder(), Object? errors = const $CopyWithPlaceholder(),
Object? loader = const $CopyWithPlaceholder(), Object? loaders = const $CopyWithPlaceholder(),
Object? richTextBuilder = const $CopyWithPlaceholder(), Object? richTextBuilders = const $CopyWithPlaceholder(),
Object? textInput = const $CopyWithPlaceholder(), Object? textInputs = const $CopyWithPlaceholder(),
Object? fileSelectionButton = const $CopyWithPlaceholder(), Object? fileSelectionButtons = const $CopyWithPlaceholder(),
Object? flatButton = const $CopyWithPlaceholder(), Object? flatButtons = const $CopyWithPlaceholder(),
Object? simpleIconButton = const $CopyWithPlaceholder(), Object? simpleIconButtons = const $CopyWithPlaceholder(),
Object? symbolButton = const $CopyWithPlaceholder(), Object? symbolButtons = const $CopyWithPlaceholder(),
Object? informationCard = const $CopyWithPlaceholder(), Object? informationCards = const $CopyWithPlaceholder(),
Object? portfolioCard = const $CopyWithPlaceholder(), Object? portfolioCards = const $CopyWithPlaceholder(),
Object? quoteCard = const $CopyWithPlaceholder(), Object? quoteCards = const $CopyWithPlaceholder(),
Object? skillCard = const $CopyWithPlaceholder(), Object? skillCards = const $CopyWithPlaceholder(),
Object? pricingCard = const $CopyWithPlaceholder(), Object? pricingCards = const $CopyWithPlaceholder(),
Object? floatingActionButton = const $CopyWithPlaceholder(), Object? floatingActionButtons = const $CopyWithPlaceholder(),
}) { }) {
return ComponentThemeData( return ComponentThemeData(
topAppBar: topAppBar == const $CopyWithPlaceholder() topAppBars: topAppBars == const $CopyWithPlaceholder()
? _value.topAppBar ? _value.topAppBars
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: topAppBar as TopAppBarComponent?, : topAppBars as ComponentRegistry<TopAppBarComponent>?,
topNavigationBar: topNavigationBar == const $CopyWithPlaceholder() topNavigationBars: topNavigationBars == const $CopyWithPlaceholder()
? _value.topNavigationBar ? _value.topNavigationBars
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: topNavigationBar as TopNavigationBarComponent?, : topNavigationBars as ComponentRegistry<TopNavigationBarComponent>?,
bottomNavigationBar: bottomNavigationBar == const $CopyWithPlaceholder() bottomNavigationBars: bottomNavigationBars == const $CopyWithPlaceholder()
? _value.bottomNavigationBar ? _value.bottomNavigationBars
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: bottomNavigationBar as BottomNavigationBarComponent?, : bottomNavigationBars
error: error == const $CopyWithPlaceholder() as ComponentRegistry<BottomNavigationBarComponent>?,
? _value.error errors: errors == const $CopyWithPlaceholder()
? _value.errors
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: error as ErrorComponent?, : errors as ComponentRegistry<ErrorComponent>?,
loader: loader == const $CopyWithPlaceholder() loaders: loaders == const $CopyWithPlaceholder()
? _value.loader ? _value.loaders
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: loader as LoaderComponent?, : loaders as ComponentRegistry<LoaderComponent>?,
richTextBuilder: richTextBuilder == const $CopyWithPlaceholder() richTextBuilders: richTextBuilders == const $CopyWithPlaceholder()
? _value.richTextBuilder ? _value.richTextBuilders
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: richTextBuilder as RichTextBuilderComponent?, : richTextBuilders as ComponentRegistry<RichTextBuilderComponent>?,
textInput: textInput == const $CopyWithPlaceholder() textInputs: textInputs == const $CopyWithPlaceholder()
? _value.textInput ? _value.textInputs
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: textInput as TextInputComponent?, : textInputs as ComponentRegistry<TextInputComponent>?,
fileSelectionButton: fileSelectionButton == const $CopyWithPlaceholder() fileSelectionButtons: fileSelectionButtons == const $CopyWithPlaceholder()
? _value.fileSelectionButton ? _value.fileSelectionButtons
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: fileSelectionButton as FileSelectionButtonComponent?, : fileSelectionButtons
flatButton: flatButton == const $CopyWithPlaceholder() as ComponentRegistry<FileSelectionButtonComponent>?,
? _value.flatButton flatButtons: flatButtons == const $CopyWithPlaceholder()
? _value.flatButtons
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: flatButton as FlatButtonComponent?, : flatButtons as ComponentRegistry<FlatButtonComponent>?,
simpleIconButton: simpleIconButton == const $CopyWithPlaceholder() simpleIconButtons: simpleIconButtons == const $CopyWithPlaceholder()
? _value.simpleIconButton ? _value.simpleIconButtons
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: simpleIconButton as SimpleIconButtonComponent?, : simpleIconButtons as ComponentRegistry<SimpleIconButtonComponent>?,
symbolButton: symbolButton == const $CopyWithPlaceholder() symbolButtons: symbolButtons == const $CopyWithPlaceholder()
? _value.symbolButton ? _value.symbolButtons
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: symbolButton as SymbolButtonComponent?, : symbolButtons as ComponentRegistry<SymbolButtonComponent>?,
informationCard: informationCard == const $CopyWithPlaceholder() informationCards: informationCards == const $CopyWithPlaceholder()
? _value.informationCard ? _value.informationCards
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: informationCard as InformationCardComponent?, : informationCards as ComponentRegistry<InformationCardComponent>?,
portfolioCard: portfolioCard == const $CopyWithPlaceholder() portfolioCards: portfolioCards == const $CopyWithPlaceholder()
? _value.portfolioCard ? _value.portfolioCards
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: portfolioCard as PortfolioCardComponent?, : portfolioCards as ComponentRegistry<PortfolioCardComponent>?,
quoteCard: quoteCard == const $CopyWithPlaceholder() quoteCards: quoteCards == const $CopyWithPlaceholder()
? _value.quoteCard ? _value.quoteCards
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: quoteCard as QuoteCardComponent?, : quoteCards as ComponentRegistry<QuoteCardComponent>?,
skillCard: skillCard == const $CopyWithPlaceholder() skillCards: skillCards == const $CopyWithPlaceholder()
? _value.skillCard ? _value.skillCards
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: skillCard as SkillCardComponent?, : skillCards as ComponentRegistry<SkillCardComponent>?,
pricingCard: pricingCard == const $CopyWithPlaceholder() pricingCards: pricingCards == const $CopyWithPlaceholder()
? _value.pricingCard ? _value.pricingCards
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: pricingCard as PricingCardComponent?, : pricingCards as ComponentRegistry<PricingCardComponent>?,
floatingActionButton: floatingActionButton == const $CopyWithPlaceholder() floatingActionButtons:
? _value.floatingActionButton floatingActionButtons == const $CopyWithPlaceholder()
? _value.floatingActionButtons
// ignore: cast_nullable_to_non_nullable // ignore: cast_nullable_to_non_nullable
: floatingActionButton as FloatingActionButtonComponent?, : floatingActionButtons
as ComponentRegistry<FloatingActionButtonComponent>?,
); );
} }
} }

View File

@ -6,7 +6,7 @@ version: 0.2.2
publish_to: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub publish_to: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub
environment: environment:
sdk: ">=2.19.0 <3.0.0" sdk: ">=3.0.0 <4.0.0"
dependencies: dependencies:
flutter: { sdk: flutter } flutter: { sdk: flutter }

View File

@ -27,7 +27,7 @@ class Bars extends DemoPage {
), ),
), ),
actions: [ actions: [
IconButton(onPressed: () {}, icon: const Icon(Icons.menu)) IconButton(onPressed: () {}, icon: const Icon(Icons.menu)),
], ],
), ),
const Gap(20), const Gap(20),
@ -54,13 +54,13 @@ class Bars extends DemoPage {
), ),
ListTile( ListTile(
title: Text('Votre programme'), title: Text('Votre programme'),
) ),
], ],
actions: [ actions: [
IconButton( IconButton(
onPressed: () {}, onPressed: () {},
icon: const Icon(Icons.clear), icon: const Icon(Icons.clear),
) ),
], ],
), ),
const Gap(20), const Gap(20),
@ -81,7 +81,7 @@ class Bars extends DemoPage {
TextWrapper('ACCUEIL'), TextWrapper('ACCUEIL'),
TextWrapper('VOTRE PROGRAMME'), TextWrapper('VOTRE PROGRAMME'),
TextWrapper('LE STUDIO'), TextWrapper('LE STUDIO'),
TextWrapper('SAVOIR FAIRE') TextWrapper('SAVOIR FAIRE'),
], ],
), ),
], ],

View File

@ -50,7 +50,7 @@ class Buttons extends DemoPage {
Gap(20), Gap(20),
SimpleIconButtons(), SimpleIconButtons(),
Gap(20), Gap(20),
FileSelectionButtons() FileSelectionButtons(),
], ],
), ),
], ],

View File

@ -30,7 +30,7 @@ class PortfolioCards extends StatelessWidget {
'quis elit ut amet velit. Incididunt fugiat proident ' 'quis elit ut amet velit. Incididunt fugiat proident '
'proident deserunt tempor Lorem cillum qui do '), 'proident deserunt tempor Lorem cillum qui do '),
ctas: [ ctas: [
context.components.flatButtonComponent.call( context.components.flatButtonComponent().call(
label: const TextWrapper('En savoir plus'), label: const TextWrapper('En savoir plus'),
suffix: const Icon( suffix: const Icon(
Icons.arrow_forward_ios, Icons.arrow_forward_ios,
@ -43,12 +43,12 @@ class PortfolioCards extends StatelessWidget {
'assets/images/mockup_1.png', 'assets/images/mockup_1.png',
alignment: Alignment.topCenter, alignment: Alignment.topCenter,
fit: BoxFit.cover, fit: BoxFit.cover,
) ),
], ],
keywords: const [ keywords: const [
TextWrapper('UI Design'), TextWrapper('UI Design'),
TextWrapper('Developpement'), TextWrapper('Developpement'),
TextWrapper('Deploiement') TextWrapper('Deploiement'),
], ],
), ),
const Gap(20), const Gap(20),
@ -65,7 +65,7 @@ class PortfolioCards extends StatelessWidget {
'quis elit ut amet velit. Incididunt fugiat proident ' 'quis elit ut amet velit. Incididunt fugiat proident '
'proident deserunt tempor Lorem cillum qui do '), 'proident deserunt tempor Lorem cillum qui do '),
ctas: [ ctas: [
context.components.flatButtonComponent.call( context.components.flatButtonComponent().call(
label: const TextWrapper('En savoir plus'), label: const TextWrapper('En savoir plus'),
suffix: const Icon( suffix: const Icon(
Icons.arrow_forward_ios, Icons.arrow_forward_ios,
@ -78,9 +78,9 @@ class PortfolioCards extends StatelessWidget {
'assets/images/mockup_1.png', 'assets/images/mockup_1.png',
alignment: Alignment.topCenter, alignment: Alignment.topCenter,
fit: BoxFit.cover, fit: BoxFit.cover,
) ),
], ],
) ),
], ],
), ),
const Gap(20), const Gap(20),
@ -100,7 +100,7 @@ class PortfolioCards extends StatelessWidget {
'quis elit ut amet velit. Incididunt fugiat proident ' 'quis elit ut amet velit. Incididunt fugiat proident '
'proident deserunt tempor Lorem cillum qui do '), 'proident deserunt tempor Lorem cillum qui do '),
ctas: [ ctas: [
context.components.flatButtonComponent.call( context.components.flatButtonComponent().call(
label: const TextWrapper('En savoir plus'), label: const TextWrapper('En savoir plus'),
suffix: const Icon( suffix: const Icon(
Icons.arrow_forward_ios, Icons.arrow_forward_ios,
@ -118,12 +118,12 @@ class PortfolioCards extends StatelessWidget {
'assets/images/mockup_1.png', 'assets/images/mockup_1.png',
alignment: Alignment.topCenter, alignment: Alignment.topCenter,
fit: BoxFit.cover, fit: BoxFit.cover,
) ),
], ],
keywords: const [ keywords: const [
TextWrapper('UI Design'), TextWrapper('UI Design'),
TextWrapper('Developpement'), TextWrapper('Developpement'),
TextWrapper('Deploiement') TextWrapper('Deploiement'),
], ],
), ),
const Gap(20), const Gap(20),
@ -145,7 +145,7 @@ class PortfolioCards extends StatelessWidget {
'quis elit ut amet velit. Incididunt fugiat proident ' 'quis elit ut amet velit. Incididunt fugiat proident '
'proident deserunt tempor Lorem cillum qui do '), 'proident deserunt tempor Lorem cillum qui do '),
ctas: [ ctas: [
context.components.flatButtonComponent.call( context.components.flatButtonComponent().call(
label: const TextWrapper('En savoir plus'), label: const TextWrapper('En savoir plus'),
suffix: const Icon( suffix: const Icon(
Icons.arrow_forward_ios, Icons.arrow_forward_ios,
@ -168,12 +168,12 @@ class PortfolioCards extends StatelessWidget {
'assets/images/mockup_1.png', 'assets/images/mockup_1.png',
alignment: Alignment.topCenter, alignment: Alignment.topCenter,
fit: BoxFit.cover, fit: BoxFit.cover,
) ),
], ],
keywords: const [ keywords: const [
TextWrapper('UI Design'), TextWrapper('UI Design'),
TextWrapper('Developpement'), TextWrapper('Developpement'),
TextWrapper('Deploiement') TextWrapper('Deploiement'),
], ],
), ),
], ],

View File

@ -73,7 +73,7 @@ class PricingCards extends StatelessWidget {
), ),
), ),
], ],
cta: context.components.flatButtonComponent.call( cta: context.components.flatButtonComponent().call(
label: const TextWrapper( label: const TextWrapper(
'Contactez-nous', 'Contactez-nous',
style: TextStyle(color: Colors.white), style: TextStyle(color: Colors.white),
@ -130,7 +130,7 @@ class PricingCards extends StatelessWidget {
), ),
), ),
], ],
cta: context.components.flatButtonComponent.call( cta: context.components.flatButtonComponent().call(
label: const TextWrapper( label: const TextWrapper(
'Contactez-nous', 'Contactez-nous',
style: TextStyle(color: Colors.white), style: TextStyle(color: Colors.white),

View File

@ -47,7 +47,7 @@ class SkillCards extends StatelessWidget {
gradientColors: gradientColors:
const MultiColor([Colors.red, Colors.orange]), const MultiColor([Colors.red, Colors.orange]),
), ),
) ),
], ],
bulletColors: const MultiColor([Colors.red, Colors.orange]), bulletColors: const MultiColor([Colors.red, Colors.orange]),
title: const TextWrapper('Lorem Ipsum'), title: const TextWrapper('Lorem Ipsum'),
@ -78,7 +78,7 @@ class SkillCards extends StatelessWidget {
gradientColors: gradientColors:
const MultiColor([Colors.blue, Colors.green]), const MultiColor([Colors.blue, Colors.green]),
), ),
) ),
], ],
bulletColors: const MultiColor([Colors.blue, Colors.green]), bulletColors: const MultiColor([Colors.blue, Colors.green]),
title: const TextWrapper('Lorem Ipsum'), title: const TextWrapper('Lorem Ipsum'),

View File

@ -15,8 +15,8 @@ dependencies:
flutter_bloc: ^8.1.2 flutter_bloc: ^8.1.2
flutter_localizations: { sdk: flutter } flutter_localizations: { sdk: flutter }
gap: ^2.0.1 gap: ^3.0.1
google_fonts: ^4.0.3 google_fonts: ^5.1.0
wyatt_ui_components: wyatt_ui_components:
hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub hosted: https://git.wyatt-studio.fr/api/packages/Wyatt-FOSS/pub

View File

@ -63,7 +63,7 @@ class NavigationItem extends StatelessWidget {
.themeExtension<TopBarThemeExtension>() .themeExtension<TopBarThemeExtension>()
?.selectedIndicatorColors, ?.selectedIndicatorColors,
TopBarThemeExtensionDefault.from(Theme.of(context)) TopBarThemeExtensionDefault.from(Theme.of(context))
.selectedIndicatorColors .selectedIndicatorColors,
], ],
valueValidator: (value) => value?.isGradient, valueValidator: (value) => value?.isGradient,
transform: (value) => transform: (value) =>
@ -75,7 +75,7 @@ class NavigationItem extends StatelessWidget {
.themeExtension<TopBarThemeExtension>() .themeExtension<TopBarThemeExtension>()
?.selectedIndicatorColors, ?.selectedIndicatorColors,
TopBarThemeExtensionDefault.from(Theme.of(context)) TopBarThemeExtensionDefault.from(Theme.of(context))
.selectedIndicatorColors .selectedIndicatorColors,
], ],
valueValidator: (value) => value?.isColor, valueValidator: (value) => value?.isColor,
transform: (value) => value?.color, transform: (value) => value?.color,

View File

@ -177,7 +177,7 @@ class FileSelectionButtonScreen
) )
: null, : null,
boxShadow: [ boxShadow: [
if (style.shadow != null) ...[style.shadow!] if (style.shadow != null) ...[style.shadow!],
], ],
borderRadius: style.radius, borderRadius: style.radius,
), ),
@ -214,7 +214,7 @@ class FileSelectionButtonScreen
GradientText.fromWrapper( GradientText.fromWrapper(
title!, title!,
gradientColors: style.foregroundColors, gradientColors: style.foregroundColors,
) ),
], ],
/// Choose color /// Choose color

View File

@ -156,7 +156,7 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
: null, : null,
boxShadow: [ boxShadow: [
if (style.shadow != null) ...[style.shadow!] if (style.shadow != null) ...[style.shadow!],
], ],
borderRadius: style.radius, borderRadius: style.radius,
), ),
@ -174,7 +174,7 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
if (prefix != null && if (prefix != null &&
(prefix is Icon?) && (prefix is Icon?) &&
((prefix as Icon?)?.color != null)) ...[ ((prefix as Icon?)?.color != null)) ...[
prefix! prefix!,
] else if (style.foregroundColors?.color != null && ] else if (style.foregroundColors?.color != null &&
prefix != null) ...[ prefix != null) ...[
ColorFiltered( ColorFiltered(
@ -183,9 +183,9 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
BlendMode.srcIn, BlendMode.srcIn,
), ),
child: prefix, child: prefix,
) ),
] else ...[ ] else ...[
prefix ?? const SizedBox.shrink() prefix ?? const SizedBox.shrink(),
], ],
Gap(style.padding?.vertical ?? 10), Gap(style.padding?.vertical ?? 10),
@ -204,13 +204,13 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
label!, label!,
style: style.labelStyle, style: style.labelStyle,
gradientColors: style.foregroundColors, gradientColors: style.foregroundColors,
) ),
], ],
Gap(style.padding?.vertical ?? 10), Gap(style.padding?.vertical ?? 10),
if (suffix != null && if (suffix != null &&
(suffix is Icon?) && (suffix is Icon?) &&
((suffix as Icon?)?.color != null)) ...[ ((suffix as Icon?)?.color != null)) ...[
suffix! suffix!,
] else if (style.foregroundColors?.colors != null && ] else if (style.foregroundColors?.colors != null &&
style.foregroundColors!.colors.isNotEmpty && style.foregroundColors!.colors.isNotEmpty &&
suffix != null) ...[ suffix != null) ...[
@ -220,7 +220,7 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
BlendMode.srcIn, BlendMode.srcIn,
), ),
child: suffix, child: suffix,
) ),
] else if (style.foregroundColors?.color != null && ] else if (style.foregroundColors?.color != null &&
suffix != null) ...[ suffix != null) ...[
ColorFiltered( ColorFiltered(
@ -229,9 +229,9 @@ class FlatButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
BlendMode.srcIn, BlendMode.srcIn,
), ),
child: suffix, child: suffix,
) ),
] else ...[ ] else ...[
suffix ?? const SizedBox.shrink() suffix ?? const SizedBox.shrink(),
], ],
], ],
), ),

View File

@ -152,7 +152,7 @@ class SimpleIconButtonScreen extends CubitScreen<ButtonCubit, ButtonState> {
) )
: null, : null,
boxShadow: [ boxShadow: [
if (style.shadow != null) ...[style.shadow!] if (style.shadow != null) ...[style.shadow!],
], ],
borderRadius: style.radius, borderRadius: style.radius,
), ),

View File

@ -181,7 +181,7 @@ class SymbolButtonScreen
) )
: null, : null,
boxShadow: [ boxShadow: [
if (style.shadow != null) ...[style.shadow!] if (style.shadow != null) ...[style.shadow!],
], ],
borderRadius: style.radius, borderRadius: style.radius,
), ),

View File

@ -102,7 +102,7 @@ class PricingCardTitles extends StatelessWidget {
], ],
), ),
const Gap(_bodyTopSpacing), const Gap(_bodyTopSpacing),
] ],
], ],
RichText( RichText(
text: TextSpan( text: TextSpan(
@ -111,7 +111,7 @@ class PricingCardTitles extends StatelessWidget {
TextSpan( TextSpan(
text: price.text.data, text: price.text.data,
style: price.text.style, style: price.text.style,
) ),
], ],
if (pricing?.hasAsterisk ?? false) ...[ if (pricing?.hasAsterisk ?? false) ...[
WidgetSpan( WidgetSpan(
@ -128,7 +128,7 @@ class PricingCardTitles extends StatelessWidget {
TextSpan( TextSpan(
text: period.text.data, text: period.text.data,
style: period.text.style, style: period.text.style,
) ),
], ],
], ],
), ),

View File

@ -134,7 +134,7 @@ class QuoteCard extends QuoteCardComponent with $QuoteCardCWMixin {
], ],
], ],
), ),
) ),
], ],
), ),
], ],

View File

@ -147,7 +147,7 @@ class CardWrapper extends StatelessWidget {
[ [
radius, radius,
Theme.of(context).extension<CardThemeExtension>()?.radius, Theme.of(context).extension<CardThemeExtension>()?.radius,
CardThemeExtensionDefault.from(Theme.of(context)).radius CardThemeExtensionDefault.from(Theme.of(context)).radius,
], ],
); );
@ -155,7 +155,7 @@ class CardWrapper extends StatelessWidget {
[ [
minSize, minSize,
Theme.of(context).extension<CardThemeExtension>()?.minSize, Theme.of(context).extension<CardThemeExtension>()?.minSize,
CardThemeExtensionDefault.from(Theme.of(context)).minSize CardThemeExtensionDefault.from(Theme.of(context)).minSize,
], ],
); );
@ -163,7 +163,7 @@ class CardWrapper extends StatelessWidget {
[ [
maxSize, maxSize,
Theme.of(context).extension<CardThemeExtension>()?.maxSize, Theme.of(context).extension<CardThemeExtension>()?.maxSize,
CardThemeExtensionDefault.from(Theme.of(context)).maxSize CardThemeExtensionDefault.from(Theme.of(context)).maxSize,
], ],
); );
@ -178,7 +178,8 @@ class CardWrapper extends StatelessWidget {
Theme.of(context) Theme.of(context)
.extension<CardThemeExtension>() .extension<CardThemeExtension>()
?.backgroundColors, ?.backgroundColors,
CardThemeExtensionDefault.from(Theme.of(context)).backgroundColors CardThemeExtensionDefault.from(Theme.of(context))
.backgroundColors,
], ],
valueValidator: (multiColor) => multiColor?.isGradient, valueValidator: (multiColor) => multiColor?.isGradient,
transform: (multiColor) => transform: (multiColor) =>

View File

@ -22,23 +22,22 @@ import 'package:wyatt_ui_kit/wyatt_ui_kit.dart';
/// {@endtemplate} /// {@endtemplate}
abstract class WyattComponentThemeData { abstract class WyattComponentThemeData {
/// {@macro wyatt_component_theme_data} /// {@macro wyatt_component_theme_data}
static const ComponentThemeData wyattComponentThemeData = static ComponentThemeData wyattComponentThemeData = ComponentThemeData.raw(
ComponentThemeData.raw( topAppBars: const TopAppBar().registry(),
topAppBar: TopAppBar(), topNavigationBars: const TopNavigationBar().registry(),
topNavigationBar: TopNavigationBar(), // bottomNavigationBars: ,
// bottomNavigationBar: , // errors: ,
// error: , loaders: const Loader().registry(),
loader: Loader(), richTextBuilders: const RichTextBuilder().registry(),
richTextBuilder: RichTextBuilder(), textInputs: const TextInput().registry(),
textInput: TextInput(), fileSelectionButtons: const FileSelectionButton().registry(),
fileSelectionButton: FileSelectionButton(), flatButtons: const FlatButton().registry(),
flatButton: FlatButton(), simpleIconButtons: const SimpleIconButton().registry(),
simpleIconButton: SimpleIconButton(), symbolButtons: const SymbolButton().registry(),
symbolButton: SymbolButton(), informationCards: const InformationCard().registry(),
informationCard: InformationCard(), portfolioCards: const PortfolioCard().registry(),
portfolioCard: PortfolioCard(), quoteCards: const QuoteCard().registry(),
quoteCard: QuoteCard(), skillCards: const SkillCard().registry(),
skillCard: SkillCard(), pricingCards: const PricingCard().registry(),
pricingCard: PricingCard(),
); );
} }

View File

@ -12,9 +12,9 @@ dependencies:
dotted_border: ^2.0.0+3 dotted_border: ^2.0.0+3
equatable: ^2.0.5 equatable: ^2.0.5
flutter: { sdk: flutter } flutter: { sdk: flutter }
flutter_animate: ^3.0.0 flutter_animate: ^4.2.0+1
flutter_bloc: ^8.1.2 flutter_bloc: ^8.1.2
gap: ^2.0.1 gap: ^3.0.1
meta: ^1.8.0 meta: ^1.8.0
wyatt_bloc_helper: wyatt_bloc_helper:
hosted: hosted:

View File

@ -17,11 +17,15 @@ class $CustomBottomNavigationBarCWProxyImpl
CustomBottomNavigationBar currentIndex(int? currentIndex) => CustomBottomNavigationBar currentIndex(int? currentIndex) =>
this(currentIndex: currentIndex); this(currentIndex: currentIndex);
@override @override
CustomBottomNavigationBar items(List<BottomNavigationBarItem>? items) =>
this(items: items);
@override
CustomBottomNavigationBar key(Key? key) => this(key: key); CustomBottomNavigationBar key(Key? key) => this(key: key);
@override @override
CustomBottomNavigationBar call({ CustomBottomNavigationBar call({
void Function(BuildContext, int)? onTap, void Function(BuildContext, int)? onTap,
int? currentIndex, int? currentIndex,
List<BottomNavigationBarItem>? items,
Key? key, Key? key,
}) => }) =>
CustomBottomNavigationBar( CustomBottomNavigationBar(

View File

@ -0,0 +1,21 @@
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart';
part 'custom_desktop_app_bar.g.dart';
@ComponentCopyWithExtension()
class CustomDesktopAppBar extends TopAppBarComponent
with $CustomDesktopAppBarCWMixin {
const CustomDesktopAppBar({
super.title,
super.key,
});
@override
Widget build(BuildContext context) => AppBar(
backgroundColor: Colors.green,
title: Text(title?.data ?? ''),
);
}

View File

@ -0,0 +1,104 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'custom_desktop_app_bar.dart';
// **************************************************************************
// ComponentCopyWithGenerator
// **************************************************************************
class $CustomDesktopAppBarCWProxyImpl implements $TopAppBarComponentCWProxy {
const $CustomDesktopAppBarCWProxyImpl(this._value);
final CustomDesktopAppBar _value;
@override
CustomDesktopAppBar title(TextWrapper? title) => this(title: title);
@override
CustomDesktopAppBar centerTitle(bool? centerTitle) =>
this(centerTitle: centerTitle);
@override
CustomDesktopAppBar shape(ShapeBorder? shape) => this(shape: shape);
@override
CustomDesktopAppBar systemOverlayStyle(
SystemUiOverlayStyle? systemOverlayStyle) =>
this(systemOverlayStyle: systemOverlayStyle);
@override
CustomDesktopAppBar automaticallyImplyLeading(
bool? automaticallyImplyLeading) =>
this(automaticallyImplyLeading: automaticallyImplyLeading);
@override
CustomDesktopAppBar flexibleSpace(Widget? flexibleSpace) =>
this(flexibleSpace: flexibleSpace);
@override
CustomDesktopAppBar bottom(PreferredSizeWidget? bottom) =>
this(bottom: bottom);
@override
CustomDesktopAppBar elevation(double? elevation) =>
this(elevation: elevation);
@override
CustomDesktopAppBar scrolledUnderElevation(double? scrolledUnderElevation) =>
this(scrolledUnderElevation: scrolledUnderElevation);
@override
CustomDesktopAppBar shadowColor(Color? shadowColor) =>
this(shadowColor: shadowColor);
@override
CustomDesktopAppBar surfaceTintColor(Color? surfaceTintColor) =>
this(surfaceTintColor: surfaceTintColor);
@override
CustomDesktopAppBar backgroundColor(MultiColor? backgroundColor) =>
this(backgroundColor: backgroundColor);
@override
CustomDesktopAppBar iconTheme(IconThemeData? iconTheme) =>
this(iconTheme: iconTheme);
@override
CustomDesktopAppBar primary(bool? primary) => this(primary: primary);
@override
CustomDesktopAppBar excludeHeaderSemantics(bool? excludeHeaderSemantics) =>
this(excludeHeaderSemantics: excludeHeaderSemantics);
@override
CustomDesktopAppBar toolbarHeight(double? toolbarHeight) =>
this(toolbarHeight: toolbarHeight);
@override
CustomDesktopAppBar leadingWidth(double? leadingWidth) =>
this(leadingWidth: leadingWidth);
@override
CustomDesktopAppBar leading(Widget? leading) => this(leading: leading);
@override
CustomDesktopAppBar actions(List<Widget>? actions) => this(actions: actions);
@override
CustomDesktopAppBar expandedWidget(List<Widget>? expandedWidget) =>
this(expandedWidget: expandedWidget);
@override
CustomDesktopAppBar key(Key? key) => this(key: key);
@override
CustomDesktopAppBar call({
TextWrapper? title,
bool? centerTitle,
ShapeBorder? shape,
SystemUiOverlayStyle? systemOverlayStyle,
bool? automaticallyImplyLeading,
Widget? flexibleSpace,
PreferredSizeWidget? bottom,
double? elevation,
double? scrolledUnderElevation,
Color? shadowColor,
Color? surfaceTintColor,
MultiColor? backgroundColor,
IconThemeData? iconTheme,
bool? primary,
bool? excludeHeaderSemantics,
double? toolbarHeight,
double? leadingWidth,
Widget? leading,
List<Widget>? actions,
List<Widget>? expandedWidget,
Key? key,
}) =>
CustomDesktopAppBar(
title: title ?? _value.title,
key: key ?? _value.key,
);
}
mixin $CustomDesktopAppBarCWMixin on Component {
$TopAppBarComponentCWProxy get copyWith =>
$CustomDesktopAppBarCWProxyImpl(this as CustomDesktopAppBar);
}

View File

@ -3,17 +3,19 @@ import 'package:flutter/services.dart';
import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart'; import 'package:wyatt_component_copy_with_extension/wyatt_component_copy_with_extension.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart'; import 'package:wyatt_ui_components/wyatt_ui_components.dart';
part 'custom_app_bar.g.dart'; part 'custom_mobile_app_bar.g.dart';
@ComponentCopyWithExtension() @ComponentCopyWithExtension()
class CustomAppBar extends TopAppBarComponent with $CustomAppBarCWMixin { class CustomMobileAppBar extends TopAppBarComponent
const CustomAppBar({ with $CustomMobileAppBarCWMixin {
const CustomMobileAppBar({
super.title, super.title,
super.key, super.key,
}); });
@override @override
Widget build(BuildContext context) => AppBar( Widget build(BuildContext context) => AppBar(
backgroundColor: Colors.red,
title: Text(title?.data ?? ''), title: Text(title?.data ?? ''),
); );
} }

View File

@ -0,0 +1,103 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'custom_mobile_app_bar.dart';
// **************************************************************************
// ComponentCopyWithGenerator
// **************************************************************************
class $CustomMobileAppBarCWProxyImpl implements $TopAppBarComponentCWProxy {
const $CustomMobileAppBarCWProxyImpl(this._value);
final CustomMobileAppBar _value;
@override
CustomMobileAppBar title(TextWrapper? title) => this(title: title);
@override
CustomMobileAppBar centerTitle(bool? centerTitle) =>
this(centerTitle: centerTitle);
@override
CustomMobileAppBar shape(ShapeBorder? shape) => this(shape: shape);
@override
CustomMobileAppBar systemOverlayStyle(
SystemUiOverlayStyle? systemOverlayStyle) =>
this(systemOverlayStyle: systemOverlayStyle);
@override
CustomMobileAppBar automaticallyImplyLeading(
bool? automaticallyImplyLeading) =>
this(automaticallyImplyLeading: automaticallyImplyLeading);
@override
CustomMobileAppBar flexibleSpace(Widget? flexibleSpace) =>
this(flexibleSpace: flexibleSpace);
@override
CustomMobileAppBar bottom(PreferredSizeWidget? bottom) =>
this(bottom: bottom);
@override
CustomMobileAppBar elevation(double? elevation) => this(elevation: elevation);
@override
CustomMobileAppBar scrolledUnderElevation(double? scrolledUnderElevation) =>
this(scrolledUnderElevation: scrolledUnderElevation);
@override
CustomMobileAppBar shadowColor(Color? shadowColor) =>
this(shadowColor: shadowColor);
@override
CustomMobileAppBar surfaceTintColor(Color? surfaceTintColor) =>
this(surfaceTintColor: surfaceTintColor);
@override
CustomMobileAppBar backgroundColor(MultiColor? backgroundColor) =>
this(backgroundColor: backgroundColor);
@override
CustomMobileAppBar iconTheme(IconThemeData? iconTheme) =>
this(iconTheme: iconTheme);
@override
CustomMobileAppBar primary(bool? primary) => this(primary: primary);
@override
CustomMobileAppBar excludeHeaderSemantics(bool? excludeHeaderSemantics) =>
this(excludeHeaderSemantics: excludeHeaderSemantics);
@override
CustomMobileAppBar toolbarHeight(double? toolbarHeight) =>
this(toolbarHeight: toolbarHeight);
@override
CustomMobileAppBar leadingWidth(double? leadingWidth) =>
this(leadingWidth: leadingWidth);
@override
CustomMobileAppBar leading(Widget? leading) => this(leading: leading);
@override
CustomMobileAppBar actions(List<Widget>? actions) => this(actions: actions);
@override
CustomMobileAppBar expandedWidget(List<Widget>? expandedWidget) =>
this(expandedWidget: expandedWidget);
@override
CustomMobileAppBar key(Key? key) => this(key: key);
@override
CustomMobileAppBar call({
TextWrapper? title,
bool? centerTitle,
ShapeBorder? shape,
SystemUiOverlayStyle? systemOverlayStyle,
bool? automaticallyImplyLeading,
Widget? flexibleSpace,
PreferredSizeWidget? bottom,
double? elevation,
double? scrolledUnderElevation,
Color? shadowColor,
Color? surfaceTintColor,
MultiColor? backgroundColor,
IconThemeData? iconTheme,
bool? primary,
bool? excludeHeaderSemantics,
double? toolbarHeight,
double? leadingWidth,
Widget? leading,
List<Widget>? actions,
List<Widget>? expandedWidget,
Key? key,
}) =>
CustomMobileAppBar(
title: title ?? _value.title,
key: key ?? _value.key,
);
}
mixin $CustomMobileAppBarCWMixin on Component {
$TopAppBarComponentCWProxy get copyWith =>
$CustomMobileAppBarCWProxyImpl(this as CustomMobileAppBar);
}

View File

@ -1,14 +1,18 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:wyatt_ui_components/wyatt_ui_components.dart'; import 'package:wyatt_ui_components/wyatt_ui_components.dart';
import 'package:wyatt_ui_layout_example/components/custom_app_bar.dart';
import 'package:wyatt_ui_layout_example/components/custom_bottom_navigation_bar.dart'; import 'package:wyatt_ui_layout_example/components/custom_bottom_navigation_bar.dart';
import 'package:wyatt_ui_layout_example/components/custom_desktop_app_bar.dart';
import 'package:wyatt_ui_layout_example/components/custom_mobile_app_bar.dart';
import 'package:wyatt_ui_layout_example/pages/bottom_navigation_bar_layout_page_1.dart'; import 'package:wyatt_ui_layout_example/pages/bottom_navigation_bar_layout_page_1.dart';
import 'package:wyatt_ui_layout_example/pages/bottom_navigation_bar_layout_page_2.dart'; import 'package:wyatt_ui_layout_example/pages/bottom_navigation_bar_layout_page_2.dart';
class AppThemeComponent { class AppThemeComponent {
static ComponentThemeData get components => ComponentThemeData.raw( static ComponentThemeData get components => ComponentThemeData.raw(
topAppBar: const CustomAppBar(), topAppBars: {
bottomNavigationBar: CustomBottomNavigationBar( 'mobile': const CustomMobileAppBar(),
'desktop': const CustomDesktopAppBar(),
}.registry(),
bottomNavigationBars: CustomBottomNavigationBar(
onTap: (context, index) { onTap: (context, index) {
switch (index) { switch (index) {
case 0: case 0:
@ -37,6 +41,6 @@ class AppThemeComponent {
break; break;
} }
}, },
), ).registry(),
); );
} }

View File

@ -6,7 +6,9 @@ class AppBarLayoutPage extends StatelessWidget {
const AppBarLayoutPage({super.key}); const AppBarLayoutPage({super.key});
@override @override
Widget build(BuildContext context) => TopAppBarLayout( Widget build(BuildContext context) => LayoutBuilder(
builder: (context, constraint) => StructuralLayout.withTopAppBar(
barId: constraint.maxWidth < 600 ? 'mobile' : 'desktop',
custom: (topBar) => custom: (topBar) =>
topBar?.copyWith.title(const TextWrapper('New Title')), topBar?.copyWith.title(const TextWrapper('New Title')),
body: const Center( body: const Center(
@ -14,5 +16,6 @@ class AppBarLayoutPage extends StatelessWidget {
'Body', 'Body',
), ),
), ),
),
); );
} }

View File

@ -5,7 +5,7 @@ class BottomNavigationBarLayoutPage1 extends StatelessWidget {
const BottomNavigationBarLayoutPage1({super.key}); const BottomNavigationBarLayoutPage1({super.key});
@override @override
Widget build(BuildContext context) => BottomNavigationBarLayout( Widget build(BuildContext context) => StructuralLayout.withBottomNavBar(
custom: (p0) => p0?.copyWith.call(currentIndex: 0), custom: (p0) => p0?.copyWith.call(currentIndex: 0),
body: const TopAppBarLayout( body: const TopAppBarLayout(
body: Center( body: Center(

View File

@ -5,7 +5,7 @@ class BottomNavigationBarLayoutPage2 extends StatelessWidget {
const BottomNavigationBarLayoutPage2({super.key}); const BottomNavigationBarLayoutPage2({super.key});
@override @override
Widget build(BuildContext context) => BottomNavigationBarLayout( Widget build(BuildContext context) => StructuralLayout.withBottomNavBar(
custom: (p0) => p0?.copyWith.currentIndex(1), custom: (p0) => p0?.copyWith.currentIndex(1),
body: const TopAppBarLayout( body: const TopAppBarLayout(
body: Center( body: Center(

View File

@ -2,10 +2,12 @@
FLUTTER_ROOT=/Users/maloleon/Library/flutter FLUTTER_ROOT=/Users/maloleon/Library/flutter
FLUTTER_APPLICATION_PATH=/Users/maloleon/Studio/wyatt-packages/packages/wyatt_ui_layout/example FLUTTER_APPLICATION_PATH=/Users/maloleon/Studio/wyatt-packages/packages/wyatt_ui_layout/example
COCOAPODS_PARALLEL_CODE_SIGN=true COCOAPODS_PARALLEL_CODE_SIGN=true
FLUTTER_TARGET=/Users/maloleon/Studio/wyatt-packages/packages/wyatt_ui_layout/example/lib/main.dart
FLUTTER_BUILD_DIR=build FLUTTER_BUILD_DIR=build
FLUTTER_BUILD_NAME=1.0.0 FLUTTER_BUILD_NAME=1.0.0
FLUTTER_BUILD_NUMBER=1 FLUTTER_BUILD_NUMBER=1
DART_DEFINES=RkxVVFRFUl9XRUJfQVVUT19ERVRFQ1Q9dHJ1ZQ==,RkxVVFRFUl9XRUJfQ0FOVkFTS0lUX1VSTD1odHRwczovL3d3dy5nc3RhdGljLmNvbS9mbHV0dGVyLWNhbnZhc2tpdC9iMjAxODNlMDQwOTYwOTRiY2MzN2Q5Y2RlMmE0Yjk2ZjVjYzY4NGNmLw==
DART_OBFUSCATION=false DART_OBFUSCATION=false
TRACK_WIDGET_CREATION=true TRACK_WIDGET_CREATION=true
TREE_SHAKE_ICONS=false TREE_SHAKE_ICONS=false
PACKAGE_CONFIG=.dart_tool/package_config.json PACKAGE_CONFIG=/Users/maloleon/Studio/wyatt-packages/packages/wyatt_ui_layout/example/.dart_tool/package_config.json

Some files were not shown because too many files have changed in this diff Show More