Posted: 27th Jun 2007 7:59
I have complicated organic mesh that I have been able to extract the locations of all vertices. I now want to move the vertices around.

It wasn't working so I simplified it to a sphere and it still is not working. Could some one look at the code I got here and see if I'm just not seeing the obvious.

I've read BatVink tutorials up and down and looked at all manner of posts, etc. Still not happening. I don't want to use memblocks if I can help it.

Essentially the code creates a sphere (or my complicated object) and then uses MAKE MESH FROM OBJECT. That seems ok and when I step thru each vertex placing a small sphere at each triple value index it has determined the vertex locations ok.

So then I lock the mesh again and try moving any vertices and nothing happens.


After locking mesh use
SET VERTEXDATA POSITION indexnumber, x#,y#-3.0,z#
(adding a value to the original position i.e. y#+3.0)
then locking the mesh again but there is no movement of any vertices!!

I've been at this for days so any help would be greatly appreciated!


+ Code Snippet
make object sphere 2, 50,20,20
MAKE MESH FROM OBJECT 2, 2
LOCK VERTEXDATA FOR mesh 2
z=GET VERTEXDATA VERTEX COUNT ()
global dim OVertexPos#( z, 2 )
for t = 0 to z
OVertexPos#( t, 0 ) = GET VERTEXDATA POSITION X( t )
OVertexPos#( t, 1 ) = GET VERTEXDATA POSITION Y( t )
OVertexPos#( t, 2 ) = GET VERTEXDATA POSITION Z( t )
next t
unlock vertexdata

Rem Step thru incrementing index number ...
for t = 0 to z
x# = OVertexPos#(indexnumber, 0 )
y# = OVertexPos#(indexnumber, 1 )
z# = OVertexPos#(indexnumber, 2 )

LOCK VERTEXDATA FOR mesh 2
SET VERTEXDATA POSITION indexnumber, x#,y#-3.0,z#
unlock vertexdata
REM vertices should have moved 
next t

Posted: 27th Jun 2007 8:14
BTW I base my code on this example which uses LOCK VERTEXDATA FOR LIMB and seems to work fine for this example. I'm sorry but I don't know the source of this code so I apologize if I post it but I really I'm stuck here.

+ Code Snippet
Rem Project: manip
Rem Created: 5/20/2007 10:54:08 PM

Rem ***** Main Source File *****
` This code was downloaded from The Game Creators
` It is reproduced here with full permission
` http://www.thegamecreators.com

sync on : sync rate 0 : hide mouse : randomize timer( )

rem make object sphere 1, 50 ` The object to be deformed. The one below this will do the deforming
make object sphere 1, 100,20,20 ` The object to be deformed. The one below this will do the deforming
rem load image "LIMESTO1.JPG",1,0
rem texture object 1, 1
SET OBJECT WIREFRAME 1, 1
make object plain 2, 100, 100 : position object 2, 50, 0, 0 : rotate object 2, 0, 90, 0
Marker = 3 : make object sphere Marker, 5 : hide object Marker ` A marker object
SET OBJECT WIREFRAME 2, 1
LOCK VERTEXDATA FOR LIMB 1, 0 : n=GET VERTEXDATA VERTEX COUNT( ) ` So we can move vertices
global dim OVertexPos#( n, 2 ) ` Get all the vertices original vertex data
for t = 0 to n
OVertexPos#( t, 0 ) = GET VERTEXDATA POSITION X( t )
OVertexPos#( t, 1 ) = GET VERTEXDATA POSITION Y( t )
OVertexPos#( t, 2 ) = GET VERTEXDATA POSITION Z( t )
next t
x# = object position x( 1 ) : y# = object position y( 1 ) : z# = object position z( 1 )
px# = 100 ` Get object #1's centerpoint above; this line is the initial position of object #2
x# = 85: y#=180: z# = -40: ym#=145: zm# = -5
position camera y#,ym#,zm#

 xrotate camera x#
 yrotate camera y#
 zrotate camera z#

do
for t = 0 to n ` Go through all the vertices
x2# = GET VERTEXDATA POSITION X( t ) ` Get the vertex position
y2# = GET VERTEXDATA POSITION Y( t )
z2# = GET VERTEXDATA POSITION Z( t )

x3# = OVertexPos#( t, 0 ) : y3# = OVertexPos#( t, 1 ) : z3# = OVertexPos#( t, 2 )
x4# = x3# - x2# : y4# = y3# - y2# : z4# = z3# - z2# ` This tries to move all the vertices
x2# = x2# + ( x4# * 0.01 ) : y2# = y2# + ( y4# * 0.01 ) : z2# = z2# + ( z4# * 0.01 )
SET VERTEXDATA POSITION t, x2#, y2#, z2# ` back to their original positions

position object 1, x2#, y2#, z2#
rotate object 1, object angle x( 2 ), object angle y( 2 ), object angle z( 2 )
move object 1, -20
xb# = object position x( 1 ) : yb# = object position y( 1 ) : zb# = object position z( 1 )
d# = intersect object( 2, xb#, yb#, zb#, x2#, y2#, z2# )
` The above code is a simple way of checking wether the vertex is being affected by the plain.
` It checks against the anlge of the plain. At the bottom is code that will check from the
` middle of the object.

if d# <> 0 ` If the vertex is behind the plain
move object Marker, d#
SET VERTEXDATA POSITION t, object position x( Marker ), object position y( Marker ), object position z( Marker )
` That repositions the vertex onto the plain. :)
endif
next t
rem cy# = wrapvalue( cy# + 0.1 ) ` Code to rotate the camera
position camera px#, 0, 0
rotate camera 0, cy#, 0
move camera 0, -200

if inkey$()="1"
  pxm# = pxm# + 0.01 : px# = px# + pxm#
endif
 if inkey$()="2"
  pxm# = pxm# + 0.01 : px# = px# - pxm#
endif
if inkey$()="3"
  pxm# = pxm# + 0.01 : px# = px# + pxm#
endif
 if inkey$()="4"
  pxm# = pxm# + 0.01 : px# = px# - pxm#
endif
position object 2, px#, 0, 0 ` So we can move the plain with the mouse.


printXset=10
printYset=10
printSpacing=13
 set cursor printXset,printYset+printSpacing*4:print "  # Scene Polygons: ";statistic(1)
 set cursor printXset,printYset+printSpacing*5:print "  Fps: "+str$(screen fps())
 set cursor printXset,printYset+printSpacing*6:print "  x# "; x#
 set cursor printXset,printYset+printSpacing*7:print "  y# "; y#
 set cursor printXset,printYset+printSpacing*8:print "  z# "; z#
 set cursor printXset,printYset+printSpacing*9:print "  ym# "; ym#
 set cursor printXset,printYset+printSpacing*10:print "  zm# "; zm#
 set cursor printXset,printYset+printSpacing*11:print "  d# "; d#

 if upkey()=1 then ym#=ym#-1
 if downkey()=1 then ym#=ym#+1
 if leftkey()=1 then zm#=zm#-1
 if rightkey()=1 then zm#=zm#+1
 if inkey$()="d" then x#=x#-5
 if inkey$()="c" then x#=x#+5
 if inkey$()="a" then y#=y#-5
 if inkey$()="z" then y#=y#+5
 if inkey$()="s" then z#=z#-5
 if inkey$()="x" then z#=z#+5
 xrotate camera x#
 yrotate camera y#
 zrotate camera z#
 position camera y#, ym#, zm#


sync
loop

 ` This code has the advantage of operating independant
 ` of the object that's doing the squishing. It also
 ` squishes towards the center - But for helmets and hair
 ` nobody's going to see, anyway. :)
remstart
if d# <> 0
x3# = abs( x2# - x# ) : y3# = abs( y2# - y# ) : z3# = abs( z2# - z# )
tc# = ( x3#^2 + y3#^2 + z3#^2 ) ^ 0.5 ` Get the distance between the center and the vertex
x4# = x3# / tc# : y4# = y3# / tc# : z4# = z3# / tc#
x5# = x4# * d# : y5# = y4# * d# : z5# = z4# * d# ` And squish
if x2# < 0 then x5# = x5# * -1
if y2# < 0 then y5# = y5# * -1
if z2# < 0 then z5# = z5# * -1
SET VERTEXDATA POSITION t, x5#, y5#, z5#
endif
remend

Posted: 27th Jun 2007 8:18
to move a vertex, you don't need the index to the index data, you need the index to the vertexdata.
All you have to do is loop through the vertexdata and change the values of the positions.
psuedo code:

z = get vertexdata vertex count()

for i = 0 to z

set vertexdata position i,your x value#, your y value#, your z value#

next i

hopes this helps

oops! I made the same mistake!
I edited it.
Posted: 27th Jun 2007 8:29
hmmm ... so are you implying that I have to reset every vertexdata position for the entire object even if I only want to move 1 vertex?

If you could indulge me some more ... I thought with these calls:

x# = OVertexPos#(indexnumber, 0 )
y# = OVertexPos#(indexnumber, 1 )
z# = OVertexPos#(indexnumber, 2 )

I was in fact getting the actual vertex data ... i.e. the x,y,z positions of triangle which has index value of indexnumber (i.e. number 10).


Am I missing something here?
Posted: 27th Jun 2007 8:31
Sorry I just realized that the little for loop I had in my first post should have been:

+ Code Snippet
make object sphere 2, 50,20,20
MAKE MESH FROM OBJECT 2, 2
LOCK VERTEXDATA FOR mesh 2
z=GET VERTEXDATA VERTEX COUNT ()
global dim OVertexPos#( z, 2 )
for t = 0 to z
OVertexPos#( t, 0 ) = GET VERTEXDATA POSITION X( t )
OVertexPos#( t, 1 ) = GET VERTEXDATA POSITION Y( t )
OVertexPos#( t, 2 ) = GET VERTEXDATA POSITION Z( t )
next t
unlock vertexdata

Rem Step thru incrementing index number ...
for indexnumber = 0 to z
x# = OVertexPos#(indexnumber, 0 )
y# = OVertexPos#(indexnumber, 1 )
z# = OVertexPos#(indexnumber, 2 )

LOCK VERTEXDATA FOR mesh 2
SET VERTEXDATA POSITION indexnumber, x#,y#-3.0,z#
unlock vertexdata
REM vertices should have moved 
next indexnumber




Sorry about that ... but it still doesn't work.
Posted: 27th Jun 2007 8:50
you can set just one vertex, of course.
If you want to change just one position, you just point to the index in the vertexdata, and use set vertexdata position()

set vertexdata position 12,0,15,0
that would set the vertex at position 12 in the vertexdata to the coordinates 0,15,0
do not confuse indexdata and vertexdata.
Indexdata is a list of 3 vertexes that make up a triangle.
If you change the indexdata, you change the triangles, not the vertex. So, say you have three vertexes,
0,0,0
0,0,1
1,0,1
this makes a righthand drawn triangle
in the vertexdata the first coordinate is index 0
the second is 1
the third is 1
in the index data, there would only be one index and it would be 0
the data for the index of 0 would be 0,1,2
because 0 is the first coordinate in the vertexdata
1 is the second one
2 is the third one

if you change the indexdata to say, 0,1,1 it won't draw anything, because those coordinates can't make a triangle

Can I give you a tip, something I've been doing that really helps me out?
When I make a mesh, and I want to see what is going on, I use the save mesh command to write an .x file. then, I just open the file to see what the heck is going on.
Sprinkle these save meshes before and after you modify a mesh, and you can see your changes. Just remember to save the file names different, because unlike all the other file stuff, you can rewrite over an existing .x file.
Posted: 27th Jun 2007 9:28
It's late so if I'm not making sense it's from lack of sleep, etc.


Indexdata is a list of 3 vertexes that make up a triangle.


So my calls in my code:
x# = OVertexPos#(indexnumber, 0 )
y# = OVertexPos#(indexnumber, 1 )
z# = OVertexPos#(indexnumber, 2 )
is what you are talking about since the 2nd index of the array OVertexPos# (i.e. the index data) is 0,1,2 which are the x,y,z positions of a single vertex with index number "indexnumber" which is just one "point" that makes up a triangle (the vertex data). The x#,y#,z# are the vertexdata of position "indexnumber", right?

Looking at the code bit I posted I think I got right, didn't I?

I print out the actual values I get for x#,y#,z# and they appear reasonable float numbers.

I like the idea of save mesh/load mesh ... that's good.

I think the best thing to do is extract a small bit of code from my project, simplify it, test it, and if it still doesn't work I'll post the bit of code with a mesh object if that is ok to do.
Posted: 27th Jun 2007 10:24
Here is a simpler (hopefully more readable) version of the code I'm trying to create and I have attached the mesh too.

Please try it out or let me know if you see any errors that would explain why the mesh's vertices are not moving.

+ Code Snippet
global z
global x#
global y#
global z#
global indexnumber

sync on
sync rate 60
autocam on

REM create a little sphere to move from vertex to vertex while incrmenting
make object sphere 3, 2,4,4

REM main mesh object to have it's vertices moved
load object "female_body_fix_3.X",2
rem make object sphere 2, 50,20,20
SET OBJECT WIREFRAME 2,1
position object 2, 0, 0, 0
MAKE MESH FROM OBJECT 2, 2

REM get the x,y,z positions for each vertex that makes up the mesh adn store in array OVertexPos#
LOCK VERTEXDATA FOR mesh 2
z=GET VERTEXDATA VERTEX COUNT ()
global dim OVertexPos#( z, 2 )
for t = 0 to z
OVertexPos#( t, 0 ) = GET VERTEXDATA POSITION X( t )
OVertexPos#( t, 1 ) = GET VERTEXDATA POSITION Y( t )
OVertexPos#( t, 2 ) = GET VERTEXDATA POSITION Z( t )
next t
unlock vertexdata
timestart=timer()

REM program loop
do
      varprints()

      REM timer to slow down movement of tiny sphere & step thru
      timenow = timer()
      if (timenow-timestart)>100 and (timenow-timestart)<200
         if nnn = z then nnn = 0
         nnn=nnn+1
         timestart=timenow
      endif
      indexnumber=nnn

      x# = OVertexPos#(indexnumber, 0 )
      y# = OVertexPos#(indexnumber, 1 )
      z# = OVertexPos#(indexnumber, 2 )

      position object 3, x#,y#,z#

      LOCK VERTEXDATA FOR mesh 2
      SET VERTEXDATA POSITION indexnumber, x#,y#-3.0,z#
      unlock vertexdata

      sync
loop
end


Function varPrints()
   set cursor 0,50
   print "  DBPro Fps: "+str$(screen fps())
   print "  # Scene Polygons: ";statistic(1)
   print "  # Object Vertices: ";z
   print "  Current Grahics Card: ";CURRENT GRAPHICS CARD$()
   print "  mousex:";mousex()
   print "  mousey:";mousey()
   print "  mousez:";mousez()
   print "  index number ";indexnumber
   print "  x#:";str$(x#)
   print "  y#:";str$(y#)
   print "  z#:";str$(z#)
   if SCREEN TYPE() = 0
      print " Not Harware Accelerated"
   else
      print " Harware Accelerated"
   endif
endfunction
Posted: 27th Jun 2007 10:38
ok, i'm looking at it now
Posted: 27th Jun 2007 10:51
Got it!

It works for limb but not for mesh (my original concern) ...hmmm

Replace

LOCK VERTEXDATA FOR mesh 2
with
LOCK VERTEXDATA FOR limb 2, 0, 0

You would think it would work for mesh, though ... hmmm
Posted: 27th Jun 2007 11:07
coolio.
This is actually a cool idea you have here.
Posted: 27th Jun 2007 11:11
thanks!

hopefully I'll be able to complete this project with DB ... could make some money and has nothing to do with gaming ... if I ever finish it ...