clray

view src/rt.cc @ 9:a09622aaa043

moving to triangles
author John Tsiombikas <nuclear@member.fsf.org>
date Sat, 24 Jul 2010 06:28:17 +0100
parents deaf85acf6af
children d9a1bab1c3f5
line source
1 #include <stdio.h>
2 #include <string.h>
3 #include <math.h>
4 #include <assert.h>
5 #include "ocl.h"
6 #include "mesh.h"
8 struct RendInfo {
9 int xsz, ysz;
10 int num_faces, num_lights;
11 int max_iter;
12 } __attribute__((packed));
14 struct Ray {
15 float origin[4], dir[4];
16 } __attribute__((packed));
18 struct Light {
19 float pos[4], color[4];
20 } __attribute__((packed));
22 static Ray get_primary_ray(int x, int y, int w, int h, float vfov_deg);
24 static Ray *prim_rays;
25 static CLProgram *prog;
26 static int global_size;
28 static Face faces[] = {
29 {/* face0 */
30 {
31 {{-1, 0, 0, 1}, {0, 0, -1, 1}, {0, 0}},
32 {{0, 1, 0, 1}, {0, 0, -1, 1}, {0, 0}},
33 {{1, 0, 0, 1}, {0, 0, -1, 1}, {0, 0}}
34 },
35 {0, 0, -1, 1}, 0
36 },
37 {/* face1 */
38 {
39 {{-5, 0, -3, 1}, {0, 0, -1, 1}, {0, 0}},
40 {{0, 0, 3, 1}, {0, 0, -1, 1}, {0, 0}},
41 {{5, 0, -3, 1}, {0, 0, -1, 1}, {0, 0}}
42 },
43 {0, 0, -1, 1}, 1
44 }
45 };
47 static Material matlib[] = {
48 {{1, 0, 0, 1}, {1, 1, 1, 1}, 0, 0, 60.0},
49 {{0.2, 0.8, 0.3, 1}, {0, 0, 0, 0}, 0, 0, 0}
50 };
52 static Light lightlist[] = {
53 {{-10, 10, -20, 1}, {1, 1, 1, 1}}
54 };
56 static float xform[16] = {
57 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1
58 };
60 static RendInfo rinf;
63 bool init_renderer(int xsz, int ysz, float *fb)
64 {
65 // render info
66 rinf.xsz = xsz;
67 rinf.ysz = ysz;
68 rinf.num_faces = sizeof faces / sizeof *faces;
69 rinf.num_lights = sizeof lightlist / sizeof *lightlist;
70 rinf.max_iter = 6;
72 /* calculate primary rays */
73 prim_rays = new Ray[xsz * ysz];
75 for(int i=0; i<ysz; i++) {
76 for(int j=0; j<xsz; j++) {
77 prim_rays[i * xsz + j] = get_primary_ray(j, i, xsz, ysz, 45.0);
78 }
79 }
81 /* setup opencl */
82 prog = new CLProgram("render");
83 if(!prog->load("rt.cl")) {
84 return false;
85 }
87 /* setup argument buffers */
88 prog->set_arg_buffer(0, ARG_WR, xsz * ysz * 4 * sizeof(float), fb);
89 prog->set_arg_buffer(1, ARG_RD, sizeof rinf, &rinf);
90 prog->set_arg_buffer(2, ARG_RD, sizeof faces, faces);
91 prog->set_arg_buffer(3, ARG_RD, sizeof matlib, matlib);
92 prog->set_arg_buffer(4, ARG_RD, sizeof lightlist, lightlist);
93 prog->set_arg_buffer(5, ARG_RD, xsz * ysz * sizeof *prim_rays, prim_rays);
94 prog->set_arg_buffer(6, ARG_RD, sizeof xform, &xform);
96 global_size = xsz * ysz;
97 return true;
98 }
100 void destroy_renderer()
101 {
102 delete [] prim_rays;
103 delete prog;
104 }
106 bool render()
107 {
108 if(!prog->run(1, global_size)) {
109 return false;
110 }
112 CLMemBuffer *mbuf = prog->get_arg_buffer(0);
113 map_mem_buffer(mbuf, MAP_RD);
114 unmap_mem_buffer(mbuf);
115 return true;
116 }
118 void set_xform(float *matrix)
119 {
120 CLMemBuffer *mbuf = prog->get_arg_buffer(6);
121 assert(mbuf);
123 assert(map_mem_buffer(mbuf, MAP_WR) == xform);
124 memcpy(xform, matrix, sizeof xform);
125 unmap_mem_buffer(mbuf);
126 }
128 static Ray get_primary_ray(int x, int y, int w, int h, float vfov_deg)
129 {
130 float vfov = M_PI * vfov_deg / 180.0;
131 float aspect = (float)w / (float)h;
133 float ysz = 2.0;
134 float xsz = aspect * ysz;
136 float px = ((float)x / (float)w) * xsz - xsz / 2.0;
137 float py = 1.0 - ((float)y / (float)h) * ysz;
138 float pz = 1.0 / tan(0.5 * vfov);
140 px *= 100.0;
141 py *= 100.0;
142 pz *= 100.0;
144 Ray ray = {{0, 0, 0, 1}, {px, py, pz, 1}};
145 return ray;
146 }