* Content of 'comma' including [[:syntax|wiki syntax]]
* Content of 'separated' and here **is** //some// ''formatting''
* Content of 'list'
*
*
* @license GPL 2 (http://www.gnu.org/licenses/gpl.html)
*/
if(!defined('DOKU_INC')) define('DOKU_INC',realpath(dirname(__FILE__).'/../../').'/');
if(!defined('DOKU_PLUGIN')) define('DOKU_PLUGIN',DOKU_INC.'lib/plugins/');
require_once(DOKU_PLUGIN.'syntax.php');
/**
* All DokuWiki plugins to extend the parser/rendering mechanism
* need to inherit from this class
*/
class syntax_plugin_simpletabs
extends DokuWiki_Syntax_Plugin
{
var $current_tab;
var $tab_area_counter;
var $tab_counter;
var $tabs;
function __construct()
{
global $PARSER_MODES;
$this->allowedModes = array_merge($PARSER_MODES['container'],
$PARSER_MODES['formatting'],
$PARSER_MODES['substition'],
$PARSER_MODES['protected'],
$PARSER_MODES['disabled'],
$PARSER_MODES['paragraphs']);
$this->tab_area_counter = 0;
$this->tab_counter = 0;
$this->tabs = array();
}
/**
* Get the type of syntax this plugin defines.
*/
function getType()
{
return 'container';
}
/**
* What kind of syntax do we allow (optional)
*/
function getAllowedTypes()
{
return array('container', 'formatting', 'substition', 'protected', 'disabled', 'paragraphs');
}
/** getAllowedTypes() **/
/**
* Define how this plugin is handled regarding paragraphs.
*
*
* This method is important for correct XHTML nesting. It returns
* one of the following values:
*
*
* - normal
- The plugin can be used inside paragraphs.
* - block
- Open paragraphs need to be closed before
* plugin output.
* - stack
- Special case: Plugin wraps other paragraphs.
*
*/
// function getPType()
// {
// return 'normal';
// }
/**
* Where to sort in?
*/
function getSort()
{
return 45;
}
/**
* Connect lookup pattern to lexer.
*/
function connectTo($mode)
{
$this->Lexer->addEntryPattern('(?=.*?)$',$mode,'plugin_simpletabs');
$this->Lexer->addPattern('', 'plugin_simpletabs');
$this->Lexer->addPattern('', 'plugin_simpletabs');
}
function postConnect()
{
$this->Lexer->addExitPattern('','plugin_simpletabs');
}
/**
* Handler to prepare matched data for the rendering process.
*
*
* The $aState parameter gives the type of pattern
* which triggered the call to this method:
*
*
* - DOKU_LEXER_ENTER
* - a pattern set by addEntryPattern()
* - DOKU_LEXER_MATCHED
* - a pattern set by addPattern()
* - DOKU_LEXER_EXIT
* - a pattern set by addExitPattern()
* - DOKU_LEXER_SPECIAL
* - a pattern set by addSpecialPattern()
* - DOKU_LEXER_UNMATCHED
* - ordinary text encountered within the plugin's syntax mode
* which doesn't match any pattern.
*
* @param $aMatch String The text matched by the patterns.
* @param $aState Integer The lexer state for the match.
* @param $aPos Integer The character position of the matched text.
* @param $aHandler Object Reference to the Doku_Handler object.
* @return Integer The current lexer state for the match.
* @public
* @see render()
* @static
*/
function handle($match, $state, $pos, &$handler)
{
switch ($state)
{
case DOKU_LEXER_ENTER:
$this->tab_area_counter++;
//cho "[DEBUG] Encountered tabbed area: " . $this->tab_area_counter . "
";
$this->current_tab = '';
$this->tab_count = 0;
$this->tab_names = array();
if (preg_match('/tabs="(.+)"/', $match, $matches))
{
$this->tab_names = explode(',', $matches[1]);
}
return array($state, array($this->tab_area_counter, $this->tab_names, $this->getConf('defaulttab')));
break;
case DOKU_LEXER_MATCHED:
$params = $match;
if ($match == '')
{
$this->current_tab = '';
// close any section edit block
$handler->_addCall('finishSectionEdit', array($pos - 1), $pos);
// render end of tabbed area
$params = array(true, $this->tab_area_counter, '', 0, false);
}
else
{
// Do we have a tab open?
$close_first = false;
if (!empty($this->current_tab))
{
// close any section edit block
$handler->_addCall('finishSectionEdit', array($pos - 1), $pos);
$close_first = true;
}
$this->current_tab = $this->tab_names[$this->tab_count];
$this->tab_count++;
$active = false;
if ($this->current_tab == $this->getConf('defaulttab'))
{
$active = true;
}
// start section edit
// - note the +5 is to account for the section starting ""
$handler->_addCall('startSectionEdit', array(($pos + 5), 'section', $this->current_tab), $pos);
$params = array($close_first, $this->tab_area_counter, $this->current_tab, $this->tab_count, $active);
}
return array($state, $params);
break;
case DOKU_LEXER_UNMATCHED:
if (!empty($this->current_tab))
{
// SPECIAL CASE: We have to handle headers ourselves (apparently -
// having looked in several other plugins similar to this)
$headerMatch = preg_grep('/([ \t]*={2,}[^\n]+={2,}[ \t]*(?=))/msSi', array($match));
// - not a header, just pass it through
if (empty($headerMatch))
{
//$handler->_addCall('cdata', array($match), $pos);
return array($state, $match);
}
else
{
// if it's a == header ==, use the core header() renderer
// (copied from core header() in inc/parser/handler.php)
$title = trim($match);
$level = 7 - strspn($title,'=');
if ($level < 1)
{
$level = 1;
}
$title = trim($title,'=');
$title = trim($title);
$handler->_addCall('header',array($title,$level,$pos), $pos);
// close the section edit the header could open
/*
if ($title && $level <= $conf['maxseclevel'])
{
$handler->addPluginCall('wrap_closesection', array(), DOKU_LEXER_SPECIAL, $pos, '');
}
*/
}
return false;
}
break;
case DOKU_LEXER_EXIT:
$close_first = false;
if (!empty($this->current_tab))
{
// close any pending section edit block
$handler->_addCall('finishSectionEdit', array($pos - 1), $pos);
$close_first = true;
}
// generate dummy heading at top level to ensure that no following headers are nested under titles in the tabbed area
$handler->_addCall('header', array('#',1,$pos), $pos);
return array($state, $close_first);
break;
case DOKU_LEXER_SPECIAL:
break;
}
return array();
}
/**
* Handle the actual output creation.
*
*
* The method checks for the given $aFormat and returns
* FALSE when a format isn't supported. $aRenderer
* contains a reference to the renderer object which is currently
* handling the rendering. The contents of $aData is the
* return value of the handle() method.
*
* @see handle()
*/
function render($mode, &$renderer, $data)
{
if($mode == 'xhtml')
{
list($state, $params) = $data;
switch ($state)
{
case DOKU_LEXER_ENTER:
list($tab_area_id, $tab_names, $active_tab) = $params;
//cho "[DEBUG] Generating tabbed area: " . $tab_area_id . "
";
$renderer->doc .= '
';
break;
case DOKU_LEXER_MATCHED:
list($close_tab, $tab_area_counter, $tab_name, $tab_content_count, $active) = $params;
if ($close_tab)
{
$renderer->doc .= '
';
}
if (!empty($tab_name))
{
$this->tab_content_counter++;
$renderer->doc .= ' doc .= ' style="display:none;"';
}
$renderer->doc .= '>';
}
break;
case DOKU_LEXER_UNMATCHED:
$renderer->doc .= $params;
break;
case DOKU_LEXER_EXIT:
$renderer->doc .= '
';
break;
}
return true;
}
return false;
}
}
//Setup VIM: ex: et ts=4 enc=utf-8 :
?>