Estou trabalhando em um projeto de arte generativo em que gostaria de permitir que os usuários salvem as imagens resultantes de um algoritmo. A ideia geral é:
- Crie uma imagem em uma tela HTML5 usando um algoritmo generativo
- Quando a imagem estiver concluída, permita aos usuários salvar a tela como um arquivo de imagem no servidor
- Permita que o usuário baixe a imagem ou adicione-a a uma galeria de peças produzidas usando o algoritmo.
No entanto, estou preso no segundo passo. Depois de alguma ajuda do Google, encontrei esta postagem no blog , que parecia exatamente o que eu queria:
O que levou ao código 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);
}
e PHP correspondente (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);
}
?>
Mas isso parece não fazer nada.
Mais pesquisas no Google aparecem nesta postagem do blog, baseada no tutorial anterior. Não é muito diferente, mas talvez vale a pena tentar:
$data = $_POST['imgData'];
$file = "/path/to/file.png";
$uri = substr($data,strpos($data, ",") + 1);
file_put_contents($file, base64_decode($uri));
echo $file;
Este cria um arquivo (yay), mas está corrompido e parece não conter nada. Também parece estar vazio (tamanho do arquivo 0).
Existe algo realmente óbvio que estou fazendo de errado? O caminho em que estou armazenando meu arquivo é gravável, portanto isso não é um problema, mas nada parece estar acontecendo e não tenho muita certeza de como depurar isso.
Editar
Seguindo o link de Salvidor Dali, alterei a solicitação do AJAX para:
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);
}
E agora o arquivo de imagem é criado e não está vazio! Parece que o tipo de conteúdo é importante e que a alteração para x-www-form-urlencoded
permitir o envio dos dados da imagem.
O console retorna a sequência (bastante grande) do código base64 e o arquivo de dados é ~ 140 kB. No entanto, ainda não consigo abri-lo e parece não estar formatado como uma imagem.
$data
no segundo código php), tudo o que é retornado é uma linha em branco. Por que isso seria? Parece que talvez os dados enviados não é correto, mas parece que eu estou enviando-o assim como os exemplos mostram ...
DataUriUpload
componente. Está documentado aqui e vem com vários meios adicionais de validação e reforço da segurança.
ajax.send(canvasData );
enquanto você usaajax.send("imgData="+canvasData);
. Portanto$GLOBALS["HTTP_RAW_POST_DATA"]
, não será o que você espera, você provavelmente deve usar$_POST['imgData']
.