From 4cb2b8c3c43d26569960e271ac35e0dd9f4de5b4 Mon Sep 17 00:00:00 2001 From: Vicent Marti Date: Sun, 13 Jul 2008 10:50:57 +0000 Subject: Improved support for graphics positioning. More widgets. New triangle drawing function. svn-id: r33027 --- base/main.cpp | 13 --------- graphics/VectorRenderer.cpp | 46 +++++++++++++++++++++++++++++-- graphics/VectorRenderer.h | 62 +++++++++++++++++++++++++++++++++++++---- gui/ThemeDefaultXML.cpp | 6 ++-- gui/ThemeParser.cpp | 67 ++++++++++++++++++++++++++++++++++++++++----- gui/ThemeRenderer.cpp | 10 +++---- 6 files changed, 167 insertions(+), 37 deletions(-) diff --git a/base/main.cpp b/base/main.cpp index b7d30d30f8..219fa0cdc5 100644 --- a/base/main.cpp +++ b/base/main.cpp @@ -70,17 +70,6 @@ static bool launcherDialog(OSystem &system) { // Clear the main screen system.clearScreen(); -// GUI::ThemeRenderer *test = new GUI::ThemeRenderer("modern", GUI::ThemeRenderer::kGfxAntialias16bit); - -#if defined LOL - -// g_InterfaceManager.runGUI(); - InterfaceManager *manager = new InterfaceManager(); - manager->openDialog(kDialogLauncher); - return (manager.runGUI() != -1); - -#else - #if defined(_WIN32_WCE) CELauncherDialog dlg; #elif defined(__DC__) @@ -89,8 +78,6 @@ static bool launcherDialog(OSystem &system) { GUI::LauncherDialog dlg; #endif return (dlg.runModal() != -1); - -#endif // vector renderer debug } static const EnginePlugin *detectPlugin() { diff --git a/graphics/VectorRenderer.cpp b/graphics/VectorRenderer.cpp index 8856386819..efdaea80c8 100644 --- a/graphics/VectorRenderer.cpp +++ b/graphics/VectorRenderer.cpp @@ -399,7 +399,12 @@ drawTriangle(int x, int y, int w, int h, TriangleOrientation orient) { switch(orient) { case kTriangleUp: case kTriangleDown: - drawTriangleVertAlg(x, y, w, h, (orient == kTriangleDown), color, Base::_fillMode); +#ifdef VECTOR_RENDERER_FAST_TRIANGLES + if (w == h) + drawTriangleFast(x, y, w, (orient == kTriangleDown), color, Base::_fillMode); + else +#endif + drawTriangleVertAlg(x, y, w, h, (orient == kTriangleDown), color, Base::_fillMode); break; case kTriangleLeft: @@ -408,8 +413,14 @@ drawTriangle(int x, int y, int w, int h, TriangleOrientation orient) { } if (Base::_strokeWidth > 0) - if (Base::_fillMode == kFillBackground || Base::_fillMode == kFillGradient) - drawTriangleVertAlg(x, y, w, h, (orient == kTriangleDown), _fgColor, kFillDisabled); + if (Base::_fillMode == kFillBackground || Base::_fillMode == kFillGradient) { +#ifdef VECTOR_RENDERER_FAST_TRIANGLES + if (w == h) + drawTriangleFast(x, y, w, (orient == kTriangleDown), _fgColor, kFillDisabled); + else +#endif + drawTriangleVertAlg(x, y, w, h, (orient == kTriangleDown), _fgColor, kFillDisabled); + } } /******************************************************************** @@ -616,6 +627,35 @@ drawTriangleVertAlg(int x1, int y1, int w, int h, bool inverted, PixelType color } +/** VERTICAL TRIANGLE DRAWING - FAST VERSION FOR SQUARED TRIANGLES */ +template +void VectorRendererSpec:: +drawTriangleFast(int x1, int y1, int size, bool inverted, PixelType color, VectorRenderer::FillMode fill_m) { + int pitch = Base::surfacePitch(); + int hstep = 0; + + PixelType *ptr_right = 0, *ptr_left = 0; + + if (inverted) { + ptr_left = (PixelType *)_activeSurface->getBasePtr(x1, y1); + ptr_right = (PixelType *)_activeSurface->getBasePtr(x1 + size, y1); + } else { + ptr_left = (PixelType *)_activeSurface->getBasePtr(x1, y1 + size); + ptr_right = (PixelType *)_activeSurface->getBasePtr(x1 + size, y1 + size); + pitch = -pitch; + } + + while (ptr_left != ptr_right) { + colorFill(ptr_left, ptr_right, color); + ptr_left += pitch; + ptr_right += pitch; + if (hstep++ % 3) { + ptr_left++; + ptr_right--; + } + } +} + /** ROUNDED SQUARE ALGORITHM **/ template void VectorRendererSpec:: diff --git a/graphics/VectorRenderer.h b/graphics/VectorRenderer.h index 4dcef24e31..3af682953d 100644 --- a/graphics/VectorRenderer.h +++ b/graphics/VectorRenderer.h @@ -65,6 +65,15 @@ struct DrawStep { bool autoWidth, autoHeight; int16 x, y, w, h; /** width, height and position, if not measured automatically. negative values mean counting from the opposite direction */ + + enum VectorAlignment { + kVectorAlignManual, + kVectorAlignLeft, + kVectorAlignRight, + kVectorAlignBottom, + kVectorAlignTop, + kVectorAlignCenter + } xAlign, yAlign; uint8 shadow, stroke, factor, radius; /** Misc options... */ @@ -327,18 +336,58 @@ public: void stepGetPositions(const DrawStep &step, const Common::Rect &area, uint16 &in_x, uint16 &in_y, uint16 &in_w, uint16 &in_h) { if (!step.autoWidth) { - in_w = step.w; - if (step.x >= 0) in_x = area.left + step.x; - else in_x = area.left + area.width() + step.x; // value relative to the opposite corner. + in_w = step.w == -1 ? area.height() : step.w; + + switch(step.xAlign) { + case Graphics::DrawStep::kVectorAlignManual: + if (step.x >= 0) in_x = area.left + step.x; + else in_x = area.left + area.width() + step.x; // value relative to the opposite corner. + break; + + case Graphics::DrawStep::kVectorAlignCenter: + in_x = area.left + (area.width() / 2) - (in_w / 2); + break; + + case Graphics::DrawStep::kVectorAlignLeft: + in_x = area.left; + break; + + case Graphics::DrawStep::kVectorAlignRight: + in_x = area.left + area.width() - in_w; + break; + + default: + error("Vertical alignment in horizontal data."); + } } else { in_x = area.left; in_w = area.width(); } if (!step.autoHeight) { - in_h = step.h; - if (step.y >= 0) in_y = area.top + step.y; - else in_y = area.top + area.height() + step.y; // relative + in_h = step.h == -1 ? area.width() : step.h; + + switch(step.yAlign) { + case Graphics::DrawStep::kVectorAlignManual: + if (step.y >= 0) in_y = area.top + step.y; + else in_y = area.top + area.height() + step.y; // relative + break; + + case Graphics::DrawStep::kVectorAlignCenter: + in_y = area.top + (area.height() / 2) - (in_h / 2); + break; + + case Graphics::DrawStep::kVectorAlignTop: + in_y = area.top; + break; + + case Graphics::DrawStep::kVectorAlignBottom: + in_y = area.top + area.height() - in_h; + break; + + default: + error("Horizontal alignment in vertical data."); + } } else { in_y = area.top; in_h = area.height(); @@ -682,6 +731,7 @@ protected: virtual void drawRoundedSquareAlg(int x1, int y1, int r, int w, int h, PixelType color, FillMode fill_m); virtual void drawSquareAlg(int x, int y, int w, int h, PixelType color, FillMode fill_m); virtual void drawTriangleVertAlg(int x, int y, int w, int h, bool inverted, PixelType color, FillMode fill_m); + virtual void drawTriangleFast(int x, int y, int size, bool inverted, PixelType color, FillMode fill_m); virtual void drawBevelSquareAlg(int x, int y, int w, int h, int bevel, PixelType top_color, PixelType bottom_color); /** diff --git a/gui/ThemeDefaultXML.cpp b/gui/ThemeDefaultXML.cpp index 0c35fa1e1f..3cd2d735d2 100644 --- a/gui/ThemeDefaultXML.cpp +++ b/gui/ThemeDefaultXML.cpp @@ -51,12 +51,12 @@ bool ThemeRenderer::loadDefaultXML() { "" "" - "" - "/* */" + "" + "" "" "" - "" + "" "" "" diff --git a/gui/ThemeParser.cpp b/gui/ThemeParser.cpp index e882945ff1..eec9801b59 100644 --- a/gui/ThemeParser.cpp +++ b/gui/ThemeParser.cpp @@ -89,6 +89,13 @@ Graphics::DrawStep *ThemeParser::defaultDrawStep() { step->gradColor1.set = false; step->gradColor2.set = false; + step->xAlign = Graphics::DrawStep::kVectorAlignManual; + step->yAlign = Graphics::DrawStep::kVectorAlignManual; + step->x = 0; + step->y = 0; + step->w = 0; + step->h = 0; + step->extraData = 0; step->factor = 1; step->autoWidth = true; @@ -433,18 +440,64 @@ bool ThemeParser::parseDrawStep(ParserNode *stepNode, Graphics::DrawStep *drawst warning("The keyword has been deprecated. Use and instead"); } - if (stepNode->values.contains("width")) { + if (stepNode->values.contains("width") && stepNode->values["width"] != "auto") { drawstep->autoWidth = false; - __PARSER_ASSIGN_INT(x, "xpos", true); + + val = stepNode->values["width"]; + if (parseIntegerKey(val.c_str(), 1, &x)) + drawstep->w = x; + else if (val == "height") + drawstep->w = -1; + else return parserError("Invalid value for vector width."); + + if (stepNode->values.contains("xpos")) { + val = stepNode->values["xpos"]; + + if (parseIntegerKey(val.c_str(), 1, &x)) + drawstep->x = x; + else if (val == "center") + drawstep->xAlign = Graphics::DrawStep::kVectorAlignCenter; + else if (val == "left") + drawstep->xAlign = Graphics::DrawStep::kVectorAlignLeft; + else if (val == "right") + drawstep->xAlign = Graphics::DrawStep::kVectorAlignRight; + else + return parserError("Invalid value for X Position"); + } else { + return parserError("When width is not set to 'auto', a tag must be included."); + } } - if (stepNode->values.contains("height")) { + if (stepNode->values.contains("height") && stepNode->values["height"] != "auto") { drawstep->autoHeight = false; - __PARSER_ASSIGN_INT(y, "ypos", true); - } - __PARSER_ASSIGN_INT(w, "width", false); - __PARSER_ASSIGN_INT(h, "height", false); + val = stepNode->values["height"]; + if (parseIntegerKey(val.c_str(), 1, &x)) + drawstep->h = x; + else if (val == "width") + drawstep->h = -1; + else return parserError("Invalid value for vector height."); + + if (stepNode->values.contains("ypos")) { + val = stepNode->values["ypos"]; + + if (parseIntegerKey(val.c_str(), 1, &x)) + drawstep->y = x; + else if (val == "center") + drawstep->yAlign = Graphics::DrawStep::kVectorAlignCenter; + else if (val == "top") + drawstep->yAlign = Graphics::DrawStep::kVectorAlignTop; + else if (val == "bottom") + drawstep->yAlign = Graphics::DrawStep::kVectorAlignBottom; + else + return parserError("Invalid value for Y Position"); + } else { + return parserError("When height is not set to 'auto', a tag must be included."); + } + } + + if (drawstep->h == -1 && drawstep->w == -1) + return parserError("Cross-reference in Vector Size: Height is set to width and width is set to height."); } if (stepNode->values.contains("fill")) { diff --git a/gui/ThemeRenderer.cpp b/gui/ThemeRenderer.cpp index 2df58ed343..ce9e94faa2 100644 --- a/gui/ThemeRenderer.cpp +++ b/gui/ThemeRenderer.cpp @@ -416,11 +416,11 @@ void ThemeRenderer::drawTab(const Common::Rect &r, int tabHeight, int tabWidth, } void ThemeRenderer::debugWidgetPosition(const char *name, const Common::Rect &r) { - _font->drawString(_screen, name, r.left, r.top, r.width(), 0xFFFF, Graphics::kTextAlignRight, 0, true); - _screen->hLine(r.left, r.top, r.right, 0xFFFF); - _screen->hLine(r.left, r.bottom, r.right, 0xFFFF); - _screen->vLine(r.left, r.top, r.bottom, 0xFFFF); - _screen->vLine(r.right, r.top, r.bottom, 0xFFFF); + // _font->drawString(_screen, name, r.left, r.top, r.width(), 0xFFFF, Graphics::kTextAlignRight, 0, true); + // _screen->hLine(r.left, r.top, r.right, 0xFFFF); + // _screen->hLine(r.left, r.bottom, r.right, 0xFFFF); + // _screen->vLine(r.left, r.top, r.bottom, 0xFFFF); + // _screen->vLine(r.right, r.top, r.bottom, 0xFFFF); } void ThemeRenderer::updateScreen() { -- cgit v1.2.3