Возможно ли для представления отобразить WebImage без предварительного сохранения его в файл?
Я не совсем уверен, если я использую WebImage
класс правильно.
У меня есть контроллер, который извлекает фотографию и некоторую связанную информацию (комментарии, дату загрузки, имя файла) из базы данных. Я хочу вернуть частичное представление, которое содержит эту информацию, и отобразить изображение вместе с дополнительной информацией.
Итак, я создал новый WebImage из байтового массива, но как мне его отобразить?
Согласно этой статье это должно быть довольно просто
Вам нужно поработать с синтаксисом Razor и создать переменную, которая будет содержать изображение:
@{ var myImage = WebImage("/Content/myImage.jpg") // Work with the image… }
Затем, чтобы загрузить изображение на странице, вы должны показать переменную, которая содержит изображение внутри HTML
<img/>
тег:<img src="@myImage"/>
За исключением того, что не работает, он просто выводит <img src="System.Web.Helpers.WebImage">
и звонит .Write
не помогает
Есть ли способ сделать это, или мне нужно разделить мое действие на два разных действия: одно для возврата информации о фотографии и одно для возврата самой фотографии?
5 ответов
Нет никакого способа сделать это в одном виде бритвы... вам нужно создать отдельное действие для рендеринга изображения.
Тег img на странице будет выполнять ОТДЕЛЬНЫЙ http-вызов к серверу на основе URL, предоставленного в img src.
Вы можете написать это на лету!
Вы просто не используете WebImage.Save(), как вы думаете, вместо этого вы используете WebImage.GetBytes().
В этом примере вы уже сохранили изображение в виде байтового массива в базе данных. Немного упростил, чтобы обрабатывать только JPEG.
/// <summary>
/// Reference this in HTML as <img src="/Photo/WatermarkedImage/{ID}" />
/// Simplistic example supporting only jpeg images.
/// </summary>
/// <param name="ID">Photo ID</param>
public ActionResult WatermarkedImage(Guid ID)
{
// Attempt to fetch the photo record from the database using Entity Framework 4.2.
var photo = db.Photos.Find(ID);
if (photo != null) // Found the indicated photo record.
{
// Create WebImage from photo data.
// Should have 'using System.Web.Helpers' but just to make it clear...
var wi = new System.Web.Helpers.WebImage(photo.Data);
// Apply the watermark.
wi.AddImageWatermark(Server.MapPath("~/Content/Images/Watermark.png"),
opacity: 75,
horizontalAlign: "Center",
verticalAlign: "Bottom");
// Extract byte array.
var image = wi.GetBytes("image/jpeg");
// Return byte array as jpeg.
return File(image, "image/jpeg");
}
else // Did not find a record with passed ID.
{
return null; // 'Missing image' icon will display on browser.
}
}
Попробуйте использовать URL-адреса данных для отображения изображения. Это позволит избежать временного сохранения изображения на диск и повторного HTTP-запроса для получения изображения. Вам просто нужно сделать одну поездку туда и обратно, чтобы кодировать изображение в строке.
Вы можете преобразовать WebImage в закодированную строку Base64 и использовать в URL-адресе данных на странице. Использование холста HTML делает это довольно простым.
На стороне сервера сгенерируйте строку Base64 и создайте URL-адрес данных
// C# Razor code
WebImage myWebImage;
// you need to now set the WebImage object in your code
string imagebase64string = Convert.ToBase64String(myWebImage.GetBytes());
string dataUrl = string.Format("data:image/jpeg;base64,{0}", imagebase64string);
Используя синтаксис Razor, вставьте URL-адрес данных в код Javascript, который отображает изображение в браузере при загрузке страницы:
// Javascript Code
var myCanvas = document.getElementById('my-image-canvas');
var imageCtx = myCanvas.getContext('2d');
var myImage = new Image;
myImage.onload = function () {
imageCtx.drawImage(myImage, 0, 0);
}
myImage.src = '@dataUrl';
Ниже приведена ссылка на пример приложения, который демонстрирует эту концепцию, а также показывает, как легко визуализировать диаграммы ASP.Net, используя одну страницу Razor, используя ту же концепцию.
Я не верю, что помощник WebImage предоставляет возможность записи в поток. Из-за этого вам, вероятно, потребуется сохранить файл во временную папку (или в кэшируемую папку), а затем прочитать байты и записать изображение обратно как FileStreamResult
указав тип контента и данные.
Как и мой предыдущий ответ, основанный на ответе Brady321, у меня есть аналогичный альтернативный подход, который работает для проектов ASP.NET 4.7.2, которые не используют Razor/.cshtml. Это в VB.NET, но будет работать и на C#:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
. . .
If IsPostBack Then
' A postback
Dim dataURL As String
Dim photo As System.Web.Helpers.WebImage
photo = System.Web.Helpers.WebImage.GetImageFromRequest()
If (photo IsNot Nothing) Then
Dim imagebase64string As String
imagebase64string = Convert.ToBase64String(photo.GetBytes())
dataURL = String.Format("data:image/jpeg;base64,{0}", imagebase64string)
UploadedImage.Src = dataURL
End If
. . .
End Sub
HTML-код.aspx выглядит так (отсутствие параметра src вызывает предупреждение, но работает нормально):
<form action="" method="post" enctype="multipart/form-data">
<fieldset>
<legend> Upload Image </legend>
<label for="Image">Image</label>
<input type="file" name="Image" />
<br />
<input type="submit" value="Upload" id="Submit" onsubmit="UploadFile2" runat="server" />
</fieldset>
</form>
<h1>Uploaded Images</h1>
<img alt="image" id="UploadedImage" runat="server" />
Я использовал подход @Brady321 (спасибо;)), но мой код выглядит немного иначе (см. Ниже). Преимущество подхода Брэди в том, что файл не нужно сохранять на диск - его нужно просто загрузить и отобразить!
WebImage photo = null;
var dataUrl = "";
if (IsPost)
{
photo = WebImage.GetImageFromRequest();
if (photo != null)
{
string imagebase64string = Convert.ToBase64String(photo.GetBytes());
dataUrl = string.Format("data:image/jpeg;base64,{0}", imagebase64string);
}
}
Часть загрузки и отображения файлов выглядит так:
<div class="col-md-4">
<h2>Display Image on the Fly</h2>
<h1>Displaying an Image On the Fly</h1>
<form action="" method="post" enctype="multipart/form-data">
<fieldset>
<legend> Upload Image </legend>
<label for="Image">Image</label>
<input type="file" name="Image" />
<br />
<input type="submit" value="Upload" />
</fieldset>
</form>
<h1>Uploaded Image</h1>
@if (dataUrl != "")
{
<div class="result">
<img src="@dataUrl" alt="image" />
</div>
}
</div>
Ключевой частью является: <img src="@dataUrl" alt="image" />