I was wondering if someone could walk me through drawing a basic hexagon using DirectX 9.0c in C#.
I've been using the Vector3 structure, and I am having problems understanding how to initialize the view transformation matrix for a hexagon, as well as what input vectors will represent the hexagon (understandably 6).
Thank you in advance,
Owen

C# - DirectX 9.0c - Creating a Basic Hexagon
SaranT
A B
C X D
E F
If these are the points of your hexagon then a triangle LIST will have a vertex buffer with 6 triangles - i.e. 18 vertices
Don't forget to keep your triangles veritices wound in the same counter clockwise direction.
so the vertices will be AXB BXD DXF FXE EXC CXA
Triangle strips will be very hard to use because the extra vertex you add each time will not make complete triangles. eg. for vertiex strips you would get the following vertices AXB (counter clockwise) D (clockwise) F (oh dear this means we draw triangle BDF which isn't what we wanted (and is what you are seeing).
The other problem you are seeing is that for a 6 triangle shape you would have 8 vertices in the buffer. You have to specify the entire 1st triangle (3 vertices) then add a vertex for each additional triangle (+5).
So when you have a triangle list working then go and read about triangle fans - that will solve your problem.
TylerDurden
Z-Man,
Thanks for another reply. I've never tried TriangleList, but as I continued to read through your article you mentioned I should move onto TriangleFan following TriangleList.
I was a step ahead, and have already completed the TriangleFan, but I am still stuggling on how to work with TriangleStrips.
I read in another article:
"If I was to render 2500 (50*50) it would result in 2500 Draw calls to the device.. At high hex counts triangle strips were the best by 20-50%, the second best was triangle lists,. So I decided on triangle strips."
I would like to understand how to implement a hex in TriangleStrips. If it's even possible. I understand what you mean by "Triangle strips will be very hard to use because the extra vertex you add each time will not make complete triangles."
In the meantime, I am going back over TriangleLists and will re-implement my Hex arrangement using that technique.
Looking forward to your response.
Owen
yllams
Thanks for your reply Zman,
"Firstly, draw out your hexgon and use some math to calculate the coordinates of the vertices. If you math isn't up to doing this then give up now - it only gets harder with 3d stuff :-)"
Do you have any resources (links) to get me started with calculating these coordinates using a left handed cartesian system I'm would be very interested in making sure I have the groundwork established.
"For a solid hexagon you need to make 6 triangles between these points and the center. Then create a vertex buffer and put the coordinates of the triangles in it. The draw the vertex buffer."
I have been trying to create the vertex buffer, and I have been successful in drawing the first triangle using the msdn tutorial 2: rendering vertices (http://msdn.microsoft.com/archive/default.asp url=/archive/en-us/directx9_m_Summer_04/directx/direct3d/tutorials/tutorial2.asp).
I can't seem to figure out how to add the second triangle; it may just be the math i've been using. I've changed the PrimitiveType to TriangleStrip.
Also, I read that using an IndexBuffer would be more effecient when drawing hexagons, being that there are only 7 points possibilities.
Could you offer me any help on how to output a second triangle
I look forward to your response.
Thank you,
Owen
kokain
I use MathWorld to check any maths-related things - might be worth having a look. Also, if you're serious about spending some time with 3D graphics, a textbook on the *theory* side of things might be a valuable investment. I forget the title, but Eric Lengyel's maths for games and graphics book was pretty good.
Regarding changing the primitive type - be careful with this. Each one of those types has a specific meaning and it'll interpret your vertex data differently. Check out this page in the SDK documentation to see some diagrams and explanations of what each one does.
As for rendering the second triangle... if you're using a triangle list and you've correctly defined 6 triangles then changing the last parameter in the following line from 1 to 6 should do the trick:
device.DrawPrimitives(PrimitiveType.TriangleList, 0, 1);
Yes, Index buffers are a more efficient way of rendering. However, get this first step sorted before you worry about them
hth
Jack
rogermk
Thanks again Zman. I think I'm going to stick with triangle fans based on your suggestion. So i've got the answers I need.
One more quick question, in relation to the code above:
verts[0].Normal=new Vector3(0.0f, 0.0f, -1.0f);
What exactly is the above line doing
Owen
Pzyber
Thanks for your answer Jack. I am using the following Lighting arrangement:
// Lighting
device.Lights[0].Type = LightType.Point;
device.Lights[0].Position = new Vector3();
device.Lights[0].Diffuse = System.Drawing.Color.White;
device.Lights[0].Attenuation0 = 0.2f;
device.Lights[0].Range = 10000.0f;
device.Lights[0].Enabled = true;
Does this mean that the lighting is pointing at the object from position (0,0,-1)
Alex V.
I've made it a little further using the following code.
----------
// Triangle Definition
CustomVertex.PositionNormalColored[] verts = new CustomVertex.PositionNormalColored[7];
verts[0].Position=new Vector3(-5.0f, -5.0f, 1.0f);
verts[0].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[0].Color = System.Drawing.Color.Aqua.ToArgb();
verts[1].Position=new Vector3(0.0f, 5.0f, 1.0f);
verts[1].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[1].Color = System.Drawing.Color.Aqua.ToArgb();
verts[2].Position=new Vector3(5.0f, -5.0f, 1.0f);
verts[2].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[2].Color = System.Drawing.Color.Aqua.ToArgb();
verts[3].Position=new Vector3(10.0f, 5.0f, 1.0f);
verts[3].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[3].Color = System.Drawing.Color.Aqua.ToArgb();
verts[4].Position=new Vector3(5.0f, 15.0f, 1.0f);
verts[4].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[4].Color = System.Drawing.Color.Aqua.ToArgb();
verts[5].Position=new Vector3(-5.0f, 15.0f, 1.0f);
verts[5].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[5].Color = System.Drawing.Color.Aqua.ToArgb();
verts[ 6 ].Position=new Vector3(-10.0f, 5.0f, 1.0f);
verts[ 6 ].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[ 6 ].Color = System.Drawing.Color.Aqua.ToArgb();
// Lighting
device.Lights[0].Type = LightType.Point;
device.Lights[0].Position = new Vector3();
device.Lights[0].Diffuse = System.Drawing.Color.White;
device.Lights[0].Attenuation0 = 0.2f;
device.Lights[0].Range = 10000.0f;
device.Lights[0].Enabled = true;
device.BeginScene();
device.VertexFormat = CustomVertex.PositionNormalColored.Format;
device.DrawUserPrimitives(PrimitiveType.TriangleStrip, 6, verts);
device.EndScene();
------------------------------------------
Take a look at the screen results of the above code: http://hlds2.therubysquare.com/TriangleStrip.gif
Now I am running into another problem, drawing the 2d image so it appears flat to the screen. #1 and #2 look correct, but as of #3, the triangles start to run off on me.
Where am I going wrong
Looking forward to your expertise.
Owen
Schtrudel
The book by Eric Lengyel is very good ( although I do only have the first edition) it provides enough of mathematics and physics to play with for a long time.
Michael (MCPNS)
Thank you for your time Jack. I still am having problems getting the second triangle to appear. I have been using TriangleStrips.
CustomVertex.PositionNormalColored[] verts = new CustomVertex.PositionNormalColored
;
verts[0].Position=new Vector3(0.0f, 1.0f, 1.0f);
verts[0].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[0].Color = System.Drawing.Color.Aqua.ToArgb();
verts[1].Position=new Vector3(-1.0f, -1.0f, 1.0f);
verts[1].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[1].Color = System.Drawing.Color.Black.ToArgb();
verts[2].Position=new Vector3(1.0f, -1.0f, 1.0f);
verts[2].Normal=new Vector3(0.0f, 0.0f, -1.0f);
verts[2].Color = System.Drawing.Color.Purple.ToArgb();
verts[3].Position=new Vector3(0.0f, 1.0f, 1.0f);
verts[3].Color = System.Drawing.Color.Blue.ToArgb();
verts[4].Position=new Vector3(1.0f, -1.0f, 1.0f);
verts[4].Color = System.Drawing.Color.Yellow.ToArgb();
verts[5].Position=new Vector3(2.0f, 0.0f, 1.0f);
verts[5].Color = System.Drawing.Color.YellowGreen.ToArgb();
// Lighting
device.Lights[0].Type = LightType.Point;
device.Lights[0].Position = new Vector3();
device.Lights[0].Diffuse = System.Drawing.Color.White;
device.Lights[0].Attenuation0 = 0.2f;
device.Lights[0].Range = 10000.0f;
device.Lights[0].Enabled = true;
device.BeginScene();
device.VertexFormat = CustomVertex.PositionNormalColored.Format;
device.DrawUserPrimitives(PrimitiveType.TriangleStrip, 2, verts);
device.EndScene();
-------
I am confused as to what the verts[0].Normal=new Vector3(0.0f, 0.0f, -1.0f); call is really doing, but I am at a loss as to how to add them for the following 3 points in the list.
device.DrawUserPrimitives(PrimitiveType.TriangleStrip, 2, verts);As you can see I am using an array for the number of points in the triangle. So I grow the number of points in the array by changing the number in CustomVertex.PositionNormalColored
;
Given this information, could you point me in the right direction If I increase the number in the DrawUserPrimitives int primitiveCount to 6, I get a very odd looking shape.
Thanks again,
Owen
J im Diamond
The view matrix (nor the world or projection) isn't something you change to draw a shape. They change how the shape is drawn to the screen.
Firstly, draw out your hexgon and use some math to calculate the coordinates of the vertices. If you math isn't up to doing this then give up now - it only gets harder with 3d stuff :-)
For the outline of a hexagon use the D3DX line class and draw lines between these points.
For a solid hexagon you need to make 6 triangles between these points and the center. Then create a vertex buffer and put the coordinates of the triangles in it. The draw the vertex buffer.
Mayomano
A vertex normal is a unit vector (length == 1.0) that points in the direction that the vertex is facing (okay, a point shouldn't really have orientation... but hang in there...). The three vertices making up a triangle should have vertex normals, and they can be used to determine what direction the triangle is facing.
This information can then be used to perform lighting operations (to compute the amount of light at a given point on the surface, it's position and direction must be known).
If you're not using lighting yet, I'd advise ignoring it for now :-) I know copy-n-paste programming is a bad idea, but wait until you've got the rest sorted before you jump into lighting...
hth
Jack
sina.ebadi
triangle strips start with 3 vertices to define a triangle. Then each additional vertex uses the previous 2 to complete the triangle.
So triangle string ABCDEF draws triangles ABC BCD CDE DEF notice that the winding switches from clockwise to anitclockwise with each triangle. THis is useful for shapes where the triangles are in a long strip. Try to work out the vertices for your shape and you will find it doesn't work. You will need 3 triangle strips or you will have to introduce redundant vertices.
Triangle fans reusue the last vertex and the first one in the list
So ABCDEF draws triangles ABC ACD ADE AEF
This is most efficient for shapes that have a common center point like your shape.
The only next step would be to use an index buffer, however you have no reusued vertices to the index buffer is just extra memory and an extra lookup. Probably slower.
Billy J
device.Lights[0].Position = new Vector3(x,y,z);
would put the light at x,y,z
the normal you set tells directx which way the triangle is facing at the vertex. This might seem really stupid becuase its pretty obvious with your 2d shape which way its facing. But when you have lots of triangles makind up a curved surface you can make each corner of the triangle face a slightly different way and the lighting looks more realistic.
I *really* suggest you go and get a good book on 3d topics, this thread is going to get very very long if we have to cover every basic topic like normals and lighting and like I said in the first reply its only gets harder and more complex from here.
abwebsvcs
Zman -- I have purchased Tom Millers - Managed DirectX 9.0 (Graphics and Game Programming) and also downloaded the new and updated codeset from your site.
In addition, I have on order some suggestion reading including:
- Math for 3d Game Programming & Computer Graphics -- Eric Lengyel
- Beginning Math and Physics for Game Programmers -- Wendy Stahler
If anyone has some suggestions as to other great resources (books) that I could add to my list, it would be much appreciated.
Your help here has been very much appreciated, and while this thread, and other questions I ask may be rather simplistic for the more experienced programmer, I am really excited to wrap my head around these topics, and I hope there is no better place to do it on the net than here.
Thank you again for all your help and suggestions.
Best Regards,
Owen