Display an image contained in a byte[] with ASP.Net MVC3
Asked Answered
C

6

21

I've a view with a strong type. This strong type has a field consisting of a byte[], this array contains a picture.

Is it possible to display this image with something like @Html.Image(Model.myImage) ?

Thank you very much

Corticosteroid answered 18/5, 2011 at 6:51 Comment(0)
A
17

You can create a controller action method that returns an image as a FileContentResult:

public FileContentResult Display(string id) {
   byte[] byteArray = GetImageFromDB(id);
   return new FileContentResult(byteArray, "image/jpeg");
}

Then you can create an ActionLink to the action method in the view using the image id from the model.

Antipasto answered 18/5, 2011 at 17:20 Comment(6)
It's exactly this I needed, but I used a new File(...) not a FileContentResultCorticosteroid
@J4N, what do you mean by "use a new File(...)"?Zero
You can use the "File(...)" controller method but there is no "new"Antipasto
Note: for an image of any size, you would want to do this using a streaming API, deferring the iteration (via a moderate buffer) to the ActionResult.Costumer
@DmitryStarosta Would we strongly type the View to a "FileContentResult" object then?Unmannerly
The "ViewResult" object is the only one that requires a Razor/ASPX view. Other action result objects like the "FileContentResult" or "JsonResult" do not need a view.Antipasto
C
8

It depends on how big the image is. If it is small, you could write something to base-64 encode it and embed it in the html, like any of these.

For a concrete example from here:

<img src="data:image/gif;base64,R0lGODlhUAAPAKIAAAsLav///88PD9WqsYmApmZmZtZfYmdakyH5BAQUAP8ALAAAAABQAA8AAAPbWLrc/jDKSVe4OOvNu/9gqARDSRBHegyGMahqO4R0bQcjIQ8E4BMCQc930JluyGRmdAAcdiigMLVrApTYWy5FKM1IQe+Mp+L4rphz+qIOBAUYeCY4p2tGrJZeH9y79mZsawFoaIRxF3JyiYxuHiMGb5KTkpFvZj4ZbYeCiXaOiKBwnxh4fnt9e3ktgZyHhrChinONs3cFAShFF2JhvCZlG5uchYNun5eedRxMAF15XEFRXgZWWdciuM8GCmdSQ84lLQfY5R14wDB5Lyon4ubwS7jx9NcV9/j5+g4JADs=" alt="British Blog Directory" width="80" height="15">

If the image is of any appreciable size, you may want instead to write a route that allows lookup via some key to the image, i.e. a route like /images/{id} - in that route you fetch the image binary and use return File(bytes, contentType), additionally setting caching headers (and remember to re-check any necessary security). In your html you would just have an

<img src="/images/@imageId" ... />

(using razor syntax, but similar for aspx).

The separate route approach requires an additional hop to the server, but allows caching at the client (the inline base-64 approach puts the data on every request).

Costumer answered 18/5, 2011 at 7:6 Comment(3)
There is a good implementation of this contained in the code for ASP.Net Sprite and Image Optimization Framework (aspnet.codeplex.com/releases/view/65787)Zero
Thanks a lot! It was wonderful for me, because I had on-the-fly made image and I wanted to show it in ajax way. After some hours at last your suggestion solved my problem!Burgee
About the Route approach we can read here dotnetslackers.com/articles/aspnet/…Avitzur
I
8

If you already happen to have the image loaded in your model as a byte[] array you can do this as @Marc Gravell mentions in his answer:

<img src="data:image;base64,@System.Convert.ToBase64String(Model.Photo)" />

This greatly simplifies the whole process and you won't need to have a specific FileContentResult action method and hit the database again (see @Dmitry S's answer) just to fetch that byte[] array with your image/photo since you already have it loaded in your model.

Ignaz answered 27/9, 2013 at 3:37 Comment(0)
P
4

Sounds like you'd need a new action that gets the byte array (from a database?) and returns the image via the File method....

Then generate an anchor that points to that action, that way the image can be loaded while the page is loading, speeding up the display.

Pigskin answered 18/5, 2011 at 7:4 Comment(0)
S
0

I would design a simple generic handler for serving your images. This handler could, given some parameter, load images from the database, and write them to the http output stream.

public class UserImage : IHttpHandler
{
    public bool IsReusable
    {
        get { return false; }
    }

    public void ProcessRequest(HttpContext context)
    {
        context.Response.ContentType = "image/jpeg";

        // Get the stream from the database
        var image = System.Drawing.Image.FromStream(stream);

        image.Save(context.Response.OutputStream, ImageFormat.Jpeg);
    }
}
Sobriquet answered 18/5, 2011 at 8:32 Comment(1)
There is no point in loading and saving the image. You should just send the original stream.Feleciafeledy

© 2022 - 2024 — McMap. All rights reserved.