SymField rewrite (#1444)

* First WIP symfield

* Cleanup widget code

* Rebase and format

* Fix 'to_integer' bug, fix siggen UI.

* to_string_hex fix, unit tests for string code

* Pass instance in callback

* Fix on_change callbacks

* Fix keyfob (not active)

* to_byte_array, coaster tx cleanup

* Add to_byte_array tests

* Changes in ui_numbers

* Fix ui_encoders

* Format

* Fix modemsetup view's symfields

* Remove header

* Format
This commit is contained in:
Kyle Reed 2023-09-12 12:38:19 -07:00 committed by GitHub
parent 70e0f2913f
commit af424aa5f8
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
30 changed files with 607 additions and 371 deletions

View file

@ -751,52 +751,93 @@ class NumberField : public Widget {
const char fill_char;
int32_t value_{0};
bool can_loop{};
int32_t clip_value(int32_t value);
};
/* A widget that allows for character-by-character editing of its value. */
class SymField : public Widget {
public:
std::function<void(SymField&)> on_select{};
std::function<void()> on_change{};
std::function<void(SymField&)> on_change{};
enum symfield_type {
SYMFIELD_OCT,
SYMFIELD_DEC,
SYMFIELD_HEX,
SYMFIELD_ALPHANUM,
SYMFIELD_DEF // User DEFined
enum class Type {
Custom,
Oct,
Dec,
Hex,
Alpha,
};
SymField(Point parent_pos, size_t length, symfield_type type);
/* When "explicit_edits" is true, the field must be selected before it can
* be modified. This means that "slots" are not individually highlighted.
* This makes navigation on Views with SymFields easier because the
* whole control can be skipped over instead of one "slot" at a time. */
SymField(
Point parent_pos,
size_t length,
Type type = Type::Dec,
bool explicit_edits = false);
SymField(
Point parent_pos,
size_t length,
std::string symbol_list,
bool explicit_edits = false);
SymField(const SymField&) = delete;
SymField(SymField&&) = delete;
uint32_t get_sym(const uint32_t index);
void set_sym(const uint32_t index, const uint32_t new_value);
void set_length(const uint32_t new_length);
void set_symbol_list(const uint32_t index, const std::string symbol_list);
uint16_t concatenate_4_octal_u16();
uint32_t value_dec_u32();
uint64_t value_hex_u64();
std::string value_string();
/* Gets the symbol (character) at the specified index. */
char get_symbol(size_t index) const;
/* Sets the symbol (character) at the specified index. */
void set_symbol(size_t index, char symbol);
/* Gets the symbol's offset in the symbol list at the specified index. */
size_t get_offset(size_t index) const;
/* Sets the symbol's offset in the symbol list at the specified index. */
void set_offset(size_t index, size_t offset);
/* Sets the list of allowable symbols for the field. */
void set_symbol_list(std::string symbol_list);
/* Sets the integer value of the field. Only works for OCT/DEC/HEX. */
void set_value(uint64_t value);
/* Sets the string value of the field. Characters that are not in
* the symbol list will be set to the first symbol in the symbol list. */
void set_value(std::string_view value);
/* Gets the integer value of the field for OCT/DEC/HEX. */
uint64_t to_integer() const;
/* Gets the string value of the field. */
const std::string& to_string() const;
void paint(Painter& painter) override;
bool on_key(const KeyEvent key) override;
bool on_encoder(const EncoderEvent delta) override;
bool on_touch(const TouchEvent event) override;
bool on_key(KeyEvent key) override;
bool on_encoder(EncoderEvent delta) override;
bool on_touch(TouchEvent event) override;
private:
std::string symbol_list_[32] = {"01"}; // Failsafe init
uint32_t values_[32] = {0};
uint32_t selected_ = 0;
size_t length_, prev_length_ = 0;
bool erase_prev_ = false;
symfield_type type_{};
/* Ensure the specified symbol is in the symbol list. */
char ensure_valid(char symbol) const;
int32_t clip_value(const uint32_t index, const uint32_t value);
/* Ensures all the symbols are valid. */
void ensure_all_symbols();
/* Sets without validation and fires on_change if necessary. */
void set_symbol_internal(size_t index, char symbol);
/* Gets the radix for the current Type. */
uint8_t get_radix() const;
std::string symbols_{};
std::string value_{};
Type type_ = Type::Custom;
size_t selected_ = 0;
bool editing_ = false;
bool explicit_edits_ = true;
};
class Waveform : public Widget {