Browse Source

Clean up DBusSystemDialog.cs + add factory method

pull/8217/head
affederaffe 4 years ago
parent
commit
3c3fc4521e
  1. 4
      src/Avalonia.Dialogs/Avalonia.Dialogs.csproj
  2. 8
      src/Avalonia.Dialogs/ManagedFileDialogExtensions.cs
  3. 50
      src/Avalonia.FreeDesktop/DBusSystemDialog.cs
  4. 3
      src/Avalonia.X11/X11Platform.cs

4
src/Avalonia.Dialogs/Avalonia.Dialogs.csproj

@ -14,6 +14,10 @@
<ProjectReference Include="..\Markup\Avalonia.Markup.Xaml\Avalonia.Markup.Xaml.csproj" /> <ProjectReference Include="..\Markup\Avalonia.Markup.Xaml\Avalonia.Markup.Xaml.csproj" />
</ItemGroup> </ItemGroup>
<ItemGroup Label="InternalsVisibleTo">
<InternalsVisibleTo Include="Avalonia.X11, PublicKey=$(AvaloniaPublicKey)" />
</ItemGroup>
<Import Project="..\..\build\ApiDiff.props" /> <Import Project="..\..\build\ApiDiff.props" />
<Import Project="..\..\build\DevAnalyzers.props" /> <Import Project="..\..\build\DevAnalyzers.props" />
</Project> </Project>

8
src/Avalonia.Dialogs/ManagedFileDialogExtensions.cs

@ -8,7 +8,7 @@ namespace Avalonia.Dialogs
{ {
public static class ManagedFileDialogExtensions public static class ManagedFileDialogExtensions
{ {
private class ManagedSystemDialogImpl<T> : ISystemDialogImpl where T : Window, new() internal class ManagedSystemDialogImpl<T> : ISystemDialogImpl where T : Window, new()
{ {
async Task<string[]> Show(SystemDialog d, Window parent, ManagedFileDialogOptions options = null) async Task<string[]> Show(SystemDialog d, Window parent, ManagedFileDialogOptions options = null)
{ {
@ -139,12 +139,6 @@ namespace Avalonia.Dialogs
return builder; return builder;
} }
public static Task<string[]> ShowManagedAsync(this FileDialog dialog, Window parent)
=> new ManagedSystemDialogImpl<Window>().ShowFileDialogAsync(dialog, parent);
public static Task<string> ShowManagedAsync(this OpenFolderDialog dialog, Window parent)
=> new ManagedSystemDialogImpl<Window>().ShowFolderDialogAsync(dialog, parent);
public static Task<string[]> ShowManagedAsync(this OpenFileDialog dialog, Window parent, public static Task<string[]> ShowManagedAsync(this OpenFileDialog dialog, Window parent,
ManagedFileDialogOptions options = null) => ShowManagedAsync<Window>(dialog, parent, options); ManagedFileDialogOptions options = null) => ShowManagedAsync<Window>(dialog, parent, options);

50
src/Avalonia.FreeDesktop/DBusSystemDialog.cs

@ -5,7 +5,6 @@ using System.Text;
using System.Threading.Tasks; using System.Threading.Tasks;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Controls.Platform; using Avalonia.Controls.Platform;
using Avalonia.Dialogs;
using Avalonia.Logging; using Avalonia.Logging;
using Tmds.DBus; using Tmds.DBus;
@ -13,48 +12,31 @@ namespace Avalonia.FreeDesktop
{ {
internal class DBusSystemDialog : ISystemDialogImpl internal class DBusSystemDialog : ISystemDialogImpl
{ {
private readonly IFileChooser? _fileChooser; private readonly IFileChooser _fileChooser;
private bool _isDbusAvailable;
internal DBusSystemDialog() internal static DBusSystemDialog? TryCreate()
{ {
_fileChooser = DBusHelper.Connection?.CreateProxy<IFileChooser>("org.freedesktop.portal.Desktop", "/org/freedesktop/portal/desktop"); var fileChooser = DBusHelper.Connection?.CreateProxy<IFileChooser>("org.freedesktop.portal.Desktop", "/org/freedesktop/portal/desktop");
_isDbusAvailable = _fileChooser is not null; if (fileChooser is null)
} return null;
public async Task<string[]?> ShowFileDialogAsync(FileDialog dialog, Window parent)
{
if (!_isDbusAvailable)
return await dialog.ShowManagedAsync(parent);
try try
{ {
return await ShowNativeFileDialogAsync(dialog, parent); fileChooser.GetVersionAsync().GetAwaiter().GetResult();
return new DBusSystemDialog(fileChooser);
} }
catch (Exception e) catch (Exception e)
{ {
Logger.TryGet(LogEventLevel.Error, LogArea.X11Platform)?.Log(this, e.Message); Logger.TryGet(LogEventLevel.Error, LogArea.X11Platform)?.Log(null, $"Unable to connect to org.freedesktop.portal.Desktop: {e.Message}");
_isDbusAvailable = false; return null;
return await dialog.ShowManagedAsync(parent);
} }
} }
public async Task<string?> ShowFolderDialogAsync(OpenFolderDialog dialog, Window parent) private DBusSystemDialog(IFileChooser fileChooser)
{ {
if (!_isDbusAvailable) _fileChooser = fileChooser;
return await dialog.ShowManagedAsync(parent);
try
{
return await ShowNativeFolderDialogAsync(dialog, parent);
}
catch (Exception e)
{
Logger.TryGet(LogEventLevel.Error, LogArea.X11Platform)?.Log(this, e.Message);
_isDbusAvailable = false;
return await dialog.ShowManagedAsync(parent);
}
} }
private async Task<string[]?> ShowNativeFileDialogAsync(FileDialog dialog, Window parent) public async Task<string[]?> ShowFileDialogAsync(FileDialog dialog, Window parent)
{ {
var parentWindow = $"x11:{parent.PlatformImpl!.Handle.Handle.ToString("X")}"; var parentWindow = $"x11:{parent.PlatformImpl!.Handle.Handle.ToString("X")}";
ObjectPath objectPath; ObjectPath objectPath;
@ -66,14 +48,14 @@ namespace Avalonia.FreeDesktop
{ {
case OpenFileDialog openFileDialog: case OpenFileDialog openFileDialog:
options.Add("multiple", openFileDialog.AllowMultiple); options.Add("multiple", openFileDialog.AllowMultiple);
objectPath = await _fileChooser!.OpenFileAsync(parentWindow, openFileDialog.Title ?? string.Empty, options); objectPath = await _fileChooser.OpenFileAsync(parentWindow, openFileDialog.Title ?? string.Empty, options);
break; break;
case SaveFileDialog saveFileDialog: case SaveFileDialog saveFileDialog:
if (saveFileDialog.InitialFileName is not null) if (saveFileDialog.InitialFileName is not null)
options.Add("current_name", saveFileDialog.InitialFileName); options.Add("current_name", saveFileDialog.InitialFileName);
if (saveFileDialog.Directory is not null) if (saveFileDialog.Directory is not null)
options.Add("current_folder", Encoding.UTF8.GetBytes(saveFileDialog.Directory)); options.Add("current_folder", Encoding.UTF8.GetBytes(saveFileDialog.Directory));
objectPath = await _fileChooser!.SaveFileAsync(parentWindow, saveFileDialog.Title ?? string.Empty, options); objectPath = await _fileChooser.SaveFileAsync(parentWindow, saveFileDialog.Title ?? string.Empty, options);
break; break;
} }
@ -88,14 +70,14 @@ namespace Avalonia.FreeDesktop
return uris; return uris;
} }
private async Task<string?> ShowNativeFolderDialogAsync(OpenFolderDialog dialog, Window parent) public async Task<string?> ShowFolderDialogAsync(OpenFolderDialog dialog, Window parent)
{ {
var parentWindow = $"x11:{parent.PlatformImpl!.Handle.Handle.ToString("X")}"; var parentWindow = $"x11:{parent.PlatformImpl!.Handle.Handle.ToString("X")}";
var options = new Dictionary<string, object> var options = new Dictionary<string, object>
{ {
{ "directory", true } { "directory", true }
}; };
var objectPath = await _fileChooser!.OpenFileAsync(parentWindow, dialog.Title ?? string.Empty, options); var objectPath = await _fileChooser.OpenFileAsync(parentWindow, dialog.Title ?? string.Empty, options);
var request = DBusHelper.Connection!.CreateProxy<IRequest>("org.freedesktop.portal.Request", objectPath); var request = DBusHelper.Connection!.CreateProxy<IRequest>("org.freedesktop.portal.Request", objectPath);
var tsc = new TaskCompletionSource<string[]?>(); var tsc = new TaskCompletionSource<string[]?>();
using var disposable = await request.WatchResponseAsync(x => tsc.SetResult(x.results["uris"] as string[]), tsc.SetException); using var disposable = await request.WatchResponseAsync(x => tsc.SetResult(x.results["uris"] as string[]), tsc.SetException);

3
src/Avalonia.X11/X11Platform.cs

@ -5,6 +5,7 @@ using System.Reflection;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Controls.Platform; using Avalonia.Controls.Platform;
using Avalonia.Dialogs;
using Avalonia.FreeDesktop; using Avalonia.FreeDesktop;
using Avalonia.FreeDesktop.DBusIme; using Avalonia.FreeDesktop.DBusIme;
using Avalonia.Input; using Avalonia.Input;
@ -79,7 +80,7 @@ namespace Avalonia.X11
.Bind<IClipboard>().ToConstant(new X11Clipboard(this)) .Bind<IClipboard>().ToConstant(new X11Clipboard(this))
.Bind<IPlatformSettings>().ToConstant(new PlatformSettingsStub()) .Bind<IPlatformSettings>().ToConstant(new PlatformSettingsStub())
.Bind<IPlatformIconLoader>().ToConstant(new X11IconLoader(Info)) .Bind<IPlatformIconLoader>().ToConstant(new X11IconLoader(Info))
.Bind<ISystemDialogImpl>().ToConstant(new DBusSystemDialog()) .Bind<ISystemDialogImpl>().ToConstant(DBusSystemDialog.TryCreate() as ISystemDialogImpl ?? new ManagedFileDialogExtensions.ManagedSystemDialogImpl<Window>())
.Bind<IMountedVolumeInfoProvider>().ToConstant(new LinuxMountedVolumeInfoProvider()) .Bind<IMountedVolumeInfoProvider>().ToConstant(new LinuxMountedVolumeInfoProvider())
.Bind<IPlatformLifetimeEventsImpl>().ToConstant(new X11PlatformLifetimeEvents(this)); .Bind<IPlatformLifetimeEventsImpl>().ToConstant(new X11PlatformLifetimeEvents(this));

Loading…
Cancel
Save