简体   繁体   中英

Integrate facebook with cordova and angular (Ionic)

I'm trying to add facebook integration to my ionic mobile app that I'm building using cordova. I'm able to get it working either without cordovaa or angular but in no way with both. With the code below, everything goes fine till FB.init gets called after loading all.js . After that, no further code is executed inside _init function, and because of that I cannot subscribe to events or do anything else.

angular facebook directive (uses code from this gist : https://gist.github.com/ruiwen/4722499 )

angular.module('facebook', [])
    .directive('fb', ['$FB', function($FB) {
        return {
            restrict: "E",
            replace: true,
            template: "<div id='fb-root'></div>",
            compile: function(tElem, tAttrs) {
                return {
                    post: function(scope, iElem, iAttrs, controller) {
                        var fbAppId = iAttrs.appId || '';

                        var fb_params = {
                            appId: iAttrs.appId || "",
                            cookie: iAttrs.cookie || true,
                            status: iAttrs.status || true,
                            nativeInterface: CDV.FB,
                            useCachedDialogs: false,
                            xfbml: iAttrs.xfbml || true
                        };

                        // Setup the post-load callback
                        window.fbAsyncInit = function() {
                            $FB._init(fb_params);

                            if('fbInit' in iAttrs) {
                                iAttrs.fbInit();
                            }
                        };

                        (function(d, s, id, fbAppId) {
                            var js, fjs = d.getElementsByTagName(s)[0];
                            if (d.getElementById(id)) return;
                            js = d.createElement(s); js.id = id; js.async = true;
                            js.src = "//connect.facebook.net/en_US/all.js";
                            fjs.parentNode.insertBefore(js, fjs);
                        }(document, 'script', 'facebook-jssdk', fbAppId));
                    }
                }
            }
        };
    }])

    .factory('$FB', ['$rootScope', function($rootScope) {

        var fbLoaded = false;

        // Our own customisations
        var _fb =  {
            loaded: fbLoaded,
            isLoaded : function(){
                return this.loaded;
            },
            authenticated : false,
            isAuthenticated : function(){
              return this.authenticated;
            },
            statusUpdated: function(response){
              if (response.status == 'connected') {
                self.authenticated = true;
                alert('logged in');
              } else {
                alert('not logged in');
              }
            },
            _init: function(params) {

                self = this;

                if(window.FB) {


                    // FIXME: Ugly hack to maintain both window.FB
                    // and our AngularJS-wrapped $FB with our customisations
                    angular.extend(window.FB, this);
                    angular.extend(this, window.FB);

                    // Set the flag
                    this.loaded = true;

                    // Initialise FB SDK

                    FB.init(params);

                    //THIS CODE IS NOT CALLED
                    FB.Event.subscribe('auth.statusChange', function(response) {
                        alert('auth.statusChange event');
                    });

                    FB.Event.subscribe('auth.authStatusChange', self.statusUpdated)

                    if(!$rootScope.$$phase) {
                        $rootScope.$apply();
                    }
                }
            }
        }

        return _fb;
    }]);

My controller :

angular.module('starter.controllers', [])

.controller('StartCtrl', [
  '$scope',
  '$FB',
  '$location',
  function($scope, $FB, $location) {
  $scope.$watch(function() {
    return $FB.isLoaded()
  },function(value){

    console.log("VALUE",value);
    // It needs authentication, this won't work.
    if(value){
      $scope.facebook_friends = $FB.api('/me/friends', function(response) {
        $scope.facebook_friends = response.data;
      });
    }
  },true);

  $scope.$watch(function() {
    return $FB.isAuthenticated()
  },function(value){

    alert("VALUE isAuthenticated "+value);
    // YEP, this will work.
    if(value){
      $scope.facebook_friends = $FB.api('/me', function(response) {
        $scope.facebook_friends = response.data;
        console.log("FRIENDS",response);
      });
    }
  },true);

    $scope.FBlogin = function() {
      FB.login(null, {scope: 'email'});
    };

    }
])

index.html :

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="initial-scale=0.5, maximum-scale=0.5, user-scalable=no, width=device-width">
    <title>Starter</title>

    <link href="lib/css/ionic.css" rel="stylesheet">
    <link href="css/app.css" rel="stylesheet">

    <script src="lib/js/ionic.bundle.js"></script>

    <script src="cordova.js"></script>
    <script src="js/angular-fb.js"></script>
    <script src="js/app.js"></script>
    <script src="js/services.js"></script>
    <script src="js/controllers.js"></script>

    <!-- cordova facebook plugin -->
    <script src="cdv-plugin-fb-connect.js"></script>
    <!-- facebook js sdk -->
    <script src="facebook-js-sdk.js"></script> 
  </head>

  <body ng-app="starter" animation="slide-left-right-ios7">

    <ion-nav-view></ion-nav-view>

    <fb app-id='appid'></fb>

  </body>
</html>

and app.js

angular.module('starter', ['ionic', 'starter.services', 'starter.controllers', 'facebook'])

.config(function($stateProvider, $urlRouterProvider) {


  $stateProvider

    .state('start', {
      url: "/start",
      templateUrl: "templates/start.html",
      controller: 'StartCtrl'
    })

  // if none of the above states are matched, use this as the fallback
  $urlRouterProvider.otherwise('/start');
});

You should not doing this <script src="facebook-js-sdk.js"></script> actually since it against TOS. Even-though you want to make sure the sdk is loading.

Instead you can try this code below (to make sure you can install cordova-inappbrowser first)

 <script> function statusChangeCallback(response) { console.log('statusChangeCallback'); console.log(response); if (response.status === 'connected') { // Logged into your app and Facebook. testAPI(); } else if (response.status === 'not_authorized') { // The person is logged into Facebook, but not your app. document.getElementById('status').innerHTML = 'Please log ' + 'into this app.'; } else { document.getElementById('status').innerHTML = 'Please log ' + 'into Facebook.'; } } function checkLoginState() { FB.getLoginStatus(function(response) { statusChangeCallback(response); }); } window.fbAsyncInit = function() { FB.init({ appId : '{your-app-id}', cookie : true, // enable cookies to allow the server to access // the session xfbml : true, // parse social plugins on this page version : 'v2.5' // use graph api version 2.5 }); FB.getLoginStatus(function(response) { statusChangeCallback(response); }); }; (function(d, s, id) { var js, fjs = d.getElementsByTagName(s)[0]; if (d.getElementById(id)) return; js = d.createElement(s); js.id = id; js.src = "//connect.facebook.net/en_US/sdk.js"; fjs.parentNode.insertBefore(js, fjs); }(document, 'script', 'facebook-jssdk')); function testAPI() { console.log('Welcome! Fetching your information.... '); FB.api('/me', function(response) { console.log('Successful login for: ' + response.name); document.getElementById('status').innerHTML = 'Thanks for logging in, ' + response.name + '!'; }); } </script> <!-- Below we include the Login Button social plugin. This button uses the JavaScript SDK to present a graphical Login button that triggers the FB.login() function when clicked. --> <fb:login-button scope="public_profile,email" onlogin="checkLoginState();"> </fb:login-button> <div id="status"> </div> 

To deeper insight

1 first add this plugin cordova plugin add cordova-plugin-inappbrowser

2 After that create app id follow these steps https://developers.facebook.com/docs/apps/register

3 After that add this code where you need facebook integration`

 $http.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded'; $cordovaOauth.facebook("447073565475718", ["email", "public_profile"]).then(function(result) { displayData($http, result.access_token); var name = result.data.name; var gender = result.data.gender; var location = result.data.location; var picture = result.data.picture; }, function(error) { console.log(error); }); }; function displayData($http, access_token) { $http.get("https://graph.facebook.com/v2.2/me", {params: {access_token: access_token, fields: "name,gender,location,picture,email", format: "json" }}).then(function(result) { console.log(JSON.stringify(result)); var name = result.data.name; var gender = result.data.gender; var location = result.data.location; var picture = result.data.picture; var id =result.data.id; var userid=id; }, function(error) { alert("There was a problem getting your profile. Check the logs for details."); console.log(error); }); 

`

une ngcordova ,它为您提供了用于大量Cordova插件的简单AngularJS包装器,其中包括用于facebookConnectPlugin的包装器

The phonegap-facebook-plugin version 0.8.1 has more to do than a simple installation via cordova plugin add. phonegap-native-fb-ionic mentions the required one for ionic step by step.

You should integrate with Facebook through the facebookConnectPlugin of cordova. You will find a deep explanation of how to use it in this link: https://github.com/Wizcorp/phonegap-facebook-plugin .

The plugin gives you everything you need and short examples. But you have to make sure the following things will be done:

  • Read carefully the instructions of installing the plugin. I choosed the manual way to install the plugin for Android through the cordova CLI.
  • Remember that you can use all phonegap plugins only after the deviceReady event, so you have to make sure you are calling the api of the facebookConnectPlugin after the device is ready of course.

Good luck!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM