by davedave » Thu Aug 24, 2006 10:04 pm
Yup, modified the screen dump event to only spit out the brightest pixel and displaying the results in matlab. The result is poor at the moment so I'll be implementing a software low pass filter (average) on the data between rows (columns with the camera on its side).
So the modfied code: Receive 'EF' over serial then
1. get dump line
2. pick off red pixels
3. run 3 point averager
4. pick off brightest pixel
5. send brightest pixel over serial
6. repeat till finished
3 and 4 run in one pass, hopefully 2,3,4 in one pass once I get some time.
Here's my modifications and shamless rip off of Johns code with some matlab code including sample data. I haven't put the averager/filter in yet. It should appear as almost a straight line, but obviously doesn't.
function ans = goodData()
% cam holds uncalibrated hexadecimal range data from AVRcam. First byte
% seems to always be bad
% cam2 is similar, but more carefully set up to have a chance at seeing
% side to side
cam = '01 69 69 69 69 69 69 69 69 69 69 67 67 87 87 87 89 67 67 67 67 67 67 65 67 65 65 65 65 65 41 65 65 65 65 65 65 65 65 65 65 65 65 65 63 63 63 63 63 63 63 73 03 05 4D 07 25 07 05 43 73 03 5F 03 2D 09 01 1F 55 01 05 2D';
cam2 = '01 01 01 01 57 43 57 57 57 57 55 55 55 55 55 55 55 55 55 55 55 55 49 55 53 55 03 55 55 53 55 55 55 53 53 53 53 53 53 53 53 53 53 53 51 51 43 51 51 01 23 17 15 51 51 51 4F 51 51 53 53 53 53 1B 2F 51 51 51 4F 4F 4F 4F';
hold on;
m=0;
for n=1:3:(length(cam)-1)
m = m+1;
camN(m)=hex2dec([cam(n),cam(n+1)]);
end
plot(camN,'g');
m=0;
for n=1:3:(length(cam2)-1)
m = m+1;
camN(m)=hex2dec([cam2(n),cam2(n+1)]);
end
plot(camN,'r');
hold off;
Modifications to AVRcam:
Added rangefinding event.
In frameMgr_aquireLine():
if ((currentState == ST_FrameMgr_DumpingFrame)||( currentState == ST_FrameMgr_RF))
In frameMgr_processLine():
else if (currentState == ST_FrameMgr_RF)
{
unsigned char count =0;
unsigned char max =0;
unsigned char place =0;
unsigned char count1 =0;
unsigned char max1 =0;
unsigned char place1 =0;
volatile unsigned char dataToSend1;
/* pick off the largest red value then send it through serial followed
by byte containing magnitude and number of counts at that level (max = 16) */
/* currentLineBuffer is getting "g" previousLineBuffer is getting "b-r" */
//UartInt_txByte(0x0B); /* send the header byte */
//UartInt_txByte(lineCount); /* send the line count */
for (i=0; i<NUM_PIXELS_IN_A_DUMP_LINE; i+=2)
{
/* *previousLineBuffer contains red and blue data*/
place = previousLineBuffer[i];
place &= 0x0F;
if (max < place)
{
count=1;
max = place;
dataToSend = i;
}
if (max==place)
{
count++;
}
place1 = previousLineBuffer[i+1];
place1 &= 0x0F;
if (max1 < place1)
{
count1=1;
max1 = place1;
dataToSend1 = (i+1);
}
if (max1==place1)
{
count1++;
}
}
/* dataToSend should be packed now */
//UartInt_txByte(dataToSend);
//UartInt_txByte((count<<4)|(max&0x0F)); // send count and max as one byte
//UartInt_txByte(max); // send count and max as one byte
//UartInt_txByte(max1);
UartInt_txByte(dataToSend1); // this is the maximum red location
//UartInt_txByte((count1<<4)|(max1&0x0F)); // send count1 and max1 as one byte
//UartInt_txByte(0x0F); /* send line end */
/* once all the data is sent, increment out line count by 2 since
we really get 2 lines worth of pixels on each pass */
/* Update...increment only by 1, but only send 72 double-lines */
lineCount++;
/* check to see if we have retrieved all of the needed lines */
if (lineCount >= 72) /* half 144, since we send two lines at a time */
{
/* we're done, so send the dump complete?...nope, just change
states and we should be fine */
lineCount = 0;
currentState = ST_FrameMgr_idle;
/* disable the PCLK counting overflow interrupt */
TIMSK &= DISABLE_PCLK_TIMER1_OVERFLOW_BITMASK;
CamConfig_setCamReg(0x11,0x00); /* reset the frame rate to normal*/
CamConfig_sendFifoCmds();
}
else
{
/* we have more lines to acquire in this frame, so keep on truckin...*/
PUBLISH_FAST_EVENT(FEV_PROCESS_LINE_COMPLETE);
}
}