Compare commits

..

No commits in common. "main" and "v0.10" have entirely different histories.
main ... v0.10

34 changed files with 692 additions and 763 deletions

View File

@ -16,7 +16,7 @@ jobs:
- name: Setup .NET - name: Setup .NET
uses: actions/setup-dotnet@v1 uses: actions/setup-dotnet@v1
with: with:
dotnet-version: 7.0.x dotnet-version: 6.0.x
- name: Publish - name: Publish
run: | run: |
sudo chmod +x ./test.sh sudo chmod +x ./test.sh
@ -25,9 +25,9 @@ jobs:
with: with:
name: Linux-Artifact name: Linux-Artifact
path: | path: |
./src/bin/Release/net7.0/linux-x64/publish/*.bin ./src/bin/x64/Release/net6.0/linux-x64/publish/*.bin
./src/bin/Release/net7.0/linux-x64/publish/*.so ./src/bin/x64/Release/net6.0/linux-x64/publish/*.so
./src/bin/Release/net7.0/linux-x64/publish/*.png ./src/bin/x64/Release/net6.0/linux-x64/publish/*.png
build-on-windows: build-on-windows:
runs-on: windows-latest runs-on: windows-latest
steps: steps:
@ -35,16 +35,16 @@ jobs:
- name: Setup .NET - name: Setup .NET
uses: actions/setup-dotnet@v1 uses: actions/setup-dotnet@v1
with: with:
dotnet-version: 7.0.x dotnet-version: 6.0.x
- name: Publish - name: Publish
run: ./test.cmd run: ./test.cmd
- uses: actions/upload-artifact@v2 - uses: actions/upload-artifact@v2
with: with:
name: Windows-Artifact name: Windows-Artifact
path: | path: |
.\src\bin\Release\net7.0\win-x64\publish\*.exe .\src\bin\x64\Release\net6.0\win-x64\publish\*.exe
.\src\bin\Release\net7.0\win-x64\publish\*.dll .\src\bin\x64\Release\net6.0\win-x64\publish\*.dll
.\src\bin\Release\net7.0\win-x64\publish\*.png .\src\bin\x64\Release\net6.0\win-x64\publish\*.png
build-on-macos: build-on-macos:
runs-on: macos-latest runs-on: macos-latest
steps: steps:
@ -52,14 +52,14 @@ jobs:
- name: Setup .NET - name: Setup .NET
uses: actions/setup-dotnet@v1 uses: actions/setup-dotnet@v1
with: with:
dotnet-version: 7.0.x dotnet-version: 6.0.x
- name: Publish - name: Publish
run: | run: |
sudo chmod +x ./test.command sudo chmod +x ./test.command
./test.command ./test.command
cd ./src/bin/Release/net7.0/osx-x64/publish cd ./src/bin/x64/Release/net6.0/osx-x64/publish
zip -r -0 macOS-Artifact.zip *.app zip -r -0 macOS-Artifact.zip *.app
mv *.zip ../../../../../../. mv *.zip ../../../../../../../.
- uses: actions/upload-artifact@v2 - uses: actions/upload-artifact@v2
with: with:
name: macOS-Artifact name: macOS-Artifact

View File

@ -7,14 +7,14 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AvaloniaCoreRTDemo", "src\A
EndProject EndProject
Global Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU Debug|x64 = Debug|x64
Release|Any CPU = Release|Any CPU Release|x64 = Release|x64
EndGlobalSection EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution GlobalSection(ProjectConfigurationPlatforms) = postSolution
{41A52A04-F7D8-4981-9546-DB020E54851D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {41A52A04-F7D8-4981-9546-DB020E54851D}.Debug|x64.ActiveCfg = Debug|x64
{41A52A04-F7D8-4981-9546-DB020E54851D}.Debug|Any CPU.Build.0 = Debug|Any CPU {41A52A04-F7D8-4981-9546-DB020E54851D}.Debug|x64.Build.0 = Debug|x64
{41A52A04-F7D8-4981-9546-DB020E54851D}.Release|Any CPU.ActiveCfg = Release|Any CPU {41A52A04-F7D8-4981-9546-DB020E54851D}.Release|x64.ActiveCfg = Release|x64
{41A52A04-F7D8-4981-9546-DB020E54851D}.Release|Any CPU.Build.0 = Release|Any CPU {41A52A04-F7D8-4981-9546-DB020E54851D}.Release|x64.Build.0 = Release|x64
EndGlobalSection EndGlobalSection
GlobalSection(SolutionProperties) = preSolution GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE HideSolutionNode = FALSE

View File

@ -7,7 +7,7 @@ This project is tested only under Windows, and this readme assumes you are using
* Any supported 64-bit edition of Windows. NativeAOT requires 64-bit Windows and produces only 64-bit Windows apps. * Any supported 64-bit edition of Windows. NativeAOT requires 64-bit Windows and produces only 64-bit Windows apps.
* Visual Studio. VS 2022 Community is free for personal use. Get if from [here](https://visualstudio.microsoft.com). * Visual Studio. VS 2022 Community is free for personal use. Get if from [here](https://visualstudio.microsoft.com).
When installing Visual Studio, select *.NET desktop development* and *Desktop development with C++* workloads. To generate native code, NativeAOT requires the native C++ toolchain and Windows SDK. This configuration ensures you have them. When installing Visual Studio, select *.NET desktop development* and *Desktop development with C++* workloads. To generate native code, NativeAOT requires the native C++ toolchain and Windows SDK. This configuration ensures you have them.
* .Net 7.0 SDK. Download it from [here](https://dotnet.microsoft.com/download/dotnet/7.0). Note: Make sure that you download and install the *SDK*. The runtime is not enough for building apps. * .Net 6.0 SDK. Download it from [here](https://dotnet.microsoft.com/download/dotnet/6.0). Note: Make sure that you download and install the *SDK*. The runtime is not enough for building apps.
* Git. Install [Git for Windows](https://git-scm.com/download/win). * Git. Install [Git for Windows](https://git-scm.com/download/win).
## Getting started ## Getting started
@ -34,6 +34,8 @@ We are ready - In your terminal, navigate to `src\bin\Release\net6.0\win-x64\pub
Feel free to use this sample as a base for your projects. Feel free to use this sample as a base for your projects.
When developing, keep in mind that Avalonia uses Reflection extensively. NativeAOT, being an AOT compiler, needs your help to get reflection right. Refer to `rd.xml` file in the solution. In it, you describe all assemblies and types which your app would potentially reflect over. For more information, see [Reflection in AOT mode](https://github.com/dotnet/runtimelab/blob/feature/NativeAOT/docs/using-nativeaot/reflection-in-aot-mode.md)
This project is configured to help you debug issues with publishing. Before publishing, check the CSPROJ file and modify the various Ilc* properties according to [Optimizing programs targeting Native AOT](https://github.com/dotnet/runtimelab/blob/feature/NativeAOT/docs/using-nativeaot/optimizing.md) document. This project is configured to help you debug issues with publishing. Before publishing, check the CSPROJ file and modify the various Ilc* properties according to [Optimizing programs targeting Native AOT](https://github.com/dotnet/runtimelab/blob/feature/NativeAOT/docs/using-nativeaot/optimizing.md) document.
## Artifact test ## Artifact test

View File

@ -1,26 +0,0 @@
{
"version": "0.2.0",
"configurations": [
{
// Use IntelliSense to find out which attributes exist for C# debugging
// Use hover for the description of the existing attributes
// For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
"name": ".NET Core Launch (console)",
"type": "coreclr",
"request": "launch",
"preLaunchTask": "build",
// If you have changed target frameworks, make sure to update the program path.
"program": "${workspaceFolder}/bin/Debug/net7.0/linux-x64/AvaloniaCoreRTDemo.dll",
"args": [],
"cwd": "${workspaceFolder}",
// For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
"console": "internalConsole",
"stopAtEntry": false
},
{
"name": ".NET Core Attach",
"type": "coreclr",
"request": "attach"
}
]
}

View File

@ -1,41 +0,0 @@
{
"version": "2.0.0",
"tasks": [
{
"label": "build",
"command": "dotnet",
"type": "process",
"args": [
"build",
"${workspaceFolder}/AvaloniaCoreRTDemo.csproj",
"/property:GenerateFullPaths=true",
"/consoleloggerparameters:NoSummary"
],
"problemMatcher": "$msCompile"
},
{
"label": "publish",
"command": "dotnet",
"type": "process",
"args": [
"publish",
"${workspaceFolder}/AvaloniaCoreRTDemo.csproj",
"/property:GenerateFullPaths=true",
"/consoleloggerparameters:NoSummary"
],
"problemMatcher": "$msCompile"
},
{
"label": "watch",
"command": "dotnet",
"type": "process",
"args": [
"watch",
"run",
"--project",
"${workspaceFolder}/AvaloniaCoreRTDemo.csproj"
],
"problemMatcher": "$msCompile"
}
]
}

View File

@ -1,22 +1,18 @@
<Application <Application xmlns="https://github.com/avaloniaui"
x:Class="AvaloniaCoreRTDemo.App"
xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:viewModels1="clr-namespace:AvaloniaCoreRTDemo.Windows.ViewModels" x:Class="AvaloniaCoreRTDemo.App">
x:CompileBindings="True"
x:DataType="viewModels1:ApplicationModelBase"
RequestedThemeVariant="Light">
<NativeMenu.Menu> <NativeMenu.Menu>
<NativeMenu> <NativeMenu>
<NativeMenuItem <NativeMenuItem Header="About" Gesture="cmd+b" IsEnabled="{Binding AboutEnabled}" Command="{Binding HelpAboutMethod}"/>
Command="{Binding HelpAboutCommand}"
Gesture="cmd+b"
Header="About"
IsEnabled="{Binding AboutEnabled}" />
</NativeMenu> </NativeMenu>
</NativeMenu.Menu> </NativeMenu.Menu>
<Application.Styles>
<StyleInclude Source="avares://Avalonia.Themes.Default/Accents/BaseDark.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Default/Accents/BaseLight.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Default/DefaultTheme.xaml"/>
</Application.Styles>
<Application.Resources> <Application.Resources>
<StyleInclude x:Key="fluentDataGrid" Source="avares://Avalonia.Controls.DataGrid/Themes/Fluent.xaml" /> <FluentTheme x:Key="fluentLight" Mode="Light" />
<StyleInclude x:Key="simpleDataGrid" Source="avares://Avalonia.Controls.DataGrid/Themes/Simple.xaml" /> <FluentTheme x:Key="fluentDark" Mode="Dark" />
</Application.Resources> </Application.Resources>
</Application> </Application>

View File

@ -1,108 +1,83 @@
using Avalonia; using Avalonia;
using Avalonia.Controls;
using Avalonia.Controls.ApplicationLifetimes; using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml; using Avalonia.Markup.Xaml;
using Avalonia.Styling; using Avalonia.Styling;
using Avalonia.Themes.Fluent; using Avalonia.Themes.Fluent;
using Avalonia.Themes.Simple;
using AvaloniaCoreRTDemo.Interfaces; using AvaloniaCoreRTDemo.Interfaces;
using AvaloniaCoreRTDemo.Windows; using AvaloniaCoreRTDemo.Windows;
namespace AvaloniaCoreRTDemo; namespace AvaloniaCoreRTDemo
public sealed class App : Application, IThemeSwitch
{ {
private FluentTheme _fluentTheme = default!; public sealed class App : Application, IThemeSwitch
private SimpleTheme _simpleTheme = default!; {
private IStyle _fluentDataGrid = default!; private IStyle _baseLight;
private IStyle _simpleDataGrid = default!; private IStyle _baseDark;
private IStyle _fluentLight;
private IStyle _fluentDark;
private ApplicationTheme _currentTheme; private ApplicationTheme _currentTheme;
public override void Initialize() public override void Initialize()
{ {
AvaloniaXamlLoader.Load(this); AvaloniaXamlLoader.Load(this);
Name = "AvaloniaCoreRTDemo"; this.Name = "AvaloniaCoreRTDemo";
} }
public override void OnFrameworkInitializationCompleted() public override void OnFrameworkInitializationCompleted()
{ {
InitializeThemes(); this.InitializeThemes();
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop) if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
{ {
desktop.MainWindow = new MainWindow(); desktop.MainWindow = !Utilities.IsOSX ? new MainWindow() : new MainWindowMacOS();
DataContext = desktop.MainWindow.DataContext; this.DataContext = desktop.MainWindow.DataContext;
} }
base.OnFrameworkInitializationCompleted(); base.OnFrameworkInitializationCompleted();
} }
private void InitializeThemes() private void InitializeThemes()
{ {
_simpleTheme = new SimpleTheme(); this._baseDark = this.Styles[0];
_fluentTheme = new FluentTheme(); this._baseLight = this.Styles[1];
_fluentDataGrid = (IStyle)Resources["fluentDataGrid"]!; this.Styles.Remove(this._baseDark);
_simpleDataGrid = (IStyle)Resources["simpleDataGrid"]!;
Styles.Add(_fluentTheme); this._fluentLight = (FluentTheme)this.Resources["fluentLight"]!;
Styles.Add(_fluentDataGrid); this._fluentDark = (FluentTheme)this.Resources["fluentDark"]!;
_currentTheme = ApplicationTheme.FluentLight;
this._currentTheme = ApplicationTheme.DefaultLight;
} }
ApplicationTheme IThemeSwitch.Current => _currentTheme; ApplicationTheme IThemeSwitch.Current => this._currentTheme;
void IThemeSwitch.ChangeTheme(ApplicationTheme theme) void IThemeSwitch.ChangeTheme(ApplicationTheme theme)
{ {
if (theme == _currentTheme) this._currentTheme = theme;
return;
var themeChanged = theme switch
{
ApplicationTheme.SimpleLight
=> _currentTheme is ApplicationTheme.FluentDark or ApplicationTheme.FluentLight,
ApplicationTheme.SimpleDark
=> _currentTheme is ApplicationTheme.FluentDark or ApplicationTheme.FluentLight,
ApplicationTheme.FluentLight
=> _currentTheme is ApplicationTheme.SimpleLight or ApplicationTheme.SimpleDark,
ApplicationTheme.FluentDark
=> _currentTheme is ApplicationTheme.SimpleLight or ApplicationTheme.SimpleDark,
_ => throw new ArgumentOutOfRangeException(nameof(theme), theme, null)
};
_currentTheme = theme;
switch (theme) switch (theme)
{ {
case ApplicationTheme.SimpleLight: case ApplicationTheme.DefaultLight:
SetValue(ThemeVariantScope.ActualThemeVariantProperty, ThemeVariant.Light); this.Styles[0] = this._baseLight;
Styles[0] = _simpleTheme; this.Styles.Remove(this._baseDark);
Styles[1] = _simpleDataGrid;
break; break;
case ApplicationTheme.SimpleDark: case ApplicationTheme.DefaultDark:
SetValue(ThemeVariantScope.ActualThemeVariantProperty, ThemeVariant.Dark); this.Styles[0] = this._baseDark;
Styles[0] = _simpleTheme; this.Styles.Remove(this._baseLight);
Styles[1] = _simpleDataGrid;
break; break;
case ApplicationTheme.FluentLight: case ApplicationTheme.FluentLight:
SetValue(ThemeVariantScope.ActualThemeVariantProperty, ThemeVariant.Light); this.Styles[0] = this._fluentLight;
Styles[0] = _fluentTheme; this.Styles.Remove(this._fluentDark);
Styles[1] = _fluentDataGrid; if (!this.Styles.Contains(this._baseLight))
this.Styles.Add(this._baseLight);
break; break;
case ApplicationTheme.FluentDark: case ApplicationTheme.FluentDark:
SetValue(ThemeVariantScope.ActualThemeVariantProperty, ThemeVariant.Dark); this.Styles[0] = this._fluentDark;
Styles[0] = _fluentTheme; this.Styles.Remove(this._baseLight);
Styles[1] = _fluentDataGrid; if (!this.Styles.Contains(this._baseDark))
this.Styles.Add(this._baseDark);
break; break;
} }
}
if (!themeChanged || ApplicationLifetime is not IClassicDesktopStyleApplicationLifetime desktop) return;
var oldWindow = (desktop.MainWindow as MainWindow)!;
var newWindow = new MainWindow(oldWindow);
desktop.MainWindow = newWindow;
DataContext = newWindow.DataContext;
oldWindow.Hide();
newWindow.Show();
oldWindow.Close();
} }
} }

View File

@ -1,9 +1,12 @@
namespace AvaloniaCoreRTDemo; using System;
public enum ApplicationTheme : byte namespace AvaloniaCoreRTDemo
{ {
SimpleLight = 0, public enum ApplicationTheme : Byte
SimpleDark = 1, {
DefaultLight = 0,
DefaultDark = 1,
FluentLight = 2, FluentLight = 2,
FluentDark = 3, FluentDark = 3,
}
} }

View File

@ -2,69 +2,59 @@
<PropertyGroup> <PropertyGroup>
<!-- if you want to check exceptions, change this to "Exe" and start your app from the console --> <!-- if you want to check exceptions, change this to "Exe" and start your app from the console -->
<OutputType Condition="'$(Configuration.toUpper())' != 'DEBUG'">WinExe</OutputType> <OutputType>WinExe</OutputType>
<OutputType Condition="'$(Configuration.toUpper())' == 'DEBUG'">Exe</OutputType> <TargetFramework>net6.0</TargetFramework>
<TargetFramework>net9.0</TargetFramework> <Platforms>x64</Platforms>
<ApplicationIcon>Assets/app.ico</ApplicationIcon> <ApplicationIcon>Assets/app.ico</ApplicationIcon>
<InvariantGlobalization>true</InvariantGlobalization> <InvariantGlobalization>true</InvariantGlobalization>
<Nullable>enable</Nullable> <!--https://docs.microsoft.com/en-us/dotnet/core/deploying/trimming/trimming-options-->
<PublishAot>true</PublishAot> <TrimmerDefaultAction>link</TrimmerDefaultAction>
<PublishTrimmed>true</PublishTrimmed>
<SelfContained>true</SelfContained>
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>
<PropertyGroup>
<IsWindows Condition="$([MSBuild]::IsOSPlatform('Windows'))">true</IsWindows> <IsWindows Condition="$([MSBuild]::IsOSPlatform('Windows'))">true</IsWindows>
<IsLinux Condition="$([MSBuild]::IsOSPlatform('Linux'))">true</IsLinux> <IsLinux Condition="$([MSBuild]::IsOSPlatform('Linux'))">true</IsLinux>
<IsOSX Condition="$([MSBuild]::IsOSPlatform('OSX'))">true</IsOSX> <IsOSX Condition="$([MSBuild]::IsOSPlatform('OSX'))">true</IsOSX>
<DefineConstants Condition="'$(IsOSX)'=='true'">OSX</DefineConstants>
</PropertyGroup> </PropertyGroup>
<PropertyGroup> <PropertyGroup>
<TrimMode>link</TrimMode> <!--Tthese can help when debugging weird exceptions especially when reflection is involved. See https://github.com/dotnet/corert/blob/master/Documentation/using-corert/optimizing-corert.md -->
<!--These can help when debugging weird exceptions especially when reflection is involved. See https://github.com/dotnet/corert/blob/master/Documentation/using-corert/optimizing-corert.md -->
<!--RootAllApplicationAssemblies: False -> TrimMode:link See https://github.com/dotnet/runtimelab/issues/597 and https://github.com/dotnet/runtimelab/blob/feature/NativeAOT/docs/using-nativeaot/optimizing.md --> <!--RootAllApplicationAssemblies: False -> TrimMode:link See https://github.com/dotnet/runtimelab/issues/597 and https://github.com/dotnet/runtimelab/blob/feature/NativeAOT/docs/using-nativeaot/optimizing.md -->
<IlcGenerateCompleteTypeMetadata>false</IlcGenerateCompleteTypeMetadata> <IlcGenerateCompleteTypeMetadata>false</IlcGenerateCompleteTypeMetadata>
<IlcGenerateStackTraceData Condition="'$(Configuration.toUpper())' != 'DEBUG'">false</IlcGenerateStackTraceData> <IlcGenerateStackTraceData>false</IlcGenerateStackTraceData>
<IlcDisableUnhandledExceptionExperience>true</IlcDisableUnhandledExceptionExperience> <IlcDisableUnhandledExceptionExperience>true</IlcDisableUnhandledExceptionExperience>
<StripSymbols Condition="'$(Configuration.toUpper())' != 'DEBUG'">true</StripSymbols>
</PropertyGroup> </PropertyGroup>
<!-- Instruct NativeAOT to use this native dependency, required to build Avalonia. This library comes from the Windows SDK. -->
<ItemGroup Condition="'$(IsWindows)'=='true'">
<NativeLibrary Include="WindowsApp.lib" />
</ItemGroup>
<ItemGroup> <ItemGroup>
<AvaloniaResource Include="Assets/**" /> <AvaloniaResource Include="Assets/**" />
<AvaloniaResource Include="Images/**" /> <EmbeddedResource Include="Images/**" />
<None Update="avalonia.png" CopyToPublishDirectory="PreserveNewest">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="dotnet.png" CopyToPublishDirectory="PreserveNewest">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="Assets/app.icns" CopyToPublishDirectory="PreserveNewest" Condition="$(RuntimeIdentifier.StartsWith('osx'))"> <None Update="Assets/app.icns" CopyToPublishDirectory="PreserveNewest" Condition="$(RuntimeIdentifier.StartsWith('osx'))">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None> </None>
<None Update="dotnet.png">
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="avalonia.png">
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<RuntimeHostConfigurationOption Include="Switch.System.Reflection.Assembly.SimulatedCallingAssembly" Value="true" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<PackageReference Include="Avalonia" Version="11.1.3" /> <PackageReference Include="Avalonia" Version="0.10.18" />
<PackageReference Include="Avalonia.Desktop" Version="11.1.3" /> <PackageReference Include="Avalonia.Desktop" Version="0.10.18" />
<PackageReference Include="Avalonia.Controls.DataGrid" Version="11.1.3" /> <PackageReference Include="Avalonia.Native" Version="0.10.18" />
<PackageReference Include="Avalonia.Themes.Simple" Version="11.1.3" /> <PackageReference Include="Avalonia.ReactiveUI" Version="0.10.18" />
<PackageReference Include="Avalonia.Themes.Fluent" Version="11.1.3" />
<!--Condition below is needed to remove Avalonia.Diagnostics package from build output in Release configuration.--> <!--Condition below is needed to remove Avalonia.Diagnostics package from build output in Release configuration.-->
<PackageReference Condition="'$(Configuration)' == 'Debug'" Include="Avalonia.Diagnostics" Version="11.0.3" /> <PackageReference Condition="'$(Configuration)' == 'Debug'" Include="Avalonia.Diagnostics" Version="0.10.18" />
<!--Condition below is needed to generate macOS App only.--> <!--Condition below is needed to generate macOS App only.-->
<PackageReference Include="Dotnet.Bundle" Version="0.9.13" Condition="$(RuntimeIdentifier.StartsWith('osx'))" /> <PackageReference Include="Dotnet.Bundle" Version="*" Condition="$(RuntimeIdentifier.StartsWith('osx'))" />
<PackageReference Include="MvvmGen.PureCodeGeneration" Version="1.3.0">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
</ItemGroup> </ItemGroup>
<!-- Information for Dotnet.Bundle to Generate macOS app--> <!-- Information for Dotnet.Bundle to Generate macOS app-->
<PropertyGroup> <PropertyGroup Condition="'$(IsOSX)'=='true'">
<CFBundleName>$(AssemblyName)</CFBundleName> <CFBundleName>$(AssemblyName)</CFBundleName>
<CFBundleDisplayName>$(AssemblyName)</CFBundleDisplayName> <CFBundleDisplayName>$(AssemblyName)</CFBundleDisplayName>
<CFBundleIdentifier>com.$(username).$(AssemblyName)</CFBundleIdentifier> <CFBundleIdentifier>com.$(username).$(AssemblyName)</CFBundleIdentifier>
@ -80,4 +70,39 @@
<NSRequiresAquaSystemAppearance>true</NSRequiresAquaSystemAppearance> <NSRequiresAquaSystemAppearance>true</NSRequiresAquaSystemAppearance>
</PropertyGroup> </PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.DotNet.ILCompiler" Version="8.0.0-*" />
<!-- Avalonia relies heavily on reflection. Describe types reflected upon here. -->
<RdXmlFile Include="rd.xml" />
<RuntimeHostConfigurationOption Include="Switch.System.Reflection.Assembly.SimulatedCallingAssembly" Value="true" />
</ItemGroup>
<!--App axaml-->
<ItemGroup>
<Compile Update="App.axaml.cs">
<DependentUpon>App.axaml</DependentUpon>
</Compile>
</ItemGroup>
<!--Cross platform xaml-->
<ItemGroup>
<Compile Update="Controls/MainControl.axaml.cs">
<DependentUpon>MainControl.axaml</DependentUpon>
</Compile>
<Compile Update="Windows/AboutWindow.axaml.cs">
<DependentUpon>AboutWindow.axaml</DependentUpon>
</Compile>
</ItemGroup>
<!--No-OSX only xaml-->
<ItemGroup Condition="'$(IsOSX)'!='true'">
<Compile Update="Windows/MainWindow.axaml.cs">
<DependentUpon>MainWindow.axaml</DependentUpon>
</Compile>
</ItemGroup>
<!--OSX only xaml-->
<ItemGroup Condition="'$(IsOSX)'=='true'">
<Compile Update="Windows/MainWindowMacOS.axaml.cs">
<DependentUpon>MainWindowMacOS.axaml</DependentUpon>
</Compile>
</ItemGroup>
</Project> </Project>

View File

@ -1,44 +1,9 @@
<UserControl <UserControl xmlns="https://github.com/avaloniaui" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
x:Class="AvaloniaCoreRTDemo.Controls.MainControl" mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" x:Class="AvaloniaCoreRTDemo.Controls.MainControl">
xmlns="https://github.com/avaloniaui" <Grid ColumnDefinitions="*,*" RowDefinitions="Auto,Auto,*" Margin="32">
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" <TextBlock Grid.Row="0" Grid.Column="0" Grid.ColumnSpan="2" TextAlignment="Center" Margin="0,6">Welcome to Avalonia UI + NativeAOT!</TextBlock>
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" <Image Grid.Row="1" Grid.Column="0" Stretch="None" Source="{Binding DotNetImage}"/>
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" <Image Grid.Row="1" Grid.Column="1" Stretch="None" Source="{Binding AvaloniaImage}"/>
xmlns:viewModels="clr-namespace:AvaloniaCoreRTDemo.Controls.ViewModels" <TextBox Grid.Row="2" Grid.Column="0" Grid.ColumnSpan="2" Watermark="Type here" AcceptsReturn="True" TextWrapping="Wrap"/>
d:DesignHeight="450"
d:DesignWidth="800"
x:CompileBindings="True"
x:DataType="viewModels:MainControlViewModel"
mc:Ignorable="d">
<Grid
Margin="32"
ColumnDefinitions="*,*"
RowDefinitions="Auto,Auto,*">
<TextBlock
Grid.Row="0"
Grid.Column="0"
Grid.ColumnSpan="2"
Margin="0,6"
TextAlignment="Center">
Welcome to Avalonia UI + NativeAOT!
</TextBlock>
<Image
Grid.Row="1"
Grid.Column="0"
Source="{Binding DotNetImage}"
Stretch="None" />
<Image
Grid.Row="1"
Grid.Column="1"
Source="{Binding AvaloniaImage}"
Stretch="None" />
<TextBox
Grid.Row="2"
Grid.Column="0"
Grid.ColumnSpan="2"
AcceptsReturn="True"
Text="{Binding Text}"
TextWrapping="Wrap"
Watermark="Type here" />
</Grid> </Grid>
</UserControl> </UserControl>

View File

@ -1,11 +1,12 @@
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Markup.Xaml; using Avalonia.Markup.Xaml;
using AvaloniaCoreRTDemo.Controls.ViewModels; using AvaloniaCoreRTDemo.Controls.ViewModels;
namespace AvaloniaCoreRTDemo.Controls; namespace AvaloniaCoreRTDemo.Controls
public sealed partial class MainControl : UserControl
{ {
public sealed partial class MainControl : UserControl
{
public MainControl() public MainControl()
{ {
InitializeComponent(); InitializeComponent();
@ -14,11 +15,7 @@ public sealed partial class MainControl : UserControl
private void InitializeComponent() private void InitializeComponent()
{ {
AvaloniaXamlLoader.Load(this); AvaloniaXamlLoader.Load(this);
DataContext = new MainControlViewModel(); this.DataContext = new MainViewModel();
} }
public void Reload(IMainWindowState model)
{
DataContext = new MainControlViewModel(model);
} }
} }

View File

@ -1,45 +0,0 @@
using Avalonia.Media.Imaging;
namespace AvaloniaCoreRTDemo.Controls.ViewModels;
[ViewModel]
internal sealed partial class MainControlViewModel : IMainWindowState
{
private Bitmap _dotNetImage;
private Bitmap _avaloniaImage;
private bool _unloadable = false;
public Bitmap DotNetImage => _dotNetImage;
public Bitmap AvaloniaImage => _avaloniaImage;
public string? Text { get; set; }
partial void OnInitialize()
{
_dotNetImage = Utilities.GetImageFromFile("dotnet.png");
_avaloniaImage = Utilities.GetImageFromFile("avalonia.png");
}
public MainControlViewModel(IMainWindowState state)
: this()
{
_avaloniaImage = state.AvaloniaImage;
_dotNetImage = state.DotNetImage;
Text = state.Text;
state.SetUnloadable();
}
~MainControlViewModel()
{
if (!_unloadable)
{
_dotNetImage.Dispose();
_avaloniaImage.Dispose();
}
}
void IMainWindowState.SetUnloadable()
{
_unloadable = true;
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.IO;
using Avalonia.Media.Imaging;
using ReactiveUI;
namespace AvaloniaCoreRTDemo.Controls.ViewModels
{
internal sealed class MainViewModel : ReactiveObject
{
private readonly IBitmap _dotNetImage;
private readonly IBitmap _avaloniaImage;
public IBitmap DotNetImage => this._dotNetImage;
public IBitmap AvaloniaImage => this._avaloniaImage;
public MainViewModel()
{
this._dotNetImage = Utilities.GetImageFromFile(GetImageFullPath("dotnet.png"));
this._avaloniaImage = Utilities.GetImageFromFile(GetImageFullPath("avalonia.png"));
}
private static String GetImageFullPath(String fileName)
=> Path.Combine(AppDomain.CurrentDomain.BaseDirectory, fileName);
~MainViewModel()
{
this._dotNetImage.Dispose();
this._avaloniaImage.Dispose();
}
}
}

View File

@ -1,3 +0,0 @@
// Global using directives
global using MvvmGen;

View File

@ -1,14 +1,9 @@
using Avalonia; using AvaloniaCoreRTDemo.Interfaces;
using Avalonia.Controls;
namespace AvaloniaCoreRTDemo.Interfaces; namespace AvaloniaCoreRTDemo
public interface IMainWindow
{ {
public interface IMainWindow
{
IThemeSwitch ThemeSwitch { get; } IThemeSwitch ThemeSwitch { get; }
IMainWindowState Model { get; } }
PixelPoint Position { get; }
Size ClientSize { get; }
Size? FrameSize { get; }
WindowState State { get; }
} }

View File

@ -1,12 +0,0 @@
using Avalonia.Media.Imaging;
namespace AvaloniaCoreRTDemo;
public interface IMainWindowState
{
Bitmap DotNetImage { get; }
Bitmap AvaloniaImage { get; }
string? Text { get; }
void SetUnloadable();
}

View File

@ -1,7 +1,8 @@
namespace AvaloniaCoreRTDemo.Interfaces; namespace AvaloniaCoreRTDemo.Interfaces
public interface IThemeSwitch
{ {
public interface IThemeSwitch
{
ApplicationTheme Current { get; } ApplicationTheme Current { get; }
void ChangeTheme(ApplicationTheme theme); void ChangeTheme(ApplicationTheme theme);
}
} }

View File

@ -1,16 +1,21 @@
using Avalonia; using Avalonia;
namespace AvaloniaCoreRTDemo; namespace AvaloniaCoreRTDemo
public static class Program
{ {
public static class Program
{
// Initialization code. Don't use any Avalonia, third-party APIs or any // Initialization code. Don't use any Avalonia, third-party APIs or any
// SynchronizationContext-reliant code before AppMain is called: things aren't initialized // SynchronizationContext-reliant code before AppMain is called: things aren't initialized
// yet and stuff might break. // yet and stuff might break.
public static void Main(string[] args) => public static void Main(string[] args) => BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
// Avalonia configuration, don't remove; also used by visual designer. // Avalonia configuration, don't remove; also used by visual designer.
public static AppBuilder BuildAvaloniaApp() => public static AppBuilder BuildAvaloniaApp()
AppBuilder.Configure<App>().UsePlatformDetect().LogToTrace(); => AppBuilder.Configure<App>().UsePlatformDetect()
.UseAvaloniaNativeOSX()
.LogToTrace();
private static AppBuilder UseAvaloniaNativeOSX(this AppBuilder appBuilder)
=> Utilities.IsOSX ? appBuilder.UseAvaloniaNative() : appBuilder;
}
} }

View File

@ -1,44 +1,39 @@
using System.Runtime.InteropServices; using System;
using Avalonia; using System.IO;
using Avalonia.Controls; using System.Linq;
using System.Reflection;
using System.Runtime.InteropServices;
using Avalonia.Media.Imaging; using Avalonia.Media.Imaging;
using Avalonia.Platform;
namespace AvaloniaCoreRTDemo; namespace AvaloniaCoreRTDemo
internal static class Utilities
{ {
public static readonly bool IsWindows = RuntimeInformation.IsOSPlatform(OSPlatform.Windows); internal static class Utilities
public static readonly bool IsOSX = RuntimeInformation.IsOSPlatform(OSPlatform.OSX);
public static Bitmap GetImageFromResources(string fileName)
{ {
using var assetStream = AssetLoader.Open( public static readonly Boolean IsWindows = RuntimeInformation.IsOSPlatform(OSPlatform.Windows);
new Uri($"avares://AvaloniaCoreRTDemo/Images/{fileName}") public static readonly Boolean IsOSX = RuntimeInformation.IsOSPlatform(OSPlatform.OSX);
);
return new Bitmap(assetStream); public static Bitmap GetImageFromResources(String fileName)
{
Assembly asm = Assembly.GetExecutingAssembly();
String resourceName = asm.GetManifestResourceNames().FirstOrDefault(str => str.EndsWith(fileName));
if (resourceName != null)
using (Stream bitmapStream = asm.GetManifestResourceStream(resourceName))
return new Bitmap(bitmapStream);
else
return default;
} }
public static PixelPoint GetWindowPosition(Window window) public static Bitmap GetImageFromFile(String path)
{
if (!IsOSX || !window.FrameSize.HasValue)
return window.Position;
var yOffset = (int)(window.FrameSize.Value.Height - window.ClientSize.Height);
return new(window.Position.X, window.Position.Y + yOffset);
}
public static Bitmap GetImageFromFile(string path)
{ {
try try
{ {
return new Bitmap(GetImageFullPath(path)); return new Bitmap(path);
} }
catch (Exception) catch (Exception)
{ {
return GetImageFromResources("broken-link.png"); return GetImageFromResources("broken-link.png");
} }
} }
}
private static string GetImageFullPath(string fileName) =>
Path.Combine(AppDomain.CurrentDomain.BaseDirectory, fileName);
} }

View File

@ -1,50 +1,64 @@
<Window <Window xmlns="https://github.com/avaloniaui" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
x:Class="AvaloniaCoreRTDemo.Windows.AboutWindow" mc:Ignorable="d" x:Class="AvaloniaCoreRTDemo.Windows.AboutWindow" d:DesignWidth="640" d:DesignHeight="256"
xmlns="https://github.com/avaloniaui" WindowState="Normal" WindowStartupLocation="CenterOwner" MinHeight="256" MinWidth="640" Height="256" Width="640" MaxHeight="256" MaxWidth="640" Title="About" CanResize="false" ShowInTaskbar="False" Icon="avares://AvaloniaCoreRTDemo/Assets/about.ico">
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" <Grid VerticalAlignment="Top" HorizontalAlignment="Left" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" <Image Margin="0, 60" Grid.Row="0" Grid.Column="0" Stretch="None" Source="{Binding ComputerImage}" VerticalAlignment="Top" HorizontalAlignment="Left">
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" </Image>
xmlns:viewModels="clr-namespace:AvaloniaCoreRTDemo.Windows.ViewModels" <ScrollViewer Margin="0, 10" Width="500" Height="230" Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" ScrollViewer.VerticalScrollBarVisibility="Auto" ScrollViewer.HorizontalScrollBarVisibility="Auto">
Title="About" <Grid ColumnDefinitions="Auto" RowDefinitions="Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto,Auto">
Height="256" <Grid Grid.Row="0" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
MaxWidth="840" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Number of Cores: "/>
d:DesignHeight="256" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding NCores}"/>
d:DesignWidth="640" </Grid>
x:CompileBindings="True" <Grid Grid.Row="1" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
x:DataType="viewModels:AboutViewModel" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="OS: "/>
CanResize="false" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding OS}"/>
Icon="avares://AvaloniaCoreRTDemo/Assets/about.ico" </Grid>
ShowInTaskbar="False" <Grid Grid.Row="2" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
SizeToContent="Width" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="OS Arch: "/>
WindowStartupLocation="CenterOwner" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding OSArch}"/>
WindowState="Normal" </Grid>
mc:Ignorable="d"> <Grid Grid.Row="3" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<Grid <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="OS Version: "/>
HorizontalAlignment="Left" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding OSVersion}"/>
VerticalAlignment="Top" </Grid>
ColumnDefinitions="Auto,*"> <Grid Grid.Row="4" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<Image <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Computer: "/>
Grid.Column="0" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding ComputerName}"/>
Margin="0,60" </Grid>
HorizontalAlignment="Left" <Grid Grid.Row="5" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
VerticalAlignment="Top" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="User: "/>
Source="{Binding ComputerImage}" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding UserName}"/>
Stretch="None" /> </Grid>
<DataGrid <Grid Grid.Row="6" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
Grid.Column="1" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="System Path: "/>
CanUserReorderColumns="False" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding SystemPath}"/>
CanUserResizeColumns="False" </Grid>
CanUserSortColumns="False" <Grid Grid.Row="7" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
HeadersVisibility="None" <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Current Path: "/>
IsReadOnly="True" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding CurrentPath}"/>
ItemsSource="{Binding SystemDetails}"> </Grid>
<DataGrid.Columns> <Grid Grid.Row="8" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<DataGridTextColumn <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Process Arch: "/>
Binding="{Binding Key, x:DataType=viewModels:SystemDetail}" <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding ProcessArch}"/>
FontWeight="Bold" </Grid>
Header="Key" /> <Grid Grid.Row="9" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<DataGridTextColumn Binding="{Binding Value, x:DataType=viewModels:SystemDetail}" Header="Value" /> <TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Runtime Name: "/>
</DataGrid.Columns> <TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding RuntimeName}"/>
</DataGrid> </Grid>
<Grid Grid.Row="10" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Runtime Path: "/>
<TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding RuntimePath}"/>
</Grid>
<Grid Grid.Row="11" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Runtime Version: "/>
<TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding RuntimeVersion}"/>
</Grid>
<Grid Grid.Row="12" Grid.Column="0" ColumnDefinitions="Auto,Auto" RowDefinitions="Auto">
<TextBlock Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" FontWeight="Bold" Text="Framework Version: "/>
<TextBlock Grid.Row="0" Grid.Column="1" VerticalAlignment="Top" HorizontalAlignment="Left" TextAlignment="Left" Text="{Binding FrameworkVersion}"/>
</Grid>
</Grid>
</ScrollViewer>
</Grid> </Grid>
</Window> </Window>

View File

@ -1,28 +1,28 @@
using System;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Markup.Xaml; using Avalonia.Markup.Xaml;
using AvaloniaCoreRTDemo.Windows.ViewModels; using AvaloniaCoreRTDemo.Windows.ViewModels;
namespace AvaloniaCoreRTDemo.Windows; namespace AvaloniaCoreRTDemo.Windows
public sealed partial class AboutWindow : Window
{ {
private readonly bool _darkTheme; public sealed partial class AboutWindow : Window
public AboutWindow()
: this(false) { }
public AboutWindow(bool darkTheme)
{ {
_darkTheme = darkTheme; public AboutWindow()
InitializeComponent(); {
#if DEBUG this.InitializeComponent();
this.AttachDevTools();
#endif
} }
private void InitializeComponent() public AboutWindow(Boolean darkTheme)
{
this.InitializeComponent(darkTheme);
}
private void InitializeComponent(Boolean darkTheme = default)
{ {
AvaloniaXamlLoader.Load(this); AvaloniaXamlLoader.Load(this);
DataContext = new AboutViewModel(_darkTheme); this.DataContext = new AboutViewModel(darkTheme);
}
} }
} }

View File

@ -1,66 +1,21 @@
<Window <Window xmlns="https://github.com/avaloniaui" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
x:Class="AvaloniaCoreRTDemo.Windows.MainWindow" xmlns:controls="clr-namespace:AvaloniaCoreRTDemo.Controls" mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" x:Class="AvaloniaCoreRTDemo.Windows.MainWindow"
xmlns="https://github.com/avaloniaui" Width="640" Height="480" WindowStartupLocation="CenterScreen" Title="AvaloniaCoreRTDemo" Icon="avares://AvaloniaCoreRTDemo/Assets/app.ico" MinWidth="400" MinHeight="350">
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:controls="clr-namespace:AvaloniaCoreRTDemo.Controls"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:viewModels1="clr-namespace:AvaloniaCoreRTDemo.Windows.ViewModels"
Title="AvaloniaCoreRTDemo"
Width="640"
Height="480"
MinWidth="400"
MinHeight="350"
d:DesignHeight="450"
d:DesignWidth="800"
x:CompileBindings="True"
x:DataType="viewModels1:ApplicationModelBase"
Icon="avares://AvaloniaCoreRTDemo/Assets/app.ico"
WindowStartupLocation="CenterScreen"
mc:Ignorable="d">
<DockPanel> <DockPanel>
<NativeMenuBar DockPanel.Dock="Top" /> <Menu DockPanel.Dock="Top">
<controls:MainControl Name="MainControl" /> <MenuItem Header="_File">
<MenuItem Header="_Exit" Command="{Binding FileExitCommand}"/>
</MenuItem>
<MenuItem Header="_Theme">
<MenuItem Header="Default Light" IsEnabled="{Binding DefaultLightEnabled}" Command="{Binding DefaultLightMethod}"/>
<MenuItem Header="Default Dark" IsEnabled="{Binding DefaultDarkEnabled}" Command="{Binding DefaultDarkMethod}"/>
<MenuItem Header="Fluent Light" IsEnabled="{Binding FluentLightEnabled}" Command="{Binding FluentLightMethod}"/>
<MenuItem Header="Fluent Dark" IsEnabled="{Binding FluentDarkEnabled}" Command="{Binding FluentDarkMethod}"/>
</MenuItem>
<MenuItem Header="_Help">
<MenuItem Header="_About" IsEnabled="{Binding AboutEnabled}" Command="{Binding HelpAboutMethod}"/>
</MenuItem>
</Menu>
<controls:MainControl/>
</DockPanel> </DockPanel>
<NativeMenu.Menu>
<NativeMenu>
<NativeMenuItem Header="File">
<NativeMenuItem.Menu>
<NativeMenu>
<NativeMenuItem
Command="{Binding FileExitCommand}"
Gesture="cmd+e"
Header="Exit" />
<NativeMenuItem
Command="{Binding HelpAboutCommand}"
Gesture="cmd+b"
Header="About"
IsEnabled="{Binding AboutEnabled}" />
</NativeMenu>
</NativeMenuItem.Menu>
</NativeMenuItem>
<NativeMenuItem Header="Theme">
<NativeMenuItem.Menu>
<NativeMenu>
<NativeMenuItem
Command="{Binding DefaultLightCommand}"
Header="Default Light"
IsEnabled="{Binding DefaultLightEnabled}" />
<NativeMenuItem
Command="{Binding DefaultDarkCommand}"
Header="Default Dark"
IsEnabled="{Binding DefaultDarkEnabled}" />
<NativeMenuItem
Command="{Binding FluentLightCommand}"
Header="Fluent Light"
IsEnabled="{Binding FluentLightEnabled}" />
<NativeMenuItem
Command="{Binding FluentDarkCommand}"
Header="Fluent Dark"
IsEnabled="{Binding FluentDarkEnabled}" />
</NativeMenu>
</NativeMenuItem.Menu>
</NativeMenuItem>
</NativeMenu>
</NativeMenu.Menu>
</Window> </Window>

View File

@ -1,48 +1,28 @@
using Avalonia; using Avalonia;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Markup.Xaml; using Avalonia.Markup.Xaml;
using AvaloniaCoreRTDemo.Controls;
using AvaloniaCoreRTDemo.Interfaces; using AvaloniaCoreRTDemo.Interfaces;
using AvaloniaCoreRTDemo.Windows.ViewModels; using AvaloniaCoreRTDemo.Windows.ViewModels;
namespace AvaloniaCoreRTDemo.Windows; namespace AvaloniaCoreRTDemo.Windows
public sealed partial class MainWindow : Window, IMainWindow
{ {
private readonly Application? _app = Application.Current; public sealed partial class MainWindow : Window, IMainWindow
private MainControl MainController => this.GetControl<MainControl>("MainControl");
public MainWindow()
: this(default) { }
public MainWindow(IMainWindow? window)
{ {
InitializeComponent(window); public MainWindow()
{
InitializeComponent();
#if DEBUG #if DEBUG
this.AttachDevTools(); this.AttachDevTools();
#endif #endif
} }
IThemeSwitch IMainWindow.ThemeSwitch => (IThemeSwitch)_app!; private void InitializeComponent()
IMainWindowState IMainWindow.Model => (IMainWindowState)this.MainController.DataContext!;
PixelPoint IMainWindow.Position => Utilities.GetWindowPosition(this);
Size IMainWindow.ClientSize => ClientSize;
Size? IMainWindow.FrameSize => FrameSize;
WindowState IMainWindow.State => WindowState;
private void InitializeComponent(IMainWindow? window)
{ {
AvaloniaXamlLoader.Load(this); AvaloniaXamlLoader.Load(this);
DataContext = new MainViewModel<MainWindow>(this); this.DataContext = new MainViewModel<MainWindow>(this);
if (window is not null)
{
this.MainController.Reload(window.Model);
WindowStartupLocation = WindowStartupLocation.Manual;
WindowState = window.State;
Position = window.Position;
FrameSize = window.FrameSize;
ClientSize = window.ClientSize;
} }
IThemeSwitch IMainWindow.ThemeSwitch => App.Current as IThemeSwitch;
} }
} }

View File

@ -0,0 +1,26 @@
<Window xmlns="https://github.com/avaloniaui" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:controls="clr-namespace:AvaloniaCoreRTDemo.Controls" mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" x:Class="AvaloniaCoreRTDemo.Windows.MainWindowMacOS"
Width="640" Height="480" WindowStartupLocation="CenterScreen" Title="AvaloniaCoreRTDemo" Icon="avares://AvaloniaCoreRTDemo/Assets/app.ico" MinWidth="400" MinHeight="350">
<controls:MainControl/>
<NativeMenu.Menu>
<NativeMenu>
<NativeMenuItem Header="File">
<NativeMenuItem.Menu>
<NativeMenu>
<NativeMenuItem Header="Exit" Gesture="cmd+e" Command="{Binding FileExitCommand}"/>
</NativeMenu>
</NativeMenuItem.Menu>
</NativeMenuItem>
<NativeMenuItem Header="Theme">
<NativeMenuItem.Menu>
<NativeMenu>
<NativeMenuItem Header="Default Light" IsEnabled="{Binding DefaultLightEnabled}" Command="{Binding DefaultLightMethod}"/>
<NativeMenuItem Header="Default Dark" IsEnabled="{Binding DefaultDarkEnabled}" Command="{Binding DefaultDarkMethod}"/>
<NativeMenuItem Header="Fluent Light" IsEnabled="{Binding FluentLightEnabled}" Command="{Binding FluentLightMethod}"/>
<NativeMenuItem Header="Fluent Dark" IsEnabled="{Binding FluentDarkEnabled}" Command="{Binding FluentDarkMethod}"/>
</NativeMenu>
</NativeMenuItem.Menu>
</NativeMenuItem>
</NativeMenu>
</NativeMenu.Menu>
</Window>

View File

@ -0,0 +1,28 @@
using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;
using AvaloniaCoreRTDemo.Interfaces;
using AvaloniaCoreRTDemo.Windows.ViewModels;
namespace AvaloniaCoreRTDemo.Windows
{
public partial class MainWindowMacOS : Window, IMainWindow
{
public MainWindowMacOS()
{
InitializeComponent();
#if DEBUG
this.AttachDevTools();
#endif
}
private void InitializeComponent()
{
AvaloniaXamlLoader.Load(this);
this.DataContext = new MainViewModel<MainWindowMacOS>(this);
}
IThemeSwitch IMainWindow.ThemeSwitch => App.Current as IThemeSwitch;
}
}

View File

@ -1,56 +1,54 @@
using System.Runtime.InteropServices; using System;
using System.Runtime.InteropServices;
using Avalonia.Media.Imaging; using Avalonia.Media.Imaging;
namespace AvaloniaCoreRTDemo.Windows.ViewModels; using ReactiveUI;
internal record SystemDetail(string Key, string Value); namespace AvaloniaCoreRTDemo.Windows.ViewModels
[ViewModel]
internal sealed partial class AboutViewModel
{ {
private readonly Bitmap _computerImage; internal sealed class AboutViewModel : ReactiveObject
private readonly bool _darkTheme; {
private readonly IBitmap _computerImage;
private readonly Boolean _darkTheme;
public Bitmap ComputerImage => _computerImage; public IBitmap ComputerImage => _computerImage;
public static String NCores => Environment.ProcessorCount.ToString();
public static String OS => RuntimeInformation.OSDescription;
public static String OSArch => RuntimeInformation.OSArchitecture.ToString();
public static String OSVersion => Environment.OSVersion.ToString();
public static String ComputerName => Environment.MachineName;
public static String UserName => Environment.UserName;
public static String SystemPath => Environment.SystemDirectory;
public static String CurrentPath => Environment.CurrentDirectory;
public static String ProcessArch => RuntimeInformation.ProcessArchitecture.ToString();
public static String RuntimeName => RuntimeInformation.FrameworkDescription;
public static String RuntimePath => RuntimeEnvironment.GetRuntimeDirectory();
public static String RuntimeVersion => RuntimeEnvironment.GetSystemVersion();
public static String FrameworkVersion => Environment.Version.ToString();
public IReadOnlyList<SystemDetail> SystemDetails { get; } = private String ComputerImageName
[
new SystemDetail("Number of Cores", Environment.ProcessorCount.ToString()),
new SystemDetail("OS", RuntimeInformation.OSDescription),
new SystemDetail("OS Arch", RuntimeInformation.OSArchitecture.ToString()),
new SystemDetail("OS Version", Environment.OSVersion.ToString()),
new SystemDetail("Computer", Environment.MachineName),
new SystemDetail("User", Environment.UserName),
new SystemDetail("System Path", Environment.SystemDirectory),
new SystemDetail("Current Path", Environment.CurrentDirectory),
new SystemDetail("Process Arch", RuntimeInformation.ProcessArchitecture.ToString()),
new SystemDetail("Runtime Name", RuntimeInformation.FrameworkDescription),
new SystemDetail("Runtime Path", RuntimeEnvironment.GetRuntimeDirectory()),
new SystemDetail("Runtime Version", RuntimeEnvironment.GetSystemVersion()),
new SystemDetail("Framework Version", Environment.Version.ToString())
];
private string ComputerImageName
{ {
get get
{ {
if (Utilities.IsWindows) if (Utilities.IsWindows)
return !_darkTheme ? "windows.png" : "windows_d.png"; return !this._darkTheme ? "windows.png" : "windows_d.png";
if (Utilities.IsOSX) else if (Utilities.IsOSX)
return !_darkTheme ? "macos.png" : "macos_d.png"; return !this._darkTheme ? "macos.png" : "macos_d.png";
return !_darkTheme ? "linux.png" : "linux_d.png"; else
return !this._darkTheme ? "linux.png" : "linux_d.png";
} }
} }
public AboutViewModel(bool darkTheme) public AboutViewModel(Boolean darkTheme)
: this()
{ {
_darkTheme = darkTheme; this._darkTheme = darkTheme;
_computerImage = Utilities.GetImageFromResources(ComputerImageName); this._computerImage = Utilities.GetImageFromResources(this.ComputerImageName);
} }
~AboutViewModel() ~AboutViewModel()
{ {
_computerImage.Dispose(); this._computerImage.Dispose();
}
} }
} }

View File

@ -1,86 +0,0 @@
using Avalonia.Controls;
using AvaloniaCoreRTDemo.Interfaces;
namespace AvaloniaCoreRTDemo.Windows.ViewModels;
[ViewModel]
internal abstract partial class ApplicationModelBase
{
private readonly IThemeSwitch _themeSwitch;
[Property]
private bool _aboutEnabled = true;
[Property]
private bool _defaultLightEnabled;
[Property]
private bool _defaultDarkEnabled;
[Property]
private bool _fluentLightEnabled;
[Property]
private bool _fluentDarkEnabled;
public ApplicationModelBase(IThemeSwitch themeSwitch)
: this()
{
_themeSwitch = themeSwitch;
InitializeTheme(themeSwitch.Current);
}
[Command]
protected abstract void HelpAbout();
[Command]
protected abstract void DefaultLight();
[Command]
protected abstract void DefaultDark();
[Command]
protected abstract void FluentLight();
[Command]
protected abstract void FluentDark();
protected async void RunHelpAbout(Window currentWindow)
{
if (AboutEnabled)
try
{
AboutEnabled = false;
await new AboutWindow(IsDarkTheme(_themeSwitch.Current)).ShowDialog(currentWindow);
}
finally
{
AboutEnabled = true;
}
}
protected void SetTheme(ApplicationTheme theme)
{
InitializeTheme(theme);
_themeSwitch.ChangeTheme(theme);
}
[Command]
private void FileExit() => Environment.Exit(0);
private void InitializeTheme(ApplicationTheme theme)
{
DefaultLightEnabled = theme != ApplicationTheme.SimpleLight;
DefaultDarkEnabled = theme != ApplicationTheme.SimpleDark;
FluentLightEnabled = theme != ApplicationTheme.FluentLight;
FluentDarkEnabled = theme != ApplicationTheme.FluentDark;
}
private static bool IsDarkTheme(ApplicationTheme? theme) =>
theme switch
{
ApplicationTheme.SimpleDark => true,
ApplicationTheme.FluentDark => true,
_ => false,
};
}

View File

@ -1,26 +1,72 @@
using Avalonia.Controls; using System;
using AvaloniaCoreRTDemo.Interfaces; using System.Reactive;
namespace AvaloniaCoreRTDemo.Windows.ViewModels; using Avalonia.Controls;
internal sealed class MainViewModel<TWindow> : ApplicationModelBase using ReactiveUI;
where TWindow : Window, IMainWindow
namespace AvaloniaCoreRTDemo.Windows.ViewModels
{ {
internal sealed class MainViewModel<TWindow> : MainViewModelBase
where TWindow : Window, IMainWindow
{
private readonly TWindow _window; private readonly TWindow _window;
private Boolean _defaultLightEnable = true;
private Boolean _defaultDarkEnable = true;
private Boolean _fluentLightEnable = true;
private Boolean _fluentDarkEnable = true;
public Boolean DefaultLightEnabled
{
get => this._defaultLightEnable;
set => this.RaiseAndSetIfChanged(ref this._defaultLightEnable, value);
}
public Boolean DefaultDarkEnabled
{
get => this._defaultDarkEnable;
set => this.RaiseAndSetIfChanged(ref this._defaultDarkEnable, value);
}
public Boolean FluentLightEnabled
{
get => this._fluentLightEnable;
set => this.RaiseAndSetIfChanged(ref this._fluentLightEnable, value);
}
public Boolean FluentDarkEnabled
{
get => this._fluentDarkEnable;
set => this.RaiseAndSetIfChanged(ref this._fluentDarkEnable, value);
}
public ReactiveCommand<Unit, Unit> FileExitCommand { get; }
public MainViewModel(TWindow window) public MainViewModel(TWindow window)
: base(window.ThemeSwitch) : base(window.ThemeSwitch)
{ {
_window = window; this._window = window;
this.FileExitCommand = ReactiveCommand.Create(RunFileExit);
this.ChangeTheme(window.ThemeSwitch.Current);
} }
protected override void HelpAbout() => RunHelpAbout(_window); public void DefaultLightMethod() => this.ChangeTheme(ApplicationTheme.DefaultLight);
public void DefaultDarkMethod() => this.ChangeTheme(ApplicationTheme.DefaultDark);
public void FluentLightMethod() => this.ChangeTheme(ApplicationTheme.FluentLight);
public void FluentDarkMethod() => this.ChangeTheme(ApplicationTheme.FluentDark);
public override void HelpAboutMethod() => base.RunHelpAbout(this._window);
protected override void DefaultLight() => SetTheme(ApplicationTheme.SimpleLight); private void RunFileExit()
=> Environment.Exit(0);
protected override void DefaultDark() => SetTheme(ApplicationTheme.SimpleDark); private void ChangeTheme(ApplicationTheme theme)
{
protected override void FluentLight() => SetTheme(ApplicationTheme.FluentLight); this.DefaultLightEnabled = theme != ApplicationTheme.DefaultLight && theme != ApplicationTheme.FluentLight;
this.DefaultDarkEnabled = theme != ApplicationTheme.DefaultDark && theme != ApplicationTheme.FluentDark;
protected override void FluentDark() => SetTheme(ApplicationTheme.FluentDark); this.FluentLightEnabled = theme != ApplicationTheme.FluentLight;
this.FluentDarkEnabled = theme != ApplicationTheme.FluentDark;
this._window.ThemeSwitch?.ChangeTheme(theme);
}
}
} }

View File

@ -0,0 +1,49 @@
using System;
using Avalonia.Controls;
using AvaloniaCoreRTDemo.Interfaces;
using ReactiveUI;
namespace AvaloniaCoreRTDemo.Windows.ViewModels
{
internal abstract class MainViewModelBase : ReactiveObject
{
private readonly IThemeSwitch _themeSwitch;
private Boolean _aboutEnable = true;
public Boolean AboutEnabled
{
get => this._aboutEnable;
set => this.RaiseAndSetIfChanged(ref this._aboutEnable, value);
}
public MainViewModelBase(IThemeSwitch window)
=> this._themeSwitch = window;
public abstract void HelpAboutMethod();
protected async void RunHelpAbout(Window currentWindow)
{
if (this.AboutEnabled)
try
{
this.AboutEnabled = false;
await new AboutWindow(IsDarkTheme(this._themeSwitch.Current)).ShowDialog(currentWindow);
}
finally
{
this.AboutEnabled = true;
}
}
private static Boolean IsDarkTheme(ApplicationTheme? theme)
=> theme switch
{
ApplicationTheme.DefaultDark => true,
ApplicationTheme.FluentDark => true,
_ => false,
};
}
}

View File

@ -1,7 +1,8 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<configuration> <configuration>
<packageSources> <packageSources>
<!--<add key="avalonia" value="https://nuget.avaloniaui.net/repository/avalonia-all/index.json" />--> <add key="dotnet7" value="https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet7/nuget/v3/index.json" />
<add key="dotnet8" value="https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet8/nuget/v3/index.json" />
<add key="nuget" value="https://api.nuget.org/v3/index.json" /> <add key="nuget" value="https://api.nuget.org/v3/index.json" />
</packageSources> </packageSources>
</configuration> </configuration>

48
src/rd.xml Normal file
View File

@ -0,0 +1,48 @@
<Directives>
<Application>
<!-- main app assembly provides types which needs to be reflected upon -->
<Assembly Name="AvaloniaCoreRTDemo" Dynamic="Required All"></Assembly>
<!-- these are needed when you show images and draw text -->
<Assembly Name="Avalonia.Animation">
<Type Name="Avalonia.Animation.Easings.QuadraticEaseIn" Dynamic="Required All" />
<Type Name="Avalonia.Animation.Easings.QuadraticEaseOut" Dynamic="Required All" />
<Type Name="Avalonia.Animation.Easings.CubicEaseOut" Dynamic="Required All" />
<Type Name="Avalonia.Animation.Easings.LinearEasing" Dynamic="Required All" />
</Assembly>
<Assembly Name="Avalonia.Themes.Default" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Visuals" Dynamic="Required All">
<Type Name="Avalonia.Media.SolidColorBrush" Dynamic="Required All" />
</Assembly>
<Assembly Name="SkiaSharp" Dynamic="Required All"></Assembly>
<!-- To support Fluent themes trimming the final assembly we need to add this entry -->
<Assembly Name="Avalonia.Themes.Fluent" Dynamic="Required All"></Assembly>
<!-- Not known if and when you need these:
<Assembly Name="Avalonia.Controls" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Base" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Interactivity" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Layout" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Markup" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Markup.Xaml" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Styling" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.DesktopRuntime" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.DesignerSupport" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Diagnostics" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Dialogs" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Input" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Logging.Serilog" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.OpenGL" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Desktop" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Direct2D1" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.ReactiveUI" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Skia" Dynamic="Required All"></Assembly>
<Assembly Name="Avalonia.Win32" Dynamic="Required All"></Assembly>
<Assembly Name="ReactiveUI" Dynamic="Required All"></Assembly>
<Assembly Name="System.Reactive" Dynamic="Required All"></Assembly>
<Assembly Name="Splat" Dynamic="Required All"></Assembly>
-->
</Application>
</Directives>

View File

@ -1,2 +1,2 @@
del src\packages.lock.json del src\packages.lock.json
dotnet publish -r win-x64 -c Release /p:RestoreLockedMode=true dotnet publish -r win-x64 -c release /p:RestoreLockedMode=true /p:TrimLink=true --self-contained

View File

@ -4,7 +4,10 @@ if [ -d "$dir" ]; then
cd "$dir" cd "$dir"
fi fi
rm -f src/packages.lock.json rm -f src/packages.lock.json
dotnet publish -r osx-x64 -c Release /p:RestoreLockedMode=true -t:BundleApp dotnet publish -r osx-x64 -c release /p:RestoreLockedMode=true -t:BundleApp /p:TrimLink=true --self-contained
rm -rf src/bin/Release/net7.0/osx-x64/publish/Assets/ rm -rf src/bin/x64/Release/net6.0/osx-x64/publish/Assets/
rm -rf src/bin/Release/net7.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/Assets/ strip src/bin/x64/Release/net6.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/AvaloniaCoreRTDemo
rm src/bin/Release/net7.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/AvaloniaCoreRTDemo.dwarf rm -rf src/bin/x64/Release/net6.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/Assets/
rm src/bin/x64/Release/net6.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/AvaloniaCoreRTDemo.runtimeconfig.json
rm src/bin/x64/Release/net6.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/AvaloniaCoreRTDemo.pdb
rm src/bin/x64/Release/net6.0/osx-x64/publish/AvaloniaCoreRTDemo.app/Contents/MacOS/AvaloniaCoreRTDemo.deps.json

View File

@ -1,5 +1,6 @@
#!/bin/bash #!/bin/bash
rm -f src/packages.lock.json rm -f src/packages.lock.json
dotnet publish -r linux-x64 -c Release /p:RestoreLockedMode=true dotnet publish -r linux-x64 -c release /p:RestoreLockedMode=true /p:TrimLink=true --self-contained
cd src/bin/Release/net7.0/linux-x64/publish cd src/bin/x64/Release/net6.0/linux-x64/publish
cp AvaloniaCoreRTDemo AvaloniaCoreRTDemo.bin cp AvaloniaCoreRTDemo AvaloniaCoreRTDemo.bin
strip AvaloniaCoreRTDemo.bin