00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #include <cams/control/visca.h>
00025
00026 #include <sys/ioctl.h>
00027 #include <stdio.h>
00028 #include <sys/time.h>
00029 #include <termios.h>
00030 #include <fcntl.h>
00031 #include <errno.h>
00032
00033 #include <utils/system/console_colors.h>
00034
00035 namespace firevision {
00036 #if 0
00037 }
00038 #endif
00039
00040
00041
00042
00043
00044
00045
00046
00047 ViscaControlException::ViscaControlException(const char *msg)
00048 : Exception(msg)
00049 {
00050 }
00051
00052
00053
00054
00055
00056
00057 ViscaControlException::ViscaControlException(const char *msg, const int _errno)
00058 : Exception(msg, _errno)
00059 {
00060 }
00061
00062
00063
00064
00065
00066
00067 ViscaControlInquiryRunningException::ViscaControlInquiryRunningException()
00068 : ViscaControlException("Inquiry already running")
00069 {
00070 }
00071
00072
00073 const unsigned int ViscaControl::VISCA_WHITEBLANCE_AUTO = VISCA_WB_AUTO;
00074
00075 const unsigned int ViscaControl::VISCA_WHITEBALANCE_INDOOR = VISCA_WB_INDOOR;
00076
00077 const unsigned int ViscaControl::VISCA_WHITEBALANCE_OUTDOOR = VISCA_WB_OUTDOOR;
00078
00079 const unsigned int ViscaControl::VISCA_WHITEBALANCE_ONE_PUSH = VISCA_WB_ONE_PUSH;
00080
00081 const unsigned int ViscaControl::VISCA_WHITEBALANCE_ATW = VISCA_WB_ATW;
00082
00083 const unsigned int ViscaControl::VISCA_WHITEBALANCE_MANUAL = VISCA_WB_MANUAL;
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094 ViscaControl::ViscaControl(bool blocking)
00095 {
00096 opened = false;
00097 inquire = VISCA_RUNINQ_NONE;
00098 this->blocking = blocking;
00099
00100 for (unsigned int i = 0; i < VISCA_NONBLOCKING_NUM; ++i) {
00101 nonblocking_sockets[i] = 0;
00102 nonblocking_running[i] = false;
00103 }
00104 }
00105
00106
00107
00108
00109
00110 void
00111 ViscaControl::open(const char *port) {
00112
00113 struct termios param;
00114
00115 dev = ::open(port, O_CREAT | O_RDWR | O_NONBLOCK);
00116 if (! dev) {
00117 throw ViscaControlException("Cannot open device", errno);
00118 }
00119
00120 if (tcgetattr(dev, ¶m) == -1) {
00121 ViscaControlException ve("Getting the port parameters failed", errno);
00122 ::close(dev);
00123 throw ve;
00124 }
00125
00126 cfsetospeed(¶m, B9600);
00127 cfsetispeed(¶m, B9600);
00128
00129 param.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);
00130 param.c_cflag |= CREAD;
00131 param.c_cflag |= CLOCAL;
00132
00133
00134 param.c_cc[VMIN] = 1;
00135 param.c_cc[VTIME] = 0;
00136
00137 param.c_iflag |= IGNBRK;
00138 param.c_iflag &= ~PARMRK;
00139 param.c_iflag &= ~ISTRIP;
00140 param.c_iflag &= ~INLCR;
00141 param.c_iflag &= ~IGNCR;
00142 param.c_iflag &= ~ICRNL;
00143 param.c_iflag &= ~IXON;
00144 param.c_iflag &= ~IXOFF;
00145
00146 param.c_lflag &= ~ECHO;
00147
00148
00149 param.c_lflag |= IEXTEN;
00150 param.c_oflag &= ~OPOST;
00151
00152 tcflow (dev, TCOON);
00153 tcflow (dev, TCION);
00154
00155
00156 param.c_cflag &= ~CS5 & ~CS6 & ~CS7 & ~CS8;
00157
00158 param.c_cflag |= CS8;
00159
00160
00161 param.c_cflag &=~(PARENB & PARODD);
00162
00163
00164 param.c_cflag &= ~CSTOPB;
00165
00166 if (tcsetattr(dev, TCSANOW, ¶m) != 0) {
00167 ViscaControlException ve("Setting the port parameters failed", errno);
00168 ::close(dev);
00169 throw ve;
00170 }
00171
00172 opened = true;
00173
00174 sender = VISCA_BUS_0;
00175 recipient = VISCA_BUS_1;
00176
00177 #ifdef TIMETRACKER_VISCA
00178 tracker = new TimeTracker();
00179 track_file.open("tracker_visca.txt");
00180 ttcls_pantilt_get_send = tracker->addClass("getPanTilt: send");
00181 ttcls_pantilt_get_read = tracker->addClass("getPanTilt: read");
00182 ttcls_pantilt_get_handle = tracker->addClass("getPanTilt: handling responses");
00183 ttcls_pantilt_get_interpret = tracker->addClass("getPanTilt: interpreting");
00184 #endif
00185
00186
00187 }
00188
00189
00190
00191 void
00192 ViscaControl::close()
00193 {
00194 if (opened) {
00195 opened = false;
00196 ::close(dev);
00197 }
00198 }
00199
00200
00201
00202
00203
00204 void
00205 ViscaControl::set_address(unsigned int num_cameras)
00206 {
00207 unsigned char recp_backup = recipient;
00208 recipient = VISCA_BUS_BROADCAST;
00209 obuffer[1] = 0x30;
00210 obuffer[2] = 0x01;
00211 obuffer_length = 2;
00212
00213 try {
00214 send();
00215 recv(0);
00216 } catch (ViscaControlException &e) {
00217 e.append("set_address(%u) failed", num_cameras);
00218 throw;
00219 }
00220
00221 recipient = recp_backup;
00222 }
00223
00224
00225
00226 void
00227 ViscaControl::clear()
00228 {
00229 if (!opened) throw ViscaControlException("Serial port not open");
00230
00231 obuffer[1] = 0x01;
00232 obuffer[2] = 0x00;
00233 obuffer[3] = 0x01;
00234 obuffer_length = 3;
00235
00236 try {
00237 send();
00238 recv(0);
00239 } catch (ViscaControlException &e) {
00240 e.append("clear() failed");
00241 throw;
00242 }
00243 }
00244
00245
00246
00247 void
00248 ViscaControl::send()
00249 {
00250 if (!opened) throw ViscaControlException("Serial port not open");
00251
00252
00253 obuffer[0] = 0x80;
00254 obuffer[0] |= (sender << 4);
00255 obuffer[0] |= recipient;
00256
00257 obuffer[++obuffer_length] = VISCA_TERMINATOR;
00258 ++obuffer_length;
00259
00260 int written = write(dev, obuffer, obuffer_length);
00261
00262
00263
00264
00265
00266 if (written < obuffer_length) {
00267 throw ViscaControlException("Not all bytes send");
00268 }
00269 }
00270
00271
00272
00273
00274
00275 bool
00276 ViscaControl::data_available()
00277 {
00278 int num_bytes = 0;
00279 ioctl(dev, FIONREAD, &num_bytes);
00280 return (num_bytes > 0);
00281 }
00282
00283
00284
00285
00286
00287 void
00288 ViscaControl::recv(unsigned int max_wait_ms)
00289 {
00290 try {
00291 recv_packet(max_wait_ms);
00292 } catch (ViscaControlException &e) {
00293 e.append("Receiving failed, recv_packet() call failed");
00294 throw;
00295 }
00296
00297
00298 unsigned char type = ibuffer[1] & 0xF0;
00299 while (type == VISCA_RESPONSE_ACK) {
00300 try {
00301 recv_packet(max_wait_ms);
00302 } catch (ViscaControlException &e) {
00303 e.append("Receiving failed, recv_packet() call 2 failed");
00304 throw;
00305 }
00306 type = ibuffer[1] & 0xF0;
00307 }
00308
00309 switch (type) {
00310 case VISCA_RESPONSE_CLEAR:
00311 case VISCA_RESPONSE_ADDRESS:
00312 case VISCA_RESPONSE_COMPLETED:
00313 case VISCA_RESPONSE_ERROR:
00314 break;
00315 default:
00316 throw ViscaControlException("Receiving failed, unexpected packet type received");
00317 }
00318 }
00319
00320
00321
00322
00323
00324 void
00325 ViscaControl::recv_ack(unsigned int *socket)
00326 {
00327 try {
00328 recv_packet(0);
00329 } catch (ViscaControlException &e) {
00330 throw ViscaControlException("recv_ack(): recv_packet() failed");
00331 }
00332
00333
00334 unsigned char type = ibuffer[1] & 0xF0;
00335 while (type != VISCA_RESPONSE_ACK) {
00336
00337 try {
00338 handle_response();
00339 recv_packet();
00340 } catch (ViscaControlException &e) {
00341 e.append("Handling message of type %u failed", type);
00342 throw;
00343 }
00344 type = ibuffer[1] & 0xF0;
00345 }
00346
00347
00348 if (socket != NULL) {
00349 *socket = ibuffer[1] & 0x0F;
00350 }
00351
00352 }
00353
00354
00355
00356
00357
00358
00359 void
00360 ViscaControl::send_nonblocking(unsigned int *socket)
00361 {
00362 try {
00363 send();
00364 recv_ack(socket);
00365 } catch (ViscaControlException &e) {
00366 e.append("Non-blocking send failed!");
00367 throw;
00368 }
00369 }
00370
00371
00372
00373
00374 void
00375 ViscaControl::send_with_reply()
00376 {
00377 try {
00378 send();
00379 recv();
00380 } catch (ViscaControlException &e) {
00381 e.append("Sending with reply failed");
00382 throw;
00383 }
00384 }
00385
00386
00387
00388
00389
00390 void
00391 ViscaControl::recv_packet(unsigned int max_wait_ms)
00392 {
00393
00394 timeval start, now;
00395 unsigned int diff_msec = 0;
00396 gettimeofday(&start, NULL);
00397
00398 int num_bytes = 0;
00399 ioctl(dev, FIONREAD, &num_bytes);
00400 while ( ((max_wait_ms == 0) || (diff_msec < max_wait_ms)) && (num_bytes == 0)) {
00401 usleep(max_wait_ms / 100);
00402 ioctl(dev, FIONREAD, &num_bytes);
00403
00404 gettimeofday(&now, NULL);
00405 diff_msec = (now.tv_sec - start.tv_sec) * 1000 + (now.tv_usec - start.tv_usec) / 1000;
00406 }
00407 if (num_bytes == 0) {
00408 throw ViscaControlException("recv_packet() failed: no bytes to read");
00409 }
00410
00411
00412 int bytes_read = read(dev, ibuffer, 1);
00413 int pos = 0;
00414 while (ibuffer[pos] != VISCA_TERMINATOR) {
00415 bytes_read = read(dev, &ibuffer[++pos], 1);
00416 usleep(0);
00417 }
00418 ibuffer_length = pos + 1;
00419
00420
00421
00422
00423
00424 }
00425
00426
00427
00428
00429
00430 void
00431 ViscaControl::finish_nonblocking( unsigned int socket )
00432 {
00433 for (unsigned int i = 0; i < VISCA_NONBLOCKING_NUM; ++i) {
00434 if (nonblocking_sockets[i] == socket) {
00435 nonblocking_sockets[i] = 0;
00436 nonblocking_running[i] = false;
00437 return;
00438 }
00439 }
00440
00441 throw ViscaControlException("finish_nonblocking() failed: socket not found");
00442 }
00443
00444
00445
00446 void
00447 ViscaControl::handle_response()
00448 {
00449 unsigned int type = ibuffer[1] & 0xF0;
00450 unsigned int socket = ibuffer[1] & 0x0F;
00451
00452 if (socket == 0) {
00453
00454 throw ViscaControlException("handle_response(): Received an inquire response, can't handle");
00455 }
00456
00457 if ( type == VISCA_RESPONSE_COMPLETED ) {
00458
00459 try {
00460 finish_nonblocking( ibuffer[1] & 0x0F );
00461 } catch (ViscaControlException &e) {
00462
00463
00464
00465 }
00466 } else if ( type == VISCA_RESPONSE_ERROR ) {
00467 finish_nonblocking( ibuffer[1] & 0x0F );
00468 throw ViscaControlException("handle_response(): got an error message from camera");
00469 } else {
00470 ViscaControlException ve("Got unknown/unhandled response type");
00471 ve.append("Received message of type %u", type);
00472 throw ve;
00473 }
00474
00475 }
00476
00477
00478
00479
00480
00481 void
00482 ViscaControl::cancel_command( unsigned int socket )
00483 {
00484 unsigned char cancel_socket = socket & 0x0000000F;
00485
00486 obuffer[1] = VISCA_CANCEL | cancel_socket;
00487 obuffer_length = 1;
00488
00489 try {
00490 send_with_reply();
00491 } catch (ViscaControlException &e) {
00492 e.append("cancel_command() failed");
00493 throw;
00494 }
00495
00496 if ( ((ibuffer[1] & 0xF0) == VISCA_RESPONSE_ERROR) &&
00497 ((ibuffer[1] & 0x0F) == cancel_socket) &&
00498 ((ibuffer[2] == VISCA_ERROR_CANCELLED)) ) {
00499 return;
00500 } else {
00501 throw ViscaControlException("Command could not be cancelled");
00502 }
00503 }
00504
00505
00506
00507 void
00508 ViscaControl::process()
00509 {
00510
00511 inquire = VISCA_RUNINQ_NONE;
00512
00513 while (data_available()) {
00514 try {
00515 recv();
00516 handle_response();
00517 } catch (ViscaControlException &e) {
00518
00519 return;
00520 }
00521 }
00522 }
00523
00524
00525
00526
00527
00528
00529 void
00530 ViscaControl::setPanTilt(int pan, int tilt)
00531 {
00532
00533
00534
00535
00536
00537
00538
00539
00540
00541
00542
00543
00544
00545
00546 unsigned short int tilt_val = 0 + tilt;
00547 unsigned short int pan_val = 0 + pan;
00548
00549 obuffer[1] = VISCA_COMMAND;
00550 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00551 obuffer[3] = VISCA_PT_ABSOLUTE_POSITION;
00552
00553 obuffer[4] = 0x18;
00554
00555 obuffer[5] = 0x14;
00556
00557
00558 obuffer[6] = (pan_val & 0xf000) >> 12;
00559 obuffer[7] = (pan_val & 0x0f00) >> 8;
00560 obuffer[8] = (pan_val & 0x00f0) >> 4;
00561 obuffer[9] = (pan_val & 0x000f);
00562
00563 obuffer[10] = (tilt_val & 0xf000) >> 12;
00564 obuffer[11] = (tilt_val & 0x0f00) >> 8;
00565 obuffer[12] = (tilt_val & 0x00f0) >> 4;
00566 obuffer[13] = (tilt_val & 0x000f);
00567
00568 obuffer_length = 13;
00569
00570 try {
00571 if (! blocking) {
00572 nonblocking_running[ VISCA_NONBLOCKING_PANTILT ] = true;
00573 send_nonblocking( &(nonblocking_sockets[ VISCA_NONBLOCKING_PANTILT ]) );
00574 } else {
00575 send_with_reply();
00576 }
00577 } catch (ViscaControlException &e) {
00578 e.append("setPanTilt() failed");
00579 throw;
00580 }
00581 }
00582
00583
00584
00585 void
00586 ViscaControl::startGetPanTilt()
00587 {
00588
00589 if ( inquire ) throw ViscaControlInquiryRunningException();
00590
00591 inquire = VISCA_RUNINQ_PANTILT;
00592
00593 obuffer[1] = VISCA_INQUIRY;
00594 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00595 obuffer[3] = VISCA_PT_POSITION_INQ;
00596 obuffer_length = 3;
00597
00598 try {
00599 send();
00600 } catch (ViscaControlException &e) {
00601 e.append("startGetPanTilt() failed");
00602 throw;
00603 }
00604 }
00605
00606
00607
00608
00609
00610
00611
00612
00613
00614 void
00615 ViscaControl::getPanTilt(int *pan, int *tilt)
00616 {
00617
00618 if ( inquire ) {
00619 if ( inquire != VISCA_RUNINQ_PANTILT ) {
00620 throw ViscaControlException("Inquiry running, but it is not a pan/tilt inquiry");
00621 } else {
00622 #ifdef TIMETRACKER_VISCA
00623 tracker->pingStart( ttcls_pantilt_get_read );
00624 #endif
00625 try {
00626 recv();
00627 } catch (ViscaControlException &e) {
00628
00629 }
00630 #ifdef TIMETRACKER_VISCA
00631 tracker->pingEnd( ttcls_pantilt_get_read );
00632 #endif
00633 }
00634 } else {
00635
00636 obuffer[1] = VISCA_INQUIRY;
00637 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00638 obuffer[3] = VISCA_PT_POSITION_INQ;
00639 obuffer_length = 3;
00640
00641 try {
00642 #ifdef TIMETRACKER_VISCA
00643 tracker->pingStart( ttcls_pantilt_get_send );
00644 send();
00645 tracker->pingEnd( ttcls_pantilt_get_send );
00646 tracker->pingStart( ttcls_pantilt_get_read );
00647 recv();
00648 tracker->pingEnd( ttcls_pantilt_get_read );
00649 #else
00650 send_with_reply();
00651 #endif
00652 } catch (ViscaControlException &e) {
00653
00654 }
00655 }
00656
00657 #ifdef TIMETRACKER_VISCA
00658 tracker->pingStart( ttcls_pantilt_get_handle );
00659 #endif
00660
00661 while (ibuffer[1] != VISCA_RESPONSE_COMPLETED) {
00662
00663
00664 try {
00665 handle_response();
00666 recv();
00667 } catch (ViscaControlException &e) {
00668
00669 }
00670 }
00671
00672 #ifdef TIMETRACKER_VISCA
00673 tracker->pingEnd( ttcls_pantilt_get_handle );
00674 tracker->pingStart( ttcls_pantilt_get_interpret );
00675 #endif
00676
00677
00678
00679 if ( ibuffer[1] == VISCA_RESPONSE_COMPLETED ) {
00680 unsigned short int pan_val = 0;
00681 unsigned short int tilt_val = 0;
00682
00683 pan_val |= (ibuffer[2] & 0x0F) << 12;
00684 pan_val |= (ibuffer[3] & 0x0F) << 8;
00685 pan_val |= (ibuffer[4] & 0x0F) << 4;
00686 pan_val |= (ibuffer[5] & 0x0F);
00687
00688 tilt_val |= (ibuffer[6] & 0x0F) << 12;
00689 tilt_val |= (ibuffer[7] & 0x0F) << 8;
00690 tilt_val |= (ibuffer[8] & 0x0F) << 4;
00691 tilt_val |= (ibuffer[9] & 0x0F);
00692
00693 if (pan_val < 0x8000) {
00694
00695 *pan = pan_val;
00696 } else {
00697
00698 *pan = pan_val - 0xFFFF;
00699 }
00700
00701 if (tilt_val < 0x8000) {
00702
00703 *tilt = tilt_val;
00704 } else {
00705
00706 *tilt = tilt_val - 0xFFFF;
00707 }
00708
00709 } else {
00710 throw ViscaControlException("getPanTilt(): Wrong response received");
00711 }
00712 #ifdef TIMETRACKER_VISCA
00713 tracker->pingEnd( ttcls_pantilt_get_interpret );
00714 tracker->printToStream( track_file );
00715 #endif
00716
00717 inquire = VISCA_RUNINQ_NONE;
00718 }
00719
00720
00721
00722 void
00723 ViscaControl::resetPanTiltLimit()
00724 {
00725 obuffer[1] = VISCA_COMMAND;
00726 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00727 obuffer[3] = VISCA_PT_LIMITSET;
00728 obuffer[3] = VISCA_PT_LIMITSET_CLEAR;
00729 obuffer[4] = VISCA_PT_LIMITSET_SET_UR;
00730 obuffer[5] = 0x07;
00731 obuffer[6] = 0x0F;
00732 obuffer[7] = 0x0F;
00733 obuffer[8] = 0x0F;
00734 obuffer[9] = 0x07;
00735 obuffer[10] = 0x0F;
00736 obuffer[11] = 0x0F;
00737 obuffer[12] = 0x0F;
00738 obuffer_length = 12;
00739
00740 try {
00741 send_with_reply();
00742
00743 obuffer[4] = VISCA_PT_LIMITSET_SET_DL;
00744
00745 send_with_reply();
00746 } catch (ViscaControlException &e) {
00747 e.append("resetPanTiltLimit() failed");
00748 throw;
00749 }
00750 }
00751
00752
00753
00754
00755
00756
00757
00758
00759 void
00760 ViscaControl::setPanTiltLimit(int pan_left, int pan_right, int tilt_up, int tilt_down)
00761 {
00762 try {
00763 obuffer[1] = VISCA_COMMAND;
00764 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00765 obuffer[3] = VISCA_PT_LIMITSET;
00766 obuffer[3] = VISCA_PT_LIMITSET_SET;
00767 obuffer[4] = VISCA_PT_LIMITSET_SET_UR;
00768
00769 obuffer[5] = (pan_right & 0xf000) >> 12;
00770 obuffer[6] = (pan_right & 0x0f00) >> 8;
00771 obuffer[7] = (pan_right & 0x00f0) >> 4;
00772 obuffer[8] = (pan_right & 0x000f);
00773
00774 obuffer[9] = (tilt_up & 0xf000) >> 12;
00775 obuffer[10] = (tilt_up & 0x0f00) >> 8;
00776 obuffer[11] = (tilt_up & 0x00f0) >> 4;
00777 obuffer[12] = (tilt_up & 0x000f);
00778
00779 obuffer_length = 12;
00780
00781 send_with_reply();
00782
00783 obuffer[4] = VISCA_PT_LIMITSET_SET_DL;
00784
00785 obuffer[5] = (pan_left & 0xf000) >> 12;
00786 obuffer[6] = (pan_left & 0x0f00) >> 8;
00787 obuffer[7] = (pan_left & 0x00f0) >> 4;
00788 obuffer[8] = (pan_left & 0x000f);
00789
00790 obuffer[9] = (tilt_down & 0xf000) >> 12;
00791 obuffer[10] = (tilt_down & 0x0f00) >> 8;
00792 obuffer[11] = (tilt_down & 0x00f0) >> 4;
00793 obuffer[12] = (tilt_down & 0x000f);
00794
00795 send_with_reply();
00796 } catch (ViscaControlException &e) {
00797 e.append("setPanTiltLimit() failed");
00798 throw;
00799 }
00800 }
00801
00802
00803
00804 void
00805 ViscaControl::resetPanTilt()
00806 {
00807 obuffer[1] = VISCA_COMMAND;
00808 obuffer[2] = VISCA_CATEGORY_PAN_TILTER;
00809 obuffer[3] = VISCA_PT_HOME;
00810 obuffer_length = 3;
00811
00812 try {
00813 send_with_reply();
00814 } catch (ViscaControlException &e) {
00815 e.append("resetPanTilt() failed");
00816 throw;
00817 }
00818 }
00819
00820
00821
00822 void
00823 ViscaControl::resetZoom()
00824 {
00825 obuffer[1] = VISCA_COMMAND;
00826 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00827 obuffer[3] = VISCA_ZOOM;
00828 obuffer[4] = VISCA_ZOOM_STOP;
00829 obuffer_length = 4;
00830
00831 try {
00832 send_with_reply();
00833 } catch (ViscaControlException &e) {
00834 e.append("resetZoom() failed");
00835 throw;
00836 }
00837 }
00838
00839
00840
00841
00842
00843 void
00844 ViscaControl::setZoomSpeedTele(unsigned int speed)
00845 {
00846 obuffer[1] = VISCA_COMMAND;
00847 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00848 obuffer[3] = VISCA_ZOOM;
00849 obuffer[4] = VISCA_ZOOM_TELE_SPEED;
00850
00851 obuffer[5] = (speed & 0x000f) | 0x0020;
00852 obuffer_length = 5;
00853
00854 try {
00855 send_with_reply();
00856 } catch (ViscaControlException &e) {
00857 e.append("setZoomSpeedTele() failed");
00858 throw;
00859 }
00860 }
00861
00862
00863
00864
00865
00866 void
00867 ViscaControl::setZoomSpeedWide(unsigned int speed)
00868 {
00869 obuffer[1] = VISCA_COMMAND;
00870 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00871 obuffer[3] = VISCA_ZOOM;
00872 obuffer[4] = VISCA_ZOOM_WIDE_SPEED;
00873
00874 obuffer[5] = (speed & 0x000f) | 0x0020;
00875 obuffer_length = 5;
00876
00877 try {
00878 send_with_reply();
00879 } catch (ViscaControlException &e) {
00880 e.append("setZoomSpeedWide() failed");
00881 throw;
00882 }
00883 }
00884
00885
00886
00887
00888
00889 void
00890 ViscaControl::setZoom(unsigned int zoom)
00891 {
00892 obuffer[1] = VISCA_COMMAND;
00893 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00894 obuffer[3] = VISCA_ZOOM_VALUE;
00895
00896 obuffer[4] = (zoom & 0xf000) >> 12;
00897 obuffer[5] = (zoom & 0x0f00) >> 8;
00898 obuffer[6] = (zoom & 0x00f0) >> 4;
00899 obuffer[7] = (zoom & 0x000f);
00900
00901 obuffer_length = 7;
00902
00903 try {
00904 send_with_reply();
00905 } catch (ViscaControlException &e) {
00906 e.append("setZoom() failed");
00907 throw;
00908 }
00909 }
00910
00911
00912
00913
00914
00915 void
00916 ViscaControl::getZoom(unsigned int *zoom)
00917 {
00918 obuffer[1] = VISCA_INQUIRY;
00919 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00920 obuffer[3] = VISCA_ZOOM_VALUE;
00921 obuffer_length = 3;
00922
00923 try {
00924 send_with_reply();
00925 } catch (ViscaControlException &e) {
00926 e.append("getZoom() failed");
00927 throw;
00928 }
00929
00930
00931 if ( ibuffer[1] == VISCA_RESPONSE_COMPLETED ) {
00932 unsigned short int zoom_val = 0;
00933
00934 zoom_val |= (ibuffer[2] & 0x0F) << 12;
00935 zoom_val |= (ibuffer[3] & 0x0F) << 8;
00936 zoom_val |= (ibuffer[4] & 0x0F) << 4;
00937 zoom_val |= (ibuffer[5] & 0x0F);
00938
00939 *zoom = zoom_val;
00940 } else {
00941 throw ViscaControlException("getZoom(): zoom inquiry failed, response code not VISCA_RESPONSE_COMPLETED");
00942 }
00943
00944 }
00945
00946
00947
00948
00949
00950 void
00951 ViscaControl::setZoomDigitalEnabled(bool enabled)
00952 {
00953 obuffer[1] = VISCA_COMMAND;
00954 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00955 obuffer[3] = VISCA_DZOOM;
00956 if (enabled) {
00957 obuffer[4] = VISCA_DZOOM_ON;
00958 } else {
00959 obuffer[4] = VISCA_DZOOM_OFF;
00960 }
00961 obuffer_length = 4;
00962
00963 try {
00964 send_with_reply();
00965 } catch (ViscaControlException &e) {
00966 e.append("setZoomDigitalEnabled() failed");
00967 throw;
00968 }
00969 }
00970
00971
00972
00973
00974
00975 void
00976 ViscaControl::applyEffect(unsigned char filter)
00977 {
00978 obuffer[1] = VISCA_COMMAND;
00979 obuffer[2] = VISCA_CATEGORY_CAMERA1;
00980 obuffer[3] = VISCA_PICTURE_EFFECT;
00981 obuffer[4] = filter;
00982 obuffer_length = 4;
00983
00984 try {
00985 send_with_reply();
00986 } catch (ViscaControlException &e) {
00987 e.append("applyEffect() failed");
00988 throw;
00989 }
00990 }
00991
00992
00993
00994 void
00995 ViscaControl::resetEffect()
00996 {
00997 try {
00998 applyEffect(VISCA_PICTURE_EFFECT_OFF);
00999 } catch (ViscaControlException &e) {
01000 e.append("resetEffect() failed");
01001 throw;
01002 }
01003 }
01004
01005
01006
01007 void
01008 ViscaControl::applyEffectPastel()
01009 {
01010 try {
01011 applyEffect(VISCA_PICTURE_EFFECT_PASTEL);
01012 } catch (ViscaControlException &e) {
01013 e.append("applyEffectPastel() failed");
01014 throw;
01015 }
01016 }
01017
01018
01019
01020 void
01021 ViscaControl::applyEffectNegArt()
01022 {
01023 try {
01024 applyEffect(VISCA_PICTURE_EFFECT_NEGATIVE);
01025 } catch (ViscaControlException &e) {
01026 e.append("applyEffectNegArt() failed");
01027 throw;
01028 }
01029 }
01030
01031
01032
01033 void
01034 ViscaControl::applyEffectSepia()
01035 {
01036 try {
01037 applyEffect(VISCA_PICTURE_EFFECT_SEPIA);
01038 } catch (ViscaControlException &e) {
01039 e.append("applyEffectSepia() failed");
01040 throw;
01041 }
01042 }
01043
01044
01045
01046 void
01047 ViscaControl::applyEffectBnW()
01048 {
01049 try {
01050 applyEffect(VISCA_PICTURE_EFFECT_BW);
01051 } catch (ViscaControlException &e) {
01052 e.append("applyEffectBnW() failed");
01053 throw;
01054 }
01055 }
01056
01057
01058
01059 void
01060 ViscaControl::applyEffectSolarize()
01061 {
01062 try {
01063 applyEffect(VISCA_PICTURE_EFFECT_SOLARIZE);
01064 } catch (ViscaControlException &e) {
01065 e.append("applyEffectSolarize() failed");
01066 throw;
01067 }
01068 }
01069
01070
01071
01072 void
01073 ViscaControl::applyEffectMosaic()
01074 {
01075 try {
01076 applyEffect(VISCA_PICTURE_EFFECT_MOSAIC);
01077 } catch (ViscaControlException &e) {
01078 e.append("applyEffectMosaic() failed");
01079 throw;
01080 }
01081 }
01082
01083
01084
01085 void
01086 ViscaControl::applyEffectSlim()
01087 {
01088 try {
01089 applyEffect(VISCA_PICTURE_EFFECT_SLIM);
01090 } catch (ViscaControlException &e) {
01091 e.append("applyEffectSlim() failed");
01092 throw;
01093 }
01094 }
01095
01096
01097
01098 void
01099 ViscaControl::applyEffectStretch()
01100 {
01101 try {
01102 applyEffect(VISCA_PICTURE_EFFECT_STRETCH);
01103 } catch (ViscaControlException &e) {
01104 e.append("applyEffectStretch() failed");
01105 throw;
01106 }
01107 }
01108
01109
01110
01111
01112
01113 unsigned int
01114 ViscaControl::getWhiteBalanceMode()
01115 {
01116 obuffer[1] = VISCA_INQUIRY;
01117 obuffer[2] = VISCA_CATEGORY_CAMERA1;
01118 obuffer[3] = VISCA_WB;
01119 obuffer_length = 3;
01120
01121 try {
01122 send_with_reply();
01123 } catch (ViscaControlException &e) {
01124 e.append("getWhiteBalanceMode() failed");
01125 throw;
01126 }
01127
01128 while (ibuffer[1] != VISCA_RESPONSE_COMPLETED) {
01129
01130
01131 try {
01132 handle_response();
01133 recv();
01134 } catch (ViscaControlException &e) {
01135 e.append("getWhiteBalanceMode() failed");
01136 throw;
01137 }
01138 }
01139
01140
01141 if ( ibuffer[1] == VISCA_RESPONSE_COMPLETED ) {
01142 return ibuffer[2];
01143 } else {
01144 throw ViscaControlException("Did not get 'request completed' response");
01145 }
01146
01147 }
01148
01149 }