blob: bd8a418d675c9dafcd3d5e8378f8cca75c507105 [file] [log] [blame]
//
// Copyright (c) 2002-2013 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// winrt/windowadapter.cpp: WinRT specific window utility functionality
#include "windowadapter.h"
#include <dxgi1_2.h>
#include "common/debug.h"
using namespace Microsoft::WRL;
using namespace Windows::UI::Core;
namespace egl
{
typedef RuntimeClass<RuntimeClassFlags<ClassicCom>, IWindowAdapter> WindowAdapterBase;
class WindowAdapter : public WindowAdapterBase
{
public:
WindowAdapter(ComPtr<IUnknown> window, AngleWindowType type);
// IWindowAdapter methods
virtual HRESULT GetType(AngleWindowType *type) override;
virtual HRESULT GetWindow(IUnknown **ptr) override;
protected:
virtual ~WindowAdapter() {}
private:
AngleWindowType mWindowType;
ComPtr<IUnknown> mWindow;
};
WindowAdapter::WindowAdapter(ComPtr<IUnknown> window, AngleWindowType type)
: mWindowType(type)
, mWindow(window)
{
}
HRESULT WindowAdapter::GetType(AngleWindowType *type)
{
if (mWindowType < 0 || mWindowType >= AWT_NUM_TYPES)
return E_FAIL;
*type = mWindowType;
return S_OK;
}
HRESULT WindowAdapter::GetWindow(IUnknown **ptr)
{
*ptr = mWindow.Get();
if (*ptr)
(*ptr)->AddRef();
return S_OK;
}
IWindowAdapter::Ptr createWindowAdapter(EGLNativeWindowType window)
{
if (window == nullptr)
return nullptr;
ComPtr<IUnknown> unk(window);
// Try a trivial conversion first
IWindowAdapter::Ptr adapter;
if (SUCCEEDED(unk.As(&adapter)))
return adapter;
// Check if this is a CoreWindow
ComPtr<WindowAdapterABIType<CoreWindow>::Type> coreWindow;
if (SUCCEEDED(unk.As(&coreWindow)))
return Make<WindowAdapter>(unk, AWT_COREWINDOW);
// Check if this is a DXGI swapchain adapter
ComPtr<ISwapChainAdapter> swapChainAdapter;
if (SUCCEEDED(unk.As(&swapChainAdapter)))
return Make<WindowAdapter>(unk, AWT_SWAPCHAIN_ADAPTER);
return nullptr;
}
bool verifyWindowAccessible(IWindowAdapter::Ptr windowAdapter)
{
if (windowAdapter == nullptr)
return false;
AngleWindowType windowType;
if (FAILED(windowAdapter->GetType(&windowType)))
return false;
if (windowType == AWT_COREWINDOW)
{
CoreWindow^ coreWindow;
windowAdapter->GetWindowAsWinRT(&coreWindow);
if (coreWindow != CoreWindow::GetForCurrentThread())
{
ERR("CoreWindow doesn't belong to the current thread,"
"was the function called from the matching UI thread?");
return false;
}
}
return true;
}
} // namespace egl