Direct3D 10 - Sprites with transparency.

i've been struggling for about 3 days now, i searched almost everywhere possible for an answer but with no luck.
i was reading this book
Thomson - Beginning DirectX 10 Game Programming
it looks really promising, but i'm stuck with sprites a little.

i managed to make the picture in Photoshop CS6 with alpha channel, i checked the picture in a hex editor and made sure that alpha channel is sat properly.
problem is: the picture isn't transparent.
i tried different combinations for blending effect, some times, the transparent pixels of the sprite overwrite everything underneath it.
the current code posted below produces a sprite that isn't transparent at all.



here's part of the InitializeDirect3D() that i created:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
//   . . .
// set the sprite members :
{
	// we'll be using this identifier heavily in this part.
	// so let's remove its full qualification name in here:
	using global::D3DX10_Sprite;


	// determine the colod modulate:
	D3DX10_Sprite.ColorModulate = ::D3DXCOLOR ( 1.0f , 1.0f , 1.0f , 1.0f ); // white color
		

	// set the shader-resource-view texture to be used by this sprite:
	D3DX10_Sprite.pTexture = global::p_D3D10_ShaderResourceView ;

	// top-left location of the sprite:
	D3DX10_Sprite.TexCoord.x = 0.0f;
	D3DX10_Sprite.TexCoord.y = 0.0f;

	// Determine the texture size in U,V coordinates:
	D3DX10_Sprite.TexSize.x = global::BirdSizeH;
	D3DX10_Sprite.TexSize.y = global::BirdSizeV;

	// the texture index.
	// the texture isn' an array, so this value must be 0:
	D3DX10_Sprite.TextureIndex = 0U;

	// create the sprite object in order to create the projection matrix:
	hr = ::D3DX10CreateSprite( global::p_D3D10_Device , 0 , & global::p_D3DX10_SpriteObject );

	if( FAILED(hr) )
		return false;

	// create the projection matrix:
	::D3DXMATRIX ProjectionMatrix ;
	ZeroMemory( &ProjectionMatrix , sizeof(ProjectionMatrix) );

	// set the projection matrix:
	::D3DXMatrixOrthoOffCenterLH(
		& ProjectionMatrix,
		(float)vp.TopLeftX , (float)vp.Width,
		(float)vp.TopLeftY , (float)vp.Height,
		0.f , 10.f);

	hr = global::p_D3DX10_SpriteObject->SetProjectionTransform( & ProjectionMatrix);

	if( FAILED(hr))
		return false;

	// create the scaling and translation matrices:
	D3DXMatrixTranslation	( & global::TranslationMatrix , global::SpritePosX , (global::height - global::SpritePosY) , 1.0f );
	D3DXMatrixScaling		( & global::ScalingMatrix , global::SpriteWidth , global::SpriteHeight , 1.0f );

	// the world matrix:
	D3DX10_Sprite.matWorld = (global::ScalingMatrix * global::TranslationMatrix );

}

{
		// Initialize the blend state for alpha blending
	D3D10_BLEND_DESC StateDesc;
	ZeroMemory(&StateDesc, sizeof(StateDesc));
	StateDesc.AlphaToCoverageEnable = false;
	StateDesc.BlendEnable[0] = true;

	StateDesc.SrcBlend			= D3D10_BLEND_SRC_ALPHA;
	StateDesc.DestBlend			= D3D10_BLEND_INV_SRC_ALPHA;
	StateDesc.BlendOp			= D3D10_BLEND_OP_ADD;

	StateDesc.SrcBlendAlpha		= D3D10_BLEND_ZERO;
	StateDesc.DestBlendAlpha	= D3D10_BLEND_ZERO;
	StateDesc.BlendOpAlpha		= D3D10_BLEND_OP_ADD;
		
		
	StateDesc.RenderTargetWriteMask[0] = D3D10_COLOR_WRITE_ENABLE_ALL ;

	hr = global::p_D3D10_Device->CreateBlendState(&StateDesc, & global::pBlendState10);
	if( FAILED(hr) )
		return false;
}
//   . . . 


here's the rendering function:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
FLOAT NewBlendFactor[4] = {1.f,1.f,1.f,1.f};
UINT old_mask = NULL;
FLOAT old_factor[4] = {NULL};
::ID3D10BlendState * old_state = NULL;
global::p_D3D10_Device->OMGetBlendState( & old_state , old_factor , & old_mask ); 
global::p_D3D10_Device->OMSetBlendState( global::pBlendState10 , NewBlendFactor , 0xffffffff);
HRESULT hr = S_OK;

// clear the current image with the desired color:
global::p_D3D10_Device->ClearRenderTargetView( 
	global::p_D3D10_RenderTargetView , global::ClearColor );

// perform any drawing operations here:

//get the descriptor of the global texture bitmap:
D3D10_TEXTURE2D_DESC TexDesc = {NULL};
global::p_D3D10_Texture2D->GetDesc(&TexDesc);


// define the region to be opied from the source texture:
// in this case, the whole image.
::D3D10_BOX srcRegion = {NULL};
srcRegion.left = 0;
srcRegion.right = TexDesc.Width;
srcRegion.top = 0;
srcRegion.bottom = TexDesc.Height;
srcRegion.front = 0;
srcRegion.back = 1;


// copy that desired part of the source texture to the back buffer:
global::p_D3D10_Device->CopySubresourceRegion(
	global::pBackBuffer,
	0 , 200 , 150 , 0 ,
	global::p_D3D10_Texture2D,
	0 , &srcRegion);


// draw the sprite object:

hr = global::p_D3DX10_SpriteObject->Begin(::D3DX10_SPRITE_SORT_TEXTURE);
if(FAILED(hr))
	return;

hr = global::p_D3DX10_SpriteObject->DrawSpritesBuffered( & global::D3DX10_Sprite , 1 );
if( FAILED(hr) )
	return;

hr = global::p_D3DX10_SpriteObject->Flush();
if( FAILED(hr) )
	return;

hr = global::p_D3DX10_SpriteObject->End();
if( FAILED(hr) )
	return;

global::p_D3D10_Device->OMSetBlendState( old_state , old_factor , old_mask);

// flip page the back buffer of the swap chain:
hr = global::p_DXGI_SwapChain->Present(0,0);
if( FAILED(hr) )
	return;


some site posted this equation and claims that this is the equation the the output merger evaluates to get the final pixel color:
final_color = ( src_color * blend_src ) blend_op ( dest_color * blend_dest )
is this equation true ?
if so, then the blend description posted in the code above should do the desired effect, but it's not doing any transparency at all.
all i see is two rectangular fully-opaque images.

i'm really desperate,i just want a picture that is fully transparent in some parts and fully opaque in all other parts.
please guys, i can't find any thing on this question.
at least, give me guides/links/books/tutorials on how to make a 2D game with DirectX...
Sorry I don't know anything about using DirectX of any version; however, you might try checking your return codes and post a message somewhere when FAILED() returns true.

Sorry if this was a lame suggestion, but I hope you find the answer. I see lots of discussion out there about this.
I'm in the same boat as kooth, but I'm pretty sure it has to do with your "alpha color". I think that you need to define the alpha color that you want to use, it doesn't have anything to do with a a pic with an alpha from photoshop. You need to tell your program that you don't want to draw pure black, or other common alphas are hot pink or bright red. I have no idea what Photoshop sets their alpha color to. I ran a google search for "Directx Alpha Mask Tutorial" and this one seemed like a good explanation. http://www.two-kings.de/tutorials/dxgraphics/dxgraphics10.html... Again, I don't have experience in DirectX so I'm not sure how good the tutorial actually is, just that it covers your problem and it's not too long winded.
Another bit of reading says that if you are using DirectX11 instead of 9 then you should be using "Shaders". I'll leave it to you to look that up if the tutorial fails you.

Last edited on
thanks guys, for even caring to take a look at the post.
the reason i asked in the first place is because, this same question (exactly the same) has been asked so many times and no one ever answered it, you can do a Google search and see how many people have already had the same problem as mine.

however, just a about an hour ago i found an answer to this question(i've been searching for days though :P), and the favor goes to Bobby Anguelov in his tutorial that comes with source code:
http://takinginitiative.wordpress.com/2010/04/09/directx-10-tutorial-6-transparency-and-alpha-blending/

after looking at that code, i found he was using a PNG image not a bitmap, i went back to my own project and converted my same image to a PNG and it worked like magic.

transparency worked with Direct2D, yet Direct3D didn't work well with those transparent PNGs.

i'm just gonna have to research in this topic some more, and maybe i can get it to work on Direct3D as well.

after i find the convenient answer, i shall go search for all those un-answered threads and give them the right answer so that any new-comer to DirectX can avoid this nonsense i struggled in.

again, thanks for noticing this thread, it's now officially closed.
Topic archived. No new replies allowed.