Adding experimental support for enums overriding using @enum_override token

This commit is contained in:
Pavel Shevaev 2023-07-14 16:21:21 +03:00
parent 1e9d2c31e8
commit 259efc20ab
2 changed files with 32 additions and 5 deletions

View File

@ -706,7 +706,7 @@ class mtgMetaEnum extends mtgUserType
function calcOrValue($or_keys)
{
$res = 0;
foreach ($or_keys as $value_name)
foreach($or_keys as $value_name)
{
if(!isset($this->values[$value_name]))
throw new Exception("Enum '{$this->name}' has no value '{$value_name}'");
@ -726,6 +726,12 @@ class mtgMetaEnum extends mtgUserType
{
return $this->values;
}
function override(mtgMetaEnum $other)
{
$this->tokens = array_merge($this->tokens, $other->getTokens());
$this->values = array_merge($this->values, $other->getValues());
}
}
function mtg_get_all_fields(mtgMetaStruct $struct)

View File

@ -45,6 +45,8 @@ class mtgMetaInfoParser
function __construct($config = array())
{
self::addDefaultTokens($config);
$this->config = $config;
if(!isset($this->config['include_path']))
$this->config['include_path'] = array('.');
@ -82,6 +84,14 @@ class mtgMetaInfoParser
$this->token_strs[self::T_Func] = '<func>';
}
function addDefaultTokens(array &$config)
{
if(!isset($config['valid_tokens']))
$config['valid_tokens'] = array();
$config['valid_tokens'][] = 'enum_override';
}
function parse(mtgMetaInfo $meta, $raw_file)
{
$this->current_meta = $meta;
@ -306,12 +316,8 @@ class mtgMetaInfoParser
$name = $this->_parseDotName();
$enum = new mtgMetaEnum($name);
$this->current_meta->addUnit(new mtgMetaInfoUnit($this->file, $enum));
if($this->token == self::T_Prop)
{
$enum->setTokens($this->_parsePropTokens());
}
$or_values = array();
while(true)
@ -331,6 +337,21 @@ class mtgMetaInfoParser
}
}
$enum->addOrValues($or_values);
//NOTE: special case for enums when we allow to 'override' the original one,
// with additional values
if($enum->hasToken('enum_override'))
{
$existing = $this->current_meta->findUnit($enum->getId());
if(!$existing)
throw new Exception("Not found '{$name}' enum to override");
if(!($existing->object instanceof mtgMetaEnum))
throw new Exception("Not an enum struct '{$name}'");
$existing->object->override($enum);
}
else
$this->current_meta->addUnit(new mtgMetaInfoUnit($this->file, $enum));
}
private function _parseFields($next_doer)