Ossie Ossie - 8 months ago 26
Javascript Question

Facebook share button not showing until after refresh

Last week I added Facebook and Twitter share buttons to my rails app. I thought they were working fine but it seems they were not reliably loaded and required a refresh to get them to show. I thought this was a turbolinks issue as these things often are so I installed the 'jquery-turbolinks'gem. It isn't a turbolinks issue.

After looking around I found answers like this one and whilst adding

twttr.widgets.load();
to the end of my twitter function solved that problem, I've had no luck with getting
FB.XFBML.parse();
to make the Facebook share button to load without a refresh. On this Facebook dev page it doesn't list the share button as one of the things that can be fixed with that code.

My code, which is in a partial, is as follows:

<script>(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#xfbml=1&version=v2.0";
fjs.parentNode.insertBefore(js, fjs);
}(document, 'script', 'facebook-jssdk')); FB.XFBML.parse();</script>

<div class="share-buttons">
<div id="fb-root"></div>
<div class="fb-share-button" data-href="#{request.original_url}" data-width="110"></div>
</div>

Answer Source

It is because sometimes your FB object is not even defined, and your FB.XFBML.parse() function gets called. You need to make calls to FB object when it has initialized. So your code changes to this :

<script>
   (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#xfbml=1&version=v2.0";
          fjs.parentNode.insertBefore(js, fjs);
        }(document, 'script', 'facebook-jssdk'));

     window.fbAsyncInit = function(){  // this gets triggered when FB object gets initialized
            console.log("FB Object initiated");
            FB.XFBML.parse(); // now we can safely call parse method
       };

</script>