2016-06-20 28 views
1

私はカスタムファイルタイプのサムネイルハンドラを作成しています。私はそれを登録すると、成功メッセージとともに戻ります。 「サムネイル」は完全に空白として表示されていますが、「サムネイルを使用できません」とは言いません。問題は、実際のサムネイルハンドラが呼び出されないことです。私はhandler::initializehandler::queryinterfaceおよびhandler::getthumbnailの下に私のハンドラに一連の声明を書いているので、これを知っています。私はthis documentation.のほとんどを見てきましたが、私が見つけることができるのは、initializeとgetthumbnailを使う必要があることだけです。ここに私のコードは次のとおりです。Windowsサムネイルハンドラが呼び出されない

ヘッダー:

#pragma once 

#include <windows.h> 
#include <thumbcache.h>  // For IThumbnailProvider 
#include <wincodec.h>  // Windows Imaging Codecs 

#include <fstream> 
#include <iostream> 

#pragma comment(lib, "windowscodecs.lib") 


class ThumbnailProvider : 
    public IInitializeWithStream, 
    public IThumbnailProvider 
{ 
public: 
    // IUnknown 
    IFACEMETHODIMP QueryInterface(REFIID riid, void **ppv); 
    IFACEMETHODIMP_(ULONG) AddRef(); 
    IFACEMETHODIMP_(ULONG) Release(); 

    // IInitializeWithStream 
    IFACEMETHODIMP Initialize(IStream *pStream, DWORD grfMode); 

    // IThumbnailProvider 
    IFACEMETHODIMP GetThumbnail(UINT cx, HBITMAP *phbmp, WTS_ALPHATYPE *pdwAlpha); 

    ThumbnailProvider(); 

protected: 
    ~ ThumbnailProvider(); 

private: 
    // Reference count of component. 
    long m_cRef; 

    // Provided during initialization. 
    IStream *m_pStream; 

    std::ofstream output; 

    void stripImageFrom (IStream *stream, HBITMAP *phbmp); 
}; 

ボディ:

#include " ThumbnailProvider.h" 
#include <Shlwapi.h> 
#include <Wincrypt.h> // For CryptStringToBinary. 
#include <msxml6.h> 
#include <atlimage.h> 
#include <fstream> 

#pragma comment(lib, "Shlwapi.lib") 
#pragma comment(lib, "Crypt32.lib") 
#pragma comment(lib, "msxml6.lib") 

extern HINSTANCE g_hInst; 
extern long g_cDllRef; 

ThumbnailProvider:: ThumbnailProvider() : m_cRef(1), m_pStream(NULL) 
{ 
    std::ofstream st; 
    st.open("C:\\Users\\labs\\Desktop\\Output\\out.txt", std::ios_base::app); 
    st << "Made provider"; 
    st.close(); 
    InterlockedIncrement(&g_cDllRef); 

} 


ThumbnailProvider::~ ThumbnailProvider() 
{ 
    InterlockedDecrement(&g_cDllRef); 
} 

#pragma region IUnknown 

// Query to the interface the component supported. 
IFACEMETHODIMP ThumbnailProvider::QueryInterface(REFIID riid, void **ppv) 
{ 
    std::ofstream st; 
    st.open("C:\\Users\\labs\\Desktop\\Output\\out.txt", std::ios_base::app); 
    st << "Querying interface"; 
    st.close(); 
    static const QITAB qit[] = 
    { 
     QITABENT(ThumbnailProvider, IThumbnailProvider), 
     QITABENT(ThumbnailProvider, IInitializeWithStream), 
     { 0 }, 
    }; 
    return QISearch(this, qit, riid, ppv); 
} 

// Increase the reference count for an interface on an object. 
IFACEMETHODIMP_(ULONG) ThumbnailProvider::AddRef() 
{ 
    return InterlockedIncrement(&m_cRef); 
} 

// Decrease the reference count for an interface on an object. 
IFACEMETHODIMP_(ULONG) ThumbnailProvider::Release() 
{ 
    ULONG cRef = InterlockedDecrement(&m_cRef); 
    if (0 == cRef) 
    { 
     delete this; 
    } 

    return cRef; 
} 

#pragma endregion 

#pragma region IInitializeWithStream 

// Initializes the thumbnail handler with a stream. 
IFACEMETHODIMP ThumbnailProvider::Initialize(IStream *pStream, DWORD grfMode) 
{ 
    std::ofstream st; 
    st.open("C:\\Users\\labs\\Desktop\\Output\\out.txt", std::ios_base::app); 
    st << "Got to initialization"; 
    st.close(); 
    // A handler instance should be initialized only once in its lifetime. 
    HRESULT hr = HRESULT_FROM_WIN32(ERROR_ALREADY_INITIALIZED); 
    if (m_pStream == NULL) 
    { 
     // Take a reference to the stream if it has not been initialized yet. 
     hr = pStream->QueryInterface(&m_pStream); 
    } 
    return hr; 
} 

#pragma endregion 


#pragma region IThumbnailProvider 

// Gets a thumbnail image and alpha type. The GetThumbnail is called with the 
// largest desired size of the image, in pixels. Although the parameter is 
// called cx, this is used as the maximum size of both the x and y dimensions. 
// If the retrieved thumbnail is not square, then the longer axis is limited 
// by cx and the aspect ratio of the original image respected. On exit, 
// GetThumbnail provides a handle to the retrieved image. It also provides a 
// value that indicates the color at of the image and whether it has 
// valid alpha in ation. 
IFACEMETHODIMP ThumbnailProvider::GetThumbnail(UINT cx, HBITMAP *phbmp, 
    WTS_ALPHATYPE *pdwAlpha) { 
    std::ofstream st; 
    st.open("C:\\Users\\labs\\Desktop\\Output\\out.txt", std::ios_base::app); 
    st << "Getting thumbnail"; 
    st.close(); 
    ThumbnailProvider::stripImageFrom (m_pStream, phbmp); 
    cx = 1024 * 1024; 
    *pdwAlpha = WTSAT_UNKNOWN; 
    return S_OK; 
} 

#pragma endregion 

#pragma region Helper Functions 

// The PNG signature is 137 80 78 71 13 10 26 10. This does not make sense to do backward. I will do it forward. 
void ThumbnailProvider::stripImageFrom (IStream *stream, HBITMAP *phbmp) { 
    unsigned long numBytes = 0; 
    unsigned long *numBytesPtr = &numBytes; 
    char *chptr = nullptr; 
    byte vals[8] = { 0 }; 
    STATSTG *stat = nullptr; 
    DWORD temp = NULL; 
    stream->Stat(stat, temp); 
    unsigned long long length = stat->cbSize.QuadPart; 
    unsigned long long i; 
    for (i = 0; i<length; i++) { 
     stream->Read(chptr, 1, numBytesPtr); 
     if (*chptr == 137) { 
      vals[0] = 1; 
     } 
     else if (*chptr == 80 && vals[0]) { 
      vals[1] = 1; 
     } 
     else if (*chptr == 78 && vals[1]) { 
      vals[2] = 1; 
     } 
     else if (*chptr == 71 && vals[2]) { 
      vals[3] = 1; 
     } 
     else if (*chptr == 13 && vals[3]) { 
      vals[4] = 1; 
     } 
     else if (*chptr == 10 && vals[4] && !vals[5]) { 
      vals[5] = 1; 
     } 
     else if (*chptr == 26 && vals[5]) { 
      vals[6] = 1; 
     } 
     else if (*chptr == 10 && vals[6]) { 
      vals[7] = 1; 
      i -= 7; 
      break; 
     } 
     else { 
      memset(vals, 0, 8 * sizeof(vals[0])); 
     } 
    } 
    if (vals[7]) { 
     IStream *imgstream = nullptr; 
     stream->Read(imgstream, length-i, numBytesPtr); 
     CImage *img = nullptr; 
     img->Load(imgstream); 
     *phbmp = *img; 
    } 
} 
#pragma endregion 

それ以外はただ、Microsoftの例の一つから編集されたので、私はそれは大丈夫ですかなり確信しています。 The example is here.

+0

拡張機能の登録に使用されたProgIdは何​​ですか? –

+0

私はProgIdが何であるか分かりません。 – FatherOfNations

+0

あなたはdllmainのために生成するcslidを意味しますか? – FatherOfNations

答えて

0

この問題が発生している場合は、適切なアーキテクチャを構築していることを確認してください。それは私のためにそれを解決しました。

関連する問題