Drawings
Create drawings using canvases and shapes. You can combine lines and curves
with fill patterns using a variety of colors and styles.
View on YouTube
Shapes
A
Shape
formatter holds a group of open or closed paths. Here the path is a simple line segment.
LineSize
=
LessonExample
.
FontHeight
*
0.5;
readonly
Stroke
Stroke1
=
new
(
LineSize
);
LineSeg
=
Canvas
(
ExtentWidth
*
50%,
ExtentWidth
*
10%) {
Margin
:
LineSize
;
Shape
(
null
,
Stroke1
) {
OpenPath
(0, 0) {
LineTo
(33%, 100%);
};
};
};
Open Paths
Make an open line path using the
OpenPath
formatterThe arguments are the starting point of the
shape.
ZigZag
(
Stroke
stroke
)
=
Canvas
(
ExtentWidth
*
50%,
ExtentWidth
*
10%) {
Margin
:
LineSize
;
Shape
(
null
,
stroke
) {
OpenPath
(0, 0) {
LineTo
(33%, 100%);
LineTo
(66%, 0);
LineTo
(100%, 100%);
}
};
};
BlackZigZag
=
ZigZag
(
Stroke1
);
Color options
Change the color of the line with the 2nd parameter of the
Stroke
constructor.
Stroke
LS1
=
new
(
LineSize
,
Colors
.
Red
);
Line1
=
ZigZag
(
LS1
);
Line Styles
Change the style of the line using LineStyles, the 3rd parameter of the
Stroke
constructor.
Stroke
LS2
=
new
(
LineSize
,
Colors
.
Red
,
Dotted
);
Line2
=
ZigZag
(
LS2
);
Line Style Gallery
Use a loop to enumerate the different
LineStyles
options.
DrawLineStyle
(
LineStyles
linestyle
)
=
Canvas
(40%,
LessonExample
.
FontHeight
) {
Shape
(
null
,
new
(
LineSize
,
Colors
.
Black
,
linestyle
,
Flat
)) {
OpenPath
(0, 50%) {
LineTo
(100%, 50%)};
};
};
LineStyleList
=
TwoColumTable
{
foreach
(
var
style
in
LineStyles
)
Row
{
style
.
Name
;
DrawLineStyle
(
style
)};
};
Solid
Dashed
Dotted
DashDot
DashDotDot
Line Caps
Change the LineCap style using the 4th parameter of the
Stroke
constructor.
Stroke
LS3
=
new
(
LineSize
,
Colors
.
Red
,
Dotted
,
Round
);
Line3
=
ZigZag
(
LS3
);
Line Cap Gallery
Iterate over the different
LineCaps
options.
DrawLineCap
(
LineCaps
cap
)
=
Canvas
(10%,
LessonExample
.
FontHeight
*
2) {
Shape
(
null
,
new
(
LineSize
*
2,
Colors
.
Black
,
LineStyles
.
Solid
,
cap
)) {
OpenPath
(0, 50%) {
LineTo
(100%, 50%);}
};
Shape
(
null
,
new
(
LineSize
*
0.25,
Colors
.
Red
,
LineStyles
.
Solid
,
cap
)) {
OpenPath
(0, 50%) {
LineTo
(100%, 50%);}
};
};
LineCapTable
=
TwoColumTable
{
foreach
(
var
cap
in
LineCaps
)
Row
{
cap
.
Name
;
DrawLineCap
(
cap
)};
};
Flat
Square
Round
Line Joins
Change the LineJoin style using the 5th parameter of the
Stroke
constructor.
Stroke
LS4
=
new
(
LineSize
*
2,
Colors
.
Blue
,
Solid
,
Flat
,
Round
);
Line4
=
ZigZag
(
LS4
);
Line Join Gallery
Loop over the different
LineJoins
options.
DrawLineJoin
(
LineJoins
linejoin
)
=
Canvas
(7%,
LessonExample
.
FontHeight
*
2) {
VAlign
:
Center
;
Shape
(
null
,
new
(
LineSize
,
Colors
.
Black
,
Solid
,
Flat
,
linejoin
)) {
OpenPath
(0) {
LineTo
(50%, 70%);
LineTo
(100%, 0)};
};
};
LineJoinTable
=
TwoColumTable
{
foreach
(
var
linejoin
in
LineJoins
)
Row
{
linejoin
.
Name
;
DrawLineJoin
(
linejoin
)};
};
Miter
Round
Bevel
Miter limit
Use the miterlimit parameter to limit the ratio of the extent of a miter join to the stroke size
(default: 4.0).
DrawMiterJoin
(
miter
)
=
Canvas
(6%,
LessonExample
.
FontHeight
*
1.5) {
VAlign
:
Center
;
Shape
(
null
,
new
(
LineSize
*
0.25,
Colors
.
Black
,
Solid
,
Flat
,
Miter
,
miter
)) {
OpenPath
(0, 30%) {
LineTo
(100%, 50%);
LineTo
(0, 70%)};
};
};
MiterTable
=
TwoColumTable
{
Row
{
Bold
;
"Miter Limit"
;
"Effect"
};
foreach
(
var
m
in
[50, 1])
Row
{
TextDigits
:
0;
m
;
DrawMiterJoin
(
m
)};
};
Miter Limit
Effect
50
1
Closed paths
Use the
ClosedPath
formatter to create a closed, fillable path. A final line segment to the origin of
the path is automatically added to the end of the path.
ShowClosedPath
=
Canvas
(
LessonExample
.
FontHeight
*
10,
LessonExample
.
FontHeight
*
10) {
Shape
(
Colors
.
Green
) {
ClosedPath
(10%, 10%) {
LineTo
(90%, 90%);
LineTo
(10%, 90%);
// Line to origin is added automatically
};
};
};
Cutouts
Adding a second closed path in the same shape will 'cut a hole' in the first shape.
CutoutFigure
=
Canvas
(
LessonExample
.
FontHeight
*
10,
LessonExample
.
FontHeight
*
10) {
Shape
(
Colors
.
Green
) {
ClosedPath
(10%, 10%) {
LineTo
(90%, 90%);
LineTo
(10%, 90%);
};
EllipsePath
(
new
(
new
(15%, 40%),
new
(20%)));
// Cutout
};
};
Repeated segments
Use a loop to make a shape with a repeated set of line segments.
Saw
=
Canvas
(90%,
LessonExample
.
FontHeight
*
3) {
Shape
(
Colors
.
Silver
) {
ClosedPath
(0) {
foreach
(
var
x
in
0%
..
100%
step
10%)
{
LineTo
(
x
, 100%);
LineTo
(
x
, 50%);
}
LineTo
(100%, 0);
};
};
};
PolygonPath
Make a regular n-sided polygon using the
PolygonPath
function.
NGon
(
radius
,
n
)
=
VBox
(
radius
*
2
+
6) {
HAlign
:
Center
;
Span
{
TextColor
:
Colors
.
Red
;
n
};
Shape
(
Colors
.
Yellow
, 3) {
PolygonPath
(
new
(0,
radius
*
2),
n
,
-
90
degrees
);
};
};
NGons
=
HBox
{
VAlign
:
Top
;
var
sep
=
LessonExample
.
FontHeight
*
0.5;
Separation
:
sep
;
NGon
(
ExtentWidth
/
16
-
sep
,
each
3
..
10);
};
3
4
5
6
7
8
9
10
QuadTo formatter
Make a quadratic curve with two endpoints and a control point using the
QuadTo
function.
CheckMark
=
Canvas
(
LessonExample
.
FontHeight
*
7,
LessonExample
.
FontHeight
*
5) {
Shape
(
Colors
.
LightGreen
,
Colors
.
DarkGreen
) {
ClosedPath
(1%, 50%) {
QuadTo
(
new
(9%, 44%),
new
(20%, 43%));
QuadTo
(
new
(31%, 52%),
new
(36%, 69%));
QuadTo
(
new
(60%, 28%),
new
(99%, 5%));
QuadTo
(
new
(55%, 39%),
new
(36%, 96%));
QuadTo
(
new
(34.5%, 100%),
new
(33%, 96%));
QuadTo
(
new
(21%, 60%),
new
(1%, 50%));
};
};
};
Quadratic Examples
Here are some examples of how the position of the control point affects the shape of a quadratic
curve.
ShowQuads
=
Canvas
{
Margin
:
LineSize
;
ShowQExample
(
each
QuadExamples
);
};
Cubic curves
Make a cubic curve with two endpoints and two control points, using the
CurveTo
function.
BowTie
=
Canvas
(
LessonExample
.
FontHeight
*
5,
LessonExample
.
FontHeight
*
5) {
Shape
(
null
,
LS1
) {
OpenPath
(33%, 10%) {
CurveTo
(
new
(100%, 100%),
new
(0, 100%),
new
(65%, 10%));
};
};
};
Cubic Examples
The following examples show how the control points bend the curve.
ShowCubics
=
Canvas
{
Margin
:
LineSize
;
ShowCurve
(
each
CubicExamples
);
};
Glyph paths
Placing a string inside a shape will cause the paths of the character glyphs to be added to the
shape. This allows you to build fanciful titles and designs with text.
GlyphBox
(
text
,
angle
=
0)
=
Canvas
(
null
,
null
,
new
Edge
(0,
LineSize
*
2)) {
Background
:
AgedWood
;
BorderRadius
:
LineSize
;
Transform
:
Transform
.
Rotate
(
angle
);
TransformFit
:
true
;
Shape
(
null
,
new
(
LineSize
*
0.25,
Colors
.
Black
,
Dotted
,
Round
)) {
text
;
};
};
AGlyph
=
HBox
{
VAlign
:
Top
;
TextHeight
:
LessonExample
.
FontHeight
*
5;
GlyphBox
(
"Shooting"
);
GlyphBox
(
"Range"
, 20
degrees
);
};