将图像从 MVC 控制器渲染到屏幕

发布于 2024-10-20 09:43:11 字数 693 浏览 2 评论 0原文

我的数据库中有图像,我想返回图像以通过操作查看。这是我的行动。

public FileContentResult Index(ItemImageRequest request)
{
    var result = queueService.GetItemImage(request);

    if (result.TotalResults == 0)
        return File(new byte[0], "image/jpeg");

    var image = result.FirstResult;

    return File(image.Image, "image/tif");
}

我也尝试过此代码

public FileStreamResult Index(ItemImageRequest request)
{
    //retrieval omitted

    var image = result.FirstResult;

    System.IO.Stream stream = new System.IO.MemoryStream(image.Image);

    return new FileStreamResult(stream, "image/tif");
}

当我在浏览器中执行操作时,它会提示我下载。我不想下载它,我希望它显示在浏览器中。我该如何实现这个目标?

I have images in the database and I want to return the image for viewing from an action. Here's my action.

public FileContentResult Index(ItemImageRequest request)
{
    var result = queueService.GetItemImage(request);

    if (result.TotalResults == 0)
        return File(new byte[0], "image/jpeg");

    var image = result.FirstResult;

    return File(image.Image, "image/tif");
}

I have also tried this code

public FileStreamResult Index(ItemImageRequest request)
{
    //retrieval omitted

    var image = result.FirstResult;

    System.IO.Stream stream = new System.IO.MemoryStream(image.Image);

    return new FileStreamResult(stream, "image/tif");
}

When I go to my action in the browser it prompts me for download. I don't want it to download, I want it to show in the browser. How do I accomplish this?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

是你 2024-10-27 09:43:11

如果您使用 return Controller.File(filename, ...) ,您将返回一个 FilePathResult,这可能不是您想要的 - 我假设您的示例中的“image”是图像文件名(“var”对任何人都没有帮助的情况...)

如果您使用其他文件重载之一,或者直接使用 FileContentResult 或 FileStreamResult,您将获得您想要的效果。

您不需要创建自定义 ActionResult 类(当然,它可能因其他原因有用。)

但是,刚刚写完所有这些,我意识到您的问题是 TIFF 不是文件浏览器始终(永远?)在内部显示的格式,这可能就是它们提示下载的原因。

您需要将其重新渲染为 PNG 或服务器上的其他内容才能在浏览器中显示。

If you use return Controller.File(filename, ...), you'll return a FilePathResult, which probably isn't what you want - I'm assuming that 'image' in your sample is an image filename (a case where 'var' isn't helping anyone...)

If you use one of the other File overloads, or use FileContentResult or FileStreamResult directly, you'll get the effect you want.

You don't need to make a custom ActionResult class (though of course, it might be useful for other reasons.)

HOWEVER, having just written all this, I've realised that your problem is that TIFF is not a file format which browsers can always (ever?) display internally, which is probably why they're prompting for a download.

You will need to re-render it to a PNG or something on the server to display in a browser.

舟遥客 2024-10-27 09:43:11

File ActionResult 在 HTTP 标头中添加一行,如下所示:

Content-disposition: attachment; filename=foo

这将导致浏览器尝试下载文件。这就是为什么有一个重载来指定文件名。

您可以创建自己的 ActionResult 来执行下载,并省略 Content-disposition。

如果您想复制粘贴,我在 codeplex 上有一个代码:ImageResult.cs

The File ActionResult adds a line to the HTTP header like this:

Content-disposition: attachment; filename=foo

This will cause the browser to attempt to download the file. That's why there is an overload to specify the filename.

You can create your own ActionResult to do the downloading, and omit the Content-disposition.

If you want to copy-and-paste, I have the code for one on codeplex: ImageResult.cs

浪荡不羁 2024-10-27 09:43:11

根据要求,这是我的解决方案。

这是从 John 复制和修改的 ImageResult

public class ImageResult : ActionResult
{
    public ImageResult()
    {
    }

    public byte[] ImageData
    {
        get;
        set;
    }

    public MemoryStream ImageStream
    {
        get;
        set;
    }

    public string MimeType
    {
        get;
        set;
    }

    public HttpCacheability Cacheability
    {
        get;
        set;
    }

    public string ETag
    {
        get;
        set;
    }

    public DateTime? Expires
    {
        get;
        set;
    }

    public override void ExecuteResult(ControllerContext context)
    {
        if (this.ImageData == null && ImageStream == null)
        {
            throw new ArgumentNullException("ImageData or ImageStream");
        }

        if (string.IsNullOrEmpty(this.MimeType))
        {
            throw new ArgumentNullException("MimeType");
        }

        context.HttpContext.Response.ContentType = this.MimeType;

        if (!string.IsNullOrEmpty(this.ETag))
        {
            context.HttpContext.Response.Cache.SetETag(this.ETag);
        }

        if (this.Expires.HasValue)
        {
            context.HttpContext.Response.Cache.SetCacheability(this.Cacheability);
            context.HttpContext.Response.Cache.SetExpires(this.Expires.Value);
        }

        if (ImageStream != null)
        {
            ImageData = ImageStream.ToArray();
        } 

        context.HttpContext.Response.OutputStream.Write(this.ImageData, 0, this.ImageData.Length);

    }
}

这是我的操作,为了清晰起见进行了修改

public ActionResult Index(ItemImageRequest request)
{
    var result = queueService.GetItemImage(request);

    if (result.TotalResults == 0)
        return new EmptyResult();

    ItemImage image = result.FirstResult;

    //image.Image is type byte[]
    MemoryStream tiffStream = new MemoryStream(image.Image);

    MemoryStream pngStream = new MemoryStream();

    System.Drawing.Bitmap.FromStream(tiffStream).Save(pngStream, System.Drawing.Imaging.ImageFormat.Png);

    return new ImageResult()
    {
        ImageStream = pngStream,
        MimeType = "image/png",
        Cacheability = HttpCacheability.NoCache
    };
}

感谢 John 和 Will 帮助我解决了这个问题。

As requested, here is my solution.

Here is the ImageResult class, copied and modified from John

public class ImageResult : ActionResult
{
    public ImageResult()
    {
    }

    public byte[] ImageData
    {
        get;
        set;
    }

    public MemoryStream ImageStream
    {
        get;
        set;
    }

    public string MimeType
    {
        get;
        set;
    }

    public HttpCacheability Cacheability
    {
        get;
        set;
    }

    public string ETag
    {
        get;
        set;
    }

    public DateTime? Expires
    {
        get;
        set;
    }

    public override void ExecuteResult(ControllerContext context)
    {
        if (this.ImageData == null && ImageStream == null)
        {
            throw new ArgumentNullException("ImageData or ImageStream");
        }

        if (string.IsNullOrEmpty(this.MimeType))
        {
            throw new ArgumentNullException("MimeType");
        }

        context.HttpContext.Response.ContentType = this.MimeType;

        if (!string.IsNullOrEmpty(this.ETag))
        {
            context.HttpContext.Response.Cache.SetETag(this.ETag);
        }

        if (this.Expires.HasValue)
        {
            context.HttpContext.Response.Cache.SetCacheability(this.Cacheability);
            context.HttpContext.Response.Cache.SetExpires(this.Expires.Value);
        }

        if (ImageStream != null)
        {
            ImageData = ImageStream.ToArray();
        } 

        context.HttpContext.Response.OutputStream.Write(this.ImageData, 0, this.ImageData.Length);

    }
}

Here is my action, modified for clarity

public ActionResult Index(ItemImageRequest request)
{
    var result = queueService.GetItemImage(request);

    if (result.TotalResults == 0)
        return new EmptyResult();

    ItemImage image = result.FirstResult;

    //image.Image is type byte[]
    MemoryStream tiffStream = new MemoryStream(image.Image);

    MemoryStream pngStream = new MemoryStream();

    System.Drawing.Bitmap.FromStream(tiffStream).Save(pngStream, System.Drawing.Imaging.ImageFormat.Png);

    return new ImageResult()
    {
        ImageStream = pngStream,
        MimeType = "image/png",
        Cacheability = HttpCacheability.NoCache
    };
}

Thanks to John and Will for helping me out with this.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文