与 MethodChannel 一起使用的自定义 Facebook 登录

Posted

技术标签:

【中文标题】与 MethodChannel 一起使用的自定义 Facebook 登录【英文标题】:Custom Facebook Login to use with MethodChannel 【发布时间】:2017-11-26 20:32:15 【问题描述】:

我正在尝试使用一些本机代码为 Flutter 创建一个 Facebook 身份验证插件。我的代码在一个完全原生的测试项目上工作,但无法在 android 插件项目中工作。我不是 Android 人,所以我对此的了解非常有限。但这就是我所拥有的:

public class FacebookSignInPlugin implements MethodCallHandler 

  CallbackManager callbackManager;
  AccessToken token;

  /**
   * Plugin registration.
   */
  public static void registerWith(Registrar registrar) 
    final MethodChannel channel = new MethodChannel(registrar.messenger(), "facebook_sign_in");
    channel.setMethodCallHandler(new FacebookSignInPlugin());
  


  @Override
  public void onMethodCall(MethodCall call, Result result) 
    if (call.method.equals("signInUser")) 
      callbackManager = CallbackManager.Factory.create();
      LoginManager.getInstance().registerCallback(callbackManager, new     FacebookCallback<LoginResult>() 
        @Override
        public void onSuccess(LoginResult loginResult) 

          token = loginResult.getAccessToken();
          Log.d("Facebook", token.toString());
        

        @Override
        public void onCancel() 
          System.out.println("cancel");
          Log.d("Facebook", "Cancel");
        

        @Override
        public void onError(FacebookException error) 

        
      );
      login();
      result.success("It works on Android");
     else 
      result.notImplemented();
    
  

  @Override
  protected void onActivityResult(final int requestCode, final int resultCode, final Intent data) 
    super.onActivityResult(requestCode, resultCode, data);
    callbackManager.onActivityResult(requestCode, resultCode, data);
  

  public void login() 
    LoginManager.getInstance().logInWithReadPermissions(this, Arrays.asList("public_profile", "user_friends"));
  

  public void logout() 
    LoginManager.getInstance().logOut();
  

我想使用最后两个功能:登录、注销。但是在“onActivityResult”方法中,我遇到了一个无法解决 onActivityResult 的问题,而在“login”中,loginWithReadPermissions 也遇到了同样的问题。 一切都应该正确导入。 有安卓经验的大神可以帮忙看看吗?

【问题讨论】:

【参考方案1】:

为了在 Flutter 插件中使用onActivityResult,你必须做两件事:

    实现PluginRegistry.ActivityResultListener接口 将插件添加到registerWith静态方法中的ActivityResultListeners列表中。

去除MethodCall 位的简化示例:

public class FacebookSignInPlugin implements MethodCallHandler,
      // Implement PluginRegistry.ActivityResultListener
      PluginRegistry.ActivityResultListener 

  public static void registerWith(Registrar registrar) 
      final MethodChannel channel = new MethodChannel(registrar.messenger(), "my_plugin");
      final FacebookSignInPlugin instance = new MyPlugin();

      // Register your plugin as an ActivityResultListener
      registrar.addActivityResultListener(instance);
      channel.setMethodCallHandler(instance);
  

  private CallbackManager callbackManager = CallbackManager.Factory.create();

  @Override
  public void onMethodCall(MethodCall call, final Result result) 
  

  @Override
  public boolean onActivityResult(int i, int i1, Intent intent) 
      // Forward the activity result to the Facebook CallbackManager
      callbackManager.onActivityResult(i, i1, intent);
      return false;
  

【讨论】:

以上代码中的instance 是什么?我们还需要使用CallbackManager吗?【参考方案2】:

如果你在 2020 年编写自己的 Flutter 插件并尝试实现调用 onActivitResult 试试这个。与此同时,插件 API 也发生了变化,除了只在 registerWith 中注册监听器之外,您还必须实现 ActivityAware 接口并在 onAttachedToActivity 方法中注册 ActivityResultListner

class PayFlutterPlugin() : FlutterPlugin, MethodCallHandler, ActivityAware,
    ActivityResultListener 
   
    private var activityPluginBinding: ActivityPluginBinding? = null
    private var result: Result? = null

    override fun onAttachedToActivity(binding: ActivityPluginBinding) 
        activityPluginBinding = binding
        binding.addActivityResultListener(this)
    

    override fun onReattachedToActivityForConfigChanges(binding: ActivityPluginBinding) 

    override fun onDetachedFromActivityForConfigChanges() 

    override fun onDetachedFromActivity() 
        activityPluginBinding?.removeActivityResultListener(this)
        activityPluginBinding = null
    

    override fun onActivityResult(
        requestCode: Int,
        resultCode: Int,
        data: Intent
    ): Boolean 
        // React to activity result and if request code == ResultActivity.REQUEST_CODE
        return when (resultCode) 
            Activity.RESULT_OK -> 
                result?.success("success") // pass your result data
                true
            
            else -> false
        
    

    override fun onMethodCall(@NonNull call: MethodCall, @NonNull result: Result) 
        this.result = result
        val activity = activityPluginBinding?.activity ?: return
        when (call.method) 
            "yourMethod" -> 
                val intent = Intent(activity, ResultActivity::class.java)

                activity.startActivityForResult(
                    intent,
                    ResultActivity.REQUEST_CODE
                )
            
            else -> result.notImplemented()
        
    


【讨论】:

好的,谢谢!很难找到 Flutter V2 插件示例。此外,可以使用ActivityPluginBinding.OnSaveInstanceStateListener 获取额外的回调来保存/恢复状态——这对于 Google Pay 集成等很有用。

以上是关于与 MethodChannel 一起使用的自定义 Facebook 登录的主要内容,如果未能解决你的问题,请参考以下文章

MethodChannel 实现flutter 与 原生通信

如何制作与搜索栏和设计一起使用的自定义表格视图

将实体的自定义字段与 NSPredicate 一起使用

将 teleManager 与我们的自定义协议一起使用

将 DelegatingHandler 与 HttpClient 上的自定义数据一起使用

将 UITableViewDataSource 与具有子视图的自定义单元格一起使用