mbed serial interface for the OV528 camera (uCAM TTL 120 from 4D systems).
Dependents: mbed_uCAM_TTL120_20141118
Library for interfacing the mbed to the OV528 jpeg engine camera from Omnivision. I tested this program using the uCAM TTL 120 from 4D systems, now obsolete.
Above is a saved jpeg image from the camera at 480x640 resolution
Camera and TFT screen setup
Closeup of the TFT screen displaying a 60x80 pixel 16 bit color bitmap image. The RGB (565) pixel colors were reversed when read from the camera relative to the TFT screen so a bit mask and shift had to be applied when displaying the pixel color.
bit mask and shift
int k=12; for(int i=0;i<60;i++){ for(int j=0;j<80;j++){ //returned 16-bit color is 565(RGB) pixel_col = (imageData[k] << 8); k++; pixel_col += imageData[k]; k++; // fputc(((picture[k] >> 8) & 0xff), fp); //write pixel high byte to file // fputc(picture[k] & 0xff, fp); //write low byte //swap R and B bits in returned pixel for TFT display int TFT_pix_col = 0; TFT_pix_col += (pixel_col & 0x001f) << 11; TFT_pix_col += (pixel_col & 0xf800) >> 11; TFT_pix_col += (pixel_col & 0x07e0); TFT.pixel(j, i, TFT_pix_col); //Do something with the pixel } }
Revision 3:85db6ea8c0a4, committed 2014-11-26
- Comitter:
- jebradshaw
- Date:
- Wed Nov 26 16:57:13 2014 +0000
- Parent:
- 2:f80257456c6e
- Commit message:
- uCAM_TTL120 Library; -Improved cam_read() function with numbytes check and timeout
Changed in this revision
uCAM_TTL120.cpp | Show annotated file Show diff for this revision Revisions of this file |
uCAM_TTL120.h | Show annotated file Show diff for this revision Revisions of this file |
--- a/uCAM_TTL120.cpp Tue Nov 18 20:26:06 2014 +0000 +++ b/uCAM_TTL120.cpp Wed Nov 26 16:57:13 2014 +0000 @@ -12,24 +12,49 @@ timerCam->start(); } -int uCAM_TTL120::uCAM_read(char *str, int numchars, float timeout){ - int i = 0; - float t_start = timerCam->read(); +int uCAM_TTL120::uCAM_read(char *str, int numchars, float timeout){ + Timer t_Frame; + int i=0; + int timeoutState=0; + t_Frame.start(); - while((timerCam->read() < (t_start + timeout)) && (i < numchars)){ - if(_cam.readable()){ - str[i] = _cam.getc(); - i++; - } - } - if(timerCam->read() >= (t_start + timeout)){ - return -1; - } - if(i >= numchars){ - return -2; - } - - return i; + while(timeoutState != 3 && (i < numchars)){ + switch(timeoutState){ + case 0: + while(_cam.readable()){ //if characters are in buffer, read them + str[i++] = _cam.getc(); + if(i == numchars){ + timeoutState = 3; + break; + } + } + //if no characters in buffer, initiate timeout + timeoutState = 1; + break; + case 1: + timeout = t_Frame.read() + timeout; //current time plus timeout time + timeoutState = 2; +// pc.printf("Timeout initiated %f\r\n", timeout); + break; + case 2: + if(_cam.readable()){ //check buffer while timeout is running + str[i++] = _cam.getc(); + if(i == numchars){ + timeoutState = 3; + } + else{ + timeoutState = 0; + } + break; + } + if(t_Frame.read() >= timeout) //if timeout has elapsed, exit the while loop with state 3 + timeoutState = 3; + break; + default: + timeoutState = 0; + }//switch timeoutState + }//while timeoutState != 2 + return i; //return number of bytes read } void uCAM_TTL120::uCAM_Command_Send(int command,char p1,char p2,char p3,char p4) @@ -53,7 +78,7 @@ wait(.1); //read serial buffer and wait for ACK (0xAA0E0DXX0000) - uCAM_read(ser_read, 6, .1); + uCAM_read(ser_read, 6, .5); if((ser_read[0] == 0xAA) && (ser_read[1] == 0x0E)){ if((command & 0xff) == ser_read[2]) @@ -82,7 +107,7 @@ wait(.2); //read serial buffer and wait for ACK (0xAA0E0DXX0000) - uCAM_read(ser_read, 6, .01); + uCAM_read(ser_read, 6, .1); if((ser_read[0] == 0xAA) && (ser_read[1] == 0x0E) && @@ -103,7 +128,7 @@ uCAM_Command_Send(uCAM_ACK,0x0D,0x00,0x00,0x00); printf("\r\n uCAM 120 Initialized\r\nDelaying 2 seconds for AGC and AEC \r\n circuits to stabilise before image capture."); -/* wait(.5); //2 second delay before capturing first image + wait(.5); //2 second delay before capturing first image printf("."); wait(.5); printf("."); @@ -111,7 +136,7 @@ printf("."); wait(.5); printf(".\r\nFinished\r\n"); -*/ + return 1; //Camera connection successful } } @@ -129,14 +154,14 @@ int i; uCAM_Command_Send(uCAM_INITIAL,0x00,0x06,0x01,0x00); // p2=0x06-16 bit color(RAW,565(RGB)) - // p3=0x01-80 x 60 bit resolution // p4=0x01-JPEG res 80 x 64 - wait(.02); + // p3=0x01-80 x 60 bit resolution + // p4=0x00-raw for(i=0;i<7;i++) //clear the string ser_read[i] = 0; //read serial C buffer and wait for ACK (0xAA0E0DXX0000) - uCAM_read(ser_read, 6, 100); + uCAM_read(ser_read, 6, .02); //.01 if((ser_read[0] == 0xAA) && (ser_read[1] == 0x0E) && @@ -166,7 +191,7 @@ (ser_read[1] == 0x0E) && (ser_read[2] == 0x01)) { - wait(.050); + wait(.010); return 1; } else @@ -186,13 +211,13 @@ ser_read[i] = 0; //read serial buffer and wait for ACK (0xAA0E0DXX0000) - uCAM_read(ser_read, 6, 100); + uCAM_read(ser_read, 6, .100); if((ser_read[0] == 0xAA) && (ser_read[1] == 0x0E) && (ser_read[2] == 0x01)) { - wait(.05); + wait(.02); return 1; } else @@ -202,7 +227,7 @@ { uCAM_Command_Send(uCAM_SNAPSHOT,0x01,0x00,0x00,0x00); // p1=0x01-Uncompressed Image // p2 and p3 = 0, current frame - wait(.05); + wait(.01); if(uCAM_GetACK(uCAM_SNAPSHOT)) return 1; @@ -210,17 +235,15 @@ return 0; } -int uCAM_TTL120::uCAM_send_GET_PICTURE_80x60_16COL_RAW(void) +int uCAM_TTL120::uCAM_send_GET_PICTURE_80x60_16COL_RAW(FILE *fp) { char ser_read[7]; - char c; unsigned long pic_bytes; unsigned int i, j, k; unsigned int serbytes_read; - unsigned int pixel_col; + unsigned int pixel_col; pic_bytes = 0; - c=0; serbytes_read = 0; for(i=0;i<100;i++) @@ -233,59 +256,46 @@ uCAM_Command_Send(uCAM_GET_PICTURE,0x01,0x00,0x00,0x00); // p1=0x01-Snapshot picture wait(.3); - //read serial C buffer and wait for ACK (0xAA0E0DXX0000) - c=uCAM_read(ser_read, 6, 1); - wait(.3); + if(uCAM_GetACK(uCAM_GET_PICTURE)) //returned get pic + { + //read serial C buffer and wait for ACK (0xAA0E0DXX0000) + char c=uCAM_read(ser_read, 6, .1); - if(c==6) //received 6 bytes back - { - if((ser_read[0] == 0xAA) && //first 2 bytes indicate it was a DATA packet - (ser_read[1] == 0x0E) && - (ser_read[2] == 0x04)) //returned get pic - { - //read serial C buffer and wait for ACK (0xAA0E0DXX0000) - c=uCAM_read(ser_read, 6, 1); + if((ser_read[0] == 0xAA) && //first 2 bytes indicate it was a DATA packet + (ser_read[1] == 0x0A)) + { + pic_bytes = (unsigned long)ser_read[3]; + pic_bytes += (unsigned long)ser_read[4] << 8; + pic_bytes += (unsigned long)ser_read[5] << 16; - if(c==6) //received 6 bytes back - { - if((ser_read[0] == 0xAA) && //first 2 bytes indicate it was a DATA packet - (ser_read[1] == 0x0A)) - { - pic_bytes = (unsigned long)ser_read[3]; - pic_bytes += (unsigned long)ser_read[4] << 8; - pic_bytes += (unsigned long)ser_read[5] << 16; - - serbytes_read = uCAM_read(picture, pic_bytes, .200); + serbytes_read = uCAM_read(picture, pic_bytes, .200); - if(serbytes_read == pic_bytes) - { - k=0; - for(i=0;i<60;i++) - { - for(j=0;j<80;j++) - { - pixel_col = picture[k]; - k++; -// printf("%d ", pixel_col); -// uLCD144_Put_Pixel(j, i, pixel_col); //Do something with the pixel - } - } + if(serbytes_read == pic_bytes) + { + k=0; + for(i=0;i<60;i++) + { + for(j=0;j<80;j++) + { + pixel_col = picture[k]; + k++; + fputc(((picture[k] >> 8) & 0xff), fp); //write pixel high byte to file + fputc(picture[k] & 0xff, fp); //write low byte +// printf("%d ", pixel_col); +// TFT.pixel(j, i, pixel_col); //Do something with the pixel + } + } - uCAM_Command_Send(uCAM_ACK, 0x0A, 0x00, 0x01, 0x00); + uCAM_Command_Send(uCAM_ACK, 0x0A, 0x00, 0x01, 0x00); - return pic_bytes; - } - else - return -4; - } - else - return -3; - } - } - else - return -2; - } - return -1; + return pic_bytes; + } + else + return -4; + } + } + else + return -1; } int uCAM_TTL120::uCAM_send_GET_PICTURE_80x60_2GRAY_RAW(void) @@ -414,7 +424,7 @@ wait(.3); //read serial C buffer and wait for ACK (0xAA0E0DXX0000) - c=uCAM_read(ser_read, 6, 1); + c=uCAM_read(ser_read, 6, .1); wait(.2); if(c==6) //received 6 bytes back @@ -424,7 +434,7 @@ (ser_read[2] == 0x04)) //returned get pic { //read serial C buffer and wait for ACK (0xAA0E0DXX0000) - c=uCAM_read(ser_read, 6, 1); + c=uCAM_read(ser_read, 6, .1); if(c==6) //received 6 bytes back { @@ -511,13 +521,13 @@ // _cam.baud(1228800); } -void uCAM_TTL120::uCAM_TakePic_RAW_16COLOR_80x60(void) +void uCAM_TTL120::uCAM_TakePic_RAW_16COLOR_80x60(FILE *fp) { uCAM_send_INITIAL_80x60_16RAW(); wait(.1); uCAM_send_SNAPSHOT(); wait(.1); - uCAM_send_GET_PICTURE_80x60_16COL_RAW(); + uCAM_send_GET_PICTURE_80x60_16COL_RAW(fp); } void uCAM_TTL120::uCAM_TakePic_RAW_2GRAY_80x60(void) @@ -553,7 +563,7 @@ } } -int uCAM_TTL120::uCAM_get_jpeg(FILE *fileName){ +int uCAM_TTL120::uCAM_get_jpeg(FILE *fp){ char ser_read[7]; unsigned long pic_bytes; @@ -651,11 +661,10 @@ if((verifyCode[0] & 0xff) == (vCodeCheck & 0xff)){ //pc.printf("\r\nPack ID = %d\r\n", packID);//debugging - for(int j=0;j<imageDataSize;j++){ - fputc(imageData[j], fileName); + for(int j=0;j<imageDataSize;j++){ //write image data to file pointer + fputc(imageData[j], fp); //pc.printf("%2X ", imageData[j]); - } - + } packID++; numPackages--; }
--- a/uCAM_TTL120.h Tue Nov 18 20:26:06 2014 +0000 +++ b/uCAM_TTL120.h Wed Nov 26 16:57:13 2014 +0000 @@ -45,15 +45,15 @@ int uCAM_send_INITIAL_80x60_2RAW(void); int uCAM_send_INITIAL_128x128_4RAW(void); int uCAM_send_SNAPSHOT(void); - int uCAM_send_GET_PICTURE_80x60_16COL_RAW(void); + int uCAM_send_GET_PICTURE_80x60_16COL_RAW(FILE *fp); int uCAM_send_GET_PICTURE_80x60_2GRAY_RAW(void); int uCAM_send_GET_PICTURE_128x128_4GRAY_RAW(void); - void uCAM_TakePic_RAW_16COLOR_80x60(void); + void uCAM_TakePic_RAW_16COLOR_80x60(FILE *fp); void uCAM_TakePic_RAW_2GRAY_80x60(void); void uCAM_TakePic_RAW_4GRAY_128x128(void); - int uCAM_get_jpeg(FILE *fileName); + int uCAM_get_jpeg(FILE *fp); void uCAM_set_baud(void);