From 82c48006d51bbb7b36278b4e5dd45a316138b765 Mon Sep 17 00:00:00 2001 From: bpohvoodoo Date: Sun, 19 Apr 2020 11:18:23 +0200 Subject: [PATCH 1/2] Version Bump to 3.1.2 * Almost finished: bugfixes regarding issue #80 * ToDo: bugfixes regarding issue #70 --- Arduino/McLighting/McLighting.ino | 34 +++----------- Arduino/McLighting/definitions.h | 8 ++-- Arduino/McLighting/helper_functions.h | 12 +++++ Arduino/McLighting/request_handlers.h | 68 +++++++++++++++++++++------ Arduino/McLighting/rest_api.h | 50 +++++++++++++++++++- Arduino/McLighting/version.h | 2 +- Arduino/McLighting/version_info.ino | 7 ++- 7 files changed, 132 insertions(+), 49 deletions(-) diff --git a/Arduino/McLighting/McLighting.ino b/Arduino/McLighting/McLighting.ino index b229a748..83f18ba8 100644 --- a/Arduino/McLighting/McLighting.ino +++ b/Arduino/McLighting/McLighting.ino @@ -271,9 +271,11 @@ void initMqtt() { mqtt_intopic[sizeof(mqtt_intopic) - 1] = 0x00; snprintf(mqtt_outtopic, sizeof(mqtt_outtopic), "%s/out", mqtt_clientid); mqtt_outtopic[sizeof(mqtt_outtopic) - 1] = 0x00; - #if defined(MQTT_HOME_ASSISTANT_SUPPORT) - snprintf(mqtt_ha_config, sizeof(mqtt_ha_config), "homeassistant/light/%s/config", mqtt_clientid); - mqtt_ha_config[sizeof(mqtt_ha_config) - 1] = 0x00; + #if defined(ENABLE_HOMEASSISTANT) + #if defined(MQTT_HOMEASSISTANT_SUPPORT) + snprintf(mqtt_ha_config, sizeof(mqtt_ha_config), "homeassistant/light/%s/config", mqtt_clientid); + mqtt_ha_config[sizeof(mqtt_ha_config) - 1] = 0x00; + #endif snprintf(mqtt_ha_state_in, sizeof(mqtt_ha_state_in), "home/%s_ha/state/in", mqtt_clientid); mqtt_ha_state_in[sizeof(mqtt_ha_state_in) - 1] = 0x00; snprintf(mqtt_ha_state_out, sizeof(mqtt_ha_state_out), "home/%s_ha/state/out", mqtt_clientid); @@ -655,9 +657,6 @@ void loop() { if (State.mode == OFF) { if (prevmode != State.mode) { - #if defined(ENABLE_MQTT) - snprintf(mqtt_buf, sizeof(mqtt_buf), "OK =off", ""); - #endif #if defined(POWER_SUPPLY) digitalWrite(POWER_SUPPLY, !POWER_ON); // power off -> external power supply #endif @@ -674,19 +673,9 @@ void loop() { if (State.mode == SET) { State.mode = HOLD; - // Segment - if (prevsegment != State.segment) { - #if defined(ENABLE_MQTT) - snprintf(mqtt_buf, sizeof(mqtt_buf), "OK Ss%i", State.segment); - #endif - //prevsegment = State.segment; - } // Mode - if (segState.mode[State.segment] != fx_mode) { + if ((segState.mode[State.segment] != fx_mode) || prevmode == OFF) { segState.mode[State.segment] = fx_mode; - #if defined(ENABLE_MQTT) - snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", segState.mode[State.segment]); - #endif strip->strip_off(); autoCount[State.segment] = 0; autoDelay[State.segment] = 0; @@ -701,13 +690,10 @@ void loop() { }*/ // Brightness if (strip->getBrightness() != State.brightness) { - #if defined(ENABLE_MQTT) - snprintf(mqtt_buf, sizeof(mqtt_buf), "OK %%%i", State.brightness); - #endif brightness_trans = State.brightness; } // Speed - if (fx_speed != segState.speed[State.segment]) { + if (fx_speed != segState.speed[prevsegment]) { #if defined(ENABLE_MQTT) snprintf(mqtt_buf, sizeof(mqtt_buf), "OK ?%i", segState.speed[prevsegment]); #endif @@ -739,12 +725,6 @@ void loop() { } //strip->setBrightness(brightness_actual); #if defined(ENABLE_MQTT) - #if ENABLE_MQTT == 0 - mqtt_client->publish(mqtt_outtopic, mqtt_buf); - #endif - #if ENABLE_MQTT == 1 - mqtt_client->publish(mqtt_outtopic, qospub, false, mqtt_buf); - #endif #if defined(ENABLE_HOMEASSISTANT) if(ha_send_data.active()) ha_send_data.detach(); ha_send_data.once(DELAY_MQTT_HA_MESSAGE, tickerSendState); diff --git a/Arduino/McLighting/definitions.h b/Arduino/McLighting/definitions.h index 60fdbc3c..47803f34 100644 --- a/Arduino/McLighting/definitions.h +++ b/Arduino/McLighting/definitions.h @@ -19,7 +19,7 @@ char HOSTNAME[65] = "McLightingRGBW"; // Friedly hostname is configurable just //#define ENABLE_MQTT_HOSTNAME_CHIPID // Uncomment/comment to add ESPChipID to end of MQTT hostname //#define ENABLE_MQTT_INCLUDE_IP // uncomment/comment to add the IP-adress to the MQTT message #define ENABLE_HOMEASSISTANT // If defined, enable Homeassistant integration, ENABLE_MQTT must be active -#define MQTT_HOME_ASSISTANT_SUPPORT // If defined, use AMQTT and select Tools -> IwIP Variant -> Higher Bandwidth +#define MQTT_HOMEASSISTANT_SUPPORT // If defined, use AMQTT and select Tools -> IwIP Variant -> Higher Bandwidth #define DELAY_MQTT_HA_MESSAGE 5 // HA Status is send after DELAY_MQTT_HA_MESSAGE seconds, to save bandwith //#define ENABLE_BUTTON 14 // If defined, enable button handling code, see: https://github.com/toblum/McLighting/wiki/Button-control, the value defines the input pin (14 / D5) for switching the LED strip on / off, connect this PIN to ground to trigger button. @@ -28,7 +28,7 @@ char HOSTNAME[65] = "McLightingRGBW"; // Friedly hostname is configurable just #if defined(POWER_SUPPLY) #define POWER_ON HIGH // Define the output state to turn on the power supply, either HIGH or LOW. Opposite will be uses for power off. #endif -#define ENABLE_REMOTE 13 // If defined, enable Remote Control via TSOP31238. The value defines the input pin (13 / D7) for TSOP31238 Out +//#define ENABLE_REMOTE 13 // If defined, enable Remote Control via TSOP31238. The value defines the input pin (13 / D7) for TSOP31238 Out #if defined(ENABLE_BUTTON_GY33) #define GAMMA 2.5 // Gamma correction for GY-33 sensor @@ -74,7 +74,7 @@ uint8_t prevsegment = 0; uint8_t _sn[4] = {255,255,255,0}; #endif -#if defined(MQTT_HOME_ASSISTANT_SUPPORT) +#if defined(MQTT_HOMEASSISTANT_SUPPORT) #define MQTT_HOME_ASSISTANT_0_87_SUPPORT // Comment if using HA version < 0.87 #endif @@ -93,7 +93,7 @@ uint8_t prevsegment = 0; #if defined(ENABLE_HOMEASSISTANT) and !defined(ENABLE_MQTT) #error "To use HA, you have to either enable PubCubClient or AsyncMQTT" #endif -#if !defined(ENABLE_HOMEASSISTANT) and defined(MQTT_HOME_ASSISTANT_SUPPORT) +#if !defined(ENABLE_HOMEASSISTANT) and defined(MQTT_HOMEASSISTANT_SUPPORT) #error "To use HA support, you have to either enable Homeassistant component" #endif diff --git a/Arduino/McLighting/helper_functions.h b/Arduino/McLighting/helper_functions.h index 70a5150c..61eee633 100644 --- a/Arduino/McLighting/helper_functions.h +++ b/Arduino/McLighting/helper_functions.h @@ -321,3 +321,15 @@ uint32_t trans(uint32_t _newcolor, uint32_t _oldcolor, uint8_t _level, uint8_t _ _oldcolor = scale_wrgb(_oldcolor, 255-_level); return _newcolor + _oldcolor; } + +#if defined(ENABLE_MQTT) + void sendmqtt() { + #if ENABLE_MQTT == 0 + mqtt_client->publish(mqtt_outtopic, mqtt_buf); + #endif + #if ENABLE_MQTT == 1 + mqtt_client->publish(mqtt_outtopic, qospub, false, mqtt_buf); + #endif + memset(mqtt_buf,0,sizeof(mqtt_buf)); + } +#endif diff --git a/Arduino/McLighting/request_handlers.h b/Arduino/McLighting/request_handlers.h index 1dc18f1c..8954208e 100644 --- a/Arduino/McLighting/request_handlers.h +++ b/Arduino/McLighting/request_handlers.h @@ -199,9 +199,25 @@ void handleSetWS2812FXMode(uint8_t * mypayload) { fx_mode = (uint8_t) strtol((const char *) &mypayload[1], NULL, 10); fx_mode = constrain(fx_mode, 0, strip->getModeCount() - 1); State.mode = SET; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", fx_mode); + sendmqtt(); + #endif } else { if (strcmp((char *) &mypayload[1], "off") == 0) { - if (State.mode == OFF) { State.mode = SET; } else { State.mode = OFF; }; + if (State.mode == OFF) { + State.mode = SET; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", segState.mode[State.segment]); + sendmqtt(); + #endif + } else { + State.mode = OFF; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /off", ""); + sendmqtt(); + #endif + } } if (strcmp((char *) &mypayload[1], "on") == 0) { State.mode = SET; @@ -276,7 +292,11 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { //memcpy(hexcolors_trans, segState.colors[State.segment], sizeof(hexcolors_trans)); _updateState = true; Dbg_Prefix(mqtt, num); - DBG_OUTPUT_PORT.printf("Set segment to: [%u]\r\n", State.segment); + DBG_OUTPUT_PORT.printf("Set segment to: [%u]\r\n", _seg); + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK Ss%i", _seg); + sendmqtt(); + #endif } } // / ==> Set segment first LED @@ -289,6 +309,10 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { setSegmentSize(); Dbg_Prefix(mqtt, num); DBG_OUTPUT_PORT.printf("Set segment start to: [%u]\r\n", _seg_start); + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK S[%i", _seg_start); + sendmqtt(); + #endif } } // / ==> Set segment last LED @@ -301,18 +325,25 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { setSegmentSize(); Dbg_Prefix(mqtt, num); DBG_OUTPUT_PORT.printf("Set segment stop to: [%u]\r\n", _seg_stop); + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK S]%i", _seg_stop); + sendmqtt(); + #endif } } if (_payload[1] == 'o') { - char _fx_options[4]; - snprintf(_fx_options, sizeof(_fx_options), "%s", &_payload[2]); - _fx_options[3] = 0x00; - if (((constrain(atoi(_fx_options), 0, 255)>>1)<<1) != segState.options) { - segState.options= ((constrain(atoi(_fx_options), 0, 255)>>1)<<1); + uint8_t _fx_options = (uint8_t) strtol((const char *) &_payload[2], NULL, 10); + _fx_options = ((constrain(server.arg("fxopt").toInt(), 0, 255)>>1)<<1); + if (_fx_options != segState.options) { + segState.options= _fx_options; _updateSegState = true; strip->setOptions(State.segment, segState.options); Dbg_Prefix(mqtt, num); - DBG_OUTPUT_PORT.printf("Set segment options to: [%u]\r\n", segState.options); + DBG_OUTPUT_PORT.printf("Set segment options to: [%u]\r\n", _fx_options); + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK So%i", _fx_options); + sendmqtt(); + #endif } } char * buffer = listSegmentStateJSON(State.segment); @@ -373,11 +404,16 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { // ? ==> Set speed if (_payload[0] == '?') { uint16_t _fx_speed = (uint16_t) strtol((const char *) &_payload[1], NULL, 10); - segState.speed[State.segment] = constrain(_fx_speed, SPEED_MIN, SPEED_MAX ); - State.mode = SET; + _fx_speed = constrain(_fx_speed, SPEED_MIN, SPEED_MAX ); + //if (segState.speed[State.segment] != _fx_speed) {} + segState.speed[State.segment] = _fx_speed; _updateSegState = true; Dbg_Prefix(mqtt, num); - DBG_OUTPUT_PORT.printf("Set speed to: [%u]\r\n", segState.speed[State.segment]); + DBG_OUTPUT_PORT.printf("Set speed to: [%u]\r\n", _fx_speed); + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK ?%i", _fx_speed); + sendmqtt(); + #endif } // % ==> Set brightness @@ -385,10 +421,13 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { uint8_t b = (uint8_t) strtol((const char *) &_payload[1], NULL, 10); State.brightness = constrain(b, 0, 255); if (strip->getBrightness() != State.brightness) { - State.mode = SET; Dbg_Prefix(mqtt, num); DBG_OUTPUT_PORT.printf("Set brightness to: [%u]\r\n", State.brightness); _updateState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK %%%i", State.brightness); + sendmqtt(); + #endif } } @@ -432,6 +471,7 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { } #if defined(ENABLE_STATE_SAVE) if (_updateState) { + State.mode = SET; if(save_state.active()) save_state.detach(); save_state.once(3, tickerSaveState); } @@ -941,7 +981,7 @@ void webSocketEvent(uint8_t num, WStype_t type, uint8_t * payload, size_t lenght ha_send_data.detach(); mqtt_client->subscribe(mqtt_ha_state_in, qossub); ha_send_data.once(DELAY_MQTT_HA_MESSAGE, tickerSendState); - #if defined(MQTT_HOME_ASSISTANT_SUPPORT) + #if defined(MQTT_HOMEASSISTANT_SUPPORT) const size_t bufferSize = JSON_ARRAY_SIZE(strip->getModeCount()+ 4) + JSON_OBJECT_SIZE(11) + 1500; DynamicJsonDocument jsonBuffer(bufferSize); JsonObject root = jsonBuffer.to(); @@ -1047,7 +1087,7 @@ void webSocketEvent(uint8_t num, WStype_t type, uint8_t * payload, size_t lenght ha_send_data.detach(); uint16_t packetIdSub2 = mqtt_client->subscribe((char *)mqtt_ha_state_in, qossub); DBG_OUTPUT_PORT.printf("Subscribing at QoS %d, packetId: ", qossub); DBG_OUTPUT_PORT.println(packetIdSub2); - #if defined(MQTT_HOME_ASSISTANT_SUPPORT) + #if defined(MQTT_HOMEASSISTANT_SUPPORT) const size_t bufferSize = JSON_ARRAY_SIZE(strip->getModeCount()+ 4) + JSON_OBJECT_SIZE(11) + 1500; DynamicJsonDocument jsonBuffer(bufferSize); JsonObject root = jsonBuffer.to(); diff --git a/Arduino/McLighting/rest_api.h b/Arduino/McLighting/rest_api.h index 52e3b80b..663b43e9 100644 --- a/Arduino/McLighting/rest_api.h +++ b/Arduino/McLighting/rest_api.h @@ -319,7 +319,19 @@ server.on("/config", []() { }); server.on("/off", []() { - if (State.mode == OFF) { State.mode = SET; } else { State.mode = OFF; }; + if (State.mode == OFF) { + State.mode = SET; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", segState.mode[State.segment]); + sendmqtt(); + #endif + } else { + State.mode = OFF; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /off", ""); + sendmqtt(); + #endif + } getACK("OK"); #if defined(ENABLE_STATE_SAVE) if(save_state.active()) save_state.detach(); @@ -330,6 +342,10 @@ server.on("/off", []() { server.on("/on", []() { if (prevmode == OFF) { State.mode = SET; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", segState.mode[State.segment]); + sendmqtt(); + #endif getACK("OK"); #if defined(ENABLE_STATE_SAVE) if(save_state.active()) save_state.detach(); @@ -354,6 +370,10 @@ server.on("/set", []() { //memcpy(hexcolors_trans, segState.colors[State.segment], sizeof(hexcolors_trans)); State.mode = SET; _updateState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK Ss%i", _seg); + sendmqtt(); + #endif } } if ((server.arg("start") != "") && (server.arg("start").toInt() >= 0) && (server.arg("start").toInt() <= segState.stop)) { @@ -363,6 +383,10 @@ server.on("/set", []() { segState.start = _seg_start; setSegmentSize(); _updateSegState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK S[%i", _seg_start); + sendmqtt(); + #endif } } if ((server.arg("stop") != "") && (server.arg("stop").toInt() >= segState.start) && (server.arg("stop").toInt() <= Config.stripSize)) { @@ -372,6 +396,10 @@ server.on("/set", []() { segState.stop = _seg_stop; setSegmentSize(); _updateSegState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK S]%i", _seg_stop); + sendmqtt(); + #endif } } @@ -381,6 +409,10 @@ server.on("/set", []() { segState.options = _fx_options; strip->setOptions(State.segment, segState.options); _updateSegState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK So%i", _fx_options); + sendmqtt(); + #endif } } //color wrgb @@ -475,14 +507,24 @@ server.on("/set", []() { // Speed if ((server.arg("s") != "") && (server.arg("s").toInt() >= 0) && (server.arg("s").toInt() <= 255)) { - segState.speed[State.segment] = constrain(server.arg("s").toInt(), 0, 255); + uint8_t _fx_speed = constrain(server.arg("s").toInt(), 0, 255); + segState.speed[State.segment] = _fx_speed; _updateSegState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK ?%i", _fx_speed); + sendmqtt(); + #endif } + //Mode if ((server.arg("m") != "") && (server.arg("m").toInt() >= 0) && (server.arg("m").toInt() <= strip->getModeCount())) { fx_mode = constrain(server.arg("m").toInt(), 0, strip->getModeCount() - 1); if (fx_mode != segState.mode[State.segment]) { _updateSegState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", fx_mode); + sendmqtt(); + #endif } } @@ -495,6 +537,10 @@ server.on("/set", []() { if (strip->getBrightness() != State.brightness) { State.mode = SET; _updateState = true; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK %%%i", State.brightness); + sendmqtt(); + #endif } //DBG_OUTPUT_PORT.printf("Get Args: %s\r\n", listStateJSONfull()); //possibly causing heap problems getACK("OK"); diff --git a/Arduino/McLighting/version.h b/Arduino/McLighting/version.h index 5aaef448..852f153a 100644 --- a/Arduino/McLighting/version.h +++ b/Arduino/McLighting/version.h @@ -1 +1 @@ -#define SKETCH_VERSION "3.1.1" \ No newline at end of file +#define SKETCH_VERSION "3.1.2" diff --git a/Arduino/McLighting/version_info.ino b/Arduino/McLighting/version_info.ino index 6b134296..a5216e6f 100644 --- a/Arduino/McLighting/version_info.ino +++ b/Arduino/McLighting/version_info.ino @@ -261,4 +261,9 @@ * 18 April 2020 * Version Bump to 3.1.1 * bugfixes regarding issue #80 - */ \ No newline at end of file + * + * 19 April 2020 + * Version Bump to 3.1.2 + * Almost finished: bugfixes regarding issue #80 + * ToDo: bugfixes regarding issue #70 + */ From 5c7bf36fd5c3102ff133e3b939205a5aaa51cfa6 Mon Sep 17 00:00:00 2001 From: Dzillum Date: Sun, 25 Oct 2020 15:40:45 +0100 Subject: [PATCH 2/2] Bugfixes * Updated WS2812FX Lib * Version Bump to 3.1.3 * fixed issue #100 * included pull request from issue #93 * Fixed a GUI bug on reloading --- Arduino/McLighting/WS2812FX.cpp | 934 ++++++++--------- Arduino/McLighting/WS2812FX.h | 276 ++--- Arduino/McLighting/data/index.htm | 102 +- Arduino/McLighting/data/index.htm.gz | Bin 20878 -> 20635 bytes Arduino/McLighting/definitions.h | 2 +- Arduino/McLighting/htm_index_gz.h | 1356 ++++++++++++------------- Arduino/McLighting/json_functions.h | 8 +- Arduino/McLighting/request_handlers.h | 37 +- Arduino/McLighting/rest_api.h | 20 +- Arduino/McLighting/version.h | 2 +- Arduino/McLighting/version_info.ino | 8 + clients/web/index.htm | 104 +- clients/web/index.htm.gz | Bin 20878 -> 20635 bytes 13 files changed, 1433 insertions(+), 1416 deletions(-) diff --git a/Arduino/McLighting/WS2812FX.cpp b/Arduino/McLighting/WS2812FX.cpp index dad49aca..2e49feb7 100644 --- a/Arduino/McLighting/WS2812FX.cpp +++ b/Arduino/McLighting/WS2812FX.cpp @@ -61,7 +61,7 @@ void WS2812FX::init() { // void WS2812FX::timer() { // for (int j=0; j < 1000; j++) { -// uint16_t delay = (this->*_mode[SEGMENT.mode])(); +// uint16_t delay = (this->*_modes[_seg->mode])(); // } // } @@ -69,15 +69,20 @@ void WS2812FX::service() { if(_running || _triggered) { unsigned long now = millis(); // Be aware, millis() rolls over every 49 days bool doShow = false; - for(uint8_t i=0; i < _num_segments; i++) { - _segment_index = i; - CLR_FRAME; - if(now > SEGMENT_RUNTIME.next_time || _triggered) { - SET_FRAME; - doShow = true; - uint16_t delay = (this->*_mode[SEGMENT.mode])(); - SEGMENT_RUNTIME.next_time = now + max(delay, SPEED_MIN); - SEGMENT_RUNTIME.counter_mode_call++; + for(uint8_t i=0; i < _active_segments_len; i++) { + if(_active_segments[i] != INACTIVE_SEGMENT) { + _segment_index = i; + _seg = &_segments[_active_segments[i]]; + _seg_len = (uint16_t)(_seg->stop - _seg->start + 1); + _seg_rt = &_segment_runtimes[i]; + CLR_FRAME_CYCLE; + if(now > _seg_rt->next_time || _triggered) { + SET_FRAME; + doShow = true; + uint16_t delay = (this->*_modes[_seg->mode])(); + _seg_rt->next_time = now + max(delay, SPEED_MIN); + _seg_rt->counter_mode_call++; + } } } if(doShow) { @@ -91,23 +96,15 @@ void WS2812FX::service() { // overload setPixelColor() functions so we can use gamma correction // (see https://learn.adafruit.com/led-tricks-gamma-correction/the-issue) void WS2812FX::setPixelColor(uint16_t n, uint32_t c) { - if(IS_GAMMA) { - uint8_t w = (c >> 24) & 0xFF; - uint8_t r = (c >> 16) & 0xFF; - uint8_t g = (c >> 8) & 0xFF; - uint8_t b = c & 0xFF; - Adafruit_NeoPixel::setPixelColor(n, gamma8(r), gamma8(g), gamma8(b), gamma8(w)); - } else { - Adafruit_NeoPixel::setPixelColor(n, c); - } + uint8_t w = (c >> 24) & 0xFF; + uint8_t r = (c >> 16) & 0xFF; + uint8_t g = (c >> 8) & 0xFF; + uint8_t b = c & 0xFF; + setPixelColor(n, r, g, b, w); } void WS2812FX::setPixelColor(uint16_t n, uint8_t r, uint8_t g, uint8_t b) { - if(IS_GAMMA) { - Adafruit_NeoPixel::setPixelColor(n, gamma8(r), gamma8(g), gamma8(b)); - } else { - Adafruit_NeoPixel::setPixelColor(n, r, g, b); - } + setPixelColor(n, r, g, b, 0); } void WS2812FX::setPixelColor(uint16_t n, uint8_t r, uint8_t g, uint8_t b, uint8_t w) { @@ -125,13 +122,17 @@ void WS2812FX::copyPixels(uint16_t dest, uint16_t src, uint16_t count) { memmove(pixels + (dest * bytesPerPixel), pixels + (src * bytesPerPixel), count * bytesPerPixel); } +// change the underlying Adafruit_NeoPixel pixels pointer (use with care) +void WS2812FX::setPixels(uint16_t num_leds, uint8_t* ptr) { + free(Adafruit_NeoPixel::pixels); // free existing data (if any) + Adafruit_NeoPixel::pixels = ptr; + Adafruit_NeoPixel::numLEDs = num_leds; + Adafruit_NeoPixel::numBytes = num_leds * ((wOffset == rOffset) ? 3 : 4); +} + // overload show() functions so we can use custom show() void WS2812FX::show(void) { - if(customShow == NULL) { - Adafruit_NeoPixel::show(); - } else { - customShow(); - } + customShow == NULL ? Adafruit_NeoPixel::show() : customShow(); } void WS2812FX::start() { @@ -174,17 +175,16 @@ void WS2812FX::setSpeed(uint16_t s) { } void WS2812FX::setSpeed(uint8_t seg, uint16_t s) { -// resetSegmentRuntime(seg); _segments[seg].speed = constrain(s, SPEED_MIN, SPEED_MAX); } void WS2812FX::increaseSpeed(uint8_t s) { - uint16_t newSpeed = constrain(SEGMENT.speed + s, SPEED_MIN, SPEED_MAX); + uint16_t newSpeed = constrain(_seg->speed + s, SPEED_MIN, SPEED_MAX); setSpeed(newSpeed); } void WS2812FX::decreaseSpeed(uint8_t s) { - uint16_t newSpeed = constrain(SEGMENT.speed - s, SPEED_MIN, SPEED_MAX); + uint16_t newSpeed = constrain(_seg->speed - s, SPEED_MIN, SPEED_MAX); setSpeed(newSpeed); } @@ -201,13 +201,11 @@ void WS2812FX::setColor(uint32_t c) { } void WS2812FX::setColor(uint8_t seg, uint32_t c) { -// resetSegmentRuntime(seg); _segments[seg].colors[0] = c; } void WS2812FX::setColors(uint8_t seg, uint32_t* c) { -// resetSegmentRuntime(seg); - for(uint8_t i=0; i _segments[0].stop - _segments[0].start + 1) s = 1; - s = _segments[0].stop - _segments[0].start + 1 - s; - - for(uint16_t i=_segments[0].start + s; i <= (_segments[0].stop - _segments[0].start + 1); i++) { - setPixelColor(i, 0); - } + uint16_t seglen = _segments[0].stop - _segments[0].start + 1; + fill(BLACK, _segments[0].start, seglen); show(); - setLength(s); + if (s < seglen) setLength(seglen - s); } boolean WS2812FX::isRunning() { @@ -271,16 +265,24 @@ boolean WS2812FX::isFrame() { return isFrame(0); } -boolean WS2812FX::isFrame(uint8_t segIndex) { - return (_segment_runtimes[segIndex].aux_param2 & FRAME); +boolean WS2812FX::isFrame(uint8_t seg) { + uint8_t* ptr = (uint8_t*)memchr(_active_segments, seg, _active_segments_len); + if(ptr == NULL) return false; // segment not active + return (_segment_runtimes[ptr - _active_segments].aux_param2 & FRAME); } boolean WS2812FX::isCycle() { return isCycle(0); } -boolean WS2812FX::isCycle(uint8_t segIndex) { - return (_segment_runtimes[segIndex].aux_param2 & CYCLE); +boolean WS2812FX::isCycle(uint8_t seg) { + uint8_t* ptr = (uint8_t*)memchr(_active_segments, seg, _active_segments_len); + if(ptr == NULL) return false; // segment not active + return (_segment_runtimes[ptr - _active_segments].aux_param2 & CYCLE); +} + +void WS2812FX::setCycle() { + SET_CYCLE; } uint8_t WS2812FX::getMode(void) { @@ -299,7 +301,6 @@ uint16_t WS2812FX::getSpeed(uint8_t seg) { return _segments[seg].speed; } - uint8_t WS2812FX::getOptions(uint8_t seg) { return _segments[seg].options; } @@ -343,9 +344,9 @@ uint32_t* WS2812FX::getColors(uint8_t seg) { uint8_t WS2812FX::getSegmentIndex(void) { return _segment_index; } - + WS2812FX::Segment* WS2812FX::getSegment(void) { - return &_segments[_segment_index]; + return _seg; } WS2812FX::Segment* WS2812FX::getSegment(uint8_t seg) { @@ -357,17 +358,23 @@ WS2812FX::Segment* WS2812FX::getSegments(void) { } WS2812FX::Segment_runtime* WS2812FX::getSegmentRuntime(void) { - return &_segment_runtimes[_segment_index]; + return _seg_rt; } WS2812FX::Segment_runtime* WS2812FX::getSegmentRuntime(uint8_t seg) { - return &_segment_runtimes[seg]; + uint8_t* ptr = (uint8_t*)memchr(_active_segments, seg, _active_segments_len); + if(ptr == NULL) return NULL; // segment not active + return &_segment_runtimes[ptr - _active_segments]; } WS2812FX::Segment_runtime* WS2812FX::getSegmentRuntimes(void) { return _segment_runtimes; } +uint8_t* WS2812FX::getActiveSegments(void) { + return _active_segments; +} + const __FlashStringHelper* WS2812FX::getModeName(uint8_t m) { if(m < MODE_COUNT) { return _names[m]; @@ -376,22 +383,32 @@ const __FlashStringHelper* WS2812FX::getModeName(uint8_t m) { } } -void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, bool reverse) { +void WS2812FX::setIdleSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, uint8_t options) { uint32_t colors[] = {color, 0, 0}; - setSegment(n, start, stop, mode, colors, speed, reverse); + setIdleSegment(n, start, stop, mode, colors, speed, options); } -void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, uint8_t options) { - uint32_t colors[] = {color, 0, 0}; +void WS2812FX::setIdleSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, uint8_t options) { setSegment(n, start, stop, mode, colors, speed, options); + if(n < _active_segments_len) removeActiveSegment(n);; +} + +void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, bool reverse) { + uint32_t colors[] = {color, 0, 0}; + setSegment(n, start, stop, mode, colors, speed, (uint8_t)(reverse ? REVERSE : NO_OPTIONS)); } void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, bool reverse) { setSegment(n, start, stop, mode, colors, speed, (uint8_t)(reverse ? REVERSE : NO_OPTIONS)); } +void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, uint8_t options) { + uint32_t colors[] = {color, 0, 0}; + setSegment(n, start, stop, mode, colors, speed, options); +} + void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, uint8_t options) { - if(n < (sizeof(_segments) / sizeof(_segments[0]))) { + if(n < _segments_len) { if(n + 1 > _num_segments) _num_segments = n + 1; _segments[n].start = start; _segments[n].stop = stop; @@ -399,34 +416,75 @@ void WS2812FX::setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode _segments[n].speed = speed; _segments[n].options = options; - for(uint8_t i=0; i g -> b -> back to r @@ -454,7 +511,6 @@ uint32_t WS2812FX::color_wheel(uint8_t pos) { } } - /* * Returns a new, random wheel index with a minimum distance of 42 from pos. */ @@ -483,7 +539,7 @@ uint8_t WS2812FX::random8() { // note random8(lim) generates numbers in the range 0 to (lim -1) uint8_t WS2812FX::random8(uint8_t lim) { uint8_t r = random8(); - r = (r * lim) >> 8; + r = ((uint16_t)r * lim) >> 8; return r; } @@ -528,14 +584,20 @@ uint32_t* WS2812FX::intensitySums() { return intensities; } + +/* ##################################################### +# +# Mode Functions +# +##################################################### */ + /* * No blinking. Just plain old static light. */ uint16_t WS2812FX::mode_static(void) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, SEGMENT.colors[0]); - } - return 500; + fill(_seg->colors[0], _seg->start, _seg_len); + SET_CYCLE; + return _seg->speed; } @@ -545,16 +607,15 @@ uint16_t WS2812FX::mode_static(void) { * if(strobe == true) then create a strobe effect */ uint16_t WS2812FX::blink(uint32_t color1, uint32_t color2, bool strobe) { - uint32_t color = ((SEGMENT_RUNTIME.counter_mode_call & 1) == 0) ? color1 : color2; - if(IS_REVERSE) color = (color == color1) ? color2 : color1; - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color); - } - - if((SEGMENT_RUNTIME.counter_mode_call & 1) == 0) { - return strobe ? 20 : (SEGMENT.speed / 2); + if(_seg_rt->counter_mode_call & 1) { + uint32_t color = (IS_REVERSE) ? color1 : color2; // off + fill(color, _seg->start, _seg_len); + SET_CYCLE; + return strobe ? _seg->speed - 20 : (_seg->speed / 2); } else { - return strobe ? SEGMENT.speed - 20 : (SEGMENT.speed / 2); + uint32_t color = (IS_REVERSE) ? color2 : color1; // on + fill(color, _seg->start, _seg_len); + return strobe ? 20 : (_seg->speed / 2); } } @@ -563,7 +624,7 @@ uint16_t WS2812FX::blink(uint32_t color1, uint32_t color2, bool strobe) { * Normal blinking. 50% on/off time. */ uint16_t WS2812FX::mode_blink(void) { - return blink(SEGMENT.colors[0], SEGMENT.colors[1], false); + return blink(_seg->colors[0], _seg->colors[1], false); } @@ -571,7 +632,7 @@ uint16_t WS2812FX::mode_blink(void) { * Classic Blink effect. Cycling through the rainbow. */ uint16_t WS2812FX::mode_blink_rainbow(void) { - return blink(color_wheel(SEGMENT_RUNTIME.counter_mode_call & 0xFF), SEGMENT.colors[1], false); + return blink(color_wheel(_seg_rt->counter_mode_call & 0xFF), _seg->colors[1], false); } @@ -579,7 +640,7 @@ uint16_t WS2812FX::mode_blink_rainbow(void) { * Classic Strobe effect. */ uint16_t WS2812FX::mode_strobe(void) { - return blink(SEGMENT.colors[0], SEGMENT.colors[1], true); + return blink(_seg->colors[0], _seg->colors[1], true); } @@ -587,7 +648,7 @@ uint16_t WS2812FX::mode_strobe(void) { * Classic Strobe effect. Cycling through the rainbow. */ uint16_t WS2812FX::mode_strobe_rainbow(void) { - return blink(color_wheel(SEGMENT_RUNTIME.counter_mode_call & 0xFF), SEGMENT.colors[1], true); + return blink(color_wheel(_seg_rt->counter_mode_call & 0xFF), _seg->colors[1], true); } @@ -597,46 +658,46 @@ uint16_t WS2812FX::mode_strobe_rainbow(void) { * if (bool rev == true) then LEDs are turned off in reverse order */ uint16_t WS2812FX::color_wipe(uint32_t color1, uint32_t color2, bool rev) { - if(SEGMENT_RUNTIME.counter_mode_step < SEGMENT_LENGTH) { - uint32_t led_offset = SEGMENT_RUNTIME.counter_mode_step; + if(_seg_rt->counter_mode_step < _seg_len) { + uint32_t led_offset = _seg_rt->counter_mode_step; if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - led_offset, color1); + setPixelColor(_seg->stop - led_offset, color1); } else { - setPixelColor(SEGMENT.start + led_offset, color1); + setPixelColor(_seg->start + led_offset, color1); } } else { - uint32_t led_offset = SEGMENT_RUNTIME.counter_mode_step - SEGMENT_LENGTH; + uint32_t led_offset = _seg_rt->counter_mode_step - _seg_len; if((IS_REVERSE && !rev) || (!IS_REVERSE && rev)) { - setPixelColor(SEGMENT.stop - led_offset, color2); + setPixelColor(_seg->stop - led_offset, color2); } else { - setPixelColor(SEGMENT.start + led_offset, color2); + setPixelColor(_seg->start + led_offset, color2); } } - if(SEGMENT_RUNTIME.counter_mode_step % SEGMENT_LENGTH == 0) SET_CYCLE; - else CLR_CYCLE; + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % (_seg_len * 2); + + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % (SEGMENT_LENGTH * 2); - return (SEGMENT.speed / (SEGMENT_LENGTH * 2)); + return (_seg->speed / (_seg_len * 2)); } /* * Lights all LEDs one after another. */ uint16_t WS2812FX::mode_color_wipe(void) { - return color_wipe(SEGMENT.colors[0], SEGMENT.colors[1], false); + return color_wipe(_seg->colors[0], _seg->colors[1], false); } uint16_t WS2812FX::mode_color_wipe_inv(void) { - return color_wipe(SEGMENT.colors[1], SEGMENT.colors[0], false); + return color_wipe(_seg->colors[1], _seg->colors[0], false); } uint16_t WS2812FX::mode_color_wipe_rev(void) { - return color_wipe(SEGMENT.colors[0], SEGMENT.colors[1], true); + return color_wipe(_seg->colors[0], _seg->colors[1], true); } uint16_t WS2812FX::mode_color_wipe_rev_inv(void) { - return color_wipe(SEGMENT.colors[1], SEGMENT.colors[0], true); + return color_wipe(_seg->colors[1], _seg->colors[0], true); } @@ -645,10 +706,10 @@ uint16_t WS2812FX::mode_color_wipe_rev_inv(void) { * Then starts over with another color. */ uint16_t WS2812FX::mode_color_wipe_random(void) { - if(SEGMENT_RUNTIME.counter_mode_step % SEGMENT_LENGTH == 0) { // aux_param will store our random color wheel index - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); + if(_seg_rt->counter_mode_step % _seg_len == 0) { // aux_param will store our random color wheel index + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); } - uint32_t color = color_wheel(SEGMENT_RUNTIME.aux_param); + uint32_t color = color_wheel(_seg_rt->aux_param); return color_wipe(color, color, false) * 2; } @@ -657,10 +718,10 @@ uint16_t WS2812FX::mode_color_wipe_random(void) { * Random color introduced alternating from start and end of strip. */ uint16_t WS2812FX::mode_color_sweep_random(void) { - if(SEGMENT_RUNTIME.counter_mode_step % SEGMENT_LENGTH == 0) { // aux_param will store our random color wheel index - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); + if(_seg_rt->counter_mode_step % _seg_len == 0) { // aux_param will store our random color wheel index + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); } - uint32_t color = color_wheel(SEGMENT_RUNTIME.aux_param); + uint32_t color = color_wheel(_seg_rt->aux_param); return color_wipe(color, color, true) * 2; } @@ -670,13 +731,11 @@ uint16_t WS2812FX::mode_color_sweep_random(void) { * to the next random color. */ uint16_t WS2812FX::mode_random_color(void) { - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); // aux_param will store our random color wheel index - uint32_t color = color_wheel(SEGMENT_RUNTIME.aux_param); - - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color); - } - return (SEGMENT.speed); + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); // aux_param will store our random color wheel index + uint32_t color = color_wheel(_seg_rt->aux_param); + fill(color, _seg->start, _seg_len); + SET_CYCLE; + return _seg->speed; } @@ -685,14 +744,15 @@ uint16_t WS2812FX::mode_random_color(void) { * to another random color. */ uint16_t WS2812FX::mode_single_dynamic(void) { - if(SEGMENT_RUNTIME.counter_mode_call == 0) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { + if(_seg_rt->counter_mode_call == 0) { + for(uint16_t i=_seg->start; i <= _seg->stop; i++) { setPixelColor(i, color_wheel(random8())); } } - setPixelColor(SEGMENT.start + random16(SEGMENT_LENGTH), color_wheel(random8())); - return (SEGMENT.speed); + setPixelColor(_seg->start + random16(_seg_len), color_wheel(random8())); + SET_CYCLE; + return _seg->speed; } @@ -701,10 +761,11 @@ uint16_t WS2812FX::mode_single_dynamic(void) { * to new random colors. */ uint16_t WS2812FX::mode_multi_dynamic(void) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { + for(uint16_t i=_seg->start; i <= _seg->stop; i++) { setPixelColor(i, color_wheel(random8())); } - return (SEGMENT.speed); + SET_CYCLE; + return _seg->speed; } @@ -713,7 +774,7 @@ uint16_t WS2812FX::mode_multi_dynamic(void) { * Use mode "fade" if you like to have something similar with a different speed. */ uint16_t WS2812FX::mode_breath(void) { - int lum = SEGMENT_RUNTIME.counter_mode_step; + int lum = _seg_rt->counter_mode_step; if(lum > 255) lum = 511 - lum; // lum = 15 -> 255 -> 15 uint16_t delay; @@ -726,17 +787,14 @@ uint16_t WS2812FX::mode_breath(void) { else if(lum <= 150) delay = 11; // 5 else delay = 10; // 4 - uint32_t color = SEGMENT.colors[0]; - uint8_t w = (color >> 24 & 0xFF) * lum / 256; - uint8_t r = (color >> 16 & 0xFF) * lum / 256; - uint8_t g = (color >> 8 & 0xFF) * lum / 256; - uint8_t b = (color & 0xFF) * lum / 256; - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, r, g, b, w); - } + uint32_t color = color_blend(_seg->colors[1], _seg->colors[0], lum); + fill(color, _seg->start, _seg_len); - SEGMENT_RUNTIME.counter_mode_step += 2; - if(SEGMENT_RUNTIME.counter_mode_step > (512-15)) SEGMENT_RUNTIME.counter_mode_step = 15; + _seg_rt->counter_mode_step += 2; + if(_seg_rt->counter_mode_step > (512-15)) { + _seg_rt->counter_mode_step = 15; + SET_CYCLE; + } return delay; } @@ -745,17 +803,18 @@ uint16_t WS2812FX::mode_breath(void) { * Fades the LEDs between two colors */ uint16_t WS2812FX::mode_fade(void) { - int lum = SEGMENT_RUNTIME.counter_mode_step; + int lum = _seg_rt->counter_mode_step; if(lum > 255) lum = 511 - lum; // lum = 0 -> 255 -> 0 - uint32_t color = color_blend(SEGMENT.colors[0], SEGMENT.colors[1], lum); - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color); - } + uint32_t color = color_blend(_seg->colors[1], _seg->colors[0], lum); + fill(color, _seg->start, _seg_len); - SEGMENT_RUNTIME.counter_mode_step += 4; - if(SEGMENT_RUNTIME.counter_mode_step > 511) SEGMENT_RUNTIME.counter_mode_step = 0; - return (SEGMENT.speed / 128); + _seg_rt->counter_mode_step += 4; + if(_seg_rt->counter_mode_step > 511) { + _seg_rt->counter_mode_step = 0; + SET_CYCLE; + } + return (_seg->speed / 128); } @@ -763,27 +822,28 @@ uint16_t WS2812FX::mode_fade(void) { * scan function - runs a block of pixels back and forth. */ uint16_t WS2812FX::scan(uint32_t color1, uint32_t color2, bool dual) { - int8_t dir = SEGMENT_RUNTIME.aux_param ? -1 : 1; + int8_t dir = _seg_rt->aux_param ? -1 : 1; uint8_t size = 1 << SIZE_OPTION; - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color2); - } + fill(color2, _seg->start, _seg_len); for(uint8_t i = 0; i < size; i++) { if(IS_REVERSE || dual) { - setPixelColor(SEGMENT.stop - SEGMENT_RUNTIME.counter_mode_step - i, color1); + setPixelColor(_seg->stop - _seg_rt->counter_mode_step - i, color1); } if(!IS_REVERSE || dual) { - setPixelColor(SEGMENT.start + SEGMENT_RUNTIME.counter_mode_step + i, color1); + setPixelColor(_seg->start + _seg_rt->counter_mode_step + i, color1); } } - SEGMENT_RUNTIME.counter_mode_step += dir; - if(SEGMENT_RUNTIME.counter_mode_step == 0) SEGMENT_RUNTIME.aux_param = 0; - if(SEGMENT_RUNTIME.counter_mode_step >= (uint16_t)(SEGMENT_LENGTH - size)) SEGMENT_RUNTIME.aux_param = 1; + _seg_rt->counter_mode_step += dir; + if(_seg_rt->counter_mode_step == 0) { + _seg_rt->aux_param = 0; + SET_CYCLE; + } + if(_seg_rt->counter_mode_step >= (uint16_t)(_seg_len - size)) _seg_rt->aux_param = 1; - return (SEGMENT.speed / (SEGMENT_LENGTH * 2)); + return (_seg->speed / (_seg_len * 2)); } @@ -791,7 +851,7 @@ uint16_t WS2812FX::scan(uint32_t color1, uint32_t color2, bool dual) { * Runs a block of pixels back and forth. */ uint16_t WS2812FX::mode_scan(void) { - return scan(SEGMENT.colors[0], SEGMENT.colors[1], false); + return scan(_seg->colors[0], _seg->colors[1], false); } @@ -799,7 +859,7 @@ uint16_t WS2812FX::mode_scan(void) { * Runs two blocks of pixels back and forth in opposite directions. */ uint16_t WS2812FX::mode_dual_scan(void) { - return scan(SEGMENT.colors[0], SEGMENT.colors[1], true); + return scan(_seg->colors[0], _seg->colors[1], true); } @@ -807,13 +867,14 @@ uint16_t WS2812FX::mode_dual_scan(void) { * Cycles all LEDs at once through a rainbow. */ uint16_t WS2812FX::mode_rainbow(void) { - uint32_t color = color_wheel(SEGMENT_RUNTIME.counter_mode_step); - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color); - } + uint32_t color = color_wheel(_seg_rt->counter_mode_step); + fill(color, _seg->start, _seg_len); + + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) & 0xFF; + + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) & 0xFF; - return (SEGMENT.speed / 256); + return (_seg->speed / 256); } @@ -821,13 +882,61 @@ uint16_t WS2812FX::mode_rainbow(void) { * Cycles a rainbow over the entire string of LEDs. */ uint16_t WS2812FX::mode_rainbow_cycle(void) { - for(uint16_t i=0; i < SEGMENT_LENGTH; i++) { - uint32_t color = color_wheel(((i * 256 / SEGMENT_LENGTH) + SEGMENT_RUNTIME.counter_mode_step) & 0xFF); - setPixelColor(SEGMENT.start + i, color); + for(uint16_t i=0; i < _seg_len; i++) { + uint32_t color = color_wheel(((i * 256 / _seg_len) + _seg_rt->counter_mode_step) & 0xFF); + setPixelColor(_seg->start + i, color); + } + + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) & 0xFF; + + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; + + return (_seg->speed / 256); +} + + +/* + * Tricolor chase function + */ +uint16_t WS2812FX::tricolor_chase(uint32_t color1, uint32_t color2, uint32_t color3) { + uint8_t sizeCnt = 1 << SIZE_OPTION; + uint8_t sizeCnt2 = sizeCnt + sizeCnt; + uint8_t sizeCnt3 = sizeCnt2 + sizeCnt; + uint16_t index = _seg_rt->counter_mode_step % sizeCnt3; + for(uint16_t i=0; i < _seg_len; i++, index++) { + index = index % sizeCnt3; + + uint32_t color = color3; + if(index < sizeCnt) color = color1; + else if(index < sizeCnt2) color = color2; + + if(IS_REVERSE) { + setPixelColor(_seg->start + i, color); + } else { + setPixelColor(_seg->stop - i, color); + } } - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) & 0xFF; - return (SEGMENT.speed / 256); + _seg_rt->counter_mode_step++; + if(_seg_rt->counter_mode_step % _seg_len == 0) SET_CYCLE; + + return (_seg->speed / _seg_len); +} + + +/* + * Tricolor chase mode + */ +uint16_t WS2812FX::mode_tricolor_chase(void) { + return tricolor_chase(_seg->colors[0], _seg->colors[1], _seg->colors[2]); +} + + +/* + * Alternating white/red/black pixels running. + */ +uint16_t WS2812FX::mode_circus_combustus(void) { + return tricolor_chase(RED, WHITE, BLACK); } @@ -836,7 +945,7 @@ uint16_t WS2812FX::mode_rainbow_cycle(void) { * Inspired by the Adafruit examples. */ uint16_t WS2812FX::mode_theater_chase(void) { - return tricolor_chase(SEGMENT.colors[0], SEGMENT.colors[1], SEGMENT.colors[1]); + return tricolor_chase(_seg->colors[0], _seg->colors[1], _seg->colors[1]); } @@ -845,9 +954,9 @@ uint16_t WS2812FX::mode_theater_chase(void) { * Inspired by the Adafruit examples. */ uint16_t WS2812FX::mode_theater_chase_rainbow(void) { - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) & 0xFF; - uint32_t color = color_wheel(SEGMENT_RUNTIME.counter_mode_step); - return tricolor_chase(color, SEGMENT.colors[1], SEGMENT.colors[1]); + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) & 0xFF; + uint32_t color = color_wheel(_seg_rt->counter_mode_step); + return tricolor_chase(color, _seg->colors[1], _seg->colors[1]); } @@ -855,23 +964,20 @@ uint16_t WS2812FX::mode_theater_chase_rainbow(void) { * Running lights effect with smooth sine transition. */ uint16_t WS2812FX::mode_running_lights(void) { - uint8_t w = ((SEGMENT.colors[0] >> 24) & 0xFF); - uint8_t r = ((SEGMENT.colors[0] >> 16) & 0xFF); - uint8_t g = ((SEGMENT.colors[0] >> 8) & 0xFF); - uint8_t b = (SEGMENT.colors[0] & 0xFF); - uint8_t size = 1 << SIZE_OPTION; - uint8_t sineIncr = max(1, (256 / SEGMENT_LENGTH) * size); - for(uint16_t i=0; i < SEGMENT_LENGTH; i++) { - int lum = (int)sine8(((i + SEGMENT_RUNTIME.counter_mode_step) * sineIncr)); + uint8_t sineIncr = max(1, (256 / _seg_len) * size); + for(uint16_t i=0; i < _seg_len; i++) { + int lum = (int)sine8(((i + _seg_rt->counter_mode_step) * sineIncr)); + uint32_t color = color_blend(_seg->colors[0], _seg->colors[1], lum); if(IS_REVERSE) { - setPixelColor(SEGMENT.start + i, (r * lum) / 256, (g * lum) / 256, (b * lum) / 256, (w * lum) / 256); + setPixelColor(_seg->start + i, color); } else { - setPixelColor(SEGMENT.stop - i, (r * lum) / 256, (g * lum) / 256, (b * lum) / 256, (w * lum) / 256); + setPixelColor(_seg->stop - i, color); } } - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % 256; - return (SEGMENT.speed / SEGMENT_LENGTH); + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % 256; + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; + return (_seg->speed / _seg_len); } @@ -879,19 +985,17 @@ uint16_t WS2812FX::mode_running_lights(void) { * twinkle function */ uint16_t WS2812FX::twinkle(uint32_t color1, uint32_t color2) { - if(SEGMENT_RUNTIME.counter_mode_step == 0) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, color2); - } - uint16_t min_leds = max(1, SEGMENT_LENGTH / 5); // make sure, at least one LED is on - uint16_t max_leds = max(1, SEGMENT_LENGTH / 2); // make sure, at least one LED is on - SEGMENT_RUNTIME.counter_mode_step = random(min_leds, max_leds); + if(_seg_rt->counter_mode_step == 0) { + fill(color2, _seg->start, _seg_len); + uint16_t min_leds = (_seg_len / 4) + 1; // make sure, at least one LED is on + _seg_rt->counter_mode_step = random(min_leds, min_leds * 2); + SET_CYCLE; } - setPixelColor(SEGMENT.start + random16(SEGMENT_LENGTH), color1); + setPixelColor(_seg->start + random16(_seg_len), color1); - SEGMENT_RUNTIME.counter_mode_step--; - return (SEGMENT.speed / SEGMENT_LENGTH); + _seg_rt->counter_mode_step--; + return (_seg->speed / _seg_len); } /* @@ -899,7 +1003,7 @@ uint16_t WS2812FX::twinkle(uint32_t color1, uint32_t color2) { * Inspired by www.tweaking4all.com/hardware/arduino/arduino-led-strip-effects/ */ uint16_t WS2812FX::mode_twinkle(void) { - return twinkle(SEGMENT.colors[0], SEGMENT.colors[1]); + return twinkle(_seg->colors[0], _seg->colors[1]); } /* @@ -907,7 +1011,7 @@ uint16_t WS2812FX::mode_twinkle(void) { * Inspired by www.tweaking4all.com/hardware/arduino/arduino-led-strip-effects/ */ uint16_t WS2812FX::mode_twinkle_random(void) { - return twinkle(color_wheel(random8()), SEGMENT.colors[1]); + return twinkle(color_wheel(random8()), _seg->colors[1]); } @@ -915,7 +1019,7 @@ uint16_t WS2812FX::mode_twinkle_random(void) { * fade out functions */ void WS2812FX::fade_out() { - return fade_out(SEGMENT.colors[1]); + return fade_out(_seg->colors[1]); } void WS2812FX::fade_out(uint32_t targetColor) { @@ -932,7 +1036,7 @@ void WS2812FX::fade_out(uint32_t targetColor) { int g2 = (color >> 8) & 0xff; int b2 = color & 0xff; - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { + for(uint16_t i=_seg->start; i <= _seg->stop; i++) { color = getPixelColor(i); // current color if(rate == 0) { // old fade-to-black algorithm setPixelColor(i, (color >> 1) & 0x7F7F7F7F); @@ -995,12 +1099,11 @@ uint16_t WS2812FX::twinkle_fade(uint32_t color) { if(random8(3) == 0) { uint8_t size = 1 << SIZE_OPTION; - uint16_t index = SEGMENT.start + random16(SEGMENT_LENGTH - size); - for(uint8_t i=0; istart + random16(_seg_len - size); + fill(color, index, size); + SET_CYCLE; } - return (SEGMENT.speed / 8); + return (_seg->speed / 8); } @@ -1008,7 +1111,7 @@ uint16_t WS2812FX::twinkle_fade(uint32_t color) { * Blink several LEDs on, fading out. */ uint16_t WS2812FX::mode_twinkle_fade(void) { - return twinkle_fade(SEGMENT.colors[0]); + return twinkle_fade(_seg->colors[0]); } @@ -1019,21 +1122,33 @@ uint16_t WS2812FX::mode_twinkle_fade_random(void) { return twinkle_fade(color_wheel(random8())); } +/* + * Sparkle function + * color1 = background color + * color2 = sparkle color + */ +uint16_t WS2812FX::sparkle(uint32_t color1, uint32_t color2) { + if(_seg_rt->counter_mode_step == 0) { + fill(color1, _seg->start, _seg_len); + } + + uint8_t size = 1 << SIZE_OPTION; + fill(color1, _seg->start + _seg_rt->aux_param3, size); + + _seg_rt->aux_param3 = random16(_seg_len - size); // aux_param3 stores the random led index + fill(color2, _seg->start + _seg_rt->aux_param3, size); + + SET_CYCLE; + return (_seg->speed / 32); +} + /* * Blinks one LED at a time. * Inspired by www.tweaking4all.com/hardware/arduino/arduino-led-strip-effects/ */ uint16_t WS2812FX::mode_sparkle(void) { - uint8_t size = 1 << SIZE_OPTION; - for(uint8_t i=0; icolors[1], _seg->colors[0]); } @@ -1042,20 +1157,7 @@ uint16_t WS2812FX::mode_sparkle(void) { * Inspired by www.tweaking4all.com/hardware/arduino/arduino-led-strip-effects/ */ uint16_t WS2812FX::mode_flash_sparkle(void) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, SEGMENT.colors[0]); - } - - if(random8(5) == 0) { - uint8_t size = 1 << SIZE_OPTION; - uint16_t index = SEGMENT.start + random16(SEGMENT_LENGTH - size); - for(uint8_t j=0; jcolors[0], WHITE); } @@ -1064,17 +1166,15 @@ uint16_t WS2812FX::mode_flash_sparkle(void) { * Inspired by www.tweaking4all.com/hardware/arduino/arduino-led-strip-effects/ */ uint16_t WS2812FX::mode_hyper_sparkle(void) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, SEGMENT.colors[0]); - } + fill(_seg->colors[0], _seg->start, _seg_len); - if(random8(5) < 2) { - for(uint16_t i=0; i < max(1, SEGMENT_LENGTH/3); i++) { - setPixelColor(SEGMENT.start + random16(SEGMENT_LENGTH), WHITE); - } - return 20; + uint8_t size = 1 << SIZE_OPTION; + for(uint8_t i=0; i<8; i++) { + fill(WHITE, _seg->start + random16(_seg_len - size), size); } - return SEGMENT.speed; + + SET_CYCLE; + return (_seg->speed / 32); } @@ -1082,23 +1182,21 @@ uint16_t WS2812FX::mode_hyper_sparkle(void) { * Strobe effect with different strobe count and pause, controlled by speed. */ uint16_t WS2812FX::mode_multi_strobe(void) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, BLACK); - } + fill(_seg->colors[1], _seg->start, _seg_len); - uint16_t delay = 200 + ((9 - (SEGMENT.speed % 10)) * 100); - uint16_t count = 2 * ((SEGMENT.speed / 100) + 1); - if(SEGMENT_RUNTIME.counter_mode_step < count) { - if((SEGMENT_RUNTIME.counter_mode_step & 1) == 0) { - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, SEGMENT.colors[0]); - } + uint16_t delay = 200 + ((9 - (_seg->speed % 10)) * 100); + uint16_t count = 2 * ((_seg->speed / 100) + 1); + if(_seg_rt->counter_mode_step < count) { + if((_seg_rt->counter_mode_step & 1) == 0) { + fill(_seg->colors[0], _seg->start, _seg_len); delay = 20; } else { delay = 50; } } - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % (count + 1); + + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % (count + 1); + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; return delay; } @@ -1108,29 +1206,27 @@ uint16_t WS2812FX::mode_multi_strobe(void) { * color1 = background color * color2 and color3 = colors of two adjacent leds */ - uint16_t WS2812FX::chase(uint32_t color1, uint32_t color2, uint32_t color3) { uint8_t size = 1 << SIZE_OPTION; for(uint8_t i=0; icounter_mode_step + i) % _seg_len; + uint16_t b = (a + size) % _seg_len; + uint16_t c = (b + size) % _seg_len; if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - a, color1); - setPixelColor(SEGMENT.stop - b, color2); - setPixelColor(SEGMENT.stop - c, color3); + setPixelColor(_seg->stop - a, color1); + setPixelColor(_seg->stop - b, color2); + setPixelColor(_seg->stop - c, color3); } else { - setPixelColor(SEGMENT.start + a, color1); - setPixelColor(SEGMENT.start + b, color2); - setPixelColor(SEGMENT.start + c, color3); + setPixelColor(_seg->start + a, color1); + setPixelColor(_seg->start + b, color2); + setPixelColor(_seg->start + c, color3); } } - if(SEGMENT_RUNTIME.counter_mode_step + (size * 3) == SEGMENT_LENGTH) SET_CYCLE; - else CLR_CYCLE; + if(_seg_rt->counter_mode_step + (size * 3) == _seg_len) SET_CYCLE; - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - return (SEGMENT.speed / SEGMENT_LENGTH); + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % _seg_len; + return (_seg->speed / _seg_len); } @@ -1138,7 +1234,7 @@ uint16_t WS2812FX::chase(uint32_t color1, uint32_t color2, uint32_t color3) { * Bicolor chase mode */ uint16_t WS2812FX::mode_bicolor_chase(void) { - return chase(SEGMENT.colors[0], SEGMENT.colors[1], SEGMENT.colors[2]); + return chase(_seg->colors[0], _seg->colors[1], _seg->colors[2]); } @@ -1146,7 +1242,7 @@ uint16_t WS2812FX::mode_bicolor_chase(void) { * White running on _color. */ uint16_t WS2812FX::mode_chase_color(void) { - return chase(SEGMENT.colors[0], WHITE, WHITE); + return chase(_seg->colors[0], WHITE, WHITE); } @@ -1154,7 +1250,7 @@ uint16_t WS2812FX::mode_chase_color(void) { * Black running on _color. */ uint16_t WS2812FX::mode_chase_blackout(void) { - return chase(SEGMENT.colors[0], BLACK, BLACK); + return chase(_seg->colors[0], BLACK, BLACK); } @@ -1162,7 +1258,7 @@ uint16_t WS2812FX::mode_chase_blackout(void) { * _color running on white. */ uint16_t WS2812FX::mode_chase_white(void) { - return chase(WHITE, SEGMENT.colors[0], SEGMENT.colors[0]); + return chase(WHITE, _seg->colors[0], _seg->colors[0]); } @@ -1170,10 +1266,10 @@ uint16_t WS2812FX::mode_chase_white(void) { * White running followed by random color. */ uint16_t WS2812FX::mode_chase_random(void) { - if(SEGMENT_RUNTIME.counter_mode_step == 0) { - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); + if(_seg_rt->counter_mode_step == 0) { + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); } - return chase(color_wheel(SEGMENT_RUNTIME.aux_param), WHITE, WHITE); + return chase(color_wheel(_seg_rt->aux_param), WHITE, WHITE); } @@ -1181,10 +1277,10 @@ uint16_t WS2812FX::mode_chase_random(void) { * Rainbow running on white. */ uint16_t WS2812FX::mode_chase_rainbow_white(void) { - uint16_t n = SEGMENT_RUNTIME.counter_mode_step; - uint16_t m = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - uint32_t color2 = color_wheel(((n * 256 / SEGMENT_LENGTH) + (SEGMENT_RUNTIME.counter_mode_call & 0xFF)) & 0xFF); - uint32_t color3 = color_wheel(((m * 256 / SEGMENT_LENGTH) + (SEGMENT_RUNTIME.counter_mode_call & 0xFF)) & 0xFF); + uint16_t n = _seg_rt->counter_mode_step; + uint16_t m = (_seg_rt->counter_mode_step + 1) % _seg_len; + uint32_t color2 = color_wheel(((n * 256 / _seg_len) + (_seg_rt->counter_mode_call & 0xFF)) & 0xFF); + uint32_t color3 = color_wheel(((m * 256 / _seg_len) + (_seg_rt->counter_mode_call & 0xFF)) & 0xFF); return chase(WHITE, color2, color3); } @@ -1194,9 +1290,9 @@ uint16_t WS2812FX::mode_chase_rainbow_white(void) { * White running on rainbow. */ uint16_t WS2812FX::mode_chase_rainbow(void) { - uint8_t color_sep = 256 / SEGMENT_LENGTH; - uint8_t color_index = SEGMENT_RUNTIME.counter_mode_call & 0xFF; - uint32_t color = color_wheel(((SEGMENT_RUNTIME.counter_mode_step * color_sep) + color_index) & 0xFF); + uint8_t color_sep = 256 / _seg_len; + uint8_t color_index = _seg_rt->counter_mode_call & 0xFF; + uint32_t color = color_wheel(((_seg_rt->counter_mode_step * color_sep) + color_index) & 0xFF); return chase(color, WHITE, WHITE); } @@ -1206,45 +1302,50 @@ uint16_t WS2812FX::mode_chase_rainbow(void) { * Black running on rainbow. */ uint16_t WS2812FX::mode_chase_blackout_rainbow(void) { - uint8_t color_sep = 256 / SEGMENT_LENGTH; - uint8_t color_index = SEGMENT_RUNTIME.counter_mode_call & 0xFF; - uint32_t color = color_wheel(((SEGMENT_RUNTIME.counter_mode_step * color_sep) + color_index) & 0xFF); + uint8_t color_sep = 256 / _seg_len; + uint8_t color_index = _seg_rt->counter_mode_call & 0xFF; + uint32_t color = color_wheel(((_seg_rt->counter_mode_step * color_sep) + color_index) & 0xFF); return chase(color, BLACK, BLACK); } - /* - * White flashes running on _color. + * running white flashes function. + * color1 = background color + * color2 = flash color */ -uint16_t WS2812FX::mode_chase_flash(void) { +uint16_t WS2812FX::chase_flash(uint32_t color1, uint32_t color2) { const static uint8_t flash_count = 4; - uint8_t flash_step = SEGMENT_RUNTIME.counter_mode_call % ((flash_count * 2) + 1); + uint8_t flash_step = _seg_rt->counter_mode_call % ((flash_count * 2) + 1); - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { - setPixelColor(i, SEGMENT.colors[0]); - } - - uint16_t delay = (SEGMENT.speed / SEGMENT_LENGTH); if(flash_step < (flash_count * 2)) { - if(flash_step % 2 == 0) { - uint16_t n = SEGMENT_RUNTIME.counter_mode_step; - uint16_t m = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - n, WHITE); - setPixelColor(SEGMENT.stop - m, WHITE); - } else { - setPixelColor(SEGMENT.start + n, WHITE); - setPixelColor(SEGMENT.start + m, WHITE); - } - delay = 20; + uint32_t color = (flash_step % 2 == 0) ? color2 : color1; + uint16_t n = _seg_rt->counter_mode_step; + uint16_t m = (_seg_rt->counter_mode_step + 1) % _seg_len; + if(IS_REVERSE) { + setPixelColor(_seg->stop - n, color); + setPixelColor(_seg->stop - m, color); } else { - delay = 30; + setPixelColor(_seg->start + n, color); + setPixelColor(_seg->start + m, color); } + return 30; } else { - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % _seg_len; + if(_seg_rt->counter_mode_step == 0) { + // update aux_param so mode_chase_flash_random() will select the next color + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); + SET_CYCLE; + } } - return delay; + return (_seg->speed / _seg_len); +} + +/* + * White flashes running on _color. + */ +uint16_t WS2812FX::mode_chase_flash(void) { + return chase_flash(_seg->colors[0], WHITE); } @@ -1252,34 +1353,7 @@ uint16_t WS2812FX::mode_chase_flash(void) { * White flashes running, followed by random color. */ uint16_t WS2812FX::mode_chase_flash_random(void) { - const static uint8_t flash_count = 4; - uint8_t flash_step = SEGMENT_RUNTIME.counter_mode_call % ((flash_count * 2) + 1); - - for(uint16_t i=0; i < SEGMENT_RUNTIME.counter_mode_step; i++) { - setPixelColor(SEGMENT.start + i, color_wheel(SEGMENT_RUNTIME.aux_param)); - } - - uint16_t delay = (SEGMENT.speed / SEGMENT_LENGTH); - if(flash_step < (flash_count * 2)) { - uint16_t n = SEGMENT_RUNTIME.counter_mode_step; - uint16_t m = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - if(flash_step % 2 == 0) { - setPixelColor(SEGMENT.start + n, WHITE); - setPixelColor(SEGMENT.start + m, WHITE); - delay = 20; - } else { - setPixelColor(SEGMENT.start + n, color_wheel(SEGMENT_RUNTIME.aux_param)); - setPixelColor(SEGMENT.start + m, BLACK); - delay = 30; - } - } else { - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - - if(SEGMENT_RUNTIME.counter_mode_step == 0) { - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); - } - } - return delay; + return chase_flash(color_wheel(_seg_rt->aux_param), WHITE); } @@ -1287,32 +1361,28 @@ uint16_t WS2812FX::mode_chase_flash_random(void) { * Alternating pixels running function. */ uint16_t WS2812FX::running(uint32_t color1, uint32_t color2) { - uint8_t size = 4 << SIZE_OPTION; - for(uint16_t i=0; i < SEGMENT_LENGTH; i++) { - if((i + SEGMENT_RUNTIME.counter_mode_step) % size < (size / 2)) { - if(IS_REVERSE) { - setPixelColor(SEGMENT.start + i, color1); - } else { - setPixelColor(SEGMENT.stop - i, color1); - } - } else { - if(IS_REVERSE) { - setPixelColor(SEGMENT.start + i, color2); - } else { - setPixelColor(SEGMENT.stop - i, color2); - } - } + uint8_t size = 2 << SIZE_OPTION; + uint32_t color = (_seg_rt->counter_mode_step & size) ? color1 : color2; + + if(IS_REVERSE) { + copyPixels(_seg->start, _seg->start + 1, _seg_len - 1); + setPixelColor(_seg->stop, color); + } else { + copyPixels(_seg->start + 1, _seg->start, _seg_len - 1); + setPixelColor(_seg->start, color); } - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % size; - return (SEGMENT.speed / SEGMENT_LENGTH); + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % _seg_len; + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; + return (_seg->speed / _seg_len); } + /* * Alternating color/white pixels running. */ uint16_t WS2812FX::mode_running_color(void) { - return running(SEGMENT.colors[0], WHITE); + return running(_seg->colors[0], _seg->colors[1]); } @@ -1343,23 +1413,14 @@ uint16_t WS2812FX::mode_halloween(void) { * Random colored pixels running. */ uint16_t WS2812FX::mode_running_random(void) { - if(IS_REVERSE) { - copyPixels(SEGMENT.start, SEGMENT.start + 1, SEGMENT_LENGTH - 1); - } else { - copyPixels(SEGMENT.start + 1, SEGMENT.start, SEGMENT_LENGTH - 1); + uint8_t size = 2 << SIZE_OPTION; + if((_seg_rt->counter_mode_step) % size == 0) { + _seg_rt->aux_param = get_random_wheel_index(_seg_rt->aux_param); } - if(SEGMENT_RUNTIME.counter_mode_step == 0) { - SEGMENT_RUNTIME.aux_param = get_random_wheel_index(SEGMENT_RUNTIME.aux_param); - if(IS_REVERSE) { - setPixelColor(SEGMENT.stop, color_wheel(SEGMENT_RUNTIME.aux_param)); - } else { - setPixelColor(SEGMENT.start, color_wheel(SEGMENT_RUNTIME.aux_param)); - } - } + uint32_t color = color_wheel(_seg_rt->aux_param); - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % (2 << SIZE_OPTION); - return (SEGMENT.speed / SEGMENT_LENGTH); + return running(color, color); } @@ -1369,30 +1430,28 @@ uint16_t WS2812FX::mode_running_random(void) { uint16_t WS2812FX::mode_larson_scanner(void) { fade_out(); - if(SEGMENT_RUNTIME.counter_mode_step < SEGMENT_LENGTH) { + if(_seg_rt->counter_mode_step < _seg_len) { if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - SEGMENT_RUNTIME.counter_mode_step, SEGMENT.colors[0]); + setPixelColor(_seg->stop - _seg_rt->counter_mode_step, _seg->colors[0]); } else { - setPixelColor(SEGMENT.start + SEGMENT_RUNTIME.counter_mode_step, SEGMENT.colors[0]); + setPixelColor(_seg->start + _seg_rt->counter_mode_step, _seg->colors[0]); } } else { - uint16_t index = (SEGMENT_LENGTH * 2) - SEGMENT_RUNTIME.counter_mode_step - 2; + uint16_t index = (_seg_len * 2) - _seg_rt->counter_mode_step - 2; if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - index, SEGMENT.colors[0]); + setPixelColor(_seg->stop - index, _seg->colors[0]); } else { - setPixelColor(SEGMENT.start + index, SEGMENT.colors[0]); + setPixelColor(_seg->start + index, _seg->colors[0]); } } - if(SEGMENT_RUNTIME.counter_mode_step % SEGMENT_LENGTH == 0) SET_CYCLE; - else CLR_CYCLE; - - SEGMENT_RUNTIME.counter_mode_step++; - if(SEGMENT_RUNTIME.counter_mode_step >= (uint16_t)((SEGMENT_LENGTH * 2) - 2)) { - SEGMENT_RUNTIME.counter_mode_step = 0; + _seg_rt->counter_mode_step++; + if(_seg_rt->counter_mode_step >= (uint16_t)((_seg_len * 2) - 2)) { + _seg_rt->counter_mode_step = 0; + SET_CYCLE; } - return (SEGMENT.speed / (SEGMENT_LENGTH * 2)); + return (_seg->speed / (_seg_len * 2)); } @@ -1403,13 +1462,15 @@ uint16_t WS2812FX::mode_comet(void) { fade_out(); if(IS_REVERSE) { - setPixelColor(SEGMENT.stop - SEGMENT_RUNTIME.counter_mode_step, SEGMENT.colors[0]); + setPixelColor(_seg->stop - _seg_rt->counter_mode_step, _seg->colors[0]); } else { - setPixelColor(SEGMENT.start + SEGMENT_RUNTIME.counter_mode_step, SEGMENT.colors[0]); + setPixelColor(_seg->start + _seg_rt->counter_mode_step, _seg->colors[0]); } - SEGMENT_RUNTIME.counter_mode_step = (SEGMENT_RUNTIME.counter_mode_step + 1) % SEGMENT_LENGTH; - return (SEGMENT.speed / SEGMENT_LENGTH); + _seg_rt->counter_mode_step = (_seg_rt->counter_mode_step + 1) % _seg_len; + if(_seg_rt->counter_mode_step == 0) SET_CYCLE; + + return (_seg->speed / _seg_len); } @@ -1422,8 +1483,8 @@ uint16_t WS2812FX::fireworks(uint32_t color) { // for better performance, manipulate the Adafruit_NeoPixels pixels[] array directly uint8_t *pixels = getPixels(); uint8_t bytesPerPixel = getNumBytesPerPixel(); // 3=RGB, 4=RGBW - uint16_t startPixel = SEGMENT.start * bytesPerPixel + bytesPerPixel; - uint16_t stopPixel = SEGMENT.stop * bytesPerPixel ; + uint16_t startPixel = _seg->start * bytesPerPixel + bytesPerPixel; + uint16_t stopPixel = _seg->stop * bytesPerPixel ; for(uint16_t i=startPixel; i > 2) + pixels[i] + @@ -1433,23 +1494,22 @@ uint16_t WS2812FX::fireworks(uint32_t color) { uint8_t size = 2 << SIZE_OPTION; if(!_triggered) { - for(uint16_t i=0; istart + random16(_seg_len - size); + fill(color, index, size); + SET_CYCLE; } } } else { - for(uint16_t i=0; istart + random16(_seg_len - size); + fill(color, index, size); + SET_CYCLE; } } - return (SEGMENT.speed / SEGMENT_LENGTH); + + return (_seg->speed / _seg_len); } /* @@ -1458,7 +1518,7 @@ uint16_t WS2812FX::fireworks(uint32_t color) { uint16_t WS2812FX::mode_fireworks(void) { uint32_t color = BLACK; do { // randomly choose a non-BLACK color from the colors array - color = SEGMENT.colors[random8(NUM_COLORS)]; + color = _seg->colors[random8(MAX_NUM_COLORS)]; } while (color == BLACK); return fireworks(color); } @@ -1475,16 +1535,18 @@ uint16_t WS2812FX::mode_fireworks_random(void) { * Fire flicker function */ uint16_t WS2812FX::fire_flicker(int rev_intensity) { - byte w = (SEGMENT.colors[0] >> 24) & 0xFF; - byte r = (SEGMENT.colors[0] >> 16) & 0xFF; - byte g = (SEGMENT.colors[0] >> 8) & 0xFF; - byte b = (SEGMENT.colors[0] & 0xFF); + byte w = (_seg->colors[0] >> 24) & 0xFF; + byte r = (_seg->colors[0] >> 16) & 0xFF; + byte g = (_seg->colors[0] >> 8) & 0xFF; + byte b = (_seg->colors[0] & 0xFF); byte lum = max(w, max(r, max(g, b))) / rev_intensity; - for(uint16_t i=SEGMENT.start; i <= SEGMENT.stop; i++) { + for(uint16_t i=_seg->start; i <= _seg->stop; i++) { int flicker = random8(lum); setPixelColor(i, max(r - flicker, 0), max(g - flicker, 0), max(b - flicker, 0), max(w - flicker, 0)); } - return (SEGMENT.speed / SEGMENT_LENGTH); + + SET_CYCLE; + return (_seg->speed / _seg_len); } /* @@ -1505,83 +1567,45 @@ uint16_t WS2812FX::mode_fire_flicker_soft(void) { * Random flickering, more intensity. */ uint16_t WS2812FX::mode_fire_flicker_intense(void) { - return fire_flicker(1.7); -} - - -/* - * Tricolor chase function - */ -uint16_t WS2812FX::tricolor_chase(uint32_t color1, uint32_t color2, uint32_t color3) { - uint8_t sizeCnt = 1 << SIZE_OPTION; - uint16_t index = SEGMENT_RUNTIME.counter_mode_call % (sizeCnt * 3); - for(uint16_t i=0; i < SEGMENT_LENGTH; i++, index++) { - index = index % (sizeCnt * 3); - - uint32_t color = color3; - if(index < sizeCnt) color = color1; - else if(index < (sizeCnt * 2)) color = color2; - - if(IS_REVERSE) { - setPixelColor(SEGMENT.start + i, color); - } else { - setPixelColor(SEGMENT.stop - i, color); - } - } - - return (SEGMENT.speed / SEGMENT_LENGTH); -} - - -/* - * Tricolor chase mode - */ -uint16_t WS2812FX::mode_tricolor_chase(void) { - return tricolor_chase(SEGMENT.colors[0], SEGMENT.colors[1], SEGMENT.colors[2]); + return fire_flicker(1); } -/* - * Alternating white/red/black pixels running. - */ -uint16_t WS2812FX::mode_circus_combustus(void) { - return tricolor_chase(RED, WHITE, BLACK); -} - /* * ICU mode */ uint16_t WS2812FX::mode_icu(void) { - uint16_t dest = SEGMENT_RUNTIME.counter_mode_step & 0xFFFF; + uint16_t dest = _seg_rt->counter_mode_step & 0xFFFF; - setPixelColor(SEGMENT.start + dest, SEGMENT.colors[0]); - setPixelColor(SEGMENT.start + dest + SEGMENT_LENGTH/2, SEGMENT.colors[0]); + setPixelColor(_seg->start + dest, _seg->colors[0]); + setPixelColor(_seg->start + dest + _seg_len/2, _seg->colors[0]); - if(SEGMENT_RUNTIME.aux_param3 == dest) { // pause between eye movements + if(_seg_rt->aux_param3 == dest) { // pause between eye movements if(random8(6) == 0) { // blink once in a while - setPixelColor(SEGMENT.start + dest, BLACK); - setPixelColor(SEGMENT.start + dest + SEGMENT_LENGTH/2, BLACK); + setPixelColor(_seg->start + dest, BLACK); + setPixelColor(_seg->start + dest + _seg_len/2, BLACK); return 200; } - SEGMENT_RUNTIME.aux_param3 = random16(SEGMENT_LENGTH/2); + _seg_rt->aux_param3 = random16(_seg_len/2); + SET_CYCLE; return 1000 + random16(2000); } - setPixelColor(SEGMENT.start + dest, BLACK); - setPixelColor(SEGMENT.start + dest + SEGMENT_LENGTH/2, BLACK); + setPixelColor(_seg->start + dest, BLACK); + setPixelColor(_seg->start + dest + _seg_len/2, BLACK); - if(SEGMENT_RUNTIME.aux_param3 > SEGMENT_RUNTIME.counter_mode_step) { - SEGMENT_RUNTIME.counter_mode_step++; + if(_seg_rt->aux_param3 > _seg_rt->counter_mode_step) { + _seg_rt->counter_mode_step++; dest++; - } else if (SEGMENT_RUNTIME.aux_param3 < SEGMENT_RUNTIME.counter_mode_step) { - SEGMENT_RUNTIME.counter_mode_step--; + } else if (_seg_rt->aux_param3 < _seg_rt->counter_mode_step) { + _seg_rt->counter_mode_step--; dest--; } - setPixelColor(SEGMENT.start + dest, SEGMENT.colors[0]); - setPixelColor(SEGMENT.start + dest + SEGMENT_LENGTH/2, SEGMENT.colors[0]); + setPixelColor(_seg->start + dest, _seg->colors[0]); + setPixelColor(_seg->start + dest + _seg_len/2, _seg->colors[0]); - return (SEGMENT.speed / SEGMENT_LENGTH); + return (_seg->speed / _seg_len); } /* @@ -1616,7 +1640,7 @@ uint16_t WS2812FX::mode_custom_8() { } uint16_t WS2812FX::mode_custom_9() { return customModes[9](); -} +} /* * Custom mode helpers */ diff --git a/Arduino/McLighting/WS2812FX.h b/Arduino/McLighting/WS2812FX.h index 5405457b..975681d7 100644 --- a/Arduino/McLighting/WS2812FX.h +++ b/Arduino/McLighting/WS2812FX.h @@ -45,6 +45,8 @@ #define DEFAULT_MODE (uint8_t)0 #define DEFAULT_SPEED (uint16_t)1000 #define DEFAULT_COLOR (uint32_t)0xFF0000 +#define DEFAULT_COLORS { RED, GREEN, BLUE } +#define COLORS(...) (const uint32_t[]){__VA_ARGS__} #if defined(ESP8266) || defined(ESP32) //#pragma message("Compiling for ESP") @@ -58,14 +60,13 @@ #define BRIGHTNESS_MIN (uint8_t)0 #define BRIGHTNESS_MAX (uint8_t)255 -/* each segment uses 36 bytes of SRAM memory, so if you're application fails because of - insufficient memory, decreasing MAX_NUM_SEGMENTS may help */ -#define MAX_NUM_SEGMENTS 10 -#define NUM_COLORS 3 /* number of colors per segment */ -#define MAX_CUSTOM_MODES 10 -#define SEGMENT _segments[_segment_index] -#define SEGMENT_RUNTIME _segment_runtimes[_segment_index] -#define SEGMENT_LENGTH (uint16_t)(SEGMENT.stop - SEGMENT.start + 1) +/* each segment uses 36 bytes of SRAM memory, so if you're compile fails + because of insufficient flash memory, decreasing MAX_NUM_SEGMENTS may help */ +#define MAX_NUM_SEGMENTS 10 +#define MAX_NUM_ACTIVE_SEGMENTS 10 +#define INACTIVE_SEGMENT 255 /* max uint_8 */ +#define MAX_NUM_COLORS 3 /* number of colors per segment */ +#define MAX_CUSTOM_MODES 10 // some common colors #define RED (uint32_t)0xFF0000 @@ -79,8 +80,11 @@ #define PURPLE (uint32_t)0x400080 #define ORANGE (uint32_t)0xFF3000 #define PINK (uint32_t)0xFF1493 +#define GRAY (uint32_t)0x101010 #define ULTRAWHITE (uint32_t)0xFFFFFFFF -#define DARK(c) (uint32_t)((c >> 4) & 0x0f0f0f0f) +#define DIM(c) (uint32_t)((c >> 2) & 0x3f3f3f3f) // color at 25% intensity +#define DARK(c) (uint32_t)((c >> 4) & 0x0f0f0f0f) // color at 6% intensity + // segment options // bit 7: reverse animation @@ -90,7 +94,7 @@ // bits 0: TBD #define NO_OPTIONS (uint8_t)B00000000 #define REVERSE (uint8_t)B10000000 -#define IS_REVERSE ((SEGMENT.options & REVERSE) == REVERSE) +#define IS_REVERSE ((_seg->options & REVERSE) == REVERSE) #define FADE_XFAST (uint8_t)B00010000 #define FADE_FAST (uint8_t)B00100000 #define FADE_MEDIUM (uint8_t)B00110000 @@ -98,22 +102,23 @@ #define FADE_XSLOW (uint8_t)B01010000 #define FADE_XXSLOW (uint8_t)B01100000 #define FADE_GLACIAL (uint8_t)B01110000 -#define FADE_RATE ((SEGMENT.options >> 4) & 7) +#define FADE_RATE ((_seg->options >> 4) & 7) #define GAMMA (uint8_t)B00001000 -#define IS_GAMMA ((SEGMENT.options & GAMMA) == GAMMA) +#define IS_GAMMA ((_seg->options & GAMMA) == GAMMA) #define SIZE_SMALL (uint8_t)B00000000 #define SIZE_MEDIUM (uint8_t)B00000010 #define SIZE_LARGE (uint8_t)B00000100 #define SIZE_XLARGE (uint8_t)B00000110 -#define SIZE_OPTION ((SEGMENT.options >> 1) & 3) +#define SIZE_OPTION ((_seg->options >> 1) & 3) // segment runtime options (aux_param2) -#define FRAME (uint8_t)B10000000 -#define SET_FRAME (SEGMENT_RUNTIME.aux_param2 |= FRAME) -#define CLR_FRAME (SEGMENT_RUNTIME.aux_param2 &= ~FRAME) -#define CYCLE (uint8_t)B01000000 -#define SET_CYCLE (SEGMENT_RUNTIME.aux_param2 |= CYCLE) -#define CLR_CYCLE (SEGMENT_RUNTIME.aux_param2 &= ~CYCLE) +#define FRAME (uint8_t)B10000000 +#define SET_FRAME (_seg_rt->aux_param2 |= FRAME) +#define CLR_FRAME (_seg_rt->aux_param2 &= ~FRAME) +#define CYCLE (uint8_t)B01000000 +#define SET_CYCLE (_seg_rt->aux_param2 |= CYCLE) +#define CLR_CYCLE (_seg_rt->aux_param2 &= ~CYCLE) +#define CLR_FRAME_CYCLE (_seg_rt->aux_param2 &= ~(FRAME | CYCLE)) #define MODE_COUNT (sizeof(_names)/sizeof(_names[0])) @@ -172,7 +177,7 @@ #define FX_MODE_HALLOWEEN 52 #define FX_MODE_BICOLOR_CHASE 53 #define FX_MODE_TRICOLOR_CHASE 54 -#define FX_MODE_ICU 55 +#define FX_MODE_ICU 55 #define FX_MODE_CUSTOM 56 // keep this for backward compatiblity #define FX_MODE_CUSTOM_0 56 // custom modes need to go at the end #define FX_MODE_CUSTOM_1 57 @@ -183,10 +188,11 @@ #define FX_MODE_CUSTOM_6 62 #define FX_MODE_CUSTOM_7 63 #define FX_MODE_CUSTOM_8 64 -#define FX_MODE_CUSTOM_9 65 +#define FX_MODE_CUSTOM_9 65 -// create GLOBAL names to allow WS2812FX to compile with sketches and other libs that store strings -// in PROGMEM (get rid of the "section type conflict with __c" errors once and for all. Amen.) +// create GLOBAL names to allow WS2812FX to compile with sketches and other libs +// that store strings in PROGMEM (get rid of the "section type conflict with __c" +// errors once and for all. Amen.) const char name_0[] PROGMEM = "Static"; const char name_1[] PROGMEM = "Blink"; const char name_2[] PROGMEM = "Breath"; @@ -320,25 +326,25 @@ static const __FlashStringHelper* _names[] = { FSH(name_62), FSH(name_63), FSH(name_64), - FSH(name_65) + FSH(name_65) }; class WS2812FX : public Adafruit_NeoPixel { - typedef uint16_t (WS2812FX::*mode_ptr)(void); - - // segment parameters public: + typedef uint16_t (WS2812FX::*mode_ptr)(void); + + // segment parameters typedef struct Segment { // 20 bytes uint16_t start; uint16_t stop; uint16_t speed; uint8_t mode; uint8_t options; - uint32_t colors[NUM_COLORS]; + uint32_t colors[MAX_NUM_COLORS]; } segment; - // segment runtime parameters + // segment runtime parameters typedef struct Segment_runtime { // 16 bytes unsigned long next_time; uint32_t counter_mode_step; @@ -348,91 +354,28 @@ class WS2812FX : public Adafruit_NeoPixel { uint16_t aux_param3; // auxilary param (usually stores a segment index) } segment_runtime; - WS2812FX(uint16_t n, uint8_t p, neoPixelType t) : Adafruit_NeoPixel(n, p, t) { - _mode[FX_MODE_STATIC] = &WS2812FX::mode_static; - _mode[FX_MODE_BLINK] = &WS2812FX::mode_blink; - _mode[FX_MODE_COLOR_WIPE] = &WS2812FX::mode_color_wipe; - _mode[FX_MODE_COLOR_WIPE_INV] = &WS2812FX::mode_color_wipe_inv; - _mode[FX_MODE_COLOR_WIPE_REV] = &WS2812FX::mode_color_wipe_rev; - _mode[FX_MODE_COLOR_WIPE_REV_INV] = &WS2812FX::mode_color_wipe_rev_inv; - _mode[FX_MODE_COLOR_WIPE_RANDOM] = &WS2812FX::mode_color_wipe_random; - _mode[FX_MODE_RANDOM_COLOR] = &WS2812FX::mode_random_color; - _mode[FX_MODE_SINGLE_DYNAMIC] = &WS2812FX::mode_single_dynamic; - _mode[FX_MODE_MULTI_DYNAMIC] = &WS2812FX::mode_multi_dynamic; - _mode[FX_MODE_RAINBOW] = &WS2812FX::mode_rainbow; - _mode[FX_MODE_RAINBOW_CYCLE] = &WS2812FX::mode_rainbow_cycle; - _mode[FX_MODE_SCAN] = &WS2812FX::mode_scan; - _mode[FX_MODE_DUAL_SCAN] = &WS2812FX::mode_dual_scan; - _mode[FX_MODE_FADE] = &WS2812FX::mode_fade; - _mode[FX_MODE_THEATER_CHASE] = &WS2812FX::mode_theater_chase; - _mode[FX_MODE_THEATER_CHASE_RAINBOW] = &WS2812FX::mode_theater_chase_rainbow; - _mode[FX_MODE_TWINKLE] = &WS2812FX::mode_twinkle; - _mode[FX_MODE_TWINKLE_RANDOM] = &WS2812FX::mode_twinkle_random; - _mode[FX_MODE_TWINKLE_FADE] = &WS2812FX::mode_twinkle_fade; - _mode[FX_MODE_TWINKLE_FADE_RANDOM] = &WS2812FX::mode_twinkle_fade_random; - _mode[FX_MODE_SPARKLE] = &WS2812FX::mode_sparkle; - _mode[FX_MODE_FLASH_SPARKLE] = &WS2812FX::mode_flash_sparkle; - _mode[FX_MODE_HYPER_SPARKLE] = &WS2812FX::mode_hyper_sparkle; - _mode[FX_MODE_STROBE] = &WS2812FX::mode_strobe; - _mode[FX_MODE_STROBE_RAINBOW] = &WS2812FX::mode_strobe_rainbow; - _mode[FX_MODE_MULTI_STROBE] = &WS2812FX::mode_multi_strobe; - _mode[FX_MODE_BLINK_RAINBOW] = &WS2812FX::mode_blink_rainbow; - _mode[FX_MODE_CHASE_WHITE] = &WS2812FX::mode_chase_white; - _mode[FX_MODE_CHASE_COLOR] = &WS2812FX::mode_chase_color; - _mode[FX_MODE_CHASE_RANDOM] = &WS2812FX::mode_chase_random; - _mode[FX_MODE_CHASE_RAINBOW] = &WS2812FX::mode_chase_rainbow; - _mode[FX_MODE_CHASE_FLASH] = &WS2812FX::mode_chase_flash; - _mode[FX_MODE_CHASE_FLASH_RANDOM] = &WS2812FX::mode_chase_flash_random; - _mode[FX_MODE_CHASE_RAINBOW_WHITE] = &WS2812FX::mode_chase_rainbow_white; - _mode[FX_MODE_CHASE_BLACKOUT] = &WS2812FX::mode_chase_blackout; - _mode[FX_MODE_CHASE_BLACKOUT_RAINBOW] = &WS2812FX::mode_chase_blackout_rainbow; - _mode[FX_MODE_COLOR_SWEEP_RANDOM] = &WS2812FX::mode_color_sweep_random; - _mode[FX_MODE_RUNNING_COLOR] = &WS2812FX::mode_running_color; - _mode[FX_MODE_RUNNING_RED_BLUE] = &WS2812FX::mode_running_red_blue; - _mode[FX_MODE_RUNNING_RANDOM] = &WS2812FX::mode_running_random; - _mode[FX_MODE_LARSON_SCANNER] = &WS2812FX::mode_larson_scanner; - _mode[FX_MODE_COMET] = &WS2812FX::mode_comet; - _mode[FX_MODE_FIREWORKS] = &WS2812FX::mode_fireworks; - _mode[FX_MODE_FIREWORKS_RANDOM] = &WS2812FX::mode_fireworks_random; - _mode[FX_MODE_MERRY_CHRISTMAS] = &WS2812FX::mode_merry_christmas; - _mode[FX_MODE_FIRE_FLICKER] = &WS2812FX::mode_fire_flicker; - _mode[FX_MODE_FIRE_FLICKER_SOFT] = &WS2812FX::mode_fire_flicker_soft; - _mode[FX_MODE_FIRE_FLICKER_INTENSE] = &WS2812FX::mode_fire_flicker_intense; - _mode[FX_MODE_CIRCUS_COMBUSTUS] = &WS2812FX::mode_circus_combustus; - _mode[FX_MODE_HALLOWEEN] = &WS2812FX::mode_halloween; - _mode[FX_MODE_BICOLOR_CHASE] = &WS2812FX::mode_bicolor_chase; - _mode[FX_MODE_TRICOLOR_CHASE] = &WS2812FX::mode_tricolor_chase; -// if flash memory is constrained (I'm looking at you Arduino Nano), replace modes -// that use a lot of flash with mode_static (reduces flash footprint by about 2100 bytes) -#ifdef REDUCED_MODES - _mode[FX_MODE_BREATH] = &WS2812FX::mode_static; - _mode[FX_MODE_RUNNING_LIGHTS] = &WS2812FX::mode_static; - _mode[FX_MODE_ICU] = &WS2812FX::mode_static; -#else - _mode[FX_MODE_BREATH] = &WS2812FX::mode_breath; - _mode[FX_MODE_RUNNING_LIGHTS] = &WS2812FX::mode_running_lights; - _mode[FX_MODE_ICU] = &WS2812FX::mode_icu; -#endif - _mode[FX_MODE_CUSTOM_0] = &WS2812FX::mode_custom_0; - _mode[FX_MODE_CUSTOM_1] = &WS2812FX::mode_custom_1; - _mode[FX_MODE_CUSTOM_2] = &WS2812FX::mode_custom_2; - _mode[FX_MODE_CUSTOM_3] = &WS2812FX::mode_custom_3; - _mode[FX_MODE_CUSTOM_4] = &WS2812FX::mode_custom_4; - _mode[FX_MODE_CUSTOM_5] = &WS2812FX::mode_custom_5; - _mode[FX_MODE_CUSTOM_6] = &WS2812FX::mode_custom_6; - _mode[FX_MODE_CUSTOM_7] = &WS2812FX::mode_custom_7; - _mode[FX_MODE_CUSTOM_8] = &WS2812FX::mode_custom_8; - _mode[FX_MODE_CUSTOM_9] = &WS2812FX::mode_custom_9; - + WS2812FX(uint16_t num_leds, uint8_t pin, neoPixelType type, + uint8_t max_num_segments=MAX_NUM_SEGMENTS, + uint8_t max_num_active_segments=MAX_NUM_ACTIVE_SEGMENTS) + : Adafruit_NeoPixel(num_leds, pin, type) { + brightness = DEFAULT_BRIGHTNESS + 1; // Adafruit_NeoPixel internally offsets brightness by 1 _running = false; - _num_segments = 1; - _segments[0].mode = DEFAULT_MODE; - _segments[0].colors[0] = DEFAULT_COLOR; - _segments[0].start = 0; - _segments[0].stop = n - 1; - _segments[0].speed = DEFAULT_SPEED; - resetSegmentRuntimes(); + + _segments_len = max_num_segments; + _active_segments_len = max_num_active_segments; + + // create all the segment arrays and init to zeros + _segments = new segment[_segments_len](); + _active_segments = new uint8_t[_active_segments_len](); + _segment_runtimes = new segment_runtime[_active_segments_len](); + + // init segment pointers + _seg = _segments; + _seg_rt = _segment_runtimes; + + resetSegments(); + setSegment(0, 0, num_leds - 1, DEFAULT_MODE, DEFAULT_COLOR, DEFAULT_SPEED, NO_OPTIONS); } void @@ -467,18 +410,25 @@ class WS2812FX : public Adafruit_NeoPixel { increaseLength(uint16_t s), decreaseLength(uint16_t s), trigger(void), + setCycle(void), setNumSegments(uint8_t n), setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, bool reverse), setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, uint8_t options), setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, bool reverse), setSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, uint8_t options), - resetSegments(), - resetSegmentRuntimes(), + setIdleSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, uint32_t color, uint16_t speed, uint8_t options), + setIdleSegment(uint8_t n, uint16_t start, uint16_t stop, uint8_t mode, const uint32_t colors[], uint16_t speed, uint8_t options), + addActiveSegment(uint8_t seg), + removeActiveSegment(uint8_t seg), + swapActiveSegment(uint8_t oldSeg, uint8_t newSeg), + resetSegments(void), + resetSegmentRuntimes(void), resetSegmentRuntime(uint8_t), setPixelColor(uint16_t n, uint32_t c), setPixelColor(uint16_t n, uint8_t r, uint8_t g, uint8_t b), setPixelColor(uint16_t n, uint8_t r, uint8_t g, uint8_t b, uint8_t w), copyPixels(uint16_t d, uint16_t s, uint16_t c), + setPixels(uint16_t, uint8_t*), show(void); boolean @@ -487,7 +437,8 @@ class WS2812FX : public Adafruit_NeoPixel { isFrame(void), isFrame(uint8_t), isCycle(void), - isCycle(uint8_t); + isCycle(uint8_t), + isActiveSegment(uint8_t seg); uint8_t random8(void), @@ -519,6 +470,7 @@ class WS2812FX : public Adafruit_NeoPixel { uint32_t* getColors(uint8_t); uint32_t* intensitySums(void); + uint8_t* getActiveSegments(void); const __FlashStringHelper* getModeName(uint8_t m); @@ -540,12 +492,15 @@ class WS2812FX : public Adafruit_NeoPixel { color_wipe(uint32_t, uint32_t, bool), twinkle(uint32_t, uint32_t), twinkle_fade(uint32_t), + sparkle(uint32_t, uint32_t), chase(uint32_t, uint32_t, uint32_t), + chase_flash(uint32_t, uint32_t), running(uint32_t, uint32_t), fireworks(uint32_t), fire_flicker(int), tricolor_chase(uint32_t, uint32_t, uint32_t), scan(uint32_t, uint32_t, bool); + uint32_t color_blend(uint32_t, uint32_t, uint8_t); @@ -616,7 +571,8 @@ class WS2812FX : public Adafruit_NeoPixel { mode_custom_6(void), mode_custom_7(void), mode_custom_8(void), - mode_custom_9(void); + mode_custom_9(void); + private: uint16_t _rand16seed; uint16_t (*customModes[MAX_CUSTOM_MODES])(void) { @@ -637,15 +593,89 @@ class WS2812FX : public Adafruit_NeoPixel { _running, _triggered; - mode_ptr _mode[MODE_COUNT]; // SRAM footprint: 4 bytes per element + segment* _segments; // array of segments (20 bytes per element) + segment_runtime* _segment_runtimes; // array of segment runtimes (16 bytes per element) + uint8_t* _active_segments; // array of active segments (1 bytes per element) + uint8_t _segments_len = 0; // size of _segments array + uint8_t _active_segments_len = 0; // size of _segments_runtime and _active_segments arrays + uint8_t _num_segments = 0; // number of configured segments in the _segments array uint8_t _segment_index = 0; - uint8_t _num_segments = 1; - segment _segments[MAX_NUM_SEGMENTS] = { // SRAM footprint: 20 bytes per element - // start, stop, speed, mode, options, color[] - { 0, 7, DEFAULT_SPEED, FX_MODE_STATIC, NO_OPTIONS, {DEFAULT_COLOR}} - }; - segment_runtime _segment_runtimes[MAX_NUM_SEGMENTS]; // SRAM footprint: 16 bytes per element + + segment* _seg; // currently active segment (20 bytes) + segment_runtime* _seg_rt; // currently active segment runtime (16 bytes) + + uint16_t _seg_len; // num LEDs in the currently active segment }; +// define static array of member function pointers. +// function pointers MUST be in the same order as the corresponding name in the _name array. +static WS2812FX::mode_ptr _modes[MODE_COUNT] = { + &WS2812FX::mode_static, + &WS2812FX::mode_blink, + &WS2812FX::mode_breath, + &WS2812FX::mode_color_wipe, + &WS2812FX::mode_color_wipe_inv, + &WS2812FX::mode_color_wipe_rev, + &WS2812FX::mode_color_wipe_rev_inv, + &WS2812FX::mode_color_wipe_random, + &WS2812FX::mode_random_color, + &WS2812FX::mode_single_dynamic, + &WS2812FX::mode_multi_dynamic, + &WS2812FX::mode_rainbow, + &WS2812FX::mode_rainbow_cycle, + &WS2812FX::mode_scan, + &WS2812FX::mode_dual_scan, + &WS2812FX::mode_fade, + &WS2812FX::mode_theater_chase, + &WS2812FX::mode_theater_chase_rainbow, + &WS2812FX::mode_running_lights, + &WS2812FX::mode_twinkle, + &WS2812FX::mode_twinkle_random, + &WS2812FX::mode_twinkle_fade, + &WS2812FX::mode_twinkle_fade_random, + &WS2812FX::mode_sparkle, + &WS2812FX::mode_flash_sparkle, + &WS2812FX::mode_hyper_sparkle, + &WS2812FX::mode_strobe, + &WS2812FX::mode_strobe_rainbow, + &WS2812FX::mode_multi_strobe, + &WS2812FX::mode_blink_rainbow, + &WS2812FX::mode_chase_white, + &WS2812FX::mode_chase_color, + &WS2812FX::mode_chase_random, + &WS2812FX::mode_chase_rainbow, + &WS2812FX::mode_chase_flash, + &WS2812FX::mode_chase_flash_random, + &WS2812FX::mode_chase_rainbow_white, + &WS2812FX::mode_chase_blackout, + &WS2812FX::mode_chase_blackout_rainbow, + &WS2812FX::mode_color_sweep_random, + &WS2812FX::mode_running_color, + &WS2812FX::mode_running_red_blue, + &WS2812FX::mode_running_random, + &WS2812FX::mode_larson_scanner, + &WS2812FX::mode_comet, + &WS2812FX::mode_fireworks, + &WS2812FX::mode_fireworks_random, + &WS2812FX::mode_merry_christmas, + &WS2812FX::mode_fire_flicker, + &WS2812FX::mode_fire_flicker_soft, + &WS2812FX::mode_fire_flicker_intense, + &WS2812FX::mode_circus_combustus, + &WS2812FX::mode_halloween, + &WS2812FX::mode_bicolor_chase, + &WS2812FX::mode_tricolor_chase, + &WS2812FX::mode_icu, + &WS2812FX::mode_custom_0, + &WS2812FX::mode_custom_1, + &WS2812FX::mode_custom_2, + &WS2812FX::mode_custom_3, + &WS2812FX::mode_custom_4, + &WS2812FX::mode_custom_5, + &WS2812FX::mode_custom_6, + &WS2812FX::mode_custom_7, + &WS2812FX::mode_custom_8, + &WS2812FX::mode_custom_9 +}; #endif diff --git a/Arduino/McLighting/data/index.htm b/Arduino/McLighting/data/index.htm index d601d0c1..7b1c6920 100644 --- a/Arduino/McLighting/data/index.htm +++ b/Arduino/McLighting/data/index.htm @@ -1602,8 +1602,9 @@

warning

else xhr.open("GET", url, true); xhr.send(post); } + function getModes() { - document.getElementById("percentage").innerHTML = "0%"; + document.getElementById("percentage").innerHTML = "0%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "0,100"); document.getElementById("modal-content").innerHTML = language.en.loadModes; xhttp("http://" + host + "/get_modes", false, function(e) { @@ -1611,7 +1612,7 @@

warning

if (e && e.substring(0,6) !== "ERROR!") { modes = JSON.parse(e); if (typeof modes[0] !== "undefined") { - modes.forEach(item => { + modes.forEach(item => { if (item.name && item.name.length > 0) { data.modes.push({ title: item.name, id: item.mode }); } @@ -1625,45 +1626,7 @@

warning

}); } -function getConfig() { - document.getElementById("percentage").innerHTML = "75%"; - document.getElementById("percentage-done").setAttribute("stroke-dasharray", "75,100"); - document.getElementById("modal-content").innerHTML = language.en.loadConfig; - xhttp("http://" + host + "/config", false, function(e) { - console.log("Getting config via REST:", e); - if (e && e.substring(0,6) !== "ERROR!") { - var res = JSON.parse(e); - if (res) { - if (typeof res.hostname !== "undefined") config.hostname = res.hostname; - if (typeof res.mqtt_host !== "undefined") config.mqtt_host = res.mqtt_host; - if (typeof res.mqtt_port !== "undefined") config.mqtt_port = res.mqtt_port; - if (typeof res.mqtt_user !== "undefined") config.mqtt_user = res.mqtt_user; - if (typeof res.mqtt_pass !== "undefined") config.mqtt_pass = res.mqtt_pass; - if (typeof res.ws_seg !== "undefined") config.ws_seg = res.ws_seg; - if (typeof res.ws_cnt !== "undefined") config.ws_cnt = res.ws_cnt; - if (typeof res.ws_rgbo !== "undefined") { - config.ws_rgbo = res.ws_rgbo; - config.enable_rgbw = config.ws_rgbo.includes("W"); - } - if (typeof res.ws_pin !== "undefined") config.ws_pin = res.ws_pin; - if (typeof res.ws_trans !== "undefined") config.ws_trans = res.ws_trans; - } - } else { - console.error(e); - document.getElementById("percentage").innerHTML = language.en.error; - showSnackbar(language.en.loadError, "error", 5000); - } - if (config.enable_rgbw) { - document.getElementById("white").parentNode.className = ""; - } else { - document.getElementById("white").parentNode.className = "hidden"; - white.value = 0; - segstate.color.w = 0; - segstate.color.w2 = 0; - segstate.color.w3 = 0; - } - }); -} + function showModes(mode, index) { //console.log("Mode: " + mode.title + " - ID: " + mode.id + " - Hidden: " + mode.hidden); var div = document.createElement("DIV"); @@ -1691,7 +1654,7 @@

warning

document.getElementById("modes").appendChild(div); } function readSettings() { - document.getElementById("percentage").innerHTML = "25%"; + document.getElementById("percentage").innerHTML = "33%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "25,100"); document.getElementById("modal-content").innerHTML = language.en.loadSettings; xhttp("http://" + host + "/uistate.json", false, function(e) { @@ -1711,6 +1674,7 @@

warning

} }); } + function applySettings() { // Make sure language contains all the words from English translation. if (settings.lang !== "en") { @@ -1723,6 +1687,7 @@

warning

translate(document.body); document.title = language[settings.lang].title; data.modes.forEach(mode => { + console.log("something"); mode.hidden = false; if (settings.visibility.indexOf(mode.id) > -1) { mode.hidden = true; @@ -2037,8 +2002,6 @@

warning

colmain.dispatchEvent(event); colfont.dispatchEvent(event); colback.dispatchEvent(event); - colbtn.dispatchEvent(event); - colbtns.dispatchEvent(event); document.getElementById("settings-open").addEventListener('click', ()=>{ var icons = document.getElementsByClassName("icon--link"); @@ -2159,7 +2122,7 @@

warning

function ws_connect() { data.connection = new ReconnectingWebSocket(ws_url, "arduino", ws_options); - document.getElementById("percentage").innerHTML = "75%"; + document.getElementById("percentage").innerHTML = "66%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "75,100"); document.getElementById("modal-content").innerHTML = language[settings.lang].loadWebsock; @@ -2167,14 +2130,10 @@

warning

data.connection.onopen = function() { console.log("WebSocket open"); data.is_connected = true; - data.refresh_interval = setInterval(() => ws_send("$"), 10000); var con = document.getElementById("disconnected"); con.className = "hidden"; con = document.getElementById("connected"); con.className = con.className = ""; - //setTimeout(function() { ws_send("$"); }, 2000); - //setTimeout(function() { ws_send("C"); }, 3000); - //setTimeout(function() { ws_send("~"); }, 4000); document.getElementById("percentage").innerHTML = "100%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "100,100"); document.getElementById("modal-content").innerHTML = language[settings.lang].loadReady; @@ -2205,6 +2164,7 @@

warning

// Log messages from the server data.connection.onmessage = function(e) { console.log("WebSocket from server: ", e.data); + console.log("data.init: ", data.init); try { var res = JSON.parse(e.data); // document.getElementById('modal').style.display = "none"; @@ -2311,10 +2271,9 @@

warning

// init display Colors displayColors(true); console.log("displayColors finished!"); - select_active_button(); - console.log("select_active_button finished!"); + select_active_button(); + console.log("select_active_button finished!"); } - console.log("data.init: ", data.init); if (data.init == true) { console.log("Initializing..."); // Set selected mode button @@ -2323,10 +2282,11 @@

warning

setTimeout(() => { document.getElementById('modal').style.display = "none"; document.getElementById('container').style.display = ""; - }, 500); + }, 50); initSettings(); initcolorSliders(); data.init = false; + data.refresh_interval = setInterval(() => ws_send("$"), 10000); } } catch (e) {} }; @@ -2361,7 +2321,7 @@

warning

function select_active_button() { btns = document.getElementsByClassName("btn"); - for (i = 0; i < btns.length; i++) { + for (i = 0; i < btns.length; i++) { btns[i].style.backgroundColor = settings.theme_btn; } if (state.mode != 1 || (state.mode == 1 && segstate.mode != 57)) { // CUSTOM WS MODE @@ -2374,8 +2334,9 @@

warning

segments.className = segments.className.replace(/\b hidden\b/g, ""); } if (state.mode >= 1) { - document.getElementById(segstate.mode).style.backgroundColor = settings.theme_btnsel; - if (segstate.mode == 56) { // AUTOPLAY + document.getElementById(segstate.mode).style.backgroundColor = settings.theme_btnsel; + document.getElementById("on").style.backgroundColor = settings.theme_btnsel; + if (segstate.mode == 56) { // AUTOPLAY disable_modebuttons(false); disable_color_selection(true); disable_bright_selection(false); @@ -2451,6 +2412,7 @@

warning

} select_active_button(); ws_send("/" + mode_id); + ws_send("$"); } function set_speed() { ws_send("?" + segstate.speed); @@ -2597,7 +2559,7 @@

warning

function drawCircle() { let radius = canvas.width / 2; let image = context.createImageData(2 * radius, 2 * radius); - let data = image.data; + let idata = image.data; for (let x = -radius; x < radius; x++) { for (let y = -radius; y < radius; y++) { @@ -2624,10 +2586,10 @@

warning

let [red, green, blue] = hsv2rgb(hue, saturation, value); let alpha = 255; - data[index] = red; - data[index + 1] = green; - data[index + 2] = blue; - data[index + 3] = alpha; + idata[index] = red; + idata[index + 1] = green; + idata[index + 2] = blue; + idata[index + 3] = alpha; } } this.context.putImageData(image, 0, 0); @@ -2682,14 +2644,16 @@

warning

document.addEventListener("DOMContentLoaded", function(event) { // Code to run since DOM is loaded and ready getModes(); - readSettings(); - ws_connect(); - ws_send("$"); - //ws_send("C"); - getConfig(); - canvas.width = 400; - canvas.height = 400; - redrawColorPicker(); + setTimeout(function() { + readSettings(); + }, 500); + setTimeout(function() { + ws_connect(); + ws_send("$"); + canvas.width = 400; + canvas.height = 400; + redrawColorPicker(); + }, 1000); }); diff --git a/Arduino/McLighting/data/index.htm.gz b/Arduino/McLighting/data/index.htm.gz index c85a898181e1a69bd15a16b59f36cc23e5c41ee4..c777c4195a0dcd966fa4512e816739b49a67183f 100644 GIT binary patch delta 8069 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 -#define index_htm_gz_len 20878 +#define index_htm_gz_len 20635 static const char index_htm_gz[] PROGMEM ={ - 0x1f, 0x8b, 0x08, 0x08, 0x15, 0xb1, 0x36, 0x5e, 0x04, 0x00, 0x69, 0x6e, + 0x1f, 0x8b, 0x08, 0x08, 0xc8, 0x7c, 0x95, 0x5f, 0x04, 0x00, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x00, 0xe4, 0x5d, 0x59, 0x77, 0x1b, 0x4b, 0x11, 0x7e, 0xe7, 0x1c, 0xfe, 0xc3, 0x5c, 0x05, 0x12, 0x09, 0x24, 0x59, 0x8b, 0x6d, 0x1c, 0x3b, 0xf2, 0x25, 0xc9, 0x75, 0x42, 0x20, @@ -1055,690 +1055,670 @@ static const char index_htm_gz[] PROGMEM ={ 0x29, 0x0d, 0xfd, 0x15, 0xb0, 0x3d, 0x7a, 0x04, 0x1a, 0x71, 0x52, 0xcd, 0x60, 0x36, 0x7f, 0xb1, 0x0c, 0x62, 0xa8, 0x04, 0x4e, 0xe3, 0x14, 0x2c, 0x2c, 0x59, 0x39, 0x9e, 0x0f, 0x06, 0x18, 0xf1, 0xff, 0x55, 0xde, 0x91, - 0x28, 0xb7, 0x52, 0xc3, 0x7e, 0x65, 0x09, 0xc7, 0xdb, 0x40, 0x92, 0x36, - 0xe9, 0x6b, 0x81, 0x17, 0x02, 0x03, 0xe5, 0x01, 0x8f, 0xe1, 0x1a, 0xfa, - 0xb8, 0xa6, 0xd3, 0xe9, 0xe4, 0xd8, 0xa6, 0x0b, 0x69, 0x12, 0x76, 0x37, - 0xb4, 0xa5, 0x94, 0xe1, 0x0f, 0xf9, 0x25, 0x24, 0xd9, 0x5e, 0xdf, 0xbb, - 0xde, 0xd0, 0x70, 0x76, 0xe0, 0x25, 0xb1, 0x25, 0x59, 0x96, 0x65, 0x59, - 0xbe, 0xe4, 0x17, 0x5a, 0x16, 0x32, 0xfc, 0x74, 0xd2, 0xa9, 0x15, 0x4e, - 0x5b, 0x21, 0xff, 0xf4, 0xcb, 0x2f, 0x3f, 0xff, 0xf2, 0x85, 0xc8, 0x7a, - 0x4a, 0x8b, 0x95, 0x67, 0x94, 0x75, 0xaf, 0x2c, 0x66, 0x63, 0x2b, 0xb7, - 0xa9, 0xbd, 0xe8, 0xf2, 0x7f, 0xeb, 0x8b, 0xcf, 0x31, 0xee, 0x4f, 0x44, - 0x1a, 0x50, 0x64, 0xd2, 0xff, 0x26, 0xce, 0x24, 0xd8, 0x87, 0x4f, 0x5d, - 0x50, 0x04, 0x80, 0x4a, 0x4b, 0x64, 0x4d, 0xaf, 0x78, 0x9e, 0x14, 0x14, - 0x2d, 0x55, 0xb6, 0xbd, 0x77, 0xfb, 0x6a, 0x9d, 0x64, 0x53, 0xf8, 0x01, - 0xbe, 0x93, 0xb9, 0x7f, 0xb5, 0xff, 0x72, 0x6b, 0x18, 0x8c, 0xdc, 0x9d, - 0xad, 0x96, 0x48, 0x01, 0xfc, 0xaf, 0x77, 0x8b, 0x22, 0x4b, 0x27, 0x9b, - 0x22, 0xa1, 0x33, 0xfd, 0xab, 0x1f, 0x20, 0x6f, 0x9c, 0x5f, 0x8e, 0xb3, - 0x0c, 0x2f, 0x34, 0x00, 0xd9, 0x4e, 0x1f, 0xce, 0xf7, 0xb4, 0xeb, 0x48, - 0xc3, 0x21, 0x94, 0xf1, 0xa2, 0xcb, 0xd5, 0xc0, 0x60, 0x4d, 0x78, 0x7b, - 0x3d, 0xf0, 0x12, 0xca, 0xc8, 0xb0, 0x8c, 0x20, 0xef, 0x56, 0x2d, 0xfc, - 0xd7, 0x38, 0x50, 0xb7, 0x07, 0x45, 0x9c, 0x5f, 0x21, 0x28, 0xb0, 0xc1, - 0xce, 0xe4, 0xc8, 0x4e, 0x92, 0x90, 0xa4, 0x9c, 0x6f, 0xfb, 0x7d, 0x08, - 0x2e, 0xa5, 0x7c, 0xa4, 0x6c, 0x91, 0x02, 0xb5, 0x9f, 0xd2, 0x31, 0xbc, - 0x78, 0x76, 0xf2, 0xfc, 0x09, 0x50, 0xb2, 0x56, 0x1b, 0x12, 0x54, 0x73, - 0x98, 0x39, 0x6d, 0x26, 0xec, 0x4a, 0x03, 0x2c, 0xa9, 0x1f, 0xb5, 0xa9, - 0x07, 0x70, 0xdd, 0x69, 0x59, 0xaa, 0x4f, 0xa4, 0xa1, 0x62, 0x1f, 0x9f, - 0x7c, 0xfe, 0x59, 0x6f, 0x3d, 0xce, 0xe8, 0x7a, 0xbe, 0xa3, 0x3b, 0xf1, - 0xab, 0x11, 0x57, 0x7c, 0xa7, 0x84, 0x88, 0xca, 0x98, 0x2d, 0x06, 0x5d, - 0xab, 0x80, 0xf2, 0x72, 0x3f, 0x8c, 0x45, 0x57, 0x60, 0x53, 0x9d, 0xd0, - 0xb2, 0x34, 0x02, 0xeb, 0x2d, 0xc7, 0x57, 0x54, 0xa1, 0xf2, 0x07, 0xbf, - 0x5e, 0x24, 0xdf, 0x44, 0xac, 0xf8, 0xa3, 0x15, 0x0f, 0x2a, 0x9b, 0xdd, - 0xb2, 0xba, 0xe3, 0x51, 0x92, 0x25, 0xb5, 0x4e, 0x94, 0xce, 0xd8, 0x4f, - 0x82, 0x43, 0x63, 0xea, 0x27, 0x09, 0x2a, 0xee, 0x4c, 0x6e, 0xdc, 0xd1, - 0x45, 0xfb, 0xf2, 0x20, 0x10, 0xc1, 0x2f, 0x36, 0x4a, 0x7d, 0xf7, 0x6b, - 0x24, 0x23, 0x6a, 0x50, 0xcc, 0x2f, 0x57, 0xd7, 0x27, 0x4b, 0xb0, 0x1f, - 0x93, 0x71, 0x16, 0xab, 0xc0, 0x65, 0xe0, 0xdd, 0x4e, 0x24, 0x8e, 0xc6, - 0xc2, 0x74, 0x77, 0x7f, 0xdf, 0x65, 0x4b, 0x30, 0xcd, 0xea, 0xe7, 0x2c, - 0x6e, 0xf0, 0x9f, 0xea, 0xe8, 0xaf, 0x1f, 0xee, 0xa6, 0xa7, 0xbf, 0x7e, - 0xf8, 0xf0, 0x5d, 0x9d, 0x55, 0xb7, 0xbe, 0xaf, 0x4f, 0x09, 0x6e, 0xbb, - 0x8e, 0xce, 0x70, 0x1f, 0xbc, 0x93, 0x53, 0x38, 0xa7, 0xa0, 0x6e, 0x0e, - 0x50, 0x12, 0xdb, 0x6d, 0x02, 0x00, 0xa4, 0x3c, 0x9b, 0x1c, 0x59, 0x76, - 0x80, 0x57, 0x41, 0x42, 0x8c, 0x34, 0x84, 0x61, 0x2d, 0xe9, 0xf2, 0x48, - 0xad, 0x97, 0xb4, 0x84, 0x18, 0xe9, 0x18, 0x81, 0xc4, 0xd7, 0xab, 0xcc, - 0x4f, 0x5c, 0x42, 0x8c, 0x34, 0x8c, 0x50, 0xe2, 0x78, 0xca, 0xd7, 0x4b, - 0x5c, 0x42, 0x8c, 0x74, 0x8c, 0x40, 0xe2, 0x78, 0x5c, 0xd8, 0x4b, 0x5c, - 0x42, 0x8c, 0x74, 0x8c, 0x7a, 0xe2, 0xec, 0xdc, 0x31, 0xa4, 0xfb, 0x88, - 0x0b, 0x88, 0x91, 0x02, 0x1e, 0x44, 0x76, 0xba, 0x2c, 0xaa, 0xc9, 0x12, - 0xc4, 0x48, 0x82, 0x07, 0xc8, 0x99, 0x9f, 0x82, 0x8e, 0xa2, 0xf0, 0x41, - 0x88, 0x17, 0x27, 0x31, 0x47, 0x2a, 0xa5, 0x61, 0x35, 0x96, 0x72, 0x7a, - 0x1a, 0xf0, 0x74, 0x52, 0x60, 0x31, 0xa6, 0x8b, 0x0d, 0xfa, 0x3b, 0xad, - 0x6f, 0xc8, 0xdc, 0x04, 0x0c, 0x1c, 0x76, 0x75, 0xd6, 0xe9, 0xb2, 0x5a, - 0x4a, 0x04, 0x31, 0x52, 0xc0, 0x83, 0xa4, 0x44, 0x27, 0xc1, 0xbd, 0x64, - 0x25, 0xc4, 0x48, 0x43, 0xf8, 0x5f, 0x8c, 0x68, 0x42, 0x60, 0x76, 0x13, - 0x83, 0x12, 0x05, 0x56, 0x80, 0x66, 0xd6, 0xc0, 0x3b, 0x98, 0x53, 0x48, - 0xc3, 0x33, 0x24, 0xda, 0xa1, 0x8d, 0x16, 0x8e, 0x6c, 0xf5, 0xb3, 0x87, - 0xad, 0xc9, 0xb3, 0x47, 0xaf, 0xd5, 0x42, 0xdc, 0xfb, 0x56, 0xfb, 0x36, - 0x84, 0xb5, 0xf3, 0x13, 0x08, 0x36, 0x08, 0x84, 0x3b, 0x30, 0xe0, 0xee, - 0xdd, 0x4b, 0xe8, 0xd4, 0x92, 0x6c, 0xb6, 0x80, 0x1e, 0x58, 0x27, 0xa2, - 0x07, 0xb0, 0xcb, 0x06, 0xd8, 0xdb, 0xd3, 0xc6, 0x48, 0x04, 0x7c, 0x12, - 0xe1, 0x50, 0x8b, 0xc0, 0x3d, 0x72, 0xe7, 0x70, 0xc0, 0x8d, 0xba, 0xd1, - 0xb3, 0xf7, 0x95, 0x8c, 0x74, 0xc6, 0x53, 0x3f, 0x22, 0x01, 0x29, 0x39, - 0x4c, 0x62, 0x6d, 0xe5, 0x38, 0x10, 0xbe, 0x5c, 0x3e, 0x12, 0x4d, 0x20, - 0xe2, 0x44, 0xf2, 0x56, 0x88, 0x5b, 0xef, 0x3f, 0xfb, 0xba, 0xa5, 0x42, - 0xe7, 0xeb, 0x65, 0x05, 0xf4, 0xc9, 0x17, 0xef, 0x7e, 0xa6, 0x81, 0xa7, - 0xd3, 0x55, 0x05, 0xf8, 0x33, 0x0d, 0x76, 0x52, 0x54, 0x91, 0x7e, 0xef, - 0xab, 0xe7, 0xcf, 0x3f, 0xd7, 0x89, 0x4f, 0x1a, 0x71, 0x5e, 0xdc, 0x14, - 0x36, 0x34, 0x4c, 0x9c, 0x49, 0xad, 0x62, 0x43, 0x9e, 0xb1, 0x21, 0xca, - 0xb6, 0x20, 0x85, 0x85, 0xe2, 0x25, 0xfd, 0x04, 0x4e, 0x3b, 0xe2, 0xb1, - 0xa9, 0x18, 0xc8, 0x2a, 0x59, 0xba, 0x7a, 0x6a, 0x2f, 0xb5, 0x73, 0x20, - 0x48, 0xd3, 0xf0, 0x01, 0xa9, 0xad, 0x64, 0x81, 0xf5, 0x42, 0x54, 0xf1, - 0x06, 0xbc, 0xcc, 0x41, 0x46, 0x46, 0x82, 0x25, 0x99, 0x4c, 0x01, 0xc5, - 0xe0, 0x62, 0x0f, 0xe4, 0x59, 0x9b, 0x38, 0x08, 0x1c, 0x73, 0x0c, 0xdc, - 0xca, 0x91, 0x58, 0x3a, 0x9b, 0xc9, 0x22, 0xf9, 0x89, 0xd6, 0x4a, 0xba, - 0x47, 0x90, 0xa9, 0x16, 0xea, 0x3d, 0xe1, 0x59, 0x2e, 0xf4, 0x97, 0xf7, - 0x90, 0x38, 0x12, 0x34, 0xb8, 0x4e, 0x1c, 0x12, 0x96, 0x90, 0x0a, 0xc4, - 0xe9, 0x6d, 0x7d, 0xf3, 0x35, 0x7a, 0x89, 0xa6, 0xd9, 0xbf, 0x58, 0x51, - 0x56, 0x5a, 0x04, 0xa0, 0xc9, 0x77, 0xf4, 0x4e, 0xd4, 0xa2, 0x5d, 0x93, - 0xf3, 0xc9, 0xea, 0xe6, 0x1c, 0x36, 0xae, 0x80, 0x62, 0xc2, 0xdf, 0xe8, - 0x8f, 0x9e, 0x28, 0x79, 0x0a, 0x59, 0x9f, 0x80, 0x8a, 0xd5, 0x7c, 0xbe, - 0x48, 0x58, 0xa7, 0xa3, 0xc5, 0x14, 0x29, 0x21, 0x54, 0x72, 0xaf, 0x9d, - 0xa1, 0x6c, 0xbd, 0x09, 0xa1, 0x94, 0xd2, 0xcb, 0x36, 0xb4, 0x03, 0x40, - 0x7d, 0x59, 0x93, 0x42, 0xcd, 0xd2, 0xcb, 0xbb, 0x58, 0x24, 0x37, 0xd1, - 0x4d, 0xde, 0x1f, 0x44, 0xf9, 0xd5, 0x51, 0x74, 0x35, 0x7b, 0x1c, 0x2d, - 0xe0, 0x00, 0xc8, 0xcd, 0x62, 0x80, 0x6a, 0x19, 0xfb, 0x85, 0x13, 0xb1, - 0x44, 0x12, 0x46, 0x90, 0xe7, 0x9f, 0xc0, 0x85, 0x46, 0x8d, 0x2b, 0x60, - 0xc5, 0xb4, 0x50, 0x59, 0x52, 0x3e, 0xca, 0xf2, 0xe7, 0x96, 0x34, 0x06, - 0x3b, 0x9a, 0xe9, 0x0c, 0x76, 0x30, 0xd3, 0xe1, 0x15, 0x0e, 0x58, 0xd7, - 0xd8, 0xa4, 0xcc, 0xee, 0x7f, 0x9f, 0xaf, 0x96, 0xcd, 0x66, 0x3c, 0xf8, - 0x28, 0x4c, 0x24, 0xe3, 0xc4, 0x9b, 0x13, 0x9d, 0xe2, 0x6a, 0x2d, 0x2f, - 0x1e, 0x86, 0xcd, 0x79, 0xde, 0xd1, 0x27, 0x37, 0xa0, 0x06, 0x77, 0xf7, - 0xfa, 0x1a, 0xec, 0x97, 0xec, 0xdc, 0x64, 0xf9, 0x50, 0x7f, 0x59, 0xc2, - 0x75, 0x5a, 0x5c, 0xb2, 0xb8, 0xf2, 0x11, 0xc8, 0x3d, 0x97, 0x48, 0x17, - 0xd0, 0xe1, 0x63, 0x7e, 0x0b, 0x12, 0x46, 0xa7, 0x12, 0xa3, 0xed, 0x5a, - 0xbf, 0x7b, 0x41, 0xe4, 0x9a, 0x91, 0x8e, 0x21, 0xbd, 0x4d, 0x5e, 0x17, - 0xe4, 0x6e, 0x12, 0xef, 0xe2, 0x4a, 0xac, 0x54, 0x1a, 0x77, 0x13, 0xcf, - 0xda, 0xb6, 0xeb, 0xa6, 0xe5, 0x83, 0x64, 0x4c, 0x14, 0xb7, 0xa7, 0x43, - 0x81, 0x55, 0x4a, 0x35, 0x7e, 0x80, 0x09, 0x25, 0x5f, 0x78, 0x94, 0x4f, - 0xd5, 0x7e, 0xc6, 0xd6, 0xfc, 0x6a, 0x3d, 0x1e, 0xa1, 0x03, 0xf8, 0x7c, - 0x0e, 0x5f, 0xd0, 0x8c, 0x16, 0xc6, 0xd3, 0xf8, 0x9a, 0x2e, 0xd8, 0xaf, - 0x0a, 0x40, 0x31, 0x01, 0xae, 0x85, 0x51, 0x65, 0xe9, 0x53, 0x44, 0x9f, - 0x8a, 0x73, 0x0d, 0xa5, 0xde, 0x53, 0xd3, 0x8c, 0x53, 0xf0, 0x84, 0xf1, - 0x02, 0x0e, 0x58, 0xf5, 0x08, 0x5f, 0x0d, 0xc9, 0xa3, 0x8b, 0x6c, 0x75, - 0x15, 0x3d, 0x5d, 0xce, 0x61, 0xe1, 0xed, 0x52, 0x3c, 0x1c, 0x84, 0xc4, - 0x7b, 0x72, 0x65, 0x55, 0xdb, 0xf4, 0x65, 0x32, 0x4b, 0x96, 0x28, 0x2f, - 0x5b, 0x87, 0x88, 0x28, 0x28, 0x91, 0xda, 0xdd, 0xdc, 0x7a, 0xa4, 0x00, - 0x98, 0xaa, 0x84, 0x34, 0xdc, 0xba, 0x64, 0x7b, 0x4c, 0x04, 0xeb, 0xd5, - 0x36, 0xef, 0xc6, 0x35, 0xa2, 0x81, 0xea, 0x8d, 0x4c, 0xd5, 0xab, 0x84, - 0xd7, 0xad, 0x08, 0xa5, 0x99, 0xba, 0x28, 0x3f, 0x84, 0x28, 0x93, 0xb8, - 0x34, 0x57, 0x93, 0xd5, 0xec, 0xd6, 0xb4, 0x61, 0xdc, 0x25, 0x19, 0xf9, - 0x4a, 0x66, 0xf9, 0x80, 0x24, 0xd7, 0xfb, 0xb4, 0xb5, 0x46, 0xfc, 0x65, - 0xac, 0x35, 0x6a, 0x83, 0x07, 0x99, 0x2b, 0x81, 0x6f, 0x35, 0xa8, 0xbc, - 0x46, 0xdc, 0x23, 0xb7, 0xf4, 0xf3, 0x8b, 0xd2, 0x9d, 0x80, 0x05, 0xc8, - 0x6e, 0x5f, 0x36, 0x9d, 0x93, 0x76, 0x91, 0x39, 0x5a, 0x87, 0x56, 0xf8, - 0x5f, 0x82, 0x22, 0x68, 0xad, 0x9f, 0xb1, 0xcb, 0xbd, 0xde, 0x0e, 0xe1, - 0xbb, 0x67, 0x2a, 0x86, 0x9f, 0xac, 0xed, 0xfe, 0xd8, 0xcd, 0x2e, 0x25, - 0x61, 0xf4, 0x09, 0xbd, 0x13, 0x69, 0x7b, 0x3d, 0x20, 0xb2, 0xab, 0xf7, - 0x01, 0x8f, 0x6f, 0xf8, 0x7c, 0xc0, 0x7f, 0xc6, 0x9a, 0xc7, 0xb9, 0x58, - 0x4d, 0x78, 0xfe, 0x7b, 0xf0, 0x35, 0x3e, 0x25, 0x73, 0xcb, 0x4c, 0x46, - 0x7a, 0x71, 0x5b, 0x4a, 0xae, 0x7d, 0xd6, 0x89, 0xee, 0xd8, 0x45, 0xeb, - 0x47, 0xd8, 0x0b, 0x53, 0x76, 0x9f, 0x7d, 0x0f, 0xc7, 0x88, 0x47, 0x82, - 0xe7, 0xb2, 0x44, 0x3e, 0x00, 0xc7, 0x8f, 0x04, 0xfa, 0xa3, 0x0e, 0x95, - 0xd4, 0x89, 0x1e, 0x69, 0xa3, 0x0b, 0x9d, 0x4f, 0x70, 0xce, 0x0b, 0x4e, - 0xd8, 0xd5, 0x53, 0x1a, 0x43, 0x04, 0xd5, 0x76, 0xfd, 0xd0, 0x95, 0x80, - 0xe9, 0x52, 0x30, 0x8c, 0x51, 0xeb, 0x21, 0x2c, 0xa4, 0xc2, 0xe2, 0x57, - 0xc7, 0xc7, 0x4f, 0x4f, 0x4e, 0x8c, 0x06, 0x40, 0x3b, 0xd7, 0x91, 0x43, - 0x4a, 0xc8, 0x2c, 0xd7, 0xec, 0x01, 0x34, 0x66, 0x81, 0x17, 0x90, 0xb3, - 0x8d, 0x27, 0xa0, 0x78, 0x40, 0xf3, 0xdd, 0xc6, 0xd6, 0xba, 0xec, 0x42, - 0x20, 0x16, 0xe6, 0x3c, 0x8b, 0xfe, 0x11, 0x6c, 0xd2, 0xd9, 0xfc, 0x9f, - 0x09, 0xc4, 0x51, 0xd3, 0xed, 0xeb, 0x17, 0x38, 0xa5, 0x37, 0x87, 0x00, - 0xdd, 0xcb, 0x4d, 0xd8, 0xb1, 0x22, 0xbb, 0xa3, 0xbe, 0xa0, 0xfc, 0x2c, - 0xb7, 0xc1, 0xbc, 0xfe, 0x78, 0x73, 0x37, 0x1c, 0xbb, 0xce, 0x7a, 0x85, - 0x5e, 0x4c, 0x88, 0x69, 0x51, 0x36, 0xed, 0x54, 0xc6, 0x40, 0xff, 0x90, - 0x88, 0x65, 0x78, 0x9c, 0x34, 0x73, 0xec, 0x73, 0x49, 0x0c, 0xf0, 0x9d, - 0xa8, 0xaf, 0xdf, 0x32, 0x21, 0xc2, 0x36, 0x5d, 0x34, 0xf6, 0x21, 0x94, - 0x71, 0x27, 0xc5, 0x64, 0xf5, 0xde, 0xd9, 0x29, 0xd9, 0xdc, 0x9b, 0x76, - 0x57, 0x72, 0x9a, 0x81, 0xbb, 0xe8, 0xb5, 0xad, 0x63, 0x61, 0xab, 0xe5, - 0x89, 0x78, 0x21, 0x0a, 0x76, 0xbf, 0x61, 0x75, 0x66, 0x01, 0xa7, 0xa0, - 0x4a, 0xb6, 0xcc, 0x53, 0xac, 0x11, 0xcb, 0xe7, 0x8c, 0x68, 0xe5, 0xe7, - 0x44, 0x26, 0x99, 0xf1, 0x48, 0x02, 0xc0, 0x00, 0x07, 0x96, 0x36, 0x33, - 0x3a, 0x01, 0x0d, 0x8c, 0x74, 0x40, 0x7e, 0xd4, 0x51, 0xd9, 0x04, 0x87, - 0x52, 0x1c, 0x3e, 0x75, 0xfe, 0xde, 0xed, 0xb1, 0x98, 0xb3, 0xc4, 0x2d, - 0xc6, 0x12, 0x05, 0x95, 0x38, 0x5f, 0x24, 0x73, 0xb0, 0x47, 0xc2, 0x1f, - 0x97, 0x83, 0x7f, 0x4a, 0x4b, 0x22, 0xf0, 0xf1, 0x56, 0x74, 0xc3, 0xf7, - 0xb1, 0xe0, 0x17, 0xc4, 0xc9, 0x53, 0x65, 0x7e, 0x73, 0x9a, 0x9e, 0xa9, - 0x93, 0x21, 0x4a, 0x70, 0x5f, 0xfc, 0x91, 0xf3, 0xd6, 0x37, 0xf9, 0xe5, - 0x1f, 0x99, 0x72, 0xd0, 0x32, 0x1a, 0x07, 0x6a, 0x51, 0x7f, 0xa9, 0xd1, - 0x96, 0xd1, 0x8d, 0xce, 0x4b, 0x1d, 0x23, 0x07, 0x16, 0x23, 0x6f, 0xb6, - 0x54, 0x71, 0x27, 0xfc, 0x1e, 0x38, 0x7b, 0x21, 0x2b, 0x1a, 0x2f, 0x67, - 0xe5, 0x31, 0xb6, 0x62, 0x65, 0x34, 0x04, 0x60, 0xe9, 0x57, 0x52, 0x8c, - 0x35, 0xa6, 0xd3, 0x56, 0x86, 0xfc, 0x72, 0x0d, 0x81, 0x7e, 0xd1, 0x87, - 0x8e, 0xc9, 0x7f, 0xd0, 0xfc, 0xef, 0x4c, 0xbd, 0x9b, 0xe1, 0x25, 0x32, - 0x0f, 0x23, 0x32, 0x01, 0x6c, 0x2f, 0x8d, 0x49, 0x18, 0x0d, 0x5c, 0x94, - 0xf3, 0x13, 0xb9, 0x0e, 0x23, 0xe2, 0x3b, 0x68, 0xe3, 0x3f, 0x98, 0x62, - 0x1f, 0x4a, 0xb9, 0x37, 0xce, 0x0a, 0x3a, 0x9d, 0x64, 0x18, 0x2b, 0x4a, - 0xb7, 0x8b, 0x9a, 0x47, 0xfc, 0xe0, 0xed, 0x24, 0x7b, 0x08, 0x66, 0x54, - 0xa9, 0x97, 0x40, 0xb4, 0xba, 0x04, 0x1d, 0x4e, 0x51, 0xfd, 0x61, 0x2a, - 0xdf, 0xe9, 0x08, 0x9b, 0x5e, 0x30, 0x62, 0xba, 0xbd, 0x60, 0xa4, 0x4b, - 0x91, 0xef, 0xaa, 0x96, 0xd3, 0xe0, 0xad, 0xba, 0x67, 0x72, 0x39, 0x0d, - 0xff, 0x38, 0x8e, 0x31, 0xdf, 0xa6, 0xc6, 0x6a, 0x75, 0x88, 0x51, 0x1b, - 0xd8, 0x39, 0x85, 0x3e, 0x45, 0xd8, 0xb3, 0x5e, 0xf9, 0x60, 0xaf, 0xc4, - 0x22, 0x10, 0x6d, 0xb9, 0x81, 0x91, 0x31, 0xba, 0x2a, 0x41, 0x09, 0x2d, - 0xd1, 0x46, 0xc3, 0xa1, 0x04, 0x68, 0x74, 0x90, 0x7b, 0x06, 0x7d, 0x6b, - 0x75, 0x95, 0x14, 0x97, 0x40, 0x29, 0xba, 0x4c, 0xb2, 0xc4, 0xf0, 0x1e, - 0x69, 0x6a, 0x92, 0xf3, 0xa8, 0x4a, 0x55, 0x2d, 0xc9, 0x81, 0x64, 0x53, - 0x4a, 0x34, 0xc1, 0x31, 0xe8, 0xaa, 0x99, 0xd5, 0x80, 0x57, 0xda, 0x57, - 0x02, 0x5f, 0xd0, 0x20, 0x2b, 0x4a, 0xf3, 0x97, 0x68, 0x57, 0x48, 0x6e, - 0x3f, 0xfa, 0xeb, 0xc3, 0x61, 0x64, 0x75, 0x44, 0x82, 0xa0, 0x6d, 0xee, - 0x65, 0xea, 0x60, 0x4d, 0x6a, 0x66, 0x6d, 0x8a, 0x1a, 0x65, 0x0d, 0x6d, - 0x21, 0xb4, 0x8e, 0x2f, 0xc1, 0x26, 0x98, 0x98, 0x6d, 0x57, 0x65, 0xe5, - 0x86, 0x68, 0x45, 0x6d, 0x4b, 0x20, 0x51, 0x5d, 0x89, 0x66, 0xd6, 0xb7, - 0xcc, 0x30, 0x01, 0x9b, 0xd7, 0x58, 0x65, 0x4d, 0x92, 0xf1, 0xd7, 0xf9, - 0x0a, 0x2b, 0x6d, 0x21, 0xfb, 0x6b, 0x0d, 0x3b, 0xb3, 0xf5, 0xb5, 0x06, - 0x20, 0x59, 0x6b, 0x91, 0x62, 0xd7, 0x5a, 0x64, 0x18, 0x80, 0xdb, 0xd6, - 0x9a, 0xb3, 0x26, 0xbe, 0x57, 0xd6, 0x7a, 0x0d, 0xb5, 0x36, 0x91, 0xfd, - 0xb5, 0xa6, 0x2d, 0xe3, 0xda, 0x5a, 0x23, 0x90, 0xac, 0xb5, 0x48, 0xb1, - 0x6a, 0x2d, 0x32, 0x4c, 0xc0, 0x2d, 0x6b, 0xcd, 0x58, 0x93, 0x64, 0xaa, - 0x6a, 0xbd, 0x81, 0x5a, 0x5b, 0xc8, 0x15, 0x6d, 0x0d, 0xde, 0x47, 0x6d, - 0xad, 0x11, 0x48, 0xd6, 0x5a, 0xa4, 0x58, 0xb5, 0x16, 0x19, 0x26, 0xe0, - 0x96, 0xb5, 0x66, 0xac, 0x49, 0x32, 0x55, 0xb5, 0xc6, 0xa1, 0xde, 0x42, - 0x76, 0xd6, 0x1a, 0x86, 0x5a, 0x1e, 0x80, 0xcb, 0x5f, 0x6d, 0xe1, 0xea, - 0x02, 0xa0, 0x3a, 0xc2, 0x1a, 0x3e, 0xa7, 0xbe, 0x8d, 0x2f, 0x1c, 0xcf, - 0x1d, 0x0f, 0x9b, 0x69, 0xcd, 0x98, 0x99, 0xca, 0x6c, 0xa5, 0xaa, 0xf5, - 0x43, 0xa4, 0x84, 0x2d, 0x9b, 0x95, 0xf9, 0x52, 0x3c, 0x75, 0x68, 0x80, - 0x35, 0xe9, 0xc0, 0x1a, 0x21, 0x20, 0x2c, 0x89, 0xf8, 0x9b, 0xf4, 0x24, - 0x87, 0x16, 0xd5, 0x31, 0x5d, 0xcd, 0x49, 0xe1, 0xbb, 0x78, 0x7e, 0x1e, - 0xd4, 0xa0, 0xd3, 0xa5, 0x34, 0x5b, 0x2a, 0xb2, 0xa8, 0xb6, 0xde, 0xaa, - 0x36, 0xe0, 0x16, 0xda, 0x2c, 0xce, 0x79, 0xe8, 0x64, 0xfc, 0xda, 0x9c, - 0x63, 0xdd, 0x75, 0x64, 0x6d, 0xb8, 0x86, 0x56, 0x4c, 0xa2, 0x58, 0x91, - 0xe2, 0x45, 0x9a, 0xe5, 0x05, 0x35, 0xae, 0xb5, 0x64, 0x22, 0xa1, 0x78, - 0x8c, 0x4b, 0x02, 0xf3, 0x20, 0xdb, 0xf3, 0xff, 0xed, 0x34, 0xff, 0xcf, - 0x68, 0x7f, 0xb3, 0x1e, 0x10, 0xd0, 0x0b, 0x82, 0x7b, 0x82, 0x52, 0xed, - 0x06, 0x3d, 0x42, 0xd3, 0xc6, 0x75, 0xba, 0xac, 0x57, 0x42, 0x00, 0x12, - 0x35, 0x46, 0x04, 0x87, 0xe2, 0x41, 0xaa, 0xcc, 0xdf, 0x4a, 0xdf, 0x18, - 0x23, 0xf0, 0x6f, 0x95, 0x9a, 0x89, 0x01, 0x52, 0xe2, 0x38, 0xbb, 0x18, - 0x1e, 0xc9, 0xa9, 0xaf, 0x15, 0x42, 0xf9, 0xa7, 0x23, 0x12, 0x66, 0xf7, - 0x26, 0x32, 0x60, 0x66, 0x21, 0xd9, 0x61, 0x73, 0x0b, 0x05, 0x1a, 0x13, - 0xeb, 0xcd, 0x25, 0x41, 0xd9, 0x0d, 0x87, 0xc9, 0x43, 0x09, 0xb1, 0x55, - 0xd3, 0x71, 0x71, 0xe3, 0x47, 0x55, 0xe3, 0xe1, 0x54, 0xdd, 0xc0, 0x72, - 0x8f, 0x77, 0xc5, 0xb8, 0xda, 0x9b, 0x63, 0xb3, 0x66, 0xe9, 0xcc, 0x31, - 0x0c, 0x43, 0xb6, 0x10, 0x47, 0xbc, 0xd5, 0xd1, 0xce, 0x97, 0x75, 0xfb, - 0x1a, 0xbc, 0x3d, 0x09, 0xa7, 0x64, 0x09, 0xd2, 0xc8, 0xe5, 0xd3, 0x89, - 0x00, 0x55, 0xfc, 0xac, 0x1a, 0x2d, 0x4e, 0x41, 0x1a, 0x06, 0x96, 0x47, - 0x1a, 0xab, 0x75, 0xad, 0x30, 0x56, 0x6b, 0x29, 0x0b, 0xf8, 0xd1, 0x48, - 0x14, 0x00, 0x6e, 0x4b, 0x02, 0x52, 0x15, 0x80, 0xed, 0xe4, 0x40, 0x7c, - 0xe3, 0x47, 0x85, 0x14, 0xce, 0x74, 0x29, 0x00, 0xb0, 0x53, 0x08, 0xd3, - 0xd5, 0x26, 0xc4, 0xfb, 0x41, 0x30, 0xa9, 0x15, 0xf4, 0xcb, 0x52, 0x79, - 0xaa, 0xbf, 0x84, 0x68, 0xe4, 0x16, 0x98, 0xc7, 0x15, 0x09, 0xbf, 0x4a, - 0xe5, 0xa7, 0xba, 0xca, 0x4f, 0xa5, 0x4b, 0xb0, 0x8d, 0xda, 0x6e, 0xd1, - 0xbc, 0x9a, 0x14, 0xd9, 0x73, 0xd3, 0xf5, 0x62, 0x64, 0x70, 0x55, 0xa6, - 0x51, 0x42, 0xfd, 0x83, 0x8c, 0x23, 0x63, 0xc8, 0x32, 0x8f, 0x2c, 0xb9, - 0xde, 0x40, 0x72, 0x38, 0xa1, 0x2f, 0x71, 0xa9, 0x95, 0x22, 0x02, 0x6c, - 0xf4, 0x0a, 0x3e, 0xc6, 0x8d, 0x58, 0x12, 0xbc, 0x81, 0xf2, 0xd8, 0xf4, - 0x46, 0x7a, 0x99, 0xbf, 0x44, 0xfc, 0x2d, 0x6f, 0xf9, 0x9b, 0xbf, 0x84, - 0x2d, 0x13, 0xd8, 0xc3, 0xd6, 0x15, 0x1d, 0x6a, 0x05, 0x1a, 0x67, 0x17, - 0xe5, 0x51, 0x07, 0x2a, 0x2d, 0x48, 0x1f, 0x10, 0x30, 0x40, 0x21, 0x10, - 0xec, 0x9f, 0xa5, 0x11, 0xc8, 0x91, 0xa5, 0x12, 0x3c, 0x3d, 0x48, 0x27, - 0x10, 0xb0, 0x46, 0x29, 0xfa, 0x03, 0x44, 0x93, 0xf0, 0x4d, 0x96, 0x84, - 0xfe, 0x89, 0x5a, 0x41, 0xd4, 0x83, 0xd4, 0x82, 0x20, 0x03, 0xf4, 0x82, - 0xe0, 0xfe, 0x59, 0x8a, 0x41, 0x2c, 0x59, 0x9a, 0x21, 0x32, 0x82, 0x54, - 0x83, 0x20, 0xab, 0x75, 0x03, 0xcc, 0x85, 0x0e, 0xfe, 0x2f, 0x57, 0x0d, - 0x20, 0x16, 0x66, 0x30, 0x00, 0x30, 0xc4, 0x60, 0x00, 0xd8, 0x3f, 0xcc, - 0x60, 0x20, 0x47, 0xb6, 0x5a, 0x50, 0x7a, 0x98, 0xc1, 0x00, 0xc0, 0x1a, - 0x83, 0x71, 0xd4, 0x56, 0x81, 0xff, 0xb5, 0xd6, 0x82, 0x22, 0xe6, 0x53, - 0xc0, 0x7c, 0x7b, 0xa7, 0x42, 0x89, 0xa6, 0xbf, 0xdd, 0x86, 0x85, 0x7e, - 0xa2, 0x6a, 0xc4, 0xd0, 0x99, 0xc8, 0xf3, 0x53, 0xfa, 0x21, 0x76, 0x0a, - 0x9f, 0xe1, 0xde, 0xf9, 0x19, 0x63, 0xc1, 0x3d, 0xc3, 0x9d, 0xfe, 0x50, - 0xbd, 0x4e, 0xca, 0x20, 0xf0, 0x9c, 0xaf, 0x54, 0x59, 0x96, 0xd6, 0xa3, - 0x7d, 0xfc, 0x64, 0x46, 0x2d, 0x29, 0x38, 0x52, 0x1e, 0x11, 0x60, 0xc7, - 0xa3, 0xa6, 0x69, 0x36, 0x95, 0xa8, 0xb8, 0x5d, 0x99, 0x8d, 0xaf, 0x95, - 0x3d, 0x4e, 0xd8, 0x6f, 0xa3, 0x73, 0x87, 0x94, 0xce, 0x76, 0xe2, 0x38, - 0x53, 0xc5, 0x8a, 0x9f, 0x37, 0x14, 0xc4, 0x65, 0xe1, 0x8d, 0x96, 0x5e, - 0x9d, 0xbc, 0x01, 0xcf, 0x7a, 0x2d, 0xe0, 0xd4, 0x42, 0xc9, 0x6c, 0x54, - 0xbe, 0x7f, 0xc0, 0xb9, 0x76, 0x73, 0xee, 0x59, 0x90, 0x2c, 0xe8, 0xec, - 0x16, 0x1d, 0x23, 0x79, 0x7a, 0x71, 0x91, 0x4c, 0xeb, 0x56, 0xb2, 0x8a, - 0xae, 0x85, 0x20, 0xc4, 0xe5, 0xa4, 0x26, 0xe5, 0x6e, 0xde, 0x52, 0xf1, - 0x22, 0x6d, 0xb9, 0xcc, 0xc5, 0xaf, 0xbe, 0x54, 0x72, 0x61, 0x9d, 0x0d, - 0xf3, 0x83, 0x86, 0x5f, 0x1b, 0x71, 0x51, 0x99, 0xcc, 0x49, 0x39, 0x5a, - 0xed, 0xe6, 0x87, 0xce, 0xed, 0xc9, 0x47, 0xd2, 0x07, 0x11, 0x47, 0xbb, - 0xfa, 0x33, 0x8f, 0x03, 0xed, 0xb8, 0xde, 0xad, 0x96, 0xbf, 0x9e, 0xfb, - 0x0f, 0x59, 0x4f, 0xa5, 0x5e, 0xce, 0x79, 0xe8, 0xe2, 0x6a, 0x9c, 0x2e, - 0x6b, 0xcf, 0x51, 0x74, 0x11, 0x4a, 0x68, 0xb8, 0xc0, 0xb2, 0xad, 0xa4, - 0xf2, 0x2a, 0x8a, 0x0a, 0xda, 0x68, 0x05, 0xcd, 0x45, 0x0c, 0xca, 0x50, - 0xca, 0xb4, 0x76, 0xc6, 0x2f, 0x93, 0x1b, 0x02, 0xab, 0x62, 0x45, 0x42, - 0xdf, 0xa6, 0x3f, 0xa2, 0x29, 0x89, 0xe9, 0x44, 0xf5, 0x33, 0x18, 0x7e, - 0x05, 0x3a, 0x3f, 0x08, 0x17, 0xf7, 0x3b, 0x83, 0x76, 0xa7, 0x7f, 0xd4, - 0x7e, 0x75, 0xf0, 0xe6, 0x9b, 0xed, 0xd7, 0xfc, 0x70, 0x07, 0x02, 0xee, - 0xf0, 0x8d, 0xd7, 0xab, 0xe0, 0x0e, 0x05, 0x5c, 0xbf, 0xff, 0xb8, 0xdd, - 0xde, 0xeb, 0xc3, 0x39, 0xaf, 0x90, 0x30, 0xd8, 0xc5, 0x6a, 0xb5, 0x98, - 0x8c, 0x1b, 0x74, 0x1e, 0x2a, 0x34, 0x84, 0xf2, 0xc5, 0x6a, 0x55, 0x24, - 0xbb, 0x20, 0x6c, 0xb2, 0x2c, 0x5a, 0x25, 0x06, 0x99, 0x53, 0xb4, 0xe1, - 0xc1, 0x21, 0xda, 0xec, 0x47, 0x2f, 0xf6, 0xfb, 0xfd, 0x47, 0xd1, 0x13, - 0xf8, 0xf2, 0xf4, 0xe9, 0xd3, 0x47, 0x21, 0x94, 0x89, 0xe5, 0xdd, 0x11, - 0xa6, 0x7b, 0x2c, 0xdb, 0x51, 0x37, 0xfb, 0x13, 0xbe, 0x17, 0x54, 0xdf, - 0x9f, 0x10, 0x4a, 0xf4, 0x27, 0x81, 0xe5, 0xeb, 0x4f, 0x98, 0xa7, 0x42, - 0x36, 0x5a, 0xe2, 0xb1, 0x69, 0x01, 0x77, 0x7a, 0x89, 0x21, 0x62, 0xa2, - 0x83, 0xb7, 0xa6, 0x80, 0x5c, 0xc4, 0x3d, 0x52, 0x41, 0x1d, 0xab, 0x97, - 0x0a, 0x42, 0x09, 0xa9, 0x08, 0x2c, 0x9f, 0x54, 0x30, 0x4f, 0x87, 0xdc, - 0x5e, 0x2a, 0x8c, 0x3b, 0x41, 0x27, 0x5c, 0x2a, 0xfc, 0x80, 0x7d, 0x93, - 0xbe, 0x84, 0x00, 0x21, 0xa4, 0xc5, 0xc9, 0x9b, 0x87, 0xa7, 0x5c, 0xee, - 0xc3, 0xed, 0x8a, 0x34, 0x2e, 0x84, 0xef, 0x8a, 0x36, 0x9b, 0x1c, 0xec, - 0x90, 0x3a, 0xcc, 0x35, 0x76, 0x26, 0x73, 0x31, 0x75, 0xd9, 0x21, 0x7d, - 0x98, 0x09, 0x6d, 0xcf, 0x3e, 0x3f, 0xcd, 0x58, 0x24, 0x37, 0xc5, 0x1e, - 0xdd, 0xf1, 0x63, 0xfd, 0x7c, 0x96, 0xac, 0xd9, 0x59, 0xf4, 0x08, 0x92, - 0x24, 0xcd, 0x08, 0x23, 0xb4, 0x63, 0x90, 0xce, 0xd0, 0xc1, 0x18, 0x51, - 0xff, 0xd9, 0x63, 0xb1, 0x08, 0xa5, 0x9f, 0x87, 0x1c, 0x8f, 0x95, 0x17, - 0x20, 0xe5, 0xc4, 0xdd, 0x73, 0x34, 0x96, 0x68, 0x7a, 0x8f, 0xc7, 0xc2, - 0x1f, 0x83, 0x80, 0x53, 0xb1, 0x75, 0x23, 0xd0, 0x60, 0x30, 0x70, 0x8e, - 0x6f, 0xf7, 0xc1, 0x4a, 0x72, 0x92, 0xcc, 0xe1, 0x81, 0x80, 0xed, 0xc6, - 0x3a, 0xf8, 0x0b, 0x38, 0x47, 0xb7, 0x1b, 0xf2, 0x2c, 0xe4, 0xe1, 0x0e, - 0x08, 0xd3, 0x51, 0xda, 0xdd, 0x90, 0xc6, 0x03, 0xb6, 0xbb, 0xa1, 0x8c, - 0xc7, 0x6e, 0x77, 0x44, 0x9a, 0x05, 0x9c, 0xdb, 0x0d, 0xed, 0x7c, 0x9d, - 0xec, 0xaa, 0x19, 0x85, 0xb1, 0xd9, 0x8e, 0xb4, 0xe5, 0xaf, 0x14, 0x01, - 0x93, 0x22, 0x00, 0xd2, 0xbc, 0x95, 0xc2, 0x3b, 0x25, 0x82, 0x2c, 0x15, - 0xee, 0x4f, 0xcc, 0x87, 0x88, 0x31, 0x4e, 0x25, 0xdc, 0x51, 0x11, 0x44, - 0xba, 0xb0, 0x3a, 0xd3, 0x64, 0x7c, 0x28, 0x96, 0x21, 0xd4, 0xd9, 0xaa, - 0x4c, 0xfd, 0xa4, 0xd7, 0xa6, 0xde, 0x68, 0x25, 0xe2, 0x81, 0xa7, 0xe0, - 0x95, 0xdc, 0x30, 0x5b, 0x79, 0x3e, 0x9e, 0x16, 0x29, 0xac, 0xfb, 0xb1, - 0x9b, 0xfb, 0x71, 0xdb, 0xaf, 0x2c, 0x79, 0x90, 0xb6, 0x00, 0x55, 0x43, - 0x61, 0x72, 0xaf, 0xc6, 0x10, 0xb4, 0x06, 0xdb, 0x64, 0x41, 0xc8, 0x49, - 0x0d, 0x4a, 0xd1, 0x4a, 0x6d, 0x5c, 0x5f, 0xee, 0x20, 0xd0, 0x53, 0x8b, - 0x17, 0xe3, 0x69, 0xc2, 0x9f, 0x5c, 0x69, 0x12, 0x87, 0x97, 0xcf, 0xe3, - 0xbd, 0xe1, 0x1f, 0xe5, 0x24, 0xa7, 0x06, 0x04, 0x1b, 0xb4, 0x0e, 0xa4, - 0x58, 0xd6, 0x43, 0xe4, 0x1e, 0x10, 0xb8, 0xbf, 0x13, 0xd6, 0xa5, 0xd8, - 0x73, 0xd1, 0x8e, 0xb6, 0xa1, 0x18, 0x05, 0xa2, 0x69, 0x1e, 0xd6, 0xc9, - 0x10, 0x77, 0xb7, 0x47, 0xf5, 0xfc, 0x59, 0x78, 0xe3, 0x8c, 0x6b, 0xbf, - 0xbc, 0xf8, 0x42, 0x77, 0xab, 0x60, 0x1f, 0x22, 0x6a, 0x99, 0x97, 0xa8, - 0x01, 0xb8, 0xbc, 0xcc, 0x25, 0x42, 0x26, 0xb4, 0xed, 0x7b, 0x55, 0xf4, - 0xa7, 0xd3, 0x8c, 0x5e, 0x1b, 0xc9, 0xe0, 0x05, 0xd6, 0x95, 0x51, 0xcc, - 0x48, 0x58, 0xb8, 0x6c, 0xb8, 0x54, 0x96, 0xe4, 0x74, 0x6d, 0x46, 0x3c, - 0xd5, 0x19, 0x31, 0xfd, 0xcb, 0x15, 0x24, 0xfd, 0x2a, 0xec, 0xd5, 0x78, - 0x6d, 0x5d, 0x83, 0x95, 0x7f, 0xe6, 0x6d, 0x30, 0x8b, 0xcf, 0x1a, 0x83, - 0x26, 0xae, 0x82, 0xa9, 0x31, 0x6a, 0xc2, 0xea, 0x65, 0x78, 0x62, 0x5a, - 0xdf, 0xf9, 0x73, 0xfe, 0xa1, 0xea, 0x23, 0xfa, 0xd9, 0xe2, 0x5c, 0x35, - 0x0d, 0x75, 0xa4, 0xb7, 0x1b, 0xe9, 0x86, 0xfb, 0x52, 0x14, 0xaf, 0x36, - 0xbf, 0x10, 0xd5, 0x6a, 0x5b, 0xcd, 0x4a, 0xd7, 0x1f, 0xcd, 0x66, 0x1d, - 0x2f, 0x16, 0x7f, 0x55, 0x8b, 0xa2, 0x5c, 0x99, 0x74, 0xa2, 0x51, 0x93, - 0xe6, 0x1d, 0xba, 0xc9, 0x11, 0x80, 0x2e, 0x1b, 0x4a, 0xda, 0x4e, 0x3c, - 0x7f, 0xa7, 0x76, 0x8c, 0x7c, 0xf9, 0x76, 0x2d, 0xaa, 0x2b, 0x71, 0x6f, - 0x2f, 0x28, 0xd7, 0x06, 0xe9, 0xd0, 0xbc, 0x8f, 0x26, 0xa6, 0xd2, 0xb5, - 0xfd, 0x56, 0x65, 0xf3, 0xe4, 0x0e, 0x1e, 0x94, 0x62, 0x0c, 0x71, 0xc6, - 0xdd, 0xdd, 0x07, 0x9e, 0xf5, 0x85, 0xa9, 0x72, 0x88, 0x1a, 0x37, 0xd0, - 0xda, 0x30, 0xa3, 0xa4, 0xb6, 0xd8, 0x03, 0x4e, 0x54, 0x9b, 0xb0, 0xa1, - 0xb0, 0x20, 0xbf, 0x05, 0x38, 0x96, 0x72, 0x0c, 0xab, 0x2e, 0xe3, 0xde, - 0xba, 0x72, 0xab, 0xdf, 0xc3, 0xbe, 0xca, 0xe7, 0xf8, 0x9c, 0xcd, 0x6d, - 0x27, 0xc2, 0x27, 0xeb, 0xa1, 0x4e, 0xb5, 0x37, 0x61, 0x79, 0xf9, 0x9c, - 0x40, 0xd9, 0xd4, 0x37, 0xda, 0x1e, 0x3b, 0x90, 0x15, 0xe9, 0x5e, 0x2f, - 0x33, 0x86, 0x62, 0x71, 0xbc, 0x14, 0xf7, 0xbc, 0x69, 0xcf, 0xf2, 0xc5, - 0xf1, 0x6c, 0xf0, 0xfa, 0xe0, 0x75, 0xda, 0xb4, 0x7c, 0xf1, 0xf1, 0x74, - 0x7c, 0x71, 0xb8, 0xdf, 0x92, 0x2e, 0xd6, 0xbb, 0xcb, 0xf4, 0x6a, 0x4c, - 0x95, 0x48, 0x73, 0x62, 0x78, 0xc6, 0x22, 0xb9, 0x90, 0x08, 0xe8, 0x9e, - 0x55, 0x8c, 0xd7, 0xe1, 0xd9, 0x8d, 0xf1, 0x08, 0x4a, 0xe9, 0xe3, 0x97, - 0xb6, 0xeb, 0x72, 0x6b, 0x0b, 0xc5, 0x00, 0xbb, 0xdf, 0x44, 0x86, 0x95, - 0xe0, 0x7e, 0x23, 0xe4, 0x2e, 0xe0, 0x56, 0xac, 0x46, 0x8c, 0xd9, 0x86, - 0xe8, 0x9e, 0x8b, 0x54, 0x06, 0xec, 0x8e, 0xbe, 0x49, 0x26, 0x27, 0x2b, - 0xf0, 0xd8, 0x0b, 0x3a, 0xa6, 0x40, 0x41, 0xba, 0x17, 0x09, 0x3d, 0xcc, - 0xcf, 0xb7, 0xbb, 0x81, 0xfc, 0x9d, 0xf9, 0x62, 0x38, 0xe7, 0xe8, 0x49, - 0xd4, 0xc7, 0x9a, 0xb1, 0x5c, 0x38, 0x07, 0xf8, 0x65, 0x52, 0x64, 0x29, - 0x3e, 0x32, 0x3e, 0xe0, 0x69, 0x59, 0x22, 0x71, 0xde, 0x4f, 0x16, 0xe3, - 0xdb, 0x0f, 0xb3, 0xd5, 0xf5, 0x07, 0x63, 0x7c, 0x14, 0x5b, 0x02, 0xcd, - 0x92, 0xc9, 0x66, 0xce, 0x5e, 0x2f, 0x07, 0xb6, 0x86, 0xfa, 0xbb, 0xc4, - 0x22, 0x6a, 0xc0, 0x62, 0xa1, 0x07, 0x0e, 0xd0, 0x2f, 0x8a, 0x1e, 0x2f, - 0x56, 0x30, 0x4e, 0xae, 0x57, 0x05, 0xe8, 0x42, 0x0a, 0x03, 0xd8, 0x6d, - 0x84, 0x6e, 0x9e, 0xc2, 0x70, 0xae, 0xdc, 0xdd, 0x76, 0x3e, 0x5e, 0x2e, - 0x03, 0x76, 0xc4, 0x98, 0x68, 0x85, 0x5c, 0x87, 0x34, 0x90, 0x31, 0x94, - 0x12, 0x53, 0x95, 0xa3, 0xd6, 0xa7, 0xe3, 0xe5, 0x86, 0x4a, 0xa2, 0xd4, - 0xd9, 0x93, 0x27, 0x15, 0xcc, 0x52, 0xec, 0x81, 0xbb, 0x1f, 0x92, 0x64, - 0x7d, 0x4c, 0xc0, 0xac, 0xb2, 0xf7, 0x8a, 0xc3, 0x5e, 0xcb, 0x1e, 0xb4, - 0xc2, 0xe9, 0x99, 0x0a, 0xe6, 0x7f, 0x86, 0x1d, 0xed, 0x83, 0x36, 0xe3, - 0xa9, 0x9c, 0x1b, 0x4b, 0x1a, 0x5d, 0x80, 0xa4, 0xae, 0xa3, 0xbb, 0x9e, - 0x90, 0xea, 0x73, 0x3d, 0x1b, 0xbb, 0x9d, 0x40, 0xab, 0xc6, 0x34, 0xe8, - 0x37, 0x83, 0x79, 0xad, 0x7c, 0x4d, 0x5f, 0xa3, 0x20, 0x40, 0x53, 0x6a, - 0x08, 0x81, 0x51, 0xa8, 0x7b, 0x98, 0x63, 0xf1, 0x1d, 0xf8, 0x4d, 0x06, - 0x9d, 0x95, 0x06, 0x20, 0x06, 0x07, 0x8a, 0xcf, 0x7e, 0x7a, 0xce, 0x92, - 0x88, 0xda, 0x0f, 0x45, 0xed, 0x19, 0xb4, 0x54, 0x1d, 0xbc, 0x26, 0x68, - 0xaa, 0x0e, 0xa6, 0xf1, 0xab, 0x96, 0x3d, 0xe8, 0x1e, 0x57, 0x56, 0xe4, - 0x23, 0x19, 0x66, 0xd6, 0x0e, 0xe0, 0x01, 0x1c, 0x91, 0x10, 0xf8, 0x24, - 0xed, 0x4b, 0xd1, 0x9f, 0x80, 0xb3, 0xb2, 0xe3, 0xe2, 0x5a, 0x9e, 0x11, - 0x57, 0xe4, 0xc9, 0x1b, 0x7d, 0x0c, 0xcb, 0x35, 0xce, 0x66, 0x9b, 0x74, - 0xb9, 0x82, 0xaf, 0xb2, 0x3b, 0x43, 0xe9, 0xfe, 0x10, 0x21, 0xc7, 0x25, - 0x75, 0x14, 0x94, 0x54, 0x0d, 0xaa, 0x27, 0x90, 0x41, 0xfa, 0x26, 0x01, - 0xbf, 0xd2, 0xf2, 0xa0, 0xd7, 0x98, 0xc0, 0x90, 0xac, 0x92, 0x31, 0x78, - 0x1e, 0xf5, 0xd4, 0x91, 0xfe, 0xca, 0x41, 0x1d, 0x83, 0xc9, 0x2c, 0x9c, - 0xbf, 0x80, 0x1e, 0xf3, 0xda, 0x6b, 0x06, 0xce, 0x9f, 0xeb, 0x3b, 0x06, - 0xf7, 0xaa, 0xa5, 0xb6, 0x7e, 0xb7, 0x5a, 0x6e, 0x24, 0x3d, 0x6e, 0xdb, - 0x6b, 0xd0, 0xb8, 0x75, 0x95, 0x30, 0xfd, 0x88, 0xa1, 0x53, 0xda, 0x64, - 0xad, 0x82, 0xc5, 0xfd, 0x3e, 0xf4, 0xaf, 0x9d, 0x48, 0xbc, 0xdb, 0xdd, - 0xa9, 0xc4, 0xff, 0xac, 0xf0, 0x44, 0xd7, 0xac, 0xb3, 0xb4, 0x6f, 0x8d, - 0x22, 0x69, 0xe0, 0x1c, 0x8c, 0x84, 0xc6, 0x4a, 0xbd, 0x0f, 0x6a, 0x3b, - 0x72, 0x49, 0x82, 0xdb, 0xee, 0x29, 0x41, 0xaf, 0x96, 0x81, 0x8d, 0x76, - 0x1f, 0x10, 0xcb, 0x06, 0xac, 0x48, 0x39, 0xa2, 0xab, 0xe3, 0x2f, 0x89, - 0x49, 0xca, 0xa5, 0x27, 0x81, 0x44, 0x29, 0x80, 0x59, 0x26, 0x85, 0x8f, - 0x4d, 0x92, 0x64, 0xf7, 0x62, 0x9c, 0x2e, 0x12, 0x19, 0xd1, 0xc4, 0x2b, - 0x5b, 0x62, 0x58, 0x67, 0xd9, 0x62, 0x58, 0x67, 0xb7, 0xda, 0xb6, 0x02, - 0xfe, 0x26, 0x5b, 0x78, 0x6c, 0x69, 0xed, 0x54, 0xea, 0xdf, 0x1d, 0x73, - 0xde, 0x88, 0x83, 0x44, 0x51, 0x19, 0x41, 0x32, 0x39, 0x48, 0x46, 0x1d, - 0x5a, 0xbf, 0xb9, 0x4c, 0x96, 0x6c, 0x50, 0x95, 0x22, 0x4d, 0x73, 0xf2, - 0xc0, 0x3a, 0xf4, 0xae, 0x0c, 0x45, 0x7e, 0x20, 0xa9, 0xf3, 0xe1, 0x17, - 0x52, 0xb3, 0x9f, 0x92, 0xcc, 0xd9, 0x1a, 0x72, 0x44, 0x90, 0xee, 0xae, - 0x37, 0x7e, 0x63, 0xd9, 0x4e, 0x54, 0x9a, 0x3d, 0xc5, 0x4b, 0xcb, 0xd6, - 0x4f, 0x66, 0x76, 0x38, 0x34, 0x02, 0xc9, 0x92, 0x8b, 0x2c, 0xc9, 0x2f, - 0xcf, 0x69, 0x95, 0x14, 0x26, 0xa1, 0x6c, 0xe8, 0x7f, 0xc6, 0x7f, 0xc5, - 0xd4, 0xd7, 0xe4, 0x71, 0xaf, 0x97, 0x5a, 0xed, 0x0e, 0x39, 0xbd, 0xfb, - 0x58, 0x56, 0x03, 0xc3, 0x25, 0x3d, 0x15, 0xae, 0xc5, 0x0d, 0xac, 0x44, - 0x58, 0x2f, 0xe1, 0x74, 0xb7, 0x1a, 0x78, 0xf6, 0xf6, 0x7c, 0x4f, 0x11, - 0xca, 0x9a, 0xf3, 0xf9, 0xc3, 0x00, 0xeb, 0xde, 0x0c, 0xf5, 0x98, 0xa3, - 0x1e, 0x34, 0x47, 0xfd, 0x95, 0xa3, 0x3e, 0x46, 0xd4, 0xa0, 0xcd, 0x0d, - 0x6f, 0x8f, 0x83, 0x56, 0x7b, 0xb9, 0xd5, 0x8c, 0x44, 0x78, 0xb7, 0x03, - 0xe2, 0xd4, 0xef, 0x82, 0x78, 0xdc, 0xb6, 0xef, 0x61, 0xb4, 0xd2, 0x5b, - 0xe1, 0x28, 0xef, 0xb4, 0x07, 0x92, 0x97, 0xd0, 0xb4, 0x0b, 0xb2, 0x89, - 0x50, 0x6d, 0x27, 0x34, 0xe3, 0xb9, 0xd1, 0x63, 0x99, 0x65, 0x7f, 0x73, - 0xf6, 0xc9, 0xb6, 0xab, 0xd2, 0x9f, 0xac, 0xe6, 0x11, 0x8d, 0x88, 0xb9, - 0xaf, 0x16, 0x94, 0xab, 0xd6, 0x82, 0x12, 0x9c, 0x55, 0xa1, 0x1c, 0xb5, - 0x32, 0x22, 0xcc, 0x1b, 0x7d, 0x36, 0xad, 0x12, 0xba, 0x0e, 0xf6, 0x98, - 0x58, 0x64, 0xb7, 0xc7, 0x74, 0x91, 0xf0, 0xed, 0x91, 0x32, 0x86, 0xf4, - 0xe4, 0xbc, 0x99, 0x38, 0x6b, 0xe8, 0x10, 0x79, 0xed, 0x0a, 0xfc, 0xd5, - 0x3b, 0x9b, 0x5b, 0x59, 0x96, 0x20, 0xeb, 0x22, 0xac, 0x58, 0xe3, 0x0a, - 0x19, 0x63, 0xfe, 0x36, 0x65, 0xb7, 0xb6, 0x09, 0xf2, 0xc7, 0xcb, 0x25, - 0xaf, 0xa9, 0x1f, 0xbd, 0xe6, 0x6e, 0x21, 0x48, 0x0f, 0xc1, 0x1f, 0x28, - 0x71, 0x02, 0xfb, 0x56, 0xa0, 0x40, 0x8f, 0x2e, 0xf3, 0xe3, 0x18, 0x2c, - 0xe0, 0x6b, 0x40, 0x1f, 0x2d, 0x63, 0x25, 0x05, 0x45, 0x3a, 0x96, 0x9a, - 0x8d, 0xe4, 0x39, 0x69, 0x16, 0xf1, 0xb8, 0x87, 0xb4, 0x55, 0x0e, 0x41, - 0x51, 0xc3, 0xde, 0x6e, 0x29, 0x31, 0xf7, 0xf6, 0x82, 0x16, 0x45, 0x1f, - 0x91, 0xe5, 0x7b, 0x24, 0x36, 0x79, 0xf9, 0x9b, 0x85, 0xd8, 0x64, 0x4b, - 0xe8, 0xad, 0xf6, 0xb6, 0x93, 0x5e, 0x05, 0x28, 0x1f, 0xd8, 0x85, 0x7f, - 0xff, 0xc4, 0x93, 0x31, 0x22, 0xa6, 0x86, 0xfd, 0x66, 0x87, 0x1e, 0xab, - 0x60, 0xa4, 0x42, 0x0f, 0xa3, 0xa0, 0xd3, 0x79, 0xee, 0xa0, 0x07, 0x01, - 0x6f, 0x6f, 0xe0, 0x5a, 0xb1, 0x9f, 0x23, 0xca, 0x1d, 0x95, 0x80, 0x21, - 0x04, 0xe5, 0x8b, 0xcc, 0xc1, 0x8f, 0x93, 0xd8, 0x6f, 0x4d, 0x1b, 0x94, - 0x0c, 0x99, 0xcb, 0x46, 0xa2, 0xf0, 0x6d, 0xd1, 0xb1, 0x7c, 0xeb, 0x15, - 0x63, 0xbc, 0x39, 0x80, 0x8d, 0x27, 0xb1, 0x43, 0x0a, 0xb0, 0x6b, 0x4a, - 0x7b, 0xda, 0xbc, 0x0d, 0x4f, 0xe8, 0xa1, 0x3e, 0x76, 0x8d, 0x39, 0xa7, - 0x98, 0x62, 0xb5, 0x82, 0x21, 0x58, 0x4b, 0x26, 0x00, 0x77, 0x67, 0xdc, - 0x85, 0x1f, 0x49, 0xf0, 0x61, 0x48, 0x24, 0x00, 0xf7, 0x6d, 0xfe, 0xa0, - 0xd6, 0xc7, 0x2b, 0xd5, 0x36, 0x4b, 0x26, 0x4f, 0x00, 0x33, 0x2a, 0xc1, - 0x87, 0x01, 0xf7, 0xf1, 0xdd, 0xb7, 0xea, 0x43, 0x18, 0xba, 0xb8, 0x39, - 0xf7, 0x69, 0x24, 0xd0, 0xb2, 0x94, 0x12, 0xc0, 0x43, 0xf5, 0x92, 0xce, - 0x13, 0x05, 0xab, 0xa4, 0xf5, 0x08, 0xb7, 0xa4, 0x51, 0xa3, 0x8c, 0x95, - 0x7a, 0x68, 0x3e, 0x0e, 0x2e, 0xa9, 0x86, 0x69, 0xa0, 0x51, 0x27, 0x3a, - 0x53, 0x11, 0x5c, 0x27, 0xfb, 0xc9, 0x13, 0x49, 0x04, 0x1e, 0xb4, 0x1b, - 0x06, 0x61, 0x65, 0x1a, 0x56, 0x3f, 0x10, 0x6b, 0xae, 0x61, 0x0d, 0x02, - 0xb1, 0x26, 0x1a, 0xd6, 0x41, 0x20, 0x16, 0x9c, 0xe3, 0x64, 0x11, 0x39, - 0x9e, 0xaf, 0x3e, 0x4a, 0x6e, 0xe2, 0x53, 0xb5, 0x8e, 0x1d, 0x8d, 0xf7, - 0x8e, 0xc6, 0x53, 0x47, 0x2b, 0xeb, 0xac, 0x1d, 0x56, 0xda, 0xf5, 0x40, - 0x63, 0xf2, 0x71, 0x20, 0x93, 0x99, 0x8e, 0x76, 0x18, 0x88, 0x36, 0xd7, - 0xd1, 0x8e, 0x02, 0xd1, 0x26, 0x3a, 0xda, 0xeb, 0x81, 0x68, 0x20, 0xc9, - 0x81, 0x47, 0x94, 0x8f, 0x35, 0x71, 0x1d, 0x6a, 0xbf, 0x8e, 0xf0, 0x97, - 0x2c, 0x2c, 0x5c, 0x94, 0x07, 0x1a, 0x97, 0x6f, 0x04, 0x72, 0x99, 0xe9, - 0x68, 0x6f, 0x06, 0xa2, 0xcd, 0x75, 0xb4, 0x7e, 0x68, 0x07, 0x98, 0x18, - 0x78, 0xa1, 0x5d, 0x00, 0x84, 0x79, 0xe0, 0x11, 0xe6, 0x1b, 0x9a, 0xc0, - 0xde, 0xd4, 0xb5, 0xd4, 0x50, 0xda, 0x3e, 0x88, 0xf3, 0x21, 0x86, 0x43, - 0xb4, 0x24, 0x66, 0x34, 0xe1, 0x51, 0xd5, 0x8a, 0x62, 0x54, 0x19, 0x8d, - 0xb6, 0x97, 0x79, 0x98, 0x8a, 0x6a, 0x22, 0xd0, 0xf6, 0xe6, 0x3e, 0xc4, - 0xea, 0xa8, 0xb3, 0xbd, 0x89, 0x1f, 0xcf, 0x1f, 0x69, 0x96, 0xd4, 0x8c, - 0x23, 0x06, 0x98, 0xdb, 0x0a, 0x41, 0x0d, 0xb6, 0x16, 0xd4, 0x60, 0x6b, - 0x49, 0x0d, 0xb6, 0x15, 0xd5, 0x60, 0x6b, 0x59, 0x0d, 0x1a, 0x09, 0xcb, - 0x23, 0xab, 0x83, 0xad, 0x65, 0x75, 0xb0, 0xb5, 0xac, 0x0e, 0xb6, 0x95, - 0xd5, 0xc1, 0xd6, 0xb2, 0x3a, 0x08, 0x97, 0x95, 0xdb, 0xb9, 0x64, 0xef, - 0x6b, 0x36, 0x72, 0x2a, 0x2b, 0x9e, 0xa1, 0xbc, 0xb3, 0x62, 0xae, 0x9a, - 0x2f, 0x51, 0x86, 0x04, 0x86, 0xf5, 0x44, 0x82, 0x0d, 0x72, 0xb9, 0x2a, - 0x1e, 0xb2, 0xbc, 0xab, 0x7f, 0xca, 0x32, 0x28, 0x90, 0xab, 0x2f, 0x70, - 0x6b, 0x90, 0xf7, 0x2b, 0xe2, 0x8c, 0xd6, 0xf2, 0xe7, 0x78, 0x0d, 0xb3, - 0x96, 0x3f, 0x80, 0xf1, 0xf0, 0x07, 0x59, 0x61, 0xde, 0x79, 0xc5, 0x73, - 0x9a, 0x77, 0xf5, 0x0f, 0x6a, 0x06, 0x05, 0x47, 0xf5, 0x06, 0x43, 0x0d, - 0xe6, 0xcf, 0xfd, 0x22, 0xe7, 0x5d, 0xfd, 0x9b, 0x9c, 0x51, 0x48, 0x18, - 0x53, 0x6f, 0xd8, 0xd2, 0x10, 0xfe, 0x2a, 0x1e, 0xf5, 0xbc, 0xab, 0x78, - 0xd6, 0x33, 0x64, 0xca, 0x3d, 0x5d, 0x1a, 0x8d, 0x2b, 0x69, 0x05, 0x72, - 0x06, 0x14, 0x6a, 0x39, 0xd3, 0x5f, 0x06, 0x0d, 0x58, 0x0c, 0x98, 0xae, - 0x36, 0x1e, 0xc6, 0xa6, 0x61, 0xcb, 0x01, 0x7f, 0xd9, 0xcb, 0xa2, 0x61, - 0x17, 0x03, 0x8d, 0x7a, 0xfc, 0x05, 0xaf, 0x95, 0x46, 0x51, 0xf8, 0xbb, - 0x98, 0x61, 0x15, 0xba, 0x6e, 0xf0, 0x48, 0x26, 0xfd, 0xe9, 0x27, 0x70, - 0x77, 0x53, 0xa8, 0xb2, 0x44, 0x1a, 0x36, 0xd8, 0xed, 0x0b, 0xd0, 0x00, - 0x57, 0xf7, 0xba, 0x29, 0xfc, 0xa0, 0x29, 0xc2, 0x41, 0x15, 0x02, 0x68, - 0x79, 0xd0, 0x88, 0x1b, 0xfe, 0x0a, 0xed, 0x5d, 0xc5, 0x3b, 0xb4, 0xb5, - 0x7d, 0x12, 0x60, 0x9c, 0x9a, 0x0c, 0xe9, 0x81, 0x3d, 0xd2, 0xf7, 0x8a, - 0xed, 0x5d, 0xdd, 0x3b, 0xb6, 0x8d, 0xe3, 0x92, 0xd8, 0x6c, 0x12, 0xa5, - 0x50, 0x6b, 0x4b, 0xc1, 0x72, 0xc2, 0x4d, 0x87, 0x23, 0xa4, 0x8f, 0x46, - 0x69, 0xd8, 0xec, 0x2c, 0xbe, 0x71, 0xef, 0x37, 0x38, 0x9c, 0x5d, 0x73, - 0xfa, 0x78, 0xf3, 0xb7, 0xb6, 0x80, 0xfe, 0x60, 0xfb, 0x02, 0xf8, 0xdd, - 0xdf, 0xc0, 0x00, 0x5b, 0xcd, 0xe9, 0xc3, 0xdd, 0xdf, 0xda, 0x0a, 0x1c, - 0xc1, 0xee, 0x67, 0x50, 0x3f, 0xc2, 0x17, 0xe5, 0xc0, 0xc0, 0x34, 0x5a, - 0x0d, 0x85, 0xb5, 0x98, 0x60, 0x35, 0x01, 0x78, 0x79, 0xcc, 0x0d, 0xdf, - 0xd3, 0x31, 0x4f, 0xa0, 0xd8, 0x25, 0x11, 0x58, 0x0f, 0xfc, 0x54, 0x7a, - 0xb7, 0xaa, 0xfc, 0xc1, 0x8f, 0x2b, 0x47, 0x6f, 0x47, 0xfb, 0xfe, 0xd2, - 0xec, 0x63, 0xda, 0x74, 0x92, 0xec, 0x2e, 0xa2, 0xc7, 0xd6, 0x9e, 0x48, - 0x6a, 0x9d, 0x28, 0x9d, 0xb1, 0x9f, 0x04, 0x27, 0x8f, 0x52, 0x06, 0x4e, - 0x02, 0x28, 0x39, 0xe0, 0xe4, 0xbf, 0x39, 0xb5, 0x8f, 0x1c, 0xb3, 0x7a, - 0xfb, 0x99, 0x13, 0x03, 0xc0, 0xfb, 0x74, 0x8a, 0xaf, 0x24, 0xba, 0x8b, - 0x15, 0x7d, 0x49, 0xff, 0x02, 0x49, 0x0b, 0xd2, 0xff, 0xe0, 0x8a, 0x9f, - 0xf3, 0x9c, 0x1e, 0x2c, 0xc9, 0x56, 0x8b, 0xdc, 0x0f, 0x28, 0x36, 0x66, - 0x08, 0xc1, 0x86, 0x13, 0xf9, 0xbc, 0x0a, 0xf4, 0xf6, 0xe9, 0xb0, 0xe6, - 0x34, 0x92, 0x86, 0x12, 0x5d, 0x40, 0x31, 0xf9, 0x65, 0x32, 0x7b, 0x41, - 0x1b, 0xff, 0x83, 0x6e, 0xb7, 0x79, 0x4b, 0x70, 0x61, 0x79, 0x0b, 0xa2, - 0x06, 0xf6, 0x92, 0x22, 0xbd, 0x43, 0x49, 0xd0, 0x06, 0x59, 0xf9, 0xcb, - 0xb5, 0xef, 0x54, 0x66, 0x46, 0xe2, 0x15, 0xd8, 0xda, 0x83, 0x59, 0xcf, - 0x00, 0x3a, 0x1d, 0x2f, 0xd2, 0x9f, 0x61, 0xf7, 0xb0, 0xd7, 0xeb, 0x59, - 0x9c, 0xc9, 0xab, 0x7b, 0xf2, 0x39, 0x22, 0x52, 0x6e, 0x56, 0x27, 0x17, - 0xb0, 0xcf, 0xda, 0x68, 0xeb, 0xf5, 0x4d, 0xee, 0x56, 0x42, 0xc1, 0x36, - 0x57, 0xf2, 0xa4, 0xf5, 0x27, 0xfc, 0xb1, 0x4c, 0xb0, 0x39, 0x2e, 0xb5, - 0x94, 0xc7, 0x3a, 0xd8, 0xf9, 0x99, 0xa6, 0x37, 0xba, 0x9a, 0xed, 0x13, - 0xd6, 0x52, 0x2b, 0xe3, 0x7e, 0xb8, 0x28, 0x3a, 0x8f, 0xe3, 0xd1, 0x61, - 0x7d, 0x6f, 0xff, 0x65, 0xd2, 0xf2, 0x77, 0xf0, 0xa9, 0x5c, 0xfc, 0x73, - 0x02, 0x49, 0x8d, 0x92, 0x67, 0x07, 0xfc, 0x57, 0xc0, 0xa6, 0x78, 0xd9, - 0x31, 0xa2, 0xbd, 0x5d, 0xb9, 0x75, 0x6c, 0x9f, 0x72, 0xa3, 0xf3, 0x32, - 0x7c, 0x4f, 0x98, 0x74, 0xd0, 0xde, 0x02, 0x3e, 0x89, 0x10, 0x88, 0x74, - 0x5a, 0x00, 0x0e, 0xdd, 0xbb, 0xcb, 0x2a, 0x31, 0xf5, 0xa0, 0xb7, 0x48, - 0x7b, 0x61, 0x84, 0xe7, 0x81, 0xd0, 0xae, 0xcb, 0x14, 0x3c, 0xab, 0x43, - 0x90, 0x46, 0xf2, 0xb1, 0x0e, 0x28, 0x0f, 0x8a, 0x1f, 0x5f, 0x42, 0x0e, - 0x9d, 0x11, 0xf7, 0x01, 0xe4, 0xd3, 0x5a, 0x88, 0x75, 0x2d, 0x44, 0x26, - 0x20, 0x24, 0x77, 0x36, 0xd8, 0xc9, 0x69, 0x0d, 0x9d, 0x93, 0xb3, 0x12, - 0x80, 0xa4, 0x1b, 0x72, 0xfa, 0xb9, 0xf2, 0x46, 0x81, 0xaf, 0x79, 0xd4, - 0xe3, 0x9a, 0xc5, 0x8a, 0x1a, 0x0b, 0xd1, 0x7b, 0x9b, 0x6c, 0xe1, 0x38, - 0x08, 0x61, 0x37, 0x95, 0x1c, 0xd5, 0x9c, 0x47, 0xea, 0xc5, 0xad, 0xcd, - 0x73, 0xb6, 0x3c, 0x88, 0x06, 0x86, 0xd2, 0xe3, 0x9c, 0x76, 0x53, 0x5d, - 0xaf, 0xdc, 0x31, 0x0c, 0xda, 0x80, 0x63, 0x40, 0x40, 0xb8, 0x2e, 0xf6, - 0x03, 0x38, 0x36, 0xdb, 0xa0, 0xc1, 0x20, 0xb6, 0x25, 0xe6, 0x36, 0x68, - 0xb4, 0x7a, 0xb9, 0x35, 0xe2, 0x96, 0xbc, 0xe2, 0xc2, 0xe7, 0xb6, 0x78, - 0x5b, 0x16, 0x89, 0xb3, 0xc8, 0xad, 0xca, 0x44, 0xc4, 0x9a, 0x42, 0xc1, - 0x2a, 0x98, 0xaa, 0x73, 0x6f, 0x58, 0x27, 0xcf, 0x78, 0x2e, 0xc0, 0x27, - 0x45, 0xd8, 0x55, 0x3e, 0x80, 0xd3, 0x23, 0xba, 0xca, 0x8b, 0x70, 0x40, - 0xc3, 0x7f, 0x0f, 0x0e, 0x32, 0xe9, 0x0a, 0x5c, 0x83, 0xd1, 0x4f, 0xf4, - 0x1c, 0xbd, 0x8a, 0x89, 0x38, 0xa8, 0x11, 0xf5, 0xa3, 0x5f, 0x7e, 0xd1, - 0xd2, 0x46, 0x90, 0x86, 0x76, 0x03, 0xc6, 0x5b, 0x1d, 0xf2, 0xf0, 0x75, - 0x34, 0x17, 0x6c, 0xe4, 0xfc, 0xea, 0xe4, 0xf9, 0xe7, 0x9f, 0x46, 0xd0, - 0xcd, 0x3f, 0xfd, 0xfc, 0xfd, 0xa7, 0xc6, 0x63, 0x62, 0x95, 0xf7, 0x24, - 0x79, 0xef, 0x76, 0x5f, 0x0d, 0xe7, 0xf8, 0x0f, 0x7e, 0x3b, 0x9c, 0x91, - 0x6d, 0x74, 0x59, 0x30, 0xec, 0x59, 0x19, 0x06, 0x03, 0xcc, 0xd9, 0x88, - 0xda, 0xfa, 0x88, 0x48, 0x6c, 0x74, 0x79, 0xd7, 0xdd, 0x64, 0x6f, 0xb3, - 0x4d, 0xb5, 0xfa, 0xa3, 0x99, 0x0f, 0xe4, 0x2f, 0x41, 0xf1, 0x82, 0x94, - 0x54, 0x90, 0xc3, 0x23, 0x60, 0x81, 0x2e, 0x0c, 0x7e, 0xf5, 0xfc, 0xf3, - 0x2f, 0x3e, 0x79, 0xf7, 0x3b, 0x5d, 0xde, 0xc2, 0x2e, 0x23, 0x38, 0xbf, - 0x7e, 0x1d, 0x93, 0x6f, 0x60, 0x58, 0x7d, 0xaf, 0x01, 0x07, 0xe7, 0xd3, - 0x0b, 0xcb, 0x4e, 0xd9, 0x48, 0xe0, 0x6a, 0xca, 0x74, 0x18, 0xc2, 0x43, - 0x59, 0x2e, 0x8a, 0x79, 0x6a, 0xf9, 0x3a, 0xab, 0x25, 0xd3, 0xf6, 0xf3, - 0x6f, 0x4e, 0x18, 0xda, 0x9f, 0x53, 0x76, 0x97, 0x3e, 0x0a, 0xcd, 0x6f, - 0xa6, 0x1f, 0x52, 0xe3, 0xb6, 0xd3, 0x54, 0xbd, 0xeb, 0x71, 0x90, 0xda, - 0xce, 0xb7, 0x55, 0x07, 0x54, 0x3a, 0x46, 0x40, 0x37, 0xa4, 0x76, 0xf9, - 0x6f, 0x6a, 0xd4, 0x1b, 0x4c, 0xa3, 0x9e, 0x7f, 0xfd, 0xaf, 0xa9, 0x1e, - 0x02, 0x87, 0xd7, 0xef, 0x4d, 0x3e, 0x42, 0x3c, 0xed, 0xf7, 0x0e, 0xfa, - 0xff, 0x9a, 0x3a, 0x36, 0x69, 0xc2, 0xa3, 0x7d, 0x5e, 0xc5, 0x0f, 0xd2, - 0x2c, 0x19, 0xec, 0xf7, 0x07, 0xff, 0x9a, 0x5a, 0x32, 0xe0, 0xda, 0xd7, - 0xc7, 0xff, 0x74, 0x0d, 0x10, 0xf8, 0x2f, 0xab, 0x82, 0xf5, 0x16, 0xb7, - 0xde, 0x5a, 0xfb, 0x8d, 0x02, 0x1d, 0xb4, 0x56, 0x17, 0x17, 0x8d, 0xc2, - 0x36, 0xc9, 0xa1, 0x72, 0x2b, 0x09, 0x36, 0xd5, 0x03, 0x5b, 0x90, 0x0d, - 0x10, 0xfc, 0x4a, 0x6f, 0xbb, 0xb9, 0xde, 0x52, 0x54, 0xff, 0x38, 0x20, - 0x94, 0xdb, 0x36, 0x8e, 0x3a, 0xc3, 0xf4, 0x7a, 0xea, 0x36, 0xa3, 0xb2, - 0x76, 0x5b, 0xf0, 0x09, 0x78, 0xdb, 0x4d, 0xb8, 0x08, 0xb1, 0x29, 0x97, - 0x8a, 0x46, 0x38, 0x27, 0xa9, 0x57, 0xda, 0x15, 0x6c, 0x3b, 0x94, 0x07, - 0x98, 0x1d, 0xd4, 0xf1, 0x90, 0x77, 0xef, 0xf1, 0x65, 0xfb, 0x30, 0x47, - 0x51, 0x60, 0xd8, 0xf5, 0xa8, 0x88, 0x71, 0x91, 0x14, 0x54, 0x19, 0x42, - 0x3e, 0xc7, 0xe2, 0xee, 0xa4, 0xb7, 0x0a, 0x52, 0x99, 0x24, 0xe0, 0x1d, - 0xe4, 0x78, 0x13, 0x66, 0x9e, 0x64, 0x25, 0x90, 0xca, 0x8e, 0x7e, 0x22, - 0xbc, 0xaf, 0x7b, 0xd0, 0x5a, 0x1e, 0xc7, 0x06, 0x08, 0xb7, 0xd1, 0x02, - 0x37, 0xf4, 0x03, 0xe8, 0x9f, 0xb0, 0x84, 0xce, 0x17, 0x17, 0x73, 0xcd, - 0x7b, 0x15, 0xa5, 0xa3, 0x39, 0xa0, 0x0e, 0x2e, 0xb9, 0xb0, 0xf9, 0xd8, - 0xb7, 0x6d, 0x0b, 0x7c, 0xd4, 0x2e, 0xe4, 0x96, 0x77, 0xbc, 0xe8, 0xe6, - 0x3a, 0x2f, 0x90, 0xa4, 0x66, 0xc8, 0x8c, 0xb4, 0x06, 0xe7, 0x8b, 0x06, - 0xde, 0x3b, 0x80, 0xa7, 0x9f, 0x11, 0x76, 0xa2, 0xcb, 0x13, 0xe6, 0x0e, - 0x1a, 0x2f, 0x03, 0x0d, 0xeb, 0xec, 0xbb, 0x8b, 0x0a, 0x99, 0x1a, 0x46, - 0x20, 0xf8, 0xe8, 0x5e, 0x59, 0xca, 0x8b, 0x58, 0x8a, 0x3c, 0x75, 0x68, - 0xee, 0xa4, 0x76, 0xac, 0x33, 0x57, 0x56, 0xca, 0xdc, 0x4a, 0x99, 0x9c, - 0xb5, 0x15, 0x4b, 0x14, 0x7c, 0x4a, 0x4e, 0xf2, 0x54, 0xc3, 0xd4, 0xc0, - 0xe6, 0xca, 0x4e, 0x9a, 0xdb, 0x49, 0x93, 0x41, 0x28, 0x63, 0x07, 0x1e, - 0xc6, 0xea, 0x38, 0x3b, 0xb0, 0x39, 0xb3, 0x93, 0xe6, 0x76, 0xd2, 0xe4, - 0x40, 0xe3, 0xec, 0x1e, 0x3f, 0x79, 0x10, 0x14, 0xe5, 0xcd, 0x09, 0xf8, - 0xce, 0xc3, 0xa0, 0xd0, 0x65, 0xa5, 0xf1, 0xf2, 0xa7, 0x71, 0xd5, 0x34, - 0xe1, 0x11, 0xab, 0x13, 0xbd, 0x65, 0x71, 0xce, 0xa0, 0x29, 0x78, 0x1e, - 0xbf, 0xe9, 0x84, 0xc1, 0x79, 0x01, 0x9b, 0x65, 0x20, 0xee, 0x31, 0x4b, - 0x8b, 0x1f, 0x0d, 0x66, 0x04, 0xa7, 0x05, 0xbb, 0xb8, 0x5a, 0xaf, 0x96, - 0x40, 0x98, 0xd5, 0x7b, 0x5a, 0x8a, 0x27, 0x4b, 0x8a, 0x4d, 0xb6, 0x8c, - 0xe2, 0xd6, 0x3e, 0x0a, 0x86, 0x59, 0x0a, 0xc8, 0xee, 0x15, 0xab, 0x93, - 0x22, 0x03, 0x9b, 0x16, 0x43, 0x84, 0x5c, 0x18, 0x81, 0x17, 0x29, 0x4c, - 0x7d, 0xba, 0x03, 0x4c, 0xff, 0x6a, 0xbd, 0x86, 0x1d, 0xa6, 0x71, 0x9e, - 0xc4, 0x96, 0x19, 0x92, 0x82, 0x85, 0x2f, 0x56, 0x11, 0x92, 0x07, 0x01, - 0x02, 0xbb, 0x84, 0x6d, 0x28, 0xd5, 0x91, 0xd1, 0xf7, 0x65, 0x0c, 0x7c, - 0x19, 0xd0, 0x00, 0x36, 0x3f, 0xab, 0xe5, 0x09, 0x99, 0x09, 0x6a, 0x03, - 0x16, 0xcf, 0x4f, 0xeb, 0x66, 0x2f, 0x38, 0x96, 0x22, 0xb5, 0x98, 0x40, - 0xeb, 0x95, 0x30, 0xba, 0x84, 0xdc, 0x5b, 0x67, 0xf4, 0xf9, 0x7e, 0x72, - 0x31, 0xde, 0x2c, 0x0a, 0x92, 0x80, 0xa4, 0xc6, 0x40, 0xe4, 0xe3, 0x29, - 0xc5, 0x6a, 0x33, 0xbd, 0xc4, 0x67, 0x5e, 0xa5, 0x89, 0x13, 0x74, 0x29, - 0x02, 0x23, 0x87, 0x1f, 0x67, 0xd0, 0x76, 0xd2, 0xce, 0x61, 0x99, 0x90, - 0x69, 0xb8, 0x49, 0x37, 0x4f, 0xa2, 0x4f, 0xc7, 0xc5, 0x65, 0x8f, 0x1c, - 0xa0, 0x58, 0xc5, 0x7c, 0x8e, 0xa5, 0xd0, 0x8e, 0x6b, 0x6f, 0x0d, 0x93, - 0xdb, 0x6f, 0xa3, 0x2e, 0x50, 0xef, 0x81, 0x61, 0x05, 0xd3, 0xf2, 0x49, - 0x72, 0x51, 0xb4, 0x3b, 0x3a, 0xa5, 0xdb, 0x50, 0x4a, 0xdf, 0x49, 0x4a, - 0x98, 0xb7, 0x6e, 0x2b, 0xa6, 0x58, 0xa8, 0xba, 0xbf, 0xf2, 0x14, 0xc7, - 0x0b, 0x2b, 0xbe, 0x45, 0xc5, 0x58, 0x91, 0xdf, 0x86, 0x70, 0xce, 0x40, - 0xbf, 0x73, 0xf3, 0x26, 0xdb, 0x91, 0x47, 0x80, 0xe5, 0xdd, 0x86, 0x7a, - 0xda, 0xb3, 0x2b, 0xa8, 0xe3, 0xfb, 0xd0, 0xfe, 0x31, 0xf0, 0xd5, 0xbb, - 0xe9, 0x44, 0xf8, 0x71, 0x0b, 0x97, 0xea, 0xe0, 0xbf, 0x36, 0xdd, 0x3e, - 0x43, 0x42, 0x32, 0x94, 0xf5, 0x39, 0xa7, 0x21, 0x95, 0x9c, 0x12, 0x8c, - 0x00, 0xa0, 0x64, 0x80, 0x7c, 0xf6, 0x1b, 0xe2, 0x3d, 0x61, 0xa0, 0x27, - 0x3d, 0x93, 0xe1, 0x1b, 0x06, 0xe5, 0xb4, 0x05, 0x25, 0x42, 0x8f, 0xe4, - 0x24, 0xcf, 0xa2, 0x91, 0x64, 0xc1, 0x83, 0x90, 0xe9, 0xe0, 0xe2, 0x4a, - 0x84, 0x07, 0x7a, 0xee, 0x82, 0xee, 0xfb, 0xa0, 0x27, 0x2e, 0xe8, 0x81, - 0x0f, 0xfa, 0x5a, 0x81, 0x96, 0x63, 0xb8, 0x3c, 0x08, 0xac, 0x73, 0x67, - 0x9c, 0xf5, 0xb5, 0x99, 0x91, 0xc7, 0x79, 0xed, 0xa2, 0xed, 0x43, 0x4c, - 0xf6, 0x1e, 0x32, 0xb6, 0x90, 0x77, 0x7f, 0xdc, 0xbf, 0xd3, 0xed, 0xdc, - 0x73, 0x37, 0x36, 0x3c, 0xec, 0x57, 0x85, 0x34, 0xf3, 0xc2, 0xb5, 0x4d, - 0xeb, 0x04, 0x42, 0x03, 0xe9, 0x6a, 0xf2, 0x97, 0x18, 0x3b, 0x62, 0xbf, - 0x13, 0xc1, 0x7f, 0xdc, 0x8c, 0x5f, 0xa7, 0xb3, 0xe2, 0xb2, 0xfc, 0x75, - 0x99, 0xa0, 0xdf, 0xa0, 0x0c, 0x2c, 0x82, 0x76, 0xc8, 0x9b, 0x4d, 0x6a, - 0xa9, 0xc4, 0x26, 0xa5, 0x43, 0x35, 0x6c, 0xc7, 0x4d, 0x02, 0x7d, 0x83, - 0x83, 0x4d, 0xac, 0x94, 0x58, 0x16, 0xba, 0xf7, 0xea, 0xab, 0x1c, 0xf4, - 0xd5, 0xe8, 0x7d, 0x80, 0xcc, 0x79, 0xa7, 0xc2, 0x51, 0x42, 0x64, 0xec, - 0x49, 0xd9, 0x28, 0xd4, 0x34, 0x8b, 0x3a, 0x4d, 0xa0, 0xfe, 0xd9, 0xb7, - 0xd1, 0x48, 0xab, 0x71, 0xb4, 0x17, 0x0d, 0x86, 0x26, 0xd0, 0x77, 0x00, - 0xa4, 0x09, 0x42, 0x40, 0xd9, 0x17, 0x38, 0x39, 0xd5, 0x8e, 0xc0, 0x0c, - 0x92, 0x27, 0x96, 0x44, 0xf7, 0xe3, 0xbf, 0x84, 0x1d, 0xe7, 0x4d, 0x6e, - 0xb3, 0xf4, 0xb8, 0x77, 0xa8, 0x80, 0xc2, 0x96, 0xb3, 0x02, 0x1a, 0x6b, - 0xb0, 0xdd, 0xa8, 0xbf, 0xdf, 0xd6, 0xd9, 0x23, 0xf0, 0x68, 0xb2, 0xca, - 0x40, 0xe1, 0x30, 0x51, 0x36, 0xfd, 0x24, 0x99, 0xa7, 0xcb, 0x2f, 0xc0, - 0x92, 0xc5, 0x6d, 0x13, 0x9c, 0xb5, 0x9d, 0x0e, 0x3e, 0xce, 0xa6, 0x76, - 0xfd, 0x54, 0x6e, 0x48, 0x7f, 0x06, 0xd0, 0x2c, 0x64, 0x1d, 0xbf, 0x78, - 0xd6, 0x61, 0x1b, 0xbf, 0x92, 0x38, 0xb5, 0x05, 0x5e, 0xfb, 0xd5, 0x98, - 0x7a, 0x12, 0xc5, 0x60, 0x06, 0x73, 0xca, 0x5c, 0x46, 0x63, 0xb2, 0xaa, - 0x08, 0xc4, 0x99, 0x78, 0xa1, 0xad, 0xb3, 0xb1, 0x48, 0x97, 0xc9, 0x37, - 0x54, 0xd9, 0x51, 0xf4, 0x78, 0xa8, 0xe7, 0xb1, 0xb0, 0x05, 0x27, 0x38, - 0x4f, 0x87, 0xdc, 0xd6, 0x8b, 0xfb, 0xf4, 0xd7, 0x72, 0x42, 0xc5, 0x6d, - 0x23, 0x99, 0xee, 0xf6, 0x97, 0xe2, 0x28, 0x79, 0xbe, 0x48, 0x17, 0x0b, - 0x16, 0xed, 0x6e, 0x92, 0x8c, 0x37, 0x45, 0x7a, 0xb1, 0x59, 0x88, 0x20, - 0xc3, 0x02, 0xa4, 0x18, 0xff, 0x90, 0x2c, 0xe9, 0xd2, 0x31, 0x1d, 0x4a, - 0x7a, 0x12, 0x5d, 0x16, 0xc5, 0x1a, 0xc2, 0x55, 0xe5, 0x05, 0xac, 0x15, - 0xc0, 0xb8, 0x9b, 0x5d, 0x2c, 0x56, 0xd7, 0x60, 0x95, 0xae, 0xf6, 0x7e, - 0xdc, 0x24, 0x39, 0x6d, 0x9c, 0xee, 0xf5, 0xdf, 0x18, 0x1c, 0x1d, 0xbe, - 0xb1, 0xff, 0x78, 0x6f, 0xb2, 0x49, 0x17, 0x78, 0xd0, 0xa0, 0x3b, 0xee, - 0x12, 0xd9, 0x2e, 0xf9, 0x59, 0xdd, 0x74, 0xd9, 0xbd, 0x2c, 0xae, 0x16, - 0x87, 0xc6, 0xf3, 0x7e, 0x60, 0x1c, 0x16, 0xcc, 0xc4, 0xf0, 0xaf, 0x6f, - 0x81, 0x93, 0x79, 0x54, 0xfe, 0x7a, 0xcd, 0xf0, 0xcf, 0xe5, 0x6b, 0xcf, - 0xef, 0x72, 0xc4, 0x98, 0x01, 0x76, 0xc1, 0x67, 0x96, 0x2d, 0x05, 0x1a, - 0xd3, 0x7f, 0xc3, 0x7c, 0x76, 0x00, 0x3c, 0x55, 0x81, 0x44, 0x38, 0x1e, - 0x70, 0x9f, 0x46, 0xd9, 0xb9, 0xe8, 0x82, 0x3c, 0x5f, 0x59, 0x3a, 0x24, - 0x40, 0x4d, 0x5d, 0xd3, 0x07, 0x5d, 0x81, 0x65, 0xa7, 0x02, 0x09, 0x3d, - 0x55, 0xd5, 0x49, 0x23, 0x47, 0x8a, 0xc2, 0xc8, 0x80, 0xca, 0xba, 0x92, - 0x49, 0x81, 0x65, 0x92, 0x60, 0xd5, 0xa7, 0x36, 0x76, 0x2e, 0x6a, 0x4f, - 0xa9, 0x8f, 0x97, 0xf9, 0x22, 0x86, 0x31, 0x49, 0xb4, 0x15, 0xee, 0x7b, - 0x63, 0xc4, 0x0e, 0x3c, 0x89, 0xf1, 0x72, 0xbb, 0xe5, 0xc1, 0x8e, 0xc3, - 0x0a, 0xbd, 0x97, 0x2a, 0x8b, 0xc6, 0xa4, 0x49, 0x97, 0x2f, 0x2e, 0xd3, - 0xbc, 0x57, 0xdd, 0xcb, 0x33, 0x26, 0x4c, 0x55, 0x7e, 0x52, 0x64, 0x40, - 0x7d, 0x83, 0x70, 0xc7, 0x0b, 0xb8, 0x7d, 0x7f, 0x9d, 0x62, 0x8f, 0x0f, - 0xb1, 0x1c, 0xc0, 0x65, 0xb8, 0xe5, 0x40, 0x49, 0xa0, 0x51, 0xe0, 0xe8, - 0xd2, 0x1a, 0x5e, 0xdd, 0x9e, 0xcf, 0x91, 0x3b, 0x48, 0x96, 0x7e, 0x15, - 0x7f, 0xcd, 0xf2, 0x13, 0x30, 0x15, 0xe3, 0xec, 0x43, 0x96, 0x2d, 0x06, - 0xb8, 0xfe, 0xeb, 0xf8, 0x29, 0x48, 0x4b, 0x74, 0x7a, 0xc2, 0x88, 0xdd, - 0x69, 0x2b, 0x56, 0x6b, 0x04, 0x86, 0xfd, 0x68, 0x7c, 0xfd, 0xa7, 0x16, - 0x14, 0x3c, 0x35, 0xb1, 0xff, 0x4c, 0x86, 0xc3, 0xd3, 0xfe, 0x2a, 0x81, - 0xa1, 0x17, 0x4a, 0x90, 0x02, 0x08, 0xa7, 0x26, 0x58, 0xb6, 0x94, 0xb7, - 0x36, 0x9a, 0x45, 0xbf, 0xa1, 0x1c, 0xec, 0xce, 0x50, 0xd6, 0x0e, 0xcc, - 0xcc, 0x8c, 0xbb, 0x87, 0x66, 0xe9, 0x0d, 0x08, 0xa3, 0xb5, 0x48, 0x0a, - 0xae, 0x6d, 0xde, 0xa1, 0x99, 0x60, 0x52, 0x74, 0x9b, 0xad, 0x16, 0x97, - 0xce, 0x34, 0x68, 0x53, 0xa9, 0xb5, 0xf2, 0x7b, 0x5b, 0x52, 0x20, 0xf7, - 0x17, 0x08, 0x10, 0x21, 0xe1, 0x67, 0x2b, 0xd6, 0x16, 0x41, 0x6e, 0x20, - 0xbf, 0xcb, 0x30, 0x87, 0xf0, 0xe3, 0xad, 0xa8, 0xfc, 0xae, 0xef, 0xbf, - 0x4b, 0x8c, 0x5b, 0x15, 0xe3, 0x56, 0xc1, 0xb8, 0x35, 0x30, 0x04, 0x17, - 0xa7, 0x19, 0x78, 0xfc, 0x97, 0x29, 0x3a, 0xa8, 0x37, 0xb7, 0x83, 0xf5, - 0x6a, 0x31, 0xce, 0x62, 0x98, 0x04, 0xdc, 0x22, 0xa7, 0x8e, 0x10, 0x10, - 0xd1, 0xdb, 0x9c, 0xa2, 0x24, 0x66, 0x84, 0xbb, 0xfe, 0x21, 0x5d, 0x53, - 0x7c, 0x6b, 0xa0, 0x72, 0xdb, 0x06, 0xf1, 0x80, 0x15, 0x48, 0x97, 0x20, - 0x9a, 0x1c, 0x94, 0x65, 0x5c, 0xc0, 0xf8, 0x4a, 0xa3, 0x6f, 0x9e, 0xce, - 0xe0, 0xf3, 0x42, 0x19, 0x67, 0x9d, 0x27, 0xfa, 0xc0, 0xb5, 0xdb, 0x38, - 0x4e, 0x6e, 0xd9, 0xd5, 0x98, 0xd1, 0xe5, 0x16, 0x60, 0x6d, 0x00, 0xdf, - 0x62, 0xa8, 0x90, 0xc5, 0x3f, 0xad, 0xc7, 0xa5, 0xf3, 0x0d, 0x2b, 0x9f, - 0x0a, 0x26, 0x6b, 0x82, 0x67, 0xec, 0x68, 0x91, 0x92, 0xb1, 0x93, 0xe6, - 0xd1, 0x3a, 0xbd, 0x49, 0x16, 0x90, 0x46, 0x30, 0xd4, 0x3c, 0xac, 0xad, - 0x28, 0x12, 0x51, 0xcf, 0x2e, 0x3b, 0x5b, 0x5d, 0x7f, 0xc2, 0x0e, 0xdc, - 0x8e, 0x94, 0xa6, 0x1e, 0xda, 0x80, 0xe3, 0xd9, 0xf7, 0x9b, 0xbc, 0x48, - 0x66, 0xdf, 0xa2, 0xb0, 0xc1, 0xfe, 0x72, 0x40, 0xee, 0xc4, 0xc1, 0x38, - 0x0d, 0x2d, 0xce, 0x86, 0xf1, 0xd3, 0xee, 0x21, 0x45, 0xb3, 0x3d, 0xc3, - 0x58, 0x42, 0xa7, 0xfb, 0x68, 0xa7, 0xe1, 0x7b, 0x0c, 0x0c, 0xa9, 0x12, - 0x05, 0x8e, 0x9d, 0x3c, 0xb6, 0xfd, 0x45, 0xa3, 0x2f, 0x79, 0xeb, 0x2e, - 0xfa, 0x76, 0x47, 0x45, 0x93, 0x38, 0xa5, 0xc7, 0x84, 0x45, 0x26, 0xb0, - 0x8c, 0xcc, 0xc5, 0x9c, 0x25, 0x3f, 0x6e, 0xd2, 0x0c, 0x08, 0x3e, 0x8e, - 0xf2, 0xc5, 0xaa, 0xc8, 0x85, 0xdc, 0x25, 0x49, 0x9b, 0x22, 0x35, 0x17, - 0xf9, 0x12, 0x42, 0xa0, 0x50, 0xa3, 0x58, 0x56, 0xf1, 0x55, 0xd9, 0x24, - 0x6d, 0xf4, 0x32, 0x24, 0x07, 0x43, 0x97, 0xee, 0x5c, 0xd2, 0xa4, 0x09, - 0xf4, 0xc6, 0xd1, 0x64, 0xf9, 0x18, 0x16, 0x6d, 0xc6, 0x3c, 0x84, 0x5d, - 0x16, 0xed, 0xf9, 0x1b, 0x57, 0x4c, 0xbe, 0xfa, 0xbd, 0x7d, 0x67, 0x29, - 0xa7, 0x30, 0x49, 0xea, 0xb0, 0x19, 0x5e, 0x87, 0xe6, 0x72, 0x34, 0x99, - 0xcd, 0x7f, 0x1a, 0xc0, 0x3c, 0x3a, 0x06, 0x16, 0x3a, 0x4a, 0x59, 0x1d, - 0x46, 0xad, 0xed, 0xd2, 0xa1, 0xc5, 0xfa, 0x72, 0x8c, 0x8a, 0x76, 0x78, - 0x68, 0x16, 0x43, 0x32, 0x3b, 0x25, 0xe1, 0x20, 0x6d, 0x28, 0x6f, 0xe8, - 0xcb, 0x07, 0x79, 0xf5, 0x01, 0x86, 0xb1, 0x53, 0x05, 0x35, 0x00, 0x28, - 0xe2, 0xb6, 0x0a, 0xe8, 0x00, 0x80, 0x18, 0x63, 0xbe, 0x65, 0x6a, 0x7d, - 0x8c, 0x5f, 0x6f, 0x94, 0x55, 0x07, 0xd2, 0x20, 0x1a, 0x19, 0xf7, 0x8d, - 0x45, 0x61, 0xdd, 0x20, 0xe9, 0x16, 0x1a, 0x0a, 0xa4, 0xb1, 0x3a, 0xff, - 0x31, 0x2b, 0xe2, 0x1b, 0x68, 0x63, 0xe4, 0xe3, 0x16, 0x3e, 0x6f, 0x55, - 0x13, 0x0b, 0x76, 0x40, 0x00, 0x42, 0x51, 0xcb, 0x41, 0x0c, 0xeb, 0x1a, - 0x37, 0x04, 0x20, 0xd7, 0xe3, 0x84, 0x01, 0x34, 0xca, 0x16, 0xa6, 0x04, - 0x3e, 0xd5, 0x28, 0xc8, 0xf0, 0x13, 0xd4, 0x0f, 0x3a, 0xc9, 0xef, 0xbf, - 0x75, 0xa2, 0xdf, 0x7f, 0x3b, 0x83, 0x04, 0x98, 0x2e, 0x8b, 0x6c, 0x41, - 0x13, 0x10, 0x41, 0xb0, 0x04, 0x08, 0xf5, 0x02, 0xff, 0x58, 0xc2, 0xc9, - 0x82, 0x63, 0xa4, 0x0d, 0x5c, 0x73, 0x9f, 0x03, 0xa7, 0x4d, 0xb1, 0xe2, - 0x83, 0x90, 0xe6, 0x02, 0xaa, 0xce, 0x57, 0x8d, 0xc6, 0x68, 0x42, 0x9a, - 0x5e, 0x42, 0x7f, 0x06, 0x5d, 0x61, 0x59, 0x40, 0x4d, 0x82, 0x2b, 0x32, - 0x02, 0x42, 0x7d, 0x80, 0x81, 0x0f, 0x60, 0x00, 0x8a, 0x93, 0x39, 0xd0, - 0xc5, 0x38, 0x0d, 0xc0, 0x8d, 0xfb, 0x51, 0x97, 0x4b, 0x72, 0x92, 0xc7, - 0x31, 0x61, 0xbd, 0x8c, 0x4e, 0x7c, 0x17, 0x3c, 0x7e, 0x55, 0xe6, 0x59, - 0x1f, 0xb4, 0x1c, 0xfe, 0x9f, 0xf4, 0xb5, 0x45, 0x41, 0x42, 0x78, 0x1b, - 0x26, 0x0e, 0x70, 0x86, 0x8b, 0xca, 0xb4, 0x03, 0x7b, 0xc6, 0xa7, 0x12, - 0x17, 0x35, 0xea, 0x94, 0x15, 0x0e, 0x4d, 0x06, 0xba, 0x71, 0xa6, 0xcf, - 0xd7, 0x35, 0x9a, 0x7d, 0x95, 0xe6, 0xa0, 0x9a, 0x26, 0xd0, 0x62, 0x64, - 0x6b, 0x68, 0x0e, 0x54, 0x9a, 0x07, 0xd5, 0x34, 0xf7, 0x25, 0xcd, 0x9b, - 0x2a, 0x9a, 0x07, 0x2a, 0xcd, 0xc7, 0xb5, 0x34, 0x4b, 0x56, 0xab, 0x68, - 0x3e, 0x56, 0x69, 0x1e, 0xd6, 0xd6, 0x7d, 0x3f, 0x84, 0xe6, 0xa1, 0x4a, - 0xf3, 0x28, 0xac, 0x8d, 0xf6, 0x65, 0xdd, 0xa9, 0xd3, 0x4b, 0x85, 0xb8, - 0x2a, 0x35, 0xb0, 0xcb, 0xcb, 0x26, 0x28, 0xe9, 0x7e, 0xcc, 0x81, 0x18, - 0xd1, 0xa2, 0xa0, 0x60, 0x57, 0x90, 0xc0, 0x3f, 0x27, 0xf4, 0x79, 0xa6, - 0x78, 0x9d, 0xe2, 0xbe, 0x46, 0xd6, 0x99, 0x77, 0x26, 0x44, 0x55, 0x04, - 0xf3, 0x02, 0x81, 0xf5, 0xc5, 0x90, 0x05, 0xb6, 0xf1, 0x4c, 0xef, 0xe3, - 0x90, 0x02, 0x3a, 0x0c, 0x65, 0xb1, 0x2f, 0x73, 0xfe, 0x05, 0xca, 0xb5, - 0xd6, 0xca, 0xe9, 0x22, 0xd8, 0x02, 0xc6, 0xb8, 0x18, 0x23, 0xb9, 0xaa, - 0xeb, 0x58, 0x94, 0xd0, 0xc3, 0x7f, 0x9e, 0x8b, 0x45, 0x26, 0x6a, 0x51, - 0x4a, 0xa6, 0xf1, 0x2a, 0x5d, 0x96, 0xb1, 0xcb, 0x7a, 0xfa, 0x63, 0x06, - 0x12, 0xc8, 0x1f, 0x80, 0xf0, 0xb4, 0x84, 0x39, 0x93, 0x72, 0xf4, 0x97, - 0x4d, 0x5a, 0x5f, 0x26, 0xd3, 0xc1, 0x25, 0xba, 0x6a, 0x74, 0x72, 0xfc, - 0xe5, 0xb3, 0x2f, 0x9e, 0xe3, 0xba, 0x57, 0xf5, 0xcb, 0x06, 0x84, 0x3a, - 0xc5, 0x87, 0xee, 0xf1, 0xde, 0x64, 0xf5, 0x1b, 0x07, 0x52, 0x28, 0x06, - 0x16, 0x1c, 0xfa, 0x74, 0x9d, 0x7b, 0x20, 0xa1, 0x8a, 0xfd, 0x1c, 0xfb, - 0x75, 0x8b, 0xd6, 0xfb, 0x9f, 0x7f, 0x4a, 0xbb, 0x34, 0x90, 0xb6, 0x1a, - 0xcf, 0x92, 0x19, 0xcc, 0x44, 0x45, 0x03, 0x94, 0xdb, 0x13, 0xb2, 0xcd, - 0xa1, 0x20, 0x6c, 0xd9, 0x6c, 0xb3, 0x8c, 0xf2, 0x74, 0x39, 0x4d, 0x22, - 0x40, 0xc7, 0xe0, 0x8b, 0x0b, 0xc2, 0xa5, 0x17, 0x55, 0x32, 0x8c, 0xdb, - 0xc8, 0x17, 0x51, 0x93, 0x82, 0xee, 0x69, 0x89, 0x79, 0x03, 0xe5, 0xc9, - 0x0b, 0x05, 0xde, 0x68, 0xb9, 0x7a, 0x1c, 0x4e, 0x51, 0xba, 0x16, 0x61, - 0xb3, 0x2c, 0x80, 0x85, 0x30, 0x10, 0x98, 0xfa, 0x3c, 0x01, 0xfa, 0xa4, - 0x78, 0x42, 0x51, 0x5f, 0x6f, 0x93, 0x39, 0xde, 0x87, 0xd8, 0xb5, 0x7b, - 0x52, 0x6f, 0xed, 0xe5, 0xd3, 0x2c, 0x5d, 0x17, 0x6f, 0x43, 0x12, 0xfd, - 0x9c, 0xac, 0x66, 0xb7, 0xf0, 0xe3, 0xad, 0x3d, 0x5c, 0x99, 0x81, 0x2f, - 0x7f, 0x00, 0x39, 0x32, 0x9d, 0xe3, 0x7a, 0xa8, 0x01, 0x00 + 0x36, 0xb7, 0x4e, 0x03, 0x3f, 0xf3, 0x2f, 0x4c, 0x38, 0x9e, 0x03, 0x49, + 0x9a, 0xa4, 0xaf, 0xe5, 0x08, 0x81, 0x81, 0x72, 0x3d, 0x86, 0x6b, 0xe8, + 0xe3, 0x9a, 0x4e, 0xe7, 0x4d, 0x92, 0xba, 0xa9, 0x21, 0x4d, 0x82, 0xed, + 0xd0, 0x16, 0x28, 0xc3, 0x3f, 0xe4, 0x2f, 0xb1, 0xbb, 0x92, 0xac, 0xdb, + 0x96, 0xcd, 0x0b, 0x67, 0x07, 0x5e, 0x12, 0x69, 0x77, 0xb5, 0x5a, 0xad, + 0x56, 0xab, 0x6b, 0xf5, 0x6c, 0xc7, 0x42, 0x86, 0x9f, 0x4e, 0x3a, 0xb5, + 0xc2, 0xe9, 0x2a, 0xe4, 0xdf, 0xfb, 0xe2, 0x8b, 0xcf, 0xbe, 0x78, 0x36, + 0xb2, 0x9e, 0xd2, 0x62, 0xe5, 0x19, 0x65, 0xdd, 0x2b, 0x8b, 0xd9, 0xd8, + 0xca, 0x5d, 0x6a, 0x2f, 0xba, 0xfc, 0xdf, 0xf9, 0xfc, 0x33, 0x8c, 0xfb, + 0x13, 0x91, 0x06, 0x14, 0x99, 0xf4, 0xbf, 0x89, 0x33, 0x09, 0xf6, 0xc1, + 0x7b, 0x2e, 0x28, 0x02, 0x40, 0xa5, 0x65, 0x64, 0x2d, 0xd7, 0x6e, 0x99, + 0x14, 0x14, 0x2f, 0x95, 0xb5, 0xfe, 0x33, 0xde, 0xdd, 0xab, 0x6d, 0x92, + 0x2d, 0xe0, 0x07, 0xb8, 0x4e, 0xe6, 0xf6, 0xd5, 0xf0, 0x85, 0x0e, 0x2f, + 0x2a, 0x00, 0xb9, 0x7f, 0xb1, 0x59, 0x23, 0x05, 0x70, 0xbf, 0xde, 0x2e, + 0x8a, 0x2c, 0x9d, 0xef, 0x8a, 0x84, 0x8e, 0xf4, 0x6f, 0xbe, 0x87, 0xbc, + 0x59, 0x7e, 0x35, 0xcb, 0x32, 0xbc, 0xcf, 0x00, 0x64, 0x7b, 0x23, 0x38, + 0xde, 0xd3, 0xad, 0x23, 0x0d, 0x67, 0x50, 0x66, 0xab, 0x3e, 0xd7, 0x02, + 0x83, 0x35, 0xe1, 0xec, 0x0d, 0xc0, 0x49, 0x28, 0x03, 0xc3, 0x32, 0x82, + 0xbc, 0x57, 0x75, 0xf0, 0x5f, 0xe3, 0x3c, 0xdd, 0x01, 0x14, 0xf1, 0xe4, + 0x1a, 0x41, 0x81, 0x0d, 0x76, 0x24, 0x47, 0xf6, 0x91, 0x84, 0xc4, 0xe4, + 0x7c, 0xda, 0xef, 0x03, 0xf0, 0x28, 0xe5, 0x1b, 0x65, 0xab, 0x14, 0xa8, + 0xfd, 0x98, 0xce, 0xe0, 0xc1, 0xb3, 0xd3, 0xc7, 0xaf, 0x03, 0x25, 0x6b, + 0xb1, 0x21, 0x41, 0x2d, 0x87, 0x89, 0xd3, 0x6e, 0xce, 0x6e, 0x34, 0xc0, + 0x8a, 0xfa, 0x71, 0x97, 0x3a, 0x00, 0x57, 0x9d, 0x8e, 0xa5, 0xf9, 0x44, + 0x1a, 0x2a, 0xf6, 0xd1, 0xe9, 0x67, 0x9f, 0x0e, 0xb6, 0xb3, 0x8c, 0x6e, + 0xe7, 0x3b, 0x7a, 0x13, 0xbf, 0x19, 0x71, 0xcd, 0x37, 0x4a, 0x18, 0x51, + 0x19, 0xb2, 0x85, 0x35, 0x35, 0xfe, 0x31, 0x90, 0xf2, 0x32, 0x3f, 0x8c, + 0x3d, 0xd7, 0xc2, 0x86, 0x7a, 0xfe, 0x80, 0x3c, 0x81, 0x0d, 0xd6, 0xb3, + 0x6b, 0xaa, 0x41, 0xf9, 0x83, 0x5f, 0x27, 0x92, 0x6f, 0x20, 0x56, 0xfc, + 0xd1, 0x0a, 0x07, 0x95, 0xcd, 0x6e, 0x55, 0xfd, 0xcc, 0xa3, 0x22, 0x4b, + 0x6a, 0xbd, 0x28, 0xbd, 0x60, 0x3f, 0x09, 0x0e, 0x8d, 0xa7, 0x9f, 0x24, + 0xa8, 0xb4, 0x33, 0xb9, 0x71, 0xc7, 0x16, 0x0d, 0xca, 0x83, 0x3e, 0x04, + 0xbf, 0xd0, 0x28, 0x15, 0xdc, 0xaf, 0x82, 0x8c, 0xa8, 0x41, 0x31, 0xbf, + 0xda, 0xdc, 0x9c, 0xae, 0xc1, 0x5e, 0xcc, 0x67, 0x59, 0xac, 0x02, 0x97, + 0x81, 0x76, 0x7b, 0x91, 0x38, 0x0a, 0x0b, 0xd3, 0xdb, 0xe1, 0xd0, 0x65, + 0x3b, 0x30, 0xcd, 0xe8, 0xd7, 0x44, 0x98, 0x75, 0x6c, 0x10, 0x1f, 0x48, + 0x93, 0x5e, 0xab, 0x14, 0xed, 0x02, 0x43, 0x9c, 0xa6, 0xba, 0x00, 0x08, + 0xb2, 0xc7, 0x4e, 0x80, 0xc0, 0x03, 0x6a, 0x0b, 0xec, 0x0a, 0x51, 0x3f, + 0x7a, 0xf4, 0xae, 0x92, 0x91, 0x5e, 0xf0, 0xd4, 0x0f, 0xe9, 0x09, 0x4f, + 0x25, 0xe7, 0x8a, 0x12, 0xba, 0xca, 0xde, 0x1d, 0x3e, 0x33, 0x3a, 0x15, + 0x12, 0x13, 0x41, 0x9d, 0xb8, 0xd0, 0xe2, 0xce, 0xbb, 0x8f, 0xbe, 0xea, + 0xa8, 0xd0, 0xf9, 0x76, 0x5d, 0x01, 0x7d, 0xfa, 0xf9, 0xdb, 0x9f, 0x02, + 0xb8, 0xb6, 0x31, 0x58, 0x01, 0xfe, 0x48, 0x83, 0x9d, 0x17, 0x55, 0xa4, + 0xdf, 0xf9, 0xf2, 0xf1, 0xe3, 0xcf, 0x74, 0xe2, 0xf3, 0x46, 0x9c, 0x17, + 0xb7, 0x85, 0x05, 0x4d, 0xa3, 0x1c, 0x6e, 0x53, 0xc6, 0x86, 0x3c, 0x63, + 0x43, 0x94, 0x5d, 0x41, 0x0a, 0x0b, 0xc5, 0x1b, 0x75, 0x09, 0x1c, 0x4d, + 0xc0, 0x3d, 0xce, 0x18, 0xc8, 0x2a, 0x59, 0xda, 0xfe, 0x62, 0x47, 0x7b, + 0x56, 0x95, 0x03, 0x41, 0x9a, 0x86, 0x0f, 0x48, 0x5d, 0x25, 0x0b, 0x2c, + 0x02, 0xa2, 0x8a, 0x07, 0x5b, 0x65, 0x0e, 0x32, 0x32, 0x15, 0x2c, 0xc9, + 0x64, 0x8a, 0xfe, 0x01, 0xa7, 0x70, 0x21, 0xcf, 0x5a, 0x71, 0x41, 0xe0, + 0x98, 0x63, 0xe0, 0xba, 0x8b, 0xc4, 0xd2, 0xd8, 0x34, 0x1e, 0xf4, 0x55, + 0x0b, 0xf5, 0x1e, 0xc7, 0x28, 0x67, 0xe5, 0xe5, 0xa1, 0x61, 0x8e, 0x04, + 0x0d, 0xae, 0x13, 0xa7, 0xad, 0x61, 0xfc, 0xa7, 0x4f, 0x0f, 0xe1, 0x9a, + 0x4f, 0xc7, 0x4a, 0x34, 0xad, 0x3b, 0xc6, 0x8a, 0xb2, 0xd2, 0x88, 0x4d, + 0x23, 0x65, 0xf4, 0x56, 0xd4, 0xa1, 0x25, 0x8e, 0x27, 0xf3, 0xcd, 0xed, + 0x13, 0x58, 0x65, 0x02, 0x8a, 0x09, 0x7f, 0x50, 0x37, 0x7a, 0x5d, 0xc9, + 0x53, 0xc8, 0xfa, 0x04, 0x54, 0x6c, 0x96, 0xcb, 0x55, 0xc2, 0x3a, 0x1d, + 0x79, 0x3e, 0x52, 0x42, 0xa0, 0xe4, 0x86, 0x84, 0x18, 0x23, 0x1d, 0x99, + 0xad, 0x35, 0x21, 0x94, 0x52, 0x0e, 0x7f, 0x86, 0x76, 0x00, 0xa8, 0x2f, + 0x6b, 0x5e, 0xa8, 0x59, 0x5a, 0x79, 0xda, 0x03, 0xf5, 0xc7, 0xd1, 0xf5, + 0xc5, 0xc3, 0x68, 0x05, 0xbb, 0x35, 0xb7, 0xab, 0x31, 0xaa, 0x65, 0xec, + 0x17, 0x4e, 0xc4, 0x12, 0x49, 0x18, 0x41, 0x43, 0x32, 0x8c, 0x9d, 0x5d, + 0x8d, 0x2b, 0x60, 0xc5, 0x5c, 0x91, 0xcb, 0x12, 0x19, 0x41, 0x1d, 0x45, + 0x17, 0xec, 0x43, 0x98, 0x0e, 0xc8, 0xe1, 0xe1, 0x7e, 0x3c, 0x90, 0xf1, + 0xd1, 0xd3, 0x77, 0x41, 0x78, 0x85, 0x03, 0xbc, 0x90, 0x5d, 0xca, 0x16, + 0x56, 0xbf, 0xcb, 0x37, 0xeb, 0x66, 0x8e, 0x08, 0x46, 0x70, 0x8f, 0x64, + 0x50, 0x57, 0xd3, 0xf7, 0x28, 0xae, 0xb7, 0xf2, 0x96, 0x40, 0x98, 0x1b, + 0xf2, 0x96, 0xee, 0x71, 0x80, 0x1a, 0xfc, 0x7c, 0xaf, 0x4f, 0x98, 0xbe, + 0x60, 0x87, 0x1c, 0xca, 0x57, 0x75, 0xcb, 0x12, 0x6e, 0xd2, 0xe2, 0x8a, + 0x05, 0x81, 0x8d, 0x40, 0xee, 0xb9, 0x44, 0xba, 0x84, 0x0e, 0x1f, 0xf3, + 0x2b, 0x0b, 0x30, 0x3a, 0x95, 0x18, 0x5d, 0x97, 0xb3, 0xfd, 0xac, 0xc8, + 0x35, 0xc3, 0x12, 0x42, 0x7a, 0xb7, 0x8b, 0xd5, 0x87, 0xdc, 0x5d, 0xe2, + 0x75, 0x85, 0x62, 0xa5, 0xd2, 0xb8, 0xf4, 0x77, 0xde, 0xb5, 0x7d, 0x22, + 0x2d, 0x1f, 0x24, 0x63, 0xa2, 0xb8, 0x9f, 0x44, 0xa6, 0x5b, 0xd0, 0xa5, + 0x1a, 0x3f, 0x05, 0x1f, 0x8f, 0xcf, 0x12, 0xe4, 0xbb, 0x72, 0x38, 0x8e, + 0x20, 0xe5, 0x50, 0xdf, 0x05, 0x63, 0xdd, 0xf3, 0xd9, 0x47, 0xb4, 0x32, + 0xde, 0xb1, 0xd5, 0x75, 0xc1, 0x0e, 0x01, 0x1c, 0xbb, 0xdd, 0x0b, 0xc3, + 0xb9, 0x30, 0x2b, 0x2d, 0xbd, 0x8a, 0xe8, 0x13, 0xb1, 0x0d, 0x21, 0x5f, + 0x50, 0xe6, 0x8f, 0x4d, 0xe7, 0x11, 0x9e, 0x97, 0x05, 0xbb, 0xce, 0x9e, + 0x62, 0x8e, 0x2e, 0xb3, 0xcd, 0xb5, 0x78, 0x79, 0x59, 0x7d, 0xb4, 0x79, + 0x20, 0x27, 0x42, 0xda, 0x1a, 0x2d, 0x93, 0x5a, 0xb2, 0x46, 0x89, 0xd9, + 0x5a, 0x44, 0x44, 0x41, 0x8d, 0xd4, 0x0e, 0xe7, 0xd6, 0x24, 0x05, 0xc0, + 0x54, 0x26, 0xa4, 0xe1, 0xd6, 0x26, 0xdb, 0x67, 0x22, 0x58, 0xaf, 0xbe, + 0x79, 0xd7, 0x99, 0x11, 0x0d, 0x94, 0x6f, 0x6a, 0x2a, 0x5f, 0x25, 0xbc, + 0x6e, 0x47, 0x28, 0xcd, 0xd4, 0x46, 0xf9, 0x21, 0x44, 0x99, 0xc4, 0xa5, + 0xc1, 0x9a, 0x6f, 0x2e, 0xee, 0x4c, 0x2b, 0xc6, 0x9d, 0x92, 0xa9, 0xaf, + 0x64, 0x96, 0x0f, 0x48, 0xd2, 0x5d, 0xd7, 0xa6, 0x0a, 0xf8, 0x8b, 0x4f, + 0x15, 0x9e, 0xd1, 0xac, 0x4f, 0xf9, 0xca, 0xae, 0x36, 0xcd, 0xd5, 0x86, + 0x16, 0x32, 0x66, 0x82, 0xb6, 0xd5, 0xd8, 0xf2, 0x46, 0x90, 0x78, 0x62, + 0xbd, 0x74, 0x36, 0x60, 0x6e, 0xd1, 0x1f, 0xc9, 0x66, 0x75, 0xd2, 0x2e, + 0x32, 0x47, 0xcb, 0xd1, 0x64, 0xfd, 0x79, 0x28, 0x82, 0xa6, 0xed, 0xac, + 0x2a, 0xdc, 0x27, 0xee, 0x11, 0x7e, 0xd7, 0xd9, 0xbb, 0x0d, 0x2f, 0x5a, + 0x5b, 0xc8, 0xb1, 0x55, 0x42, 0x4a, 0xc9, 0x18, 0xea, 0xf4, 0x2e, 0xa6, + 0x2d, 0xdb, 0x80, 0x38, 0xaf, 0xdf, 0x05, 0x3c, 0xbe, 0x76, 0xf3, 0x3e, + 0xff, 0x19, 0x6b, 0xfe, 0xe8, 0x6a, 0x33, 0xe7, 0xf9, 0xef, 0xc0, 0xd7, + 0xf8, 0x8c, 0x8c, 0x31, 0x33, 0x28, 0xe9, 0xe5, 0x5d, 0x29, 0xb9, 0xee, + 0x79, 0x2f, 0xfa, 0x99, 0xdd, 0x99, 0x7a, 0x80, 0x3d, 0x34, 0x65, 0x57, + 0xd3, 0x0e, 0x70, 0x04, 0x79, 0x20, 0x78, 0x2e, 0x4b, 0xe4, 0xc3, 0x73, + 0xfc, 0x40, 0xa0, 0x3f, 0xe8, 0x51, 0x49, 0xbd, 0xe8, 0x81, 0x36, 0xf6, + 0xd0, 0x56, 0x83, 0x73, 0xd6, 0x70, 0xca, 0x6e, 0x91, 0xd0, 0x08, 0x23, + 0xa8, 0x76, 0xeb, 0x07, 0xb6, 0x04, 0x0c, 0x9b, 0x82, 0x61, 0x8c, 0x69, + 0x4f, 0xc3, 0x7e, 0x2a, 0x2c, 0x7e, 0x79, 0x72, 0xf2, 0xde, 0xe9, 0xa9, + 0xd1, 0x00, 0x68, 0x05, 0x7b, 0x72, 0xc0, 0x09, 0x99, 0x92, 0x99, 0xbd, + 0x83, 0x46, 0x34, 0xf0, 0x11, 0x72, 0xb6, 0x86, 0x04, 0x14, 0x0f, 0x69, + 0x72, 0xd6, 0xd8, 0x96, 0x97, 0xdd, 0x0b, 0xc4, 0xc2, 0x5c, 0x6b, 0xd1, + 0x3f, 0x82, 0x0d, 0x3e, 0x9b, 0xac, 0x32, 0x81, 0x38, 0x6a, 0xda, 0xbe, + 0x7e, 0x4d, 0xe6, 0x9f, 0x8a, 0xba, 0xeb, 0x3e, 0x70, 0xc2, 0x76, 0x08, + 0xed, 0x8e, 0xfa, 0xac, 0xf2, 0xb3, 0x5c, 0xd1, 0xf2, 0x7a, 0xeb, 0xcd, + 0x9d, 0x74, 0xe8, 0x3a, 0xb8, 0x60, 0x0a, 0x74, 0x42, 0x4c, 0x8b, 0xb2, + 0xfe, 0xa6, 0x32, 0x06, 0xfa, 0x87, 0x44, 0x2c, 0xc3, 0xe3, 0xa4, 0x99, + 0x63, 0x9f, 0x4b, 0x62, 0x80, 0xef, 0x45, 0x23, 0xfd, 0xc0, 0x28, 0x11, + 0xb6, 0xe9, 0xe2, 0x40, 0x10, 0x42, 0x19, 0x17, 0x49, 0x4c, 0x56, 0xef, + 0x9d, 0x9d, 0x92, 0xcd, 0xcc, 0x69, 0xe1, 0x24, 0xa7, 0xf9, 0xb9, 0x8b, + 0x9e, 0x3d, 0xa2, 0x6f, 0xd6, 0xa7, 0xe2, 0xb1, 0x07, 0x58, 0xc8, 0x86, + 0x55, 0xd5, 0x15, 0x6c, 0x68, 0x96, 0x6c, 0x99, 0x07, 0x52, 0x22, 0x96, + 0xcf, 0x19, 0xd1, 0xca, 0x2f, 0x5f, 0xd7, 0x26, 0xf0, 0xd7, 0x81, 0x01, + 0x0e, 0x2c, 0x6d, 0x66, 0x74, 0x0a, 0x1a, 0x18, 0xe9, 0x80, 0xfc, 0xd4, + 0x82, 0xb2, 0x9e, 0x0d, 0xa5, 0x38, 0x3c, 0xee, 0xfc, 0x9d, 0xbb, 0x13, + 0x31, 0xa3, 0x89, 0x3b, 0x8c, 0x25, 0xba, 0x1f, 0x0a, 0x9b, 0xb7, 0x4b, + 0xb0, 0x47, 0x62, 0xd0, 0x91, 0x8e, 0x41, 0x0a, 0x84, 0x86, 0x13, 0xf8, + 0x78, 0x23, 0xba, 0xe5, 0x4b, 0x54, 0xf0, 0x0b, 0x42, 0xde, 0xa8, 0x32, + 0xbf, 0x3d, 0x4b, 0xcf, 0xd5, 0xa9, 0x12, 0x25, 0xb8, 0xcf, 0xf0, 0xca, + 0x59, 0xed, 0x6b, 0xfc, 0x1c, 0xaf, 0x4c, 0x39, 0xec, 0x18, 0x8d, 0x03, + 0xb5, 0xa8, 0xbf, 0x9f, 0x60, 0xcb, 0xe8, 0x56, 0xe7, 0xa5, 0x8e, 0x91, + 0x43, 0x8b, 0x91, 0xd7, 0x3a, 0xaa, 0xb8, 0x13, 0x7e, 0xa5, 0x8b, 0x3d, + 0x76, 0x11, 0xcd, 0xd6, 0x17, 0xe5, 0x8e, 0x74, 0xb1, 0x31, 0x1a, 0x02, + 0xb0, 0xf4, 0xd3, 0xa5, 0xc6, 0xb9, 0xa3, 0xb3, 0x4e, 0x86, 0xfc, 0x72, + 0x0d, 0x81, 0x7e, 0x31, 0x82, 0x8e, 0xc9, 0x7f, 0xd0, 0xec, 0xf0, 0x5c, + 0x3d, 0x66, 0xe9, 0x25, 0xb2, 0x0c, 0x23, 0x32, 0x07, 0x6c, 0x2f, 0x8d, + 0x79, 0x18, 0x0d, 0xdc, 0x52, 0xf3, 0x13, 0xb9, 0x09, 0x23, 0xe2, 0xdb, + 0x33, 0xf3, 0xef, 0x31, 0xd9, 0xfb, 0x4b, 0xf7, 0xc6, 0xb6, 0xbf, 0xd3, + 0x81, 0x86, 0xb1, 0xa2, 0x74, 0xc9, 0xa8, 0x79, 0xc4, 0x0f, 0xde, 0x4e, + 0xb2, 0x87, 0x60, 0x46, 0x95, 0x7a, 0x09, 0x44, 0xab, 0x4b, 0xd0, 0x3e, + 0x93, 0xea, 0x2b, 0x53, 0xf9, 0x4e, 0x27, 0xd9, 0xf4, 0x90, 0x11, 0xd3, + 0xed, 0x21, 0x23, 0x5d, 0x0a, 0x62, 0x53, 0xb5, 0xd8, 0x06, 0xcf, 0xce, + 0x3c, 0x92, 0x8b, 0x6d, 0xf8, 0xc7, 0x71, 0x8c, 0xd9, 0x38, 0x35, 0x56, + 0xa7, 0x47, 0x8c, 0xda, 0xc0, 0xce, 0x09, 0xf6, 0x19, 0xc2, 0x9e, 0x0f, + 0xca, 0xb7, 0xf7, 0x24, 0x16, 0x81, 0x68, 0x8b, 0x11, 0x8c, 0x8c, 0xd1, + 0x55, 0x09, 0x4a, 0x68, 0x89, 0x36, 0x1a, 0x4e, 0x24, 0x40, 0xa3, 0x33, + 0x59, 0x17, 0x9b, 0xa8, 0x74, 0x86, 0xa3, 0xab, 0x24, 0x4b, 0x0c, 0xef, + 0x91, 0xa6, 0x2d, 0x39, 0x0f, 0x90, 0x50, 0xd5, 0x92, 0x1c, 0x48, 0x36, + 0xa5, 0x44, 0x13, 0x1c, 0x83, 0xae, 0x9a, 0x59, 0x0d, 0x78, 0xa5, 0x9b, + 0xec, 0xe0, 0x0b, 0x1a, 0x64, 0x45, 0x69, 0xde, 0x12, 0xed, 0x0a, 0x89, + 0x6b, 0xf7, 0x95, 0xf5, 0xe1, 0x30, 0xb2, 0x3a, 0x22, 0x41, 0xd0, 0xe6, + 0x97, 0xf9, 0x07, 0x22, 0x5d, 0x07, 0x6b, 0x52, 0x33, 0x9d, 0x10, 0x90, + 0x36, 0xca, 0x9a, 0xd8, 0x42, 0xe8, 0x9c, 0x5c, 0x81, 0x4d, 0x30, 0x31, + 0xbb, 0x8e, 0xca, 0xca, 0x80, 0x02, 0x55, 0xb5, 0x2d, 0x81, 0x44, 0x75, + 0x25, 0x9a, 0x59, 0xdf, 0x32, 0xc3, 0x04, 0x6c, 0x5e, 0x63, 0x95, 0x35, + 0x49, 0xc6, 0x5f, 0xe7, 0x6b, 0xac, 0xb4, 0x85, 0xec, 0xaf, 0xf5, 0x76, + 0x93, 0xd5, 0xd7, 0x1a, 0x80, 0x64, 0xad, 0x45, 0x8a, 0x5d, 0x6b, 0x91, + 0x61, 0x00, 0xb6, 0xad, 0x35, 0x67, 0x4d, 0x7c, 0xaf, 0xac, 0xf5, 0x16, + 0x6a, 0x6d, 0x22, 0xfb, 0x6b, 0x4d, 0x51, 0x21, 0x6a, 0x6b, 0x8d, 0x40, + 0xb2, 0xd6, 0x22, 0xc5, 0xaa, 0xb5, 0xc8, 0x30, 0x01, 0x5b, 0xd6, 0x9a, + 0xb1, 0x26, 0xc9, 0x54, 0xd5, 0x7a, 0x07, 0xb5, 0xb6, 0x90, 0x2b, 0xda, + 0x1a, 0xbc, 0x8f, 0xda, 0x5a, 0x23, 0x90, 0xac, 0xb5, 0x48, 0xb1, 0x6a, + 0x2d, 0x32, 0x4c, 0xc0, 0x96, 0xb5, 0x66, 0xac, 0x49, 0x32, 0x55, 0xb5, + 0xc6, 0xa1, 0xde, 0x42, 0x76, 0xd6, 0x1a, 0x86, 0x5a, 0x1e, 0x4b, 0xc3, + 0x5f, 0x6d, 0xe1, 0xea, 0x02, 0xa0, 0x3a, 0xc2, 0x1a, 0x3e, 0xa7, 0x28, + 0x8f, 0xd8, 0x58, 0x0a, 0xc7, 0x73, 0xcf, 0xc3, 0x66, 0x5a, 0x33, 0x66, + 0xa6, 0x32, 0x5b, 0xa9, 0x6a, 0xfd, 0x10, 0x29, 0x61, 0xcb, 0x66, 0x65, + 0xbe, 0x14, 0x4f, 0x9d, 0x18, 0x60, 0x4d, 0x3a, 0xb0, 0x46, 0x08, 0x08, + 0x4b, 0x22, 0xfe, 0x26, 0x3d, 0xcd, 0xa1, 0x45, 0x75, 0x4c, 0x57, 0x73, + 0x52, 0x24, 0x0e, 0x9e, 0x9f, 0x07, 0x35, 0xe8, 0x62, 0x2d, 0xcd, 0x96, + 0x8a, 0x2c, 0xaa, 0xad, 0xb7, 0xaa, 0x0d, 0xd8, 0x42, 0x9b, 0x19, 0x29, + 0x20, 0xad, 0x91, 0xf1, 0x6b, 0x73, 0x8e, 0x75, 0xd7, 0x91, 0xb5, 0xe1, + 0x1a, 0x5a, 0x31, 0x89, 0x62, 0x45, 0x8a, 0x97, 0x69, 0x96, 0x17, 0xd4, + 0xb8, 0xd6, 0x92, 0x89, 0x84, 0xe2, 0xe1, 0xaa, 0x08, 0xcc, 0x83, 0x6c, + 0xcf, 0xff, 0xdb, 0x69, 0xfe, 0x9f, 0xd1, 0xfe, 0x66, 0x3d, 0x20, 0xa0, + 0x17, 0x04, 0xf7, 0x04, 0xa5, 0xda, 0x0d, 0x7a, 0x84, 0xa6, 0x8d, 0xdb, + 0x74, 0x5d, 0xaf, 0x84, 0x00, 0x24, 0x6a, 0x8c, 0x08, 0x0e, 0xc5, 0x83, + 0x54, 0x99, 0xdf, 0x4a, 0xdf, 0x18, 0x23, 0xf0, 0x6f, 0x95, 0x9a, 0x89, + 0x01, 0x52, 0xe2, 0x38, 0xbb, 0x18, 0x06, 0x3a, 0xaa, 0xaf, 0x15, 0x42, + 0xf9, 0xa7, 0x23, 0x12, 0x66, 0xff, 0x26, 0x32, 0x60, 0x66, 0x21, 0xd9, + 0x61, 0x73, 0x0b, 0x05, 0x1a, 0x13, 0xeb, 0xcd, 0x25, 0x41, 0xd9, 0x0d, + 0x87, 0xc9, 0x13, 0x09, 0xd1, 0xaa, 0xe9, 0xb8, 0xb8, 0xf1, 0xa3, 0xaa, + 0xf1, 0x70, 0xaa, 0x6e, 0x60, 0xb9, 0xc7, 0xbb, 0x62, 0x56, 0xed, 0xcd, + 0xb1, 0x59, 0xb3, 0x74, 0xe6, 0x18, 0x86, 0x21, 0x5b, 0x08, 0x09, 0xda, + 0xe9, 0xc9, 0xd2, 0x16, 0x18, 0xbc, 0x56, 0x83, 0xb7, 0x27, 0xe1, 0x94, + 0x2c, 0x41, 0x1a, 0xb9, 0x7c, 0x3a, 0x11, 0xa0, 0x8a, 0x9f, 0x55, 0xa3, + 0xc5, 0x19, 0x48, 0xc3, 0xc0, 0xf2, 0x48, 0x63, 0xb3, 0xad, 0x15, 0xc6, + 0x66, 0x2b, 0x65, 0x01, 0x3f, 0x1a, 0x89, 0x02, 0xc0, 0x6d, 0x49, 0x40, + 0xaa, 0x02, 0xd0, 0x4e, 0x0e, 0xc4, 0x37, 0x7e, 0x54, 0x48, 0xe1, 0x5c, + 0x97, 0x02, 0x00, 0x3b, 0x85, 0xb0, 0xd8, 0xec, 0x42, 0xbc, 0x1f, 0x04, + 0x93, 0x5a, 0x41, 0xbf, 0x2c, 0x95, 0xa7, 0xfa, 0x4b, 0x88, 0x46, 0x6e, + 0x81, 0x46, 0x03, 0x68, 0x12, 0x7e, 0x95, 0xca, 0x2f, 0x74, 0x95, 0x5f, + 0x48, 0x97, 0xa0, 0x8d, 0xda, 0xb6, 0x68, 0x5e, 0x4d, 0x8a, 0xec, 0xe5, + 0xc8, 0x7a, 0x31, 0x32, 0xb8, 0x2a, 0xd3, 0x28, 0xa1, 0xfe, 0x41, 0xc6, + 0x91, 0x31, 0x64, 0x99, 0x47, 0x96, 0x5c, 0x6f, 0x20, 0x39, 0x9c, 0xd0, + 0x97, 0xb8, 0xd4, 0x4a, 0x11, 0xcc, 0x2d, 0x7a, 0x11, 0xdf, 0xd5, 0x44, + 0x2c, 0x09, 0xde, 0x40, 0x79, 0x6c, 0x7a, 0x53, 0xbd, 0xcc, 0x5f, 0x22, + 0xfe, 0x2c, 0xa7, 0xfc, 0xcd, 0x1f, 0xb5, 0x94, 0x09, 0xec, 0x8d, 0xca, + 0x8a, 0x0e, 0xb5, 0x01, 0x8d, 0xb3, 0x8b, 0xf2, 0xa8, 0x03, 0x95, 0x16, + 0xa4, 0x0f, 0x08, 0x18, 0xa0, 0x10, 0x08, 0xf6, 0xcf, 0xd2, 0x08, 0xe4, + 0xc8, 0x52, 0x09, 0x9e, 0x1e, 0xa4, 0x13, 0x08, 0x58, 0xa3, 0x14, 0xa3, + 0x31, 0xa2, 0x49, 0xf8, 0x26, 0x4b, 0x42, 0xff, 0x44, 0xad, 0x20, 0xea, + 0x41, 0x6a, 0x41, 0x90, 0x01, 0x7a, 0x41, 0x70, 0xff, 0x2c, 0xc5, 0x20, + 0x96, 0x2c, 0xcd, 0x10, 0x19, 0x41, 0xaa, 0x41, 0x90, 0xd5, 0xba, 0x01, + 0xe6, 0x42, 0x07, 0xff, 0x97, 0xab, 0x06, 0x10, 0x0b, 0x33, 0x18, 0x00, + 0x18, 0x62, 0x30, 0x00, 0xec, 0x1f, 0x66, 0x30, 0x90, 0x23, 0x5b, 0x2d, + 0x28, 0x3d, 0xcc, 0x60, 0x00, 0x60, 0x8d, 0xc1, 0x38, 0xee, 0xaa, 0xc0, + 0xff, 0x5a, 0x6b, 0x41, 0xc1, 0x6f, 0x29, 0xf6, 0xad, 0xbd, 0x53, 0xa1, + 0x04, 0xc6, 0x6d, 0xb7, 0x61, 0xa1, 0x9f, 0xb6, 0x9a, 0x32, 0x74, 0x26, + 0xf2, 0xfc, 0x8c, 0x7e, 0x88, 0x9d, 0xc2, 0x47, 0xb8, 0x77, 0x7e, 0xce, + 0x58, 0x70, 0xcf, 0x70, 0x17, 0xdf, 0x57, 0xaf, 0x93, 0x32, 0x08, 0x3c, + 0x05, 0x2c, 0x55, 0x96, 0xa5, 0x0d, 0x68, 0x1f, 0x9f, 0xae, 0x92, 0xcb, + 0x23, 0x41, 0x4a, 0x3c, 0x60, 0x76, 0x74, 0x8a, 0x3d, 0xc5, 0xdf, 0x51, + 0x6e, 0xc1, 0x66, 0xb3, 0x1b, 0x65, 0x8f, 0x13, 0xf6, 0xdb, 0xe8, 0x54, + 0x22, 0xa5, 0xb3, 0x9d, 0x38, 0xce, 0x54, 0xb1, 0xe1, 0xa7, 0x11, 0x05, + 0x71, 0x59, 0x78, 0xa3, 0xa5, 0x57, 0x27, 0x6f, 0xc0, 0xb3, 0x5e, 0x0b, + 0x38, 0xb5, 0x50, 0x32, 0x1b, 0x95, 0xa1, 0x8c, 0x39, 0xd7, 0x6e, 0xce, + 0x3d, 0x0b, 0x92, 0x05, 0x9d, 0xeb, 0xa2, 0x63, 0x24, 0xef, 0x5d, 0x5e, + 0x26, 0x8b, 0xba, 0x95, 0xac, 0xa2, 0x6f, 0x21, 0x08, 0x71, 0x39, 0xa9, + 0x09, 0x8e, 0x35, 0xbf, 0x9d, 0xa0, 0xbc, 0x48, 0x2d, 0x97, 0xb9, 0x88, + 0x0a, 0x14, 0x53, 0xc5, 0x85, 0x75, 0x36, 0xcc, 0x0f, 0x0a, 0xb6, 0x2c, + 0xf0, 0x92, 0x86, 0x8b, 0xca, 0x7c, 0x49, 0xca, 0xd1, 0xe9, 0x36, 0x3f, + 0x92, 0x6e, 0x4f, 0x3e, 0x92, 0x11, 0x88, 0x38, 0xda, 0xd7, 0x9f, 0x79, + 0x1c, 0x68, 0xcf, 0xf5, 0xee, 0x74, 0xfc, 0xf5, 0x1c, 0x3e, 0xcd, 0x7a, + 0x2a, 0xf5, 0x72, 0xce, 0x43, 0x57, 0xd7, 0xb3, 0x74, 0x5d, 0x7b, 0x8e, + 0xa2, 0x8f, 0x50, 0x42, 0xc3, 0x05, 0x96, 0x6d, 0x25, 0x95, 0x00, 0xe7, + 0x2a, 0x68, 0xa3, 0x15, 0x34, 0x17, 0x31, 0x28, 0x43, 0x29, 0xd3, 0xda, + 0x19, 0xbf, 0x4a, 0x6e, 0x09, 0xac, 0x8a, 0x15, 0x09, 0x7d, 0x97, 0xfe, + 0x80, 0xa6, 0x24, 0xa6, 0xf3, 0xd6, 0x8f, 0x60, 0xf8, 0x15, 0xe8, 0xfc, + 0x20, 0x5c, 0x3c, 0xea, 0x8d, 0xbb, 0xbd, 0xd1, 0x71, 0xf7, 0xa5, 0xf1, + 0x6b, 0xaf, 0x75, 0x5f, 0xf6, 0xc3, 0x1d, 0x0a, 0xb8, 0xa3, 0x57, 0x5f, + 0xa9, 0x82, 0x3b, 0x12, 0x70, 0xa3, 0xd1, 0xc3, 0x6e, 0xf7, 0x60, 0x04, + 0xe7, 0xbc, 0x42, 0x22, 0x5a, 0x16, 0x9b, 0xcd, 0x6a, 0x3e, 0x6b, 0xd0, + 0x79, 0xa8, 0xd0, 0x10, 0xca, 0x97, 0x9b, 0x4d, 0x91, 0xec, 0x83, 0xb0, + 0xc9, 0xb2, 0x68, 0x95, 0x18, 0x64, 0x4e, 0x81, 0x03, 0xc7, 0x47, 0x68, + 0xb3, 0x1f, 0x3c, 0x37, 0x1a, 0x8d, 0x1e, 0x44, 0xaf, 0xc3, 0x97, 0xf7, + 0xde, 0x7b, 0xef, 0x41, 0x08, 0x65, 0x62, 0x79, 0x7f, 0x84, 0xe9, 0x96, + 0x4b, 0x3b, 0xea, 0x66, 0x7f, 0xc2, 0xd0, 0xff, 0xf5, 0xfd, 0x09, 0xa1, + 0x44, 0x7f, 0x12, 0x58, 0xbe, 0xfe, 0x84, 0x79, 0x2a, 0x64, 0xa3, 0x25, + 0x1e, 0x9b, 0x16, 0x70, 0xa7, 0x97, 0x18, 0x22, 0x26, 0x3a, 0x78, 0x6b, + 0x0a, 0xc8, 0x45, 0xdc, 0x23, 0x15, 0xd4, 0xb1, 0x7a, 0xa9, 0x20, 0x94, + 0x90, 0x8a, 0xc0, 0xf2, 0x49, 0x05, 0xf3, 0x74, 0xc8, 0xf6, 0x52, 0x61, + 0xdc, 0x09, 0x3a, 0xe1, 0x52, 0xe1, 0x87, 0xef, 0x9b, 0xf4, 0x25, 0x04, + 0x08, 0x21, 0x2d, 0x4e, 0xde, 0x3c, 0x7d, 0xca, 0xe5, 0x3e, 0xdc, 0xbe, + 0x48, 0xe3, 0x42, 0xf8, 0xbe, 0x68, 0xb3, 0xc9, 0xc1, 0x1e, 0xa9, 0xc3, + 0x5c, 0x63, 0x6f, 0x32, 0x17, 0x53, 0x97, 0x3d, 0xd2, 0x87, 0x99, 0x50, + 0x7b, 0xf6, 0xf9, 0x69, 0xc6, 0x22, 0xb9, 0x2d, 0x0e, 0xe8, 0x06, 0x20, + 0xeb, 0xe7, 0x17, 0xc9, 0x96, 0x9d, 0x45, 0x8f, 0x20, 0x49, 0xd2, 0x8c, + 0x30, 0xd8, 0x2a, 0xc6, 0xdb, 0x0a, 0x1d, 0x8c, 0x11, 0xf5, 0x9f, 0x3d, + 0x16, 0x8b, 0xa8, 0xb8, 0x79, 0xc8, 0xf1, 0x58, 0x79, 0x3d, 0x52, 0x4e, + 0xdc, 0x3d, 0x47, 0x63, 0x89, 0xa6, 0xf7, 0x78, 0x2c, 0xfc, 0x31, 0x08, + 0x38, 0x15, 0x5b, 0x37, 0x02, 0x8d, 0xc7, 0x63, 0xe7, 0xf8, 0x76, 0x1f, + 0xac, 0x24, 0xa7, 0xc9, 0x12, 0x62, 0xfd, 0xb6, 0x1b, 0xeb, 0xe0, 0x2f, + 0xe0, 0x1c, 0xdd, 0x7e, 0xc8, 0xb3, 0xe8, 0x45, 0x7b, 0x20, 0x4c, 0x47, + 0x69, 0xf7, 0x43, 0x1a, 0x0f, 0xd8, 0xee, 0x87, 0x32, 0x1e, 0xbb, 0xdd, + 0x13, 0x69, 0x16, 0x3b, 0x66, 0x3f, 0xb4, 0xf3, 0x6d, 0xb2, 0xaf, 0x66, + 0x14, 0xc6, 0xa6, 0x1d, 0x69, 0xcb, 0x5f, 0x29, 0x02, 0x26, 0x45, 0x00, + 0xa4, 0x79, 0x2b, 0x85, 0x77, 0x4a, 0x04, 0x59, 0x2a, 0xdc, 0x9f, 0x98, + 0x0f, 0x11, 0x63, 0x9c, 0x4a, 0xb8, 0xa3, 0x22, 0x88, 0xf4, 0x61, 0x75, + 0xa6, 0xc9, 0xf8, 0x50, 0xac, 0x43, 0xa8, 0xb3, 0x55, 0x99, 0xfa, 0x49, + 0xaf, 0x4d, 0xbd, 0xd1, 0x4a, 0xc4, 0x53, 0x9e, 0x82, 0x57, 0x72, 0xc3, + 0x6c, 0xe5, 0x93, 0xd9, 0xa2, 0x48, 0x61, 0xdd, 0x8f, 0xdd, 0xeb, 0x8f, + 0xbb, 0x7e, 0x65, 0xc9, 0x83, 0xb4, 0x05, 0xa8, 0x1a, 0x0a, 0x93, 0x7b, + 0x35, 0x86, 0xa0, 0x35, 0xd8, 0x26, 0x0b, 0x42, 0x4e, 0x6a, 0x50, 0x8a, + 0x56, 0x6a, 0xe3, 0xfa, 0x72, 0x07, 0x81, 0x5e, 0x4d, 0xba, 0x9c, 0x2d, + 0x12, 0x1e, 0x3d, 0xbd, 0x49, 0x48, 0x3d, 0x3e, 0x8f, 0xf7, 0x46, 0x72, + 0x92, 0x93, 0x9c, 0x1a, 0x10, 0x6c, 0x50, 0x0f, 0x08, 0x5c, 0xbd, 0x09, + 0xeb, 0x0d, 0xec, 0xd1, 0x46, 0x97, 0x58, 0x57, 0xa0, 0xd2, 0x42, 0xaa, + 0x4f, 0xd7, 0x3f, 0x10, 0x97, 0xb2, 0xa7, 0xf5, 0xfc, 0x59, 0x78, 0xb3, + 0x8c, 0x2b, 0xae, 0xbc, 0xb3, 0x42, 0xd7, 0xa2, 0x60, 0x0b, 0x21, 0xea, + 0x98, 0xb7, 0xa3, 0x01, 0xb8, 0xbc, 0x87, 0x25, 0x62, 0x21, 0x74, 0xed, + 0x2b, 0x51, 0xf4, 0xa7, 0xd3, 0x8c, 0x5e, 0x9e, 0xca, 0xa8, 0x04, 0xd6, + 0x6d, 0x4f, 0xcc, 0x48, 0x58, 0xd0, 0x4a, 0xb8, 0x0f, 0x96, 0xe4, 0x74, + 0xe3, 0x45, 0x3c, 0x98, 0x15, 0x31, 0xd5, 0xc9, 0x15, 0x24, 0xfd, 0x86, + 0xeb, 0xf5, 0x6c, 0xab, 0xde, 0x6e, 0x8d, 0xf4, 0x3f, 0xf3, 0x22, 0x97, + 0xc5, 0x67, 0x9d, 0x2d, 0x12, 0xb7, 0xb8, 0xf0, 0x36, 0x3d, 0xa4, 0x7d, + 0x0a, 0x3f, 0xc3, 0xea, 0x65, 0x38, 0x51, 0x9a, 0xda, 0xff, 0x39, 0xd7, + 0x4e, 0x75, 0xef, 0xfc, 0x6c, 0x71, 0xae, 0x9a, 0x86, 0xd4, 0xd1, 0xdb, + 0x8d, 0x74, 0xc3, 0x7d, 0x9f, 0x89, 0x57, 0x9b, 0xdf, 0x65, 0xea, 0x74, + 0xad, 0x66, 0xa5, 0x9b, 0x8b, 0x66, 0xb3, 0xce, 0x56, 0xab, 0xbf, 0xaa, + 0x45, 0x51, 0xae, 0x4c, 0x3a, 0xd1, 0xb4, 0x49, 0xf3, 0x4e, 0xdc, 0xe4, + 0x08, 0x40, 0x97, 0x0d, 0x25, 0xb5, 0x13, 0xcf, 0xdf, 0xa9, 0x1d, 0x53, + 0x5f, 0xbe, 0x5d, 0x8b, 0xea, 0x4a, 0xdc, 0xdb, 0x6b, 0xc1, 0xb5, 0xd1, + 0x37, 0x34, 0xc7, 0xa1, 0x89, 0xa9, 0x74, 0xed, 0x9c, 0x55, 0xd9, 0x3c, + 0xb9, 0xf9, 0x06, 0xa5, 0x18, 0xa3, 0x93, 0x71, 0xed, 0xf6, 0x29, 0x4f, + 0xd8, 0xc2, 0x54, 0x39, 0x44, 0x8d, 0x1b, 0x68, 0x6d, 0x98, 0x51, 0x52, + 0x5b, 0xec, 0x29, 0xce, 0x31, 0x9b, 0xb0, 0xa1, 0xb0, 0x20, 0xbf, 0x05, + 0xf8, 0x84, 0x72, 0x0c, 0xf3, 0x95, 0xe1, 0x8b, 0x7f, 0xa1, 0x5f, 0xa1, + 0xbe, 0xce, 0x97, 0x18, 0x54, 0xfe, 0xae, 0x17, 0xe1, 0xc3, 0xb1, 0x50, + 0xa7, 0xda, 0x4b, 0xac, 0xbc, 0x7c, 0x4e, 0xa0, 0x6c, 0xea, 0x5b, 0x6d, + 0x7b, 0x1c, 0xc8, 0x8a, 0x74, 0xaf, 0x83, 0x18, 0x43, 0xb1, 0x38, 0x5e, + 0x8a, 0x2b, 0xda, 0xb4, 0xdd, 0xf8, 0xdc, 0xec, 0x62, 0xfc, 0xca, 0xf8, + 0x15, 0xda, 0x6f, 0x7c, 0xee, 0xe1, 0x62, 0x76, 0x79, 0x34, 0xec, 0x48, + 0xef, 0xe8, 0xed, 0x75, 0x7a, 0x3d, 0xa3, 0x4a, 0xa4, 0x39, 0x31, 0x7c, + 0xc1, 0x42, 0xb4, 0x90, 0x08, 0xe8, 0x8a, 0x54, 0x8c, 0x37, 0xd9, 0xd9, + 0x65, 0xef, 0x08, 0x4a, 0x19, 0xe1, 0x97, 0xae, 0xeb, 0x5e, 0x6a, 0x07, + 0xc5, 0x00, 0x1b, 0xd7, 0x44, 0x86, 0x97, 0xe0, 0x7e, 0x06, 0x3c, 0xe0, + 0x42, 0xab, 0x46, 0x8c, 0xd9, 0x86, 0xe8, 0x9e, 0x8b, 0x54, 0x86, 0xcd, + 0x54, 0x1f, 0x6c, 0x07, 0xe5, 0xa0, 0x50, 0x99, 0x2b, 0xf8, 0x71, 0x93, + 0x8b, 0x17, 0xf4, 0xe5, 0x5b, 0x9f, 0xf6, 0xd3, 0xf7, 0xd1, 0x08, 0x6b, + 0xc6, 0x72, 0x95, 0xa7, 0xf4, 0xa3, 0x31, 0x4f, 0xcb, 0x12, 0x89, 0xf3, + 0x6e, 0xb2, 0x9a, 0xdd, 0x7d, 0x90, 0x6d, 0x6e, 0xde, 0x9f, 0xe1, 0xd3, + 0x94, 0x12, 0x88, 0x5e, 0x5a, 0x66, 0x6f, 0x88, 0x02, 0x5b, 0x13, 0xfd, + 0x75, 0x40, 0x71, 0xe1, 0x7f, 0xb5, 0xd2, 0xef, 0xfc, 0xeb, 0x77, 0x3c, + 0xe9, 0xd5, 0xe4, 0x68, 0xbb, 0x29, 0x40, 0x17, 0x52, 0x18, 0xc0, 0xee, + 0xe8, 0x6d, 0x6e, 0x85, 0xe1, 0x5c, 0xb9, 0x76, 0xed, 0x7c, 0x42, 0x54, + 0xc6, 0xe1, 0x88, 0x31, 0xd1, 0x0a, 0x7c, 0x0a, 0x69, 0xfc, 0x85, 0x71, + 0xaa, 0x72, 0xd4, 0xf9, 0x64, 0xb6, 0xde, 0x51, 0x49, 0x94, 0x7a, 0xf1, + 0xfa, 0xeb, 0x15, 0xcc, 0x52, 0xd8, 0x80, 0x9f, 0xbf, 0x4f, 0x92, 0xed, + 0x09, 0x01, 0xb3, 0xca, 0xde, 0x2b, 0xbe, 0x76, 0x2d, 0x7b, 0xd0, 0x0a, + 0x67, 0xe7, 0x2a, 0x98, 0xff, 0x31, 0x54, 0xb4, 0x0f, 0xda, 0x64, 0xa5, + 0x72, 0x5a, 0x2b, 0x69, 0xf4, 0x01, 0x92, 0xba, 0x8e, 0xee, 0x7a, 0x42, + 0xaa, 0xcf, 0xf5, 0x6c, 0xec, 0x76, 0x02, 0xad, 0x1a, 0xd3, 0xa0, 0x5f, + 0xea, 0xe5, 0xb5, 0xf2, 0x35, 0x7d, 0x8d, 0x82, 0x00, 0x4d, 0xa9, 0x21, + 0x04, 0x46, 0x01, 0x67, 0x61, 0x7a, 0xc4, 0x37, 0xcf, 0x77, 0x18, 0xc9, + 0x9f, 0x06, 0x20, 0x06, 0x07, 0x8a, 0xcf, 0x7e, 0x7a, 0x8e, 0x81, 0x88, + 0xda, 0x4f, 0x44, 0xed, 0x19, 0xb4, 0x54, 0x1d, 0xbc, 0xe1, 0x67, 0xaa, + 0x0e, 0xa6, 0xf1, 0x5b, 0x92, 0x03, 0xe8, 0x1e, 0xd7, 0x56, 0x48, 0x23, + 0x02, 0xa0, 0x08, 0x1c, 0x76, 0xec, 0x0d, 0xe0, 0x88, 0x84, 0xc0, 0xe7, + 0x57, 0x5f, 0x88, 0xfe, 0x04, 0x9c, 0x95, 0x1d, 0x37, 0x76, 0xbf, 0x60, + 0x0d, 0x3a, 0x3a, 0xcb, 0x2e, 0x76, 0xe9, 0x7a, 0x03, 0x5f, 0x65, 0x77, + 0x86, 0xd2, 0xfd, 0xd1, 0x3d, 0x4e, 0x4a, 0xea, 0x28, 0x28, 0xa9, 0x1a, + 0x54, 0x4f, 0x20, 0x83, 0xf4, 0x4d, 0x02, 0x7e, 0xa5, 0xe5, 0xa1, 0x28, + 0x31, 0x81, 0x21, 0x59, 0x25, 0x63, 0x54, 0x3c, 0xea, 0xa9, 0x53, 0x3d, + 0xd6, 0x70, 0x1d, 0x83, 0xc9, 0x45, 0x38, 0x7f, 0x01, 0x3d, 0xe6, 0xe5, + 0x97, 0x0d, 0x9c, 0x3f, 0xd7, 0x77, 0x0c, 0xee, 0x55, 0x4b, 0x6d, 0xfd, + 0xee, 0x74, 0xdc, 0x48, 0x7a, 0x40, 0xb6, 0x97, 0xa1, 0x71, 0xeb, 0x2a, + 0x61, 0xfa, 0x11, 0x13, 0xa7, 0xb4, 0xc9, 0x5a, 0x05, 0x8b, 0xfb, 0x5d, + 0xe8, 0x5f, 0x7b, 0x91, 0x78, 0xbf, 0xbf, 0x57, 0x89, 0xff, 0x59, 0xe1, + 0x89, 0xae, 0x59, 0x67, 0x69, 0xdf, 0x98, 0x46, 0xd2, 0xc0, 0xd5, 0x35, + 0x7d, 0x27, 0x7c, 0x16, 0xea, 0x6e, 0x3b, 0x72, 0x49, 0x82, 0xdb, 0xee, + 0x3d, 0x82, 0xde, 0xac, 0x03, 0x1b, 0xed, 0x3e, 0x20, 0x0c, 0x0d, 0x58, + 0x91, 0x72, 0x44, 0x57, 0xc7, 0x5f, 0x12, 0x93, 0x94, 0xcb, 0x40, 0x02, + 0x89, 0x52, 0x00, 0xb3, 0x4c, 0x0a, 0x1f, 0x9b, 0x24, 0xc9, 0xfe, 0xe5, + 0x2c, 0x5d, 0x25, 0x32, 0x18, 0x89, 0x57, 0xb6, 0xc4, 0xb0, 0xce, 0xb2, + 0xc5, 0xb0, 0xce, 0x6e, 0xb5, 0x6d, 0x05, 0xfc, 0x5d, 0xb6, 0xf2, 0xd8, + 0xd2, 0xda, 0xa9, 0x94, 0x3f, 0xc4, 0xe2, 0xf1, 0xf1, 0x7e, 0x42, 0x2c, + 0xbe, 0xf2, 0x14, 0x43, 0x2c, 0x1a, 0x21, 0x8c, 0x28, 0xdc, 0x22, 0x48, + 0x26, 0x07, 0xc9, 0xa8, 0x43, 0xeb, 0xd7, 0x57, 0xc9, 0x9a, 0x0d, 0xaa, + 0x52, 0xa4, 0x69, 0x4e, 0x1e, 0x58, 0x8f, 0xa2, 0xbb, 0x53, 0xd0, 0x06, + 0x92, 0x3a, 0x1f, 0x7e, 0x21, 0x35, 0xfb, 0x31, 0xc9, 0x5c, 0xad, 0x21, + 0x47, 0x04, 0x3b, 0x8c, 0xba, 0xad, 0xe3, 0x65, 0x3b, 0x51, 0x69, 0xf6, + 0x14, 0x4f, 0x7d, 0x0d, 0x5e, 0x46, 0x32, 0x6b, 0x60, 0x6f, 0xa4, 0x83, + 0xc1, 0x95, 0xaf, 0x41, 0xe7, 0x0e, 0x53, 0x6e, 0x4e, 0xb7, 0xd5, 0x78, + 0x11, 0xa0, 0x39, 0xa6, 0xde, 0x81, 0x72, 0xbc, 0xd0, 0x90, 0x44, 0xb8, + 0xf2, 0x01, 0x71, 0xa6, 0x7d, 0x21, 0x05, 0xb4, 0xd5, 0x40, 0x0c, 0xc6, + 0x79, 0x27, 0xdc, 0xc5, 0xbd, 0xea, 0x21, 0x8d, 0x95, 0x4d, 0x15, 0x91, + 0x4d, 0x07, 0x6a, 0x55, 0xd1, 0x0c, 0x48, 0x46, 0x0f, 0x37, 0xc1, 0xee, + 0x35, 0x30, 0x34, 0x5b, 0xb1, 0x71, 0x27, 0x4b, 0x2e, 0xb3, 0x24, 0xbf, + 0x7a, 0x92, 0xf2, 0xd4, 0xae, 0xab, 0xd2, 0x1f, 0x6f, 0x96, 0x11, 0x8d, + 0x0b, 0xb9, 0xaf, 0x16, 0x94, 0xab, 0xd6, 0x82, 0x12, 0x9c, 0x55, 0xa1, + 0x1c, 0xb5, 0x32, 0x22, 0x4e, 0x19, 0x7d, 0x36, 0xad, 0x12, 0x0e, 0xa0, + 0xf6, 0xc8, 0x50, 0x64, 0x77, 0x27, 0x74, 0x13, 0xee, 0xcd, 0xa9, 0x62, + 0x49, 0x07, 0x72, 0xf6, 0x48, 0x9c, 0x35, 0x74, 0x0b, 0xbc, 0xdd, 0x14, + 0xfe, 0xea, 0x5d, 0xae, 0x56, 0x1d, 0x35, 0xa8, 0xb3, 0x0a, 0xa3, 0xd0, + 0xb8, 0x42, 0xc6, 0xc8, 0xd7, 0xa6, 0xec, 0x4e, 0x9b, 0x28, 0x75, 0xbc, + 0x5c, 0xf2, 0x1d, 0x46, 0xd1, 0xcb, 0xee, 0x16, 0x82, 0xf4, 0x10, 0xfc, + 0xb1, 0x12, 0xe8, 0x6e, 0x64, 0x45, 0xba, 0xf3, 0xe8, 0x32, 0x3f, 0x4f, + 0xc0, 0xa2, 0x99, 0x06, 0xf4, 0xd1, 0x32, 0xd8, 0x4f, 0x50, 0x20, 0x5f, + 0xa9, 0xd9, 0x48, 0x9e, 0x93, 0x66, 0x01, 0x7d, 0x07, 0x48, 0x1b, 0x39, + 0x7c, 0x46, 0x8f, 0xbe, 0x49, 0x45, 0x62, 0x70, 0x29, 0x02, 0x2b, 0x7f, + 0xa9, 0x75, 0x01, 0x95, 0x76, 0xe9, 0x6c, 0x66, 0xbe, 0x2c, 0x20, 0xcb, + 0x38, 0x38, 0x08, 0x5a, 0x44, 0x7c, 0x40, 0x36, 0xf2, 0x81, 0xd8, 0xcf, + 0xe4, 0x2f, 0xed, 0x60, 0xe3, 0xae, 0xd1, 0x24, 0xdb, 0xeb, 0xf9, 0x1a, + 0xe7, 0x50, 0x3e, 0x70, 0x0c, 0xff, 0xba, 0xa2, 0xaa, 0x42, 0xb2, 0xd3, + 0x71, 0x95, 0x11, 0x57, 0x11, 0x53, 0xdc, 0xba, 0x77, 0xbc, 0x77, 0xa0, + 0x5f, 0xcb, 0x9f, 0xaa, 0xd0, 0x93, 0x28, 0xe8, 0x20, 0x9a, 0xfb, 0x7e, + 0x7f, 0x74, 0x5f, 0xcb, 0x14, 0xae, 0xad, 0xfa, 0x39, 0xa2, 0xdc, 0x69, + 0x09, 0x18, 0x42, 0x50, 0xbe, 0x23, 0x68, 0x92, 0xf5, 0x3a, 0xf7, 0xf6, + 0x0b, 0x89, 0x06, 0x25, 0xcf, 0x1e, 0x05, 0x7f, 0x42, 0x3d, 0x3a, 0x91, + 0x2f, 0x94, 0x61, 0x38, 0x33, 0x07, 0xb0, 0xf1, 0x90, 0x63, 0x48, 0x01, + 0x76, 0x4d, 0x69, 0xfb, 0x96, 0xb7, 0xe1, 0x29, 0x3d, 0x2f, 0xc3, 0x6e, + 0xec, 0xe6, 0x14, 0x3e, 0xab, 0x56, 0x30, 0x04, 0x6b, 0xc9, 0x04, 0xe0, + 0x7e, 0x36, 0xae, 0x7d, 0x4f, 0x25, 0xf8, 0x24, 0xe4, 0xd2, 0xbb, 0xfb, + 0xe2, 0x7a, 0x50, 0xeb, 0xe3, 0xed, 0x61, 0x9b, 0x25, 0x93, 0x27, 0x80, + 0x99, 0x96, 0xe0, 0x93, 0x80, 0xab, 0xe7, 0xee, 0x0b, 0xe4, 0x21, 0x0c, + 0x5d, 0xde, 0x3e, 0xf1, 0x69, 0x24, 0xd0, 0xb2, 0x94, 0x12, 0xc0, 0x43, + 0xf5, 0x92, 0x8e, 0xce, 0x04, 0xab, 0xa4, 0xf5, 0x74, 0xa4, 0xa4, 0x51, + 0xa3, 0x8c, 0x95, 0x7a, 0x68, 0x3e, 0x69, 0x29, 0xa9, 0x86, 0x69, 0xa0, + 0x51, 0x27, 0x3a, 0x3e, 0x10, 0x5c, 0x27, 0xfb, 0xa5, 0x58, 0x49, 0x04, + 0x1f, 0xac, 0x0f, 0xc2, 0xca, 0x34, 0xac, 0x51, 0x20, 0xd6, 0x52, 0xc3, + 0x1a, 0x07, 0x62, 0xcd, 0x35, 0xac, 0xc3, 0x40, 0x2c, 0x38, 0xb2, 0xc8, + 0x82, 0x4f, 0x3c, 0xde, 0x7c, 0x98, 0xdc, 0xc6, 0x67, 0x6a, 0x1d, 0x7b, + 0x1a, 0xef, 0x3d, 0x8d, 0xa7, 0x9e, 0x56, 0xd6, 0x79, 0x37, 0xac, 0xb4, + 0x9b, 0xb1, 0xc6, 0xe4, 0xc3, 0x40, 0x26, 0x33, 0x1d, 0xed, 0x28, 0x10, + 0x6d, 0xa9, 0xa3, 0x1d, 0x07, 0xa2, 0xcd, 0x75, 0xb4, 0x57, 0x02, 0xd1, + 0x40, 0x92, 0x63, 0x8f, 0x28, 0x1f, 0x6a, 0xe2, 0x3a, 0xd2, 0x7e, 0x1d, + 0xe3, 0x2f, 0x59, 0x58, 0xb8, 0x28, 0x0f, 0x35, 0x2e, 0x5f, 0x0d, 0xe4, + 0x32, 0xd3, 0xd1, 0x5e, 0x0b, 0x44, 0x5b, 0xea, 0x68, 0xa3, 0xd0, 0x0e, + 0x30, 0x37, 0xf0, 0x42, 0xbb, 0x00, 0x08, 0xf3, 0xd0, 0x23, 0xcc, 0x57, + 0x35, 0x81, 0xbd, 0xa6, 0x6b, 0xa9, 0xa1, 0xb4, 0x23, 0x10, 0xe7, 0xd3, + 0x18, 0x0e, 0x7d, 0x0f, 0x4a, 0xfb, 0x2d, 0x62, 0x65, 0xe0, 0xd5, 0x41, + 0xe6, 0x61, 0x2a, 0xaa, 0x09, 0xb6, 0x3a, 0x58, 0xfa, 0x10, 0xab, 0x03, + 0xac, 0x0e, 0xe6, 0x7e, 0x3c, 0x7f, 0x50, 0x55, 0x52, 0x33, 0x8e, 0x18, + 0x60, 0x6e, 0x2b, 0x04, 0x35, 0x6e, 0x2d, 0xa8, 0x71, 0x6b, 0x49, 0x8d, + 0xdb, 0x8a, 0x6a, 0xdc, 0x5a, 0x56, 0xe3, 0x46, 0xc2, 0xf2, 0xc8, 0xea, + 0xb0, 0xb5, 0xac, 0x0e, 0x5b, 0xcb, 0xea, 0xb0, 0xad, 0xac, 0x0e, 0x5b, + 0xcb, 0xea, 0x30, 0x5c, 0x56, 0x6e, 0xe7, 0xf2, 0x84, 0x36, 0xd2, 0x1a, + 0x39, 0x95, 0x65, 0xe8, 0x50, 0x87, 0x17, 0x60, 0x85, 0x17, 0x8d, 0xa6, + 0x1a, 0xce, 0x24, 0x24, 0x06, 0xaa, 0x27, 0xe8, 0x69, 0x90, 0xcb, 0x25, + 0xa3, 0x7c, 0xfa, 0x99, 0x93, 0x30, 0x53, 0x1d, 0x67, 0x12, 0x14, 0xb3, + 0xd4, 0x17, 0xa3, 0x34, 0xc8, 0xfb, 0x15, 0x21, 0x35, 0x6b, 0xf9, 0x23, + 0x98, 0xa9, 0x86, 0x53, 0xcb, 0x1f, 0xc0, 0x78, 0xf8, 0x83, 0xac, 0x30, + 0xef, 0x5c, 0x46, 0xce, 0xf4, 0xf3, 0x27, 0x61, 0xa6, 0x3a, 0xce, 0x24, + 0x28, 0x0e, 0xa8, 0x37, 0xee, 0x67, 0x30, 0x7f, 0x14, 0xe3, 0xd2, 0xcf, + 0x9f, 0x84, 0x99, 0xea, 0x38, 0x93, 0x28, 0x24, 0x62, 0xa7, 0x37, 0x42, + 0x67, 0x08, 0x7f, 0x3c, 0x6a, 0x61, 0x54, 0xd1, 0x39, 0x04, 0xcc, 0x54, + 0x41, 0x08, 0x99, 0x72, 0x2f, 0xd6, 0x46, 0xe3, 0x4a, 0x5a, 0x81, 0x9c, + 0x01, 0x85, 0x5a, 0xce, 0x00, 0x46, 0x72, 0xb6, 0x08, 0x58, 0x0c, 0x58, + 0x6c, 0x76, 0x1e, 0xc6, 0x16, 0x61, 0xcb, 0x01, 0x22, 0x7a, 0x5b, 0x14, + 0x3c, 0xab, 0xe0, 0x65, 0x48, 0x4c, 0xc1, 0xb1, 0x8c, 0x25, 0xd7, 0xe4, + 0x00, 0xaa, 0x76, 0x07, 0xce, 0x17, 0x9f, 0xae, 0x9a, 0x93, 0x64, 0x8d, + 0x47, 0x69, 0x11, 0xf2, 0xc6, 0x42, 0x1d, 0xa4, 0xb0, 0x12, 0xbd, 0xbb, + 0x48, 0x72, 0x58, 0xbf, 0x92, 0xcb, 0x80, 0x2e, 0xa1, 0xd8, 0xc4, 0x4a, + 0x11, 0x34, 0xab, 0x10, 0x0d, 0x1a, 0x1d, 0xf5, 0xf0, 0x5a, 0xfd, 0xa6, + 0xb5, 0x72, 0x62, 0x75, 0x3f, 0x85, 0x2a, 0x8b, 0xa9, 0x61, 0x83, 0xdd, + 0x50, 0x80, 0x06, 0xb8, 0xba, 0x37, 0x4d, 0xe1, 0xc7, 0x4d, 0x11, 0x0e, + 0xab, 0x10, 0x40, 0xcb, 0x83, 0x46, 0x5c, 0x5b, 0xf5, 0xb7, 0xe9, 0xba, + 0xb6, 0x4f, 0x22, 0xcc, 0x54, 0x41, 0xa8, 0xed, 0x93, 0x00, 0xe3, 0xd4, + 0x64, 0x48, 0x0f, 0xec, 0x91, 0x74, 0x39, 0xa3, 0x82, 0x2d, 0x09, 0x33, + 0xd5, 0x50, 0x26, 0x8d, 0x43, 0x70, 0xd8, 0x6c, 0x12, 0xa5, 0x50, 0x6b, + 0x4b, 0x71, 0x61, 0xc2, 0x4d, 0x87, 0x23, 0x7a, 0x8d, 0x46, 0x69, 0xd2, + 0xec, 0xec, 0xba, 0x71, 0xc5, 0x35, 0x38, 0x72, 0x5b, 0x73, 0xfa, 0x78, + 0xc9, 0xb5, 0xb6, 0x80, 0xd1, 0xb8, 0x7d, 0x01, 0xfc, 0x9a, 0x6b, 0x60, + 0x2c, 0xa9, 0xe6, 0xf4, 0xe1, 0x9a, 0x6b, 0x6d, 0x05, 0x8e, 0xe1, 0x8c, + 0x63, 0x50, 0x3f, 0xc2, 0x87, 0xd5, 0xc0, 0xc0, 0x34, 0x5a, 0x0d, 0x85, + 0xb5, 0x98, 0x60, 0x35, 0x89, 0xb2, 0xff, 0xd1, 0x23, 0xc0, 0x12, 0xd6, + 0x3b, 0xb5, 0x8f, 0x9c, 0xb3, 0x7a, 0xff, 0x8b, 0xf1, 0xf4, 0xe7, 0x7d, + 0x25, 0xc4, 0x53, 0x12, 0x7f, 0x59, 0xfe, 0x0b, 0xfa, 0x17, 0x48, 0x1a, + 0x90, 0xb5, 0xef, 0xd7, 0x3b, 0x39, 0xcf, 0xe9, 0x6d, 0x8e, 0x6c, 0xb3, + 0xca, 0xfd, 0x80, 0x62, 0x63, 0x86, 0x10, 0x6c, 0x38, 0x91, 0xcf, 0xab, + 0xc0, 0xde, 0x12, 0xaf, 0x39, 0xbd, 0xa3, 0xa1, 0x44, 0x97, 0x50, 0x4c, + 0x7e, 0x95, 0x5c, 0xd0, 0x4b, 0xe7, 0xf4, 0xd0, 0xb4, 0xef, 0xf2, 0x16, + 0x65, 0x6a, 0x94, 0x5c, 0x90, 0x06, 0x41, 0x7f, 0x43, 0xca, 0xe9, 0x31, + 0x55, 0x54, 0x3c, 0x61, 0x5a, 0x7b, 0xf8, 0xe8, 0x11, 0x40, 0xa7, 0xb3, + 0x55, 0xfa, 0x13, 0xec, 0x0d, 0x0e, 0x06, 0x03, 0xab, 0x14, 0x79, 0xb3, + 0x4c, 0xbe, 0x96, 0x43, 0x0a, 0xc9, 0xf8, 0x73, 0x01, 0xfb, 0x2c, 0x84, + 0xb6, 0xc6, 0xde, 0xe4, 0xea, 0x1f, 0x14, 0x6c, 0x73, 0x25, 0x4f, 0x13, + 0x7f, 0xcc, 0x5f, 0x7a, 0x04, 0x3b, 0x61, 0xaa, 0x92, 0x71, 0x2e, 0x9b, + 0xce, 0x63, 0x35, 0xbd, 0xb5, 0xd4, 0x6c, 0x6f, 0xaf, 0x96, 0x5a, 0x19, + 0x96, 0xc2, 0x45, 0xd1, 0x79, 0xe4, 0x0c, 0x0f, 0xa4, 0x7b, 0xbb, 0x1c, + 0x13, 0x96, 0xbf, 0x4f, 0x2e, 0xe4, 0x7a, 0x9d, 0x1b, 0x48, 0xea, 0x8c, + 0x3c, 0x18, 0x80, 0xaa, 0xe9, 0x3c, 0xd9, 0xc0, 0x9a, 0x47, 0x9c, 0x7e, + 0x60, 0xf2, 0x94, 0xd1, 0x91, 0x9e, 0xef, 0x74, 0x7b, 0x74, 0xd0, 0x7c, + 0x58, 0xf9, 0xfa, 0xf8, 0x02, 0x2f, 0x05, 0x46, 0xb4, 0xfb, 0x2b, 0x37, + 0x97, 0xed, 0xd3, 0x60, 0x44, 0x93, 0xef, 0x1a, 0x93, 0x1e, 0xdb, 0x9b, + 0xc4, 0xa7, 0x11, 0x02, 0xd1, 0x7e, 0xaf, 0x00, 0x9c, 0xb8, 0xf7, 0x9f, + 0x55, 0x62, 0xea, 0x81, 0x68, 0x91, 0xf6, 0xec, 0x14, 0xb9, 0x47, 0x7b, + 0xae, 0xa4, 0xfc, 0xda, 0xe9, 0x12, 0xa4, 0x91, 0x7c, 0xa2, 0x03, 0xca, + 0x03, 0xd5, 0x27, 0x57, 0x90, 0x43, 0x67, 0xa9, 0x7d, 0x00, 0xf9, 0xa2, + 0x16, 0x62, 0x5b, 0x0b, 0x91, 0x09, 0x08, 0xc9, 0x9d, 0x0d, 0x76, 0x7a, + 0x56, 0x43, 0xe7, 0xf4, 0xbc, 0x04, 0x20, 0xe9, 0x86, 0x9c, 0x12, 0xae, + 0x3c, 0x79, 0xef, 0x6b, 0x1e, 0xf5, 0x58, 0x63, 0xb1, 0xa1, 0xc6, 0x42, + 0xf4, 0xc1, 0x2e, 0x5b, 0x39, 0x8e, 0x4a, 0xd8, 0x4d, 0x25, 0x47, 0x33, + 0xe7, 0xd1, 0x73, 0x71, 0xbb, 0xf1, 0x09, 0x5b, 0x16, 0x44, 0x23, 0x45, + 0xe9, 0x71, 0x4e, 0xbb, 0xa8, 0xae, 0x87, 0xdc, 0x18, 0x06, 0x6d, 0xbc, + 0x31, 0x20, 0x20, 0x5c, 0x17, 0xde, 0x00, 0x1c, 0x9a, 0x36, 0x68, 0x30, + 0x78, 0xb5, 0xc4, 0x6c, 0x83, 0x46, 0xab, 0x96, 0xad, 0x11, 0x5b, 0xf2, + 0x8a, 0x0b, 0x9e, 0x6d, 0xf1, 0x5a, 0x16, 0x89, 0xb3, 0xc7, 0x56, 0x65, + 0x22, 0x62, 0x4d, 0xa1, 0x60, 0x15, 0x4c, 0xd5, 0xb9, 0x37, 0xad, 0x93, + 0x7b, 0x4c, 0x17, 0xe0, 0xf3, 0x22, 0xec, 0xca, 0x1b, 0xc0, 0x31, 0x2f, + 0x81, 0x6e, 0x8c, 0xc9, 0xdb, 0x62, 0x40, 0xc0, 0x7f, 0x59, 0x0c, 0x32, + 0xe9, 0x9e, 0x58, 0x83, 0xe1, 0x53, 0x74, 0x1b, 0xbd, 0x7e, 0x89, 0x38, + 0x9d, 0x11, 0x8d, 0xa2, 0x5f, 0x7e, 0xd1, 0xd2, 0xa6, 0x90, 0x86, 0x46, + 0x03, 0x06, 0x6c, 0x1d, 0xf2, 0xe8, 0x15, 0xb4, 0x15, 0x6c, 0xe8, 0xfd, + 0xf2, 0xf4, 0xf1, 0x67, 0x9f, 0x44, 0xd0, 0xc7, 0x3f, 0xf9, 0xec, 0xdd, + 0xf7, 0x8c, 0xc7, 0xb2, 0x2a, 0x2f, 0x13, 0xf2, 0xae, 0xed, 0xbe, 0x3f, + 0xcd, 0xf1, 0x9f, 0xfa, 0x15, 0x6a, 0x46, 0xb6, 0xd1, 0x8d, 0xba, 0xb0, + 0x67, 0x53, 0x18, 0x0c, 0x30, 0x67, 0x23, 0x6a, 0x8b, 0x22, 0x22, 0xb1, + 0xd1, 0x0d, 0x57, 0x77, 0x93, 0xbd, 0xc9, 0x77, 0xd2, 0x60, 0x98, 0xde, + 0xb3, 0xab, 0xe5, 0xad, 0xf7, 0x66, 0xdd, 0x28, 0x76, 0x03, 0x51, 0x05, + 0x76, 0xb1, 0x22, 0xc6, 0x49, 0x0b, 0x50, 0xaa, 0x63, 0xa8, 0x0c, 0xdd, + 0xcf, 0xfb, 0xf2, 0xf1, 0x67, 0x9f, 0x7f, 0xfc, 0xf6, 0xb7, 0x7a, 0xcb, + 0x09, 0xf3, 0x8e, 0xe0, 0xfc, 0xb6, 0x73, 0x8c, 0x7e, 0x8a, 0xe9, 0x99, + 0x7b, 0xc7, 0x01, 0xf0, 0x83, 0xbd, 0xb0, 0xec, 0x90, 0x8e, 0x04, 0xae, + 0xa6, 0x4c, 0x67, 0x29, 0x7c, 0x94, 0xe5, 0x9a, 0x9a, 0xbb, 0x96, 0xaf, + 0xb0, 0x5a, 0xb2, 0x7e, 0xf3, 0xe4, 0xeb, 0x53, 0x86, 0xf6, 0xe7, 0xba, + 0x8d, 0x4b, 0xb3, 0x45, 0x1f, 0x6a, 0xa6, 0x69, 0x52, 0x77, 0xdb, 0xe9, + 0xbc, 0xde, 0x89, 0x39, 0x48, 0x6d, 0x37, 0x6e, 0xd5, 0x95, 0x95, 0x2e, + 0x16, 0xd0, 0xa1, 0xa9, 0x5d, 0xfe, 0x9b, 0x1a, 0xf5, 0x2a, 0xd3, 0xa8, + 0xc7, 0x5f, 0xfd, 0x6b, 0xaa, 0x87, 0xc0, 0xe1, 0xf5, 0x7b, 0x8d, 0x8f, + 0x35, 0xef, 0x8d, 0x06, 0x87, 0xa3, 0x7f, 0x4d, 0x1d, 0x9b, 0x34, 0xe1, + 0xf1, 0x90, 0x57, 0xf1, 0xfd, 0x34, 0x4b, 0xc6, 0xc3, 0xd1, 0xf8, 0x5f, + 0x53, 0x4b, 0x06, 0x5c, 0xfb, 0x4e, 0xf7, 0x9f, 0xae, 0x01, 0x02, 0xff, + 0x65, 0x55, 0xb0, 0x5e, 0xad, 0xd6, 0x5b, 0x6b, 0xd8, 0x28, 0xae, 0x40, + 0x67, 0x73, 0x79, 0xd9, 0x62, 0x90, 0x44, 0x92, 0xad, 0x24, 0xd8, 0x54, + 0x0f, 0x6c, 0x41, 0x36, 0x40, 0xf0, 0x2b, 0xbd, 0xed, 0x2d, 0x7b, 0x4b, + 0x51, 0xdd, 0xec, 0x80, 0xa0, 0x67, 0x6d, 0xfc, 0x7d, 0x86, 0xe9, 0x75, + 0xf8, 0x6d, 0x46, 0x65, 0xed, 0x5a, 0xf0, 0x09, 0x78, 0xed, 0xe6, 0x6d, + 0x84, 0xd8, 0x94, 0x4b, 0x45, 0x23, 0x9c, 0x73, 0xdd, 0x6b, 0xed, 0xc6, + 0xb3, 0x1d, 0x39, 0x03, 0xcc, 0x0e, 0xea, 0x78, 0xc8, 0x0b, 0xf1, 0xe2, + 0x0d, 0xf8, 0x7a, 0xcf, 0x50, 0x60, 0xd8, 0xf5, 0xa8, 0x08, 0x29, 0x91, + 0x14, 0x54, 0x19, 0x42, 0x7e, 0x82, 0xc5, 0xfd, 0x2c, 0xfd, 0x5e, 0x90, + 0xca, 0x3c, 0x01, 0xef, 0x20, 0xc7, 0x45, 0xa7, 0x65, 0x92, 0x95, 0x40, + 0x2a, 0x3b, 0xfa, 0x81, 0xf2, 0x91, 0xee, 0x8b, 0x6b, 0x79, 0x1c, 0x1b, + 0x20, 0xdc, 0x46, 0x0b, 0xdc, 0xd0, 0xf7, 0xa1, 0x7f, 0xc2, 0x0a, 0x3c, + 0x5f, 0xe7, 0xcc, 0xb5, 0x49, 0x87, 0x28, 0x1d, 0xcd, 0x01, 0x75, 0x70, + 0xc9, 0x85, 0xcd, 0xc7, 0xd0, 0xb6, 0x2d, 0xf0, 0x51, 0x1b, 0xd0, 0xab, + 0x5c, 0x4e, 0xa3, 0x8b, 0xe2, 0xbc, 0x40, 0x9a, 0x27, 0x2a, 0x0b, 0x6d, + 0x24, 0x45, 0x43, 0x86, 0xa4, 0x45, 0x72, 0x1a, 0x5a, 0x42, 0xbf, 0x05, + 0x74, 0x8c, 0x23, 0xc7, 0x2e, 0x74, 0x79, 0x60, 0xdd, 0x41, 0xe3, 0x05, + 0xa0, 0x61, 0x1d, 0xa5, 0x77, 0x51, 0x21, 0xd3, 0xc3, 0x08, 0x04, 0x9f, + 0x04, 0x2c, 0x4b, 0x79, 0x0e, 0x4b, 0x91, 0x87, 0x18, 0xcd, 0x8d, 0xd9, + 0x9e, 0x75, 0x84, 0xcb, 0x4a, 0x59, 0x5a, 0x29, 0xf3, 0xf3, 0xae, 0x62, + 0x99, 0x82, 0x0f, 0xdd, 0x49, 0x9e, 0x6a, 0x98, 0x1a, 0xdb, 0x5c, 0xd9, + 0x49, 0x4b, 0x3b, 0x69, 0x3e, 0x0e, 0x65, 0xec, 0xd0, 0xc3, 0x58, 0x1d, + 0x67, 0x87, 0x36, 0x67, 0x76, 0xd2, 0xd2, 0x4e, 0x9a, 0x1f, 0x6a, 0x9c, + 0xdd, 0xe3, 0x27, 0x8b, 0x41, 0xa2, 0xbd, 0xa5, 0x7f, 0x22, 0xa2, 0x90, + 0xd0, 0x2d, 0xa9, 0xd9, 0xfa, 0xc7, 0x59, 0xd5, 0xb4, 0xe1, 0x01, 0xab, + 0x13, 0xbd, 0x02, 0xf1, 0x84, 0x41, 0x53, 0xd8, 0x39, 0x7e, 0xc5, 0x0a, + 0xc3, 0xda, 0x02, 0x36, 0xcb, 0x40, 0xdc, 0x13, 0x96, 0x16, 0x3f, 0x18, + 0x5f, 0x10, 0x9c, 0x16, 0x6b, 0xe2, 0x7a, 0xbb, 0x59, 0x03, 0x61, 0x56, + 0xef, 0x45, 0x29, 0x9e, 0x2c, 0x29, 0x76, 0xd9, 0x3a, 0x8a, 0x3b, 0x43, + 0x14, 0x0c, 0xb3, 0x1c, 0x90, 0x3d, 0x28, 0x36, 0xa7, 0x45, 0x06, 0x36, + 0x2e, 0x86, 0xd8, 0xb2, 0x30, 0x22, 0xaf, 0x52, 0x98, 0x0a, 0xf5, 0xc7, + 0x98, 0xfe, 0xe5, 0x76, 0x0b, 0x1b, 0x56, 0xb3, 0x3c, 0x89, 0x2d, 0xb3, + 0x24, 0x05, 0x0b, 0x5f, 0xac, 0x22, 0x24, 0x0f, 0x02, 0x04, 0x36, 0x1d, + 0xbb, 0x50, 0xaa, 0x23, 0x63, 0xe4, 0xcb, 0x18, 0xfb, 0x32, 0xa0, 0x01, + 0x6c, 0x7e, 0x36, 0xeb, 0x53, 0x32, 0x1b, 0xd4, 0x06, 0x2c, 0x9c, 0x9e, + 0xd6, 0xcd, 0x9e, 0x75, 0xac, 0x70, 0x6a, 0x21, 0x79, 0xb6, 0x1b, 0x61, + 0x84, 0x09, 0x79, 0xb0, 0xcd, 0xe8, 0xf3, 0xdd, 0xe4, 0x72, 0xb6, 0x5b, + 0x15, 0x24, 0x01, 0x49, 0x8d, 0x81, 0xc8, 0x67, 0x47, 0x8a, 0xcd, 0x6e, + 0x71, 0x85, 0x0f, 0xa4, 0x4a, 0x93, 0x27, 0xe8, 0x52, 0xec, 0x42, 0x0e, + 0x3f, 0xcb, 0xa0, 0xed, 0xa4, 0xdd, 0xc3, 0x32, 0x21, 0xd3, 0x70, 0x9b, + 0x6e, 0x5f, 0x8f, 0x3e, 0x99, 0x15, 0x57, 0x03, 0x72, 0x88, 0x62, 0x15, + 0xf3, 0x31, 0x96, 0x42, 0x1b, 0xb8, 0x83, 0x2d, 0x4c, 0x76, 0xbf, 0x89, + 0xfa, 0x40, 0x7d, 0x00, 0x86, 0x16, 0x4c, 0xcb, 0xc7, 0xc9, 0x65, 0xd1, + 0xed, 0xe9, 0x94, 0xee, 0x42, 0x29, 0x7d, 0x2b, 0x29, 0x61, 0xde, 0xb6, + 0xab, 0x98, 0x66, 0xa1, 0xea, 0xfe, 0xca, 0x53, 0x18, 0x2d, 0xac, 0x78, + 0x8b, 0x8a, 0xb1, 0x22, 0xbf, 0x09, 0xe1, 0x9c, 0x81, 0x7e, 0xeb, 0xe6, + 0x4d, 0xb6, 0x23, 0x8f, 0x9d, 0xca, 0xbb, 0x0d, 0xf5, 0xb4, 0x47, 0xd7, + 0x50, 0xc7, 0x77, 0xa1, 0xfd, 0x63, 0xe0, 0x6b, 0x70, 0xdb, 0x8b, 0xf0, + 0xe3, 0x0e, 0x36, 0x63, 0xe0, 0xbf, 0x2e, 0x5d, 0x66, 0x43, 0x42, 0x32, + 0x08, 0xf4, 0x13, 0x4e, 0x43, 0x2a, 0x39, 0x25, 0x18, 0xa1, 0x33, 0xc9, + 0x00, 0xf9, 0xec, 0x37, 0x84, 0x5b, 0xc2, 0x38, 0x4b, 0x7a, 0x26, 0xc3, + 0x37, 0x0c, 0xca, 0x59, 0x07, 0x4a, 0x84, 0x1e, 0xc9, 0x49, 0x9e, 0x47, + 0x53, 0xc9, 0x82, 0x07, 0x21, 0xd3, 0xc1, 0xc5, 0x0d, 0x0b, 0x0f, 0xf4, + 0xd2, 0x05, 0x3d, 0xf2, 0x41, 0xcf, 0x5d, 0xd0, 0x63, 0x1f, 0xf4, 0x8d, + 0x02, 0x2d, 0xc7, 0x74, 0x79, 0xae, 0x58, 0xe7, 0xce, 0x38, 0x3a, 0x6c, + 0x33, 0x23, 0x4f, 0x07, 0xdb, 0x45, 0xdb, 0x67, 0xa2, 0xec, 0x2d, 0x69, + 0x6c, 0x21, 0xef, 0x76, 0xbb, 0x7f, 0xe3, 0xdc, 0xb9, 0x85, 0x6f, 0xec, + 0xa3, 0xd8, 0xef, 0xf1, 0x68, 0xe6, 0x85, 0x6b, 0x9b, 0xd6, 0x09, 0x84, + 0x06, 0xd2, 0x9d, 0xe8, 0x2f, 0x30, 0x74, 0xc3, 0xb0, 0x17, 0xc1, 0x7f, + 0xdc, 0x8c, 0xdf, 0xa4, 0x17, 0xc5, 0x55, 0xf9, 0xeb, 0x2a, 0x41, 0xbf, + 0x41, 0x19, 0x58, 0x04, 0xed, 0x90, 0xd7, 0x8e, 0xd4, 0x52, 0x89, 0x4d, + 0x4a, 0x87, 0x6a, 0xd8, 0x8e, 0x9c, 0x04, 0xfa, 0x1a, 0x07, 0x9b, 0x58, + 0x29, 0xb1, 0x2c, 0xf4, 0xe0, 0xa5, 0x97, 0x38, 0xe8, 0x4b, 0xd1, 0xbb, + 0x00, 0x99, 0xf3, 0x4e, 0x85, 0xa3, 0x84, 0xc8, 0x38, 0x90, 0xb2, 0x51, + 0xa8, 0x69, 0x16, 0x75, 0x91, 0xe0, 0x4e, 0xe8, 0x37, 0xd1, 0x54, 0xab, + 0x71, 0x74, 0x10, 0x8d, 0x27, 0x26, 0xd0, 0xb7, 0x00, 0xa4, 0x09, 0x42, + 0x40, 0xd9, 0xf7, 0x41, 0x39, 0xd5, 0x9e, 0xc0, 0x0c, 0x92, 0x27, 0x96, + 0x44, 0x17, 0xf3, 0xbf, 0x80, 0xcd, 0xf0, 0x5d, 0x6e, 0xb3, 0xf4, 0x70, + 0x70, 0xa4, 0x80, 0xc2, 0x6e, 0xb8, 0x02, 0x1a, 0x6b, 0xb0, 0x7d, 0xd8, + 0xc3, 0xed, 0xea, 0xec, 0x11, 0x78, 0x34, 0xdf, 0x64, 0xa0, 0x70, 0x98, + 0x28, 0x9b, 0x7e, 0x9e, 0x2c, 0xd3, 0xf5, 0xe7, 0x60, 0xc9, 0xe2, 0xae, + 0x09, 0xce, 0xda, 0x4e, 0x07, 0x9f, 0x65, 0x0b, 0xbb, 0x7e, 0x2a, 0x37, + 0xa4, 0x3f, 0x63, 0x68, 0x16, 0xb2, 0x8e, 0x9f, 0x3f, 0xea, 0xb1, 0x4d, + 0x69, 0x49, 0x9c, 0xda, 0x02, 0xef, 0x1b, 0x6b, 0x4c, 0xbd, 0x1e, 0xc5, + 0x60, 0x06, 0x73, 0xca, 0x5c, 0x47, 0x33, 0xb2, 0xaa, 0x08, 0xc4, 0x99, + 0x78, 0xb6, 0xab, 0xb3, 0xb1, 0x4a, 0xd7, 0xc9, 0xd7, 0x54, 0xd9, 0x69, + 0xf4, 0x70, 0xa2, 0xe7, 0xb1, 0x78, 0x09, 0xa7, 0x38, 0x6f, 0x87, 0xdc, + 0xce, 0x73, 0x43, 0xfa, 0xeb, 0x38, 0xa1, 0xe2, 0xae, 0x91, 0x4c, 0x41, + 0x05, 0x4a, 0x71, 0x94, 0x3c, 0x5f, 0xa6, 0xab, 0x15, 0x0b, 0x36, 0x37, + 0x4f, 0x66, 0xbb, 0x22, 0xbd, 0xdc, 0xad, 0x44, 0x78, 0x5e, 0x01, 0x52, + 0xcc, 0xbe, 0x4f, 0xd6, 0x74, 0xdb, 0x99, 0xce, 0x38, 0xbd, 0x1e, 0x5d, + 0x15, 0xc5, 0x16, 0xa2, 0x45, 0xe5, 0x05, 0xac, 0x1d, 0xc0, 0xb8, 0x9b, + 0x5d, 0xae, 0x36, 0x37, 0x60, 0x95, 0xae, 0x0f, 0x7e, 0xd8, 0x25, 0x39, + 0xed, 0xc7, 0x1e, 0x8c, 0x5e, 0x1d, 0x1f, 0x1f, 0xbd, 0x3a, 0x7c, 0x78, + 0x30, 0xdf, 0xa5, 0x2b, 0x3c, 0x03, 0xd1, 0x9f, 0xf5, 0x89, 0x6c, 0x9f, + 0xfc, 0xac, 0x7e, 0xba, 0xee, 0x5f, 0x15, 0xd7, 0xab, 0x23, 0xe3, 0x61, + 0x3c, 0x30, 0x0e, 0x2b, 0x66, 0x62, 0xf8, 0xd7, 0x37, 0xc0, 0xc9, 0x3c, + 0x2e, 0x7f, 0xbd, 0x6c, 0xf8, 0xe7, 0xf2, 0x9d, 0xe4, 0xb7, 0x39, 0x62, + 0xcc, 0x00, 0xfb, 0xe0, 0x33, 0xcb, 0x96, 0x02, 0x8d, 0x19, 0xbd, 0x6a, + 0x06, 0xec, 0x07, 0x4f, 0x55, 0x20, 0x11, 0x8e, 0x07, 0xdc, 0xa7, 0x51, + 0x76, 0x2e, 0xba, 0x20, 0x8f, 0x37, 0x96, 0x0e, 0x09, 0x50, 0x53, 0xd7, + 0xf4, 0x41, 0x57, 0x60, 0xd9, 0xa9, 0x40, 0x42, 0x4f, 0x55, 0x75, 0xd2, + 0xc8, 0x91, 0xa2, 0x30, 0x32, 0xa0, 0xb2, 0xae, 0x64, 0x52, 0x60, 0x99, + 0x24, 0x58, 0xf5, 0xa9, 0x8d, 0x9d, 0x8b, 0xda, 0x53, 0xea, 0xe3, 0x55, + 0xbe, 0x8a, 0x61, 0x4c, 0x12, 0x6d, 0x85, 0xdb, 0xe9, 0x18, 0x2a, 0x04, + 0x0f, 0x89, 0xbc, 0xd0, 0xed, 0x78, 0xb0, 0xe3, 0xb0, 0x42, 0xef, 0xa5, + 0xca, 0xa2, 0x31, 0x69, 0xd2, 0xe5, 0x8b, 0xab, 0x34, 0x1f, 0x54, 0xf7, + 0xf2, 0x8c, 0x09, 0x53, 0x95, 0x9f, 0x14, 0x19, 0x50, 0xdf, 0x21, 0xdc, + 0xc9, 0x0a, 0xae, 0xfd, 0xdf, 0xa4, 0xd8, 0xe3, 0x43, 0x2c, 0x07, 0x70, + 0x19, 0x6e, 0x39, 0x50, 0x12, 0x68, 0x14, 0x38, 0xba, 0xb4, 0x86, 0xd7, + 0x77, 0x4f, 0x96, 0xc8, 0x1d, 0x24, 0x4b, 0xbf, 0x8a, 0xbf, 0x03, 0xf9, + 0x31, 0x98, 0x8a, 0x59, 0xf6, 0x01, 0xcb, 0x16, 0x03, 0xdc, 0xe8, 0x15, + 0xfc, 0x14, 0xa4, 0x25, 0x3a, 0x3d, 0xfe, 0xc3, 0xae, 0xc8, 0x15, 0x9b, + 0x2d, 0x02, 0xc3, 0x36, 0x37, 0xbe, 0x9b, 0x53, 0x0b, 0x0a, 0x9e, 0x9a, + 0xd8, 0xd6, 0x26, 0xc3, 0xe1, 0x69, 0x7f, 0x95, 0xc0, 0xc4, 0x0b, 0x25, + 0x48, 0x01, 0x84, 0x53, 0x13, 0x2c, 0x5b, 0xca, 0x5b, 0x1b, 0xcd, 0xa2, + 0xdf, 0x50, 0x8e, 0xf7, 0x67, 0x28, 0x6b, 0x07, 0x66, 0x66, 0xc6, 0xdd, + 0x43, 0xb3, 0xf4, 0x06, 0x84, 0xd1, 0x5a, 0x25, 0x05, 0xd7, 0x36, 0xef, + 0xd0, 0x4c, 0x30, 0x29, 0xba, 0xcd, 0x56, 0x8b, 0x4b, 0x67, 0x1a, 0xb4, + 0xa9, 0xd4, 0x5a, 0xf9, 0xbd, 0xab, 0x52, 0xa0, 0x20, 0x35, 0x53, 0x46, + 0x49, 0x38, 0xda, 0x8a, 0xb9, 0x45, 0x98, 0x5b, 0xc8, 0xef, 0x33, 0xd4, + 0x09, 0xfc, 0x78, 0x23, 0x2a, 0xbf, 0xeb, 0x5b, 0xfb, 0x12, 0xe3, 0x4e, + 0xc5, 0xb8, 0x53, 0x30, 0xee, 0x0c, 0x0c, 0xc1, 0xc6, 0x59, 0x06, 0x2e, + 0xff, 0x55, 0x8a, 0x1e, 0xea, 0xed, 0xdd, 0x78, 0xbb, 0x59, 0xcd, 0xb2, + 0x18, 0x66, 0x01, 0x77, 0xc8, 0xaa, 0x23, 0xa4, 0x44, 0xf4, 0x26, 0xa7, + 0x28, 0x89, 0x19, 0xe1, 0xa6, 0xbf, 0x4f, 0xb7, 0x14, 0x5f, 0x1a, 0xa8, + 0xdc, 0x75, 0x41, 0x3e, 0x60, 0x06, 0xd2, 0x35, 0xc8, 0x26, 0x07, 0x6d, + 0x99, 0x15, 0x30, 0xc0, 0xd2, 0xf0, 0x9b, 0xa7, 0x17, 0xf0, 0x79, 0xa9, + 0x0c, 0xb4, 0xce, 0xd3, 0x86, 0xe0, 0xdb, 0xed, 0x12, 0x7b, 0x4f, 0xce, + 0xae, 0xc6, 0x05, 0x5d, 0x96, 0x01, 0xd6, 0xc6, 0xf0, 0x2d, 0x86, 0x0a, + 0x59, 0xfc, 0xd3, 0x02, 0x5d, 0xba, 0xdc, 0xb1, 0xf2, 0xa9, 0x60, 0x32, + 0x27, 0x78, 0xfe, 0x8f, 0x56, 0x2d, 0x19, 0x3b, 0x69, 0x1e, 0x6d, 0xd3, + 0xdb, 0x64, 0x05, 0x69, 0x08, 0xc3, 0x1b, 0x9a, 0xda, 0x8a, 0x62, 0x20, + 0x0d, 0xec, 0xb2, 0xb3, 0xcd, 0xcd, 0xc7, 0xec, 0x00, 0xef, 0x54, 0x69, + 0xeb, 0x89, 0x0d, 0x38, 0xbb, 0xf8, 0x6e, 0x97, 0x17, 0xc9, 0xc5, 0x37, + 0x28, 0x6c, 0x30, 0xc0, 0x1c, 0x90, 0x7b, 0x71, 0x30, 0x50, 0x43, 0x8b, + 0xb3, 0x71, 0xfc, 0xac, 0x7f, 0x44, 0xd1, 0x64, 0xcf, 0x31, 0x8a, 0xd1, + 0xd9, 0x10, 0x0d, 0x35, 0x7c, 0x8f, 0x81, 0x21, 0x55, 0xa2, 0xc0, 0xb1, + 0x93, 0xc7, 0xae, 0xbf, 0x68, 0x74, 0x26, 0xef, 0xdc, 0x45, 0xdf, 0xed, + 0xa9, 0x68, 0x12, 0xa7, 0x74, 0x99, 0xb0, 0xc8, 0x04, 0xd6, 0x95, 0xb9, + 0x98, 0xb3, 0xe4, 0x87, 0x5d, 0x9a, 0x01, 0xc1, 0x87, 0x51, 0xbe, 0xda, + 0x14, 0xb9, 0x90, 0xbb, 0x24, 0x69, 0x53, 0xa4, 0xe6, 0x22, 0x67, 0x42, + 0x08, 0x14, 0x6a, 0x14, 0xcb, 0x2a, 0xbe, 0x24, 0x9b, 0xa4, 0x8b, 0x6e, + 0x86, 0xe4, 0x60, 0xe2, 0xd2, 0x9d, 0x2b, 0x9a, 0x35, 0x81, 0xde, 0x38, + 0x9a, 0x2c, 0x9f, 0xc1, 0xaa, 0xcd, 0x8c, 0x87, 0x90, 0xcb, 0xa2, 0x03, + 0x7f, 0xe3, 0x8a, 0xd9, 0xd7, 0x68, 0x30, 0x74, 0x96, 0x72, 0x06, 0xb3, + 0xa4, 0x1e, 0x9b, 0xe2, 0xf5, 0x68, 0x32, 0x47, 0xb3, 0xd9, 0xfc, 0xc7, + 0x31, 0x4c, 0xa4, 0x63, 0x60, 0xa1, 0xa7, 0x94, 0xd5, 0x63, 0xd4, 0xba, + 0x2e, 0x1d, 0x5a, 0x6d, 0xaf, 0x66, 0xa8, 0x68, 0x47, 0x47, 0x56, 0x31, + 0x64, 0x52, 0xce, 0x48, 0x3a, 0x48, 0x1c, 0x0a, 0x9c, 0x78, 0x01, 0x40, + 0x62, 0x23, 0x00, 0x62, 0x0c, 0x55, 0x82, 0x8d, 0x01, 0x8c, 0x18, 0xae, + 0x84, 0x3a, 0x04, 0x28, 0xc6, 0x9c, 0x6f, 0xed, 0x5a, 0x1f, 0xe8, 0xb7, + 0x3b, 0x65, 0xe9, 0x81, 0xb4, 0x88, 0x86, 0xc7, 0xa1, 0xb1, 0x32, 0xac, + 0x1b, 0x25, 0xdd, 0x4c, 0x43, 0x81, 0x34, 0x60, 0xe7, 0x3f, 0x64, 0x45, + 0x7c, 0x0b, 0xed, 0x8c, 0x7c, 0xdc, 0xc1, 0xe7, 0x9d, 0x6a, 0x67, 0xc1, + 0x16, 0x08, 0x40, 0x28, 0x6a, 0x3d, 0x8e, 0x61, 0x71, 0xe3, 0x96, 0x00, + 0xe4, 0xa2, 0x9c, 0x30, 0x82, 0x46, 0xd9, 0xc2, 0x9c, 0xc0, 0xa7, 0x1a, + 0x89, 0x18, 0x7e, 0x82, 0x0a, 0x42, 0x47, 0xf9, 0xfd, 0xb7, 0x5e, 0xf4, + 0xfb, 0x6f, 0xe7, 0x90, 0x00, 0x73, 0x66, 0x91, 0x2d, 0x68, 0x02, 0x22, + 0x88, 0x96, 0x00, 0xa1, 0x5e, 0xe0, 0x24, 0x4b, 0x38, 0x59, 0x70, 0x8c, + 0xb4, 0x81, 0x6b, 0xee, 0x78, 0xe0, 0xdc, 0x29, 0x56, 0x1c, 0x11, 0xd2, + 0x5e, 0x40, 0xd5, 0xf9, 0xaa, 0xd1, 0x1a, 0x4d, 0x48, 0x8b, 0x2b, 0xe8, + 0xd3, 0xa0, 0x2f, 0x2c, 0x0b, 0xa8, 0x49, 0x70, 0x45, 0x46, 0x40, 0x68, + 0x04, 0x30, 0xf0, 0x01, 0x0c, 0x40, 0x71, 0x32, 0x07, 0xba, 0x19, 0xa7, + 0x01, 0xb8, 0xf1, 0x28, 0xea, 0x73, 0x49, 0xce, 0xf3, 0x38, 0x26, 0xac, + 0x17, 0xd0, 0x93, 0xef, 0x83, 0xdb, 0xaf, 0xca, 0x3c, 0x1b, 0x81, 0xa6, + 0xc3, 0xff, 0xf3, 0x91, 0xb6, 0x32, 0x48, 0x08, 0x6f, 0xc2, 0xec, 0x01, + 0x8e, 0x88, 0x51, 0x99, 0x76, 0x70, 0xcd, 0xf8, 0x4c, 0xe2, 0xa2, 0x46, + 0x9d, 0xb1, 0xc2, 0xa1, 0xc9, 0x40, 0x37, 0xce, 0xf5, 0x49, 0xbb, 0x46, + 0x73, 0xa4, 0xd2, 0x1c, 0x57, 0xd3, 0x04, 0x5a, 0x8c, 0x6c, 0x0d, 0xcd, + 0xb1, 0x4a, 0xf3, 0xb0, 0x9a, 0xe6, 0x50, 0xd2, 0xbc, 0xad, 0xa2, 0x79, + 0xa8, 0xd2, 0x7c, 0x58, 0x4b, 0xb3, 0x64, 0xb5, 0x8a, 0xe6, 0x43, 0x95, + 0xe6, 0x51, 0x6d, 0xdd, 0x87, 0x21, 0x34, 0x8f, 0x54, 0x9a, 0xc7, 0x61, + 0x6d, 0x34, 0x94, 0x75, 0xa7, 0x4e, 0x2f, 0x15, 0xe2, 0xba, 0xd4, 0xc0, + 0x3e, 0x2f, 0x9b, 0xa0, 0xa4, 0x0b, 0xb2, 0x04, 0x62, 0x44, 0x8b, 0x42, + 0x92, 0x5d, 0x43, 0x02, 0xff, 0x9c, 0xd3, 0xe7, 0xb9, 0xe2, 0x7a, 0x8a, + 0x3b, 0x20, 0x59, 0x6f, 0xd9, 0x9b, 0x13, 0x55, 0x11, 0x4a, 0x0c, 0x04, + 0x36, 0x12, 0xc3, 0x16, 0xd8, 0xc7, 0x73, 0xbd, 0x8f, 0x43, 0x0a, 0xe8, + 0x30, 0x94, 0xc5, 0xbe, 0x2c, 0xf9, 0x17, 0x28, 0xd7, 0x5a, 0x30, 0xa7, + 0xcb, 0x65, 0x2b, 0x18, 0xe7, 0x62, 0x8c, 0xa6, 0xaa, 0x2e, 0x66, 0x51, + 0xc2, 0x00, 0xff, 0x79, 0x2c, 0x56, 0x9a, 0xa8, 0x45, 0x29, 0x99, 0xc6, + 0xac, 0x74, 0x5d, 0x46, 0x4e, 0x1b, 0xe8, 0x0f, 0x0a, 0x48, 0x20, 0x7f, + 0xf8, 0xc3, 0xb3, 0x12, 0xe6, 0x5c, 0xca, 0xd1, 0x5f, 0x36, 0x69, 0x7d, + 0x99, 0x4c, 0xa7, 0x99, 0xe8, 0xfa, 0xd2, 0xe9, 0xc9, 0x17, 0x8f, 0x3e, + 0x7f, 0x8c, 0x8b, 0x5f, 0xd5, 0xaf, 0x0b, 0x10, 0xea, 0x02, 0xdf, 0x89, + 0xc7, 0xbb, 0x98, 0xd5, 0xef, 0x0c, 0x48, 0xa1, 0x18, 0x58, 0x70, 0xa6, + 0xd4, 0x75, 0x18, 0x82, 0x84, 0x2a, 0x36, 0x75, 0xec, 0x17, 0x26, 0x3a, + 0xef, 0x7e, 0xf6, 0x09, 0x6d, 0xd5, 0x40, 0xda, 0x66, 0x76, 0x91, 0x5c, + 0xc0, 0x74, 0x54, 0x34, 0x40, 0xb9, 0x47, 0x21, 0xdb, 0x1c, 0x0a, 0xc2, + 0x96, 0xcd, 0x76, 0xeb, 0x28, 0x4f, 0xd7, 0x8b, 0x24, 0x02, 0x74, 0x0c, + 0xfd, 0xb8, 0x22, 0x5c, 0x7a, 0xd5, 0x24, 0xc3, 0xa8, 0x91, 0x7c, 0x25, + 0x35, 0x29, 0xe8, 0xee, 0x17, 0xbb, 0x2e, 0xe3, 0x8a, 0xaf, 0xcf, 0x8f, + 0x41, 0x22, 0x8e, 0xbc, 0x09, 0x81, 0xc0, 0x74, 0x69, 0x62, 0x58, 0x85, + 0xf7, 0x0c, 0x64, 0x59, 0x01, 0x6f, 0x21, 0xcd, 0xd8, 0x65, 0x85, 0x04, + 0x6d, 0x02, 0x01, 0xfd, 0x74, 0x38, 0xa4, 0x64, 0x7d, 0x35, 0x4f, 0xa6, + 0x57, 0xbc, 0x6b, 0x4e, 0x6e, 0x18, 0x1b, 0x1c, 0x55, 0x59, 0xbf, 0x71, + 0x90, 0x2f, 0xb2, 0x74, 0x5b, 0xbc, 0x09, 0x49, 0xf4, 0x73, 0xbe, 0xb9, + 0xb8, 0x83, 0x1f, 0x6f, 0x1c, 0xe0, 0xea, 0xcd, 0x9b, 0x7f, 0x00, 0xd4, + 0x4d, 0x20, 0xf1, 0xa1, 0x9f, 0x01, 0x00 }; diff --git a/Arduino/McLighting/json_functions.h b/Arduino/McLighting/json_functions.h index 9967a027..84fb74f3 100644 --- a/Arduino/McLighting/json_functions.h +++ b/Arduino/McLighting/json_functions.h @@ -136,9 +136,15 @@ void getConfigJSON() { } char * listModesJSON() { - const size_t bufferSize = JSON_ARRAY_SIZE(strip->getModeCount() + 1) + (strip->getModeCount() + 1)*JSON_OBJECT_SIZE(2) + 2000; + const size_t bufferSize = JSON_ARRAY_SIZE(strip->getModeCount() + 3) + (strip->getModeCount() + 1)*JSON_OBJECT_SIZE(2) + 2000; DynamicJsonDocument jsonBuffer(bufferSize); JsonArray root = jsonBuffer.to(); + JsonObject objecttoggle = root.createNestedObject(); + objecttoggle["mode"] = "toggle"; + objecttoggle["name"] = "TOGGLE"; + JsonObject objecton = root.createNestedObject(); + objecton["mode"] = "on"; + objecton["name"] = "ON"; JsonObject objectoff = root.createNestedObject(); objectoff["mode"] = "off"; objectoff["name"] = "OFF"; diff --git a/Arduino/McLighting/request_handlers.h b/Arduino/McLighting/request_handlers.h index 8954208e..fa1c68bc 100644 --- a/Arduino/McLighting/request_handlers.h +++ b/Arduino/McLighting/request_handlers.h @@ -150,14 +150,23 @@ void handleRangeDifferentColors(uint8_t * mypayload) { bool setModeByStateString(String saved_state_string) { if (getValue(saved_state_string, '|', 0) == "STA") { DBG_OUTPUT_PORT.printf("Parsed state: %s\r\n", saved_state_string.c_str()); + String str_mode = getValue(saved_state_string, '|', 1); State.mode = static_cast(str_mode.toInt()); + String str_fx_mode = getValue(saved_state_string, '|', 2); fx_mode = str_fx_mode.toInt(); - String str_fx_speed = getValue(saved_state_string, '|', 3); - segState.speed[State.segment] = str_fx_speed.toInt(); + + String _fx_speed = getValue(saved_state_string, '|', 3); + segState.speed[State.segment] = _fx_speed.toInt(); + #if defined(ENABLE_MQTT) + //snprintf(mqtt_buf, sizeof(mqtt_buf), "OK ?%i", _fx_speed); + //sendmqtt(); + #endif + String str_brightness = getValue(saved_state_string, '|', 4); State.brightness = str_brightness.toInt(); + String str_red = getValue(saved_state_string, '|', 5); main_color.red = str_red.toInt(); String str_green = getValue(saved_state_string, '|', 6); @@ -166,6 +175,7 @@ bool setModeByStateString(String saved_state_string) { main_color.blue = str_blue.toInt(); String str_white = getValue(saved_state_string, '|', 8); main_color.white = str_white.toInt(); + str_red = getValue(saved_state_string, '|', 9); back_color.red = str_red.toInt(); str_green = getValue(saved_state_string, '|', 10); @@ -174,6 +184,7 @@ bool setModeByStateString(String saved_state_string) { back_color.blue = str_blue.toInt(); str_white = getValue(saved_state_string, '|', 12); back_color.white = str_white.toInt(); + str_red = getValue(saved_state_string, '|', 13); xtra_color.red = str_red.toInt(); str_green = getValue(saved_state_string, '|', 14); @@ -182,10 +193,9 @@ bool setModeByStateString(String saved_state_string) { xtra_color.blue = str_blue.toInt(); str_white = getValue(saved_state_string, '|', 16); xtra_color.white = str_white.toInt(); + DBG_OUTPUT_PORT.print("Set to state: "); DBG_OUTPUT_PORT.println(listStateJSON()); - //prevmode=mode; - //State.mode = SET; return true; } else { DBG_OUTPUT_PORT.println("Saved state not found!"); @@ -204,7 +214,7 @@ void handleSetWS2812FXMode(uint8_t * mypayload) { sendmqtt(); #endif } else { - if (strcmp((char *) &mypayload[1], "off") == 0) { + if (strcmp((char *) &mypayload[1], "toggle") == 0) { if (State.mode == OFF) { State.mode = SET; #if defined(ENABLE_MQTT) @@ -221,6 +231,17 @@ void handleSetWS2812FXMode(uint8_t * mypayload) { } if (strcmp((char *) &mypayload[1], "on") == 0) { State.mode = SET; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /%i", segState.mode[State.segment]); + sendmqtt(); + #endif + } + if (strcmp((char *) &mypayload[1], "off") == 0) { + State.mode = OFF; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /off", ""); + sendmqtt(); + #endif } } } @@ -333,7 +354,7 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { } if (_payload[1] == 'o') { uint8_t _fx_options = (uint8_t) strtol((const char *) &_payload[2], NULL, 10); - _fx_options = ((constrain(server.arg("fxopt").toInt(), 0, 255)>>1)<<1); + _fx_options = ((constrain(_fx_options, 0, 255)>>1)<<1); if (_fx_options != segState.options) { segState.options= _fx_options; _updateSegState = true; @@ -406,6 +427,7 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { uint16_t _fx_speed = (uint16_t) strtol((const char *) &_payload[1], NULL, 10); _fx_speed = constrain(_fx_speed, SPEED_MIN, SPEED_MAX ); //if (segState.speed[State.segment] != _fx_speed) {} + State.mode = SET; segState.speed[State.segment] = _fx_speed; _updateSegState = true; Dbg_Prefix(mqtt, num); @@ -421,6 +443,7 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { uint8_t b = (uint8_t) strtol((const char *) &_payload[1], NULL, 10); State.brightness = constrain(b, 0, 255); if (strip->getBrightness() != State.brightness) { + State.mode = SET; Dbg_Prefix(mqtt, num); DBG_OUTPUT_PORT.printf("Set brightness to: [%u]\r\n", State.brightness); _updateState = true; @@ -471,7 +494,7 @@ void checkpayload(uint8_t * _payload, bool mqtt = false, uint8_t num = 0) { } #if defined(ENABLE_STATE_SAVE) if (_updateState) { - State.mode = SET; + //State.mode = SET; if(save_state.active()) save_state.detach(); save_state.once(3, tickerSaveState); } diff --git a/Arduino/McLighting/rest_api.h b/Arduino/McLighting/rest_api.h index 663b43e9..553b2842 100644 --- a/Arduino/McLighting/rest_api.h +++ b/Arduino/McLighting/rest_api.h @@ -84,6 +84,7 @@ server.on("/restart", []() { DBG_OUTPUT_PORT.printf("/restart\r\n"); server.sendHeader("Access-Control-Allow-Origin", "*"); server.send(200, "text/plain", "restarting..." ); + delay(1000); ESP.restart(); }); @@ -318,7 +319,7 @@ server.on("/config", []() { getConfigJSON(); }); -server.on("/off", []() { +server.on("/toggle", []() { if (State.mode == OFF) { State.mode = SET; #if defined(ENABLE_MQTT) @@ -356,6 +357,23 @@ server.on("/on", []() { } }); +server.on("/off", []() { + if (State.mode == SET) { + State.mode = OFF; + #if defined(ENABLE_MQTT) + snprintf(mqtt_buf, sizeof(mqtt_buf), "OK /off", ""); + sendmqtt(); + #endif + getACK("OK"); + #if defined(ENABLE_STATE_SAVE) + if(save_state.active()) save_state.detach(); + save_state.once(3, tickerSaveState); + #endif + } else { + getACK("NOK"); + } +}); + server.on("/set", []() { prevmode = HOLD; boolean _updateState = false; diff --git a/Arduino/McLighting/version.h b/Arduino/McLighting/version.h index 852f153a..140ae89a 100644 --- a/Arduino/McLighting/version.h +++ b/Arduino/McLighting/version.h @@ -1 +1 @@ -#define SKETCH_VERSION "3.1.2" +#define SKETCH_VERSION "3.1.3" diff --git a/Arduino/McLighting/version_info.ino b/Arduino/McLighting/version_info.ino index a5216e6f..93f67969 100644 --- a/Arduino/McLighting/version_info.ino +++ b/Arduino/McLighting/version_info.ino @@ -266,4 +266,12 @@ * Version Bump to 3.1.2 * Almost finished: bugfixes regarding issue #80 * ToDo: bugfixes regarding issue #70 + * + * 25.10.2020 + * Updated WS2812FX Lib + * Version Bump to 3.1.3 + * fixed issue #100 + * included pull request from issue #93 + * Fixed a GUI bug on reloading + * ToDo: bugfixes regarding issue #70 */ diff --git a/clients/web/index.htm b/clients/web/index.htm index b56bd4c1..7b1c6920 100644 --- a/clients/web/index.htm +++ b/clients/web/index.htm @@ -1602,8 +1602,9 @@

warning

else xhr.open("GET", url, true); xhr.send(post); } + function getModes() { - document.getElementById("percentage").innerHTML = "0%"; + document.getElementById("percentage").innerHTML = "0%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "0,100"); document.getElementById("modal-content").innerHTML = language.en.loadModes; xhttp("http://" + host + "/get_modes", false, function(e) { @@ -1611,7 +1612,7 @@

warning

if (e && e.substring(0,6) !== "ERROR!") { modes = JSON.parse(e); if (typeof modes[0] !== "undefined") { - modes.forEach(item => { + modes.forEach(item => { if (item.name && item.name.length > 0) { data.modes.push({ title: item.name, id: item.mode }); } @@ -1625,45 +1626,7 @@

warning

}); } -function getConfig() { - document.getElementById("percentage").innerHTML = "75%"; - document.getElementById("percentage-done").setAttribute("stroke-dasharray", "75,100"); - document.getElementById("modal-content").innerHTML = language.en.loadConfig; - xhttp("http://" + host + "/config", false, function(e) { - console.log("Getting config via REST:", e); - if (e && e.substring(0,6) !== "ERROR!") { - var res = JSON.parse(e); - if (res) { - if (typeof res.hostname !== "undefined") config.hostname = res.hostname; - if (typeof res.mqtt_host !== "undefined") config.mqtt_host = res.mqtt_host; - if (typeof res.mqtt_port !== "undefined") config.mqtt_port = res.mqtt_port; - if (typeof res.mqtt_user !== "undefined") config.mqtt_user = res.mqtt_user; - if (typeof res.mqtt_pass !== "undefined") config.mqtt_pass = res.mqtt_pass; - if (typeof res.ws_seg !== "undefined") config.ws_seg = res.ws_seg; - if (typeof res.ws_cnt !== "undefined") config.ws_cnt = res.ws_cnt; - if (typeof res.ws_rgbo !== "undefined") { - config.ws_rgbo = res.ws_rgbo; - config.enable_rgbw = config.ws_rgbo.includes("W"); - } - if (typeof res.ws_pin !== "undefined") config.ws_pin = res.ws_pin; - if (typeof res.ws_trans !== "undefined") config.ws_trans = res.ws_trans; - } - } else { - console.error(e); - document.getElementById("percentage").innerHTML = language.en.error; - showSnackbar(language.en.loadError, "error", 5000); - } - if (config.enable_rgbw) { - document.getElementById("white").parentNode.className = ""; - } else { - document.getElementById("white").parentNode.className = "hidden"; - white.value = 0; - segstate.color.w = 0; - segstate.color.w2 = 0; - segstate.color.w3 = 0; - } - }); -} + function showModes(mode, index) { //console.log("Mode: " + mode.title + " - ID: " + mode.id + " - Hidden: " + mode.hidden); var div = document.createElement("DIV"); @@ -1691,7 +1654,7 @@

warning

document.getElementById("modes").appendChild(div); } function readSettings() { - document.getElementById("percentage").innerHTML = "25%"; + document.getElementById("percentage").innerHTML = "33%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "25,100"); document.getElementById("modal-content").innerHTML = language.en.loadSettings; xhttp("http://" + host + "/uistate.json", false, function(e) { @@ -1711,6 +1674,7 @@

warning

} }); } + function applySettings() { // Make sure language contains all the words from English translation. if (settings.lang !== "en") { @@ -1723,6 +1687,7 @@

warning

translate(document.body); document.title = language[settings.lang].title; data.modes.forEach(mode => { + console.log("something"); mode.hidden = false; if (settings.visibility.indexOf(mode.id) > -1) { mode.hidden = true; @@ -2037,8 +2002,6 @@

warning

colmain.dispatchEvent(event); colfont.dispatchEvent(event); colback.dispatchEvent(event); - colbtn.dispatchEvent(event); - colbtns.dispatchEvent(event); document.getElementById("settings-open").addEventListener('click', ()=>{ var icons = document.getElementsByClassName("icon--link"); @@ -2159,7 +2122,7 @@

warning

function ws_connect() { data.connection = new ReconnectingWebSocket(ws_url, "arduino", ws_options); - document.getElementById("percentage").innerHTML = "75%"; + document.getElementById("percentage").innerHTML = "66%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "75,100"); document.getElementById("modal-content").innerHTML = language[settings.lang].loadWebsock; @@ -2167,14 +2130,10 @@

warning

data.connection.onopen = function() { console.log("WebSocket open"); data.is_connected = true; - data.refresh_interval = setInterval(() => ws_send("$"), 10000); var con = document.getElementById("disconnected"); con.className = "hidden"; con = document.getElementById("connected"); con.className = con.className = ""; - //setTimeout(function() { ws_send("$"); }, 2000); - //setTimeout(function() { ws_send("C"); }, 3000); - //setTimeout(function() { ws_send("~"); }, 4000); document.getElementById("percentage").innerHTML = "100%"; document.getElementById("percentage-done").setAttribute("stroke-dasharray", "100,100"); document.getElementById("modal-content").innerHTML = language[settings.lang].loadReady; @@ -2205,6 +2164,7 @@

warning

// Log messages from the server data.connection.onmessage = function(e) { console.log("WebSocket from server: ", e.data); + console.log("data.init: ", data.init); try { var res = JSON.parse(e.data); // document.getElementById('modal').style.display = "none"; @@ -2311,10 +2271,9 @@

warning

// init display Colors displayColors(true); console.log("displayColors finished!"); - select_active_button(); - console.log("select_active_button finished!"); + select_active_button(); + console.log("select_active_button finished!"); } - console.log("data.init: ", data.init); if (data.init == true) { console.log("Initializing..."); // Set selected mode button @@ -2323,10 +2282,11 @@

warning

setTimeout(() => { document.getElementById('modal').style.display = "none"; document.getElementById('container').style.display = ""; - }, 500); + }, 50); initSettings(); initcolorSliders(); data.init = false; + data.refresh_interval = setInterval(() => ws_send("$"), 10000); } } catch (e) {} }; @@ -2361,7 +2321,7 @@

warning

function select_active_button() { btns = document.getElementsByClassName("btn"); - for (i = 0; i < btns.length; i++) { + for (i = 0; i < btns.length; i++) { btns[i].style.backgroundColor = settings.theme_btn; } if (state.mode != 1 || (state.mode == 1 && segstate.mode != 57)) { // CUSTOM WS MODE @@ -2374,8 +2334,9 @@

warning

segments.className = segments.className.replace(/\b hidden\b/g, ""); } if (state.mode >= 1) { - document.getElementById(segstate.mode).style.backgroundColor = settings.theme_btnsel; - if (segstate.mode == 56) { // AUTOPLAY + document.getElementById(segstate.mode).style.backgroundColor = settings.theme_btnsel; + document.getElementById("on").style.backgroundColor = settings.theme_btnsel; + if (segstate.mode == 56) { // AUTOPLAY disable_modebuttons(false); disable_color_selection(true); disable_bright_selection(false); @@ -2451,6 +2412,7 @@

warning

} select_active_button(); ws_send("/" + mode_id); + ws_send("$"); } function set_speed() { ws_send("?" + segstate.speed); @@ -2597,7 +2559,7 @@

warning

function drawCircle() { let radius = canvas.width / 2; let image = context.createImageData(2 * radius, 2 * radius); - let data = image.data; + let idata = image.data; for (let x = -radius; x < radius; x++) { for (let y = -radius; y < radius; y++) { @@ -2624,10 +2586,10 @@

warning

let [red, green, blue] = hsv2rgb(hue, saturation, value); let alpha = 255; - data[index] = red; - data[index + 1] = green; - data[index + 2] = blue; - data[index + 3] = alpha; + idata[index] = red; + idata[index + 1] = green; + idata[index + 2] = blue; + idata[index + 3] = alpha; } } this.context.putImageData(image, 0, 0); @@ -2682,15 +2644,17 @@

warning

document.addEventListener("DOMContentLoaded", function(event) { // Code to run since DOM is loaded and ready getModes(); - readSettings(); - ws_connect(); - ws_send("$"); - //ws_send("C"); - getConfig(); - canvas.width = 400; - canvas.height = 400; - redrawColorPicker(); + setTimeout(function() { + readSettings(); + }, 500); + setTimeout(function() { + ws_connect(); + ws_send("$"); + canvas.width = 400; + canvas.height = 400; + redrawColorPicker(); + }, 1000); }); - + \ No newline at end of file diff --git a/clients/web/index.htm.gz b/clients/web/index.htm.gz index c85a898181e1a69bd15a16b59f36cc23e5c41ee4..c777c4195a0dcd966fa4512e816739b49a67183f 100644 GIT binary patch delta 8069 zcmV;0A9~=9qXCi*^uLKS3HHHzE+_&(rDcC) zE!S?D6cjI&wf-~S-K%YqE#L>ZPUiO2@P!U9Dge2Eu~{PpaKGLziY%S)iiD2zZ@!1T zS$;LkGQ7_KWP2kx-qWok4QEhht3KBPgEiso4Zuk#1H&?cyjOMbU*kO80Tl7%8bN^# zb|gpkk%YwLeA@2=@F?XQWvdjZ{g{8w;K8%g$FBn=Yq23gEr*HIZq9Brz>4~DmpTAf zosOmXL>emg(dlQO4z{z5Zs$9C6Tca8%{NLIQ5mv@H8uV*kn%D=j6K)FhI;;hJb?|? zvumnB`Ga34l5ZeZ{Lu;rmCbHd{mi2xOKQC+y7kVf{ds^F~8c}oUXxM%x77w0+)eydyzN_3)9=-&}BO?&FI%en00IrA4rp4s}$`5 zL!73%00^?jPJqAzY76WNQ9pY0u9A^n@YE0K2~Q>GiW0iY-W@(OIu#NVL7lkJ;?BE| zzUrvZ`F33aefs&^p8~kHF<5^A{z!wJ7geO+`SS7O&vfGRMw}P7g#}Hc9Bxy_hCE|K zlwCmz3&k6C2^>wpJZRl+(Qc|KA?pyY;x7$Y5- ztu-N(QVxHHb^xd^YhI{XT6x+7^~cfm#lvU?yEV6~F{)+k7f!?yNf<#xGK`&FjVoZq zT#?HX89^OI7wkir4#zO%2##E5^mDsiUomFjx`YlN^D7H5I+Yk*m$Ut> z$ThzW1_g9M5bHNr5b-f1s{*k66CvbIF2CY zP~Qb(-SgQ;v@+hY)pfxR0UW#C3&XiED=oc>=o7IGAzx7Dk4@(ho|gr?&Yoh9F0;+G zczIcUw0R&WLfRTFlUlMyiP>62L_v+z4(HY+1;A7$q~X>k+h-zJufBQLnGp??Z)z%E zCA@A&D9zMH`5}KqnZ%{Rnr|-dOe@BnlBus`mJdkMUDu`x_=`^!p3$sN`O2;~&DDk$ zGG>Cd)!6bzka%LfbT(ja(I3fXb}N6XP<{dp*YrtPdM+$Zi4e%IN%4KG?-$gx#I zO34`N^e(0?+kiN)-vvCrcJn^}8EgLNYBT5g@4(mijEsLVGbrihT`9Tlc`y2z-I;oT zJv3!k(++S1c_4T$OXS0I{6L^T=ut_%=z%u&&{l(U)^N&hk%SY-pBjnFmrLmd_c{$}eBnCh*sR0S+u}W^{iF8W`z-{M3T7o(-iqJnsCRyAv^^ zi93uXx*rOgw@a``V$hL}K?;P16Zm)|y5&n$@C!oTs4~AjOV8D*5+%6L@XA^3Yy2Fq zOgZcrjRUo)zn@^s=vL>Yj*&x)k=Ht^xD$S*i#>J`&DIy?j&!jx8UnEN)1}6_qq9zi z{BnN{fqpT9j>&(}?C@MYX6Yre3?niJY%h&@7!BM~^AouVBjVdL^Y1a)`%Cx6w!hPX zhOwe_$*6h658h6)hhRpPdI?0UOVB=(>MK+EPAA#)kP*}EAtPN1VpFx)2G7nsl8bHl z$8n6=I5k$MM~vFQ&I$Gz!k!PxxA!C#foOk=5sZw{RS8OHi8dNeBtWAxSr?nAbcUm= zBufnMk)|y<50FsRk{n1jr9=}PgRYuc4S1!S?BEL;WJPJ-6733!YxkA);V`l~B0H?rT!WurOD391!3deKL!)AY4GiIhTTd8XO5Gi5HW@Wwz5 z$rB0Ds_D46@uRBoaH?)#xyQR=R_)EPS+jKJ7=|HR2npKh$uDsshkX4#YQpR7l}mmjVDgg|OJ{ zLcAXYlUhN)ES0DFONd5pfkp#p5`LA+FLae(NSC0E+O}w3O^WR0$a*m{xGK{qq5eU} zkuhYMN0wY~AUT}Sm$=kQ5zH-m5#QBBED7E~d2D)9z06-C{w$~b%^!cYlnLyO%8CxP z0gbbZ@~8uq7Nidd7@!ac_RrD?OpEjkO6u@ zaQ`gDAeJo65E((LL6FtD0p>yn|Cg%<5DPOH02pF00PG)TFpwi#Ehs(AU;to^!8q=! z!2eonLBVe+_N~2Bp#*=%ZMR{epSGGZbSCorjDCon!biAwe$H5M&u|ytSFe*Y2s{NW zRhFdWTbSJ$(2U3-qAk5EFx1(t0kl>p}|XrmQ07cnS9Dbv~+ze;Witcn#0eV6`#rX;5G z){kKL73lmRTs(j3jk~?kardS1Yp-=*_QM?txT9BJse(HaaHG+~ZuejW=e$B9S{9ql zYCdbwd8p73%9oo>k?e!8$+Bpb7-UX?1II^bvmZP+8jT)Aufv!3-h1ys2xVel#q(R z@<|2rbjbEnVcZEi;Zos;@0;``1PCE5PTo9y%H=-XzDVOj_`Ybf$-y3}!(3x;G8a>q zJ<^AnPrY$7ARCb|0)Hr^ymx{k9wH;4k1D-G0ck=tX-VOh;+= zLmCg*?uRlSyWJCM7CUA?wDWDUuVxg+rX6X^Unv46MF6CED}{GT1X(KFpO_C3W1LF3 zqauj(VRfd-_)x4vsIyg>`bn=%z0pdIXY<&)W>NMYTN-RqCLer3snv<0Xd z3X^*^hM+arCJRDNYEX(+YUBEH2Z3Hqx|}T%9zDHDNIgD}_eOG(lbjk5Y)}sfT)heF z4eZfImsnSz(n6|F*FO-KvZwX@S$MOIE3Uk=Lf4{T3nA*5x1#~LyoV)XA$094QS_(N zj9!19%BTd^ZBNWdSkOwi50>O~<3&7}6*1Mx6(s$J>-B7_-foTbKl37&#b=!@61TYU zHa(<$3O~c@WjIlq+W$G%PId46Y;mrdhSbs9jda6(pNUtS-(~7_t!Aa0i)ORVR;$0N zMNzIyI?=RA^G@942tbz&CAAaJ->Dr_U%r1`i|R_;+iStK(Kj^5p^2$ zr5K}=aqadgPuRj#IYf;cXl|*@N_!Zi3eD2|5c6om^ z>`3qE?R9!Rqe`SXF?_*7w2%nsid2j@+1X|92uc~@m#*txY6ryt8`ngJm*9Q|Jm5mB zMvU2p=$?yIhRswTYzO6_P?;vufq)#PZqDL@xe7{Ko6ZEl6(T)B4b zd_q*l;fOKO3VaG_{DpC{>lMsW*npqEPm=8k0kg{9E53Fud(aAJ z=PH>0F;uh<+GM42S}SSv0g}3o?s`J1&-HBVb^@&$)1Y7K<+buPeT{+uO{sq&1V#a8 zVS2Zwyb)^Htz$whxSe*rz_<(CbdKi78*?o~@|{qA(!NP0lFm!Wa%Dq;E& z6Q{JvS_O;yUFctXk$AtqSBd{w;fbzUXKCMQ?mdFutOFbE zJ|GMYSdnr>SI1uxla$Lq0*O)pvrGyfnl*LM*=W6hkZ;A&e;8B1k3&$*4o?*H_7!4XRS4X-*zkkD|L%&<2t^ zAATV<`!UH}tszGQJB+%m<7GQhY4#LPeGOhlGHYOOq=UhguR-SyQ*KVT)p!x0Ii}u$ za=g%xM7Z(+ai)DC1+;(FKn%utC)~xo>LHDlO%;(%2WnN(3`j-~H^J^TFf?1SaVJYI zvn0QIlJeB9tI{8DmJy8$xvv(KtJZ=NoK>M5wK5`38GSab5)PpD$WUZ=Cv+3;&8cEZ z2XgjEoHcX{yxkQ3>Rql@9W|)43Zu}tLdM9~rtD6eD0RGC@*RIh(aY`@g7gslu@dNR zWJS93=rTV~z@nK3^wBcdPf#FVso6-LlV$;Z2S^(^d`6GHNkw9CDFQ2hsdWLBcIj+p zzAPZiI5-GeM0`Lt@`2dT*MWV znc}d4dj0^)6rfFL|f`;qtFg8H}FEc00{HYBg|JdfxV_{siCwZ5a-hv4t)N+ z;MGCqVJfN#wmMk)5UT^M4(5J5e^6CYGmaQwZYu;eZY`*BYe|jUifY_iR^vv(^2qA2 zwX6M&eZZs+oZHqsh7m1XEqhZlcfg%^#c8qOpn2C66MX^_h$qkQ_A zlQ2^qXA%^%)EA>P$omx`HEa1Jn5l+S%OAja_=Bu4?_5UC^z$cSraI0fC=RGM?q@K6 z6yws*pM;s}IFl$OVy8DkX9#~hYGG8-IRwm9K?s?0FV;rmN?L)O0fk!507i1Q2v`hQ zY<7Ph#uj1A0U~-^6g;coWk^iHv5Y0xYCQ-B5rAxVkq@;m1u84yzDA%Y#N- zTlKf;y0%Xu%v3?B?UMlG)MQ8x?2&Xiqk?}e2{YADCXGXI*lZG|P-{zZVZu#^BYKTS zY0~WMx^cxdIC5Ka`gqB;wt&&NeF6NMYhWy?=Jes3Yi$LN;f!NYKf;IAz`!(G4TZIs zU^R)d|Is7B64pDlkDRl5|BLbT=Y1u_Qxbn!{tNmSNE(o}@7Fsy&*^QBY_rP!fMS1R zh7fExkP|C)NF6BmRcE>!bQ<}|VDgmF zk)H2#dvwrzSo!++0xtzdwEHVJm+jMFM3e6tlOEff#HSGg(SEN0oVfR&RbuLaXp#2p z6uC!xuB80h=@O)oe4+!&1Jx&2kV9vweE|8Q7GhfqkqHRNoeg$+Rzv6XyaazB>4uyV zt~`0~YaaDjW3i#eLiE8dTRDzO*i9uzGw0EBal7#eTNXqkMd@))yQr>*+!zLJyfGjk zTo>K|9GW(0FnG1ZY=cItmaP$6@`?+dZSh(biL=L6Wg=otp z=>78a@n@ez(8oXd?A`Z_$FeFf6Y{R@zCX?JpZXPQMz+z7y0B+c7z{9HBWjBxBC*j8 zS9g=W$#>FVnBKFi<*oN--6(bgQ3ZCfBF0GzP^x374BgNB^6_V%fBb*;w|dJ7^N!&B zwsVYris_kq#{uwzy|C<%js&izOlK*4l;xV5yOyu8TC#rg69^ zkXP~jG)uj`%d?tt^or7WmT|Vt=3y>*eI?*XLEVkVvt0Vtt8k~4{Sj; zK=3QQ?JavtQQho-pl5CTeTM0E_-#gI?ON~&cf%1{=i)(ot z8z9_93*6B6p?|^(JYVO`wMmC49nArCaLI+u$I!Md@KGDkt6WZ_i{iXMnkOm?Z6rlQ zhNMMu8d^fX1$2xf$1ZevVBJCE1)yOarFT&w)58b^p9CyRc@9gFhZxO`*`9TT%Su^V zDf9ELVwr*u-AR9*YM2_^T-ixWJ83=+W$e(ySRH4FHfMIy(oUKmYMkBUCyPO%y`_I5 zqL9!nsoDC+S=F@R0jm?e0`Y`FQ`k9v#R|jP0yfJ)+!K}-KNw#SoEB^1db?QzVOH-& zDV{7TcG)_LJ3|x1~x8+*s?GpuTq!_^~Zmh{^fQH8&>_QGd%b@L~-NP~=({P(^UynYS6;}gth+-A< zF_uCbxPyN!Om@GC`apdEh89fA$H`^U?dg>6LMeSKDPi8WtC(h?>i)`87%i-Li;A%# zzX{=-fqv`eO|~PCoyxln^|VLVP{((n{bS&3aNCRU;|?}s;J+?iWQmOL`{5Hw?;I2TFt<$w{6^Q^|jV2O-nJ#SIG&^wI@A@1|ycDsM$+_{Bs?4#K4@o46SYn#>yga*=` z=r1sI!>|{@f831Uq!-0i`Rgh{zd;#T1nrR5j?_|#O-hGq*p8e8`WgqDSShhA^x&nJ zIOu;%(YpYd^G=1MgvdCMvQemM7Il%}PUtt$RI71x5RE4$(6<1j2|_^G_dz+;p1=%} zCzeDP^S^-2@Lg`R^l)&bfWmIL0vcg*ACG~Z;PaF{5Yex5AT_2*#8;;sqK z+D-?bWedB0DmSD*V`vt#j-Nm3u}x`7oZ5c^?;C4Oy&lD226M_>M>Ddj2*jCqwyU$T zO4rHPRM~0taH8k2cnPOCZ-?B@b3^*;IHBUMkxW4aN^z7tU#6=S3pO`TX1gN2+^s}- zUI9|fzE9S4+nLTdy&hc^#TKGPSrOKi)Y0~A3t27@} z_wtMhQk0zly&D`7xM^ zS@r?T76aVq75o&WB|1I+!>-5`n=JyvHaEVTQws{7n%LGR!{KRvmB7RcB}jh(gi{kN zTgqD-&7$8>j`wFMYX@d##@$1+^ag~{S|tV7Ht*0(Fe$ptR*Oq#8nmg@TKT=JQlKC; zQ$|TR+KRbFm|Mv2Gt>$Ecq1ym>s$L0<4(o6Q!wrf48g`(1}^_qiXQ6i-FUlM&9WF~ z0e8r%Bcw$1CZ{Ng8R4eCPq%**UmB>~bwNI02GTXiCI@Yq6)?ck@SCR>@Oh~Ww9eCp z;M?sIdr!`;#syuL0oKOwErtqN{L=zmy4a%8Eg3s$9&OXxWCdvm!yB5~ zieexQ?6R}X&ByEj?^J2)i48cr_->aM$;CG)Y%stakb7}3P(zEear}R*e?-w_&oPS8 z*$@pie2;-4RiePLlgF;VXmlp;+(qB*sb~_XbeXWo1lE1Dl+|O@x-K1BZLemiXh%m@F=SHCNIFOy3Y>TW zKw={RVhmM+jRA}pu7o-SD8`&`?OGq`w>xF&fwYK*$Dy$@tQ#fWOhbV*VCO$%MSKhG zjC|a|=bdV2!4?QWC~7^9VR7S@0OX>aFoH(e!koaT8i^Qwf(m~^NBRA?UiABK=a2w% zW|1vu0wRc(0HI#sBuhA1aE!EpYwmd9+$mNZ5z<~j)%mK?8cj%xE9ldpFDwhFNpM9* zKxhOo@Bs`!aWV(G8K(ib@hIwZNzU^)Caf3GlkbDuugW|dfu_U%^O3ePNC;aC5 zQJHpd&G<~>qDFt6vBIIrKsV0yNxMdKq|zK$(*#A%VjGV=VFYesxD?x z!T|qyELNJRMJbuataM#QP8;YC3P>P-_`|aj=3L6rUp8rdnM|jd==##>$rq14e~gP? z)vpT>>H^=1$Ge!-?+i$x7+7$o)O8qwgeo?5>=!0F?|$|PZPh^9W_FQWz;skJK)FXD z+Z+nQmd$Z?>nKmxizEVc4E?wwTzb_c!>EybB{eDN?iaf*MXsTEFJA^-Ht zFF*hCg~)nJix<7Z?oUJ-P-N2oCe9?-hfiHl1b|9QWKDms zc%Bp#EmgL?cl&CcWK;M7zLU9swf}N!7>wMVt(Hgu{I7S5B1?J@69B$gqqc?^Z4R*EmqO2SuD;At@)BpVBeBcy@pC{0UI9RvQvjbC@}8ChSTBEU6#0sRwY~X<4dI zq@iLTpM3sVZ#~ZFdcLDO@v9M6e5Ztn%9t$%U8{idazBhkS71|}(6TfF>n+DuRH5<* zzg{HYM6CFu6%Q(#-LkslQIaLKPL$5rPl7{Z>L&>*?o4jn(M9|6AP~VXHcEee_iH30 zYEaBCSJx*?upg6g7OTKz;N4Cnj>f`tcYohyOEAsq=PYjUpX%tZAMU27zkc}eU7c08 zzOPRSZo7`oa38#rQ#hxfZVpfq+id~>q&%A(S$2R|K|+i)gkde|@<^?hw1gPx7=gss ztISVaLX0$wP~v#X*GpVNjC6mDK;n2@*h^eOjC728;_Tcpr2B{qh>-#wM0UC?s>u?> zNP-8*nV*7=qVPe87bh`CDy3mHmU4O;@N`mOF{X9Sf%1Tj*; zgQP?!!M$W9#7IN_NCbQm;ZTdfJ#y!8z>T`m zv-g#ZbjDLZA^|BmOk!>2I1s*EJ`znJ;zaURh+FSJ`?{q<=j&w!^vM_Rex`w^(^Uod zGYxi9RFQt~tLM)@*NJ~m8gX9S6gD(WoJp->L!PlA%C;bdh2kas1Wr5Rv8foyDp|UE zYA>~OAV|~j0jaHIf%QUE@dmuiK}JS`C7DbC#o%HOgF6au7F~~-{_B?D0vE5pMZ+he7;Cnr=!IbDIrvHubrW6y$PX|(#tlq13-OQlS0kX z%ez=4H_=VrA4K`pQFJwX94+7g$jxGaY8m^56R|`RMv&*9z=cMQD`3U6P+3ww%JS!y zGzL4G=?r!-)8T&=4p`UNq|EMrpRbn9W<2;POeEvPn-iVlYAr7whRu22(I+>c26y-R z8tj+s++_Jse_6tHT3oWY@)5{Amq-`T;bVRa5=N&IqwQM1dqL!yk&Yp~O+{AxWOp#%7Q4qwoW7RJ-~ znl9L{3P3Rdu7y!$=~G0XigOL6-c!?zQ}BfG0uEU92wx4!ql;{H6+K$ZlUYos)KvIa-HS_+Nq|Xsw^I%e~$X;k#!lhM%nM{@BefC1Laly%TABJs`5H z_W_S@_B#+t{uSWS5Td+;?rC3DM6MtX5uO0Iu>)`{-eMe9e{3sZKVeGkWoM}p_F zL_Pq=j|BRo4wcl29%-WsolkJi3r^V8QyN1A)pq^Rm4N9|FpN>_AuOcA;#bGVPft#a z20%O4kwZ$zEZ6J-G-iPpkh6^^pm;#@-Nx3s>_Q+G<~)o35p2@g{GSQLQPb_~7dWLi zhX8-w%T3s^BDb2l8j&U%GjOo(YwHtkf#K>v`4Wq6!4bL?|T4Dg+( zuir8u!Zuwr_92vUC&gs--q|VH+?#e+a+-m==(Vk5VXNhdcp(aQzhQM|0jHo!w#-wk z5zFU{XyxZbCYkX_0>A(VmNqjw0S%0FKz@JJQP~8CQXD>Y{@(4en6tz!#u5dUIA0`l zut&llmxF&wOCs>`R&>MnvEUcP$x~&1bDEy1lOalQU;L5t);Ia(ADME{G8zYJQGcn? zmeGyQOC2Kz79(%ARB&(2 z(ERUAy_?}BG7lp%0cIhw7LWxPEq|~D&Oe{n_e(ty1iheOOfxYmeb&^x@U4Z4gWZfG2f=fYITTF z8`wF8K1JBGUio0J#3B%Fxq*=}x+;G`2`$k^!=VIdbdY-neQR}<6qi6Lx=gaf@E&Pu zlJlraRV~SZWK&8s!7=Ennbm+-+E)T!&>$;H^OtB>NNzv+>%(DWbwq-oZSH02U`=Xf zZHgLY4Q(N`jxWI`n3!!>W#xuwMQuwUQC*2<*0;9KrK*4RL!^W)o0a)eJauS*HR-?_As{S?_?z@3hZfZ_UCl}1 zyLf&c)S%O)G+QdNsJ7m!HsBW8EY5l8Wc=EkW8HORZMcS3Orltk;zgR}1vRd zj7tLZAlvi*?KJ<-Xn(UF5YP*PdxBE!20cR4#&x=^S3&?1HAV!7;z56^%->4i7$fj+ zm70kGQsOwf7#_)~uN6Z1ry~+(_a-u6W+B;Oa|;C;6YI?-LD>z5$wLXTRnu{C<40BF z;Z)tga*ub#xZ0azvu5ecF$_bt5J$Y#(ax83`x?AG38!QU(#Yl0i2zmntQsv&K^g{@ zM;fbjtuR(=DGT_~NECknZc74E6@cyJKz!pzg%r+oDFCoj2-DRj#QQ-osTK6gQhBPs zglOazn8y_fze?q&y2?+bOR$aFZqdA&6xnmr^fQ3on5NFNX| zKp_z9pQRDVk);wmJxC`Iutq8R14NVXO_qfIiCRI_gVcf`1N4I6{#lAaELoZ%GJ;ft zAggr)%!LmAFINp97G^L2FvMU0*gwo*AV;=ZPsGRgu7x1P<)kL%Zr*=V@gi-x%*C(1RB~aR4fBJB zUmI~znaoK!TJ7eC&h5!Z(gzVoyZSSa1MRrpt(L!@`wv-9rC!c?=;CUeE^E(GbP-Bu zxWKZlr1C0?3fgD|%|#5#P|CD+#xIi_0;^(0Lf@u8qA7{#MD;Tmeg!%|2p9J|gLbEX z)P8mF=9_=**Zgn?0`BmQ*Q?+T1zf-XxZU3C!#S^zFxbUvwU~?>bRH@+g!08|RV2G0 zY_cp`B?g&OwBf-a+U!R!_WS)u(G&Rc^y$+_A(V;b-4UjHEZb2x`xCwwRNtQvO7tgz z`Plw!IDvUcpCtNE0 zfPIs`ga9F=#mSq8r(EvC?TR!mgzt(rn;h(rI?Oe8CUY@$*&%(H32o0lKh0PqH^m;^ z@nijbmaN%X^azq9%?Km3W020!!5C5h*<-N?rJsi!kChi7<;2}{G?r+3kH^9vgMd@9 zbt8Y!U@&lwZ}-7Ua+1v9fq?DCI`|7XN4FdDEac%12-8v8-H^ruw!5K>$8L8-ngyKO z4eflL?5Y`svDuEa<*yV0lOh1pyp_T`C4wv!?oZ5zh%rtj+))uky0ALaWPB)=A=KHb zO#P(Srru~J;(@2&mE15}c|M*NDXjakoBMxp+pjEnkhTC-Lt%2S#t^gy+hjq=NexQT zN^M+U?jX=pix=Z*!k=7e5{H-1XzZ2G_*mKd2wxJjW zqG=x1$q;w9NA>(!c;k#~zr6TDcdK9@B5IkJr~$aV%q2o5wC#IU^rzE|UK`2a1=fF+ zQOrnKxNNvomgID8Mm*ISG5yOGB>gJv)p%`PgOz{gZ7_?^8iOXTf~hfT!s=ysVp`w% zbN->~Bl_9mTr~}Kq_-RChWkfo3Np0U20hGKEN6!*Mo&+^6bZ1DQvb=tIi@$qzgak$@-F4nut^lE=hl}K}9 zc*Y{RkO=6WRgBl+*^TiCO6lX5w(D|h3&jAt-$aI$;C>_IF5p(IMvU2p=$?yI2JDW$ zNhT*N@YoAFra(cu7YRMg&$qjQ{GIt?IOpg|)W@2!TsQ~#Wm04*J~BSwX;~t1-cJ_e z+YhtV^#@~o6k7t#lF4SyUN3(Kwubt<#3E|IVxb2P&@YM}FIF&4u2%))~ z!f>wK-F7}+E(3PNm}rGuhcu8eloC^wqt>V6<%UY4)Y+3K70goXfx91)WPMD)tg`ot z!(PiCw8H6`3g&-?9qofQH?ud+Ks>HZKQ$0c zCy+tt5ek}-H5_0*C6%0V52$t;||fFASOYX;7r>pKSbs-?Dmw_0u_ zJ#O1;(71J#F#U+3Q`%&$g2nwl^sk*ryxZNW#Q&`DMAxjdv~P_fY2X};gvLs}4{AGd zNrKz%DM7E6fsJ+_5X%OvNI9ab<1dLx%B3fPL@9t-CWVhpl4O7PVw^4#8PUWmTVhye z*{w7;^Y-#OO>far6-iU)lQ5iupIY>qwTEDqWmTXX!B29Dhz&iA<3`Kq* zsq^6%QnR0u%-I@pM3C;TH-2N;PE?vb#Y@Z9PiA&FGy=(zi!8}6&uNtuCZTNTf5v~s z)Ys&3ua{cw4mp3l`&d>3!zDcxuEhF5z3nL`NII~-VF7aqaHLz z{gtCWM%19q4R4QwR(rYCj6`_11LD;0f_U7v?_spkTj410vC^ zW0_@tbN0!$tJ0sW<`IpExvv(KtJZ=NoK>M5wK5{i8-0H^trEHp_Lx{?x5spm@a>T@ zhV~TUnMM>msaJ;|dvL{x)T|wh8jb%O$U=AHC*oAxICwA1HAG z`&OVpk1q4$7%bpxKp!n*B?Uz~mYR*^IcXO0xQDb=4na}F-fk%|_x6GoMIVvndn7h_ z`J08c0*E9G94 z(T;xt(Iz_D>w#z>$$>|dk2P@}YQK)~mn1b~TqRn-*erN}n7aw;pHp}ezVu9`1Vh6IN7M1l=+xhfvAysLl8GANL%FK}y+_bcLz*7E0g4YQU% zfbsALSz+FJ#dDf>^$%(W1xNJ;Lk;H7{UYaG{hORoNElOZ*wPUGDjxN`t9aHkWXgX% zT^fxmX$5iy6lyusUj_|W44AGq9>%6&%K?Ac%c5Zy1C4t81+SGxQTV%d~;8aCMN3(x>p_qr+kpee#Z6#{5^(1;uU3hiCRJG8ZZ5@4K~4C#SA()Wt( zUEMpjjpLHoY!anVYfHg$!cB)Gq>q0_Y1r&6zH#q2IGkN``grrVwt)U%`vUmg-@pJ{ z&FRD4-`WZs!R}{JKf)K~z`!(G4TZIsU^M}FdCU#p(=kt=*d-BI5ByYmx2pWXk1I!S zNBjQL>|@$=lI$*`$JU-mYMm&Zv7ZDdk5UFs0w_7)8p?Gx5gE8~8+C_0bh z(P4dW|7FthckroP{Br_Hjgn^v{8zxHc-b+cy{%HG z1I*co+WLq{Y;<|o-DGdGO||-?nGfVILGgl=RFK0XV1X_Se)WI+^DjPm_d8wQ!Y(5? zzkVH)Z(vw`uK@?=(+kT^*+}4O%5)gQLs>40d20DOt0mL+^KVWV+MiQ)mp%&3Z>Aqo z6(kvP5_XmIfnp!g8+SkYbbPW*rFROy}7PsD7`;7t}v{n}vjlwp`p>it;Hq`@L zkPQ(0N^iTl-cnTmI3SeUHjX;O^m^(xqq25e@CkU^O}GfLDVK^yI47xB+7)a&ln0m{ z)bWsa@9|~(Fh@~f*!8H0agh{M8A3kC;_jrk3R0OQ;2nSDcoSxxWF?Twj(#G%uY1s1 z9>)d6Xp&YF9Qwh?7NE!nHokQ_~>3)%8OWvJauU9q;{+`S60g0N|~Is z6-yL+N=|?BRKwK3=E_c*+ewo_C}Rg6#_BjbusO4n=62HLK;!HlKY0)o<;@BB&cmS4 zWu@`*r*YLZ;SsA7y=8IEpecABzv+a*c>$YcAnq|siysYU1g8bNxLU84K$z8gT8bx2 zicPkR;?_P2hFJ>8?iH((A_JQiLxfxyffp%EeY$@GO#f=Vh8?DHp2U_Jl7fXVRuPg1 z0Rp>(Z79`|(f4Hxd>POHHb1N737H9M0~XIu>t-)FmLj#7K7@J z&OpC&^CsJoM}XzshI-nwE2!i9(Ec&-)w}6L_;CxD>fpaN-9AG?GL-c>ry-S`5{v+# zWPp738{$1-peH?(;Ts0!v;`$XkK`oJqLF`O!GnYjEP{5(n@wt|#3rRfHEhRC0)2ynO{|ny7P|N9s~msy z)#!bI%z3B6Q9@+wN!cjWG>bY-p#Isn(MYRtv=*&3l{Bel8iS+da+rEAj1Nr z82^wg>C!PBN_rAq7R4IERpkY&6~MTgT`X4DV3n@+e%vHEZJh4)-xwSnzOjG*cyF>v z7kJR1JMI$MF8NvAblJTut`>*J^L}6)7R474Cau#11@(@p8N6!H&ZUy_YJB#-vG?FD}!(SKZ4q zCQMa+Qe;4VgK)ZGQQ+v(8eZL=&yhPwmVOm~&GHj4731tf zmMsRj{_FTDNK15j!ie2zD^_a+hW%)K{ihZbJT7C~+xzsoR(@Z+th{I2i6ON?6;<5t1AH82Dhrx|$smnk}^H@AcJYBA1Ym;~G+ zr;ZR1(c7G&BxZ!W{vm%|Q+#Wna@z*+fE7rWAetPMWn94cN~3R{&fxPx8E2g*`oOi@ zI8JWa)tJ%c7GP}v-(skc#XqgbrSlCdp9&^xf@kb#k&>~K=FvL6NfwYsFw{J(ttb*v z&n`P#U4Oz3+>Vr{9@>E8+4q~gNM_%nu)+RvK<>oBI1Me%hVg&X?jc39J;PW+r~7E9 z;d=}WsS*W_ojkVvMWZiy>n{3sM@5r3rN@LtCa{dm#hfKSZqf`0K92Ims>p@hB}tni zH5d63LZDEiSXS{>*(7cBG9(8>m+oBBqzUxK(Pa4;7H!5ngk2Wx`5RYEzWTj=XDO#J zN$Ri}UWev#G?{4C@*<1R&SrgaI_l7N!I~)hNjD6V!hXI?3<9b)w&YJA(w6E{kkI z6A(eL1PJv4|5(Dwf@7o&TyviTr%kcqgOKI|s?Jx9#%MyCUP6BcU13>3O@b>j0z!R& zfe&B+ijz6e#W)SXjr&oTOLCIOF=4%oPJ9i zXg*eH9@f@3+P*887-O1m_Wwi?fp8O%gQ1C-knvdy6& zY}saPvyAd|IZYx!$KZ<#!lf5gGK|~E7g3Xf?rDj61LesJ1>R`6dK^wsx)x!xEP#bD z5SaQr0s5qPLQ!9DlR4gp*tL67Z|&vNEL|6GLlXU*tY)|H