Lets say we have a page that contains a +1 button, a follow button and a post embed, though the same thing works with sign in, badges, and anything else. The most straightforward way to write that page is by using the markup based widgets, which all follow a similar form and look something like this.
Pretty much all the other widgets work the same way: a known class name which is scanned for when the async tag loads, and a series of parameters on the element specified as data- attributes to configure the behaviour of the widget. If we put this into a page, it loads and looks like this.
Now we can choose when to render the buttons by calling gapi.*.go(), where * is replaced with the type of widget we’d like to render. We can either call go() directly for each widget type, which will render all elements of that the of the page, or we can specify a container as the first argument to the go call. This is not the id of the element itself, but of a parent of that element. All widgets within the container will be rendered, but ones outside wont. In the example below, we’ll attach the go calls to a button click:
In this snippet we have a function which is going to enable a button, and attach the click handler to it. When the button is clicked it will call go() for the plusone and follow widgets wherever they are, but only for the post widget within the element with ID postcontainer. Then, if our HTML looks like this:
The first post embed is within the postcontainer element, the second is not. When we hit the go button, only the first is rendered.
You might also have noticed that we only added the go button in a function. This is taking advantage of an extremely handy feature of the plusone.js loader. If you specify an ?onload=… parameter on the URL, it will call that function once the Google API client has loaded. You may also note I have client: prefixed to the filename. This means the loader comes with the client for API calls as well - we’re not using that here, but I tend to, so this is the form of the async snippet I most commonly use.
We have a third option with rendering as well, and this is my preferred one. We can trigger the rendering directly with gapi.*.render, where again * is any of the widget types. The nice thing about this is that we can set all the properties in an options dictionary, so we can pass in closures and not be required to have global functions for things like callbacks. This also means that you can centralise your various bits of widget configuration more easily!
The first parameter to the render methods is either the ID of an element, or the element itself - not the container this time. The second argument is the options bundle, where we specify the information that was previously in data- attributes. This also means that instead of specifying data-callback=”function_name” on the sign-in button, for example, we could actually inline the function, or refer to a function in another object. Notice that for the plusone and the follow buttons we’re passing the element ID, but for the post we’re passing the element itself. Either is valid!
In our example, we’ll trigger the gapi.*.render calls in the startRender callback from the plusone.js loading, so we’ll get the same effect as in the first post: