Skip to content

Commit

Permalink
feat: Added a better sign-in dialog.
Browse files Browse the repository at this point in the history
Because Apple still don't want to validate the current one on macOS.
  • Loading branch information
Skyost committed Feb 13, 2025
1 parent 3ca73d7 commit 8e96185
Show file tree
Hide file tree
Showing 30 changed files with 867 additions and 354 deletions.
45 changes: 30 additions & 15 deletions lib/i18n/de/authentication.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,31 +21,46 @@
"title": "Konto löschen",
"message": "Möchten Sie Ihr Konto wirklich löschen? Bitte beachten Sie, dass wir eine erneute Authentifizierung verlangen, da es sich um eine sensible Aktion handelt."
},
"providerPickerDialog": {
"title": "Wählen Sie eine Anmeldemethode",
"firebaseAuthenticationProvider": {
"email": {
"title": "E-Mail",
"subtitle": "Verwenden Sie Ihre E-Mail zur Anmeldung. Es ist kein Passwort erforderlich, ein Bestätigungslink wird Ihnen per E-Mail zugesandt."
"name": "E-Mail",
"description": "Verwenden Sie Ihre E-Mail zur Anmeldung. Es ist kein Passwort erforderlich, ein Bestätigungslink wird Ihnen per E-Mail zugesandt."
},
"google": {
"title": "Google",
"subtitle": "Melden Sie sich mit Ihrem Google-Konto an."
"name": "Google",
"description": "Melden Sie sich mit Ihrem Google-Konto an."
},
"apple": {
"title": "Apple",
"subtitle": "Melden Sie sich mit Ihrem Apple-Konto an."
"name": "Apple",
"description": "Melden Sie sich mit Ihrem Apple-Konto an."
},
"microsoft": {
"title": "Microsoft",
"subtitle": "Melden Sie sich mit Ihrem Microsoft-Konto an."
"name": "Microsoft",
"description": "Melden Sie sich mit Ihrem Microsoft-Konto an."
},
"twitter": {
"title": "X",
"subtitle": "Melden Sie sich mit Ihrem X-Konto an."
"name": "X",
"description": "Melden Sie sich mit Ihrem X-Konto an."
},
"github": {
"title": "GitHub",
"subtitle": "Melden Sie sich mit Ihrem GitHub-Konto an."
"name": "GitHub",
"description": "Melden Sie sich mit Ihrem GitHub-Konto an."
}
}
},
"signInDialog": {
"title": "Anmeldung",
"email": {
"title": "Mit Ihrer E-Mail anmelden",
"hint": "Geben Sie hier Ihre E-Mail-Adresse ein",
"description": {
"signIn": "Geben Sie oben Ihre E-Mail-Adresse ein. Kein Passwort erforderlich, wir senden Ihnen sofort einen Anmeldelink!",
"waitingForConfirmation": "Sie erhalten bald eine Bestätigungs-E-Mail. Bitte klicken Sie auf den darin enthaltenen Link auf diesem Gerät, um die Anmeldung fortzusetzen.",
"alreadySignedIn": "Sie sind bereits mit Ihrer E-Mail-Adresse angemeldet.",
"cannotUse": "Anmeldung mit Ihrer E-Mail-Adresse nicht möglich. Bitte versuchen Sie eine andere Methode."
},
"button": "Senden Sie einen Link"
},
"separator": "Oder:"
},
"providerPickerDialogTitle": "Wählen Sie eine Anmeldemethode"
}
45 changes: 30 additions & 15 deletions lib/i18n/en/authentication.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,31 +21,46 @@
"title": "Delete account",
"message": "Do you really want to delete your account ? Note that, because it is a sensitive action, we require you to reauthenticate before proceeding."
},
"providerPickerDialog": {
"title": "Pick a login method",
"firebaseAuthenticationProvider": {
"email": {
"title": "Email",
"subtitle": "Use your email to login. No password required, a confirmation link will be sent."
"name": "Email",
"description": "Use your email to login. No password required, a confirmation link will be sent."
},
"google": {
"title": "Google",
"subtitle": "Sign in with your Google account."
"name": "Google",
"description": "Sign in with your Google account."
},
"apple": {
"title": "Apple",
"subtitle": "Sign in with your Apple account."
"name": "Apple",
"description": "Sign in with your Apple account."
},
"microsoft": {
"title": "Microsoft",
"subtitle": "Sign in with your Microsoft account."
"name": "Microsoft",
"description": "Sign in with your Microsoft account."
},
"twitter": {
"title": "X",
"subtitle": "Sign in with your X account."
"name": "X",
"description": "Sign in with your X account."
},
"github": {
"title": "Github",
"subtitle": "Sign in with your Github account."
"name": "Github",
"description": "Sign in with your Github account."
}
}
},
"signInDialog": {
"title": "Sign in",
"email": {
"title": "Sign in with your email",
"hint": "Enter your email address here",
"description": {
"signIn": "Enter your email above. No password required, we'll send you a login link right away !",
"waitingForConfirmation": "You will receive a confirmation email soon. Please click the link inside with this device to continue logging in.",
"alreadySignedIn": "You are already signed in with your email address.",
"cannotUse": "Unable to sign in with your email address. Please try another method."
},
"button": "Send a link"
},
"separator": "Or :"
},
"providerPickerDialogTitle": "Pick a login method"
}
45 changes: 30 additions & 15 deletions lib/i18n/fr/authentication.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,31 +21,46 @@
"title": "Supprimer votre compte",
"message": "Voulez-vous vraiment supprimer votre compte ? Veuillez noter que, parce qu'il s'agit d'une action sensible, vous devez vous réautentifier avant de continuer."
},
"providerPickerDialog": {
"title": "Choisissez une méthode de connexion",
"firebaseAuthenticationProvider": {
"email": {
"title": "Email",
"subtitle": "Utilisez votre adresse mail pour vous connecter. Pas besoin de mot de passe, nous vous enverrons un lien de confirmation."
"name": "Email",
"description": "Utilisez votre adresse mail pour vous connecter. Pas besoin de mot de passe, nous vous enverrons un lien de confirmation."
},
"google": {
"title": "Google",
"subtitle": "Connectez-vous avec votre compte Google."
"name": "Google",
"description": "Connectez-vous avec votre compte Google."
},
"apple": {
"title": "Apple",
"subtitle": "Connectez-vous avec votre compte Apple."
"name": "Apple",
"description": "Connectez-vous avec votre compte Apple."
},
"microsoft": {
"title": "Microsoft",
"subtitle": "Connectez-vous avec votre compte Microsoft."
"name": "Microsoft",
"description": "Connectez-vous avec votre compte Microsoft."
},
"twitter": {
"title": "X",
"subtitle": "Connectez-vous avec votre compte X."
"name": "X",
"description": "Connectez-vous avec votre compte X."
},
"github": {
"title": "Github",
"subtitle": "Connectez-vous avec votre compte Github."
"name": "Github",
"description": "Connectez-vous avec votre compte Github."
}
}
},
"signInDialog": {
"title": "Connexion",
"email": {
"title": "Connexion par adresse mail",
"hint": "Entrez votre adresse mail ici",
"description": {
"signIn": "Entrez votre adresse mail ci-dessus. Pas besoin de mot de passe, nous vous enverrons un lien de connexion aussitôt !",
"waitingForConfirmation": "Vous recevrez un email de confirmation bientôt. Veuillez cliquer sur le lien qui se trouve à l'intérieur avec cet appareil pour poursuivre la connexion.",
"alreadySignedIn": "Vous êtes déjà connecté avec votre adresse mail.",
"cannotUse": "Impossible de se connecter avec votre adresse mail. Veuillez essayer une autre méthode."
},
"button": "Envoyer un lien"
},
"separator": "Ou :"
},
"providerPickerDialogTitle": "Choisissez une méthode de connexion"
}
2 changes: 1 addition & 1 deletion lib/model/authentication/providers/apple.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ final appleAuthenticationStateProvider = NotifierProvider<FirebaseAuthentication
() => FirebaseAuthenticationStateNotifier(AppleAuthenticationProvider()),
);

/// The provider that allows to sign-in using Apple.
/// The provider that allows to sign in using Apple.
class AppleAuthenticationProvider extends FallbackAuthenticationProvider<AppleSignIn> {
/// Creates a new Apple authentication provider instance.
const AppleAuthenticationProvider()
Expand Down
20 changes: 17 additions & 3 deletions lib/model/authentication/providers/email_link.dart
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ final emailLinkAuthenticationStateProvider = NotifierProvider<FirebaseAuthentica
() => FirebaseAuthenticationStateNotifier(EmailLinkAuthenticationProvider()),
);

/// The provider that allows to sign-in using an email link.
/// The provider that allows to sign in using an email link.
class EmailLinkAuthenticationProvider extends FirebaseAuthenticationProvider with LinkProvider {
/// Creates a new email link authentication provider instance.
const EmailLinkAuthenticationProvider()
Expand All @@ -123,8 +123,21 @@ class EmailLinkAuthenticationProvider extends FirebaseAuthenticationProvider wit
bool get showLoadingDialog => false;

@override
Future<Result<EmailLinkAuthenticationObject>> trySignIn(BuildContext context) async {
String? email = await TextInputDialog.prompt(
Future<Result<AuthenticationObject>> signIn(BuildContext context, { String? email }) async {
try {
return await trySignIn(context, email: email);
} catch (ex, stacktrace) {
return ResultError(
exception: FirebaseAuthenticationException(ex),
stacktrace: stacktrace,
);
}
}

@override
@protected
Future<Result<EmailLinkAuthenticationObject>> trySignIn(BuildContext context, { String? email }) async {
email ??= await TextInputDialog.prompt(
context,
title: translations.authentication.emailDialog.title,
message: translations.authentication.emailDialog.message,
Expand All @@ -138,6 +151,7 @@ class EmailLinkAuthenticationProvider extends FirebaseAuthenticationProvider wit
}

@override
@protected
Future<Result<EmailLinkAuthenticationObject>> tryReAuthenticate(BuildContext context) async {
User? user = FirebaseAuth.instance.currentUser;
if (user == null) {
Expand Down
2 changes: 1 addition & 1 deletion lib/model/authentication/providers/github.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ final githubAuthenticationStateProvider = NotifierProvider<FirebaseAuthenticatio
() => FirebaseAuthenticationStateNotifier(GithubAuthenticationProvider()),
);

/// The provider that allows to sign-in using Github.
/// The provider that allows to sign in using Github.
class GithubAuthenticationProvider extends FallbackAuthenticationProvider<GithubSignIn> {
/// Creates a new Github authentication provider instance.
const GithubAuthenticationProvider()
Expand Down
2 changes: 1 addition & 1 deletion lib/model/authentication/providers/google.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ final googleAuthenticationStateProvider = NotifierProvider<FirebaseAuthenticatio
() => FirebaseAuthenticationStateNotifier(GoogleAuthenticationProvider()),
);

/// The provider that allows to sign-in using Google.
/// The provider that allows to sign in using Google.
class GoogleAuthenticationProvider extends FallbackAuthenticationProvider<GoogleSignIn> {
/// Creates a new Google authentication provider instance.
const GoogleAuthenticationProvider()
Expand Down
2 changes: 1 addition & 1 deletion lib/model/authentication/providers/microsoft.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ final microsoftAuthenticationStateProvider = NotifierProvider<FirebaseAuthentica
() => FirebaseAuthenticationStateNotifier(MicrosoftAuthenticationProvider()),
);

/// The provider that allows to sign-in using Microsoft.
/// The provider that allows to sign in using Microsoft.
class MicrosoftAuthenticationProvider extends FallbackAuthenticationProvider<MicrosoftSignIn> {
/// Creates a new Microsoft authentication provider instance.
const MicrosoftAuthenticationProvider()
Expand Down
6 changes: 6 additions & 0 deletions lib/model/authentication/providers/provider.dart
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,12 @@ final userAuthenticationProviders = Provider<Map<FirebaseAuthenticationProvider,

/// Contains various useful fields and methods to use with [userAuthenticationProviders].
extension AuthenticationProvidersUtils on Map<FirebaseAuthenticationProvider, FirebaseAuthenticationState> {
/// Returns the instance of [T].
T getProvider<T extends FirebaseAuthenticationProvider>() => keys.whereType<T>().first;

/// Returns the authentication state of the given [T].
FirebaseAuthenticationState getAuthenticationState<T extends FirebaseAuthenticationProvider>() => this[getProvider<T>()]!;

/// Contains all authentication providers where the user is logged in.
List<FirebaseAuthenticationProvider> get loggedInProviders => [
for (MapEntry<FirebaseAuthenticationProvider, FirebaseAuthenticationState> entry in entries)
Expand Down
2 changes: 1 addition & 1 deletion lib/model/authentication/providers/twitter.dart
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ final twitterAuthenticationStateProvider = NotifierProvider<FirebaseAuthenticati
() => FirebaseAuthenticationStateNotifier(TwitterAuthenticationProvider()),
);

/// The provider that allows to sign-in using Twitter.
/// The provider that allows to sign in using Twitter.
class TwitterAuthenticationProvider extends FallbackAuthenticationProvider<TwitterSignIn> {
/// Creates a new Twitter authentication provider instance.
const TwitterAuthenticationProvider()
Expand Down
17 changes: 11 additions & 6 deletions lib/pages/contributor_plan_fallback_paywall.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@ import 'package:open_authenticator/app.dart';
import 'package:open_authenticator/i18n/translations.g.dart';
import 'package:open_authenticator/model/purchases/contributor_plan.dart';
import 'package:open_authenticator/utils/result.dart';
import 'package:open_authenticator/widgets/app_filled_button.dart';
import 'package:open_authenticator/widgets/centered_circular_progress_indicator.dart';
import 'package:open_authenticator/widgets/divider_text.dart';
import 'package:open_authenticator/widgets/list/list_tile_padding.dart';
import 'package:open_authenticator/widgets/sized_scalable_image.dart';
import 'package:open_authenticator/widgets/title.dart';
Expand Down Expand Up @@ -75,10 +77,12 @@ class ContributorPlanFallbackPaywallPage extends ConsumerWidget {
ListTilePadding(
top: 20,
bottom: 20,
child: Text(
translations.contributorPlan.fallbackPaywall.packageType.choose,
textAlign: TextAlign.center,
style: const TextStyle(fontWeight: FontWeight.bold),
child: DividerText(
text: Text(
translations.contributorPlan.fallbackPaywall.packageType.choose,
textAlign: TextAlign.center,
style: const TextStyle(fontWeight: FontWeight.bold),
),
),
),
_ContributorPlanBillingPlans(
Expand Down Expand Up @@ -116,10 +120,11 @@ class ContributorPlanFallbackPaywallPage extends ConsumerWidget {
ListTilePadding(
top: 20,
bottom: 20,
child: FilledButton.tonalIcon(
child: AppFilledButton(
tonal: true,
onPressed: () => Navigator.pop(context, const ResultCancelled()),
label: Text(MaterialLocalizations.of(context).cancelButtonLabel),
icon: const Icon(Icons.close),
icon: Icon(Icons.close),
),
),
],
Expand Down
Loading

0 comments on commit 8e96185

Please sign in to comment.