/* Copyright 2020 Jay Greco * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #define I2C_TIMEOUT 100 #define OSC_ENABLED 0x01 #define OSC_DISABLED 0x00 #define HT16K33_DISP_ON 0x01 #define HT16K33_DISP_OFF 0x01 #define HT16K33_BLINK_OFF 0x00 #define HT16K33_BLINK_ON 0x01 #define HT16K33_BLINK_2HZ 0x01 #define HT16K33_BLINK_1HZ 0x02 #define HT16K33_BLINK_HALFHZ 0x03 #define HT16K33_CMD_DISP 0x00 #define HT16K33_CMD_ENABLE 0x20 #define HT16K33_CMD_BLINK 0x80 #define HT16K33_CMD_BRIGHTNESS 0xE0 #define HT16K33_BRIGHTNESS_MIN 0x00 #define HT16K33_BRIGHTNESS_MAX 0x0F void ht16K33_init(uint8_t addr), ht16K33_setBlinkMode(uint8_t addr, uint8_t mode), ht16K33_setBrightness(uint8_t addr, uint8_t brightness), ht16K33_refresh(uint8_t addr, uint16_t *displayBuffer, uint8_t bufLen); #if defined(__AVR__) static i2c_status_t i2c_transmit_P(uint8_t address, const uint8_t *data, uint16_t length, uint16_t timeout) { i2c_status_t status = i2c_start(address | I2C_WRITE, timeout); for (uint16_t i = 0; i < length && status >= 0; i++) { status = i2c_write(pgm_read_byte((const char *)data++), timeout); if (status) break; } i2c_stop(); return status; } #endif void ht16K33_init(uint8_t addr) { i2c_init(); static const uint8_t PROGMEM data[] = {HT16K33_CMD_ENABLE | OSC_ENABLED}; i2c_transmit_P((addr << 1), &data[0], sizeof(data), I2C_TIMEOUT); ht16K33_setBrightness(addr, HT16K33_BRIGHTNESS_MIN); ht16K33_setBlinkMode(addr, HT16K33_BLINK_OFF); } void ht16K33_setBlinkMode(uint8_t addr, uint8_t mode) { if ((mode < HT16K33_BLINK_OFF)|(mode > HT16K33_BLINK_HALFHZ)) { mode = HT16K33_BLINK_OFF; } uint8_t data[] = {(HT16K33_CMD_BLINK | mode << 1 | HT16K33_DISP_ON)}; i2c_transmit((addr << 1), &data[0], sizeof(data), I2C_TIMEOUT); } void ht16K33_setBrightness(uint8_t addr, uint8_t brightness) { uint8_t data[] = {(HT16K33_CMD_BRIGHTNESS | brightness)}; i2c_transmit((addr << 1), &data[0], sizeof(data), I2C_TIMEOUT); } void ht16K33_refresh(uint8_t addr, uint16_t *displayBuffer, uint8_t bufLen) { i2c_start((addr << 1), I2C_TIMEOUT); i2c_write((uint8_t)HT16K33_CMD_DISP, I2C_TIMEOUT); for (int i = 0; i < bufLen; i++) { i2c_write((displayBuffer[i] & 0xFF), I2C_TIMEOUT); i2c_write((displayBuffer[i] >> 8), I2C_TIMEOUT); } i2c_stop(); }