protected function parseData()
    {
        if (is_null($this->dataCache)) {
            $patternNamespace  = '(?P<namespace>[a-zA-Z0-9\\\\]+\\\\)?';
            $patternName       = '(?P<name>[a-zA-Z0-9]+)';
            $patternString     = '\"[^\"]*\"|\'[^\']*\'';
            $patternFloat      = '[0-9]+\.[0-9]+';
            $patternInt        = '[0-9]+';
            $patternBool       = 'true|false';
            $patternAttrValues = "({$patternString}|{$patternFloat}|{$patternInt}|{$patternBool})";
            $patternAttributes = "(?P<attr>\(\s*([a-zA-Z0-9]+\={$patternAttrValues}\s*\,?\s*)+\s*\))?";
            $pattern           = "^\@{$patternNamespace}{$patternName}\s*{$patternAttributes}(?P<rawtext>.*)$";
            
            if (preg_match("/{$pattern}/is", $this->getValue(), $matches)) {
                $this->dataCache = array(
                    'namespace'   => $matches['namespace'],
                    'name'        => $matches['name'],
                    'attributes'  => array(),
                    'tags'        => array(),
                );
                
                if (preg_match_all("/(?P<key>[a-zA-Z0-9]+)\s*\=\s*(?P<value>{$patternAttrValues})/is", $matches['attr'], $attributeMatches, PREG_SET_ORDER)) {
                    foreach ($attributeMatches as $attributeMatch) {
                        $key   = $attributeMatch['key'];
                        $value = $attributeMatch['value'];
                        switch(true){
                            case $value === 'true':
                                $value = true;
                                break;
                                
                            case $value === 'false':
                                $value = false;
                                break;
                                
                            case $value[0] === '"':
                            case $value[0] === "'":
                                $value = substr($value, 1, strlen($value)-2);
                                break;
                                
                            case strpos($value, '.')>0:
                                $value = (float)$value;
                                break;
                                
                            case is_numeric($value):
                                $value = (int)$value;
                                break;
                                
                        }
                        $this->dataCache['attributes'][$key] = $value;
                    }
                }
                
                foreach (preg_split("/\s+/is", trim($matches['rawtext'])) as $attributeTag) {
                    $this->dataCache['tags'][] = $attributeTag;
                }
            }
        }
        return $this->dataCache;
    }