mirror of
https://github.com/daveallie/crosspoint-reader.git
synced 2025-12-18 23:27:44 +03:00
First pass at moving to SDK EInkDisplay library
This commit is contained in:
parent
de453fed1d
commit
9e046d7086
@ -9,18 +9,19 @@ inline int max(const int a, const int b) { return a > b ? a : b; }
|
|||||||
template <typename Renderable>
|
template <typename Renderable>
|
||||||
class EpdFontRenderer {
|
class EpdFontRenderer {
|
||||||
Renderable& renderer;
|
Renderable& renderer;
|
||||||
void renderChar(uint32_t cp, int* x, const int* y, uint16_t color, EpdFontStyle style = REGULAR);
|
void renderChar(uint32_t cp, int* x, const int* y, bool pixelState, EpdFontStyle style = REGULAR);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
const EpdFontFamily* fontFamily;
|
const EpdFontFamily* fontFamily;
|
||||||
explicit EpdFontRenderer(const EpdFontFamily* fontFamily, Renderable& renderer)
|
explicit EpdFontRenderer(const EpdFontFamily* fontFamily, Renderable& renderer)
|
||||||
: fontFamily(fontFamily), renderer(renderer) {}
|
: fontFamily(fontFamily), renderer(renderer) {}
|
||||||
~EpdFontRenderer() = default;
|
~EpdFontRenderer() = default;
|
||||||
void renderString(const char* string, int* x, int* y, uint16_t color, EpdFontStyle style = REGULAR);
|
void renderString(const char* string, int* x, int* y, bool pixelState = true, EpdFontStyle style = REGULAR);
|
||||||
|
void drawPixel(int x, int y, bool pixelState);
|
||||||
};
|
};
|
||||||
|
|
||||||
template <typename Renderable>
|
template <typename Renderable>
|
||||||
void EpdFontRenderer<Renderable>::renderString(const char* string, int* x, int* y, const uint16_t color,
|
void EpdFontRenderer<Renderable>::renderString(const char* string, int* x, int* y, const bool pixelState,
|
||||||
const EpdFontStyle style) {
|
const EpdFontStyle style) {
|
||||||
// cannot draw a NULL / empty string
|
// cannot draw a NULL / empty string
|
||||||
if (string == nullptr || *string == '\0') {
|
if (string == nullptr || *string == '\0') {
|
||||||
@ -34,14 +35,48 @@ void EpdFontRenderer<Renderable>::renderString(const char* string, int* x, int*
|
|||||||
|
|
||||||
uint32_t cp;
|
uint32_t cp;
|
||||||
while ((cp = utf8NextCodepoint(reinterpret_cast<const uint8_t**>(&string)))) {
|
while ((cp = utf8NextCodepoint(reinterpret_cast<const uint8_t**>(&string)))) {
|
||||||
renderChar(cp, x, y, color, style);
|
renderChar(cp, x, y, pixelState, style);
|
||||||
}
|
}
|
||||||
|
|
||||||
*y += fontFamily->getData(style)->advanceY;
|
*y += fontFamily->getData(style)->advanceY;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: Consolidate this with EpdRenderer implementation
|
||||||
template <typename Renderable>
|
template <typename Renderable>
|
||||||
void EpdFontRenderer<Renderable>::renderChar(const uint32_t cp, int* x, const int* y, uint16_t color,
|
void EpdFontRenderer<Renderable>::drawPixel(const int x, const int y, const bool pixelState) {
|
||||||
|
uint8_t* frameBuffer = renderer.getFrameBuffer();
|
||||||
|
|
||||||
|
// Early return if no framebuffer is set
|
||||||
|
if (!frameBuffer) {
|
||||||
|
Serial.printf("!!No framebuffer\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Bounds checking (portrait: 480x800)
|
||||||
|
if (x < 0 || x >= EInkDisplay::DISPLAY_HEIGHT || y < 0 || y >= EInkDisplay::DISPLAY_WIDTH) {
|
||||||
|
Serial.printf("!!Outside range (%d, %d)\n", x, y);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Rotate coordinates: portrait (480x800) -> landscape (800x480)
|
||||||
|
// Rotation: 90 degrees clockwise
|
||||||
|
const int16_t rotatedX = y;
|
||||||
|
const int16_t rotatedY = EInkDisplay::DISPLAY_HEIGHT - 1 - x;
|
||||||
|
|
||||||
|
// Calculate byte position and bit position
|
||||||
|
const uint16_t byteIndex = rotatedY * EInkDisplay::DISPLAY_WIDTH_BYTES + (rotatedX / 8);
|
||||||
|
const uint8_t bitPosition = 7 - (rotatedX % 8); // MSB first
|
||||||
|
|
||||||
|
// Set or clear the bit
|
||||||
|
if (pixelState) {
|
||||||
|
frameBuffer[byteIndex] &= ~(1 << bitPosition); // Clear bit
|
||||||
|
} else {
|
||||||
|
frameBuffer[byteIndex] |= (1 << bitPosition); // Set bit
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename Renderable>
|
||||||
|
void EpdFontRenderer<Renderable>::renderChar(const uint32_t cp, int* x, const int* y, const bool pixelState,
|
||||||
const EpdFontStyle style) {
|
const EpdFontStyle style) {
|
||||||
const EpdGlyph* glyph = fontFamily->getGlyph(cp, style);
|
const EpdGlyph* glyph = fontFamily->getGlyph(cp, style);
|
||||||
if (!glyph) {
|
if (!glyph) {
|
||||||
@ -74,7 +109,7 @@ void EpdFontRenderer<Renderable>::renderChar(const uint32_t cp, int* x, const in
|
|||||||
const uint8_t bit_index = 7 - (pixelPosition % 8);
|
const uint8_t bit_index = 7 - (pixelPosition % 8);
|
||||||
|
|
||||||
if ((byte >> bit_index) & 1) {
|
if ((byte >> bit_index) & 1) {
|
||||||
renderer.drawPixel(screenX, screenY, color);
|
drawPixel(screenX, screenY, pixelState);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,11 +21,16 @@ EpdFont ubuntu10Font(&ubuntu_10);
|
|||||||
EpdFont ununtuBold10Font(&ubuntu_bold_10);
|
EpdFont ununtuBold10Font(&ubuntu_bold_10);
|
||||||
EpdFontFamily ubuntuFontFamily(&ubuntu10Font, &ununtuBold10Font);
|
EpdFontFamily ubuntuFontFamily(&ubuntu10Font, &ununtuBold10Font);
|
||||||
|
|
||||||
EpdRenderer::EpdRenderer(XteinkDisplay& display)
|
EpdRenderer::EpdRenderer(EInkDisplay& einkDisplay)
|
||||||
: display(display), marginTop(11), marginBottom(30), marginLeft(10), marginRight(10), lineCompression(0.95f) {
|
: einkDisplay(einkDisplay),
|
||||||
this->regularFontRenderer = new EpdFontRenderer<XteinkDisplay>(&bookerlyFontFamily, display);
|
marginTop(11),
|
||||||
this->smallFontRenderer = new EpdFontRenderer<XteinkDisplay>(&smallFontFamily, display);
|
marginBottom(30),
|
||||||
this->uiFontRenderer = new EpdFontRenderer<XteinkDisplay>(&ubuntuFontFamily, display);
|
marginLeft(10),
|
||||||
|
marginRight(10),
|
||||||
|
lineCompression(0.95f) {
|
||||||
|
this->regularFontRenderer = new EpdFontRenderer<EInkDisplay>(&bookerlyFontFamily, einkDisplay);
|
||||||
|
this->smallFontRenderer = new EpdFontRenderer<EInkDisplay>(&smallFontFamily, einkDisplay);
|
||||||
|
this->uiFontRenderer = new EpdFontRenderer<EInkDisplay>(&ubuntuFontFamily, einkDisplay);
|
||||||
}
|
}
|
||||||
|
|
||||||
EpdRenderer::~EpdRenderer() {
|
EpdRenderer::~EpdRenderer() {
|
||||||
@ -34,6 +39,40 @@ EpdRenderer::~EpdRenderer() {
|
|||||||
delete uiFontRenderer;
|
delete uiFontRenderer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void EpdRenderer::drawPixel(const int x, const int y, const bool state) const {
|
||||||
|
uint8_t* frameBuffer = einkDisplay.getFrameBuffer();
|
||||||
|
|
||||||
|
// Early return if no framebuffer is set
|
||||||
|
if (!frameBuffer) {
|
||||||
|
Serial.printf("!!No framebuffer\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const int adjX = x + marginLeft;
|
||||||
|
const int adjY = y + marginTop;
|
||||||
|
|
||||||
|
// Bounds checking (portrait: 480x800)
|
||||||
|
if (adjX < 0 || adjX >= EInkDisplay::DISPLAY_HEIGHT || adjY < 0 || adjY >= EInkDisplay::DISPLAY_WIDTH) {
|
||||||
|
Serial.printf("!!Outside range (%d, %d)\n", adjX, adjY);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Rotate coordinates: portrait (480x800) -> landscape (800x480)
|
||||||
|
// Rotation: 90 degrees clockwise
|
||||||
|
const int rotatedX = adjY;
|
||||||
|
const int rotatedY = EInkDisplay::DISPLAY_HEIGHT - 1 - adjX;
|
||||||
|
|
||||||
|
// Calculate byte position and bit position
|
||||||
|
const uint16_t byteIndex = rotatedY * EInkDisplay::DISPLAY_WIDTH_BYTES + (rotatedX / 8);
|
||||||
|
const uint8_t bitPosition = 7 - (rotatedX % 8); // MSB first
|
||||||
|
|
||||||
|
if (state) {
|
||||||
|
frameBuffer[byteIndex] &= ~(1 << bitPosition); // Clear bit
|
||||||
|
} else {
|
||||||
|
frameBuffer[byteIndex] |= 1 << bitPosition; // Set bit
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int EpdRenderer::getTextWidth(const char* text, const EpdFontStyle style) const {
|
int EpdRenderer::getTextWidth(const char* text, const EpdFontStyle style) const {
|
||||||
int w = 0, h = 0;
|
int w = 0, h = 0;
|
||||||
|
|
||||||
@ -58,25 +97,25 @@ int EpdRenderer::getSmallTextWidth(const char* text, const EpdFontStyle style) c
|
|||||||
return w;
|
return w;
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawText(const int x, const int y, const char* text, const uint16_t color,
|
void EpdRenderer::drawText(const int x, const int y, const char* text, const bool state,
|
||||||
const EpdFontStyle style) const {
|
const EpdFontStyle style) const {
|
||||||
int ypos = y + getLineHeight() + marginTop;
|
int ypos = y + getLineHeight() + marginTop;
|
||||||
int xpos = x + marginLeft;
|
int xpos = x + marginLeft;
|
||||||
regularFontRenderer->renderString(text, &xpos, &ypos, color > 0 ? GxEPD_BLACK : GxEPD_WHITE, style);
|
regularFontRenderer->renderString(text, &xpos, &ypos, state, style);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawUiText(const int x, const int y, const char* text, const uint16_t color,
|
void EpdRenderer::drawUiText(const int x, const int y, const char* text, const bool state,
|
||||||
const EpdFontStyle style) const {
|
const EpdFontStyle style) const {
|
||||||
int ypos = y + uiFontRenderer->fontFamily->getData(style)->advanceY + marginTop;
|
int ypos = y + uiFontRenderer->fontFamily->getData(style)->advanceY + marginTop;
|
||||||
int xpos = x + marginLeft;
|
int xpos = x + marginLeft;
|
||||||
uiFontRenderer->renderString(text, &xpos, &ypos, color > 0 ? GxEPD_BLACK : GxEPD_WHITE, style);
|
uiFontRenderer->renderString(text, &xpos, &ypos, state, style);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawSmallText(const int x, const int y, const char* text, const uint16_t color,
|
void EpdRenderer::drawSmallText(const int x, const int y, const char* text, const bool state,
|
||||||
const EpdFontStyle style) const {
|
const EpdFontStyle style) const {
|
||||||
int ypos = y + smallFontRenderer->fontFamily->getData(style)->advanceY + marginTop;
|
int ypos = y + smallFontRenderer->fontFamily->getData(style)->advanceY + marginTop;
|
||||||
int xpos = x + marginLeft;
|
int xpos = x + marginLeft;
|
||||||
smallFontRenderer->renderString(text, &xpos, &ypos, color > 0 ? GxEPD_BLACK : GxEPD_WHITE, style);
|
smallFontRenderer->renderString(text, &xpos, &ypos, state, style);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawTextBox(const int x, const int y, const std::string& text, const int width, const int height,
|
void EpdRenderer::drawTextBox(const int x, const int y, const std::string& text, const int width, const int height,
|
||||||
@ -115,51 +154,67 @@ void EpdRenderer::drawTextBox(const int x, const int y, const std::string& text,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawLine(int x1, int y1, int x2, int y2, uint16_t color) const {
|
void EpdRenderer::drawLine(int x1, int y1, int x2, int y2, const bool state) const {
|
||||||
display.drawLine(x1 + marginLeft, y1 + marginTop, x2 + marginLeft, y2 + marginTop,
|
if (x1 == x2) {
|
||||||
color > 0 ? GxEPD_BLACK : GxEPD_WHITE);
|
if (y2 < y1) {
|
||||||
|
std::swap(y1, y2);
|
||||||
|
}
|
||||||
|
for (int y = y1; y <= y2; y++) {
|
||||||
|
drawPixel(x1, y, state);
|
||||||
|
}
|
||||||
|
} else if (y1 == y2) {
|
||||||
|
if (x2 < x1) {
|
||||||
|
std::swap(x1, x2);
|
||||||
|
}
|
||||||
|
for (int x = x1; x <= x2; x++) {
|
||||||
|
drawPixel(x, y1, state);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// TODO: Implement
|
||||||
|
Serial.println("Line drawing not supported");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawRect(const int x, const int y, const int width, const int height, const uint16_t color) const {
|
void EpdRenderer::drawRect(const int x, const int y, const int width, const int height, const bool state) const {
|
||||||
display.drawRect(x + marginLeft, y + marginTop, width, height, color > 0 ? GxEPD_BLACK : GxEPD_WHITE);
|
drawLine(x, y, x + width - 1, y, state);
|
||||||
|
drawLine(x + width - 1, y, x + width - 1, y + height - 1, state);
|
||||||
|
drawLine(x + width - 1, y + height - 1, x, y + height - 1, state);
|
||||||
|
drawLine(x, y, x, y + height - 1, state);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::fillRect(const int x, const int y, const int width, const int height, const uint16_t color) const {
|
void EpdRenderer::fillRect(const int x, const int y, const int width, const int height, const bool state) const {
|
||||||
display.fillRect(x + marginLeft, y + marginTop, width, height, color > 0 ? GxEPD_BLACK : GxEPD_WHITE);
|
for (int fillY = y; fillY < y + height; fillY++) {
|
||||||
|
drawLine(x, fillY, x + width - 1, fillY, state);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawCircle(const int x, const int y, const int radius, const uint16_t color) const {
|
void EpdRenderer::drawImage(const uint8_t bitmap[], const int x, const int y, const int width, const int height) const {
|
||||||
display.drawCircle(x + marginLeft, y + marginTop, radius, color > 0 ? GxEPD_BLACK : GxEPD_WHITE);
|
drawImageNoMargin(bitmap, x + marginLeft, y + marginTop, width, height);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::fillCircle(const int x, const int y, const int radius, const uint16_t color) const {
|
// TODO: Support y-mirror?
|
||||||
display.fillCircle(x + marginLeft, y + marginTop, radius, color > 0 ? GxEPD_BLACK : GxEPD_WHITE);
|
void EpdRenderer::drawImageNoMargin(const uint8_t bitmap[], const int x, const int y, const int width,
|
||||||
|
const int height) const {
|
||||||
|
einkDisplay.drawImage(bitmap, x, y, width, height);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::drawImage(const uint8_t bitmap[], const int x, const int y, const int width, const int height,
|
void EpdRenderer::clearScreen(const uint8_t color) const {
|
||||||
const bool invert, const bool mirrorY) const {
|
|
||||||
drawImageNoMargin(bitmap, x + marginLeft, y + marginTop, width, height, invert, mirrorY);
|
|
||||||
}
|
|
||||||
|
|
||||||
void EpdRenderer::drawImageNoMargin(const uint8_t bitmap[], const int x, const int y, const int width, const int height,
|
|
||||||
const bool invert, const bool mirrorY) const {
|
|
||||||
display.drawImage(bitmap, x, y, width, height, invert, mirrorY);
|
|
||||||
}
|
|
||||||
|
|
||||||
void EpdRenderer::clearScreen(const bool black) const {
|
|
||||||
Serial.println("Clearing screen");
|
Serial.println("Clearing screen");
|
||||||
display.fillScreen(black ? GxEPD_BLACK : GxEPD_WHITE);
|
einkDisplay.clearScreen(color);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EpdRenderer::flushDisplay(const bool partialUpdate) const { display.display(partialUpdate); }
|
void EpdRenderer::flushDisplay(const bool partialUpdate) const {
|
||||||
|
einkDisplay.displayBuffer(partialUpdate ? EInkDisplay::FAST_REFRESH : EInkDisplay::FULL_REFRESH);
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: Support partial window update
|
||||||
void EpdRenderer::flushArea(const int x, const int y, const int width, const int height) const {
|
void EpdRenderer::flushArea(const int x, const int y, const int width, const int height) const {
|
||||||
display.displayWindow(x + marginLeft, y + marginTop, width, height);
|
einkDisplay.displayBuffer();
|
||||||
}
|
}
|
||||||
|
|
||||||
int EpdRenderer::getPageWidth() const { return display.width() - marginLeft - marginRight; }
|
int EpdRenderer::getPageWidth() const { return EInkDisplay::DISPLAY_HEIGHT - marginLeft - marginRight; }
|
||||||
|
|
||||||
int EpdRenderer::getPageHeight() const { return display.height() - marginTop - marginBottom; }
|
int EpdRenderer::getPageHeight() const { return EInkDisplay::DISPLAY_WIDTH - marginTop - marginBottom; }
|
||||||
|
|
||||||
int EpdRenderer::getSpaceWidth() const { return regularFontRenderer->fontFamily->getGlyph(' ', REGULAR)->advanceX; }
|
int EpdRenderer::getSpaceWidth() const { return regularFontRenderer->fontFamily->getGlyph(' ', REGULAR)->advanceX; }
|
||||||
|
|
||||||
|
|||||||
@ -1,16 +1,14 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <GxEPD2_BW.h>
|
#include <EInkDisplay.h>
|
||||||
|
|
||||||
#include <EpdFontRenderer.hpp>
|
#include <EpdFontRenderer.hpp>
|
||||||
|
|
||||||
#define XteinkDisplay GxEPD2_BW<GxEPD2_426_GDEQ0426T82, GxEPD2_426_GDEQ0426T82::HEIGHT>
|
|
||||||
|
|
||||||
class EpdRenderer {
|
class EpdRenderer {
|
||||||
XteinkDisplay& display;
|
EInkDisplay& einkDisplay;
|
||||||
EpdFontRenderer<XteinkDisplay>* regularFontRenderer;
|
EpdFontRenderer<EInkDisplay>* regularFontRenderer;
|
||||||
EpdFontRenderer<XteinkDisplay>* smallFontRenderer;
|
EpdFontRenderer<EInkDisplay>* smallFontRenderer;
|
||||||
EpdFontRenderer<XteinkDisplay>* uiFontRenderer;
|
EpdFontRenderer<EInkDisplay>* uiFontRenderer;
|
||||||
int marginTop;
|
int marginTop;
|
||||||
int marginBottom;
|
int marginBottom;
|
||||||
int marginLeft;
|
int marginLeft;
|
||||||
@ -18,25 +16,23 @@ class EpdRenderer {
|
|||||||
float lineCompression;
|
float lineCompression;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit EpdRenderer(XteinkDisplay& display);
|
explicit EpdRenderer(EInkDisplay& einkDisplay);
|
||||||
~EpdRenderer();
|
~EpdRenderer();
|
||||||
|
void drawPixel(int x, int y, bool state = true) const;
|
||||||
int getTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
int getTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
||||||
int getUiTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
int getUiTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
||||||
int getSmallTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
int getSmallTextWidth(const char* text, EpdFontStyle style = REGULAR) const;
|
||||||
void drawText(int x, int y, const char* text, uint16_t color = 1, EpdFontStyle style = REGULAR) const;
|
void drawText(int x, int y, const char* text, bool state = true, EpdFontStyle style = REGULAR) const;
|
||||||
void drawUiText(int x, int y, const char* text, uint16_t color = 1, EpdFontStyle style = REGULAR) const;
|
void drawUiText(int x, int y, const char* text, bool state = true, EpdFontStyle style = REGULAR) const;
|
||||||
void drawSmallText(int x, int y, const char* text, uint16_t color = 1, EpdFontStyle style = REGULAR) const;
|
void drawSmallText(int x, int y, const char* text, bool state = true, EpdFontStyle style = REGULAR) const;
|
||||||
void drawTextBox(int x, int y, const std::string& text, int width, int height, EpdFontStyle style = REGULAR) const;
|
void drawTextBox(int x, int y, const std::string& text, int width, int height, EpdFontStyle style = REGULAR) const;
|
||||||
void drawLine(int x1, int y1, int x2, int y2, uint16_t color = 1) const;
|
void drawLine(int x1, int y1, int x2, int y2, bool state = true) const;
|
||||||
void drawRect(int x, int y, int width, int height, uint16_t color = 1) const;
|
void drawRect(int x, int y, int width, int height, bool state = true) const;
|
||||||
void fillRect(int x, int y, int width, int height, uint16_t color = 1) const;
|
void fillRect(int x, int y, int width, int height, bool state = true) const;
|
||||||
void drawCircle(int x, int y, int radius, uint16_t color = 1) const;
|
void drawImage(const uint8_t bitmap[], int x, int y, int width, int height) const;
|
||||||
void fillCircle(int x, int y, int radius, uint16_t color = 1) const;
|
void drawImageNoMargin(const uint8_t bitmap[], int x, int y, int width, int height) const;
|
||||||
void drawImage(const uint8_t bitmap[], int x, int y, int width, int height, bool invert = false,
|
|
||||||
bool mirrorY = false) const;
|
void clearScreen(uint8_t color = 0xFF) const;
|
||||||
void drawImageNoMargin(const uint8_t bitmap[], int x, int y, int width, int height, bool invert = false,
|
|
||||||
bool mirrorY = false) const;
|
|
||||||
void clearScreen(bool black = false) const;
|
|
||||||
void flushDisplay(bool partialUpdate = true) const;
|
void flushDisplay(bool partialUpdate = true) const;
|
||||||
void flushArea(int x, int y, int width, int height) const;
|
void flushArea(int x, int y, int width, int height) const;
|
||||||
|
|
||||||
@ -44,6 +40,7 @@ class EpdRenderer {
|
|||||||
int getPageHeight() const;
|
int getPageHeight() const;
|
||||||
int getSpaceWidth() const;
|
int getSpaceWidth() const;
|
||||||
int getLineHeight() const;
|
int getLineHeight() const;
|
||||||
|
|
||||||
// set margins
|
// set margins
|
||||||
void setMarginTop(const int newMarginTop) { this->marginTop = newMarginTop; }
|
void setMarginTop(const int newMarginTop) { this->marginTop = newMarginTop; }
|
||||||
void setMarginBottom(const int newMarginBottom) { this->marginBottom = newMarginBottom; }
|
void setMarginBottom(const int newMarginBottom) { this->marginBottom = newMarginBottom; }
|
||||||
|
|||||||
@ -1 +1 @@
|
|||||||
Subproject commit 8224d278c58e76abf781c2e015f28a09419f27b2
|
Subproject commit fe963b32821dec7fb22abbfa22daa8fc67f286d1
|
||||||
@ -34,7 +34,7 @@ build_flags =
|
|||||||
|
|
||||||
; Libraries
|
; Libraries
|
||||||
lib_deps =
|
lib_deps =
|
||||||
zinggjm/GxEPD2@^1.6.5
|
|
||||||
https://github.com/leethomason/tinyxml2.git#11.0.0
|
https://github.com/leethomason/tinyxml2.git#11.0.0
|
||||||
BatteryMonitor=symlink://open-x4-sdk/libs/hardware/BatteryMonitor
|
BatteryMonitor=symlink://open-x4-sdk/libs/hardware/BatteryMonitor
|
||||||
InputManager=symlink://open-x4-sdk/libs/hardware/InputManager
|
InputManager=symlink://open-x4-sdk/libs/hardware/InputManager
|
||||||
|
EInkDisplay=symlink://open-x4-sdk/libs/display/EInkDisplay
|
||||||
|
|||||||
14
src/main.cpp
14
src/main.cpp
@ -1,7 +1,7 @@
|
|||||||
#include <Arduino.h>
|
#include <Arduino.h>
|
||||||
|
#include <EInkDisplay.h>
|
||||||
#include <EpdRenderer.h>
|
#include <EpdRenderer.h>
|
||||||
#include <Epub.h>
|
#include <Epub.h>
|
||||||
#include <GxEPD2_BW.h>
|
|
||||||
#include <InputManager.h>
|
#include <InputManager.h>
|
||||||
#include <SD.h>
|
#include <SD.h>
|
||||||
#include <SPI.h>
|
#include <SPI.h>
|
||||||
@ -28,10 +28,9 @@
|
|||||||
#define SD_SPI_CS 12
|
#define SD_SPI_CS 12
|
||||||
#define SD_SPI_MISO 7
|
#define SD_SPI_MISO 7
|
||||||
|
|
||||||
GxEPD2_BW<GxEPD2_426_GDEQ0426T82, GxEPD2_426_GDEQ0426T82::HEIGHT> display(GxEPD2_426_GDEQ0426T82(EPD_CS, EPD_DC,
|
EInkDisplay einkDisplay(EPD_SCLK, EPD_MOSI, EPD_CS, EPD_DC, EPD_RST, EPD_BUSY);
|
||||||
EPD_RST, EPD_BUSY));
|
|
||||||
InputManager inputManager;
|
InputManager inputManager;
|
||||||
EpdRenderer renderer(display);
|
EpdRenderer renderer(einkDisplay);
|
||||||
Screen* currentScreen;
|
Screen* currentScreen;
|
||||||
CrossPointState appState;
|
CrossPointState appState;
|
||||||
|
|
||||||
@ -123,7 +122,7 @@ void enterDeepSleep() {
|
|||||||
// Enable Wakeup on LOW (button press)
|
// Enable Wakeup on LOW (button press)
|
||||||
esp_deep_sleep_enable_gpio_wakeup(1ULL << InputManager::POWER_BUTTON_PIN, ESP_GPIO_WAKEUP_GPIO_LOW);
|
esp_deep_sleep_enable_gpio_wakeup(1ULL << InputManager::POWER_BUTTON_PIN, ESP_GPIO_WAKEUP_GPIO_LOW);
|
||||||
|
|
||||||
display.hibernate();
|
einkDisplay.deepSleep();
|
||||||
|
|
||||||
// Enter Deep Sleep
|
// Enter Deep Sleep
|
||||||
esp_deep_sleep_start();
|
esp_deep_sleep_start();
|
||||||
@ -170,10 +169,7 @@ void setup() {
|
|||||||
SPI.begin(EPD_SCLK, SD_SPI_MISO, EPD_MOSI, EPD_CS);
|
SPI.begin(EPD_SCLK, SD_SPI_MISO, EPD_MOSI, EPD_CS);
|
||||||
|
|
||||||
// Initialize display
|
// Initialize display
|
||||||
const SPISettings spi_settings(SPI_FQ, MSBFIRST, SPI_MODE0);
|
einkDisplay.begin();
|
||||||
display.init(115200, true, 2, false, SPI, spi_settings);
|
|
||||||
display.setRotation(3); // 270 degrees
|
|
||||||
display.setTextColor(GxEPD_BLACK);
|
|
||||||
Serial.println("Display initialized");
|
Serial.println("Display initialized");
|
||||||
|
|
||||||
exitScreen();
|
exitScreen();
|
||||||
|
|||||||
@ -11,4 +11,5 @@ void BootLogoScreen::onEnter() {
|
|||||||
renderer.clearScreen();
|
renderer.clearScreen();
|
||||||
// Location for images is from top right in landscape orientation
|
// Location for images is from top right in landscape orientation
|
||||||
renderer.drawImage(CrossLarge, (pageHeight - 128) / 2, (pageWidth - 128) / 2, 128, 128);
|
renderer.drawImage(CrossLarge, (pageHeight - 128) / 2, (pageWidth - 128) / 2, 128, 128);
|
||||||
|
renderer.flushDisplay();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -4,4 +4,9 @@
|
|||||||
|
|
||||||
#include "images/SleepScreenImg.h"
|
#include "images/SleepScreenImg.h"
|
||||||
|
|
||||||
void SleepScreen::onEnter() { renderer.drawImageNoMargin(SleepScreenImg, 0, 0, 800, 480, false, true); }
|
void SleepScreen::onEnter() {
|
||||||
|
renderer.clearScreen();
|
||||||
|
renderer.flushDisplay();
|
||||||
|
renderer.drawImageNoMargin(SleepScreenImg, 0, 0, 800, 480);
|
||||||
|
renderer.flushDisplay();
|
||||||
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user