셸 확장 처리기 초기화

Shell 확장 처리기 개체 구현의 대부분은 해당 형식에 따라 결정됩니다. 그러나 몇 가지 일반적인 요소가 있습니다. 이 항목에서는 모든 Shell 확장 처리기에서 공유하는 구현의 이러한 측면에 대해 설명합니다.

모든 셸 확장 처리기는 COM(In-process Component Object Model) 개체입니다. GUID를 할당하고 셸 확장 처리기 등록에 설명된 대로 등록해야 합니다. DLL로 구현되며 다음 표준 함수를 내보내야 합니다.

  • DllMain. DLL에 대한 표준 진입점입니다.
  • DllGetClassObject. 개체의 클래스 팩터리를 노출합니다.
  • DllCanUnloadNow. COM은 이 함수를 호출하여 개체가 클라이언트에 서비스를 제공하는지 여부를 확인합니다. 그렇지 않은 경우 시스템에서 DLL을 언로드하고 연결된 메모리를 해제할 수 있습니다.

모든 COM 개체와 마찬가지로 셸 확장 처리기는 IUnknown 인터페이스 및 클래스 팩터리를 구현해야 합니다. 또한 대부분은 Windows XP 또는 이전 버전에서 IPersistFile 또는 IShellExtInit 인터페이스를 구현해야 합니다. 이러한 항목은 Windows Vista의 IInitializeWithStream, IInitializeWithItemIInitializeWithFile 로 대체되었습니다. 셸은 이러한 인터페이스를 사용하여 처리기를 초기화합니다.

IPersistFile 인터페이스는 다음을 통해 구현해야 합니다.

  • 아이콘 처리기
  • 데이터 처리기
  • 드롭 처리기

IShellExtInit 인터페이스는 다음을 통해 구현해야 합니다.

  • 바로 가기 메뉴 처리기
  • 끌어서 놓기 처리기
  • 속성 시트 처리기

이 항목의 나머지 부분에서는 다음 주제에 대해 설명합니다.

IPersistFile 구현

IPersistFile 인터페이스는 개체를 디스크 파일에서 로드하거나 디스크 파일에 저장할 수 있도록 설계되었습니다. IUnknown 외에도 6개의 메서드, 5개의 자체 메서드 및 IPersist에서 상속하는 GetClassID 메서드가 있습니다. 셸 확장을 사용하면 IPersist 는 Shell 확장 처리기 개체를 초기화하는 데만 사용됩니다. 일반적으로 디스크에서 읽거나 쓸 필요가 없으므로 GetClassIDLoad 메서드만 토큰이 아닌 구현이 필요합니다.

Shell은 GetClassID 를 먼저 호출하고 함수는 확장 처리기 개체의 CLSID(클래스 식별자)를 반환합니다. 그런 다음 셸은 Load 를 호출하고 두 값을 전달합니다. 첫 번째 pszFile은 Shell이 작동하려고 하는 파일 또는 폴더의 이름을 가진 유니코드 문자열입니다. 두 번째는 파일 액세스 모드를 나타내는 dwMode입니다. 일반적으로 파일에 액세스할 필요가 없으므로 dwMode 는 일반적으로 0입니다. 메서드는 나중에 참조하기 위해 필요에 따라 이러한 값을 저장합니다.

다음 코드 조각에서는 일반적인 Shell 확장 처리기가 GetClassIDLoad 메서드를 구현하는 방법을 보여 줍니다. ANSI 또는 유니코드를 처리하도록 설계되었습니다. CLSID_SampleExtHandler 확장 처리기 개체의 GUID이고 CSampleShellExtension은 인터페이스를 구현하는 데 사용되는 클래스의 이름입니다. m_szFileNamem_dwMode 변수는 파일의 이름 및 액세스 플래그를 저장하는 데 사용되는 프라이빗 변수입니다.

class CSampleShellExtension : public IPersistFile
{
    // Method declarations not included

    private:
    WCHAR m_szFileName[MAX_PATH];    // The file name
    DWORD m_dwMode;                  // The file access mode
}

IFACEMETHODIMP CSampleShellExtension::GetClassID(__out CLSID *pCLSID)
{
    *pCLSID = CLSID_SampleExtHandler;
}

IFACEMETHODIMP CSampleShellExtension::Load(PCWSTR pszFile, DWORD dwMode)
{
    m_dwMode = dwMode;
    return StringCchCopy(m_szFileName, ARRAYSIZE(m_szFileName), pszFile); 
}

// The implementation sample is continued in the next section.

IShellExtInit 구현

IShellExtInit 인터페이스에는 IUnknown 외에도 IShellExtInit::Initialize라는 메서드가 하나만 있습니다. 메서드에는 Shell이 다양한 유형의 정보를 전달하는 데 사용할 수 있는 세 가지 매개 변수가 있습니다. 전달된 값은 처리기 유형에 따라 달라지고 일부는 NULL로 설정할 수 있습니다.

  • pidlFolder 는 PIDL(항목 식별자 목록)에 대한 폴더의 포인터를 보유합니다. 이는 절대 PIDL입니다. 속성 시트 확장의 경우 이 값은 NULL입니다. 바로 가기 메뉴 확장의 경우 바로 가기 메뉴가 표시되는 항목이 포함된 폴더의 PIDL입니다. 기본이 아닌 끌어서 놓기 처리기의 경우 대상 폴더의 PIDL입니다.
  • pDataObject 는 데이터 개체의 IDataObject 인터페이스에 대한 포인터를 보유합니다. 데이터 개체는 CF_HDROP 형식으로 하나 이상의 파일 이름을 보유합니다.
  • hRegKey 는 파일 개체 또는 폴더 형식에 대한 레지스트리 키를 보유합니다.

IShellExtInit::Initialize 메서드는 나중에 사용하기 위해 필요에 따라 파일 이름, IDataObject 포인터 및 레지스트리 키를 저장합니다. 다음 코드 조각은 IShellExtInit::Initialize의 구현을 보여 줍니다. 간단히 하기 위해 이 예제에서는 데이터 개체에 단일 파일만 포함되어 있다고 가정합니다. 일반적으로 데이터 개체에는 여러 파일이 포함될 수 있으며, 각 파일은 추출해야 합니다.

// This code continues the CSampleShellExtension sample shown in the
// "Implementing IPersistFile" section above.

class CSampleShellExtension : public IShellExtInit
{
    // Method declarations not included
    
    private:
    // IDList of the folder for extensions invoked on the folder, such as 
    // background context menu handlers or nondefault drag-and-drop handlers. 
    PIDLIST_ABSOLUTE m_pidlFolder;
    
    // The data object contains an expression of the items that the handler is 
    // being initialized for. Use SHCreateShellItemArrayFromDataObject to 
    // convert this object to an array of items. Use SHGetItemFromObject if you
    // are only interested in a single Shell item. If you need a file system
    // path, use IShellItem::GetDisplayName(SIGDN_FILESYSPATH, ...).
    IDataObject *m_pdtobj;
    
    // For context menu handlers, the registry key provides access to verb 
    // instance data that might be stored there. This is a rare feature to use 
    // so most extensions do not need this variable.
    HKEY m_hRegKey;             
}
    
// This method must be very efficient. Do not do any unnecessary work here.
// Use Initialize to acquire resources that will be used later.

IFACEMETHODIMP CSampleShellExtension::Initialize(__in_opt PCIDLIST_ABSOLUTE pidlFolder,
                                                 __in_opt IDataObject *pDataObject, 
                                                 __in_opt HKEY hRegKey) 
{ 
    // In some cases, handlers are initialized multiple times. Therefore, 
    // clear any previous state here.
    CoTaskMemFree(m_pidlFolder);
    m_pidlFolder = NULL;
    
    if (m_pdtobj)
    { 
        m_pdtobj->Release(); 
    }
    
    if (m_hRegKey)
    {
        RegCloseKey(m_hRegKey);
        m_hRegKey = NULL;
    }
    
    // Capture the inputs for use later.
    HRESULT hr = S_OK;
    
    if (pidlFolder)
    {
        m_pidlFolder = ILClone(pidlFolder);   // Make a copy to use later.
        hr = m_pidlFolder ? S_OK : E_OUTOFMEMORY;
    }
    
    if (SUCCEEDED(hr))
    {
        // If a data object pointer was passed into the method, save it and
        // extract the file name. 
        if (pDataObject) 
        { 
            m_pdtobj = pDataObject; 
            m_pdtobj->AddRef(); 
        }
    
        // It is uncommon to use the registry handle, but if you need it,
        // duplicate it now.
        if (hRegKey)
        {
            LSTATUS const result = RegOpenKeyEx(hRegKey, NULL, 0, KEY_READ, &m_hRegKey); 
            hr = HRESULT_FROM_WIN32(result);
        }
    }
    
    return hr;
}

Infotip 사용자 지정

인포 설명을 사용자 지정하는 방법에는 두 가지가 있습니다. 한 가지 방법은 IQueryInfo 를 지원하는 개체를 구현한 다음 레지스트리의 적절한 하위 키 아래에 개체를 등록하는 것입니다(아래 참조). 또는 표시할 고정 문자열 또는 특정 파일 속성 목록을 지정할 수 있습니다.

네임스페이스 확장의 고정 문자열을 표시하려면 네임스페이스 확장의 CLSID 키 아래에 InfoTip 이라는 하위 키를 만듭니다. 해당 하위 키의 데이터를 표시할 문자열로 설정합니다.

HKEY_CLASSES_ROOT
   CLSID
      {CLSID}
         InfoTip = InfoTip string for your namespace extension

파일 형식에 대한 고정 문자열을 표시하려면 infotip을 제공하려는 파일 형식의 ProgID 키 아래에 InfoTip이라는 하위 키를 만듭니다. 해당 하위 키의 데이터를 표시할 문자열로 설정합니다.

HKEY_CLASSES_ROOT
   ProgID
      InfoTip = InfoTip string for all files of this type

셸이 특정 파일 형식에 대한 정보 설명에 특정 파일 속성을 표시하려면 해당 파일 형식의 ProgID 키 아래에 InfoTip이라는 하위 키를 만듭니다. 해당 하위 키의 데이터를 정식 속성 이름 또는 {fmtid}의 세미콜론으로 구분된 목록으로 설정하고, propname 이 정식 속성 이름이고 {fmtid},pidFMTID/PID 쌍인 pid 쌍으로 설정합니다.

HKEY_CLASSES_ROOT
   ProgID
      InfoTip = propname;propname;{fmtid},pid;{fmtid},pid

다음 속성 이름을 사용할 수 있습니다.

속성 이름 설명 에서 검색됨
작성자 문서 작성자 PIDSI_AUTHOR
제목 문서의 제목 PIDSI_TITLE
제목 제목 요약 PIDSI_SUBJECT
의견 문서 주석 PIDSI_COMMENT 또는 폴더/드라이브 속성
PageCount 페이지 수 PIDSI_PAGECOUNT
Name 이름 표준 폴더 보기
OriginalLocation 원본 파일의 위치 서류 가방 폴더 및 휴지통 폴더
DateDeleted 날짜 파일이 삭제되었습니다. 휴지통 폴더
형식 파일 형식 표준 폴더 세부 정보 보기
크기 파일 크기 표준 폴더 세부 정보 보기
SyncCopyIn OriginalLocation과 동일 OriginalLocation과 동일
수정자 마지막으로 수정한 날짜 표준 폴더 세부 정보 보기
생성일 만든 날짜 표준 폴더 세부 정보 보기
액세스함 마지막으로 액세스한 날짜 표준 폴더 세부 정보 보기
InFolder 파일이 포함된 디렉터리 문서 검색 결과
순위 검색 일치 품질 문서 검색 결과
FreeSpace 사용 가능한 스토리지 공간 디스크 드라이브
NumberOfVisits 방문 횟수 즐겨찾기 폴더
특성 파일 특성 표준 폴더 세부 정보 보기
회사 회사 이름 PIDDSI_COMPANY
범주 문서 범주 PIDDSI_CATEGORY
Copyright 미디어 저작권 PIDMSI_COPYRIGHT
HTMLInfoTipFile HTML InfoTip 파일 폴더에 대한 파일 Desktop.ini

 

셸 확장 처리기 등록