Выбрать главу

The variable points will reference a single VERTEX (x, y and z values). This allows us to grab the x, y or z value of any point using points[{point we want to access}].{x, y or z}.

The name of this structure is… you guessed it… OBJECT!

typedef struct // Structure For An Object

{

 int verts; // Number Of Vertices For The Object

 VERTEX *points; // One Vertice (Vertex x,y & z)

} OBJECT; // Called OBJECT

Now that we have created a VERTEX structure and an OBJECT structure we can define some objects.

The variable maxver will be used to keep track of the maximum number of variables used in any of the objects. If one object only had 5 points, another had 20, and the last object had 15, the value of maxver would be equal to the greatest number of points used. So maxver would be equal to 20.

After we define maxver we can define the objects. morph1, morph2, morph3, morph4 & helper are all defined as an OBJECT. *sour & *dest are defined as OBJECT* (pointer to an object). The object is made up of verticies (VERTEX). The first 4 morph{num} objects will hold the 4 objects we want to morph to and from. helper will be used to keep track of changes as the object is morphed. *sour will point to the source object and *dest will point to the object we want to morph to (destination object).

int maxver; // Will Eventually Hold The Maximum Number Of Vertices

OBJECT morph1, morph2, morph3, morph4, // Our 4 Morphable Objects (morph1,2,3 & 4)

 helper, *sour, *dest; // Helper Object, Source Object, Destination Object

Same as always, we declare WndProc().

LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); // Declaration

The code below allocates memory for each object, based on the number of vertices we pass to n. *k will point to the object we want to allocate memory for.

The line inside the { }'s allocates the memory for object k's points. A point is an entire VERTEX (3 floats). The memory allocated is the size of VERTEX (3 floats) multiplied by the number of points (n). So if there were 10 points (n=10) we would be allocating room for 30 floating point values (3 floats * 10 points).

void objallocate(OBJECT *k,int n) // Allocate Memory For Each Object

{ // And Defines points

 k->points=(VERTEX*)malloc(sizeof(VERTEX)*n); // Sets points Equal To VERTEX * Number Of Vertices

} // (3 Points For Each Vertice)

The following code frees the object, releasing the memory used to create the object. The object is passed as k. The free command tells our program to release all the points used to make up our object (k).

void objfree(OBJECT *k) // Frees The Object (Releasing The Memory)

{

 free(k->points); // Frees Points

}

The code below reads a string of text from a file. The pointer to our file structure is passed to *f. The variable string will hold the text that we have read in.

We start off be creating a do / while loop. fgets() will read up to 255 characters from our file f and store the characters at *string. If the line read is blank (carriage return \n), the loop will start over, attempting to find a line with text. The while() statement checks for blank lines and if found starts over again.

After the string has been read in we return.

void readstr(FILE *f,char *string) // Reads A String From File (f)

{

 do // Do This

 {

  fgets(string, 255, f); // Gets A String Of 255 Chars Max From f (File)

 } while ((string[0] == '/') || (string[0] == '\n')); // Until End Of Line Is Reached

 return; // Return

}

Now we load in an object. *name points to the filename. *k points to the object we wish to load data into.

We start off with an integer variable called ver. ver will hold the number of vertices used to build the object.

The variables rx, ry & rz will hold the x, y & z values of each vertex.

The variable filein is the pointer to our file structure, and oneline[ ] will be used to hold 255 characters of text.

We open the file name for read in text translated mode (meaning CTRL-Z represents the end of a line). Then we read in a line of text using readstr(filein,oneline). The line of text will be stored in oneline.

After we have read in the text, we scan the line of text (oneline) for the phrase "Vertices: {some number}{carriage return}. If the text is found, the number is stored in the variable ver. This number is the number of vertices used to create the object. If you look at the object text files, you'll see that the first line of text is: Vertices: {some number}.

After we know how many vertices are used we store the results in the objects verts variable. Each object could have a different value if each object had a different number of vertices.

The last thing we do in this section of code is allocate memory for the object. We do this by calling objallocate({object name},{number of verts}).

void objload(char *name,OBJECT *k) // Loads Object From File (name)

{

 int ver; // Will Hold Vertice Count

 float rx,ry,rz; // Hold Vertex X, Y & Z Position

 FILE *filein; // Filename To Open

 char oneline[255]; // Holds One Line Of Text (255 Chars Max)

 filein = fopen(name, "rt"); // Opens The File For Reading Text In Translated Mode

 // CTRL Z Symbolizes End Of File In Translated Mode

 readstr(filein,oneline); // Jumps To Code That Reads One Line Of Text From The File

 sscanf(oneline, "Vertices: %d\n", &ver); // Scans Text For "Vertices: ". Number After Is Stored In ver

 k->verts=ver; // Sets Objects verts Variable To Equal The Value Of ver

 objallocate(k,ver); // Jumps To Code That Allocates Ram To Hold The Object

We know how many vertices the object has. We have allocated memory, now all that is left to do is read in the vertices. We create a loop using the variable i. The loop will go through all the vertices.

Next we read in a line of text. This will be the first line of valid text underneath the "Vertices: {some number}" line. What we should end up reading is a line with floating point values for x, y & z.

The line is analyzed with sscanf() and the three floating point values are extracted and stored in rx, ry and rz.

 for (int i=0;i<ver;i++) // Loops Through The Vertices

 {

  readstr(filein, oneline); // Reads In The Next Line Of Text

  sscanf(oneline, "%f %f %f", &rx, &ry, &rz); // Searches For 3 Floating Point Numbers, Store In rx,ry & rz

The following three lines are hard to explain in plain english if you don't understand structures, etc, but I'll try my best :)

The line k->points[i].x=rx can be broken down like this:

rx is the value on the x axis for one of the points.

points[i].x is the x axis position of point[i].

If i is 0 then were are setting the x axis value of point 1, if i is 1, we are setting the x axis value of point 2, and so on.

points[i] is part of our object (which is represented as k).

So if i is equal to 0, what we are saying is: The x axis of point 1 (point[0].x) in our object (k) equals the x axis value we just read from the file (rx).

The other two lines set the y & z axis values for each point in our object.