New Integrated Encoder module

So the good news is that my new IEM’s arrived today. I had hoped to write a post telling everyone how great they are with ROBOTC V3.05, however, they don’t work, code just throws an exception about an internal RAM sensor buffer. Oh well, now comes the fun of figuring out why with no documentation.

Perhaps the software does not support them yet, don’t see the point in releasing hardware if the software is not ready yet though.

Anyone else have them yet? Anyone else have them working?

1 Like

Mine come tomorrow, and I’ll be experimenting with them over the weekend…

  • Dean

There was a post on the robotc forums implying that support is not finished yet. I have to say that if that is the case I’m pretty annoyed that this was not made clear in the product launch thread. Anyway, I will bring my scope home tomorrow and perhaps another board that can talk I2C and see what I can find out.

1 Like

Guess I can post a picture of the guts :slight_smile:

1 Like

As of Jan 24, ROBOTC has not said that they work yet, so I don’t know if it’s fair to criticize them over it:
As for having no documentation, I’m sure that they’ll release the API soon.

I’m not really criticizing the ROBOTC folks, I knew that the PID control was not finished but there was an expectation that I could read the encoder value based on the fact that it has a new “I2C sensors” tab under motors and setup and that it allows me to write code such as;

#pragma config(UART_Usage, UART1, VEX_2x16_LCD, baudRate19200, IOPins, None, None)
#pragma config(I2C_Usage, I2C1, i2cSensors)
#pragma config(Sensor, I2C_1,  testA,  sensorQuadEncoderOnI2CPort,    , AutoAssign)
#pragma config(Motor,  port10, motorA, tmotorNormal, openLoop)
//*!!Code automatically generated by 'ROBOTC' configuration wizard               !!*//

task main()
    string str;

    bLCDBacklight = true;

      motor motorA ] = vexRT Ch1 ];

      sprintf(str,"%d", SensorValue testA ] );
      displayLCDString(0, 0, str);

… which implied that support was finished. It may also be my mistake and a misunderstanding on how to program them. However, I am concerned that many teams may be spending their $30 for a product which without software support is useless until that is available. If the software is/was not finished then the product should not have been released without a disclaimer to that effect. Anyway, until we have more facts this is very much a hypothetical discussion.

1 Like

I went digging around in the robot c files as the kids were rebuilding the lift last night to see what I could find (6 hours later it’s finally rebuilt and better than ever).

I think I see some new I2C functions and typedefs but I am not 100% sure if they are for Cortex or just NXT. It seems NXT has I2C support already. Never having touched an NXT I am not sure what theya re doing.

I assume the Cortex is going to be the master and the I2C sensors as slaves giving info back to the master upon request. So the master needs to ping out and address each sensor and ask for its information. Are we thinking the robot C low level stuff is going to do that for us or will we have to have a loop to do this activity of send/receive of the I2C sensor data? Looks like SensorValue[myI2csensor] is not going to do it. Darn.

The serial control functions might work but you have to know the structure of the data coming back and the address of the device. I assume the address is regulated by the name we give the sensor in the new I2C window.

I also found some structs in the headers for the I2C information. I don’t think it’s just a position you get with these new sensors. I think you should be able to get velocity and acceleration too. Is this to be exposed to the programmer or handled behind the scenes? They did say programming required so this may exactly what they mean. Now we have to teach about pointers now too. Yeah. :frowning:

I am at work now so no robot C in front of me. I’ll take a look tonight and make a test program too and try these structs with some of the functions I see in the function list file. Maybe I’ll get a little further, but no guarantees.

1 Like

My assumption that ROBOTC V3.05 has I2C support was wrong, I received information from my contacts within CMU today indicating that it is not finished but will be available soon.

Now if VEX would release the I2C message protocol at least I could interface the IME to another cpu.

1 Like

The spec is available here:

easyC and ROBOTC support is coming soon.

We could have held the product until easyC and ROBOTC were ready for launch, but we wanted to give our customers the ability to get these on order, this is especially important for users who can’t just “put it on a credit card” and are instead dealing with school purchasing departments.


1 Like


Thank you, this is a good thing you did and lets us help you.

If there were an “Amaze” award to be given back to VEX then you would be receiving one from me this week. :slight_smile:

1 Like

Can someone who has one of these please let us know how much thicker the new encoder is from the backing cap that comes with a 393 motor. That is, if I replaced the standard backing cap of a 393 motor with a new encoder, what is the net change in thickness (or depth depending on how you look at it) of the overall motor assembly?



The 393 motor gets approximately .3" taller.
The 269 motor gets approximately .28" taller.

Note, STEP files of the assembled motors w/ IMEs have been posted on the product pages:


FYI – the folks at easyC tell me they are anticipating a major new release next week with over 30 new functions (including the IMEs). They seem excited. :slight_smile:


that 0.3" taller gets you to 9/16" overall for the new 393 quad encoder lid. I measured my original 393 lid to be 9/32".

So it’s just over 1/2" for the new encoder lid.

Thanks very much,


So I hooked the new IME to another development board I had and wrote a simple test program to initialize the IME and then dump encoder data. It’s alive and works but notice a few issues to look into.

  1. Encoder data only seems to be 16 bit not 32 bit as the spec indicates
  2. Velocity data seems all over the place

Anyway, most likely my bugs, may be off on register access or something.

Here is a dump of the code output showing version, vendor, device id etc.


Init I2C bus...

Version:   56 31 2E 30 33 20 20 20 : V1.03   
Vendor:    56 45 58 20 20 20 20 20 : VEX     
Device ID: 49 4D 45 20 31 39 38 35 : IME 1985
Status:    03 01 02 01 : ....

Data:      00 11 00 00 03 1E : ......
counter 17 velocity 798

Data:      00 63 00 00 03 10 : .c....
counter 99 velocity 784

Data:      00 BF 00 00 02 94 : ......
counter 191 velocity 660

Data:      01 23 00 00 02 83 : .#....
counter 291 velocity 643

Data:      01 87 00 00 02 7F : ......
counter 391 velocity 639

Data:      01 ED 00 00 02 7B : .....{
counter 493 velocity 635

Ok, after a bit more digging it looks like the counter is 32bit but not with the byte order posted in the official spec, this is what I find wrt registers.

0x40 Rotation tics bits 15-08
0x41 Rotation tics bits 07-00
0x42 Rotation tics bits 31-24
0x43 Rotation tics bits 23-16

Top and bottom words are swapped, this is usually caused by big/little endian problems, could be two wrongs making a right in the VEX firmware, anyway, all other buffers I read are ok so assume this is how it is.

Velocity still make no sense, it keep also counting well after the motor stops.

I2C seems to work at both 100KHz and 400KHz.

1 Like

It turns out that the velocity data is more like 1/velocity, or more specifically the time (measured in some unknown units as yet) between pulses received in the encoder. For example, if the motor is running at full speed the encoder changes by 473 counts/sec on my 269 motor, the velocity data is 269. If the speed is halved to 240 counts/sec then the velocity is 550. As the speed is slowed then the velocity number increases until the motor stops, the velocity data then just keeps increasing until hitting the maximum of 65535. VEX probably has a timer running that is latched and reset each time the encoder count changes, not what I expected at all, I would have scaled into something more directly useful.

Otherwise the encoder is working mostly as advertised. If you have never used I2C before then the posted spec is probably not quite enough to explain how to interface to it, I had to make certain assumptions based on prior experience. The only mistake I found was the byte order of the “rotation ticks” 32 bit word.

There is a comment in the spec about the LED being red when writing to EEprom, I had hoped that the scratch pad data might be non volatile but, unless there is another command to write EEprom, that does not seem to be the case.

I’m done with this for now, I may do a write up at some point explaining in more detail how to use the I2C commands but, as there are only a handful of people on the forum who may ever do this, it’s not a high priority.

Now just have to wait for the next update to ROBOTC.

1 Like

Velocity is dx/dt; It looks like their dx is fixed, and they report changes in dt.
You’d rather have “instantaneous velocity” during the previous small fixed dt.
Nice work.

1 Like

Not sure what I would rather have, perhaps both.

It feels like the processor may be an STM8S103F3, a 20pin 8 bit micro, not 100% certain as the part number is not quite right. If that is the case then it has 640 bytes of true EEprom with a 300K cycle life, I would like access to that for parameter storage that we cannot do currently on the cortex. John, any thoughts? Is that the micro? Can we access the EEprom?

1 Like

I managed to get both the 269 and 393 IEMs working with the VEXpro last night. They came up fairly easily for me, and my observations match what jpearman has posted.

Thanks for decoding that! Hopefully John will be able to post the timer frequency; otherwise we’ll have to experimentally determine it in order to convert this to RPM in software.

Yep, though I suspect the intended audience of the spec wasn’t really people without prior I2C experience. I very much appreciate Vex posting it, and would encourage them to continue posting this type of information in the future. It allows students that want to understand the underlying technology to dig deeper, and it lets hobbyists like me use these in random and unexpected ways.

I can corroborate this finding. The bytes are delivered in a mixed-endian order. It is nice that they used 32b tick values, though, since that means you can run the motor at full speed for over 3 weeks without having to worry about overflow.

I hadn’t spotted that before, and there doesn’t seem to be any other mention of EEPROM. I assume that the encoders will always default to address 0x60, and that they will be relocated by the support libraries on each power cycle or general call reset. You wouldn’t want the terminator setting to come from the EEPROM, since the chain can be re-cabled during a power off, and that may result in a non-functional configuration.

Having the EEPROM store the scratchpad data might be interesting, since you could “name” each encoder for the motor it is attached to. If you check that in your code, you could easily verify that you’re talking to the correct encoder.

I’m going to try chaining 8 of them together (yes, I got 4 of each type since the spec says it allows for up to 8) and verify that it all works.


  • Dean
1 Like