display.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124
  1. #include "display.h"
  2. #include <stdlib.h>
  3. #include "pico/stdlib.h"
  4. #include "pico/binary_info.h"
  5. #include "hardware/i2c.h"
  6. #include "pico/util/queue.h"
  7. #include "pico/multicore.h"
  8. #include "pico/util/queue.h"
  9. uint8_t display_buffer[OLED_BUF_LEN];
  10. // ディスプレイコマンドqueue
  11. queue_t command_queue;
  12. void _d_putchar(char c, uint8_t col_x, uint8_t col_y, bool reverse)
  13. {
  14. uint32_t offset = col_x * FONT_WIDTH + OLED_WIDTH * col_y + FONT_WIDTH;
  15. if( c < 0 ) return;
  16. if(col_x > 15 || col_y > 3) return;
  17. // フォントの縦横変換
  18. for(int i = 0; i < 8 ; i++ ) {
  19. volatile uint8_t f;
  20. f = ((font8x8[(int)c][reverse ? 0 : 7] << (reverse ? 7 - i : i)) & 0x80) >> 0;
  21. f |= ((font8x8[(int)c][reverse ? 1 : 6] << (reverse ? 7 - i : i)) & 0x80) >> 1;
  22. f |= ((font8x8[(int)c][reverse ? 2 : 5] << (reverse ? 7 - i : i)) & 0x80) >> 2;
  23. f |= ((font8x8[(int)c][reverse ? 3 : 4] << (reverse ? 7 - i : i)) & 0x80) >> 3;
  24. f |= ((font8x8[(int)c][reverse ? 4 : 3] << (reverse ? 7 - i : i)) & 0x80) >> 4;
  25. f |= ((font8x8[(int)c][reverse ? 5 : 2] << (reverse ? 7 - i : i)) & 0x80) >> 5;
  26. f |= ((font8x8[(int)c][reverse ? 6 : 1] << (reverse ? 7 - i : i)) & 0x80) >> 6;
  27. f |= ((font8x8[(int)c][reverse ? 7 : 0] << (reverse ? 7 - i : i)) & 0x80) >> 7;
  28. display_buffer[offset - i] = f;
  29. }
  30. }
  31. void _d_putstr(char *str, uint8_t col_x, uint8_t col_y, bool reverse)
  32. {
  33. int i = 0;
  34. while(str[i] != '\0') {
  35. _d_putchar(str[i++], col_x++, col_y, reverse);
  36. }
  37. }
  38. void _d_clear(void)
  39. {
  40. fill(display_buffer, 0x00);
  41. }
  42. bool display_putstr(char *str, uint8_t col_x, uint8_t col_y, bool reverse)
  43. {
  44. display_cmd_t cmd;
  45. cmd.command = DISPLAY_CMD_PUTSTR;
  46. cmd.x1 = col_x;
  47. cmd.y1 = col_y;
  48. cmd.x2 = (uint8_t)reverse;
  49. strcpy((char *)cmd.data, str);
  50. return queue_try_add(&command_queue, &cmd);
  51. }
  52. bool display_clear(void)
  53. {
  54. display_cmd_t cmd;
  55. cmd.command = DISPLAY_CMD_CLEAR;
  56. return queue_try_add(&command_queue, &cmd);
  57. }
  58. void display_main(void)
  59. {
  60. // I2C初期化
  61. i2c_init(i2c_default, 800 * 1000);
  62. // I2Cピン初期化
  63. gpio_set_function(PICO_DEFAULT_I2C_SDA_PIN, GPIO_FUNC_I2C);
  64. gpio_set_function(PICO_DEFAULT_I2C_SCL_PIN, GPIO_FUNC_I2C);
  65. gpio_pull_up(PICO_DEFAULT_I2C_SDA_PIN);
  66. gpio_pull_up(PICO_DEFAULT_I2C_SCL_PIN);
  67. // OLED初期化
  68. oled_init();
  69. struct render_area frame_area = {start_col: 0,
  70. end_col : OLED_WIDTH - 1,
  71. start_page : 0,
  72. end_page : OLED_NUM_PAGES - 1,
  73. buflen : 0 };
  74. calc_render_area_buflen(&frame_area);
  75. // ディスプレイクリア
  76. fill(display_buffer, 0x00);
  77. // ディスプレイメインループ
  78. while(true) {
  79. display_cmd_t cmd;
  80. render(display_buffer, &frame_area);
  81. while(! queue_is_empty(&command_queue)) {
  82. queue_remove_blocking(&command_queue, &cmd);
  83. switch(cmd.command) {
  84. case DISPLAY_CMD_CLEAR:
  85. _d_clear();
  86. break;
  87. case DISPLAY_CMD_PUTSTR:
  88. _d_putstr((char *)cmd.data, cmd.x1, cmd.y1, (bool)cmd.x2);
  89. break;
  90. default:
  91. break;
  92. };
  93. }
  94. sleep_us(4*1000);
  95. }
  96. }
  97. void display_init(void)
  98. {
  99. //queue初期化
  100. queue_init(&command_queue, sizeof(display_cmd_t), 8);
  101. // display_main起動
  102. multicore_launch_core1(display_main);
  103. }