Colin Stearns
/
qcControl
QC Control software
Fork of dgps by
Diff: camera.cpp
- Revision:
- 6:434d20e99e49
- Parent:
- 2:f480097b329d
--- a/camera.cpp Sun Feb 16 22:12:08 2014 +0000 +++ b/camera.cpp Fri Feb 21 15:15:25 2014 +0000 @@ -0,0 +1,372 @@ +/*************************************************** + This is a library for the Adafruit TTL JPEG Camera (VC0706 chipset) + + Pick one up today in the adafruit shop! + ------> http://www.adafruit.com/products/397 + + These displays use Serial to communicate, 2 pins are required to interface + + Adafruit invests time and resources providing this open source code, + please support Adafruit and open-source hardware by purchasing + products from Adafruit! + + Written by Limor Fried/Ladyada for Adafruit Industries. + BSD license, all text above must be included in any redistribution + ****************************************************/ + + +#include "camera.h" + +Serial* Camera::camera=NULL; +uint8_t Camera::serialNum=0; + +Serial& Camera::getSerial(){ + if(camera==NULL){ + // Init Camera + camera=new Serial(CAMERAPINTX,CAMERAPINRX); + camera->baud(CAMERABAUD); + serialNum=0; + Camera temp; + temp.reset(); + } + return *camera; +} + +bool Camera::reset() { + uint8_t args[] = {0x0}; + return runCommand(VC0706_RESET, args, 1, 5); +} + +/* +// Initialization code used by all constructor types +void Camera::common_init(void) { + swSerial = NULL; + hwSerial = NULL; + frameptr = 0; + bufferLen = 0; + serialNum = 0; +} + +// Constructor when using SoftwareSerial or NewSoftSerial +#if ARDUINO >= 100 +Camera::Camera(SoftwareSerial *ser) { +#else +Camera::Camera(NewSoftSerial *ser) { +#endif + common_init(); // Set everything to common state, then... + swSerial = ser; // ...override swSerial with value passed. +} + +// Constructor when using HardwareSerial +Camera::Camera(HardwareSerial *ser) { + common_init(); // Set everything to common state, then... + hwSerial = ser; // ...override hwSerial with value passed. +} + +boolean Camera::begin(uint16_t baud) { + if(swSerial) swSerial->begin(baud); + else hwSerial->begin(baud); + return reset(); +} + + +boolean Camera::motionDetected() { + if (readResponse(4, 200) != 4) { + return false; + } + if (! verifyResponse(VC0706_COMM_MOTION_DETECTED)) + return false; + + return true; +} + + +uint8_t Camera::setMotionStatus(uint8_t x, uint8_t d1, uint8_t d2) { + uint8_t args[] = {0x03, x, d1, d2}; + + return runCommand(VC0706_MOTION_CTRL, args, sizeof(args), 5); +} + + +uint8_t Camera::getMotionStatus(uint8_t x) { + uint8_t args[] = {0x01, x}; + + return runCommand(VC0706_MOTION_STATUS, args, sizeof(args), 5); +} + + +boolean Camera::setMotionDetect(boolean flag) { + if (! setMotionStatus(VC0706_MOTIONCONTROL, + VC0706_UARTMOTION, VC0706_ACTIVATEMOTION)) + return false; + + uint8_t args[] = {0x01, flag}; + + runCommand(VC0706_COMM_MOTION_CTRL, args, sizeof(args), 5); +} + + + +boolean Camera::getMotionDetect(void) { + uint8_t args[] = {0x0}; + + if (! runCommand(VC0706_COMM_MOTION_STATUS, args, 1, 6)) + return false; + + return camerabuff[5]; +} +*/ +uint8_t Camera::getImageSize() { + uint8_t args[] = {0x4, 0x4, 0x1, 0x00, 0x19}; + if (! runCommand(VC0706_READ_DATA, args, sizeof(args), 6)) + return 0xFF; + + return camerabuff[5]; +} + +bool Camera::setImageSize(uint8_t x) { + uint8_t args[] = {0x05, 0x04, 0x01, 0x00, 0x19, x}; + return runCommand(VC0706_WRITE_DATA, args, sizeof(args), 5); +} +/* +// downsize image control + +uint8_t Camera::getDownsize(void) { + uint8_t args[] = {0x0}; + if (! runCommand(VC0706_DOWNSIZE_STATUS, args, 1, 6)) + return -1; + + return camerabuff[5]; +} + +boolean Camera::setDownsize(uint8_t newsize) { + uint8_t args[] = {0x01, newsize}; + + return runCommand(VC0706_DOWNSIZE_CTRL, args, 2, 5); +} + +// other high level commands +*/ +char * Camera::getVersion(void) { + uint8_t args[] = {0x01}; + + sendCommand(VC0706_GEN_VERSION, args, 1); + // get reply + if (!readResponse(CAMERABUFFSIZ, 200)){ + return 0; + } + camerabuff[bufferLen] = 0; // end it! + return (char *)camerabuff; // return it! +} +/* + +// high level photo comamnds + +void Camera::OSD(uint8_t x, uint8_t y, char *str) { + if (strlen(str) > 14) { str[13] = 0; } + + uint8_t args[17] = {strlen(str), strlen(str)-1, (y & 0xF) | ((x & 0x3) << 4)}; + + for (uint8_t i=0; i<strlen(str); i++) { + char c = str[i]; + if ((c >= '0') && (c <= '9')) { + str[i] -= '0'; + } else if ((c >= 'A') && (c <= 'Z')) { + str[i] -= 'A'; + str[i] += 10; + } else if ((c >= 'a') && (c <= 'z')) { + str[i] -= 'a'; + str[i] += 36; + } + + args[3+i] = str[i]; + } + + runCommand(VC0706_OSD_ADD_CHAR, args, strlen(str)+3, 5); + printBuff(); +} + +boolean Camera::setCompression(uint8_t c) { + uint8_t args[] = {0x5, 0x1, 0x1, 0x12, 0x04, c}; + return runCommand(VC0706_WRITE_DATA, args, sizeof(args), 5); +} + +uint8_t Camera::getCompression(void) { + uint8_t args[] = {0x4, 0x1, 0x1, 0x12, 0x04}; + runCommand(VC0706_READ_DATA, args, sizeof(args), 6); + printBuff(); + return camerabuff[5]; +} + +boolean Camera::setPTZ(uint16_t wz, uint16_t hz, uint16_t pan, uint16_t tilt) { + uint8_t args[] = {0x08, wz >> 8, wz, + hz >> 8, wz, + pan>>8, pan, + tilt>>8, tilt}; + + return (! runCommand(VC0706_SET_ZOOM, args, sizeof(args), 5)); +} + + +boolean Camera::getPTZ(uint16_t &w, uint16_t &h, uint16_t &wz, uint16_t &hz, uint16_t &pan, uint16_t &tilt) { + uint8_t args[] = {0x0}; + + if (! runCommand(VC0706_GET_ZOOM, args, sizeof(args), 16)) + return false; + printBuff(); + + w = camerabuff[5]; + w <<= 8; + w |= camerabuff[6]; + + h = camerabuff[7]; + h <<= 8; + h |= camerabuff[8]; + + wz = camerabuff[9]; + wz <<= 8; + wz |= camerabuff[10]; + + hz = camerabuff[11]; + hz <<= 8; + hz |= camerabuff[12]; + + pan = camerabuff[13]; + pan <<= 8; + pan |= camerabuff[14]; + + tilt = camerabuff[15]; + tilt <<= 8; + tilt |= camerabuff[16]; + + return true; +} + +*/ +bool Camera::takePicture() { + frameptr = 0; + return cameraFrameBuffCtrl(VC0706_STOPCURRENTFRAME); +} +/* +boolean Camera::resumeVideo() { + return cameraFrameBuffCtrl(VC0706_RESUMEFRAME); +} + +boolean Camera::TVon() { + uint8_t args[] = {0x1, 0x1}; + return runCommand(VC0706_TVOUT_CTRL, args, sizeof(args), 5); +} +boolean Camera::TVoff() { + uint8_t args[] = {0x1, 0x0}; + return runCommand(VC0706_TVOUT_CTRL, args, sizeof(args), 5); +} +*/ +bool Camera::cameraFrameBuffCtrl(uint8_t command) { + uint8_t args[] = {0x1, command}; + return runCommand(VC0706_FBUF_CTRL, args, sizeof(args), 5); +} + +uint32_t Camera::frameLength(void) { + uint8_t args[] = {0x01, 0x00}; + if (!runCommand(VC0706_GET_FBUF_LEN, args, sizeof(args), 9)) + return 0; + + uint32_t len; + len = camerabuff[5]; + len <<= 8; + len |= camerabuff[6]; + len <<= 8; + len |= camerabuff[7]; + len <<= 8; + len |= camerabuff[8]; + + return len; +} +/* + +uint8_t Camera::available(void) { + return bufferLen; +} + +*/ +uint8_t * Camera::readPicture(uint8_t n,uint8_t* outSize) { + uint8_t args[] = {0x0C, 0x0, 0x0A, + 0, 0, frameptr >> 8, frameptr & 0xFF, + 0, 0, 0, n, + CAMERADELAY >> 8, CAMERADELAY & 0xFF}; + + if (! runCommand(VC0706_READ_FBUF, args, sizeof(args), 5, false)) + return 0; + + + // read into the buffer PACKETLEN! + int outputSize=readResponse(n+5, CAMERADELAY)-5; + if (outputSize == 0) + return 0; + if(outSize!=NULL)*outSize=outputSize; + + frameptr += outputSize; + + return camerabuff; +} + + +// +// Low level commands +// + +bool Camera::runCommand(uint8_t cmd, uint8_t *args, uint8_t argn, uint8_t resplen, bool flushflag) { + // flush out anything in the buffer? + if (flushflag) { + readResponse(100, 10); + } + + sendCommand(cmd, args, argn); + if (readResponse(resplen, 200) != resplen) + return false; + if (! verifyResponse(cmd)) + return false; + return true; +} + + +void Camera::sendCommand(uint8_t cmd, uint8_t args[], uint8_t argn) { + getSerial().putc(0x56); + getSerial().putc(serialNum); + getSerial().putc(cmd); + + for (uint8_t i=0; i<argn; i++) { + getSerial().putc(args[i]); + } +} + +uint8_t Camera::readResponse(uint8_t numbytes, uint8_t timeout) { + uint8_t counter = 0; + bufferLen = 0; + + while ((timeout != counter) && (bufferLen != numbytes)){ + int avail = getSerial().readable(); + if (avail <= 0) { + wait_ms(1); + counter++; + continue; + } + counter = 0; + // there's a byte! + camerabuff[bufferLen++] = getSerial().getc(); + } + return bufferLen; +} + +bool Camera::verifyResponse(uint8_t command) { + if ((camerabuff[0] != 0x76) || + (camerabuff[1] != serialNum) || + (camerabuff[2] != command) || + (camerabuff[3] != 0x0)) + return false; + return true; + +} + +void Camera::printBuff() { +} \ No newline at end of file