diff --git a/CHANGELOG.md b/CHANGELOG.md
index b0b22548d6..21513856b6 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -20,6 +20,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 - Buy and sell prices in tooltips when trading with a merchant now have colors.
 - Attacks now emit sound effects from the target on hit.
 - Crafting menu tabs
+- Auto camera setting, making the game easier to play with one hand
 
 ### Changed
 
diff --git a/assets/voxygen/i18n/en/hud/hud_settings.ron b/assets/voxygen/i18n/en/hud/hud_settings.ron
index 23f3b83899..88e8572bd3 100644
--- a/assets/voxygen/i18n/en/hud/hud_settings.ron
+++ b/assets/voxygen/i18n/en/hud/hud_settings.ron
@@ -49,6 +49,7 @@
         "hud.settings.auto_walk_behavior": "Auto walk behavior",
         "hud.settings.camera_clamp_behavior": "Camera clamp behavior",
         "hud.settings.stop_auto_walk_on_input": "Stop auto walk on movement",
+        "hud.settings.auto_camera": "Auto camera",
         "hud.settings.reset_gameplay": "Reset to Defaults",
 
         "hud.settings.view_distance": "View Distance",
@@ -77,7 +78,7 @@
         "hud.settings.particles": "Particles",
         "hud.settings.resolution": "Resolution",
         "hud.settings.bit_depth": "Bit Depth",
-        "hud.settings.refresh_rate": "Refresh Rate",        
+        "hud.settings.refresh_rate": "Refresh Rate",
         "hud.settings.lighting_rendering_mode": "Lighting Rendering Mode",
         "hud.settings.lighting_rendering_mode.ashikhmin": "Type A - High    ",
         "hud.settings.lighting_rendering_mode.blinnphong": "Type B - Medium",
diff --git a/voxygen/src/hud/mod.rs b/voxygen/src/hud/mod.rs
index 61f79ba9f5..a62fb5fed8 100644
--- a/voxygen/src/hud/mod.rs
+++ b/voxygen/src/hud/mod.rs
@@ -434,6 +434,7 @@ pub enum Event {
     ChangeAutoWalkBehavior(PressBehavior),
     ChangeCameraClampBehavior(PressBehavior),
     ChangeStopAutoWalkOnInput(bool),
+    ChangeAutoCamera(bool),
     CraftRecipe(String),
     InviteMember(Uid),
     AcceptInvite,
@@ -2663,6 +2664,9 @@ impl Hud {
                     settings_window::Event::ChangeStopAutoWalkOnInput(state) => {
                         events.push(Event::ChangeStopAutoWalkOnInput(state));
                     },
+                    settings_window::Event::ChangeAutoCamera(state) => {
+                        events.push(Event::ChangeAutoCamera(state));
+                    },
                     settings_window::Event::ResetInterfaceSettings => {
                         self.show.help = false;
                         self.show.debug = false;
diff --git a/voxygen/src/hud/settings_window.rs b/voxygen/src/hud/settings_window.rs
index e94cac45de..12f70555c1 100644
--- a/voxygen/src/hud/settings_window.rs
+++ b/voxygen/src/hud/settings_window.rs
@@ -243,6 +243,8 @@ widget_ids! {
         camera_clamp_behavior_list,
         stop_auto_walk_on_input_button,
         stop_auto_walk_on_input_label,
+        auto_camera_button,
+        auto_camera_label,
     }
 }
 
@@ -350,6 +352,7 @@ pub enum Event {
     ChangeAutoWalkBehavior(PressBehavior),
     ChangeCameraClampBehavior(PressBehavior),
     ChangeStopAutoWalkOnInput(bool),
+    ChangeAutoCamera(bool),
 }
 
 #[derive(Clone)]
@@ -1703,7 +1706,7 @@ impl<'a> Widget for SettingsWindow<'a> {
                 self.imgs.checkbox_checked,
             )
             .w_h(18.0, 18.0)
-            .right_from(state.ids.auto_walk_behavior_text, 80.0)
+            .down_from(state.ids.smooth_pan_toggle_button, 8.0)
             .hover_images(self.imgs.checkbox_mo, self.imgs.checkbox_checked_mo)
             .press_images(self.imgs.checkbox_press, self.imgs.checkbox_checked)
             .set(state.ids.stop_auto_walk_on_input_button, ui);
@@ -1728,6 +1731,32 @@ impl<'a> Widget for SettingsWindow<'a> {
             .color(TEXT_COLOR)
             .set(state.ids.stop_auto_walk_on_input_label, ui);
 
+            // Auto-camera toggle
+            let auto_camera_toggle = ToggleButton::new(
+                self.global_state.settings.gameplay.auto_camera,
+                self.imgs.checkbox,
+                self.imgs.checkbox_checked,
+            )
+            .w_h(18.0, 18.0)
+            .down_from(state.ids.stop_auto_walk_on_input_button, 8.0)
+            .hover_images(self.imgs.checkbox_mo, self.imgs.checkbox_checked_mo)
+            .press_images(self.imgs.checkbox_press, self.imgs.checkbox_checked)
+            .set(state.ids.auto_camera_button, ui);
+
+            if self.global_state.settings.gameplay.auto_camera != auto_camera_toggle {
+                events.push(Event::ChangeAutoCamera(
+                    !self.global_state.settings.gameplay.auto_camera,
+                ));
+            }
+
+            Text::new(&self.localized_strings.get("hud.settings.auto_camera"))
+                .right_from(state.ids.auto_camera_button, 10.0)
+                .font_size(self.fonts.cyri.scale(14))
+                .font_id(self.fonts.cyri.conrod_id)
+                .graphics_for(state.ids.auto_camera_button)
+                .color(TEXT_COLOR)
+                .set(state.ids.auto_camera_label, ui);
+
             // Reset the gameplay settings to the default settings
             if Button::image(self.imgs.button)
                 .w_h(RESET_BUTTONS_WIDTH, RESET_BUTTONS_HEIGHT)
diff --git a/voxygen/src/scene/camera.rs b/voxygen/src/scene/camera.rs
index ebd005a004..9f018445e5 100644
--- a/voxygen/src/scene/camera.rs
+++ b/voxygen/src/scene/camera.rs
@@ -52,6 +52,17 @@ pub struct Camera {
     frustum: Frustum<f32>,
 }
 
+fn clamp_and_modulate(ori: Vec3<f32>) -> Vec3<f32> {
+    Vec3 {
+        // Wrap camera yaw
+        x: ori.x.rem_euclid(2.0 * PI),
+        // Clamp camera pitch to the vertical limits
+        y: ori.y.min(PI / 2.0 - 0.0001).max(-PI / 2.0 + 0.0001),
+        // Wrap camera roll
+        z: ori.z.rem_euclid(2.0 * PI),
+    }
+}
+
 impl Camera {
     /// Create a new `Camera` with default parameters.
     pub fn new(aspect: f32, mode: CameraMode) -> Self {
@@ -156,23 +167,12 @@ impl Camera {
     }
 
     /// Set the orientation of the camera about its focus.
-    pub fn set_orientation(&mut self, ori: Vec3<f32>) {
-        // Wrap camera yaw
-        self.tgt_ori.x = ori.x.rem_euclid(2.0 * PI);
-        // Clamp camera pitch to the vertical limits
-        self.tgt_ori.y = ori.y.min(PI / 2.0 - 0.0001).max(-PI / 2.0 + 0.0001);
-        // Wrap camera roll
-        self.tgt_ori.z = ori.z.rem_euclid(2.0 * PI);
-    }
+    pub fn set_orientation(&mut self, ori: Vec3<f32>) { self.tgt_ori = clamp_and_modulate(ori); }
 
     /// Set the orientation of the camera about its focus without lerping.
-    pub fn set_ori_instant(&mut self, ori: Vec3<f32>) {
-        // Wrap camera yaw
-        self.ori.x = ori.x.rem_euclid(2.0 * PI);
-        // Clamp camera pitch to the vertical limits
-        self.ori.y = ori.y.min(PI / 2.0 - 0.0001).max(-PI / 2.0 + 0.0001);
-        // Wrap camera roll
-        self.ori.z = ori.z.rem_euclid(2.0 * PI);
+    pub fn set_orientation_instant(&mut self, ori: Vec3<f32>) {
+        self.set_orientation(ori);
+        self.ori = self.tgt_ori;
     }
 
     /// Zoom the camera by the given delta, limiting the input accordingly.
@@ -249,15 +249,16 @@ impl Camera {
             Lerp::lerp(a, b + *offs, rate)
         };
 
-        if smoothing_enabled {
-            self.set_ori_instant(Vec3::new(
+        let ori = if smoothing_enabled {
+            Vec3::new(
                 lerp_angle(self.ori.x, self.tgt_ori.x, LERP_ORI_RATE * dt),
                 Lerp::lerp(self.ori.y, self.tgt_ori.y, LERP_ORI_RATE * dt),
                 lerp_angle(self.ori.z, self.tgt_ori.z, LERP_ORI_RATE * dt),
-            ));
+            )
         } else {
-            self.set_ori_instant(self.tgt_ori)
+            self.tgt_ori
         };
+        self.ori = clamp_and_modulate(ori);
     }
 
     pub fn interp_time(&self) -> f32 {
diff --git a/voxygen/src/session.rs b/voxygen/src/session.rs
index 646c4f1239..ff7c946075 100644
--- a/voxygen/src/session.rs
+++ b/voxygen/src/session.rs
@@ -732,6 +732,27 @@ impl PlayState for SessionState {
             // Get the current state of movement related inputs
             let input_vec = self.key_state.dir_vec();
             let (axis_right, axis_up) = (input_vec[0], input_vec[1]);
+            let dt = global_state.clock.get_stable_dt().as_secs_f32();
+
+            // Auto camera mode
+            if global_state.settings.gameplay.auto_camera
+                && matches!(
+                    self.scene.camera().get_mode(),
+                    camera::CameraMode::ThirdPerson | camera::CameraMode::FirstPerson
+                )
+                && input_vec.magnitude_squared() > 0.0
+            {
+                let camera = self.scene.camera_mut();
+                let ori = camera.get_orientation();
+                camera.set_orientation_instant(Vec3::new(
+                    ori.x
+                        + input_vec.x
+                            * (3.0 - input_vec.y * 1.5 * if is_aiming { 1.5 } else { 1.0 })
+                            * dt,
+                    std::f32::consts::PI * if is_aiming { 0.015 } else { 0.1 },
+                    0.0,
+                ));
+            }
 
             match self.scene.camera().get_mode() {
                 camera::CameraMode::FirstPerson | camera::CameraMode::ThirdPerson => {
@@ -753,7 +774,6 @@ impl PlayState for SessionState {
                     let right = self.scene.camera().right();
                     let dir = right * axis_right + forward * axis_up;
 
-                    let dt = global_state.clock.get_stable_dt().as_secs_f32();
                     if self.freefly_vel.magnitude_squared() > 0.01 {
                         let new_vel = self.freefly_vel
                             - self.freefly_vel.normalized() * (FREEFLY_DAMPING * dt);
@@ -1406,6 +1426,10 @@ impl PlayState for SessionState {
                         global_state.settings.gameplay.stop_auto_walk_on_input = state;
                         global_state.settings.save_to_file_warn();
                     },
+                    HudEvent::ChangeAutoCamera(state) => {
+                        global_state.settings.gameplay.auto_camera = state;
+                        global_state.settings.save_to_file_warn();
+                    },
                     HudEvent::CraftRecipe(r) => {
                         self.client.borrow_mut().craft_recipe(&r);
                     },
diff --git a/voxygen/src/settings.rs b/voxygen/src/settings.rs
index 66244a2e07..55dcd9851a 100644
--- a/voxygen/src/settings.rs
+++ b/voxygen/src/settings.rs
@@ -503,6 +503,7 @@ pub struct GameplaySettings {
     pub auto_walk_behavior: PressBehavior,
     pub camera_clamp_behavior: PressBehavior,
     pub stop_auto_walk_on_input: bool,
+    pub auto_camera: bool,
 }
 
 impl Default for GameplaySettings {
@@ -518,6 +519,7 @@ impl Default for GameplaySettings {
             auto_walk_behavior: PressBehavior::Toggle,
             camera_clamp_behavior: PressBehavior::Toggle,
             stop_auto_walk_on_input: true,
+            auto_camera: false,
         }
     }
 }