1#ifndef ISF15ACP4_BUTTON_UI_HEADER_INCLUDED
2#error "isf15acp4_button_ui.ipp must be included from isf15acp4_button_ui.hpp"
10 : debounce_ms_(debounce_ms), long_press_ms_(long_press_ms) {}
13 stable_ms_ += elapsed_ms;
14 if (stable_ms_ < debounce_ms_) {
19 if (pressed && !is_down_) {
27 if (!pressed && is_down_) {
34 if (pressed && is_down_) {
35 hold_ms_ += elapsed_ms;
36 if (!long_fired_ && hold_ms_ >= long_press_ms_) {
48 gfx.DrawString(4, 2, label !=
nullptr ? label :
"BTN",
colors::White);
50 gfx.DrawRect({2, 14,
static_cast<uint8_t
>(gfx.Width() - 3),
static_cast<uint8_t
>(gfx.Height() - 3)},
56 if (value_0_to_1 < 0.0f) {
59 if (value_0_to_1 > 1.0f) {
63 for (uint8_t r = 0; r <= radius; ++r) {
64 for (
int angle = 180; angle >= 0; --angle) {
65 const float rad =
static_cast<float>(angle) * 3.14159265f / 180.0f;
66 const int x =
static_cast<int>(cx + std::cos(rad) *
static_cast<float>(r));
67 const int y =
static_cast<int>(cy + std::sin(rad) *
static_cast<float>(r));
68 const float t =
static_cast<float>(angle) / 180.0f;
69 const Color565 c = (t <= value_0_to_1) ? fg : bg;
70 if (x >= 0 && y >= 0 && x < gfx.Width() && y < gfx.Height()) {
71 gfx.SetPixel(
static_cast<uint8_t
>(x),
static_cast<uint8_t
>(y), c);
Owns the active graphics backend selected at construction time.
Definition isf15acp4_graphics_context.hpp:42
constexpr Color565 Black
Definition isf15acp4_types.hpp:116
constexpr Color565 White
Definition isf15acp4_types.hpp:117
constexpr Color565 Gray
Definition isf15acp4_types.hpp:125
constexpr Color565 Green
Definition isf15acp4_types.hpp:119
constexpr Color565 Blue
Definition isf15acp4_types.hpp:120
Definition isf15acp4.hpp:19
ButtonEvent
Edge-qualified button events from debounced polling.
Definition isf15acp4_button_ui.hpp:27
uint16_t Color565
16-bit RGB565 color value (R5G6B5).
Definition isf15acp4_types.hpp:50
constexpr Color565 MakeColor565(uint8_t r, uint8_t g, uint8_t b) noexcept
Build an RGB565 color from 8-bit RGB channels.
Definition isf15acp4_types.hpp:110