—— The Third Island of Misfit Code ——

Started on 6/26/2022. (Moved to here from testbed2.html)




Project #3.58: Smooth Line Between Any Points






Tension: 67%






Curve Formula:




(7/11/2024): I've been looking on and off for years for some kind of algorithm to smoothly connect a series of points on a canvas. Every source I've found points to Bezier curves, but those are useless without additional algorithms since the only two points the curve actually passes through is the endpoints, and not every single point. A few days ago, I finally came across a viable solution that uses tangent data to create a smooth curve between any number of points.
(Later that day): I actually got it working! I added mouse controls to drag the points as well. I'm really pleased with how satisfying this algorithm is. Also, in the original algorithm, the control points are placed a distance away based on a third of the distance between the points before and after. This 1/3 value can be modified, however, and it makes the line get really loopy. I added a slider to control this.
(Slightly later that day): I added an option to make a loop instead of a line, by just wrapping the points around the end of the list. I later experimented with negative loopiness, and added buttons to put the points in preset shapes.

(7/12/2024): I finally got an algorithm working for correctly inserting points on clicks! The naive approach is just to add the point to the end of the path, but that usually isn't remotely where the point should be, and the path is really disrupted. I came up with this algorithm, which I'll outline here since I think it's handy for later: To insert (x, y) into a path of points, first find the closest point in the path to (x, y). Then, consider the straight-line distance that would be added to the path if the point was inserted *before* the closest point (dist(prev, {x, y}) + dist({x, y}, closest) - dist(prev, closest)), and the same for if the point was inserted *after* the closest point. Whichever is smaller will be the most reasonable place to put the point, so we insert it there. This works really well and adds points exactly where you'd expect it to, so I'm really pleased with it.
(Later that day): While looking at other questions on the same topic, I came across this StackOverflow question, where one of the answers pointed me to this paper on Hermite curves. The idea is that they provide formula for the velocity vectors of a Hermite curve that satisfies tangent requirements while minimizing "bending energy" to form a smooth curve. I wrote up some code to use their equation, and unfortunately it doesn't work super well. It's smooth, but has lots of sharp turns. But, I think I know the problem - the equation gives me the starting and ending velocity vectors, but I can't just convert that to control points for a Bezier curve. I think I'll end up needing to use linear algebra to convert between the basis functions of a Hermite curve and those of a Bezier curve. I found this PDF that I think will give me the formula I need to convert Hermite tangent vectors into Bezier control points.
(Slightly later that day): Well, I did the math, got the change of base matrix, and got the curve working! Except...I realized that after doing all that math, my original formula was actually correct. So, the Hermite curve is just going to be less satisfying than the Bezier curve, which I'm fine with, and is really interesting.

(7/16/2024): I've started implementing various cubic Hermite curve interpolation algorithms from the Wikipedia page. I added Finite Differences so far, though I think there are still some kinks to iron out.

(7/17/2024): I'm not completely sure what changed, but after redoing Finite Differences today, I got it working! It looks very similar to the Bezier 1/3 method in a lot of cases, but less loopy, so I think I prefer it. I also added the Kochanek-Bartels Spline method from the same Wikipedia page, and renamed "Loopiness" to "Tension", since I realized that setting is the same as the tension variable in these spline interpolation algorithms (except 1 - loopiness, so a minor relabeling).
(Later that day): I found an article by Paul Bourke talking about spline interpolation. In there, he mentions a method of calculating tangents using cross products, so I implemented this algorithm. I had to normalize a vector at one step to make sure the tangents weren't stupidly large and impossible to work with. Interestingly though, this is the first algorithm I've come across that doesn't smoothly change the curve as the points are dragged - the curve can suddenly "jump" over a 1px difference.
(Even later that day): Added more functionality with improved UI and buttons to add, remove, and wiggle points.


Project #3.57: Animated Fabrik Arm
[ Click to set target ]

Arm Segments: 10


Arm Movement:






[ FPS: ]
(7/9/2024): I want to make a FABRIK implementation that would move like an actual robotic arm. Before, the angles of the joints aren't even considered, and the arm just moves its points to reach the target. This project aims to instead use FABRIK to calculate the ideal joint angles for the arm, so that the arm can actually rotate towards those angles and behave like a real arm. I started this a few days ago and didn't update this devlog, but it went through a lot of complications to get the relative turn calculation working, but I think I finally have it working. I added mouse controls today to test it. The biggest problem right now is that it doesn't rotate efficiently, so it might take a full +356° turn instead of a single -4° turn. This makes it spin completely out of control often, even though it ends up in the correct position afterwards.

(7/11/2024): Fixed the angle calculation, now it takes the shortest path. This Reddit post solved the problem immediately, and a lot cleaner than what I was going to come up with. I also modified the algorithm so that joints with less distance to turn will turn slower, which looks a lot better. Interestingly though, I feel like the movement looks less natural than when I just lerped towards the mouse, full FABRIK snapping along the way. But, this was an interesting experiment anyway.

(7/12/2024): I added more movement modes and form elements for various settings.


Project #3.56: Convex Hulls
(6/28/2024): Experimenting with layering convex hulls - I generate a random smattering of points, draw the convex hull, and then remove 20% of the points from the hull and repeat. Layering this a couple of times creates a really cool effect with concentric shapes. I wanna fuss with this more.
(Later that day): I've messed around with this a ton. Now the hulls are drawn multiple times in varying shades of cyan and randomly shifted around to add an almost electrical look to them. I'm still not fully satisfied with this, but it's turning into something.

(7/3/2024): Holy cow. Canvases are frustrating. Turns out this project is 500-600 times slower on my laptop than on my desktop! I reduced the canvas size to try to help with this some.


Project #3.55: Frabtil Tree


Tree Size: %
Branch Length: %
Branch Spread: °
Color Contrast: %
Tree Reforming:










Reform Speed:
Trunk Thickness: px
Branch Thickness: %
Number of Branches:
Trunk Hue: °
Branch Hue Offset: °
Number of Splits:
Trailing Amount: %
Trunk Segments:
 
Max Offset:
Shake Speed: %
Shake Dampening: %
[ FPS: ]
(6/25/2024): Experimenting with FABRIK chains again, this time creating a fractal tree out of FABRIK chains (a "Frabtil" tree, if you will...I might need to work on that name). I currently have a prototype running with only 2 layers (which I want to improve the creation of, since currently I just manually assigned the pointers and did the calculations). You can click and drag with the mouse, and the chain closest to your click will be dragged, pulling along any branches it has recursively. Branches don't pull their parents - this is intentional, since it helps the tree maintain its structure even when branches are moving.
(Later that day): I got recursive tree building implemented, and to my surprise it all worked on the first try! So you can now build an entire fractal tree and grab it at any depth and drag it around. This creates a really cool effect where the branches get pulled together and it's really satisfying.
(Later-er that day): Game-changer for FABRIK chains, I implemented a slideToPoint() method that works a lot better than easeToPoint(), which I'd typically used. Easing means moving x% of the way every frame, which means it slows down as you get closer. But sliding moves the same amount every frame, creating smoother movement and also allowing the chain to actually reach its final position. I added a system where any branches not currently being dragged will slide back to their original positions, creating a really satisfying animation as the tree pops back into shape. I also implemented another system for repositioning, where it uses local displacement to correct itself, meaning if you drag the whole tree down 100 pixels it will rebuild to the normal shape, instead of reaching upwards towards its original position 100px away. I like both, so it's a setting to go between the two now. I also improved the mouse dragging by only letting the first 4 (variable) layers be dragged, so you don't accidentally grab tiny branches that don't really do anything. I'm working on improving the visuals, right now there's a width ratio so that's something. I also added an option for trailing, which creates a super cool effect as you drag the tree.

(6/26/2024): Spent ages implementing an autoscale calculation, which I finally got working. The tree is scaled uniformly to ensure it fits within the canvas, and then the first branch is lengthened to ensure the branches don't go below the canvas. This means I can now manipulate the scale of the entire tree independently of settings like branch angle and length ratio.
(Later that day): I added sliders for everything and added some more visual settings for color and hue.

(6/27/2024): Holy cow. I just realized I've been doing really slow FABRIK this whole time. I came across an article talking about the FABRIK algorithm, and it called it "iterative"...for some reason, I just never treated it like this. You're supposed to run the FinalToRoot and RootToFinal sequence multiple times when snapping to a point. I've always just been doing it once, which works perfectly fine, but converges very slowly and makes the chain take ages to reach it's destination at times. So, I made the iteration run 20 times per frame - with no FPS drop! - and now the tree is much more responsive and quick to reform. Now, I can more finely control the speed at which chains move, since they won't randomly take ages to reach their destination.
(Later that day): Arghhh...I just spent ages trying to optimize the rendering. I found that changing the canvas state can be a big bottleneck in drawing, so I spent ages implementing a breadth-first search for drawing the tree, and ensuring that I don't change the strokeStyle or lineWidth if it's the same, and I even added the branches to the queue from the outside-in to get same-color branches next to each other, and...it didn't work. It's like 4-5x slower. Ugh. I'll try to optimize it in a different way, maybe.
(A few minutes later): Found an off-by-one error causing exponentially worse performance. Now it's only 2x slower than before the BFS "optimization."
(A few more minutes later): Nevermind, it isn't twice as slow! I forgot that I changed "Number of Splits" between this version and the previous (which I was testing against), so it wasn't a fair fight when my optimized version had 3x the branches. Keeping this in mind, I now have a ~30% performance increase in some cases!

(7/24/2024): Went back to this project after nearly a month to implement something I'd wanted to do at first but never got around to - tree wiggling. Or, more specifically, making the end of each branch randomly wander around an invisible circle, dragging further branches along with it and making the whole tree sway and shake. I got this working using Brownian motion, and added a bunch of settings for it, along with improving the settings UI. I also changed how the number of FABRIK segments is calculated, so that the number of segments in the trunk can be directly changed, and added a slider for that.


Project #3.54: Pixel Rotation With Three Shears

Rotation Angle: 0.00°



Rotation Speed: 40%


Rotation Algorithm:






Image: Mario (16×16)
[ FPS: ]
(5/6/2024): I was inspired by this Matt Parker video, which explains how any rotation can be replicated with 3 specific shears, which means you can use it to rotate 8-bit pixel art without having to lose any pixels or average any non-grid-aligned pixels. I got the shearing implemented, but...for some reason, it completely breaks down past 90° and I can't figure out why. I think it might have something to do with how I am wrapping pixels around the edges in between shears, but I don't know how to account for that. In the meantime, the effect - though completely, horribly wrong - is actually pretty cool, so I've got it going with some images. And for some reason everything completely breaks at exactly 180°, and you get like 3 colors across the whole thing and most pixels are missing.

(5/7/2024, past midnight): I added settings and sliders and a few sample images. I added a "smooth angles" option to make the slider effectively slow down around 180° so you get longer at the weird angles. I've also noticed that I can see patterns at hyper-specific angles near 180°. Like, occasionally as it's sliding, I'll catch a glimpse of the original image but mirrored, or upside-down, or skewed. Nicolas Cage is himself but with a slight skew at exactly 179.9983704478203° and 179.9998410922108°.
(Later that day): After debugging for ages, I thought I got a working solution, but just ended up with a different wrong broken way. Then I spent ages more debugging and found that the shearing method just simply doesn't really work past 90°. So, I just transpose the image as needed and then every rotation becomes a 0°-90° rotation, and it works great now! I also added padding around the edge of the image instead of wrapping around the canvas, which looks much better. I added more images and more settings as well. Frustratingly, the rotation still isn't perfect, and it gets choppy near 0° and 90°. Like, 0° to 0.001° is a huge jump, and then it's smooth after that. I'm not sure why this is happening.

(5/8/2024): Added an option to add padding to the image so that the corners of it don't go offscreen when rotating, and cleaned up the code a little.


Project #3.53: Depth-2 Deterministic Cellular Automata

Generations:
Population:
Density:
[ FPS: ]
(4/17/2024): Typical cellular automatas are deterministic, meaning the current state of the CA is all you need to determine what the next state will be, and every current state of the grid only evolves into ONE possible next state. I wanted to extend this, making a CA that is deterministic based on the current AND the previous state. I'm calling it a "Depth-2 Deterministic Cellular Automata" until I can come up with a better name. Essentially, each cell keeps track of the number of neighbors it had on the previous generation, and uses the sum of (last generation's neighbors) + (this generation's neighbors) to determine born/survive conditions. Thus, born and survive can go from 0-16 neighbors to reach the whole space. A neat little rule I found is 1<b5/10/16s3/4/5, which has a lot of p2 oscillators that wouldn't be possible in a 1-depth deterministic CA. You also get asymmetric oscillators since the current state isn't enough to determine the next state.

(5/7/2024): I was informed by a user on the Conway's Game of Life Discord server that this is equivalent to a 4-state outer-totalistic CA, which is cool.


Project #3.52: Blur-onoi Diagram

Z-Axis Depth: 50%
Number of Z-Slices: 15
Number of Points: 15
Hue Variation: 100%
Brightness Multiplier: ×1.00
Brightness Variation: 80%


(3/12/2024): Experiments with 3D Voronoi diagrams (each pixel colored based on the closest point to it, from a given set of points). Here, the points are placed randomly in three dimensions, and then the pixels are considered with z = 0. Turns out, this just makes a regular Voronoi, so I made it where the plane "moves" through the z-axis, and redraws the Voronoi for that given flat z-value 10 times at a low opacity. This creates an interesting blurry Voronoi shape that is essentially layered cross sections of the true 3D Voronoi diagram. I call it a "Blur-onoi Diagram", since its a blurry Voronoi.


Project #3.51: Polygon Cursor Art

(12/24/2023): Art that is drawn by dragging with the cursor. Moving from left-to-right changes the size of the polygon, and moving from top-to-bottom increases the number of edges. Distance from the center determines hue and brightness. Together, different cursor paths and speeds create unique intricate shapes. I got inspiration for this from a book I got for Christmas - "Generative Design" by Hartmut Bohnacker, et al. - and modified the algorithm to fit my liking.

(12/25/2023): I've been modifying the parameters a ton, and there's now a LOT that changes based on the cursor position, and I really like the output now.

(12/26/2023): I added functionality to have the shapes follow the angle of the mouse cursor (slightly), along with a possibility to have lines drawn from the vertices to the center, to add more lines and variation. I'm brainstorming some ideas for an auto-draw mechanism that moves a "cursor" automatically so I can have a draw-at-once artwork for generative-art-gallery.html, but we'll see if that ends up being made or not, since it's tricky to replicate cursor movement. Also, there are currently 22 parameters that are varied every generation...

(12/28/2023): I added some more minor parameters today. Also, I started experimenting with the auto-draw feature, which generates a randomly dense unit interval of points and "clicks" along a path at those ratios. Currently, there's only random circle paths for the auto cursor to draw along, but I want to add more shapes and functionality. It's a struggle to try to mimic cursor movement; I'm trying to solve this with lots of different path shapes, but it's a hard balance between complex shapes and OVER-complex shapes that just clutter the screen and remove any semblance of design.


Project #3.50: Spacetime Ripples
(12/13/2023): Yet more experimenting with the same "layered wiggly lines over each other" concept. This time, the lines are all perfect sine waves, but their *amplitude* varies as along the wave, based on certain parameters. There's currently 3 modes, a circle, a line, and a cross shape. The waves are drawn with a white shadow to give a 3D effect.
(Later that day): Added randomization for 12 different parameters.


Project #3.49: Neon Landscape
(12/11/2023): Another variation on the previous algorithm; this time, there's less lines, and they're less jagged, but they get more jagged towards the bottom and darker, giving a cool neon effect to a mountain range-like landscape. I also added a mode where the bottom is smooth, and there are instead jagged mountains in the background; this mode is randomly toggled on/off each regeneration.


Project #3.48: Noisy Cave Wall
(12/11/2023): Experimenting with random simple algorithms yet again gave me a super interesting, surprising result. The basic algorithm here is: draw a line, with a little bit of variation so it's like a hand-drawn line. Move down, and try to follow that same line but a bit lower, and again with some randomness. Over time, the slight random skews multiply and you get interesting patterns as the lines go down. I varied this, making the lines really close together and really thin, with a LOT of variation, but also a lot of "smooth iterations" (going through and averaging each point with its neighbor). The result is this, and it looks really 3D and natural to me, like the wall of a rough cave.


Project #3.47: [TEMPLATE] Circle/Rectangle Physics
[ FPS: ]
(10/11/2023): An early start on trying to redesign pinball.html. Currently there's nothing but a ball that falls. I want to get proper circle-to-rectangle collision physics working, since pinball.html has lots of collision bugs.

(10/13/2023): Changed the ball image and fixed a trailing issue. I also started trying to implement circle-to-rectangle collision, but it's even worse than pinball.html at this point.
(Later that day): I redid the collisions entirely, and I think I got the corner collisions working! Now I just need to implement the edge collisions and I think this will be functional.

(10/18/2023): Finally some progress! I got the top and bottom collision working correctly, and added controls to move the ball with the arrow keys.
(Later that day): There's still some minor bugs but I got the rectangle collision working properly, at long last!

(10/19/2023): Added some band-aid-y hacks to fix a bug with corner collision not working in specific cases.

(10/21/2023): I finally fixed a bug with corner bouncing, where I had to choose between (a) the corners always having 100% bounciness, making them super uncontrollable, or (b) the corners having regular bounciness (40%-ish), but this meaning that the ball "sticks" to the corner as it rolls off. I just added a check to have 100% bounciness if the ball's y-velocity is under 4, and regular bounciness otherwise. Now, the ball bounces off corners normally, but also doesn't stick to the corners. I also added some more colors and different modes for how the rectangles are placed. I think I'll keep this one as just a physics test, and reserve a different project for Pinball 1.5 (the old name of this project), so I could reuse my rectangle collision code without taking out a ton of other stuff. I also added a random color to the ball every reset.


Project #3.46: Faster Game of Life
[ FPS: ]
(10/10/2023): I wanted to see how much more efficient I could get a GoL simulation to be using some optimizations I found online. I stored the previous and next grid state as a 3D array (gridSize×gridSize×2), and also keep track of which cells are active (have changed, or had their neighbors change), and ignore inactive cells. This did end up making it faster, but unfortunately it's only like a 10% increase at best. It runs a pretty decent 17ish FPS on a 600×600 grid, which is about 6 million cells rendered per second.


Project #3.45: Paint Smearing Loop
[ FPS: ]
(9/19/2023): More experiments, like Project #1.55, experimenting with drawing the canvas on top of itself, but at a lower opacity and slightly askew. All that happens is random colored dots are placed randomly, as the canvas is smeared on top of itself, making the colors bleed and cover the screen in super interesting patterns. I added a bunch of settings that are randomized (including changing the rendering context's global composite operation) to make it look super different every time. Also, the animation automatically clears itself and resets, creating an infinite loop. I made this a few days ago for a Networks and Data Communications assignment. We had to set up a web server and request an HTML file, so I made a random HTML page to send, and got carried away making a little animation for it.


Project #3.44: Cursor-Following Twirling Strings
[ FPS: ]
(9/1/2023): An attempt to combine a random walker with a bouncing ball, by having "Wind" objects "blow" it randomly across the screen. I'm not super happy with how it looks right now, though, so I want to work on the physics of the wind more.

(9/6/2023): Totally revamped how this works. Now, each "ball" is just a line through its previous 10 positions, and has its own random Brownian motion built-in to it, making it move randomly. I removed gravity and added air resistance so the lines float through the air better. I also added a targeting system that I really like. With targeting off, each ball gets a random vector added to its velocity every frame. With targeting on, that random vector is pointed (mostly) towards the target, so that over time it slides around and towards the target. So now when you hold down the mouse, all of the balls are attracted and swarm towards it. I really like how this looks over the previous version with balls. This one reminds me of colorful strings, or little fish swarming.


Project #3.43: Grabbable and Throwable Balls


[ FPS: ]
(8/31/2023): Using mouse controls, this ball can be grabbed, and you can throw it if you let go of the mouse after moving it quickly.

(9/1/2023): Improved throwing physics by boosting the mouse power but capping the velocity. I also added multiple balls with different sprites and sizes and weights.

(9/4/2023): Fixed some really dumb bugs so now the throwing works better and the balls never get NaN positions. I also implemented the Center and Randomize Balls buttons from last project, and added a button to add a new random ball.


Project #3.42: [TEMPLATE] Bouncing Balls


[ FPS: ]
(8/31/2023): Another barebones template, this time for ball bouncing with realistic physics (accounting for acceleration, overrun, etc.). There's also mouse control to add more balls.

(9/1/2023): Fixed some mouse controls and added Center and Randomize Balls buttons.


Project #3.41: Wiggly FABRIK Chain
[ FPS: ]
(8/25/2023): A slight modification to the FABRIK algorithm makes it jiggly and wiggly (scientific terms). Every frame, along with the normal snapping to the mouse cursor, it also snaps to itself, but slightly randomizes the angles of each line segment, making the whole thing vary over time. Later, I added a trailing effect and made multiple chains over the same area to create a hair-like effect that's kinda unsettling and cool.
(Later that day): I added a "net", which connects all the first points of the chains, connects all the second points of the chains, and so on. This creates an interesting wavy effect that resembles DNA. I also added some presets.

(8/28/2023): Added the "Overlay" and "Tri-Chain" presets.

(8/31/2023): Added the "Default" and "Pipe Cleaner" presets.


Project #3.40: [TEMPLATE] FABRIK Chain
[ FPS: ]
(8/23/2023): A simple barebones implementation of the FABRIK algorithm (with mouse control) so that I can quickly make a project using FABRIK without rewriting the same code every time. Most of this code came from Project #3.37 FABRIK Cone, but I removed all the extra stuff.


Project #3.39: Random Mostly-Directed Walkers
(8/18/2023): Another experiment with random walks. These I call "random mostly-directed walkers." They have a start point and an target, and every step they move directly towards it by some step. Except, there is a small chance they will instead walk in a random direction, instead of towards the target, which adds jagged spikes into the path. I put 8 of them on the edges of the canvas to give a kind of lightning-path effect.

(8/19/2023): Added some better color picking using random RGB variation per path. I also added variation to all of the settings between generations.

(8/21/2023): Added a draw chance variable to vary the number of lines randomly per generation. I also later changed how the paths generate; instead of being placed across the edges of the canvas, they're now placed around a circle, with additional paths providing a polygon boundary to that.

(8/22/2023): Updated the color to be HSL-based for less grayscale random generation, and tweaked the settings some. I also added some skew to the points so they're not perfectly spaced.


Project #3.38: Random Ideal Taxicab Walks
(8/10/2023): An "ideal taxicab walk" is any of the infinite number of shortest paths between two points, using the taxicab metric (these walks will be stairstepped). The "random" part comes from making the step sizes randomized, so that the overall shape of the path varies with each generation, but is still an ideal walk because it is the shortest path (every x-step is towards the x-value of the goal, and same with y-steps). In this project, a random ideal taxicab walk is taken between 2 random points, repeated several times with different biases, colored, and skewed to add some more interesting design to it.


Project #3.37: FABRIK Cone
Cone Length: 200%
Tracing Rate: 0%
Follow Speed: Instant
Cone Inner Radius: 0px
Number of Chains: 100
Cone Opacity: 70%
Cone Outer Radius: 80px
Segments Per Chain: 300
Line Width: 1px
[ FPS: ]
(7/21/2023): Another FABRIK experiment, this time involving a cone of FABRIK chains that follow the cursor. The chains have a set radius from the cursor that they follow, and a set radius around the center, creating a cone shape that is really fun to drag around.

(7/25/2023): Added some randomness to the initial spawning of the Fabrik cone. I also added settings and sliders for everything. I also added functionality to let the chain properties be modified without resetting everything, which was very difficult to do but I got it working. For example, if you change the number of segments, it doesn't reset the chain positions, it just puts new points on the chains so they retain their shape but with the new number of segments.

(7/26/2023): Fixed a bug where modifying the chain length would make the chains get bunched up, and added mouse control outside the canvas to make dragging the cone easier.


Project #3.36: Aligned Random Dribbles

Remaining Dribbles:
[ FPS: ]
(7/10/2023): I was playing around some more with aligned random walkers, i.e. random walkers that have a set "alignment" property that orients them towards some initial direction. I wanted to expand on what I last did on this in Project #2.37. This time, I added multiple "steps" that the walkers dribble down, so that when they hit a step, their alignment goes back to 0, but gets higher as they approach the next step. This isn't the coolest thing I was imagining, but I added some randomization and I think the final result is interesting.


Project #3.35: Circle Packing Meets Voronoi (Meets a Lattice)
Lines Drawn: 0
[ FPS: ]
(7/6/2023): Another modified circle packing implementation. This time, the circle packing is done immediately when Reset is clicked, and every frame adds a few thousand random lines. For each line, a random point on the canvas is picked, and then the nearest circle is located and a line is drawn from that random point to the closest point on the nearest circle. Also, if the center of the circle is closer than the edge of the circle, the line is drawn to there instead. The result is an interesting cross between a Voronoi diagram and circle packing. Note: I have slightly modified some settings to make this cooler looking, so the circles have a size ratio of 80% and the line endpoint is randomly varied by 3.5px in any direction, to add some more variation.
(Literally like 15 minutes later): I just made the coolest random discovery ever. I randomly thought, what if I constrain the spawn points of the lines to a grid? I.e., the lines can be at 5%, 10%, 15%, etc. of the canvas size, sticking them on a regular lattice. I didn't expect anything special to happen, but when I tried it, I got the coolest result and it resembles icy spikes reaching out in chaotic patterns. The endpoint of the line still has the random jitter, so it isn't stuck on the lattice, but the spawn point is, giving a cool triangular look to everything. Now, endpointJiggle35 corresponds to the thickness of the spikes, sizeRatio35 (inversely) corresponds to the length of the spikes, and spawnGridSize35 corresponds to the number of spikes. This is so extremely interesting to me because the result is stunning and complex, but the algorithm is stupidly simple.
(Later that day): Added setting randomization every time you click Reset. I also added some more settings to manipulate the lattice and its structure, and the point at which center spikes generate. Finally, I added a Draw At Once button that skips the animation process and draws instantly, and this also adds some white or black accents to the shapes.
(Later that night): Actually finished! Added to generative-art-gallery.html as "Frozen Supernovas"


Project #3.34: Circle Packing With Obstacles

Obstacles Presets:
(7/2/2023): I modified the old circle packing algorithm I wrote to add in Line objects, with a set angle and width, and the circles will avoid those lines as well, letting you create interesting patterns in the negative space.

(7/4/2023): Reworked the code so that there is an Obstacle class with a Line class derived from it, making the code more modular and easy to add other obstacles to.
(Later that day): Added functionality for obstacles to have circles packed within them, dividing the canvas into multiple regions with different styles and colors. Also, because of how the code checks for overlap, you can position obstacles "above" other obstacles, giving the effect of different layers. Note to self: Fix bug where minCircle34Size is not taken into account when packing circles inside obstacles, allowing for very tiny circles that mess with the desired density (and don't match circles outside obstacles).

(7/5/2023): Fixed yesterday's bug so now no circles go below the minimum size, and I also added a circle-shaped obstacle.
(Later that day): Added some extra checks so that the bounding boxes of obstacles don't overlap, which means the center circle looks less choppy now.

(7/6/2023): Added buttons for different obstacle presets. I also added a LineSegment obstacle, which is the same as a Line but has endpoints, and I added the "Jacob's Ladder" obstacle preset.

(7/9/2023): Reworked the code again so that every derived object from the Obstacle34 class only needs to have its own overridden .distSqToPoint() method, which now greatly reduces the amount of code reuse and makes adding new objects much easier. I also added the "Effervescence++" obstacle preset, which parodies Effervescence from generative-art-gallery.html. I honestly think I (might) (maybe) like this better than regular Effervescence, since it has more variation and also small white circles in the negative space, which give it a more interesting look. The original still means too much for me to change it, though.
(Later that day): I added a "Text Test" obstacle preset which I might want to expand into support for a full text-writing system, for writing any string of letters on the canvas (although that might end up being overkill and too much work to be worth it).

(7/10/2023): Squashed some more bugs and added the "Concentric Rings" preset.
(Later that day): Added the Rectangle34 class and added "Concentric Quads" as a dual to the "Concentric Rings" preset.

(7/11/2023): Added the "Checkerboard" preset. This one project alone is now over 1300 lines long (!!), though over half most of that length comes from the code for generating the obstacle presets.

(7/13/2023, slightly past midnight): Added settings to Obstacle objects for offsetAngle and offsetAngleVariation, which affect the rotation of circles when drawn as polygons (before, this was always just random for every circle, but now obstacles can have aligned objects). I also added the "Arrow Columns" and "Doodling Squares" presets that utilize this new mechanic.
(Later that day): Added the "American Flag" preset.


Project #3.33: Better Hotness Rating System
Identifier:

Area of Attractiveness: /200

Time: o'clock

Beautiful: /10
Cute: /10
Hot: /10
Pretty: /10
(6/24/2023): A stupid random project I'd had the idea for a few days ago and decided to code up a little implementation of it. Basically, it extends the usual "/10" rating for girls to be instead a measure of 4 different attributes, allowing a quadrilateral to be generated from these points.
Area of Attractiveness: The area of the quadrilateral (maximum area is 200 at 10/10/10/10)
Time: A measure of the alignment towards each attribute. This one is a bit more convoluted, but it's found by getting the center of mass of the quadrilateral (shown as a blue line), extending that line, and finding where that lies on a clock face. This basically just indicates what attribute a girl has the most of, but also allowing you to go between two values. A girl with a time of 5 o'clock is between cute and hot, but more hot than cute. 0 o'clock indicates all the attributes are equal, meaning there is no angle to draw.


Project #3.32: Silk Tapestry

Selected Strings:


Weaving Speed: ×1
Number of Strings: 4
Threads Per String: 6
String Length: 70%
Thread Spacing: 25%
Dye Intensity: 40%
String Thickness: 2px
Presets:
[ FPS: ]
(6/14/2023): A basic little animation based on squares and lines sliding around inside it. Currently there's a few different modes of how the lines slide around the square:
Mode 1: The first endpoint of the line travels uniformly along the square, with the second endpoint always one side-length along the perimeter in front of it.
Mode 2: The first endpoint of the line travels uniformly along the square, with the second endpoint maintaining a constant length for the line.

(Later that day): Added a few different modes with different combinations of settings and line types. (Even later that day): Removed the mode system and instead added settings that control the line movement, number of lines, etc. Everything works correctly, except that for some reason everything breaks when I try to add more than 1 ray. And since I'm coding this on my phone, I have no way to see the errors, so I'm pretty much stuck until I get back to my laptop.

(6/15/2023): I finally realized what was causing the ray bug (square root of a negative number), and fixed that, so everything is working now! I added some more settings as well. I changed the name from "Squares and Lines" to "Silk Tapestry" to reflect the new theme I'm going for, since I think it looks like weaving strings and threads together.
(Later that day): I added trailing and 2 modes for bendy lines (quadratic curves), one with the control point lying on the square between the endpoints, and one with the control point always in the center of the square. I also added sliders for everything, and made the box full-size to the canvas.
(Even later that day): Added colors to the strings.

(6/30/2023): For the past 2 weeks I've been having significant performance issues with the performance of this animation, when it seemed to be working perfectly fine before. Eventually I just had to reduce the canvas resolution (1000x1000 --> 500x500), and this significantly sped things up. For the record, this was the first thing I did for this program on my laptop, everything before this was on my phone. Also, I added a speed slider and presets.


Project #3.31: Ground-Breaking Ball
[ FPS: ]
(4/10/2023): This is the my proof-of-concept for a game idea I had, which will have Atari Breakout-like mechanics and involve mining into a planet. Currently nothing works except randomly making blocks and having the "vehicle" (currently a watermelon) fall down, completely ignoring the blocks. I need to work out effective and efficient rectangle-to-circle collision detection (compared to the very buggy physics of pinball.html).


Project #3.30: Slightly Generalized Dragon Curve

Sequence of Unfolding Angles:
(3/25/2023): A random small project inspired by a talk I heard today by Dr. Edward Burger at the Texas MAA Conference on the dragon curve fractal. A friend suggested I try making the Dragon Curve but you alternate unfolding 90° and 180° from the folded up paper. The result is this interesting looking fractal that flips orientation every iteration but still approaches a shape. There's definitely more generalizations I could make but it's late and I don't feel like coding a bunch of new functionality.

(3/27/2023): Added a text input for defining custom unfold-angle sequences. The one from two days ago is [270, 180].


Project #3.29: Stitch Walker
[ FPS: ]
(2/13/2023): I only got barely started on this but I want it to be a random walker that takes large steps and each step it draws a + end-to-end, to create a sort of "stitch" pattern across the canvas.


Project #3.28: Generative Slideshow
[ FPS: ]
(1/4/2023): An experiment with generatively displaying images. Currently, there's only one mode, which is randomly filling the screen with pixels, but I want to add other modes. It's also just set to show random images I put in from the `images` folder on this website.


Project #3.27: City Skyline
(12/30/2022): Currently this is just a basic proof-of-concept but I want to develop an interesting random city skyline generator, with buildings, windows, trees, maybe even streetlights and things like that.

(1/4/2023): Added some color and made things more visible.


Project #3.26: Random Bead Bracelets
(12/24/2022): I combined random smooth blobs from Project #3.20 and tangent circle rings from Project #3.24 to create blobby rings of tangent circles. Each circle sits on the edge of a random smoothed blob, but is always tangent to the circles adjacent to it. This creates organic shaped strings of beads, resembling bracelets or something similar to that. Currently, they're just randomly placed on the canvas.

(12/30/2022): I added a new CirclePack class and used that to make the bracelets fill the canvas without overlapping.


Project #3.25: Multi-Seed DLA
(12/17/2022): A failed ChatGPT program inspired me to make Diffusion Limited Aggregation, except with lots of particles moving at once, and they can all stick to each other. The result ended up being...underwhelming. The canvas fills up too quickly and doesn't make interesting patterns.
(Later that day): I redid how the program draws, and I actually like how it turned out now. Instead of drawing the circles themselves, I draw lines between each pair of colliding particles. Along with this, the frozen particle affects the color of the line, so you get small webs of the same color.
(Even later that day): I changed things even more. Now, I keep track of each particle's base particle and connected particle, and then draw it all at once (drawn by base particle) after the canvas is filled. I removed the frame() and animation functionality, now it's just a draw() function. I also added some settings that get randomized every generation, to create unique shapes every time; the settings are randomized for every blob, so that each blob looks unique as well. I also added a "zoom" setting, which scales everything on the canvas up by some certain factor, so I can modify `canvas25Scale` to zoom the final image in or out on regeneration.

(12/18/2022): I completely removed the "blob" algorithm and restructured how the program works. Before, I would slowly spawn particles over time, and if any of them collided, they'd stick and start a "blob." Then each time something stuck to something else, it would join that particle's "blob" and match the style of it. After the canvas is filled, I'd draw each "blob." The problem was, this is unnecessarily complicated, and also had some annoying bugs where blobs would share particles sometimes, for reasons I couldn't understand. So, I changed it. NOW, I lay out a few initial "seed" particles, and then apply DLA to that, just with multiple different trees to stick to. Now the drawing algorithm is much simpler and it seems to be quicker. Most encouragingly, I was able to remove those bugs, and now distinct trees don't touch. I also zoomed out the canvas a bit so that the trees never touch the edge, instead of always going past it.
(Later that day): I added different types of accents, instead of just a black dot at endpoints of each line. I want to consider adding a setting to vary "global styles" versus "individual styles," where, if active, some styles (line width, accent chance, accent type, etc.) will be global: randomized per generation, but not randomized for each tree.
(Even later that day): I implemented the global styles settings, and made it overcomplicated as well -- there's different presets for which settings will be synced, and complicated random value generation and synergy with that in an attempt to create random but interesting synced settings.

(12/19/2022): I added different spawning modes for seed particles: spawning randomly, spawning only on the edges, or spawning only on one edge.

(12/20/2022): I added a new accent type, along with a new connector type, which resembles a leaf instead of a simple line. I later added a third connector type, which is a cross shape.

(12/21/2022): Added a connector ratio setting to affect the sizes of different connector types, and some minor visual changes.

(3/6/2023): Actually finished! Added to generative-art-gallery.html as "Disrupted Possibilities (What Might Have Been)"


Project #3.24: Concentric Rings of Tangent Circles
(12/11/2022): I was experimenting with creating rings of circles that all touched at a single point. After doing some calculations, I realized that the answer lied in inscribed polygons, since n circles around a ring, touching at a single point, would form the vertices of an n-gon. So, I found a surprisingly simple formula for the radius of each circle, in terms of n: sin(Ï€/n). This program uses randomly spaced concentric rings of circles, with random designs on each one.

(12/12/2022): Added more circle types.


Project #3.23: "Generations" Cellular Automata


[ FPS: ]


Random Density: 50%

Grid Size: 100×100

Currently Drawing: State #1
Rule Presets:
(11/26/2022): I decided to run this as an experiment to see if I could accurately code a "Generations" cellular automata, which is an extension of a regular Life-like cellular automata but with support for multiple states. I did actually get it working relatively quickly and introduced some functionality like clicking and drawing.
(Later that day): Added lots of rule presets, along with settings and sliders for various things.


Project #3.22: Dynamic Shape Packing


Min Circle Size: 10
Max Circle Size: 100
Visual Size Ratio: 100%
Corner Skew: 20%
Shape Sides: 4 sides
(10/11/22): Simple bare-bones circle packing generative art, except I implemented the xoshiro128** seeded PRNG algorithm, so that the art doesn't randomize when you change settings, and you can see what the current piece would've looked like with those settings. "Randomize" sets a new seed.


Project #3.21: Connected Random Walkers
[ FPS: ]
(10/2/2022): Another idea that was less underwhelming in my head. Each shape is generated by a group of random walkers that connect together and draw lines as they move randomly around, which in turn randomly moves the entire group. It looks interesting enough, but I wish I could do something more with it to make it look really cool.


Project #3.20: 3D Blobby Terrain
(9/5/2022): Right now, this is just the base code for a simple grid averaging to create smooth noise, but I want to do more with it.

(9/6/2022): I finished up the grid averaging and added a more interesting way to draw the cells. Instead of grayscale squares at every value, they're instead circles (larger than the cells) with varying color, which are also drawn in a random order so they overlap randomly. I also added lots of random settings that make each output look unique. I like how this looks, but it still feels like something is missing.
(Later that day): I slightly changed the code so that instead of randomly ordering the cells, they are drawn lowest to highest, to create an interesting 3D look.
(Also later that day): I used my random smooth blob code from Project #3.14 to replace the circles, and added more randomness to how the blobs generate, along with adding yet more settings that are randomized every generation. There's currently 10 parameters that vary every time it redraws. I also added a chance to draw circles again instead of blobs.

(9/7/2022): I added a "jitter" variable that is randomized every generation, which controls how much variation each blob is drawn at from its original position. I also upped the number of points on each blob to make them less jagged, and slightly changed the smoothness variable to reflect that. I'm really pleased with how this turned out now, it's really satisfying to zoom in on it and look around at the landscape.

(9/8/2022): As one finishing touch, I just added an extra row and column on each side of the grid, so that there isn't a chance for gaps around the edges of the canvas, and the whole thing comes together better.

(9/13/2022): Actually finished! Added to generative-art-gallery.html as "Into The Floral Caverns"


Project #3.19: Flag Generator
(8/6/2022): A random flag generator that currently only generates flags in the style of Germany, Italy, Gambia, and that same general structure. Eventually I want to add a lot more to this, like flags similar to the US or Australia or England.


Project #3.18: Bouncing Blobs
[ FPS: ]
(8/3/2022): A bouncing simulation except that the objects that bounce are ellipses with a set width, and a height that just always stretches to the floor, creating a blobby bouncing effect.

(8/4/2022): Added a maximum height to the blobs so that it doesn't always reach the floor and bounces more convincingly now. I also made the blob's width adjust dynamically so that it stretches and squishes as it hits the floor. I also added mouse control, so you can click to add more blobs, and fixed some bugs.


Project #3.17: Sierpinski Quilt
(7/31/2022): Experimenting with Sierpinski Triangles resulted in this artwork, which tiles the plane with widely varying Sierpinski Triangles. Each one has a random set of settings, including "skew," which affects how imperfect each triangle is drawn, and messes with the overall structure of the Sierpinski Triangle.


Project #3.16: Von Neumann Fractal
(7/29/2022): I started wondering what would happen if you translated the brackets in a Von Neumann ordinal into L/R directions and ran it as an L-System. The Von Neumann ordinals are a system for representing natural numbers in set theory, such that 0 = {}, 1 = {{}}, 2 = {{}, {{}}}, 3 = {{}, {{}}, {{}, {{}}}}, etc. If we remove the commas and convert any "{" into "L" and "}" into "R," we obtain a set of left/right directions for each number. An L-System generator then acts out drawing these numbers by moving forward one unit and turning 90° left or right, based on the current letter in the directions. I was at first expecting some boring shape, but I was surprised to see that the Levy C Curve fractal appeared! And the interesting part is that the first steps don't actually match the typical first steps of a Levy C Curve, and yet it approaches the same shape. This is, in a sense, what numbers "look like" using the Von Neumann representation of natural numbers.

(7/30/2022): Added a text box displaying the Von Neumann Ordinal of the current number.


Project #3.15: Text Walker
Running...0.01% drawn

[ FPS: ]
(7/27/2022): A random walker that gradually writes out a given string of text. If it walks off the canvas, it picks a random edge position and continues. I also made the font size and brightness change gradually to give more variation. Currently, the quote that it is writing out is "Auguries of Innocence" by William Blake.

(7/28/2022, slightly past midnight): I changed the code for coloring so that instead of a color with varying brightness, it instead takes the color of an image based on it's current position, so that the text traces out an image over time. For now, it's just set to background.jpg. I also added a shadow blur so that text still stands out even when drawing over other text.
(Later that day): I made the stepsPerFrame change dynamically over time so that it starts off slow but gets really fast over time. After the Walker has reached 40,000 letters, it stops, completing the image. I also changed the background image to flower.png. I also added buttons to change between different modes, so that there's not just the Blake poem and flower as an option. Note for future self: If you want to change the image in the console, use img15.src, and use quote15 to change the quote.

(7/29/2022): Added percent complete text.

(7/30/2022): Added "Squares" mode.


Project #3.14: Sunny-Side-Up Eggsteroid Belt
(7/18/2022): Experimenting with random blob generating turning into this Eggsteroid Belt. The eggs are placed with normal circle packing, and the shapes of the eggs are are made by assigning random radii around a point and then averaging out each radius with its neighbors a few times (and scaling so it matches the initial given radius).

(7/20/2022): I spent ages trying to change the code so that eggs could be closer together, based on the actual shape of the egg, instead of just the bounding circle around it. I finally got it working though, which means that the eggs pack together better and leave less awkward spaces.
(Later that night): I added a Path object that eggs can't touch, which is a randomized sine wave snaking across the canvas, clearing a path through the asteroid field.

(7/18/2022): I added a rocket that is placed randomly in the open path, and is angled so it looks like it's flying through the path. It's just a blue rectangle for now but I want to make it a bacon rocketship to fit with the breakfast/space theme. I also added random tiny stars in the background to fill the empty space better and also make it more clear that this is in space, and added some randomization for the minimum and maximum circle sizes to create more variation on each generation.

(7/24/2022): I finally got an algorithm working for drawing random bacon, and I actually like how it turned out. It has a random size, waviness, number of stripes, etc. and it replaces the blue rectangle as the rocket body.
(Later that day): Added a fire trail to the bacon rocket and added motion blur lines that slope with the path to show the route the rocket has taken, and indicate it's going really fast.

(9/15/2022): Actually finished! Added to generative-art-gallery.html as "Surfing the Sunny-Side-Up Eggsteroid Belt"


Project #3.13: Luminous Snowflakes
[ FPS: ]
(7/17/2022): I was inspired by the look of Project #3.12 so this has a similar structure. A number of "Collectors" are strewn about the canvas, each with a set position, hue, scale, angle, etc. Each frame (2000 times), a random Collector is chosen and a line is drawn, biased towards the center of the collector. The angle of the drawn line is constrained to be a multiple of 60° to make 6-fold symmetry (and angled by the Collector's angle). This creates interesting patterns from the overlay of hundreds of thousands of incredibly thin and translucent lines that resemble snowflake shapes.
(Later that night): Added more settings that are randomized every time you click "Reset." I wanted to make this a piece in the Generative Art Gallery, but in order for it to have the look I want, over 300,000 lines have to be drawn, which takes a solid 5-6 seconds every single time, which would probably be way too laggy to actually implement.
(Even later that night): Added a tilt variable that affects how offset the lines' angles are, instead of always snapping to a 60° multiple.


Project #3.12: Random Crossing Lines
(7/16/2022): I'm honestly not really sure what this is. It started out as an attempt to draw some simple colorful pattern for a background on Project #3.11, but it didn't fit the galaxy theme so I moved it to a new project. It's basically a 50×50 grid randomly filled with bars that go from left-to-right or top-to-bottom, but positioned from their corner, and biased towards the center of the canvas. This creates an interesting shape in the middle of the canvas.


Project #3.11: Clustering Stars
(7/16/2022): I wanted to make a generative art galaxy generator, but currently I only have the stars working. The stars randomly lerp to a few random invisible black holes around the canvas so that they cluster and form structures and groups, instead of just being randomly strewn about the canvas. I want to add more to this generator eventually so that it actually looks like an intricate galaxy.


Project #3.10: Random Open Circles in a Grid
(7/14/2022): I'm not really sure where I was going with this, but the final result is kinda interesting looking. It's a variation on Project #2.87 in Test Bed 2, but where the smallest circles aren't drawn, and each circle has a random "mouth" cut out from it. It looked different in my head before making it, so I'm not super proud of the outcome, but it looks cool enough that I'll keep it.

(7/16/2022): I changed how the "mouths" draw to just be a slice cut out of a full circle instead of a strange rounded cutout (but added a button to switch to the old moded too).


Project #3.9: Generative Pipes
(7/9/2022): This started out as a variation on Project #3.4, except without the self-avoidance. Basically, it's just a random walker that only draws a line when it isn't on a previously visited square, which will eventually fill the whole grid with one connected path. Soon after I got that working, I added lots of varying settings and designs and it now resembles abstract pipes or connectors. This was a small project initially that I didn't really care about but I really love how it looks now.
(Later that night): Added a simple black shadow blur to everything and it greatly improved the depth of the piece overall.

(7/10/2022): Modified the grid so that there's extra tiles off the canvas, so that the pipes connect offscreen, which brings the piece together better.
(Later that day): Actually finished! Added to generative-art-gallery.html as "Jumbled Pipeworks"


Project #3.8: Camera-Following Random Walker
[ FPS: ]
(7/4/2022, slightly past midnight): A random walker that moves with Brownian motion and traces out a path behind it, except a "camera" always centers on it as it moves around, so the walker is always in the middle of the canvas. I like how this looks but I want to find some way to make a smoother random walker, so the camera doesn't shake around so much every frame.
(Later that day): I improved the smoothness by only taking 1 step per frame, instead of 5, and just turning up the velocity, and fiddling with some other settings. I also gave it a cool visual change which reminds me of maybe a firefly or a spark, with a glowing yellow trail that gets smaller and dimmer towards the end of the tail.
(Even later that day): Added a glowing Spark object that spawns around the walker's trail as it moves.
(Later that night): Modified the Sparks and made them spawn randomly on the canvas, and made the walker's hue gradually change.

(7/9/2022) Made the walker always draw above Sparks, which looks better when it moves over one.


Project #3.7: Generative Caves With Marching Squares
(7/2/2022): Procedural cave generator using cellular automata. I used the same idea as this tutorial from Sebastian Lague but with my own code.
(Later that night): I implemented the marching squares algorithm onto the cave generator so it creates smoother and more natural looking formations, and added colors.
(Even later that night): Still following the videos, I added polishing the cave to remove tiny sections of walls and tiny pockets of air.

(7/3/2022, continuing past midnight): Added the beginning of making passageways between isolated rooms so that they're all connected. It doesn't work yet but the groundwork for the code is there and functional.
(Later that day): Got the passageway algorithm working properly, though they still don't actually draw yet.

(7/9/2022): Finally finished the tutorial and got the passageways working!


Project #3.6: 1D Circle Packing
(7/2/2022): Circle packing in one dimension, but repeated several times at different heights. I like the structure that the output has, but even after fiddling with the visual style a lot I can't get it to look quite how I want it to.
(Later that day): I changed up the code a lot for how it draws. Now there's between 20 and 30 rows (so they smush together), and lots of settings are randomized every generation. The ends also vary in length and together, and there's a shadow blur. I'm actually really pleased with how it turned out now.

(7/9/2022): Actually finished! Added to generative-art-gallery.html as "Harmonic Precision"


Project #3.5: Alien Hieroglyphs
(7/2/2022): Alien glyph generator, using the same random path generator from Project #3.4, but run multiple times in a grid, resembling some kind of intricate alien language. I added glow and colors to increase the effect, and also made the characters generate similar to Japanese kanji (in columns from the top). I also added lots of randomization for each character to increase the variety.

(7/9/2022): Actually finished! Added to generative-art-gallery.html as "Alien Hieroglyphs"


Project #3.4: Space-Filling Path
[ FPS: ]
Grid Size: 10×10



Turn Chance: 10%



Total Coverage: 100%
Path Thickness: 40%



Path Hue: 60°



Path Contrast: 0%



(6/30/2022): A variation on the previous project where there is only ever one path, but once it gets stuck it just stops drawing and is allowed to walk through itself, until it reaches an open square. This is repeated over and over, slowly filling the canvas with a single branching path.
(Later that night): I spent over an hour trying half a dozen different ways to fix one bug and finally got it (hopefully) fixed. The bug was that diagonal paths could sometimes cause lines to be drawn incorrectly and you could have 2 distinct disconnected paths, instead of a single connected path every time.

(7/1/2022, and 7/2/2022 past midnight): Added more visual settings like hue and contrast, and added sliders for everything.


Project #3.3: Self-Avoiding Random Walkers
[ FPS: ]

Grid Size: 50×50



Turn Chance: 10%



Total Coverage: 100%
Path Thickness: 50%



End Node Size: 0%



Drawing Mode:

Movement Directions:





Rendering Speed:


(6/28/2022): I finally got an implementation of a self-avoiding random walk working correctly--the walker moves randomly (with a low turn chance) but never crosses itself or an old path. When it gets stuck, it starts a new path with a new color and repeats until the canvas is filled.
(Later that day): Added a second drawing mode which is just filled squares instead of connected paths.

(6/29/2022): Added sliders for everything. Added support for diagonal movement which works well but not perfectly. I got the kinks worked out so that even diagonal paths never cross--but there's often lots of space left open as a result of that, and I'm not sure if I can do anything about that.
(Slightly later that night): I fiddled with the code some more and got diagonal movement working perfectly now, and added radio buttons for directions.

(10/1/2022): Actually finished! Added to generative-art-gallery.html as "The Jeweled Halls of Isfet"


Project #3.2: Skewed Grid
(6/27/2022): A grid of squares but with an added skew variable (which affects how much the corners of each square move from their normal position), which increases towards the center of the grid. There is also a draw chance variable for various lines across each square that also increases towards the center of the grid.


Project #3.1: Banded Bouncing Trails
[ FPS: ]
(6/26/2022): A random project involving bouncing circles that randomly change their hue over time, and which slowly grow darker and smaller until they disappear, creating twisting trails with bands of color along them. Click to add more circles. This isn't a super important project but I implemented a really important idea for bouncing--smoothness. Instead of getting blocky trails (like in bounce.html) when trailing is turned on, the circles instead render 5 times per frame, moving at 1/5 their speed every time. This results in identical behavior, but with more pleasing and smooth trails.