OMRON BCD format

Hello.

I'm comunicating with OMRON using FINS.
In ledder (Omron) I use BCD values for variables (older project).
How can I convert / get the right BCD value?
Thanks.

BR, Andrej.

Hi Andrej, what node are you using to conduct FINS communication with OMRON PLC?

Heh - i wrote that :slight_smile:

So, yes, BCD is a pain (I rarely use BCD anymore since moving away from C series - almost everything is CJ or N series now)

I have a private repo I use but its not ready for publishing to NPM.

It takes the plain 16bit data returned from PLC and converts it to WD, String, Bits, BCD etc. (quite useful)

If I get some time I'll sort it out later.

For a test, try this in a function node attached to the output of the read node...

Note - untested

/*
 * number2bcd -> takes a number and returns the corresponding BCD in a nodejs buffer object.
 * input: 32 bit positive number, nodejs buffer size
 * output: nodejs buffer 
 */
var number2bcd = function(number, size) {
    var s = size || 4; //default value: 4
    var bcd = new Buffer(s);
    bcd.fill(0);
    while(number !== 0 && s !== 0) {
        s-=1;
        bcd[s] = (number % 10);
        number = (number / 10)|0;
        bcd[s] += (number % 10) << 4;
        number = (number / 10)|0;
    }
    return bcd;
}

msg.bcd = []
msg.bcd[0] = number2bcd(msg.payload[0]
//Do more or loop payload)

Then attach a debug node (show complete object) and inspect msg.bcd

First integer is 8328bcd it should shown 2088dec
Second -26215 it should be 9999dec.
The second number should be unsigned integer. (39321) but if I change setting in READ node to unsigned I've got error:

[Type not printable]Uint16Array { '0': 8336, '1': 39321, '2': 0, '3': 0, '4': 0, '5': 0, '6': 0, '7': 0, '8': 2, '9': 4369}

So that formula was for the other direction.

I guess this is what you want...
image

code...

var bcd2number = function(num) {
    let loByte = (num & 0x00ff);
    let hiByte = (num >> 8) & 0x00ff;
    let n = 0;
    n += (loByte & 0x0F) * 1;
    n += ((loByte>>4) & 0x0F) * 10;
    n += (hiByte & 0x0F) * 100;
    n += ((hiByte>>4) & 0x0F) * 1000;
    return n;
}

//all of them at once to BCD
msg.bcd = msg.payload.map(bcd2number); 

/* 
//individual cherry picking
msg.motorRuntimeBCD = bcd2number(msg.payload[0])
msg.motorSpeedDEC = msg.payload[1] 
msg.luxLevelBCD = bcd2number(msg.payload[2])
*/

return msg;

Here is a working demo (press the play button to see it in action)...

Thanks.

It works perfectly.
Thanks.