Skip to content

Commit 762e607

Browse files
author
ArthurHub
committed
nicer arc's api
1 parent 8bcfbd4 commit 762e607

6 files changed

Lines changed: 87 additions & 24 deletions

File tree

Source/HtmlRenderer.PdfSharp/Adapters/GraphicsPathAdapter.cs

Lines changed: 31 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
// - Sun Tsu,
1111
// "The Art of War"
1212

13+
using System;
1314
using HtmlRenderer.Adapters;
1415
using HtmlRenderer.Adapters.Entities;
1516
using PdfSharp.Drawing;
@@ -50,15 +51,41 @@ public override void LineTo(double x, double y)
5051
_lastPoint = new RPoint(x, y);
5152
}
5253

53-
public override void ArcTo(double x, double y, double size, int startAngle, int sweepAngle)
54+
public override void ArcTo(double x, double y, double size, Corner corner)
5455
{
55-
float left = (float)(System.Math.Min(x, _lastPoint.X) - (startAngle == 270 || startAngle == 0 ? size : 0));
56-
float top = (float)(System.Math.Min(y, _lastPoint.Y) - (startAngle == 90 || startAngle == 0 ? size : 0));
57-
_graphicsPath.AddArc(left, top, (float)size * 2, (float)size * 2, startAngle, sweepAngle);
56+
float left = (float)(Math.Min(x, _lastPoint.X) - (corner == Corner.TopRight || corner == Corner.BottomRight ? size : 0));
57+
float top = (float)(Math.Min(y, _lastPoint.Y) - (corner == Corner.BottomLeft || corner == Corner.BottomRight ? size : 0));
58+
_graphicsPath.AddArc(left, top, (float)size * 2, (float)size * 2, GetStartAngle(corner), 90);
5859
_lastPoint = new RPoint(x, y);
5960
}
6061

6162
public override void Dispose()
6263
{ }
64+
65+
/// <summary>
66+
/// Get arc start angle for the given corner.
67+
/// </summary>
68+
private static int GetStartAngle(Corner corner)
69+
{
70+
int startAngle;
71+
switch (corner)
72+
{
73+
case Corner.TopLeft:
74+
startAngle = 180;
75+
break;
76+
case Corner.TopRight:
77+
startAngle = 270;
78+
break;
79+
case Corner.BottomLeft:
80+
startAngle = 90;
81+
break;
82+
case Corner.BottomRight:
83+
startAngle = 0;
84+
break;
85+
default:
86+
throw new ArgumentOutOfRangeException("corner");
87+
}
88+
return startAngle;
89+
}
6390
}
6491
}

Source/HtmlRenderer.WPF/Adapters/GraphicsPathAdapter.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ public override void LineTo(double x, double y)
4646
_geometryContext.LineTo(new Point(x, y), true, true);
4747
}
4848

49-
public override void ArcTo(double x, double y, double size, int i, int i1)
49+
public override void ArcTo(double x, double y, double size, Corner corner)
5050
{
5151
_geometryContext.ArcTo(new Point(x, y), new Size(size, size), 0, false, SweepDirection.Clockwise, true, true);
5252
}

Source/HtmlRenderer.WinForms/Adapters/GraphicsPathAdapter.cs

Lines changed: 30 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -51,11 +51,11 @@ public override void LineTo(double x, double y)
5151
_lastPoint = new RPoint(x, y);
5252
}
5353

54-
public override void ArcTo(double x, double y, double size, int startAngle, int sweepAngle)
54+
public override void ArcTo(double x, double y, double size, Corner corner)
5555
{
56-
float left = (float)(Math.Min(x, _lastPoint.X) - (startAngle == 270 || startAngle == 0 ? size : 0));
57-
float top = (float)(Math.Min(y, _lastPoint.Y) - (startAngle == 90 || startAngle == 0 ? size : 0));
58-
_graphicsPath.AddArc(left, top, (float)size*2, (float)size*2, startAngle, sweepAngle);
56+
float left = (float)(Math.Min(x, _lastPoint.X) - (corner == Corner.TopRight || corner == Corner.BottomRight ? size : 0));
57+
float top = (float)(Math.Min(y, _lastPoint.Y) - (corner == Corner.BottomLeft || corner == Corner.BottomRight ? size : 0));
58+
_graphicsPath.AddArc(left, top, (float)size * 2, (float)size * 2, GetStartAngle(corner), 90);
5959
_lastPoint = new RPoint(x, y);
6060
}
6161

@@ -66,5 +66,31 @@ public override void Dispose()
6666
{
6767
_graphicsPath.Dispose();
6868
}
69+
70+
/// <summary>
71+
/// Get arc start angle for the given corner.
72+
/// </summary>
73+
private static int GetStartAngle(Corner corner)
74+
{
75+
int startAngle;
76+
switch (corner)
77+
{
78+
case Corner.TopLeft:
79+
startAngle = 180;
80+
break;
81+
case Corner.TopRight:
82+
startAngle = 270;
83+
break;
84+
case Corner.BottomLeft:
85+
startAngle = 90;
86+
break;
87+
case Corner.BottomRight:
88+
startAngle = 0;
89+
break;
90+
default:
91+
throw new ArgumentOutOfRangeException("corner");
92+
}
93+
return startAngle;
94+
}
6995
}
7096
}

Source/HtmlRenderer/Adapters/RGraphicsPath.cs

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,12 +32,22 @@ public abstract class RGraphicsPath : IDisposable
3232
/// <summary>
3333
/// Add circular arc of the given size to the given point from the last point.
3434
/// </summary>
35-
public abstract void ArcTo(double x, double y, double size, int startAngle, int sweepAngle);
35+
public abstract void ArcTo(double x, double y, double size, Corner corner);
3636

3737
/// <summary>
3838
/// Release path resources.
3939
/// </summary>
4040
public abstract void Dispose();
41-
41+
42+
/// <summary>
43+
/// The 4 corners that are handled in arc rendering.
44+
/// </summary>
45+
public enum Corner
46+
{
47+
TopLeft,
48+
TopRight,
49+
BottomLeft,
50+
BottomRight,
51+
}
4252
}
4353
}

Source/HtmlRenderer/Core/Handlers/BordersDrawHandler.cs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -212,12 +212,12 @@ private static RGraphicsPath GetRoundedBorderPath(RGraphics g, Border border, Cs
212212
path.Start(r.Left + b.ActualBorderLeftWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNw);
213213

214214
if (b.ActualCornerNw > 0)
215-
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2 + b.ActualCornerNw, r.Top + b.ActualBorderTopWidth / 2, b.ActualCornerNw, 180, 90);
215+
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2 + b.ActualCornerNw, r.Top + b.ActualBorderTopWidth / 2, b.ActualCornerNw, RGraphicsPath.Corner.TopLeft);
216216

217217
path.LineTo(r.Right - b.ActualBorderRightWidth / 2 - b.ActualCornerNe, r.Top + b.ActualBorderTopWidth / 2);
218218

219219
if (b.ActualCornerNe > 0)
220-
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNe, b.ActualCornerNe, 270, 90);
220+
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNe, b.ActualCornerNe, RGraphicsPath.Corner.TopRight);
221221
}
222222
break;
223223
case Border.Bottom:
@@ -227,12 +227,12 @@ private static RGraphicsPath GetRoundedBorderPath(RGraphics g, Border border, Cs
227227
path.Start(r.Right - b.ActualBorderRightWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSe);
228228

229229
if (b.ActualCornerSe > 0)
230-
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2 - b.ActualCornerSe, r.Bottom - b.ActualBorderBottomWidth / 2, b.ActualCornerSe, 0, 90);
230+
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2 - b.ActualCornerSe, r.Bottom - b.ActualBorderBottomWidth / 2, b.ActualCornerSe, RGraphicsPath.Corner.BottomRight);
231231

232232
path.LineTo(r.Left + b.ActualBorderLeftWidth / 2 + b.ActualCornerSw, r.Bottom - b.ActualBorderBottomWidth / 2);
233233

234234
if (b.ActualCornerSw > 0)
235-
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSw, b.ActualCornerSw, 90, 90);
235+
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSw, b.ActualCornerSw, RGraphicsPath.Corner.BottomLeft);
236236
}
237237
break;
238238
case Border.Right:
@@ -245,12 +245,12 @@ private static RGraphicsPath GetRoundedBorderPath(RGraphics g, Border border, Cs
245245
path.Start(r.Right - b.ActualBorderRightWidth / 2 - (noTop ? b.ActualCornerNe : 0), r.Top + b.ActualBorderTopWidth / 2 + (noTop ? 0 : b.ActualCornerNe));
246246

247247
if (b.ActualCornerNe > 0 && noTop)
248-
path.ArcTo(r.Right - b.ActualBorderLeftWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNe, b.ActualCornerNe, 270, 90);
248+
path.ArcTo(r.Right - b.ActualBorderLeftWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNe, b.ActualCornerNe, RGraphicsPath.Corner.TopRight);
249249

250250
path.LineTo(r.Right - b.ActualBorderRightWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSe);
251251

252252
if (b.ActualCornerSe > 0 && noBottom)
253-
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2 - b.ActualCornerSe, r.Bottom - b.ActualBorderBottomWidth / 2, b.ActualCornerSe, 0, 90);
253+
path.ArcTo(r.Right - b.ActualBorderRightWidth / 2 - b.ActualCornerSe, r.Bottom - b.ActualBorderBottomWidth / 2, b.ActualCornerSe, RGraphicsPath.Corner.BottomRight);
254254
}
255255
break;
256256
case Border.Left:
@@ -263,12 +263,12 @@ private static RGraphicsPath GetRoundedBorderPath(RGraphics g, Border border, Cs
263263
path.Start(r.Left + b.ActualBorderLeftWidth / 2 + (noBottom ? b.ActualCornerSw : 0), r.Bottom - b.ActualBorderBottomWidth / 2 - (noBottom ? 0 : b.ActualCornerSw));
264264

265265
if (b.ActualCornerSw > 0 && noBottom)
266-
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSw, b.ActualCornerSw, 90, 90);
266+
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2, r.Bottom - b.ActualBorderBottomWidth / 2 - b.ActualCornerSw, b.ActualCornerSw, RGraphicsPath.Corner.BottomLeft);
267267

268268
path.LineTo(r.Left + b.ActualBorderLeftWidth / 2, r.Top + b.ActualBorderTopWidth / 2 + b.ActualCornerNw);
269269

270270
if (b.ActualCornerNw > 0 && noTop)
271-
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2 + b.ActualCornerNw, r.Top + b.ActualBorderTopWidth / 2, b.ActualCornerNw, 180, 90);
271+
path.ArcTo(r.Left + b.ActualBorderLeftWidth / 2 + b.ActualCornerNw, r.Top + b.ActualBorderTopWidth / 2, b.ActualCornerNw, RGraphicsPath.Corner.TopLeft);
272272
}
273273
break;
274274
}

Source/HtmlRenderer/Core/Utils/RenderUtils.cs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -128,22 +128,22 @@ public static RGraphicsPath GetRoundRect(RGraphics g, RRect rect, double nwRadiu
128128
path.LineTo(rect.Right - neRadius, rect.Y);
129129

130130
if (neRadius > 0f)
131-
path.ArcTo(rect.Right, rect.Top + neRadius, neRadius, 270, 90);
131+
path.ArcTo(rect.Right, rect.Top + neRadius, neRadius, RGraphicsPath.Corner.TopRight);
132132

133133
path.LineTo(rect.Right, rect.Bottom - seRadius);
134134

135135
if (seRadius > 0f)
136-
path.ArcTo(rect.Right - seRadius, rect.Bottom, seRadius, 0, 90);
136+
path.ArcTo(rect.Right - seRadius, rect.Bottom, seRadius, RGraphicsPath.Corner.BottomRight);
137137

138138
path.LineTo(rect.Left + swRadius, rect.Bottom);
139139

140140
if (swRadius > 0f)
141-
path.ArcTo(rect.Left, rect.Bottom - swRadius, swRadius, 90, 90);
141+
path.ArcTo(rect.Left, rect.Bottom - swRadius, swRadius, RGraphicsPath.Corner.BottomLeft);
142142

143-
path.LineTo(rect.Left, rect.Top + swRadius);
143+
path.LineTo(rect.Left, rect.Top + nwRadius);
144144

145145
if (nwRadius > 0f)
146-
path.ArcTo(rect.Left + nwRadius, rect.Top, swRadius, 180, 90);
146+
path.ArcTo(rect.Left + nwRadius, rect.Top, nwRadius, RGraphicsPath.Corner.TopLeft);
147147

148148
return path;
149149
}

0 commit comments

Comments
 (0)