mbrot-mt

changeset 0:e9ae6289e14f

initial commit
author John Tsiombikas <nuclear@member.fsf.org>
date Fri, 07 Mar 2014 07:42:48 +0200
parents
children 3a893f9831ac
files Makefile src/mbrot-mt.c
diffstat 2 files changed, 172 insertions(+), 0 deletions(-) [+]
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/Makefile	Fri Mar 07 07:42:48 2014 +0200
     1.3 @@ -0,0 +1,13 @@
     1.4 +src = $(wildcard src/*.c)
     1.5 +obj = $(src:.c=.o)
     1.6 +bin = mbrot
     1.7 +
     1.8 +CFLAGS = -pedantic -Wall -g `pkg-config --cflags sdl`
     1.9 +LDFLAGS = `pkg-config --libs sdl`
    1.10 +
    1.11 +$(bin): $(obj)
    1.12 +	$(CC) -o $@ $(obj) $(LDFLAGS)
    1.13 +
    1.14 +.PHONY: clean
    1.15 +clean:
    1.16 +	rm -f $(obj) $(bin)
     2.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     2.2 +++ b/src/mbrot-mt.c	Fri Mar 07 07:42:48 2014 +0200
     2.3 @@ -0,0 +1,159 @@
     2.4 +#include <stdio.h>
     2.5 +#include <complex.h>
     2.6 +#include <SDL/SDL.h>
     2.7 +
     2.8 +void display(void);
     2.9 +int mandelbrot(float x, float y, int max_iter, int *iter);
    2.10 +int handle_event(SDL_Event *ev);
    2.11 +
    2.12 +static SDL_Surface *fbsurf;
    2.13 +static int win_width, win_height;
    2.14 +static float win_aspect;
    2.15 +static float xoffs, yoffs, zoom = 1.0;
    2.16 +static int max_iter = 64;
    2.17 +
    2.18 +int main(void)
    2.19 +{
    2.20 +	win_width = 800;
    2.21 +	win_height = 600;
    2.22 +	win_aspect = (float)win_width / (float)win_height;
    2.23 +
    2.24 +	SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER);
    2.25 +	if(!(fbsurf = SDL_SetVideoMode(win_width, win_height, 32, SDL_SWSURFACE | SDL_RESIZABLE))) {
    2.26 +		fprintf(stderr, "failed to create framebuffer\n");
    2.27 +		return 1;
    2.28 +	}
    2.29 +
    2.30 +	SDL_WM_SetCaption("Mandelbrot", 0);
    2.31 +
    2.32 +	for(;;) {
    2.33 +		SDL_Event ev;
    2.34 +
    2.35 +		while(SDL_PollEvent(&ev)) {
    2.36 +			if(handle_event(&ev) == -1) {
    2.37 +				goto done;
    2.38 +			}
    2.39 +		}
    2.40 +
    2.41 +		display();
    2.42 +	}
    2.43 +
    2.44 +done:
    2.45 +	SDL_Quit();
    2.46 +	return 0;
    2.47 +}
    2.48 +
    2.49 +void display(void)
    2.50 +{
    2.51 +	unsigned char *fbuf, *pixptr;
    2.52 +	int i, j, xsz, ysz;
    2.53 +
    2.54 +	if(SDL_MUSTLOCK(fbsurf)) {
    2.55 +		SDL_LockSurface(fbsurf);
    2.56 +	}
    2.57 +	fbuf = fbsurf->pixels;
    2.58 +	xsz = fbsurf->w;
    2.59 +	ysz = fbsurf->h;
    2.60 +
    2.61 +	pixptr = fbuf;
    2.62 +	for(i=0; i<ysz; i++) {
    2.63 +		float y = 2.0 * (float)i / (float)ysz - 1.0;
    2.64 +		for(j=0; j<xsz; j++) {
    2.65 +			float x = (2.0 * (float)j / (float)xsz - 1.0) * win_aspect;
    2.66 +
    2.67 +			int iter, r, g, b;
    2.68 +			int inset = mandelbrot((x - xoffs) * zoom, (y - yoffs) * zoom, max_iter, &iter);
    2.69 +			if(!inset) {
    2.70 +				r = iter * 256 / max_iter;
    2.71 +				g = 0;
    2.72 +				b = 0;
    2.73 +			} else {
    2.74 +				r = g = b = 0;
    2.75 +			}
    2.76 +
    2.77 +			pixptr[0] = b;
    2.78 +			pixptr[1] = g;
    2.79 +			pixptr[2] = r;
    2.80 +			pixptr[3] = 255;
    2.81 +			pixptr += 4;
    2.82 +		}
    2.83 +	}
    2.84 +
    2.85 +	if(SDL_MUSTLOCK(fbsurf)) {
    2.86 +		SDL_UnlockSurface(fbsurf);
    2.87 +	}
    2.88 +	SDL_Flip(fbsurf);
    2.89 +}
    2.90 +
    2.91 +int mandelbrot(float x, float y, int max_iter, int *iter)
    2.92 +{
    2.93 +	int i;
    2.94 +	complex float c = x + y * I;
    2.95 +	complex float z = c;
    2.96 +
    2.97 +	for(i=0; i<max_iter; i++) {
    2.98 +		float re = creal(z);
    2.99 +		float im = cimag(z);
   2.100 +		if(re * re + im * im > 4) {
   2.101 +			if(iter) *iter = i;
   2.102 +			return 0;
   2.103 +		}
   2.104 +
   2.105 +		z = z * z + c;
   2.106 +	}
   2.107 +
   2.108 +	return 1;
   2.109 +}
   2.110 +
   2.111 +int handle_event(SDL_Event *ev)
   2.112 +{
   2.113 +	static int prev_x, prev_y;
   2.114 +	static int bnstate[32];
   2.115 +
   2.116 +	switch(ev->type) {
   2.117 +	case SDL_KEYDOWN:
   2.118 +		if(ev->key.keysym.sym == SDLK_ESCAPE) {
   2.119 +			return -1;
   2.120 +		}
   2.121 +
   2.122 +	case SDL_MOUSEBUTTONDOWN:
   2.123 +		prev_x = ev->button.x;
   2.124 +		prev_y = ev->button.y;
   2.125 +		bnstate[ev->button.button - SDL_BUTTON_LEFT] = 1;
   2.126 +		break;
   2.127 +
   2.128 +	case SDL_MOUSEBUTTONUP:
   2.129 +		bnstate[ev->button.button - SDL_BUTTON_LEFT] = 0;
   2.130 +		break;
   2.131 +
   2.132 +	case SDL_MOUSEMOTION:
   2.133 +		{
   2.134 +			int dx = ev->button.x - prev_x;
   2.135 +			int dy = ev->button.y - prev_y;
   2.136 +			prev_x = ev->button.x;
   2.137 +			prev_y = ev->button.y;
   2.138 +
   2.139 +			if(!dx && !dy) break;
   2.140 +
   2.141 +			if(bnstate[0]) {
   2.142 +				xoffs += win_aspect * 2.0 * (float)dx / (float)win_width;
   2.143 +				yoffs += 2.0 * (float)dy / (float)win_height;
   2.144 +			}
   2.145 +			if(bnstate[2]) {
   2.146 +				zoom += (float)dy / (float)win_height;
   2.147 +				if(zoom < 1e-6) zoom = 1e-6;
   2.148 +			}
   2.149 +		}
   2.150 +		break;
   2.151 +
   2.152 +	case SDL_VIDEORESIZE:
   2.153 +		win_width = ev->resize.w;
   2.154 +		win_height = ev->resize.h;
   2.155 +		win_aspect = (float)win_width / (float)win_height;
   2.156 +		break;
   2.157 +
   2.158 +	default:
   2.159 +		break;
   2.160 +	}
   2.161 +	return 0;
   2.162 +}