microsoft / DirectXTex

DirectXTex texture processing library
https://walbourn.github.io/directxtex/
MIT License
1.82k stars 447 forks source link

COM are not initialized by using the initalizion code in DirectXTex.md #163

Closed Akarinnnnn closed 4 years ago

Akarinnnnn commented 4 years ago

Initialization

The library assumes that the client code will have already called CoInitialize, CoInitializeEx, or Windows::Foundation::Initialize as needed by the application before calling any DirectXTex routines. Most DirectXTex functions use the Windows Imaging Component which requires COM.

For a Universal Windows Platform (UWP) app, the Windows Runtime and COM is initialized by the C/C++ Run-Time. For a classic Windows desktop application you have to do this explicitly:

#if (_WIN32_WINNT >= 0x0A00 /*_WIN32_WINNT_WIN10*/)
    Microsoft::WRL::Wrappers::RoInitializeWrapper initialize(RO_INIT_MULTITHREADED);
    if (FAILED(initialize))
        // error
#else
    HRESULT hr = CoInitializeEx(nullptr, COINITBASE_MULTITHREADED);
    if (FAILED(hr))
        // error
#endif

In desktop win10, when I try to use DirectX::LoadFromWICFile() function, it returns E_NOINTERFACE, I think it's imopssiable. As I use debugger to find out why it returns this, I found

line 1103    
IWICImagingFactory* pWIC = GetWICFactory(iswic2);
    if (!pWIC)
        return E_NOINTERFACE;  

get into GetWICFactory(iswic2)

line 280:
    if (!InitOnceExecuteOnce(&s_initOnce,
        InitializeWICFactory,
        nullptr,
        reinterpret_cast<LPVOID*>(&g_Factory)))
    {
        return nullptr;
    }

into InitializeWICFactory()

line 78:
       HRESULT hr = CoCreateInstance(
            CLSID_WICImagingFactory2,
            nullptr,
            CLSCTX_INPROC_SERVER,
            __uuidof(IWICImagingFactory2),
            ifactory
        );

here, hr is E_NOTINITIALIZED,means COM are not initialized.
So, maybe we need to change this initializiation code?

walbourn commented 4 years ago

Did you in fact call CoInitializeEx in your main entry-point? As noted in the doc page you reference, I'm assuming your app has already initialized COM. This is not done by the internal library code since there are some parameters involved, and depends on the exact platform you are targeting.

In other words, your application is supposed to initialize COM before you call LoadWICFromFile.

Akarinnnnn commented 4 years ago

Did you in fact call CoInitializeEx in your main entry-point? As noted in the doc page you reference, I'm assuming your app has already initialized COM. This is not done by the internal library code since there are some parameters involved, and depends on the exact platform you are targeting.

In other words, your application is supposed to initialize COM before you call LoadWICFromFile.

Not at all. In my case I reference _DirectXTex_Desktop_2019Win10.vcxproj, which means Classic Win32 Application. preprocessor ignored CoInitializeEx because _WIN32_WINNT >= 0x0A00.

walbourn commented 4 years ago

Then you called RoInitialize which does init COM.

Are you trying to use WIC loader from a different thread?

Akarinnnnn commented 4 years ago

Then you called RoInitialize which does init COM.

Are you trying to use WIC loader from a different thread?

  1. RoInitialize in my case does not initalize s COM.
  2. That is a single thread win32 app.
walbourn commented 4 years ago

That's what RoInitialize does... The Windows Runtime includes starting up COM.

That said, you don't need the Windows Runtime for DirectXTex. Have you tried just using:

    HRESULT hr = CoInitializeEx(nullptr, COINITBASE_MULTITHREADED);
    if (FAILED(hr))
        // error

And making sure that the HRESULT is a success?

Akarinnnnn commented 4 years ago

That's what RoInitialize does... The Windows Runtime includes starting up COM.

That said, you don't need the Windows Runtime for DirectXTex. Have you tried just using:

    HRESULT hr = CoInitializeEx(nullptr, COINITBASE_MULTITHREADED);
    if (FAILED(hr))
        // error

And making sure that the HRESULT is a success?

Yes.That's what I use, hr is also success.
again, RoInitalize DID NOT INITIALIZE COM

walbourn commented 4 years ago

I'm sorry, but I'm at a loss as to the cause of your problem. The Microsoft Docs covers this in detail, so hopefully something there makes sense to you.