private void LoadShaderToyFile(string filepath) { int displayOutputBufferId = 1; renderer.Clear(); using (ZipArchive zip = ZipFile.OpenRead(filepath)) { renderer.SharedFragmentCode = zip.GetEntry("common.glsl")?.ReadToEnd(); string vertexShader = zip.GetEntry("shared.vs.glsl").ReadToEnd(); foreach (ZipArchiveEntry entry in zip.Entries) { if (entry.Name.StartsWith("rp") && entry.Name.EndsWith(".json")) { JObject jRenderPass = JObject.Parse(entry.ReadToEnd()); if (jRenderPass["type"].Value <string>() == "image") { displayOutputBufferId = jRenderPass["outputs"].Values <int>().First(); } ZipArchiveEntry shaderEntry = zip.GetEntry(jRenderPass["code"].Value <string>()); string shaderCode = shaderEntry.ReadToEnd(); RenderPassBuilder rpb = RenderPassBuilder.FromString(jRenderPass["name"].Value <string>(), vertexShader, shaderCode); foreach (JObject obj in jRenderPass["inputs"]) { string type = obj["type"].Value <string>(); if (type == "buffer") { rpb.AddBufferInput(obj["channel"].Value <int>(), obj["id"].Value <int>()); } else if (type == "texture") { string src = obj["src"].Value <string>(); ZipArchiveEntry e = zip.Entries.FirstOrDefault(x => src.EndsWith(x.Name)); rpb.AddTextureInput(obj["channel"].Value <int>(), e.Name, e.ReadAllBytes()); } } foreach (int bufferId in jRenderPass["outputs"].Values <int>()) { rpb.AddOutput(bufferId); } RenderPass rp = rpb.Create(); renderer.Add(rp); } } } renderer.DisplayOutputBufferId = displayOutputBufferId; renderer.InitPasses(); }