diff --git a/headers/private/servers/app/Painter.h b/headers/private/servers/app/Painter.h index e6bba007b2..b9e8467018 100644 --- a/headers/private/servers/app/Painter.h +++ b/headers/private/servers/app/Painter.h @@ -26,7 +26,8 @@ class ServerFont; // * most all functions should take a DrawData* context parameter instead // of the current pattern argument, that way, each function can // decide for itself, which pieces of information in DrawData it -// needs +// needs -> well I'm not so sure about this, there could also +// be a DrawData member in Painter fGraphicsState or something... // * Painter itself should be made thread safe. Because no // ServerWindow is supposed to draw outside of its clipping region, // there is actually no reason to lock the DisplayDriver. Multiple @@ -66,6 +67,8 @@ class Painter { void SetDrawingMode(drawing_mode mode); void SetBlendingMode(source_alpha alphaSrcMode, alpha_function alphaFncMode); + void SetPattern(const pattern& p); + void SetPenLocation(const BPoint& location); void SetFont(const BFont& font); void SetFont(const ServerFont& font); @@ -220,6 +223,7 @@ class Painter { void _UpdateFont(); void _UpdateLineWidth(); + void _UpdateDrawingMode(); // drawing functions stroke/fill BRect _DrawTriangle( BPoint pt1, @@ -258,7 +262,6 @@ class Painter { template BRect _FillPath(VertexSource& path) const; - void _SetPattern(const pattern& p) const; void _SetRendererColor(const rgb_color& color) const; agg::rendering_buffer* fBuffer; diff --git a/headers/private/servers/app/PatternHandler.h b/headers/private/servers/app/PatternHandler.h index c0f227f133..4544b422bb 100644 --- a/headers/private/servers/app/PatternHandler.h +++ b/headers/private/servers/app/PatternHandler.h @@ -66,6 +66,10 @@ class Pattern { Pattern& operator=(const pattern &from) { memcpy(&fPattern.type64, &from, sizeof(pattern)); return *this; } + + bool operator==(const Pattern& other) const + { return fPattern.type64 == other.fPattern.type64; } + private: typedef union @@ -128,6 +132,8 @@ class PatternHandler { const pattern* GetR5Pattern(void) const { return (const pattern*)fPattern.GetInt8(); } + const Pattern& GetPattern(void) const + { return fPattern; } private: Pattern fPattern; RGBColor fHighColor; diff --git a/src/servers/app/drawing/Painter/Painter.cpp b/src/servers/app/drawing/Painter/Painter.cpp index be1eba9f3f..78b74a7213 100644 --- a/src/servers/app/drawing/Painter/Painter.cpp +++ b/src/servers/app/drawing/Painter/Painter.cpp @@ -153,14 +153,25 @@ Painter::SetDrawData(const DrawData* data) SetHighColor(data->highcolor.GetColor32()); SetLowColor(data->lowcolor.GetColor32()); SetPenSize(data->pensize); - SetDrawingMode(data->draw_mode); - SetBlendingMode(data->alphaSrcMode, data->alphaFncMode); SetPenLocation(data->penlocation); SetFont(data->font); // if (data->clipReg) { // ConstrainClipping(*data->clipReg); // } + // any of these conditions means we need to use a different drawing + // mode instance + bool updateDrawingMode = !(data->patt == fPatternHandler->GetPattern()) || + data->draw_mode != fDrawingMode || + (data->draw_mode == B_OP_ALPHA && (data->alphaSrcMode != fAlphaSrcMode || + data->alphaFncMode != fAlphaFncMode)); + + fDrawingMode = data->draw_mode; + fAlphaSrcMode = data->alphaSrcMode; + fAlphaFncMode = data->alphaFncMode; fPatternHandler->SetPattern(data->patt); + + if (updateDrawingMode) + _UpdateDrawingMode(); } // #pragma mark - @@ -213,11 +224,7 @@ Painter::SetDrawingMode(drawing_mode mode) { if (fDrawingMode != mode) { fDrawingMode = mode; - if (fPixelFormat) { - fPixelFormat->set_drawing_mode(DrawingModeFactory::DrawingModeFor(fDrawingMode, - fAlphaSrcMode, - fAlphaFncMode)); - } + _UpdateDrawingMode(); } } @@ -228,11 +235,18 @@ Painter::SetBlendingMode(source_alpha alphaSrcMode, alpha_function alphaFncMode) if (fAlphaSrcMode != alphaSrcMode || fAlphaFncMode != alphaFncMode) { fAlphaSrcMode = alphaSrcMode; fAlphaFncMode = alphaFncMode; - if (fDrawingMode == B_OP_ALPHA && fPixelFormat) { - fPixelFormat->set_drawing_mode(DrawingModeFactory::DrawingModeFor(fDrawingMode, - fAlphaSrcMode, - fAlphaFncMode)); - } + if (fDrawingMode == B_OP_ALPHA) + _UpdateDrawingMode(); + } +} + +// SetPattern +void +Painter::SetPattern(const pattern& p) +{ + if (!(p == *fPatternHandler->GetR5Pattern())) { + fPatternHandler->SetPattern(p); + _UpdateDrawingMode(); } } @@ -999,6 +1013,36 @@ Painter::_UpdateLineWidth() fLineProfile.width(fPenSize); } +// _UpdateDrawingMode +void +Painter::_UpdateDrawingMode() +{ + if (fPixelFormat) { + DrawingMode* mode = NULL; + pattern p = *fPatternHandler->GetR5Pattern(); + if (p == B_SOLID_HIGH) { + _SetRendererColor(fPatternHandler->HighColor().GetColor32()); + mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, + fAlphaSrcMode, + fAlphaFncMode, + true); + } else if (p == B_SOLID_LOW) { + _SetRendererColor(fPatternHandler->LowColor().GetColor32()); + mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, + fAlphaSrcMode, + fAlphaFncMode, + true); + } else { + mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, + fAlphaSrcMode, + fAlphaFncMode, + false); + } + fPixelFormat->set_drawing_mode(mode); + } + +} + // #pragma mark - // _DrawTriangle @@ -1282,39 +1326,6 @@ Painter::_FillPath(VertexSource& path) const return _Clipped(_BoundingBox(path)); } -// _SetPattern -void -Painter::_SetPattern(const pattern& p) const -{ -// TODO: currently unused, purpose is to construct -// special drawing mode instances that work on solid patterns -// currently, there is only such a thing for B_OP_COPY - if (!(p == *fPatternHandler->GetR5Pattern())) { -printf("Painter::_SetPattern()\n"); - fPatternHandler->SetPattern(p); - DrawingMode* mode = NULL; - if (p == B_SOLID_HIGH) { - _SetRendererColor(fPatternHandler->HighColor().GetColor32()); - mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, - fAlphaSrcMode, - fAlphaFncMode, - true); - } else if (p == B_SOLID_LOW) { - _SetRendererColor(fPatternHandler->LowColor().GetColor32()); - mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, - fAlphaSrcMode, - fAlphaFncMode, - true); - } else { - mode = DrawingModeFactory::DrawingModeFor(fDrawingMode, - fAlphaSrcMode, - fAlphaFncMode, - false); - } - fPixelFormat->set_drawing_mode(mode); - } -} - // _SetRendererColor void Painter::_SetRendererColor(const rgb_color& color) const