For my undergraduate capstone in Computer Science, I chose to pursue an independent project based on the concept of String Art. String Art is a labor-intensive art-form, characterized by a thread that loops around nails on a board to create patterns or representational forms.
In this article, I provide an overview of the tools and techniques I used to devise a software algorithm to drawing string art, along with my results and take-aways.
Project Scope:
My goals for this project were to:
1. Develop an algorithmic technique for automating string art
2. Emulate the physical logic of string art—i.e. determine and place nails onto a canvas, to loop around with a single and continuous string
Deliverable:
Software that takes digital images as input and outputs subsequent 2D string art visualizations.
Tools:
Due to the computation-intensive requirements of this project, I decided to use OpenCV—a computer vision programming library optimized for image processing—which uses Intel’s Integrated Performance Primitives for GPU acceleration. I used the OpenCV-Python bindings to leverage NumPy for matrix operations, and its Matplotlib library for processing arrays to images.
Process:
To devise my algorithmic strategy, I conceptually deconstructed the making of string art into two constituent parts: drawing contours (with nails), and filling in values (with recursive thread loops).
Contours
In the context of string art, drawing contours requires breaking an image into its outlines, and then placing nails at optimal intervals. I began this step by testing on saturated illustrations containing stark lines. For detecting the outlines, I used an optimized no-parameter Canny Edge Detection method. Additionally, I used an OpenCV method called Good Features to Track to place points on the canny output.
To connect these points from a single string such that every point was looped just once, I quickly realized I required a nearest-neighbor technique to determine the next closest neighbor at any point. I subsequently used a KD Tree and KNN search to achieve this.
While using a KNN tree to draw contours (right) added time complexity, it yielded significantly better contours compared to an unordered traversal of points (left).
Values
In order to create light and dark values, I decided to allocate additional nails onto the canvas based on average values of a region for denser string loops. To break an image into its value-regions, I used Delaunay Triangulation which effectively splits points into triangles, favouring regular triangles over ‘skinny’ ones.
Generating these triangles also allowed me to calculate midpoints, values of which could be read to get an approximation of the region value. This proved to be sufficient, and exponentially more efficient than calculating exact averages of pixel values from triangle areas. I also calculated the middle value of every input image, assigning nails to only midpoints with darker values, as demonstrated below:
At this point, I started working on actual images. Dark string regions require both additional nails and denser looping. In large dark regions, such as the clothing in the image below, midpoint nails did not suffice and more points were required. One way to do this would have been to create a random but controlled Poisson distribution inside these triangles.
However, I implemented a much simpler solution by adding a ‘noise’ filter over every input image. The added noise—made using the lower quartile pixel value—produced contrast in very dark regions; in lighter regions, middle-value noise did not create enough contrast for dark-point detection.
Results and Conclusion
Combining all the aforementioned results allowed successful and optimized string art visuals.
Future goals:
This was a fun extension of several familiar tools and concepts.
In terms of areas for improvement, midpoint values can be used to loop the farthest points in dark triangles and closest points in light triangles. Doing so would yield much starker regions and better utilize looping as opposed to nail placement for creating dark values. While automation cannot (and should not) replace the ingenuity of an artist, further development of this algorithm could lead to very realistic results.
Mentored by faculty advisor Bret Jackson, with thanks to Satya Mallick for Delaunay Triangulation, and Adrian Roseblock for Canny Edge Detection methods. Special thanks to Laarco Studio, and fellow artist Petros Vrellis for inspiring this project.