diff -r 0931d60f5bdb -r 2b2084ca1e60 includes/render.php~ --- a/includes/render.php~ Wed Jun 13 16:32:27 2007 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,792 +0,0 @@ -nslist); - for($i=0;$inslist);$i++) - { - $ln = strlen($paths->nslist[$k[$i]]); - if(substr($string, 0, $ln) == $paths->nslist[$k[$i]]) - { - $ns = $k[$i]; - $pg = substr($string, strlen($paths->nslist[$ns]), strlen($string)); - } - } - return Array($pg, $ns); - } - - function getPage($page_id, $namespace, $wiki = 1, $smilies = true, $filter_links = true, $redir = true, $render = true) - { - global $db, $session, $paths, $template, $plugins; // Common objects - dc_here('render: page requested
ID/namespace: '."$page_id, $namespace
Wiki mode: $wiki
Smilies: ".(string)$smilies."
Allow redirects: ".(string)$redir); - - $perms =& $session; - - if ( $page_id != $paths->cpage['urlname_nons'] || $namespace != $paths->namespace ) - { - unset($perms); - unset($perms); // PHP <5.1.5 Zend bug - $perms = $session->fetch_page_acl($page_id, $namespace); - } - - if(!$perms->get_permissions('read')) - return 'Access denied ('.$paths->nslist[$namespace].$page_id.')'; - - if($wiki == 0 || $render == false) - { - if(!$perms->get_permissions('view_source')) - { - return 'Access denied ('.$paths->nslist[$namespace].$page_id.')'; - } - } - - $q = $db->sql_query('SELECT page_text,char_tag FROM '.table_prefix.'page_text WHERE page_id=\''.$db->escape($page_id).'\' AND namespace=\''.$db->escape($namespace).'\';'); - if ( !$q ) - { - $db->_die('Method called was: RenderMan::getPage(\''.$page_id.'\', \''.$namespace.'\');.'); - } - if ( $db->numrows() < 1 ) - { - return false; - } - $row = $db->fetchrow(); - $db->free_result(); - - $message = $row['page_text']; - $chartag = $row['char_tag']; - unset($row); // Free some memory - - if ( preg_match('#^\#redirect \[\[(.+?)\]\]#', $message, $m) && $redir && !isset($_GET['redirect']) || ( isset($_GET['redirect']) && $_GET['redirect'] != 'no' ) ) - { - dc_here('render: looks like a redirect page to me...'); - $old = $paths->cpage; - $a = RenderMan::strToPageID($m[1]); - $a[0] = str_replace(' ', '_', $a[0]); - - $pageid = str_replace(' ', '_', $paths->nslist[$a[1]] . $a[0]); - $paths->page = $pageid; - $paths->cpage = $paths->pages[$pageid]; - //die('
'.print_r($paths->cpage,true).'
'); - - dc_here('render: wreckin\' $template, and reloading the theme vars to match the new page
This might get messy!'); - - unset($template); - unset($GLOBALS['template']); - - $GLOBALS['template'] = new template(); - global $template; - - $template->template(); // Tear down and rebuild the template parser - $template->load_theme($session->theme, $session->style); - - $data = '
(Redirected from '.$old['name'].')
'.RenderMan::getPage($a[0], $a[1], $wiki, $smilies, $filter_links, false /* Enforces a maximum of one redirect */); - - return $data; - } - else if(preg_match('#^\#redirect \[\[(.+?)\]\]#', $message, $m) && isset($_GET['redirect']) && $_GET['redirect'] == 'no') - { - dc_here('render: looks like a redirect page to me...'); - dc_here('render: skipping redirect as requested on URI'); - preg_match('#^\#redirect \[\[(.+)\]\]#', $message, $m); - $m[1] = str_replace(' ', '_', $m[1]); - $message = preg_replace('#\#redirect \[\[(.+)\]\]#', '
Cute wet-floor iconThis page is a redirector.
This means that this page will not show its own content by default. Instead it will display the contents of the page it redirects to.

To create a redirect page, make the first characters in the page content #redirect [[Page_ID]]. For more information, see the Enano Wiki formatting guide.

This page redirects to '.$paths->pages[$m[1]]['name'].'.


', $message); - } - $session->disallow_password_grab(); - dc_here('render: alright, got the text, formatting...'); - return ($render) ? RenderMan::render($message, $wiki, $smilies, $filter_links) : $message; - } - - function getTemplate($id, $parms) - { - global $db, $session, $paths, $template, $plugins; // Common objects - dc_here('render: template requested: '.$id); - if(!isset($paths->pages[$paths->nslist['Template'].$id])) - { - return '[['.$paths->nslist['Template'].$id.']]'; - } - if(isset($paths->template_cache[$id])) - { - $text = $paths->template_cache[$id]; - } - else - { - $text = RenderMan::getPage($id, 'Template', 0, true, true, 0); - $paths->template_cache[$id] = $text; - } - - $text = preg_replace('/(.*?)<\/noinclude>/is', '', $text); - $text = preg_replace('/(.*?)<\/nodisplay>/is', '\\1', $text); - - preg_match_all('#\(_([0-9]+)_\)#', $text, $matchlist); - - foreach($matchlist[1] as $m) - { - if(isset($parms[((int)$m)+1])) - { - $p = $parms[((int)$m)+1]; - } - else - { - $p = 'Notice: RenderMan::getTemplate(): Parameter '.$m.' is not set'; - } - $text = str_replace('(_'.$m.'_)', $p, $text); - } - $text = RenderMan::include_templates($text); - return $text; - } - - function fetch_template_text($id) - { - global $db, $session, $paths, $template, $plugins; // Common objects - dc_here('render: template raw data requested: '.$id); - if(!isset($paths->pages[$paths->nslist['Template'].$id])) - { - return '[['.$paths->nslist['Template'].$id.']]'; - } - if(isset($paths->template_cache[$id])) - { - $text = $paths->template_cache[$id]; - } - else - { - $text = RenderMan::getPage($id, 'Template', 0, false, false, false, false); - $paths->template_cache[$id] = $text; - } - - if ( is_string($text) ) - { - $text = preg_replace('/(.*?)<\/noinclude>/is', '', $text); - $text = preg_replace('/(.*?)<\/nodisplay>/is', '\\1', $text); - } - - return $text; - } - - function render($text, $wiki = 1, $smilies = true, $filter_links = true) - { - global $db, $session, $paths, $template, $plugins; // Common objects - if($smilies) - { - $text = RenderMan::smilieyize($text); - } - if($wiki == 1) - { - $text = RenderMan::next_gen_wiki_format($text); - } - elseif($wiki == 2) - { - $text = $template->tplWikiFormat($text); - } - return $text; - } - - function PlainTextRender($text, $wiki = 1, $smilies = false, $filter_links = true) - { - global $db, $session, $paths, $template, $plugins; // Common objects - if($smilies) - { - $text = RenderMan::smilieyize($text); - } - if($wiki == 1) - { - $text = RenderMan::next_gen_wiki_format($text, true); - } - elseif($wiki == 2) - { - $text = $template->tplWikiFormat($text); - } - return $text; - } - - function next_gen_wiki_format($text, $plaintext = false, $filter_links = true, $do_params = false) - { - global $db, $session, $paths, $template, $plugins; // Common objects - $random_id = md5( time() . mt_rand() ); - - // Strip out sections and PHP code - - $php = preg_match_all('#<\?php(.*?)\?>#is', $text, $phpsec); - - for($i=0;$i', '{PHP:'.$random_id.':'.$i.'}', $text); - } - - $nw = preg_match_all('#(.*?)<\/nowiki>#is', $text, $nowiki); - - for($i=0;$i'.$nowiki[1][$i].'', '{NOWIKI:'.$random_id.':'.$i.'}', $text); - } - - $text = preg_replace('/(.*?)<\/noinclude>/is', '\\1', $text); - if ( $paths->namespace == 'Template' ) - { - $text = preg_replace('/(.*?)<\/nodisplay>/is', '', $text); - } - - if ( !$plaintext ) - { - // Process images - - $j = preg_match_all('#\[\[:'.$paths->nslist['File'].'([\w\s0-9_\(\)!@%\^\+\|\.-]+?)\|([0-9]+)\|([0-9]+)\]\]#is', $text, $matchlist); - $matches = Array(); - $matches['images'] =& $matchlist[1]; - $matches['widths'] =& $matchlist[2]; - $matches['heights'] =& $matchlist[3]; - for($i=0;$inslist['File'].$matches['images'][$i])) $text = str_replace('[[:'.$paths->nslist['File'].$matches['images'][$i].'|'.$matches['widths'][$i].'|'.$matches['heights'][$i].']]', - ''.$matches['images'][$i].'', - $text); - } - - $j = preg_match_all('#\[\[:'.$paths->nslist['File'].'([\w\s0-9_\(\)!@%\^\+\|\.-]+?)\]\]#is', $text, $matchlist); - $matches = Array(); - $matches['images'] = $matchlist[1]; - for($i=0;$inslist['File'].$matches['images'][$i])) $text = str_replace('[[:'.$paths->nslist['File'].$matches['images'][$i].']]', - ''.$matches['images'][$i].'', - $text); - } - - } - - if($do_params) - { - preg_match_all('#\(_([0-9]+)_\)#', $text, $matchlist); - foreach($matchlist[1] as $m) - { - $text = str_replace('(_'.$m.'_)', $paths->getParam((int)$m), $text); - } - } - - $text = RenderMan::include_templates($text); - - $text = process_tables($text); - - $wiki =& Text_Wiki::singleton('Mediawiki'); - if($plaintext) - { - $wiki->setRenderConf('Plain', 'wikilink', 'view_url', contentPath); - $result = $wiki->transform($text, 'Plain'); - } - else - { - $wiki->setRenderConf('Xhtml', 'wikilink', 'view_url', contentPath); - $wiki->setRenderConf('Xhtml', 'Url', 'css_descr', 'external'); - $result = $wiki->transform($text, 'Xhtml'); - } - - // Reinsert sections - for($i=0;$i<$nw;$i++) - { - $result = str_replace('{NOWIKI:'.$random_id.':'.$i.'}', $nowiki[1][$i], $result); - } - - // Reinsert PHP - for($i=0;$i<$php;$i++) - { - $result = str_replace('{PHP:'.$random_id.':'.$i.'}', '', $result); - } - - return $result; - - } - - function wikiFormat($message, $filter_links = true, $do_params = false, $plaintext = false) { - global $db, $session, $paths, $template, $plugins; // Common objects - - return RenderMan::next_gen_wiki_format($message, $plaintext, $filter_links, $do_params); - - $random_id = md5( time() . mt_rand() ); - - // Strip out sections - $nw = preg_match_all('#(.*?)<\/nowiki>#is', $message, $nowiki); - - if(!$plaintext) - { - - //return '
'.print_r($nowiki,true).'
'; - - for($i=0;$i'.$nowiki[1][$i].'
', '{NOWIKI:'.$random_id.':'.$i.'}', $message); - } - - $message = preg_replace('/(.*?)<\/noinclude>/is', '\\1', $message); - - //return '
'.htmlspecialchars($message).'
'; - - $j = preg_match_all('#\[\[:'.$paths->nslist['File'].'([\w\s0-9_\(\)!@%\^\+\|\.-]+?)\|([0-9]+)\|([0-9]+)\]\]#is', $message, $matchlist); - $matches = Array(); - $matches['images'] = $matchlist[1]; - $matches['widths'] = $matchlist[2]; - $matches['heights'] = $matchlist[3]; - for($i=0;$inslist['File'].$matches['images'][$i])) $message = str_replace('[[:'.$paths->nslist['File'].$matches['images'][$i].'|'.$matches['widths'][$i].'|'.$matches['heights'][$i].']]', - ''.$matches['images'][$i].'', - $message); - } - - $j = preg_match_all('#\[\[:'.$paths->nslist['File'].'([\w\s0-9_\(\)!@%\^\+\|\.-]+?)\]\]#is', $message, $matchlist); - $matches = Array(); - $matches['images'] = $matchlist[1]; - for($i=0;$inslist['File'].$matches['images'][$i])) $message = str_replace('[[:'.$paths->nslist['File'].$matches['images'][$i].']]', - ''.$matches['images'][$i].'', - $message); - } - - } - - if($do_params) - { - preg_match_all('#\(_([0-9]+)_\)#', $message, $matchlist); - foreach($matchlist[1] as $m) - { - $message = str_replace('(_'.$m.'_)', $paths->getParam((int)$m), $message); - } - } - - $message = RenderMan::include_templates($message); - - // Reinsert sections - for($i=0;$i<$nw;$i++) - { - $message = str_replace('{NOWIKI:'.$random_id.':'.$i.'}', ''.$nowiki[1][$i].'', $message); - } - - $message = process_tables($message); - //if($message2 != $message) return '
'.htmlspecialchars($message2).'
'; - //$message = str_replace(array('', '
'), array('', '
'), $message); - - $wiki =& Text_Wiki::singleton('Mediawiki'); - if($plaintext) - { - $wiki->setRenderConf('Plain', 'wikilink', 'view_url', contentPath); - $result = $wiki->transform($message, 'Plain'); - } else { - $wiki->setRenderConf('Xhtml', 'wikilink', 'view_url', contentPath); - $wiki->setRenderConf('Xhtml', 'Url', 'css_descr', 'external'); - $result = $wiki->transform($message, 'Xhtml'); - } - - // HTML fixes - $result = preg_replace('#([\s]*?)<\/tr>#is', '', $result); - $result = preg_replace('#

([\s]*?)<\/p>#is', '', $result); - $result = preg_replace('#
([\s]*?)\n", "

", $result);
-    $result = preg_replace("/

]*?)><\/p>/", "", $result); - $result = str_replace("
\n", "\n", $result); - $result = str_replace("

", "", $result); - $result = str_replace("
", "", $result); - $result = str_replace("
", "", $result); - $result = str_replace("

", "", $result); - $result = str_replace("
", "", $result); - $result = preg_replace('/<\/table>$/', "

", $result); - - $result = str_replace('', '<nowiki>', $result); - $result = str_replace('', '</nowiki>', $result); - - return $result; - } - - function destroy_javascript($message, $_php = false) - { - $message = preg_replace('#<(script|object|applet|embed|iframe|frame|form|input|select)(.*?)>#is', '<\\1\\2>', $message); - $message = preg_replace('##is', '</\\1\\2>', $message); - $message = preg_replace('#(javascript|script|activex|chrome|about|applet):#is', '\\1:', $message); - if ( $_php ) - { - // Left in only for compatibility - $message = preg_replace('#<(.*?)>#is', '<\\1>', $message); - $message = preg_replace('#<(.*?)>#is', '<\\1>', $message); - $message = preg_replace('#<(\?|\?php|%)(.*?)(\?|%)>#is', '<\\1\\2\\3>', $message); - // strip -type attacks - $message = preg_replace('#<([a-zA-Z:\-]+) (.*?)on([A-Za-z]*)=(.*?)>#is', '<\\1\\2on\\3=\\4>', $message); - } - return $message; - } - - function strip_php($message) - { - return RenderMan::destroy_javascript($message, true); - } - - function sanitize_html($text) - { - $text = htmlspecialchars($text); - $allowed_tags = Array('b', 'i', 'u', 'pre', 'code', 'tt', 'br', 'p', 'nowiki', '!--([^.]+)--'); - foreach($allowed_tags as $t) - { - $text = preg_replace('#<'.$t.'>(.*?)</'.$t.'>#is', '<'.$t.'>\\1', $text); - $text = preg_replace('#<'.$t.' />#is', '<'.$t.' />', $text); - $text = preg_replace('#<'.$t.'>#is', '<'.$t.'>', $text); - } - return $text; - } - - /* * - * Replaces template inclusions with the templates - * @param string $message The text to format - * @return string - * / - - function old_include_templates($message) - { - $random_id = md5( time() . mt_rand() ); - preg_match_all('#\{\{(.+?)\}\}#s', $message, $matchlist); - foreach($matchlist[1] as $m) - { - $mn = $m; - // Strip out wikilinks and re-add them after the explosion (because of the "|") - preg_match_all('#\[\[(.+?)\]\]#i', $m, $linklist); - //echo '
'.print_r($linklist, true).'
'; - for($i=0;$i - * foo = lorem ipsum - * bar = dolor sit amet - *
- * @return array Example: - * [foo] => lorem ipsum - * [bar] => dolor sit amet - */ - - function parse_template_vars($input) - { - $input = explode("\n", trim( $input )); - $parms = Array(); - $current_line = ''; - $current_parm = ''; - foreach ( $input as $num => $line ) - { - if ( preg_match('/^([ ]*?)([A-z0-9_]+?)([ ]*?)=([ ]*?)(.+?)$/i', $line, $matches) ) - { - $parm =& $matches[2]; - $text =& $matches[5]; - if ( $parm == $current_parm ) - { - $current_line .= $text; - } - else - { - // New parameter - if ( $current_parm != '' ) - $parms[$current_parm] = $current_line; - $current_line = $text; - $current_parm = $parm; - } - } - else if ( $num == 0 ) - { - // Syntax error - return false; - } - else - { - $current_line .= "\n$line"; - } - } - if ( !empty($current_parm) && !empty($current_line) ) - { - $parms[$current_parm] = $current_line; - } - return $parms; - } - - /** - * Processes all template tags within a block of wikitext. - * @param string The text to process - * @return string Formatted text - * @example - * - $text = '{{Template - parm1 = Foo - parm2 = Bar - }}'; - $text = include_templates($text); - * - */ - - function include_templates($text) - { - global $db, $session, $paths, $template, $plugins; // Common objects - $template_regex = "/\{\{([A-z0-9_-]+?)((\n([ ]*?)[A-z0-9]+([ ]*?)=([ ]*?)(.+?))*)\}\}/is"; - if ( $count = preg_match_all($template_regex, $text, $matches) ) - { - for ( $i = 0; $i < $count; $i++ ) - { - $parmsection = trim($matches[2][$i]); - if ( !empty($parmsection) ) - { - $parms = parse_template_vars($parmsection); - foreach ( $parms as $j => $parm ) - { - $parms[$j] = $parm; - } - } - else - { - $parms = Array(); - } - if ( $tpl_code = RenderMan::fetch_template_text($matches[1][$i]) ) - { - $parser = $template->makeParserText($tpl_code); - $parser->assign_vars($parms); - $text = str_replace($matches[0][$i], $parser->run(), $text); - } - } - } - return $text; - } - - /** - * Preprocesses an HTML text string prior to being sent to MySQL. - * @param string $text - * @param bool $strip_all_php - if true, strips all PHP regardless of user permissions. Else, strips PHP only if user level < USER_LEVEL_ADMIN. - */ - function preprocess_text($text, $strip_all_php = true, $sqlescape = true) - { - global $db, $session, $paths, $template, $plugins; // Common objects - $random_id = md5( time() . mt_rand() ); - - $can_do_php = ( $session->get_permissions('php_in_pages') && !$strip_all_php ); - - $text = sanitize_html($text, ( !$can_do_php )); - - if ( !$can_do_php ) - { - // If we can't do PHP, we can't do Javascript either. - $text = RenderMan::destroy_javascript($text); - } - - // Strip out sections and PHP code - - $php = preg_match_all('#(<|<)\?php(.*?)\?(>|>)#is', $text, $phpsec); - - //die('
'.htmlspecialchars(print_r($phpsec, true))."\n".htmlspecialchars(print_r($text, true)).'
'); - - for($i=0;$i(.*?)<\/nowiki>#is', $text, $nowiki); - - for($i=0;$i'.$nowiki[1][$i].'
', '{NOWIKI:'.$random_id.':'.$i.'}', $text); - } - - $text = str_replace('~~~~~', date('G:i, j F Y (T)'), $text); - $text = str_replace('~~~~', "[[User:$session->username|$session->username]] ".date('G:i, j F Y (T)'), $text); - $text = str_replace('~~~', "[[User:$session->username|$session->username]] ", $text); - - // Reinsert sections - for($i=0;$i<$nw;$i++) - { - $text = str_replace('{NOWIKI:'.$random_id.':'.$i.'}', ''.$nowiki[1][$i].'', $text); - } - // Reinsert PHP - for($i=0;$i<$php;$i++) - { - $phsec = ''.$phpsec[1][$i].'?php'.$phpsec[2][$i].'?'.$phpsec[3][$i].''; - if ( $strip_all_php ) - $phsec = htmlspecialchars($phsec); - $text = str_replace('{PHP:'.$random_id.':'.$i.'}', $phsec, $text); - } - - $text = ( $sqlescape ) ? $db->escape($text) : $text; - - return $text; - } - - function smilieyize($text, $complete_urls = false) - { - - $random_id = md5( time() . mt_rand() ); - - // Smileys array - eventually this will be fetched from the database by - // RenderMan::initSmileys during initialization, but it will all be hardcoded for beta 2 - - $smileys = Array( - 'O:-)' => 'face-angel.png', - 'O:)' => 'face-angel.png', - 'O=)' => 'face-angel.png', - ':-)' => 'face-smile.png', - ':)' => 'face-smile.png', - '=)' => 'face-smile-big.png', - ':-(' => 'face-sad.png', - ':(' => 'face-sad.png', - ';(' => 'face-sad.png', - ':-O' => 'face-surprise.png', - ';-)' => 'face-wink.png', - ';)' => 'face-wink.png', - '8-)' => 'face-glasses.png', - '8)' => 'face-glasses.png', - ':-D' => 'face-grin.png', - ':D' => 'face-grin.png', - '=D' => 'face-grin.png', - ':-*' => 'face-kiss.png', - ':*' => 'face-kiss.png', - '=*' => 'face-kiss.png', - ':\'(' => 'face-crying.png', - ':-|' => 'face-plain.png', - ':-\\' => 'face-plain.png', - ':-/' => 'face-plain.png', - ':joke:' => 'face-plain.png', - ']:->' => 'face-devil-grin.png', - ':kiss:' => 'face-kiss.png', - ':-P' => 'face-tongue-out.png', - ':P' => 'face-tongue-out.png', - ':-p' => 'face-tongue-out.png', - ':p' => 'face-tongue-out.png', - ':-X' => 'face-sick.png', - ':X' => 'face-sick.png', - ':sick:' => 'face-sick.png', - ':-]' => 'face-oops.png', - ':]' => 'face-oops.png', - ':oops:' => 'face-oops.png', - ':-[' => 'face-embarassed.png', - ':[' => 'face-embarassed.png' - ); - /* - $keys = array_keys($smileys); - foreach($keys as $k) - { - $regex1 = '#([\W]+)'.preg_quote($k).'([\s\n\r\.]+)#s'; - $regex2 = '\\1'.$k.'\\2'; - $text = preg_replace($regex1, $regex2, $text); - } - */ - - // Strip out sections - //return '
'.htmlspecialchars($text).'
'; - $nw = preg_match_all('#(.*?)<\/nowiki>#is', $text, $nowiki); - - for($i=0;$i'.$nowiki[1][$i].'', '{NOWIKI:'.$random_id.':'.$i.'}', $text); - } - - $keys = array_keys($smileys); - foreach($keys as $k) - { - $t = str_hex($k); - $t = explode(' ', $t); - $s = ''; - foreach($t as $b) - { - $s.='&#x'.$b.';'; - } - $pfx = ( $complete_urls ) ? 'http' . ( isset($_SERVER['HTTPS']) ? 's' : '' ) . '://'.$_SERVER['HTTP_HOST'] : ''; - $text = str_replace(' '.$k, ' '.$s.'', $text); - } - //*/ - - // Reinsert sections - for($i=0;$i<$nw;$i++) - { - $text = str_replace('{NOWIKI:'.$random_id.':'.$i.'}', ''.$nowiki[1][$i].'', $text); - } - - return $text; - } - - /* - * **** DEPRECATED **** - * Replaces some critical characters in a string with MySQL-safe equivalents - * @param $text string the text to escape - * @return array key 0 is the escaped text, key 1 is the character tag - * / - - function escape_page_text($text) - { - $char_tag = md5(microtime() . mt_rand()); - $text = str_replace("'", "{APOS:$char_tag}", $text); - $text = str_replace('"', "{QUOT:$char_tag}", $text); - $text = str_replace("\\", "{SLASH:$char_tag}", $text); - return Array($text, $char_tag); - } - */ - - /* **** DEPRECATED **** - * Reverses the result of RenderMan::escape_page_text(). - * @param $text string the text to unescape - * @param $char_tag string the character tag - * @return string - * / - - function unescape_page_text($text, $char_tag) - { - $text = str_replace("{APOS:$char_tag}", "'", $text); - $text = str_replace("{QUOT:$char_tag}", '"', $text); - $text = str_replace("{SLASH:$char_tag}", "\\", $text); - return $text; - } - */ - - /** - * Generates a summary of the differences between two texts, and formats it as XHTML. - * @param $str1 string the first block of text - * @param $str2 string the second block of text - * @return string - */ - function diff($str1, $str2) - { - global $db, $session, $paths, $template, $plugins; // Common objects - $str1 = explode("\n", $str1); - $str2 = explode("\n", $str2); - $diff = new Diff($str1, $str2); - $renderer = new TableDiffFormatter(); - return ''.$renderer->format($diff).'
'; - } - -} - -?>