Skip to content

Instantly share code, notes, and snippets.

@skeeto

skeeto/colorsort.c

Last active Jun 25, 2020
Embed
What would you like to do?
Color sort
/* Sort lines independently and animate it
* $ cc -O3 -DN=720 colorsort.c
* $ ./a.out | mpv --no-correct-pts --fps=30 -
* https://nullprogram.com/video/?v=colors-odd-even
* https://redd.it/73oz1x
* This is free and unencumbered software released into the public domain.
*/
#include <time.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#ifndef N
# define N 360
#endif
static uint32_t
pcg32(uint64_t s[1])
{
uint64_t m = 0x9b60933458e17d7d;
uint64_t a = 0xd737232eeccdf7ed;
*s = *s * m + a;
int shift = 29 - (*s >> 61);
return *s >> shift;
}
static int
mod(int a, int b)
{
return (a % b + b) % b;
}
static void
print_pixel(int v)
{
int h = mod(v, N) / (N / 6);
int f = mod(v, N) % (N / 6);
int t = 255 * f / (N / 6);
int q = 255 - t;
switch (h) {
case 0:
putchar(0xff);
putchar(t);
putchar(0);
break;
case 1:
putchar(q);
putchar(0xff);
putchar(0);
break;
case 2:
putchar(0);
putchar(0xff);
putchar(t);
break;
case 3:
putchar(0);
putchar(q);
putchar(0xff);
break;
case 4:
putchar(t);
putchar(0);
putchar(0xff);
break;
case 5:
putchar(0xff);
putchar(0);
putchar(q);
break;
}
}
static void
dump(int image[N][N])
{
printf("P6\n%d %d\n255\n", N, N);
for (int y = 0; y < N; y++)
for (int x = 0; x < N; x++)
print_pixel(image[y][x]);
fflush(stdout);
}
static void
image_init(int image[N][N])
{
for (int y = 0; y < N; y++)
for (int x = 0; x < N; x++)
image[y][x] = x;
}
static void
image_shuffle(int image[N][N], uint64_t *s)
{
for (int y = 0; y < N; y++) {
for (int x = N - 1; x > 1; x--) {
int i = pcg32(s) % (x + 1);
int tmp = image[y][x];
image[y][x] = image[y][i];
image[y][i] = tmp;
}
}
}
static long
image_sort_step(int image[N][N])
{
/* Odd-even sort */
long c = 0;
for (int y = 0; y < N; y++) {
for(int x = 1; x < N - 1; x += 2) {
if (image[y][x] > image[y][x + 1]) {
int tmp = image[y][x];
image[y][x] = image[y][x + 1];
image[y][x + 1] = tmp;
c++;
}
}
for (int x = 0; x < N - 1; x += 2) {
if (image[y][x] > image[y][x + 1]) {
int tmp = image[y][x];
image[y][x] = image[y][x + 1];
image[y][x + 1] = tmp;
c++;
}
}
}
return c;
}
int
main(void)
{
static int image[N][N];
uint64_t s[] = {0xf34813d8cc836d98};
*s ^= time(0);
image_init(image);
image_shuffle(image, s);
do
dump(image);
while (image_sort_step(image));
dump(image);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.