Search code examples
phpdrawinggifgdanimated-gif

Draw lines and write text on animated GIF image using PHP


Hello lovely swarm intelligence!

I have some PHP code, which draws lines in form of a grid system to an image and afterwards, it also writes some text on this image. My code works as expected with static images like PNG or JPG/JPEG, when I use the respective PHP imagecreatefrom* and image* functions.

Following the adjusted and simplified (without a lot of try-catch, if-conditions and variables) code for GIF images:

$gif_filepath = '/tmp/animated.gif';
$font_filepath = '/tmp/some-font.ttf';

list($width, $height) = getimagesize($gif_filepath);

$gd_image = imagecreatefromgif($gif_filepath);

$line_color = imagecolorallocatealpha($gd_image, 0, 0, 0, 80);

$spacing = 25;

// Draw vertical lines
for ($iw = 0; $iw < $width / $spacing; $iw++) {
    imageline($gd_image, $iw * $spacing, 0, $iw * $spacing, $width, $line_color);
}

// Draw horizontal lines
for ($ih = 0; $ih < $height / $spacing; $ih++) {
    imageline($gd_image, 0, $ih * $spacing, $width, $ih * $spacing, $line_color);
}

$font_color = imagecolorallocate($gd_image, 255, 0, 0);

// Write text
imagefttext($gd_image,
    25,
    0,
    30,
    60,
    $font_color,
    $font_filepath,
    'Let\'s ask Stackoverflow!'
);

imagegif($gd_image);

PHP properly adds the respective lines and text to the GIF, but at the end it's only returning a single (probably the first) frame of the entire GIF.

Is it possible with PHP (in best case without any third-party libraries / tools) to draw these lines and write the text on the animated GIF image, so that it is afterwards still animated or is this technically not supported / possible?

I've seen, that there is a PHP function imagecopymerge, but I wasn't able to archive my target with this function.


Solution

  • It seems like as it's technically not possible to solve this with PHP native functions.

    However, using shell_exec() and ffmpeg it can be archived in PHP:

    $gif_filepath = '/tmp/animated.gif';
    $target_image_filepath = '/tmp/modified_animated.gif';
    $font_filepath = '/tmp/some-font.ttf';
    
    $spacing = 25;
    
    # Draw grid system (horizontal + vertical lines)
    shell_exec("ffmpeg -hide_banner -loglevel error -nostdin -y -i $gif_filepath -vf 'drawgrid=width=$spacing:height=$spacing:thickness=1:[email protected]' $target_image_filepath 2>&1");
    
    # Write text
    shell_exec("ffmpeg -hide_banner -loglevel error -nostdin -y -i $gif_filepath -vf \"drawtext=text='Let\'s ask Stackoverflow!':fontsize=25:x=30:y=60:fontcolor=red:fontfile=$font_filepath\" $target_image_filepath 2>&1");
    
    // $target_image_filepath now contains the grid system and respective text
    

    There also exists a third-party PHP library PHP-FFMpeg, which maybe can be used instead of shell_exec(), if it supports the respective filters for GIF files.