gpio_reader.c 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. #include "gpio_reader.h"
  2. #include "../gpio_item.h"
  3. #include <gui/elements.h>
  4. #include <furi_hal_resources.h>
  5. struct GpioReader {
  6. View* view;
  7. GpioReaderOkCallback callback;
  8. void* context;
  9. };
  10. typedef struct {
  11. uint8_t pin_idx;
  12. bool pullUp[GPIO_ITEM_COUNT];
  13. } GpioReaderModel;
  14. static bool gpio_reader_process_ok(GpioReader* gpio_reader, InputEvent* event);
  15. static bool gpio_reader_process_left(GpioReader* gpio_reader);
  16. static bool gpio_reader_process_right(GpioReader* gpio_reader);
  17. static void gpio_reader_draw_callback(Canvas* canvas, void* _model) {
  18. GpioReaderModel* model = _model;
  19. canvas_set_font(canvas, FontPrimary);
  20. elements_multiline_text_aligned(canvas, 64, 2, AlignCenter, AlignTop, "GPIO Reader");
  21. canvas_set_font(canvas, FontSecondary);
  22. elements_multiline_text_aligned(
  23. canvas, 64, 16, AlignCenter, AlignTop, "A7 A6 A4 B3 B2 C3 C1 C0");
  24. elements_multiline_text_aligned(canvas, 64, 40, AlignCenter, AlignTop, "Pull Up");
  25. int charOffset = 10;
  26. for(uint8_t i = 0; i < GPIO_ITEM_COUNT; i++) {
  27. bool high = gpio_item_get_pin(i);
  28. if(high) {
  29. elements_multiline_text_aligned(canvas, charOffset, 25, AlignCenter, AlignTop, "1");
  30. } else {
  31. elements_multiline_text_aligned(canvas, charOffset, 25, AlignCenter, AlignTop, "0");
  32. }
  33. if(model->pullUp[i]) {
  34. elements_multiline_text_aligned(canvas, charOffset, 50, AlignCenter, AlignTop, "1");
  35. } else {
  36. elements_multiline_text_aligned(canvas, charOffset, 50, AlignCenter, AlignTop, "0");
  37. }
  38. if(i == model->pin_idx) {
  39. elements_multiline_text_aligned(canvas, charOffset, 53, AlignCenter, AlignTop, "_");
  40. }
  41. charOffset += 16;
  42. }
  43. //~ free(charOffset);
  44. }
  45. static bool gpio_reader_input_callback(InputEvent* event, void* context) {
  46. furi_assert(context);
  47. GpioReader* gpio_reader = context;
  48. bool consumed = false;
  49. if(event->type == InputTypeShort) {
  50. if(event->key == InputKeyRight) {
  51. consumed = gpio_reader_process_right(gpio_reader);
  52. } else if(event->key == InputKeyLeft) {
  53. consumed = gpio_reader_process_left(gpio_reader);
  54. }
  55. } else if(event->key == InputKeyOk) {
  56. consumed = gpio_reader_process_ok(gpio_reader, event);
  57. }
  58. return consumed;
  59. }
  60. static bool gpio_reader_process_left(GpioReader* gpio_reader) {
  61. with_view_model(
  62. gpio_reader->view,
  63. GpioReaderModel * model,
  64. {
  65. if(model->pin_idx) {
  66. model->pin_idx--;
  67. }
  68. },
  69. true);
  70. return true;
  71. }
  72. static bool gpio_reader_process_right(GpioReader* gpio_reader) {
  73. with_view_model(
  74. gpio_reader->view,
  75. GpioReaderModel * model,
  76. {
  77. if(model->pin_idx < GPIO_ITEM_COUNT - 1) {
  78. model->pin_idx++;
  79. }
  80. },
  81. true);
  82. return true;
  83. }
  84. static bool gpio_reader_process_ok(GpioReader* gpio_reader, InputEvent* event) {
  85. bool consumed = false;
  86. with_view_model(
  87. gpio_reader->view,
  88. GpioReaderModel * model,
  89. {
  90. if(event->type == InputTypePress) {
  91. if(model->pullUp[model->pin_idx]) {
  92. gpio_item_configure_pin(model->pin_idx, GpioModeInput, GpioPullDown);
  93. model->pullUp[model->pin_idx] = 0;
  94. consumed = true;
  95. } else {
  96. gpio_item_configure_pin(model->pin_idx, GpioModeInput, GpioPullUp);
  97. model->pullUp[model->pin_idx] = 1;
  98. consumed = true;
  99. }
  100. }
  101. gpio_reader->callback(event->type, gpio_reader->context);
  102. },
  103. true);
  104. return consumed;
  105. }
  106. GpioReader* gpio_reader_alloc() {
  107. GpioReader* gpio_reader = malloc(sizeof(GpioReader));
  108. gpio_reader->view = view_alloc();
  109. view_allocate_model(gpio_reader->view, ViewModelTypeLocking, sizeof(GpioReaderModel));
  110. view_set_context(gpio_reader->view, gpio_reader);
  111. view_set_draw_callback(gpio_reader->view, gpio_reader_draw_callback);
  112. view_set_input_callback(gpio_reader->view, gpio_reader_input_callback);
  113. return gpio_reader;
  114. }
  115. void gpio_reader_free(GpioReader* gpio_reader) {
  116. furi_assert(gpio_reader);
  117. view_free(gpio_reader->view);
  118. free(gpio_reader);
  119. }
  120. View* gpio_reader_get_view(GpioReader* gpio_reader) {
  121. furi_assert(gpio_reader);
  122. return gpio_reader->view;
  123. }
  124. void gpio_reader_set_ok_callback(
  125. GpioReader* gpio_reader,
  126. GpioReaderOkCallback callback,
  127. void* context) {
  128. furi_assert(gpio_reader);
  129. furi_assert(callback);
  130. with_view_model(
  131. gpio_reader->view,
  132. GpioReaderModel * model,
  133. {
  134. UNUSED(model);
  135. gpio_reader->callback = callback;
  136. gpio_reader->context = context;
  137. },
  138. false);
  139. }