Je travaille sur un projet d'art génératif où j'aimerais permettre aux utilisateurs de sauvegarder les images résultantes d'un algorithme. L'idée générale est:
- Créer une image sur un canevas HTML5 à l'aide d'un algorithme génératif
- Une fois l'image terminée, autorisez les utilisateurs à enregistrer le canevas en tant que fichier image sur le serveur
- Permettez à l'utilisateur de télécharger l'image ou de l'ajouter à une galerie de pièces produites à l'aide de l'algorithme.
Cependant, je suis coincé sur la deuxième étape. Après un peu d'aide de Google, j'ai trouvé ce billet de blog , qui semblait être exactement ce que je voulais:
Ce qui a conduit au code JavaScript:
function saveImage() {
var canvasData = canvas.toDataURL("image/png");
var ajax = new XMLHttpRequest();
ajax.open("POST", "testSave.php", false);
ajax.onreadystatechange = function() {
console.log(ajax.responseText);
}
ajax.setRequestHeader("Content-Type", "application/upload");
ajax.send("imgData=" + canvasData);
}
et PHP correspondant (testSave.php):
<?php
if (isset($GLOBALS["HTTP_RAW_POST_DATA"])) {
$imageData = $GLOBALS['HTTP_RAW_POST_DATA'];
$filteredData = substr($imageData, strpos($imageData, ",") + 1);
$unencodedData = base64_decode($filteredData);
$fp = fopen('/path/to/file.png', 'wb');
fwrite($fp, $unencodedData);
fclose($fp);
}
?>
Mais cela ne semble rien faire du tout.
Plus Google recherche ce blog qui est basé sur le tutoriel précédent. Pas très différent, mais peut-être mérite un essai:
$data = $_POST['imgData'];
$file = "/path/to/file.png";
$uri = substr($data,strpos($data, ",") + 1);
file_put_contents($file, base64_decode($uri));
echo $file;
Celui-ci crée un fichier (ouais) mais il est corrompu et ne semble rien contenir. Il semble également être vide (taille de fichier de 0).
Y a-t-il quelque chose de vraiment évident que je fais mal? Le chemin où je stocke mon fichier est accessible en écriture, donc ce n'est pas un problème, mais rien ne semble se produire et je ne sais pas vraiment comment déboguer cela.
Éditer
Suite au lien de Salvidor Dali, j'ai changé la demande AJAX pour qu'elle soit:
function saveImage() {
var canvasData = canvas.toDataURL("image/png");
var xmlHttpReq = false;
if (window.XMLHttpRequest) {
ajax = new XMLHttpRequest();
}
else if (window.ActiveXObject) {
ajax = new ActiveXObject("Microsoft.XMLHTTP");
}
ajax.open("POST", "testSave.php", false);
ajax.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
ajax.onreadystatechange = function() {
console.log(ajax.responseText);
}
ajax.send("imgData=" + canvasData);
}
Et maintenant, le fichier image est créé et n'est pas vide! Il semble que le type de contenu soit important et que le changer pour x-www-form-urlencoded
autoriser l'envoi des données d'image.
La console renvoie la chaîne (plutôt volumineuse) de code base64 et le fichier de données est ~ 140 Ko. Cependant, je ne peux toujours pas l'ouvrir et il ne semble pas être formaté en tant qu'image.
$data
dans le deuxième code php), tout ce que je reçois est une ligne vierge. Pourquoi serait-ce? Il semble que les données envoyées ne soient peut-être pas correctes, mais il semble que je les envoie comme le montrent les exemples ...
DataUriUpload
composant à la place. Il est documenté ici et est livré avec plusieurs moyens supplémentaires de validation et d'application de la sécurité.
ajax.send(canvasData );
que vous avez fournies pendant que vous l'utilisezajax.send("imgData="+canvasData);
. Par conséquent,$GLOBALS["HTTP_RAW_POST_DATA"]
ce ne sera pas ce que vous attendez, vous devriez probablement l'utiliser$_POST['imgData']
.