1 #include "PathView.h" 2 #include "LinePathBuilder.h" 3 #include <InterfaceKit.h> 4 5 class ShapeLPB : public LinePathBuilder 6 { 7 BShape fShape; 8 9 protected: 10 virtual void MoveTo(BPoint p); 11 virtual void LineTo(BPoint p); 12 virtual void BezierTo(BPoint* p); 13 virtual void ClosePath(void); 14 15 public: 16 ShapeLPB(SubPath *subPath, float penSize, cap_mode capMode, join_mode joinMode, float miterLimit); 17 BShape *Shape() { return &fShape; } 18 }; 19 20 ShapeLPB::ShapeLPB(SubPath *subPath, float penSize, cap_mode capMode, join_mode joinMode, float miterLimit) 21 : LinePathBuilder(subPath, penSize, capMode, joinMode, miterLimit) 22 { 23 } 24 25 void ShapeLPB::MoveTo(BPoint p) 26 { 27 fShape.MoveTo(p); 28 } 29 30 void ShapeLPB::LineTo(BPoint p) 31 { 32 fShape.LineTo(p); 33 } 34 35 void ShapeLPB::BezierTo(BPoint p[3]) 36 { 37 fShape.BezierTo(p); 38 } 39 40 void ShapeLPB::ClosePath(void) 41 { 42 fShape.Close(); 43 } 44 45 PathView::PathView(BRect rect) 46 : BView(rect, NULL, B_FOLLOW_ALL_SIDES, B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE | B_SUBPIXEL_PRECISE) { 47 //SetViewColor(B_TRANSPARENT_COLOR); 48 fMode = kStroke; 49 fCurPoint = -1; 50 fWidth = 16; 51 } 52 53 void PathView::Draw(BRect updateRect) { 54 if (fMode == kDrawOutline) { 55 56 } else if (fMode == kStroke) { 57 const int n = fPath.CountPoints(); 58 BShape shape; 59 for (int i = 0; i < n; i++) { 60 if (i == 0) 61 shape.MoveTo(fPath.PointAt(i)); 62 else 63 shape.LineTo(fPath.PointAt(i)); 64 } 65 if (fPath.IsClosed()) shape.Close(); 66 SetPenSize(fWidth); 67 StrokeShape(&shape); 68 69 ShapeLPB path(&fPath, fWidth, LineCapMode(), LineJoinMode(), LineMiterLimit()); 70 path.CreateLinePath(); 71 SetPenSize(1); 72 73 BPicture picture; 74 BeginPicture(&picture); 75 FillShape(path.Shape()); 76 EndPicture(); 77 78 PushState(); 79 ClipToPicture(&picture); 80 SetHighColor(0, 255, 0); 81 FillRect(Bounds()); 82 PopState(); 83 84 SetOrigin(200, 0); 85 SetHighColor(255, 0, 0); 86 StrokeShape(path.Shape()); 87 Flush(); 88 } 89 } 90 91 void PathView::MouseDown(BPoint point) { 92 uint32 buttons; 93 GetMouse(&point, &buttons, false); 94 95 if (buttons == B_SECONDARY_MOUSE_BUTTON) { 96 fCurPoint = fPath.CountPoints(); 97 fPath.AddPoint(point); 98 } else { 99 float d = 100000000000.0; 100 for (int i = 0; i < fPath.CountPoints(); i++) { 101 BPoint p = point - fPath.PointAt(i); 102 float e = p.x*p.x + p.y*p.y; 103 if (e < d) { fCurPoint = i; d = e; } 104 } 105 fPath.AtPut(fCurPoint, point); 106 } 107 Invalidate(); 108 } 109 110 void PathView::MouseMoved(BPoint point, uint32 transit, const BMessage *message) { 111 if (fCurPoint != -1) { 112 fPath.AtPut(fCurPoint, point); 113 Invalidate(); 114 } 115 } 116 117 void PathView::MouseUp(BPoint point) { 118 fCurPoint = -1; 119 } 120 121 void PathView::SetClose(bool close) { 122 if (close) fPath.Close(); 123 else fPath.Open(); 124 } 125