当前位置: 代码迷 >> 综合 >> 【LuatOS-air551G】6.2 修复:画线导致重启
  详细解决方案

【LuatOS-air551G】6.2 修复:画线导致重启

热度:87   发布时间:2023-12-05 20:27:40.0

前言

解决画线起点和终点的x或y坐标相同时会出现重启问题。

问题

[2022-02-12 15:21:18.439] I/user.74	23	69	23
[2022-02-12 15:21:18.455] Guru Meditation Error: Core  0 panic'ed (Store access fault). Exception was unhandled.[2022-02-12 15:28:01.448] I/user.68	64	64	64
[2022-02-12 15:28:01.448] Guru Meditation Error: Core  0 panic'ed (Store access fault). Exception was unhandled.[2022-02-12 15:30:12.171] I/user.64	64	58	64
[2022-02-12 15:30:12.202] Guru Meditation Error: Core  0 panic'ed (Store access fault). Exception was unhandled.

当使用lcd.drawline()时,如果输入坐标的x或者y相同,会导致重启,这个目前不知道怎么解决

解决

lcd.drawLine(64,64,59,64,0xf000)无法运行
lcd.drawLine(59,64,64,64,0xf000)可以运行
看起来应该是同x或同y的时候只能是从坐标值小的点到大的点。

新增一个函数用于交换两个点的位置就可以了

-- 用于当lcd画线时,横纵坐标相同时从小的点画到大的点
function judge_lcd_xy_same(x1,y1,x2,y2)if x1 == x2 thenif y1>y2 thentemp = y1y1 = y2y2 = tempendendif y1 == y2 thenif x1>x2 thentemp = x1x1 = x2x2 = tempendendreturn x1,y1,x2,y2end

源码

int luat_lcd_draw_line(luat_lcd_conf_t* conf,uint16_t x1, uint16_t y1, uint16_t x2, uint16_t y2,uint32_t color){
    uint16_t t;uint32_t i = 0;int xerr = 0, yerr = 0, delta_x, delta_y, distance;int incx, incy, row, col;if (x1 == x2 || y1 == y2){
    /* fast draw transverse line */luat_lcd_set_address(conf,x1, y1, x2, y2);size_t dots = (x2 - x1 + 1) * (y2 - y1 + 1);//点数量uint8_t* line_buf = (uint8_t*)luat_heap_malloc(dots * 2);for (i = 0; i < dots; i++){
    line_buf[2 * i] = color >> 8;line_buf[2 * i + 1] = color;}luat_gpio_set(conf->pin_dc, Luat_GPIO_HIGH);if (conf->port == LUAT_LCD_SPI_DEVICE){
    luat_spi_device_send((luat_spi_device_t*)(conf->userdata),  (const char*)line_buf, dots * 2);}else{
    luat_spi_send(conf->port,  (const char*)line_buf, dots * 2);}luat_heap_free(line_buf);return 0;}delta_x = x2 - x1;delta_y = y2 - y1;row = x1;col = y1;if (delta_x > 0)incx = 1;else if (delta_x == 0)incx = 0;else{
    incx = -1;delta_x = -delta_x;}if (delta_y > 0)incy = 1;else if (delta_y == 0)incy = 0;else{
    incy = -1;delta_y = -delta_y;}if (delta_x > delta_y)distance = delta_x;else distance = delta_y;for (t = 0; t <= distance + 1; t++){
    luat_lcd_draw_point(conf,row, col,color);xerr += delta_x ;yerr += delta_y ;if (xerr > distance){
    xerr -= distance;row += incx;}if (yerr > distance){
    yerr -= distance;col += incy;}}return 0;
}