What it is
The BBCode extension allows your application to add additional BBCode tags to the parsing system within Invision Community. It should be noted that the preferred way of adding new editing capabilities is through CKEditor plugins (and custom editor plugins which can be created right from the AdminCP), however in some cases, particularly when an application has been upgraded from an older version of the software, you may wish to allow direct BBCode content to be translated during submission as well.
How to use
When you create a new instance of this extension through the Developer Center, it is important that you supply the BBCode tag as the extension name. If you want to use the BBCode tag "myapplication", then this should be the extension name. As an example, Blog supports both 'blog' and 'entry' as custom BBCodes, and these are the file names and class names for the extensions themselves.
The extension defines two methods. The first method allows you to control who can use the BBCode tag.
public function permissionCheck( \IPS\Member $member, $area )
{
return \IPS\Text\Parser::canUse( $member, 'ipsLink', $area );
}
Here, as an example we are simply checking if the member can use the 'link' button in the editor. If so, we will allow them to use this BBCode tag as well.
The second method returns a definition for how to parse the BBCode tag. It would be prudent to take a look at \IPS\Text\Parser::bbcodeTags() to see how the existing built in tags are defined as a reference point. Some tags are very simply - for instance, this is the definition for the acronym BBCode tag
array( 'tag' => 'abbr', 'attributes' => array( 'title' => '{option}' ), 'allowOption' => TRUE );
Other tags, however, define much more complicated parsing structures out of necessity. For instance, here is the definition for the member BBCode tag
array(
'tag' => 'a',
'attributes'=> array( 'contenteditable' => 'false', 'data-ipsHover' => '' ),
'callback' => function( \DOMElement $node, $matches, \DOMDocument $document )
{
try
{
$member = \IPS\Member::load( $matches[2], 'name' );
if ( $member->member_id != 0 )
{
$node->setAttribute( 'href', $member->url() );
$node->setAttribute( 'data-ipsHover-target', $member->url()->setQueryString( 'do', 'hovercard' ) );
$node->setAttribute( 'data-mentionid', $member->member_id );
$node->appendChild( $document->createTextNode( '@' . $member->name ) );
}
);
'allowOption' => TRUE
'single' => TRUE,
},
return $node;
catch ( \Exception $e ) {}
}
The single method, named getConfiguration(), should return a definition array akin to the above examples. The complete list of array elements which can be returned include:
- tag: (string) This is the HTML tag that will be used when creating the BBCode replacement, e.g. 'span' or 'div'
- attributes: (array) An array of HTML attributes to add to the tag in key => value pairs. You can use the special macro {option} to retrieve the value of any user supplied option data. e.g. [mycustomtag=somevalue] may be represented here with array( 'title' => '{option}' )
- defaultOption: (string) The default value to use for {option} if one has not been specified by the user.
- block: (bool) Whether the resulting HTML replacement should be considered a block-level element or not. Defaults to FALSE.
- single: (bool) Whether this is a single tag without content and a closing tag (e.g. 'member' is a single BBCode tag as it does not contain a closing tag). Defaults to FALSE.
- noParse: (bool) Enable this flag to prevent other BBCode parsing within this tag (for instance, BBCode should not be parsed inside 'code' BBCode tags). Defaults to FALSE.
- noChildren: (bool) Enable this flag if it is not appropriate for the resulting HTML element to have children elements (for instance, a <pre> HTML tag should not have children <p> HTML tags). Defaults to FALSE.
- callback: (callable) This is a callback that is passed 3 parameters (\DOMElement $node, $matches, \DOMDocument $document) which allows you to modify the DOMNode object as needed. This is optional, but necessary for more complex BBCode tags.
- getBlockContentElement: (callable) If callback is defined, this is an optional additional callback which can be defined in order to allow you to specify which node the children should be placed into. The callback function is passed a single parameter: \DOMElement $node. As an example, spoilers have both a header element and a content body element, and the content supplied by a user must be placed into the content body element.
- finishedCallback: (callable) The only argument passed to this callback is \DOMElement $originalNode. This parameter allows you to define a callback which is called after all other parsing has completed, in order to allow you to do any additional or post processing as needed.
- allowOption: (bool) Whether or not to allow option values to be specified. Defaults to TRUE, however some tags (such as 'b') do not require or support any optional values passed in.
The custom 'blog' BBCode, thus, is defined as so:
public function getConfiguration()
{
return array(
'tag' => 'a',
'callback' => function( \DOMElement $node, $matches, \DOMDocument $document )
{
try
{
$node->setAttribute( 'href', (string) \IPS\blog\Blog::load( intval( $matches[2] ) )->url() );
}
catch ( \Exception $e ) {}
return $node;
},
);
}
Report Document