Never Before Seen

The first entry in a 100 day of generative art and creative code project. My goal is to learn a few new things each project, document them to help clarify my understand and move on. By the end, I hope to be creating some cool things and learn a ton.

Click on the image below to re-arrange, refresh for new color palette. Full screen here.

Playing with the excellent GreenSock tween library and CSS shapes. And setting up with parcel for a journey back into creative code.

CSS Triangles?

Making shapes with css is fun. Boxes are easy, of course. Circles and ellipses are the same boxes with border radius tweaks. But triangles compelled some research on how the border properties actually work.

Here’s how to make a triangle in css (from Chris Coyier)

width: 0;
height: 0;
border-left: 50px solid transparent;
border-right: 50px solid transparent;
border-bottom: 100px solid red;"


Border sizes are outside of the content size, setting height and width to 0 applies to the content and doesn’t affect borders. If we assume borders are straight rectangles it is hard to imagine how this tapers into a triangle The secret is that borders join other borders at 45 degree miter type joint rather than overlapping square. If there’s no top border the two sides will join each other at the top. Detailed discussion here.


The project generates a color palette using color-scheme-js

var scheme = new ColorScheme();
.from_hue(randomIntFromInterval(0, 100)) // Start the scheme
.scheme("analogic") // Use the 'triade' scheme, that is, colors
// selected from 3 points equidistant around
// the color wheel.
var colors = scheme.colors();

Then a number of divs are generated with random sizes, shapes (circle, rectangle or triangle), assigned colors and inserted into the dom.


Results are then rearranged by tweening to random coordinates and rotating using TweenMax

function shuffle() {
let divs = document.getElementsByTagName("div");
for (let i = 0; i < divs.length; i++) {
TweenMax.set(divs[i], { xPercent: -50, yPercent: -50, left: 0, top: 0 });[i], 1.5, {
rotation: "+=" + randomIntFromInterval(20, 270),
x: randomIntFromInterval(
Math.floor(maxW * 0.15),
Math.floor(maxW * 0.75)
y: randomIntFromInterval(
Math.floor(maxH * 0.15),
Math.floor(maxH * 0.75)

with every mouse click and/or touch

document.addEventListener("touchstart", (e) => {

document.addEventListener("click", (e) => {

The number of objects created and their sizes depends on the size of the screen and these constraints are regenerated with each resize after clearing the dom of its previous divs

document.body.innerHTML = "";
Previous Building Electron Applications with Multiple Pages Next Starfields