node_shader.ts 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653
  1. type node_shader_t = {
  2. context?: node_shader_context_t;
  3. shader_type?: string;
  4. ins?: string[];
  5. outs?: string[];
  6. shared_samplers?: string[];
  7. uniforms?: string[];
  8. functions?: map_t<string, string>;
  9. main?: string;
  10. main_end?: string;
  11. main_normal?: string;
  12. main_attribs?: string;
  13. write_normal?: i32;
  14. // References
  15. bposition?: bool;
  16. wposition?: bool;
  17. mposition?: bool;
  18. vposition?: bool;
  19. wvpposition?: bool;
  20. ndcpos?: bool;
  21. wtangent?: bool;
  22. vvec?: bool;
  23. vvec_cam?: bool;
  24. n?: bool;
  25. nattr?: bool;
  26. dotnv?: bool;
  27. };
  28. function node_shader_create(context: node_shader_context_t, shader_type: string): node_shader_t {
  29. let raw: node_shader_t = {};
  30. raw.context = context;
  31. raw.shader_type = shader_type;
  32. raw.ins = [];
  33. raw.outs = [];
  34. raw.shared_samplers = [];
  35. raw.uniforms = [];
  36. raw.functions = map_create();
  37. raw.main = "";
  38. raw.main_end = "";
  39. raw.main_normal = "";
  40. raw.main_attribs = "";
  41. raw.write_normal = 0;
  42. return raw;
  43. }
  44. function node_shader_add_in(raw: node_shader_t, s: string) {
  45. array_push(raw.ins, s);
  46. }
  47. function node_shader_add_out(raw: node_shader_t, s: string) {
  48. array_push(raw.outs, s);
  49. }
  50. function node_shader_add_uniform(raw: node_shader_t, s: string, link: string = null) {
  51. let ar: string[] = string_split(s, " ");
  52. // layout(RGBA8) image3D voxels
  53. let utype: string = ar[ar.length - 2];
  54. let uname: string = ar[ar.length - 1];
  55. if (starts_with(utype, "sampler") || starts_with(utype, "image") || starts_with(utype, "uimage")) {
  56. let is_image: bool = (starts_with(utype, "image") || starts_with(utype, "uimage")) ? true : false;
  57. node_shader_context_add_texture_unit(raw.context, utype, uname, link, is_image);
  58. }
  59. else {
  60. // Prefer vec4[] for d3d to avoid padding
  61. if (ar[0] == "float" && string_index_of(ar[1], "[") >= 0) {
  62. ar[0] = "floats";
  63. ar[1] = string_split(ar[1], "[")[0];
  64. }
  65. else if (ar[0] == "vec4" && string_index_of(ar[1], "[") >= 0) {
  66. ar[0] = "floats";
  67. ar[1] = string_split(ar[1], "[")[0];
  68. }
  69. node_shader_context_add_constant(raw.context, ar[0], ar[1], link);
  70. }
  71. if (array_index_of(raw.uniforms, s) == -1) {
  72. array_push(raw.uniforms, s);
  73. }
  74. }
  75. function node_shader_add_shared_sampler(raw: node_shader_t, s: string) {
  76. if (array_index_of(raw.shared_samplers, s) == -1) {
  77. array_push(raw.shared_samplers, s);
  78. let ar: string[] = string_split(s, " ");
  79. // layout(RGBA8) sampler2D tex
  80. let utype: string = ar[ar.length - 2];
  81. let uname: string = ar[ar.length - 1];
  82. node_shader_context_add_texture_unit(raw.context, utype, uname, null, false);
  83. }
  84. }
  85. function node_shader_add_function(raw: node_shader_t, s: string) {
  86. let fname: string = string_split(s, "(")[0];
  87. if (map_get(raw.functions, fname) != null) {
  88. return;
  89. }
  90. map_set(raw.functions, fname, s);
  91. }
  92. function node_shader_write(raw: node_shader_t, s: string) {
  93. if (raw.write_normal > 0) {
  94. raw.main_normal += s + "\n";
  95. }
  96. else {
  97. raw.main += s + "\n";
  98. }
  99. }
  100. function node_shader_write_end(raw: node_shader_t, s: string) {
  101. raw.main_end += s + "\n";
  102. }
  103. function node_shader_write_attrib(raw: node_shader_t, s: string) {
  104. raw.main_attribs += s + "\n";
  105. }
  106. function node_shader_data_size(raw: node_shader_t, data: string): string {
  107. if (data == "float1") {
  108. return "1";
  109. }
  110. else if (data == "float2" || data == "short2norm") {
  111. return "2";
  112. }
  113. else if (data == "float3") {
  114. return "3";
  115. }
  116. else { // float 4 || short4norm
  117. return "4";
  118. }
  119. }
  120. function node_shader_vstruct_to_vsin(raw: node_shader_t) {
  121. let vs: vertex_element_t[] = raw.context.data.vertex_elements;
  122. for (let i: i32 = 0; i < vs.length; ++i) {
  123. let e: vertex_element_t = vs[i];
  124. node_shader_add_in(raw, "vec" + node_shader_data_size(raw, e.data) + " " + e.name);
  125. }
  126. }
  127. ///if (arm_direct3d11 || arm_direct3d12)
  128. function node_shader_get_hlsl(raw: node_shader_t, shared_sampler: string): string {
  129. let s: string = "#define HLSL\n";
  130. s += "#define textureArg(tex) Texture2D tex,SamplerState tex ## _sampler\n";
  131. s += "#define texturePass(tex) tex,tex ## _sampler\n";
  132. s += "#define sampler2D Texture2D\n";
  133. s += "#define sampler3D Texture3D\n";
  134. s += "#define texture(tex, coord) tex.Sample(tex ## _sampler, coord)\n";
  135. s += "#define textureShared(tex, coord) tex.Sample(" + shared_sampler + ", coord)\n";
  136. s += "#define textureLod(tex, coord, lod) tex.SampleLevel(tex ## _sampler, coord, lod)\n";
  137. s += "#define textureLodShared(tex, coord, lod) tex.SampleLevel(" + shared_sampler + ", coord, lod)\n";
  138. s += "#define texelFetch(tex, coord, lod) tex.Load(float3(coord.xy, lod))\n";
  139. s += "uint2 _GetDimensions(Texture2D tex, uint lod) { uint x, y; tex.GetDimensions(x, y); return uint2(x, y); }\n";
  140. s += "#define textureSize _GetDimensions\n";
  141. s += "#define mod(a, b) (a % b)\n";
  142. s += "#define vec2 float2\n";
  143. s += "#define vec3 float3\n";
  144. s += "#define vec4 float4\n";
  145. s += "#define ivec2 int2\n";
  146. s += "#define ivec3 int3\n";
  147. s += "#define ivec4 int4\n";
  148. s += "#define mat2 float2x2\n";
  149. s += "#define mat3 float3x3\n";
  150. s += "#define mat4 float4x4\n";
  151. s += "#define dFdx ddx\n";
  152. s += "#define dFdy ddy\n";
  153. s += "#define inversesqrt rsqrt\n";
  154. s += "#define fract frac\n";
  155. s += "#define mix lerp\n";
  156. let in_ext: string = "";
  157. let out_ext: string = "";
  158. // Input structure
  159. let index: i32 = 0;
  160. if (raw.ins.length > 0) {
  161. s += "struct SPIRV_Cross_Input {\n";
  162. index = 0;
  163. array_sort(raw.ins, function (pa: any_ptr, pb: any_ptr): i32 {
  164. let stra: string = DEREFERENCE(pa);
  165. let strb: string = DEREFERENCE(pb);
  166. // Sort inputs by name
  167. return strcmp(substring(stra, 4, stra.length), substring(strb, 4, strb.length));
  168. });
  169. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  170. let a: string = raw.ins[i];
  171. s += a + in_ext + " : TEXCOORD" + index + ";\n";
  172. index++;
  173. }
  174. // Built-ins
  175. if (raw.shader_type == "vert" && string_index_of(raw.main, "gl_VertexID") >= 0) {
  176. s += "uint gl_VertexID : SV_VertexID;\n";
  177. array_push(raw.ins, "uint gl_VertexID");
  178. }
  179. if (raw.shader_type == "vert" && string_index_of(raw.main, "gl_InstanceID") >= 0) {
  180. s += "uint gl_InstanceID : SV_InstanceID;\n";
  181. array_push(raw.ins, "uint gl_InstanceID");
  182. }
  183. s += "};\n";
  184. }
  185. // Output structure
  186. let num: i32 = 0;
  187. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  188. s += "struct SPIRV_Cross_Output {\n";
  189. array_sort(raw.outs, function (pa: any_ptr, pb: any_ptr): i32 {
  190. let stra: string = DEREFERENCE(pa);
  191. let strb: string = DEREFERENCE(pb);
  192. // Sort outputs by name
  193. return strcmp(substring(stra, 4, stra.length), substring(strb, 4, strb.length));
  194. });
  195. index = 0;
  196. if (raw.shader_type == "vert") {
  197. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  198. let a: string = raw.outs[i];
  199. s += a + out_ext + " : TEXCOORD" + index + ";\n";
  200. index++;
  201. }
  202. s += "float4 svpos : SV_POSITION;\n";
  203. }
  204. else {
  205. let out: string = raw.outs[0];
  206. // Multiple render targets
  207. if (char_at(out, out.length - 1) == "]") {
  208. num = parse_int(char_at(out, out.length - 2));
  209. s += "vec4 frag_color[" + num + "] : SV_TARGET0;\n";
  210. }
  211. else {
  212. s += "vec4 frag_color : SV_TARGET0;\n";
  213. }
  214. }
  215. s += "};\n";
  216. }
  217. for (let i: i32 = 0; i < raw.uniforms.length; ++i) {
  218. let a: string = raw.uniforms[i];
  219. s += "uniform " + a + ";\n";
  220. if (starts_with(a, "sampler")) {
  221. s += "SamplerState " + string_split(a, " ")[1] + "_sampler;\n";
  222. }
  223. }
  224. if (raw.shared_samplers.length > 0) {
  225. for (let i: i32 = 0; i < raw.shared_samplers.length; ++i) {
  226. let a: string = raw.shared_samplers[i];
  227. s += "uniform " + a + ";\n";
  228. }
  229. s += "SamplerState " + shared_sampler + ";\n";
  230. }
  231. let keys: string[] = map_keys(raw.functions);
  232. for (let i: i32 = 0; i < keys.length; ++i) {
  233. let f: string = map_get(raw.functions, keys[i]);
  234. s += f + "\n";
  235. }
  236. // Begin main
  237. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  238. if (raw.ins.length > 0) {
  239. s += "SPIRV_Cross_Output main(SPIRV_Cross_Input stage_input) {\n";
  240. }
  241. else {
  242. s += "SPIRV_Cross_Output main() {\n";
  243. }
  244. }
  245. else {
  246. if (raw.ins.length > 0) {
  247. s += "void main(SPIRV_Cross_Input stage_input) {\n";
  248. }
  249. else {
  250. s += "void main() {\n";
  251. }
  252. }
  253. // Declare inputs
  254. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  255. let a: string = raw.ins[i];
  256. let b: string = substring(a, 5, a.length); // Remove type "vec4 "
  257. s += a + " = stage_input." + b + ";\n";
  258. }
  259. if (raw.shader_type == "vert") {
  260. s += "vec4 gl_Position;\n";
  261. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  262. let a: string = raw.outs[i];
  263. s += a + ";\n";
  264. }
  265. }
  266. else {
  267. if (raw.outs.length > 0) {
  268. if (num > 0) {
  269. s += "vec4 frag_color[" + num + "];\n";
  270. }
  271. else {
  272. s += "vec4 frag_color;\n";
  273. }
  274. }
  275. }
  276. s += raw.main_attribs;
  277. s += raw.main_normal;
  278. s += raw.main;
  279. s += raw.main_end;
  280. // Write output structure
  281. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  282. s += "SPIRV_Cross_Output stage_output;\n";
  283. if (raw.shader_type == "vert") {
  284. s += "gl_Position.z = (gl_Position.z + gl_Position.w) * 0.5;\n";
  285. s += "stage_output.svpos = gl_Position;\n";
  286. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  287. let a: string = raw.outs[i];
  288. let b: string = substring(a, 5, a.length); // Remove type "vec4 "
  289. s += "stage_output." + b + " = " + b + ";\n";
  290. }
  291. }
  292. else {
  293. if (num > 0) {
  294. for (let i: i32 = 0; i < num; ++i) {
  295. s += "stage_output.frag_color[" + i + "] = frag_color[" + i + "];\n";
  296. }
  297. }
  298. else {
  299. s += "stage_output.frag_color = frag_color;\n";
  300. }
  301. }
  302. s += "return stage_output;\n";
  303. }
  304. s += "}\n";
  305. return s;
  306. }
  307. ///end
  308. ///if arm_metal
  309. function node_shader_get_msl(raw: node_shader_t, shared_sampler: string): string {
  310. let s: string = "#define METAL\n";
  311. s += "#include <metal_stdlib>\n";
  312. s += "#include <simd/simd.h>\n";
  313. s += "using namespace metal;\n";
  314. s += "#define textureArg(tex) texture2d<float> tex,sampler tex ## _sampler\n";
  315. s += "#define texturePass(tex) tex,tex ## _sampler\n";
  316. s += "#define sampler2D texture2d<float>\n";
  317. s += "#define sampler3D texture3d<float>\n";
  318. s += "#define texture(tex, coord) tex.sample(tex ## _sampler, coord)\n";
  319. s += "#define textureShared(tex, coord) tex.sample(" + shared_sampler + ", coord)\n";
  320. s += "#define textureLod(tex, coord, lod) tex.sample(tex ## _sampler, coord, level(lod))\n";
  321. s += "#define textureLodShared(tex, coord, lod) tex.sample(" + shared_sampler + ", coord, level(lod))\n";
  322. s += "#define texelFetch(tex, coord, lod) tex.read(uint2(coord), uint(lod))\n";
  323. s += "float2 _getDimensions(texture2d<float> tex, uint lod) { return float2(tex.get_width(lod), tex.get_height(lod)); }\n";
  324. s += "#define textureSize _getDimensions\n";
  325. s += "#define mod(a, b) fmod(a, b)\n";
  326. s += "#define vec2 float2\n";
  327. s += "#define vec3 float3\n";
  328. s += "#define vec4 float4\n";
  329. s += "#define ivec2 int2\n";
  330. s += "#define ivec3 int3\n";
  331. s += "#define ivec4 int4\n";
  332. s += "#define mat2 float2x2\n";
  333. s += "#define mat3 float3x3\n";
  334. s += "#define mat4 float4x4\n";
  335. s += "#define dFdx dfdx\n";
  336. s += "#define dFdy dfdy\n";
  337. s += "#define inversesqrt rsqrt\n";
  338. s += "#define mul(a, b) b * a\n";
  339. s += "#define discard discard_fragment()\n";
  340. // Input structure
  341. let index: i32 = 0;
  342. s += "struct main_in {\n";
  343. index = 0;
  344. array_sort(raw.ins, function (pa: any_ptr, pb: any_ptr): i32 {
  345. let stra: string = DEREFERENCE(pa);
  346. let strb: string = DEREFERENCE(pb);
  347. // Sort inputs by name
  348. return strcmp(substring(stra, 4, stra.length), substring(strb, 4, strb.length));
  349. });
  350. if (raw.shader_type == "vert") {
  351. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  352. let a: string = raw.ins[i];
  353. s += a + " [[attribute(" + index + ")]];\n";
  354. index++;
  355. }
  356. }
  357. else {
  358. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  359. let a: string = raw.ins[i];
  360. s += a + " [[user(locn" + index + ")]];\n";
  361. index++;
  362. }
  363. }
  364. s += "};\n";
  365. // Output structure
  366. let num: i32 = 0;
  367. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  368. s += "struct main_out {\n";
  369. array_sort(raw.outs, function (pa: any_ptr, pb: any_ptr): i32 {
  370. let stra: string = DEREFERENCE(pa);
  371. let strb: string = DEREFERENCE(pb);
  372. // Sort outputs by name
  373. return strcmp(substring(stra, 4, stra.length), substring(strb, 4, strb.length));
  374. });
  375. index = 0;
  376. if (raw.shader_type == "vert") {
  377. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  378. let a: string = raw.outs[i];
  379. s += a + " [[user(locn" + index + ")]];\n";
  380. index++;
  381. }
  382. s += "float4 svpos [[position]];\n";
  383. }
  384. else {
  385. let out: string = raw.outs[0];
  386. // Multiple render targets
  387. if (char_at(out, out.length - 1) == "]") {
  388. num = parse_int(char_at(out, out.length - 2));
  389. for (let i: i32 = 0; i < num; ++i) {
  390. s += "float4 frag_color_" + i + " [[color(" + i + ")]];\n";
  391. }
  392. }
  393. else {
  394. s += "float4 frag_color [[color(0)]];\n";
  395. }
  396. }
  397. s += "};\n";
  398. }
  399. let samplers: string[] = [];
  400. if (raw.uniforms.length > 0) {
  401. s += "struct main_uniforms {\n";
  402. for (let i: i32 = 0; i < raw.uniforms.length; ++i) {
  403. let a: string = raw.uniforms[i];
  404. if (starts_with(a, "sampler")) {
  405. array_push(samplers, a);
  406. }
  407. else {
  408. s += a + ";\n";
  409. }
  410. }
  411. s += "};\n";
  412. }
  413. let keys: string[] = map_keys(raw.functions);
  414. for (let i: i32 = 0; i < keys.length; ++i) {
  415. let f: string = map_get(raw.functions, keys[i]);
  416. s += f + "\n";
  417. }
  418. // Begin main declaration
  419. s += "#undef texture\n";
  420. if (raw.shader_type == "vert") {
  421. s += "vertex ";
  422. }
  423. else {
  424. s += "fragment ";
  425. }
  426. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  427. s += "main_out ";
  428. }
  429. else {
  430. s += "void ";
  431. }
  432. s += "my_main(";
  433. s += "main_in in [[stage_in]]";
  434. if (raw.uniforms.length > 0) {
  435. let bufi: i32 = raw.shader_type == "vert" ? 1 : 0;
  436. s += ", constant main_uniforms& uniforms [[buffer(" + bufi + ")]]";
  437. }
  438. if (samplers.length > 0) {
  439. for (let i: i32 = 0; i < samplers.length; ++i) {
  440. s += ", " + samplers[i] + " [[texture(" + i + ")]]";
  441. s += ", sampler " + string_split(samplers[i], " ")[1] + "_sampler [[sampler(" + i + ")]]";
  442. }
  443. }
  444. if (raw.shared_samplers.length > 0) {
  445. for (let i: i32 = 0; i < raw.shared_samplers.length; ++i) {
  446. let index: i32 = samplers.length + i;
  447. s += ", " + raw.shared_samplers[i] + " [[texture(" + index + ")]]";
  448. }
  449. let len: i32 = samplers.length;
  450. s += ", sampler " + shared_sampler + " [[sampler(" + len + ")]]";
  451. }
  452. // Built-ins
  453. if (raw.shader_type == "vert" && string_index_of(raw.main, "gl_VertexID") >= 0) {
  454. s += ", uint gl_VertexID [[vertex_id]]";
  455. }
  456. if (raw.shader_type == "vert" && string_index_of(raw.main, "gl_InstanceID") >= 0) {
  457. s += ", uint gl_InstanceID [[instance_id]]";
  458. }
  459. // End main declaration
  460. s += ") {\n";
  461. s += "#define texture(tex, coord) tex.sample(tex ## _sampler, coord)\n";
  462. // Declare inputs
  463. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  464. let a: string = raw.ins[i];
  465. let b: string = substring(a, 5, a.length); // Remove type "vec4 "
  466. s += a + " = in." + b + ";\n";
  467. }
  468. for (let i: i32 = 0; i < raw.uniforms.length; ++i) {
  469. let a: string = raw.uniforms[i];
  470. if (!starts_with(a, "sampler")) {
  471. let b: string = string_split(a, " ")[1]; // Remove type "vec4 "
  472. if (string_index_of(b, "[") >= 0) {
  473. b = substring(b, 0, string_index_of(b, "["));
  474. let type: string = string_split(a, " ")[0];
  475. s += "constant " + type + " *" + b + " = uniforms." + b + ";\n";
  476. }
  477. else {
  478. s += a + " = uniforms." + b + ";\n";
  479. }
  480. }
  481. }
  482. if (raw.shader_type == "vert") {
  483. s += "vec4 gl_Position;\n";
  484. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  485. let a: string = raw.outs[i];
  486. s += a + ";\n";
  487. }
  488. }
  489. else {
  490. if (raw.outs.length > 0) {
  491. if (num > 0) {
  492. s += "vec4 frag_color[" + num + "];\n";
  493. }
  494. else {
  495. s += "vec4 frag_color;\n";
  496. }
  497. }
  498. }
  499. s += raw.main_attribs;
  500. s += raw.main_normal;
  501. s += raw.main;
  502. s += raw.main_end;
  503. // Write output structure
  504. if (raw.outs.length > 0 || raw.shader_type == "vert") {
  505. s += "main_out out = {};\n";
  506. if (raw.shader_type == "vert") {
  507. s += "gl_Position.z = (gl_Position.z + gl_Position.w) * 0.5;\n";
  508. s += "out.svpos = gl_Position;\n";
  509. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  510. let a: string = raw.outs[i];
  511. let b: string = string_split(a, " ")[1]; // Remove type "vec4 "
  512. s += "out." + b + " = " + b + ";\n";
  513. }
  514. }
  515. else {
  516. if (num > 0) {
  517. for (let i: i32 = 0; i < num; ++i) {
  518. s += "out.frag_color_" + i + " = frag_color[" + i + "];\n";
  519. }
  520. }
  521. else {
  522. s += "out.frag_color = frag_color;\n";
  523. }
  524. }
  525. s += "return out;\n";
  526. }
  527. s += "}\n";
  528. return s;
  529. }
  530. ///end
  531. ///if (arm_opengl || arm_vulkan)
  532. function node_shader_get_glsl(raw: node_shader_t, shared_sampler: string, version_header: string): string {
  533. let s: string = version_header;
  534. s += "#define textureArg(tex) sampler2D tex\n";
  535. s += "#define texturePass(tex) tex\n";
  536. s += "#define mul(a, b) b * a\n";
  537. s += "#define textureShared texture\n";
  538. s += "#define textureLodShared textureLod\n";
  539. s += "#define atan2(x, y) atan(y, x)\n";
  540. let in_ext: string = "";
  541. let out_ext: string = "";
  542. for (let i: i32 = 0; i < raw.ins.length; ++i) {
  543. let a: string = raw.ins[i];
  544. s += "in " + a + in_ext + ";\n";
  545. }
  546. for (let i: i32 = 0; i < raw.outs.length; ++i) {
  547. let a: string = raw.outs[i];
  548. s += "out " + a + out_ext + ";\n";
  549. }
  550. for (let i: i32 = 0; i < raw.uniforms.length; ++i) {
  551. let a: string = raw.uniforms[i];
  552. s += "uniform " + a + ";\n";
  553. }
  554. for (let i: i32 = 0; i < raw.shared_samplers.length; ++i) {
  555. let a: string = raw.shared_samplers[i];
  556. s += "uniform " + a + ";\n";
  557. }
  558. let keys: string[] = map_keys(raw.functions);
  559. for (let i: i32 = 0; i < keys.length; ++i) {
  560. let f: string = map_get(raw.functions, keys[i]);
  561. s += f + "\n";
  562. }
  563. s += "void main() {\n";
  564. s += raw.main_attribs;
  565. s += raw.main_normal;
  566. s += raw.main;
  567. s += raw.main_end;
  568. s += "}\n";
  569. return s;
  570. }
  571. ///end
  572. function node_shader_get(raw: node_shader_t): string {
  573. if (raw.shader_type == "vert") {
  574. node_shader_vstruct_to_vsin(raw);
  575. }
  576. let shared_sampler: string = "shared_sampler";
  577. if (raw.shared_samplers.length > 0) {
  578. shared_sampler = string_split(raw.shared_samplers[0], " ")[1] + "_sampler";
  579. }
  580. ///if (arm_direct3d11 || arm_direct3d12)
  581. let s: string = node_shader_get_hlsl(raw, shared_sampler);
  582. ///elseif arm_metal
  583. let s: string = node_shader_get_msl(raw, shared_sampler);
  584. ///elseif arm_vulkan
  585. let version_header: string = "#version 450\n";
  586. let s: string = node_shader_get_glsl(raw, shared_sampler, version_header);
  587. ///elseif arm_android
  588. let version_header: string = "#version 300 es\n";
  589. if (raw.shader_type == "frag") {
  590. version_header += "precision highp float;\n";
  591. version_header += "precision mediump int;\n";
  592. }
  593. let s: string = node_shader_get_glsl(raw, shared_sampler, version_header);
  594. ///elseif arm_opengl
  595. let version_header: string = "#version 330\n";
  596. let s: string = node_shader_get_glsl(raw, shared_sampler, version_header);
  597. ///end
  598. return s;
  599. }