VichUploader и CroppieJS: как отправить обрезанное изображение base64 для сохранения в Symfony 4 - PullRequest
0 голосов
/ 24 января 2019

У меня есть небольшое приложение Symfony 4 с кроппером, использующим CroppieJS. Когда я обрезаю и нажимаю кнопку сохранения, Кроппи посылает мне изображение base64:

 $( "#cropSave" ).click(function() {
    basic.croppie('result','canvas'
    ).then(function (result) {}

как отправить этот результат на мой контроллер и сохранить образ с помощью VichUploader и Doctrine?

Вот мой контроллер:

public function updateProfilePicture(Request $request): Response
{
    $this->denyAccessUnlessGranted('IS_AUTHENTICATED_FULLY');
    $user = $this->getUser();
    $entityManager = $this->getDoctrine()->getManager();
    $user->setImageFile($request->files->get('image'));
    $entityManager->flush();
    return new Response("ok");
}

Я много чего пробовал, но мне не хватает опыта, потому что это не работает:

var form = document.getElementById("myAwesomeForm");
var ImageURL = result;
// Split the base64 string in data and contentType
var block = ImageURL.split(";");
// Get the content type of the image
var contentType = block[0].split(":")[1];
// get the real base64 content of the file
var realData = block[1].split(",")[1];
// Convert it to a blob to upload
var blob = b64toBlob(realData, contentType);
// Create a FormData and append the file with "image" as parameter name
var formDataToUpload = new FormData(form);
formDataToUpload.append("image", blob);

или

function urltoFile(url, filename, mimeType){
return (fetch(url)
    .then(function(res){return res.arrayBuffer();})
    .then(function(buf){return new File([buf], filename, {type:mimeType});})
);
}

вот один из моих запросов ajax:

$.ajax({
    type : "POST",
    data: formDataToUpload,
    url : $('#updateProfilePictureLink').val(),
    contentType:false,
    processData:false,
    cache:false,
    dataType:"json",
    success : function(response) {
        $('#profilePicture').attr('src', result);
        alert(response);
    },
    error : function (response) {
        alert("error !");
    }
});

Я подумал, может быть, "Имитировать" загрузку файла в JS из base64, используя поле ввода VichUploader formType, но я хочу знать, есть ли более простые способы.

Спасибо

1 Ответ

0 голосов
/ 25 января 2019

Мне удалось обойти это благодаря Ронни Хинту. Вы должны:

  • использовать JS FormData
  • положить каплю внутрь
  • восстановить его в контроллере Symfony как изображение
  • сохранить как есть

Но вы должны реализовать сериализуемость на объекте вашего изображения (сериализовать и десериализовать все поля, если это не нарушит ваши другие функции).

Вот пример рабочего кода:

// JS
$( "#cropSave" ).click(function() {
    alert("click !");
    basic.croppie('result','blob'
    ).then(function (result) {
        var fd = new FormData();
        //Third parameter is the blob name
        fd.append('data', 
        result,$('#userId').val()+"."+result.type.split("/")[1]);
            $.ajax({
            type: 'POST',
            url : $('#updateProfilePictureLink').val(),
            data: fd,
            processData: false,
            contentType: false
        }).done(function(data) {
            // your things
        });

// PHP

// Controller
try {
    $this->denyAccessUnlessGranted('IS_AUTHENTICATED_FULLY');
    $user = $this->getUser();
    $entityManager = $this->getDoctrine()->getManager();
    $user->setImageFile($request->files->get('data'));
    $entityManager->flush();
}
catch (exception $e) {
}

// Entity
class User implements UserInterface, \Serializable
{

/** @see \Serializable::serialize() */
public function serialize()
{
    return serialize(array(
        $this->id,
        $this->profilePicture,
        $this->email,
        $this->password
    ));
}
/** @see \Serializable::unserialize() */
public function unserialize($serialized)
{
    list (
        $this->id,
        $this->profilePicture,
        $this->email,
        $this->password
        ) = unserialize($serialized);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...