aboutsummaryrefslogtreecommitdiff
path: root/engines
diff options
context:
space:
mode:
Diffstat (limited to 'engines')
-rw-r--r--engines/sci/gui/gui.cpp2
-rw-r--r--engines/sci/gui/gui_gfx.cpp77
-rw-r--r--engines/sci/gui/gui_gfx.h2
-rw-r--r--engines/sci/gui/gui_picture.cpp6
4 files changed, 61 insertions, 26 deletions
diff --git a/engines/sci/gui/gui.cpp b/engines/sci/gui/gui.cpp
index 31ff341aa6..3ca7794b0c 100644
--- a/engines/sci/gui/gui.cpp
+++ b/engines/sci/gui/gui.cpp
@@ -335,7 +335,7 @@ void SciGui::graphFillBox(Common::Rect rect, uint16 colorMask, int16 color, int1
}
void SciGui::graphDrawLine(Common::Point startPoint, Common::Point endPoint, int16 color, int16 priority, int16 control) {
- _gfx->Draw_Line(startPoint.x, startPoint.y, endPoint.x, endPoint.y, color, priority, control);
+ _gfx->drawLine(startPoint.x, startPoint.y, endPoint.x, endPoint.y, color, priority, control);
_screen->copyToScreen();
}
diff --git a/engines/sci/gui/gui_gfx.cpp b/engines/sci/gui/gui_gfx.cpp
index 4c173f4e93..f6c5f62104 100644
--- a/engines/sci/gui/gui_gfx.cpp
+++ b/engines/sci/gui/gui_gfx.cpp
@@ -616,20 +616,9 @@ void SciGuiGfx::RestoreBits(GuiMemoryHandle memoryHandle) {
}
}
-// Data passed to drawProc()
-struct LineData {
- byte drawMask;
- byte prio;
- byte control;
- SciGuiScreen *screen;
-};
-
-static void drawProc(int x, int y, int c, void *data) {
- LineData *lineData = (LineData *)data;
- lineData->screen->putPixel(x, y, lineData->drawMask, (byte)c, lineData->prio, lineData->control);
-}
-
-void SciGuiGfx::Draw_Line(int16 left, int16 top, int16 right, int16 bottom, byte color, byte priority, byte control) {
+// Sierra's Bresenham line drawing
+// WARNING: Do not just blindly replace this with Graphics::drawLine(), as it seems to create issues with flood fill
+void SciGuiGfx::drawLine(int16 left, int16 top, int16 right, int16 bottom, byte color, byte priority, byte control) {
//set_drawing_flag
byte drawMask = _screen->getDrawingMask(color, priority, control);
@@ -639,13 +628,59 @@ void SciGuiGfx::Draw_Line(int16 left, int16 top, int16 right, int16 bottom, byte
top += _curPort->top;
bottom += _curPort->top;
- LineData lineData;
- lineData.drawMask = drawMask;
- lineData.prio = priority;
- lineData.control = control;
- lineData.screen = _screen;
-
- Graphics::drawLine(left, top, right, bottom, color, drawProc, &lineData);
+ // horizontal line
+ if (top == bottom) {
+ if (right < left)
+ SWAP(right, left);
+ for (int i = left; i <= right; i++)
+ _screen->putPixel(i, top, drawMask, color, priority, control);
+ return;
+ }
+ // vertical line
+ if (left == right) {
+ if (top > bottom)
+ SWAP(top, bottom);
+ for (int i = top; i <= bottom; i++)
+ _screen->putPixel(left, i, drawMask, color, priority, control);
+ return;
+ }
+ // sloped line - draw with Bresenham algorithm
+ int dy = bottom - top;
+ int dx = right - left;
+ int stepy = dy < 0 ? -1 : 1;
+ int stepx = dx < 0 ? -1 : 1;
+ dy = ABS(dy) << 1;
+ dx = ABS(dx) << 1;
+
+ // setting the 1st and last pixel
+ _screen->putPixel(left, top, drawMask, color, priority, control);
+ _screen->putPixel(right, bottom, drawMask, color, priority, control);
+ // drawing the line
+ if (dx > dy) { // going horizontal
+ int fraction = dy - (dx >> 1);
+ while (left != right) {
+ if (fraction >= 0) {
+ top += stepy;
+ fraction -= dx;
+ }
+ left += stepx;
+ fraction += dy;
+ _screen->putPixel(left, top, drawMask, color, priority, control);
+ }
+ } else { // going vertical
+ int fraction = dx - (dy >> 1);
+ while (top != bottom) {
+ if (fraction >= 0) {
+ left += stepx;
+ fraction -= dy;
+ }
+ top += stepy;
+ fraction += dx;
+ _screen->putPixel(left, top, drawMask, color, priority, control);
+ }
+ }
+ //g_sci->eventMgr->waitUntil(5);
+ //ShowBits(&_rThePort->rect,6);
}
// Bitmap for drawing sierra circles
diff --git a/engines/sci/gui/gui_gfx.h b/engines/sci/gui/gui_gfx.h
index 0c84d017e2..15302bf9a8 100644
--- a/engines/sci/gui/gui_gfx.h
+++ b/engines/sci/gui/gui_gfx.h
@@ -92,7 +92,7 @@ public:
GuiMemoryHandle SaveBits(const Common::Rect &rect, byte screenFlags);
void RestoreBits(GuiMemoryHandle memoryHandle);
- void Draw_Line(int16 left, int16 top, int16 right, int16 bottom, byte color, byte prio, byte control);
+ void drawLine(int16 left, int16 top, int16 right, int16 bottom, byte color, byte prio, byte control);
void Draw_Box(Common::Rect box, byte color, byte prio, byte control);
void Draw_TexturedBox(Common::Rect box, byte color, byte prio, byte control, byte texture);
void Draw_Circle(Common::Rect box, byte size, byte color, byte prio, byte control);
diff --git a/engines/sci/gui/gui_picture.cpp b/engines/sci/gui/gui_picture.cpp
index d7b48865d4..0678fdfb83 100644
--- a/engines/sci/gui/gui_picture.cpp
+++ b/engines/sci/gui/gui_picture.cpp
@@ -352,7 +352,7 @@ void SciGuiPicture::drawVectorData(byte *data, int dataSize) {
while (vectorIsNonOpcode(data[curPos])) {
oldx = x; oldy = y;
vectorGetRelCoords(data, curPos, x, y);
- _gfx->Draw_Line(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
+ _gfx->drawLine(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
}
break;
case PIC_OP_MEDIUM_LINES: // medium line
@@ -360,7 +360,7 @@ void SciGuiPicture::drawVectorData(byte *data, int dataSize) {
while (vectorIsNonOpcode(data[curPos])) {
oldx = x; oldy = y;
vectorGetRelCoordsMed(data, curPos, x, y);
- _gfx->Draw_Line(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
+ _gfx->drawLine(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
}
break;
case PIC_OP_LONG_LINES: // long line
@@ -368,7 +368,7 @@ void SciGuiPicture::drawVectorData(byte *data, int dataSize) {
while (vectorIsNonOpcode(data[curPos])) {
oldx = x; oldy = y;
vectorGetAbsCoords(data, curPos, x, y);
- _gfx->Draw_Line(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
+ _gfx->drawLine(oldx, oldy, x, y, pic_color, pic_priority, pic_control);
}
break;