2011-11-10 12 views
0

私は以前にこれを行うことができました.2週間前と最後のウィンドウアップデートの間に何が変わったのか分かりませんが、何らかの理由でSetPixelFormatがアルファチャンネル。SetPixelFormatがOpenGL用のアルファチャンネルを作成していない

gDebuggerは、ウィンドウのバックバッファに3つのチャネルしかないことを示しています。

白+ 0アルファは白としてレンダリングされます。

私がやっていたことに本質的に何かが間違っている、または更新がそれを壊しました。

次のコードは、空のVSプロジェクトに貼り付けることができます。

#include <Windows.h> 
#include <dwmapi.h> 
#include <gl/GL.h> 

#pragma comment(lib,"opengl32.lib") 
#pragma comment(lib,"dwmapi.lib") 

HWND hWnd = 0; 
HDC hDC = 0; 
HGLRC hRC = 0; 
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); 

int APIENTRY WinMain(
    HINSTANCE hInstance, 
    HINSTANCE hPrevInstance, 
    LPSTR lpCmdLine, 
    int nCmdShow 
    ) 
{ 
    WNDCLASSEX wcex = {0}; 

    wcex.cbSize = sizeof(WNDCLASSEX); 
    wcex.lpfnWndProc = WndProc; 
    wcex.hCursor  = LoadCursor(NULL, IDC_ARROW); 
    wcex.lpszClassName = TEXT("why_class"); 

    RegisterClassEx(&wcex); 
    // no errors 

    hWnd = CreateWindowEx(
      NULL, 
      TEXT("why_class"), 
      TEXT("why_window"), 
      WS_OVERLAPPEDWINDOW, 
      128,128, 
      256,256, 
      NULL, 
      NULL, 
      hInstance, 
      NULL 
     ); 
    // no errors 

    PIXELFORMATDESCRIPTOR pfd = {0}; 
    pfd.nSize = sizeof(pfd); 
    pfd.nVersion = 1; 
    pfd.dwFlags = PFD_DRAW_TO_WINDOW| 
     PFD_SUPPORT_OPENGL| 
     PFD_DOUBLEBUFFER| 
     PFD_SUPPORT_COMPOSITION; 
    pfd.cColorBits = 32; 
    pfd.cAlphaBits = 8;  // need an alpha channel 
    pfd.cDepthBits = 24; 
    pfd.cStencilBits = 8; 

    hDC = GetDC(hWnd); 
    int i = ChoosePixelFormat(hDC,&pfd); 
    SetPixelFormat(hDC,i,&pfd); 
    // no errors 

    hRC = wglCreateContext(hDC); 
    // no errors 

    wglMakeCurrent(hDC,hRC); 
    // no errors 

    // EDIT: Turn on alpha testing (which actually won't 
    // fix the clear color problem below) 
    glEnable(GL_BLEND); 
    glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA); 

    // EDIT: Regardless of whether or not GL_BLEND is enabled, 
    // a clear color with an alpha of 0 should (or did at one time) 
    // make this window transparent 

    glClearColor(
     0,0,0, // if this is (1,1,1), the window renders 
       // solid white regardless of the alpha 
     0 // changing the alpha here has some effect 
     ); 

    DWM_BLURBEHIND bb = {0}; 
    bb.dwFlags = DWM_BB_ENABLE|DWM_BB_TRANSITIONONMAXIMIZED; 
    bb.fEnable = TRUE; 
    bb.fTransitionOnMaximized = TRUE; 
    DwmEnableBlurBehindWindow(hWnd,&bb); 
    // no errors 

    ShowWindow(hWnd, SW_SHOWNORMAL); 
    UpdateWindow(hWnd); 
    // no errors 

    MSG msg = {0}; 
    while(true){ 
     GetMessage(&msg,NULL,NULL,NULL); 
     if(msg.message == WM_QUIT){ 
      return (int)msg.wParam; 
     } 
     TranslateMessage(&msg); 
     DispatchMessage(&msg); 

     glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); 

     glBegin(GL_TRIANGLES); 
     // this vertex should be transparent, 
     // as it was when I last built this test 
     // 
     // it renders as white 
     glColor4f(1,1,1,0); 
     glVertex2f(0,0); 
     glColor4f(0,1,1,1); 
     glVertex2f(1,0); 
     glColor4f(1,0,1,1); 
     glVertex2f(0,1); 
     glEnd(); 

     SwapBuffers(hDC); 
    } 

    return (int)msg.wParam; 
} 

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) 
{ 
    switch (message) 
    { 
    case WM_DESTROY: 
     { 
      PostQuitMessage(0); 
     }return 0; 
    default: 
     break; 
    } 

    return DefWindowProc(hWnd, message, wParam, lParam); 
} 
+0

「白+アルファは白としてレンダリングされます」もちろん、それは白をレンダリングします。あなたはブレンドをオンにしませんでした。アルファは「透明」を意味しません。それはあなたが何を意味するのかを意味します。したがって、アルファに「透明」を意味させたい場合は、「透明」を意味する_make_を使用する必要があります。一般的に、ブレンドモードを使用します。 –

+0

アルファテストがここになかったことは正直に気付かなかった...私はそれ以前のスクリーンショットを持っていればいいと思うが、フレームバッファに直接レンダリングできるバグに取り組んでいたと思う。私はそれが動作するかどうかを確認するためにアルファテストを有効にしましたが、指示された頂点には影響しませんでした(まだ白をレンダリングしています。しかし私が持っている質問は、私のウィンドウに突然アルファチャンネルがないということです。なぜなら、ウィンドウはプレマルチプルアルファを期待しているように見えます。 – defube

+0

@NicolBolas:私は、OPはウィンドウ構成、すなわち透明なウィンドウに使用されるアルファチャンネルを意味すると思います。 (PFD_SUPPORT_COMPOSITIONフラグセット)。コンポーザーがアルファチャンネルをどのように扱うかにはほとんど影響がありませんが、通常は不透明と見なされます。いくつかのコンポジターは、事前に乗算されたアルファを仮定します。 X11/GLXの同等の例については、https://github.com/datenwolf/codesamples/tree/master/samples/OpenGL/x11argb_opengl_glslを参照してください。 – datenwolf

答えて

0

通常、32ビットの色と8ビットのアルファの両方を持つフレームバッファを取得することはできません。

私はあなたのコードを試していませんが、あなたはブレンドを使用する場合は24

pfd.cColorBits = 24; 
pfd.cAlphaBits = 8; 
+0

MSDNの 'PIXELFORMATDESCRIPTOR'の' cAlphaBits'のドキュメンテーションページに、次のように書いてあります: "各RGBAカラーバッファのアルファビットプレーンの数を指定します。アルファビットプレーンはサポートされていません。アルファチャンネルを取得できないということですか? – JWWalker

+0

@JWウォーカー:私は、その文書が意味するものが何であるか分かりません。 – Bahbar

+0

あなたの答えをありがとう。私は、たとえ全部0(フラグ、バージョン、サイズを除いて)のままにしても、アルファなしの24ビットカラーバッファで終わります。唯一の違いは、私がcAlphaBitsに任意の数値を指定すると、ウィンドウは実際に透明にレンダリングされます(asinineの事前乗算されたアルファナンセンスで)、私はアルファチャンネルにアクセスできません。 – defube

0

に色のビットを切り替えることを示唆している、ちょうど呼び出し:

glEnable(GL_BLEND); 
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 

このためもののへあなたは三角形の裏に何かを混ぜる必要があります(黒い背景は数えません)

+0

黒い背景もカウントされます。半透明の白い四角形をレンダリングして完全に見ることができます。 – Kromster

関連する問題