Sign in to follow this  
GodlyGamr

DIP Problem [SOLVED], Smaller Problem Awaits

Recommended Posts

Hey all, ***SCROLL DOWN FOR NEWER PROBLEM*** I've been attempting to get some 2D graphics displayed using textured quads. Everything seems to be loading fine, but when I display my quad, I only get 1 triangle and it isn't the right size or in the right position.
HRESULT Graphics2D::Init(HWND hwnd, bool windowed){
		
	d3dObject = Direct3DCreate9(D3D_SDK_VERSION);
	if (d3dObject == NULL)
		return E_FAIL;

	D3DPRESENT_PARAMETERS d3dpp; 
    ZeroMemory( &d3dpp, sizeof(d3dpp) );
	d3dpp.BackBufferWidth = 1024;
	d3dpp.BackBufferHeight = 768;
    d3dpp.Windowed = windowed;
    d3dpp.SwapEffect = D3DSWAPEFFECT_FLIP;
    d3dpp.hDeviceWindow = hwnd;
    d3dpp.BackBufferCount = 1;
    d3dpp.BackBufferFormat = D3DFMT_A8R8G8B8;
	d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;

    if( FAILED( d3dObject->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hwnd,
                                      D3DCREATE_HARDWARE_VERTEXPROCESSING, &d3dpp, &d3dDevice ) ) )
    {
        return E_FAIL;
    }

	d3dDevice->SetVertexShader(NULL);
	d3dDevice->SetFVF(D3DFVF_TLVERTEX);
	d3dDevice->CreateVertexBuffer(sizeof(TLVERTEX) * 4, NULL,
								  D3DFVF_TLVERTEX, D3DPOOL_MANAGED, &vertexBuffer, NULL);
	d3dDevice->SetStreamSource(0, vertexBuffer, 0, sizeof(TLVERTEX));
	d3dDevice->SetRenderState(D3DRS_LIGHTING, FALSE);
	d3dDevice->SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE);
	d3dDevice->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
	d3dDevice->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
	d3dDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);

	font -> InitDeviceObjects( d3dDevice );
	font -> RestoreDeviceObjects();

	quad = new TexQuad(this, "rainbowtex.jpg");
	position.left = 64;
	position.right = 128;
	position.top = 64;
	position.bottom = 128;

	return S_OK;
}

IDirect3DTexture9* Graphics2D::LoadTexture(char *fileName)
{
  IDirect3DTexture9 *d3dTexture;
  D3DXIMAGE_INFO SrcInfo;      //Optional

  //Use a magenta colourkey
  D3DCOLOR colorkey = 0xFFFF00FF;

  // Load image from file
  if (FAILED(D3DXCreateTextureFromFileEx (d3dDevice, fileName, 0, 0, 1, 0, 
        D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, D3DX_FILTER_NONE, D3DX_DEFAULT, 
        colorkey, &SrcInfo, NULL, &d3dTexture)))
  {
	MessageBox(NULL, "", "NO TEXTURE", MB_OK);
    return NULL;
  }

  //Return the newly made texture
  return d3dTexture;
}


//Draw a textured quad on the back-buffer
void Graphics2D::BlitD3D (TexQuad* texture, RECT* rDest, D3DCOLOR vertexColour)
{
  TLVERTEX* vertices = texture->getVerticies();

  //Lock the vertex buffer
  vertexBuffer->Lock(0, 0, (void**)&vertices, NULL);

  //Setup vertices
  //A -0.5f modifier is applied to vertex coordinates to match texture
  //and screen coords. Some drivers may compensate for this
  //automatically, but on others texture alignment errors are introduced
  //More information on this can be found in the Direct3D 9 documentation
  vertices[0].colour = vertexColour;
  vertices[0].x = (float) rDest->left - 0.5f;
  vertices[0].y = (float) rDest->top - 0.5f;
  vertices[0].z = 0.0f;
  vertices[0].rhw = 1.0f;
  vertices[0].u = 0.0f + (TEXDIM * texture->getTexRef().animPoint);
  vertices[0].v = 0.0f + (TEXDIM * texture->getTexRef().posNum);

  vertices[1].colour = vertexColour;
  vertices[1].x = (float) rDest->right - 0.5f;
  vertices[1].y = (float) rDest->top - 0.5f;
  vertices[1].z = 0.0f;
  vertices[1].rhw = 1.0f;
  vertices[1].u = TEXDIM + (TEXDIM * texture->getTexRef().animPoint);
  vertices[1].v = 0.0f + (TEXDIM * texture->getTexRef().posNum);

  vertices[2].colour = vertexColour;
  vertices[2].x = (float) rDest->right - 0.5f;
  vertices[2].y = (float) rDest->bottom - 0.5f;
  vertices[2].z = 0.0f;
  vertices[2].rhw = 1.0f;
  vertices[2].u = TEXDIM + (TEXDIM * texture->getTexRef().animPoint);
  vertices[2].v = TEXDIM + (TEXDIM * texture->getTexRef().posNum);

  vertices[3].colour = vertexColour;
  vertices[3].x = (float) rDest->left - 0.5f;
  vertices[3].y = (float) rDest->bottom - 0.5f;
  vertices[3].z = 0.0f;
  vertices[3].rhw = 1.0f;
  vertices[3].u = 0.0f + (TEXDIM * texture->getTexRef().animPoint);
  vertices[3].v = TEXDIM + (TEXDIM * texture->getTexRef().posNum);

  //Unlock the vertex buffer
  vertexBuffer->Unlock();

  //Set texture
  d3dDevice->SetTexture (0, texture->getTexRef().d3dTex);
  //Draw image
  d3dDevice->DrawPrimitive (D3DPT_TRIANGLEFAN, 0, 2);
}



TexQuad::TexQuad(Graphics2D* handle, char* filename)
{
	texRef.d3dTex = handle->LoadTexture("C:\\Programming\\NewGame\\yellow.jpg");
	texRef.posNum = 0;
	texRef.animPoint = 0;
}



Thanks in advance for any help, Jeff [Edited by - GodlyGamr on June 5, 2005 6:18:46 PM]

Share this post


Link to post
Share on other sites
Thanks for the article, streamer, and welcome to gamedev. It was a good read, but my blitd3d function is (almost, not in any way that should cause this behavior) identical to the function in the tutorial I am following. The function works with the sample code from the tutorial, so I'm sure my problem must be elsewhere.

Thanks,
Jeff

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
If only one vertex is being displayed, it might be a backface culling issue.
To find out if this is the problem, try this to turn culling off
d3dDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);

if it solves you problem, it means you need to re-order your vertices, I believe they should go in clockwise order, off course once this is fixed you can turn back face culling back on, although for 2d its not really going to do anything

Share this post


Link to post
Share on other sites
Hmm, i get a bit more displayed..but it definitely still isn't correct. Everything is still displayed in the top left corner no matter the position I give the function and the quad is definitely still not 64x64.

Thanks for the reply,
Jeff

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
I'm not sure what you're trying to do here:

TLVERTEX* vertices = texture->getVerticies();
vertexBuffer->Lock(0, 0, (void**)&vertices, NULL);

The Lock() func is going to point 'vertices' to the vertex buffer, so there is no point in assinging a value to it.

Also, you should check the return code of the lock to make sure it is actually succeeding.

Share this post


Link to post
Share on other sites
Since TLVERTEX does not appear to be a D3D defined structure, yet you are using the defined D3DFVF_TLVERTEX, you should probably show us the structure definition of TLVERTEX to make sure it really agrees with the FVF.

Share this post


Link to post
Share on other sites
agreed. Here is the relevant code.

const DWORD D3DFVF_TLVERTEX = D3DFVF_XYZRHW | D3DFVF_DIFFUSE | D3DFVF_TEX1;

struct TLVERTEX
{
float x;
float y;
float z;
float rhw;
D3DCOLOR colour;
float u;
float v;
};

Share this post


Link to post
Share on other sites
Well, I see a potential problem here. The d3dtypes.h header contains the following define:


#define D3DFVF_TLVERTEX ( D3DFVF_XYZRHW | D3DFVF_DIFFUSE | D3DFVF_SPECULAR | D3DFVF_TEX1 )


Which clearly does not match the layout of your structure. So I'm guessing the compiler is using the macro rather than your const variable for the FVF. Simply try renaming your FVF const so that it does not collide with the macro name.

Share this post


Link to post
Share on other sites
OK, that didn't fix it completely, but it will probably be better off in the long run.

I've just noticed some strange behavior. I added a message box to check if my Lock() function was succeeding (and it is). When I exit the messagebox back to my program, it works fine. However, it's working fine when it has 0 FPS. If I get rid of the messagebox generating code, it stops working again. Also, when the messagebox is there, the program only displays correctly the first run though (presumably because it's the only time it has 0.00 FPS). Perhaps this could be the key to finding the problem.

Thanks,
Jeff

Share this post


Link to post
Share on other sites
OK, OK...I fixed the problem..sorta.

I can get it to display correctly as long as I'm not displaying my FPS. Is there any reason that the Draw() method should be messing up the blitting of the quads?

Thanks,
Jeff

Share this post


Link to post
Share on other sites
Hmmm I had a similar problem, and the bug was that if you have two different calls to font interface with begin and didn't ended the previous one, some things will not show properly.

bugged example:

pDXFont1->Begin();
pDXFont1->DrawTextA(szSomething, -1, &rc1, DT_LEFT, fontColor); //Draw the text

pDXFont2->Begin();
pDXFont2->DrawTextA(szAnotherOne, -1, &rc1, DT_LEFT, fontColor); //Draw the text
pDXFont2->End();

pDXFont1->End();

//
and good one:

pDXFont1->Begin();
pDXFont1->DrawTextA(szSomething, -1, &rc1, DT_LEFT, fontColor); //Draw the text
pDXFont1->End();

pDXFont2->Begin();
pDXFont2->DrawTextA(szAnotherOne, -1, &rc1, DT_LEFT, fontColor); //Draw the text
pDXFont2->End();



Share this post


Link to post
Share on other sites
Could have been, but the CD3DFont interface doesn't have a begin and end function, though I got really excited when I saw that and went "oh, so that's why", haha. Thanks for the reply, though.

Jeff

Share this post


Link to post
Share on other sites
Anyway it is faster if you call 3 line of code than calling CD3DFont::DrawText function. I'm using ID3DXFont* interface because I can calculate the length of the text drawed, and as I said it is faster.

Share this post


Link to post
Share on other sites
Also you can try to put a FPS text draw code before bliting or after...try to figure out why text drawing routine is messing up with blitting routine. And debug mode didn't throw any warnings or errors?

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this