This entry contain two parts:

- some small modifications to the code
- improved functionality and a link to the modif.

Get more info and SW here here

The small modif is about the values returned by GetPanTiltValue: it returns a data_two_int struct, and in your code, the first value contains -1 or -2 when there is a problem. The example in your postscript doc consider that there is a problem whenever the first value (pan) is negative. But negative angles, between -100 and -1 are correct values, they shoudn't be rejected.

Actually we shouldn't return a struct this way. Like gettimeofday(), etc..., we should return an int which indicates success or failure, and take as argument a pointer to a struct in which we write the result.

To keep interoperability with existing code I didn't change the return type, even if I think it would be better (or create another function that does the same thing but returns an int).

Now the example program ptz.c reads correctly the values, even for negative angles.

I've added a #define PANTILT_ERROR_VALUE 0x7FFF in EVI-D31.h

Here is the modified function. The mail continues after it.

/* * * Get pan and tilt values * */ data_two_int GetPanTiltValue(int aFd) {
/* we shouldn't return a struct this way. Like gettimeofday(), etc..., we should return an int which indicates success or failure, and take as argument a pointer to a struct in which we write the result */
visca_command sndCommand,revCommand;
data_two_int result;
/* int nr_of_tries=0; */
int pan,tilt,tilt_sign=1,pan_sign=1;
float pan_factor,tilt_factor;

/* Camera and command id */

sndCommand.pos[0]=0x81; sndCommand.pos[1]=0x09;
sndCommand.pos[2]=0x06; sndCommand.pos[3]=0x12;
sndCommand.pos[4]=0xff; /* Stop byte */
sndCommand.length=5;

/* Send request */

if(SendToCam(aFd,&sndCommand) < 0) {
result.z1 = PANTILT_ERROR_VALUE; /* Error message */
return result;
}

/* Read the pan/tilt values */
if((WaitFor(aFd, RETRIES, &revCommand) < 0) || (revCommand.length != 11)) { printf("\nCouldn't read the pan/tilt values of the camera\n");
result.z1 = PANTILT_ERROR_VALUE; /* Error message */
return result;
}

/* Convert from a Hex number to the pan angle */

if(revCommand.pos[2] > 0) { /* A negativ pan angle */
revCommand.pos[3] = 15 - revCommand.pos[3];
revCommand.pos[4] = 15 - revCommand.pos[4];
revCommand.pos[5] = 15 - revCommand.pos[5] + 1;
pan_sign = -1;
pan_factor = STEPSPERPANDEGLEFT;
}
else pan_factor = STEPSPERPANDEGRIGHT;

pan = pan_sign * ((int)(256*revCommand.pos[3]+
16*revCommand.pos[4]+
1 + revCommand.pos[5])/pan_factor);

/* Convert from a Hex number to the tilt angle */

if(revCommand.pos[6] > 0) { /* A negativ tilt angle */
revCommand.pos[7] = 15 - revCommand.pos[7];
revCommand.pos[8] = 15 - revCommand.pos[8];
revCommand.pos[9] = 15 - revCommand.pos[9] + 1;
tilt_sign = -1;
tilt_factor = STEPSPERTILTDEGDOWN;
}
else tilt_factor = STEPSPERTILTDEGUP;

tilt = tilt_sign * ((int)(256*revCommand.pos[7]+
16*revCommand.pos[8]+
1+ revCommand.pos[9])/tilt_factor);
result.z1 = pan;
result.z2 = tilt;
return result;
}

###################################################################

Now the big modifications.

The fact that I could not query the camera while it was moving was a problem for my purpose. So I did substantial modification of the reply reception code. I added the possibility that queries to the camera return immediatly, instead of waiting until the motion is finished. This allows to query the camera position and give other orders while it is moving, including cancelling the motion. This feature was allowed by the VISCA protocol but had to be dealt with by the driver. This was the reason that made this work necessary.

For this purpose, I set up a packet expectation mechanism, so that the driver knows when the camera says the motion is over.

To get this running, I did other modifications to the code, for comfort and aid in debugging.

I kept using my Makefile with automatic dependencies. Just extract the archive and do a make, it should work. (Unfortunately, it cannot deal with subdirectories, so it can't work with your original code layout. If you have modifications to offer that's great.) I also use standard header files.

I added debug facilities (depending on NDEBUG being defined) with selectable verbose levels.


Last modified: Thu May 31 11:26:20 2001