Page 1 of 2

openGL draws it but DirectX not

Posted: Thu Dec 07, 2006 8:27 pm
by jAyTeA
Hi,

i have a very basic custom scenenode, that draws a rectangle in front of the camera with some basic calculations. I use it to make a fast and basic bloom-effect (I have found the idea in this forum, but it just worked with FPS-cameras).

My problem is, that directX don't draws this rectangle, if the camerarotation is between two particular angles. When i render with openGL the rectangle is drawn always.
Here are 2 pictures of it:
first the one with the bloom:
Image
and then the one without:
Image

I hope you see the difference.

and some code of the scenenode:

Code: Select all

CQuadSceneNode::CQuadSceneNode(scene::ISceneNode* parent,scene::ISceneManager* mgr,s32 id): scene::ISceneNode(parent, mgr, id)
{
	Material.DiffuseColor = video::SColor(200,200,200,200);
	Material.EmissiveColor = video::SColor(200,200,200,200);
	Material.SpecularColor = video::SColor(200,200,200,200);
	Material.ZBuffer = false;
	Material.Wireframe = false;
	Material.PointCloud = false;
	Material.Lighting = false;
	Material.BackfaceCulling = false;
	Material.FogEnable = false;
	Material.GouraudShading = false;
	Material.NormalizeNormals = true;
	Material.MaterialType = video::EMT_TRANSPARENT_VERTEX_ALPHA;

	irr::video::E_DRIVER_TYPE dr = mgr->getVideoDriver()->getDriverType();

	if (dr != video::EDT_OPENGL)
	{
		video::SColor Color = video::SColor(4,40,40,40);
		VertexQuad[0]=video::S3DVertex(-1,1,1,0,0,0,Color,0,0);
		VertexQuad[1]=video::S3DVertex(1,1,1,0,0,0,Color,1,0);
		VertexQuad[2]=video::S3DVertex(-1,-1,1,0,0,0,Color,0,1);
		VertexQuad[3]=video::S3DVertex(1,-1,1,0,0,0,Color,1,1);
	}
	else
	{
		video::SColor Color = video::SColor(4,34,34,34);
		VertexQuad[0]=video::S3DVertex(-1,1,0,0,0,0,Color,0,0);
		VertexQuad[1]=video::S3DVertex(1,1,0,0,0,0,Color,1,0);
		VertexQuad[2]=video::S3DVertex(-1,-1,0,0,0,0,Color,0,-1);
		VertexQuad[3]=video::S3DVertex(1,-1,0,0,0,0,Color,1,-1);
	}

	Box.reset(VertexQuad[0].Pos);

	for (s32 i=1; i<4; ++i)
	{
		Box.addInternalPoint(VertexQuad[i].Pos);
	}
}

void CQuadSceneNode::OnPreRender()
{
	if (IsVisible)
		SceneManager->registerNodeForRendering(this, ESNRP_TRANSPARENT);
	ISceneNode::OnPreRender();
}

void CQuadSceneNode::render()
{
	u16 indices[] = {	0,1,2, 3,2,1	};
	video::IVideoDriver* driver = SceneManager->getVideoDriver();

	vector3df vCamPos = SceneManager->getActiveCamera()->getPosition();
	vector3df vPlayerPos = SceneManager->getActiveCamera()->getTarget();
	vector3df vCamPlayer = (vPlayerPos-vCamPos);

	vector3df vNormal1 = vector3df(0,1,0).crossProduct( vCamPlayer ).normalize();
	vector3df vNormal2 = vNormal1.crossProduct( vCamPlayer ).normalize()*3/4;
	vector3df vTempPoint = vCamPos + (vCamPlayer.normalize())*1.01;

	VertexQuad[0].Pos = vTempPoint - vNormal1 - vNormal2;
	VertexQuad[1].Pos = vTempPoint + vNormal1 - vNormal2;
	VertexQuad[2].Pos = vTempPoint - vNormal1 + vNormal2;
	VertexQuad[3].Pos = vTempPoint + vNormal1 + vNormal2;

	driver->setMaterial(Material);
	driver->drawIndexedTriangleList(&VertexQuad[0], 4, &indices[0], 2);
}
I hope this is enough information.

Posted: Thu Dec 07, 2006 9:17 pm
by omar shaaban
the 2 pictures for me are the same!!

Posted: Thu Dec 07, 2006 9:45 pm
by jAyTeA
yes, its really hard to see, but the first one is brighter. you can see that at the sky.
I should try to make it brighter and replace the pictures. But the pictures are just to show, that at one point the rectangle is drawn correct but at another point nearby its not.


EDIT: I have uploaded a new bloom-picture with very exaggerated bloom, so now you should see a difference.

Posted: Fri Dec 08, 2006 12:32 am
by BastetFurry
Please, mark what you want to show us with paint or something.
To me both pics are the same sans more brightness in the upper one.

Posted: Fri Dec 08, 2006 8:11 am
by goaty
I've illustrated this before with OpenGL rendering working, but not DirectX. I found it with using billboard colourisations, as in the OpenGL renderer coloured the billboards on command, but the DirectX didn't perform the same results to the command. See unresolved thread on billboard colourisation.

Posted: Fri Dec 08, 2006 8:48 am
by bgsteffens
Bastet: The difference -is- the brightness. He's trying to simulate a rendering effect by alpha-blending an image over the entire doublebuffer before flipping it to the screen.

Posted: Fri Dec 08, 2006 1:44 pm
by jAyTeA
@goaty: yes, i have seen this thread, but my problem is, that directX draws it in most cases but when the camara goes in a specific position behind the box it doesn't render.
The zone where it doesn't draw seems to be a (filled) circle (the camera can fly around the box in a specific distance).

@bgsteffens: yes, thats exactly what i want to do!

Posted: Fri Dec 08, 2006 2:23 pm
by goaty
jAyTeA : Ahhhhhh you're right. If I view it from the opposite direction using ths FPS camera, they are coloured as you would expect. So it must be the drawing direction of the create billboard node. How can the node be flipped the other way then?

Posted: Fri Dec 08, 2006 4:30 pm
by jAyTeA
just deaktivate BackfaceCulling in the billboards material.

But i don't use billboards so there must be a problem with the renderer.

Posted: Sat Dec 09, 2006 6:35 pm
by goaty
And how is that done?

Posted: Sat Dec 09, 2006 6:58 pm
by vitek
At the very least you should probably be setting the world transformation matrix. If you are actually going to do a post processing effect [via render-to-texture], I don't think you want this thing to be a scene node in the graph, otherwise you need to hide when rendering the scene, and then you would manually render it later.

Travis

Posted: Sat Dec 09, 2006 11:26 pm
by jAyTeA
@goaty: just call pSceneNode->getMaterial(0).BackfaceCulling = false;

@vitek: I don't know what you exactly mean. When should I set the transformation matrix? This scenenode is drawn after all other things.
Please explain what you would do.

Posted: Mon Dec 11, 2006 11:54 am
by goaty
thankz for the response, but I tried that and it still didnt work. But as I said previously, it still works on the reverse?!?!??!? :cry:

Posted: Mon Dec 11, 2006 4:28 pm
by vitek
When should I set the transformation matrix? This scenenode is drawn after all other things.
You should set the transformation matrices before you call drawIndexedTriangleList().

You can simplify your code a bit by setting the world, view and projection matrices to identity and just rendering a quad from (-1,-1) to (1,1). You still have to disable lighting, but that should simplify your render logic a bit.

Travis

Posted: Mon Dec 11, 2006 5:23 pm
by jAyTeA
@goaty: hmm, then i really don't know. sorry!

@vitek: Thanks very much!! with the identitymatrices it looks much better!

But the problem with directX not drawing it correct is still there. This is really strange. I don't have any idea, where the problem could be. There must be a problem in the directX-piece of the engine. It works fine with openGL, but directX 9 and 8.1 have this problem.