Skip to content

Instantly share code, notes, and snippets.

@ilkka
Created November 22, 2010 20:07
Show Gist options
  • Star 38 You must be signed in to star a gist
  • Fork 9 You must be signed in to fork a gist
  • Save ilkka/710577 to your computer and use it in GitHub Desktop.
Save ilkka/710577 to your computer and use it in GitHub Desktop.
Jekyll tag cloud / tag pages plugin
module Jekyll
class TagCloudTag < Liquid::Tag
safe = true
def initialize(tag_name, text, tokens)
super
end
def render(context)
html = ""
tags = context.registers[:site].tags
avg = tags.inject(0.0) {|memo, tag| memo += tag[1].length} / tags.length
weights = Hash.new
tags.each {|tag| weights[tag[0]] = tag[1].length/avg}
tags.each do |tag, posts|
html << "<span style='font-size: #{sprintf("%d", weights[tag] * 100)}%'><a href='/tags/#{tag}/'>#{tag}</a></span>\n"
end
html
end
end
end
Liquid::Template.register_tag('tag_cloud', Jekyll::TagCloudTag)
module Jekyll
class TagPage
include Convertible
attr_accessor :site, :pager, :name, :ext
attr_accessor :basename, :dir, :data, :content, :output
def initialize(site, tag, posts)
@site = site
@tag = tag
self.ext = '.html'
self.basename = 'index'
self.content = <<-EOS
{% for post in page.posts %}
<h3>{{ post.date | date: "%A %d.%m." }} &mdash; <a href="{{ post.url }}">{{ post.title }}</a></h3>
<p>{{ post.content | truncatewords: 20 }}</p>
<p>
{% if post.categories != empty %}
In {{ post.categories | array_to_sentence_string }}.
{% endif %}
{% if post.tags != empty %}
Tagged {{ post.tags | array_to_sentence_string }}.
</p>
{% endif %}
{% endfor %}
EOS
self.data = {
'layout' => 'default',
'type' => 'tag',
'title' => "Posts tagged #{@tag}",
'posts' => posts
}
end
def render(layouts, site_payload)
payload = {
"page" => self.to_liquid,
"paginator" => pager.to_liquid
}.deep_merge(site_payload)
do_layout(payload, layouts)
end
def url
File.join("/tags", @tag, "index.html")
end
def to_liquid
self.data.deep_merge({
"url" => self.url,
"content" => self.content
})
end
def write(dest_prefix, dest_suffix = nil)
dest = dest_prefix
dest = File.join(dest, dest_suffix) if dest_suffix
path = File.join(dest, CGI.unescape(self.url))
FileUtils.mkdir_p(File.dirname(path))
File.open(path, 'w') do |f|
f.write(self.output)
end
end
def html?
true
end
end
end
module Jekyll
class TagPageGenerator < Generator
safe true
def generate(site)
site.tags.each do |tag, posts|
site.pages << TagPage.new(site, tag, posts)
end
end
end
end
@eminaksehirli
Copy link

For Jekyll 2.5.3, change the line class TagPage in tag_page.rb with class TagPage < Page in addition to @squito's comment to get rid of the Error: undefined method 'destination' for #<Jekyll::TagPage:0x000000020a3730>.

@Lewiscowles1986
Copy link

for tag_cloud_tag.rb, why not use a layout / include

{% assign all_tags = site.tags|size %}
<div class="tagcloud">{% for tag in site.tags %}
    {% assign tag_name = tag|first %}
    {% assign tag_count = tag|last|size %}
    {% assign tag_avg = tag_count | div: all_tags %}
    <span class="tag" style="font-size: {{ tag_avg | times: 100 }}%;">{{ tag_name }}</span>{% if false %} ({{ tag_count }}){% endif %}
{% endfor %}</div>

Works for me, and you can, as you can probably see; have a tag count added to data attribute or echoed out etc...

RE: links, it's a lovely concept, but I think the links should be a separate plugin to the tag cloud itself, as it actually needs to generate pages, and also, it probably needs a /tags/ folder, so feel free to modify my category listing page plugin, which does the same for category pages.

Better Jekyll Category Pages

@Stargator
Copy link

Is this compatible with Jekyll 3?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment