From 44ec09a8e7466ac3245fba1b0a9b74001fdb1b98 Mon Sep 17 00:00:00 2001
From: timokoesters <timo@koesters.xyz>
Date: Fri, 20 Mar 2020 17:15:09 +0100
Subject: [PATCH 1/4] Go to idle state when picking items up

---
 common/src/sys/controller.rs | 19 ++++++++++++++++---
 voxygen/src/scene/mod.rs     |  2 ++
 voxygen/src/session.rs       |  3 ++-
 3 files changed, 20 insertions(+), 4 deletions(-)

diff --git a/common/src/sys/controller.rs b/common/src/sys/controller.rs
index 4a0e033651..9b3718d849 100644
--- a/common/src/sys/controller.rs
+++ b/common/src/sys/controller.rs
@@ -1,5 +1,5 @@
 use crate::{
-    comp::{ControlEvent, Controller},
+    comp::{CharacterState, ControlEvent, Controller},
     event::{EventBus, LocalEvent, ServerEvent},
     state::DeltaTime,
     sync::{Uid, UidAllocator},
@@ -22,15 +22,27 @@ impl<'a> System<'a> for Sys {
         Read<'a, EventBus<LocalEvent>>,
         Read<'a, DeltaTime>,
         WriteStorage<'a, Controller>,
+        WriteStorage<'a, CharacterState>,
         ReadStorage<'a, Uid>,
     );
 
     fn run(
         &mut self,
-        (entities, uid_allocator, server_bus, _local_bus, _dt, mut controllers, uids): Self::SystemData,
+        (
+            entities,
+            uid_allocator,
+            server_bus,
+            _local_bus,
+            _dt,
+            mut controllers,
+            mut character_states,
+            uids,
+        ): Self::SystemData,
     ) {
         let mut server_emitter = server_bus.emitter();
-        for (entity, _uid, controller) in (&entities, &uids, &mut controllers).join() {
+        for (entity, _uid, controller, character_state) in
+            (&entities, &uids, &mut controllers, &mut character_states).join()
+        {
             let inputs = &mut controller.inputs;
 
             // Update `inputs.move_dir`.
@@ -59,6 +71,7 @@ impl<'a> System<'a> for Sys {
                     },
                     ControlEvent::Unmount => server_emitter.emit(ServerEvent::Unmount(entity)),
                     ControlEvent::InventoryManip(manip) => {
+                        *character_state = CharacterState::Idle;
                         server_emitter.emit(ServerEvent::InventoryManip(entity, manip))
                     }, /*ControlEvent::Respawn =>
                         * server_emitter.emit(ServerEvent::Unmount(entity)), */
diff --git a/voxygen/src/scene/mod.rs b/voxygen/src/scene/mod.rs
index 947fcb3ed3..ae8bd95089 100644
--- a/voxygen/src/scene/mod.rs
+++ b/voxygen/src/scene/mod.rs
@@ -126,6 +126,8 @@ impl Scene {
     /// Set the block position that the player is interacting with
     pub fn set_select_pos(&mut self, pos: Option<Vec3<i32>>) { self.select_pos = pos; }
 
+    pub fn select_pos(&self) -> Option<Vec3<i32>> { self.select_pos }
+
     /// Handle an incoming user input event (e.g.: cursor moved, key pressed,
     /// window closed).
     ///
diff --git a/voxygen/src/session.rs b/voxygen/src/session.rs
index d50203726b..64571ae644 100644
--- a/voxygen/src/session.rs
+++ b/voxygen/src/session.rs
@@ -269,7 +269,8 @@ impl PlayState for SessionState {
                         } else {
                             self.inputs.secondary.set_state(state);
 
-                            if let Some(select_pos) = select_pos {
+                            // Check for select_block that is highlighted
+                            if let Some(select_pos) = self.scene.select_pos() {
                                 client.collect_block(select_pos);
                             }
                         }

From 4153df66ea1aa62708c04f5b5baac9155d56e220 Mon Sep 17 00:00:00 2001
From: Pfauenauge90 <44173739+Pfauenauge90@users.noreply.github.com>
Date: Fri, 20 Mar 2020 20:52:32 +0100
Subject: [PATCH 2/4] stat icons, frame colours

---
 .../voxygen/element/frames/server_frame.vox   |  4 +--
 assets/voxygen/element/frames/window.vox      |  4 +--
 assets/voxygen/element/frames/window_3.vox    |  4 +--
 assets/voxygen/element/frames/window_4.vox    |  4 +--
 assets/voxygen/element/icons/endurance.png    |  3 ++
 assets/voxygen/element/icons/fitness.png      |  3 ++
 assets/voxygen/element/icons/willpower.png    |  3 ++
 voxygen/src/hud/bag.rs                        | 27 +++++++++++++---
 voxygen/src/hud/img_ids.rs                    | 11 ++++---
 voxygen/src/hud/social.rs                     |  7 ++++-
 voxygen/src/hud/spell.rs                      |  3 +-
 voxygen/src/menu/char_selection/ui.rs         | 31 +++++++++----------
 voxygen/src/menu/main/ui.rs                   |  4 +++
 13 files changed, 72 insertions(+), 36 deletions(-)
 create mode 100644 assets/voxygen/element/icons/endurance.png
 create mode 100644 assets/voxygen/element/icons/fitness.png
 create mode 100644 assets/voxygen/element/icons/willpower.png

diff --git a/assets/voxygen/element/frames/server_frame.vox b/assets/voxygen/element/frames/server_frame.vox
index a7b0744a2d..275e25e4b9 100644
--- a/assets/voxygen/element/frames/server_frame.vox
+++ b/assets/voxygen/element/frames/server_frame.vox
@@ -1,3 +1,3 @@
 version https://git-lfs.github.com/spec/v1
-oid sha256:602bbe3f01982feda6c79da82b5000ed151da1e5e59be0f75f19c9bc7b86af66
-size 1624
+oid sha256:d64f764aa7ea65bf21201a7c0574486c7c73425ac94872cd4c5d27845f056029
+size 56107
diff --git a/assets/voxygen/element/frames/window.vox b/assets/voxygen/element/frames/window.vox
index 9a9b5957b4..cc1ec0d0e2 100644
--- a/assets/voxygen/element/frames/window.vox
+++ b/assets/voxygen/element/frames/window.vox
@@ -1,3 +1,3 @@
 version https://git-lfs.github.com/spec/v1
-oid sha256:67e0e42e279400c50f41c2fe8e0a3558885fa852f105c8c1eb38ec4c5eabd54e
-size 153836
+oid sha256:3e00dce196b1454d243126fca7ce2b5ea3c1f23391a4debec2bd774cff6dc22d
+size 208320
diff --git a/assets/voxygen/element/frames/window_3.vox b/assets/voxygen/element/frames/window_3.vox
index af01983c4d..534f4fe15e 100644
--- a/assets/voxygen/element/frames/window_3.vox
+++ b/assets/voxygen/element/frames/window_3.vox
@@ -1,3 +1,3 @@
 version https://git-lfs.github.com/spec/v1
-oid sha256:664d22942cb76f938ea4b7b68efc18dc9e2305c3e667ab7ea5ad256b2b42cea0
-size 241316
+oid sha256:502eb49272f79935ccd309a53c67db691f64736e2aa18814e51f75e86a83e6cd
+size 252692
diff --git a/assets/voxygen/element/frames/window_4.vox b/assets/voxygen/element/frames/window_4.vox
index 6f69e5b24b..5ef43b401e 100644
--- a/assets/voxygen/element/frames/window_4.vox
+++ b/assets/voxygen/element/frames/window_4.vox
@@ -1,3 +1,3 @@
 version https://git-lfs.github.com/spec/v1
-oid sha256:3e679e7e2147fb31fc03f3fcc26bd174e2334d6f8f10bdbba143e0d2b3114e2c
-size 2440
+oid sha256:e1fd9cf331ae3bf6a45de507b5e28072fac2566a65086334dc0de7e1932ba5f8
+size 56924
diff --git a/assets/voxygen/element/icons/endurance.png b/assets/voxygen/element/icons/endurance.png
new file mode 100644
index 0000000000..ede3667e9b
--- /dev/null
+++ b/assets/voxygen/element/icons/endurance.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:6376aa744efcbb3acf5cb5e81ec271522185239c030a4071f6c67f3b15903f33
+size 550
diff --git a/assets/voxygen/element/icons/fitness.png b/assets/voxygen/element/icons/fitness.png
new file mode 100644
index 0000000000..6e68775f5d
--- /dev/null
+++ b/assets/voxygen/element/icons/fitness.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:f40b0799bff94dfd23f2b172e672d480a86a86363ad5ce4c969c97762f63d760
+size 697
diff --git a/assets/voxygen/element/icons/willpower.png b/assets/voxygen/element/icons/willpower.png
new file mode 100644
index 0000000000..7bf2a8328c
--- /dev/null
+++ b/assets/voxygen/element/icons/willpower.png
@@ -0,0 +1,3 @@
+version https://git-lfs.github.com/spec/v1
+oid sha256:cada9e202c460f1b23eb267114fbbe0ea06daefd91010feff6fcb8dc28723b6f
+size 784
diff --git a/voxygen/src/hud/bag.rs b/voxygen/src/hud/bag.rs
index 82db8367f5..902cd1cb50 100644
--- a/voxygen/src/hud/bag.rs
+++ b/voxygen/src/hud/bag.rs
@@ -14,6 +14,7 @@ use conrod_core::{
     widget::{self, Button, Image, Rectangle, Text},
     widget_ids, Color, Colorable, Labelable, Positionable, Sizeable, Widget, WidgetCommon,
 };
+//use const_tweaker::tweak;
 
 widget_ids! {
     pub struct Ids {
@@ -84,6 +85,9 @@ widget_ids! {
         tabard_ico,
         mainhand_ico,
         offhand_ico,
+        end_ico,
+        fit_ico,
+        wp_ico,
     }
 }
 
@@ -144,10 +148,10 @@ pub enum Event {
     Stats,
     Close,
 }
-
-//#[const_tweaker::tweak(min = -10.0, max = 10.0, step = 1.0)]
-//const X: f64 = 10.0;
-
+/*
+#[tweak(min = -100.0, max = 20.0, step = 1.0)]
+const END_X: f64 = 10.0;
+*/
 impl<'a> Widget for Bag<'a> {
     type Event = Option<Event>;
     type State = State;
@@ -559,6 +563,21 @@ impl<'a> Widget for Bag<'a> {
             .font_size(self.fonts.cyri.scale(16))
             .color(TEXT_COLOR)
             .set(state.ids.statnames, ui);
+            Image::new(self.imgs.endurance_ico)
+                .w_h(30.0, 30.0)
+                .top_left_with_margins_on(state.ids.statnames, -10.0, -40.0)
+                .color(Some(UI_HIGHLIGHT_0))
+                .set(state.ids.end_ico, ui);
+            Image::new(self.imgs.fitness_ico)
+                .w_h(30.0, 30.0)
+                .down_from(state.ids.end_ico, 10.0)
+                .color(Some(UI_HIGHLIGHT_0))
+                .set(state.ids.fit_ico, ui);
+            Image::new(self.imgs.willpower_ico)
+                .w_h(30.0, 30.0)
+                .down_from(state.ids.fit_ico, 10.0)
+                .color(Some(UI_HIGHLIGHT_0))
+                .set(state.ids.wp_ico, ui);
 
             Text::new(&format!(
                 "{}\n\n{}\n\n{}",
diff --git a/voxygen/src/hud/img_ids.rs b/voxygen/src/hud/img_ids.rs
index cc4ca58dd4..32d025b463 100644
--- a/voxygen/src/hud/img_ids.rs
+++ b/voxygen/src/hud/img_ids.rs
@@ -187,9 +187,6 @@ image_ids! {
         divider: "voxygen.element.frames.divider_charwindow",
 
         // Close button
-        close_button: "voxygen.element.buttons.x",
-        close_button_hover: "voxygen.element.buttons.x_hover",
-        close_button_press: "voxygen.element.buttons.x_press",
 
 
         // Items
@@ -227,6 +224,9 @@ image_ids! {
         close_btn: "voxygen.element.buttons.close_btn",
         close_btn_hover: "voxygen.element.buttons.close_btn_hover",
         close_btn_press: "voxygen.element.buttons.close_btn_press",
+        close_button: "voxygen.element.buttons.close_btn",
+        close_button_hover: "voxygen.element.buttons.close_btn_hover",
+        close_button_press: "voxygen.element.buttons.close_btn_press",
 
         // Inventory
         coin_ico: "voxygen.element.icons.coin",
@@ -258,8 +258,9 @@ image_ids! {
         necklace_bg: "voxygen.element.icons.necklace",
         mainhand_bg: "voxygen.element.icons.mainhand",
         offhand_bg: "voxygen.element.icons.offhand",
-
-
+        willpower_ico: "voxygen.element.icons.willpower",
+        endurance_ico: "voxygen.element.icons.endurance",
+        fitness_ico: "voxygen.element.icons.fitness",
 
         not_found:"voxygen.element.not_found",
 
diff --git a/voxygen/src/hud/social.rs b/voxygen/src/hud/social.rs
index 4d6588246e..c278ec1963 100644
--- a/voxygen/src/hud/social.rs
+++ b/voxygen/src/hud/social.rs
@@ -1,4 +1,4 @@
-use super::{img_ids::Imgs, Show, TEXT_COLOR, TEXT_COLOR_3};
+use super::{img_ids::Imgs, Show, TEXT_COLOR, TEXT_COLOR_3, UI_MAIN};
 
 use crate::{i18n::VoxygenLocalization, ui::fonts::ConrodVoxygenFonts};
 use client::{self, Client};
@@ -90,6 +90,7 @@ impl<'a> Widget for Social<'a> {
 
         Image::new(self.imgs.window_3)
             .top_left_with_margins_on(ui.window, 200.0, 25.0)
+            .color(Some(UI_MAIN))
             .w_h(103.0 * 4.0, 122.0 * 4.0)
             .set(ids.social_frame, ui);
 
@@ -131,6 +132,7 @@ impl<'a> Widget for Social<'a> {
         Image::new(self.imgs.social_frame)
             .w_h(99.0 * 4.0, 100.0 * 4.0)
             .mid_bottom_of(ids.align)
+            .color(Some(UI_MAIN))
             .set(ids.frame, ui);
 
         // Online Tab
@@ -156,6 +158,7 @@ impl<'a> Widget for Social<'a> {
         .label_font_size(self.fonts.cyri.scale(14))
         .label_font_id(self.fonts.cyri.conrod_id)
         .parent(ids.frame)
+        .color(UI_MAIN)
         .label_color(TEXT_COLOR)
         .set(ids.online_tab, ui)
         .was_clicked()
@@ -222,6 +225,7 @@ impl<'a> Widget for Social<'a> {
         .label_font_size(self.fonts.cyri.scale(14))
         .label_font_id(self.fonts.cyri.conrod_id)
         .parent(ids.frame)
+        .color(UI_MAIN)
         .label_color(TEXT_COLOR_3)
         .set(ids.friends_tab, ui)
         .was_clicked()
@@ -253,6 +257,7 @@ impl<'a> Widget for Social<'a> {
             .parent(ids.frame)
             .label_font_size(self.fonts.cyri.scale(14))
             .label_font_id(self.fonts.cyri.conrod_id)
+            .color(UI_MAIN)
             .label_color(TEXT_COLOR_3)
             .set(ids.faction_tab, ui)
             .was_clicked()
diff --git a/voxygen/src/hud/spell.rs b/voxygen/src/hud/spell.rs
index 552c0c1074..a35d4bf029 100644
--- a/voxygen/src/hud/spell.rs
+++ b/voxygen/src/hud/spell.rs
@@ -1,4 +1,4 @@
-use super::{img_ids::Imgs, Show, TEXT_COLOR};
+use super::{img_ids::Imgs, Show, TEXT_COLOR, UI_MAIN};
 use crate::ui::fonts::ConrodVoxygenFonts;
 use conrod_core::{
     color,
@@ -77,6 +77,7 @@ impl<'a> Widget for Spell<'a> {
         Image::new(self.imgs.window_3)
             .top_left_with_margins_on(ui.window, 200.0, 25.0)
             .w_h(103.0 * 4.0, 122.0 * 4.0)
+            .color(Some(UI_MAIN))
             .set(state.spell_frame, ui);
 
         // X-Button
diff --git a/voxygen/src/menu/char_selection/ui.rs b/voxygen/src/menu/char_selection/ui.rs
index bbeeb524dc..3963298e42 100644
--- a/voxygen/src/menu/char_selection/ui.rs
+++ b/voxygen/src/menu/char_selection/ui.rs
@@ -12,7 +12,7 @@ use crate::{
 };
 use client::Client;
 use common::{
-    assets::{load_expect, load_glob},
+    assets::load_expect,
     comp::{self, humanoid},
 };
 use conrod_core::{
@@ -22,7 +22,7 @@ use conrod_core::{
     widget::{text_box::Event as TextBoxEvent, Button, Image, Rectangle, Scrollbar, Text, TextBox},
     widget_ids, Borderable, Color, Colorable, Labelable, Positionable, Sizeable, UiCell, Widget,
 };
-use std::{borrow::Borrow, sync::Arc};
+use std::sync::Arc;
 
 const STARTER_HAMMER: &str = "common.items.weapons.starter_hammer";
 const STARTER_BOW: &str = "common.items.weapons.starter_bow";
@@ -31,6 +31,10 @@ const STARTER_STAFF: &str = "common.items.weapons.starter_staff";
 const STARTER_SWORD: &str = "common.items.weapons.starter_sword";
 const STARTER_DAGGER: &str = "common.items.weapons.starter_dagger";
 
+// UI Color-Theme
+const UI_MAIN: Color = Color::Rgba(0.61, 0.70, 0.70, 1.0); // Greenish Blue
+//const UI_HIGHLIGHT_0: Color = Color::Rgba(0.79, 1.09, 1.09, 1.0);
+
 widget_ids! {
     struct Ids {
         // Background and logo
@@ -383,6 +387,7 @@ impl CharSelectionUi {
             Image::new(self.imgs.info_frame)
                 .w_h(550.0, 150.0)
                 .middle_of(self.ids.info_bg)
+                .color(Some(UI_MAIN))
                 .set(self.ids.info_frame, ui_widgets);
             Rectangle::fill_with([275.0, 150.0], color::TRANSPARENT)
                 .bottom_left_with_margins_on(self.ids.info_frame, 0.0, 0.0)
@@ -450,6 +455,7 @@ impl CharSelectionUi {
                     .set(self.ids.server_frame_bg, ui_widgets);
                 Image::new(self.imgs.server_frame)
                     .w_h(400.0, 100.0)
+                    .color(Some(UI_MAIN))
                     .middle_of(self.ids.server_frame_bg)
                     .set(self.ids.server_frame, ui_widgets);
 
@@ -460,6 +466,7 @@ impl CharSelectionUi {
                 Image::new(self.imgs.charlist_frame)
                     .w_h(400.0, 800.0)
                     .middle_of(self.ids.charlist_bg)
+                    .color(Some(UI_MAIN))
                     .set(self.ids.charlist_frame, ui_widgets);
                 Rectangle::fill_with([386.0, 783.0], color::TRANSPARENT)
                     .middle_of(self.ids.charlist_bg)
@@ -469,7 +476,7 @@ impl CharSelectionUi {
                 Scrollbar::y_axis(self.ids.charlist_alignment)
                     .thickness(5.0)
                     .auto_hide(true)
-                    .rgba(0.0, 0.0, 0., 0.0)
+                    .color(UI_MAIN)
                     .set(self.ids.selection_scrollbar, ui_widgets);
                 // Server Name
                 Text::new(&client.server_info.name)
@@ -757,6 +764,7 @@ impl CharSelectionUi {
                 Image::new(self.imgs.charlist_frame)
                     .w_h(400.0, ui_widgets.win_h - ui_widgets.win_h * 0.19)
                     .middle_of(self.ids.creation_bg)
+                    .color(Some(UI_MAIN))
                     .set(self.ids.charlist_frame, ui_widgets);
                 Rectangle::fill_with(
                     [386.0, ui_widgets.win_h - ui_widgets.win_h * 0.19],
@@ -864,13 +872,6 @@ impl CharSelectionUi {
                     "",
                     &tooltip_human,
                 )
-                /*.tooltip_image(
-                    if let humanoid::BodyType::Male = body.body_type {
-                        self.imgs.human_m
-                    } else {
-                        self.imgs.human_f
-                    },
-                )*/
                 .set(self.ids.race_1, ui_widgets)
                 .was_clicked()
                 {
@@ -1029,10 +1030,6 @@ impl CharSelectionUi {
                 {
                     *tool = Some(STARTER_HAMMER);
                 }
-                // REMOVE THIS AFTER IMPLEMENTATION
-                /*Rectangle::fill_with([67.0, 67.0], color::rgba(0.0, 0.0, 0.0, 0.8))
-                .middle_of(self.ids.hammer)
-                .set(self.ids.hammer_grey, ui_widgets);*/
 
                 // Bow
                 Image::new(self.imgs.bow)
@@ -1292,7 +1289,7 @@ impl CharSelectionUi {
                         .set(self.ids.beard_slider, ui_widgets);
                 }
                 // Chest
-                let armor = load_glob::<comp::Item>("common.items.armor.chest.*")
+                /*let armor = load_glob::<comp::Item>("common.items.armor.chest.*")
                     .expect("Unable to load armor!");
                 if let Some(new_val) = char_slider(
                     self.ids.beard_slider,
@@ -1313,7 +1310,7 @@ impl CharSelectionUi {
                     ui_widgets,
                 ) {
                     loadout.chest = Some((*armor[new_val]).clone());
-                }
+                }*/
                 // Pants
                 /*let current_pants = body.pants;
                 if let Some(new_val) = char_slider(
@@ -1331,7 +1328,7 @@ impl CharSelectionUi {
                     body.pants = humanoid::ALL_PANTS[new_val];
                 }*/
                 Rectangle::fill_with([20.0, 20.0], color::TRANSPARENT)
-                    .down_from(self.ids.chest_slider, 15.0)
+                    .down_from(self.ids.beard_slider, 15.0)
                     .set(self.ids.space, ui_widgets);
 
                 if to_select {
diff --git a/voxygen/src/menu/main/ui.rs b/voxygen/src/menu/main/ui.rs
index 8732f36ac9..ea427879c8 100644
--- a/voxygen/src/menu/main/ui.rs
+++ b/voxygen/src/menu/main/ui.rs
@@ -20,6 +20,10 @@ use conrod_core::{
 use rand::{seq::SliceRandom, thread_rng};
 use std::time::Duration;
 
+// UI Color-Theme
+/*const UI_MAIN: Color = Color::Rgba(0.61, 0.70, 0.70, 1.0); // Greenish Blue
+const UI_HIGHLIGHT_0: Color = Color::Rgba(0.79, 1.09, 1.09, 1.0);*/
+
 widget_ids! {
     struct Ids {
         // Background and logo

From 0cdb80427d96cb9b1649e531d537cda38f3859da Mon Sep 17 00:00:00 2001
From: Adam Whitehurst <Adam.Whitehurst@live.com>
Date: Fri, 20 Mar 2020 15:03:29 -0700
Subject: [PATCH 3/4] better triple_strike

---
 common/src/comp/ability.rs         |  1 +
 common/src/states/triple_strike.rs | 66 ++++++++++++++++++------------
 common/src/states/utils.rs         |  4 ++
 voxygen/src/scene/figure/mod.rs    |  9 +++-
 4 files changed, 52 insertions(+), 28 deletions(-)

diff --git a/common/src/comp/ability.rs b/common/src/comp/ability.rs
index a7894238a6..a114326870 100644
--- a/common/src/comp/ability.rs
+++ b/common/src/comp/ability.rs
@@ -150,6 +150,7 @@ impl From<&CharacterAbility> for CharacterState {
                     stage: 0,
                     stage_exhausted: false,
                     stage_time_active: Duration::default(),
+                    should_transition: true,
                 })
             },
         }
diff --git a/common/src/states/triple_strike.rs b/common/src/states/triple_strike.rs
index 9bbc7b285b..41414796bb 100644
--- a/common/src/states/triple_strike.rs
+++ b/common/src/states/triple_strike.rs
@@ -10,7 +10,7 @@ use vek::vec::Vec2;
 const STAGE_DURATION: u64 = 600;
 
 const BASE_ACCEL: f32 = 200.0;
-const BASE_SPEED: f32 = 250.0;
+const BASE_SPEED: f32 = 25.0;
 /// ### A sequence of 3 incrementally increasing attacks.
 ///
 /// While holding down the `primary` button, perform a series of 3 attacks,
@@ -27,6 +27,8 @@ pub struct Data {
     pub stage_time_active: Duration,
     /// Whether current stage has exhausted its attack
     pub stage_exhausted: bool,
+    /// Whether to go to next stage
+    pub should_transition: bool,
 }
 
 impl CharacterBehavior for Data {
@@ -41,26 +43,28 @@ impl CharacterBehavior for Data {
             server_events: VecDeque::new(),
         };
 
-        let new_stage_time_active = self
+        let stage_time_active = self
             .stage_time_active
             .checked_add(Duration::from_secs_f32(data.dt.0))
             .unwrap_or(Duration::default());
 
+        let mut should_transition = self.should_transition;
+
         // If player stops holding input,
         if !data.inputs.primary.is_pressed() {
-            // Done
-            update.character = CharacterState::Wielding;
-            // Make sure attack component is removed
-            data.updater.remove::<Attacking>(data.entity);
-            return update;
+            // // Done
+            // update.character = CharacterState::Wielding;
+            // // Make sure attack component is removed
+            // data.updater.remove::<Attacking>(data.entity);
+            // return update;
+
+            should_transition = false;
         }
 
-        handle_move(data, &mut update);
-
         if self.stage < 3 {
-            if new_stage_time_active < Duration::from_millis(STAGE_DURATION / 3) {
+            // Handling movement
+            if stage_time_active < Duration::from_millis(STAGE_DURATION / 3) {
                 // Move player forward while in first third of each stage
-                // Move player according to move_dir
                 if update.vel.0.magnitude_squared() < BASE_SPEED.powf(2.0) {
                     update.vel.0 =
                         update.vel.0 + Vec2::broadcast(data.dt.0) * data.ori.0 * BASE_ACCEL;
@@ -69,14 +73,12 @@ impl CharacterBehavior for Data {
                         update.vel.0 = update.vel.0.normalized() * BASE_SPEED;
                     }
                 };
+            } else {
+                handle_orientation(data, &mut update);
+            }
 
-                update.character = CharacterState::TripleStrike(Data {
-                    base_damage: self.base_damage,
-                    stage: self.stage,
-                    stage_time_active: new_stage_time_active,
-                    stage_exhausted: false,
-                });
-            } else if new_stage_time_active > Duration::from_millis(STAGE_DURATION / 2)
+            // Handling attacking
+            if stage_time_active > Duration::from_millis(STAGE_DURATION / 2)
                 && !self.stage_exhausted
             {
                 // Try to deal damage in second half of stage
@@ -90,22 +92,32 @@ impl CharacterBehavior for Data {
                 update.character = CharacterState::TripleStrike(Data {
                     base_damage: self.base_damage,
                     stage: self.stage,
-                    stage_time_active: new_stage_time_active,
+                    stage_time_active,
                     stage_exhausted: true,
+                    should_transition,
                 });
-            } else if new_stage_time_active > Duration::from_millis(STAGE_DURATION) {
-                update.character = CharacterState::TripleStrike(Data {
-                    base_damage: self.base_damage,
-                    stage: self.stage + 1,
-                    stage_time_active: Duration::default(),
-                    stage_exhausted: false,
-                });
+            } else if stage_time_active > Duration::from_millis(STAGE_DURATION) {
+                if should_transition {
+                    update.character = CharacterState::TripleStrike(Data {
+                        base_damage: self.base_damage,
+                        stage: self.stage + 1,
+                        stage_time_active: Duration::default(),
+                        stage_exhausted: false,
+                        should_transition,
+                    });
+                } else {
+                    // Done
+                    update.character = CharacterState::Wielding;
+                    // Make sure attack component is removed
+                    data.updater.remove::<Attacking>(data.entity);
+                }
             } else {
                 update.character = CharacterState::TripleStrike(Data {
                     base_damage: self.base_damage,
                     stage: self.stage,
-                    stage_time_active: new_stage_time_active,
+                    stage_time_active,
                     stage_exhausted: self.stage_exhausted,
+                    should_transition,
                 });
             }
         } else {
diff --git a/common/src/states/utils.rs b/common/src/states/utils.rs
index 67eac06545..a02d5ad99f 100644
--- a/common/src/states/utils.rs
+++ b/common/src/states/utils.rs
@@ -53,6 +53,10 @@ fn basic_move(data: &JoinData, update: &mut StateUpdate) {
         }
     }
 
+    handle_orientation(data, update);
+}
+
+pub fn handle_orientation(data: &JoinData, update: &mut StateUpdate) {
     // Set direction based on move direction
     let ori_dir = if update.character.is_attack() || update.character.is_block() {
         Vec2::from(data.inputs.look_dir).normalized()
diff --git a/voxygen/src/scene/figure/mod.rs b/voxygen/src/scene/figure/mod.rs
index 49718623cd..4f80df76f6 100644
--- a/voxygen/src/scene/figure/mod.rs
+++ b/voxygen/src/scene/figure/mod.rs
@@ -504,7 +504,14 @@ impl FigureMgr {
                             )
                         },
                         CharacterState::TripleStrike(s) => match s.stage {
-                            0 | 2 => anim::character::AttackAnimation::update_skeleton(
+                            0 => anim::character::AttackAnimation::update_skeleton(
+                                &target_base,
+                                (active_tool_kind, time),
+                                state.state_time,
+                                &mut state_animation_rate,
+                                skeleton_attr,
+                            ),
+                            1 => anim::character::AttackAnimation::update_skeleton(
                                 &target_base,
                                 (active_tool_kind, time),
                                 state.state_time,

From ae175e57f3d1639caccf946ce5b883973de07922 Mon Sep 17 00:00:00 2001
From: Adam Whitehurst <Adam.Whitehurst@live.com>
Date: Fri, 20 Mar 2020 15:20:14 -0700
Subject: [PATCH 4/4] Tweaking consts

---
 common/src/states/triple_strike.rs | 11 +++++++++--
 1 file changed, 9 insertions(+), 2 deletions(-)

diff --git a/common/src/states/triple_strike.rs b/common/src/states/triple_strike.rs
index 41414796bb..05971a2c0f 100644
--- a/common/src/states/triple_strike.rs
+++ b/common/src/states/triple_strike.rs
@@ -9,7 +9,8 @@ use vek::vec::Vec2;
 // In millis
 const STAGE_DURATION: u64 = 600;
 
-const BASE_ACCEL: f32 = 200.0;
+const INITIAL_ACCEL: f32 = 200.0;
+const SECONDARY_ACCEL: f32 = 100.0;
 const BASE_SPEED: f32 = 25.0;
 /// ### A sequence of 3 incrementally increasing attacks.
 ///
@@ -64,10 +65,16 @@ impl CharacterBehavior for Data {
         if self.stage < 3 {
             // Handling movement
             if stage_time_active < Duration::from_millis(STAGE_DURATION / 3) {
+                let adjusted_accel = if self.stage == 0 {
+                    INITIAL_ACCEL
+                } else {
+                    SECONDARY_ACCEL
+                };
+
                 // Move player forward while in first third of each stage
                 if update.vel.0.magnitude_squared() < BASE_SPEED.powf(2.0) {
                     update.vel.0 =
-                        update.vel.0 + Vec2::broadcast(data.dt.0) * data.ori.0 * BASE_ACCEL;
+                        update.vel.0 + Vec2::broadcast(data.dt.0) * data.ori.0 * adjusted_accel;
                     let mag2 = update.vel.0.magnitude_squared();
                     if mag2 > BASE_SPEED.powf(2.0) {
                         update.vel.0 = update.vel.0.normalized() * BASE_SPEED;