public Task<string[]> ShowFileDialogAsync(FileDialog dialog, IWindowImpl parent) { var tcs = new TaskCompletionSource<string[]>(); var dlg = new global::Gtk.FileChooserDialog(dialog.Title, ((WindowImpl)parent), dialog is OpenFileDialog ? FileChooserAction.Open : FileChooserAction.Save, "Cancel", ResponseType.Cancel, "Open", ResponseType.Accept) { SelectMultiple = (dialog as OpenFileDialog)?.AllowMultiple ?? false, }; foreach (var filter in dialog.Filters) { var ffilter = new FileFilter() { Name = filter.Name + " (" + string.Join(";", filter.Extensions.Select(e => "*." + e)) + ")" }; foreach (var ext in filter.Extensions) ffilter.AddPattern("*." + ext); dlg.AddFilter(ffilter); } dlg.SetFilename(dialog.InitialFileName); dlg.Modal = true; dlg.Response += (_, args) => { if (args.ResponseId == ResponseType.Accept) tcs.TrySetResult(dlg.Filenames); dlg.Hide(); dlg.Dispose(); }; dlg.Close += delegate { tcs.TrySetResult(null); dlg.Dispose(); }; dlg.Show(); return tcs.Task; }
public unsafe Task<string[]> ShowFileDialogAsync(FileDialog dialog, IWindowImpl parent) { var hWnd = parent?.Handle?.Handle ?? IntPtr.Zero; return Task.Factory.StartNew(() => { var filters = new StringBuilder(); foreach (var filter in dialog.Filters) { var extMask = string.Join(";", filter.Extensions.Select(e => "*." + e)); filters.Append(filter.Name); filters.Append(" ("); filters.Append(extMask); filters.Append(")"); filters.Append('\0'); filters.Append(extMask); filters.Append('\0'); } if (filters.Length == 0) filters.Append("All files\0*.*\0"); filters.Append('\0'); var filterBuffer = new char[filters.Length]; filters.CopyTo(0, filterBuffer, 0, filterBuffer.Length); var defExt = (dialog as SaveFileDialog)?.DefaultExtension; var fileBuffer = new char[256]; dialog.InitialFileName?.CopyTo(0, fileBuffer, 0, dialog.InitialFileName.Length); string userSelectedExt = null; fixed (char* pFileBuffer = fileBuffer) fixed (char* pFilterBuffer = filterBuffer) fixed (char* pDefExt = defExt) fixed (char* pInitDir = dialog.InitialDirectory) fixed (char* pTitle = dialog.Title) { var ofn = new UnmanagedMethods.OpenFileName() { hwndOwner = hWnd, hInstance = IntPtr.Zero, lCustData = IntPtr.Zero, nFilterIndex = 0, Flags = UnmanagedMethods.OpenFileNameFlags.OFN_EXPLORER | UnmanagedMethods.OpenFileNameFlags.OFN_HIDEREADONLY, nMaxCustFilter = 0, nMaxFile = fileBuffer.Length - 1, nMaxFileTitle = 0, lpTemplateName = IntPtr.Zero, lpfnHook = IntPtr.Zero, lpstrCustomFilter = IntPtr.Zero, lpstrDefExt = new IntPtr(pDefExt), lpstrFile = new IntPtr(pFileBuffer), lpstrFileTitle = IntPtr.Zero, lpstrFilter = new IntPtr(pFilterBuffer), lpstrInitialDir = new IntPtr(pInitDir), lpstrTitle = new IntPtr(pTitle), }; ofn.lStructSize = Marshal.SizeOf(ofn); if ((dialog as OpenFileDialog)?.AllowMultiple == true) ofn.Flags |= UnmanagedMethods.OpenFileNameFlags.OFN_ALLOWMULTISELECT; if (dialog is SaveFileDialog) ofn.Flags |= UnmanagedMethods.OpenFileNameFlags.OFN_NOREADONLYRETURN | UnmanagedMethods.OpenFileNameFlags.OFN_OVERWRITEPROMPT; var pofn = &ofn; var res = dialog is OpenFileDialog ? UnmanagedMethods.GetOpenFileName(new IntPtr(pofn)) : UnmanagedMethods.GetSaveFileName(new IntPtr(pofn)); if (!res) return null; if (dialog?.Filters.Count > 0) userSelectedExt = dialog.Filters[ofn.nFilterIndex - 1].Extensions.FirstOrDefault(); } var cStart = 0; string dir = null; var files = new List<string>(); for (var c = 0; c < fileBuffer.Length; c++) { if (fileBuffer[c] == 0) { //Encountered double zero char if (cStart == c) break; var s = new string(fileBuffer, cStart, c - cStart); if (dir == null) dir = s; else files.Add(s); cStart = c + 1; } } if (files.Count == 0) { if (dialog is SaveFileDialog) { if (string.IsNullOrWhiteSpace(Path.GetExtension(dir)) && !string.IsNullOrWhiteSpace(userSelectedExt) && !userSelectedExt.Contains("*")) dir = Path.ChangeExtension(dir, userSelectedExt); } return new[] {dir}; } return files.Select(f => Path.Combine(dir, f)).ToArray(); }); }
public Task<string[]> ShowFileDialogAsync(FileDialog dialog, IWindowImpl parent) { throw new NotImplementedException(); }