diff --git a/config.h b/config.h
index ec1befa4d78bc3d184ef130bf97ec4532c801ba2..ad03ff94b84ac0f9c6f7b627f5769e04a5d5375c 100644
--- a/config.h
+++ b/config.h
@@ -1,70 +1,134 @@
+/*
+   ESP8266 + FastLED + IR Remote: https://github.com/NimmLor/esp8266-fastled-iot-webserver
+   Copyright (C) 2021 Ricardo Bartels
+
+   This program is free software: you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation, either version 3 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
 
 // define EEPROM settings
-//  https://www.kriwanek.de/index.php/de/homeautomation/esp8266/364-eeprom-für-parameter-verwenden
+// https://www.kriwanek.de/index.php/de/homeautomation/esp8266/364-eeprom-für-parameter-verwenden
+
+#define CONFIG_SAVE_MAX_DELAY 10            // delay in seconds when the settings are saved after last change occured
+#define CONFIG_COMMIT_DELAY   200           // commit delay in ms
 
 typedef struct {
-  uint8_t brightness;
-  uint8_t currentPatternIndex;
-  uint8_t red;
-  uint8_t green;
-  uint8_t blue;
-  uint8_t power;
-  uint8_t autoplay;
-  uint8_t autoplayDuration;
-  uint8_t currentPaletteIndex;
-  uint8_t speed;
-  char hostname[33];
-  uint8_t MQTTEnabled;
-  char MQTTHost[65];
-  uint16_t MQTTPort;
-  char MQTTUser[33];
-  char MQTTPass[65];
-  char MQTTTopic[65];
-  char MQTTDeviceName[33];
+    uint8_t brightness;
+    uint8_t currentPatternIndex;
+    uint8_t red;
+    uint8_t green;
+    uint8_t blue;
+    uint8_t power;
+    uint8_t autoplay;
+    uint8_t autoplayDuration;
+    uint8_t currentPaletteIndex;
+    uint8_t speed;
+    char hostname[33];
+    uint8_t MQTTEnabled;
+    char MQTTHost[65];
+    uint16_t MQTTPort;
+    char MQTTUser[33];
+    char MQTTPass[65];
+    char MQTTTopic[65];
+    char MQTTDeviceName[33];
 } configData_t;
 
-
 configData_t cfg;
 configData_t default_cfg;
 
-// set to true if config has changed
-bool save_config = false;
+// save last "timestamp" the config has been saved
+unsigned long last_config_change = 0;
+
+void saveConfig(bool force = false) {
+
+    if (last_config_change == 0 && force == false) {
+        return;
+    }
+
+    static bool write_config = false;
+    static bool write_config_done = false;
+    static bool commit_config = false;
+
+    if (force == true) {
+        write_config = true;
+        commit_config = true;
+    }
+
+    if (last_config_change > 0) {
+
+        if (last_config_change + (CONFIG_SAVE_MAX_DELAY * 1000) < millis()) {
 
+            // timer expired and config has not been written
+            if (write_config_done == false) {
+                write_config = true;
+
+            // config has been written but we should wait 200ms to commit
+            } else if (last_config_change + (CONFIG_SAVE_MAX_DELAY * 1000) + CONFIG_COMMIT_DELAY < millis()) {
+                commit_config = true;
+            }
+        }
+    }
 
-void saveConfig(bool save) {
     // Save configuration from RAM into EEPROM
-    if (save == true) {
+    if (write_config == true) {
         SERIAL_DEBUG_LN(F("Saving Config"))
         EEPROM.begin(4095);
         EEPROM.put(0, cfg );
-        delay(200);
+        write_config_done = true;
+        write_config = false;
+    }
+
+    if (commit_config == true) {
+        if (force == true) delay(CONFIG_COMMIT_DELAY);
+        SERIAL_DEBUG_LN(F("Comitting config"))
         EEPROM.commit();
         EEPROM.end();
 
-        save_config = false;
+        // reset all triggers
+        last_config_change = 0;
+        write_config = false;
+        write_config_done = false;
+        commit_config = false;
     }
 }
 
+// trigger a config write/commit
+void setConfigChanged() {
+    // start timer
+    last_config_change = millis();
+}
+
+// overwrite all config settings with "0"
 void resetConfig() {
 
-        // delete EEPROM config
-        EEPROM.begin(4095);
-        for (int i = 0 ; i < sizeof(cfg) ; i++) {
-            EEPROM.write(i, 0);
-        }
-        delay(200);
-        EEPROM.commit();
-        EEPROM.end();
+    // delete EEPROM config
+    EEPROM.begin(4095);
+    for (unsigned int i = 0 ; i < sizeof(cfg) ; i++) {
+        EEPROM.write(i, 0);
+    }
+    delay(CONFIG_COMMIT_DELAY);
+    EEPROM.commit();
+    EEPROM.end();
 
-        // set to default config
-        cfg = default_cfg;
-        saveConfig(true);  
+    // set to default config
+    cfg = default_cfg;
+    saveConfig(true);
 }
 
-void setHostname(String new_hostname)
-{
+// parse and set a new hostname to config
+void setHostname(String new_hostname) {
     int j = 0;
-    for (int i = 0; i < new_hostname.length() && i < sizeof(cfg.hostname); i++) {
+    for (unsigned int i = 0; i < new_hostname.length() && i < sizeof(cfg.hostname); i++) {
         if (new_hostname.charAt(i) == '-' or \
            (new_hostname.charAt(i) >= '0' && new_hostname.charAt(i) <= '9') or \
            (new_hostname.charAt(i) >= 'A' && new_hostname.charAt(i) <= 'Z') or \
@@ -75,6 +139,7 @@ void setHostname(String new_hostname)
         }
     }
     cfg.hostname[j] = '\0';
-    save_config = true;
+    setConfigChanged();
 }
+
 // EOF
diff --git a/esp8266-fastled-iot-webserver.ino b/esp8266-fastled-iot-webserver.ino
index 5433cdc432cfeb2e142128cf2826b05260456f14..7a8df779cc7f33efdc243703f1613c8a7934819b 100644
--- a/esp8266-fastled-iot-webserver.ino
+++ b/esp8266-fastled-iot-webserver.ino
@@ -650,7 +650,7 @@ void setSolidColor(uint8_t r, uint8_t g, uint8_t b, bool updatePattern)
     cfg.red = r;
     cfg.green = g;
     cfg.blue = b;
-    save_config = true;
+    setConfigChanged();
 
     if (updatePattern && currentPatternIndex != patternCount - 2)setPattern(patternCount - 1);
 
@@ -1085,7 +1085,7 @@ void setup() {
 
         if (cfg.MQTTEnabled != mqtt_enabled) {
             cfg.MQTTEnabled = mqtt_enabled;
-            save_config = true;
+            setConfigChanged();
         }
         if (cfg.MQTTPort != mqtt_port) {
             cfg.MQTTPort = mqtt_port;
@@ -1473,10 +1473,8 @@ void loop() {
     //FastLED.delay(1000 / FRAMES_PER_SECOND);
     delay(1000 / FRAMES_PER_SECOND);
 
-    // save config changes only every 10 seconds
-    EVERY_N_SECONDS(10) {
-        saveConfig(save_config);
-    }
+    // call to save config if config has changed
+    saveConfig();
 }
 
 void loadConfig()
@@ -1520,7 +1518,7 @@ void loadConfig()
 
     if (!isValidHostname(cfg.hostname, sizeof(cfg.hostname))) {
         strncpy(cfg.hostname, DEFAULT_HOSTNAME, sizeof(cfg.hostname));
-        save_config = true;
+        setConfigChanged();
     }
 
 #ifdef ENABLE_MQTT_SUPPORT
@@ -1533,7 +1531,7 @@ void loadConfig()
         strncpy(cfg.MQTTPass, MQTT_PASS, sizeof(cfg.MQTTPass));
         strncpy(cfg.MQTTTopic, MQTT_TOPIC, sizeof(cfg.MQTTTopic));
         strncpy(cfg.MQTTDeviceName, MQTT_DEVICE_NAME, sizeof(cfg.MQTTDeviceName));
-        save_config = true;
+        setConfigChanged();
     }
 #endif
 }
@@ -1563,7 +1561,7 @@ void setPower(uint8_t value)
     power = value == 0 ? 0 : 1;
 
     cfg.power = power;
-    save_config = true;
+    setConfigChanged();
     SERIAL_DEBUG_LNF("Setting: power %s", (power == 0) ? "off" : "on")
     broadcastInt("power", power);
 }
@@ -1573,7 +1571,7 @@ void setAutoplay(uint8_t value)
     autoplay = value == 0 ? 0 : 1;
 
     cfg.autoplay = autoplay;
-    save_config = true;
+    setConfigChanged();
     SERIAL_DEBUG_LNF("Setting: autoplay %s", (autoplay == 0) ? "off" : "on")
     broadcastInt("autoplay", autoplay);
 }
@@ -1583,7 +1581,7 @@ void setAutoplayDuration(uint8_t value)
     autoplayDuration = value;
 
     cfg.autoplayDuration = autoplayDuration;
-    save_config = true;
+    setConfigChanged();
 
     autoPlayTimeout = millis() + (autoplayDuration * 1000);
     SERIAL_DEBUG_LNF("Setting: autoplay duration: %d seconds", autoplayDuration)
@@ -1626,7 +1624,7 @@ void adjustPattern(bool up)
 
     if (autoplay == 0) {
         cfg.currentPatternIndex = currentPatternIndex;
-        save_config = true;
+        setConfigChanged();
     }
 
 #ifdef AUTOPLAY_IGNORE_UDP_PATTERNS
@@ -1651,7 +1649,7 @@ void setPattern(uint8_t value)
 
     if (autoplay != 1) {
         cfg.currentPatternIndex = currentPatternIndex;
-        save_config = true;
+        setConfigChanged();
     }
 
     SERIAL_DEBUG_LNF("Setting: pattern: %s", patterns[currentPatternIndex].name.c_str())
@@ -1677,7 +1675,7 @@ void setPalette(uint8_t value)
     currentPaletteIndex = value;
 
     cfg.currentPaletteIndex = currentPaletteIndex;
-    save_config = true;
+    setConfigChanged();
 
     SERIAL_DEBUG_LNF("Setting: pallette: %s", paletteNames[currentPaletteIndex].c_str())
     broadcastInt("palette", currentPaletteIndex);
@@ -1714,7 +1712,7 @@ void setBrightness(uint8_t value)
     FastLED.setBrightness(brightness);
 
     cfg.brightness = brightness;
-    save_config = true;
+    setConfigChanged();
     SERIAL_DEBUG_LNF("Setting: brightness: %d", brightness)
     broadcastInt("brightness", brightness);
 }
@@ -1728,7 +1726,7 @@ void setSpeed(uint8_t value)
     speed = value;
 
     cfg.speed = speed;
-    save_config = true;
+    setConfigChanged();
     SERIAL_DEBUG_LNF("Setting: speed: %d", speed)
     broadcastInt("speed", speed);
 }