How to create and call global functions?

Hello,

I probably didn’t yet fully get the philosophy of Homey… but I want to write a function XYtoRGB and don’t really find how to do this properly with Homey.

The function will to convert into an RGB string any input ‘Philips hue scene’ (represented by it’s x, y colors and brillance). Obviously, I don’t want to type its code in all my flows.

So far, I found that I could probably use an HomeyScript like this:

//args[0] = '{ "x":0.5019, "y":0.4152, "bri":143 }';

if (args[0] === '' || args[0] === undefined)  {
  throw new Error('This script needs a json as parameter: { "x":0.561, "y":0.4042, "bri":90 }');
}


const flow_args = JSON.parse(args[0]);
if (Object.keys( flow_args).length != 3) {
  throw new Error('This script has only ' + Object.keys( flow_args).length + ' parameters and needs 3. Ex.: { "x":0.561, "y":0.4042, "bri":90 } ');
}

console.log('x:' + flow_args.x );
console.log('y:' + flow_args.y );
console.log('bri:' + flow_args.bri );

const x = (typeof flow_args.x === 'number')
  ? flow_args.x
  : 0.561;
const y = (typeof flow_args.y === 'number')
  ? flow_args.y
  : 0.4042;
const bri = (typeof flow_args.bri === 'number')
  ? flow_args.bri
  : 90;

z = 1.0 - x - y;

Y = bri / 255.0; // Brightness of lamp
X = (Y / y) * x;
Z = (Y / y) * z;
r = X * 1.612 - Y * 0.203 - Z * 0.302;
g = -X * 0.509 + Y * 1.412 + Z * 0.066;
b = X * 0.026 - Y * 0.072 + Z * 0.962;
r = r <= 0.0031308 ? 12.92 * r : (1.0 + 0.055) * Math.pow(r, (1.0 / 2.4)) - 0.055;
g = g <= 0.0031308 ? 12.92 * g : (1.0 + 0.055) * Math.pow(g, (1.0 / 2.4)) - 0.055;
b = b <= 0.0031308 ? 12.92 * b : (1.0 + 0.055) * Math.pow(b, (1.0 / 2.4)) - 0.055;
maxValue = Math.max(r,g,b);
r /= maxValue;
g /= maxValue;
b /= maxValue;
r = r * 255;   if (r < 0) { r = 255 };
g = g * 255;   if (g < 0) { g = 255 };
b = b * 255;   if (b < 0) { b = 255 };

r = Math.round(r).toString(16);
g = Math.round(g).toString(16);
b = Math.round(b).toString(16);

if (r.length < 2)
    r="0"+r;        
if (g.length < 2)
    g="0"+g;        
if (b.length < 2)
    b="0"+r;        
rgb = "#"+r+g+b;

console.log(args[0] + ' = ' + rgb);
return rgb;

Unfortunately, I don’t see how to call it properly from a flow.
I tried with a HomeScript’s card "Run … with argument’

image

But first, I struggled to pass an array of parameters. I read on this forum that people recommend using splitting the single input argument or use a json string… Really no other way ? I guess there is some trick with the notation (ex.: {{ [0.40, 0.3605, 80] }]) ? indeed, the HomeScript documentation is clearly mentioning an array :

image

And next, I can’t find how to retrieve the result. I read also on this forum that one could create and set a tag with the output value. But I don’t want to define one distinct tag per flow where I use this script :confused: Maybe I am not using/calling correctly my HomeyScript ??

Any advice for me to achieve my purpose ?
Thx a lot in adv for any tip !

V.