PHP – dynamisch Bilder erstellen
Für mein aktuelles Projekt musste ich dynamisch Bilder erstellen. In diesem Tutorial zeige ich euch wie ihr PHP Funktionen verwendet um Bilder automatisch zu erstellen. Die Technik kann dazu verwendet werden um einen Konfigurator zu erstellen in dem man ein eigenes Profilbild, einen Avatar, ein Logo oder ein Wappen zusammenklicken kann. In meinem Fall erstelle ich Wappen. Zusätzlich bietet der Konfigurator auch die Möglichkeit automatisch beliebig viele zufällig erstellte Bilder zu erzeugen.
PHP – dynamisch Bilder erstellen
Mein Generator ist relativ einfach geschrieben. Er erstellt aus 3 Ebenen ein neues Bild. Jede Ebene kann aus einer Anzahl zufälliger Bilder mit zufälligen Farben erstellt werden. Das heißt, es sind fast unendlich viele Kombinationen möglich. Es gibt folgende Ebenen:
- Muster (Pattern)
das unterste Bild ist ein Muster aus 2 Farben (schwarz und weiß). Es wird ein zufälliges Muster ausgewählt und die beiden Farben (schwarz und weiß) mit zwei zufälligen Farben ersetzt. - Form (Shape)
die zweite Ebene besteht aus einem Bild mit Alpha Werten. Alle Pixel des resultierenden Bildes nehmen den Alpha Wert dieses Bildes an, wodurch man Pixel transparent machen kann. - Auflage (Overlay)
für die Details sorgt ein Overlay Bild. Eine Form wird mit der dritten zufälligen Farbe eingefärbt und auf das zuvor erstellte Bild kopiert.
Durch diese 3 Ebenen und den zahlreichen Mustern, Formen und Farben ist es möglich fast unbeschränkt unterschiedliche Bilder zu erstellen. Außerdem kann man den Generator problemlos durch neue Muster und Formen erweitern. Das ganz sieht im Code wie folgt aus.
Source Code
Das Bild wird in meiner createLogo Funktion erstellt, dieser Funktion übergebe ich alle notwendigen Parameter als array. Wir brauchen die maximale Anzahl des jeweiligen Bildtyps. Wenn man den Konfigurator durch neue Muster erweitert erhöht man den Wert pattern_max einfach. Die drei Farben werden in dem Array mit Zufallswerten erstellt. Das klappt zwar, die resultierenden Farben sind aber schlecht. Besser man erstellt eine Farbpalette und weist Farben daraus zufällig zu.
$params = array( "overlay_max" => $overlay_max, "pattern_max" => $pattern_max, "shape_max" => $shape_max, "color1" => array('red' => rand(0,255), 'green' => rand(0,255), 'blue' => rand(0,255)), "color2" => array('red' => rand(0,255), 'green' => rand(0,255), 'blue' => rand(0,255)), "color3" => array('red' => rand(0,255), 'green' => rand(0,255), 'blue' => rand(0,255)), "filename" => "generated.png" ); createLogo($params);
Und noch die Funktion.
function createLogo($params) { $overlay_max = $params['overlay_max']; $pattern_max = $params['pattern_max']; $shape_max = $params['shape_max']; $color1 = $params['color1']; $color2 = $params['color2']; $color3 = $params['color3']; $filename = $params['filename'];
es werden zuerst alle lokalen Variablen der Funktion aus dem übergebenen Array gesetzt. An dieser Stelle kann man recht gut mit var_dump den Inhalt prüfen, falls das Ergebnis nicht der erwarteten Ausgabe entspricht.
//first create pattern image with color $pattern = "gfx/pattern".str_pad(rand(1, $pattern_max), 2 ,'0', STR_PAD_LEFT).".png"; $shape = "gfx/shape".str_pad(rand(1, $shape_max), 2 ,'0', STR_PAD_LEFT).".png"; $overlay = "gfx/overlay".str_pad(rand(1, $overlay_max), 2 ,'0', STR_PAD_LEFT).".png"; $im = imagecreatefrompng($pattern); $im_shape = imagecreatefrompng($shape); imagealphablending($im, false);
Nun holen wir uns die Dateinamen der Bilder für die 3 Ebenen. Dabei wählt der Zufallsgenerator zufällig ein Bild aus. Mit der imagecreatefrompng Funktion laden wir das Muster (pattern) und die Form (shape) um damit im PHP Code weiter arbeiten zu können.
for ($x = imagesx($im); $x--;) { for ($y = imagesy($im); $y--;) { $rgb = imagecolorat($im, $x, $y); $c = imagecolorsforindex($im, $rgb); $rgb_shape = imagecolorat($im_shape, $x, $y); $c_shape = imagecolorsforindex($im_shape, $rgb_shape); if ($c['red'] == 0 && $c['green'] == 0 && $c['blue'] == 0) { // black $colorNew = imagecolorallocatealpha($im, $color1['red'], $color1['green'], $color1['blue'], $c_shape['alpha']); imagesetpixel($im, $x, $y, $colorNew); } else { if ($c['red'] > 0 && $c['green'] > 0 && $c['blue'] > 0) { //white $colorNew = imagecolorallocatealpha($im, $color2['red'], $color2['green'], $color2['blue'], $c_shape['alpha']); imagesetpixel($im, $x, $y, $colorNew); } } } }
Es wird nun spannend. In einer doppelten Schleife gehen wir das 2 dimensionale Bild Pixel für Pixel entlang der x und y Achse durch. Das funktioniert übrigens nur, wenn alle Bilder die selbe Auflösung haben (in meinem Fall 500×500 Pixel). Pro Pixel holen wir und mit imagecolorsforindex die Farbe samt Alpha Wert des jeweiligen Pixels vom Muster und der Form. In einer if Abfrage entscheidet die Farbe des Musters, welche Farbe gesetzt werden soll. Das heißt: ist der Pixel schwarz, dann wird dieser auf die erste Farbe geändert. Ist er weiß (nicht schwarz), dann ändern wir die Farbe auf die zweite übergebene Farbe. In beiden Fällen setzen wir den Alpha Wert der Form. Dadurch wird der Transparenzwert jedes Pixels der Form auf das neue Bild übertragen. Das Ergebnis dieser Berechnung ist im $im Bild gespeichert. Das benötigen wir später wieder.
//overlay $im_overlay = imagecreatefrompng($overlay); for ($x = imagesx($im); $x--;) { for ($y = imagesy($im); $y--;) { $rgb_overlay = imagecolorat($im_overlay, $x, $y); $c_overlay = imagecolorsforindex($im_overlay, $rgb_overlay); $colorNew = imagecolorallocatealpha($im, $color3['red'], $color3['green'], $color3['blue'], $c_overlay['alpha']); imagesetpixel($im_overlay, $x, $y, $colorNew); } }
Wir haben nun bereits ein Bild, dass aus dem Muster und der Form berechnet wurde. Es fehlt nun noch das Overlay. Dieses laden wir wieder mit imagecreatefrompng um damit im PHP Code zu arbeiten. In einer weiteren doppelten Schleife gehen wir das zuvor erzeigte Bild Pixel für Pixel durch. Jedesmal laden wir den Farbwert des Overlays, färben dieses mit der dritten Farbe ein und speichern es in das $im Bild ab. Dadurch wird das Overlay auf das Bild aufgerechnet.
imageAlphaBlending($im, true); imageSaveAlpha($im, true); imagecopy($im, $im_overlay, 0, 0, 0, 0, 500, 500); imagepng($im, $filename, 9, PNG_ALL_FILTERS); imagedestroy($im); }
Die Funktion endet damit, das errechnete Bild im Dateisystem mit dem übergebenen Dateinamen abzuspeichern. Die Bildgröße ist in der imagecopy Funktion fix mit 500×500 abgelegt. Falls ihr den Code mit eigenen Bildern verwendet bitte das ändern.
Ergebnis
Viel Text, viel erklärt, aber am besten man sieht sich das fertige Ergebnis an. Wie ihr sehen könnt liegen alle Bilder nur monochron im PNG Format vor mit Transparenzwerten. Diese Bilder könnt ihr recht einfach mit Programmen wie Gimp oder Photoshop erstellen.
Fazit
Ich habe euch gezeigt wie man mit PHP dynamisch Bilder erstellen kann. Aus monochronen, transparenten PNG Bildern erstellt man beliebig viele unterschiedliche Bilder die man für die Webseite, das Forum oder ein Spiel verwenden kann. Mit PHP kann man dazu recht einfach einen eigenen Konfigurator bauen, damit der Benutzer das Bild selbst gestaltet. Ein Mehrwert für jedes interaktive Medium.
Moin Werner,
vielen Dank für deinen tollen Blogbeitrag! Vieles wusste ich schon, aber der Beitrag hat mir auch viele Themen gezeigt, wo ich mich noch nicht richtig auskannte! Deine Themen und dein Blog allgemein gefällt mir auch sehr gut – weiter so! 🙂 Dynamische Bilder, Logos und Algorithmen sind sehr wichtig für Webseiten, aber meinst du nicht auch, dass Kundenzufriedenheit auf der eigenen Seite stehen sollte? Schau doch mal bei https://kundentests.com/guetesiegel/ vorbei und mach dir selbst ein Bild davon! Über ein Feedback würden wir uns sehr freuen!
Liebe Grüße