2015-02-07 58 views
0

我想写一个脚本,从文本,大小和它获得的$ _GET参数中的字体生成一个PNG图像,但我不知道如何使图像的大小完全符合文本。我已经在使用imagettfbox:PHP GD imagettftext测量

$widthPx = abs($ttfBox[2] - $ttfBox[0]); 
$heightPx = abs($ttfBox[1] - $ttfBox[7]); 

这可能会给我正确的测量结果,但是当我绘制文本时,它会出现一些超出范围的情况。例如,如果我尝试使用arial.ttf绘制一个“a”,它至少有5个像素越界。有没有一种方法可以在没有测试的情况下绘制完全适合图像的任何字体的文本?

$text = $_GET["text"]; 

$cmToPixel = 15.0; 

$sizeCm = floatval($_GET["sizeCm"]); 
$sizePx = $cmToPixel * $sizeCm; 
$fontFile = "fonts/".pathinfo($_GET["font"])["filename"].".".pathinfo($_GET["font"])["extension"]; 

if(!file_exists($fontFile)){ 
    die; 
} 
$ttfBox = imagettfbbox($sizePx, 0, $fontFile, $text); 

$widthPx = abs($ttfBox[2] - $ttfBox[0]); 
$heightPx = abs($ttfBox[1] - $ttfBox[7]); 

$image = ImageCreate($widthPx, $heightPx); 

$x = $ttfBox[0] + (imagesx($image)-$ttfBox[4])/ 2 - 0; 
$y = $ttfBox[1] + (imagesy($image)/2) - ($ttfBox[5]/2) - 5; 

ImageRectangle($image,0,0,imagesx($image),imagesy($image), ImageColorAllocate($image,255,255,255)); 
imagettftext($image, $sizePx,0,$x,$y, ImageColorAllocate($image, 0, 0, 0), $fontFile, $text); 

header("Content-Type: image/png"); 
ImagePng($image); 
ImageDestroy($image); 
+0

您是否查看了本手册提供的示例?他们可能会帮助:[imagettfbbox - 使用TrueType字体给文本的边界框](http://php.net/manual/en/function.imagettfbbox.php) – 2015-02-08 02:53:14

+0

我已经看过所有的例子,它似乎我必须通过测试像素颜色来修剪图像,因为文本输出太不准确了。当我绘制它时,每个文本都有不同的偏移量,所以它总是超出范围。 – user1563232 2015-02-08 08:54:07

+0

是否可以发布您使用的代码,以便我们可以试用它? – 2015-02-08 09:00:51

回答

0

您从边界框的计算已关闭。这工作:

<?php 
/*- 
* $MirOS: www/mk/ttf2png,v 1.8 2016/11/02 16:16:26 tg Exp $ 
*- 
* Copyright (c) 2009, 2016 
* mirabilos <[email protected]> 
* 
* Provided that these terms and disclaimer and all copyright notices 
* are retained or reproduced in an accompanying document, permission 
* is granted to deal in this work without restriction, including un- 
* limited rights to use, publicly perform, distribute, sell, modify, 
* merge, give away, or sublicence. 
* 
* This work is provided "AS IS" and WITHOUT WARRANTY of any kind, to 
* the utmost extent permitted by applicable law, neither express nor 
* implied; without malicious intent or gross negligence. In no event 
* may a licensor, author or contributor be held liable for indirect, 
* direct, other damage, loss, or other issues arising in any way out 
* of dealing in the work, even if advised of the possibility of such 
* damage or existence of a defect, except proven that it results out 
* of said person's immediate fault when using the work as intended. 
*- 
* Syntax: 
* php ttf2png [text [size [/path/to/font.ttf]]] >out.png 
*/ 

if (!function_exists('gd_info')) 
    die("Install php5-gd first."); 
$gd = gd_info(); 
if ($gd["FreeType Support"] == false) 
    die("Compile php5-gd with FreeType 2 support."); 


$font = "/usr/src/www/files/FNT/GenI102.ttf"; 
$fontsize = 30; 
$text = "EINVAL"; 

if (isset($argv[1])) 
    $text = $argv[1]; 
if (isset($argv[2])) 
    $fontsize = $argv[2]; 
if (isset($argv[3])) 
    $font = $argv[3]; 


// Get bounding box 
$bbox = imageftbbox($fontsize, 0, $font, $text); 
// Transform coordinates into width+height and position 
$ascender = abs($bbox[7]); 
$descender = abs($bbox[1]); 
$size_w = abs($bbox[0]) + abs($bbox[2]); 
$size_h = $ascender + $descender; 
$x = -$bbox[0]; 
$y = $ascender; 

// Create image 
$im = imagecreatetruecolor($size_w, $size_h); 
// Allocate colours 
$bgcol = imagecolorallocate($im, 0x24, 0x24, 0x24); 
$fgcol = imagecolorallocate($im, 0xFF, 0xFF, 0xFF); 

// Fill image with background colour 
imagefilledrectangle($im, 0, 0, $size_w - 1, $size_h - 1, $bgcol); 
// Render text into image 
imagefttext($im, $fontsize, 0, $x, $y, $fgcol, $font, $text); 

// Convert true colour image (needed for above) to palette image 
imagetruecolortopalette($im, FALSE, 256); 

// Output created image 
imagepng($im, NULL, 9); 

exit(0); 

如果你写在同一行多个字符串,需要计算总的高度和行偏移,它是所有最大所有伸的加上最大全部下伸,并$yimagefttext该行的调用类似于所有上行的最大值。

+0

我试过你的代码,它输出:http://prntscr.com/eo4gfx – 2017-03-24 22:58:50

+0

@MarcielFonseca这是一个PNG,保存到一个文件或管道它通过'xloadimage stdin'或其他合适的图像浏览器。 Unix工具通常会将结果转储到stdout,以便能够通过管道用作过滤器。 – mirabilos 2017-03-25 01:25:53