Add BBCodes from the bundled repository

$configurator = new s9e\TextFormatter\Configurator;
$configurator->BBCodes->addFromRepository('B');
$configurator->BBCodes->addFromRepository('I');
$configurator->BBCodes->addFromRepository('URL');

// Get an instance of the parser and the renderer
extract($configurator->finalize());

$text = 'Here be [url=http://example.org]the [b]bold[/b] [i]italic[/i] URL[/url].';
$xml  = $parser->parse($text);
$html = $renderer->render($xml);

echo $html;
Here be <a href="http://example.org">the <b>bold</b> <i>italic</i> URL</a>.

Add a configurable BBCode from the bundled repository

$configurator = new s9e\TextFormatter\Configurator;
$configurator->BBCodes->addFromRepository('SIZE', 'default', ['min' => 5, 'max' => 40]);

// Get an instance of the parser and the renderer
extract($configurator->finalize());

$text = "[size=1]Smallest[/size]\n[size=99]Biggest[/size]";
$xml  = $parser->parse($text);
$html = $renderer->render($xml);

echo $html;
<span style="font-size:5px">Smallest</span>
<span style="font-size:40px">Biggest</span>

Inspect BBCodes from the bundled repository

The definitions from the bundled default repository can be retrieved by name via the BBCodes plugin without actually creating the corresponding BBCodes. The returned array contains the BBCode's name, a BBCode object, and a Tag object.

$configurator = new s9e\TextFormatter\Configurator;

$definition = $configurator->BBCodes->repositories['default']->get('B');

var_dump(trim($definition['tag']->template));
var_export(array_keys($definition));
string(29) "<b><xsl:apply-templates/></b>"
array (
  0 => 'bbcode',
  1 => 'bbcodeName',
  2 => 'tag',
)

List of bundled BBCodes

ACRONYM

[ACRONYM title={TEXT1?}]{TEXT2}[/ACRONYM]

<acronym title="{TEXT1}">{TEXT2}</acronym>
ALIGN

[ALIGN={CHOICE=left,right,center,justify}]{TEXT}[/ALIGN]

<div style="text-align:{CHOICE}">{TEXT}</div>
B

[B]{TEXT}[/B]

<b><xsl:apply-templates /></b>
BACKGROUND

[BACKGROUND={COLOR}]{TEXT}[/BACKGROUND]

<span style="background-color:{COLOR}">{TEXT}</span>
C

[C]{TEXT}[/C]

<code class="inline"><xsl:apply-templates /></code>
CENTER

[CENTER]{TEXT}[/CENTER]

<div style="text-align:center">{TEXT}</div>
CODE

[CODE lang={IDENTIFIER?}]{TEXT}[/CODE]

<pre data-s9e-livepreview-hash="" data-s9e-livepreview-onupdate="if(typeof hljsLoader!=='undefined')hljsLoader.highlightBlocks(this)">
    <code>
        <xsl:if test="@lang">
            <xsl:attribute name="class">language-<xsl:value-of select="@lang"/></xsl:attribute>
        </xsl:if>
        <xsl:apply-templates />
    </code>
    <script async="" crossorigin="anonymous">
        <xsl:if test="'default' != 'github'">
            <xsl:attribute name="data-hljs-style">
                github
            </xsl:attribute>
        </xsl:if>
        <xsl:if test="'https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.1.0/build/' != 'https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.1.0/build/'">
            <xsl:attribute name="data-hljs-url">
                https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.1.0/build/
            </xsl:attribute>
        </xsl:if>
        <xsl:attribute name="data-s9e-livepreview-onrender">if(typeof hljsLoader!=='undefined')this.parentNode.removeChild(this)</xsl:attribute>
        <xsl:attribute name="integrity">sha384-oTqfbnKDrROJYNQZI1U//Vr36HEjwJafOewSUYYyb5OXhv0r2qRQcjAP3yXa4HCg</xsl:attribute>
        <xsl:attribute name="onload">hljsLoader.highlightBlocks(this.parentNode)</xsl:attribute>
        <xsl:attribute name="src">https://cdn.jsdelivr.net/gh/s9e/hljs-loader@1.0.24/loader.min.js</xsl:attribute>
    </script>
</pre>
Var name Default Description
style github highlight.js style name (or "none")
url https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.1.0/build/ highlight.js CDN URL
COLOR

[COLOR={COLOR}]{TEXT}[/COLOR]

<span style="color:{COLOR}">{TEXT}</span>
DD

[DD]{TEXT}[/DD]

<dd>{TEXT}</dd>
DEL

[DEL]{TEXT}[/DEL]

<del>{TEXT}</del>
DL

[DL]{TEXT}[/DL]

<dl>{TEXT}</dl>
DT

[DT]{TEXT}[/DT]

<dt>{TEXT}</dt>
EM

[EM]{TEXT}[/EM]

<em>{TEXT}</em>
EMAIL

[EMAIL={EMAIL;useContent}]{TEXT}[/EMAIL]

<a href="mailto:{EMAIL}">{TEXT}</a>
FLASH

[FLASH={PARSE=/^(?<width>\d+),(?<height>\d+)/} width={RANGE=0,1920;defaultValue=80} height={RANGE=0,1080;defaultValue=60} url={URL;useContent}]

<object classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000" codebase="http://fpdownload.macromedia.com/get/shockwave/cabs/flash/swflash.cab#version=7,0,0,0" width="{@width}" height="{@height}">
    <param name="movie" value="{@url}" />
    <param name="quality" value="high" />
    <param name="wmode" value="opaque" />
    <param name="play" value="false" />
    <param name="loop" value="false" />

    <param name="allowScriptAccess" value="never" />
    <param name="allowNetworking" value="internal" />

    <embed src="{@url}" quality="high" width="{@width}" height="{@height}" wmode="opaque" type="application/x-shockwave-flash" pluginspage="http://www.adobe.com/go/getflashplayer" play="false" loop="false" allowscriptaccess="never" allownetworking="internal"></embed>
</object>
Var name Default Description
minWidth 0 Minimum width for the Flash object
maxWidth 1920 Maximum width for the Flash object
minHeight 0 Minimum height for the Flash object
maxHeight 1080 Maximum height for the Flash object
FLOAT

[float={CHOICE=left,right,none}]{TEXT}[/float]

<div style="float:{CHOICE}">{TEXT}</div>
FONT

[font={FONTFAMILY}]{TEXT}[/font]

<span style="font-family:{FONTFAMILY}">{TEXT}</span>
H1

[H1]{TEXT}[/H1]

<h1>{TEXT}</h1>
H2

[H2]{TEXT}[/H2]

<h2>{TEXT}</h2>
H3

[H3]{TEXT}[/H3]

<h3>{TEXT}</h3>
H4

[H4]{TEXT}[/H4]

<h4>{TEXT}</h4>
H5

[H5]{TEXT}[/H5]

<h5>{TEXT}</h5>
H6

[H6]{TEXT}[/H6]

<h6>{TEXT}</h6>
HR

[HR]

<hr/>
I

[I]{TEXT}[/I]

<i>{TEXT}</i>
IMG

[IMG src={URL;useContent} title={TEXT?} alt={TEXT?} height={UINT?} width={UINT?} ]

<img src="{@src}" title="{@title}" alt="{@alt}">
    <xsl:copy-of select="@height"/>
    <xsl:copy-of select="@width"/>
</img>
INS

[INS]{TEXT}[/INS]

<ins>{TEXT}</ins>
JUSTIFY

[JUSTIFY]{TEXT}[/JUSTIFY]

<div style="text-align:justify">{TEXT}</div>
LEFT

[LEFT]{TEXT}[/LEFT]

<div style="text-align:left">{TEXT}</div>
LIST

[LIST type={HASHMAP=1:decimal,a:lower-alpha,A:upper-alpha,i:lower-roman,I:upper-roman;optional;postFilter=#simpletext} start={UINT;optional} #createChild=LI]{TEXT}[/LIST]

<xsl:choose>
    <xsl:when test="not(@type)">
        <ul><xsl:apply-templates /></ul>
    </xsl:when>
    <xsl:when test="starts-with(@type,'decimal') or starts-with(@type,'lower') or starts-with(@type,'upper')">
        <ol style="list-style-type:{@type}"><xsl:copy-of select="@start"/><xsl:apply-templates /></ol>
    </xsl:when>
    <xsl:otherwise>
        <ul style="list-style-type:{@type}"><xsl:apply-templates /></ul>
    </xsl:otherwise>
</xsl:choose>
*

[*]{TEXT}[/*]

<li><xsl:apply-templates /></li>
MAGNET

[MAGNET={REGEXP=/^magnet:/;useContent}]{TEXT}[/MAGNET]

<a href="{REGEXP}"><img alt="" src="data:image/gif;base64,R0lGODlhDAAMALMPAOXl5ewvErW1tebm5oocDkVFRePj47a2ts0WAOTk5MwVAIkcDesuEs0VAEZGRv///yH5BAEAAA8ALAAAAAAMAAwAAARB8MnnqpuzroZYzQvSNMroUeFIjornbK1mVkRzUgQSyPfbFi/dBRdzCAyJoTFhcBQOiYHyAABUDsiCxAFNWj6UbwQAOw==" style="vertical-align:middle;border:0;margin:0 5px 0 0"/>{TEXT}</a>
NOPARSE

[NOPARSE #ignoreTags=true]{TEXT}[/NOPARSE]

{TEXT}
OL

[OL]{TEXT}[/OL]

<ol>{TEXT}</ol>
QUOTE

[QUOTE author={TEXT?}]{TEXT}[/QUOTE]

<blockquote>
    <xsl:if test="not(@author)">
        <xsl:attribute name="class">uncited</xsl:attribute>
    </xsl:if>
    <div>
        <xsl:if test="@author">
            <cite>
                <xsl:value-of select="@author" /> wrote:
            </cite>
        </xsl:if>
        <xsl:apply-templates />
    </div>
</blockquote>
Var name Default Description
authorStr <xsl:value-of select="@author" /> wrote: Author string

[RIGHT]{TEXT}[/RIGHT]

<div style="text-align:right">{TEXT}</div>
S

[S]{TEXT}[/S]

<s>{TEXT}</s>
SIZE

[SIZE={RANGE=8,36}]{TEXT}[/SIZE]

<span style="font-size:{RANGE}px">{TEXT}</span>
Var name Default Description
min 8 Minimum size in px
max 36 Maximum size in px
SPOILER

[SPOILER title={TEXT1?}]{TEXT2}[/SPOILER]

<div class="spoiler">
    <div class="spoiler-header">
        <button onclick="var a=parentNode.nextSibling.style,b=firstChild.style,c=lastChild.style;b.display=a.display;a.display=c.display=(b.display)?'':'none';return!1"><span>Show</span><span style="display:none">Hide</span></button>
        <span class="spoiler-title">Spoiler: {TEXT1}</span>
    </div>
    <div class="spoiler-content" style="display:none">{TEXT2}</div>
</div>
Var name Default Description
showStr Show String used for the Show button
hideStr Hide String used for the Hide button
spoilerStr Spoiler: String used for the spoiler label
STRONG

[STRONG]{TEXT}[/STRONG]

<strong>{TEXT}</strong>
SUB

[SUB]{TEXT}[/SUB]

<sub>{TEXT}</sub>
SUP

[SUP]{TEXT}[/SUP]

<sup>{TEXT}</sup>
TABLE

[TABLE]{ANYTHING}[/TABLE]

<table>{ANYTHING}</table>
TBODY

[TBODY]{ANYTHING}[/TBODY]

<tbody>{ANYTHING}</tbody>
TD

[TD align={CHOICE=left,center,right,justify;caseSensitive;optional;preFilter=strtolower} colspan={UINT?} rowspan={UINT?} #createParagraphs=false]{TEXT}[/TD]

<td>
    <xsl:copy-of select="@colspan"/>
    <xsl:copy-of select="@rowspan"/>
    <xsl:if test="@align">
        <xsl:attribute name="style">text-align:{CHOICE}</xsl:attribute>
    </xsl:if>
    <xsl:apply-templates/>
</td>
TH

[TH align={CHOICE=left,center,right,justify;caseSensitive;optional;preFilter=strtolower} colspan={UINT?} rowspan={UINT?} #createParagraphs=false]{TEXT}[/TH]

<th>
    <xsl:copy-of select="@colspan"/>
    <xsl:copy-of select="@rowspan"/>
    <xsl:if test="@align">
        <xsl:attribute name="style">text-align:{CHOICE}</xsl:attribute>
    </xsl:if>
    <xsl:apply-templates/>
</th>
THEAD

[THEAD]{ANYTHING}[/THEAD]

<thead>{ANYTHING}</thead>
TR

[TR]{ANYTHING}[/TR]

<tr>{ANYTHING}</tr>
U

[U]{TEXT}[/U]

<u>{TEXT}</u>
UL

[UL]{TEXT}[/UL]

<ul>{TEXT}</ul>
URL

[URL={URL;useContent} title={TEXT?}]{TEXT}[/URL]

<a href="{@url}"><xsl:copy-of select="@title" /><xsl:apply-templates /></a>
VAR

[VAR]{TEXT}[/VAR]

<var>{TEXT}</var>