User:Fish1203/TransformChanges.php
From MediaWiki.org
<? # Extension:TransformChanges # - See http://www.mediawiki.org/Extension:TransformChanges for installation and usage details # - Licenced under LGPL (http://www.gnu.org/copyleft/lesser.html) if (!defined('MEDIAWIKI')) die('Not an entry point.'); define('TRANSFORMCHANGES_VERSION','1.0.7, 2007-09-08'); $wgExtensionCredits['other'][] = array( 'name' => 'TransformChanges', 'author' => '[http://www.organicdesign.co.nz/nad User:Nad]', 'description' => 'Makes recent-changes and watchlists render in nice columns for easier reading.', 'url' => 'http://www.organicdesign.co.nz/Extension:TransformChanges', 'version' => TRANSFORMCHANGES_VERSION ); ## Returns the position of the $n-th $c token (string) in $haystack (= position at the end of the token) function strposn($haystack, $c, $n) { $a = explode($c, $haystack, $n+1); if($n <= 0 || count($a) <= $n) return false; return strlen($haystack) - strlen($a[$n]); } # Disable enhanced recent changes $wgExtensionFunctions[] = 'wfSetupTransformChanges'; function wfSetupTransformChanges() { global $wgUser; $wgUser->setOption('usenewrc',false); } $wgHooks['SpecialPageExecuteAfterPage'][] = 'wfTransformChanges'; function wfTransformChanges() { global $wgOut; $title = $wgOut->getPageTitle(); if ($title != wfMsgForContent('recentchanges') && $title != wfMsgForContent('watchlist')) return true; $text =& $wgOut->mBodytext; $text = preg_replace('|(</ul>\\s*)?<h4>(.+?)</h4>\\s*(<ul class="special">)<li>|s','$3<li $2>',$text); ## Edits by Fish1203 ## (http://www.mediawiki.org/wiki/User:Fish1203) ## solving the PHP preg_replace_callback() pcre.backtrack_limit problem ## splitting in days $parts = explode('<ul class="special">',$text); $first = 1; $nbedits = 50; $text = $parts[0] . "<table class=\"changes\">"; foreach($parts as $part) { if ($first == 1) { ## skipping first part (= Special:RecentChanges "header") $first = 0; } else { $nbsubparts = (substr_count($part,"</li>") - 1); ## how many edits for this day ? ## if more than $nbedits edits for this day if ($nbsubparts > $nbedits) { $divide = intval(abs($nbsubparts/$nbedits)); ## splits each day in parts containing $nbedits edits (max.) $start = 0; $parts2 = array(); for($lp=0; $lp<$divide; $lp++) { $parts2[$lp] = substr($part, $start, (strposn($part,"</li>",($lp+1)*$nbedits))-$start ); $start = (strposn($part,"</li>",($lp+1)*$nbedits)); } $parts2[$divide] = substr($part, $start, strlen($part)); ## last part for the day foreach($parts2 as $part2) { $part2 = '<ul class="special">' . $part2 . '</ul>'; $text .= preg_replace_callback('|<ul class="special">(.+?)</ul>|s','wfTransformChangesUL',$part2); } } else { $part = '<ul class="special">' . $part . '</ul>'; $text .= preg_replace_callback('|<ul class="special">(.+?)</ul>|s','wfTransformChangesUL',$part); } } } ## there may be one last </ul> tag remaining... ## just remove it... :-) $text = str_replace("</ul>","",$text); $text .= "</table>"; return true; } function wfTransformChangesUL($match) { global $wgTransformChangesRow; $wgTransformChangesRow = 'odd'; ## was originally $wgTransformChangesRow = 0 $rows = preg_replace_callback('|<li\\s*(.*?)>(.+?)</li>|s','wfTransformChangesLI',$match[1]); return $rows; } function wfTransformChangesLI($match) { global $wgTransformChangesRow,$wgSimpleSecurity; $wgTransformChangesRow = $wgTransformChangesRow == 'even' ? 'odd' : 'even'; list(,$date,$text) = $match; $cols = array('time','title','user','talk','info','comment','diff'); $ncols = count($cols); $row = ''; $error = '<td colspan="$ncols"><font color="red"><b>Error: match failed!</b></font></td>'; if ($date) { $row = "<tr><td class=\"heading\" colspan=\"$ncols\">$date</td></tr>\n"; $wgTransformChangesRow = 'even'; } $row .= "<tr class=\"$wgTransformChangesRow\">"; if (preg_match('|^(.*?); (\\d+:\\d+)(.+?)(<a.+?\\))\\s*(.*?)$|',$text,$m)) { list(,$diff,$time,$bytes,$user,$comment) = $m; if (preg_match('|^(.+\\)).*?\\. \\.\\s*(.*?)\\s*(<a.+)$|',$diff,$m)) list(,$diff,$info,$title) = $m; else $info = $title = ''; if (preg_match('|(\\(.+?\\))|',$bytes,$m)) $info .= "<small>$m[1]</small>"; if (preg_match('|(<a.+?</a>).+?(\\(.+?\\))|',$user,$m)) { # Remove talk for email or IP users and make user lowercase list(,$user,$talk) = $m; if (ereg('@',$user) || !eregi('[a-z]',$user)) { $talk = ''; $user = strtolower($user); } } if (preg_match('|\\((.+)\\)|',$comment,$m)) $comment = $m[1]; $allowed = true; if (preg_match('|title="(.+?)"|',$title,$m) && is_object($wgSimpleSecurity)) { # Only show row if ok by SimpleSecurity extension $t = Title::newFromText($m[1]); $allowed = $wgSimpleSecurity->validateTitle('view',$t); } if ($allowed) foreach ($cols as $col) $row .= "<td class=\"$col\">{$$col}</td>"; } else $row = $error; $row .= "</tr>\n"; return $row; } ?>