can I have multiline text with GD and PHP?
I'm trying to output multiline text with GD+PHP but can't get it working. my php knowledge is really basic. here's the code, any idea on how to output 开发者_Python百科2 or 3 lines of text?
$theText = (isset($_GET['caption']))? stripslashes($_GET['caption']) :'';
imagettftext($baseImage, $textSize, $textAngle, $textXposition, $textYposition, $textColor, $fontName, $theText);
imagettftext($baseImage, $textSize, $textAngle, $textXposition, $textYposition, $textColor, $fontName, $theText);
imagettftext($baseImage, $textSize, $textAngle, $textXposition+(25), $textYposition, $textColor, $fontName, $theText);
imagettftext($baseImage, $textSize, $textAngle, $textXposition+(50), $textYposition, $textColor, $fontName, $theText);
you have to add x pixel to move it downwards to the X position. keep in mind that your whole image should be high and wide enough to fit the text.
It's not supported by API. Here is the code to do it "manually":
http://php.net/manual/en/function.imagettftext.php#75718
You can repeat one imagettftext per line; just split $theText
into an array (separator is the NewLine) and loop for each element in the array, incrementing $textYposition
by the height of the line (see $textSize
, but indeed you'll get it better using imageftbbox
. Read the page in the PHP manual
I had an unknown length of string, but only a certain width to work with. So I came up with this. Basically it splits the sentence in chars. If it bumps on a whitespace, it checks if the word can be added to the previous line, if not, it starts a new line. There is also a lame safety for extra long words, who are just being chopped of, so as not to go out of the image.
In the stage where I actually print the text to the image, I check if the line is smaller than the maximum allowed characters and add leading + trailing whitespaces, to mimic text-align: center.
# Split up the lines
$arrMessage = str_split(stripcslashes($strMessage));
$arrTemp = array();
$line = 0;
$word = array();
$arrTemp[$line] = array();
foreach($arrMessage as $char){
//if we hit a space, see if we should continue line, or make a new line
if($char == " ")
{
//calculate numbers of chars currently on line + number of chars in word
$numTotalChars = (int) count($word) + (int) count($arrTemp[$line]);
//if total > 14 chars on a line, create new line
if($numTotalChars > 14)
{
$line++;
$arrTemp[$line] = array();
}
$word[] = $char;
//push word-array onto line + empty word array
$arrTemp[$line] = array_merge($arrTemp[$line], $word);
$word = array();
}
else
{
//if word is too long for a line, split it
if( count($word) > 16)
{
$numTotalChars = (int) count($word) + (int) count($arrTemp[$line]);
if($numTotalChars > 16)
{
$line++;
$arrTemp[$line] = array();
}
$arrTemp[$line] = array_merge($arrTemp[$line], $word);
$word = array();
}
$word[] = $char;
}
}
Don't forget to add the last word to a line as well. You also need to the the check to see if it should be on a new line or not.
Add lines to image:
//add some px to x and y for every new line
$pos_x = $font->position[0];
$pos_y = $font->position[1];
$numLineHeight = 20;
$addToX = 0;
if($font->angle > 5)
{
$addToX = 2;
}
else if($font->angle < 0)
{
$addToX = -2;
}
# ADD MESSAGE
foreach($arrTemp as $arrLine){
//leading/trailing whitespace (==center text)
$numCharsOnThisLine = count($arrLine);
$extraWhiteSpace = 14 - $numCharsOnThisLine;
$frontBackSpace = floor($extraWhiteSpace / 2);
for($i = 0; $i < $frontBackSpace; $i++){
array_unshift($arrLine, " ");
$arrLine[] = " ";
}
//make string from char array
$strLine = implode("", $arrLine);
imagettftext ($image, $font->size, $font->angle, $pos_x, $pos_y, $tlt, $font->family, $strLine);
$pos_x = $pos_x + $addToX;
$pos_y = $pos_y + $numLineHeight;
}
My two cents... (adding text in a loop because of multi-line text requirement)
<?php
error_reporting(E_ALL);
error_reporting(-1);
ini_set('error_reporting', E_ALL);
/*
construction of the tcp scan
I would prefer building a C C.G.I.
but let's experiment with php
(apache user rights over nmap resources)
no php ressources on google website,
noor ajax call (worker) other then 'self'
so
I will use a php trick into the <img> html tag.
(<img src="mysite.com/gdtrick.php">)
I'm wondering if I can do the same with, let's say,
gdtrick.cgi... that would be so cool.
*/
// size of the image to create
$x = 300;
$y = 300;
$displacement_y = 24;
//debug
//$zetext = "test";
$image = imagecreate($x,$y);
$white = imagecolorallocate($image, 255,255,255);
$black = imagecolorallocate($image, 0,0,0);
$zeipaddr = "";
$zetext = "";
function getUserIP() {
$ipaddress = '';
if (isset($_SERVER['HTTP_CLIENT_IP']))
$ipaddress = $_SERVER['HTTP_CLIENT_IP'];
else if(isset($_SERVER['HTTP_X_FORWARDED_FOR']))
$ipaddress = $_SERVER['HTTP_X_FORWARDED_FOR'];
else if(isset($_SERVER['HTTP_X_FORWARDED']))
$ipaddress = $_SERVER['HTTP_X_FORWARDED'];
else if(isset($_SERVER['HTTP_X_CLUSTER_CLIENT_IP']))
$ipaddress = $_SERVER['HTTP_X_CLUSTER_CLIENT_IP'];
else if(isset($_SERVER['HTTP_FORWARDED_FOR']))
$ipaddress = $_SERVER['HTTP_FORWARDED_FOR'];
else if(isset($_SERVER['HTTP_FORWARDED']))
$ipaddress = $_SERVER['HTTP_FORWARDED'];
else if(isset($_SERVER['REMOTE_ADDR']))
$ipaddress = $_SERVER['REMOTE_ADDR'];
else
$ipaddress = 'UNKNOWN';
return $ipaddress;
}
$zeipaddr = getUserIP();
//for debug
//echo "IP: " .$zeipaddr."<br>\n";
//$zeipaddr = "192.168.1.18";
$ports = array(21, 22, 23, 80, 8080, 8081, 8082, 5900, 5901, 5902, 3306, 6000, 6001, 6002, 6003);
//$ports = array(80);
$text1 = imagettftext($image, 12, 0, 12, $displacement_y, $black, "/usr/share/fonts/truetype/freefont/FreeSans.ttf", "PHP SCAN ON DEMAND");
$displacement_y += 12;
foreach ($ports as $port)
{
$connection = @fsockopen($zeipadrr, $port, $errno, $errstr, 1);
if (is_resource($connection))
{
$zetext = $zeipadrr . ':' . $port . ' ' . '(' . getservbyport($port, 'tcp') . ') is open.' ;
$text1 = imagettftext($image, 10, 0, 6, $displacement_y, $black, "/usr/share/fonts/truetype/freefont/FreeSans.ttf", $zetext);
fclose($connection);
}
else
{
$zetext = $zeipaddr . ':' . $port . " not active." ;
$text1 = imagettftext($image, 10, 0, 6, $displacement_y, $black, "/usr/share/fonts/truetype/freefont/FreeSans.ttf", $zetext);
}
$displacement_y += 16;
}
$displacement_y += 12;
$text1 = imagettftext($image, 12, 0, 12, $displacement_y, $black, "/usr/share/fonts/truetype/freefont/FreeSans.ttf", "Port scanning done !!!");
header('Content-Type: image/jpeg');
imagejpeg($image);
?>
精彩评论