Formaat wijzigen en afbeeldingen manipuleren in PHP (met voorbeelden)

In mijn vorige zelfstudie bespraken we algemene beeldmanipulatie met behulp van de PHP GD-bibliotheek. In die tutorial gaf ik een korte inleiding tot de bibliotheek en liet je zien hoe je afbeeldingen vanuit een bestand laadt of vanuit het niets creëert in PHP. Daarna leerden we hoe we een afbeelding bijsnijden, roteren, schalen en omdraaien met GD. Ik heb de ImageFilter () functie om verschillende filters toe te passen op afbeeldingsbronnen die in het script zijn geladen. Ik noemde ook enkele nuttige functies in GD-achtig imagesx () en imagesy () om de breedte en hoogte van de geladen afbeelding te krijgen.

Aan het einde van mijn laatste GD-zelfstudie, hebt u geleerd hoe u de bibliotheek kunt gebruiken om basistaken zoals het formaat van alle afbeeldingen in een map te automatiseren of filters zoals grijswaarden toe te passen voordat u het eindresultaat opslaat. Als je de PHP GD-bibliotheek nog nooit eerder hebt gebruikt, zou ik willen voorstellen dat je dit GD-inleidende artikel leest voordat je dit leest.

In deze tutorial leren we over veel meer nuttige functies in GD en hoe deze kunnen worden gebruikt om meer van onze beeldmanipulatie taken te automatiseren.

Afbeeldingen manipuleren met behulp van een convolutiematrix

Behalve de pixels aan de randen, is elke pixel in een afbeelding omringd door acht andere pixels. Effecten zoals vervaging of randdetectie worden voor elke pixel berekend, afhankelijk van de waarde van die pixel en de waarden van de omringende pixels. Bij randdetectie impliceert een scherpe kleurverandering bijvoorbeeld dat we de rand van een object in de afbeelding hebben bereikt. Een plotselinge verandering van wit naar bruin in de onderstaande afbeelding betekent bijvoorbeeld de grens van de beker en de tafel.

Een eenvoudige manier om dit soort filter op te geven, is met wat een "convolutiematrix" wordt genoemd. GD levert het imageconvolution ($ afbeelding, $ matrix, $ div, $ offset) functie om een ​​3x3 convolutiematrix toe te passen op een beeldresource image $

De $ matrix parameter is een array van drie arrays, die elk drie floatwaarden bevatten, d.w.z. het is een 3x3 matrix. Het eerste element van de eerste array wordt vermenigvuldigd met de kleurwaarde van de pixel linksboven. Evenzo wordt het tweede element van de eerste array vermenigvuldigd met de kleurwaarde van de pixel direct boven de centrale pixel. De uiteindelijke kleur van de pixel wordt verkregen door het resultaat van al deze vermenigvuldigingen toe te voegen en deze vervolgens te delen door $ div voor normalisatie. Normalisatie houdt over het algemeen de uiteindelijke kleurwaarde onder 255.

Zoals we hebben gezien, de $ div parameter wordt gebruikt als een deler voor het resultaat van convolutie om de waarde te normaliseren. De $ offset parameter, aan de andere kant, wordt gebruikt om een ​​offsetwaarde voor alle kleuren op te geven. In de onderstaande voorbeelden ziet u hoe dit van invloed is op het eindresultaat.

Voorbeelden van convolutie

Hier is een lijst van enkele verschillende convolutiematrices die we hebben toegepast op de afbeelding van een kopje op een tafel.

Box Blur

$ box_blur = array ([1, 1, 1], [1, 1, 1], [1, 1, 1]); imageconvolution ($ im_php, $ box_blur, 9, 0);

Box blur werkt door slechts elke pixel met zijn buren te middelen. We stellen de waarde van de deler in op 9 omdat de som van alle elementen in de drie arrays 9 is.

verscherpen 

$ sharpen = array ([0, -1, 0], [-1, 5, -1], [0, -1, 0]); imageconvolution ($ im_php, $ verscherpen, 1, 0); 

Verscherpen werkt door de verschillen tussen elke pixel en zijn buren te overdrijven. Dit maakt de randen een beetje duidelijker. In het geval van verscherpen is de deler nog steeds 1 omdat de som van alle elementen in de drie arrays 1 is. 

in reliëf maken

$ emboss = array ([- 2, -1, 0], [-1, 1, 1], [0, 1, 2]); imageconvolution ($ im_php, $ emboss, 1, 0);

De matrix met reliëf is vergelijkbaar met de verscherpen matrix, behalve dat de waarden negatief zijn naar linksboven en positief naar rechtsonder - dat is wat het reliëfeffect creëert. De som van alle elementen in het geval van de emboss convolutie matrix is ​​1, dus we hoeven ons geen zorgen te maken over normalisatie of kleuroffset.

Rand detectie

$ edge_detect = array ([- 1, -1, -1], [-1, 8, -1], [-1, -1, -1]); imageconvolution ($ im_php, $ edge_detect, 1, 0); imageconvolution ($ im_php, $ edge_detect, 1, 255); 

Randdetectie lijkt op verscherpen, maar het effect is nog sterker. Ook krijgt de oorspronkelijke waarde van het beeld niet meer gewicht dan de buren - dat betekent dat we alleen om de randen geven, niet om de originele, effen gekleurde gebieden. 

Met randdetectie is de som van alle array-elementen 0. Dit betekent dat de afbeelding die we zullen krijgen meestal zwart is tenzij er een scherpe kleurverandering is, die meestal voorkomt aan de randen van objecten. De meestal zwarte afbeelding kan in wit worden omgezet door de parameter offset in te stellen op 255.

De volgende afbeelding toont het resultaat van al deze convolutiematrices.

Functies afbeelding kopiëren

PHP GD heeft veel functies om een ​​deel van een afbeelding te kopiëren en het formaat van de afbeelding aan te passen of samen te voegen. Wanneer u deze functies gebruikt, is het belangrijk om te onthouden dat PHP de linkerbovenhoek van een beeldresource als zijn oorsprong beschouwt. Een positief X waarde zal je naar de rechterkant van de afbeelding brengen, en een positieve Y waarde zal je verder omlaag brengen.

De eenvoudigste van deze functies is imagecopy ($ dst_im, $ src_im, $ dst_x, $ dst_y, $ src_x, $ src_y, $ src_w, $ src_h). Het kopieert de bronafbeelding naar een bestemmingsafbeelding. De $ dst_x en $ dst_y parameters bepalen de linkerbovenhoek, waar de gekopieerde afbeelding wordt geplakt. De $ src_x, $ src_y, $ src_w, en $ src_h parameters bepalen het rechthoekige gedeelte van de bronafbeelding, die naar de bestemming wordt gekopieerd.

U kunt deze functie gebruiken om afbeeldingen bij te snijden door vanuit het niets een afbeelding te maken met imagecreatetruecolor () en het kopiëren van de crop-rechthoek van de bronafbeelding erin. Je kunt het ook gebruiken om watermerken toe te voegen aan afbeeldingen, maar je moet onthouden dat met deze methode de grootte van het watermerk niet kan worden aangepast aan de grootte van onze afbeeldingen.

Een oplossing voor dit probleem is het gebruik van de imagecopyresized ($ dst_im, $ src_im, $ dst_x, $ dst_y, $ src_x, $ src_y, $ dst_w, $ dst_h, $ src_w, $ src_h) functie. Het accepteert alle parameters van imagecopy () en twee extra parameters om de grootte van het bestemmingsgebied te bepalen waar de bronafbeelding zal worden gekopieerd.

De imagecopyresized () De functie is niet perfect, omdat het beeld niet op en top wordt geschaald. U kunt echter een betere kwaliteit aanpassen met behulp van de imagecopyresampled () functie, die alle dezelfde parameters accepteert.

Kopieer met transparantie

Er zijn nog twee functies gerelateerd aan het kopiëren van afbeeldingen die u erg handig zult vinden: imagecopymerge () en imagecopymergegray ().

De functie imagecopymerge ($ dst_im, $ src_im, $ dst_x, $ dst_y, $ src_x, $ src_y, $ src_w, $ src_h, $ pct) is gelijkaardig aan imagecopy (), waar de extra $ pct parameter bepaalt de transparantie van de gekopieerde afbeelding. Een waarde van 0 betekent geen transparantie en een waarde van 100 betekent volledige transparantie. Dit zal van grote hulp zijn wanneer u de inhoud van de hoofdafbeelding achter uw watermerk niet volledig wilt verbergen.

De imagecopymergegray () De functie gebruikt de laatste parameter daarentegen om de bronafbeelding in grijswaarden om te zetten. Als deze is ingesteld op 0, verliest de bronafbeelding alle kleuren. Als deze is ingesteld op 100, blijft de bronafbeelding ongewijzigd.

Voorbeeld van kopie kopiëren

Het volgende voorbeeld gebruikt de imagecopy () functie om de rechter helft van een afbeelding in negatief te zetten. We hebben al andere functies besproken, zoals ImageFilter () en Schaal afbeelding () gebruikt in dit codefragment in de vorige zelfstudie.

$ im_php = imagecreatefromjpeg ('fish-mosaic.jpg'); $ im_php = imagescale ($ im_php, 800); $ im_php_inv = imagescale ($ im_php, 800); $ im_width = imagesx ($ im_php); $ im_height = imagesy ($ im_php); afbeeldingsfilter ($ im_php_inv, IMG_FILTER_NEGATE); imagecopy ($ im_php, $ im_php_inv, $ im_width / 2, 0, $ im_width / 2, 0, $ im_width / 2, $ im_height); $ new_name = 'fish-mosaic-half-negate.jpg'; imagejpeg ($ im_php, $ nieuwe_naam);

Hier maken we twee exemplaren van de originele afbeelding, waarvan elk is verkleind tot 800 pixels breed. Daarna gebruiken we de ImageFilter () functie om een ​​negatief van de te maken $ img_php_inv beeldbron. De rechter helft van deze negatieve afbeelding wordt vervolgens gekopieerd naar de originele afbeelding met behulp van de imagecopy () functie.

Dit was een zeer basaal gebruik van de imagecopy () functie. U kunt de resultaten hieronder bekijken. U kunt de afbeelding ook in kleinere delen of strepen verdelen om interessantere beeldeffecten te creëren. We zullen de gebruiken imagecopymergegray () functie in het onderstaande codefragment om veel meer strepen in het oorspronkelijke visbeeld te creëren.

$ im_php = imagecreatefromjpeg ('fish-mosaic.jpg'); $ im_php = imagescale ($ im_php, 800); $ im_php_bw = imagescale ($ im_php, 800); $ im_width = imagesx ($ im_php); $ im_height = imagesy ($ im_php); $ strepen = 200; voor ($ i = 0; $ i < $stripes; $i++)  if($i%2 == 0)  imagecopymergegray($im_php, $im_php_bw, $i*$im_width/$stripes, 0, $i*$im_width/$stripes, 0, $im_width/$stripes, $im_height, 0);  else  imagecopymergegray($im_php, $im_php_bw, $i*$im_width/$stripes, 0, $i*$im_width/$stripes, 0, $im_width/$stripes, $im_height, 100);   imagefilter($im_php, IMG_FILTER_CONTRAST, -255); imagefilter($im_php, IMG_FILTER_COLORIZE, 250, 0, 0, 100); $new_name = 'fish-mosaic-stripes.jpg'; imagejpeg($im_php, $new_name);

In het bovenstaande codevoorbeeld wordt een vergelijkbare strategie gebruikt als in het vorige voorbeeld, maar deze keer hebben we de afbeelding opgedeeld in kleinere strepen, die in grijswaarden zijn omgezet of ongewijzigd zijn gebleven op basis van de waarde van de variabele $ i. Nadat alle kopieer samenvoegbewerkingen zijn voltooid, passen we twee filters op de afbeelding toe om de strepen te laten opvallen.

De volgende afbeelding toont het eindresultaat van deze twee functies in combinatie met verschillende afbeeldingsfilters.

Insluiten van watermerken of andere informatie in afbeeldingen

Sommige organisaties voegen watermerken toe aan hun afbeeldingen om duidelijk te maken dat ze de eigenaar van de afbeelding zijn. Het helpt ook bij het herkennen van het merk en ontmoedigt andere mensen van het flagrant kopiëren van de afbeeldingen. Dankzij PHP GD is het maken van watermerken een eenvoudige taak.

$ im_php = imagecreatefromjpeg ('waterfall.jpg'); $ watermark = imagecreatefrompng ('watermark.png'); $ im_width = imagesx ($ im_php); $ im_height = imagesy ($ im_php); $ watermark = imagescale ($ watermark, $ im_width / 5); $ wt_width = imagesx ($ watermerk); $ wt_height = imagesy ($ watermerk); imagecopy ($ im_php, $ watermark, 0.95 * $ im_width - $ wt_width, 0.95 * $ im_height - $ wt_height, 0, 0, $ wt_width, $ wt_height); $ new_name = 'waterfall-watermark.jpg'; imagejpeg ($ im_php, $ nieuwe_naam);

In het bovenstaande codefragment hebben we twee verschillende beeldbronnen gebruikt imagecreatefromjpeg () voor de hoofdafbeelding en imagecreatefrompng () voor het watermerk respectievelijk. We bepalen de breedte en hoogte van het hoofdbeeld met behulp van de imagesx () en imagesy () functies.

Niet alle afbeeldingen die u wilt watermerk hebben dezelfde afmetingen. Als u het formaat van het watermerk niet wijzigt op basis van de afmetingen van de hoofdafbeelding, ziet het er misschien raar uit. Een watermerk van 200px ziet er bijvoorbeeld goed uit op een afbeelding van 1000 px, maar het zal te groot zijn voor een afbeelding met een breedte van 600px en het lijkt te klein op een 2400px breed beeld.

Daarom gebruiken we de Schaal afbeelding () functie om het watermerk altijd op één vijfde van de originele beeldbreedte te houden. We gebruiken dan de imagecopy () functie om het watermerk op de juiste locatie te plaatsen. Dit is het eindresultaat van het bovenstaande codefragment.

Naast watermerken kunt u ook andere informatie toevoegen, zoals de plaats waar een foto werd genomen of de tijd dat een foto werd genomen.

Laatste gedachten

Na de basisbeginselen van beeldmanipulatie te hebben behandeld in onze vorige zelfstudie, leerden we over enkele andere nuttige functies in de GD-bibliotheek. In het eerste deel van de tutorial is besproken hoe we afbeeldingen in PHP kunnen manipuleren met behulp van de convolutiematrix. Ik heb ook enkele voorbeelden getoond van de convolutiematrixbewerking om u te helpen begrijpen hoe PHP de kleurwaarden van verschillende pixels bereikt.

In het tweede deel van de zelfstudie werd uitgelegd hoe je een deel van een afbeelding kopieert en / of vergroot of verkleint om deze ergens anders te plakken. Dit is handig als we iets willen toevoegen aan een afbeelding zoals een watermerk of een tijdstempel.

Probeer al deze functies te gebruiken om een ​​aantal interessante afbeeldingseffecten te creëren!