U8g2
u8g2适配¶
给u8g2适配串口屏的代码:
// note: u8g2适配参考文档 https://github.com/olikraus/u8g2/wiki/internal#new-displays
extern const u8x8_display_info_t u8x8_sdl_192x64_info;
class BoardPanelGui : public PanelGui {
public:
BOOL init(HwSerialPort *sp)
{
_sp = sp;
return PanelGui::init();
}
uint8_t _buf[192*64/8];
HwSerialPort *_sp;
protected:
BOOL initDisplayBuffer() override
{
u8x8_t *u8x8 = u8g2.getU8x8();
u8x8_SetupDefaults(u8x8);
u8x8->display_cb = u8x8_d_sdl_192x64;
/* setup display info */
u8x8_SetupMemory(u8x8);
u8g2_SetupBuffer(u8g2.getU8g2(), _buf, 8, u8g2_ll_hvline_vertical_top_lsb, &u8g2_cb_r0);
return TRUE;
}
private:
static uint8_t u8x8_d_sdl_192x64(u8x8_t *u8g2, uint8_t msg, uint8_t arg_int, void *arg_ptr)
{
BoardPanelGui* THIS = (BoardPanelGui*) BoardPanelGui::getInstance();
uint8_t x, y, c, w, h;
uint8_t *ptr;
switch(msg) {
case U8X8_MSG_DISPLAY_SETUP_MEMORY:
C_LOG("U8X8_MSG_DISPLAY_SETUP_MEMORY");
u8g2->display_info = &u8x8_sdl_192x64_info;
u8g2->x_offset = u8x8_sdl_192x64_info.default_x_offset;
break;
case U8X8_MSG_DISPLAY_INIT:
// u8x8_d_helper_display_init(u8g2);
break;
case U8X8_MSG_DISPLAY_SET_POWER_SAVE:
break;
case U8X8_MSG_DISPLAY_SET_FLIP_MODE:
break;
case U8X8_MSG_DISPLAY_SET_CONTRAST:
break;
case U8X8_MSG_DISPLAY_DRAW_TILE:
// C_LOG("U8X8_MSG_DISPLAY_DRAW_TILE");
x = ((u8x8_tile_t *)arg_ptr)->x_pos;
x *= 8;
x += u8g2->x_offset;
y = ((u8x8_tile_t *)arg_ptr)->y_pos;
y *= 8;
c = ((u8x8_tile_t *)arg_ptr)->cnt;
w = c*8;
h = 8;
assert(arg_int == 1);
ptr = ((u8x8_tile_t *)arg_ptr)->tile_ptr;
// C_LOG("u8g_sdl_set_multiple_8pixel(%d,%d,%d,ptr)", x, y, c*8);
send_uart2lcd(x, y, w, h, ptr, w*h/8);
break;
default:
return 0;
}
return 1;
}
static void trans_uart2lcd_fmt(UINT8 *buf, const UINT8 *dat, int width)
{
int cnt_byte = 0, cnt_bits = 0;
for (int i = 0; i < 8; i++) {
for (int j = 0; j < width; j++) {
if (dat[j] & BIT(i)) {
BIT_SET(buf[cnt_byte], cnt_bits);
}
else {
BIT_CLR(buf[cnt_byte], cnt_bits);
}
if (++cnt_bits >= 8) {
cnt_bits = 0;
cnt_byte++;
}
}
}
}
static void send_uart2lcd(int x, int y, int w, int h, const uint8_t *dat, int datlen)
{
BoardPanelGui* THIS = (BoardPanelGui*) BoardPanelGui::getInstance();
UINT8 t[2048];
memset(t, 0, sizeof(t));
t[0] = 'l';
t[1] = 'c';
t[2] = 'd';
t[3] = x;
t[4] = y;
t[5] = w;
t[6] = h;
trans_uart2lcd_fmt(&t[7], dat, w);
ssize_t s = 7 + datlen;
int byte_interval_us = 1e6 / THIS->_sp->getBaudrate() * 11;
THIS->_sp->write(t, s);
usleep(byte_interval_us*(s+4));
}
};