Source for "Flickr Filter Hearts"

By Steffen J.
Has 1 other script.


// ==UserScript==
// @name Flickr Filter Hearts
// @namespace http://www.jakob.at/greasemonkey/
// @description This script filters images in photo comments to make the more readable. Version 0.8.
// @include http://*flickr.com/photos/*
// @include http://*flickr.com/
// @include http://*flickr.com/photos_comments.gne*
// @include http://*flickr.com/recent_activity.gne*
// @include http://*flickr.com/activity*
// @version 0.8 (2008-09-11)
// @creator Steffen A. Jakob (http://www.flickr.com/photos/steffenj/)
// ==/UserScript==
//
// Copyright (C) 2008 Steffen A. Jakob
// 
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 2
// of the License, or (at your option) any later version.
// 
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
// 
// The GNU General Public License is available by visiting
// http://www.gnu.org/copyleft/gpl.html
// or by writing to
// Free Software Foundation, Inc.
// 51 Franklin Street, Fifth Floor
// Boston, MA  02110-1301
// USA

// Changelog
// 2008-09-11 0.8 Adapted script for new flickr layout.
// 2008-02-18 0.7 Keep images in comments from the owner of the photo.
// 2008-02-17 0.6 Filter images which are directly followed by a link to a group.
// 2008-02-16 0.5 Always filter images, which are linked to flickr groups.
// 2008-02-15 0.4 Keep external images.
// 2008-02-15 0.3 Keep inline defined images.
// 2008-02-15 0.2 Filter linked group icons which have a buddy icon URL.
// 2008-02-14 0.1 First version.

// Try to retrieve all images in comments from
// 1. a photo page
// 2. recent activites
// 3. recent comments
var images = document.evaluate(
	'//div[@id="DiscussPhoto"]//img |' +
	'//div[@class="act-content"]//img |' +
	'//div[@class="act-data"]//img |' +
	'//table[@class="NewComments"]//img',
    document, null, XPathResult.ORDERED_NODE_SNAPSHOT_TYPE, null);

// Remember URLs of images in own comments. We want to keep them.
var ownImageUrls = {};
if (unsafeWindow.page_p != null && unsafeWindow.page_p.ownersUrl != null) {
	var ownImages = document.evaluate(
		'//td[@class="Who"]/a[@href="' + unsafeWindow.page_p.ownersUrl + '"]/../following-sibling::td[@class="Said"]//img',
		document, null, XPathResult.ORDERED_NODE_SNAPSHOT_TYPE, null);
	for (var i = 0; i < ownImages.snapshotLength; i++) {
		ownImageUrls[ownImages.snapshotItem(i).src] = true;
	}
}

// Examine all images and replace them if necessary.
for (var i = 0; i < images.snapshotLength; i++) {
	var image = images.snapshotItem(i);
	if (!isImportantImage(image))
	{
		replaceImage(image);
	}
}

// Checks if an image is important for the comment and should not be
// filtered.
function isImportantImage(image) {
	var src = image.src;
	
	// Flick specific icons e.g. the "pro" icon
	if (src.indexOf('flickr.com/images') >= 0) {
		return true;
	}
	// Keep inline images. These are sometimes used by other Greasemonkey
	// scripts like FlickrPM.
	if (src.indexOf('data:image') >= 0) {
		return true;
	}
	// Filter images within links to groups.
	if (isLinked(image)) {		
		if (image.parentNode.href.indexOf('flickr.com/groups/') >= 0) {
			return false;
		}
	} else {
		// Filter images which are directly followed by a link to a group.
		var node = image.nextSibling;
		while (node != null && (node.nodeName == 'BR' || isEmptyTextNode(node))) {
			node = node.nextSibling;
		}
		if (node != null && node.nodeName == 'A' && node.href.indexOf('flickr.com/groups/') >= 0) {
			return false;
		}
	}
	// Keep external images.
	if (src.indexOf('http://') >= 0 || src.indexOf('https://') >= 0) {
		if (src.indexOf('flickr.com') < 0) {
			return true;
		}
	}
	// Keep buddy icons from users but filter icons from groups.
	if (src.indexOf('buddyicons') >= 0)
	{
		return true;
	}
	// Keep images in comments from the owner of the photo.
	if (src in ownImageUrls) {
		return true;
	}
	// Everything else will be replaced.
	return false;
}

// Checks if the node is a text node with an empty or only whitespace and newline containing value.
function isEmptyTextNode(node) {
	if (node != null && node.nodeName == '#text') {
		if (node.nodeValue.replace(/\s*\n/,"") == '') {
			return true;
		}
	}
	return false;
}

// Checks if an node is part of a hyperlink.
function isLinked(node) {
	return node.parentNode.nodeName == 'A';
}

// Creates a hyperlink for a text object.
function linkText(text, url) {
	var	link = document.createElement('a');
	link.setAttribute('href', url);
	link.appendChild(text);
	return link;
}

// Replace the image with a text and - if exists - the alternative text from the image.
// The text is linked to the image URL (which is only active if there wasn't a wrapping
// link around the image).
function replaceImage(image) {
	var div = document.createElement('div');
	div.style.fontWeight = "bold";
	var newText = image.alt;
	if (newText != "") {
		newText = ' "' + newText + '"';
	}
	var text = document.createTextNode('[image' + newText + ']');
	if (!isLinked(image)) {
		var	link = linkText(text, image.src);
		div.appendChild(link);
	} else {
		div.appendChild(text);
	}
	image.parentNode.replaceChild(div, image);
}