using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace Convention.RScript.Variable.CStyle { public class CScriptRScriptVariableGenerater : RScriptInjectVariableGenerater { /// /// 获取类型的友好显示名称,支持泛型、数组等复杂类型 /// public static string GetFriendlyName(Type type) { if (type == null) return null; // 处理泛型类型 if (type.IsGenericType) { // 特殊处理可空类型(Nullable) 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; } /// /// 判断是否为可空类型 /// 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 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); } } }