From 0972988345c2a9795f462f64ff1c62461422e76e Mon Sep 17 00:00:00 2001
From: Martin <MartinMueller2003@yahoo.com>
Date: Tue, 31 Dec 2024 13:07:25 -0500
Subject: [PATCH] Changed how timing is generated in the input sub system.
 Removed a lot of fiddely flags that made the code hard to follow.

---
 include/input/InputAlexa.h                    |  2 +-
 include/input/InputArtnet.hpp                 |  4 +-
 include/input/InputCommon.hpp                 |  6 +-
 include/input/InputDDP.h                      |  2 +-
 include/input/InputDisabled.hpp               |  2 +-
 include/input/InputE131.hpp                   |  2 +-
 include/input/InputEffectEngine.hpp           |  2 +-
 include/input/InputFPPRemote.h                |  6 +-
 include/input/InputFPPRemotePlayEffect.hpp    |  2 +-
 include/input/InputFPPRemotePlayEffectFsm.hpp |  6 +-
 include/input/InputFPPRemotePlayFile.hpp      |  4 +-
 include/input/InputFPPRemotePlayFileFsm.hpp   | 12 +--
 include/input/InputFPPRemotePlayItem.hpp      |  2 +-
 include/input/InputFPPRemotePlayList.hpp      |  2 +-
 include/input/InputFPPRemotePlayListFsm.hpp   | 12 +--
 include/input/InputMQTT.h                     |  2 +-
 include/input/InputMgr.hpp                    |  4 +-
 include/input/externalInput.h                 |  2 +-
 include/output/OutputMgr.hpp                  |  4 +-
 include/service/FPPDiscovery.h                |  1 +
 src/input/InputAlexa.cpp                      |  4 +-
 src/input/InputArtnet.cpp                     |  7 +-
 src/input/InputDDP.cpp                        |  4 +-
 src/input/InputDisabled.cpp                   |  2 +-
 src/input/InputE131.cpp                       |  4 +-
 src/input/InputEffectEngine.cpp               | 63 +-----------
 src/input/InputFPPRemote.cpp                  | 95 ++-----------------
 src/input/InputFPPRemotePlayEffect.cpp        |  5 +-
 src/input/InputFPPRemotePlayEffectFsm.cpp     |  6 +-
 src/input/InputFPPRemotePlayFile.cpp          |  6 +-
 src/input/InputFPPRemotePlayFileFsm.cpp       | 21 ++--
 src/input/InputFPPRemotePlayList.cpp          |  4 +-
 src/input/InputFPPRemotePlayListFsm.cpp       | 14 +--
 src/input/InputMQTT.cpp                       |  6 +-
 src/input/InputMgr.cpp                        | 68 ++++++++++++-
 src/input/externalInput.cpp                   |  2 +-
 src/main.cpp                                  |  4 +-
 src/output/OutputMgr.cpp                      | 14 ++-
 src/service/FPPDiscovery.cpp                  |  9 +-
 39 files changed, 174 insertions(+), 243 deletions(-)

diff --git a/include/input/InputAlexa.h b/include/input/InputAlexa.h
index fa24cae88..7e2294020 100644
--- a/include/input/InputAlexa.h
+++ b/include/input/InputAlexa.h
@@ -37,7 +37,7 @@ class c_InputAlexa : public c_InputCommon
       bool SetConfig (JsonObject& jsonConfig); ///< Set a new config in the driver
       void GetConfig (JsonObject& jsonConfig); ///< Get the current config used by the driver
       void GetStatus (JsonObject& jsonStatus);
-      void Process   (bool StayDark);
+      void Process   ();
       void GetDriverName (String& sDriverName) { sDriverName = "Alexa"; } ///< get the name for the instantiated driver
       void SetBufferInfo (uint32_t BufferSize);
 
diff --git a/include/input/InputArtnet.hpp b/include/input/InputArtnet.hpp
index c58545188..5240c943e 100644
--- a/include/input/InputArtnet.hpp
+++ b/include/input/InputArtnet.hpp
@@ -3,7 +3,7 @@
 * ArtnetInput.h - Code to wrap ESPAsyncArtnet for input
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and Artnet based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -79,6 +79,6 @@ class c_InputArtnet : public c_InputCommon
     void SetBufferInfo (uint32_t BufferSize);
     void NetworkStateChanged (bool IsConnected); // used by poorly designed rx functions
     bool isShutDownRebootNeeded () { return HasBeenInitialized; }
-    virtual void Process (bool StayDark) {}                                       ///< Call from loop(),  renders Input data
+    virtual void Process () {}                                       ///< Call from loop(),  renders Input data
 
 };
diff --git a/include/input/InputCommon.hpp b/include/input/InputCommon.hpp
index 0d980ec06..db129741a 100644
--- a/include/input/InputCommon.hpp
+++ b/include/input/InputCommon.hpp
@@ -3,7 +3,7 @@
 * InputCommon.hpp - Input base class
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and E1.31 based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -36,7 +36,7 @@ class c_InputCommon
     virtual bool SetConfig (ArduinoJson::JsonObject & jsonConfig) = 0; ///< Set a new config in the driver
     virtual void GetConfig (ArduinoJson::JsonObject & jsonConfig) = 0; ///< Get the current config used by the driver
     virtual void GetStatus (JsonObject & jsonStatus) = 0;
-    virtual void Process (bool StayDark) = 0;                                       ///< Call from loop(),  renders Input data
+    virtual void Process (void) = 0;                                       ///< Call from loop(),  renders Input data
     virtual void GetDriverName (String & sDriverName) = 0;             ///< get the name for the instantiated driver
     virtual void SetBufferInfo (uint32_t BufferSize) = 0;
     virtual void SetOperationalState (bool ActiveFlag) { IsInputChannelActive = ActiveFlag; }
@@ -49,7 +49,7 @@ class c_InputCommon
 
 protected:
     bool        HasBeenInitialized  = false;
-    uint32_t      InputDataBufferSize = 0;
+    uint32_t    InputDataBufferSize = 0;
     bool        IsInputChannelActive = true;
     c_InputMgr::e_InputChannelIds InputChannelId = c_InputMgr::e_InputChannelIds::InputChannelId_ALL;
     c_InputMgr::e_InputType       ChannelType = c_InputMgr::e_InputType::InputType_Disabled;
diff --git a/include/input/InputDDP.h b/include/input/InputDDP.h
index 480a5f4d0..0782331c5 100644
--- a/include/input/InputDDP.h
+++ b/include/input/InputDDP.h
@@ -137,7 +137,7 @@ class c_InputDDP : public c_InputCommon
     bool SetConfig (JsonObject& jsonConfig);   ///< Set a new config in the driver
     void GetConfig (JsonObject& jsonConfig);   ///< Get the current config used by the driver
     void GetStatus (JsonObject& jsonStatus);
-    void Process (bool StayDark);                                        ///< Call from loop(),  renders Input data
+    void Process ();                                        ///< Call from loop(),  renders Input data
     void GetDriverName (String& sDriverName) { sDriverName = "DDP"; } ///< get the name for the instantiated driver
     void SetBufferInfo (uint32_t BufferSize);
     bool isShutDownRebootNeeded () { return HasBeenInitialized; }
diff --git a/include/input/InputDisabled.hpp b/include/input/InputDisabled.hpp
index 85ee765d1..855898a19 100644
--- a/include/input/InputDisabled.hpp
+++ b/include/input/InputDisabled.hpp
@@ -38,7 +38,7 @@ class c_InputDisabled : public c_InputCommon
     bool SetConfig (JsonObject & jsonConfig);   ///< Set a new config in the driver
     void GetConfig (JsonObject & jsonConfig);   ///< Get the current config used by the driver
     void GetStatus (JsonObject & jsonStatus);
-    void Process   (bool StayDark);
+    void Process   ();
     void GetDriverName (String& sDriverName) { sDriverName = "Disabled"; } ///< get the name for the instantiated driver
     void SetBufferInfo (uint32_t BufferSize) {}
 
diff --git a/include/input/InputE131.hpp b/include/input/InputE131.hpp
index a9312ffea..9d48bc6f1 100644
--- a/include/input/InputE131.hpp
+++ b/include/input/InputE131.hpp
@@ -69,7 +69,7 @@ class c_InputE131 : public c_InputCommon
     bool SetConfig (JsonObject & jsonConfig);   ///< Set a new config in the driver
     void GetConfig (JsonObject & jsonConfig);   ///< Get the current config used by the driver
     void GetStatus (JsonObject & jsonStatus);
-    void Process   (bool StayDark);
+    void Process   ();
     void GetDriverName (String & sDriverName) { sDriverName = "E1.31"; } ///< get the name for the instantiated driver
     void SetBufferInfo (uint32_t BufferSize);
     void NetworkStateChanged (bool IsConnected); // used by poorly designed rx functions
diff --git a/include/input/InputEffectEngine.hpp b/include/input/InputEffectEngine.hpp
index e5742b37c..5b46cd626 100644
--- a/include/input/InputEffectEngine.hpp
+++ b/include/input/InputEffectEngine.hpp
@@ -102,7 +102,7 @@ class c_InputEffectEngine : public c_InputCommon
     void GetMqttConfig (MQTTConfiguration_s& mqttConfig);   ///< Get the current config used by the driver
     void GetMqttEffectList (JsonObject& jsonConfig);   ///< Get the current config used by the driver
     void GetStatus (JsonObject& jsonStatus);
-    void Process   (bool StayDark);
+    void Process   ();
     void Poll ();                              ///< Call from loop(),  renders Input data
     void GetDriverName (String  & sDriverName) { sDriverName = "Effects"; } ///< get the name for the instantiated driver
     void SetBufferInfo (uint32_t BufferSize);
diff --git a/include/input/InputFPPRemote.h b/include/input/InputFPPRemote.h
index 094e86dda..5a7df9f0f 100644
--- a/include/input/InputFPPRemote.h
+++ b/include/input/InputFPPRemote.h
@@ -38,8 +38,7 @@ class c_InputFPPRemote : public c_InputCommon
       bool SetConfig (JsonObject& jsonConfig); ///< Set a new config in the driver
       void GetConfig (JsonObject& jsonConfig); ///< Get the current config used by the driver
       void GetStatus (JsonObject& jsonStatus);
-      void Process   (bool StayDark);
-      void TaskProcess ();                     ///< Call from loop(),  renders Input data
+      void Process   ();
       void GetDriverName (String& sDriverName) { sDriverName = "FPP Remote"; } ///< get the name for the instantiated driver
       void SetBufferInfo (uint32_t BufferSize);
       void ProcessButtonActions(c_ExternalInput::InputValue_t value);
@@ -53,9 +52,6 @@ class c_InputFPPRemote : public c_InputCommon
     bool    GetSendFppSync () { return SendFppSync; }
 
     String StatusType;
-    bool StayDark = false;
-    bool Disabled = false;
-    bool DisableTask = false;
 
 private:
 
diff --git a/include/input/InputFPPRemotePlayEffect.hpp b/include/input/InputFPPRemotePlayEffect.hpp
index d669ae93e..8d404d7a5 100644
--- a/include/input/InputFPPRemotePlayEffect.hpp
+++ b/include/input/InputFPPRemotePlayEffect.hpp
@@ -33,7 +33,7 @@ class c_InputFPPRemotePlayEffect : public c_InputFPPRemotePlayItem
     virtual void Start     (String & FileName, float duration, uint32_t PlayCount);
     virtual void Stop      ();
     virtual void Sync      (String & FileName, float SecondsElapsed);
-    virtual bool Poll      (bool StayDark);
+    virtual bool Poll      ();
     virtual void GetStatus (JsonObject & jsonStatus);
     virtual bool IsIdle    () { return (pCurrentFsmState == &fsm_PlayEffect_state_Idle_imp); }
 
diff --git a/include/input/InputFPPRemotePlayEffectFsm.hpp b/include/input/InputFPPRemotePlayEffectFsm.hpp
index 2ae6ca18d..eefce94f9 100644
--- a/include/input/InputFPPRemotePlayEffectFsm.hpp
+++ b/include/input/InputFPPRemotePlayEffectFsm.hpp
@@ -35,7 +35,7 @@ class fsm_PlayEffect_state
     fsm_PlayEffect_state() {}
     virtual ~fsm_PlayEffect_state() {}
 
-    virtual bool Poll (bool StayDark) = 0;
+    virtual bool Poll () = 0;
     virtual void Init (c_InputFPPRemotePlayEffect * Parent) = 0;
     virtual void GetStateName (String & sName) = 0;
     virtual void Start (String & FileName, float SecondsElapsed) = 0;
@@ -56,7 +56,7 @@ class fsm_PlayEffect_state_Idle : public fsm_PlayEffect_state
     fsm_PlayEffect_state_Idle() {}
     virtual ~fsm_PlayEffect_state_Idle() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayEffect* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Idle; }
     virtual void Start (String & FileName, float SecondsElapsed);
@@ -73,7 +73,7 @@ class fsm_PlayEffect_state_PlayingEffect : public fsm_PlayEffect_state
     fsm_PlayEffect_state_PlayingEffect() {}
     virtual ~fsm_PlayEffect_state_PlayingEffect() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayEffect* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Effect; }
     virtual void Start (String & FileName, float SecondsElapsed);
diff --git a/include/input/InputFPPRemotePlayFile.hpp b/include/input/InputFPPRemotePlayFile.hpp
index 19006ef8c..c637d5e61 100644
--- a/include/input/InputFPPRemotePlayFile.hpp
+++ b/include/input/InputFPPRemotePlayFile.hpp
@@ -39,7 +39,7 @@ class c_InputFPPRemotePlayFile : public c_InputFPPRemotePlayItem
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
     virtual void Stop ();
     virtual void Sync (String& FileName, float SecondsElapsed);
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void GetStatus (JsonObject & jsonStatus);
     virtual bool IsIdle () { return (pCurrentFsmState == &fsm_PlayFile_state_Idle_imp); }
 
@@ -105,7 +105,7 @@ class c_InputFPPRemotePlayFile : public c_InputFPPRemotePlayItem
     void        UpdateElapsedPlayTimeMS ();
     uint32_t    CalculateFrameId (uint32_t ElapsedMS, int32_t SyncOffsetMS);
     bool        ParseFseqFile ();
-    uint32_t      ReadFile(uint32_t DestinationIntensityId, uint32_t NumBytesToRead, uint32_t FileOffset);
+    uint32_t    ReadFile(uint32_t DestinationIntensityId, uint32_t NumBytesToRead, uint32_t FileOffset);
 
     String      LastFailedPlayStatusMsg;
 
diff --git a/include/input/InputFPPRemotePlayFileFsm.hpp b/include/input/InputFPPRemotePlayFileFsm.hpp
index e601a3e20..28bc0a13b 100644
--- a/include/input/InputFPPRemotePlayFileFsm.hpp
+++ b/include/input/InputFPPRemotePlayFileFsm.hpp
@@ -36,7 +36,7 @@ class fsm_PlayFile_state
     fsm_PlayFile_state() {}
     virtual ~fsm_PlayFile_state() {}
 
-    virtual bool Poll (bool StayDark) = 0;
+    virtual bool Poll () = 0;
     virtual void Init (c_InputFPPRemotePlayFile * Parent) = 0;
     virtual void GetStateName (String & sName) = 0;
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t RemainingPlayCount) = 0;
@@ -57,7 +57,7 @@ class fsm_PlayFile_state_Idle : public fsm_PlayFile_state
     fsm_PlayFile_state_Idle() {}
     virtual ~fsm_PlayFile_state_Idle() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayFile* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Idle; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
@@ -74,7 +74,7 @@ class fsm_PlayFile_state_Starting : public fsm_PlayFile_state
     fsm_PlayFile_state_Starting() {}
     virtual ~fsm_PlayFile_state_Starting() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayFile* Parent);
     virtual void GetStateName (String& sName) { sName = F ("Starting"); }
     virtual void Start (String& FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
@@ -91,7 +91,7 @@ class fsm_PlayFile_state_PlayingFile : public fsm_PlayFile_state
     fsm_PlayFile_state_PlayingFile() {}
     virtual ~fsm_PlayFile_state_PlayingFile() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayFile* Parent);
     virtual void GetStateName (String & sName) { sName = CN_File; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
@@ -116,7 +116,7 @@ class fsm_PlayFile_state_Stopping : public fsm_PlayFile_state
     fsm_PlayFile_state_Stopping() {}
     virtual ~fsm_PlayFile_state_Stopping() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayFile* Parent);
     virtual void GetStateName (String& sName) { sName = F("Stopping"); }
     virtual void Start (String& FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
@@ -138,7 +138,7 @@ class fsm_PlayFile_state_Error : public fsm_PlayFile_state
     fsm_PlayFile_state_Error() {}
     virtual ~fsm_PlayFile_state_Error() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayFile* Parent);
     virtual void GetStateName (String& sName) { sName = F ("Error"); }
     virtual void Start (String& FileName, float SecondsElapsed, uint32_t RemainingPlayCount);
diff --git a/include/input/InputFPPRemotePlayItem.hpp b/include/input/InputFPPRemotePlayItem.hpp
index 05a3b1e12..6ce4c4c63 100644
--- a/include/input/InputFPPRemotePlayItem.hpp
+++ b/include/input/InputFPPRemotePlayItem.hpp
@@ -28,7 +28,7 @@ class c_InputFPPRemotePlayItem
     c_InputFPPRemotePlayItem (c_InputMgr::e_InputChannelIds InputChannelId);
     virtual ~c_InputFPPRemotePlayItem ();
 
-    virtual bool     Poll           (bool StayDark) = 0;
+    virtual bool     Poll           () = 0;
     virtual void     Start          (String & FileName, float SecondsElapsed, uint32_t RemainingPlayCount) = 0;
     virtual void     Stop           () = 0;
     virtual void     Sync           (String & FileName, float SecondsElapsed) = 0;
diff --git a/include/input/InputFPPRemotePlayList.hpp b/include/input/InputFPPRemotePlayList.hpp
index bda8a63e9..d0f08ab04 100644
--- a/include/input/InputFPPRemotePlayList.hpp
+++ b/include/input/InputFPPRemotePlayList.hpp
@@ -34,7 +34,7 @@ class c_InputFPPRemotePlayList : public c_InputFPPRemotePlayItem
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
     virtual void Stop  ();
     virtual void Sync  (String & FileName, float SecondsElapsed);
-    virtual bool Poll  (bool StayDark);
+    virtual bool Poll  ();
     virtual void GetStatus (JsonObject & jsonStatus);
     virtual bool IsIdle () { return (pCurrentFsmState == &fsm_PlayList_state_Idle_imp); }
 
diff --git a/include/input/InputFPPRemotePlayListFsm.hpp b/include/input/InputFPPRemotePlayListFsm.hpp
index 89d455bce..1c3a05d5a 100644
--- a/include/input/InputFPPRemotePlayListFsm.hpp
+++ b/include/input/InputFPPRemotePlayListFsm.hpp
@@ -35,7 +35,7 @@ class fsm_PlayList_state
     fsm_PlayList_state() {}
     virtual ~fsm_PlayList_state() {}
 
-    virtual bool Poll (bool StayDark) = 0;
+    virtual bool Poll () = 0;
     virtual void Init (c_InputFPPRemotePlayList * Parent) = 0;
     virtual void GetStateName (String & sName) = 0;
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount) = 0;
@@ -56,7 +56,7 @@ class fsm_PlayList_state_WaitForStart : public fsm_PlayList_state
     fsm_PlayList_state_WaitForStart() {}
     virtual ~fsm_PlayList_state_WaitForStart() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayList* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Idle; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
@@ -72,7 +72,7 @@ class fsm_PlayList_state_Idle : public fsm_PlayList_state
     fsm_PlayList_state_Idle() {}
     virtual ~fsm_PlayList_state_Idle() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayList* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Idle; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
@@ -88,7 +88,7 @@ class fsm_PlayList_state_PlayingFile : public fsm_PlayList_state
     fsm_PlayList_state_PlayingFile() {}
     virtual ~fsm_PlayList_state_PlayingFile() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayList* Parent);
     virtual void GetStateName (String & sName) { sName = CN_File; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
@@ -104,7 +104,7 @@ class fsm_PlayList_state_PlayingEffect : public fsm_PlayList_state
     fsm_PlayList_state_PlayingEffect() {}
     virtual ~fsm_PlayList_state_PlayingEffect() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayList* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Effect; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
@@ -120,7 +120,7 @@ class fsm_PlayList_state_Paused : public fsm_PlayList_state
     fsm_PlayList_state_Paused() {}
     virtual ~fsm_PlayList_state_Paused() {}
 
-    virtual bool Poll (bool StayDark);
+    virtual bool Poll ();
     virtual void Init (c_InputFPPRemotePlayList* Parent);
     virtual void GetStateName (String & sName) { sName = CN_Paused; }
     virtual void Start (String & FileName, float SecondsElapsed, uint32_t PlayCount);
diff --git a/include/input/InputMQTT.h b/include/input/InputMQTT.h
index 46c77f665..775944f96 100644
--- a/include/input/InputMQTT.h
+++ b/include/input/InputMQTT.h
@@ -41,7 +41,7 @@ class c_InputMQTT : public c_InputCommon
       bool SetConfig (JsonObject& jsonConfig); ///< Set a new config in the driver
       void GetConfig (JsonObject& jsonConfig); ///< Get the current config used by the driver
       void GetStatus (JsonObject& jsonStatus);
-      void Process   (bool StayDark);
+      void Process   ();
       void GetDriverName (String& sDriverName) { sDriverName = "MQTT"; } ///< get the name for the instantiated driver
       void SetBufferInfo (uint32_t BufferSize);
       void NetworkStateChanged (bool IsConnected); // used by poorly designed rx functions
diff --git a/include/input/InputMgr.hpp b/include/input/InputMgr.hpp
index 908d2d76b..820776937 100644
--- a/include/input/InputMgr.hpp
+++ b/include/input/InputMgr.hpp
@@ -3,7 +3,7 @@
 * InputMgr.hpp - Input Management class
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and E1.31 based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -94,6 +94,7 @@ class c_InputMgr
     };
 
     #define NO_CONFIG_NEEDED time_t(-1)
+    #define INPUTMGR_TASK_PRIORITY 6
 
     DriverInfo_t    InputChannelDrivers[InputChannelId_End]; ///< pointer(s) to the current active Input driver
     uint32_t        InputDataBufferSize = 0;
@@ -103,6 +104,7 @@ class c_InputMgr
     bool            IsConnected         = false;
     bool            configInProgress    = false;
     time_t          ConfigLoadNeeded    = NO_CONFIG_NEEDED;
+    bool            PauseProcessing     = false;
 
     // configuration parameter names for the channel manager within the config file
 #   define IM_EffectsControlButtonName F ("ecb")
diff --git a/include/input/externalInput.h b/include/input/externalInput.h
index cb848b772..409674db8 100644
--- a/include/input/externalInput.h
+++ b/include/input/externalInput.h
@@ -42,7 +42,7 @@ class c_ExternalInput final
 	};
 
 	void         Init              (uint32_t iInputId, uint32_t iPinId, Polarity_t Poliarity, String & sName);
-	void         Poll              (bool StayDark);
+	void         Poll              (void);
 	void         GetConfig         (JsonObject JsonData);
 	void         GetStatistics     (JsonObject JsonData);
 	void         ProcessConfig     (JsonObject JsonData);
diff --git a/include/output/OutputMgr.hpp b/include/output/OutputMgr.hpp
index c8e449447..59cd30dff 100644
--- a/include/output/OutputMgr.hpp
+++ b/include/output/OutputMgr.hpp
@@ -3,7 +3,7 @@
 * OutputMgr.hpp - Output Management class
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and E1.31 based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -238,7 +238,7 @@ class c_OutputMgr
     bool HasBeenInitialized = false;
     time_t ConfigLoadNeeded = NO_CONFIG_NEEDED;
     bool ConfigInProgress   = false;
-    bool IsOutputPaused     = false;
+    bool OutputIsPaused     = false;
     bool BuildingNewConfig  = false;
 
     bool ProcessJsonConfig (JsonDocument & jsonConfig);
diff --git a/include/service/FPPDiscovery.h b/include/service/FPPDiscovery.h
index 695de363a..07307e664 100644
--- a/include/service/FPPDiscovery.h
+++ b/include/service/FPPDiscovery.h
@@ -46,6 +46,7 @@ class c_FPPDiscovery
     bool PlayingFile ();
 
     bool inFileUpload = false;
+    bool writeFailed = false;
     bool hasBeenInitialized = false;
     bool IsEnabled = false;
     bool BlankOnStop = false;
diff --git a/src/input/InputAlexa.cpp b/src/input/InputAlexa.cpp
index c86623d17..237a3b8b0 100644
--- a/src/input/InputAlexa.cpp
+++ b/src/input/InputAlexa.cpp
@@ -100,12 +100,12 @@ void c_InputAlexa::GetStatus (JsonObject& /* jsonStatus */)
 } // GetStatus
 
 //-----------------------------------------------------------------------------
-void c_InputAlexa::Process (bool StayDark)
+void c_InputAlexa::Process ()
 {
     // DEBUG_START;
     if (IsInputChannelActive)
     {
-        pEffectsEngine->Process (StayDark);
+        pEffectsEngine->Process ();
     }
 
     // DEBUG_END;
diff --git a/src/input/InputArtnet.cpp b/src/input/InputArtnet.cpp
index f72e3cbb3..a1f5e73b7 100644
--- a/src/input/InputArtnet.cpp
+++ b/src/input/InputArtnet.cpp
@@ -2,7 +2,7 @@
 * ArtnetInput.cpp - Code to wrap ESPAsyncArtnet for input
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and Artnet based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -120,8 +120,9 @@ void c_InputArtnet::onDmxFrame (uint16_t  CurrentUniverseId,
                                 IPAddress remoteIP)
 {
     // DEBUG_START;
-
-    if ((startUniverse <= CurrentUniverseId) && (LastUniverse >= CurrentUniverseId))
+    if(!IsInputChannelActive)
+    {}
+    else if ((startUniverse <= CurrentUniverseId) && (LastUniverse >= CurrentUniverseId))
     {
         // Universe offset and sequence tracking
         Universe_t & CurrentUniverse = UniverseArray[CurrentUniverseId - startUniverse];
diff --git a/src/input/InputDDP.cpp b/src/input/InputDDP.cpp
index a0790a690..75e989b45 100644
--- a/src/input/InputDDP.cpp
+++ b/src/input/InputDDP.cpp
@@ -192,13 +192,13 @@ void c_InputDDP::ProcessReceivedUdpPacket(AsyncUDPPacket ReceivedPacket)
 } // ProcessReceivedUdpPacket
 
 //-----------------------------------------------------------------------------
-void c_InputDDP::Process (bool StayDark)
+void c_InputDDP::Process ()
 {
     // DEBUG_START;
 
     do // once
     {
-        if(!IsInputChannelActive || StayDark)
+        if(!IsInputChannelActive)
         {
             break;
         }
diff --git a/src/input/InputDisabled.cpp b/src/input/InputDisabled.cpp
index 80d7c0c13..7618bd34e 100644
--- a/src/input/InputDisabled.cpp
+++ b/src/input/InputDisabled.cpp
@@ -92,7 +92,7 @@ void c_InputDisabled::GetConfig(ArduinoJson::JsonObject & jsonConfig)
 } // GetConfig
 
 //----------------------------------------------------------------------------
-void c_InputDisabled::Process(bool /* StayDark */)
+void c_InputDisabled::Process()
 {
     // DEBUG_START;
 
diff --git a/src/input/InputE131.cpp b/src/input/InputE131.cpp
index d4d22abfb..73586da4e 100644
--- a/src/input/InputE131.cpp
+++ b/src/input/InputE131.cpp
@@ -119,7 +119,7 @@ void c_InputE131::GetStatus (JsonObject & jsonStatus)
 } // GetStatus
 
 //-----------------------------------------------------------------------------
-void c_InputE131::Process (bool /* StayDark */)
+void c_InputE131::Process ()
 {
     // DEBUG_START;
 
@@ -137,7 +137,7 @@ void c_InputE131::ProcessIncomingE131Data (e131_packet_t * packet)
 
     do // once
     {
-        if (0 == InputDataBufferSize)
+        if ((0 == InputDataBufferSize) || !IsInputChannelActive)
         {
             // no place to put any data
             break;
diff --git a/src/input/InputEffectEngine.cpp b/src/input/InputEffectEngine.cpp
index 7d12b7873..1d2e7eb62 100644
--- a/src/input/InputEffectEngine.cpp
+++ b/src/input/InputEffectEngine.cpp
@@ -2,7 +2,7 @@
 * InputEffectEngine.cpp - Code to wrap ESPAsyncE131 for input
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and E1.31 based pixel driver
-* Copyright (c) 2021, 2022 Shelby Merrick
+* Copyright (c) 2021, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -76,42 +76,6 @@ static std::vector<c_InputEffectEngine::MarqueeGroup> MarqueueGroupTable =
     {5, {255, 255, 255}, 100, 0},
 }; // MarqueueGroupTable
 
-#ifdef ARDUINO_ARCH_ESP32
-static TaskHandle_t PollTaskHandle = NULL;
-static c_InputEffectEngine *pEffectsInstance = nullptr;
-//----------------------------------------------------------------------------
-void EffectsTask (void *arg)
-{
-    uint32_t PollStartTime = millis();
-    uint32_t PollEndTime = PollStartTime;
-    uint32_t PollTime = pdMS_TO_TICKS(25);
-    const uint32_t MinPollTimeMs = 25;
-
-    while(1)
-    {
-        uint32_t DeltaTime = PollEndTime - PollStartTime;
-
-        if (DeltaTime < MinPollTimeMs)
-        {
-            PollTime = pdMS_TO_TICKS(MinPollTimeMs - DeltaTime);
-        }
-        else
-        {
-            // handle time wrap and long frames
-            PollTime = pdMS_TO_TICKS(1);
-        }
-        vTaskDelay(PollTime);
-
-        PollStartTime = millis();
-
-        pEffectsInstance->Poll();
-
-        // record the loop end time
-        PollEndTime = millis();
-    }
-} // EffectsTask
-#endif // def ARDUINO_ARCH_ESP32
-
 //-----------------------------------------------------------------------------
 c_InputEffectEngine::c_InputEffectEngine (c_InputMgr::e_InputChannelIds NewInputChannelId,
                                           c_InputMgr::e_InputType       NewChannelType,
@@ -149,14 +113,6 @@ c_InputEffectEngine::c_InputEffectEngine () :
 //-----------------------------------------------------------------------------
 c_InputEffectEngine::~c_InputEffectEngine ()
 {
-#ifdef ARDUINO_ARCH_ESP32
-    if(PollTaskHandle)
-    {
-        logcon("Stop EffectsTask");
-        vTaskDelete(PollTaskHandle);
-        PollTaskHandle = NULL;
-    }
-#endif // def ARDUINO_ARCH_ESP32
 
 } // ~c_InputEffectEngine
 
@@ -373,13 +329,12 @@ void c_InputEffectEngine::PollFlash ()
 } // PollFlash
 
 //-----------------------------------------------------------------------------
-void c_InputEffectEngine::Process (bool _StayDark)
+void c_InputEffectEngine::Process ()
 {
     // DEBUG_START;
-    Disabled = _StayDark;
     // DEBUG_V (String ("HasBeenInitialized: ") + HasBeenInitialized);
     // DEBUG_V (String ("PixelCount: ") + PixelCount);
-#ifndef ARDUINO_ARCH_ESP32
+
     do // once
     {
         if (!HasBeenInitialized)
@@ -388,7 +343,7 @@ void c_InputEffectEngine::Process (bool _StayDark)
         }
         // DEBUG_V ("Init OK");
 
-        if ((0 == PixelCount) || (StayDark))
+        if (0 == PixelCount)
         {
             break;
         }
@@ -417,16 +372,6 @@ void c_InputEffectEngine::Process (bool _StayDark)
     } while (false);
 
     // DEBUG_END;
-#else
-    if(!PollTaskHandle)
-    {
-        logcon("Start EffectsTask");
-        pEffectsInstance = this;
-        xTaskCreatePinnedToCore(EffectsTask, "EffectsTask", 4096, NULL, EFFECTS_TASK_PRIORITY, &PollTaskHandle, 1);
-        vTaskPrioritySet(PollTaskHandle, EFFECTS_TASK_PRIORITY);
-        // DEBUG_V("End EffectsTask");
-    }
-#endif // ndef ARDUINO_ARCH_ESP32
 
 } // process
 
diff --git a/src/input/InputFPPRemote.cpp b/src/input/InputFPPRemote.cpp
index 0bb604f07..c2ddccd8e 100644
--- a/src/input/InputFPPRemote.cpp
+++ b/src/input/InputFPPRemote.cpp
@@ -24,47 +24,6 @@
 #include "input/InputFPPRemotePlayList.hpp"
 #include <Int64String.h>
 
-#if defined ARDUINO_ARCH_ESP32
-#   include <functional>
-
-static TaskHandle_t PollTaskHandle = NULL;
-static c_InputFPPRemote *pFppRemoteInstance = nullptr;
-//----------------------------------------------------------------------------
-void FppRemoteTask (void *arg)
-{
-    // DEBUG_V(String("Current CPU ID: ") + String(xPortGetCoreID()));
-    // DEBUG_V(String("Current Task Priority: ") + String(uxTaskPriorityGet(NULL)));
-    uint32_t PollStartTime = millis();
-    uint32_t PollEndTime = PollStartTime;
-    uint32_t PollTime = pdMS_TO_TICKS(25);
-    const uint32_t MinPollTimeMs = 25;
-
-    while(1)
-    {
-        uint32_t DeltaTime = PollEndTime - PollStartTime;
-
-        if (DeltaTime < MinPollTimeMs)
-        {
-            PollTime = pdMS_TO_TICKS(MinPollTimeMs - DeltaTime);
-        }
-        else
-        {
-            // handle time wrap and long frames
-            PollTime = pdMS_TO_TICKS(1);
-        }
-        vTaskDelay(PollTime);
-        FeedWDT();
-
-        PollStartTime = millis();
-
-        pFppRemoteInstance->TaskProcess();
-        FeedWDT();
-
-        // record the loop end time
-        PollEndTime = millis();
-    }
-} // FppRemoteTask
-#endif // def ARDUINO_ARCH_ESP32
 
 //-----------------------------------------------------------------------------
 c_InputFPPRemote::c_InputFPPRemote (c_InputMgr::e_InputChannelIds NewInputChannelId,
@@ -88,15 +47,6 @@ c_InputFPPRemote::~c_InputFPPRemote ()
         StopPlaying ();
     }
 
-#ifdef ARDUINO_ARCH_ESP32
-    if(PollTaskHandle)
-    {
-        logcon("Stop FPP Remote Task");
-        vTaskDelete(PollTaskHandle);
-        PollTaskHandle = NULL;
-    }
-#endif // def ARDUINO_ARCH_ESP32
-
 } // ~c_InputFPPRemote
 
 //-----------------------------------------------------------------------------
@@ -237,30 +187,11 @@ void c_InputFPPRemote::PlayNextFile ()
 } // PlayNextFile
 
 //-----------------------------------------------------------------------------
-void c_InputFPPRemote::Process (bool StayDark)
+void c_InputFPPRemote::Process ()
 {
     // DEBUG_START;
-    Disabled = StayDark;
-#ifndef ARDUINO_ARCH_ESP32
-    TaskProcess();
-#else
-    if(!PollTaskHandle)
-    {
-        logcon("Start FPP Remote Task");
-        pFppRemoteInstance = this;
-        xTaskCreatePinnedToCore(FppRemoteTask, "FppRemoteTask", 4096, NULL, FPP_REMOTE_TASK_PRIORITY, &PollTaskHandle, 1);
-        // DEBUG_V("End FppRemoteTask");
-    }
-#endif // ndef ARDUINO_ARCH_ESP32
-    // DEBUG_END;
-
-} // process
 
-//-----------------------------------------------------------------------------
-void c_InputFPPRemote::TaskProcess ()
-{
-    // DEBUG_START;
-    if (!IsInputChannelActive || StayDark || Disabled || DisableTask)
+    if (!IsInputChannelActive)
     {
         // DEBUG_V ("dont do anything if the channel is not active");
     }
@@ -282,16 +213,16 @@ void c_InputFPPRemote::TaskProcess ()
     }
     // DEBUG_END;
 
-} // TaskProcess
+} // process
 
 //-----------------------------------------------------------------------------
 bool c_InputFPPRemote::Poll ()
 {
     // DEBUG_START;
     bool Response = false;
-    if(pInputFPPRemotePlayItem)
+    if(pInputFPPRemotePlayItem && IsInputChannelActive)
     {
-        Response = pInputFPPRemotePlayItem->Poll (Disabled);
+        Response = pInputFPPRemotePlayItem->Poll ();
     }
 
     // DEBUG_END;
@@ -306,9 +237,6 @@ void c_InputFPPRemote::ProcessButtonActions(c_ExternalInput::InputValue_t value)
 
     if(c_ExternalInput::InputValue_t::longOn == value)
     {
-        // DEBUG_V("flip the dark flag");
-        StayDark = !StayDark;
-        // DEBUG_V(String("StayDark: ") + String(StayDark));
     }
     else if(c_ExternalInput::InputValue_t::shortOn == value)
     {
@@ -363,11 +291,6 @@ bool c_InputFPPRemote::SetConfig (JsonObject& jsonConfig)
 void c_InputFPPRemote::StopPlaying ()
 {
     // DEBUG_START;
-    // DEBUG_V(String("Current Task Priority: ") + String(uxTaskPriorityGet(NULL)));
-
-    // save current disable state and disable FPP task.
-    bool SavedDisableTaskFlag = DisableTask;
-    DisableTask = true;
 
     do // once
     {
@@ -385,7 +308,6 @@ void c_InputFPPRemote::StopPlaying ()
         }
         Stopping = true;
 
-        // DEBUG_V(String("Current Task Priority: ") + String(uxTaskPriorityGet(NULL)));
         // DEBUG_V ("Disable FPP Discovery");
         FPPDiscovery.Disable ();
         FPPDiscovery.ForgetInputFPPRemotePlayFile ();
@@ -399,7 +321,7 @@ void c_InputFPPRemote::StopPlaying ()
             // DEBUG_V();
             while (!pInputFPPRemotePlayItem->IsIdle ())
             {
-                pInputFPPRemotePlayItem->Poll (Disabled);
+                pInputFPPRemotePlayItem->Poll ();
                 // DEBUG_V();
                 pInputFPPRemotePlayItem->Stop ();
             }
@@ -414,9 +336,6 @@ void c_InputFPPRemote::StopPlaying ()
 
     } while (false);
 
-    // restore previous state of the flag
-    DisableTask = SavedDisableTaskFlag;
-
     // DEBUG_END;
 
 } // StopPlaying
@@ -474,7 +393,7 @@ void c_InputFPPRemote::StartPlayingLocalFile (String& FileName)
                 pInputFPPRemotePlayItem = nullptr;
                 // DEBUG_V(String("pInputFPPRemotePlayItem: 0x") + String(uint32_t(pInputFPPRemotePlayItem), HEX));
             }
-            // DEBUG_V ("Start a new Playlist");
+            // DEBUG_V ("Start a new Local File");
             pInputFPPRemotePlayItem = new c_InputFPPRemotePlayList (GetInputChannelId ());
             // DEBUG_V(String("pInputFPPRemotePlayItem: 0x") + String(uint32_t(pInputFPPRemotePlayItem), HEX));
             StatusType = F ("PlayList");
diff --git a/src/input/InputFPPRemotePlayEffect.cpp b/src/input/InputFPPRemotePlayEffect.cpp
index 47e199bd1..f5a5b8465 100644
--- a/src/input/InputFPPRemotePlayEffect.cpp
+++ b/src/input/InputFPPRemotePlayEffect.cpp
@@ -44,7 +44,6 @@ c_InputFPPRemotePlayEffect::~c_InputFPPRemotePlayEffect ()
     // DEBUG_START;
 
     // allow the other input channels to run
-    InputMgr.SetOperationalState (true);
     EffectsEngine.SetOperationalState (false);
 
     // DEBUG_END;
@@ -82,11 +81,11 @@ void c_InputFPPRemotePlayEffect::Sync (String& FileName, float SecondsElapsed)
 } // Sync
 
 //-----------------------------------------------------------------------------
-bool c_InputFPPRemotePlayEffect::Poll (bool StayDark)
+bool c_InputFPPRemotePlayEffect::Poll ()
 {
     // DEBUG_START;
 
-    return pCurrentFsmState->Poll (StayDark);
+    return pCurrentFsmState->Poll ();
 
     // DEBUG_END;
 
diff --git a/src/input/InputFPPRemotePlayEffectFsm.cpp b/src/input/InputFPPRemotePlayEffectFsm.cpp
index a0ede7350..f4e6bc35a 100644
--- a/src/input/InputFPPRemotePlayEffectFsm.cpp
+++ b/src/input/InputFPPRemotePlayEffectFsm.cpp
@@ -23,7 +23,7 @@
 #include "utility/SaferStringConversion.hpp"
 
 //-----------------------------------------------------------------------------
-bool fsm_PlayEffect_state_Idle::Poll (bool /* StayDark */)
+bool fsm_PlayEffect_state_Idle::Poll ()
 {
     // DEBUG_START;
 
@@ -118,12 +118,12 @@ void fsm_PlayEffect_state_Idle::GetStatus (JsonObject& jsonStatus)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayEffect_state_PlayingEffect::Poll (bool StayDark)
+bool fsm_PlayEffect_state_PlayingEffect::Poll ()
 {
     // DEBUG_START;
 
     p_InputFPPRemotePlayEffect->EffectsEngine.SetBufferInfo (OutputMgr.GetBufferUsedSize());
-    p_InputFPPRemotePlayEffect->EffectsEngine.Process (StayDark);
+    p_InputFPPRemotePlayEffect->EffectsEngine.Process ();
 
     if (p_InputFPPRemotePlayEffect->PlayEffectTimer.IsExpired())
     {
diff --git a/src/input/InputFPPRemotePlayFile.cpp b/src/input/InputFPPRemotePlayFile.cpp
index 834563f0a..8cf0b6b89 100644
--- a/src/input/InputFPPRemotePlayFile.cpp
+++ b/src/input/InputFPPRemotePlayFile.cpp
@@ -98,7 +98,7 @@ c_InputFPPRemotePlayFile::~c_InputFPPRemotePlayFile ()
     for (uint32_t LoopCount = 10000; (LoopCount != 0) && (!IsIdle ()); LoopCount--)
     {
         Stop ();
-        Poll (false);
+        Poll ();
     }
     // DEBUG_END;
 
@@ -148,7 +148,7 @@ void c_InputFPPRemotePlayFile::Sync (String & FileName, float SecondsElapsed)
 } // Sync
 
 //-----------------------------------------------------------------------------
-bool c_InputFPPRemotePlayFile::Poll (bool StayDark)
+bool c_InputFPPRemotePlayFile::Poll ()
 {
     // xDEBUG_START;
 
@@ -156,7 +156,7 @@ bool c_InputFPPRemotePlayFile::Poll (bool StayDark)
     PollDetectionCounter = 0;
 
     // TimerPoll ();
-    return pCurrentFsmState->Poll (StayDark);
+    return pCurrentFsmState->Poll ();
 
     // xDEBUG_END;
 
diff --git a/src/input/InputFPPRemotePlayFileFsm.cpp b/src/input/InputFPPRemotePlayFileFsm.cpp
index 133634b14..3ace1b170 100644
--- a/src/input/InputFPPRemotePlayFileFsm.cpp
+++ b/src/input/InputFPPRemotePlayFileFsm.cpp
@@ -23,7 +23,7 @@
 #include "service/FPPDiscovery.h"
 
 //-----------------------------------------------------------------------------
-bool fsm_PlayFile_state_Idle::Poll (bool /* StayDark */)
+bool fsm_PlayFile_state_Idle::Poll ()
 {
     // DEBUG_START;
 
@@ -110,18 +110,11 @@ bool fsm_PlayFile_state_Idle::Sync (String& FileName, float ElapsedSeconds)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayFile_state_Starting::Poll (bool StayDark)
+bool fsm_PlayFile_state_Starting::Poll ()
 {
     // DEBUG_START;
 
-    if(StayDark)
-    {
-        p_Parent->fsm_PlayFile_state_Stopping_imp.Init (p_Parent);
-    }
-    else
-    {
-        p_Parent->fsm_PlayFile_state_PlayingFile_imp.Init (p_Parent);
-    }
+    p_Parent->fsm_PlayFile_state_PlayingFile_imp.Init (p_Parent);
     // DEBUG_V (String ("           RemainingPlayCount: ") + p_Parent->RemainingPlayCount);
     // DEBUG_V (String ("TotalNumberOfFramesInSequence: ") + String (p_Parent->FrameControl.TotalNumberOfFramesInSequence));
 
@@ -202,7 +195,7 @@ bool fsm_PlayFile_state_Starting::Sync (String& FileName, float ElapsedSeconds)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayFile_state_PlayingFile::Poll (bool StayDark)
+bool fsm_PlayFile_state_PlayingFile::Poll ()
 {
     // xDEBUG_START;
 
@@ -210,7 +203,7 @@ bool fsm_PlayFile_state_PlayingFile::Poll (bool StayDark)
 
     do // once
     {
-        if(!StayDark || (c_FileMgr::INVALID_FILE_HANDLE == p_Parent->FileHandleForFileBeingPlayed))
+        if(c_FileMgr::INVALID_FILE_HANDLE == p_Parent->FileHandleForFileBeingPlayed)
         {
             // DEBUG_V("Bad FileHandleForFileBeingPlayed");
             Stop();
@@ -504,7 +497,7 @@ bool fsm_PlayFile_state_PlayingFile::Sync (String& FileName, float ElapsedSecond
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayFile_state_Stopping::Poll (bool /* StayDark */)
+bool fsm_PlayFile_state_Stopping::Poll ()
 {
     // DEBUG_START;
 
@@ -594,7 +587,7 @@ bool fsm_PlayFile_state_Stopping::Sync (String&, float)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayFile_state_Error::Poll (bool /* StayDark */)
+bool fsm_PlayFile_state_Error::Poll ()
 {
     // xDEBUG_START;
 
diff --git a/src/input/InputFPPRemotePlayList.cpp b/src/input/InputFPPRemotePlayList.cpp
index 9289b6a32..a05845497 100644
--- a/src/input/InputFPPRemotePlayList.cpp
+++ b/src/input/InputFPPRemotePlayList.cpp
@@ -77,11 +77,11 @@ void c_InputFPPRemotePlayList::Sync (String & FileName, float ElapsedSeconds)
 } // Sync
 
 //-----------------------------------------------------------------------------
-bool c_InputFPPRemotePlayList::Poll (bool StayDark)
+bool c_InputFPPRemotePlayList::Poll ()
 {
     // DEBUG_START;
 
-    return pCurrentFsmState->Poll (StayDark);
+    return pCurrentFsmState->Poll ();
 
     // DEBUG_END;
 
diff --git a/src/input/InputFPPRemotePlayListFsm.cpp b/src/input/InputFPPRemotePlayListFsm.cpp
index d16a5f70c..3c7eb8cd9 100644
--- a/src/input/InputFPPRemotePlayListFsm.cpp
+++ b/src/input/InputFPPRemotePlayListFsm.cpp
@@ -25,7 +25,7 @@
 #include "input/InputFPPRemotePlayEffect.hpp"
 
 //-----------------------------------------------------------------------------
-bool fsm_PlayList_state_WaitForStart::Poll (bool /* StayDark */)
+bool fsm_PlayList_state_WaitForStart::Poll ()
 {
     // DEBUG_START;
 
@@ -94,7 +94,7 @@ void fsm_PlayList_state_WaitForStart::GetStatus (JsonObject& jsonStatus)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayList_state_Idle::Poll (bool /* StayDark */)
+bool fsm_PlayList_state_Idle::Poll ()
 {
     // DEBUG_START;
 
@@ -153,11 +153,11 @@ void fsm_PlayList_state_Idle::GetStatus (JsonObject& jsonStatus)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayList_state_PlayingFile::Poll (bool StayDark)
+bool fsm_PlayList_state_PlayingFile::Poll ()
 {
     // xDEBUG_START;
 
-    bool Response = pInputFPPRemotePlayList->pInputFPPRemotePlayItem->Poll (StayDark);
+    bool Response = pInputFPPRemotePlayList->pInputFPPRemotePlayItem->Poll ();
 
     if (pInputFPPRemotePlayList->pInputFPPRemotePlayItem->IsIdle ())
     {
@@ -230,11 +230,11 @@ void fsm_PlayList_state_PlayingFile::GetStatus (JsonObject& jsonStatus)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayList_state_PlayingEffect::Poll (bool StayDark)
+bool fsm_PlayList_state_PlayingEffect::Poll ()
 {
     // DEBUG_START;
 
-    pInputFPPRemotePlayList->pInputFPPRemotePlayItem->Poll (StayDark);
+    pInputFPPRemotePlayList->pInputFPPRemotePlayItem->Poll ();
 
     if (pInputFPPRemotePlayList->pInputFPPRemotePlayItem->IsIdle ())
     {
@@ -309,7 +309,7 @@ void fsm_PlayList_state_PlayingEffect::GetStatus (JsonObject& jsonStatus)
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
-bool fsm_PlayList_state_Paused::Poll (bool /* StayDark */)
+bool fsm_PlayList_state_Paused::Poll ()
 {
     // DEBUG_START;
 
diff --git a/src/input/InputMQTT.cpp b/src/input/InputMQTT.cpp
index 1e14dbc8f..d2c3b469c 100644
--- a/src/input/InputMQTT.cpp
+++ b/src/input/InputMQTT.cpp
@@ -154,7 +154,7 @@ void c_InputMQTT::GetStatus (JsonObject & jsonStatus)
 } // GetStatus
 
 //-----------------------------------------------------------------------------
-void c_InputMQTT::Process (bool StayDark)
+void c_InputMQTT::Process ()
 {
     // DEBUG_START;
 
@@ -163,12 +163,12 @@ void c_InputMQTT::Process (bool StayDark)
         if (nullptr != pEffectsEngine)
         {
             // DEBUG_V ("");
-            pEffectsEngine->Process (StayDark);
+            pEffectsEngine->Process ();
         }
 
         else if (nullptr != pPlayFileEngine)
         {
-            pPlayFileEngine->Poll (StayDark);
+            pPlayFileEngine->Poll ();
         }
         else
         {
diff --git a/src/input/InputMgr.cpp b/src/input/InputMgr.cpp
index 77a8f8487..24ba1b0b3 100644
--- a/src/input/InputMgr.cpp
+++ b/src/input/InputMgr.cpp
@@ -62,6 +62,48 @@ static const InputTypeXlateMap_t InputTypeXlateMap[c_InputMgr::e_InputType::Inpu
     {c_InputMgr::e_InputType::InputType_Disabled, "Disabled",   c_InputMgr::e_InputChannelIds::InputChannelId_ALL}
 };
 
+
+#if defined ARDUINO_ARCH_ESP32
+#   include <functional>
+
+static TaskHandle_t PollTaskHandle = NULL;
+//----------------------------------------------------------------------------
+void InputMgrTask (void *arg)
+{
+    // DEBUG_V(String("Current CPU ID: ") + String(xPortGetCoreID()));
+    // DEBUG_V(String("Current Task Priority: ") + String(uxTaskPriorityGet(NULL)));
+    uint32_t PollStartTime = millis();
+    uint32_t PollEndTime = PollStartTime;
+    uint32_t PollTime = pdMS_TO_TICKS(25);
+    const uint32_t MinPollTimeMs = 25;
+
+    while(1)
+    {
+        uint32_t DeltaTime = PollEndTime - PollStartTime;
+
+        if (DeltaTime < MinPollTimeMs)
+        {
+            PollTime = pdMS_TO_TICKS(MinPollTimeMs - DeltaTime);
+        }
+        else
+        {
+            // handle time wrap and long frames
+            PollTime = pdMS_TO_TICKS(1);
+        }
+        vTaskDelay(PollTime);
+        FeedWDT();
+
+        PollStartTime = millis();
+
+        InputMgr.Process();
+        FeedWDT();
+
+        // record the loop end time
+        PollEndTime = millis();
+    }
+} // InputMgrTask
+#endif // def ARDUINO_ARCH_ESP32
+
 //-----------------------------------------------------------------------------
 // Methods
 //-----------------------------------------------------------------------------
@@ -89,6 +131,15 @@ c_InputMgr::~c_InputMgr ()
 {
     // DEBUG_START;
 
+#ifdef ARDUINO_ARCH_ESP32
+    if(PollTaskHandle)
+    {
+        logcon("Stop Input Task");
+        vTaskDelete(PollTaskHandle);
+        PollTaskHandle = NULL;
+    }
+#endif // def ARDUINO_ARCH_ESP32
+
     // delete pInputInstances;
     int pInputChannelDriversIndex = 0;
     for (auto & CurrentInput : InputChannelDrivers)
@@ -128,13 +179,18 @@ void c_InputMgr::Begin (uint32_t BufferSize)
         InstantiateNewInputChannel(e_InputChannelIds(CurrentInput.DriverId), e_InputType::InputType_Disabled);
         // DEBUG_V ("");
     }
-    HasBeenInitialized = true;
 
     // load up the configuration from the saved file. This also starts the drivers
     LoadConfig ();
 
     // CreateNewConfig();
 
+#if defined ARDUINO_ARCH_ESP32
+    xTaskCreatePinnedToCore(InputMgrTask, "InputMgrTask", 4096, NULL, INPUTMGR_TASK_PRIORITY, &PollTaskHandle, 1);
+#endif // defined ARDUINO_ARCH_ESP32
+
+    HasBeenInitialized = true;
+
     // DEBUG_END;
 
 } // begin
@@ -633,13 +689,13 @@ void c_InputMgr::Process ()
 
     do // once
     {
-        if (configInProgress)
+        if (configInProgress || PauseProcessing)
         {
             // prevent calls to process when we are doing a long operation
             break;
         }
 
-        ExternalInput.Poll (false);
+        ExternalInput.Poll ();
 
         if (NO_CONFIG_NEEDED != ConfigLoadNeeded)
         {
@@ -659,12 +715,12 @@ void c_InputMgr::Process ()
         bool aBlankTimerIsRunning = false;
         for (auto & CurrentInput : InputChannelDrivers)
         {
-            if(nullptr == CurrentInput.pInputChannelDriver)
+            if(nullptr == CurrentInput.pInputChannelDriver || aBlankTimerIsRunning)
             {
                 continue;
             }
             // DEBUG_V(String("pInputChannelDriver: 0x") + String(uint32_t(CurrentInput.pInputChannelDriver), HEX));
-            CurrentInput.pInputChannelDriver->Process (aBlankTimerIsRunning);
+            CurrentInput.pInputChannelDriver->Process ();
 
             if (!BlankTimerHasExpired (CurrentInput.pInputChannelDriver->GetInputChannelId()))
             {
@@ -954,6 +1010,8 @@ void c_InputMgr::SetOperationalState (bool ActiveFlag)
     // DEBUG_START;
     // DEBUG_V(String("ActiveFlag: ") + String(ActiveFlag));
 
+    PauseProcessing = ActiveFlag;
+
     // pass through each active interface and set the active state
     for (auto & InputChannel : InputChannelDrivers)
     {
diff --git a/src/input/externalInput.cpp b/src/input/externalInput.cpp
index d23644fe4..d04375a52 100644
--- a/src/input/externalInput.cpp
+++ b/src/input/externalInput.cpp
@@ -125,7 +125,7 @@ void c_ExternalInput::ProcessConfig (JsonObject JsonData)
 } // ProcessConfig
 
 /*****************************************************************************/
-void c_ExternalInput::Poll (bool StayDark)
+void c_ExternalInput::Poll ()
 {
 	// DEBUG_START;
 
diff --git a/src/main.cpp b/src/main.cpp
index 1ae0a1559..619707f3f 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -2,7 +2,7 @@
 * ESPixelStick.ino
 *
 * Project: ESPixelStick - An ESP8266 / ESP32 and E1.31 based pixel driver
-* Copyright (c) 2016, 2022 Shelby Merrick
+* Copyright (c) 2016, 2025 Shelby Merrick
 * http://www.forkineye.com
 *
 *  This program is provided free for you to use in any way that you wish,
@@ -513,8 +513,10 @@ void loop()
     // Keep the Network Open
     NetworkMgr.Poll ();
 
+#if !defined ARDUINO_ARCH_ESP32
     // Process input data
     InputMgr.Process ();
+#endif // defined ARDUINO_ARCH_ESP32
 
     // Poll output
     OutputMgr.Poll();
diff --git a/src/output/OutputMgr.cpp b/src/output/OutputMgr.cpp
index 3df9fe395..cde5cc506 100644
--- a/src/output/OutputMgr.cpp
+++ b/src/output/OutputMgr.cpp
@@ -1331,7 +1331,7 @@ void c_OutputMgr::Poll()
         }
     } // done need to save the current config
 
-    if ((false == IsOutputPaused) && (false == ConfigInProgress) && (false == RebootInProgress()) )
+    if ((false == OutputIsPaused) && (false == ConfigInProgress) && (false == RebootInProgress()) )
     {
         // //DEBUG_V();
         for (DriverInfo_t & OutputChannel : OutputChannelDrivers)
@@ -1421,7 +1421,7 @@ void c_OutputMgr::PauseOutputs(bool PauseTheOutput)
     // DEBUG_START;
     // DEBUG_V(String("PauseTheOutput: ") + String(PauseTheOutput));
 
-    IsOutputPaused = PauseTheOutput;
+    OutputIsPaused = PauseTheOutput;
 
     for (auto & CurrentOutput : OutputChannelDrivers)
     {
@@ -1438,6 +1438,11 @@ void c_OutputMgr::WriteChannelData(uint32_t StartChannelId, uint32_t ChannelCoun
 
     do // once
     {
+        if(OutputIsPaused)
+        {
+            // DEBUG_V("Ignore the write request");
+            break;
+        }
         if (((StartChannelId + ChannelCount) > UsedBufferSize) || (0 == ChannelCount))
         {
             // DEBUG_V (String("ERROR: Invalid parameters"));
@@ -1497,6 +1502,11 @@ void c_OutputMgr::ReadChannelData(uint32_t StartChannelId, uint32_t ChannelCount
 
     do // once
     {
+        if(OutputIsPaused)
+        {
+            // DEBUG_V("Ignore the read request");
+            break;
+        }
         if ((StartChannelId + ChannelCount) > UsedBufferSize)
         {
             // DEBUG_V (String("ERROR: Invalid parameters"));
diff --git a/src/service/FPPDiscovery.cpp b/src/service/FPPDiscovery.cpp
index 9a5852722..42543eab7 100644
--- a/src/service/FPPDiscovery.cpp
+++ b/src/service/FPPDiscovery.cpp
@@ -821,7 +821,7 @@ void c_FPPDiscovery::ProcessFile (
         }
 
         // DEBUG_V("Write the file block");
-        bool writeFailed = !FileMgr.handleFileUpload (UploadFileName, index, data, len, final, ContentLength);
+        writeFailed = !FileMgr.handleFileUpload (UploadFileName, index, data, len, final, ContentLength);
 
         if(writeFailed)
         {
@@ -830,11 +830,13 @@ void c_FPPDiscovery::ProcessFile (
         }
 
         // DEBUG_V();
-        if (final || writeFailed)
+        if (final)
         {
             // DEBUG_V("Allow file to play");
             inFileUpload = false;
             UploadFileName = "";
+            writeFailed = false;
+            memset(OutputMgr.GetBufferAddress(), 0x00, OutputMgr.GetBufferSize());
             InputMgr.SetOperationalState(true);
             OutputMgr.PauseOutputs(false);
         }
@@ -887,6 +889,8 @@ void c_FPPDiscovery::ProcessBody (
                 // DEBUG_V ("");
             }
 
+            writeFailed = false;
+
             // DEBUG_V (String ("         name: ") + UploadFileName);
             // DEBUG_V (String ("        index: ") + String (index));
             // DEBUG_V (String ("          len: ") + String (len));
@@ -933,6 +937,7 @@ void c_FPPDiscovery::GetSysInfoJSON (JsonObject & jsonResponse)
 
 } // GetSysInfoJSON
 
+//-----------------------------------------------------------------------------
 void c_FPPDiscovery::GetStatusJSON (JsonObject & JsonData, bool adv)
 {
     // DEBUG_START;