2

This is the same question asked before and the answer is also verified but in My Project I am using WebApi 2 and want return image from Ihttpactionresult

I have searched and lot and done some code Which I don't know if I am doing right..

I also Looked at ImageReizer but it saves the resized Images in the folder. Idon't want to save the Image.

Here is My Controller Action

  [HttpGet]
    [Route("GetFile")]
    public IHttpActionResult GetFile(string filename, int w = 0, int h = 0)
    {
        //string filePath = "fdsafsa";
        //int width = 0;
        //var fileStream = File.Open("/ProjectFiles", FileMode.Open);
        //var content = new StreamContent(fileStream);
        //content.Headers.ContentType = new MediaTypeHeaderValue("png");

        var imageFile = HttpContext.Current.Server.MapPath(@filename);
        if(File.Exists(imageFile))
        {
            var srcImage = Image.FromFile(imageFile);
            var newImage = new Bitmap(w, h);
            var graphics = Graphics.FromImage(newImage);
            var stream = new MemoryStream();
            graphics.SmoothingMode = SmoothingMode.AntiAlias;
            graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
            graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;
            graphics.DrawImage(srcImage, new Rectangle(0, 0, w, h));
            newImage.Save(stream, ImageFormat.Png);
            //var content = new StreamContent(stream);

            HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
            result.Content = new ByteArrayContent(stream.ToArray());
            result.Content.Headers.ContentType = new MediaTypeHeaderValue("image/png");

            return Ok(result);
        }

This is the html where I want to render the Image

<img src="/api/Public/GetFile?filename=/ProjectFiles/Project_2087/art-therapy-career2_73937984-7e03-4067-91bf-2dd4fc10b328.jpg&w=100&h=100" alt="image" />

How can I show the resized Image dynamically without storing the resize image on the server. I don't want to save the resize Images.

I need help soon.

Thanks for your help.

Another approach ......

 [HttpGet]
    [Route("GetFileStream")]
    public IHttpActionResult GetFileStream(string filename, int w = 0, int h = 0)
    {
        var imagePath = HttpContext.Current.Server.MapPath(@filename);
        var result = getResizedImage(imagePath, w, h);
        return Ok(result);
    }


 byte[] getResizedImage(String path, int width, int height)
    {
        Bitmap imgIn = new Bitmap(path);
        double y = imgIn.Height;
        double x = imgIn.Width;

        double factor = 1;
        if (width > 0)
        {
            factor = width / x;
        }
        else if (height > 0)
        {
            factor = height / y;
        }
        System.IO.MemoryStream outStream = new System.IO.MemoryStream();
        Bitmap imgOut = new Bitmap((int)(x * factor), (int)(y * factor));
        Graphics g = Graphics.FromImage(imgOut);
        g.Clear(Color.White);

        g.DrawImage(imgIn, new Rectangle(0, 0, (int)(factor * x), (int)(factor * y)), new Rectangle(0, 0, (int)x, (int)y), GraphicsUnit.Pixel);

        imgOut.Save(outStream, getImageFormat(path));
        return outStream.ToArray();
    }

**

This is the Working Code with Mvc

**

This is the code I found working for Simple Mvc Application

An Action

public ActionResult Thumb(string filename = "Azalea.jpg", int w = 0, int h = 0)
    {
        string path = Path.Combine(Server.MapPath("~/images2"), filename);
        //Bitmap bitmap = new Bitmap(filepath);
        //if (bitmap == null)
        //{
        //    return new EmptyResult();
        //}

        //MemoryStream ms = new MemoryStream();
        //bitmap.Save(ms, System.Drawing.Imaging.ImageFormat.Png);
        Bitmap imgIn = new Bitmap(path);
        double y = imgIn.Height;
        double x = imgIn.Width;

        double factor = 1;
        if (w > 0)
        {
            factor = w / x;
        }
        else if (h > 0)
        {
            factor = h / y;
        }
        System.IO.MemoryStream outStream = new System.IO.MemoryStream();
        Bitmap imgOut = new Bitmap((int)(x * factor), (int)(y * factor));
        Graphics g = Graphics.FromImage(imgOut);
        g.Clear(Color.White);

        g.DrawImage(imgIn, new Rectangle(0, 0, (int)(factor * x), (int)(factor * y)), new Rectangle(0, 0, (int)x, (int)y), GraphicsUnit.Pixel);

        imgOut.Save(outStream, getImageFormat(path));
        outStream.Seek(0, SeekOrigin.Begin);
        FileStreamResult fileStreamResult = new FileStreamResult(outStream, "image/png");
        return fileStreamResult;
    }

In cshtml page

   <img src="~/Home/Thumb/@Model.ImageName?w=700&h=300" alt="image" />

How to use this With web Api2 ?

Answer of My Question after long search.Please Improve this

  [HttpGet]
    [Route("GetFileStream")]
    public IHttpActionResult GetFileStream(string filename, int w = 0, int h = 0)
    {
        var imagePath = HttpContext.Current.Server.MapPath(@filename);
        return new FileResult(imagePath, w, h, "image/jpeg");
    }

    public class FileResult : IHttpActionResult
    {
        private readonly string filePath;
        private readonly string contentType;
        private readonly int width;
        private readonly int height;

        public FileResult(string filePath, int width, int height, string contentType = null)
        {
            this.filePath = filePath;
            this.contentType = contentType;
            this.width = width;
            this.height = height;
        }

        public Task<HttpResponseMessage> ExecuteAsync(CancellationToken cancellationToken)
        {
            return Task.Run(() =>
            {
                var result = getResizedImage(filePath, width, height);
                var response = new HttpResponseMessage(HttpStatusCode.OK)
                {
                    Content = new ByteArrayContent(result)
                    //Content = new StreamContent(File.OpenRead(filePath))
                };

                var contentType = this.contentType ?? MimeMapping.GetMimeMapping(Path.GetExtension(filePath));
                response.Content.Headers.ContentType = new MediaTypeHeaderValue(contentType);

                return response;
            }, cancellationToken);
        }
    }

  static byte[] getResizedImage(String path, int width, int height)
    {
        Bitmap imgIn = new Bitmap(path);
        double y = imgIn.Height;
        double x = imgIn.Width;

        double factor = 1;
        if (width > 0)
        {
            factor = width / x;
        }
        else if (height > 0)
        {
            factor = height / y;
        }
        System.IO.MemoryStream outStream = new System.IO.MemoryStream();
        Bitmap imgOut = new Bitmap((int)(x * factor), (int)(y * factor));
        Graphics g = Graphics.FromImage(imgOut);
        g.Clear(Color.White);

        g.DrawImage(imgIn, new Rectangle(0, 0, (int)(factor * x), (int)(factor * y)), new Rectangle(0, 0, (int)x, (int)y), GraphicsUnit.Pixel);

        imgOut.Save(outStream, getImageFormat(path));
        //outStream.Seek(0, SeekOrigin.Begin);
        //System.Web.Mvc.FileStreamResult fileStreamResult = new System.Web.Mvc.FileStreamResult(outStream, "image/png");
        //return fileStreamResult;
        return outStream.ToArray();
    }

    string getContentType(String path)
    {
        switch (Path.GetExtension(path))
        {
            case ".bmp": return "Image/bmp";
            case ".gif": return "Image/gif";
            case ".jpg": return "Image/jpeg";
            case ".png": return "Image/png";
            default: break;
        }
        return "";
    }

    static ImageFormat getImageFormat(String path)
    {
        switch (Path.GetExtension(path))
        {
            case ".bmp": return ImageFormat.Bmp;
            case ".gif": return ImageFormat.Gif;
            case ".jpg": return ImageFormat.Jpeg;
            case ".png": return ImageFormat.Png;
            default: break;
        }
        return ImageFormat.Jpeg;
    }

Please Help in improving this answer,

Thanks, Sanuj

Community
  • 1
  • 1
Sa Nuj
  • 103
  • 10
  • I don't know what should I return so it can display Image in html Img tag. – Sa Nuj May 19 '16 at 12:32
  • Be carefull with resizing images on the fly, this is not fast operation (there are old GDI functions under the hood) and can easily be a performance bottleneck. You may add some sort of server-side caching to eliminate possible performance issues. – AndrewSilver May 19 '16 at 12:40
  • I have looked at Imageresizer handler which works great.. but the reason I am not using is because I don't want to store Images and it cached images. – Sa Nuj May 19 '16 at 12:49
  • HI after a long research and development I found the solution which I am posting in my question bczzz I don't have privilage to post answers. – Sa Nuj May 19 '16 at 14:46

1 Answers1

0

You can pass your byteArray to View, then use something like this:

Create your image model:

public class ImageData
{
    public string Name { get; set; }
    public byte[] Content { get; set; }
    . . .
}

Then in controller assign and return your model to View():

@{
    string imageBase = Convert.ToBase64String(Model.ImageContent);
    string imageSource = string.Format("data:image/gif;base64,{0}", imageBase);
}
<img src="@imageSource" alt="@Model.ImageName" width="100" height="100" />
SᴇM
  • 7,024
  • 3
  • 24
  • 41