git.s-ol.nu glsl-view / e56efe8
resolve '#pragma include "...path..."' directives s-ol 8 months ago
1 changed file(s) with 53 addition(s) and 8 deletion(s). Raw diff Collapse all Expand all
103103
104104 const shader_file = try fs.cwd().openFile(config.fragment, .{});
105105 var last_stat = try shader_file.stat();
106 try reloadShader(&main_program, shader_file, last_stat.size);
106 try reloadShader(&main_program, shader_file, config.fragment, last_stat.size);
107107
108108 var cache = gl.UniformCache.init(std.heap.c_allocator, &main_program);
109109 defer cache.deinit();
110110
111111 const control = try ctrl.ControlServer.init(&arena.allocator, config.osc, &cache);
112112 defer control.destroy();
113
114 _ = try cache.get("radius\x00");
115113
116114 while (c.glfwWindowShouldClose(window) == c.GL_FALSE) {
117115 c.glfwMakeContextCurrent(window);
123121
124122 const stat = try shader_file.stat();
125123 if (stat.mtime > last_stat.mtime) {
126 try reloadShader(&main_program, shader_file, stat.size);
124 try reloadShader(&main_program, shader_file, config.fragment, stat.size);
127125 try cache.refresh();
128126 last_stat = stat;
129127 }
153151 }
154152 }
155153
156 fn reloadShader(current: *gl.ShaderProgram, frag_file: fs.File, size: u64) !void {
157 var frag_source = try c_allocator.alloc(u8, @intCast(usize, size));
154 // given a file and the directory it is in, resolve references
155 fn loadFile(writer: anytype, dir: []const u8, filename: []const u8) !void {
156 const file_dir = try std.fs.path.resolve(c_allocator, &[_][]const u8{
157 dir,
158 std.fs.path.dirname(filename) orelse "",
159 });
160 defer c_allocator.free(file_dir);
161
162 const file_path = try std.fs.path.resolve(c_allocator, &[_][]const u8{ dir, filename });
163 defer c_allocator.free(file_path);
164
165 var file = try fs.openFileAbsolute(file_path, .{});
166 defer file.close();
167 var reader = file.reader();
168
169 var buf: [1024]u8 = undefined;
170 while (try reader.readUntilDelimiterOrEof(&buf, '\n')) |line| {
171 if (std.mem.startsWith(u8, line, "#pragma ")) {
172 var parts = std.mem.split(line, " ");
173 _ = parts.next();
174 const pragma = parts.next().?;
175
176 if (std.mem.eql(u8, pragma, "include")) {
177 var include_path = parts.next().?;
178 if (include_path[0] != '"' or include_path[include_path.len - 1] != '"') {
179 std.debug.warn("Invalid #pragma directive '{}'\n", .{line});
180 continue;
181 }
182 include_path = include_path[1 .. include_path.len - 1];
183
184 loadFile(writer, file_dir, include_path) catch unreachable;
185
186 continue;
187 } else {
188 std.debug.warn("Unknown #pragma directive '{}'\n", .{pragma});
189 }
190 }
191
192 _ = try writer.write(line);
193 _ = try writer.write("\n");
194 }
195 }
196
197 fn reloadShader(current: *gl.ShaderProgram, frag_file: fs.File, frag_filename: []const u8, size: u64) !void {
198 var buffer = try std.ArrayList(u8).initCapacity(c_allocator, @intCast(usize, size));
199 var writer = buffer.writer();
200 errdefer buffer.deinit();
201
202 try loadFile(buffer.writer(), "", frag_filename);
203
204 const frag_source = buffer.toOwnedSlice();
158205 defer c_allocator.free(frag_source);
159 try frag_file.seekTo(0);
160 const length = try frag_file.read(frag_source);
161206
162207 const vert_source =
163208 \\#version 330 core