1 //+----------------------------------------------------------------------------
11 // Created: 12 Jan 2000
13 //+----------------------------------------------------------------------------
24 #include "dc210camera.h"
27 //+----------------------------------------------------------------------------
29 // Function: CKodakDC210
37 // History: sgasch Created Header 13 Jan 2000
39 //+----------------------------------------------------------------------------
40 CKodakDC210::CKodakDC210(char *szDevice, int iSpeed)
42 _fInitialized = false;
47 // Open the serial port.
49 if (NULL == (_pSerialPort = new CSerialPort(szDevice)))
51 Trace("CKodakDC210: unable to open serial port, aborting.");
54 Trace("Port opened.\n");
57 // Send the initialize command.
61 Trace("KodakDC210: unable to initialize camera communications, "
65 Trace("Camera initialized.\n");
68 // Set communications speed.
72 if (!SetSpeed(g_iSpeed))
74 Trace("InitiailzeCamera: Can't set baud rate.\n");
78 Trace("Speed set.\n");
81 // Request a dump of properties.
83 if (!RefreshProperties())
85 Trace("Unable to get properties of camera.\n");
88 Trace("Properties received.\n");
94 //+----------------------------------------------------------------------------
96 // Function: ~CKodakDC210
104 // History: sgasch Created Header 13 Jan 2000
106 //+----------------------------------------------------------------------------
107 CKodakDC210::~CKodakDC210(void)
110 // Reset camera and serial port speed to default of 9600 bps.
114 Trace("~CKodakDC210: Can't reset the baud rate to 9600.");
118 // Close the serial port.
125 _fInitialized = false;
129 //+----------------------------------------------------------------------------
131 // Function: Initialize
139 // History: sgasch Created Header 13 Jan 2000
141 //+----------------------------------------------------------------------------
142 bool CKodakDC210::Initialize(void)
145 // The "initialize" command really causes the camera to query battery
146 // status but we send something here just to see if we can talk to the
147 // camera and fail if not. Also if the camera is asleep this will wake
150 if (!SendCommand(DC210_INITIALIZE, 0, 0, 0, 0))
152 Trace("Initialize: Initialize command failed -- camera could be "
153 "asleep. Waiting 10 sec and retrying communications.\n");
159 // According to the host interface spec the camera needs at most
160 // ten seconds to wake up and be ready to process more commands.
163 if (!SendCommand(DC210_INITIALIZE, 0, 0, 0, 0))
165 Trace("Initialize: Second try failed too, assuming bad "
172 // Like all commands, the DC210 returns a command-compete status code
173 // to notify you when it's done. If it can't send a command-complete
174 // code within three seconds it will send a busy code.
176 if (!CommandComplete())
178 Trace("Initialize: Never received command complete signal.\n");
190 //+----------------------------------------------------------------------------
192 // Function: SetSpeed
196 // Arguments: int iBps
200 // History: sgasch Created Header 13 Jan 2000
202 //+----------------------------------------------------------------------------
203 bool CKodakDC210::SetSpeed(int iBps)
208 // Determine what arguments to send to the camera to communicate
234 Trace("SetSpeed: illegal speed.\n");
239 // Send the command to the camera. There will be no response to this
242 if (!SendCommand(DC210_SET_SPEED, bArg1, bArg2, 0, 0))
244 Trace("SetSpeed: Camera communication error, speed not changed.\n");
249 // Sleep for a little while to let the camera switch speeds.
254 // Change the rate at the serial port.
256 if (!_pSerialPort->SetBaudrate(iBps))
258 Trace("SetSpeed: error switching serial port to new speed?\n");
263 // Sleep again to be sure everythign is done before another command
275 //+----------------------------------------------------------------------------
277 // Function: TakePicture
285 // History: sgasch Created Header 13 Jan 2000
287 //+----------------------------------------------------------------------------
288 bool CKodakDC210::TakePicture(void)
291 // Precondition: we are initialized.
293 ASSERT(_fInitialized == true);
296 // Send the command to the camera.
298 if (!SendCommand(DC210_TAKE_PICTURE, 0, 0, 0, 0))
300 Trace("TakePicture: Failed to send command.\n");
305 // Wait for the camera's command complete code.
307 if (!CommandComplete())
309 Trace("TakePicture: Did not receive command completion signal.\n");
320 //+----------------------------------------------------------------------------
322 // Function: RefreshProperties
328 // Returns: bool - true if command successful
330 // History: sgasch Created Header 8 Jun 1999
332 //+----------------------------------------------------------------------------
333 bool CKodakDC210::RefreshProperties(void)
336 // We do _not_ assert that we are initialized here because this routine
337 // gets called in the constructor before we are initialized fully as
338 // part of class startup.
342 // Send the command to the camera.
344 if (!SendCommand(DC210_STATUS, 0, 0, 0, 0))
346 Trace("RefreshProperties: Failed to send command.\n");
351 // Immediately after the ACK byte from the camera (which SendCommand
352 // checks for) the camera will send us a 256 byte buffer (actually
353 // one packet control byte, 256 data bytes and one checksum byte for
354 // a total of 258 bytes on the serial line) This buffer is the one
355 // with all the status data in it.
357 if (!ReadPacket(_bRawStatusData, 256))
359 Trace("RefreshProperties: Did not get expected status buffer packet "
365 // After the buffer we get the usual command complete signal.
367 if (!CommandComplete())
369 Trace("RefreshProperties: Did not get command completion signal.\n");
379 //+----------------------------------------------------------------------------
381 // Function: GetRawStatusData
385 // Arguments: BYTE *pData
389 // History: sgasch Created Header 13 Jan 2000
391 //+----------------------------------------------------------------------------
392 bool CKodakDC210::GetRawStatusData(BYTE *pData)
394 if (RefreshProperties())
396 memcpy(pData, _bRawStatusData, 256);
403 //+----------------------------------------------------------------------------
405 // Function: GetFirmwareVersion
409 // Arguments: int *piMajor,
414 // History: sgasch Created Header 13 Jan 2000
416 //+----------------------------------------------------------------------------
417 bool CKodakDC210::GetFirmwareVersion(int *piMajor, int *piMinor)
419 *piMajor = _bRawStatusData[2];
420 *piMinor = _bRawStatusData[3];
425 //+----------------------------------------------------------------------------
427 // Function: GetRomVersion
431 // Arguments: int *piMajor,
436 // History: sgasch Created Header 13 Jan 2000
438 //+----------------------------------------------------------------------------
439 bool CKodakDC210::GetRomVersion(int *piMajor, int *piMinor)
441 *piMajor = _bRawStatusData[4];
442 *piMinor = _bRawStatusData[5];
447 //+----------------------------------------------------------------------------
449 // Function: GetBatteryStatus
453 // Arguments: DC210_BATTERY_STATE *pState
457 // History: sgasch Created Header 13 Jan 2000
459 //+----------------------------------------------------------------------------
460 bool CKodakDC210::GetBatteryStatus(DC210_BATTERY_STATE *pState)
462 switch(_bRawStatusData[8])
465 *pState = battery_full;
468 *pState = battery_low;
471 *pState = battery_empty;
475 *pState = battery_unknown;
482 //+----------------------------------------------------------------------------
484 // Function: IsAdapterAttached
488 // Arguments: bool *pfAttached
492 // History: sgasch Created Header 13 Jan 2000
494 //+----------------------------------------------------------------------------
495 bool CKodakDC210::IsAdapterAttached(bool *pfAttached)
497 if (RefreshProperties())
499 if (_bRawStatusData[9])
513 //+----------------------------------------------------------------------------
515 // Function: GetZoomState
519 // Arguments: DC210_ZOOM_STATE *pZoom
523 // History: sgasch Created Header 13 Jan 2000
525 //+----------------------------------------------------------------------------
526 bool CKodakDC210::GetZoomState(DC210_ZOOM_STATE *pZoom)
528 if (RefreshProperties())
530 switch(_bRawStatusData[16] & 0x0F)
533 *pZoom = zoom_fully_zoomed;
545 *pZoom = zoom_wideangle;
548 *pZoom = zoom_closeup;
552 *pZoom = zoom_unknown;
561 //+----------------------------------------------------------------------------
563 // Function: GetResolution
567 // Arguments: int *piWidth,
572 // History: sgasch Created Header 13 Jan 2000
574 //+----------------------------------------------------------------------------
575 bool CKodakDC210::GetResolution(int *piWidth, int *piHeight)
577 if (0 == _bRawStatusData[22])
582 else if (1 == _bRawStatusData[22])
595 //+----------------------------------------------------------------------------
597 // Function: IsFlashCharged
601 // Arguments: bool *pfCharged
605 // History: sgasch Created Header 13 Jan 2000
607 //+----------------------------------------------------------------------------
608 bool CKodakDC210::IsFlashCharged(bool *pfCharged)
610 if (RefreshProperties())
612 if (_bRawStatusData[18])
626 //+----------------------------------------------------------------------------
628 // Function: GetFlashState
632 // Arguments: DC210_FLASH_STATE *pState
636 // History: sgasch Created Header 13 Jan 2000
638 //+----------------------------------------------------------------------------
639 bool CKodakDC210::GetFlashState(DC210_FLASH_STATE *pState)
641 switch (_bRawStatusData[20])
644 *pState = flash_auto;
647 *pState = flash_fill;
653 *pState = flash_auto_redeye;
656 *pState = flash_fill_redeye;
660 *pState = flash_unknown;
667 //+----------------------------------------------------------------------------
669 // Function: GetCompressionState
673 // Arguments: DC210_COMPRESSION_STATE *pState
677 // History: sgasch Created Header 13 Jan 2000
679 //+----------------------------------------------------------------------------
680 bool CKodakDC210::GetCompressionState(DC210_COMPRESSION_STATE *pState)
682 switch (_bRawStatusData[19])
685 *pState = compression_none;
688 *pState = compression_low;
691 *pState = compression_medium;
694 *pState = compression_high;
698 *pState = compression_unknown;
705 //+----------------------------------------------------------------------------
707 // Function: GetPictureFormat
711 // Arguments: DC210_FILE_FORMAT *eFormat
715 // History: sgasch Created Header 13 Jan 2000
717 //+----------------------------------------------------------------------------
718 bool CKodakDC210::GetPictureFormat(DC210_FILE_FORMAT *eFormat)
720 if (2 == _bRawStatusData[23])
722 *eFormat = format_raw;
724 else if (3 == _bRawStatusData[23])
726 *eFormat = format_jpeg;
728 else if (4 == _bRawStatusData[23])
730 *eFormat = format_flashpix;
734 *eFormat = format_unknown;
741 //+----------------------------------------------------------------------------
743 // Function: GetClock
747 // Arguments: int *piCameraClock
751 // History: sgasch Created Header 13 Jan 2000
753 //+----------------------------------------------------------------------------
754 bool CKodakDC210::GetClock(int *piCameraClock)
756 if (RefreshProperties())
758 *piCameraClock = _bRawStatusData[15] |
759 (_bRawStatusData[14] << 8) |
760 (_bRawStatusData[13] << 16) |
761 (_bRawStatusData[12] << 24);
768 //+----------------------------------------------------------------------------
770 // Function: IsUsingJpeg
774 // Arguments: bool *pfJPEG
778 // History: sgasch Created Header 13 Jan 2000
780 //+----------------------------------------------------------------------------
781 bool CKodakDC210::IsUsingJpeg(bool *pfJPEG)
783 if (3 == _bRawStatusData[23])
787 else if (4 == _bRawStatusData[23])
791 else if (2 == _bRawStatusData[23])
805 //+----------------------------------------------------------------------------
807 // Function: IsUsingFlashPix
811 // Arguments: bool *pfFlashPix
815 // History: sgasch Created Header 13 Jan 2000
817 //+----------------------------------------------------------------------------
818 bool CKodakDC210::IsUsingFlashPix(bool *pfFlashPix)
820 if (3 == _bRawStatusData[23])
824 else if (4 == _bRawStatusData[23])
828 else if (2 == _bRawStatusData[23])
842 //+----------------------------------------------------------------------------
844 // Function: GetLifetimePictureCount
848 // Arguments: int *piPictures
852 // History: sgasch Created Header 13 Jan 2000
854 //+----------------------------------------------------------------------------
855 bool CKodakDC210::GetLifetimePictureCount(int *piPictures)
857 *piPictures = _bRawStatusData[26] | (_bRawStatusData[25] << 8);
862 //+----------------------------------------------------------------------------
864 // Function: GetLifetimeFlashCount
868 // Arguments: int *piFlashes
872 // History: sgasch Created Header 13 Jan 2000
874 //+----------------------------------------------------------------------------
875 bool CKodakDC210::GetLifetimeFlashCount(int *piFlashes)
877 *piFlashes = _bRawStatusData[28] | (_bRawStatusData[27] << 8);
882 //+----------------------------------------------------------------------------
884 // Function: IsTimerOn
888 // Arguments: bool *pfTimer
892 // History: sgasch Created Header 13 Jan 2000
894 //+----------------------------------------------------------------------------
895 bool CKodakDC210::IsTimerOn(bool *pfTimer)
897 if (_bRawStatusData[29])
909 //+----------------------------------------------------------------------------
911 // Function: IsMemoryCardInserted
915 // Arguments: bool *pfInserted
919 // History: sgasch Created Header 13 Jan 2000
921 //+----------------------------------------------------------------------------
922 bool CKodakDC210::IsMemoryCardInserted(bool *pfInserted)
924 if (_bRawStatusData[30] & DC210_MEMORY_CARD_INSERTED)
936 //+----------------------------------------------------------------------------
938 // Function: IsMemoryCardWriteProtected
942 // Arguments: bool *pfWriteProt
946 // History: sgasch Created Header 13 Jan 2000
948 //+----------------------------------------------------------------------------
949 bool CKodakDC210::IsMemoryCardWriteProtected(bool *pfWriteProt)
951 if (_bRawStatusData[30] & DC210_MEMORY_CARD_WRITE_PROTECTED)
957 *pfWriteProt = false;
963 //+----------------------------------------------------------------------------
965 // Function: IsMemoryCardIllegal
969 // Arguments: bool *pfIllegal
973 // History: sgasch Created Header 13 Jan 2000
975 //+----------------------------------------------------------------------------
976 bool CKodakDC210::IsMemoryCardIllegal(bool *pfIllegal)
978 if (_bRawStatusData[30] & DC210_MEMORY_CARD_ILLEGAL)
990 //+----------------------------------------------------------------------------
992 // Function: IsMemoryCardFormatted
996 // Arguments: bool *pfFormatted
1000 // History: sgasch Created Header 13 Jan 2000
1002 //+----------------------------------------------------------------------------
1003 bool CKodakDC210::IsMemoryCardFormatted(bool *pfFormatted)
1005 *pfFormatted = (_bRawStatusData[30] & DC210_MEMORY_CARD_FORMATTED);
1010 //+----------------------------------------------------------------------------
1012 // Function: IsMemoryCardOpened
1016 // Arguments: bool *pfOpened
1020 // History: sgasch Created Header 13 Jan 2000
1022 //+----------------------------------------------------------------------------
1023 bool CKodakDC210::IsMemoryCardOpened(bool *pfOpened)
1025 *pfOpened = (_bRawStatusData[30] & DC210_MEMORY_CARD_OPENED);
1030 //+----------------------------------------------------------------------------
1032 // Function: GetMemoryCardBitvector
1036 // Arguments: BYTE *pbBitv
1040 // History: sgasch Created Header 13 Jan 2000
1042 //+----------------------------------------------------------------------------
1043 bool CKodakDC210::GetMemoryCardBitvector(BYTE *pbBitv)
1045 *pbBitv = _bRawStatusData[30];
1050 //+----------------------------------------------------------------------------
1052 // Function: IsUsingNTSC
1056 // Arguments: bool *pfNTSC
1060 // History: sgasch Created Header 13 Jan 2000
1062 //+----------------------------------------------------------------------------
1063 bool CKodakDC210::IsUsingNTSC(bool *pfNTSC)
1065 *pfNTSC = (_bRawStatusData[31]);
1070 //+----------------------------------------------------------------------------
1072 // Function: IsUsingPAL
1076 // Arguments: bool *pfPAL
1080 // History: sgasch Created Header 13 Jan 2000
1082 //+----------------------------------------------------------------------------
1083 bool CKodakDC210::IsUsingPAL(bool *pfPAL)
1085 *pfPAL = (_bRawStatusData[31]);
1090 //+----------------------------------------------------------------------------
1092 // Function: GetNumberPictures
1096 // Arguments: int *piNum
1100 // History: sgasch Created Header 13 Jan 2000
1102 //+----------------------------------------------------------------------------
1103 bool CKodakDC210::GetNumberPictures(int *piNum)
1105 *piNum = _bRawStatusData[57] | (_bRawStatusData[56] << 8);
1110 //+----------------------------------------------------------------------------
1112 // Function: GetRemainingPicturesLowCompression
1116 // Arguments: int *piNum
1120 // History: sgasch Created Header 13 Jan 2000
1122 //+----------------------------------------------------------------------------
1123 bool CKodakDC210::GetRemainingPicturesLowCompression(int *piNum)
1125 *piNum = _bRawStatusData[69] | (_bRawStatusData[68] << 8);
1130 //+----------------------------------------------------------------------------
1132 // Function: GetRemainingPicturesMedCompression
1136 // Arguments: int *piNum
1140 // History: sgasch Created Header 13 Jan 2000
1142 //+----------------------------------------------------------------------------
1143 bool CKodakDC210::GetRemainingPicturesMedCompression(int *piNum)
1145 *piNum = _bRawStatusData[71] | (_bRawStatusData[70] << 8);
1150 //+----------------------------------------------------------------------------
1152 // Function: GetRemainingPicturesHighCompression
1156 // Arguments: int *piNum
1160 // History: sgasch Created Header 13 Jan 2000
1162 //+----------------------------------------------------------------------------
1163 bool CKodakDC210::GetRemainingPicturesHighCompression(int *piNum)
1165 *piNum = _bRawStatusData[73] | (_bRawStatusData[72] << 8);
1170 //+----------------------------------------------------------------------------
1172 // Function: GetMemoryCardVolumeLabel
1176 // Arguments: char *szLabel
1180 // History: sgasch Created Header 13 Jan 2000
1182 //+----------------------------------------------------------------------------
1183 bool CKodakDC210::GetMemoryCardVolumeLabel(char *szLabel)
1185 memcpy(szLabel, &(_bRawStatusData[77]), 11);
1191 //+----------------------------------------------------------------------------
1193 // Function: GetIdString
1197 // Arguments: char *szId
1201 // History: sgasch Created Header 13 Jan 2000
1203 //+----------------------------------------------------------------------------
1204 bool CKodakDC210::GetIdString(char *szId)
1206 memcpy(szId, &(_bRawStatusData[90]), 32);
1212 //+----------------------------------------------------------------------------
1214 // Function: GetTimeValue
1218 // Arguments: int *piClock
1222 // History: sgasch Created Header 13 Jan 2000
1224 //+----------------------------------------------------------------------------
1225 bool CKodakDC210::GetTimeValue(int *piClock)
1227 if (RefreshProperties())
1229 *piClock = _bRawStatusData[15] |
1230 (_bRawStatusData[14] << 8) |
1231 (_bRawStatusData[13] << 16) |
1232 (_bRawStatusData[12] << 24);
1239 //+----------------------------------------------------------------------------
1241 // Function: GetTimeString
1245 // Arguments: char *pszTime
1249 // History: sgasch Created Header 13 Jan 2000
1251 //+----------------------------------------------------------------------------
1252 bool CKodakDC210::GetTimeString(char *pszTime)
1254 static char buf[128];
1259 memset(buf, 0, 128);
1260 GetTimeValue(&iCameraTime);
1261 iTime = 852094800 + (iCameraTime / 2);
1262 iSize = strftime(buf, 127, "%v %r", localtime( (time_t *) &iTime));
1263 strcpy(pszTime, buf);
1269 //+----------------------------------------------------------------------------
1271 // Function: GetTimeMinutes
1275 // Arguments: int *piMin
1279 // History: sgasch Created Header 13 Jan 2000
1281 //+----------------------------------------------------------------------------
1282 bool CKodakDC210::GetTimeMinutes(int *piMin)
1288 (void) GetTimeValue(&iCameraTime);
1289 iTime = 852094800 + (iCameraTime / 2);
1290 pTime = localtime( (time_t *) &iTime);
1291 *piMin = pTime->tm_min;
1296 //+----------------------------------------------------------------------------
1298 // Function: GetTimeHours
1302 // Arguments: int *piHrs
1306 // History: sgasch Created Header 13 Jan 2000
1308 //+----------------------------------------------------------------------------
1309 bool CKodakDC210::GetTimeHours(int *piHrs)
1315 (void) GetTimeValue(&iCameraTime);
1316 iTime = 852094800 + (iCameraTime / 2);
1317 pTime = localtime( (time_t *) &iTime);
1318 *piHrs = pTime->tm_hour;
1323 //+----------------------------------------------------------------------------
1325 // Function: GetTimeSeconds
1329 // Arguments: int *piSec
1333 // History: sgasch Created Header 13 Jan 2000
1335 //+----------------------------------------------------------------------------
1336 bool CKodakDC210::GetTimeSeconds(int *piSec)
1342 (void) GetTimeValue(&iCameraTime);
1343 iTime = 852094800 + (iCameraTime / 2);
1344 pTime = localtime( (time_t *) &iTime);
1345 *piSec = pTime->tm_sec;
1350 //+----------------------------------------------------------------------------
1352 // Function: GetTimeMonth
1356 // Arguments: int *piMon
1360 // History: sgasch Created Header 13 Jan 2000
1362 //+----------------------------------------------------------------------------
1363 bool CKodakDC210::GetTimeMonth(int *piMon)
1369 (void) GetTimeValue(&iCameraTime);
1370 iTime = 852094800 + (iCameraTime / 2);
1371 pTime = localtime( (time_t *) &iTime);
1372 *piMon = pTime->tm_mon + 1;
1377 //+----------------------------------------------------------------------------
1379 // Function: GetTimeDay
1383 // Arguments: int *piDay
1387 // History: sgasch Created Header 13 Jan 2000
1389 //+----------------------------------------------------------------------------
1390 bool CKodakDC210::GetTimeDay(int *piDay)
1396 (void) GetTimeValue(&iCameraTime);
1397 iTime = 852094800 + (iCameraTime / 2);
1398 pTime = localtime( (time_t *) &iTime);
1399 *piDay = pTime->tm_mday;
1404 //+----------------------------------------------------------------------------
1406 // Function: GetTimeYear
1410 // Arguments: int *piYear
1414 // History: sgasch Created Header 13 Jan 2000
1416 //+----------------------------------------------------------------------------
1417 bool CKodakDC210::GetTimeYear(int *piYear)
1423 (void) GetTimeValue(&iCameraTime);
1424 iTime = 852094800 + (iCameraTime / 2);
1425 pTime = localtime( (time_t *) &iTime);
1426 *piYear = pTime->tm_year + 1900;
1431 //+----------------------------------------------------------------------------
1433 // Function: SetFlashState
1437 // Arguments: bool fState
1441 // History: sgasch Created Header 15 Jan 2000
1443 //+----------------------------------------------------------------------------
1444 bool CKodakDC210::SetFlashState(bool fState)
1446 DC210_FLASH_STATE eState;
1450 // Precondition: we are initialized.
1452 ASSERT(_fInitialized);
1455 // Call the other SetFlashState routine.
1457 (fState) ? eState = flash_fill : eState = flash_off;
1458 return(SetFlashState(eState));
1462 //+----------------------------------------------------------------------------
1464 // Function: SetFlashState
1468 // Arguments: DC210_FLASH_STATE eState
1472 // History: sgasch Created Header 15 Jan 2000
1474 //+----------------------------------------------------------------------------
1475 bool CKodakDC210::SetFlashState(DC210_FLASH_STATE eState)
1478 // Pre: we are initialized.
1480 ASSERT(_fInitialized);
1485 if (!SendCommand(DC210_SET_FLASH, (BYTE) eState, 0, 0, 0))
1487 Trace("SetFlashState: unable to send command.\n");
1495 if (!CommandComplete())
1497 Trace("SetFlashState: did not receive command complete "
1504 // Refresh status block
1506 if (!RefreshProperties())
1508 Trace("SetFlashState: Failed to refresh status.\n");
1520 bool CKodakDC210::EraseAllPictures(void)
1523 // Precondition: we are initialized
1525 ASSERT(_fInitialized);
1530 if (!SendCommand(DC210_ERASE, 0xFF, 0xFF, 0, 0))
1532 Trace("EraseAllPictures: Failed to send command.\n");
1538 // Wait for completion
1540 if (!CommandComplete())
1542 Trace("EraseAllPictures: Failed to get command complete signal.\n");
1548 // All pictures were supposedly deleted, let's refresh camera status...
1550 if (!RefreshProperties())
1552 Trace("EraseAllPictures: Failed to refresh status.\n");
1563 bool CKodakDC210::SetResolution(int iWidth, int iHeight)
1565 BYTE bResolutionCode; // code we need to send to the camera
1568 // Preconditions: we are initialized and the resolution is supported
1570 ASSERT(_fInitialized);
1573 // DC210's support two resolutions, 640x480 and 1152x864.
1575 if ((iHeight == 480) && (iWidth == 640))
1577 bResolutionCode = 0;
1579 else if ((iHeight == 864) && (iWidth == 1152))
1581 bResolutionCode = 1;
1585 Trace("SetResolution: Unsupported resolution. Supported "
1586 "settings are 640x480 and 1152x864.\n");
1593 if (!SendCommand(DC210_SET_RESOLUTION, bResolutionCode, 0, 0, 0))
1595 Trace("SetResolution: Error sending command, aborting.\n");
1601 // Await the command complete signal
1603 if (!CommandComplete())
1605 Trace("SetResolution: Did not receive command completion "
1606 "signal, aborting.\n");
1612 // Refresh status block
1614 if (!RefreshProperties())
1616 Trace("SetResolution: Failed to refresh status.\n");
1628 //+----------------------------------------------------------------------------
1632 // Synopsis: This command resets the camera to the system default settings:
1634 // (1) Flash mode is auto
1635 // (2) No red-eye reduction flashes
1636 // (3) Wide angle zoom position
1638 // (5) Exposure compensation zero
1639 // (6) Compression low (lowest)
1640 // (7) Resolution high (1152x864)
1641 // (8) Video out mode NTSC
1642 // (9) Date/Time reset to 1/1/1997 0:00
1643 // (10) Quickview on
1645 // (12) Baud rate 9600
1649 // Returns: bool - true if successful
1651 // History: sgasch Created Header 8 Jun 1999
1653 //+----------------------------------------------------------------------------
1654 bool CKodakDC210::Reset(void)
1657 // Precondition: we are initialized
1659 ASSERT(_fInitialized);
1664 if (!SendCommand(DC210_RESET, 0, 0, 0, 0))
1666 Trace("Reset: unable to send command.\n");
1672 // Since they will change the serial baud rate to 9600, we will match.
1674 if (!_pSerialPort->SetBaudrate(9600))
1676 Trace("Reset: Cannot set serial port baud rate to 9600.\n");
1682 // Wait for completion.
1684 if (!CommandComplete())
1686 Trace("Reset: command complete signal not received.\n");
1692 // Refresh status block
1694 if (!RefreshProperties())
1696 Trace("Reset: Failed to refresh status.\n");
1708 //+----------------------------------------------------------------------------
1710 // Function: SetCompressionState
1714 // Arguments: DC210_COMPRESSION_STATE eCompression
1718 // History: sgasch Created Header 15 Jan 2000
1720 //+----------------------------------------------------------------------------
1721 bool CKodakDC210::SetCompressionState(DC210_COMPRESSION_STATE eCompression)
1726 // Precondition: we are initialized.
1728 ASSERT(_fInitialized);
1730 switch (eCompression)
1732 case compression_low:
1735 case compression_medium:
1738 case compression_high:
1742 Trace("SetCompressionState: bad parameter.\n");
1747 // Send the command to the camera.
1749 if (!SendCommand(DC210_SET_COMPRESSION, bCode, 0, 0, 0))
1751 Trace("SetCompressionState: Failed to send command.\n");
1757 // Wait for the camera's command complete code.
1759 if (!CommandComplete())
1761 Trace("SetCompressionState: Did not receive command completion "
1774 //+----------------------------------------------------------------------------
1776 // Function: SetZoomState
1780 // Arguments: DC210_ZOOM_STATE eZoom
1784 // History: sgasch Created Header 15 Jan 2000
1786 //+----------------------------------------------------------------------------
1787 bool CKodakDC210::SetZoomState(DC210_ZOOM_STATE eZoom)
1792 // Pre: we are initialized.
1794 ASSERT(_fInitialized);
1798 case zoom_fully_zoomed:
1810 case zoom_wideangle:
1817 Trace("SetZoomState: invalid parameter.\n");
1822 // Send the command to the camera.
1824 if (!SendCommand(DC210_SET_ZOOM, bCode, 0, 0, 0))
1826 Trace("SetZoomState: Failed to send command.\n");
1832 // Wait for the camera's command complete code.
1834 if (!CommandComplete())
1836 Trace("SetZoomState: Did not receive command completion signal.\n");
1847 //+----------------------------------------------------------------------------
1849 // Function: ToggleShutterDelay
1853 // Arguments: BOOL fEnable
1857 // History: sgasch Created Header 15 Jan 2000
1859 //+----------------------------------------------------------------------------
1860 bool CKodakDC210::ToggleShutterDelay(BOOL fEnable)
1862 BYTE bCode = fEnable;
1865 // Pre: we are initialized.
1867 ASSERT(_fInitialized);
1870 // Send the command to the camera.
1872 if (!SendCommand(DC210_SET_SHUTTER_DELAY, bCode, 0, 0, 0))
1874 Trace("ToggleShutterDelay: Failed to send command.\n");
1880 // Wait for the camera's command complete code.
1882 if (!CommandComplete())
1884 Trace("ToggleShutterDelay: Did not receive command completion "
1896 //+----------------------------------------------------------------------------
1898 // Function: SetPictureFormat
1902 // Arguments: DC210_FILE_FORMAT eFormat
1906 // History: sgasch Created Header 15 Jan 2000
1908 //+----------------------------------------------------------------------------
1909 bool CKodakDC210::SetPictureFormat(DC210_FILE_FORMAT eFormat)
1911 int iParam = eFormat + 2;
1916 if (!SendCommand(DC210_SET_FORMAT, iParam, 0, 0, 0))
1918 Trace("SetPictureFormat: unable to send command.\n");
1926 if (!CommandComplete())
1928 Trace("SetPictureFormat: did not receive command complete signal.\n");
1934 // Refresh status block
1936 if (!RefreshProperties())
1938 Trace("SetPictureFormat: Failed to refresh status.\n");
1950 bool CKodakDC210::SetExposureCompensationValue(float floatValue)
1955 bool CKodakDC210::FormatMemoryCard(void)
1960 bool CKodakDC210::SetIdString(char *szId)
1971 //-----------------------------------------------------------------------------
1972 //-----------------------------------------------------------------------------
1973 //-----------------------------------------------------------------------------
1974 //-----------------------------------------------------------------------------
1975 //-----------------------------------------------------------------------------
1976 //-----------------------------------------------------------------------------
1977 //-----------------------------------------------------------------------------
1978 //-----------------------------------------------------------------------------
1979 //-----------------------------------------------------------------------------
1985 //+----------------------------------------------------------------------------
1987 // Function: SendCommand
1989 // Synopsis: Send a command sequence to the camera.
1991 // Arguments: char bCommand
1993 // Returns: bool - true if command sent okay.
1995 // History: sgasch Created Header 4 Jun 1999
1997 //+----------------------------------------------------------------------------
1998 bool CKodakDC210::SendCommand(int bCommand, BYTE arg1, BYTE arg2, BYTE arg3,
2001 BYTE buf[8]; // buffer for building cmd to camera
2004 // Preconditions: the command is valid, we do _not_ assert that we
2005 // are initialized 'cause this can be called in the constructor before
2006 // we are fully initialized...
2008 ASSERT(bCommand <= 0xFF);
2009 ASSERT(bCommand >= 0);
2012 // Fill in the buffer with the command to the camera.
2024 // Send the command to the port.
2026 if (!_pSerialPort->Write(buf, 8))
2028 Trace("SendCommand: write error?!?\n");
2034 // The camera should acknowledge us, if it got the command...
2038 Trace("SendCommand: ACK not received from camera.\n"
2039 "SendCommand: %x is an illegal command.\n", bCommand);
2050 //+----------------------------------------------------------------------------
2054 // Synopsis: Read a command byte from the port and see if it's an ACK.
2058 // Returns: bool - true if successful ACK received, false otherwise
2060 // History: sgasch Created Header 4 Jun 1999
2062 //+----------------------------------------------------------------------------
2063 bool CKodakDC210::GetAck(void)
2065 BYTE buf; // buffer for byte from camera
2068 // The next byte back from the camera is an ACK or a NAK
2070 if (!_pSerialPort->Read(&buf, 1))
2072 Trace("GetAck: Read error.\n");
2077 if (DC210_COMMAND_ACK != buf)
2079 printf("GetAck: Received %x, not ACK.\n", buf);
2090 //+----------------------------------------------------------------------------
2092 // Function: CommandComplete
2094 // Synopsis: Once we have sent a command string off to the camera and
2095 // it has replied with an ACK we have to wait until the camera
2096 // tells us that it's done doing the command. The host interface
2097 // spec says that if it is bust for more than two seconds it will
2098 // send BUSY signals so we know it's still there but working.
2102 // Returns: bool - true if successful
2104 // History: sgasch Created Header 8 Jun 1999
2106 //+----------------------------------------------------------------------------
2107 bool CKodakDC210::CommandComplete(void)
2109 BYTE bStatus; // a byte from the camera
2112 // Get data from the camera and keep doing so while it's "busy"...
2116 _pSerialPort->Read(&bStatus, 1);
2118 while(bStatus == DC210_BUSY);
2121 // If it didn't say "complete" then there was an error with the command.
2123 if (DC210_COMMAND_COMPLETE != bStatus)
2125 Trace("CommandComplete: Camera reports error code %x.\n", bStatus);
2136 //+----------------------------------------------------------------------------
2138 // Function: ReadPacket
2142 // Arguments: BYTE *buf,
2147 // History: sgasch Created Header 13 Jan 2000
2149 //+----------------------------------------------------------------------------
2150 bool CKodakDC210::ReadPacket(BYTE *buf, int iPacketSize)
2152 BYTE bControl; // packet control byte from camera
2153 BYTE bChecksumFromCamera; // checksum from camera
2154 BYTE bChecksumComputed = 0; // checksum we compute from data
2155 int iAttempts = 0; // loop termination guarantor
2158 // Preconditions: we are initialized, the packet size is good, and the
2161 ASSERT(GOOD_PTR(buf));
2162 if ((iPacketSize != 1024) &&
2163 (iPacketSize != 512) &&
2164 (iPacketSize != 256) &&
2165 (iPacketSize != 16))
2167 Trace("ReadPacket: Invalid packet size.\n");
2170 ASSERT(_pSerialPort);
2173 // Loop reading packets until we get one with a checksum match.
2178 // Read the control byte first.
2180 if (!_pSerialPort->Read(&bControl, 1))
2182 Trace("ReadPacket: Read error?\n");
2188 // This byte must always be 0x01, according to the host
2191 if (bControl != DC210_NORMAL_RECEIVE_PACKET)
2193 Trace("ReadPacket: Illegal packet control byte from "
2194 "camera? (%x).\n", bControl);
2199 // Read the packet data itself.
2201 if (!_pSerialPort->Read(buf, iPacketSize))
2203 Trace("ReadPacket: Read error?\n");
2209 // Read the checksum the camera computed.
2211 if (!_pSerialPort->Read(&bChecksumFromCamera, 1))
2213 Trace("ReadPacket: Error reading checksum from camera.\n");
2219 // Compute the checksum based on the data and compare it to the
2220 // one the camera send... does it match?
2222 ComputeChecksum(&bChecksumComputed, buf, iPacketSize);
2223 if (bChecksumComputed == bChecksumFromCamera)
2226 // Yes, it matched -- send "good packet" to the camera.
2228 if (!_pSerialPort->WriteByte(DC210_CORRECT_PACKET))
2230 Trace("ReadPacket: Could not confirm packet reciept to the "
2239 // No match, garbled packet, request a resend.
2241 if (!_pSerialPort->WriteByte(DC210_ILLEGAL_PACKET))
2243 Trace("ReadPacket: Could not ask camera for resend.\n");
2250 // Continue to loop while the packet is bad and we have not yet
2251 // reached the upper limit to how many attempts to make.
2253 while ((bChecksumComputed != bChecksumFromCamera) &&
2254 (++iAttempts < g_iMaxAttempts));
2257 // If we're here because of too many bad packets, tell the camera to
2260 if (iAttempts >= _iMaxAttempts)
2262 Trace("ReadPacket: Too many illegal packets received, giving up.\n");
2263 if (!_pSerialPort->WriteByte(DC210_ABORT))
2265 Trace("ReadPacket: Could not abort the communication.\n");
2278 //+----------------------------------------------------------------------------
2280 // Function: SendPacket
2282 // Synopsis: Send a packet of data to the camera given the packet size,
2283 // a control byte, and the data itself.
2285 // Arguments: BYTE bControl - the control byte
2286 // BYTE *buf - the data
2287 // int iLength - how large is the packet
2289 // Returns: bool - true on success
2291 // History: sgasch Created Header 8 Jun 1999
2293 //+----------------------------------------------------------------------------
2294 bool CKodakDC210::SendPacket(BYTE bControl, BYTE *buf, int iLength)
2296 int iAttempts = 0; // loop termination guarantor
2297 BYTE bConfirm; // confirmation byte from camera
2298 BYTE bChecksum; // checksum we compute for packet
2301 // Preconditions: we are initialized, the control byte is valid, the
2302 // buf ptr is good, and the length is good.
2304 ASSERT(GOOD_PTR(buf));
2305 if ((iLength != 58) && (iLength != 255))
2307 Trace("SendPacket: Invalid packet length, aborting.\n");
2310 if ((bControl != DC210_NORMAL_PACKET) &&
2311 (bControl != DC210_FINAL_PACKET) &&
2312 (bControl != DC210_ABORT_PACKET))
2314 Trace("SendPacket: Invalid control byte, aborting.\n");
2317 ASSERT(_fInitialized);
2318 ASSERT(_pSerialPort);
2321 // Loop while the camera didn't get the packet.
2326 // Write the control byte first... this tells the camera if this
2327 // is just another packet or the last one.
2329 if (!_pSerialPort->WriteByte(bControl))
2331 Trace("SendPacket: Error writing control byte, aborting.\n");
2337 // Write the packet data.
2339 if (!_pSerialPort->Write(buf, iLength))
2341 Trace("SendPacket: Write error sending packet, aborting.\n");
2347 // Compute and send the checksum.
2349 (void) ComputeChecksum(&bChecksum, buf, iLength);
2350 if (!_pSerialPort->WriteByte(bChecksum))
2352 Trace("SendPacket: Error writing checksum byte, aborting.\n");
2358 // Receive acknowledgement or error from camera... this tells us
2359 // whether or not we have to resend the packet.
2361 if (!_pSerialPort->Read(&bConfirm, 1))
2363 Trace("SendPacket: Did not receive an ack from camera?!?\n");
2370 // Continue to loop while the camera wants a resend (due to garbled data
2371 // causing mismatched checksums) or until we reach the limit of packet
2374 while ((bConfirm != DC210_CORRECT_PACKET) &&
2375 (++iAttempts < _iMaxAttempts));
2378 // If we're here because of many packet failures, tell the camera we
2379 // are aborting the transfer.
2381 if (iAttempts >= g_iMaxAttempts)
2383 Trace("SendPacket: Too many packet errors, aborting "
2384 "communications.\n");
2385 if (!(_pSerialPort->WriteByte(DC210_ABORT_PACKET)))
2387 Trace("WritePacket: Could not abort the communication.\n");
2399 //+----------------------------------------------------------------------------
2401 // Function: ComputeChecksum
2403 // Synopsis: Compute and return the checksum byte of a packet. This method
2404 // is called by ReadPacket to verify the camera's packet integrity
2405 // and by SendPacket to send a checksum for the camera to verify.
2407 // Arguments: BYTE *pbChecksum - checksum computed
2408 // BYTE *buf - data ptr
2409 // int iSize - data length
2411 // Returns: bool - true if successful
2413 // History: sgasch Created Header 8 Jun 1999
2415 //+----------------------------------------------------------------------------
2416 bool CKodakDC210::ComputeChecksum(BYTE *pbChecksum, BYTE *buf, int iSize)
2418 BYTE bChecksum = *buf; // checksum begin as start byte
2419 int iCount = 1; // loop control
2422 // Preconditions: byte ptr must be good, checksum ptr must be good,
2423 // size must be good.
2425 ASSERT(GOOD_PTR(pbChecksum));
2426 ASSERT(GOOD_PTR(buf));
2427 if ((iSize <= 0) || (iSize > 10000))
2429 Trace("ComputeChecksum: illegal packet size.\n");
2435 // Compute the checksum by serially XORing the data bytes together.
2437 for (iCount = 1; iCount < iSize; iCount++)
2439 bChecksum ^= *(buf + iCount);
2441 *pbChecksum = bChecksum;