Skip to content
Snippets Groups Projects
Commit daa91a67 authored by Daniel Eichhorn's avatar Daniel Eichhorn Committed by GitHub
Browse files

Merge pull request #67 from squix78/fix-rect-drawing-differences

Improving rect drawing 
parents a2bc9762 dbafddfb
No related branches found
No related tags found
No related merge requests found
...@@ -125,13 +125,13 @@ void OLEDDisplay::drawLine(int16_t x0, int16_t y0, int16_t x1, int16_t y1) { ...@@ -125,13 +125,13 @@ void OLEDDisplay::drawLine(int16_t x0, int16_t y0, int16_t x1, int16_t y1) {
void OLEDDisplay::drawRect(int16_t x, int16_t y, int16_t width, int16_t height) { void OLEDDisplay::drawRect(int16_t x, int16_t y, int16_t width, int16_t height) {
drawHorizontalLine(x, y, width); drawHorizontalLine(x, y, width);
drawVerticalLine(x, y, height); drawVerticalLine(x, y, height);
drawVerticalLine(x + width, y, height); drawVerticalLine(x + width - 1, y, height);
drawHorizontalLine(x, y + height, width); drawHorizontalLine(x, y + height - 1, width);
} }
void OLEDDisplay::fillRect(int16_t xMove, int16_t yMove, int16_t width, int16_t height) { void OLEDDisplay::fillRect(int16_t xMove, int16_t yMove, int16_t width, int16_t height) {
for (int16_t i = yMove; i < yMove + height; i++) { for (int16_t x = xMove; x < xMove + width; x++) {
drawHorizontalLine(xMove, i, width); drawVerticalLine(x, yMove, height);
} }
} }
...@@ -161,6 +161,46 @@ void OLEDDisplay::drawCircle(int16_t x0, int16_t y0, int16_t radius) { ...@@ -161,6 +161,46 @@ void OLEDDisplay::drawCircle(int16_t x0, int16_t y0, int16_t radius) {
setPixel(x0, y0 - radius); setPixel(x0, y0 - radius);
} }
void OLEDDisplay::drawCircleQuads(int16_t x0, int16_t y0, int16_t radius, uint8_t quads) {
int16_t x = 0, y = radius;
int16_t dp = 1 - radius;
while (x < y) {
if (dp < 0)
dp = dp + 2 * (++x) + 3;
else
dp = dp + 2 * (++x) - 2 * (--y) + 5;
if (quads & 0x1) {
setPixel(x0 + x, y0 - y);
setPixel(x0 + y, y0 - x);
}
if (quads & 0x2) {
setPixel(x0 - y, y0 - x);
setPixel(x0 - x, y0 - y);
}
if (quads & 0x4) {
setPixel(x0 - y, y0 + x);
setPixel(x0 - x, y0 + y);
}
if (quads & 0x8) {
setPixel(x0 + x, y0 + y);
setPixel(x0 + y, y0 + x);
}
}
if (quads & 0x1 && quads & 0x8) {
setPixel(x0 + radius, y0);
}
if (quads & 0x4 && quads & 0x8) {
setPixel(x0, y0 + radius);
}
if (quads & 0x2 && quads & 0x4) {
setPixel(x0 - radius, y0);
}
if (quads & 0x1 && quads & 0x2) {
setPixel(x0, y0 - radius);
}
}
void OLEDDisplay::fillCircle(int16_t x0, int16_t y0, int16_t radius) { void OLEDDisplay::fillCircle(int16_t x0, int16_t y0, int16_t radius) {
int16_t x = 0, y = radius; int16_t x = 0, y = radius;
int16_t dp = 1 - radius; int16_t dp = 1 - radius;
...@@ -215,7 +255,7 @@ void OLEDDisplay::drawHorizontalLine(int16_t x, int16_t y, int16_t length) { ...@@ -215,7 +255,7 @@ void OLEDDisplay::drawHorizontalLine(int16_t x, int16_t y, int16_t length) {
} }
void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) { void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) {
if (x < 0 || x > DISPLAY_WIDTH) return; if (x < 0 || x >= DISPLAY_WIDTH) return;
if (y < 0) { if (y < 0) {
length += y; length += y;
...@@ -245,9 +285,9 @@ void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) { ...@@ -245,9 +285,9 @@ void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) {
} }
switch (color) { switch (color) {
case WHITE: *bufferPtr |= drawBit; break; case WHITE: *bufferPtr |= drawBit; break;
case BLACK: *bufferPtr &= drawBit; break; case BLACK: *bufferPtr &= ~drawBit; break;
case INVERSE: *bufferPtr ^= drawBit; break; case INVERSE: *bufferPtr ^= drawBit; break;
} }
if (length < yOffset) return; if (length < yOffset) return;
...@@ -280,28 +320,31 @@ void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) { ...@@ -280,28 +320,31 @@ void OLEDDisplay::drawVerticalLine(int16_t x, int16_t y, int16_t length) {
if (length > 0) { if (length > 0) {
drawBit = (1 << (length & 7)) - 1; drawBit = (1 << (length & 7)) - 1;
switch (color) { switch (color) {
case WHITE: *bufferPtr |= drawBit; break; case WHITE: *bufferPtr |= drawBit; break;
case BLACK: *bufferPtr &= drawBit; break; case BLACK: *bufferPtr &= ~drawBit; break;
case INVERSE: *bufferPtr ^= drawBit; break; case INVERSE: *bufferPtr ^= drawBit; break;
} }
} }
} }
void OLEDDisplay::drawProgressBar(uint16_t x, uint16_t y, uint16_t width, uint16_t height, uint8_t progress) { void OLEDDisplay::drawProgressBar(uint16_t x, uint16_t y, uint16_t width, uint16_t height, uint8_t progress) {
uint16_t radius = height / 2; uint16_t radius = height / 2;
uint16_t innerRadius = radius - 3; uint16_t xRadius = x + radius;
setColor(WHITE); uint16_t yRadius = y + radius;
drawCircle(x + radius, y + radius, radius); uint16_t doubleRadius = 2 * radius;
drawRect(x+radius, y, width - 2*radius, height); uint16_t innerRadius = radius - 2;
drawCircle(x + width - radius, y + radius, radius);
setColor(BLACK);
fillRect(x+radius, y+1, width - 2*radius + 1, height - 1);
setColor(WHITE); setColor(WHITE);
uint16_t maxProgressWidth = (width - 2 * radius) * progress / 100; drawCircleQuads(xRadius, yRadius, radius, 0b00000110);
for (uint16_t i = 0; i < maxProgressWidth; i++) { drawHorizontalLine(xRadius, y, width - doubleRadius + 1);
fillCircle(x + radius + i, y + radius, innerRadius); drawHorizontalLine(xRadius, y + height, width - doubleRadius + 1);
} drawCircleQuads(x + width - radius, yRadius, radius, 0b00001001);
uint16_t maxProgressWidth = (width - doubleRadius - 1) * progress / 100;
fillCircle(xRadius, yRadius, innerRadius);
fillRect(xRadius + 1, y + 2, maxProgressWidth, height - 3);
fillCircle(xRadius + maxProgressWidth, yRadius, innerRadius);
} }
void OLEDDisplay::drawFastImage(int16_t xMove, int16_t yMove, int16_t width, int16_t height, const char *image) { void OLEDDisplay::drawFastImage(int16_t xMove, int16_t yMove, int16_t width, int16_t height, const char *image) {
......
...@@ -138,6 +138,9 @@ class OLEDDisplay : public Print { ...@@ -138,6 +138,9 @@ class OLEDDisplay : public Print {
// Draw the border of a circle // Draw the border of a circle
void drawCircle(int16_t x, int16_t y, int16_t radius); void drawCircle(int16_t x, int16_t y, int16_t radius);
// Draw all Quadrants specified in the quads bit mask
void drawCircleQuads(int16_t x0, int16_t y0, int16_t radius, uint8_t quads);
// Fill circle // Fill circle
void fillCircle(int16_t x, int16_t y, int16_t radius); void fillCircle(int16_t x, int16_t y, int16_t radius);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment