An intro to using the GD image library with PHP
Before we really get into things, let me clue you into something. I am not a graphic designer. I have no urge to be and have no talent to be. To put it bluntly, my graphics suck. Also, to use what you learn in this tutorial, you will need PHP 4.0.6 or higher and atleast GD 2.0.1.
Ok, with that out of the way, on to the GD library! So, what use are the GD library functions in PHP? Creating images on the fly. Why would you want to do that? Well, if there are some images that have content that changes. Take for instance this clock : |
|
|
|
|
If I didn't create that clock on the fly, it would be quite a pain to show the proper time. Can you imagine having 43,200 different images on your server just to be able to show what time it is? That's why we need to create the image on the fly. Creating images on the fly isn't for everything. If you have an image that doesn't change, don't recreate it everytime. That is just putting unnecessary cycles on your server.
Getting to know the functions OK, let's take a look at some of the functions we will be using in order to create the clock.
|
|
|
int ImageCreate(int x_size, int y_size) |
|
|
This one is simple enough, all we need to do is pass this function two integers that represent the width and height of the image we are creating. This function returns an identifier to our blank image. Worth noting is that the upper left corner of an image is the coordinate 0,0. That means if you create an image with a width of 100, the x coordinates will run from 0 through 99. |
|
|
int ImageDestroy (int im) |
|
|
With ImageDestroy, we can get rid of the images we create with ImageCreate.
|
|
|
int ImageColorAllocate(int im, int red, int green, int blue) |
|
|
The first parameter to this function is the image identifier that we will have assigned by the ImageCreate funtion. Remember good old RGB colors? I hope so, you need to use them here. The next three parameters are the values for red, green and blue respectively. Some common colors are (0,0,0) for black, (255,255,255) for white and (255,0,0) for red. Here's a link to a good RGB chart that I found. If for some reason the function fails to allocate the color, it will return a value of -1. |
|
|
int ImageFilledRectangle (int im, int x1, int y1, int x2, int y2, int col) |
|
|
This function is used to create a simple filled rectangle or square. All you do is pass it the image you are working with, upper left x-y coordinates, the lower right x-y coordinates and a color that you created with ImageColorAllocate. Remember that images start at 0,0!
|
|
|
More functions |
|
|
int ImageFilledEllipse (resource im, int cx, int cy, int w, int h, int col) |
|
|
With ImageFilledEllipse, we can create filled ellipses, or ovals and circles. We pass it the pointer to the image we are working on, a center point designated by cx and cy, its width and height and a color we have created. |
|
|
int ImageFilledArc (int im, int cx, int cy, int w, int h, int s, int e, int col, int style) |
|
|
This function is a bit more complicated, but still not hard to use at all. Just think of it as cutting a piece of pie or cake. You pass it the image you are working on, a center point (think the middle of the pie) represented by cx and cy, its width and height, its start and end points in degrees (we'll touch on this in a second), a color you have created and its style (we'll also touch on this).
To visualize the start and end points, let's think of our pie again. Let's say we are really hungry and want to cut ourselves a piece of pie that is 1/4 of the entire pie. We would pass the function a start point of 0 degrees and an end point of 90 degrees. There are 360 degrees in a circle, so a total on 90 degrees would be one fourth of it. You can vary the start and end degrees to decide "where" your piece of the pie comes from.
With the style of the arc you can do some pretty cool stuff. There are four styles: IMG_ARC_PIE IMG_ARC_CHORD IMG_ARC_NOFILL IMG_ARC_EDGED. Using IMG_ARC_PIE is going to give you your traditional pie piece. The IMG_ARC_CHORD style produces a flat outer edge, rather than the traditional pie piece shape. With IMG_ARC_CHORD, you can make things like hexagons and other flat sided designs just by filling a circle with them. IMG_ARC_NOFILL tells the function not to fill the arc and IMG_ARC_EDGED tells it to connect up all the lines and have a border. If you need to use more than one of these, use the OR bitwise operator. I.e., IMG_ARC_CHORD | IMG_ARC_NOFILL.
|
|
|
And even more functions |
|
|
int ImageColorTransparent (int im [, int col]) |
|
|
With this function, we can set the transparency color of an image or find out what the current transparency color is. If all we pass this function is a pointer to an image, we will be returned the identifier of the current transparency color. If we pass it a image identifier and a color, that color will be set to transparent for the image. |
|
|
array ImageTTFText (int im, int size, int angle, int x, int y, int col, string fontfile, string text) |
|
|
Ok, so we can draw all these boxes and circles and things, but how do we put text in our image? ImageTTFText is one of the ways to do so. It's actually pretty simple, but can take a little experimenting to get your text positioned right where you want it. You pass this function a image identifier, the size of the font, the angle (standard left to right reading would be an angle of 0, 90 degrees would result in text going from bottom to top.), a starting point signified by x and y, a color, the font to use and the string to display.
Of special note here is that the starting point for this function is at the lower left corner of the text, NOT the upper left. Be careful of that or your text will not be where you want it. Also, you need to provide the path to the font you want to use, here's a link to the arial font that I use in this tutorial. |
|
|
int ImagePNG (int im [, string filename]) |
|
|
This is the function that we will use to actually display this image. All the other functions up until this point have just been manipulating the image in memory. This one will send the binary stream out so that we can see it. We could specify a filename to write the image to, but we aren't going to do that here.
Putting it all together Ok, now let's put all those functions together and create that clock! First we need to get a few variables set so that we have the proper time and all that. Here's a bit of code to do that, how we got this code is beyond the scope of this tutorial. |
|
|
<?PHP $time = strftime("%I:%M:%S", time()); $timearray = explode(':',$time); $hour = (((int)$timearray[0]) * 60) + (int)$timearray[1]; $minute = (int)$timearray[1]; $second = (int)$timearray[2]; if($hour != 0) { $hourdegree = ((360 / (720 / $hour)) - 90) % 360; if($hourdegree < 0) { $hourdegree = 360 + $hourdegree; } } else { $hourdegree = 270; } if($minute != 0) { $minutedegree = ((360 / (60 / $minute)) - 90) % 360; if($minutedegree < 0) { $minutedegree = 360 + $minutedegree; } } else { $minutedegree = 270; } if($second != 0) { $seconddegree = ((360 / (60 / $second)) - 90) % 360; if($seconddegree < 0) { $seconddegree = 360 + $seconddegree; } } else { $seconddegree = 270; } ?> |
|
|
Ok, there might be a more efficient way to get the degrees that we need, but this is the way I decided to do it. Anyway, on with making the image. Let's throw all those functions we saw earlier together and get an image created. |
|
|
<?PHP $image = imagecreate(100,100); $maroon = ImageColorAllocate($image,123,9,60); $white = ImageColorAllocate($image,255,255,255); $black = ImageColorAllocate($image,0,0,0);
ImageFilledRectangle($image,0,0,99,99,$white); ImageFilledEllipse($image,49,49,100,100,$black); ImageFilledEllipse($image,49,49,95,95,$maroon); ImageFilledEllipse($image,49,49,75,75,$white); ImageFilledEllipse($image,49,49,5,5,$maroon); ImageFilledArc($image,49,49,50,50,$hourdegree-4,$hourdegree+4,$maroon,IMG_ARC_PIE); ImageFilledArc($image,49,49,65,65,$minutedegree-3,$minutedegree+3,$maroon,IMG_ARC_PIE); ImageFilledArc($image,49,49,70,70,$seconddegree-2,$seconddegree+2,$black,IMG_ARC_PIE);
ImageColorTransparent($image,$white);
ImageTTFText ($image, 8, 0, 44, 11, $white,"/home/mjw21/www/images/arial.ttf","12"); ImageTTFText ($image, 8, 0, 89, 53, $white,"/home/mjw21/www/images/arial.ttf","3"); ImageTTFText ($image, 8, 0, 47, 96, $white,"/home/mjw21/www/images/arial.ttf","6"); ImageTTFText ($image, 8, 0, 5, 53,$white,"/home/mjw21/www/images/arial.ttf","9");
imagePNG($image); imagedestroy($image); ?> |
|
|
Let's finish it up Ok, so we have it all together and have an image created. Now if you just try and stick that code in your page, it will not display correctly. The reason for this is that the browser doesn't know how to interpret the data that is coming at it. Some people solve this by writing the image to a temporary file; I don't like that method. If you write to a temporary file then you have to go back and clean those up. What a hassle. What I do is put all the code into its own PHP file and add a header to it. Then just act as if the PHP file was an image file and use standard HTML to include it.
So, here is our finished clock all ready to go into its own PHP file :
|
|
|
<?PHP Header("Content-type: image/png"); $time = strftime("%I:%M:%S", time()); $timearray = explode(':',$time); $hour = (((int)$timearray[0]) * 60) + (int)$timearray[1]; $minute = (int)$timearray[1]; $second = (int)$timearray[2]; if($hour != 0) { $hourdegree = ((360 / (720 / $hour)) - 90) % 360; if($hourdegree < 0) { $hourdegree = 360 + $hourdegree; } } else { $hourdegree = 270; } if($minute != 0) { $minutedegree = ((360 / (60 / $minute)) - 90) % 360; if($minutedegree < 0) { $minutedegree = 360 + $minutedegree; } } else { $minutedegree = 270; } if($second != 0) { $seconddegree = ((360 / (60 / $second)) - 90) % 360; if($seconddegree < 0) { $seconddegree = 360 + $seconddegree; } } else { $seconddegree = 270; }
$image = imagecreate(100,100); $maroon = ImageColorAllocate($image,123,9,60); $white = ImageColorAllocate($image,255,255,255); $black = ImageColorAllocate($image,0,0,0);
ImageFilledRectangle($image,0,0,99,99,$white); ImageFilledEllipse($image,49,49,100,100,$black); ImageFilledEllipse($image,49,49,95,95,$maroon); ImageFilledEllipse($image,49,49,75,75,$white); ImageFilledEllipse($image,49,49,5,5,$maroon); ImageFilledArc($image,49,49,50,50,$hourdegree-4,$hourdegree+4,$maroon,IMG_ARC_PIE); ImageFilledArc($image,49,49,65,65,$minutedegree-3,$minutedegree+3,$maroon,IMG_ARC_PIE); ImageFilledArc($image,49,49,70,70,$seconddegree-2,$seconddegree+2,$black,IMG_ARC_PIE);
ImageColorTransparent($image,$white);
ImageTTFText ($image, 8, 0, 44, 11, $white, "/home/mjw21/www/images/arial.ttf","12"); ImageTTFText ($image, 8, 0, 89, 53, $white, "/home/mjw21/www/images/arial.ttf","3"); ImageTTFText ($image, 8, 0, 47, 96, $white, "/home/mjw21/www/images/arial.ttf","6"); ImageTTFText ($image, 8, 0, 5, 53, $white,"/home/mjw21/www/images/arial.ttf","9");
imagePNG($image); imagedestroy($image); ?> |
|
|
Simple huh? There are lots of other functions available in the GD library, so get out there and experiment with them. If you look around my site you will see that the graphics for the code ratings are also created on the fly. The possibilities are endless!
|
« Back
|