Paperd.Ink Library 0.0.5
Library for interacting with Paperd.Ink devices.
Loading...
Searching...
No Matches
GxEPD2_370_TC1.cpp
Go to the documentation of this file.
1// Display Library for SPI e-paper panels from Dalian Good Display and boards from Waveshare.
2// Requires HW SPI and Adafruit_GFX. Caution: the e-paper panels require 3.3V supply AND data lines!
3//
4// based on Demo Example from Good Display, available here: https://www.good-display.com/comp/xcompanyFile/downloadNew.do?appId=24&fid=553&id=374
5// Panel: ED037TC1 : https://www.waveshare.com/product/displays/e-paper/3.7inch-e-paper.htm
6// Controller : SSD1677 : https://www.waveshare.com/w/upload/2/2a/SSD1677_1.0.pdf
7// code extracted for LUT and settings from https://github.com/waveshare/e-Paper
8//
9// Author: Jean-Marc Zingg
10//
11// Version: see library.properties
12//
13// Library: https://github.com/ZinggJM/GxEPD2
14
15#include "GxEPD2_370_TC1.h"
16
17GxEPD2_370_TC1::GxEPD2_370_TC1(int16_t cs, int16_t dc, int16_t rst, int16_t busy) :
18 GxEPD2_EPD(cs, dc, rst, busy, HIGH, 10000000, WIDTH, HEIGHT, panel, hasColor, hasPartialUpdate, hasFastPartialUpdate)
19{
20}
21
22void GxEPD2_370_TC1::clearScreen(uint8_t value)
23{
24 writeScreenBuffer(value);
25 refresh(true);
27}
28
30{
31 if (!_using_partial_mode) _Init_Part();
32 if (_initial_write) _writeScreenBuffer(0x26, value); // set previous
33 _writeScreenBuffer(0x24, value); // set current
34 _initial_write = false; // initial full screen buffer clean done
35}
36
38{
39 if (!_using_partial_mode) _Init_Part();
40 _writeScreenBuffer(0x26, value); // set previous
41 _writeScreenBuffer(0x24, value); // set current
42}
43
44void GxEPD2_370_TC1::_writeScreenBuffer(uint8_t command, uint8_t value)
45{
46 _writeCommand(command);
47 for (uint32_t i = 0; i < uint32_t(WIDTH) * uint32_t(HEIGHT) / 8; i++)
48 {
49 _writeData(value);
50 }
51}
52
53void GxEPD2_370_TC1::writeImage(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
54{
55 _writeImage(0x24, bitmap, x, y, w, h, invert, mirror_y, pgm);
56}
57
58void GxEPD2_370_TC1::writeImageForFullRefresh(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
59{
60 _writeImage(0x26, bitmap, x, y, w, h, invert, mirror_y, pgm);
61 _writeImage(0x24, bitmap, x, y, w, h, invert, mirror_y, pgm);
62}
63
64
65void GxEPD2_370_TC1::writeImageAgain(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
66{
67 _writeImage(0x24, bitmap, x, y, w, h, invert, mirror_y, pgm);
68 _writeImage(0x26, bitmap, x, y, w, h, invert, mirror_y, pgm);
69}
70
71void GxEPD2_370_TC1::_writeImage(uint8_t command, const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
72{
73 if (_initial_write) writeScreenBuffer(); // initial full screen buffer clean
74 delay(1); // yield() to avoid WDT on ESP8266 and ESP32
75 int32_t wb = (w + 7) / 8; // width bytes, bitmaps are padded
76 x -= x % 8; // byte boundary
77 w = wb * 8; // byte boundary
78 int16_t x1 = x < 0 ? 0 : x; // limit
79 int16_t y1 = y < 0 ? 0 : y; // limit
80 int16_t w1 = x + w < int16_t(WIDTH) ? w : int16_t(WIDTH) - x; // limit
81 int16_t h1 = y + h < int16_t(HEIGHT) ? h : int16_t(HEIGHT) - y; // limit
82 int16_t dx = x1 - x;
83 int16_t dy = y1 - y;
84 w1 -= dx;
85 h1 -= dy;
86 if ((w1 <= 0) || (h1 <= 0)) return;
87 if (!_using_partial_mode) _Init_Part();
88 _setPartialRamArea(x1, y1, w1, h1);
89 _writeCommand(command);
90 for (int16_t i = 0; i < h1; i++)
91 {
92 for (int16_t j = 0; j < w1 / 8; j++)
93 {
94 uint8_t data;
95 // use wb, h of bitmap for index!
96 int32_t idx = mirror_y ? j + dx / 8 + ((h - 1 - (i + dy))) * wb : j + dx / 8 + (i + dy) * wb;
97 if (pgm)
98 {
99#if defined(__AVR) || defined(ESP8266) || defined(ESP32)
100 data = pgm_read_byte(&bitmap[idx]);
101#else
102 data = bitmap[idx];
103#endif
104 }
105 else
106 {
107 data = bitmap[idx];
108 }
109 if (invert) data = ~data;
110 _writeData(data);
111 }
112 }
113 delay(1); // yield() to avoid WDT on ESP8266 and ESP32
114}
115
116void GxEPD2_370_TC1::writeImagePart(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
117 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
118{
119 _writeImagePart(0x24, bitmap, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
120}
121
122void GxEPD2_370_TC1::writeImagePartAgain(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
123 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
124{
125 _writeImagePart(0x24, bitmap, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
126 _writeImagePart(0x26, bitmap, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
127}
128
129void GxEPD2_370_TC1::_writeImagePart(uint8_t command, const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
130 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
131{
132 if (_initial_write) writeScreenBuffer(); // initial full screen buffer clean
133 delay(1); // yield() to avoid WDT on ESP8266 and ESP32
134 if ((w_bitmap < 0) || (h_bitmap < 0) || (w < 0) || (h < 0)) return;
135 if ((x_part < 0) || (x_part >= w_bitmap)) return;
136 if ((y_part < 0) || (y_part >= h_bitmap)) return;
137 int32_t wb_bitmap = (w_bitmap + 7) / 8; // width bytes, bitmaps are padded
138 x_part -= x_part % 8; // byte boundary
139 w = w_bitmap - x_part < w ? w_bitmap - x_part : w; // limit
140 h = h_bitmap - y_part < h ? h_bitmap - y_part : h; // limit
141 x -= x % 8; // byte boundary
142 w = 8 * ((w + 7) / 8); // byte boundary, bitmaps are padded
143 int16_t x1 = x < 0 ? 0 : x; // limit
144 int16_t y1 = y < 0 ? 0 : y; // limit
145 int16_t w1 = x + w < int16_t(WIDTH) ? w : int16_t(WIDTH) - x; // limit
146 int16_t h1 = y + h < int16_t(HEIGHT) ? h : int16_t(HEIGHT) - y; // limit
147 int16_t dx = x1 - x;
148 int16_t dy = y1 - y;
149 w1 -= dx;
150 h1 -= dy;
151 if ((w1 <= 0) || (h1 <= 0)) return;
152 if (!_using_partial_mode) _Init_Part();
153 _setPartialRamArea(x1, y1, w1, h1);
154 _writeCommand(command);
155 for (int16_t i = 0; i < h1; i++)
156 {
157 for (int16_t j = 0; j < w1 / 8; j++)
158 {
159 uint8_t data;
160 // use wb_bitmap, h_bitmap of bitmap for index!
161 int32_t idx = mirror_y ? x_part / 8 + j + dx / 8 + ((h_bitmap - 1 - (y_part + i + dy))) * wb_bitmap : x_part / 8 + j + dx / 8 + (y_part + i + dy) * wb_bitmap;
162 if (pgm)
163 {
164#if defined(__AVR) || defined(ESP8266) || defined(ESP32)
165 data = pgm_read_byte(&bitmap[idx]);
166#else
167 data = bitmap[idx];
168#endif
169 }
170 else
171 {
172 data = bitmap[idx];
173 }
174 if (invert) data = ~data;
175 _writeData(data);
176 }
177 }
178 delay(1); // yield() to avoid WDT on ESP8266 and ESP32
179}
180
181void GxEPD2_370_TC1::writeImage(const uint8_t* black, const uint8_t* color, int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
182{
183 if (black)
184 {
185 writeImage(black, x, y, w, h, invert, mirror_y, pgm);
186 }
187}
188
189void GxEPD2_370_TC1::writeImagePart(const uint8_t* black, const uint8_t* color, int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
190 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
191{
192 if (black)
193 {
194 writeImagePart(black, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
195 }
196}
197
198void GxEPD2_370_TC1::writeNative(const uint8_t* data1, const uint8_t* data2, int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
199{
200 if (data1)
201 {
202 writeImage(data1, x, y, w, h, invert, mirror_y, pgm);
203 }
204}
205
206void GxEPD2_370_TC1::drawImage(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
207{
208 writeImage(bitmap, x, y, w, h, invert, mirror_y, pgm);
209 refresh(x, y, w, h);
210 writeImageAgain(bitmap, x, y, w, h, invert, mirror_y, pgm);
211}
212
213void GxEPD2_370_TC1::drawImagePart(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
214 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
215{
216 writeImagePart(bitmap, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
217 refresh(x, y, w, h);
218 writeImagePartAgain(bitmap, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
219}
220
221void GxEPD2_370_TC1::drawImage(const uint8_t* black, const uint8_t* color, int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
222{
223 if (black)
224 {
225 drawImage(black, x, y, w, h, invert, mirror_y, pgm);
226 }
227}
228
229void GxEPD2_370_TC1::drawImagePart(const uint8_t* black, const uint8_t* color, int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap,
230 int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
231{
232 if (black)
233 {
234 drawImagePart(black, x_part, y_part, w_bitmap, h_bitmap, x, y, w, h, invert, mirror_y, pgm);
235 }
236}
237
238void GxEPD2_370_TC1::drawNative(const uint8_t* data1, const uint8_t* data2, int16_t x, int16_t y, int16_t w, int16_t h, bool invert, bool mirror_y, bool pgm)
239{
240 if (data1)
241 {
242 drawImage(data1, x, y, w, h, invert, mirror_y, pgm);
243 }
244}
245
246void GxEPD2_370_TC1::refresh(bool partial_update_mode)
247{
248 if (partial_update_mode) refresh(0, 0, WIDTH, HEIGHT);
249 else
250 {
251 if (_using_partial_mode) _Init_Full();
252 _Update_Full();
253 _initial_refresh = false; // initial full update done
254 }
255}
256
257void GxEPD2_370_TC1::refresh(int16_t x, int16_t y, int16_t w, int16_t h)
258{
259 if (_initial_refresh) return refresh(false); // initial update needs be full update
260 // intersection with screen
261 int16_t w1 = x < 0 ? w + x : w; // reduce
262 int16_t h1 = y < 0 ? h + y : h; // reduce
263 int16_t x1 = x < 0 ? 0 : x; // limit
264 int16_t y1 = y < 0 ? 0 : y; // limit
265 w1 = x1 + w1 < int16_t(WIDTH) ? w1 : int16_t(WIDTH) - x1; // limit
266 h1 = y1 + h1 < int16_t(HEIGHT) ? h1 : int16_t(HEIGHT) - y1; // limit
267 if ((w1 <= 0) || (h1 <= 0)) return;
268 // make x1, w1 multiple of 8
269 w1 += x1 % 8;
270 if (w1 % 8 > 0) w1 += 8 - w1 % 8;
271 x1 -= x1 % 8;
272 if (!_using_partial_mode) _Init_Part();
273 _setPartialRamArea(x1, y1, w1, h1);
274 _Update_Part();
275}
276
278{
279 _PowerOff();
280}
281
283{
284 _PowerOff();
285 if (_rst >= 0)
286 {
287 _writeCommand(0x10); // deep sleep mode
288 _writeData(0x3); // enter deep sleep
289 _hibernating = true;
290 }
291}
292
293void GxEPD2_370_TC1::_setPartialRamArea(uint16_t x, uint16_t y, uint16_t w, uint16_t h)
294{
295 _writeCommand(0x11); // set ram entry mode
296 _writeData(0x03); // x increase, y increase : normal mode
297 _writeCommand(0x44);
298 _writeData(x % 256);
299 _writeData(x / 256);
300 _writeData((x + w - 1) % 256);
301 _writeData((x + w - 1) / 256);
302 _writeCommand(0x45);
303 _writeData(y % 256);
304 _writeData(y / 256);
305 _writeData((y + h - 1) % 256);
306 _writeData((y + h - 1) / 256);
307 _writeCommand(0x4e);
308 _writeData(x % 256);
309 _writeData(x / 256);
310 _writeCommand(0x4f);
311 _writeData(y % 256);
312 _writeData(y / 256);
313}
314
315void GxEPD2_370_TC1::_PowerOn()
316{
317 if (!_power_is_on)
318 {
319 _writeCommand(0x22);
320 _writeData(0xc0);
321 _writeCommand(0x20);
322 _waitWhileBusy("_PowerOn", power_on_time);
323 }
324 _power_is_on = true;
325}
326
327void GxEPD2_370_TC1::_PowerOff()
328{
329 if (_power_is_on)
330 {
331 _writeCommand(0x22);
332 _writeData(0x83);
333 _writeCommand(0x20);
334 _waitWhileBusy("_PowerOff", power_off_time);
335 }
336 _power_is_on = false;
337 _using_partial_mode = false;
338}
339
340void GxEPD2_370_TC1::_InitDisplay()
341{
342 if (_hibernating) _reset();
343 delay(10); // 10ms according to specs
344 _writeCommand(0x12); //SWRESET
345 delay(10); // 10ms according to specs
346 //_writeCommand(0x46); // Auto Write RED RAM **DON'T USE WITH GxEPD2**
347 //_writeData(0xF7);
348 //_waitWhileBusy("_InitDisplay 1", power_on_time);
349 //_writeCommand(0x47); // Auto Write B/W RAM **DON'T USE WITH GxEPD2**
350 //_writeData(0xF7);
351 //_waitWhileBusy("_InitDisplay 2", power_on_time);
352 _writeCommand(0x01); // Driver Output control
353 _writeData(0xDF);
354 _writeData(0x01);
355 _writeData(0x00);
356 _writeCommand(0x03); // Gate Driving voltage Control
357 _writeData(0x00);
358 _writeCommand(0x04); // Source Driving voltage Control
359 _writeData(0x41);
360 _writeData(0xA8);
361 _writeData(0x32);
362 _writeCommand(0x11); // Data Entry mode setting
363 _writeData(0x03);
364 _writeCommand(0x0C); // Booster Soft-start Control
365 _writeData(0xAE);
366 _writeData(0xC7);
367 _writeData(0xC3);
368 _writeData(0xC0);
369 _writeData(0xC0);
370 _writeCommand(0x18); // Temperature Sensor Control
371 _writeData(0x80); // A[7:0] = 80h Internal temperature sensor
372 _writeCommand(0x2C); // Write VCOM register
373 _writeData(0x44); // -1.7
374 _writeCommand(0x37); // Write Register for Display Option, these setting turn on previous function
375 _writeData(0x00);
376 _writeData(0xff);
377 _writeData(0xff);
378 _writeData(0xff);
379 _writeData(0xff);
380 _writeData(0x4f); // enable ping pong for mode 2
381 _writeData(0xff);
382 _writeData(0xff);
383 _writeData(0xff);
384 _writeData(0xff);
385 _setPartialRamArea(0, 0, WIDTH, HEIGHT);
386}
387
388const uint8_t GxEPD2_370_TC1::lut_full[] PROGMEM =
389{
390 0x2A, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //1
391 0x05, 0x2A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //2
392 0x2A, 0x15, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //3
393 0x05, 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //4
394 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //5
395 0x00, 0x02, 0x03, 0x0A, 0x00, 0x02, 0x06, 0x0A, 0x05, 0x00, //6
396 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //7
397 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //8
398 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //9
399 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //10
400 0x22, 0x22, 0x22, 0x22, 0x22
401};
402
403const uint8_t GxEPD2_370_TC1::lut_partial[] PROGMEM =
404{
405 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //1
406 0x01, 0x2A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
407 0x0A, 0x55, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //3
408 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
409 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //5
410 0x00, 0x00, 0x05, 0x05, 0x00, 0x05, 0x03, 0x05, 0x05, 0x00,
411 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //7
412 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
413 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, //9
414 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
415 0x22, 0x22, 0x22, 0x22, 0x22
416};
417
418void GxEPD2_370_TC1::_Init_Full()
419{
420 _InitDisplay();
421 _writeCommand(0x3C); // Border Waveform Control
422 _writeData(0x01); // LUT1, for white
423 _writeCommand(0x32);
424 _writeDataPGM(lut_full, sizeof(lut_full));
425 _PowerOn();
426 _using_partial_mode = false;
427}
428
429void GxEPD2_370_TC1::_Init_Part()
430{
431 _InitDisplay();
432 _writeCommand(0x3C); // Border Waveform Control
433 _writeData(0xC0); // HiZ, [POR], floating
434 _writeCommand(0x32);
435 _writeDataPGM(lut_partial, sizeof(lut_partial));
436 _PowerOn();
437 _using_partial_mode = true;
438}
439
440void GxEPD2_370_TC1::_Update_Full()
441{
442 _writeCommand(0x22);
443 _writeData(0xcf); // enable clock, enable analog, display mode 2, disable analog, disable clock. Waveshare demo
444 //_writeData(0xc4); // enable clock, enable analog, display mode 1
445 //_writeData(0xf4); // enable clock, enable analog, read temp, load LUT, display mode 1
446 _writeCommand(0x20);
447 _waitWhileBusy("_Update_Full", full_refresh_time);
448}
449
450void GxEPD2_370_TC1::_Update_Part()
451{
452 _writeCommand(0x22);
453 _writeData(0xcf); // enable clock, enable analog, display mode 2, disable analog, disable clock. Waveshare demo
454 //_writeData(0xc8); // enable clock, enable analog, display mode 2, ?
455 //_writeData(0xcc); // enable clock, enable analog, display mode 2, ?
456 _writeCommand(0x20);
457 _waitWhileBusy("_Update_Part", partial_refresh_time);
458}
const uint8_t GxEPD2_370_TC1::lut_full[] PROGMEM
static const uint16_t full_refresh_time
void writeScreenBufferAgain(uint8_t value=0xFF)
void writeImageAgain(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
void refresh(bool partial_update_mode=false)
void drawImagePart(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap, int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
static const uint16_t WIDTH
static const uint16_t power_on_time
void writeScreenBuffer(uint8_t value=0xFF)
void writeImagePart(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap, int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
static const uint16_t power_off_time
void writeImagePartAgain(const uint8_t bitmap[], int16_t x_part, int16_t y_part, int16_t w_bitmap, int16_t h_bitmap, int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
static const uint16_t partial_refresh_time
void writeImage(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
static const uint16_t HEIGHT
void writeImageForFullRefresh(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
void clearScreen(uint8_t value=0xFF)
void drawNative(const uint8_t *data1, const uint8_t *data2, int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
void drawImage(const uint8_t bitmap[], int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
GxEPD2_370_TC1(int16_t cs, int16_t dc, int16_t rst, int16_t busy)
void writeNative(const uint8_t *data1, const uint8_t *data2, int16_t x, int16_t y, int16_t w, int16_t h, bool invert=false, bool mirror_y=false, bool pgm=false)
void _writeCommand(uint8_t c)
void _writeData(uint8_t d)
bool _using_partial_mode
Definition GxEPD2_EPD.h:118
void _waitWhileBusy(const char *comment=0, uint16_t busy_time=5000)
bool _power_is_on
Definition GxEPD2_EPD.h:118
bool _initial_refresh
Definition GxEPD2_EPD.h:117
void _reset()
bool _initial_write
Definition GxEPD2_EPD.h:117
int16_t _rst
Definition GxEPD2_EPD.h:112
bool _hibernating
Definition GxEPD2_EPD.h:118
void _writeDataPGM(const uint8_t *data, uint16_t n, int16_t fill_with_zeroes=0)