using Microsoft.CodeAnalysis; using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Syntax; namespace Lua.SourceGenerator; internal class TypeMetadata { public TypeDeclarationSyntax Syntax { get; } public INamedTypeSymbol Symbol { get; } public string TypeName { get; } public string FullTypeName { get; } public PropertyMetadata[] Properties { get; } public MethodMetadata[] Methods { get; } public TypeMetadata(TypeDeclarationSyntax syntax, INamedTypeSymbol symbol, SymbolReferences references) { Syntax = syntax; Symbol = symbol; TypeName = symbol.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat); FullTypeName = symbol.ToDisplayString(SymbolDisplayFormat.FullyQualifiedFormat); Properties = Symbol.GetAllMembers(false) .Where(x => x is (IFieldSymbol or IPropertySymbol) and { IsImplicitlyDeclared: false }) .Where(x => { if (!x.ContainsAttribute(references.LuaMemberAttribute)) return false; if (x.ContainsAttribute(references.LuaIgnoreMemberAttribute)) return false; if (x is IPropertySymbol p) { if (p.GetMethod == null || p.SetMethod == null) return false; if (p.IsIndexer) return false; } return true; }) .Select(x => new PropertyMetadata(x, references)) .ToArray(); Methods = Symbol.GetAllMembers(false) .Where(x => x is IMethodSymbol and { IsImplicitlyDeclared: false }) .Select(x => (IMethodSymbol)x) .Where(x => { if (x.ContainsAttribute(references.LuaIgnoreMemberAttribute)) return false; return x.ContainsAttribute(references.LuaMemberAttribute) || x.ContainsAttribute(references.LuaMetamethodAttribute); }) .Select(x => new MethodMetadata(x, references)) .ToArray(); } public bool IsPartial() { return Syntax.Modifiers.Any(m => m.IsKind(SyntaxKind.PartialKeyword)); } public bool IsNested() { return Syntax.Parent is TypeDeclarationSyntax; } }