3
votes

I have the following function which I use to upload files to an azure storage account.

As you will see it does no kind of resizing etc:

public string UploadToCloud(FileUpload fup, string containerName) { // Retrieve storage account from connection string. CloudStorageAccount storageAccount = CloudStorageAccount.Parse(ConfigurationManager.AppSettings["StorageConnectionString"]);

    // Create the blob client.
    CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();

    // Retrieve a reference to a container. 
    CloudBlobContainer container = blobClient.GetContainerReference(containerName);

    string newName = "";
    string ext = "";
    CloudBlockBlob blob = null;


    // Create the container if it doesn't already exist.
    container.CreateIfNotExists();

    newName = "";
    ext = Path.GetExtension(fup.FileName);

    newName = string.Concat(Guid.NewGuid(), ext);

    blob = container.GetBlockBlobReference(newName);

    blob.Properties.ContentType = fup.PostedFile.ContentType;

    //S5: Upload the File as ByteArray            
    blob.UploadFromStream(fup.FileContent);

    return newName;


}

I then have this function which I have used on sites not hosted on azure:

public string ResizeandSave(FileUpload fileUpload, int width, int height, bool deleteOriginal, string tempPath = @"~\tempimages\", string destPath = @"~\cmsgraphics\")
        {
            fileUpload.SaveAs(Server.MapPath(tempPath) + fileUpload.FileName);

            var fileExt = Path.GetExtension(fileUpload.FileName);
            var newFileName = Guid.NewGuid().ToString() + fileExt;

            var imageUrlRS = Server.MapPath(destPath) + newFileName;

            var i = new ImageResizer.ImageJob(Server.MapPath(tempPath) + fileUpload.FileName, imageUrlRS, new ImageResizer.ResizeSettings(
                            "width=" + width + ";height=" + height + ";format=jpg;quality=80;mode=max"));

            i.CreateParentDirectory = true; //Auto-create the uploads directory.
            i.Build();

            if (deleteOriginal)
            {
                var theFile = new FileInfo(Server.MapPath(tempPath) + fileUpload.FileName);

                if (theFile.Exists)
                {
                    File.Delete(Server.MapPath(tempPath) + fileUpload.FileName);
                }
            }

            return newFileName;
        }

Now what I am trying to do is try to merge the two... or at least work out a way of being able to resize an image before storing it on azure.

Anyone have any ideas?

2

2 Answers

1
votes

I hope you already make it work, but I was looking for some working solution today, any I can't find it. But finally i did it.

Here is my code, hope that it help to someone:

    /// <summary>
    /// Saving file to AzureStorage
    /// </summary>
    /// <param name="containerName">BLOB container name</param>
    /// <param name="MyFile">HttpPostedFile</param>
    public static string SaveFile(string containerName, HttpPostedFile MyFile, bool resize, int newWidth, int newHeight)
    {
        string fileName = string.Empty;

        try
        {
            CloudStorageAccount storageAccount = CloudStorageAccount.Parse(ConfigurationManager.ConnectionStrings["StorageConnectionString"].ConnectionString);
            CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
            CloudBlobContainer container = blobClient.GetContainerReference(containerName);
            container.CreateIfNotExists(BlobContainerPublicAccessType.Container);

            string timestamp = Helper.GetTimestamp() + "_";
            string fileExtension = System.IO.Path.GetExtension(MyFile.FileName).ToLower();
            fileName = timestamp + MyFile.FileName;

            CloudBlockBlob blockBlob = container.GetBlockBlobReference(fileName);
            blockBlob.Properties.ContentType = MimeTypeMap.GetMimeType(fileExtension);

            if (resize)
            {
                Bitmap bitmap = new Bitmap(MyFile.InputStream);

                int oldWidth = bitmap.Width;
                int oldHeight = bitmap.Height;

                GraphicsUnit units = System.Drawing.GraphicsUnit.Pixel;
                RectangleF r = bitmap.GetBounds(ref units);
                Size newSize = new Size();

                float expectedWidth = r.Width;
                float expectedHeight = r.Height;
                float dimesion = r.Width / r.Height;

                if (newWidth < r.Width)
                {
                    expectedWidth= newWidth;
                    expectedHeight = expectedWidth/ dimesion;
                }
                else if (newHeight < r.Height)
                {
                    expectedHeight = newHeight;
                    expectedWidth= dimesion * expectedHeight;
                }
                if (expectedWidth> newWidth)
                {
                    expectedWidth= newWidth;
                    expectedHeight = expectedHeight / expectedWidth;
                }
                else if (nPozadovanaVyska > newHeight)
                {
                    expectedHeight = newHeight;
                    expectedWidth= dimesion* expectedHeight;
                }
                newSize.Width = (int)Math.Round(expectedWidth);
                newSize.Height = (int)Math.Round(expectedHeight);

                Bitmap b = new Bitmap(bitmap, newSize);

                Image img = (Image)b;
                byte[] data = ImageToByte(img);

                blockBlob.UploadFromByteArray(data, 0, data.Length);
            }
            else
            {
                blockBlob.UploadFromStream(MyFile.InputStream);
            }                
        }
        catch
        {
            fileName = string.Empty;
        }

        return fileName;
    }

    /// <summary>
    /// Image to byte
    /// </summary>
    /// <param name="img">Image</param>
    /// <returns>byte array</returns>
    public static byte[] ImageToByte(Image img)
    {
        byte[] byteArray = new byte[0];
        using (MemoryStream stream = new MemoryStream())
        {
            img.Save(stream, System.Drawing.Imaging.ImageFormat.Png);
            stream.Close();

            byteArray = stream.ToArray();
        }
        return byteArray;
    }
0
votes

I do a resizing operation on a Windows Phone 8 app. As you can image the runtime for WP8 is much more limited compared to the whole .NET runtime, so there may be other options to do this more efficiently if you don't have the same limitations as I do.

public static void ResizeImageToUpload(Stream imageStream, PhotoResult e)
    {            
        int fixedImageWidthInPixels = 1024;
        int verticalRatio = 1;

        BitmapImage bitmap = new BitmapImage();
        bitmap.SetSource(e.ChosenPhoto);
        WriteableBitmap writeableBitmap = new WriteableBitmap(bitmap);
        if (bitmap.PixelWidth > fixedImageWidthInPixels)
            verticalRatio = bitmap.PixelWidth / fixedImageWidthInPixels;
        writeableBitmap.SaveJpeg(imageStream, fixedImageWidthInPixels,
            bitmap.PixelHeight / verticalRatio, 0, 80);                                       
    }

The code will resize the image if its width is larger than 1024 pixels. The variable verticalRatio is used to compute the proportion of the image so as not to lose its aspect ratio during the resizing. The code then encodes the new jpeg using 80% of the original image's quality.

Hope this helps