Files
RScript/PublicTypes/InjectVariable/CStyle.cs

190 lines
6.0 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace Convention.RScript.Variable.CStyle
{
public class CScriptRScriptVariableGenerater : RScriptInjectVariableGenerater
{
/// <summary>
/// 获取类型的友好显示名称,支持泛型、数组等复杂类型
/// </summary>
public static string GetFriendlyName(Type type)
{
if (type == null) return null;
// 处理泛型类型
if (type.IsGenericType)
{
// 特殊处理可空类型Nullable<T>
if (type.IsNullable())
{
return $"{GetFriendlyName(type.GetGenericArguments()[0])}?";
}
var sb = new StringBuilder();
// 获取类型基础名称(移除 `1, `2 等后缀)
string baseName = type.Name.Contains('`') ? type.Name[..type.Name.IndexOf('`')] : type.Name;
sb.Append(baseName);
sb.Append('<');
// 递归处理泛型参数
Type[] args = type.GetGenericArguments();
for (int i = 0; i < args.Length; i++)
{
if (i > 0) sb.Append(", ");
sb.Append(GetFriendlyName(args[i]));
}
sb.Append('>');
return sb.ToString();
}
// 处理数组类型
if (type.IsArray)
{
string elementName = GetFriendlyName(type.GetElementType());
int rank = type.GetArrayRank();
return rank == 1 ? $"{elementName}[]" : $"{elementName}[{new string(',', rank - 1)}]";
}
// 处理指针类型
if (type.IsPointer)
{
return $"{GetFriendlyName(type.GetElementType())}*";
}
// 处理引用类型ref/out 参数)
if (type.IsByRef)
{
return $"{GetFriendlyName(type.GetElementType())}&";
}
// 普通类型直接返回名称
return type.Name;
}
/// <summary>
/// 判断是否为可空类型
/// </summary>
public static bool IsNullable(Type type)
{
return type.IsGenericType &&
type.GetGenericTypeDefinition() == typeof(Nullable<>);
}
public static string GetTypename(Type type)
{
if (type == typeof(int))
return "int";
if (type == typeof(float))
return "float";
if (type == typeof(double))
return "double";
if (type == typeof(bool))
return "bool";
if (type == typeof(void))
return "void";
return GetFriendlyName(type).Replace('`', '_');
}
private int m_layer = 0;
private int layer
{
get=>m_layer;
set
{
m_layer = value;
Prefix = new('\t', layer);
}
}
private string Prefix = "";
public CScriptRScriptVariableGenerater(Type targetType, Generater generater, Destorier destorier, string name) : base(targetType, generater, destorier, name)
{
}
protected override string WriteClassBodyEnter(Type currentType)
{
string result = $"{Prefix}{"{"}\n{Prefix}public:";
layer++;
return result;
}
protected override string WriteClassBodyExit(Type currentType)
{
layer--;
return $"{Prefix}{"};"}";
}
protected override string WriteClassHead(Type currentType)
{
string description = string.IsNullOrEmpty(this.description) ? "" : string.Join("", from item in this.description.Split('\n') where string.IsNullOrEmpty(item) == false select $"{Prefix}{item}\n");
string suffix = currentType.BaseType == typeof(object) ? string.Empty : $" : public {GetTypename(currentType.BaseType)}";
string result = $"{Prefix}\\*{description}*\\\n{Prefix}{Prefix}class {GetTypename(currentType)}{suffix}";
return result;
}
protected override string WriteClassMethod(Type returnType, string methodName, string[] parameterNames, Type[] parameterTypes)
{
List<string> parameters = new();
for (int i = 0, e = parameterNames.Length; i < e; i++)
{
parameters.Add($"{GetTypename(parameterTypes[i])} {parameterNames[i]}");
}
return $"{Prefix}{GetTypename(returnType)} {methodName}({string.Join(", ", parameters)});";
}
protected override string WriteClassTail(Type currentType)
{
return "";
}
protected override string WriteEnumBodyEnter(Type currentType)
{
string result = $"{Prefix}{"{"}";
layer++;
return result;
}
protected override string WriteEnumBodyExit(Type currentType)
{
layer--;
return $"{Prefix}{"};"}";
}
protected override string WriteEnumHead(Type currentEnum)
{
return $"{Prefix}enum {GetTypename(currentEnum)}";
}
protected override string WriteEnumName(string enumName)
{
return $"{Prefix}{enumName},";
}
protected override string WriteEnumTail(Type currentType)
{
return "";
}
protected override string WritePageEnd(Type currentType)
{
return "";
}
protected override string WritePageHead(Type currentType)
{
if (currentType.BaseType != null)
return $"#include\"{GetFilename(currentType.BaseType)}\"";
return string.Empty;
}
public override string GetFilename(Type currentType)
{
return GetTypename(currentType);
}
}
}