Oktatóanyag: Fájlok és mappák megnyitása kiválasztókkal a WinUI-ban

Windows App SDK fájl- és mappaválasztókkal lehetővé teszi a felhasználók számára a WinUI-alkalmazás fájljainak vagy mappáinak tallózását és kijelölését. A válogató API-k ismerős Windows felületet biztosítanak, amely segít a felhasználóknak az eszköz és a felhőbeli tárhelyek közötti navigálásban. Ez a cikk bemutatja, hogyan valósíthatja meg a fájlmegnyitási és mappaválasztókat, hogyan szabhatja testre a viselkedésüket, és hogyan kezelheti a kiválasztott eredményeket az alkalmazásban.

A Windows App SDK FileOpenPicker és FileSavePicker osztályok létrehoznak egyválasztó párbeszédpanelt, amellyel a felhasználók megadják a megnyitni vagy menteni kívánt fájl nevét és helyét. A FolderPicker osztály lehetővé teszi egy mappa kiválasztását.

Ha szeretne többet megtudni a fájlok mentéséről, olvassa el a Fájl mentése Windows App SDK választóval című témakört.

Prerequisites

  • Windows App SDK 1,8-at vagy újabb verziót. Az ebben a cikkben használt Microsoft.Windows.Storage.Pickers API-k a Windows App SDK 1.8-ban kerültek bevezetésre. Ha a projekt egy korábbi verziót céloz meg, az örökölt megközelítéshez tekintse meg a WinRT-választók használata HWND-interop használatával című témakört.

Fontos API-k

Ez a cikk a következő API-kat használja:

Fájlválasztó felhasználói felülete

A fájlválasztó információkat jelenít meg a felhasználóknak, és konzisztens felhasználói élményt nyújt a fájlok megnyitásakor vagy mentésekor.

Ezek az információk a következőket tartalmazzák:

  • Az aktuális hely
  • A felhasználó által kiválasztandó elem vagy elemek
  • A felhasználó által böngészhető helyek fája. Ezek a helyek közé tartoznak a fájlrendszer helyei (például a Zene vagy a Letöltések mappa), valamint a fájlválasztó szerződést megvalósító alkalmazások (például Kamera, Fényképek és Microsoft OneDrive).

Előfordulhat, hogy van egy alkalmazás, amely lehetővé teszi a felhasználók számára a fájlok megnyitását vagy mentését. Amikor a felhasználó elindítja ezt a műveletet, az alkalmazás meghívja a fájlválasztót, amely megjeleníti a fájlválasztó felhasználói felületét:

Képernyőkép egy megnyitott fájlválasztóról, amelyen egy szűrő van kiválasztva, amely .txt, .pdf, .doc és .docx fájlokat jelenít meg.

A válogatók használata az alkalmazással

Egy választóval az alkalmazás hozzáférhet, tallózhat és menthet fájlokat és mappákat a felhasználó rendszerében. Az alkalmazás könnyű PickFileResult és PickFolderResult objektumként fogadja ezeket a választásokat, amelyek a kijelölt fájl vagy mappa elérési útját adják meg.

A válogató egyetlen, egységes felületet használ, amely lehetővé teszi, hogy a felhasználó fájlokat és mappákat válasszon a fájlrendszerből vagy más alkalmazásokból. A más alkalmazásokból kiválasztott fájlok olyanok, mint a fájlrendszerből származó fájlok. Az alkalmazás általában ugyanúgy működik rajtuk, mint más objektumok. Más alkalmazások fájlválasztó szerződésekben való részvétellel teszik elérhetővé a fájlokat.

Meghívhatja például a fájlválasztót az alkalmazásban, hogy a felhasználó megnyithassa a fájlt. Ez a művelet az alkalmazást hívó alkalmazássá teszi. A fájlválasztó együttműködik a rendszerrel és más alkalmazásokkal, hogy lehetővé teszi a felhasználó számára a navigálást és a fájl kiválasztását. Amikor a felhasználó kiválaszt egy fájlt, a fájlválasztó visszaadja a fájl elérési útját az alkalmazáshoz.

Válasszon egy fájlt a példa megnyitásához

Az alábbi kód bemutatja, hogyan használhatja a FileOpenPicker osztályt, hogy a felhasználó egyetlen fájlt( például egy fényképet) válasszon. A kód beállítja a tulajdonságokat a kiválasztón, hogy testre szabja annak megjelenését és viselkedését, majd a PickSingleFileAsync metódussal megjelenítse a felhasználónak. Ha a felhasználó kiválaszt egy fájlt, az alkalmazás felolvassa a fájl tartalmát, és egy változóban tárolja.

using Microsoft.Windows.Storage.Pickers;

var openPicker = new FileOpenPicker(this.AppWindow.Id)
{
    // (Optional) Specify the initial location for the picker. 
    //     If the specified location doesn't exist on the user's machine, it falls back to the DocumentsLibrary.
    //     If not set, it defaults to PickerLocationId.Unspecified, and the system will use its default location.
    SuggestedStartLocation = PickerLocationId.DocumentsLibrary,
    
    // (Optional) specify the text displayed on the commit button. 
    //     If not specified, the system uses a default label of "Open" (suitably translated).
    CommitButtonText = "Choose selected files",

    // (Optional) specify file extension filters. If not specified, defaults to all files (*.*).
    FileTypeFilter = { ".txt", ".pdf", ".doc", ".docx" },

    // (Optional) specify the view mode of the picker dialog. If not specified, defaults to List.
    ViewMode = PickerViewMode.List,
};

var result = await openPicker.PickSingleFileAsync();
if (result is not null)
{
    var content = System.IO.File.ReadAllText(result.Path);
}
else
{
    // Add your error handling here.
}
#include <winrt/Microsoft.Windows.Storage.Pickers.h>
#include <fstream>
#include <string>

using namespace winrt::Microsoft::Windows::Storage::Pickers;

FileOpenPicker openPicker(this->AppWindow().Id());

// (Optional) Specify the initial location for the picker. 
//     If the specified location doesn't exist on the user's machine, it falls back to the DocumentsLibrary.
//     If not set, it defaults to PickerLocationId.Unspecified, and the system will use its default location.
openPicker.SuggestedStartLocation(PickerLocationId::DocumentsLibrary);

// (Optional) specify the text displayed on the commit button. 
//     If not specified, the system uses a default label of "Open" (suitably translated).
openPicker.CommitButtonText(L"Choose selected files");

// (Optional) specify file extension filters. If not specified, defaults to all files (*.*).
openPicker.FileTypeFilter().ReplaceAll({ L".txt", L".pdf", L".doc", L".docx" });

// (Optional) specify the view mode of the picker dialog. If not specified, defaults to List.
openPicker.ViewMode(PickerViewMode::List);

auto result{ co_await openPicker.PickSingleFileAsync() };
if (result)
{
    std::ifstream fileReader(result.Path().c_str());
    std::string text((std::istreambuf_iterator<char>(fileReader)), std::istreambuf_iterator<char>());
    winrt::hstring hText = winrt::to_hstring(text);
}
else
{
    // Add your error handling here.
}

Több fájl kiválasztása a példa megnyitásához

Azt is engedélyezheti, hogy a felhasználó több fájlt válasszon. Az alábbi kód bemutatja, hogyan használhatja a FileOpenPicker osztályt, hogy a felhasználó több fájlt, például fényképeket válasszon. A folyamat ugyanaz, de a PickMultipleFilesAsync metódus PickFileResult objektumok gyűjteményét adja vissza. Minden eredmény rendelkezik egy Path tulajdonsággal, ha szüksége van a nyers fájlútvonalra.

using Microsoft.Windows.Storage.Pickers;

var openPicker = new FileOpenPicker(this.AppWindow.Id);

var results = await openPicker.PickMultipleFilesAsync();
if (results.Count > 0)
{
    var pickedFilePaths = results.Select(f => f.Path);
    foreach (var path in pickedFilePaths)
    {
        var content = System.IO.File.ReadAllText(path);
    }
}
else
{
    // Add your error handling here.
}
#include <winrt/Microsoft.Windows.Storage.Pickers.h>
#include <fstream>
#include <string>

using namespace winrt::Microsoft::Windows::Storage::Pickers;

FileOpenPicker openPicker(this->AppWindow().Id());
auto results{ co_await openPicker.PickMultipleFilesAsync() };
if (results.Size() > 0)
{
    for (auto const& result : results)
    {
        std::ifstream fileReader(result.Path().c_str());
        std::string text((std::istreambuf_iterator<char>(fileReader)), std::istreambuf_iterator<char>());
        winrt::hstring hText = winrt::to_hstring(text);
    }
}
else
{
    // Add your error handling here.
}

Példa mappa kiválasztására

Ha a FolderPicker osztály használatával szeretne mappát választani, használja az alábbi kódot. Ez a kód létrehoz egy mappaválasztót, megjeleníti azt a felhasználónak a PickSingleFolderAsync metódussal, és lekéri a kijelölt mappa elérési útját egy PickFolderResult objektumban. Ha a felhasználó kiválaszt egy mappát, az alkalmazás lekéri a mappa elérési útját, és egy változóban tárolja későbbi használatra.

using Microsoft.Windows.Storage.Pickers;

var folderPicker = new FolderPicker(this.AppWindow.Id)
{
    // (Optional) Specify the initial location for the picker. 
    //     If the specified location doesn't exist on the user's machine, it falls back to the DocumentsLibrary.
    //     If not set, it defaults to PickerLocationId.Unspecified, and the system will use its default location.
    SuggestedStartLocation = PickerLocationId.DocumentsLibrary,

    // (Optional) specify the text displayed on the commit button. 
    //     If not specified, the system uses a default label of "Open" (suitably translated).
    CommitButtonText = "Select Folder",

    // (Optional) specify the view mode of the picker dialog. If not specified, default to List.
    ViewMode = PickerViewMode.List,
};

var result = await folderPicker.PickSingleFolderAsync();

if (result is not null)
{
    var path = result.Path;
}
else
{
    // Add your error handling here.
}
#include <winrt/Microsoft.Windows.Storage.Pickers.h>

using namespace winrt::Microsoft::Windows::Storage::Pickers;

FolderPicker folderPicker(this->AppWindow().Id());

// (Optional) Specify the initial location for the picker. 
//     If the specified location doesn't exist on the user's machine, it falls back to the DocumentsLibrary.
//     If not set, it defaults to PickerLocationId.Unspecified, and the system will use its default location.
folderPicker.SuggestedStartLocation(PickerLocationId::DocumentsLibrary);

// (Optional) specify the text displayed on the commit button. 
//     If not specified, the system uses a default label of "Open" (suitably translated).
folderPicker.CommitButtonText(L"Select Folder");

// (Optional) specify the view mode of the picker dialog. If not specified, default to List.
folderPicker.ViewMode(PickerViewMode::List);

auto result{ co_await folderPicker.PickSingleFolderAsync() };
if (result)
{
    auto path{ result.Path() };
}
else
{
    // Add your error handling here.
}

Jótanács

Amikor az alkalmazása egy kiválasztón keresztül hozzáfér egy fájlhoz vagy egy mappához, vegye fel azt az alkalmazás FutureAccessList vagy MostRecentlyUsedList listájára, hogy nyomon követhesse, a Windows-futtatókörnyezet (WinRT) API-k használatával. További információ: A legutóbb használt fájlok és mappák nyomon követése.

A mappaválasztó felhasználói felülete így néz ki:

Képernyőkép a C meghajtót megtekintő mappaválasztóról.

WinRT-választók használata HWND interop-tal

Ha a projektje a Windows App SDK 1.7-es vagy korábbi verzióját célozza, vagy ha az örökölt Windows.Storage.Pickers API-kat használja (például UWP-ről történő migráláskor), a megjelenítés előtt inicializálnia kell a kiválasztót egy ablakazonosítóval (HWND). E lépés nélkül a jelölő kivételt jelez, vagy csendesen meghiúsul az asztali (WinUI 3) alkalmazásokban.

Important

A WinUI 3 asztali alkalmazások nem rendelkeznek CoreWindow. A választót az alkalmazás ablakához kell társítania a WinRT.Interop.InitializeWithWindow.Initialize (C#) vagy a IInitializeWithWindow::Initialize (C++/WinRT) meghívásával, mielőtt bármilyen Pick*Async hívást kezdeményezne.

C# példa (régi WinRT-választók)

// This example assumes you have a reference to your app's main window.
// In a Window class, use 'this'. In a Page, use a stored reference like App.MainWindow.

var picker = new Windows.Storage.Pickers.FileOpenPicker();
picker.FileTypeFilter.Add(".png");
picker.FileTypeFilter.Add(".jpg");

// Get the window handle (HWND) for the current WinUI 3 window.
var hwnd = WinRT.Interop.WindowNative.GetWindowHandle(App.MainWindow);

// Associate the picker with the window.
WinRT.Interop.InitializeWithWindow.Initialize(picker, hwnd);

var file = await picker.PickSingleFileAsync();
if (file is null)
{
    // The user cancelled the picker.
}

C++/WinRT-példa (régi WinRT-választók)

// pch.h
#include <winrt/Windows.Storage.Pickers.h>
#include <microsoft.ui.xaml.window.h>
#include <shobjidl_core.h>

// MainWindow.xaml.cpp — inside a MainWindow member function
Windows::Storage::Pickers::FileOpenPicker picker;
picker.FileTypeFilter().Append(L".png");
picker.FileTypeFilter().Append(L".jpg");

// Get the window handle (HWND) of the current WinUI 3 window.
auto windowNative{ this->m_inner.as<::IWindowNative>() };
HWND hwnd{ 0 };
windowNative->get_WindowHandle(&hwnd);

// Associate the picker with the window.
auto initializeWithWindow{ picker.as<::IInitializeWithWindow>() };
initializeWithWindow->Initialize(hwnd);

auto file{ co_await picker.PickSingleFileAsync() };
if (!file)
{
    // The user cancelled the picker.
}

Jótanács

Új alkalmazások esetén az ajánlott megközelítés a Windows App SDK választóelemeinek használata (Microsoft.Windows.Storage.Pickers), amelyek a konstruktorban egy WindowId paramétert fogadnak, és nincs szükség a InitializeWithWindow mintára. Tekintse meg a cikk korábbi példáit.

Az ablakfogantyúk lekéréséről további információt az Ablakfogópont lekérése (HWND) című témakörben talál.