magichome-platform
Version:
discover, control, and receive status for magichome devices
182 lines (181 loc) • 6.53 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.RGBtoHSV = exports.HSVtoRGB = exports.clamp = exports.CCTtoTB = exports.TBtoCCT = exports.convertCCTValueToDualWhite = void 0;
function convertCCTValueToDualWhite(_cctValue) {
const cctValue = _cctValue - 140;
let multiplier = 0;
const CCT = { warmWhite: 0, coldWhite: 0 };
const threshold = 110;
if (cctValue >= threshold) {
CCT.warmWhite = 127;
multiplier = 1 - (cctValue - threshold) / (360 - threshold);
CCT.coldWhite = Math.round(127 * multiplier);
}
else {
CCT.coldWhite = 127;
multiplier = cctValue / threshold;
CCT.warmWhite = Math.round(127 * multiplier);
}
return CCT;
}
exports.convertCCTValueToDualWhite = convertCCTValueToDualWhite;
function TBtoCCT(tb) {
const { temperature, brightness } = tb;
// Normalize temperature from 140–500 → 0–1
const tNorm = (temperature - 140) / (500 - 140);
let warmWhite = 0;
let coldWhite = 0;
if (tNorm <= 0.5) {
// Cold white is full, warm white ramps up
coldWhite = 255;
warmWhite = Math.round(255 * (tNorm / 0.5));
}
else {
// Warm white is full, cold white ramps down
warmWhite = 255;
coldWhite = Math.round(255 * ((1 - tNorm) / 0.5));
}
return {
warmWhite: Math.round((warmWhite * brightness) / 100),
coldWhite: Math.round((coldWhite * brightness) / 100),
};
}
exports.TBtoCCT = TBtoCCT;
function CCTtoTB(cct) {
const { warmWhite, coldWhite } = cct;
if (warmWhite === 0 && coldWhite === 0) {
return { temperature: 140, brightness: 0 };
}
const brightness = Math.max(warmWhite, coldWhite) / 255 * 100;
const warmFull = warmWhite / (brightness / 100);
const coldFull = coldWhite / (brightness / 100);
let tNorm = 0;
if (warmFull >= 255) {
tNorm = 1 - (coldFull / 255) * 0.5;
}
else if (coldFull >= 255) {
tNorm = (warmFull / 255) * 0.5;
}
else {
// Fallback (balanced): estimate by warm vs total
tNorm = warmFull / (warmFull + coldFull);
}
const temperature = 140 + tNorm * (500 - 140);
return {
temperature: Math.round(temperature),
brightness: Math.round(brightness),
};
}
exports.CCTtoTB = CCTtoTB;
function clamp(value, min, max) {
return Math.min(max, Math.max(min, value));
}
exports.clamp = clamp;
function HSVtoRGB(HSV) {
const { hue, saturation, value } = HSV;
let [H, S, V] = [hue, saturation, value];
H = clamp(H, 0, 360);
S = clamp(S, 0, 100);
V = clamp(V, 0, 100);
S /= 100.0;
V /= 100.0;
const C = V * S;
const X = C * (1 - Math.abs(((H / 60) % 2) - 1));
const m = V - C;
let order = []; // Initialize order as an empty array
if (H < 60)
order = [C, X, 0];
else if (H < 120)
order = [X, C, 0];
else if (H < 180)
order = [0, C, X];
else if (H < 240)
order = [0, X, C];
else if (H < 300)
order = [X, 0, C];
else if (H <= 360)
order = [C, 0, X];
const [dR, dG, dB] = order;
const [red, green, blue] = [Math.round((dR + m) * 255), Math.round((dG + m) * 255), Math.round((dB + m) * 255)];
return { red, green, blue };
}
exports.HSVtoRGB = HSVtoRGB;
function RGBtoHSV(RGB) {
const { red, green, blue } = RGB;
const [R, G, B] = [red, green, blue];
const [dR, dG, dB] = [R / 255, G / 255, B / 255];
const dMax = Math.max(dR, dG, dB);
const dMin = Math.min(dR, dG, dB);
const D = dMax - dMin;
let H, S, V;
if (D === 0)
H = 0;
else if (dMax === dR)
H = ((dG - dB) / D) % 6;
else if (dMax === dG)
H = (dB - dR) / D + 2;
else
H = (dR - dG) / D + 4;
H *= 60;
if (H < 0)
H += 360;
V = dMax;
if (V === 0)
S = 0;
else
S = D / V;
S *= 100;
V *= 100;
return { hue: H, saturation: S, value: V };
}
exports.RGBtoHSV = RGBtoHSV;
// ColorConversionUtils.ts
// // RGB to HSV
// export function RGBStripToHSV(rgb: { red: number; green: number; blue: number }, previousHue: number): { hue: number; saturation: number; value: number } {
// // Conversion code here
// }
// // HSV to RGB
// export function HSVtoRGBStrip(hsv: { hue: number; saturation: number; value: number }): { red: number; green: number; blue: number } {
// // Conversion code here
// }
// // RGBW to HSV (non-simultaneous)
// export function RGBWtoHSVNonSimultaneous(deviceCommand: IDeviceCommand, previousHue: number): { hue: number; saturation: number; value: number } {
// // Conversion code here
// }
// // HSV to RGBW (non-simultaneous)
// export function HSVtoRGBWNonSimultaneous(hsv: { hue: number; saturation: number; value: number }): IDeviceCommand {
// // Conversion code here
// }
// // RGBW to HSV (simultaneous)
// export function RGBWtoHSVSimultaneous(deviceCommand: IDeviceCommand, previousHue: number): { hue: number; saturation: number; value: number } {
// // Conversion code here
// }
// // HSV to RGBW (simultaneous)
// export function HSVtoRGBWSimultaneous(hsv: { hue: number; saturation: number; value: number }): IDeviceCommand {
// // Conversion code here
// }
// // RGBWC to HSV (non-simultaneous)
// export function RGBWCtoHSVNonSimultaneous(deviceCommand: IDeviceCommand, previousHue: number): IColorHSV {}
// // HSV to RGBWC (non-simultaneous)
// export function HSVtoRGBWCNonSimultaneous(hsv: { hue: number; saturation: number; value: number }): IDeviceCommand {
// // Conversion code here
// }
// // RGBWC to HSV (simultaneous)
// export function RGBWCtoHSVSimultaneous(deviceState: IDeviceState, previousHue: number = null): IColorHSV {
// const {
// RGB: { red, green, blue },
// CCT: { coldWhite, warmWhite },
// } = deviceState;
// let { hue, saturation, value } = RGBtoHSV({ red, green, blue });
// if (previousHue !== null) {
// hue = previousHue;
// }
// if (Math.max(coldWhite, warmWhite) > 0) {
// const { brightness, temperature } = CCTtoTB({ coldWhite, warmWhite });
// }
// // Conversion code here
// }
// // HSV to RGBWC (simultaneous)
// export function HSVtoRGBWCSimultaneous(hsv: { hue: number; saturation: number; value: number }): IDeviceCommand {
// // Conversion code here
// }