#include "dwin_screen.hpp" #include #include namespace iflytop { namespace dwin { DwinScreen g_dwinScreen; } } // namespace iflytop using namespace iflytop; using namespace iflytop::dwin; using namespace std; #define TAG "dwin" DwinScreen& DwinScreen::ins() { return g_dwinScreen; } static void dumphex(uint8_t* data, size_t len) { printf("(%d)", len); for (size_t i = 0; i < len; i++) { printf("%02X ", data[i]); } printf("\n"); } void DwinScreen::init(UART_HandleTypeDef* huart, map& rammanager) { m_huart = huart; // m_dwcfg = dwcfg; m_rammanager_map = rammanager; ZUART::cfg_t cfg; cfg.huart = m_huart; cfg.name = "DwinScreenUart"; cfg.rxbuffersize = RX_CACHE_SIZE; cfg.rxovertime_ms = 2; m_uarthandler.initialize(&cfg); m_uarthandler.startRxIt(); m_uarthandler.setrxcb([this](uint8_t* data, size_t len) { // irq if (txcontext.receipt_ready_flag) { return; } // dumphex(data, len); memcpy(txcontext.receiptcache, data, len); txcontext.receiptlen = len; txcontext.receipt_ready_flag = true; }); // m_rammanager.init(dwcfg.freeRawStartAddr, dwcfg.freeRawEndAddr); // m_textDisplayerManager.init(dwcfg.textDisplayerStartAddr, dwcfg.textDisplayerEndAddr); // m_varIconManager.init(dwcfg.varIconStartAddr, dwcfg.varIconEndAddr); dumpram(); } void DwinScreen::dumpram() { for (auto& each : m_rammanager_map) { ZLOGI(TAG, "%-20s:(%d/%d)", each.first.c_str(), each.second->totalsize() - each.second->remainsize(), each.second->totalsize()); } } uint16_t DwinScreen::alloc_free_ram(uint16_t size) { auto item = m_rammanager_map.find(FREE_RAM_MAP); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(size); } uint16_t DwinScreen::alloc_one_text_displayer() { auto item = m_rammanager_map.find(LEVEL1_TEXT); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_one_var_icon() { auto item = m_rammanager_map.find(LEVEL1_ICON); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_one_level2_text_displayer() { auto item = m_rammanager_map.find(LEVEL2_TEXT); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_one_level2_var_icon() { auto item = m_rammanager_map.find(LEVEL2_ICON); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_one_level0_text_displayer() { auto item = m_rammanager_map.find(LEVEL0_TEXT); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_one_level0_var_icon() { auto item = m_rammanager_map.find(LEVEL0_ICON); ZASSERT(item != m_rammanager_map.end()); return item->second->alloc(); } uint16_t DwinScreen::alloc_from(const char* whichrammanager, uint16_t size) { auto item = m_rammanager_map.find(whichrammanager); if (item == m_rammanager_map.end()) { ZLOGE(TAG, "alloc_from %s failed, not found", whichrammanager); ZASSERT(false); } return item->second->alloc(size); } void DwinScreen::clearrxcache() { // CriticalContext cc; txcontext.receipt_ready_flag = false; txcontext.receiptlen = 0; } void DwinScreen::sendcmd(uint8_t* cmd, size_t len) { // printf("sendcmd:"); // for (size_t i = 0; i < len; i++) { // ZLOGE(TAG,"%02X ", cmd[i]); // } // printf("\n"); m_uarthandler.tx(cmd, len); // m_com.send((char*)cmd, len); } bool DwinScreen::sendcmdblock(int overtime) { clearrxcache(); sendcmd(txcontext.txcache, txcontext.txlen); for (int i = 0; i < overtime; i++) { if (txcontext.receipt_ready_flag) { return true; } else { // zos_delay(1); // HAL_Delay(1); osDelay(1); } } return false; } bool DwinScreen::write_varspace(uint16_t regaddr, uint8_t* data, uint8_t len, int overtime) { /** * @brief * * 2byte 1byte cmd add val * 5AA5 datalen 0x82 2 xbyte * */ txcontext.txcache[0] = 0x5A; txcontext.txcache[1] = 0xA5; txcontext.txcache[2] = 0; // data len txcontext.txcache[3] = 0x82; txcontext.txcache[4] = regaddr >> 8; txcontext.txcache[5] = regaddr & 0xFF; memcpy(&txcontext.txcache[6], data, len); txcontext.txcache[2] = len + 1 + 2; // txcontext.txlen = 6 + len; if (!sendcmdblock(overtime)) { ZLOGE(TAG, "write_varspace failed"); return false; } return true; } bool DwinScreen::read_varspace(uint16_t regaddr, uint8_t* data, uint8_t len, int overtime) { /** * @brief * * 2byte 1byte cmd add val * 5AA5 datalen 0x82 2 xbyte * */ txcontext.txcache[0] = 0x5A; txcontext.txcache[1] = 0xA5; txcontext.txcache[2] = 0; // data len txcontext.txcache[3] = 0x83; txcontext.txcache[4] = regaddr >> 8; txcontext.txcache[5] = regaddr & 0xFF; txcontext.txcache[6] = len / 2; // word len txcontext.txcache[2] = 4; // txcontext.txlen = 7; if (!sendcmdblock(overtime)) { ZLOGE(TAG, "read_varspace failed"); return false; } // ZLOGI(TAG, "read_varspace success %d", txcontext.receiptlen); memcpy(data, &txcontext.receiptcache[7], len); return true; } bool DwinScreen::write_reg16(uint16_t regaddr, uint16_t data, int overtime) { // uint8_t data8[2]; data8[0] = data >> 8; data8[1] = data & 0xFF; return write_reg(regaddr, data8, 2, overtime); } bool DwinScreen::read_reg16(uint16_t regaddr, uint16_t& data, int overtime) { uint8_t data8[2]; bool suc = read_reg(regaddr, data8, 2, overtime); if (!suc) return false; data = data8[0] << 8 | data8[1]; return true; } bool DwinScreen::write_varspace16(uint16_t regaddr, uint16_t data, int overtime) { // uint8_t data8[2]; data8[0] = data >> 8; data8[1] = data & 0xFF; return write_varspace(regaddr, data8, 2, overtime); } bool DwinScreen::write_varspace16_muti(uint16_t regaddr, uint16_t* data, size_t n16, int overtime) { for (size_t i = 0; i < n16; i++) { m_tx_pre_processcache[i * 2] = data[i] >> 8; m_tx_pre_processcache[i * 2 + 1] = data[i] & 0xFF; } return write_varspace(regaddr, m_tx_pre_processcache, n16 * 2, overtime); } bool DwinScreen::read_varspace16_muti(uint16_t regaddr, uint16_t* data, size_t n16, int overtime) { // TODO: CHECK BUFSIZE memset(m_rd_pre_processcache, 0, sizeof(m_rd_pre_processcache)); bool suc = read_varspace(regaddr, m_rd_pre_processcache, n16 * 2, overtime); if (!suc) return false; for (size_t i = 0; i < n16; i++) { data[i] = m_rd_pre_processcache[i * 2] << 8 | m_rd_pre_processcache[i * 2 + 1]; } return true; } bool DwinScreen::read_varspace8_muti(uint16_t regaddr, uint8_t* data, size_t n8, int overtime) { // TODO: CHECK BUFSIZE memset(m_rd_pre_processcache, 0, sizeof(m_rd_pre_processcache)); bool suc = read_varspace(regaddr, m_rd_pre_processcache, n8, overtime); memcpy(data, m_rd_pre_processcache, n8); if (!suc) return false; return true; } bool DwinScreen::read_varspace16(uint16_t regaddr, uint16_t& data, int overtime) { uint8_t data8[2]; bool suc = read_varspace(regaddr, data8, 2, overtime); if (!suc) return false; data = data8[0] << 8 | data8[1]; return true; } bool DwinScreen::write_varspace8(uint16_t regaddr, uint16_t subadd, uint16_t data, int overtime) { uint16_t val = 0; bool suc = read_varspace16(regaddr, val, overtime); if (!suc) return false; if (subadd == 0) { // H val = val & 0x00FF; val = val | ((data << 8) & 0xff00); } else { // L val = val & 0xFF00; val = val | (data & 0xff); } suc = write_varspace16(regaddr, val, overtime); if (!suc) return false; return true; } bool DwinScreen::read_varspace8(uint16_t regaddr, uint16_t subadd, uint16_t& data, int overtime) { uint16_t val = 0; bool suc = read_varspace16(regaddr, val, overtime); if (!suc) return false; if (subadd == 0) { // H data = val >> 8; } else { // L data = val & 0xff; } return true; } bool DwinScreen::write_reg(uint16_t regaddr, uint8_t* data, size_t len, int overtime) { /** * @brief * * 2byte 1byte cmd add val * 5AA5 datalen 0x82 2 xbyte * */ txcontext.txcache[0] = 0x5A; txcontext.txcache[1] = 0xA5; txcontext.txcache[2] = 0; // data len txcontext.txcache[3] = 0x80; txcontext.txcache[4] = regaddr >> 8; txcontext.txcache[5] = regaddr & 0xFF; memcpy(&txcontext.txcache[6], data, len); txcontext.txcache[2] = len + 1 + 2; // txcontext.txlen = 6 + len; if (!sendcmdblock(overtime)) { ZLOGE(TAG, "write_reg failed"); return false; } return true; } bool DwinScreen::read_reg(uint16_t regaddr, uint8_t* data, size_t len, int overtime) { /** * @brief * * 2byte 1byte cmd add val * 5AA5 datalen 0x82 2 xbyte * */ txcontext.txcache[0] = 0x5A; txcontext.txcache[1] = 0xA5; txcontext.txcache[2] = 0; // data len txcontext.txcache[3] = 0x81; txcontext.txcache[4] = regaddr >> 8; txcontext.txcache[5] = regaddr & 0xFF; txcontext.txcache[6] = len / 2; // word len txcontext.txcache[2] = 4; // txcontext.txlen = 7; if (!sendcmdblock(overtime)) { ZLOGE(TAG, "read_varspace failed"); return false; } memcpy(data, &txcontext.receiptcache[7], len); return true; } bool DwinScreen::set_page(uint16_t pageid) { uint16_t data[2] = {0x5A01, pageid}; return write_varspace16_muti(0x84, data, 2, 10); } uint16_t DwinScreen::get_page() { uint16_t page = 0; read_varspace16(0x14, page, 100); return page; } bool DwinScreen::ping() { uint16_t page = 0; bool suc = read_varspace16(0x14, page, 100); return suc; } bool DwinScreen::set_brightness(uint16_t brightness) { // 5A A5 04 82 0082 0A uint8_t data[3] = {0, 0x82, (uint8_t)brightness}; return write_varspace(0x82, data, 3, 10); } bool DwinScreen::set_rtc(uint16_t year, uint16_t month, uint16_t day, uint16_t hour, uint16_t minute, uint16_t second) { year = year - 2000; uint16_t year_month = year << 8 | month; uint16_t day_hour = day << 8 | hour; uint16_t min_second = minute << 8 | second; uint16_t data[4] = {0x5AA5, year_month, day_hour, min_second}; return write_varspace16_muti(0x9C, data, 4, 10); } bool DwinScreen::get_rtc(Date* date) { uint8_t data[8] = {0}; bool suc = read_varspace8_muti(0x10, data, 8, 10); // dumphex(data, 8); if (!suc) return false; date->year = (data[0] & 0xff) + 2000; date->month = data[1]; date->day = data[2]; date->weekdaynum = data[3]; date->hour = data[4]; date->minute = data[5]; date->second = data[6]; // printf("year:%d month:%d day:%d weekdaynum:%d hour:%d minute:%d second:%d\n", // // date->year, date->month, date->day, date->weekdaynum, date->hour, date->minute, date->second); return suc; }