How to transform base64 image to File?

13

I am generating a canvas within my application, then I would like to upload what is believed in that canvas as a% png image to my server. The problem I'm having is that it goes up, obviously with weight but the image can not be seen.

The canvas is in base 64

var img_b64 = fotoFirmaService.getImagenFirma(); //base64 de la imagen
var png = img_b64.split(',')[1];
var the_file = new Blob([window.atob(png)], { type: 'image/png', encoding: 'utf-8' });
var imagen_firma = new File([the_file], 'imagen_firma.png', { type: 'image/png' });

When I print the value of imagen_firma I get:

File {
    lastModified : 1489088454413
    lastModifiedDate : Thu Mar 09 2017 16:40:54 GMT-0300 (CLT)
    name : "imagen_firma.png"
    size : 16926
    type : "image/png"
    webkitRelativePath : ""
}

However, the image on my server is empty. I do the same procedure with input type file, but upload correctly. I print the structure of those files and they are identical to this File but in this case it does not work.

EDIT

It is with this code that I upload the file to my server:

var payload = new FormData();
payload.append('file', imagen_firma);

$http({
    method: 'POST',
    url: 'dsaasas/UploadImage/' + imagen_firma.name,
    data: payload,
    headers: { 'Content-Type': undefined },
    transformRequest: angular.identity
}).then(function successCallback(response) {
    // this callback will be called asynchronously
    // when the response is available
    console.log("bien");
    console.log(response);
}, function errorCallback(response) {
    console.log(response);
    // called asynchronously if an error occurs
    // or server returns response with an error status.
});

And this is my C # code, it's with WCF

public string UploadImage(string fileName)
    {
        try
        {
            HttpPostedFile file = HttpContext.Current.Request.Files[0];
            if (file == null)
                return null;
            string targetFilePath = WebConfigurationManager.AppSettings["FilePath"] + fileName;
            file.SaveAs(targetFilePath);
            return "succ   " + file.FileName.ToString();

            //return fileName;
        }
        catch (Exception ex)
        {
            return ex.Message + " - " + ex.InnerException;

        }
    }
    
asked by sioesi 09.03.2017 в 20:43
source

2 answers

9

I have found 2 possible solutions:

  • Correct the binary code that is passed to Blob :

    Example:

    function fixBinary (bin) {
      var length = bin.length;
      var buf = new ArrayBuffer(length);
      var arr = new Uint8Array(buf);
      for (var i = 0; i < length; i++) {
        arr[i] = bin.charCodeAt(i);
      }
      return buf;
    }
    
    var img_b64 = fotoFirmaService.getImagenFirma(); //base64 de la imagen
    var png = img_b64.split(',')[1];
    var binary = fixBinary(window.atob(png));// <-- Usamos la fn "fixBinary"
    var the_file = new Blob([binary], {type: 'image/png'});// <-- Sacamos el encode
    var imagen_firma = new File([the_file], 'imagen_firma.png', { type: 'image/png' });
    

    Source: SOen - encode/decode image with base64 breaks image

  • Use canvas.toBlob() (see Polyfill )

    Example:

    /// Service fotoFirmaService
    
    // Creamos un nuevo método en servicio "fotoFirmaService"
    // el cual devolverá directamente el Blob
    getImagenFirmaBlob: function(format, quality) {
      var response;
      // "canvas" debe ser un "HTMLCanvasElement"
      canvas.toBlob(function(blob){
        response = blob;
      }, format, quality);
      return response;
    }
    
    /// Controller
    
    // Usando el nuevo método "getImagenFirmaBlob"
    var the_file = fotoFirmaService.getImagenFirmaBlob("image/png"); //blob de la imagen
    var imagen_firma = new File([the_file], 'imagen_firma.png');
    
answered by 13.03.2017 / 18:41
source
7

Also apply another solution that works well for me:

var blob = dataURItoBlob(fotoFirmaService.getImagenFirma());
var imagen_firma = new File([blob], 'imagen_firma.jpg', { type: 'image/jpg' });

And the function dataURItoBlob :

function dataURItoBlob(dataURI) {
    // convert base64/URLEncoded data component to raw binary data held in a string
    var byteString;
    if (dataURI.split(',')[0].indexOf('base64') >= 0)
        byteString = atob(dataURI.split(',')[1]);
    else
        byteString = unescape(dataURI.split(',')[1]);

    // separate out the mime component
    var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0];

    // write the bytes of the string to a typed array
    var ia = new Uint8Array(byteString.length);
    for (var i = 0; i < byteString.length; i++) {
        ia[i] = byteString.charCodeAt(i);
    }

    return new Blob([ia], { type: mimeString });
}
    
answered by 14.03.2017 в 12:47