3

SD カード、SD カード シールド、および Arduino Uno R3 を持っています。SDカードに画像を書き込む必要があります。書きやすいが実際には開くことができない形式(PPM、PGMなど)を使用するよりも、生の配列からJPEG / PNG / BMP /などに移行することをお勧めします。

画像書き込み機能はArduinoの標準ライブラリに含まれていますか?そうでない場合、どのライブラリを使用すればよいですか? を調べましたがlodePNG、奇妙なエラー ( ) に遭遇しましたvector is not a member of std

4

1 に答える 1

2

Arduino フォーラム ( http://forum.arduino.cc/index.php?topic=112733.0 )のスレッドから引っ張ってきたので、このコードのクレジットはゼロです。.bmp ファイルを SD カードに書き込みます。

別の議論では、JPG および PNG ファイルに関連付けられた圧縮アルゴリズムのために、それらを機能させるためのコードの量を Arduino に収めるのがより困難になることが示されました。 /index.php?topic=76376.0 )。

お役に立てれば。Arduinoの専門家ではないことは間違いありません-少しいじりました。

#include <SdFat.h>
#include <SdFatUtil.h>

/*
 WRITE BMP TO SD CARD
 Jeff Thompson
 Summer 2012

 TO USE MEGA:
 The SdFat library must be edited slightly to use a Mega - in line 87
 of SdFatConfig.h, change to:

   #define MEGA_SOFT_SPI 1

 (this uses pins 10-13 for writing to the card)

 Writes pixel data to an SD card, saved as a BMP file.  Lots of code
 via the following...

 BMP header and pixel format:
   http://stackoverflow.com/a/2654860

 SD save:
   http://arduino.cc/forum/index.php?topic=112733 (lots of thanks!)
 ... and the SdFat example files too

 www.jeffreythompson.org
 */

char name[] = "9px_0000.bmp";       // filename convention (will auto-increment)
const int w = 16;                   // image width in pixels
const int h = 9;                    // " height
const boolean debugPrint = true;    // print details of process over serial?

const int imgSize = w*h;
int px[w*h];                        // actual pixel data (grayscale - added programatically below)

SdFat sd;
SdFile file;
const uint8_t cardPin = 8;          // pin that the SD is connected to (d8 for SparkFun MicroSD shield)

void setup() {

  // iteratively create pixel data
  int increment = 256/(w*h);        // divide color range (0-255) by total # of px
  for (int i=0; i<imgSize; i++) {
    px[i] = i * increment;          // creates a gradient across pixels for testing
  }

  // SD setup
  Serial.begin(9600);
  if (!sd.init(SPI_FULL_SPEED, cardPin)) {
    sd.initErrorHalt();
    Serial.println("---");
  }

  // if name exists, create new filename
  for (int i=0; i<10000; i++) {
    name[4] = (i/1000)%10 + '0';    // thousands place
    name[5] = (i/100)%10 + '0';     // hundreds
    name[6] = (i/10)%10 + '0';      // tens
    name[7] = i%10 + '0';           // ones
    if (file.open(name, O_CREAT | O_EXCL | O_WRITE)) {
      break;
    }
  }

  // set fileSize (used in bmp header)
  int rowSize = 4 * ((3*w + 3)/4);      // how many bytes in the row (used to create padding)
  int fileSize = 54 + h*rowSize;        // headers (54 bytes) + pixel data

  // create image data; heavily modified version via:
  // http://stackoverflow.com/a/2654860
  unsigned char *img = NULL;            // image data
  if (img) {                            // if there's already data in the array, clear it
    free(img);
  }
  img = (unsigned char *)malloc(3*imgSize);

  for (int y=0; y<h; y++) {
    for (int x=0; x<w; x++) {
      int colorVal = px[y*w + x];                        // classic formula for px listed in line
      img[(y*w + x)*3+0] = (unsigned char)(colorVal);    // R
      img[(y*w + x)*3+1] = (unsigned char)(colorVal);    // G
      img[(y*w + x)*3+2] = (unsigned char)(colorVal);    // B
      // padding (the 4th byte) will be added later as needed...
    }
  }

  // print px and img data for debugging
  if (debugPrint) {
    Serial.print("\nWriting \"");
    Serial.print(name);
    Serial.print("\" to file...\n");
    for (int i=0; i<imgSize; i++) {
      Serial.print(px[i]);
      Serial.print("  ");
    }
  }

  // create padding (based on the number of pixels in a row
  unsigned char bmpPad[rowSize - 3*w];
  for (int i=0; i<sizeof(bmpPad); i++) {         // fill with 0s
    bmpPad[i] = 0;
  }

  // create file headers (also taken from StackOverflow example)
  unsigned char bmpFileHeader[14] = {            // file header (always starts with BM!)
    'B','M', 0,0,0,0, 0,0, 0,0, 54,0,0,0   };
  unsigned char bmpInfoHeader[40] = {            // info about the file (size, etc)
    40,0,0,0, 0,0,0,0, 0,0,0,0, 1,0, 24,0   };

  bmpFileHeader[ 2] = (unsigned char)(fileSize      );
  bmpFileHeader[ 3] = (unsigned char)(fileSize >>  8);
  bmpFileHeader[ 4] = (unsigned char)(fileSize >> 16);
  bmpFileHeader[ 5] = (unsigned char)(fileSize >> 24);

  bmpInfoHeader[ 4] = (unsigned char)(       w      );
  bmpInfoHeader[ 5] = (unsigned char)(       w >>  8);
  bmpInfoHeader[ 6] = (unsigned char)(       w >> 16);
  bmpInfoHeader[ 7] = (unsigned char)(       w >> 24);
  bmpInfoHeader[ 8] = (unsigned char)(       h      );
  bmpInfoHeader[ 9] = (unsigned char)(       h >>  8);
  bmpInfoHeader[10] = (unsigned char)(       h >> 16);
  bmpInfoHeader[11] = (unsigned char)(       h >> 24);

  // write the file (thanks forum!)
  file.write(bmpFileHeader, sizeof(bmpFileHeader));    // write file header
  file.write(bmpInfoHeader, sizeof(bmpInfoHeader));    // " info header

  for (int i=0; i<h; i++) {                            // iterate image array
    file.write(img+(w*(h-i-1)*3), 3*w);                // write px data
    file.write(bmpPad, (4-(w*3)%4)%4);                 // and padding as needed
  }
  file.close();                                        // close file when done writing

  if (debugPrint) {
    Serial.print("\n\n---\n");
  }
}

void loop() { }
于 2013-05-23T22:38:01.530 に答える