I was inspired by some Haskell code written by keegan, so I had to write a version of it in C. I didn’t do any animation, but I did have a lot of fun playing around with the parameters. For instance, check out the code, and how changing the value of N from 5, 7, and 19 generates interesting and cool patterns.
[sourcecode lang=”cpp”]
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <assert.h>
/*
* quasi.c
*
* Some code, inspired by keegan @
* http://mainisusuallyafunction.blogspot.com/2011/10/quasicrystals-as-sums-of-waves-in-plane.html
* but presented without any further explanation.
*/
#define N (19)
#define XSIZE (1280)
#define YSIZE (720)
#define SCALE (0.2)
double x[N], y[N], ph[N] ;
double image[YSIZE][XSIZE] ;
int
main()
{
int i, j, k ;
for (i=0; i<N; i++) {
x[i] = cos(2.0 * M_PI * i / (double) N) ;
y[i] = sin(2.0 * M_PI * i / (double) N) ;
ph[i] = 0.0 ;
}
for (j=0; j<YSIZE; j++) {
for (i=0; i<XSIZE; i++) {
image[j][i] = 0. ;
for (k=0; k<N; k++) {
double d = (x[k] * (i – XSIZE / 2.) + y[k] * (j – YSIZE / 2.) + ph[k]) * SCALE ;
image[j][i] += (1.0 + cos(d)) / 2. ;
}
int t = (int) floor(image[j][i]) ;
assert(t >= 0.) ;
double v = image[j][i] – t ;
if (t % 2 == 1) v = 1. – v ;
image[j][i] = v ;
}
}
printf("P5\n%d %d\n%d\n", XSIZE, YSIZE, 255) ;
for (j=0; j<YSIZE; j++)
for (i=0; i<XSIZE; i++)
putchar(255. * image[j][i]) ;
return 0 ;
}
[/sourcecode]
Cool stuff!
Fun, thanks. But curious: how does it work to use putchar to write a double?
It’ll coerce it to an integer. I could have (and probably should) have put in an explicit cast.