Render MathML for mskip and mkern from texified mhchem

Bug: T340024

Change-Id: I2f9e0bbb98f33d6269009248861e4573dc9e6911
This commit is contained in:
Stegmujo 2023-07-19 14:13:23 +00:00 committed by Moritz Schubotz (physikerwelt)
parent 237ef0df8c
commit cedca8b14e
No known key found for this signature in database
GPG key ID: F803DB146DDF36C3
4 changed files with 104 additions and 11 deletions

View file

@ -483,12 +483,12 @@ class BaseMappings {
"qquad" => [ 'spacer', 2 ],
"thinspace" => [ 'spacer', MathSpace::THINMATHSPACE ],
"negthinspace" => [ 'spacer', MathSpace::NEGATIVETHINMATHSPACE ],
"hskip" => 'Hskip',
"hspace" => 'Hskip',
"kern" => 'Hskip',
"mskip" => 'Hskip',
"mspace" => 'Hskip',
"mkern" => 'Hskip',
"hskip" => 'hskip',
"hspace" => 'hskip',
"kern" => 'hskip',
"mskip" => 'hskip',
"mspace" => 'hskip',
"mkern" => 'hskip',
"rule" => 'rule',
"Rule" => [ 'Rule' ],
"Space" => [ 'Rule', 'blank' ],

View file

@ -346,11 +346,25 @@ class BaseParsing {
return $mmlRow->encapsulateRaw( "HLINE TBD" );
}
public static function hskip( $node, $passedArgs, $operatorContent, $name,
$smth1 = null, $smth2 = null, $smth3 = null, $smth4 = null ) {
// tbd hskip
$mmlRow = new MMLmrow();
return $mmlRow->encapsulateRaw( "hskip tbd" );
public static function hskip( $node, $passedArgs, $operatorContent, $name ) {
if ( $node->getArg() instanceof Curly ) {
$unit = MMLutil::squashLitsToUnit( $node->getArg() );
if ( !$unit ) {
return null;
}
$em = MMLutil::dimen2em( $unit );
} else {
// Prevent parsing in unmapped cases
return null;
}
if ( $name == "mskip" || $name == "mkern" ) {
$args = [ "width" => $em ];
} else {
return null;
}
$mspace = new MMLmspace( "", $args );
return $mspace->encapsulateRaw( "" );
}
public static function handleOperatorName( $node, $passedArgs, $operatorContent, $name,

View file

@ -2,6 +2,8 @@
namespace MediaWiki\Extension\Math\TexVC\MMLmappings\Util;
use IntlChar;
use MediaWiki\Extension\Math\TexVC\Nodes\Curly;
use MediaWiki\Extension\Math\TexVC\Nodes\Literal;
/**
* Utility Methods for parsing Tex to MathML
@ -72,6 +74,47 @@ class MMLutil {
return preg_replace( "/(\.\d\d\d).+/", '$1', $size ) . "em";
}
/**
* Assumes the input curly contains an TexArray of literals, squashes the TexArray characters to a string.
* @param Curly $node curly containing a TexArray of literals
* @return ?string squashed string in example "2mu", "-3mu" etc. Null if no TexArray inside curly.
*/
public static function squashLitsToUnit( Curly $node ): ?string {
$unit = "";
foreach ( $node->getArg()->getArgs() as $literal ) {
if ( !$literal instanceof Literal ) {
continue;
}
$unit .= $literal->getArg();
}
return $unit;
}
/**
* Convert a length dimension to em format
* currently supports "mu: math unit and forwards em"
* @param string $dimen input for length dimension like "-2mu" or "3 em"
* @return string|null converted string i.e. "0.333em" or null if error
*/
public static function dimen2em( string $dimen ): ?string {
$matches = [];
$matched = preg_match( '/([+-]?)(\d*\.*\d+)\s*(mu|em)/', $dimen, $matches );
if ( !$matched ) {
return null;
}
if ( $matches[3] == "mu" ) {
$ret = self::size2em( strval( intval( $matches[2] ) / 18 ) );
} elseif ( $matches[3] == "em" ) {
$ret = $matches[2] . "em";
} else {
return null;
}
return ( $matches[1] == "-" ? "-" : "" ) . $ret;
}
/**
* Some common steps of processing an input string before passing it as a key to the mappings.
* @param string $input string to be processed

View file

@ -0,0 +1,36 @@
<?php
namespace MediaWiki\Extension\Math\TexVC\Mhchem;
use MediaWiki\Extension\Math\TexVC\TexVC;
use MediaWikiUnitTestCase;
/**
* Some simple tests for testing MML output of TeXVC for
* equations containing mhchem. Test parsing the new TeX-commands introduced
* to TexVC for parsing texified mhchem output.
*
* @covers \MediaWiki\Extension\Math\TexVC\TexVC
*
*/
final class MhchemBasicMMLTest extends MediaWikiUnitTestCase {
public function testMskip() {
$input = "\\ce{Cr^{+3}(aq)}";
$texVC = new TexVC();
$options = [ "usemhchem" => true, "usemhchemtexified" => true ];
$warnings = [];
$checkRes = $texVC->check( $input, $options, $warnings, true );
$this->assertStringContainsString( '<mspace width="0.111em"></mspace>',
$checkRes["input"]->renderMML() );
}
public function testMkern() {
$input = "\\ce{A, B}";
$texVC = new TexVC();
$options = [ "usemhchem" => true, "usemhchemtexified" => true ];
$warnings = [];
$checkRes = $texVC->check( $input, $options, $warnings, true );
$this->assertStringContainsString( '<mspace width="0.333em"></mspace>',
$checkRes["input"]->renderMML() );
}
}