Jump to content

  • Log In with Google      Sign In   
  • Create Account


(solved) Probably stupid question on unsigned int / effect->begin


Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.

  • You cannot reply to this topic
7 replies to this topic

#1 cozzie   Members   -  Reputation: 1408

Like
0Likes
Like

Posted 04 January 2013 - 10:12 AM

Hi,

Can't figure it out, probably something stupid...
I have:

unsigned int *numpasses = new unsigned int[2];		// CLEAN UP!!!	numpasses[0] = 1;									// CLEAN UP!!!	mSkyBoxEffect->Begin(&numpasses[0], D3DXFX_DONOTSAVESTATE);

But in this situation (function within class) I always have only 0 pass for the shader.

Is there a way to pass '1' to the D3DXEFFECT->Begin function without creating the array?

Feels like a waste to create the array of unsigned ints..



Sponsor:

#2 FLeBlanc   Crossbones+   -  Reputation: 3081

Like
2Likes
Like

Posted 04 January 2013 - 10:21 AM

I'm not a DirectX user, but it seems to me from the documentation that it only wants a pointer to an unsigned int so it can return the number of passes needed to do the operation. Surely something like this would work?

 

unsigned int numpasses=1;
mSkyBoxEffect->Begin(&numpasses, D3DXFX_DONOTSAVESTATE);



#3 Paxi   Members   -  Reputation: 178

Like
1Likes
Like

Posted 04 January 2013 - 10:26 AM

In general you write it like this:
UINT numPasses = 0;
mFX->Begin(&numPasses, 0);
....

Like FLEBlanc said, DirectX will fill the variable you are passing in, with the amount of passes.

Edited by Paxi, 04 January 2013 - 10:28 AM.


#4 NightCreature83   Crossbones+   -  Reputation: 2651

Like
0Likes
Like

Posted 04 January 2013 - 10:28 AM

The function you are interested in is actually http://msdn.microsoft.com/en-us/library/windows/desktop/bb205817%28v=vs.85%29.aspx which is effect->BeginPass(1); which actually begins rendering the pass.


Worked on titles: CMR:DiRT2, DiRT 3, DiRT: Showdown, GRID 2, Mad Max

#5 cozzie   Members   -  Reputation: 1408

Like
0Likes
Like

Posted 04 January 2013 - 10:31 AM

Great, thanks for the quick reactions.

Both solutions will work, will get into it.

 

Not sure if BeginPass will do, because then I can't use the flag (D3DXFX_DONOTSAVESTATE);



#6 NightCreature83   Crossbones+   -  Reputation: 2651

Like
0Likes
Like

Posted 04 January 2013 - 06:05 PM

You need to do a begin on the effect first anyway, after that you only want to render pass one of the technique you specify, right? In any case after begin on the effect you need to do a BeginPass anyway to render with a pass in that active technique, read the remarks on both documentation pages.

Generally rendering with D3DXEffect looks like this
unsigned int numberOfPassInActiveEffect = 0;
m_effect->Begin(&numberOfPassInActiveEffect); //This sets the variable to the number of passes this technique has
for (unsigned int counter = 0; counter < numberOfPassInActiveEffect; ++counter)
{
    m_effect->BeginPass(counter);
    //Do pass specific passing of uniforms here
    m_effect->CommitChanges();
    //Do render calls here
    m_effect->EndPass();
}
m_effect->End();

If you only want to render one pass in the current effect instead of looping on all available passes, just activate the pass you are interested in with ID3DXEffect::BeginPass(unsigned int passNumber), and do your rendering.
Worked on titles: CMR:DiRT2, DiRT 3, DiRT: Showdown, GRID 2, Mad Max

#7 cozzie   Members   -  Reputation: 1408

Like
0Likes
Like

Posted 05 January 2013 - 08:01 AM

Thanks, that looks clear.

What I don't understand is why your 'Begin' function has only one parameter, I can use a 2nd using flags, like D3DXFX_DONOTSAVESTATE.

 

What do you mean with pass specific passing of uniforms? (is this setting the vars in the shader)

Like to take this opportunity to improve my frame rendering using shaders.

 

I know do the following each frame (pseudo code):

 

// rendering the meshes

- loop through all effects/shaders

- setup vars for effect: SetTechnique, SetMatrix(viewproj)

- effect->Begin

- loop through all materials

- select the material: SetFloatArrays for effect (MatAmb, MatDiff)

- loop through all meshes

- set the streamsource (vertex and indexbuffer)

- and then:

 

for(unsigned int i=0;i<pD3dscene->mEffectNumPasses[ec];++i)

{

pD3dscene->mEffect[ec]->BeginPass(i);

pD3dscene->mD3dMeshes[oc].RenderAttr(mD3ddev, att, LIST);

++mAttrRendered;

pD3dscene->mEffect[ec]->EndPass();

}

 

Is there anything wrong in this order/ should I set the effect vars after the 'BeginPass'? (functionally it all works)

 

Here the 'cleaned up' code of my renderframe function:

 

 bool CD3d::RenderFrameV2(CD3dscene *pD3dscene, CD3dcam *pCam)
{
	if(!CheckDevice()) { mDeviceLost = true; return true; }
	mObjRendered = 0;	mAttrRendered = 0;
	
	pCam->Update();

	mD3ddev->Clear(0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);
	mD3ddev->BeginScene();

	// WORLD MESHES; SHADER RENDERING
	for(ec=0;ec<pD3dscene->mNrEffects;++ec)
	{
		if(!SetVertexShader(pD3dscene, ec, "BasicShader", pCam)) return false; // Sets Technique and Vieproj matrix
		pD3dscene->mEffect[ec]->Begin(&pD3dscene->mEffectNumPasses[ec], D3DXFX_DONOTSAVESTATE);

		for(mc=0;mc<pD3dscene->mNrMaterials;++mc)
		{
			if(!pD3dscene->PreSelectMaterial(mc, ec)) return false;		// Sets 'MatAmb' and 'MatDiff' in the current 'effect/shader'

			for(oc=0;oc<pD3dscene->mNrD3dMeshes;++oc)
			{
				if(pD3dscene->mD3dMeshes[oc].mEffectIndex == ec) 
				{
					if(pCam->SphereInFrustum(&pD3dscene->mD3dMeshes[oc].mWorldPos,
						pD3dscene->mD3dMeshes[oc].mBoundingRadius))
					{
						if(!pD3dscene->PreSelectMesh(oc, mD3ddev)) return false; // Sets the streamsource, vtx/ index buffers
						for(DWORD att=0;att<pD3dscene->mD3dMeshes[oc].mAttrSize;++att)
						{
							if(pD3dscene->mD3dMeshes[oc].mMatIdPerAttr[att] == mc)
							{
								if(pCam->SphereInFrustum(&pD3dscene->mD3dMeshes[oc].mAttrWorldPos[att], 
									                     pD3dscene->mD3dMeshes[oc].mAttrBoundingRadius[att]))
								{						
									for(unsigned int i=0;i<pD3dscene->mEffectNumPasses[ec];++i)
									{
										pD3dscene->mEffect[ec]->BeginPass(i);
										pD3dscene->mD3dMeshes[oc].RenderAttr(mD3ddev, att, LIST);
										pD3dscene->mEffect[ec]->EndPass();
									}
								}
							}
						}
					}
				}
			}
		}
		pD3dscene->mEffect[ec]->End();
	}

	// SKY BOX; SHADER RENDERING
	if(pD3dscene->mSkyBoxInScene) 
		if(!pD3dscene->mSkyBox.Render(pCam->mPosition, pCam, mD3ddev)) return false;

	// FFP rendering
	if(!SetDefaultRenderStates()) return false;
	mD3ddev->EndScene();
	HRESULT hr = mD3ddev->Present(NULL, NULL, NULL, NULL); 

	return true;
}


#8 cozzie   Members   -  Reputation: 1408

Like
0Likes
Like

Posted 05 January 2013 - 01:51 PM

@nightcreature; I looked it up in MSDN and found the following on CommitChanges():

 

If the application changes any effect state using any of the ID3DXEffect::Setx methods inside of an ID3DXEffect::BeginPass/ID3DXEffect::EndPass matching pair, the application must call ID3DXEffect::CommitChanges before any DrawxPrimitive call to propagate state changes to the device before rendering. If no state changes occur within a ID3DXEffect::BeginPass and ID3DXEffect::EndPass matching pair, it is not necessary to call ID3DXEffect::CommitChanges.

 

This means I don't have toe use it 'today'.

I now do one of two things:

 

1. on initialization setup renderstates

2. ech frame frame render order: A. meshes through shader, states only in shader, no setrenderstates while shade rendering

3. render skybox using shader, setrenderstates, draw using effect, setrenderstates back (cull/ zwrite)

4. draw text using FFP

 

And optional reset RenderStates after step 3, when I use: effect->Begin(numpasses, D3DXFX_DONOTSAVESTATE).

 

In the future it might be usefull to use CommitChanges(), because I need to combine sets of objects within one pass/ effect (now probably unneccessary passes/ loops).

 

This does clear things up, few weeks ago I was trying to combine things within one begin/end of an effect, and ran into the problem that I couldn't change matrices etc, and therefor got back to multiple loops with an effect. Now I know how to do this :) Thanks






Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.



PARTNERS