commit 76fe2ff904009bdaf236f5fc7a1d8a349cfe609a
parent 4c1df7c878379b1bd3060e8622d0a88a80e3fc03
Author: M. Yamanaka <myamanaka@live.com>
Date: Tue, 16 Feb 2021 18:50:33 -0500
makefile + spiral and rose patterns
Diffstat:
A | Makefile | | | 21 | +++++++++++++++++++++ |
A | csconv.lua | | | 43 | +++++++++++++++++++++++++++++++++++++++++++ |
A | rose.lua | | | 109 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
A | spiral.lua | | | 65 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
4 files changed, 238 insertions(+), 0 deletions(-)
diff --git a/Makefile b/Makefile
@@ -0,0 +1,21 @@
+# Math Art Makefile
+# M. Yamanaka
+# email: myamanaka@live.com
+# website: csmyamanaka.com
+# license: MIT (See included "LICENSE" file for details)
+
+CC=lua
+
+all: rose spiral
+
+spiral:
+ $(CC) $@.lua
+
+rose:
+ $(CC) $@.lua
+
+topng:
+ mogrify -format png *.svg
+
+clean:
+ rm -f *.svg *.png
diff --git a/csconv.lua b/csconv.lua
@@ -0,0 +1,43 @@
+
+--[[
+ Coordinate Systems Conversion
+ "csconv.lua"
+ M. Yamanaka
+ email: myamanaka@live.com
+ website: csmyamanaka.com
+ license: MIT (See included "LICENSE" file for details)
+]]
+
+--[[
+ a series of conversions between coordinate systems
+ canvXY ... canvas to XY coordinate system
+ arguments:
+ p ... point in canvas space
+ s ... scale factor
+ t ... translation
+ xyCanv ... XY to canvas coordinate system
+ arguments:
+ p ... point in XY coordinate system
+ s ... scale factor
+ t ... translatiion
+ polarXY ... polar to XY coordinate system
+ arguments:
+ p ... point in polar coordinate system {r, theta}
+ xyPolar ... XY to polar coordinate system
+ arguments:
+ p ... point in XY coordinate system
+]]
+function canvXY(p, s, t) return {(p[1] - t[1])/s, (p[2] - t[2])/s} end
+function xyCanv(p, s, t) return {s*p[1] + t[1], s*p[2] + t[2]} end
+function polarXY(p) return {p[1]*math.cos(p[2]), p[1]*math.sin(p[2])} end
+function xyPolar(p)
+ local th = 0
+ if p[1] == 0 and p[2] >= 0 then th = math.pi/2
+ elseif p[1] == 0 and p[2] < 0 then th = 3*math.pi/2
+ elseif p[1] >=0 and p[2] == 0 then th = 0
+ elseif p[1] < 0 and p[2] == 0 then th = math.pi
+ else th = math.atan(p[2]/p[1])
+ end
+ return {math.sqrt(p[1]*p[1] + p[2]*p[2]), th}
+end
+
diff --git a/rose.lua b/rose.lua
@@ -0,0 +1,109 @@
+--[[
+ Rose Art
+ "rose.lua"
+ M. Yamanaka
+ email: myamanaka@live.com
+ website: csmyamanaka.com
+ license: MIT (See included "LICENSE" file for details)
+]]
+
+local ca = require("lgi").cairo
+require("csconv")
+
+function neonSet(ctx, p, n, r, c)
+ --[[
+ draw a set of "neon" points
+ arguments:
+ ctx ... cairo context
+ p ... point in canvas coordinate system
+ n ... number of points
+ r ... max radius
+ c ... colour
+ ]]
+ ctx:set_source_rgb(c[1], c[2], c[3])
+ for i = 1, n do
+ ctx:arc(p[i][1], p[i][2], r, 0, math.pi*2)
+ ctx:fill()
+ end
+
+ --[[
+ To give it a "neon" appearance, these points should all
+ have a white centre
+ ]]
+ ctx:set_source_rgb(1, 1, 1)
+ for i = 1, n do
+ ctx:arc(p[i][1], p[i][2], r*0.7, 0, math.pi*2)
+ ctx:fill()
+ end
+end
+
+function genPts(n, p0, l, s, t)
+ --[[
+ Generate a set of points that reside on one continous
+ function at equal intervals. The resulting set of points
+ are in canvas coordinates
+ arguments:
+ n ... total number of points
+ p0 ... initial point in polar coordinates
+ l ... the layer of the rose petals on which these pts reside
+ s ... the scaling factor for domain conversion
+ t ... the translation for domain conversion
+ ]]
+ local pts = {}
+ for i = 1, n do
+ local u = (i - 1)*(2*math.pi)/n
+ local th = u/l + p0[2]
+ local r = p0[1]*0.1*math.abs(math.sin(u*1.5)) + p0[1]
+ pts[i] = xyCanv(polarXY({r, th}), s, t)
+ end
+ return pts
+end
+
+function genFibs(n)
+ --[[
+ It is widely known that fibonacci numbers appear in nature.
+ We will employ these numbers for our designs as well
+ ]]
+ local fibs = {0, 1}
+ for i = 3, n do fibs[i] = fibs[i - 1] + fibs[i - 2] end
+ return fibs
+end
+
+function rose()
+ --[[
+ The "main" function
+ ]]
+
+ local dim = {1920, 1080}
+ local fn = "rose.svg"
+ local ctx = ca.Context.create(ca.SvgSurface.create(fn, dim[1], dim[2]))
+
+ local N = 100 -- set each segment to have 100 points
+ local P1 = {}
+ local idx = 1 -- index number for each set
+ --[[
+ the use of fibonacci numbers allow for natural looking
+ patterns
+ ]]
+ local fibs = genFibs(7)
+ for i = 4, 7 do
+ for j = 0, fibs[i] - 1 do
+ P1[idx] = genPts(N, {(i - 3)*100, j*2*math.pi/fibs[i]}, fibs[i] + 1, 1, {dim[1]/2, dim[2]/2})
+ idx = idx + 1
+ end
+ end
+
+ --[[
+ initialize the scene with a black background
+ ]]
+ ctx:set_source_rgb(0, 0, 0)
+ ctx:rectangle(0, 0, dim[1], dim[2])
+ ctx:fill()
+
+ --[[
+ Draw all segments
+ ]]
+ for i = 1, idx - 1 do neonSet(ctx, P1[i], N, 10, {1.0, 0.1, 0.9}) end
+end
+
+rose()
diff --git a/spiral.lua b/spiral.lua
@@ -0,0 +1,65 @@
+--[[
+ Spiral Art
+ "spiral.lua"
+ M. Yamanaka
+ email: myamanaka@live.com
+ website: csmyamanaka.com
+ license: MIT (See included "LICENSE" file for details)
+]]
+
+local ca = require("lgi").cairo
+require("csconv")
+
+function pebble(ctx, p, r, c)
+ --[[
+ draw a single pebble in canvs coordinate system
+ arguments:
+ ctx ... cairo context
+ p ... point in canvas coordinate system
+ r ... radius of the pebble
+ c ... colour
+ ]]
+ ctx:set_source_rgb(c[1], c[2], c[3])
+ ctx:arc(p[1], p[2], r, 0, math.pi*2)
+ ctx:fill()
+end
+
+function spiral()
+ --[[
+ The "main" function
+ The polar coordinate system is used to generate a nice
+ spiral pattern
+ ]]
+
+ local dim = {1920, 1080}
+ --local img = ca.SvgSurface.create("spiral.svg", dim[1], dim[2])
+ local fn = "spiral.svg"
+ local ctx = ca.Context.create(ca.SvgSurface.create(fn, dim[1], dim[2]))
+
+ local pts = {}
+ local dTh = 5
+ local dR = 45
+ local sz = 11
+ local N = 11
+
+ --[[
+ insert points into the list
+ ]]
+ for n = 0, N - 1 do
+ for i = 1, sz do pts[n*sz + i] = {i*dR, (i - 1)*dTh + n*2*math.pi/N} end
+ end
+
+ --[[
+ initialize the scene with a black background
+ ]]
+ ctx:set_source_rgb(0, 0, 0)
+ ctx:rectangle(0, 0, dim[1], dim[2])
+ ctx:fill()
+
+ for i = 1, N*sz do
+ local v = ((i - 1)%sz)
+ pebble(ctx, xyCanv(polarXY(pts[i]), 1, {dim[1]/2, dim[2]/2}), v + 5, {0.9*v/sz + 0.1, 0.9*v/sz + 0.1, 0.9*v/sz + 0.1})
+ end
+end
+
+spiral()