'Main.Glossary',
'TermsAndDefinitions' => array(),
'CaseSensitive' => false,
'MaxToolTipsPerTerm' => 5,
'LinkToTerm' => true,
'TermClass' => 'glossterm',
'DefClass' => 'glossdef',
'DirectiveWarnings' => true,
'ToolTipTermPattern' =>
'{GP_TERM}',
'ToolTipDefPattern' =>
'<div class="{GP_DEF_CLASS}">{GP_DEF}</div>',
));
SDVA($GlossaryPlus['ToolTipCommands'], array(
'BGCOLOR' => '',
'BORDERWIDTH' => 0,
'PADDING' => 0,
));
SDVA($GlossaryPlus['PreTermMatch'], array(
# MATCH if preceeded by newline OR any non-word character.
'\W' => '(?<=^|\\W)',
# DO NOT match if preceeded by (%) or (%div )...should catch %TERM% and >>TERM<<
'%' => '(? '(? '(? '(? '(? '(? '(?=\\W|$)',
# DO NOT match if followed by (=)...should catch TERM=
'=' => '(?!=)',
# DO NOT match if followed by (:)...should catch style="...TERM:red...", etc.
':' => '(?!:)',
# DO NOT match if followed by (/) or (\)...should catch term used in url
'/' => '(?!(\\/)|(\\\))',
# DO NOT match if followed by (.\w)...should catch TERM.Group
'.\w' => '(?!\\.\\w)',
));
##### Initialize #####
GlossaryInit();
##### Functions #####
function GlossaryInit() {
global $GlossaryPlus, $pagename;
# If current page is glossary page, process
to include named anchors and return.
$pagename = ResolvePageName($pagename);
$g_pagename = ResolvePageName($GlossaryPlus['PageName']);
if ($pagename == $g_pagename) {
if (@$GlossaryPlus['LinkToTerm']) {
Markup_e('>^::','>^::',
'/()(.*?)(<\\/dt>)/',
"GlossaryListWithNamedAnchors(PSS(\$m[2]))"
);
}
return;
}
# Prepare a few variables.
$g_group = PageVar($g_pagename, '$Group');
$g_page = PageVar($g_pagename, '$Name');
$g_url = FmtPageName('$PageUrl', $g_pagename);
$GlossaryPlus['CaseSensitive'] ? $g_cs = '' : $g_cs = 'i';
$g_max_tt = &$GlossaryPlus['MaxToolTipsPerTerm'];
foreach ($GlossaryPlus['ToolTipCommands'] as $c => $v) {
@$tt_com .= ', ' . $c . ", '" . $v . "'";
}
$t_class = &$GlossaryPlus['TermClass'];
$def_class = &$GlossaryPlus['DefClass'];
$t_pat = &$GlossaryPlus['ToolTipTermPattern'];
$def_pat = preg_replace(array("/'/", '/"/'), array("\'", '"'), $GlossaryPlus['ToolTipDefPattern']);
$t_pre = $GlossaryPlus['PreTermMatchImp'] = implode('', array_values($GlossaryPlus['PreTermMatch']));
$t_post = $GlossaryPlus['PostTermMatchImp'] = implode('', array_values($GlossaryPlus['PostTermMatch']));
# If glossary page is valid, add terms:defs to array.
if (PageExists($g_pagename)) {
$g_page_ret = RetrieveAuthPage($g_pagename, 'read', 0, READPAGE_CURRENT);
# Deal with multi-line situations.
$g_page_parse = preg_replace_callback("/\\\\(?>(\\\\*))\n/", function($matches) {
return Keep(str_repeat('
',strlen($matches[1])));
}, $g_page_ret['text']);
$g_page_parse = preg_replace_callback("/\\[\\[<<\\]\\]/", function($matches) {
return Keep("
");
}, $g_page_parse);
preg_match_all('/^(:+)(\s*)([^:]+):(.*)$/m', $g_page_parse, $matches);
foreach ($matches[3] as $k => $v) {
if (!@$GlossaryPlus['TermsAndDefinitions'][$v]) {
$GlossaryPlus['CaseSensitive'] ? $v_cs = &$v : $v_cs = strtolower($v);
$v_cs = htmlspecialchars($v_cs, ENT_NOQUOTES);
$GlossaryPlus['TermsAndDefinitions'][$v_cs] = trim($matches[4][$k]);
}
}
}
# Process directives.
Markup_e( "glossdir", ">directives",
"/\\(:gloss\\s+.*?:\\)/",
"GlossaryDirective(PSS(\$m[0]), '', '$tt_com', '$g_url', '$t_class', '$def_class', '$t_pat', '$def_pat', '$g_max_tt', '$g_cs', '$g_pagename', '$g_group', '$g_page')"
);
# Process each raw term found, adding in code for tooltip.
foreach (array_keys($GlossaryPlus['TermsAndDefinitions']) as $t) {
$t_san = preg_quote($t, '/');
Markup_e( "glossterm" . @$n++, ">links",
"/$t_pre$t_san$t_post/$g_cs",
"GlossaryTermToolTip('raw', PSS(\$m[0]), '', '$tt_com', '$g_url', '$t_class', '$def_class', '$t_pat', '$def_pat', '$g_max_tt', '$g_cs', '$g_pagename', '$g_group', '$g_page')"
);
}
}
function GlossaryDirective ($inpt, $t_alt, $tt_com = '', $g_url, $t_class, $def_class, $t_pat, $def_pat, $g_max_tt, $g_cs, $g_pagename, $g_group, $g_page) {
global $GlossaryPlus, $pagename;
# Parse arguments from directive.
$inpt_tr = preg_replace("/\\(:gloss\\s+(.*?):\\)/", "$1", $inpt);
$args = ParseArgs($inpt_tr);
# Get term.
$args['term'] ? $t_arg = &$args['term'] : $t_arg = &$args[''][0];
# Warn if no term.
if ($t_arg == '' && @$GlossaryPlus['DirectiveWarnings']) {
return Keep(
'Glossary Plus Warning: No term supplied in directive'
);
}
# Look for definition and warn if not found.
$g_cs == '' ? $t_cs = &$t_arg : $t_cs = strtolower($t_arg);
if (!@$GlossaryPlus['TermsAndDefinitions'][$t_cs]) {
if (@$GlossaryPlus['DirectiveWarnings']) {
return Keep(
'Glossary Plus Warning: Missing glossary entry " '
. $t_arg .
'
"'
);
}
return Keep($t_arg);
}
# Set alternate text if present.
if (@$args['text']) { $t_alt = &$args['text']; }
# Set alternate url if present.
if (@$args['link']) {
$g_url = FmtPageName('$PageUrl', MakePageName($pagename, $args['link']));
}
# Set term class if present.
if (@$args['termclass']) {
$t_class = &$args['termclass'];
}
elseif (@$args['termclass'] === '') {
$t_class = '';
}
# Set def class if present.
if (@$args['defclass']) {
$def_class = &$args['defclass'];
}
elseif (@$args['defclass'] === '') {
$def_class = '';
}
# Set commands if present.
if (@$args['commands']) {
$tt_com = ', ' . $args['commands'];
}
# Call and return glossary term tooltip.
return GlossaryTermToolTip('dir', $t_arg, $t_alt, $tt_com, $g_url, $t_class, $def_class, $t_pat, $def_pat, $g_max_tt, $g_cs, $g_pagename, $g_group, $g_page);
}
function GlossaryListWithNamedAnchors($t_arg) {
# Return term with named anchor.
$t_enc = GlossaryUrlEncode($t_arg);
return "" . $t_arg . "";
}
function GlossaryTermToolTip ($typ, $t_arg, $t_alt, $tt_com, $g_url, $t_class, $def_class, $t_pat, $def_pat, $g_max_tt, $g_cs, $g_pagename, $g_group, $g_page) {
global $GlossaryPlus, $MarkupFrame, $pagename;
# Limit how many times a term is processed for a tooltip.
$g_cs == 'i' ? $t_cs = strtolower($t_arg) : $t_cs = &$t_arg;
if (!isset($MarkupFrame[0]['glosscount'][$t_cs])) {
$MarkupFrame[0]['glosscount'][$t_cs] = $g_max_tt;
}
if ($typ == 'raw' && $MarkupFrame[0]['glosscount'][$t_cs]-- < 1) {
return Keep($t_arg);
}
# Prepare a few variables.
$t_alt == '' ? true : $t_arg = &$t_alt;
$d = $GlossaryPlus['TermsAndDefinitions'][$t_cs];
$d_mrkup = GlossaryMarkupToHTML($d, $g_cs, $g_group, $g_page);
$typ == 'raw' ? $g_url = GlossaryUrlEncode($t_arg, $g_url) : false;
$t_pat = preg_replace ('/{GP_TT}/', "'" . $def_pat . "'", $t_pat);
# Return tooltipped term.
return Keep(preg_replace(
array(
'/{GP_TERM}/', '/{GP_DEF}/',
'/{GP_COMMANDS}/', '/{GP_URL}/',
'/{GP_TERM_CLASS}/', '/{GP_DEF_CLASS}/',
'/{GP_PAGENAME}/', '/{GP_GROUP}/', '/{GP_PAGE}/'),
array(
$t_arg, $d_mrkup,
$tt_com, $g_url,
$t_class, $def_class,
$g_pagename, $g_group, $g_page),
$t_pat)
);
}
function GlossaryMarkupToHTML ($d_arg, $g_cs, $g_group, $g_page) {
global $GlossaryPlus, $pagename;
# Protect against looping when terms repeat in definitions...first deal with page text variables.
foreach ($GlossaryPlus['TermsAndDefinitions'] as $t => $d) {
$t_san = preg_quote($t, '/');
$d_arg = preg_replace("/(.*?)(\\{)(".$g_group."[.\\/]".$g_page.")*?(\\$:)($t_san)(\\})(.*?)/$g_cs", '$1' . $d . '$7', $d_arg);
}
# Then take care of the rest.
$t_pre = &$GlossaryPlus['PreTermMatchImp'];
$t_post = &$GlossaryPlus['PostTermMatchImp'];
foreach ($GlossaryPlus['TermsAndDefinitions'] as $t => $d) {
$t_san = preg_quote($t, '/');
$d_arg = preg_replace("/$t_pre($t_san)$t_post/$g_cs e", "Keep('$0')", $d_arg);
}
# Return marked up definition.
$d_arg = MarkupToHTML($pagename, $d_arg);
$d_arg = preg_replace("/\\\\/", '\\\\\\\\\\', $d_arg);
$d_arg = preg_replace(array("/'/", '/"/', '/', '/>/', "/\\n/"), array("\'", '"', '<', '>', ''), $d_arg);
$d_arg = preg_replace("/\\n/", '', $d_arg);
return $d_arg;
}
function GlossaryUrlEncode ($t_arg, $g_url='') {
global $GlossaryPlus;
# Url processing.
$t_arg = str_replace(' ', '', $t_arg);
$t_arg = htmlspecialchars_decode($t_arg, ENT_NOQUOTES);
$t_arg = urlencode($t_arg);
# Return for named anchor.
if ($g_url == '') {
return $t_arg;
}
# Return url.
if (@$GlossaryPlus['LinkToTerm']) {
$g_url = $g_url . '#' . $t_arg;
}
return $g_url;
}