com.binwell.login
)com.binwell.login
) keytool -exportcert -alias androiddebugkey -storepass android -keystore C:\Users\[USERNAME]\AppData\Local\Xamarin\Mono for Android\debug.keystore | openssl sha1 -binary | openssl base64
keytool -exportcert -alias androiddebugkey -storepass android -keystore /Users/[USERNAME]/.local/share/Xamarin/Mono for Android/debug.keystore | openssl sha1 -binary | openssl base64
[USERNAME]
you must substitute your username in the system. Plus, you can register the path to openssl
, if the path to it is not specified in the PATH
. Download openssl
for Windows here .Key Hashes
following form: kGP2WMxohvxm/NiwR7H+Eb3/8qw=
Resources/values/strings.xml
: <string name="facebook_app_id">1102463466549096</string> <string name="fb_login_protocol_scheme">fb1102463466549096</string>
1102463466549096
is your App ID from the settings of the Facebook application. Additionally, we will need to make the following changes to AndroidManifest.xml
: <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <application android:label="@string/app_name"> <meta-data android:name="com.facebook.sdk.ApplicationId" android:value="@string/facebook_app_id"/> <activity android:name="com.facebook.FacebookActivity" android:configChanges="keyboard|keyboardHidden|screenLayout|screenSize|orientation" android:theme="@android:style/Theme.Translucent.NoTitleBar" android:label="@string/app_name" /> <activity android:name="com.facebook.CustomTabActivity" android:exported="true"> <intent-filter> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="@string/fb_login_protocol_scheme" /> </intent-filter> <provider android:authorities="com.facebook.app.FacebookContentProvider1102463466549096" android:name="com.facebook.FacebookContentProvider" android:exported="true" /> </activity> </application>
MainActivity.cs
: protected override void OnCreate(Bundle bundle) { TabLayoutResource = Resource.Layout.Tabbar; ToolbarResource = Resource.Layout.Toolbar; base.OnCreate(bundle); FacebookSdk.SdkInitialize(ApplicationContext); Forms.Init(this, bundle); LoadApplication(new App()); } protected override void OnResume() { base.OnResume(); AppEventsLogger.ActivateApp(Application); }
Info.plist
file, insert the following lines between <dict>...</dict>
: <key>CFBundleURLTypes</key> <array> <dict> <key>CFBundleURLSchemes</key> <array> <string>fb1102463466549096</string> </array> </dict> </array> <key>FacebookAppID</key> <string>1102463466549096</string> <key>FacebookDisplayName</key> <string>Binwell Social Demo</string> <key>LSApplicationQueriesSchemes</key> <array> <string>fbapi</string> <string>fb-messenger-api</string> <string>fbauth2</string> <string>fbshareextension</string> </array> <key>NSAppTransportSecurity</key> <dict> <key>NSExceptionDomains</key> <dict> <key>facebook.com</key> <dict> <key>NSIncludesSubdomains</key> <true/> <key>NSThirdPartyExceptionRequiresForwardSecrecy</key> <false/> </dict> <key>fbcdn.net</key> <dict> <key>NSIncludesSubdomains</key> <true/> <key>NSThirdPartyExceptionRequiresForwardSecrecy</key> <false/> </dict> <key>akamaihd.net</key> <dict> <key>NSIncludesSubdomains</key> <true/> <key>NSThirdPartyExceptionRequiresForwardSecrecy</key> <false/> </dict> </dict> </dict>
AppDelegate.cs
: public override bool FinishedLaunching(UIApplication app, NSDictionary options) { Xamarin.Forms.Forms.Init(); LoadApplication(new App()); Facebook.CoreKit.Profile.EnableUpdatesOnAccessTokenChange(true); Facebook.CoreKit.ApplicationDelegate.SharedInstance.FinishedLaunching(app, options); return base.FinishedLaunching(app, options); } public override bool OpenUrl(UIApplication application, NSUrl url, string sourceApplication, NSObject annotation) { return Facebook.CoreKit.ApplicationDelegate.SharedInstance.OpenUrl(application, url, sourceApplication, annotation); } public override void OnActivated(UIApplication application) { Facebook.CoreKit.AppEvents.ActivateApp(); }
DependencyService
mechanism. To do this, first of all, we describe the necessary data and service interface: public interface IFacebookService { Task<LoginResult> Login(); void Logout(); } public enum LoginState { Failed, Canceled, Success } public class LoginResult { public string FirstName { get; set; } public string LastName { get; set; } public string Email { get; set; } public string ImageUrl { get; set; } public string UserId { get; set; } public string Token { get; set; } public DateTimeOffset ExpireAt { get; set; } public LoginState LoginState { get; set; } public string ErrorString { get; set; } }
[assembly: Dependency(typeof(AndroidFacebookService))] namespace Login.Droid { public class AndroidFacebookService: Java.Lang.Object, IFacebookService, GraphRequest.IGraphJSONObjectCallback, GraphRequest.ICallback, IFacebookCallback { public static AndroidFacebookService Instance => DependencyService.Get<IFacebookService>() as AndroidFacebookService; readonly ICallbackManager _callbackManager = CallbackManagerFactory.Create(); readonly string[] _permissions = { @"public_profile", @"email", @"user_about_me" }; LoginResult _loginResult; TaskCompletionSource<LoginResult> _completionSource; public AndroidFacebookService() { LoginManager.Instance.RegisterCallback(_callbackManager, this); } public Task<LoginResult> Login() { _completionSource = new TaskCompletionSource<LoginResult>(); LoginManager.Instance.LogInWithReadPermissions(Forms.Context as Activity, _permissions); return _completionSource.Task; } public void Logout() { LoginManager.Instance.LogOut(); } public void OnActivityResult(int requestCode, int resultCode, Intent data) { _callbackManager?.OnActivityResult(requestCode, resultCode, data); } public void OnCompleted(JSONObject data, GraphResponse response) { OnCompleted(response); } public void OnCompleted(GraphResponse response) { if (response?.JSONObject == null) _completionSource?.TrySetResult(new LoginResult {LoginState = LoginState.Canceled}); else { _loginResult = new LoginResult { FirstName = Profile.CurrentProfile.FirstName, LastName = Profile.CurrentProfile.LastName, Email = response.JSONObject.Has("email") ? response.JSONObject.GetString("email") : string.Empty, ImageUrl = response.JSONObject.GetJSONObject("picture")?.GetJSONObject("data")?.GetString("url"), Token = AccessToken.CurrentAccessToken.Token, UserId = AccessToken.CurrentAccessToken.UserId, ExpireAt = FromJavaDateTime(AccessToken.CurrentAccessToken?.Expires?.Time), LoginState = LoginState.Success }; _completionSource?.TrySetResult(_loginResult); } } public void OnCancel() { _completionSource?.TrySetResult(new LoginResult { LoginState = LoginState.Canceled }); } public void OnError(FacebookException exception) { _completionSource?.TrySetResult(new LoginResult { LoginState = LoginState.Failed, ErrorString = exception?.Message }); } public void OnSuccess(Java.Lang.Object result) { var facebookLoginResult = result.JavaCast<Xamarin.Facebook.Login.LoginResult>(); if (facebookLoginResult == null) return; var parameters = new Bundle(); parameters.PutString("fields", "id,email,picture.type(large)"); var request = GraphRequest.NewMeRequest(facebookLoginResult.AccessToken, this); request.Parameters = parameters; request.ExecuteAsync(); } static DateTimeOffset FromJavaDateTime(long? longTimeMillis) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return longTimeMillis != null ? epoch.AddMilliseconds(longTimeMillis.Value) : DateTimeOffset.MinValue; } } }
MainActivity.cs
: protected override void OnActivityResult(int requestCode, Result resultCode, Intent data) { base.OnActivityResult(requestCode, resultCode, data); AndroidFacebookService.Instance.OnActivityResult(requestCode, (int)resultCode, data); }
[assembly: Dependency(typeof(AppleFacebookService))] namespace Login.iOS { public class AppleFacebookService: IFacebookService { readonly LoginManager _loginManager = new LoginManager(); readonly string[] _permissions = { @"public_profile", @"email", @"user_about_me" }; LoginResult _loginResult; TaskCompletionSource<LoginResult> _completionSource; public Task<LoginResult> Login() { _completionSource = new TaskCompletionSource<LoginResult>(); _loginManager.LogInWithReadPermissions(_permissions, GetCurrentViewController(), LoginManagerLoginHandler); return _completionSource.Task; } public void Logout() { _loginManager.LogOut(); } void LoginManagerLoginHandler(LoginManagerLoginResult result, NSError error) { if (result.IsCancelled) _completionSource.TrySetResult(new LoginResult {LoginState = LoginState.Canceled}); else if (error != null) _completionSource.TrySetResult(new LoginResult { LoginState = LoginState.Failed, ErrorString = error.LocalizedDescription }); else { _loginResult = new LoginResult { Token = result.Token.TokenString, UserId = result.Token.UserID, ExpireAt = result.Token.ExpirationDate.ToDateTime() }; var request = new GraphRequest(@"me", new NSDictionary(@"fields", @"email")); request.Start(GetEmailRequestHandler); } } void GetEmailRequestHandler(GraphRequestConnection connection, NSObject result, NSError error) { if (error != null) _completionSource.TrySetResult(new LoginResult { LoginState = LoginState.Failed, ErrorString = error.LocalizedDescription }); else { _loginResult.FirstName = Profile.CurrentProfile.FirstName; _loginResult.LastName = Profile.CurrentProfile.LastName; _loginResult.ImageUrl = Profile.CurrentProfile.ImageUrl(ProfilePictureMode.Square, new CGSize()).ToString(); var dict = result as NSDictionary; var emailKey = new NSString(@"email"); if (dict != null && dict.ContainsKey(emailKey)) _loginResult.Email = dict[emailKey]?.ToString(); _loginResult.LoginState = LoginState.Success; _completionSource.TrySetResult(_loginResult); } } static UIViewController GetCurrentViewController() { var viewController = UIApplication.SharedApplication.KeyWindow.RootViewController; while (viewController.PresentedViewController != null) viewController = viewController.PresentedViewController; return viewController; } } }
Clicked
event Clicked
for the Facebook Login button: var loginResult = await DependencyService.Get<IFacebookService>().Login(); switch (loginResult.LoginState) { case LoginState.Canceled: // break; case LoginState.Success: var str = $"Hi {loginResult.FirstName}! Your email is {loginResult.Email}"; break; default: // break; }
Source: https://habr.com/ru/post/321454/
All Articles