以下是我正在使用的代码,当我尝试检查FX文件中的可用Tenique时发生错误。我不确定FX文件是否损坏或什么。我正在使用DirectX随附的默认simple.fx

// Include the basic Windows header files and the Direct3D header file
#include <windows.h>
#include <windowsx.h>
#include <d3d9.h>
#include <d3dx9.h>

// Define the screen resolution and keyboard macros
#define SCREEN_WIDTH 640
#define SCREEN_HEIGHT 480
#define KEY_DOWN(vk_code) ((GetAsyncKeyState(vk_code) & 0x8000) ? 1 : 0)
#define KEY_UP(vk_code) ((GetAsyncKeyState(vk_code) & 0x8000) ? 0 : 1)

// Include the Direct3D library files
#pragma comment (lib, "d3d9.lib")
#pragma comment (lib, "d3dx9.lib")

// Global declarations
LPDIRECT3D9 d3d;    // The pointer to our Direct3D interface
LPDIRECT3DDEVICE9 d3ddev;    // The pointer to the device class

// Mesh declarations
LPD3DXMESH meshTeapot;    // Define the mesh pointer

// effect declarations
LPD3DXEFFECT effect;    // Define the effect pointer
D3DXHANDLE technique;    // Define the handle for the best technique

// Function prototypes
void initD3D(HWND hWnd);    // Sets up and initializes Direct3D
void render_frame(void);    // Renders a single frame
void cleanD3D(void);    // Closes Direct3D and releases memory
void init_graphics(void);    // 3D declarations

// The WindowProc function prototype
LRESULT CALLBACK WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);

// The entry point for any Windows program
int WINAPI WinMain(HINSTANCE hInstance,
               HINSTANCE hPrevInstance,
               LPSTR lpCmdLine,
               int nCmdShow)
{
    HWND hWnd;
    WNDCLASSEX wc;

    ZeroMemory(&wc, sizeof(WNDCLASSEX));

    wc.cbSize = sizeof(WNDCLASSEX);
    wc.style = CS_HREDRAW | CS_VREDRAW;
    wc.lpfnWndProc = (WNDPROC)WindowProc;
    wc.hInstance = hInstance;
    wc.hCursor = LoadCursor(NULL, IDC_ARROW);
    wc.lpszClassName = L"WindowClass";

    RegisterClassEx(&wc);

    hWnd = CreateWindowEx(NULL, L"WindowClass", L"Our Direct3D Program",
                          WS_EX_TOPMOST | WS_POPUP, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT,
                          NULL, NULL, hInstance, NULL);

    ShowWindow(hWnd, nCmdShow);

    // Set up and initialize Direct3D
    initD3D(hWnd);

    // Enter the main loop:

    MSG msg;

    while(TRUE)
    {
        DWORD starting_point = GetTickCount();

        if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
        {
            if (msg.message == WM_QUIT)
                break;

            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }

        render_frame();

        // Check the 'escape' key
        if(KEY_DOWN(VK_ESCAPE))
            PostMessage(hWnd, WM_DESTROY, 0, 0);

        while ((GetTickCount() - starting_point) < 25);
    }

    // Clean up DirectX and COM
    cleanD3D();

    return msg.wParam;
}


// This is the main message handler for the program
LRESULT CALLBACK WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
    switch(message)
    {
        case WM_DESTROY:
        {
            PostQuitMessage(0);
            return 0;
        }
        break;
    }

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


// This function initializes and prepares Direct3D for use
void initD3D(HWND hWnd)
{
    d3d = Direct3DCreate9(D3D_SDK_VERSION);

    D3DPRESENT_PARAMETERS d3dpp;

    ZeroMemory(&d3dpp, sizeof(d3dpp));
    d3dpp.Windowed = TRUE;
    d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
    d3dpp.hDeviceWindow = hWnd;
    d3dpp.BackBufferFormat = D3DFMT_X8R8G8B8;
    d3dpp.BackBufferWidth = SCREEN_WIDTH;
    d3dpp.BackBufferHeight = SCREEN_HEIGHT;
    d3dpp.EnableAutoDepthStencil = TRUE;
    d3dpp.AutoDepthStencilFormat = D3DFMT_D16;

    // Create a device class using this information and the information from the d3dpp stuct
    d3d->CreateDevice(D3DADAPTER_DEFAULT,
                      D3DDEVTYPE_HAL,
                      hWnd,
                      D3DCREATE_SOFTWARE_VERTEXPROCESSING,
                      &d3dpp,
                      &d3ddev);

    init_graphics(); // Call the function to initialize the triangle

    LPD3DXBUFFER errorlog; // For storing errors

    // Load the effect file
    D3DXCreateEffectFromFile(d3ddev, L"simple.fx", 0, 0, 0, 0, &effect, &errorlog);

    // Find the best technique
    effect->FindNextValidTechnique(NULL, &technique);

    return;
}

// This is the function used to render a single frame
void render_frame(void)
{
    d3ddev->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);
    d3ddev->Clear(0, NULL, D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);

    d3ddev->BeginScene();

    // Set the view transform
    D3DXMATRIX matView;    // The view transform matrix
    D3DXMatrixLookAtLH(&matView,
    &D3DXVECTOR3 (0.0f, 3.0f, 6.0f),    // The camera position
    &D3DXVECTOR3 (0.0f, 0.0f, 0.0f),    // The look-at position
    &D3DXVECTOR3 (0.0f, 1.0f, 0.0f));    // The up direction
    effect->SetMatrix("View", &matView);

    // Set the projection transform
    D3DXMATRIX matProjection;    // The projection transform matrix
    D3DXMatrixPerspectiveFovLH(&matProjection,
                               D3DXToRadian(45),    // The horizontal field of view
                               (FLOAT)SCREEN_WIDTH / (FLOAT)SCREEN_HEIGHT, // Aspect ratio
                               1.0f,    // The near view-plane
                               100.0f);    // The far view-plane
    effect->SetMatrix("Projection", &matProjection);

    // Set the world transform
    static float index = 0.0f; // An ever-increasing float value
    index+=0.03f;
    D3DXMATRIX matRotateY;    // A matrix to store the rotation for each triangle
    D3DXMatrixRotationY(&matRotateY, index); // The rotation matrix
    effect->SetMatrix("World", &matRotateY);

    effect->Begin(NULL, NULL);    // Begin using the effect
    effect->BeginPass(0);    // Begin the pass

    // Render whatever
    meshTeapot->DrawSubset(0);

    effect->EndPass(); // End the pass
    effect->End();    // End the effect

    d3ddev->EndScene();

    d3ddev->Present(NULL, NULL, NULL, NULL);

    return;
}

// This is the function that cleans up Direct3D and COM
void cleanD3D(void)
{
    meshTeapot->Release();    // Close and release the teapot mesh
    effect->Release();    // Close and release the effect
    d3ddev->Release();    // Close and release the 3D device
    d3d->Release();    // Close and release Direct3D

    return;
}

// This is the function that puts the 3D models into video RAM
void init_graphics(void)
{
    D3DXCreateTeapot(d3ddev, &meshTeapot, NULL);    // Create the teapot

    return;
}

最佳答案

我想您已经从www.directxtutorial.com复制了代码。我有同样的问题。
您应该跟踪Effect编译器向您抛出的错误。将errorlog变量转换为字符串,以便正确读取错误:

char * Error = (char *)errorlog->GetBufferPointer();


您得到的第一个错误是:


  错误X3539:不再支持ps_1_x;在fxc中使用/ Gec自动升级到ps_2_0


似乎不支持ps_1_x。因此,如果打开simple.fx文件,则应该找到以下内容:

PixelShader = compile ps_1_1 PS();


ps_1_1更改为ps_2_0,所有内容都应像超级按钮一样运行。

我忘了提一下,如果错误日志不为NULL,则只应尝试从错误日志中获取缓冲区指针,因此:

if(errorlog)
{
    char * Error = (char *)errorlog->GetBufferPointer();
    // And do the output somewhere
}

关于c++ - 使用C++的Direct X,在我的FX文件中找到一种技术时,我收到访问冲突,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/9914889/

10-14 09:08