private static StringBuilder AppendPrettyNameCore(this StringBuilder name, Type type, PrettyNameContext context) { // Suffixes (array, ref, pointer) if (type.IsArray) return name .AppendPrettyName(type.GetElementType(), context) .Append('[') .Append(',', type.GetArrayRank() - 1) .Append(']'); else if (type.IsByRef) return name .AppendPrettyName(type.GetElementType(), context) .Append('&'); else if (type.IsPointer) return name .AppendPrettyName(type.GetElementType(), context) .Append('*'); // Prefixes (nesting, namespace) if (type.IsNested) name.AppendPrettyNameCore(type.DeclaringType, context) .Append('.'); else if (context.IsQualified) name.Append(type.Namespace) .Append('.'); // Name and arguments if (type.IsGenericType) return name .Append(type.Name.WithoutGenericSuffix()) .AppendPrettyArguments(type, context); else return name .Append(type.Name); }
private static StringBuilder AppendPrettyArguments(this StringBuilder name, Type type, PrettyNameContext context) { // No args remain (ex: non-generic nested in generic) var count = context.GetGenericArgumentCount(type); if (count == 0) return name; // Completely open type if (context.IsGenericTypeDefinition) return name .Append('<') .Append(',', count - 1) .Append('>'); // Partially or fully closed types name.Append('<'); for (var i = 0; i < count; i++) { var arg = context.GetNextGenericArgument(); if (arg.IsGenericParameter) { if (i != 0) name.Append(','); } else { if (i != 0) name.Append(',').Append(' '); name.AppendPrettyName(arg, context); } } return name.Append('>'); }