firmware+controller: Add round start state
This commit is contained in:
parent
1caf43c6de
commit
9543851867
@ -2,7 +2,7 @@
|
||||
import logging
|
||||
|
||||
import valconomy
|
||||
from valconomy import ValorantPlayerInfo, RiotPlayerInfo
|
||||
from valconomy import ValorantPlayerInfo, RiotPlayerInfo, EconomyDecision
|
||||
|
||||
def main():
|
||||
logging.basicConfig(
|
||||
@ -26,6 +26,18 @@ def main():
|
||||
h.game_start(None)
|
||||
h.game_over(None, False)
|
||||
h.game_over(None, True)
|
||||
h.round_start(
|
||||
RiotPlayerInfo.dummy(valorant=ValorantPlayerInfo(score=3, enemy_score=7)),
|
||||
won=True, economy=EconomyDecision.SAVE)
|
||||
h.round_start(
|
||||
RiotPlayerInfo.dummy(valorant=ValorantPlayerInfo(score=10, enemy_score=2)),
|
||||
won=False, economy=EconomyDecision.BUY)
|
||||
h.round_start(
|
||||
RiotPlayerInfo.dummy(valorant=ValorantPlayerInfo(score=10, enemy_score=2)),
|
||||
won=None, economy=EconomyDecision.MATCH_TEAM)
|
||||
h.round_start(
|
||||
RiotPlayerInfo.dummy(valorant=ValorantPlayerInfo(score=2, enemy_score=0)),
|
||||
won=True, economy=EconomyDecision.BONUS)
|
||||
|
||||
h.service()
|
||||
finally:
|
||||
|
@ -340,8 +340,24 @@ class HIDValconomyHandler(ValconomyHandler):
|
||||
def game_start(self, info: RiotPlayerInfo):
|
||||
self._enq(7)
|
||||
|
||||
def round_start(self, info: RiotPlayerInfo, won: bool, economy: EconomyDecision):
|
||||
match won:
|
||||
case False:
|
||||
won_val = 0
|
||||
case True:
|
||||
won_val = 1
|
||||
case None:
|
||||
won_val = 2
|
||||
|
||||
self._enq(
|
||||
8,
|
||||
info.valorant.score, info.valorant.enemy_score,
|
||||
won_val,
|
||||
economy.value,
|
||||
fmt='BBBB')
|
||||
|
||||
def game_over(self, info: RiotPlayerInfo, won: bool):
|
||||
self._enq(8, 1 if won else 0, fmt='B')
|
||||
self._enq(9, 1 if won else 0, fmt='B')
|
||||
|
||||
class GameState(Enum):
|
||||
NONE = 0
|
||||
|
@ -2,7 +2,6 @@
|
||||
|
||||
#include "ui.h"
|
||||
|
||||
static const char* M_VAL_TIME = "VAL TIME?";
|
||||
const char *val_ext_gamemodes[] = {
|
||||
"TDM",
|
||||
"DEATHMATCH",
|
||||
@ -12,10 +11,25 @@ const char *val_ext_gamemodes[] = {
|
||||
"GAME",
|
||||
};
|
||||
|
||||
static const char* M_VAL_TIME = "VAL TIME?";
|
||||
static const char *val_eco_titles[] = {
|
||||
"BUY",
|
||||
"SAVE",
|
||||
"BONUS",
|
||||
"MATCH TEAM",
|
||||
};
|
||||
static const char *val_eco_subtitles[] = {
|
||||
"SPEND ALL YOUR MONEY!",
|
||||
"MAKE SURE YOU CAN BUY NEXT ROUND!",
|
||||
"KEEP YOUR GUN FROM LAST ROUND!",
|
||||
"FOLLOW THE TEAM ECONOMY",
|
||||
};
|
||||
|
||||
static const lv_font_t *font_normal = &lv_font_montserrat_24;
|
||||
|
||||
static lv_color_t color_primary, color_secondary;
|
||||
static lv_color_t color_text_hero, color_text_subtitle, color_text_victory;
|
||||
static lv_color_t color_text_hero, color_text_subtitle;
|
||||
static lv_color_t color_text_won, color_text_lost;
|
||||
|
||||
static lv_style_t s_hero, s_subtitle;
|
||||
|
||||
@ -509,6 +523,105 @@ void val_ui_game_start() {
|
||||
state_ready = true;
|
||||
}
|
||||
|
||||
static void anim_text_color_mix_hero_won(void *var, int32_t v) {
|
||||
lv_obj_set_style_text_color(
|
||||
var, lv_color_mix(color_text_hero, color_text_won, v), 0);
|
||||
}
|
||||
static void anim_text_color_mix_hero_lost(void *var, int32_t v) {
|
||||
lv_obj_set_style_text_color(
|
||||
var, lv_color_mix(color_text_hero, color_text_lost, v), 0);
|
||||
}
|
||||
void val_ui_round_start(uint8_t score, uint8_t score_enemy, val_won_t won, val_eco_decision_t eco) {
|
||||
assert(won <= ROUND_NONE && eco <= ECO_MATCH_TEAM);
|
||||
setup_next_state();
|
||||
|
||||
// Widgets
|
||||
lv_obj_t *l_score = lv_label_create(o_active);
|
||||
lv_obj_add_style(l_score, &s_hero, 0);
|
||||
lv_obj_center(l_score);
|
||||
lv_label_set_text_fmt(l_score, "%hhu-%hhu", score, score_enemy);
|
||||
|
||||
lv_obj_t *l_eco = lv_label_create(o_active);
|
||||
lv_obj_add_style(l_eco, &s_hero, 0);
|
||||
lv_obj_center(l_eco);
|
||||
lv_label_set_text_static(l_eco, val_eco_titles[eco]);
|
||||
|
||||
lv_obj_t *l_advice = lv_label_create(o_active);
|
||||
lv_obj_add_style(l_advice, &s_subtitle, 0);
|
||||
lv_obj_center(l_advice);
|
||||
lv_label_set_text_static(l_advice, val_eco_subtitles[eco]);
|
||||
|
||||
lv_obj_update_layout(o_active);
|
||||
lv_obj_set_y(
|
||||
l_score,
|
||||
-(lv_obj_get_height(l_score) / 2) - 20);
|
||||
lv_obj_set_y(
|
||||
l_eco,
|
||||
lv_obj_get_height(l_eco) / 2);
|
||||
|
||||
// Animations
|
||||
// Score and eco fade in
|
||||
lv_anim_t a_fade_in;
|
||||
lv_anim_init(&a_fade_in);
|
||||
lv_anim_set_values(&a_fade_in, 0, 255);
|
||||
lv_anim_set_exec_cb(&a_fade_in, anim_opa_cb);
|
||||
lv_anim_set_path_cb(&a_fade_in, lv_anim_path_ease_in);
|
||||
lv_anim_set_duration(&a_fade_in, 750);
|
||||
|
||||
lv_anim_set_var(&a_fade_in, l_score);
|
||||
lv_anim_timeline_add(at_active, 0, &a_fade_in);
|
||||
|
||||
lv_anim_set_var(&a_fade_in, l_eco);
|
||||
lv_anim_timeline_add(at_active, 0, &a_fade_in);
|
||||
|
||||
// Advice slide up
|
||||
lv_anim_t a_advice;
|
||||
lv_anim_init(&a_advice);
|
||||
lv_anim_set_var(&a_advice, l_advice);
|
||||
lv_anim_set_values(
|
||||
&a_advice,
|
||||
(lv_obj_get_height(o_container) + lv_obj_get_height(l_advice)) / 2,
|
||||
lv_obj_get_height(l_eco) + (lv_obj_get_height(l_advice) / 2) + 5);
|
||||
lv_anim_set_exec_cb(&a_advice, anim_y_cb);
|
||||
lv_anim_set_path_cb(&a_advice, lv_anim_path_ease_out);
|
||||
lv_anim_set_duration(&a_advice, 750);
|
||||
|
||||
if (won != ROUND_NONE) {
|
||||
// Score colour
|
||||
lv_anim_t a_score;
|
||||
lv_anim_init(&a_score);
|
||||
lv_anim_set_var(&a_score, l_score);
|
||||
lv_anim_set_path_cb(&a_score, lv_anim_path_ease_in);
|
||||
lv_anim_set_exec_cb(
|
||||
&a_score,
|
||||
won == ROUND_WON ? anim_text_color_mix_hero_won : anim_text_color_mix_hero_lost);
|
||||
lv_anim_set_duration(&a_score, 2000);
|
||||
lv_anim_set_values(&a_score, 0, 255);
|
||||
lv_anim_set_completed_cb(&a_score, anim_state_ready_cb);
|
||||
lv_anim_timeline_add(at_active, 0, &a_score);
|
||||
} else {
|
||||
lv_anim_set_completed_cb(&a_advice, anim_state_ready_cb);
|
||||
}
|
||||
lv_anim_timeline_add(at_active, 0, &a_advice);
|
||||
|
||||
// Eco flash
|
||||
lv_anim_t a_eco;
|
||||
lv_anim_init(&a_eco);
|
||||
lv_anim_set_early_apply(&a_eco, false);
|
||||
lv_anim_set_var(&a_eco, l_eco);
|
||||
lv_anim_set_path_cb(&a_eco, lv_anim_path_linear);
|
||||
lv_anim_set_duration(&a_eco, 1000);
|
||||
lv_anim_set_exec_cb(&a_eco, anim_text_color_mix_hero_sub);
|
||||
|
||||
lv_anim_set_values(&a_eco, 255, 0);
|
||||
lv_anim_timeline_add(at_active_rep, 0, &a_eco);
|
||||
|
||||
lv_anim_set_values(&a_eco, 0, 255);
|
||||
lv_anim_timeline_add(at_active_rep, 1000, &a_eco);
|
||||
|
||||
lv_anim_timeline_start(at_active);
|
||||
}
|
||||
|
||||
void val_ui_game_over(bool won) {
|
||||
setup_next_state();
|
||||
|
||||
@ -517,7 +630,7 @@ void val_ui_game_over(bool won) {
|
||||
lv_obj_add_style(l_main, &s_hero, 0);
|
||||
lv_obj_center(l_main);
|
||||
lv_label_set_text_static(l_main, won ? "VICTORY" : "DEFEAT");
|
||||
if (won) lv_obj_set_style_text_color(l_main, color_text_victory, 0);
|
||||
lv_obj_set_style_text_color(l_main, won ? color_text_won : color_text_lost, 0);
|
||||
|
||||
lv_obj_t *l_subtitle = lv_label_create(o_active);
|
||||
lv_obj_add_style(l_subtitle, &s_subtitle, 0);
|
||||
@ -553,7 +666,7 @@ void val_ui_game_over(bool won) {
|
||||
lv_anim_timeline_add(at_active, 0, &a_fly);
|
||||
|
||||
|
||||
// Subtitle from bottom right
|
||||
// Subtitle from bottom-right
|
||||
// Y
|
||||
lv_anim_set_var(&a_fly, l_subtitle);
|
||||
lv_anim_set_exec_cb(&a_fly, anim_y_cb);
|
||||
@ -595,7 +708,8 @@ void val_lvgl_ui(lv_display_t *disp) {
|
||||
|
||||
color_text_hero = lv_palette_lighten(LV_PALETTE_GREY, 2);
|
||||
color_text_subtitle = lv_palette_darken(LV_PALETTE_GREY, 1);
|
||||
color_text_victory = lv_palette_lighten(LV_PALETTE_GREEN, 1);
|
||||
color_text_won = lv_palette_lighten(LV_PALETTE_GREEN, 1);
|
||||
color_text_lost = lv_palette_darken(LV_PALETTE_RED, 4);
|
||||
|
||||
// init default theme
|
||||
lv_theme_default_init(
|
||||
|
@ -5,6 +5,18 @@
|
||||
extern const char *val_ext_gamemodes[];
|
||||
#define VAL_EXT_GAMEMODES_SIZE 6
|
||||
|
||||
typedef enum val_eco_decision {
|
||||
ECO_BUY,
|
||||
ECO_SAVE,
|
||||
ECO_BONUS,
|
||||
ECO_MATCH_TEAM,
|
||||
} val_eco_decision_t;
|
||||
typedef enum val_won {
|
||||
ROUND_LOST,
|
||||
ROUND_WON,
|
||||
ROUND_NONE,
|
||||
} val_won_t;
|
||||
|
||||
LV_FONT_DECLARE(lv_font_tungsten_40)
|
||||
LV_FONT_DECLARE(lv_font_tungsten_180)
|
||||
|
||||
@ -23,6 +35,7 @@ void val_ui_match_found(bool is_premier);
|
||||
void val_ui_pregame(bool is_split);
|
||||
void val_ui_game_generic(const char *gamemode);
|
||||
void val_ui_game_start();
|
||||
void val_ui_round_start(uint8_t score, uint8_t score_enemy, val_won_t won, val_eco_decision_t eco);
|
||||
void val_ui_game_over(bool won);
|
||||
|
||||
void val_lvgl_ui(lv_display_t *disp);
|
||||
|
@ -154,6 +154,13 @@ void tud_hid_set_report_cb(uint8_t instance, uint8_t report_id, hid_report_type_
|
||||
case ST_GAME_START:
|
||||
val_ui_game_start();
|
||||
break;
|
||||
case ST_ROUND_START:
|
||||
if (bufsize < 5 || buf[3] > ROUND_NONE || buf[4] > ECO_MATCH_TEAM) {
|
||||
ESP_LOGE(TAG, "Invalid ST_ROUND_START command");
|
||||
goto ret;
|
||||
}
|
||||
val_ui_round_start(buf[1], buf[2], buf[3], buf[4]);
|
||||
break;
|
||||
case ST_GAME_OVER:
|
||||
if (bufsize < 2) {
|
||||
ESP_LOGE(TAG, "Invalid ST_GAME_OVER command");
|
||||
|
@ -14,6 +14,7 @@ typedef enum val_state {
|
||||
ST_PREGAME,
|
||||
ST_GAME_GENERIC,
|
||||
ST_GAME_START,
|
||||
ST_ROUND_START,
|
||||
ST_GAME_OVER,
|
||||
} val_state_t;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user