Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Source Generator for External Classes #73

Draft
wants to merge 20 commits into
base: master
Choose a base branch
from
Original file line number Diff line number Diff line change
@@ -1,14 +1,17 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<LangVersion>latest</LangVersion>
<GeneratePackageOnBuild>False</GeneratePackageOnBuild>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<!--<EnforceExtendedAnalyzerRules>true</EnforceExtendedAnalyzerRules>--> <!--todo enable this and fix errors-->
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Avalonia" Version="11.1.3" />
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="4.12.0-2.final" PrivateAssets="all" />
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="4.11.0" PrivateAssets="all" />
<PackageReference Include="Microsoft.CodeAnalysis.Analyzers" Version="3.11.0" PrivateAssets="all" />
</ItemGroup>

Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
using System.Collections.Immutable;
using System.Diagnostics;
using System.Text;
using AvaloniaExtensionGenerator;
using Microsoft.CodeAnalysis;

namespace Avalonia.Markup.Declarative.SourceGenerator;

[Generator]
public class AvaloniaExtensionsGenerator : ISourceGenerator
{
public void Execute(GeneratorExecutionContext context)
{
#if DEBUG
if (!Debugger.IsAttached)
{
Debugger.Launch();
}
#endif
Debug.WriteLine("Execute AvaloniaExtensionsGenerator code generator");

var comp = context.Compilation;
var sb = new StringBuilder();
var generator = new GeneratorHost();

var typeByMetadataName = comp.GetTypeByMetadataName("Avalonia.Markup.Declarative.GenerateMarkupForAssemblyAttribute");
var assemblies = ImmutableArray.CreateBuilder<IAssemblySymbol>();

assemblies.Add(context.Compilation.Assembly);

foreach (AttributeData attributeData in comp.Assembly.GetAttributes())
{
var attributeClass = attributeData.AttributeClass;
if ((attributeClass != null ? (!attributeClass.Equals(typeByMetadataName, SymbolEqualityComparer.Default) ? 1 : 0) : 1) == 0)
{
var constructorArgument = attributeData.ConstructorArguments[0];

if (constructorArgument.Value is INamedTypeSymbol iNamedTypeSymbol)
assemblies.Add(iNamedTypeSymbol.ContainingAssembly);
}
}

foreach (IAssemblySymbol assembly in assemblies)
{
foreach (INamedTypeSymbol publicClass in assembly.GlobalNamespace.GetPublicClasses())
{
var code = generator.GenerateExtensions(publicClass);

if (code != null)
{
context.AddSource($"{publicClass}.g.cs".TrimStart('.'), code);
}
}
}

return;
}

public void Initialize(GeneratorInitializationContext context)
{
Debug.WriteLine("Initialize code generator");
// No initialization required for this one
}
}
Loading