diff --git a/src/servers/app/server/DisplayDriver.cpp b/src/servers/app/server/DisplayDriver.cpp index da028b5037..bf1900a58e 100644 --- a/src/servers/app/server/DisplayDriver.cpp +++ b/src/servers/app/server/DisplayDriver.cpp @@ -98,8 +98,14 @@ void DisplayDriver::Shutdown(void) If the destination is not the same size as the source, the source should be scaled to fit. */ -void DisplayDriver::CopyBits(const BRect &src, const BRect &dest) +void DisplayDriver::CopyBits(const BRect &src, const BRect &dest, const DrawData *d) { + if(!d) + return; + + Lock(); + Blit(src,dest,d); + Unlock(); } /*! @@ -109,6 +115,7 @@ void DisplayDriver::CopyBits(const BRect &src, const BRect &dest) */ void DisplayDriver::CopyRegion(BRegion *src, const BPoint &lefttop) { + // TODO: Implement DisplayDriver;:CopyRegion } /*! @@ -566,8 +573,7 @@ void DisplayDriver::DrawString(const char *string, const int32 &length, const BP previous=glyph_index; } - // TODO: implement properly - // calculate the invalid rectangle + // TODO: implement calculation of invalid rectangle in DisplayDriver::DrawString properly BRect r; r.left=MIN(point.x,pen.x>>6); r.right=MAX(point.x,pen.x>>6); @@ -670,6 +676,8 @@ void DisplayDriver::BlitMono2RGB32(FT_Bitmap *src, const BPoint &pt, const DrawD destindex+=destinc; } ReleaseBuffer(); + + // TODO: test to see if Invalidate calls should be made in DisplayDriver::BlitMono2RGB32 Invalidate(BRect(pt.x, pt.y, pt.x + srcwidth, pt.y + srcheight)); } @@ -792,6 +800,7 @@ void DisplayDriver::BlitGray2RGB32(FT_Bitmap *src, const BPoint &pt, const DrawD destindex+=destinc; } ReleaseBuffer(); + // TODO: test to see if Invalidate calls should be made in DisplayDriver::BlitGray2RGB32 Invalidate(BRect(pt.x, pt.y, pt.x + srcwidth, pt.y + srcheight)); } @@ -1164,6 +1173,7 @@ void DisplayDriver::FillArc(const BRect &r, const float &angle, const float &spa } } } + Invalidate(r); Unlock(); } @@ -1527,6 +1537,7 @@ void DisplayDriver::FillArc(const BRect &r, const float &angle, const float &spa } } } + Invalidate(r); Unlock(); } @@ -1535,7 +1546,7 @@ void DisplayDriver::FillBezier(BPoint *pts, const RGBColor &color) Lock(); BezierCurve curve(pts); - FillPolygon(curve.GetPointArray(), curve.points.CountItems(), color); + FillPolygon(curve.GetPointArray(), curve.points.CountItems(), curve.Frame(), color); Unlock(); } @@ -1551,7 +1562,7 @@ void DisplayDriver::FillBezier(BPoint *pts, const DrawData *d) Lock(); BezierCurve curve(pts); - FillPolygon(curve.GetPointArray(), curve.points.CountItems(), d); + FillPolygon(curve.GetPointArray(), curve.points.CountItems(), curve.Frame(), d); Unlock(); } @@ -1685,6 +1696,7 @@ void DisplayDriver::FillEllipse(const BRect &r, const DrawData *d) StrokeLine(BPoint(xc-x,yc-y),BPoint(xc+x,yc-y),&data); StrokeLine(BPoint(xc-x,yc+y),BPoint(xc+x,yc+y),&data); } + Invalidate(r); Unlock(); } @@ -1694,7 +1706,7 @@ void DisplayDriver::FillEllipse(const BRect &r, const DrawData *d) \param numpts Number of points in the BPoint array. \param color The color of the polygon */ -void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const RGBColor &color) +void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const BRect &bounds, const RGBColor &color) { /* Here's the plan. Record all line segments in polygon. If a line segments crosses the y-value of a point not in the segment, split the segment into 2 segments. @@ -1721,7 +1733,8 @@ void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const RGBColor &co maxX = ROUND(ptlist[0].x); minY = ROUND(ptlist[0].y); maxY = ROUND(ptlist[0].y); - /* Generate the segment list */ + + // Generate the segment list currentPoint = ptlist; currentIndex = 0; nextPoint = &ptlist[1]; @@ -1776,7 +1789,7 @@ void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const RGBColor &co } } - /* Selection sort the segments. Probably should replace this later. */ + // Selection sort the segments. Probably should replace this later. for (i=0; iclipReg ) { - /* Draw the lines */ + // Draw the lines for (y=minY; y<=maxY; y++) { i = 0; @@ -1985,7 +2000,7 @@ void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const DrawData *d) yStart = MAX(minY,ROUND(clipRect.top)); yEnd = MIN(maxY,ROUND(clipRect.bottom)); - /* Draw the lines */ + // Draw the lines for (y=yStart; y<=yEnd; y++) { i = 0; @@ -2035,6 +2050,7 @@ void DisplayDriver::FillPolygon(BPoint *ptlist, int32 numpts, const DrawData *d) } } delete[] segmentArray; + Invalidate(bounds); Unlock(); } @@ -2077,6 +2093,7 @@ void DisplayDriver::FillRect(const BRect &r, const DrawData *d) } else FillPatternRect(r,d); + Invalidate(r); Unlock(); } @@ -2094,7 +2111,7 @@ void DisplayDriver::FillRegion(BRegion& r, const RGBColor &color) numRects = r.CountRects(); for(int32 i=0; i= startx) && (x <= endx)) ) StrokePoint(BPoint(xc+x,yc+y),color); } - + Invalidate(r); Unlock(); } @@ -2938,7 +2964,7 @@ void DisplayDriver::StrokeArc(const BRect &r, const float &angle, const float &s (shortspan && (startQuad == 4) && (x >= startx) && (x <= endx)) ) StrokePoint(BPoint(xc+x,yc+y),d); } - + Invalidate(r); Unlock(); } @@ -2957,6 +2983,7 @@ void DisplayDriver::StrokeBezier(BPoint *pts, const RGBColor &color) numLines = curve.points.CountItems()-1; for (i=0; i*setPixel)(ROUND(x),ROUND(y)); } + Invalidate(BRect(start,end)); } void DisplayDriver::StrokePoint(const BPoint& pt, const RGBColor &color) { StrokeLine(pt, pt, color); + Invalidate(BRect(pt,pt)); } void DisplayDriver::StrokePoint(const BPoint& pt, const DrawData *d) { StrokeLine(pt, pt, d); + Invalidate(BRect(pt,pt)); } -void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const RGBColor &color, bool is_closed) +void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const BRect &bounds, const RGBColor &color, bool is_closed) { if(!ptlist) return; @@ -3295,6 +3328,7 @@ void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const RGBColor & StrokeLine(ptlist[i],ptlist[i+1],color); if(is_closed) StrokeLine(ptlist[numpts-1],ptlist[0],color); + Invalidate(bounds); Unlock(); } @@ -3304,7 +3338,7 @@ void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const RGBColor & \param numpts Number of points in the BPoint array. \param d DrawData containing all of the other options */ -void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const DrawData *d, bool is_closed) +void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const BRect &bounds, const DrawData *d, bool is_closed) { if(!ptlist) return; @@ -3314,6 +3348,7 @@ void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const DrawData * StrokeLine(ptlist[i],ptlist[i+1],d); if(is_closed) StrokeLine(ptlist[numpts-1],ptlist[0],d); + Invalidate(bounds); Unlock(); } @@ -3326,10 +3361,8 @@ void DisplayDriver::StrokePolygon(BPoint *ptlist, int32 numpts, const DrawData * void DisplayDriver::StrokeRect(const BRect &r, const RGBColor &color) { Lock(); - StrokeLine(r.LeftTop(),r.RightTop(),color); - StrokeLine(r.LeftTop(),r.LeftBottom(),color); - StrokeLine(r.RightTop(),r.RightBottom(),color); - StrokeLine(r.LeftBottom(),r.RightBottom(),color); + StrokeSolidRect(r,color); + Invalidate(r); Unlock(); } @@ -3340,6 +3373,7 @@ void DisplayDriver::StrokeRect(const BRect &r, const DrawData *d) StrokeLine(r.LeftTop(),r.LeftBottom(),d); StrokeLine(r.RightTop(),r.RightBottom(),d); StrokeLine(r.LeftBottom(),r.RightBottom(),d); + Invalidate(r); Unlock(); } @@ -3356,7 +3390,7 @@ void DisplayDriver::StrokeRegion(BRegion& r, const RGBColor &color) for(int32 i=0; i fFrame.right) + fFrame.right = pts[i].x; + if (pts[i].y > fFrame.bottom) + fFrame.bottom = pts[i].y; + } +} + int BezierCurve::GeneratePoints(int startPos) { double slopeAB, slopeBC, slopeCD; diff --git a/src/servers/app/server/Jamfile b/src/servers/app/server/Jamfile index 83d91ad2d4..29eac0ab8c 100644 --- a/src/servers/app/server/Jamfile +++ b/src/servers/app/server/Jamfile @@ -31,6 +31,7 @@ SharedLibrary appserver : SysCursor.cpp SystemPalette.cpp TokenHandler.cpp + Utils.cpp ; LinkSharedOSLibs libappserver.so : root be @@ -43,7 +44,6 @@ Server app_server : FMWList.cpp PicturePlayer.cpp PNGDump.cpp - Utils.cpp # Manager Classes AppServer.cpp diff --git a/src/servers/app/server/PicturePlayer.cpp b/src/servers/app/server/PicturePlayer.cpp index 37bd0dc9e4..cf30308e47 100644 --- a/src/servers/app/server/PicturePlayer.cpp +++ b/src/servers/app/server/PicturePlayer.cpp @@ -28,6 +28,7 @@ #include "PicturePlayer.h" #include "PictureProtocol.h" +#include "Utils.h" #include "DisplayDriver.h" #include #include @@ -202,7 +203,7 @@ status_t PicturePlayer::Play(int32 tableEntries,void *userData, LayerData *d) BPoint *points = new BPoint[numPoints]; GetData(points, numPoints * sizeof(BPoint)); bool isClosed = GetBool(); - fdriver->StrokePolygon(points,numPoints,&fldata,isClosed); + fdriver->StrokePolygon(points,numPoints,CalculatePolygonBounds(points,numPoints),&fldata,isClosed); delete points; break; } @@ -211,7 +212,7 @@ status_t PicturePlayer::Play(int32 tableEntries,void *userData, LayerData *d) int32 numPoints = GetInt32(); BPoint *points = new BPoint[numPoints]; GetData(points, numPoints * sizeof(BPoint)); - fdriver->FillPolygon(points,numPoints,&fldata); + fdriver->FillPolygon(points,numPoints,CalculatePolygonBounds(points,numPoints),&fldata); delete points; break; } diff --git a/src/servers/app/server/ServerWindow.cpp b/src/servers/app/server/ServerWindow.cpp index 93d081a905..8d20c5cb59 100644 --- a/src/servers/app/server/ServerWindow.cpp +++ b/src/servers/app/server/ServerWindow.cpp @@ -1854,9 +1854,7 @@ void ServerWindow::DispatchMessage(int32 code) for(int i=0;i<3;i++) pts[i]=cl->ConvertToTop(pts[i]); - // TODO: modify DisplayDriver::StrokeTriangle to utilize a boundary BRect - desktop->GetDisplayDriver()->StrokeTriangle(pts,cl->fLayerData); -// desktop->GetDisplayDriver()->StrokeTriangle(pts,cl->ConvertToTop(rect),cl->fLayerData); + desktop->GetDisplayDriver()->StrokeTriangle(pts,cl->ConvertToTop(rect),cl->fLayerData); } break; } @@ -1876,12 +1874,174 @@ void ServerWindow::DispatchMessage(int32 code) for(int i=0;i<3;i++) pts[i]=cl->ConvertToTop(pts[i]); - // TODO: modify DisplayDriver::FillTriangle to utilize a boundary BRect - desktop->GetDisplayDriver()->FillTriangle(pts,cl->fLayerData); -// desktop->GetDisplayDriver()->FillTriangle(pts,cl->ConvertToTop(rect),cl->fLayerData); + desktop->GetDisplayDriver()->FillTriangle(pts,cl->ConvertToTop(rect),cl->fLayerData); } break; } + case AS_STROKE_POLYGON: + { + BRect polyframe; + bool isclosed; + int32 pointcount; + BPoint *pointlist; + + fSession->Read(&polyframe); + fSession->Read(&isclosed); + fSession->Read(&pointcount); + + pointlist=new BPoint[pointcount]; + + for(int32 i=0; iConvertToTop(pointlist[i]); + + // TODO: modify DisplayDriver::StrokePolygon to utilize a boundary BRect + desktop->GetDisplayDriver()->StrokePolygon(pointlist,pointcount,polyframe, + cl->fLayerData,isclosed); + + delete [] pointlist; + + break; + } + case AS_FILL_POLYGON: + { + BRect polyframe; + bool isclosed; + int32 pointcount; + BPoint *pointlist; + + fSession->Read(&polyframe); + fSession->Read(&isclosed); + fSession->Read(&pointcount); + + pointlist=new BPoint[pointcount]; + + fSession->Read(pointlist, sizeof(BPoint)*pointcount); + + for(int32 i=0; iConvertToTop(pointlist[i]); + + // TODO: modify DisplayDriver::FillPolygon to utilize a boundary BRect + desktop->GetDisplayDriver()->StrokePolygon(pointlist,pointcount,polyframe,cl->fLayerData); + + delete [] pointlist; + + break; + } + case AS_STROKE_SHAPE: + { + BRect shaperect; + int32 opcount; + int32 ptcount; + int32 *oplist; + BPoint *ptlist; + + fSession->Read(&shaperect); + fSession->Read(&opcount); + fSession->Read(&ptcount); + + oplist=new int32[opcount]; + ptlist=new BPoint[ptcount]; + + fSession->Read(oplist,sizeof(int32)*opcount); + fSession->Read(ptlist,sizeof(BPoint)*ptcount); + + for(int32 i=0; iConvertToTop(ptlist[i]); + + desktop->GetDisplayDriver()->StrokeShape(shaperect, opcount, oplist, ptcount, ptlist, cl->fLayerData); + delete oplist; + delete ptlist; + + break; + } + case AS_FILL_SHAPE: + { + BRect shaperect; + int32 opcount; + int32 ptcount; + int32 *oplist; + BPoint *ptlist; + + fSession->Read(&shaperect); + fSession->Read(&opcount); + fSession->Read(&ptcount); + + oplist=new int32[opcount]; + ptlist=new BPoint[ptcount]; + + fSession->Read(oplist,sizeof(int32)*opcount); + fSession->Read(ptlist,sizeof(BPoint)*ptcount); + + for(int32 i=0; iConvertToTop(ptlist[i]); + + desktop->GetDisplayDriver()->FillShape(shaperect, opcount, oplist, ptcount, ptlist, cl->fLayerData); + + delete oplist; + delete ptlist; + + break; + } + case AS_FILL_REGION: + { + // TODO: Implement AS_FILL_REGION + int32 rectcount; + BRect *rectlist; + + fSession->Read(&rectcount); + + rectlist=new BRect[rectcount]; + + fSession->Read(rectlist, sizeof(BRect)*rectcount); + + // Between the client-side conversion to BRects from clipping_rects to the overhead + // in repeatedly calling FillRect(), this is definitely in need of optimization. At + // least it works for now. :) + for(int32 i=0; iGetDisplayDriver()->FillRect(cl->ConvertToTop(cl->ConvertToTop(rectlist[i])),cl->fLayerData); + + delete [] rectlist; + + // TODO: create support for clipping_rect usage for faster BRegion display. + // Tweaks to DisplayDriver are necessary along with conversion routines in Layer + + break; + } + case AS_STROKE_LINEARRAY: + { + // TODO: Implement AS_STROKE_LINEARRAY + break; + } + case AS_MOVEPENBY: + { + // TODO: Implement AS_MOVEPENBY + break; + } + case AS_MOVEPENTO: + { + // TODO: Implement AS_MOVEPENTO + break; + } + case AS_SETPENSIZE: + { + // TODO: Implement AS_SETPENSIZE + break; + } + case AS_DRAW_STRING: + { + // TODO: Implement AS_DRAW_STRING + break; + } + case AS_SET_FONT: + { + // TODO: Implement AS_SET_FONT + break; + } + case AS_SET_FONT_SIZE: + { + // TODO: Implement AS_SET_FONT_SIZE + break; + } default: { printf("ServerWindow %s received unexpected code - message offset %lx\n",fTitle.String(), code - SERVER_TRUE); @@ -1890,138 +2050,6 @@ void ServerWindow::DispatchMessage(int32 code) } } //------------------------------------------------------------------------------ -/*! - \brief Iterator for graphics update messages - \param msgsize Size of the buffer containing the graphics messages - \param msgbuffer Buffer containing the graphics message -*/ -void ServerWindow::DispatchGraphicsMessage(int32 msgsize, int8 *msgbuffer) -{ -/* Layer *layer; - LayerData *layerdata; - int32 code; - int32 view_token; - uint32 sizeRemaining = (uint32)msgsize; - BRegion WindowClipRegion; - BRegion LayerClipRegion; -// Layer *sibling; - int32 numRects = 0; - - if (!msgsize || !msgbuffer) - return; - if (IsHidden()) - return; - - // TODO: fix sibling-related clipping calculations in DispatchGraphicsMessage -// WindowClipRegion.Set(fWinBorder->Frame()); -// sibling = fWinBorder->UpperSibling(); -// while (sibling) -// { -// WindowClipRegion.Exclude(sibling->Frame()); -// sibling = sibling->UpperSibling(); -// } - - - if (!WindowClipRegion.Frame().IsValid()) - return; - - // We need to decide whether coordinates are specified in view or root coordinates. - // For now, we assume root level coordinates. - code = AS_BEGIN_UPDATE; - while ((sizeRemaining > 2*sizeof(int32)) && (code != AS_END_UPDATE)) - { - code = read_from_buffer(&msgbuffer); - view_token = read_from_buffer(&msgbuffer); - - //TODO: fix code to find a layer based on a view token in DispatchGraphicsMessage - layer = NULL;//fWorkspace->GetRoot()->FindLayer(view_token); - - if (layer) - { - layerdata = layer->fLayerData; - LayerClipRegion.Set(layer->Frame()); - LayerClipRegion.IntersectWith(&WindowClipRegion); - numRects = LayerClipRegion.CountRects(); - } - else - { - layerdata = NULL; - STRACE(("ServerWindow %s received invalid view token %lx",fTitle.String(),view_token)); - } - - switch (code) - { - case AS_STROKE_LINEARRAY: - { - // TODO: Implement AS_STROKE_LINEARRAY - break; - } - case AS_STROKE_POLYGON: - { - // TODO: Implement AS_STROKE_POLYGON - break; - } - case AS_STROKE_SHAPE: - { - // TODO: Implement AS_STROKE_SHAPE - break; - } - case AS_FILL_POLYGON: - { - // TODO: Implement AS_FILL_POLYGON - break; - } - case AS_FILL_REGION: - { - // TODO: Implement AS_FILL_REGION - break; - } - case AS_FILL_SHAPE: - { - // TODO: Implement AS_FILL_SHAPE - break; - } - case AS_MOVEPENBY: - { - // TODO: Implement AS_MOVEPENBY - break; - } - case AS_MOVEPENTO: - { - // TODO: Implement AS_MOVEPENTO - break; - } - case AS_SETPENSIZE: - { - // TODO: Implement AS_SETPENSIZE - break; - } - case AS_DRAW_STRING: - { - // TODO: Implement AS_DRAW_STRING - break; - } - case AS_SET_FONT: - { - // TODO: Implement AS_SET_FONT - break; - } - case AS_SET_FONT_SIZE: - { - // TODO: Implement AS_SET_FONT_SIZE - break; - } - default: - { - sizeRemaining -= sizeof(int32); - printf("ServerWindow %s received unexpected graphics code %lx",fTitle.String(),code); - break; - } - } - } -*/ -} -//------------------------------------------------------------------------------ /*! \brief Message-dispatching loop for the ServerWindow diff --git a/src/servers/app/server/ServerWindow.h b/src/servers/app/server/ServerWindow.h index f88f3dd4e3..7c664d1434 100644 --- a/src/servers/app/server/ServerWindow.h +++ b/src/servers/app/server/ServerWindow.h @@ -126,7 +126,6 @@ private: // message handle methods. void DispatchMessage(int32 code); - void DispatchGraphicsMessage(int32 msgsize, int8 *msgbuffer); static int32 MonitorWin(void *data); diff --git a/src/servers/app/server/Utils.cpp b/src/servers/app/server/Utils.cpp index 1102d293fa..81b449cec0 100644 --- a/src/servers/app/server/Utils.cpp +++ b/src/servers/app/server/Utils.cpp @@ -301,3 +301,27 @@ status_t ConvertModeToDisplayMode(uint32 mode, display_mode *dmode) } return B_OK; } + +BRect CalculatePolygonBounds(BPoint *pts, int32 pointcount) +{ + if(!pts) + return BRect(0,0,0,0); + + BRect r(0,0,0,0); + + // shamelessly stolen from Marc's BPolygon code and tweaked to fit. :P + r = BRect(pts[0], pts[0]); + + for (int32 i = 1; i < 4; i++) + { + if (pts[i].x < r.left) + r.left = pts[i].x; + if (pts[i].y < r.top) + r.top = pts[i].y; + if (pts[i].x > r.right) + r.right = pts[i].x; + if (pts[i].y > r.bottom) + r.bottom = pts[i].y; + } + return r; +} diff --git a/src/servers/app/server/Utils.h b/src/servers/app/server/Utils.h index 30007899b5..c14b4d571e 100644 --- a/src/servers/app/server/Utils.h +++ b/src/servers/app/server/Utils.h @@ -35,5 +35,5 @@ void SendMessage(port_id port, BMessage *message, int32 target=-1); const char *MsgCodeToString(int32 code); BString MsgCodeToBString(int32 code); status_t ConvertModeToDisplayMode(uint32 mode, display_mode *dmode); - +BRect CalculatePolygonBounds(BPoint *pts, int32 pointcount); #endif