📄 camfun.cpp
字号:
// CamFum.cpp: implementation of the CCamFun class.
//
//////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include "math.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
unsigned short CapImgInfo[CAP_NUM_OF_SETUP_MODE];
ZOOM_POS_INFO ZPosInfo[] = {
//edge, FNo_26, FNo_80
{ 1758, 2663, 5619 },
{ 1899, 2751, 5805 },
{ 2039, 2844, 6001 },
{ 2180, 2944, 6212 },
{ 2320, 3052, 6440 },
{ 2461, 3170, 6689 },
{ 2601, 3298, 7959 },
{ 2742, 3436, 7250 },
{ 2882, 3575, 7543 },
{ 3022, 3745, 7902 },
{ 3163, 3912, 8254 },
{ 3303, 4079, 8607 },
{ 3444, 4243, 8953 },
{ 3584, 4405, 9295 },
{ 3725, 4578, 9660 },
{ 3865, 4751, 10025 },
{ 4006, 4921, 10383 }
};
#define ZOOM_POS_TBL_SIZE (sizeof(ZPosInfo)/sizeof(ZPosInfo[0]))
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CCamFun::CCamFun()
{
strcpy((char*)CameraDirName, "\\.CDMI1\\003K13 0");
}
CCamFun::~CCamFun()
{
}
BOOL CCamFun::Open()
{
if( I43IO_ComOpen() != I43ERR_OK ) return 1;
return 0;
}
BOOL CCamFun::Close()
{
if( I43IO_ComClose() != I43ERR_OK ) return 1;
return 0;
}
void CCamFun::WaitBusy()
{
unsigned short State;
while(1) {
Sleep(100);
I43_GetWord(BUSYFLAG, &State);
Sleep(50);
if(State != CALIB_BUSY) break;
}
}
void CCamFun::ViewMode()
{
I43_SetMode((I43_MODE)0x40);
WaitForMode(0x40);
}
void CCamFun::IdleMode()
{
I43_SetMode((I43_MODE)0x30);
WaitForMode(0x30);
}
void CCamFun::WaitForMode(unsigned short Mode)
{
unsigned short SR1,SR2;
do{
I43_QueryStatus(&SR1,&SR2);
}while(((SR1 >> 8)& 0x00ff) != Mode);
}
BOOL CCamFun::DownloadFileToBuf(unsigned char *Buf, unsigned char *FileName, unsigned long Size)
{
unsigned short wSr1,wSr2;
I43_SetMemLocationPtr((I43_MEMORY_LOCATION) 0x15, CameraDirName, 16);
I43_SetCurrentPath();
I43_SetFileType(1);
I43_SetFileName(FileName);
I43_SetMemLocationPtr((I43_MEMORY_LOCATION) 0x1D, Buf, Size);
I43_XMTFile((I43_BOOL) 1,(I43_BOOL) 0);
I43_QueryStatus(&wSr1, &wSr2);
if ((wSr1 & 0xFF) != 0x0B) return 1; //Transfer the file error
return 0;
}
void CCamFun::CaptureImage()
{
I43_SetWord(PARAM0, 2);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
}
void CCamFun::SetWBValue(unsigned short sel)
{
unsigned short i,j;
unsigned short rgb2yuv[3][3];
unsigned short RB_Ratio[8] = {
0x0064, //DayLight R = 1.000
0x0064, // B = 1.000
0x006A, //Cloudy R = 1.058
0x005F, // B = 0.944
0x0047, //Tungsten R = 0.708
0x0088, // B = 1.363
0x0052, //Fluorenscent R = 0.814
0x007B // B = 1.228
};
unsigned short RGB2YUV[3][3] = {
0x0033, 0x00E2, 0x0215,
0x0000, 0x0322, 0x0122,
0x0107, 0x0307, 0x0000
};
for( i=0; i<3; i++ ) {
rgb2yuv[i][0] = RGB2YUV[i][0];
rgb2yuv[i][1] = RGB2YUV[i][1];
rgb2yuv[i][2] = RGB2YUV[i][2];
}
switch(sel) {
case WB_AUTO:
I43_SetRGB2YUV(rgb2yuv);
I43_SetWBMode( I43WBM_AUTO ); // View/Capture in YUV algorithm
break;
case WB_DAYLIGHT:
case WB_CLOUDY:
case WB_TUNGSTEN:
case WB_FLUORESCENT:
I43_SetRGB2YUV(rgb2yuv);
I43_SetWBValues( (CapImgInfo[CAP_DAYLIGHT_R_GAIN] * RB_Ratio[sel*2 - 2]) /100,
0x0100, (CapImgInfo[CAP_DAYLIGHT_B_GAIN] * RB_Ratio[sel*2 - 1]) /100 );//bruce
I43_SetWBMode( I43WBM_MANUAL );
break;
case WB_BLACKWHITE:
for( i=1; i<3; i++ )
{ for( j=0; j<3; j++ ) rgb2yuv[i][j] = 0; }
I43_SetRGB2YUV(rgb2yuv);
break;
case WB_MANUAL:
case WB_MANUAL + 1:
I43_SetRGB2YUV(rgb2yuv);
I43_SetWBValues(CapImgInfo[CAP_MANUAL_R_GAIN], CapImgInfo[CAP_MANUAL_G_GAIN], CapImgInfo[CAP_MANUAL_B_GAIN]);
I43_SetWBMode( I43WBM_MANUAL );
break;
}
}
void CCamFun::DoFlashCharge(unsigned short sel)
{
if(sel != 1) {
I43_SetWord(PARAM0, 4);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
}
}
void CCamFun::LoadCameraDefaultValue()
{
unsigned short i;
I43_SetWord(PARAM0, 7);
Sleep(10);
I43_SetWord(PARAM1, 0);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
//Gets the default value from camera
for(i = 0; i < CAP_NUM_OF_SETUP_MODE; i++) {
I43_GetWord(0x9200 + i, &CapImgInfo[i]);
Sleep(50);
}
}
void CCamFun::SaveCameraDefaultValue()
{
unsigned short i;
for(i = 0; i < CAP_NUM_OF_SETUP_MODE; i++) {
I43_SetWord(0x9200 + i, CapImgInfo[i]);
Sleep(50);
}
I43_SetWord(PARAM0, 7);
Sleep(10);
I43_SetWord(PARAM1, 1);
Sleep(10);
I43_SetWord(PARAM2, 0);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
}
void CCamFun::TurnLCD(unsigned short sw)
{
I43_SetWord(PARAM0, 5);
Sleep(10);
I43_SetWord(PARAM1, sw);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
if(!sw) { //Green LED glittered
I43_SetWord(PARAM0, 20);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xE7);
WaitBusy();
}
}
unsigned short CCamFun::GetHceVersion()
{
unsigned short version;
I43_SetWord(CMD_ADDR, 0x90);
WaitBusy();
I43_GetWord((I43_UINT16)OUTPARAM0, &version);
Sleep(10);
return version;
}
unsigned short CCamFun::ZoomAction(unsigned short ZPos)
{
unsigned short FNum;
I43_SetWord(PARAM0, 1);
Sleep(10);
I43_SetWord(PARAM1, ZPos);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
I43_GetWord(OUTPARAM0, &FNum);
Sleep(10);
return FNum;
}
unsigned short CCamFun::RemainPics()
{
unsigned short wSuccess, wCount, Num, sizems, sizels;
I43_GetStorageMediaStatus(&wSuccess, &wCount, &Num, &sizems, &sizels);
return Num;
}
void CCamFun::SetExposureBias(unsigned short bias)
{
unsigned char ExpBias[13] = { 28, 26, 24, 23, 21, 18, 16, 14, 11, 8, 6, 3, 0 };
I43_SetExposureDeviation(ExpBias[bias]);
}
unsigned short CCamFun::FnoToZPos(unsigned short Fno)
{
unsigned short Edge0,Edge1,Edge;
unsigned short Fno0,Fno1;
unsigned char index;
if(Fno < ZPosInfo[0].OFno) return ZPosInfo[0].OFno;
if(Fno > ZPosInfo[ZOOM_POS_TBL_SIZE - 1].SFno) return ZPosInfo[ZOOM_POS_TBL_SIZE - 1].SFno;
if((Fno > ZPosInfo[ZOOM_POS_TBL_SIZE -1].OFno) && (Fno < ZPosInfo[0].SFno)) return (ZPosInfo[ZOOM_POS_TBL_SIZE - 1].OFno);
index = 0;
while(1) {
if(index / 17) Fno1 = ZPosInfo[index % 17].SFno;
else Fno1 = ZPosInfo[index % 17].OFno;
if(Fno <= Fno1) break;
index++;
};
if(Fno == Fno1) {
Edge = ZPosInfo[index].edge;
return Edge;
}
if(index / 17) {
Fno0 = ZPosInfo[index % 17 - 1].SFno;
}
else {
Fno0 = ZPosInfo[index % 17 - 1].OFno;
}
Edge1 = ZPosInfo[index % 17].edge;
Edge0 = ZPosInfo[index % 17 - 1].edge;
Edge = (unsigned short)(Edge0 + (Edge1 - Edge0) * (Fno - Fno0) / (Fno1 - Fno0));
return Edge;
}
//RTC function
unsigned char CCamFun::IsLeapYear(unsigned short year)
{
if ( year % 4 ) return 0; // not mutiple of 4
if ( year % 100 == 0 )
if ( year % 400 ) return 0; // is mutiple of 100, not 400
return 1;
}
void CCamFun::RTC2Time()
{
unsigned short Month_TBL[12] = {
31,28,31,30,31,30,31,31,30,31,30,31
};
unsigned short Month_Leap_TBL[12] = {
31,29,31,30,31,30,31,31,30,31,30,31
};
unsigned long TotalDay;
unsigned long TotalSec;
unsigned short i;
RTCTimeHi = (RTCTimeHi<<2)| (unsigned short)(RTCTimeLo >> 30);
RTCTimeLo = (RTCTimeLo<<2);
// Get TotalDay and TotalSec
TotalDay = 0;
TotalSec = 0;
for (i=0;i<RTCTimeHi;i++) {
TotalDay += (0x10000000L/(86400L/16L));
TotalSec += (0x10000000L%(86400L/16L)) * 16L; // (0x5b00)
}
TotalDay += RTCTimeLo / 86400L;
TotalSec += RTCTimeLo % 86400L;
TotalDay += TotalSec / 86400L;
TotalSec = TotalSec % 86400L;
// Process Time Struct
CurTime.Hour = (unsigned char)(TotalSec / 3600L);
TotalSec = (unsigned long)(TotalSec % 3600L);
CurTime.Minute = (unsigned char)(TotalSec / 60L);
CurTime.Sec = (unsigned char)(TotalSec % 60L);
// 400 year date = (365*400+100-4+1)
// 100 year date = (365*100+25-1)
// 4 year date = 365*4 + 1
// Increase by 400 years
CurDate.Year = (unsigned short)BASE_YEAR;
CurDate.Year += (unsigned short)(TotalDay / (365L*400L+100L-4L+1L) * 400L);
TotalDay %= (unsigned long)(365L*400L+100L-4L+1L);
// Increase by 100 years
CurDate.Year += (unsigned short)(TotalDay / (365L*100L+25L-1L) * 100L);
TotalDay %= (unsigned long)(365L*100L+25L-1L);
// Increase by 4 years
CurDate.Year += (unsigned short)(TotalDay / (365L*4L+1L) * 4L);
TotalDay %= (unsigned long)(365L*4L+1L);
// Last year may be 366 or 365 days
// note : day is calculated from 0
if ( (TotalDay / 365L) == 4 ) { // it is the last day of leap-year
CurDate.Year += 3;
TotalDay = 365L;
}
else {
CurDate.Year += (unsigned short)(TotalDay / 365L);
TotalDay %= 365L;
}
TotalDay ++; // Count date from 1
// check the 29 day issue ???
i=0;
if ( ! IsLeapYear (CurDate.Year) ) {
while ( TotalDay > Month_TBL[i] )
TotalDay -= Month_TBL[i++];
}
else {
while ( TotalDay > Month_Leap_TBL[i] )
TotalDay -= Month_Leap_TBL[i++];
}
CurDate.Month = i+1; // count month from 1
CurDate.Day = (unsigned char)TotalDay;
}
unsigned long CCamFun::GetTotalDay()
{
unsigned short Month_TBL[12] = {
31,28,31,30,31,30,31,31,30,31,30,31
};
unsigned short Month_Leap_TBL[12] = {
31,29,31,30,31,30,31,31,30,31,30,31
};
unsigned char i;
unsigned long Year;
unsigned long TotalDay;
Year = CurDate.Year - BASE_YEAR;
TotalDay = (Year*365L)+(Year/4L)-(Year/100L)+(Year/400L);
for ( i=0;i<(CurDate.Month-1);i++ ) {
if (IsLeapYear ( CurDate.Year )) {
TotalDay += (unsigned long) Month_Leap_TBL[i];
}
else {
TotalDay += (unsigned long) Month_TBL[i];
}
}
TotalDay += CurDate.Day;
return (TotalDay-1); // Day is calcualte from 0, count from 1
}
void CCamFun::Time2RTC()
{
unsigned long TotalDay;
unsigned long TotalSec;
TotalSec = (unsigned long)CurTime.Sec + (unsigned long)CurTime.Minute*60L + (unsigned long)CurTime.Hour * 3600L;
TotalDay = GetTotalDay();
RTCTimeHi = 0;
RTCTimeLo = 0;
while ( TotalDay >= (0x10000000L/(86400L/16)+1) ) {
RTCTimeHi++;
RTCTimeLo += 0xF68; // divide by 16
TotalDay -= (0x10000000L/(86400L/16)+1);
}
RTCTimeLo += TotalDay * (86400L/16) + (TotalSec/16);
if ( RTCTimeLo > 0x10000000L ) {
RTCTimeHi++;
RTCTimeLo -= 0x10000000L;
}
RTCTimeLo = (unsigned long)((RTCTimeLo << 4)+(TotalSec%16));
// RTCTime = TotalDay * (86400L) + (TotalSec);
RTCTimeLo = (RTCTimeLo>>2)|(((unsigned long)RTCTimeHi<<30)&0xC0000000 );
RTCTimeHi = (RTCTimeHi>>2);
}
void CCamFun::SetRTCTime()
{
I43_SetWord((I43_UINT16)PARAM0, (I43_UINT16)(RTCTimeLo & 0xffff));
I43_SetWord((I43_UINT16)PARAM1, (I43_UINT16)((RTCTimeLo & 0xffff0000) >>16));
I43_SetWord((I43_UINT16)PARAM2, (I43_UINT16)RTCTimeHi);
I43_SetWord(CMD_ADDR, 0xb5);
WaitBusy();
}
void CCamFun::GetRTCTime()
{
unsigned short RTCH,RTCL;
I43_SetWord(CMD_ADDR, 0xb6);
WaitBusy();
I43_GetWord((I43_UINT16)OUTPARAM0, (I43_UINT16*)&RTCL);
Sleep(10);
I43_GetWord((I43_UINT16)OUTPARAM1, (I43_UINT16*)&RTCH);
Sleep(10);
I43_GetWord((I43_UINT16)OUTPARAM2, (I43_UINT16*)&RTCTimeHi);
Sleep(10);
RTCTimeLo = (unsigned long)(RTCH << 16) | RTCL;
}
void CCamFun::SetCurTimeToRTC()
{
struct tm *newtime;
long ltime;
time( <ime );
newtime = localtime( <ime );// gmtime( <ime );
CurTime.Hour = newtime->tm_hour;//(newtime->tm_hour + 8)%24;
CurTime.Minute = newtime->tm_min;
CurTime.Sec = newtime->tm_sec;
CurDate.Day = newtime->tm_mday;
CurDate.Month = newtime->tm_mon + 1; // 0 - 11 (+1)
CurDate.Year = newtime->tm_year + 1900; //current year - 1900
Time2RTC();
SetRTCTime();
}
void CCamFun::GetCurRTC(char *TimeString)
{
GetRTCTime();
RTC2Time();
sprintf(TimeString,"%4d.%02d.%02d %02d:%02d:%02d", CurDate.Year, CurDate.Month, CurDate.Day, CurTime.Hour,CurTime.Minute,CurTime.Sec);
}
BOOL CCamFun::DeleteLastOne()
{
unsigned short ret;
IdleMode();
I43_FileOperation((I43_BOOL)0, I43_SCOPE_DCF_OBJECT, 0x40, &ret );
return ret;
}
unsigned short CCamFun::GetZoomPos()
{
unsigned short ZPos;
I43_SetWord(CMD_ADDR, 0xC8);
WaitBusy();
I43_GetWord(OUTPARAM0, &ZPos);
Sleep(50);
return ZPos;
}
unsigned short CCamFun::ZPosToFNum(unsigned short Edge, unsigned short Apt_sw)
{
unsigned short Fno[2];
unsigned short Edge0,Edge1;
unsigned short Fno0[2],Fno1[2];
unsigned char index;
unsigned char i;
if(Edge < ZPosInfo[0].edge) Edge = ZPosInfo[0].edge;
if(Edge > ZPosInfo[ZOOM_POS_TBL_SIZE].edge) Edge = ZPosInfo[ZOOM_POS_TBL_SIZE].edge;
for(i=0; i < 2; i++) {
index = 0;
while(1) {
Edge1 = ZPosInfo[index].edge;
if(Edge <= Edge1) break;
index++;
};
if(Edge == Edge1) {
Fno[0] = ZPosInfo[index].OFno;
Fno[1] = ZPosInfo[index].SFno;
return Fno[Apt_sw];
}
Edge0 = ZPosInfo[index - 1].edge;
Fno1[i] = i ? ZPosInfo[index].SFno : ZPosInfo[index].OFno;
Fno0[i] = i ? ZPosInfo[index - 1].SFno : ZPosInfo[index - 1].OFno;
Fno[i] = (unsigned short)(Fno0[i] + (Fno1[i] - Fno0[i]) * (Edge - Edge0) / (Edge1 - Edge0));
}
return Fno[Apt_sw];
}
unsigned long CCamFun::GetCaptureCount()
{
unsigned short CountL, CountH;
I43_SetWord(PARAM0, 0);
Sleep(10);
I43_SetWord(PARAM1, 4);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA3);
WaitBusy();
I43_GetWord(0x9200, &CountL);
Sleep(10);
I43_GetWord(0x9201, &CountH);
Sleep(10);
return ((CountH << 16) | CountL);
}
void CCamFun::SetManualSaturation(unsigned short level)
{
I43_SetWord(PARAM0, 0xA);
Sleep(10);
I43_SetWord(PARAM1, level);
Sleep(10);
I43_SetWord(CMD_ADDR, 0xA5);
WaitBusy();
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -