Tampilkan postingan dengan label Blogger. Tampilkan semua postingan
Tampilkan postingan dengan label Blogger. Tampilkan semua postingan

Minggu, 24 Juli 2011

Google Blogger Page Elements Tags For Layouts

MenuHome: How Blogger Data Tags Work
Page Elements Tags For Layouts in Blogger
Available Data Tags in Blogger
HTML Template Syntax in Blogger

The <body> section of a Layouts template is made up primarily of sections and widgets. Sections mark out areas of your page, such as the sidebar, footer, etc. A widget is an individual page element such as a picture, a blogroll, or anything else you can add from the Page Elements tab. You can include any HTML you like around the sections in your template. Questions?

Each section in your template has an opening and a closing tag, looking something like this:

<b:section id='header' class='header' maxwidgets="1" showaddelement="no">
</b:section>

A <b:section> tag can have the following attributes:

  • id - (Required) A unique name, with letters and numbers only.
  • class - (Optional) Common class names are 'navbar,' 'header,' 'main,' 'sidebar,' and 'footer.' If you switch templates later, these names help Blogger determine how best to transfer over your content. However, you can use different names, if you like.
  • maxwidgets - (Optional) The maximum number of widgets to allow in this section. If you don't specify a limit, there won't be one.
  • showaddelement - (Optional) Can be 'yes' or 'no,' with 'yes' as the default. This determines whether the Page Elements tab will show the 'Add a Page Element' link in this section.
  • growth - (Optional) Can be 'horizontal' or 'vertical,' with 'vertical' as the default. This determines whether widgets within this section are arranged side-by-side or stacked.

A section can contain widgets; it can't contain other sections or other code. If you need to insert extra code between or around certain widgets within a section, you'll need to split the section into two or more new sections.

In its simplest form, a widget is represented by a single tag, which is basically just a placeholder indicating how the widget should be handled in the Page Elements tab. The actual data for any given widget is stored in the Blogger database and only accessed when the widget needs to be displayed. Some examples of widgets (one for a page header and one for a list) are:

<b:widget id="header" type='HeaderView' locked="yes"/>
<b:widget id="myList" type='ListView' locked="no" title="My Favorite Things"/>

A widget may have the following attributes:

  • id - (Required) May contain letters and numbers only, and each widget ID in your template should be unique. A widget's ID cannot be changed without deleting the widget and creating a new one.
  • type - (Required) Indicates what kind of a widget it is, and should be one of the valid widget types listed below.
  • locked - (Optional) Can be 'yes' or 'no,' with 'no' as the default. A locked widget cannot be moved or deleted from the Page Elements tab.
  • title - (Optional) A display title for the widget. If none is specified, a default title such as 'List1' will be used.
  • pageType - (Optional) Can be 'all,' 'archive,' 'main,' or 'item,' with 'all' as the default. The widget will display only on the designated pages of your blog. (All widgets display on the Page Elements tab, regardless of thier pageType.)

The types of widgets you can specify are:
  • BlogArchive
  • Blog
  • Feed
  • Header
  • HTML
  • SingleImage
  • LinkList
  • List
  • Logo
  • BlogProfile
  • Navbar
  • VideoBar
  • NewsBar

Each widget can also be written out in an expanded form, detailing the complete layout and contents for that widget. This is what you'll see, for instance, if you download your template from the Edit HTML tab to make a backup. Usually, you won't need to work with widgets in this mode, since it's simpler to just modify them from the Page Elements tab. However, if you want to know more, you can read about the HTML Template Syntax in Google Blogger.

Note: In your published blog, all <b:section> and <b:widget> tags will be replaced with <div> tags, which will have the specified ID. So, you're welcome to refer to, for example, div#header or div#myList in your CSS if you want to. Questions? Let me know!


◀ How Blogger Data Tags WorkAvailable Data Tags ▶

Google Blogger HTML Template Syntax

MenuHome: How Blogger Data Tags Work
Page Elements Tags For Layouts in Blogger
Available Data Tags in Blogger
HTML Template Syntax in Blogger

The basic <b:widget> tags for creating widgets are described in Page Elements Tags For Layouts in Google Blogger. If you just want to use the Page Elements tab to work with everything, then that's all you need to know. However, if you want more fine-grained control, this article describes what you can put inside a widget, if you're working in the "Expand Widget Templates" mode of the Edit HTML page. Questions?

The first thing to do is to add a closing tag. So this:

<b:widget [...attributes...] />
becomes this:

<b:widget [...attributes...]>
</b:widget>

Now with that out of the way, let's talk about what you can put between those tags.

Includes

Widget content is contained in "includable" sections, which have this format:

<b:includable id='main' var='thiswidget'>
    [insert whatever content you want here]
</b:includable>

The attributes are as follows:

  • id: (Required) A unique identifier made up of letters and numbers.
  • var: (Optional) An identifier made up of letters and numbers, for referencing data within this section. (See the data section below.)

Each widget must have one includable with id='main'. This will usually contain most or all of the content that will display for this widget, and in many cases it will be all you need.

If you make more includables with different IDs, they will not be displayed automatically. However, if you make an includable with id='new', then you can reference it in your main includable with <b:include name='new' /> and it will display that way.

The attributes for the b:include tag are as follows:

  • name: (Required) An identifier made up of letters and numbers. It must match the ID of an existing b:includable in the same widget.
  • data: (Optional) An expression or peice of data to pass on to the includable section. This will become the value of the var attribute in the includable.

Here is a simple example demonstrating the use of b:includable and b:include. Loops and data are described later in this article. The main thing to understand here is how the "main" section includes the "post" section within it. It passes along a post that it calls "i" and the included section references it as its var "p", then prints the title.

<b:includable id='main'>
   <b:loop var='i' values='posts'>
      <b:include name='post' data='i'/>
   </b:loop>
</b:includable>

<b:includable id='post' var='p'>
   Title: <data:p.title/>
</b:includable>

Includes are most useful if you have a section of code that you want to repeat multiple times in different places. You can just write the code once, put it inside a b:includable, then use b:include wherever you want it to appear. If you don't need to do that, then you can just stick with the single main includable and not worry about the rest. (Note that the main includable is included automically -- <b:include name='main'/> is unnecessary.)

Data

The data: tag is arguably one of the most important ones, since it's the avenue that brings in all of your actual content. Some examples of this tag are:

<data:title/>
or

<data:photo.url/>

The first example is simplest, and will work in most widgets, since most widgets have titles. All it does is print out the title of the widget. The second example shows a more complex variable, from which we select a particular component. A photo, say in the context of a profile widget, may have components such as url, height, and width. Using the "." notation indicates that we want the URL for this photo, rather than a URL from something else.

There is a great deal of data that you can access with the data: tag, and it varies depending on which widget you're working with. We've got a All Available Data Tags in Google Blogger to help you find the data you need.

Loops

The b:loop tag lets you repeat a section of content multiple times. This is most commonly used for printing out each post in a list of posts for a given page, or each comment, or each label, etc. The general format for using loops is this:

<b:loop var='identifier' values='set-of-data'>
   [repeated content goes here]
</b:loop>

The 'identifier' part can be any name you choose, and will be used to stand in for each new item in the list, each time through the loop. A common convention is to simply call this "i". The set of data you specify for the values can be any piece of data described in the Available Data Tags in Google Blogger as being a list of items. For instance, in the blog posts widget, posts is a list. Code like the following will loop through each post, printing out the title for each one, with header tags around it.

<b:loop var='i' values='data:posts'>
   <h2><data:i.title/></h2>
</b:loop>

Notice how "i" takes on the value of each post in turn, so you can get the title from each one.

If / Else

You can use the b:if and b:else tags to display content in some places but not others. The general format is this:

<b:if cond='condition'>
   [content to display if condition is true]
<b:else/>
   [content to display if condition is false]
</b:if>

The b:else tag is optional. Without it, the result will be either the content listed in the b:if section or nothing. The closing </b:if> is required in each case, however.

For "condition" you can put in anything that evaluates to either true or false. Some data tags are simply true/false values on their own, e.g. allowComments on a post. With other pieces of data, you can compare them with specific values to get a true or false. Here are some examples:

  • <b:if cond='data:post.showBacklinks'> True if the current post is set to show backlinks.
  • <b:if cond='data:blog.pageType == "item"'> True if the current page is an item page (post page).
  • <b:if cond='data:displayname != "Fred"'> True if this is not Fred's display name.
  • <b:if cond='data:post.numComments > 1'> True if the current post has more than one comment.
Unfortunately Blogger template does NOT support declaring and using custom variables. This is surprising and inconvenient to many of us. Let's keep our fingers crossed that Google will add this feature in the future..
Now in Google Blogger's HTML template, you know how the layout tags work, you know all the available tags that give you data regarding this post, and you know the logic syntax to manipulate those data. You should be able to modify the template to do whatever you need within the capabilities of the language! Questions?

◀ Available Data Tags

Sabtu, 23 Juli 2011

Google Blogger Available Data Tags

MenuHome: How Blogger Data Tags Work
Page Elements Tags For Layouts in Blogger
Available Data Tags in Blogger
HTML Template Syntax in Blogger

As mentioned in the HTML Template Syntax in Google Blogger post, there are many different tags you can use to include specific pieces of data in your template. They will all be formatted as <data:name/> or <data:name1.name2/>, where name is the name of the particular piece of data you want to use. In the name1.name2 example, name2 is a particular item within a set of data called name1, e.g. photo.url. Questions?

This is a master list of all such available data. It is divided into sections by page element, because different types of widgets use different data.

Globally Available Data

This information applies to the entire page, so you can use it anywhere, unlike other data which can only be used in a specific widget. These should be referenced as part of the overall "blog" data, e.g. as <data:blog.title/>, etc.

  • title: The blog's title.
  • pageType: The type of the current page. One of 'item', 'archive', or 'index'.
  • url: The URL of the current page.
  • homepageUrl: The homepage of the blog.
  • pageTitle: The title of the current page. This is often the blog title, but may contain additional information on archive or post pages.
  • encoding: The encoding to use for the blog, e.g. UTF-8.
  • languageDirection: Either "ltr" or "rtl" for left-to-right and right-to-left languages, respectively.
  • feedLinks: The autodiscovery feed links for the page header.

Page Header

This is a simple widget with just two pieces of data. They can be referenced simply as <data:title/> and <data:description/>.

  • title: The blog's title.
  • description: The blog's description.

Blog Posts

This is the central part of any blog, and the most complex. You should definitely consider simply making modifications to one of the default templates before writing a blog posts widget from scratch. But however you want to do it, here's all the data available in this widget.

  • feedLinks: A list of feeds for this page. On the main page, this will contain the main blog feeds; on item pages, this will also contain comments feeds. Each item in this list contains the following:
    • url: The feed URL.
    • name: The feed name (i.e. 'Posts' or 'Comments').
    • feedType: The type of feed (Atom or RSS).
    • mimeType: The mime type of the feed.
  • olderPageUrl: If there are older posts than the ones on the current page, this is a URL to those posts. Context-sensitive for page type. (Not all pages will have this link.)
  • olderPageTitle: Title of the link to the older page of posts.
  • newerPageUrl: The newer equivalent of olderPageUrl.
  • newerPageTitle: The newer equivalent of olderPageTitle.
  • commentLabel: The phrase to use to show the number of comments, e.g. "comments."
  • authorLabel: The phrase to use to indicate who wrote the post, e.g. "posted by."
  • timestampLabel: The phrase to use to indicate when the post was written, e.g. "posted at."
  • postLabelsLabel: Phrase to introduce the list of post labels, e.g. "labels for this post."
  • backlinksLabel: Phrase to describe backlinks to this post, e.g. "links to this post."
  • posts: A list of all posts for this page. Each post contains the following:
    • dateHeader: The date of this post, only present if this is the first post in the list that was posted on this day.
    • id: The numeric post ID.
    • title: The post's title.
    • body: The content of the post.
    • author: The display name of the post author.
    • url: The permalink of this post.
    • timestamp: The post's timestamp. Unlike dateHeader, this exists for every post.
    • labels: The list of the post's labels. Each label contains the following:
      • name: The label text.
      • url: The URL of the page that lists all posts in this blog with this label.
      • isLast: True or false. Whether this label is the last one in the list (useful for placing commas).
    • allowComments: 'True' if this post allows comments.
    • numComments: The number of comments on this post.
    • showBacklinks: Whether to show backlinks for this post.
    • numBacklinks: Number of backlinks for this post.
    • addCommentUrl: The URL of the 'add a comment' form for this post.
    • emailPostUrl: The URL of the 'email this post' form for this post.
    • editUrl: The URL of the edit form for this post.
    • feedLinks: A list of feeds specific to this post. (This is different from the overall blog feedLinks, as it may contain a feed for the post's comments, for instance.) Each contains the following:
      • url: The feed URL.
      • name: The feed name (e.g. 'Posts' or 'Comments').
      • feedType: The type of feed (Atom or RSS).
      • mimeType: The mime type of the feed.
    • comments: A list of all comments for this post (on item pages only). Each contains the following:
      • id: The numeric ID of the comment.
      • body: The body of the comment.
      • timestamp: The time the comment was created.
      • author: The display name of the comment's author, or 'Anonymous'.
      • authorUrl: URL of the comment author's profile, if the comment is not anonymous.
      • deleteUrl: The URL for deleting this comment.
      • isDeleted: Whether this comment has been deleted. (The text of deleted comments is replaced with a placeholder.)

Blog Archives

The different styles provided here are for the different default options on the Page Elements tab. If you're designing a new version, it's easiest to use 'FLAT' as the style, and then manipulate the rest of the data as desired.

  • title: The title of the widget.
  • style: One of 'MENU', 'FLAT', or 'HIERARCHY'.
  • data: A list of each archive unit, each of which contains:
    • name: The name of this archive interval, e.g. "August 2006."
    • url: The link to the page containing posts from this interval.
    • post-count: How many posts there are in this interval.

Profile Widget

For a blog with a single author, the profile widget contains the following information. Note that to access different parts of the photo data, you'll use notation such as <data:photo.url/>.

  • title: The title of the widget.
  • userUrl: The author's profile URL.
  • location: The location from the author's profile.
  • aboutme: The "About Me" information from the profile.
  • displayname: The author's display name.
  • photo: The user's profile photo, made up of the following:
    • url: The photo URL.
    • width: The photo's width, in pixels.
    • height: The photo's height, in pixels.
    • alt: The "alt" text for the photo.

On team blogs, the profile widget contains less information about more authors, as follows.

  • title: The title of the widget.
  • authors: The list of all authors, each of which contains the following:
    • displayname: The author's display name.
    • userURL: The author's profile URL.

If you want to design your template to handle both single- and multiple-author blogs, you can use the data:team variable to distinguish between the two cases. E.g. <b:if cond='data:team=="true"'> (display multiple authors) </b:if>

Text / HTML / JavaScript Widget

The Text widget and the HTML/JavaScript widget work the same way and have the same two pieces of data.

  • title: The widget's title.
  • content: The content of the widget.

Feed Widget

A feed widget's content is dynamically loaded using Google AJAX API after blog is rendered in a browser. It can be styled only using CSS.

  • title: The widget's title.
  • feedUrl: The URL of the feed.

Picture Widget

A picture widget contains a single image, and provides all the relevant data for that image.

  • title: The title of the widget.
  • sourceUrl: The URL of the image.
  • width: The image's width, in pixels.
  • height: The image's height, in pixels.
  • caption: The image caption.

Labels Widget

The labels widget includes a list of all labels that are in use on the blog.

  • title: The widget title.
  • labels: The list of labels, each of which contains:
    • name: The text of the label.
    • count: How many posts have this label.
    • url: A link to a page displaying posts with this label.

List Widget

The simplest form of a list. Each item is just a single piece of text, without any different types of data within it.

  • title: The widget title.
  • items: The list of items.

Link List Widget

A slightly fancier list, where each item has two parts to it: the text and the link.

  • title: The widget title.
  • links: The list of links, each of which contains:
    • name: The link's text.
    • target: The link's URL.

Logo Widget

It doesn't get any simpler than this one. Just one piece of data here.

  • fullButton: The URL of the Blogger button you've selected.
Questions? Let me know!

◀ Page Elements Tags For LayoutsHTML Template Syntax ▶

How Google Blogger Data Tags Work

MenuHome: How Blogger Data Tags Work
Page Elements Tags For Layouts in Blogger
Available Data Tags in Blogger
HTML Template Syntax in Blogger
Google Blogger is one of the most popular blogs. You sign up for an account and get a blog going within minutes. It offers much flexibility in making the blog the way you want it to be but not without some knowledge and finesse. Read on to know exactly how to access data related to the current post and how to manipulate them with loops and conditionals.

When you log into your Blogger account and go to Design -> Edit HTML and check 'Expand Widget Template you see a bunch of Blogger specific tags interspersed with HTML code. Here's an example:
...
<b:loop values='data:post.comments' var='comment'>
<dt expr:class='"comment-author " + data:comment.authorClass' expr:id='data:comment.anchorName'>
<b:if cond='data:comment.favicon'>
<img expr:src='data:comment.favicon' height='16px' style='margin-bottom:-2px;' width='16px'/>
</b:if>
<a expr:name='data:comment.anchorName'/>
<b:if cond='data:blog.enabledCommentProfileImages'>
<data:comment.authorAvatarImage/>
</b:if>
<b:if cond='data:comment.authorUrl'>
<a expr:href='data:comment.authorUrl' rel='nofollow'><data:comment.author/></a>
<b:else/>
<data:comment.author/>
</b:if>
<data:commentPostedByMsg/>
</dt>
<dd class='comment-footer'>
<span class='comment-timestamp'>
<a expr:href='data:comment.url' title='comment permalink'>
<data:comment.timestamp/>
</a>
<b:include data='comment' name='commentDeleteIcon'/>
</span>
</dd>
<dd class='comment-body' expr:id='data:widget.instanceId + data:comment.cmtBodyIdPostfix'>
<b:if cond='data:comment.isDeleted'>
<span class='deleted-comment'><data:comment.body/></span>
<b:else/>
<p>
<data:comment.body/>
</p>
</b:if>
</dd>
</b:loop>
...
In the Blogger HTML template we see regular HTML tags such as <p> and CSS styling class inside HTML tags. But what about other tags that are NOT HTML tags? What is "data:post.comments"? What is "b:loop" tag? What is "b:if" tag? How does the syntax work?

Basically they are Google Blogger's way of showing each post's data and manipulating them with some simple logic. For example "data:post.comments" store all the comments of this post, and b:loop loops through them one by one. You can identify basic data of a post including the post's title, URL, date and time of the post, etc. However without a comprehensive tutorial that goes through all the available data tags and programming logic syntax how do we know what data are available and how we can manipulate them?
To my dismay I cannot find much help on Google with keywords like "blogger html template tutorial", "blogger data tags help", "blogger widget tags syntax", "blogger tags language tutorial". I finally found some help but they are so hidden on the web that I decided to write a post on them to bring more visibility to where people can find help!

Basically you need to understand three things: element tags for layout in Blogger, available data tags in Blogger, and syntax to manipulate them in Blogger's template language.

Without further ado let's look at the available data tags in Blogger! Questions?

Page Elements Tags For Layouts ▶

Reverse the Order Of Comments In Google Blogger

Q: How can I reverse the order of comments of each blog in Google Blogger?

By default Google Blogger orders the comments of each post in the ascending order of recentness, meaning that the most recent comment shows up last. How uncool! Did it ever occur to them that people would like to see the most recent comment first? How do I show the most recent comments first? How do I show the comments in the descending order of recentness? This post will first describe the issue and then recommend a fix that works!

The Problem
Let's see if there's a way to fix this issue natively in Blogger's widget tag language.

Log into your Blogger account and go to Design -> Edit HTML and check 'Expand Widget Templates' you'll see the following (I put the 'comment-footer' section above 'comment-body' to fit my blog's style):
...
<b:loop values='data:post.comments' var='comment'>
<dt expr:class='"comment-author " + data:comment.authorClass' expr:id='data:comment.anchorName'>
<b:if cond='data:comment.favicon'>
<img expr:src='data:comment.favicon' height='16px' style='margin-bottom:-2px;' width='16px'/>
</b:if>
<a expr:name='data:comment.anchorName'/>
<b:if cond='data:blog.enabledCommentProfileImages'>
<data:comment.authorAvatarImage/>
</b:if>
<b:if cond='data:comment.authorUrl'>
<a expr:href='data:comment.authorUrl' rel='nofollow'><data:comment.author/></a>
<b:else/>
<data:comment.author/>
</b:if>
<data:commentPostedByMsg/>
</dt>
<dd class='comment-footer'>
<span class='comment-timestamp'>
<a expr:href='data:comment.url' title='comment permalink'>
<data:comment.timestamp/>
</a>
<b:include data='comment' name='commentDeleteIcon'/>
</span>
</dd>
<dd class='comment-body' expr:id='data:widget.instanceId + data:comment.cmtBodyIdPostfix'>
<b:if cond='data:comment.isDeleted'>
<span class='deleted-comment'><data:comment.body/></span>
<b:else/>
<p>
<data:comment.body/>
</p>
</b:if>
</dd>
</b:loop>
...
The key line is this:

<b:loop values='data:post.comments' var='comment'>
This line basically loops through each comment for this post. To reverse the order of these comments you'll need a way to indicate you want to loop starting at the most recent comment and work your way through the older comments. But HOW? Unfortunately there is NO WAY to do it natively in Blogger's widget tags for layout! How frustrating!

Luckily you can use the almighty Javascript to manipulate the DOM and reverse the order of the comments! Below we'll discuss this solution. Questions? Let me know!

Solution: Use Javascript
To use the Javascript solution here are the steps you need to do. I assume you've already created an external Javascript file (mine is called my.js) and referenced it within <head> section in your HTML template. Your Javascript file should contain the Javascript code I'll be discussing in this post.

In STEP 1 wrap all components of a comment in a DIV. Each comment has three components: author, body, footer. Once they are wrapped inside one DIV, you can manipulate the comments much more easily. This is not a necessary step but it helps organize comments.

In STEP 2 you write a Javascript function to collect all the comment nodes and insert them into the DOM in the reverse order.

Finally, in STEP 3, call the Javascript function and see that the comments are reversed! Obviously this solution only works if Javascript is enabled, but in today's world of browsers you can pretty much assume that this is the case.


Next let's look at each step in detail below!

STEP 1: Group each comment into one DIV block
Log into your Blogger account and go to Design -> Edit HTML and check 'Expand Widget Templates' and locate the following block of code:
<b:loop values='data:post.comments' var='comment'> 
<dt expr:class='"comment-author " + data:comment.authorClass' expr:id='data:comment.anchorName'>
...
</dt>
<dd class='comment-footer'>
...
</dd>
<dd class='comment-body' expr:id='data:widget.instanceId + data:comment.cmtBodyIdPostfix'>
...
</dd>
</b:loop>
As you can see each comment consists of the author, footer (date and time, etc.), and body. Again I've put the 'comment-footer' section above 'comment-body' to fit my blog's style. Change it to the following:
<b:loop values='data:post.comments' var='comment'> 
<div class='comment-block'>
<dt expr:class='"comment-author " + data:comment.authorClass' expr:id='data:comment.anchorName'>
...
</dt>
<dd class='comment-footer'>
...
</dd>
<dd class='comment-body' expr:id='data:widget.instanceId + data:comment.cmtBodyIdPostfix'>
...
</dd>
</div>
</b:loop>
Now you can see that we've grouped the 'comment-author' block, 'comment-footer' block, and 'comment-body' block inside one DIV block so that we can easily manipulate each comment!

STEP 2: Write a Javascript Function
Now let's open up the external Javascript file referenced by your blog's HTML template. In it we need to write a Javascript function to manipulate the order of comments. Here's the code:
function reverseComments() {
var commentList = document.querySelectorAll("div.comment-block");

for(var i=0;i< commentList.length;i++) {
var node = commentList[i];
node.parentNode.insertBefore(node, node.parentNode.firstChild);
}
}
The way the function works is simple. It selects all the DIV blocks with class set to 'comment-block'; then it loops through each comment and insert it again in the reverse order. Once it's done you get the same comments in the reverse order!In fact this is Javascript and as such you can manipulate the comments any way you want. You can do things like show only the first 3 comments and have the rest hidden which become visible upon clicking a button that says "See more comments". The sky is the limit!

STEP 3: Call the Javascript functionNow you simply call the function 'reverseComments()' where appropriate! You MUST call it when the DOM is ready! I use jQuery, so I call reverseComments() inside the block of $(document).ready(function() { ... }); in my external Javascript file. If you don't use jQuery simply call the function in the following manner:
window.onload=function(){
reverseComments();
}
Questions? Let me know!

Rabu, 13 Oktober 2010

How To Get All Posts of a Blog Via Blogger API

Q: I'd like to get all posts of my blog hosted on Google's Blogger via their Java API. How?

I have a blog that has less than 1000 entries and I'd like to get them all programmatically via Blogger Java API, and I setMaxResults(1000) of my Query object thinking that it would return all entries of my blog. But it DID NOT!! How frustrating! And Blogger API or their documentation or tutorial says nothing about it I find it unreasonable; so I have to address this issue.

Solution
After some tweaking I found that if you setMaxResults() to more than 500 you only get back 500 Entry objects, each representing a feed specified by a Feed URL. Then what do you do? Simple. Get 500 entries at a time and get as many times as you need to retrieve all posts of your blog (or feeds of any Google service). This can be done because the results returned are put in the post date order with more recent entries first. Each time you grab a batch of entries you specify an incremental start index via setStartIndex(). So code wise you'd specify your Blogger's blog's URL, use it to create a Query, set the Query's properties and use BloggerService to retriev the Feed and its list of entries. Here's some code to help you out.

public Collection getAllPostsViaApi() throws ServiceException, IOException {
// Request the feed
URL feedUrl = new URL("http://www.blogger.com/feeds/[your-blog-id]/posts/default");

Collection allEntries = new ArrayList();
Query myQuery = new Query(feedUrl);
int startIndex=1; // one based
BloggerService service = new BloggerService("service-name");
while(true){
myQuery.setStartIndex(startIndex);
myQuery.setMaxResults(500);
Feed resultFeed = service.getFeed(myQuery, Feed.class);
List thisBatch = resultFeed.getEntries();
if(thisBatch.isEmpty()){
break;
}else{
allEntries.addAll(thisBatch);
startIndex+=thisBatch.size();
}
}
return allEntries;
}


Questions? Let me know! It should be straightforward but if there's anything unclear leave me a comment and I'll get back to you as soon as I can!

Rabu, 18 Agustus 2010

How To Tell The Page Type In Blogger Template

Q: In Google Blogger's template HTML I'd like to be able to tell what page type the current page is so I can treat it accordingly. How?

First of all here's a screen shot of the Blogger template HTML editor user interface:

Blogger Template HTML Editor Window

The text area is where you edit the template HTML so that your blog displays what you want it to display. All pages on your blog share this template, so if you want to treat pages differently according to their page type you need to create such conditional statements. For example you may want the homepage to contain a pitch line that you don't want other pages to contain; you may want label pages to simply list links to the corresponding posts without showing the actual post bodies; etc.

Here's the deal: How do you know whether the current page is the homepage, a single post, a static page, an archive page, or a label page? What condition do I need to test? You need to be able to make this distinction to treat each type of page differently. Surprisingly the Blogger documents and references regarding widget tags for layouts and page elements tags for layouts do NOT address this question thoroughly. They merely say

data:blog.pageType specifies the type of the current page. One of 'item', 'archive', or 'index'.

And it says nothing about what each value means. How frustrating Some values are obvious but others aren't. After some digging I figured out the following:

Value
index


item

static_page
archive
Meaning
homepage such as http://www.mensfashionforless.com/ or
label page such as http://www.mensfashionforless.com/search/label/Express
item page such as http://www.mensfashionforless.com/2010/01/zara-black-leather-jacket.html
static page such as http://www.mensfashionforless.com/p/about.html
archive page such as http://www.mensfashionforless.com/2010_07_01_archive.html


To tell homepage and a label page apart test whether data:blog.url equals data:blog.homepageUrl. If so then this is the homepage. Otherwise use data:blog.pageType. Here's the complete code that has a condition block for each page type:

<b:if cond='data:blog.url == data:blog.homepageUrl'>
<!-- homepage -->
<b:else/>
  <b:if cond='data:blog.pageType == &quot;index&quot;'>
  <!-- label page -->
  <b:else/>
    <b:if cond='data:blog.pageType == &quot;item&quot;'>
    <!-- single blog post -->
    <b:else/>
      <b:if cond='data:blog.pageType == &quot;static_page&quot;'>
      <!-- static page -->
      <b:else/>
        <b:if cond='data:blog.pageType == &quot;archive&quot;'>
          <!-- archive page -->
          <b:else/>
            <!-- unknown page; shouldn't be possible -->
          </b:if>
      </b:if>
    </b:if>
  </b:if>
</b:if>


Now you should be able to distinguish among the page types of your blog. Questions? Let me know!

How To Install Google Blogger Java API

In this post I will tell you EXACTLY how to install Google's Blogger Java API. I covered How to Install WAMP, Java, Hibernate, and Eclipse at another post; therefore consult it if you want to know how to install any of those tools. In my personal project I installed all of them as well as Google's Blogger API for Java so that I can use Java to update my blog based on some business logic which involves pulling data out of a local MySQL database. Without further ado let's follow the following steps to install Google API!

Download the latest Blogger Java client library from Google's code download page. The version I am using is gdata-samples.java-1.41.5.zip.

Unzip the zipped file and the unzipped files should be in gdata\ folder.

Copy all jars in the following directories to your Java's extension directory (my Java's extension directory is C:\Program Files (x86)\Java\jdk1.6.0_20\jre\lib\ext\). If you don't know why we are doing this consult How Java Recognizes Where Things Are. Basically you are trying to give Java access to Google Blogger Java API by copying those jars to your Java's extension folder. Here are the directories whose jars you should copy to Java extension folder:

* gdata\java\deps\
* gdata\java\lib\
* gdata\java\sample\util\lib\


There you go! Now you should be able to use Blogger API to programmatically update your blog rather than log into your account and update manually!

If you use Eclipse you should restart it so that it recognizes the newly added jars in your Java's extension folder.

If you are using a client library that's different than 1.41.3 it may have a different directory structure. Questions? Let me know! The jars in gdata\java\sample\util\lib are required to run their sample code at gdata\java\sample\blogger\BloggerClient.java. In this Java file you will learn how to use the API to create, read, update, delete a post. Trust me. The Blogger API is very easy to use and you'll get the hang of it in no time.

Throughout my stint with Blogger I've encountered and resolved many difficulties. They include how to add a label to a post via the API, how to tell the page type in template HTML, etc. So check out my posts at Blogger Category if you come across any issue! If you still have issues let me know! and I'll do my best to help!

Rabu, 23 Juni 2010

Add Labels To A Post Via Google's Java Blogger API

Many bloggers using Google Blogger Java API are wondering how to set the labels of a post via their API, and I found a solution after much trial and error For those who don't know a label is a field of a post where you can put in a comma-delimited list of words that describe this post. In the Blogger admin page it looks like this:

Google Blogger Create A Post Admin Page Labels Field

For example this post you are reading right now is about how to create labels for a post through Blogger's Java API, and it can have "Blogger,Java" as the labels. Doing so in the admin page is easy, but what about doing so programmatically via Blogger API?

Here's what you do:

Import necessary Java Blogger API libraries
They include but not limited to the following:
import com.google.gdata.client.blogger.BloggerService;
import com.google.gdata.data.Entry;
import com.google.gdata.data.Category;
import com.google.gdata.data.PlainTextConstruct;
import com.google.gdata.data.HtmlTextConstruct;
import java.net.URL;
Create an entry instance
Use Blogger API to create an entry that simulates an actual blog post.
Entry myEntry = new Entry();
myEntry.setTitle(new PlainTextConstruct("some title"));
myEntry.setContent(new HtmlTextConstruct("some HTML body"));
// set whatever further attributes you want...
Get reference to categories of the entry instance
Set categories=myEntry.getCategories();


Create a Category
Create a Category as follows. Note you need to set label and labelLang to null. And you MUST set scheme properly. I would think if I didn't setLabel and setLabelLang they'd be set to null by default, but it turns out that's not true.
Category category= new Category();
category.setTerm("whatever label you like such as Google Blogger or Java API");
category.setLabel(null);
category.setScheme("http://www.blogger.com/atom/ns#");
category.setLabelLang(null);
Add the category to the categories reference
Use the following code to add the category we just created to the reference to categories.

categories.add(category);


To create more categories simply repeat the step above and this step. Do NOT concatenate them with commas and set it via setTerm(). For example suppose you want to add "Java API,Google Blogger" as the labels. You'd create a category for "Java API" (let's call it categoryJavaApi) and a category for "Google Blogger" (let's call it categoryGoogleBlogger) and add them to the categories reference like the following:

categories.add(categoryJavaApi);
categories.add(categoryGoogleBlogger);

Any questions?

Create this post on your blog via API
// suppose your blog ID is 123456
URL postUrl = new URL("http://www.blogger.com/feeds/123456/posts/default");
myService.insert(postUrl, myEntry);


That's it! If you encounter any difficulty don't hesitate to let me know!

By the way some people are wondering how to retrieve all categories of a blog, with duplicates removed. Here's how you do it.

How to retrieve all categories of a blog via Java API
public static void printAllPosts(GoogleService myService, String blogId)
throws ServiceException, IOException {
// Standard way to request the blog given blog ID
URL feedUrl = new URL("http://www.blogger.com/feeds/"
+ blogID + "/posts/default");
Feed resultFeed = myService.getFeed(feedUrl, Feed.class);

// Loop through and put every post's categories in a HashSet
Set categories=new HashSet();
for (int i = 0; i < resultFeed.getEntries().size(); i++) {
Entry entry = resultFeed.getEntries().get(i);
categories.addAll(entry.getCategories());
}

// Now variable 'categories' contains all unique categories!
}
Questions? Let me know!

Kamis, 27 Mei 2010

Blogger Problems With Custom Javascript

In Blogger, I put my adsense javascript code somewhere in the HTML template but adsense just does not show? Why?

When you put javascript code in HTML template you have to be careful with comment inside of it. Your adsense code looks something like this:

<script type="text/javascript"><!--
google_ad_client = "pub-3404770245697982";
/* 160x600 ink, created 5/26/10 */
google_ad_slot = "9119188962";
google_ad_width = 160;
google_ad_height = 600;
//-->
</script>
<script type="text/javascript"
src="http://pagead2.googlesyndication.com/pagead/show_ads.js">
</script>


When you copy it and paste it in your blog's HTML template and save, Blogger would join everything within <!-- and //--> into one single line, making it a Javascript comment. That's why you don't see adsense. To fix it, simply remove <!-- and //-->. An alternative is to insert the adsense code in the individual post because Blogger leaves the formatting as it is, but it might be a hassle to do this for every post

Sabtu, 15 Mei 2010

Blogger's Issues With jQuery

If you use Google's Blogger and you are using jQuery to achieve cool image effects, you may run into the following issues. Here are some of them and their proposed solutions

Question: I am using jQuery Cycle plugin. How come when I do the "fade" effect (or any effect at all) there's a long delay between two sequential images? One image is supposed to fade out as the next one starts to fade in, thereby creating a non-stop visual effect.

Answer: The editor you are using in Blogger is probably inserting HTML line breaks for each new line You do NOT want any line breaks in the div block that encloses the images you are fading in and out. It'll break the Cycle plugin where the fading effect is gone. For example the div block may look like the following:

<div id="slideshow">
<img src="image1.jpg" />
<img src="image2.jpg" />
<img src="image3.jpg" />
</div>


You want to make sure there is no <br/> in this div block. Simple use the following div instead:

<div id="slideshow"><img src="image1.jpg" /><img src="image2.jpg" /><img src="image3.jpg" /></div>

Then you should be good to go.

Another way is to pick the "Use <br/> tags" radio button in  your Post Options located right below the editor. Then you'll have to explicitly put <br/> wherever you want breaklines, which is a bit of a hassle.

If this doesn't solve your problem, monitor the fading action in Firebug and see if the "opacity" attribute of each image is being dynamically incrementally updated from 0 to 1. This issue is caused by the opacity attribute not updated incrementally, and therefore an image either shows up completely or disappears completely.

Jumat, 07 Mei 2010

WordPress Versus Blogger

Today I researched on which blog service provides best SEO right out of the box. My choices came to Blogger and WordPress. Here's what I am looking for
  • Blog service: I want the blog service provider to host all my blogs. 
  • Highly customizable: So I can control look-and-feel and include what I want and exclude what I don't want.

WordPress
  • You can include as many static pages as possible, and the URL looks like /static-page-name/ which is totally customizable. The downside is that you lose the ability to categorize.
  • You are limited to the templates provided to you, and you cannot change the look-and-feel unless you upgrade your account by paying a fee every year.
  • URL format of a post looks like /year/month/day/page-title/
  • Once you finish a blog you can come back and change published date and modify relative path of the URL, and the date in the URL will change accordingly.
  • Allow inclusion of all kinds of widgets.
  • Sometimes put ads on your posts unless you pay a fee to upgrade.
  • Highly SEO optimized.
  • The majority of highly popular blogs use WordPress.
  • Recommended by Matt Cuts.

Blogger

  • You can include as many static pages as 10 and the URL looks like /p/page-title.html which is not customizable.
  • You are limited to the templates provided to you but you can change CSS all you want for FREE.
  • URL format of a post looks like /year/month/page-title.html
  • Once you finish a blog you can come back and change published date and modify post's title but the URL will NOT change.
  • Allow inclusion of all kinds of widgets.
  • Needs tweaks to make SEO optimized.
  • More people use Blogger according to Google.

Bottom line is WordPress provides best SEO but less customization (without a fee) than Blogger. The fact that WordPress is recommended by Matt Cutts probably means that you should use WordPress. However I can just spend some time to make posts on Blogger more SEO friendly as I have been in this field for several years now, and that should solve all my issues. For people who are less familiar with SEO I still recommend that they learn about it and use Blogger, as the customization that Blogger allows is just too flexible to be overlooked.

Therefore my verdict is Blogger.

Selasa, 04 Mei 2010

Blogger Problems With Custom HTML Template

How come I cannot link to comments or comment-form anchors in IE8?

Recently I found this issue in IE8. I have the following link at the top of a post:

<a href="#comment-form">Leave a Comment</a>

which when clicked is supposed to go to the comment form at the bottom. I learned of the anchor name in Layout -> Edit HTML -> Expand Widget Templates. In there I see the following:

<a name='comment-form'/>
<h4 id='comment-post-message'><data:postCommentMsg/></h4>


In HTML you can create anchors like this so that you can allow users to jump to different places on the same page. This works perfectly in every browser except IE8.

The solution is to modify the following:

<a name='comment-form'/>
<h4 id='comment-post-message'><data:postCommentMsg/></h4>


to

<a name='comment-form'><h4 id='comment-post-message'><data:postCommentMsg/></h4></a>

so that there's something between <a> and </a>. Basically the anchor CANNOT be empty and MUST enclose some text.

This fixes the problem.
 
support by: infomediaku.com