5#include <MycilaDimmer.h>
7#define DIMMER_RESOLUTION 12
8#define FIRING_DELAYS_LEN 200U
10static constexpr uint32_t FIRING_DELAY_MAX = (1 << DIMMER_RESOLUTION) - 1;
11static constexpr uint32_t FIRING_DELAYS_SCALE = (FIRING_DELAYS_LEN - 1U) * (1UL << (16 - DIMMER_RESOLUTION));
14static constexpr uint16_t FIRING_DELAYS[FIRING_DELAYS_LEN] = {
15 0xffff, 0xe877, 0xe240, 0xddd9, 0xda51, 0xd74f, 0xd4aa, 0xd248, 0xd01a, 0xce16,
16 0xcc34, 0xca6e, 0xc8c0, 0xc728, 0xc5a1, 0xc42b, 0xc2c3, 0xc168, 0xc019, 0xbed3,
17 0xbd98, 0xbc65, 0xbb3b, 0xba17, 0xb8fb, 0xb7e5, 0xb6d5, 0xb5ca, 0xb4c5, 0xb3c4,
18 0xb2c8, 0xb1d1, 0xb0dd, 0xafed, 0xaf01, 0xae18, 0xad33, 0xac51, 0xab71, 0xaa95,
19 0xa9bb, 0xa8e3, 0xa80e, 0xa73b, 0xa66b, 0xa59c, 0xa4d0, 0xa406, 0xa33d, 0xa276,
20 0xa1b1, 0xa0ed, 0xa02b, 0x9f6b, 0x9eac, 0x9dee, 0x9d32, 0x9c76, 0x9bbc, 0x9b04,
21 0x9a4c, 0x9996, 0x98e0, 0x982b, 0x9778, 0x96c5, 0x9613, 0x9563, 0x94b2, 0x9403,
22 0x9354, 0x92a6, 0x91f9, 0x914c, 0x90a0, 0x8ff5, 0x8f4a, 0x8ea0, 0x8df6, 0x8d4d,
23 0x8ca4, 0x8bfb, 0x8b53, 0x8aab, 0x8a04, 0x895d, 0x88b6, 0x8810, 0x876a, 0x86c4,
24 0x861e, 0x8579, 0x84d3, 0x842e, 0x8389, 0x82e4, 0x823f, 0x819b, 0x80f6, 0x8051,
25 0x7fad, 0x7f08, 0x7e63, 0x7dbf, 0x7d1a, 0x7c75, 0x7bd0, 0x7b2b, 0x7a85, 0x79e0,
26 0x793a, 0x7894, 0x77ee, 0x7748, 0x76a1, 0x75fa, 0x7553, 0x74ab, 0x7403, 0x735a,
27 0x72b1, 0x7208, 0x715e, 0x70b4, 0x7009, 0x6f5e, 0x6eb2, 0x6e05, 0x6d58, 0x6caa,
28 0x6bfb, 0x6b4c, 0x6a9b, 0x69eb, 0x6939, 0x6886, 0x67d3, 0x671e, 0x6668, 0x65b2,
29 0x64fa, 0x6442, 0x6388, 0x62cc, 0x6210, 0x6152, 0x6093, 0x5fd3, 0x5f11, 0x5e4d,
30 0x5d88, 0x5cc1, 0x5bf8, 0x5b2e, 0x5a62, 0x5993, 0x58c3, 0x57f0, 0x571b, 0x5643,
31 0x5569, 0x548d, 0x53ad, 0x52cb, 0x51e6, 0x50fd, 0x5011, 0x4f21, 0x4e2d, 0x4d36,
32 0x4c3a, 0x4b39, 0x4a34, 0x4929, 0x4819, 0x4703, 0x45e7, 0x44c3, 0x4399, 0x4266,
33 0x412b, 0x3fe5, 0x3e96, 0x3d3b, 0x3bd3, 0x3a5d, 0x38d6, 0x373e, 0x3590, 0x33ca,
34 0x31e8, 0x2fe4, 0x2db6, 0x2b54, 0x28af, 0x25ad, 0x2225, 0x1dbe, 0x1787, 0x0000
42uint16_t Mycila::Dimmer::_semiPeriod = 0;
44uint16_t Mycila::Dimmer::_lookupFiringDelay(
float dutyCycle, uint16_t semiPeriod) {
45 uint32_t duty = dutyCycle * FIRING_DELAY_MAX;
46 uint32_t slot = duty * FIRING_DELAYS_SCALE + (FIRING_DELAYS_SCALE >> 1);
47 uint32_t index = slot >> 16;
48 uint32_t a = FIRING_DELAYS[index];
49 uint32_t b = FIRING_DELAYS[index + 1];
50 uint32_t delay = a - (((a - b) * (slot & 0xffff)) >> 16);
51 return (delay * semiPeriod) >> 16;
54#ifdef MYCILA_JSON_SUPPORT
55static const char* H_LEVELS[] = {
"H1",
"H3",
"H5",
"H7",
"H9",
"H11",
"H13",
"H15",
"H17",
"H19",
"H21"};
62void Mycila::Dimmer::toJson(
const JsonObject& root)
const {
63 root[
"type"] = type();
64 root[
"enabled"] = _enabled;
65 root[
"online"] = _online;
66 root[
"state"] = isOn() ?
"on" :
"off";
67 root[
"duty_cycle"] = _dutyCycle;
68 root[
"duty_cycle_mapped"] = getDutyCycleMapped();
69 root[
"duty_cycle_fire"] = _dutyCycleFire;
70 root[
"duty_cycle_limit"] = _dutyCycleLimit;
71 root[
"duty_cycle_min"] = _dutyCycleMin;
72 root[
"duty_cycle_max"] = _dutyCycleMax;
73 root[
"power_lut"] = _powerLUTEnabled;
74 root[
"semi_period"] = _semiPeriod;
75 JsonObject harmonics = root[
"harmonics"].to<JsonObject>();
76 float* output =
new float[11];
77 if (calculateHarmonics(output, 11)) {
78 for (
size_t i = 0; i < 11; i++) {
79 if (!std::isnan(output[i])) {
80 harmonics[H_LEVELS[i]] = output[i];