The asterisk [*] — a star. It’s all-powerful, yet noncommittal (why should any one letter deserve my attention? You have to be special to earn that). I like stars, space, vectors, and the interplay between Sine and Cosine, so I made the formation of a galaxy.
I rarely use sketchbooks (I find them simultaneously too constraining, too unconstrained, to fast, and too slow), but I do like diagrams:
I unfortunately could not get the stars to spin the way I wanted (Two.js doesn’t have complete vector implementation), but what I ended up with serendipitously gave me something that feels more full and three-dimensional than what I was trying to achieve.
Inspiration and the discovery that Two.js has an Underscore.js dependency go to Max Hawkins, Shan Huang, and Justin Windle. Overall, my favorite characters might be Max Hawkin’s “H” or Sebastian Tissot’s “A”
Anitype.register('*', {
author: 'John Mars',
website: 'http://M4R5.io',
construct: function(two, points) {
// reference to this instance
var anitype = this;
// the letter skeleton
var polygon = anitype.makePolygon(points);
// the vertices of the letter, subdivided
var vertices = polygon.subdivide(3).vertices;
// Two.js has an Underscore.js dependency, so we can use it here
// make a random-sized "star" for each vertex, but place it randomly on the canvas
var stars = _.map(vertices, function(vertex, i) {
var star = two.makeCircle(0, 0, 10);
star.translation.set(Math.random() * 1000 - 500, Math.random() * 1000 - 500);
star.scale = Math.random() * 4;
return star;
});
// create a list of each vertex as a vector (for vector math later)
var vertexVectors = _.map(vertices, function(vertex, i) {
return new Two.Vector(vertices[i].x, vertices[i].y);
});
// pick a random sign (+/-) for each vertex (for vector math later)
var directions = _.map(vertices, function(vertex, i) {
return Math.random() < 0.5 ? -1 : 1;
});
// control individual star scaling
_.each(stars, function(star, i) {
console.log(vertices[i].x);
anitype.addTween(star, {
to: {scale: 1},
easing: Anitype.Easing.Exponential.In,
duration: 0.66,
start: 0
});
});
// control individual star movement
anitype.addTick(function(percent){
_.each(stars, function(star, i) {
// linear interpolation from current star position to goal vertex position, as a function of the current frame
star.translation.lerp(vertexVectors[i], percent * 2);
// vector rotations for orbital realism
star.translation.addSelf(
new Two.Vector(
Math.cos(percent * Math.PI * 2) * (1.0 - percent) * 5 * directions[i],
Math.sin(percent * Math.PI * 2) * (1.0 - percent) * 5 * directions[i]
)
);
});
}, Anitype.Easing.Exponential.In);
// Return stars wrapped in a group.
return two.makeGroup(stars);
}
});