''
'' This code is part of Document Solutions for Imaging demos.
'' Copyright (c) MESCIUS inc. All rights reserved.
''
Imports System
Imports System.IO
Imports System.Drawing
Imports System.Numerics
Imports GrapeCity.Documents.Drawing
Imports GrapeCity.Documents.Text
Imports GrapeCity.Documents.Imaging
Imports GrapeCity.Documents.Svg
Imports GCTEXT = GrapeCity.Documents.Text
Imports GCDRAW = GrapeCity.Documents.Drawing
'' This example shows how to render an arch on GcSvgGraphics
'' using graphics paths. It also shows how a path can be used
'' to clip the drawing, and how to draw raster images
'' on GcSvgGraphics.
'' The arch drawing code is similar to that used in SvgGraphicsArch.
Public Class SvgGraphicsPicInArch
Public ReadOnly Property DefaultMime As String
Get
Return Util.MimeTypes.SVG
End Get
End Property
Public Function GenerateImageStream(
ByVal targetMime As String,
ByVal pixelSize As Size,
ByVal dpi As Single,
ByVal opaque As Boolean,
Optional ByVal sampleParams As String() = Nothing) As Stream
If targetMime <> Util.MimeTypes.SVG Then
Throw New Exception("This sample only supports SVG output format.")
End If
'' Note that the foreground image is a PNG with some transparency:
Dim imageFn As String = Path.Combine("Resources", "ImagesBis", "minerva-masked.png")
Dim backFn As String = Path.Combine("Resources", "Images", "colosseum.jpg")
Dim background As Color = Color.FromArgb(230, 153, 77)
Dim line As Color = Color.FromArgb(102, 34, 0)
Dim arch As Color = Color.FromArgb(147, 78, 31)
Dim archBack As Color = Color.FromArgb(0, 191, 255)
Dim fill As Color = Color.FromArgb(255, 171, 145)
Dim marks As Color = Color.FromArgb(170, 62, 9)
Dim text As Color = Color.Black
Dim textBack As Color = Color.Cornsilk
Dim Inch = dpi
Dim ms = New MemoryStream()
Using g As New GcSvgGraphics(pixelSize.Width, pixelSize.Height)
If opaque Then
g.FillRectangle(New RectangleF(0, 0, g.Width, g.Height), background)
End If
'' Arc bounding rectangle:
Dim rc = New RectangleF(0, 0, Inch * 5, Inch * 6.4F)
'' Use transform to center all drawing:
Dim t = g.Transform
g.Transform = Matrix3x2.CreateTranslation(g.Width / 2 - rc.Width / 2, g.Height / 2 - rc.Height / 2)
'' Load and flip the foreground and background images.
Using bmp0 As New GcBitmap(imageFn),
bmp As GcBitmap = bmp0.FlipRotate(FlipRotateAction.FlipHorizontal),
backBmpT As New GcBitmap(backFn),
backBmp As GcBitmap = backBmpT.FlipRotate(FlipRotateAction.FlipHorizontal)
'' Draw the arch and images inside:
Dim innerPath = DrawArch(g, rc, rc.Height * 0.35F, rc.Width * 0.08F, line, arch, fill)
Using clip = g.PushClip(innerPath)
'' Fill background with a color to tint the background, draw background semi-transparently,
'' draw foreground opaque (but it has transparent pixels):
g.FillRectangle(rc, archBack)
Dim ia = New ImageAlign(ImageAlignHorz.Center, ImageAlignVert.Center, True, True, True, False, False)
g.DrawImage(backBmp, rc, rc, ia, 0.7F)
g.DrawImage(bmp, rc, rc, ia, 1.0F)
End Using
'' Add a label:
Dim tf = New TextFormat() With {
.Font = GCTEXT.Font.FromFile(Path.Combine("Resources", "Fonts", "FreeSerif.ttf")),
.FontSize = Inch / 6,
.ForeColor = text
}
'' g.DrawString("ARCH", tf, rc, TextAlignment.Center, ParagraphAlignment.Center, False)
'' Measurement lines:
Dim w = Inch / 8
Dim pen = New GCDRAW.Pen(marks)
Dim txt = $"{(rc.Width / Inch):F}"""
Dim s = g.MeasureString(txt, tf)
Dim d = s.Height * 1.5F
g.DrawLine(rc.Left, rc.Top - d, rc.Right, rc.Top - d, pen)
g.DrawLine(rc.Left, rc.Top - d, rc.Left + w, rc.Top - d - w, pen)
g.DrawLine(rc.Left, rc.Top - d, rc.Left + w, rc.Top - d + w, pen)
g.DrawLine(rc.Right, rc.Top - d, rc.Right - w, rc.Top - d - w, pen)
g.DrawLine(rc.Right, rc.Top - d, rc.Right - w, rc.Top - d + w, pen)
Dim rcTxt = New RectangleF(rc.Left + rc.Width / 2 - s.Width / 2, rc.Top - d - s.Height / 2, s.Width, s.Height)
rcTxt.Inflate(2, 2)
g.FillRectangle(rcTxt, textBack)
g.DrawString(txt, tf, rcTxt, TextAlignment.Center, ParagraphAlignment.Center, False)
txt = $"{(rc.Height / Inch):F}"""
s = g.MeasureString(txt, tf)
d = s.Width
g.DrawLine(rc.Left - d, rc.Top, rc.Left - d, rc.Bottom, pen)
g.DrawLine(rc.Left - d, rc.Top, rc.Left - d - w, rc.Top + w, pen)
g.DrawLine(rc.Left - d, rc.Top, rc.Left - d + w, rc.Top + w, pen)
g.DrawLine(rc.Left - d, rc.Bottom, rc.Left - d - w, rc.Bottom - w, pen)
g.DrawLine(rc.Left - d, rc.Bottom, rc.Left - d + w, rc.Bottom - w, pen)
rcTxt = New RectangleF(rc.Left - d - s.Width / 2, rc.Top + rc.Height / 2 - s.Height / 2, s.Width, s.Height)
rcTxt.Inflate(2, 2)
g.FillRectangle(rcTxt, textBack)
g.DrawString(txt, tf, rcTxt, TextAlignment.Center, ParagraphAlignment.Center, False)
'' Restore transform:
g.Transform = t
'' Done:
Dim svg = g.ToSvgDocument()
svg.Save(ms)
ms.Seek(0, SeekOrigin.Begin)
End Using
End Using
Return ms
End Function
Private Function DrawArch(g As GcGraphics, rc As RectangleF, harc As Single, wd As Single, line As Color, arch As Color, fill As Color) As IPath
Dim path = g.CreatePath()
'' Insides filler (start from bottom left, to clockwise):
path.BeginFigure(rc.Left + wd, rc.Bottom - wd)
path.AddLine(rc.Left + wd, rc.Top + harc)
path.AddArc(New ArcSegment() With {
.ArcSize = ArcSize.Small,
.Point = New PointF(rc.Right - wd, rc.Top + harc),
.RotationAngle = 0,
.Size = New SizeF(rc.Width / 2.0F - wd, harc - wd),
.SweepDirection = SweepDirection.Clockwise
})
path.AddLine(rc.Right - wd, rc.Bottom - wd)
path.EndFigure(FigureEnd.Closed)
g.FillPath(path, fill)
Dim innerPath = path '' keep for clipping
'' Arc outlines (start from bottom left, to clockwise):
path = g.CreatePath()
path.BeginFigure(rc.Left, rc.Bottom)
path.AddLine(rc.Left, rc.Top + harc)
path.AddLine(rc.Left + wd, rc.Top + harc)
path.AddLine(rc.Left + wd, rc.Bottom - wd)
path.EndFigure(FigureEnd.Closed)
path.BeginFigure(rc.Left, rc.Top + harc)
path.AddArc(New ArcSegment() With {
.ArcSize = ArcSize.Small,
.Point = New PointF(rc.Right, rc.Top + harc),
.RotationAngle = 0,
.Size = New SizeF(rc.Width / 2.0F, harc),
.SweepDirection = SweepDirection.Clockwise
})
path.AddLine(rc.Right - wd, rc.Top + harc)
path.AddArc(New ArcSegment() With {
.ArcSize = ArcSize.Small,
.Point = New PointF(rc.Left + wd, rc.Top + harc),
.RotationAngle = 0,
.Size = New SizeF(rc.Width / 2.0F - wd, harc - wd),
.SweepDirection = SweepDirection.CounterClockwise
})
path.EndFigure(FigureEnd.Closed)
path.BeginFigure(rc.Right, rc.Top + harc)
path.AddLine(rc.Right, rc.Bottom)
path.AddLine(rc.Right - wd, rc.Bottom - wd)
path.AddLine(rc.Right - wd, rc.Top + harc)
path.EndFigure(FigureEnd.Closed)
path.BeginFigure(rc.Right, rc.Bottom)
path.AddLine(rc.Left, rc.Bottom)
path.AddLine(rc.Left + wd, rc.Bottom - wd)
path.AddLine(rc.Right - wd, rc.Bottom - wd)
path.EndFigure(FigureEnd.Closed)
g.FillPath(path, arch)
g.DrawPath(path, New GCDRAW.Pen(line, 2))
path.Dispose()
Return innerPath
End Function
End Class