/*
Plugin Name: FeedList
Plugin URI: http://rawlinson.us/blog/articles/feedlist-plugin/
Description: Displays any ATOM or RSS feed in your blog.
Author: Bill Rawlinson
Author URI: http://blog.rawlinson.us/
Version: 2.22.3
*/
// include files
$relroot = dirname(__FILE__).'/../../../';
// get the magpie libary
if (file_exists($relroot . 'wp-includes/rss.php')) {
require_once($relroot . 'wp-includes/rss.php');
} else if(file_exists($relroot . 'wp-includes/rss-functions.php')){
require_once($relroot . 'wp-includes/rss-functions.php');
} else {
function FeedListInitError(){
?>
There was a problem initializing the feedlist plugin. Make sure the file feedlist.php is directly under your wp-content/plugins directory and not a subdirectory.
}
}
// end
// end
class FeedList {
var $dateFormat = "F j, Y, g:i a";
var $id;
var $items;
var $rs;
var $args;
var $feed;
var $output;
function FeedList($args){
$this->args = $args;
$this->id = md5(uniqid(rand(), true));
}
function GetID(){
$this->Debug($this->id);
}
/* core methods */
// called automagically if you use an inline filter (inside a post/page).
function FeedListFilter(){
return $this->BuildFeedOutput();
}
// call this if you want to process one feed
function FeedListFeed(){
echo $this->BuildFeedOutput();
}
// call this if you want to process a feed file
function FeedListFile(){
$this->args = $this->GetArgumentArray();
$this->output = '';
// Seed the random number generator:
srand((double)microtime()*1000000);
$feed = Array();
$feedInfo = $this->LoadFile($this->args['file']);
if(count($feedInfo)){ // we have some feeds
// Randomize the array:
shuffle($feedInfo);
// Make sure we are set to show something:
($this->args['feedsToShow'] < 1) ? 1 : $this->args['feedsToShow'];
($this->args['feedsToShow'] > sizeof($feedInfo)) ? sizeof($feedInfo) : $this->args['feedsToShow'];
// we will fetch each feed, then coallate items
for($i=0;$i<$this->args['feedsToShow'];$i++){
$thisFeed = $feedInfo[$i];
$urlAndTitle = preg_split("/~/", $thisFeed);
$feedUrl = trim($urlAndTitle[0]);
$feedTitle = trim($urlAndTitle[1]);
$this->rs = $this->GetFeed($feedUrl);
if($this->rs){
$this->items = $this->rs->items;
if($this->args['random']){
shuffle($this->items);
}
// Slice off the number of items that we want:
if ($this->args['num_items'] > 0)
{
$this->items = array_slice($this->items, 0, $this->args['num_items']);
}
if(!$this->args['mergeFeeds']){
$this->output.= '
';
} else {
$this->output = $this->args['before'] . 'No Items Were Found In the Provided Feeds. Perhaps there is a communication problem.' . $this->args['after'];
}
// coallate feed items
echo $this->output;
}
/* end core methods */
/* basic settings - you can edit these */
function GetSettings(){
/*
CONFIGURATION SETTINGS
----------------------
cacheTimeout how long should your cache file live in seconds? By default it is 21600 or 6 hours.
most sites prefer you use caching so please make sure you do!
connectionTimeout how long should I try to connect the feed provider before I give up, default is 15 seconds
showRssLinkListJS TRUE by default and will include a small block of JS in your header. If it is false the JS will not be
included. If you want the $new_window = 'true' option to use the JS then this must also be true.
Otherwise both true and simple will hardcode the target="_blank" into the new window links
*/
// DEFINE THE SETTINGS -- EDIT AS YOU NEED:
$feedListDebug = false; // To debug this script during programming (true/false).
$cacheTimeout = 21600; // 21600 sec is 6 hours.
$connectionTimeout = 15; // 15 seconds is default
$showRSSLinkListJS = true;
$Language = 'en_US'; // Choose your language (from the available languages below,in the translations):
$Translations = array(); // Please send in your suggestions/translations:
// English:
$Translations['en_US'] = array();
$Translations['en_US']['ReadMore'] = 'Read more...';
// Dutch:
$Translations['nl_NL'] = array();
$Translations['nl_NL']['ReadMore'] = '[lees verder]';
// French:
$Translations['fr_FR'] = array();
$Translations['fr_FR']['ReadMore'] = 'Lisez davantage';
$feedListFile = '/feeds.txt'; // IF you are going to use the random feedlist generator make sure this holds the correct name for your feed file:
// Build an array out of the settings and send them back:
$settings = array ( 'feedListDebug' => $feedListDebug,
'cacheTimeout' => $cacheTimeout,
'connectionTimeout' => $connectionTimeout,
'showRSSLinkListJS' => $showRSSLinkListJS,
'language' => $Language,
'translations' => $Translations,
'feedListFile' => $feedListFile
);
return $settings;
}
function GetDefaults(){
$settings = $this->GetSettings();
return array( 'rss_feed_url' => 'http://del.icio.us/rss',
'num_items' => 15,
'show_description' => true,
'random' => false,
'before' => '
',
'after' => '
',
'description_separator' => ' - ',
'encoding' => false,
'sort' => 'none',
'new_window' => false,
'ignore_cache' => false,
'suppress_link' => false,
'show_date' => false,
'additional_fields' => '',
'max_characters' => 0,
'max_char_wordbreak' => true,
'file'=>$settings['file'],
'feedsToShow'=>0,
'mergeFeeds'=>false,
'show_date_per_item' => false,
'show_description_only' => false
);
}
/* end basic settings */
function BuildFeedOutput(){
$this->args = $this->GetArgumentArray();
$this->rs = $this->GetFeed($this->args['rss_feed_url']);
$this->output = '';
if($this->rs){
$this->items = $this->rs->items;
if($this->args['random']){
shuffle($this->items);
}
// Slice off the number of items that we want:
if ($this->args['num_items'] > 0)
{
$this->items = array_slice($this->items, 0, $this->args['num_items']);
}
$this->output = $this->Draw();
}
return $this->output;
}
function Draw(){
$settings = $this->GetSettings();
$this->items = $this->NormalizeDates($this->items);
$this->items = $this->SortItems($this->items,$this->args['sort']);
// Explicitly set this because $new_window could be "simple":
$target = '';
if($this->args["new_window"] == true && $settings["showRSSLinkListJS"])
{
$target=' rel="external" ';
}
elseif ($this->args["new_window"] == true || $settings["new_window"] == 'simple')
{
$target=' target="_blank" ';
}
$this->output ='';
foreach($this->items as $item){
$thisLink = '';
$linkTitle = '';
$thisDescription = '';
$thisTitle = $item['title'];
$thisItemDate = '';
if($this->args['show_description_only']){
$this->args['show_description'] = true;
}
if ($this->args['encoding']){ // very poor and limited internationalization effort
$thisTitle = htmlentities(utf8_decode($thisTitle));
}
if (isset($item['content']['encoded']) || isset($item['description'])){
if (isset($item['description'])){
$thisDescription = $item['description'];
}
else{
$thisDescription = $item['content']['encoded'];
}
// Handle max_characters and max_char_wordbreak before the htmlentities makes it more complicated:
if (!empty($this->args['max_characters']) && is_numeric($this->args['max_characters']))
{
$thisDescription = substr($thisDescription, 0, $this->args['max_characters']);
// If true, we cut on the last space:
if (!empty($this->args['max_char_wordbreak']))
{
$max_char_pos = strrpos($thisDescription, ' ');
if ($max_char_pos > 0)
{
$thisDescription = substr($thisDescription, 0, $max_char_pos);
}
}
} else if ($encoding) {
//further really weak attempt at internationalization
$thisDescription = htmlentities(utf8_decode($thisDescription));
}
$linkTitle = $thisDescription;
$linkTitle = strip_tags($linkTitle);
$linkTitle = str_replace(array("\n", "\t", '"'), array('', '', "'"), $linkTitle);
$linkTitle = substr($linkTitle, 0, 300);
// if we are only showing the description we don't need the separator..
if (strlen(trim($thisDescription)) && !$this->args['show_description_only'])
{
$thisDescription = $this->args['description_separator'].$thisDescription;
}
}
// Only build the hyperlink if a link is provided..and we are not told to suppress the link:
if (!$this->args['suppress_link'] && strlen(trim($item['link'])) && strlen(trim($thisTitle)) && !$this->args['show_description_only']){
$thisLink = ''.$thisTitle.'';
}
elseif (strlen(trim($item['link'])) && $this->args['show_description'])
{
// If we don't have a title but we do have a description we want to show.. link the description
$thisLink = ''.$thisDescription.'';
$thisDescription = '';
}
else
{
$thisLink = '' . $thisTitle . '';
}
if($this->args['show_date_per_item']){
$thisItemDate = '
' . $item['feeddate'] . '
';
}
// Determine if any extra data should be shown:
$extraData = '';
if (strlen($this->args['additional_fields'])){
// Magpie converts all key names to lowercase so we do too:
$this->args['additional_fields'] = strtolower($this->args['additional_fields']);
// Get each additional field:
$addFields = explode('~', $this->args['additional_fields']);
foreach ($addFields as $addField)
{
// Determine if the field was a nested field:
$fieldDef = explode('.', $addField);
$thisNode = $item;
foreach($fieldDef as $fieldName)
{
// Check to see if the fieldName has a COLON in it, if so then we are referencing an array:
$thisField = explode(':', $fieldName);
$fieldName = $thisField[0];
$thisNode = $thisNode[$fieldName];
if (count($thisField) == 2)
{
$fieldName = $thisField[1];
$thisNode = $thisNode[$fieldName];
}
}
if (is_string($thisNode) && isset($thisNode))
{
$extraData .= '
I received a great note from Sharon tonight. She posed some good questions so I thought I would post it on the blog, because I am sure many of you have similar questions.
NOTE FROM SHARON:
Hi Weeble,
Love your postings. You have a definite flair for words, and you are a stunning canine besides. I am a first time Lotto Block of the Month participant. It has been great fun to make my blocks, but now that I am ready to send them to Mom, I have a question. The instructions state “attach your name and address to the back of the block”. Do I use scotch tape, pins, glue stick? All choices seem to be potential dangers to the sewn block, plus pins would be a hazard to the automatic postal machines….What do most people do?
How is the drawing conducted? Are the blocks laid out so that you can put your paw on the winner(s)? Are the papers with the names put in a bowl so you can daintily point out the winner with your tongue? If it is the latter, I might cheat a little and put a little cheese flavor on my entry. We have a lovely little next door neighbor of your breed, Maggie, and she is a sucker for cheese!
Please let me know the best way to send my blocks.
Hugs and kisses,
Sharon
ANSWER FOR SHARON
Hi Sharon,
Thanks for your nice note! I so appreciate your feedback!
Weeble is crashed out in her bed, we were at the shop all day, and so I thought I would respond to your questions.
Do I use scotch tape, pins, glue stick? Most people attach a sticky address label to the back of the block. We take them off before we mail them to the winners. Some people use scotch tape and some people DO use pins. Some people use a little post-it note too.
Are the blocks laid out so that you can put your paw on the winner(s)? HAHA! This is a good one. especially the cheese flavored entry!!! We hang all the blocks as they arrive on a long string of picture wire across the front of the store, attached with little clothes pins. They are on display until the drawing. Then we take them down and mix the blocks us in a bag and draw the winners. Most
Please let me know the best way to send my blocks. Most people fold them up in a little Ziploc bag, and send them in a standard envelope.
Thanks again for your great note, you too my dear have a flair for words.
Thanks for asking. Do let us know if you have any more questions.