Craft beautiful geometric art using code.
Use the code basics like loops, control flow and specialized functions to generate your geometry artworks.
Examples of g2D Geometry Art
Installation
Go get
$ go get -u github.com/lucasepe/g2d
Ready-To-Use Releases
Here you can find g2d
already compiled for:
- MacOS
- Linux
- Windows
How to use
To execute a local g2d
script:
$ g2d /path/to/my-script.g2d
To execute a g2d
script stored somewhere on the web:
$ g2d http://my-cool-site.com/remote/path/to/my-script.g2d
Use the --directory
(or the shorter -d
) flag to specify a destination folder for the generated PNG images.
The g2D
Programming Language Syntax
Example-programs can be found beneath examples/ which demonstrate these things, as well as parts of the standard-library.
Types
g2D has the following data types: bool
, int
, float
, str
, array
, and fn
.
Type | Syntax | Notes |
---|---|---|
bool | true false |
|
int | 0 42 1234 -5 |
is a signed 64-bit integer |
float | 0.5 4.2 1.234 -5.5 |
is a 64-bit double-precision floating point |
str | "" "foo" "\"quotes\" and a\nline break" |
are immutable arrays of bytes |
array | [] [1, 2] [1, 2, 3] |
grow-able arrays (use the append() builtin) |
fn | fn(a, b) { ... } |
defines a custom function |
Bindings
Variables are bounded using the :=
operator.
a := 3
b := 1.2
Variables may be integers, floats, strings, or arrays/hashes.
To update a variable you can simply specify the equals =
operator:
a := 3 // Binding
a = a + 5 // Updating
Arithmetic operations
g2D
supports all the basic arithmetic operation of int
and float
types.
a := 5
b := 3
c := a + b
d := c / 2
e := d * d
Builtin containers
g2d
has one builtin containers: array
.
Arrays
An array is a list which organizes items by linear sequence. Arrays can hold multiple types.
a := [1, 2.3, "hello!"]
b := [false, true, "Hello World", 3, 3.13]
Adding to an array is done via the push
builtin function:
a = append(a, "another")
You can iterate over the contents of an array like so:
i := 0
while( i < len(a) ) {
print( "Array index ", i, " contains ", a[i], "\n")
i = i + 1
}
With the definition we included that produces this output:
Array index 0 contains 1
Array index 1 contains 2.3
Array index 2 contains hello!
Array index 3 contains another
Functions
g2D
uses fn
to define a function which will be assigned to a variable for naming/invocation purposes:
sum := fn(a, b) { return a + b }
print(sum(5,3), "\n") // Outputs: 8
print(sum(2.5,7.5), "\n") // Outputs: 10
Functions can be passed as values to others functions:
addTwo := fn(a, b, f) {
return 2 + f(a, b)
}
tot := addTwo(68, 1, sum)
print(tot, "\n") // Outputs: 71
Functions inside functions
multiplier := fn(q) {
return fn(x) {
return x*q
}
}
multThree := multiplier(3)
print(multThree(2), "\n") // Outputs: 6
print(multThree(3), "\n") // Outputs: 9
print(multThree(4), "\n") // Outputs: 12
If-else statements
g2D
supports if-else
statements.
max := fn(a, b) {
if (a > b) {
return a;
} else {
return b;
}
}
print( max(1, 2) ) // Outputs: 2
Switch Statements
g2D
supports the switch
and case
expressions:
switch n := randi(10) {
case n % 2 == 0 {
print(n, " is even", "\n")
}
default {
print(n, " is odd", "\n")
}
}
While Loops
g2D
supports only one looping construct, the while
loop:
i := 30
while (i > 0) {
print(i, " ")
i = i - 10
}
// 30 20 10
Builtin functions
Core
Function | Description |
---|---|
exit([status]) |
exits the program immediately with the optional status or 0 |
input([prompt] |
reads a line from standard input optionally printing the specified prompt |
print(...) |
output a string to stdout |
printf(pattern, ...) |
output a string to stdout (formatted according the specified pattern) |
sprintf(pattern, ...) |
like printf(...) but returns a string
|
bool(val) |
converts value to a bool |
float(val) |
converts decimal value str to float - if val is invalid returns null |
int(val) |
converts decimal value str to int - if val is invalid returns null |
str(val) |
returns the string representation of val |
len(iterable) |
returns the length of the iterable (string or array) |
append(array, val) |
returns a new array with value pushed onto the end of array |
Calculation
Function | Description |
---|---|
abs(x) |
returns the absolute value of x |
atan(x) |
returns the arc tangent, in radians, of x |
atan2(x, y) |
returns the arc tangent of y/x |
cos(x) |
returns the cosine of the radian argument x |
degrees(angle) |
converts radians into degrees |
hypot(p, q) |
returns sqrt(p*p + q*q)
|
lerp(start, stop, amt) |
calculates a number between two numbers at a specific increment |
map(v, b1, e1, b2, e2) |
re-maps a number from one range to another |
max(v1....vn) |
returns the largest value in a sequence of numbers |
min(v1....vn) |
returns the smallest value in a sequence of numbers |
pow(x, y) |
returns x**y , the base x exponential of y
|
sin(x) |
returns the sine of the radian argument x |
sqrt(x) |
returns the square root of x |
radians(angle) |
converts a degree measurement to its corresponding value in radians |
randf([min], [max]) |
returns a random float between min and max - by default min=0.0 and max=1.0 |
randi([min], [max]) |
returns a random int between min and max |
Basic graphic functions
Function | Description |
---|---|
size(w,[h]) |
sets the size of the drawing; when both w and h are specified creates a rectangular image otherwise creates a squared one |
viewport(xMin, xMax, yMin, yMax, xOffset, yOffset) |
sets up user-defined coordinate system; performs a screen reset (drawings are cleared) |
clear() |
fills the entire image with the current color; clear all drawings |
fillColor(hexcolor) |
sets the fill color to the specified hexcolor; example fillColor("#ff0000") |
fillColor(r, g, b, [a]) |
sets the fill color to r,g,b,a values - should be between 0 and 255, inclusive |
strokeColor(hexcolor) |
sets the stroke color to the specified hexcolor; example strokeColor("#ff0000") |
strokeColor(r, g, b, [a]) |
sets the stroke color to r,g,b,a values - should be between 0 and 255, inclusive |
strokeWeight(weight) |
sets the stroke thickness to the specified width |
dashes([s1, s2, ...sn]) |
sets the current dash pattern to use (call with zero arguments to disable dashes) |
stroke() |
strokes the current path with the current stroek color and line width the path is cleared after this operation |
fill() |
fills the current path with the current fill color; open subpaths are implicity closed. The path is cleared after this operation |
fillAndStroke() |
fills the current path with the current fill color and strokes it with the current stroke color; the path is cleared after this operation |
push() |
saves the current state of the graphic context by pushing it onto a stack |
pop() |
restores the last saved graphic context state from the stack |
snapshot([filename]) |
creates a PNG image with the current drawings. If filename is omitted, it will be autogenerated with a progressive counter, that will be incremented on each snapshot() invocation; this is useful if you wants to generate an animation later (using all the generated PNG images). |
xpos() |
returns the current X position (if there is a current point) |
ypos() |
returns the current Y position (if there is a current point) |
Graphic primitives
Function | Description |
---|---|
arc(x, y, r, sa, ea) |
draws a circular arc centered at (x, y) with a radius of r. The path starts at sa angle_, ends at ea angle, and travels in the direction given by anticlockwise |
circle(x, y, r) |
draws a circle centered at [x, y] coordinates and with the radius r |
ellipse(x, y, rx ,ry) |
draws an ellipse centered at [x, y] coordinates and with the radii rx and ry |
line(x1, y1, x2, y2) |
draws a line from point (x1, y1) to point (x2, y2) |
point(x, y) |
draws a point at specified coordinates (the size is equal to the stroke weight) |
quad(x1, y1, x2,y2, x3,y3, x4,y4) |
draws a a four sided polygon using the provided vertices |
rect(x, y, w, h, [tl, tr, br, bl]) |
draws a (w x h) rectangle with upper left corner located at (x, y). If only one radius is specified, all the corners have the same bending, if tl, tr, br, bl are specified, each corner can have a different curvature |
triangle(x1,y1, x2,y2, x3,y3) |
draws a triangle using the provided vertices |
star(cx, cy, n, or, ir) |
draws a star cx, cy is the center, n the number of spikes, or and ir the outer and inner radius |
Paths
Function | Description |
---|---|
beginPath() |
starts a new path |
closePath() |
adds a line segment from the current point to the beginning of the current subpath |
moveTo(x, y) |
sets the begin of a new subpath starting at the specified x, y point |
lineTo(x, y) |
adds a line segment to the current path starting at the current point |
arcTo(x1, y1, x2, y2, r) |
adds a circular arc to the current sub-path, using the given control points and radius |
quadraticCurveTo(x1, y1, x2, y2) |
adds a quadratic Bézier curve to the current sub-path; x1, y1 is the control point and x2, y2 is the end point |
Transform
Function | Description |
---|---|
rotate(angle, [x, y] ) |
updates the current matrix with a anticlockwise rotation; when x, y are specified, rotation occurs about this point, otherwise rotation occurs about the origin (angle is in radians) |
scale(sx, sy, [x, y]) |
updates the current matrix with sx, sy scaling factor; when x,y are specified, scaling occurs about this point, otherwise scaling occurs about origin. |
translate(x, y) |
updates the current matrix with a translation to x and y |
identity() |
resets the current transformation matrix to the identity matrix |
transform(x, y) |
multiplies the point x, y by the current matrix, returning a transformed position |
Text
Function | Description |
---|---|
text(str, x, y, [ax, ay]) |
draws the specified text str at the specified anchor point x, y; the anchor point is x - w * ax, y - h * ay, where w, h is the size of the text (by default ax=0.5, ay=0.5 to center the text at the specified point) |
textWidth(str) |
returns the rendered width of the specified text str given the current font face |
fontSize(size) |
sets the font height |
Images
Function | Description |
---|---|
imageGet(path/to/png) |
loads a PNG image from the local filesystem |
imageAt(im, x, y, [ax, ay]) |
draws the specified image im at the specified anchor point x, y; (ax and ay are the x and y offsets) use ax=0.5, ay=0.5 to center the image at the specified point |
Top comments (1)
Well, honestly, for the last four months I’ve been drawing around 30 hours per week. I’ve gone through various books and videos, learned a ton, and even completed a couple 11 x 17 comic book pages of original art. However, I began suffering from the problem any learner faces in the age of the internet, which is the sheer overabundance of learning material available. Oftentimes I’d spend hours sifting through lists of the best drawing books and creating playlists of YouTube videos. I became more focused on curating the best resources than actually going through those resources. I would start one book, then wonder if I should be working on a different book, and I’d start jumping back and forth. Jumping around so often, I started to lose the big picture, and I didn’t give each resource the full attention it deserves. I was always focused on getting through one book so I could get get to the next. I realized that I needed 1) more structure and 2) a different attitude.