Search Home Members Contacts
About Us
Products
Downloads
Community
Support
Pages: [1]
  Print  
Author Topic: Building a mesh with AddFace/AddVertex that is smooth?  (Read 10431 times)
GPS
Community Member
*
Posts: 30


« on: March 23, 2005, 09:09:17 AM »

OK, time for me to ask a question. I've done some searching in the forum, but nothing productive yet.

Is there a way to build a mesh in code from tris that will share vertices so it will smooth shade? For example, just building a simple cylinder so the resulting tubular mesh is smooth shaded, not faceted?

Thanks,

GPS
Logged
Csakip
Community Member
*
Posts: 1008


« Reply #1 on: March 24, 2005, 04:26:51 PM »

I haven't tested it myself but as far as I know it will be smooth. If you want faceted then you have to create one vertex at the same place for each face.
Logged

CsakiP
Vuli
Customers
Community Member
*****
Posts: 407


« Reply #2 on: March 25, 2005, 09:00:36 PM »

This Tutorial plus many more have been added to TV3D WIKI
http://wiki.truevision3d.com/


Hi

Yes, there is a way.
You do know that there is also a built in CreateCylinder function.

If you really want to create a custom one here it is.

First a little theory
(First I am going to bore you to death and then I am going to give you the code Smiley ):

You can generate any geometric primitive or surface that can be mathematically
described (cube, cone, pyramid, torus, cylinder, sphere …). If the shape you want
can not be parameterized (i.e. Doom 3 character) you’ll need something like 3DMax
or Milkshape (or even better, create your own 3D modeler Smiley ).

With TV3D / DirectX you can create several different primitive types

TV_TRIANGLESTRIP
TV_TRIANGLELIST
TV_LINELIST
TV_LINESTRIP
TV_POINTLIST
TRIANGLE_FAN - Not available in TV6.2 (You’ll have to wait for TV6.5)

First two are obviously good for solid geometry creation.


TV_TRIANGLELIST is good for creating faceted surfaces
since each triangle has 3 unique vertices and 3 unique normal vectors.

TV_TRIANGLESTRIP is good for creating smooth surfaces
since DirectX treats triangle list as one large polygon with multiple triangles.
It also uses fewer vertexes.


There are benefits to using one over another, but I am not going to get into that.
More info on primitive types:
Link: Which primitive types (strips, fans, lists and so on) should I use?
Link: Primitive Types

Look at the cylinder bellow. If you cut it along the red line and open it up,
you get a very simple rectangle. That rectangle/polygon is very similar to
above definition of triangle strip. A third picture bellow applies the triangle
strip to the rectangle.


Just make sure vertices are added in a clockwise order (i.e. V1 – V2 – V3).
Now, the tricky part is to do all this while going in a circle. This is where cylinder
parametric equations come in handy.
More info on cylinder:
Link: Parameterization of Cylinder

Cylinder Parametric equations:

X=R*COS(Theta)
Y=Y
Z=R*SIN(Theta)

Or in our case:

X=R*COS(Theta)
Y=H
Z=R*SIN(Theta)

H – Height
R – Radius
Theta – Angular increment (from 0 – 360 deg or 0 – 2PI rad)


Code:
Public Sub Cylinder(Radius As Single, Height As Single, Sides As Single)

    Dim Theta As Single 'Current Angle
    Dim Inc As Single 'Angular increment
    Dim x As Single 'x coord
    Dim y As Single 'y coord
    Dim z As Single 'z coord
    Dim i As Integer

    Mesh.SetPrimitiveType TV_TRIANGLESTRIP

    'Cylinder Precision
    Inc = 2 * PI_ / Sides 'where each side has two triangles
       
    Theta = 0
   
    For i = 0 To Sides
       
        'Calculate Vertices
        x = Radius * Cos(Theta)
        y = Height
        z = Radius * Sin(Theta)
       
        'Vertex at the top of the cylinder
        Mesh.AddVertex x, 0, z, 0, 0, 0
        'Vertex at the bottom of the cylinder
        Mesh.AddVertex x, y, z, 0, 0, 0


        Theta = Theta + Inc
   
    Next

End Sub


Run the above code using these parameters
Cylinder (40, 40, 30)
30 sides give us 30*2 triangles and 30*2 + 2 vertices

This is what you get:



You can not really see anything since we did not generate any normals.
Switch to wireframe to get a better view ( Scene.SetRenderMode TV_LINE )



Normals are unit vectors that define the angle between the surface and the light.
Look at the picture bellow for the cylinder normals.
First drawing shows the side view.
To get a nice light on your cylinders surface normals should be perpendicular to that surface.
Second drawing shows the top view.
If you want the edges to disappear you have to tell your light to “bounce” directly
off the edge(s).



Keep in mind one thing, vertex normals are not really on the vertex like the image above shows.
In the image bellow there are 3 identical vectors where the blue one is the “real” normal vector.

Obviously, normal vectors (normals) for vertices on top of the cylinder are identical to
the ones at the bottom (you cut normals calculations by 50%).

The same deal for the top view. Red normal vectors are just representations of real normal vectors (blue)

There is lot of different ways to calculate vertex normals. This one seams to be good
for the cylinder.
My explanations here are not particularly good nor in depth. You have 2 links bellow
where people did a much better job.

More info on normals:
Link: Normals
Link: Vertex Normals

Back to coding.
As you can see in the above images normals have exactly the same
cords as the vertices (minus the y coord).

N.x = X= R*COS(Theta)
N.y = Y= 0
N.z = Z=R*SIN(Theta)

Code:

Public Sub Cylinder(Radius As Single, Height As Single, Sides As Single)

    Dim Theta As Single 'Current Angle
    Dim Inc As Single 'Angular increment
    Dim x As Single 'x coord
    Dim y As Single 'y coord
    Dim z As Single 'z coord
    Dim i As Integer
    Dim n As D3DVECTOR ‘vertex normal

    Mesh.SetPrimitiveType TV_TRIANGLESTRIP

    'Cylinder Precision
    Inc = 2 * PI_ / Sides ‘where each side has two triangles
       
    Theta = 0
   
    For i = 0 To Sides
       
        ‘Calculate Vertices
        x = Radius * Cos(Theta)
        y = Height
        z = Radius * Sin(Theta)

        'Make sure you normalize vertex cords to get proper normals
        TVVec3Normalize nv, Vector(x, 0, z)
       
        'Vertex at the top of the cylinder
        Mesh.AddVertex x, 0, z, 0, 0, 0, n.x, n.y, n.z
        'Vertex at the bottom of the cylinder
        Mesh.AddVertex x, y, z, 0, 0, 0, n.x, n.y, n.z

        Theta = Theta + Inc
   
    Next

End Sub


Run the above code using the same parameters again
Cylinder (40, 40, 30)

This is what you get:


Next step is to apply a texture to it.
To apply texture you’ll have to figure out UV coordinates.

Quote
U and V coordinates are just a way to talk about which pixel should be used in a
texture map, independent of how big the texture map finally turns out to be.
If U and V are 0.25 and 0.5 for a given vertex in your model, and the texture
map is 512 by 512, the pixel at 128,256 will be applied to the vertex


In general, UV coordinates range between 0 and 1.
See the sample image bellow


What UV (1, 1) really means is UV (100% of texture width, 100% of texture height)
or UV (0.5, 1) really means is UV (50% of texture width, 100% of texture height).

So, in the case of cylinder we open it up again to get a rectangle.

UV1=UV(0,0)
UV2=UV(0,1)
UV3=UV(1,1)
UV4=UV(1,0)



This is fine except we have applied UV cords to corner vertices only.
Next image shows triangle strip applied to textured rectangle.
There are 12 vertices (6 on top and 6 on bottom),
10 triangles and 5 sides (2 triangles per side).
6 vertices (top and bottom) are evenly spaced,
so the step between U cords is 1/Sides = 1/5.



…And once again the code:

Code:

Public Sub Cylinder(Radius As Single, Height As Single, Sides As Single)

    Dim Theta As Single 'Current Angle
    Dim Inc As Single 'Angular increment
    Dim x As Single 'x coord
    Dim y As Single 'y coord
    Dim z As Single 'z coord
    Dim i As Integer
    Dim n As D3DVECTOR 'vertex normal
    Dim tu As Single ‘U coord
    Dim tv As Single ‘V coord
    Dim UStep as Single 'step between U coords

    Mesh.SetPrimitiveType TV_TRIANGLESTRIP

    'Cylinder Precision
    Inc = 2 * PI_ / Sides 'where each side has two triangles
       
    Theta = 0 ‘Initial value

    UStep=1/Sides

    tu=0 ‘Initial value
   
    For i = 0 To Sides
       
        'Calculate Vertices
        x = Radius * Cos(Theta)
        y = Height
        z = Radius * Sin(Theta)
       
        'Make sure you normalize vertex cords to get proper normals
        TVVec3Normalize n, Vector(x, 0, z)
       
        'Vertex at the top of the cylinder
        ‘tv value is always 1for top vertices
        Mesh.AddVertex x, 0, z, 0, tu, 1, n.x, n.y, n.z

        'Vertex at the bottom of the cylinder
       ‘tv value is always 0 for bottom vertices
        Mesh.AddVertex x, y, z, 0, tu, 0, n.x, n.y, n.z

        Theta = Theta+ Inc
       
        tu = tu + UStep
   
    Next

End Sub


Run the above code (once again) using the same parameters
Cylinder (40, 40, 30)

This is what you get:


It is good idea to use checkered texture to verify texture coordinates,
since it would be very easy to spot deformed squares.
Texture looks fine except it is blurry and stretched.
The reason for that is that you applied perfectly square texture to a rectangle.

Modify the code above and replace

tu = tu + UStep

with

tu = tu + UStep*2

and run it again.

The end result:


It looks a lot better then before.

By multiplying UStep by two you have doubled UV coordinates of
the rectangle (cylinder) and effectively forced tiling of your texture.


The same way, if you use

tu = tu + UStep*4

you will force four texture tiling in U direction.

New result:


Checkered texture is nice to verify texture coordinates,
but it can not show effect of tiling.
Use this texture to see UV manipulation effects.


Original code:
One texture wrapped around


With  tu = tu + UStep*4
Four textures wrapped around


You are not limited to just one dimensional tiling

Do these modifications

tu = tu + UStep*10

and (replace tv value of 1 to 2)

'Vertex at the top of the cylinder
‘tv value is always 1 for top vertices
Mesh.AddVertex x, 0, z, 0, tu, 2, n.x, n.y, n.z

This results in 2x10 texture tiling:


More info on texturing:
Link: Texture coordinates
Link: Texture Mapping (this is for OpenGL, but the general principles are the same)

Keep in mind that this is far from "good" and "optimized" code.
This code will work if you have your application setup correctly
Textures, materials, light ...

Ok I am officially tired now

Have fun

V
Logged
Zaknafein
Customers
Community Member
*****
Posts: 2622


WWW
« Reply #3 on: March 25, 2005, 09:25:50 PM »

Wow, awesome tutorial. I had never looked the manual vertex/face creation in TV3D, this is a great read  Cheesy

A wierd kind of question... Are there performance differences between TV3D Primitives and Triangle Strips?
Logged

zaknafein.
>> the instruction limit : my blog & samples repository! <<
Vuli
Customers
Community Member
*****
Posts: 407


« Reply #4 on: March 25, 2005, 09:33:54 PM »

Quote from: "Zaknafein"
Wow, awesome tutorial. I had never looked the manual vertex/face creation in TV3D, this is a great read  Cheesy

A wierd kind of question... Are there performance differences between TV3D Primitives and Triangle Strips?


I guess it really depends on number of vertexes you send to your GPU.
There was disscussion about that  a few days ago...
I did not see any difference.
V
Logged
Waterman
Customers
Community Member
*****
Posts: 1141


« Reply #5 on: March 26, 2005, 02:46:10 AM »

Thank you Vuli for that post! I have rarely seen something that useful and clear. It will be viewed by many people, and must be stickyput right away. Admins?
Logged

Things should be described as simply as possible - but not simpler [A. Einstein]
JeffWeber
Community Member
*
Posts: 1023


« Reply #6 on: March 26, 2005, 10:21:00 AM »

Yes, thanks for taking the time to write that post.  And I 2nd the sticky motion!
Logged

""Space is deep, Man is small and Time is his relentless enemy" --Orson Scott Card
Yukito
Community Member
*
Posts: 246


WWW
« Reply #7 on: March 26, 2005, 08:42:08 PM »

yeah quite good Wink looking forward to 6.5 to be able to combine the positive aspects of the two modes
Logged

Reality is something for people, who cant handle dragons...
[Alvaron]
Community Member
*
Posts: 239


« Reply #8 on: March 28, 2005, 06:32:33 AM »

Yea.. sticky this one!!
 Cheesy
Logged
Arli
Administrator
Community Member
*****
Posts: 993


« Reply #9 on: March 28, 2005, 07:28:00 AM »

Good post! Stickied!
Logged

Happy Coding

Arli
Truevision3D Developer
Arli@Truevision3D.com
Javin
Customers
Community Member
*****
Posts: 990


« Reply #10 on: March 28, 2005, 01:20:40 PM »

Where the hell have you been, Vuli?  I've not seen many posts by you, yet you come outta no-where with this incredible, well thought-out, clear, and concise tutorial.  Very informative!  Looking forward to future posts!

-Javin
Logged

Come and join us on IRC for TV3D help!
Server: www.TrueVision3D.com:6667
Channel: #TV3DLicensed
(Open to both licensed, and non-licensed users.)
Vuli
Customers
Community Member
*****
Posts: 407


« Reply #11 on: March 28, 2005, 02:32:37 PM »

Hi

Quote from: "Javin"
Where the hell have you been, Vuli?  I've not seen many posts by you, yet you come outta no-where with this incredible, well thought-out, clear, and concise tutorial.  Very informative!  Looking forward to future posts!

-Javin


Well, I am one of those Strong and Silent Types   :lol:

I am glad you liked it.

V
Logged
GPS
Community Member
*
Posts: 30


« Reply #12 on: March 29, 2005, 07:59:18 AM »

Well that serves me right for going on vacation. I come back and find one of the most informative posts I've ever seen. Great job, Vuli.

Thanks!
Logged
Vuli
Customers
Community Member
*****
Posts: 407


« Reply #13 on: April 01, 2005, 01:22:40 PM »

Quote from: "Arli"
Good post! Stickied!


If you can "sticky" I can "Wiki" Wink

http://wiki.tv3dfilez.ath.cx/doku.php?id=tv3d:creating_objects_with_addvertex_function

V
Logged
newborn
Customers
Community Member
*****
Posts: 2433


WWW
« Reply #14 on: April 01, 2005, 01:29:04 PM »

aye, wiki would be a great idea
nice quality tutorial
Logged

kurt_hectic_PL
Community Member
*
Posts: 18


WWW
« Reply #15 on: April 02, 2005, 06:53:31 AM »

hjdfgjghjg
Logged

kurt_hectic qrt < Poland >   3d for life   :|
www.max3d.pl    www.3dtotal.com
Yukito
Community Member
*
Posts: 246


WWW
« Reply #16 on: April 02, 2005, 07:45:50 AM »

Quote from: "kurt_hectic_PL"
hjdfgjghjg


hmmm.... did you want to say anything? o.O
Logged

Reality is something for people, who cant handle dragons...
nehovsrah
Community Member
*
Posts: 119


« Reply #17 on: November 29, 2005, 05:26:15 AM »

Hey guys! I was wondering if anyone has tried using this method for "trails". Trails like a sword swinging and leaving a "ghost" of it's path. The effect is in nearly every adventure/fighting game i've ever seen and yet I can't seem to find any way to make the damn effect. I consider it the best kept secret within games. Anyway, I was wondering if anyone can give me some insight as to how I would apply this method(trianglestrips) to create this effect. I'm not askin' for code per se but a little bit of logic would help a lot. Thanks in advance.
Logged

Listen to Stephen Lynch.
nehovsrah
Community Member
*
Posts: 119


« Reply #18 on: November 29, 2005, 06:54:51 PM »

Ok so i've figured how to make the trails with this here tut! I'm using addfacefrompoint. The only thing that i havn't been able to reproduce is the fading effect on the trail. If anyone is interested in seeing how I did it, i'll put it up. Is there a way to set the opacity of the meshes so that they fade out sequentially?
Logged

Listen to Stephen Lynch.
jviper
Community Member
*
Posts: 1315

Discipline in training


« Reply #19 on: September 01, 2007, 01:15:10 PM »

I was getting ready to write an app that would really spell out all about dx meshes, index arrays, vertex arrays and attribute arrays. Problem is I've been having trouble with the property grid thing  Angry
Logged

JAbstract.....Don't just imagine, make it happen!
Pages: [1]
  Print  
 
Jump to:  

Powered by SMF 1.1.3 | SMF © 2006-2007, Simple Machines LLC
Seo4Smf v0.2 © Webmaster's Talks