Mendapatkan Informasi Tentang Isi Folder

Bagian Mendapatkan ID Folder membahas dua pendekatan untuk mendapatkan penunjuk objek namespace ke daftar pengidentifikasi item (PIDL). Salah satu pertanyaan yang jelas adalah: Setelah Anda memiliki PIDL, apa yang dapat Anda lakukan dengannya? Pertanyaan terkait adalah: Bagaimana jika tidak ada pendekatan yang berfungsi, atau cocok untuk aplikasi Anda? Jawaban untuk kedua pertanyaan mengharuskan untuk melihat lebih dekat bagaimana namespace diimplementasikan. Kuncinya adalah antarmuka IShellFolder .

Menggunakan Antarmuka IShellFolder

Sebelumnya dalam dokumentasi ini, folder namespace disebut sebagai objek. Meskipun, pada saat itu, istilah itu digunakan dalam arti longgar, itu sebenarnya benar dalam arti yang ketat juga. Setiap folder namespace diwakili oleh objek Model Objek Komponen (COM). Setiap objek folder mengekspos sejumlah antarmuka yang dapat digunakan untuk berbagai tugas. Beberapa antarmuka yang bersifat opsional mungkin tidak diekspos oleh semua folder. Namun, semua folder harus mengekspos antarmuka dasar, IShellFolder.

Langkah pertama dalam menggunakan objek folder adalah mengambil penunjuk ke antarmuka IShellFolder-nya. Selain menyediakan akses ke antarmuka lain objek, IShellFolder mengekspos sekelompok metode yang menangani sejumlah tugas umum, beberapa di antaranya dibahas di bagian ini.

Untuk mengambil penunjuk ke antarmuka IShellFolder objek namespace, Anda harus terlebih dahulu memanggil SHGetDesktopFolder. Fungsi ini mengembalikan penunjuk ke antarmuka IShellFolder dari akar namespace, desktop. Setelah Anda memiliki antarmuka IShellFolder desktop, ada berbagai cara untuk melanjutkan.

Jika Anda sudah memiliki PIDL folder yang Anda minati—misalnya, dengan memanggil SHGetFolderLocation—Anda dapat mengambil antarmuka IShellFolder-nyadengan memanggil metode IShellFolder::BindToObject desktop. Jika Anda memiliki jalur objek sistem file, Anda harus terlebih dahulu mendapatkan PIDL-nya dengan memanggil metode IShellFolder::P arseDisplayName desktop dan kemudian memanggil IShellFolder::BindToObject. Jika tidak ada pendekatan ini yang berlaku, Anda dapat menggunakan metode IShellFolder lainnya untuk menavigasi namespace layanan. Untuk informasi selengkapnya, lihat Menavigasi Namespace.

Menghitung Isi Folder

Hal pertama yang biasanya ingin Anda lakukan dengan folder adalah mencari tahu isinya. Anda harus terlebih dahulu memanggil metode IShellFolder::EnumObjects folder. Folder akan membuat objek enumerasi OLE standar dan mengembalikan antarmuka IEnumIDList-nya. Antarmuka ini mengekspos empat metode standar—Kloning, Berikutnya, Reset, dan Lewati—yang dapat digunakan untuk menghitung konten folder.

Prosedur dasar untuk menghitung konten folder adalah:

  1. Panggil folder metode IShellFolder::EnumObjects untuk mengambil pointer ke antarmuka IEnumIDList objek enumerasi.
  2. Teruskan PIDL yang tidak dialokasikan ke IEnumIDList::Next. Selanjutnya mengurus alokasi PIDL, tetapi aplikasi harus membatalkan alokasinya ketika tidak lagi diperlukan. Saat Berikutnya kembali, PIDL hanya akan berisi ID item objek dan karakter NULL yang mengakhiri. Dengan kata lain, ini adalah PIDL tingkat tunggal, relatif terhadap folder, bukan PIDL yang sepenuhnya memenuhi syarat.
  3. Ulangi langkah 2 hingga Berikutnya mengembalikan S_FALSE untuk menunjukkan bahwa semua item telah dijumlahkan.
  4. Panggil IEnumIDList::Release untuk merilis objek enumerasi.

Catatan

Penting untuk melacak apakah Anda bekerja dengan PIDL penuh atau relatif. Beberapa fungsi dan metode akan menerimanya, tetapi yang lain hanya akan mengambil satu atau yang lain.

 

Tiga metode IEnumIDList yang tersisa (Reset, Lewati, dan Kloning) berguna jika Anda perlu melakukan enumerasi folder berulang. Mereka memungkinkan Anda untuk mengatur ulang enumerasi, melewati satu atau beberapa objek, dan membuat salinan objek enumerasi untuk mempertahankan statusnya.

Menentukan Nama Tampilan dan Properti Lainnya

Setelah Anda menghitung semua PIDL yang dimuat oleh folder, Anda dapat mengetahui jenis objek apa yang diwakilinya. Antarmuka IShellFolder menyediakan sejumlah metode yang berguna, dua di antaranya dibahas di sini. Metode IShellFolder lainnya dan antarmuka folder Shell lainnya dibahas nanti.

Salah satu properti yang paling berguna adalah nama tampilan objek. Untuk mengambil nama tampilan objek, teruskan PIDL-nya ke IShellFolder::GetDisplayNameOf. Meskipun objek dapat ditemukan di mana saja di bawah folder induk di namespace layanan, PIDL-nya harus relatif terhadap folder .

IShellFolder::GetDisplayNameOf mengembalikan nama tampilan sebagai bagian dari struktur STRRET. Karena mengekstrak nama tampilan dari struktur STRRET bisa sedikit rumit, Shell menyediakan dua fungsi yang melakukan pekerjaan untuk Anda, StrRetToStr dan StrRetToBuf. Kedua fungsi mengambil struktur STRRET , dan mengembalikan nama tampilan sebagai string normal. Mereka hanya berbeda dalam bagaimana string dialokasikan.

Selain nama tampilannya, objek dapat memiliki sejumlah atribut, seperti apakah itu folder atau apakah dapat dipindahkan. Anda dapat mengambil atribut objek dengan meneruskan PIDL-nya ke IShellFolder::GetAttributesOf. Daftar lengkap atribut cukup besar, jadi Anda akan melihat referensi untuk detailnya. Perhatikan bahwa PIDL yang Anda berikan ke GetAttributesOf harus satu tingkat. Secara khusus, IShellFolder::GetAttributesOf akan menerima PIDL yang dikembalikan oleh IEnumIDList::Next. Anda dapat meneruskan array PIDL, dan GetAttributesOf akan mengembalikan atribut yang dimiliki semua objek dalam array.

Jika Anda memiliki jalur objek yang sepenuhnya memenuhi syarat atau PIDL, SHGetFileInfo menyediakan cara sederhana untuk mengambil informasi tentang objek yang cukup untuk banyak tujuan. SHGetFileInfo mengambil jalur atau PIDL yang sepenuhnya memenuhi syarat, dan mengembalikan berbagai informasi tentang objek termasuk:

  • Nama tampilan objek
  • Atribut objek
  • Menangani ikon objek
  • Handel ke daftar gambar sistem
  • Jalur file yang berisi ikon objek

Mendapatkan Pointer ke Antarmuka IShellFolder Subfolder

Anda dapat menentukan apakah folder Anda berisi subfolder apa pun dengan memanggil IShellFolder::GetAttributesOf dan memeriksa apakah bendera SFGAO_FOLDER diatur. Jika objek adalah folder, Anda dapat mengikatnya, yang memberi Anda penunjuk ke antarmuka IShellFolder-nya.

Untuk mengikat subfolder, panggil metode IShellFolder::BindToObject folder induk. Metode ini mengambil PIDL subfolder dan mengembalikan pointer ke antarmuka IShellFolder-nya. Setelah Anda memiliki pointer ini, Anda dapat menggunakan metode IShellFolder untuk menghitung konten subfolder , menentukan propertinya, dan sebagainya.

Menentukan Folder Induk Objek

Jika Anda memiliki PIDL objek, Anda mungkin memerlukan handel ke salah satu antarmuka yang diekspos oleh folder induknya. Misalnya, jika Anda ingin menentukan nama tampilan yang terkait dengan PIDL dengan menggunakan IShellFolder::GetDisplayNameOf, Anda harus terlebih dahulu mengambil antarmuka IShellFolder dari induk objek. Dimungkinkan untuk melakukan ini dengan teknik yang dibahas di bagian sebelumnya. Namun, pendekatan yang jauh lebih sederhana adalah menggunakan fungsi Shell, SHBindToParent. Fungsi ini mengambil PIDL objek yang sepenuhnya memenuhi syarat dan mengembalikan penunjuk antarmuka tertentu pada folder induk. Secara opsional, ini juga mengembalikan PIDL tingkat tunggal item untuk digunakan dalam metode seperti IShellFolder::GetAttributesOf.

Contoh aplikasi konsol berikut mengambil PIDL folder khusus Sistem dan mengembalikan nama tampilannya.

#include <shlobj.h>
#include <shlwapi.h>
#include <iostream.h>
#include <objbase.h>

int main()
{
    IShellFolder *psfParent = NULL;
    LPITEMIDLIST pidlSystem = NULL;
    LPCITEMIDLIST pidlRelative = NULL;
    STRRET strDispName;
    TCHAR szDisplayName[MAX_PATH];
    HRESULT hr;

    hr = SHGetFolderLocation(NULL, CSIDL_SYSTEM, NULL, NULL, &pidlSystem);

    hr = SHBindToParent(pidlSystem, IID_IShellFolder, (void **) &psfParent, &pidlRelative);

    if(SUCCEEDED(hr))
    {
        hr = psfParent->GetDisplayNameOf(pidlRelative, SHGDN_NORMAL, &strDispName);
        hr = StrRetToBuf(&strDispName, pidlSystem, szDisplayName, sizeof(szDisplayName));
        cout << "SHGDN_NORMAL - " <<szDisplayName << '\n';
    }

    psfParent->Release();
    CoTaskMemFree(pidlSystem);

    return 0;
}

Aplikasi ini pertama kali menggunakan SHGetFolderLocation untuk mengambil PIDL folder Sistem. Kemudian memanggil SHBindToParent, yang mengembalikan pointer ke antarmuka IShellFolder folder induk, dan PIDL folder Sistem relatif terhadap induknya. Kemudian menggunakan metode IShellFolder::GetDisplayNameOf folder induk untuk mengambil nama tampilan folder Sistem. Karena GetDisplayNameOf mengembalikan struktur STRRET, StrRetToBuf digunakan untuk mengonversi nama tampilan menjadi string normal. Setelah menampilkan nama tampilan, penunjuk antarmuka dirilis dan Pidl Sistem dibebaskan. Perhatikan bahwa Anda tidak boleh membebaskan PIDL relatif yang dikembalikan oleh SHBindToParent.