]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
Direct3D11 updates.
authorToni Wilen <twilen@winuae.net>
Sun, 29 Oct 2017 11:36:56 +0000 (13:36 +0200)
committerToni Wilen <twilen@winuae.net>
Sun, 29 Oct 2017 11:36:56 +0000 (13:36 +0200)
od-win32/direct3d.cpp
od-win32/direct3d.h
od-win32/direct3d11.cpp
od-win32/win32.cpp
od-win32/win32gfx.cpp

index fdc199b26ce8e3b6974c77e1e03cbfe7f671eafb..68cbe8f1535504969ccae3438c9e0322c15a1a6b 100644 (file)
@@ -3659,6 +3659,7 @@ void d3d9_select(void)
        D3D_getrefreshrate = xD3D_getrefreshrate;
        D3D_vblank_reset = xD3D_vblank_reset;
        D3D_restore = xD3D_restore;
+       D3D_resize = NULL;
 }
 
 #endif
index cb8a4620ddaa78341b670513603653c56b44b3f8..250dd97e23cb7361e202c9f930cdf96d94464fee 100644 (file)
@@ -20,6 +20,7 @@ extern bool(*D3D_getvblankpos)(int *vpos);
 extern double(*D3D_getrefreshrate)(void);
 extern void(*D3D_vblank_reset)(double freq);
 extern void(*D3D_restore)(void); 
+extern void(*D3D_resize)(int);
 
 extern LPDIRECT3DSURFACE9 D3D_capture(int*,int*,int*);
 extern LPDIRECT3DTEXTURE9 D3D_getcursorsurface(void);
index c8ce638ab33fc8265f5f53ac76542d32933c0897..c17088de6b7e40de90a11dfd2487778bf1ff09f6 100644 (file)
@@ -21,6 +21,7 @@ using Microsoft::WRL::ComPtr;
 #include "direct3d.h"
 #include "uae.h"
 #include "custom.h"
+#include "gfxfilter.h"
 
 void (*D3D_free)(bool immediate);
 const TCHAR* (*D3D_init)(HWND ahwnd, int w_w, int h_h, int depth, int *freq, int mmult);
@@ -43,12 +44,10 @@ bool (*D3D_getvblankpos)(int *vpos);
 double (*D3D_getrefreshrate)(void);
 void (*D3D_vblank_reset)(double freq);
 void(*D3D_restore)(void);
+void(*D3D_resize)(int);
 
 static HANDLE hd3d11, hdxgi, hd3dcompiler;
 
-static const float SCREEN_DEPTH = 1000.0f;
-static const float SCREEN_NEAR = 0.1f;
-
 struct d3d11struct
 {
        IDXGISwapChain1* m_swapChain;
@@ -56,7 +55,6 @@ struct d3d11struct
        ID3D11DeviceContext* m_deviceContext;
        ID3D11RenderTargetView* m_renderTargetView;
        ID3D11RasterizerState* m_rasterState;
-       D3DXMATRIX m_projectionMatrix;
        D3DXMATRIX m_worldMatrix;
        D3DXMATRIX m_orthoMatrix;
        ID3D11Buffer *m_vertexBuffer, *m_indexBuffer;
@@ -76,6 +74,14 @@ struct d3d11struct
        int texturelocked;
        DXGI_FORMAT format;
        bool m_tearingSupport;
+       int dmult;
+       float xoffset, yoffset;
+       DXGI_SWAP_CHAIN_DESC1 swapChainDesc;
+       DXGI_SWAP_CHAIN_FULLSCREEN_DESC  fsSwapChainDesc;
+       HWND ahwnd;
+       int fsmode;
+       bool fsmodechange;
+       bool invalidmode;
 };
 
 struct VertexType
@@ -108,6 +114,73 @@ static PFN_D3D11_CREATE_DEVICE pD3D11CreateDevice;
 static CREATEDXGIFACTORY1 pCreateDXGIFactory1;
 static D3DCOMPILEFROMFILE pD3DCompileFromFile;
 
+static D3DXMATRIX* MatrixOrthoOffCenterLH(D3DXMATRIXA16 *pOut, float l, float r, float b, float t, float zn, float zf)
+{
+       pOut->_11 = 2.0f / r; pOut->_12 = 0.0f;   pOut->_13 = 0.0f;  pOut->_14 = 0.0f;
+       pOut->_21 = 0.0f;   pOut->_22 = 2.0f / t; pOut->_23 = 0.0f;  pOut->_24 = 0.0f;
+       pOut->_31 = 0.0f;   pOut->_32 = 0.0f;   pOut->_33 = 1.0f;  pOut->_34 = 0.0f;
+       pOut->_41 = -1.0f;  pOut->_42 = -1.0f;  pOut->_43 = 0.0f;  pOut->_44 = 1.0f;
+       return pOut;
+}
+
+static D3DXMATRIX* MatrixScaling(D3DXMATRIXA16 *pOut, float sx, float sy, float sz)
+{
+       pOut->_11 = sx;     pOut->_12 = 0.0f;   pOut->_13 = 0.0f;  pOut->_14 = 0.0f;
+       pOut->_21 = 0.0f;   pOut->_22 = sy;     pOut->_23 = 0.0f;  pOut->_24 = 0.0f;
+       pOut->_31 = 0.0f;   pOut->_32 = 0.0f;   pOut->_33 = sz;    pOut->_34 = 0.0f;
+       pOut->_41 = 0.0f;   pOut->_42 = 0.0f;   pOut->_43 = 0.0f;  pOut->_44 = 1.0f;
+       return pOut;
+}
+
+static D3DXMATRIX* MatrixTranslation(D3DXMATRIXA16 *pOut, float tx, float ty, float tz)
+{
+       pOut->_11 = 1.0f;   pOut->_12 = 0.0f;   pOut->_13 = 0.0f;  pOut->_14 = 0.0f;
+       pOut->_21 = 0.0f;   pOut->_22 = 1.0f;   pOut->_23 = 0.0f;  pOut->_24 = 0.0f;
+       pOut->_31 = 0.0f;   pOut->_32 = 0.0f;   pOut->_33 = 1.0f;  pOut->_34 = 0.0f;
+       pOut->_41 = tx;     pOut->_42 = ty;     pOut->_43 = tz;    pOut->_44 = 1.0f;
+       return pOut;
+}
+
+static void setupscenecoords(void)
+{
+       struct d3d11struct *d3d = &d3d11data[0];
+
+       d3d->xoffset = 0;
+       d3d->yoffset = 0;
+
+       return;
+
+       RECT sr, dr, zr;
+       float w, h;
+       float dw, dh;
+       static RECT sr2, dr2, zr2;
+
+       d3d->dmult = 1;
+
+       getfilterrect2(&dr, &sr, &zr, d3d->m_screenWidth, d3d->m_screenHeight, d3d->m_bitmapWidth / d3d->dmult, d3d->m_bitmapHeight / d3d->dmult, d3d->dmult, d3d->m_bitmapWidth, d3d->m_bitmapHeight);
+
+       if (memcmp(&sr, &sr2, sizeof RECT) || memcmp(&dr, &dr2, sizeof RECT) || memcmp(&zr, &zr2, sizeof RECT)) {
+               write_log(_T("POS (%d %d %d %d) - (%d %d %d %d)[%d,%d] (%d %d)\n"),
+                       dr.left, dr.top, dr.right, dr.bottom, sr.left, sr.top, sr.right, sr.bottom,
+                       sr.right - sr.left, sr.bottom - sr.top,
+                       zr.left, zr.top);
+               sr2 = sr;
+               dr2 = dr;
+               zr2 = zr;
+       }
+
+       dw = dr.right - dr.left;
+       dh = dr.bottom - dr.top;
+       w = sr.right - sr.left;
+       h = sr.bottom - sr.top;
+
+       d3d->xoffset = -zr.left;
+       d3d->yoffset = -zr.top;
+
+       //write_log(_T("%.1f %.1f\n"), d3d->xoffset, d3d->yoffset);
+}
+
+
 static void FreeTexture(void)
 {
        struct d3d11struct *d3d = &d3d11data[0];
@@ -201,8 +274,10 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        TCHAR tmp[MAX_DPATH], tmp2[MAX_DPATH];
 
        plugin_path = get_plugin_path(tmp, sizeof tmp / sizeof(TCHAR), _T("filtershaders\\direct3d11"));
-       if (!plugin_path)
+       if (!plugin_path) {
+               write_log(_T("Plugin path not found\n"));
                return false;
+       }
 
        // Initialize the pointers this function will use to null.
        errorMessage = 0;
@@ -235,6 +310,7 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        result = device->CreateVertexShader(vertexShaderBuffer->GetBufferPointer(), vertexShaderBuffer->GetBufferSize(), NULL, &d3d->m_vertexShader);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateVertexShader %08x\n"), result);
                return false;
        }
 
@@ -242,6 +318,7 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        result = device->CreatePixelShader(pixelShaderBuffer->GetBufferPointer(), pixelShaderBuffer->GetBufferSize(), NULL, &d3d->m_pixelShader);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreatePixelShader %08x\n"), result);
                return false;
        }
 
@@ -270,6 +347,7 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        result = device->CreateInputLayout(polygonLayout, numElements, vertexShaderBuffer->GetBufferPointer(), vertexShaderBuffer->GetBufferSize(), &d3d->m_layout);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateInputLayout %08x\n"), result);
                return false;
        }
 
@@ -292,6 +370,7 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        result = device->CreateBuffer(&matrixBufferDesc, NULL, &d3d->m_matrixBuffer);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateBuffer(matrix) %08x\n"), result);
                return false;
        }
 
@@ -314,6 +393,7 @@ static bool TextureShaderClass_InitializeShader(ID3D11Device* device, HWND hwnd)
        result = device->CreateSamplerState(&samplerDesc, &d3d->m_sampleState);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateSamplerState %08x\n"), result);
                return false;
        }
 
@@ -378,6 +458,7 @@ static bool InitializeBuffers(ID3D11Device* device)
        result = device->CreateBuffer(&vertexBufferDesc, &vertexData, &d3d->m_vertexBuffer);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateBuffer(vertex) %08x\n"), result);
                return false;
        }
 
@@ -398,6 +479,7 @@ static bool InitializeBuffers(ID3D11Device* device)
        result = device->CreateBuffer(&indexBufferDesc, &indexData, &d3d->m_indexBuffer);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11Device CreateBuffer(index) %08x\n"), result);
                return false;
        }
 
@@ -412,7 +494,7 @@ static bool InitializeBuffers(ID3D11Device* device)
 }
 
 
-static bool UpdateBuffers(ID3D11DeviceContext* deviceContext, int positionX, int positionY)
+static bool UpdateBuffers(ID3D11DeviceContext* deviceContext)
 {
        struct d3d11struct *d3d = &d3d11data[0];
 
@@ -421,19 +503,20 @@ static bool UpdateBuffers(ID3D11DeviceContext* deviceContext, int positionX, int
        D3D11_MAPPED_SUBRESOURCE mappedResource;
        VertexType* verticesPtr;
        HRESULT result;
+       float positionX, positionY;
 
-       positionX = (d3d->m_screenWidth - d3d->m_bitmapWidth) / 2;
-       positionY = (d3d->m_screenHeight - d3d->m_bitmapHeight) / 2;
+       positionX = (d3d->m_screenWidth - d3d->m_bitmapWidth) / 2.0 + d3d->xoffset;
+       positionY = (d3d->m_screenHeight - d3d->m_bitmapHeight) / 2.0 + d3d->yoffset;
 
 
        // Calculate the screen coordinates of the left side of the bitmap.
-       left = (float)((d3d->m_screenWidth / 2) * -1) + (float)positionX;
+       left = (float)((d3d->m_screenWidth / 2) * -1) + positionX;
 
        // Calculate the screen coordinates of the right side of the bitmap.
        right = left + (float)d3d->m_bitmapWidth;
 
        // Calculate the screen coordinates of the top of the bitmap.
-       top = (float)(d3d->m_screenHeight / 2) - (float)positionY;
+       top = (float)(d3d->m_screenHeight / 2) - positionY;
 
        // Calculate the screen coordinates of the bottom of the bitmap.
        bottom = top - (float)d3d->m_bitmapHeight;
@@ -470,6 +553,7 @@ static bool UpdateBuffers(ID3D11DeviceContext* deviceContext, int positionX, int
        result = deviceContext->Map(d3d->m_vertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11DeviceContext map(vertex) %08x\n"), result);
                return false;
        }
 
@@ -489,6 +573,107 @@ static bool UpdateBuffers(ID3D11DeviceContext* deviceContext, int positionX, int
        return true;
 }
 
+static bool initd3d(struct d3d11struct *d3d)
+{
+       HRESULT result;
+       ID3D11Texture2D* backBufferPtr;
+       D3D11_RASTERIZER_DESC rasterDesc;
+       D3D11_VIEWPORT viewport;
+
+       write_log(_T("D3D11 initd3d start\n"));
+
+       // Get the pointer to the back buffer.
+       result = d3d->m_swapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&backBufferPtr);
+       if (FAILED(result))
+       {
+               write_log(_T("IDXGISwapChain1 GetBuffer %08x\n"), result);
+               return false;
+       }
+
+       // Create the render target view with the back buffer pointer.
+       result = d3d->m_device->CreateRenderTargetView(backBufferPtr, NULL, &d3d->m_renderTargetView);
+       if (FAILED(result))
+       {
+               write_log(_T("ID3D11Device CreateRenderTargetView %08x\n"), result);
+               return false;
+       }
+
+       // Release pointer to the back buffer as we no longer need it.
+       backBufferPtr->Release();
+       backBufferPtr = 0;
+
+
+       // Setup the raster description which will determine how and what polygons will be drawn.
+       rasterDesc.AntialiasedLineEnable = false;
+       rasterDesc.CullMode = D3D11_CULL_BACK;
+       rasterDesc.DepthBias = 0;
+       rasterDesc.DepthBiasClamp = 0.0f;
+       rasterDesc.DepthClipEnable = false;
+       rasterDesc.FillMode = D3D11_FILL_SOLID;
+       rasterDesc.FrontCounterClockwise = false;
+       rasterDesc.MultisampleEnable = false;
+       rasterDesc.ScissorEnable = false;
+       rasterDesc.SlopeScaledDepthBias = 0.0f;
+
+       // Create the rasterizer state from the description we just filled out.
+       result = d3d->m_device->CreateRasterizerState(&rasterDesc, &d3d->m_rasterState);
+       if (FAILED(result))
+       {
+               write_log(_T("ID3D11Device CreateRasterizerState %08x\n"), result);
+               return false;
+       }
+
+       // Now set the rasterizer state.
+       d3d->m_deviceContext->RSSetState(d3d->m_rasterState);
+
+       // Setup the viewport for rendering.
+       viewport.Width = (float)d3d->m_screenWidth;
+       viewport.Height = (float)d3d->m_screenHeight;
+       viewport.MinDepth = 0.0f;
+       viewport.MaxDepth = 1.0f;
+       viewport.TopLeftX = 0.0f;
+       viewport.TopLeftY = 0.0f;
+
+       // Create the viewport.
+       d3d->m_deviceContext->RSSetViewports(1, &viewport);
+
+       // Initialize the world matrix to the identity matrix.
+       D3DXMatrixIdentity(&d3d->m_worldMatrix);
+
+       // Create an orthographic projection matrix for 2D rendering.
+       D3DXMatrixOrthoLH(&d3d->m_orthoMatrix, (float)d3d->m_screenWidth, (float)d3d->m_bitmapHeight, 0.0f, 1.0f);
+
+       d3d->m_positionX = 0.0f;
+       d3d->m_positionY = 0.0f;
+       d3d->m_positionZ = 1.0f;
+
+       d3d->m_rotationX = 0.0f;
+       d3d->m_rotationY = 0.0f;
+       d3d->m_rotationZ = 0.0f;
+
+       if (!TextureShaderClass_InitializeShader(d3d->m_device, d3d->ahwnd))
+               return false;
+       if (!InitializeBuffers(d3d->m_device))
+               return false;
+       if (!UpdateBuffers(d3d->m_deviceContext))
+               return false;
+
+       write_log(_T("D3D11 initd3d end\n"));
+       return true;
+}
+
+static void setswapchainmode(struct d3d11struct *d3d, int fs)
+{
+       // It is recommended to always use the tearing flag when it is supported.
+       d3d->swapChainDesc.Flags &= ~DXGI_SWAP_CHAIN_FLAG_ALLOW_TEARING;
+       d3d->swapChainDesc.Flags = d3d->m_tearingSupport ? DXGI_SWAP_CHAIN_FLAG_ALLOW_TEARING : 0;
+       d3d->swapChainDesc.Flags &= ~DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH;
+       if (fs) {
+               d3d->swapChainDesc.Flags |= DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH;
+       }
+       d3d->fsSwapChainDesc.Windowed = TRUE;
+}
+
 static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *freq, int mmult)
 {
        struct d3d11struct *d3d = &d3d11data[0];
@@ -500,15 +685,11 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        ComPtr<IDXGIFactory5> factory5;
        IDXGIAdapter1* adapter;
        IDXGIOutput* adapterOutput;
-       unsigned int numModes, i;
+       DXGI_ADAPTER_DESC1 adesc;
+       DXGI_OUTPUT_DESC odesc;
+       unsigned int numModes;
        DXGI_MODE_DESC1* displayModeList;
        DXGI_ADAPTER_DESC adapterDesc;
-       DXGI_SWAP_CHAIN_DESC1 swapChainDesc;
-       DXGI_SWAP_CHAIN_FULLSCREEN_DESC  fsSwapChainDesc;
-       ID3D11Texture2D* backBufferPtr;
-       D3D11_RASTERIZER_DESC rasterDesc;
-       D3D11_VIEWPORT viewport;
-       float fieldOfView, screenAspect;
 
        write_log(_T("D3D11 init start\n"));
 
@@ -527,9 +708,14 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        d3d->m_bitmapHeight = w_h;
        d3d->m_screenWidth = w_w;
        d3d->m_screenHeight = w_h;
+       d3d->ahwnd = ahwnd;
        d3d->format = DXGI_FORMAT_B8G8R8A8_UNORM;
 
        struct MultiDisplay *md = getdisplay(&currprefs);
+       POINT pt;
+       pt.x = (md->rect.right - md->rect.left) / 2 + md->rect.left;
+       pt.y = (md->rect.bottom - md->rect.top) / 2 + md->rect.top;
+       HMONITOR winmon = MonitorFromPoint(pt, MONITOR_DEFAULTTONEAREST);
 
        // Create a DirectX graphics interface factory.
        result = pCreateDXGIFactory1(__uuidof(IDXGIFactory4), (void**)&factory4);
@@ -549,7 +735,7 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
                if (!d3d->m_tearingSupport) {
                        result = factory5->CheckFeatureSupport(DXGI_FEATURE_PRESENT_ALLOW_TEARING, &allowTearing, sizeof(allowTearing));
                        d3d->m_tearingSupport = SUCCEEDED(result) && allowTearing;
-                       write_log(_T("CheckFeatureSupport(DXGI_FEATURE_PRESENT_ALLOW_TEARING) = %08x %d"), result, allowTearing);
+                       write_log(_T("CheckFeatureSupport(DXGI_FEATURE_PRESENT_ALLOW_TEARING) = %08x %d\n"), result, allowTearing);
                }
        }
 
@@ -557,21 +743,36 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        result = factory2->EnumAdapters1(0, &adapter);
        if (FAILED(result))
        {
+               write_log(_T("IDXGIFactory2 EnumAdapters1 %08x\n"), result);
                return false;
        }
+       result = adapter->GetDesc1(&adesc);
 
-
+       UINT adapterNum = 0;
+       bool outputFound = false;
        // Enumerate the primary adapter output (monitor).
-       result = adapter->EnumOutputs(0, &adapterOutput);
-       if (FAILED(result))
-       {
-               return false;
+       while (adapter->EnumOutputs(adapterNum, &adapterOutput) != DXGI_ERROR_NOT_FOUND) {
+               result = adapterOutput->GetDesc(&odesc);
+               if (SUCCEEDED(result)) {
+                       if (odesc.Monitor == winmon || !_tcscmp(odesc.DeviceName, md->adapterid)) {
+                               outputFound = true;
+                               break;
+                       }
+               }
+               adapterNum++;
+       }
+       if (!outputFound) {
+               result = adapter->EnumOutputs(0, &adapterOutput);
+               if (FAILED(result)) {
+                       write_log(_T("EnumOutputs %08x\n"), result);
+                       return false;
+               }
        }
 
        ComPtr<IDXGIOutput1> adapterOutput1;
        result = adapterOutput->QueryInterface(__uuidof(IDXGIOutput1), &adapterOutput1);
        if (FAILED(result)) {
-               write_log(_T("QueryInterface IDXGIOutput1 %08x\n"), result);
+               write_log(_T("IDXGIOutput QueryInterface %08x\n"), result);
        }
 
 
@@ -579,6 +780,7 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        result = adapterOutput1->GetDisplayModeList1(d3d->format, DXGI_ENUM_MODES_INTERLACED, &numModes, NULL);
        if (FAILED(result))
        {
+               write_log(_T("IDXGIOutput1 GetDisplayModeList1 %08x\n"), result);
                return false;
        }
 
@@ -586,6 +788,7 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        displayModeList = new DXGI_MODE_DESC1[numModes];
        if (!displayModeList)
        {
+               write_log(_T("IDXGIAdapter1 GetDesc %08x\n"), result);
                return false;
        }
 
@@ -593,25 +796,53 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        result = adapterOutput1->GetDisplayModeList1(d3d->format, DXGI_ENUM_MODES_INTERLACED, &numModes, displayModeList);
        if (FAILED(result))
        {
+               write_log(_T("IDXGIAdapter1 GetDesc %08x\n"), result);
                return false;
        }
 
-       ZeroMemory(&fsSwapChainDesc, sizeof(fsSwapChainDesc));
+       ZeroMemory(&d3d->fsSwapChainDesc, sizeof(d3d->fsSwapChainDesc));
+
+       int hz = getrefreshrate(w_w, w_h);
 
        // Now go through all the display modes and find the one that matches the screen width and height.
        // When a match is found store the numerator and denominator of the refresh rate for that monitor.
-       for (i = 0; i < numModes; i++)
+       d3d->fsSwapChainDesc.RefreshRate.Denominator = 0;
+       d3d->fsSwapChainDesc.RefreshRate.Numerator = 0;
+       for (int i = 0; i < numModes; i++)
        {
                DXGI_MODE_DESC1 *m = &displayModeList[i];
                if (m->Format != d3d->format)
                        continue;
-               if (m->Width == md->rect.right - md->rect.left && m->Height == md->rect.bottom - md->rect.top) {
-                       fsSwapChainDesc.RefreshRate.Denominator = m->RefreshRate.Denominator;
-                       fsSwapChainDesc.RefreshRate.Numerator = m->RefreshRate.Numerator;
-                       fsSwapChainDesc.ScanlineOrdering = m->ScanlineOrdering;
-                       fsSwapChainDesc.Scaling = m->Scaling;
-                       if (apm->gfx_interlaced && !(m->ScanlineOrdering & DXGI_MODE_SCANLINE_ORDER_UPPER_FIELD_FIRST))
-                               continue;
+               if (apm->gfx_interlaced && !(m->ScanlineOrdering & DXGI_MODE_SCANLINE_ORDER_UPPER_FIELD_FIRST))
+                       continue;
+               if (m->Width == w_w && m->Height == w_h) {
+                       d3d->fsSwapChainDesc.ScanlineOrdering = m->ScanlineOrdering;
+                       d3d->fsSwapChainDesc.Scaling = m->Scaling;
+                       if (!hz)
+                               break;
+                       if (isfullscreen() > 0) {
+                               double mhz = (double)m->RefreshRate.Numerator / m->RefreshRate.Denominator;
+                               if ((int)(mhz + 0.5) == hz) {
+                                       d3d->fsSwapChainDesc.RefreshRate.Denominator = m->RefreshRate.Denominator;
+                                       d3d->fsSwapChainDesc.RefreshRate.Numerator = m->RefreshRate.Numerator;
+                                       break;
+                               }
+                       }
+               }
+       }
+       if (isfullscreen() > 0 && (hz == 0 || (d3d->fsSwapChainDesc.RefreshRate.Denominator == 0 && d3d->fsSwapChainDesc.RefreshRate.Numerator == 0))) {
+               DXGI_MODE_DESC1 md1 = { 0 }, md2;
+               md1.Format = d3d->format;
+               md1.Width = w_w;
+               md1.Height = w_h;
+               md1.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
+               md1.ScanlineOrdering = apm->gfx_interlaced ? DXGI_MODE_SCANLINE_ORDER_UPPER_FIELD_FIRST : DXGI_MODE_SCANLINE_ORDER_PROGRESSIVE;
+               result = adapterOutput1->FindClosestMatchingMode1(&md1, &md2, NULL);
+               if (FAILED(result)) {
+                       write_log(_T("FindClosestMatchingMode1 %08x\n"), result);
+               } else {
+                       d3d->fsSwapChainDesc.RefreshRate.Denominator = md2.RefreshRate.Denominator;
+                       d3d->fsSwapChainDesc.RefreshRate.Numerator = md2.RefreshRate.Numerator;
                }
        }
 
@@ -619,6 +850,7 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        result = adapter->GetDesc(&adapterDesc);
        if (FAILED(result))
        {
+               write_log(_T("IDXGIAdapter1 GetDesc %08x\n"), result);
                return false;
        }
 
@@ -635,9 +867,13 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        adapter = 0;
 
        static const D3D_FEATURE_LEVEL levels[] = { D3D_FEATURE_LEVEL_11_1, D3D_FEATURE_LEVEL_11_0 };
-       result = pD3D11CreateDevice(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, D3D11_CREATE_DEVICE_BGRA_SUPPORT, levels, 2, D3D11_SDK_VERSION, &d3d->m_device, NULL, &d3d->m_deviceContext);
+       UINT cdflags = D3D11_CREATE_DEVICE_BGRA_SUPPORT;
+#ifdef _DEBUG
+       cdflags |= D3D11_CREATE_DEVICE_DEBUG;
+#endif
+       result = pD3D11CreateDevice(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, cdflags, levels, 2, D3D11_SDK_VERSION, &d3d->m_device, NULL, &d3d->m_deviceContext);
        if (FAILED(result)) {
-               write_log(_T("D3D11CreateDevice failed %08x\n"), result);
+               write_log(_T("D3D11CreateDevice %08x\n"), result);
                return false;
        }
 
@@ -646,145 +882,66 @@ static const bool xxD3D11_init(HWND ahwnd, int w_w, int w_h, int depth, int *fre
        if (FAILED(result)) {
                write_log(_T("QueryInterface IDXGIDevice1 %08x\n"), result);
        }
-       result = dxgiDevice->SetMaximumFrameLatency(1);
+       else {
+               result = dxgiDevice->SetMaximumFrameLatency(1);
+               if (FAILED(result))
+                       write_log(_T("IDXGIDevice1 SetMaximumFrameLatency %08x\n"), result);
+       }
 
        // Initialize the swap chain description.
-       ZeroMemory(&swapChainDesc, sizeof(swapChainDesc));
+       ZeroMemory(&d3d->swapChainDesc, sizeof(d3d->swapChainDesc));
 
        // Set the width and height of the back buffer.
-       swapChainDesc.Width = w_w;
-       swapChainDesc.Height = w_h;
+       d3d->swapChainDesc.Width = w_w;
+       d3d->swapChainDesc.Height = w_h;
 
        // Set regular 32-bit surface for the back buffer.
-       swapChainDesc.Format = d3d->format;
+       d3d->swapChainDesc.Format = d3d->format;
 
        // Turn multisampling off.
-       swapChainDesc.SampleDesc.Count = 1;
-       swapChainDesc.SampleDesc.Quality = 0;
+       d3d->swapChainDesc.SampleDesc.Count = 1;
+       d3d->swapChainDesc.SampleDesc.Quality = 0;
 
        // Set the usage of the back buffer.
-       swapChainDesc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
+       d3d->swapChainDesc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
 
-       swapChainDesc.BufferCount = 2;
+       d3d->swapChainDesc.BufferCount = 2;
 
-       swapChainDesc.Scaling = DXGI_SCALING_NONE;
+       d3d->swapChainDesc.Scaling = DXGI_SCALING_NONE;
 
-       swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL;
+       d3d->swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL;
 
-       swapChainDesc.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED;
+       d3d->swapChainDesc.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED;
 
-       // It is recommended to always use the tearing flag when it is supported.
-       swapChainDesc.Flags = d3d->m_tearingSupport ? DXGI_SWAP_CHAIN_FLAG_ALLOW_TEARING : 0;
-
-       fsSwapChainDesc.Windowed = isfullscreen() <= 0;
+       setswapchainmode(d3d, isfullscreen() > 0);
 
        // Create the swap chain, Direct3D device, and Direct3D device context.
-       result = factory2->CreateSwapChainForHwnd(d3d->m_device, ahwnd, &swapChainDesc, isfullscreen() > 0 ? &fsSwapChainDesc : NULL, NULL, &d3d->m_swapChain);
-
-       // Set the feature level to DirectX 11.
-       // featureLevel = D3D_FEATURE_LEVEL_11_0;
-       // result = pD3D11CreateDeviceAndSwapChain(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, 0, &featureLevel, 1, D3D11_SDK_VERSION, &swapChainDesc, &d3d->m_swapChain,
-       // &d3d->m_device, NULL, &d3d->m_deviceContext);
-       if (FAILED(result))
-       {
-               return false;
-       }
-
-       // Get the pointer to the back buffer.
-       result = d3d->m_swapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&backBufferPtr);
+       result = factory2->CreateSwapChainForHwnd(d3d->m_device, ahwnd, &d3d->swapChainDesc, isfullscreen() > 0 ? &d3d->fsSwapChainDesc : NULL, NULL, &d3d->m_swapChain);
        if (FAILED(result))
        {
+               write_log(_T("IDXGIFactory2 CreateSwapChainForHwnd %08x\n"), result);
                return false;
        }
 
-       // Create the render target view with the back buffer pointer.
-       result = d3d->m_device->CreateRenderTargetView(backBufferPtr, NULL, &d3d->m_renderTargetView);
-       if (FAILED(result))
-       {
-               return false;
-       }
-
-       // Release pointer to the back buffer as we no longer need it.
-       backBufferPtr->Release();
-       backBufferPtr = 0;
-
-
-       // Setup the raster description which will determine how and what polygons will be drawn.
-       rasterDesc.AntialiasedLineEnable = false;
-       rasterDesc.CullMode = D3D11_CULL_BACK;
-       rasterDesc.DepthBias = 0;
-       rasterDesc.DepthBiasClamp = 0.0f;
-       rasterDesc.DepthClipEnable = false;
-       rasterDesc.FillMode = D3D11_FILL_SOLID;
-       rasterDesc.FrontCounterClockwise = false;
-       rasterDesc.MultisampleEnable = false;
-       rasterDesc.ScissorEnable = false;
-       rasterDesc.SlopeScaledDepthBias = 0.0f;
-
-       // Create the rasterizer state from the description we just filled out.
-       result = d3d->m_device->CreateRasterizerState(&rasterDesc, &d3d->m_rasterState);
-       if (FAILED(result))
-       {
-               return false;
+       result = factory2->MakeWindowAssociation(ahwnd, DXGI_MWA_NO_WINDOW_CHANGES | DXGI_MWA_NO_ALT_ENTER | DXGI_MWA_NO_PRINT_SCREEN);
+       if (FAILED(result)) {
+               write_log(_T("IDXGIFactory2 MakeWindowAssociation %08x\n"), result);
        }
 
-       // Now set the rasterizer state.
-       d3d->m_deviceContext->RSSetState(d3d->m_rasterState);
-
-       // Setup the viewport for rendering.
-       viewport.Width = (float)w_w;
-       viewport.Height = (float)w_h;
-       viewport.MinDepth = 0.0f;
-       viewport.MaxDepth = 1.0f;
-       viewport.TopLeftX = 0.0f;
-       viewport.TopLeftY = 0.0f;
-
-       // Create the viewport.
-       d3d->m_deviceContext->RSSetViewports(1, &viewport);
-
-       // Setup the projection matrix.
-       fieldOfView = (float)D3DX_PI / 4.0f;
-       screenAspect = (float)w_w / (float)w_h;
-
-       // Create the projection matrix for 3D rendering.
-       D3DXMatrixPerspectiveFovLH(&d3d->m_projectionMatrix, fieldOfView, screenAspect, SCREEN_NEAR, SCREEN_DEPTH);
-
-       // Initialize the world matrix to the identity matrix.
-       D3DXMatrixIdentity(&d3d->m_worldMatrix);
-
-       // Create an orthographic projection matrix for 2D rendering.
-       D3DXMatrixOrthoLH(&d3d->m_orthoMatrix, (float)w_w, (float)w_h, SCREEN_NEAR, SCREEN_DEPTH);
-
-       d3d->m_positionX = 0.0f;
-       d3d->m_positionY = 0.0f;
-       d3d->m_positionZ = -10.0f;
-
-       d3d->m_rotationX = 0.0f;
-       d3d->m_rotationY = 0.0f;
-       d3d->m_rotationZ = 0.0f;
-
-       if (!TextureShaderClass_InitializeShader(d3d->m_device, ahwnd))
-               return false;
-       if (!InitializeBuffers(d3d->m_device))
-               return false;
-       if (!UpdateBuffers(d3d->m_deviceContext, 0, 0))
-               return false;
+       d3d->fsmode = 0;
+       if (isfullscreen() > 0)
+               D3D_resize(1);
+       D3D_resize(0);
 
        write_log(_T("D3D11 init end\n"));
        return true;
 }
 
-static void xD3D11_free(bool immediate)
+static void freed3d(struct d3d11struct *d3d)
 {
-       struct d3d11struct *d3d = &d3d11data[0];
-
-       write_log(_T("D3D11 free start\n"));
+       write_log(_T("D3D11 freed3d start\n"));
 
        // Before shutting down set to windowed mode or when you release the swap chain it will throw an exception.
-       if (d3d->m_swapChain)
-       {
-               d3d->m_swapChain->SetFullscreenState(false, NULL);
-       }
        if (d3d->m_rasterState)
        {
                d3d->m_rasterState->Release();
@@ -797,11 +954,6 @@ static void xD3D11_free(bool immediate)
                d3d->m_renderTargetView = 0;
        }
 
-       if (d3d->m_swapChain)
-       {
-               d3d->m_swapChain->Release();
-               d3d->m_swapChain = 0;
-       }
        if (d3d->m_layout) {
                d3d->m_layout->Release();
                d3d->m_layout = NULL;
@@ -834,6 +986,27 @@ static void xD3D11_free(bool immediate)
 
        FreeTexture();
 
+       if (d3d->m_deviceContext)
+       {
+               d3d->m_deviceContext->ClearState();
+       }
+       write_log(_T("D3D11 freed3d end\n"));
+}
+
+static void xD3D11_free(bool immediate)
+{
+       struct d3d11struct *d3d = &d3d11data[0];
+
+       write_log(_T("D3D11 free start\n"));
+
+       freed3d(d3d);
+
+       if (d3d->m_swapChain)
+       {
+               d3d->m_swapChain->SetFullscreenState(false, NULL);
+               d3d->m_swapChain->Release();
+               d3d->m_swapChain = 0;
+       }
        if (d3d->m_deviceContext)
        {
                d3d->m_deviceContext->ClearState();
@@ -880,6 +1053,7 @@ static bool TextureShaderClass_SetShaderParameters(ID3D11DeviceContext* deviceCo
        result = deviceContext->Map(d3d->m_matrixBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
        if (FAILED(result))
        {
+               write_log(_T("ID3D11DeviceContext map(matrix) %08x\n"), result);
                return false;
        }
 
@@ -946,8 +1120,6 @@ static void BeginScene(float red, float green, float blue, float alpha)
 
        // Clear the back buffer.
        d3d->m_deviceContext->ClearRenderTargetView(d3d->m_renderTargetView, color);
-
-       return;
 }
 
 static void EndScene(void)
@@ -955,20 +1127,22 @@ static void EndScene(void)
        struct d3d11struct *d3d = &d3d11data[0];
 
        HRESULT hr;
+       UINT presentFlags = 0;
 
-       // Present the back buffer to the screen since rendering is complete.
        struct apmode *apm = picasso_on ? &currprefs.gfx_apmode[APMODE_RTG] : &currprefs.gfx_apmode[APMODE_NATIVE];
+       if (currprefs.turbo_emulation)
+               presentFlags |= DXGI_PRESENT_DO_NOT_WAIT;
        if (isfullscreen() > 0) {
-               hr = d3d->m_swapChain->Present(apm->gfx_vflip == 0 ? 0 : 1, 0);
+               hr = d3d->m_swapChain->Present(apm->gfx_vflip == 0 ? 0 : 1, presentFlags);
        } else {
-               UINT presentFlags = d3d->m_tearingSupport ? DXGI_PRESENT_ALLOW_TEARING : 0;
-               // Present as fast as possible.
-               hr = d3d->m_swapChain->Present(0, 0);
+               if (d3d->m_tearingSupport)
+                       presentFlags |= DXGI_PRESENT_ALLOW_TEARING;
+               hr = d3d->m_swapChain->Present(0, presentFlags);
        }
+       if (currprefs.turbo_emulation && hr == DXGI_ERROR_WAS_STILL_DRAWING)
+               return;
        if (FAILED(hr))
                write_log(_T("D3D11 Present %08x\n"), hr);
-
-       return;
 }
 
 static void TextureShaderClass_RenderShader(ID3D11DeviceContext* deviceContext, int indexCount)
@@ -987,8 +1161,6 @@ static void TextureShaderClass_RenderShader(ID3D11DeviceContext* deviceContext,
 
        // Render the triangle.
        deviceContext->DrawIndexed(indexCount, 0, 0);
-
-       return;
 }
 
 static bool TextureShaderClass_Render(ID3D11DeviceContext* deviceContext, int indexCount, D3DXMATRIX worldMatrix, D3DXMATRIX viewMatrix,
@@ -1053,8 +1225,6 @@ static void CameraClass_Render()
 
        // Finally create the view matrix from the three updated vectors.
        D3DXMatrixLookAtLH(&d3d->m_viewMatrix, &position, &lookAt, &up);
-
-       return;
 }
 
 static bool GraphicsClass_Render(float rotation)
@@ -1067,6 +1237,9 @@ static bool GraphicsClass_Render(float rotation)
        // Clear the buffers to begin the scene.
        BeginScene(0.0f, 0.0f, 0.0f, 1.0f);
 
+       setupscenecoords();
+       UpdateBuffers(d3d->m_deviceContext);
+
        // Generate the view matrix based on the camera's position.
        CameraClass_Render();
 
@@ -1087,6 +1260,12 @@ static bool xD3D11_renderframe(bool immediate)
 {
        struct d3d11struct *d3d = &d3d11data[0];
 
+       if (d3d->fsmodechange)
+               D3D_resize(0);
+
+       if (d3d->invalidmode)
+               return false;
+
        GraphicsClass_Render(0);
 
        return true;
@@ -1095,26 +1274,37 @@ static bool xD3D11_renderframe(bool immediate)
 
 static void xD3D11_showframe(void)
 {
+       struct d3d11struct *d3d = &d3d11data[0];
+       if (d3d->invalidmode)
+               return;
        // Present the rendered scene to the screen.
        EndScene();
 }
 
 static void xD3D11_clear(void)
 {
+       struct d3d11struct *d3d = &d3d11data[0];
+       if (d3d->invalidmode)
+               return;
        BeginScene(0, 0, 0, 0);
 }
 
 static void xD3D11_refresh(void)
 {
+       if (xD3D11_renderframe(true)) {
+               xD3D11_showframe();
+       }
 }
 
 static bool xD3D11_alloctexture(int w, int h)
 {
        struct d3d11struct *d3d = &d3d11data[0];
 
+       if (d3d->invalidmode)
+               return false;
        d3d->m_bitmapWidth = w;
        d3d->m_bitmapHeight = h;
-       UpdateBuffers(d3d->m_deviceContext, 0, 0);
+       UpdateBuffers(d3d->m_deviceContext);
        return CreateTexture();
 }
 
@@ -1122,11 +1312,13 @@ static uae_u8 *xD3D11_locktexture(int *pitch, int *height, bool fullupdate)
 {
        struct d3d11struct *d3d = &d3d11data[0];
 
+       if (d3d->invalidmode)
+               return NULL;
        D3D11_MAPPED_SUBRESOURCE map;
        HRESULT hr = d3d->m_deviceContext->Map(d3d->texture2d, 0, D3D11_MAP_WRITE_DISCARD, 0, &map);
        if (FAILED(hr)) {
                write_log(_T("D3D11 Map() %08x\n"), hr);
-               return false;
+               return NULL;
        }
        *pitch = map.RowPitch;
        if (height)
@@ -1139,7 +1331,7 @@ static void xD3D11_unlocktexture(void)
 {
        struct d3d11struct *d3d = &d3d11data[0];
 
-       if (!d3d->texturelocked)
+       if (!d3d->texturelocked || d3d->invalidmode)
                return;
        d3d->texturelocked--;
 
@@ -1175,6 +1367,64 @@ static int xD3D11_goodenough(void)
        return 0;
 }
 
+static void xD3D11_resize(int activate)
+{
+       static int recursive;
+       HRESULT hr;
+       struct d3d11struct *d3d = &d3d11data[0];
+
+       if (activate) {
+               if (activate != d3d->fsmode) {
+                       d3d->fsmode = activate;
+                       d3d->fsmodechange = TRUE;
+               }
+               return;
+       }
+
+       if (recursive)
+               return;
+       recursive++;
+
+       if (d3d->m_swapChain) {
+               if (d3d->fsmodechange && d3d->fsmode > 0) {
+                       ShowWindow(d3d->ahwnd, SW_SHOWNORMAL);
+                       hr = d3d->m_swapChain->SetFullscreenState(TRUE, NULL);
+                       if (FAILED(hr)) {
+                               write_log(_T("SetFullscreenState(TRUE) failed %08X\n"), hr);
+                               toggle_fullscreen(10);
+                       } else {
+                               d3d->fsmode = 1;
+                       }
+                       d3d->fsmodechange = 0;
+                       d3d->invalidmode = false;
+               } else if (d3d->fsmodechange && d3d->fsmode < 0) {
+                       hr = d3d->m_swapChain->SetFullscreenState(FALSE, NULL);
+                       if (FAILED(hr))
+                               write_log(_T("SetFullscreenState(FALSE) failed %08X\n"), hr);
+                       ShowWindow(d3d->ahwnd, SW_MINIMIZE);
+                       d3d->fsmode = 0;
+                       d3d->invalidmode = true;
+                       d3d->fsmodechange = 0;
+               }
+               if (!d3d->invalidmode) {
+                       freed3d(d3d);
+                       write_log(_T("D3D11 resize %d %d, %d %d\n"), d3d->m_screenWidth, d3d->m_screenHeight, d3d->m_bitmapWidth, d3d->m_bitmapHeight);
+                       setswapchainmode(d3d, d3d->fsmode);
+                       HRESULT hr = d3d->m_swapChain->ResizeBuffers(d3d->swapChainDesc.BufferCount, d3d->m_screenWidth, d3d->m_screenHeight, d3d->format, d3d->swapChainDesc.Flags);
+                       if (FAILED(hr)) {
+                               write_log(_T("ResizeBuffers %08x\n"), hr);
+                               d3d->invalidmode = true;
+                       }
+                       if (!d3d->invalidmode) {
+                               initd3d(d3d);
+                               xD3D11_alloctexture(d3d->m_bitmapWidth, d3d->m_bitmapHeight);
+                       }
+               }
+       }
+
+       recursive--;
+}
+
 void d3d11_select(void)
 {
        D3D_free = xD3D11_free;
@@ -1200,6 +1450,7 @@ void d3d11_select(void)
        D3D_getvblankpos = NULL;
        D3D_getrefreshrate = NULL;
        D3D_vblank_reset = xD3D11_vblank_reset;
+       D3D_resize = xD3D11_resize;
 }
 
 void d3d_select(struct uae_prefs *p)
index 00b229b961e89820bf5d9b5aa2f5d96e02488d50..d46ed40334d243e70776eda0cf9528fd26c6b631 100644 (file)
@@ -1575,6 +1575,8 @@ static LRESULT CALLBACK AmigaWindowProc (HWND hWnd, UINT message, WPARAM wParam,
                        setminimized ();
                        winuae_inactive (hWnd, minimized);
                }
+               if (D3D_resize)
+                       D3D_resize(0);
                break;
        case WM_ACTIVATE:
                //write_log (_T("active %d\n"), LOWORD(wParam));
@@ -1593,9 +1595,14 @@ static LRESULT CALLBACK AmigaWindowProc (HWND hWnd, UINT message, WPARAM wParam,
                break;
        case WM_ACTIVATEAPP:
                D3D_restore ();
-               if (!wParam && isfullscreen () <= 0 && currprefs.win32_minimize_inactive)
-                       minimizewindow ();
-
+               if (!wParam && isfullscreen() > 0 && D3D_resize) {
+                       D3D_resize(-1);
+               } else if (wParam && isfullscreen() > 0 && D3D_resize) {
+                       D3D_resize(1);
+               }
+               if (!wParam && isfullscreen() <= 0 && currprefs.win32_minimize_inactive) {
+                       minimizewindow();
+               }
 #ifdef RETROPLATFORM
                rp_activate (wParam, lParam);
 #endif
@@ -6812,6 +6819,7 @@ void registertouch(HWND hwnd)
 
 void systray (HWND hwnd, int remove)
 {
+       static const GUID iconguid = { 0xdac2e99b, 0xe8f6, 0x4150, { 0x98, 0x46, 0xd, 0x4a, 0x61, 0xfb, 0xdd, 0x03 } };
        NOTIFYICONDATA nid;
        BOOL v;
 
@@ -6837,8 +6845,11 @@ void systray (HWND hwnd, int remove)
        nid.cbSize = sizeof (nid);
        nid.hWnd = hwnd;
        nid.hIcon = LoadIcon (hInst, (LPCWSTR)MAKEINTRESOURCE (IDI_APPICON));
-       nid.uFlags = NIF_ICON | NIF_MESSAGE;
+       nid.uFlags = NIF_ICON | NIF_MESSAGE | (os_win7 ? NIF_GUID : 0);
        nid.uCallbackMessage = WM_USER + 1;
+       if (os_win7) {
+               nid.guidItem = iconguid;
+       }
        v = Shell_NotifyIcon (remove ? NIM_DELETE : NIM_ADD, &nid);
        //write_log (_T("notif: Shell_NotifyIcon returned %d\n"), v);
        if (v) {
index 69c8865a830c9371e278137084718d6475b63573..b640972416b545e63e5bd272eacf7a8d1088d70d 100644 (file)
@@ -1902,7 +1902,6 @@ static int open_windows (bool mousecapture)
        static bool started = false;
        int ret, i;
 
-       d3d_select(&currprefs);
        changevblankthreadmode (VBLANKTH_IDLE);
 
        screen_is_initialized = 0;
@@ -2171,12 +2170,10 @@ int check_prefs_changed_gfx (void)
                currprefs.gfx_autoresolution = changed_prefs.gfx_autoresolution;
                currprefs.gfx_autoresolution_vga = changed_prefs.gfx_autoresolution_vga;
                currprefs.color_mode = changed_prefs.color_mode;
-               currprefs.gfx_api = changed_prefs.gfx_api;
                currprefs.lightboost_strobo = changed_prefs.lightboost_strobo;
 
-               if (changed_prefs.gfx_apmode[0].gfx_fullscreen == GFX_FULLSCREEN) { 
-                       if (currprefs.gfx_api != changed_prefs.gfx_api)
-                               display_change_requested = 1;
+               if (currprefs.gfx_api != changed_prefs.gfx_api) {
+                       display_change_requested = 1;
                }
 
                if (c & 128) {
@@ -2300,6 +2297,10 @@ int check_prefs_changed_gfx (void)
                                unacquired = true;
                        }
                        close_windows ();
+                       if (currprefs.gfx_api != changed_prefs.gfx_api) {
+                               currprefs.gfx_api = changed_prefs.gfx_api;
+                               d3d_select(&currprefs);
+                       }
                        graphics_init (dontcapture ? false : true);
                        graphics_mode_changed = 1;
                }
@@ -2912,7 +2913,6 @@ static void gfxmode_reset (void)
                }
        }
 #endif
-       d3d_select(&currprefs);
 }
 
 int machdep_init (void)
@@ -2939,7 +2939,8 @@ int graphics_init (bool mousecapture)
 {
        systray (hHiddenWnd, TRUE);
        systray (hHiddenWnd, FALSE);
-       gfxmode_reset ();
+       d3d_select(&currprefs);
+       gfxmode_reset();
        graphics_mode_changed = 1;
        return open_windows (mousecapture);
 }
@@ -4405,7 +4406,7 @@ static int create_windows_2 (void)
                        ShowWindow (hMainWnd, firstwindow ? (currprefs.win32_start_minimized ? SW_SHOWMINIMIZED : SW_SHOWDEFAULT) : SW_SHOWNORMAL);
                UpdateWindow (hMainWnd);
        }
-       if (!currprefs.headless && !rp_isactive ())
+       if (!currprefs.headless && !rp_isactive () && !D3D_resize)
                ShowWindow (hAmigaWnd, SW_SHOWNORMAL);
        UpdateWindow (hAmigaWnd);
        firstwindow = false;
@@ -4878,6 +4879,8 @@ void toggle_fullscreen (int mode)
                        v = GFX_WINDOW;
                else
                        v = GFX_FULLWINDOW;
+       } else if (mode == 10) {
+               v = GFX_WINDOW;
        }
        *p = v;
        updatewinfsmode (&changed_prefs);