diff --git a/README.md b/README.md
index d91fbe0..f2466e5 100644
--- a/README.md
+++ b/README.md
@@ -2,6 +2,7 @@ Firmware for a homemade automated electric armchair.
 More details about this project: https://pfusch.zone/electric-armchair
 
 
+
 # Installation
 ### Install esp-idf
 For this project **ESP-IDF v4.4.1** is required (with other versions it might not compile)
@@ -93,6 +94,16 @@ A diagram which shows what components are connected to which terminals of the pc
 - Self driving algorithm
 - Lights
 - drinks holder
+- improved webinterface
+
+
+
+# Todo
+**Add switch functions**
+- set loglevel
+- define max-speed
+- calibrate joystick (min, max, center)
+- testing mode / dry-run
 
 
 
@@ -105,7 +116,7 @@ A diagram which shows what components are connected to which terminals of the pc
 | 1x | control | [MASSAGE] **freeze** input | when in massage mode: lock or unlock joystick input at current position |
 | 2x | toggle mode | **IDLE** <=> previous | enable/disable chair armchair e.g. enable after startup or timeout |
 | 3x | switch mode | **JOYSTICK** | switch to default mode JOYSTICK |
-| 4x | toggle mode | **HTTP** <=> JOYSTICK | switch to '**remote control** via web-app' or back to JOYSTICK mode |
+| 4x | toggle mode | **HTTP** <=> JOYSTICK | switch to '**remote control** via web-app `http://191.168.4.1`' or back to JOYSTICK mode |
 | 5x | | | |
 | 6x | toggle mode | **MASSAGE** <=> JOYSTICK | switch to MASSAGE mode or back to JOYSTICK mode |
 | 7x | | | |
@@ -113,16 +124,20 @@ A diagram which shows what components are connected to which terminals of the pc
 | | | | |
 | 12x | toggle option | **alt stick mapping** | toggle between default and alternative stick mapping (reverse swapped) |
 | >1s | system | **restart** | Restart the controller when pressing the button longer than 1 second | 
+| 1x short, 1x long | auto command | **eject** foot support | automatically go forward and reverse for certain time with no acceleration limits, so foot support ejects |
 
 
+## HTTP mode
+Control armchair via virtual joystick on a webinterface.  
 
-**previous functions - not implemented**
-| Count | Action |
-| --- | ---|
-| 1 | define joystick center |
-| 2 | toggle motors |
-| 3 | toggle log-level (WARN, DEBUG, INFO) |
-| 4 | define max duty |
-| 5 | toggle mode MQTT/JOYSTICK |
-| 6 | toggle mode SHAKE/JOYSTICK |
-| 7 | toggle testing-mode (dry-run) |
+**Usage**
+- Connect to wifi `armchar`, no password
+- Access http://192.168.4.1  (note: **http** NOT https, some browsers automatically add https!)  
+
+**Current Features**
+- Control direction and speed with joystick  
+
+**Todo**
+- Set parameters
+- Control other modes
+- Execute preset movement commands
diff --git a/components/gpio/gpio_evaluateSwitch.hpp b/components/gpio/gpio_evaluateSwitch.hpp
index 23caa14..c4a27e4 100644
--- a/components/gpio/gpio_evaluateSwitch.hpp
+++ b/components/gpio/gpio_evaluateSwitch.hpp
@@ -22,8 +22,8 @@ extern "C"
 class gpio_evaluatedSwitch {
     public:
         //--- input ---
-        uint32_t minOnMs = 50;
-        uint32_t minOffMs = 50;
+        uint32_t minOnMs = 30;
+        uint32_t minOffMs = 30;
         gpio_evaluatedSwitch( //constructor minimal (default parameters pullup=true, inverted=false)
                 gpio_num_t gpio_num_declare
                 );
diff --git a/connection-plan.drawio.pdf b/connection-plan.drawio.pdf
index 82ce990..4a430bc 100644
Binary files a/connection-plan.drawio.pdf and b/connection-plan.drawio.pdf differ
diff --git a/main/CMakeLists.txt b/main/CMakeLists.txt
index 6ea40c3..34de854 100644
--- a/main/CMakeLists.txt
+++ b/main/CMakeLists.txt
@@ -11,6 +11,7 @@ idf_component_register(
         "fan.cpp"
         "wifi.c"
         "http.cpp"
+        "auto.cpp"
     INCLUDE_DIRS 
         "."
     )
diff --git a/main/auto.cpp b/main/auto.cpp
new file mode 100644
index 0000000..4cf4a71
--- /dev/null
+++ b/main/auto.cpp
@@ -0,0 +1,88 @@
+#include "auto.hpp"
+#include "config.hpp"
+
+//tag for logging
+static const char * TAG = "automatedArmchair";
+
+
+//=============================
+//======== constructor ========
+//=============================
+automatedArmchair::automatedArmchair(void) {
+    //create command queue
+    commandQueue = xQueueCreate( 32, sizeof( commandSimple_t ) ); //TODO add max size to config?
+}
+
+
+
+//==============================
+//====== generateCommands ======
+//==============================
+motorCommands_t automatedArmchair::generateCommands(auto_instruction_t * instruction) {
+    //reset instruction
+    *instruction = auto_instruction_t::NONE;
+    //check if previous command is finished
+    if ( esp_log_timestamp() > timestampCmdFinished ) {
+        //get next command from queue
+        if( xQueueReceive( commandQueue, &cmdCurrent, pdMS_TO_TICKS(500) ) ) {
+            ESP_LOGI(TAG, "running next command from queue...");
+            //copy instruction to be provided to control task
+            *instruction = cmdCurrent.instruction;
+            //set acceleration / fading parameters according to command
+            motorLeft.setFade(fadeType_t::DECEL, cmdCurrent.fadeDecel);
+            motorRight.setFade(fadeType_t::DECEL, cmdCurrent.fadeDecel);
+            motorLeft.setFade(fadeType_t::ACCEL, cmdCurrent.fadeAccel);
+            motorRight.setFade(fadeType_t::ACCEL, cmdCurrent.fadeAccel);
+            //calculate timestamp the command is finished
+            timestampCmdFinished = esp_log_timestamp() + cmdCurrent.msDuration;
+            //copy the new commands
+            motorCommands = cmdCurrent.motorCmds;
+        } else { //queue empty
+            ESP_LOGD(TAG, "no new command in queue -> set motors to IDLE");
+            motorCommands = motorCmds_bothMotorsIdle;
+        }
+    } else { //previous command still running
+        ESP_LOGD(TAG, "command still running -> no change");
+    }
+
+    //TODO also return instructions via call by reference
+    return motorCommands;
+}
+
+
+
+//============================
+//======== addCommand ========
+//============================
+//function that adds a basic command to the queue
+void automatedArmchair::addCommand(commandSimple_t command) {
+    //add command to queue
+     if ( xQueueSend( commandQueue, ( void * )&command, ( TickType_t ) 0 ) ){
+         ESP_LOGI(TAG, "Successfully inserted command to queue");
+     } else {
+         ESP_LOGE(TAG, "Failed to insert new command to queue");
+     }
+}
+
+void automatedArmchair::addCommands(commandSimple_t commands[], size_t count) {
+    for (int i = 0; i < count; i++) {
+         ESP_LOGI(TAG, "Reading command no. %d from provided array", i);
+        addCommand(commands[i]);
+    }
+}
+
+
+//===============================
+//======== clearCommands ========
+//===============================
+//function that deletes all pending/queued commands
+//e.g. when switching modes
+motorCommands_t automatedArmchair::clearCommands() {
+    //clear command queue
+    xQueueReset( commandQueue );
+    ESP_LOGW(TAG, "command queue was successfully emptied");
+    //return commands for idling both motors
+    motorCommands = motorCmds_bothMotorsIdle;
+    return motorCmds_bothMotorsIdle;
+}
+
diff --git a/main/auto.hpp b/main/auto.hpp
new file mode 100644
index 0000000..8b799fb
--- /dev/null
+++ b/main/auto.hpp
@@ -0,0 +1,87 @@
+#pragma once
+
+extern "C"
+{
+#include "freertos/FreeRTOS.h"
+#include "freertos/task.h"
+#include "esp_log.h"
+#include "esp_err.h"
+}
+
+#include "freertos/queue.h"
+#include <cmath>
+#include "motorctl.hpp"
+
+
+
+//--------------------------------------------
+//---- struct, enum, variable declarations ---
+//--------------------------------------------
+//enum for special instructions / commands to be run in control task
+enum class auto_instruction_t { NONE, SWITCH_PREV_MODE, SWITCH_JOYSTICK_MODE, RESET_ACCEL_DECEL, RESET_ACCEL, RESET_DECEL };
+
+//struct for a simple command
+//e.g. put motors in a certain state for certain time
+typedef struct commandSimple_t{
+    motorCommands_t motorCmds;
+    uint32_t msDuration;
+    uint32_t fadeDecel;
+    uint32_t fadeAccel;
+    auto_instruction_t instruction;
+} commandSimple_t;
+
+
+
+//------------------------------------
+//----- automatedArmchair class  -----
+//------------------------------------
+class automatedArmchair {
+    public:
+        //--- methods ---
+        //constructor
+        automatedArmchair(void);
+        //function to generate motor commands
+        //can be also seen as handle function 
+        //TODO: go with other approach: separate task for handling auto mode
+        //  - receive commands with queue anyways
+        //  - => use delay function
+        //  - have a queue that outputs current motor state/commands -> repeatedly check the queue in control task
+        //function that handles automatic driving and returns motor commands
+        //also provides instructions to be executed in control task via pointer
+        motorCommands_t generateCommands(auto_instruction_t * instruction);
+
+        //function that adds a basic command to the queue
+        void addCommand(commandSimple_t command);
+        //function that adds an array of basic commands to queue
+        void addCommands(commandSimple_t commands[], size_t count);
+
+        //function that deletes all pending/queued commands
+        motorCommands_t clearCommands();
+
+
+    private:
+        //--- methods ---
+        //--- objects ---
+        //TODO: add buzzer here
+        //--- variables ---
+        //queue for storing pending commands
+        QueueHandle_t commandQueue = NULL;
+        //current running command
+        commandSimple_t cmdCurrent;
+        //timestamp current command is finished
+        uint32_t timestampCmdFinished = 0;
+
+        motorCommands_t motorCommands;
+
+        //command preset for idling motors
+        const motorCommand_t motorCmd_motorIdle = {
+            .state = motorstate_t::IDLE,
+            .duty = 0
+        };
+        const motorCommands_t motorCmds_bothMotorsIdle = {
+            .left = motorCmd_motorIdle,
+            .right = motorCmd_motorIdle
+        };
+};
+
+
diff --git a/main/button.cpp b/main/button.cpp
index b717328..1762e6e 100644
--- a/main/button.cpp
+++ b/main/button.cpp
@@ -19,9 +19,10 @@ static const char * TAG = "button";
 //-----------------------------
 //-------- constructor --------
 //-----------------------------
-buttonCommands::buttonCommands(gpio_evaluatedSwitch * button_f, controlledArmchair * control_f, buzzer_t * buzzer_f, controlledMotor * motorLeft_f, controlledMotor * motorRight_f){
+buttonCommands::buttonCommands(gpio_evaluatedSwitch * button_f, evaluatedJoystick * joystick_f, controlledArmchair * control_f, buzzer_t * buzzer_f, controlledMotor * motorLeft_f, controlledMotor * motorRight_f){
     //copy object pointers
     button = button_f;
+    joystick = joystick_f;
     control = control_f;
     buzzer = buzzer_f;
     motorLeft = motorLeft_f;
@@ -35,9 +36,13 @@ buttonCommands::buttonCommands(gpio_evaluatedSwitch * button_f, controlledArmcha
 //--------- action -----------
 //----------------------------
 //function that runs commands depending on a count value
-void buttonCommands::action (uint8_t count){
+void buttonCommands::action (uint8_t count, bool lastPressLong){
     //--- variable declarations ---
     bool decelEnabled; //for different beeping when toggling
+    commandSimple_t cmds[8]; //array for commands for automatedArmchair
+
+    //--- get joystick position ---
+    //joystickData_t stickData = joystick->getData();
 
     //--- actions based on count ---
     switch (count){
@@ -47,28 +52,77 @@ void buttonCommands::action (uint8_t count){
             buzzer->beep(3, 400, 100);
             break;
 
-        case 0: //special case when last button press is longer than timeout (>1s)
-            ESP_LOGW(TAG, "RESTART");
-            buzzer->beep(1,1000,1);
-            vTaskDelay(1000 / portTICK_PERIOD_MS);
-            esp_restart();
-
         case 1:
+            //restart contoller when 1x long pressed
+            if (lastPressLong){
+                ESP_LOGW(TAG, "RESTART");
+                buzzer->beep(1,1000,1);
+                vTaskDelay(1000 / portTICK_PERIOD_MS);
+                esp_restart();
+                return;
+            } 
+
             ESP_LOGW(TAG, "cmd %d: sending button event to control task", count);
             //-> define joystick center or toggle freeze input (executed in control task)
             control->sendButtonEvent(count); //TODO: always send button event to control task (not just at count=1) -> control.cpp has to be changed
             break;
+        case 2:
+            //run automatic commands to lift leg support when pressed 1x short 1x long
+            if (lastPressLong){
+                //define commands
+                cmds[0] =
+                {
+                    .motorCmds = {
+                        .left = {motorstate_t::REV, 90},
+                        .right = {motorstate_t::REV, 90}
+                    },
+                    .msDuration = 1200,
+                    .fadeDecel = 800,
+                    .fadeAccel = 1300,
+                    .instruction = auto_instruction_t::NONE
+                };
+                cmds[1] =
+                {
+                    .motorCmds = {
+                        .left = {motorstate_t::FWD, 70},
+                        .right = {motorstate_t::FWD, 70}
+                    },
+                    .msDuration = 70,
+                    .fadeDecel = 0,
+                    .fadeAccel = 300,
+                    .instruction = auto_instruction_t::NONE
+                };
+                cmds[2] =
+                {
+                    .motorCmds = {
+                        .left = {motorstate_t::IDLE, 0},
+                        .right = {motorstate_t::IDLE, 0}
+                    },
+                    .msDuration = 10,
+                    .fadeDecel = 800,
+                    .fadeAccel = 1300,
+                    .instruction = auto_instruction_t::SWITCH_JOYSTICK_MODE
+                };
+
+                //send commands to automatedArmchair command queue
+                armchair.addCommands(cmds, 3);
+
+                //change mode to AUTO
+                control->changeMode(controlMode_t::AUTO);
+                return;
+            }
+
+            //toggle idle when 2x pressed
+            ESP_LOGW(TAG, "cmd %d: toggle IDLE", count);
+            control->toggleIdle(); //toggle between idle and previous/default mode
+            break;
+
 
         case 3:
             ESP_LOGW(TAG, "cmd %d: switch to JOYSTICK", count);
             control->changeMode(controlMode_t::JOYSTICK); //switch to JOYSTICK mode
             break;
 
-        case 2:
-            ESP_LOGW(TAG, "cmd %d: toggle IDLE", count);
-            control->toggleIdle(); //toggle between idle and previous/default mode
-            break;
-
         case 4:
             ESP_LOGW(TAG, "cmd %d: toggle between HTTP and JOYSTICK", count);
             control->toggleModes(controlMode_t::HTTP, controlMode_t::JOYSTICK); //toggle between HTTP and JOYSTICK mode
@@ -120,7 +174,7 @@ void buttonCommands::startHandleLoop() {
             case inputState_t::IDLE: //wait for initial button press
                 if (button->risingEdge) {
                     count = 1;
-                    buzzer->beep(1, 60, 0);
+                    buzzer->beep(1, 65, 0);
                     timestamp_lastAction = esp_log_timestamp();
                     state = inputState_t::WAIT_FOR_INPUT;
                     ESP_LOGI(TAG, "first button press detected -> waiting for further events");
@@ -131,7 +185,7 @@ void buttonCommands::startHandleLoop() {
                 //button pressed again
                 if (button->risingEdge){
                     count++;
-                    buzzer->beep(1, 60, 0);
+                    buzzer->beep(1, 65, 0);
                     timestamp_lastAction = esp_log_timestamp();
                     ESP_LOGI(TAG, "another press detected -> count=%d -> waiting for further events", count);
                 }
@@ -143,14 +197,14 @@ void buttonCommands::startHandleLoop() {
                     ESP_LOGI(TAG, "timeout - running action function for count=%d", count);
                     //--- run action function ---
                     //check if still pressed
+                    bool lastPressLong = false;
                     if (button->state == true){
                         //run special case when last press was longer than timeout
-                        action(0); 
-                    } else {
-                        //run action function with current count of button presses
-                        action(count);
+                        lastPressLong = true;
+                    }
+                        //run action function with current count of button presses
+                        action(count, lastPressLong);
                     }
-                }
                 break;
         }
     }
diff --git a/main/button.hpp b/main/button.hpp
index b5d5900..09de729 100644
--- a/main/button.hpp
+++ b/main/button.hpp
@@ -4,6 +4,9 @@
 #include "buzzer.hpp"
 #include "control.hpp"
 #include "motorctl.hpp"
+#include "auto.hpp"
+#include "config.hpp"
+#include "joystick.hpp"
 
 
 
@@ -16,6 +19,7 @@ class buttonCommands {
         //--- constructor ---
         buttonCommands (
                 gpio_evaluatedSwitch * button_f,
+                evaluatedJoystick * joystick_f,
                 controlledArmchair * control_f,
                 buzzer_t * buzzer_f,
                 controlledMotor * motorLeft_f, 
@@ -29,10 +33,11 @@ class buttonCommands {
 
     private:
         //--- functions ---
-        void action(uint8_t count);
+        void action(uint8_t count, bool lastPressLong);
 
         //--- objects ---
         gpio_evaluatedSwitch* button;
+        evaluatedJoystick* joystick;
         controlledArmchair * control;
         buzzer_t* buzzer;
         controlledMotor * motorLeft;
diff --git a/main/config.cpp b/main/config.cpp
index 784047e..3214948 100644
--- a/main/config.cpp
+++ b/main/config.cpp
@@ -30,7 +30,7 @@ single100a_config_t configDriverRight = {
 //--- configure motor contol ---
 motorctl_config_t configMotorControl = {
     .msFadeAccel = 1300, //acceleration of the motor (ms it takes from 0% to 100%)
-    .msFadeDecel = 800, //deceleration of the motor (ms it takes from 100% to 0%)
+    .msFadeDecel = 700, //deceleration of the motor (ms it takes from 100% to 0%)
     .currentMax = 10
 };
 
@@ -126,5 +126,7 @@ httpJoystick httpJoystickMain(configHttpJoystickMain);
 //create global control object
 controlledArmchair control(configControl, &buzzer, &motorLeft, &motorRight, &joystick, &httpJoystickMain);
 
+//create global automatedArmchair object (for auto-mode)
+automatedArmchair armchair;
 
 
diff --git a/main/config.hpp b/main/config.hpp
index 20db9bc..93193b9 100644
--- a/main/config.hpp
+++ b/main/config.hpp
@@ -9,6 +9,7 @@
 #include "control.hpp"
 #include "fan.hpp"
 #include "http.hpp"
+#include "auto.hpp"
 
 
 //create global controlledMotor instances for both motors
@@ -27,6 +28,9 @@ extern buzzer_t buzzer;
 //create global control object
 extern controlledArmchair control;
 
+//create global automatedArmchair object (for auto-mode)
+extern automatedArmchair armchair;
+
 //create global httpJoystick object
 extern httpJoystick httpJoystickMain;
 
diff --git a/main/control.cpp b/main/control.cpp
index 7bc9faf..80b5393 100644
--- a/main/control.cpp
+++ b/main/control.cpp
@@ -121,6 +121,48 @@ void controlledArmchair::startHandleLoop() {
                 motorLeft->setTarget(commands.left.state, commands.left.duty); 
                break;
 
+
+            case controlMode_t::AUTO:
+                vTaskDelay(20 / portTICK_PERIOD_MS);
+               //generate commands
+               commands = armchair.generateCommands(&instruction);
+                //--- apply commands to motors ---
+                //TODO make motorctl.setTarget also accept motorcommand struct directly
+               motorRight->setTarget(commands.right.state, commands.right.duty); 
+               motorLeft->setTarget(commands.left.state, commands.left.duty); 
+
+               //process received instruction
+               switch (instruction) {
+                   case auto_instruction_t::NONE:
+                       break;
+                   case auto_instruction_t::SWITCH_PREV_MODE:
+                       toggleMode(controlMode_t::AUTO);
+                       break;
+                   case auto_instruction_t::SWITCH_JOYSTICK_MODE:
+                       changeMode(controlMode_t::JOYSTICK);
+                       break;
+                   case auto_instruction_t::RESET_ACCEL_DECEL:
+                       //enable downfading (set to default value)
+                       motorLeft->setFade(fadeType_t::DECEL, true);
+                       motorRight->setFade(fadeType_t::DECEL, true);
+                       //set upfading to default value
+                       motorLeft->setFade(fadeType_t::ACCEL, true);
+                       motorRight->setFade(fadeType_t::ACCEL, true);
+                       break;
+                   case auto_instruction_t::RESET_ACCEL:
+                       //set upfading to default value
+                       motorLeft->setFade(fadeType_t::ACCEL, true);
+                       motorRight->setFade(fadeType_t::ACCEL, true);
+                       break;
+                   case auto_instruction_t::RESET_DECEL:
+                       //enable downfading (set to default value)
+                       motorLeft->setFade(fadeType_t::DECEL, true);
+                       motorRight->setFade(fadeType_t::DECEL, true);
+                       break;
+               }
+               break;
+
+
               //  //TODO: add other modes here
         }
 
@@ -255,12 +297,19 @@ void controlledArmchair::changeMode(controlMode_t modeNew) {
     //reset timeout timer
     resetTimeout();
 
+    //exit if target mode is already active
+    if (mode == modeNew) {
+        ESP_LOGE(TAG, "changeMode: Already in target mode '%s' -> nothing to change", controlModeStr[(int)mode]);
+        return;
+    }
+
     //copy previous mode
-    controlMode_t modePrevious = mode;
+    modePrevious = mode;
 
     ESP_LOGW(TAG, "=== changing mode from %s to %s ===", controlModeStr[(int)mode], controlModeStr[(int)modeNew]);
 
-    //--- run functions when changing FROM certain mode ---
+    //========== commands change FROM mode ==========
+    //run functions when changing FROM certain mode
     switch(modePrevious){
         default:
             ESP_LOGI(TAG, "noting to execute when changing FROM this mode");
@@ -293,10 +342,22 @@ void controlledArmchair::changeMode(controlMode_t modeNew) {
             //reset frozen input state
             freezeInput = false;
             break;
+
+        case controlMode_t::AUTO:
+            ESP_LOGW(TAG, "switching from AUTO mode -> restoring fading to default");
+            //TODO: fix issue when downfading was disabled before switching to auto mode - currently it gets enabled again here...
+            //enable downfading (set to default value)
+            motorLeft->setFade(fadeType_t::DECEL, true);
+            motorRight->setFade(fadeType_t::DECEL, true);
+            //set upfading to default value
+            motorLeft->setFade(fadeType_t::ACCEL, true);
+            motorRight->setFade(fadeType_t::ACCEL, true);
+            break;
     }
 
 
-    //--- run functions when changing TO certain mode ---
+    //========== commands change TO mode ==========
+    //run functions when changing TO certain mode
     switch(modeNew){
         default:
             ESP_LOGI(TAG, "noting to execute when changing TO this mode");
@@ -352,15 +413,8 @@ void controlledArmchair::changeMode(controlMode_t modeNew) {
 //-----------------------------------
 //function to toggle between IDLE and previous active mode
 void controlledArmchair::toggleIdle() {
-    if (mode == controlMode_t::IDLE){
-        changeMode(modePrevious); //restore previous mode, or default if not switched yet
-        buzzer->beep(2, 200, 100);
-        ESP_LOGW(TAG, "toggle idle: switched mode from IDLE to %s", controlModeStr[(int)mode]);
-    } else {
-        modePrevious = mode; //store current mode
-        changeMode(controlMode_t::IDLE); //set mode to IDLE
-        ESP_LOGW(TAG, "toggle idle: switched mode from %s to IDLE", controlModeStr[(int)mode]);
-    }
+    //toggle between IDLE and previous mode
+    toggleMode(controlMode_t::IDLE);
 }
 
 
@@ -384,3 +438,25 @@ void controlledArmchair::toggleModes(controlMode_t modePrimary, controlMode_t mo
         changeMode(modePrimary);
     }
 }
+
+
+
+//-----------------------------------
+//----------- toggleMode ------------
+//-----------------------------------
+//function that toggles between certain mode and previous mode
+void controlledArmchair::toggleMode(controlMode_t modePrimary){
+
+    //switch to previous mode when primary is already active
+    if (mode == modePrimary){
+        ESP_LOGW(TAG, "toggleMode: switching from primaryMode %s to previousMode %s", controlModeStr[(int)mode], controlModeStr[(int)modePrevious]);
+        //buzzer->beep(2,200,100);
+        changeMode(modePrevious); //switch to previous mode
+    } 
+    //switch to primary mode when any other mode is active
+    else {
+        ESP_LOGW(TAG, "toggleModes: switching from %s to primary mode %s", controlModeStr[(int)mode], controlModeStr[(int)modePrimary]);
+        //buzzer->beep(4,200,100);
+        changeMode(modePrimary);
+    }
+}
diff --git a/main/control.hpp b/main/control.hpp
index 69d492a..9715a33 100644
--- a/main/control.hpp
+++ b/main/control.hpp
@@ -4,6 +4,7 @@
 #include "motorctl.hpp"
 #include "buzzer.hpp"
 #include "http.hpp"
+#include "auto.hpp"
 
 
 //--------------------------------------------
@@ -54,6 +55,8 @@ class controlledArmchair {
 
         //function that toggles between two modes, but prefers first argument if entirely different mode is currently active
         void toggleModes(controlMode_t modePrimary, controlMode_t modeSecondary);
+        //toggle between certain mode and previous mode
+        void toggleMode(controlMode_t modePrimary);
 
         //function that restarts timer which initiates the automatic timeout (switch to IDLE) after certain time of inactivity
         void resetTimeout();
@@ -90,6 +93,9 @@ class controlledArmchair {
 
         //variables for MASSAGE mode
         bool freezeInput = false;
+
+        //variables for AUTO mode
+        auto_instruction_t instruction = auto_instruction_t::NONE; //variable to receive instructions from automatedArmchair
         
         //variable to store button event
         uint8_t buttonCount = 0;
diff --git a/main/main.cpp b/main/main.cpp
index 49ec363..a9c8e4d 100644
--- a/main/main.cpp
+++ b/main/main.cpp
@@ -75,7 +75,7 @@ void task_control( void * pvParameters ){
 void task_button( void * pvParameters ){
     ESP_LOGI(TAG, "Initializing command-button and starting handle loop");
     //create button instance
-    buttonCommands commandButton(&buttonJoystick, &control, &buzzer, &motorLeft, &motorRight);
+    buttonCommands commandButton(&buttonJoystick, &joystick, &control, &buzzer, &motorLeft, &motorRight);
     //start handle loop
     commandButton.startHandleLoop();
 }
@@ -152,6 +152,7 @@ extern "C" void app_main(void) {
     esp_log_level_set("fan-control", ESP_LOG_INFO);
     esp_log_level_set("wifi", ESP_LOG_INFO);
     esp_log_level_set("http", ESP_LOG_INFO);
+    esp_log_level_set("automatedArmchair", ESP_LOG_DEBUG);
 
     
     //----------------------------------------------
@@ -175,7 +176,7 @@ extern "C" void app_main(void) {
     //--- create task for button ---
     //------------------------------
     //task that evaluates and processes the button input and runs the configured commands
-    xTaskCreate(&task_button, "task_button", 2048, NULL, 4, NULL);
+    xTaskCreate(&task_button, "task_button", 4096, NULL, 4, NULL);
 
     //-----------------------------------
     //--- create task for fan control ---