mirror of
https://github.com/StarCitizenTools/mediawiki-extensions-TabberNeue.git
synced 2024-11-27 09:42:48 +00:00
feat: allow tab name to be parsed
This is an experimental config and can lead to performance issue and unexpected behavior. Closes: #35
This commit is contained in:
parent
6e67dd2abb
commit
7b1c319e24
|
@ -52,6 +52,7 @@
|
|||
"name": "ext.tabberNeue.legacy/config.json",
|
||||
"config": {
|
||||
"enableAnimation": "TabberNeueEnableAnimation",
|
||||
"parseTabName": "TabberNeueParseTabName",
|
||||
"updateLocationOnTabChange": "TabberNeueUpdateLocationOnTabChange"
|
||||
}
|
||||
}
|
||||
|
@ -128,6 +129,11 @@
|
|||
},
|
||||
"config_prefix": "wg",
|
||||
"config": {
|
||||
"TabberNeueParseTabName": {
|
||||
"value": false,
|
||||
"description": "Parse tab name as wikitext. This can have a performance impact and cause unexpected behaviors.",
|
||||
"public": true
|
||||
},
|
||||
"TabberNeueUseCodex": {
|
||||
"value": false,
|
||||
"description": "Use Codex to render Tabber. It is experimental and many features might not work as expected.",
|
||||
|
|
|
@ -36,6 +36,8 @@ class Tabber {
|
|||
|
||||
private static $useCodex = false;
|
||||
|
||||
private static $parseTabName = false;
|
||||
|
||||
/**
|
||||
* Parser callback for <tabber> tag
|
||||
*
|
||||
|
@ -47,7 +49,9 @@ class Tabber {
|
|||
* @return string HTML
|
||||
*/
|
||||
public static function parserHook( ?string $input, array $args, Parser $parser, PPFrame $frame ) {
|
||||
self::$useCodex = MediaWikiServices::getInstance()->getMainConfig()->get( 'TabberNeueUseCodex' );
|
||||
$config = MediaWikiServices::getInstance()->getMainConfig();
|
||||
self::$parseTabName = $config->get( 'TabberNeueParseTabName' );
|
||||
self::$useCodex = $config->get( 'TabberNeueUseCodex' );
|
||||
|
||||
$html = self::render( $input ?? '', $parser, $frame );
|
||||
|
||||
|
@ -119,31 +123,48 @@ class Tabber {
|
|||
// Use array_pad to make sure at least 2 array values are always returned
|
||||
[ $tabName, $tabBody ] = array_pad( explode( '=', $tab, 2 ), 2, '' );
|
||||
|
||||
// Use language converter to get variant title and also escape html
|
||||
$tabName = $parser->getTargetLanguageConverter()->convertHtml( trim( $tabName ) );
|
||||
$tabName = trim( $tabName );
|
||||
$tabBody = trim( $tabBody );
|
||||
|
||||
// A nested tabber which should return json in codex
|
||||
if ( self::$useCodex && strpos( $tabBody, '{{#tag:tabber' ) !== false ) {
|
||||
self::$isNested = true;
|
||||
$tabBody = $parser->recursiveTagParse( $tabBody, $frame );
|
||||
self::$isNested = false;
|
||||
// The outermost tabber that must be parsed fully in codex for correct json
|
||||
} elseif ( self::$useCodex ) {
|
||||
$tabBody = $parser->recursiveTagParseFully( $tabBody, $frame );
|
||||
// Normal mode
|
||||
} else {
|
||||
$tabBody = $parser->recursiveTagParse( $tabBody, $frame );
|
||||
// Codex mode
|
||||
if ( self::$useCodex ) {
|
||||
// Use language converter to get variant title and also escape html
|
||||
$tabName = $parser->getTargetLanguageConverter()->convertHtml( $tabName );
|
||||
// A nested tabber which should return json in codex
|
||||
if ( strpos( $tabBody, '{{#tag:tabber' ) !== false ) {
|
||||
self::$isNested = true;
|
||||
$tabBody = $parser->recursiveTagParse( $tabBody, $frame );
|
||||
self::$isNested = false;
|
||||
// The outermost tabber that must be parsed fully in codex for correct json
|
||||
} else {
|
||||
$tabBody = $parser->recursiveTagParseFully( $tabBody, $frame );
|
||||
}
|
||||
|
||||
if ( self::$isNested ) {
|
||||
return json_encode( [
|
||||
'label' => $tabName,
|
||||
'content' => $tabBody
|
||||
],
|
||||
JSON_THROW_ON_ERROR
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if ( self::$useCodex && self::$isNested ) {
|
||||
return json_encode( [
|
||||
'label' => $tabName,
|
||||
'content' => $tabBody
|
||||
],
|
||||
JSON_THROW_ON_ERROR
|
||||
);
|
||||
// Legacy mode
|
||||
if ( self::$parseTabName ) {
|
||||
$tabName = $parser->recursiveTagParseFully( $tabName );
|
||||
// Remove outer paragraph tags
|
||||
if ( substr( $tabName, 0, 3 ) == '<p>' ) {
|
||||
$tabName = substr( $tabName, 3 );
|
||||
}
|
||||
if ( substr( $tabName, -4 ) == '</p>' ) {
|
||||
$tabName = substr( $tabName, 0, -4 );
|
||||
}
|
||||
$tabName = htmlentities( $tabName );
|
||||
} else {
|
||||
$tabName = $parser->getTargetLanguageConverter()->convertHtml( $tabName );
|
||||
}
|
||||
$tabBody = $parser->recursiveTagParse( $tabBody, $frame );
|
||||
|
||||
// If $tabBody does not have any HTML element (i.e. just a text node), wrap it in <p/>
|
||||
if ( $tabBody && $tabBody[0] !== '<' ) {
|
||||
|
@ -151,6 +172,6 @@ class Tabber {
|
|||
}
|
||||
|
||||
return '<article class="tabber__panel" data-title="' . $tabName .
|
||||
'">' . $tabBody . '</article>';
|
||||
'">' . $tabBody . '</article>';
|
||||
}
|
||||
}
|
||||
|
|
|
@ -51,6 +51,7 @@ module.exports = exports = defineComponent( {
|
|||
},
|
||||
methods: {
|
||||
isChildTabber() {
|
||||
// eslint-disable-next-line es-x/no-array-prototype-includes
|
||||
return Array.isArray( this.html ) || this.html.includes( '{"label":' );
|
||||
},
|
||||
parse() {
|
||||
|
|
|
@ -28,10 +28,22 @@ function initTabber( tabber, count ) {
|
|||
fragment = new DocumentFragment(),
|
||||
hashList = [];
|
||||
|
||||
const getTextFromHtml = function ( html ) {
|
||||
const tmp = document.createElement( 'div' );
|
||||
tmp.innerHTML = html;
|
||||
return tmp.textContent || tmp.innerText;
|
||||
};
|
||||
|
||||
Array.prototype.forEach.call( tabPanels, function ( tabPanel ) {
|
||||
const
|
||||
title = tabPanel.getAttribute( 'data-title' ),
|
||||
tab = document.createElement( 'a' );
|
||||
const tab = document.createElement( 'a' );
|
||||
let title = tabPanel.getAttribute( 'data-title' );
|
||||
|
||||
if ( config && config.parseTabName ) {
|
||||
tab.innerHTML = title;
|
||||
title = getTextFromHtml( title );
|
||||
} else {
|
||||
tab.innerText = title;
|
||||
}
|
||||
|
||||
let hash = mw.util.escapeIdForAttribute( title ) + '-' + count;
|
||||
|
||||
|
@ -54,7 +66,6 @@ function initTabber( tabber, count ) {
|
|||
tabPanel.setAttribute( 'aria-labelledby', 'tab-' + hash );
|
||||
tabPanel.setAttribute( 'aria-hidden', true );
|
||||
|
||||
tab.innerText = title;
|
||||
tab.classList.add( 'tabber__tab' );
|
||||
tab.setAttribute( 'role', 'tab' );
|
||||
tab.setAttribute( 'href', '#' + hash );
|
||||
|
|
2
package-lock.json
generated
2
package-lock.json
generated
|
@ -1,5 +1,5 @@
|
|||
{
|
||||
"name": "mediawiki-extensions-TabberNeue",
|
||||
"name": "TabberNeue",
|
||||
"lockfileVersion": 2,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
|
|
Loading…
Reference in a new issue