2013-07-02 3 views
0

Мне нужно извлечь значения байтов RGB каждого пикселя небольшого GIF, хранящегося на ПК (16x16 пикселей), поскольку мне нужно отправить их на светодиодный дисплей, который принимает цветовой код RGB 6 байтов.извлечение RGB из изображения GIF

После открытия тестового файла и преобразования его в 1-байтовый массив я получаю несколько байтовых значений, но я не уверен, что это декодирует GIF-кадр и в результате вернет мой желаемый массив из 192 байт RGB?

'img = Image.FromFile("mygif.gif");    
    FrameDimension dimension = new FrameDimension(img.FrameDimensionsList[0]); 
    int frameCount = img.GetFrameCount(dimension); 
    img.SelectActiveFrame(dimension, 0); 
    gifarray = imageToByteArray(img);` 

    //image to array conversion func. 
    public byte[] imageToByteArray(System.Drawing.Image imageIn) 
    { 
     MemoryStream ms = new MemoryStream(); 
     imageIn.Save(ms, System.Drawing.Imaging.ImageFormat.Gif); 
     return ms.ToArray(); 

    } 

Возможно, существует другой способ для этого?

ответ

2

Используйте этот метод, чтобы получить 2d массив, содержащий пиксели:

//using System.Drawing; 
Color[,] getPixels(Image image) 
{ 
    Bitmap bmp = (Bitmap)image; 
    Color[,] pixels = new Color[bmp.Width, bmp.Height]; 

    for (int x = 0; x < bmp.Width; x++) 
     for (int y = 0; y < bmp.Height; y++) 
      pixels[x, y] = bmp.GetPixel(x, y); 

    return pixels; 
} 

Используя данные, возвращаемые этим методом, вы можете получить каждый пиксель R, G, B и A (каждый из них представляет собой один байт) и делать с ними все, что вы хотите.

Если вы хотите, чтобы конечный результат, чтобы быть byte[], содержащие значения, как этот: { R0, G0, B0, R1, G1, B1, ... }, и пиксели должны быть записаны в byte[] в строке-мажорных порядке, то вы делаете это:

byte[] getImageBytes(Image image) 
{ 
    Bitmap bmp = (Bitmap)image; 
    byte[] bytes = new byte[(bmp.Width * bmp.Height) * 3]; // 3 for R+G+B 

    for (int x = 0; x < bmp.Width; x++) 
    { 
     for (int y = 0; y < bmp.Height; y++) 
     { 
      Color pixel = bmp.GetPixel(x, y); 
      bytes[x + y * bmp.Width + 0] = pixel.R; 
      bytes[x + y * bmp.Width + 1] = pixel.G; 
      bytes[x + y * bmp.Width + 2] = pixel.B; 
     } 
    } 

    return bytes; 
} 

You может затем отправить результат getImageBytes на ваш светодиод (предполагая, что именно так вы должны отправлять изображения на него).

+0

спасибо, его то, что я делаю, и это работает. Я просто предположил, что не могу рассматривать GIF как растровое изображение. проблема в том, что я теряю возможность цикла кадров прямо сейчас. –

+0

OK Я понимаю, это просто простое отбрасывание из класса Image в Bitmap, и это можно сделать. выпуск закрыт, спасибо за ваши ответы –

+0

@PK Если это правильный ответ, пожалуйста, отметьте его как таковой. :) – Jashaszun

1

Ваш путь не будет декодировать его до необработанных данных байта RGB. Скорее всего, будут выводиться те же самые данные, которые вы загрузили в начале (GIF-кодирование).

Вам нужно будет извлекать данные пиксел за пикселем:

public byte[] imageToByteArray(Image imageIn) 
{ 
    Bitmap lbBMP = new Bitmap(imageIn); 
    List<byte> lbBytes = new List<byte>(); 

    for(int liY = 0; liY < lbBMP.Height; liY++) 
     for(int liX = 0; liX < lbBMP.Width; liX++) 
     { 
      Color lcCol = lbBMP.GetPixel(liX, liY); 
      lbBytes.AddRange(new[] { lcCol.R, lcCol.G, lcCol.B }); 
     } 

    return lbBytes.ToArray(); 
} 
+0

Не забывайте, что gif могут иметь прозрачность. Задает ли кодек Windows это в Color.A? – plinth

+0

Да, да. Я не включал это, так как вопрос сказал «RGB», а не «RGBA». – Basuro

+0

ОК, он работает. Большое спасибо, не понимал, что могу загрузить изображение GIF как растровое изображение. Недостатком является то, что я могу управлять кадрами изображения GIF - я могу загрузить только самый первый кадр. –

Смежные вопросы