Cacher une signature dans une image

Contenu du snippet

Voilà, plus un tut de stégano qu'un code: Comment dissimuler une image signature dans une autre image... à quoi ça sert? Ben à publier vos photos de vacances en étant capable de prouver que vous en êtes le proprio si quelqu'un vous les pique pour son site!

Ce code n'est pas utilisable en l'état, il faut customizer, adapter, ...

Source / Exemple :


<?php
// comment prouver qu'on a bien proprio d'une image??? En la signant!
// voici le principe de base, il s'agit ensuite de crypter la moindre et d'optimiser les fonctions.

// provient d'un formulaire par exemple
$signature = 'copyright CS'; 

// pour faire lisible
$signature = '* '.$signature.' *'; 

// on récupère la taille de l'image à signer qui est image.jpg ici
// (image dans mon répertoire courant en l'occurence)
$im_prot = imagecreatefromjpeg('image.jpg'); 
list($width,$height) = getimagesize('image.jpg');

// on crée la signature en fonction. 
// Il s'agit d'une image en noir et blanc avec le message $signature en redondance
// (ceux qui suivent comprendront pourquoi l'image DOIT être en noir et blanc...)
$sig= imagecreate($width, $height); 
$bg = imagecolorallocate($sig, 255, 255, 255);
$tc  = imagecolorallocate($sig, 0, 0, 0);

// Pour la redondance, on part du principe qu'un caractère prend 5 pixels de large et 10 de haut
$sig_size = round($width/(strlen($signature)*5));
for ($i = 0;$i< $sig_size;$i++) $signature .= $signature;

$sig_size = round($height/10);
for ($i = 0;$i< $sig_size;$i++) imagestring($sig, 1, 5, 5+$i*10, $signature, $tc);

// l'image de signature est prête.
imagepng($sig,'sig.png'); 

// on va signer...
$image = imagecreatetruecolor($width,$height); 

// et pour ceux qui ont séché les cours d'algèbre... tant pis :o)

for ($i=0;$i<$width;$i++) {
    for ($j=0;$j<$height;$j++) {

	// on récupère rgb de l'image à signer
        	$rgb = imagecolorat($im_prot,$i,$j); 
	$r=($rgb>>16)&0xFF;
	$g=($rgb>>8)&0xFF;
	$b=$rgb&0xFF;

	// et celui de la signature
	$rgb = imagecolorat($sig,$i,$j); 

	// si c'est 0 on met le bit de droite à 0 à r, g et b (rappel: 8 bits chacun)
	if ($rgb == 0){ 

		// xxxxxxx0 AND 11111110 = xxxxxxx0 
		// xxxxxxx1 AND 11111110 = xxxxxxx0 

		$r = $r&0xFE;
		$g = $g&0xFE;
		$b = $b&0xFE;

	// si c'est 1, on met le bit de droite à 1 à r, g et b
	} else {
		// xxxxxxx0 OR 00000001 = xxxxxxx1 
		// xxxxxxx1 OR 00000001 = xxxxxxx1

	    	$r=$r|1;
	    	$g=$g|1;
	    	$b=$b|1;
	}
	$color = imagecolorallocate($image,$r,$g,$b);
	imagesetpixel($image,$i,$j,$color);
    	}
}

// voici l'image portant la signature
imagepng($image, 'signed.png'); 

/**********************************************************************************************/

// Maintenant, on va faire le chemin inverse et récupérer la signature dissimulée

$protected_pic = imagecreatefrompng('signed.png');
list($width,$height) = getimagesize('signed.png');

$restored_sig = imagecreatetruecolor($width,$height);

for ($i=0;$i<$width;$i++) {
    for ($j=0;$j<$height;$j++) {

	$rgb=imagecolorat($protected_pic,$i,$j);

	// on regarde chaque rgb,
	// si xxxxxxxy & 1 = 0, c'est que le dernier bit y est à 0.
	// si xxxxxxxy & 1 = 1, c'est que le dernier bit y est à 1.

	$r=($rgb>>16)&0xFF;
	$g=($rgb>>8)&0xFF;
	$b=$rgb&0xFF;

	// on fait donc comme avant, mais dans l'autre sens!
	if(($r&1)==0) $r=255;else $r=0;
	if(($g&1)==0) $g=255;else $g=0;
	if(($b&1)==0) $b=255;else $b=0;

        $color=imagecolorallocate($restored_sig,$r,$g,$b);
        imagesetpixel($restored_sig,$i,$j,$color);
    	}
}

imagepng($restored_sig,'back.png'); // et voilà !

// affichage des résultats. Cf image accompagnat la image pour voir un résultat
echo '<table><tr><td>Image à dissimuler<br /><img src="sig.png"></td><td>Image à protéger<br /><img src="image.jpg"></td></tr>';
echo '<tr><td>Image protégée<br /><img src="signed.png"></td><td>Signature récupérée<br /><img src="back.png"></td></tr></table>';
?>

A voir également

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.