Skip to content
This repository was archived by the owner on Jan 5, 2024. It is now read-only.

Commit 8b04269

Browse files
committed
Refactor line drawing methods
1 parent 22c59e9 commit 8b04269

File tree

2 files changed

+77
-129
lines changed

2 files changed

+77
-129
lines changed

Managers/FrameMan.cpp

Lines changed: 55 additions & 127 deletions
Original file line numberDiff line numberDiff line change
@@ -499,126 +499,88 @@ namespace RTE {
499499

500500
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
501501

502-
int FrameMan::DrawLine(BITMAP *bitmap, const Vector &start, const Vector &end, int color, int altColor, int skip, int skipStart, bool shortestWrap) {
503-
RTEAssert(bitmap, "Trying to draw line to null Bitmap");
504-
505-
//acquire_bitmap(bitmap);
502+
void FrameMan::CreateNewPlayerBackBuffer(int player, int w, int h) {
503+
for (int f = 0; f < 2; f++) {
504+
destroy_bitmap(m_NetworkBackBufferIntermediate8[f][player]);
505+
m_NetworkBackBufferIntermediate8[f][player] = create_bitmap_ex(8, w, h);
506506

507-
int error = 0;
508-
int dom = 0;
509-
int sub = 0;
510-
int domSteps = 0;
511-
int skipped = skip + (skipStart - skip);
512-
int intPos[2];
513-
int delta[2];
514-
int delta2[2];
515-
int increment[2];
516-
bool drawAlt = false;
507+
destroy_bitmap(m_NetworkBackBufferIntermediateGUI8[f][player]);
508+
m_NetworkBackBufferIntermediateGUI8[f][player] = create_bitmap_ex(8, w, h);
517509

518-
// Just make the alt the same color as the main one if no one was specified
519-
if (altColor == 0) { altColor = color; }
520-
521-
intPos[X] = floorf(start.m_X);
522-
intPos[Y] = floorf(start.m_Y);
510+
destroy_bitmap(m_NetworkBackBufferFinal8[f][player]);
511+
m_NetworkBackBufferFinal8[f][player] = create_bitmap_ex(8, w, h);
523512

524-
// Wrap line around the scene if it makes it shorter
525-
if (shortestWrap) {
526-
Vector deltaVec = g_SceneMan.ShortestDistance(start, end, false);
527-
delta[X] = floorf(deltaVec.m_X);
528-
delta[Y] = floorf(deltaVec.m_Y);
529-
} else {
530-
delta[X] = floorf(end.m_X) - intPos[X];
531-
delta[Y] = floorf(end.m_Y) - intPos[Y];
513+
destroy_bitmap(m_NetworkBackBufferFinalGUI8[f][player]);
514+
m_NetworkBackBufferFinalGUI8[f][player] = create_bitmap_ex(8, w, h);
532515
}
533-
if (delta[X] == 0 && delta[Y] == 0) {
516+
m_PlayerScreenWidth = w;
517+
m_PlayerScreenHeight = h;
518+
}
519+
520+
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
521+
522+
bool FrameMan::LoadPalette(std::string palettePath) {
523+
PALETTE newPalette;
524+
BITMAP *tempBitmap = load_bitmap(palettePath.c_str(), newPalette);
525+
RTEAssert(tempBitmap, ("Failed to load palette from bitmap with following path:\n\n" + palettePath).c_str());
526+
527+
set_palette(newPalette);
528+
529+
// Update what black is now with the loaded palette
530+
m_BlackColor = bestfit_color(newPalette, 0, 0, 0);
531+
m_AlmostBlackColor = bestfit_color(newPalette, 5, 5, 5);
532+
533+
destroy_bitmap(tempBitmap);
534+
535+
return true;
536+
}
537+
534538
return 0;
535539
}
536540

537-
// Bresenham's line drawing algorithm preparation
538-
if (delta[X] < 0) {
539-
increment[X] = -1;
540-
delta[X] = -delta[X];
541-
} else {
542-
increment[X] = 1;
543-
}
544-
if (delta[Y] < 0) {
545-
increment[Y] = -1;
546-
delta[Y] = -delta[Y];
547-
} else {
548-
increment[Y] = 1;
549541
}
550-
// Scale by 2, for better accuracy of the error at the first pixel
551-
delta2[X] = delta[X] << 1;
552-
delta2[Y] = delta[Y] << 1;
553542

554-
// If X is dominant, Y is submissive, and vice versa.
555-
if (delta[X] > delta[Y]) {
556-
dom = X;
557-
sub = Y;
558-
} else {
559-
dom = Y;
560-
sub = X;
561-
}
562-
error = delta2[sub] - delta[dom];
563543

564-
// Bresenham's line drawing algorithm execution
565-
for (domSteps = 0; domSteps < delta[dom]; ++domSteps) {
566-
intPos[dom] += increment[dom];
567-
if (error >= 0) {
568-
intPos[sub] += increment[sub];
569-
error -= delta2[dom];
570544
}
571-
error += delta2[sub];
572545

573-
// Only draw pixel if we're not due to skip any
574-
if (++skipped > skip) {
575-
// Scene wrapping, if necessary
576-
g_SceneMan.WrapPosition(intPos[X], intPos[Y]);
577546

578-
// Slap a regular pixel on there
579-
putpixel(bitmap, intPos[X], intPos[Y], drawAlt ? color : altColor);
580-
drawAlt = !drawAlt;
581-
skipped = 0;
582-
}
583547
}
584-
//release_bitmap(bitmap);
585-
586-
// Return the end phase state of the skipping
587-
return skipped;
588548
}
589549

590550
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
591551

592-
int FrameMan::DrawDotLine(BITMAP *bitmap, const Vector &start, const Vector &end, BITMAP *dot, int skip, int skipStart, bool shortestWrap) {
552+
int FrameMan::SharedDrawLine(BITMAP *bitmap, const Vector &start, const Vector &end, int color, int altColor, int skip, int skipStart, bool shortestWrap, bool drawDot, BITMAP *dot) {
593553
RTEAssert(bitmap, "Trying to draw line to null Bitmap");
594-
RTEAssert(dot, "Trying to draw line of dots without specifying a dot Bitmap");
595-
596-
//acquire_bitmap(bitmap);
554+
if (drawDot) { RTEAssert(dot, "Trying to draw line of dots without specifying a dot Bitmap"); }
597555

598-
int error = 0;
599-
int dom = 0;
600-
int sub = 0;
601-
int domSteps = 0;
602-
int skipped = skip + (skipStart - skip);
556+
int error = 0;
557+
int dom = 0;
558+
int sub = 0;
559+
int domSteps = 0;
560+
int skipped = skip + (skipStart - skip);
603561
int intPos[2];
604562
int delta[2];
605563
int delta2[2];
606564
int increment[2];
607565
bool drawAlt = false;
608-
int dotHalfHeight = dot->h / 2;
609-
int dotHalfWidth = dot->w / 2;
610566

611-
// Calculate the integer values
567+
int dotHeight = drawDot ? dot->h : 0;
568+
int dotWidth = drawDot ? dot->w : 0;
569+
570+
//acquire_bitmap(bitmap);
571+
572+
// Just make the alt the same color as the main one if no one was specified
573+
if (altColor == 0) { altColor = color; }
574+
612575
intPos[X] = floorf(start.m_X);
613576
intPos[Y] = floorf(start.m_Y);
614577

615578
// Wrap line around the scene if it makes it shorter
616579
if (shortestWrap) {
617580
Vector deltaVec = g_SceneMan.ShortestDistance(start, end, false);
618581
delta[X] = floorf(deltaVec.m_X);
619-
delta[Y] = floorf(deltaVec.m_Y);
582+
delta[Y] = floorf(deltaVec.m_Y);
620583
} else {
621-
// No wrap
622584
delta[X] = floorf(end.m_X) - intPos[X];
623585
delta[Y] = floorf(end.m_Y) - intPos[Y];
624586
}
@@ -639,6 +601,7 @@ namespace RTE {
639601
} else {
640602
increment[Y] = 1;
641603
}
604+
642605
// Scale by 2, for better accuracy of the error at the first pixel
643606
delta2[X] = delta[X] << 1;
644607
delta2[Y] = delta[Y] << 1;
@@ -667,57 +630,22 @@ namespace RTE {
667630
// Scene wrapping, if necessary
668631
g_SceneMan.WrapPosition(intPos[X], intPos[Y]);
669632

670-
// Slap the dot on there
671-
masked_blit(dot, bitmap, 0, 0, intPos[X] - dotHalfWidth, intPos[Y] - dotHalfHeight, dot->w, dot->h);
672-
633+
if (drawDot) {
634+
masked_blit(dot, bitmap, 0, 0, intPos[X] - (dotWidth / 2), intPos[Y] - (dotHeight / 2), dot->w, dot->h);
635+
} else {
636+
putpixel(bitmap, intPos[X], intPos[Y], drawAlt ? color : altColor);
637+
}
673638
drawAlt = !drawAlt;
674639
skipped = 0;
675640
}
676641
}
642+
677643
//release_bitmap(bitmap);
678644

679645
// Return the end phase state of the skipping
680646
return skipped;
681647
}
682648

683-
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
684-
685-
void FrameMan::CreateNewPlayerBackBuffer(int player, int w, int h) {
686-
for (int f = 0; f < 2; f++) {
687-
destroy_bitmap(m_NetworkBackBufferIntermediate8[f][player]);
688-
m_NetworkBackBufferIntermediate8[f][player] = create_bitmap_ex(8, w, h);
689-
690-
destroy_bitmap(m_NetworkBackBufferIntermediateGUI8[f][player]);
691-
m_NetworkBackBufferIntermediateGUI8[f][player] = create_bitmap_ex(8, w, h);
692-
693-
destroy_bitmap(m_NetworkBackBufferFinal8[f][player]);
694-
m_NetworkBackBufferFinal8[f][player] = create_bitmap_ex(8, w, h);
695-
696-
destroy_bitmap(m_NetworkBackBufferFinalGUI8[f][player]);
697-
m_NetworkBackBufferFinalGUI8[f][player] = create_bitmap_ex(8, w, h);
698-
}
699-
m_PlayerScreenWidth = w;
700-
m_PlayerScreenHeight = h;
701-
}
702-
703-
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
704-
705-
bool FrameMan::LoadPalette(std::string palettePath) {
706-
PALETTE newPalette;
707-
BITMAP *tempBitmap = load_bitmap(palettePath.c_str(), newPalette);
708-
RTEAssert(tempBitmap, ("Failed to load palette from bitmap with following path:\n\n" + palettePath).c_str());
709-
710-
set_palette(newPalette);
711-
712-
// Update what black is now with the loaded palette
713-
m_BlackColor = bestfit_color(newPalette, 0, 0, 0);
714-
m_AlmostBlackColor = bestfit_color(newPalette, 5, 5, 5);
715-
716-
destroy_bitmap(tempBitmap);
717-
718-
return true;
719-
}
720-
721649
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
722650

723651
int FrameMan::SaveScreenToBMP(const char *nameBase) {

Managers/FrameMan.h

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -356,7 +356,9 @@ namespace RTE {
356356
/// <param name="skipStart">The start of the skipping phase. If skip is 10 and this is 5, the first dot will be drawn after 5 pixels.</param>
357357
/// <param name="shortestWrap">Whether the line should take the shortest possible route across scene wraps.</param>
358358
/// <returns>The end state of the skipping phase. Eg if 4 is returned here the last dot was placed 4 pixels ago.</returns>
359-
int DrawLine(BITMAP *pBitmap, const Vector &start, const Vector &end, int color, int altColor = 0, int skip = 0, int skipStart = 0, bool shortestWrap = false);
359+
int DrawLine(BITMAP *bitmap, const Vector &start, const Vector &end, int color, int altColor = 0, int skip = 0, int skipStart = 0, bool shortestWrap = false) {
360+
return SharedDrawLine(bitmap, start, end, color, altColor, skip, skipStart, shortestWrap, false, 0);
361+
}
360362

361363
/// <summary>
362364
/// Draws a line that can be dotted with bitmaps.
@@ -369,7 +371,9 @@ namespace RTE {
369371
/// <param name="skipStart">The start of the skipping phase. If skip is 10 and this is 5, the first dot will be drawn after 5 pixels.</param>
370372
/// <param name="shortestWrap">Whether the line should take the shortest possible route across scene wraps.</param>
371373
/// <returns>The end state of the skipping phase. Eg if 4 is returned here the last dot was placed 4 pixels ago.</returns>
372-
int DrawDotLine(BITMAP *bitmap, const Vector &start, const Vector &end, BITMAP *dot, int skip = 0, int skipStart = 0, bool shortestWrap = false);
374+
int DrawDotLine(BITMAP *bitmap, const Vector &start, const Vector &end, BITMAP *dot, int skip = 0, int skipStart = 0, bool shortestWrap = false) {
375+
return SharedDrawLine(bitmap, start, end, 0, 0, skip, skipStart, shortestWrap, true, dot);
376+
}
373377
#pragma endregion
374378

375379
#pragma region Network Handling
@@ -667,6 +671,22 @@ namespace RTE {
667671
void DrawScreenFlash(short playerScreen, BITMAP *playerGUIBitmap);
668672
#pragma endregion
669673

674+
675+
/// <summary>
676+
/// Shared method for drawing lines to avoid duplicate code. Will by called by either DrawLine() or DrawDotLine().
677+
/// </summary>
678+
/// <param name="pBitmap">The Bitmap to draw to. Ownership is NOT transferred.</param>
679+
/// <param name="start">The absolute Start point.</param>
680+
/// <param name="end">The absolute end point.</param>
681+
/// <param name="color">The color value of the line.</param>
682+
/// <param name="altColor">A color to alternate with. Every other pixel drawn will have this if !0.</param>
683+
/// <param name="skip">How many pixels to skip drawing between drawn ones. 0 means solid line 2 means there's a gap of two pixels between each drawn one. Should be more than 0 for dots.</param>
684+
/// <param name="skipStart">The start of the skipping phase. If skip is 10 and this is 5, the first dot will be drawn after 5 pixels.</param>
685+
/// <param name="shortestWrap">Whether the line should take the shortest possible route across scene wraps.</param>
686+
/// <param name="dot">The bitmap to be used for dots (will be centered).</param>
687+
/// <returns>The end state of the skipping phase. Eg if 4 is returned here the last dot was placed 4 pixels ago.</returns>
688+
int SharedDrawLine(BITMAP *pBitmap, const Vector &start, const Vector &end, int color, int altColor = 0, int skip = 0, int skipStart = 0, bool shortestWrap = false, bool drawDot = 0, BITMAP *dot = 0);
689+
670690
/// <summary>
671691
/// Gets the requested font from the GUI engine's current skin. Ownership is NOT transferred!
672692
/// </summary>

0 commit comments

Comments
 (0)