바이트 배열에서 이미지로 변환
바이트 배열을 이미지로 변환하고 싶습니다.
이 바이트 배열을 얻는 데이터베이스 코드입니다.
public void Get_Finger_print()
{
try
{
using (SqlConnection thisConnection = new SqlConnection(@"Data Source=" + System.Environment.MachineName + "\\SQLEXPRESS;Initial Catalog=Image_Scanning;Integrated Security=SSPI "))
{
thisConnection.Open();
string query = "select pic from Image_tbl";// where Name='" + name + "'";
SqlCommand cmd = new SqlCommand(query, thisConnection);
byte[] image =(byte[]) cmd.ExecuteScalar();
Image newImage = byteArrayToImage(image);
Picture.Image = newImage;
//return image;
}
}
catch (Exception) { }
//return null;
}
내 전환 코드 :
public Image byteArrayToImage(byte[] byteArrayIn)
{
try
{
MemoryStream ms = new MemoryStream(byteArrayIn,0,byteArrayIn.Length);
ms.Write(byteArrayIn, 0, byteArrayIn.Length);
returnImage = Image.FromStream(ms,true);//Exception occurs here
}
catch { }
return returnImage;
}
주석이있는 줄에 도달하면 다음 예외가 발생합니다. Parameter is not valid.
이 예외의 원인을 어떻게 해결합니까?
메모리 스트림에 두 번 사용하고 폐기하지 않습니다. 또한 이미지에 내장 된 색상 보정을 신청합니다.
대신 시도하십시오.
using (var ms = new MemoryStream(byteArrayIn))
{
return Image.FromStream(ms);
}
내가 뭔가를 놓치고 아마도이 한 줄짜리 줄은 JPEG 파일의 이미지를 포함하는 배열에서 잘 작동합니다.
Image x = (Bitmap)((new ImageConverter()).ConvertFrom(jpegByteArray));
편집하다 :
이 답변의 업데이트 된 버전은 여기를 참조하십시오 : 바이트 배열에서 이미지를 변환하는 방법
public Image byteArrayToImage(byte[] bytesArr)
{
using (MemoryStream memstr = new MemoryStream(bytesArr))
{
Image img = Image.FromStream(memstr);
return img;
}
}
@ isaias-b에서 제공하는 솔루션에 버그가 있는지 알고 싶습니다.
이 솔루션 stride
은 행 길이와 같다고 가정합니다 . 그러나 항상 사실은 아닙니다. GDI에 의해 수행되는 메모리 정렬로 인해 스트라이드는 행 길이보다 클 수 있습니다. 이 점을 고려해야합니다. 그렇지 않으면 잘못된 이동 이미지가 생성됩니다. 각 행의 패딩 바이트는 무시됩니다.
스트라이드는 단일 행 픽셀 (스캔 라인)의 너비이며 4 바이트 경계로 반올림됩니다.
고정 코드 :
using System.Drawing;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;
public static class ImageExtensions
{
public static Image ImageFromRawBgraArray(this byte[] arr, int width, int height, PixelFormat pixelFormat)
{
var output = new Bitmap(width, height, pixelFormat);
var rect = new Rectangle(0, 0, width, height);
var bmpData = output.LockBits(rect, ImageLockMode.ReadWrite, output.PixelFormat);
// Row-by-row copy
var arrRowLength = width * Image.GetPixelFormatSize(output.PixelFormat) / 8;
var ptr = bmpData.Scan0;
for (var i = 0; i < height; i++)
{
Marshal.Copy(arr, i * arrRowLength, ptr, arrRowLength);
ptr += bmpData.Stride;
}
output.UnlockBits(bmpData);
return output;
}
}
이것이 무엇으로 이어질 수 있는지 설명하기 위해 PixelFormat.Format24bppRgb
그라디언트 이미지 101x101을 생성 해 보겠습니다.
var width = 101;
var height = 101;
var gradient = new byte[width * height * 3 /* bytes per pixel */];
for (int i = 0, pixel = 0; i < gradient.Length; i++, pixel = i / 3)
{
var x = pixel % height;
var y = (pixel - x) / width;
gradient[i] = (byte)((x / (double)(width - 1) + y / (double)(height - 1)) / 2d * 255);
}
전체 배열을있는 그대로 복사하여으로 가리키는 주소에 복사 bmpData.Scan0
하면 다음 이미지가 표시됩니다. 이미지의 일부가 패딩 바이트에 기록 되었기 때문에 이미지 이동이 무시되었습니다. 또한 이것이 마지막 행이 불완전한 이유입니다.
그러나 행 단위로 이동 대상 포인터를 bmpData.Stride
값으로 복사 하면 유효한 이미지가 생성됩니다.
보폭도 부정적 일 수 있습니다.
보폭이 양수이면 비트 맵이 하향식입니다. 보폭이 음수이면 비트 맵이 상향식입니다.
그러나 나는 그러한 이미지로 작업하지 않았으며 이것은 내 메모를 벗어났습니다.
관련 답변 : C #-C ++와 다른 비트 맵의 RGB 버퍼
아래와 같은 간단한 접근 방식이 있습니다 FromStream
. 이미지의 방법을 사용 하여 트릭을 수행 할 수 있습니다 System.Drawing
.
// using image object not file
public byte[] imageToByteArray(Image imageIn)
{
MemoryStream ms = new MemoryStream();
imageIn.Save(ms,System.Drawing.Imaging.ImageFormat.Gif);
return ms.ToArray();
}
public Image byteArrayToImage(byte[] byteArrayIn)
{
MemoryStream ms = new MemoryStream(byteArrayIn);
Image returnImage = Image.FromStream(ms);
return returnImage;
}
시도 (업데이트)
MemoryStream ms = new MemoryStream(byteArrayIn,0,byteArrayIn.Length);
ms.Position = 0; // this is important
returnImage = Image.FromStream(ms,true);
제시된 모든 답변은 바이트 배열에 gif, png 또는 jpg와 같은 알려진 파일 형식 표현의 데이터가 포함되어 있다고 가정합니다. 하지만 최근에 byte[]
선형화 된 BGRA 정보를 포함하는 s를 효율적으로 Image
객체 로 변환하는 데 문제가있었습니다 . 다음 코드는 Bitmap
객체를 사용하여 문제를 해결 합니다.
using System.Drawing;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;
public static class Extensions
{
public static Image ImageFromRawBgraArray(
this byte[] arr, int width, int height)
{
var output = new Bitmap(width, height);
var rect = new Rectangle(0, 0, width, height);
var bmpData = output.LockBits(rect,
ImageLockMode.ReadWrite, output.PixelFormat);
var ptr = bmpData.Scan0;
Marshal.Copy(arr, 0, ptr, arr.Length);
output.UnlockBits(bmpData);
return output;
}
}
이것은 이 사이트 에 게시 된 솔루션의 약간 변형입니다 .
어떤 종류의 변수로도 returnImage를 선언하지 않았습니다. :)
이것은 도움이 될 것입니다 :
public Image byteArrayToImage(byte[] byteArrayIn)
{
try
{
MemoryStream ms = new MemoryStream(byteArrayIn,0,byteArrayIn.Length);
ms.Write(byteArrayIn, 0, byteArrayIn.Length);
Image returnImage = Image.FromStream(ms,true);
}
catch { }
return returnImage;
}
이것은 Holstebroe의 답변과 여기에 주석을 추가 했습니다. 바이트 배열에서 이미지 객체 가져 오기
Bitmap newBitmap;
using (MemoryStream memoryStream = new MemoryStream(byteArrayIn))
using (Image newImage = Image.FromStream(memoryStream))
newBitmap = new Bitmap(newImage);
return newBitmap;
이런 일이 발생하는 대부분의 경우 SQL 열의 잘못된 데이터입니다. 다음은 이미지 열에 삽입하는 적절한 방법입니다.
INSERT INTO [TableX] (ImgColumn) VALUES (
(SELECT * FROM OPENROWSET(BULK N'C:\....\Picture 010.png', SINGLE_BLOB) as tempimg))
대부분의 사람들은 다음과 같이 잘못합니다.
INSERT INTO [TableX] (ImgColumn) VALUES ('C:\....\Picture 010.png'))
나는이 사람들을 찾았습니다 배열을 이미지로 변환
private void button1_Click(object sender, EventArgs e)
{
try
{
string hasil = "D:\\coba1000.jpg";
System.IO.File.WriteAllBytes(@hasil, bytestosend);
pictureBox1.ImageLocation = @hasil;
}
catch { }
}
참고 URL : https://stackoverflow.com/questions/9173904/byte-array-to-image-conversion
'IT' 카테고리의 다른 글
Ajax를 사용하여 PDF 파일 다운로드 및 열기 (0) | 2020.09.11 |
---|---|
Java 주석에서 코드의 위치 섹션을 표시하는 방법은 무엇입니까? (0) | 2020.09.11 |
내 페이지 중앙에 html 버튼 정렬 시도 (0) | 2020.09.11 |
Eclipse 프로젝트를 GitHub에 어떻게 업로드합니까? (0) | 2020.09.11 |
Django 템플릿에서 마지막 루프 반복을 어떻게 확인합니까? (0) | 2020.09.11 |