triangle3dTex.c 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123
  1. #include "vc.c"
  2. #include "./assets/tsodinPog.c"
  3. #define WIDTH 960
  4. #define HEIGHT 720
  5. static uint32_t pixels1[WIDTH*HEIGHT];
  6. static float zbuffer1[WIDTH*HEIGHT];
  7. static uint32_t pixels2[WIDTH*HEIGHT];
  8. static float zbuffer2[WIDTH*HEIGHT];
  9. typedef struct {
  10. float x, y;
  11. } Vector2;
  12. static Vector2 make_vector2(float x, float y)
  13. {
  14. Vector2 v2;
  15. v2.x = x;
  16. v2.y = y;
  17. return v2;
  18. }
  19. typedef struct {
  20. float x, y, z;
  21. } Vector3;
  22. static Vector3 make_vector3(float x, float y, float z)
  23. {
  24. Vector3 v3;
  25. v3.x = x;
  26. v3.y = y;
  27. v3.z = z;
  28. return v3;
  29. }
  30. static Vector2 project_3d_2d(Vector3 v3)
  31. {
  32. return make_vector2(v3.x / v3.z, v3.y / v3.z);
  33. }
  34. static Vector2 project_2d_scr(Vector2 v2)
  35. {
  36. return make_vector2((v2.x + 1)/2*WIDTH, (1 - (v2.y + 1)/2)*HEIGHT);
  37. }
  38. static float global_time = 1.0;
  39. #define PI 3.14159265359
  40. float sinf(float);
  41. float cosf(float);
  42. Olivec_Canvas vc_render(float dt)
  43. {
  44. global_time += dt;
  45. Olivec_Canvas oc1 = olivec_canvas(pixels1, WIDTH, HEIGHT, WIDTH);
  46. olivec_fill(oc1, 0xFF181818);
  47. Olivec_Canvas zb1 = olivec_canvas((uint32_t*)zbuffer1, WIDTH, HEIGHT, WIDTH);
  48. olivec_fill(zb1, 0);
  49. Olivec_Canvas tsodinPog = olivec_canvas(tsodinPog_pixels, tsodinPog_width, tsodinPog_height, tsodinPog_width);
  50. float z = 1.5;
  51. float t = 0.75;
  52. {
  53. Vector3 v1 = make_vector3(cosf(global_time)*t, -t, z + sinf(global_time)*t);
  54. Vector3 v2 = make_vector3(cosf(global_time + PI)*t, -t, z + sinf(global_time + PI)*t);
  55. Vector3 v3 = make_vector3(0, t, z);
  56. Vector2 p1 = project_2d_scr(project_3d_2d(v1));
  57. Vector2 p2 = project_2d_scr(project_3d_2d(v2));
  58. Vector2 p3 = project_2d_scr(project_3d_2d(v3));
  59. olivec_triangle3uv(
  60. oc1,
  61. p1.x, p1.y, p2.x, p2.y, p3.x, p3.y,
  62. 0/v1.z, 1/v1.z, 0.5/v2.z, 0/v2.z, 1/v3.z, 0/v3.z,
  63. 1/v1.z, 1/v2.z, 1/v3.z,
  64. tsodinPog
  65. );
  66. olivec_triangle3z(zb1, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, 1.0f/v1.z, 1.0f/v2.z, 1.0f/v3.z);
  67. }
  68. Olivec_Canvas oc2 = olivec_canvas(pixels2, WIDTH, HEIGHT, WIDTH);
  69. olivec_fill(oc2, 0xFF181818);
  70. Olivec_Canvas zb2 = olivec_canvas((uint32_t*)zbuffer2, WIDTH, HEIGHT, WIDTH);
  71. olivec_fill(zb2, 0);
  72. {
  73. Vector3 v1 = make_vector3(cosf(global_time + PI/2)*t, -t, z + sinf(global_time + PI/2)*t);
  74. Vector3 v2 = make_vector3(cosf(global_time + PI + PI/2)*t, -t, z + sinf(global_time + PI + PI/2)*t);
  75. Vector3 v3 = make_vector3(0, t, z);
  76. Vector2 p1 = project_2d_scr(project_3d_2d(v1));
  77. Vector2 p2 = project_2d_scr(project_3d_2d(v2));
  78. Vector2 p3 = project_2d_scr(project_3d_2d(v3));
  79. olivec_triangle3z(zb2, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, 1.0f/v1.z, 1.0f/v2.z, 1.0f/v3.z);
  80. olivec_triangle3c(oc2, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, 0xFF1818FF, 0xFF18FF18, 0xFFFF1818);
  81. }
  82. for (size_t y = 0; y < HEIGHT; ++y) {
  83. for (size_t x = 0; x < WIDTH; ++x) {
  84. float z1 = *(float*)&OLIVEC_PIXEL(zb1, x, y);
  85. float z2 = *(float*)&OLIVEC_PIXEL(zb2, x, y);
  86. if (z1 < z2) {
  87. OLIVEC_PIXEL(oc1, x, y) = OLIVEC_PIXEL(oc2, x, y);
  88. z1 = z2;
  89. }
  90. z1 = 1.0f/z1;
  91. if (z1 >= 1.0) {
  92. z1 -= 1.0;
  93. uint32_t v = z1*255;
  94. if (v > 255) v = 255;
  95. olivec_blend_color(&OLIVEC_PIXEL(oc1, x, y), (v<<(3*8)));
  96. }
  97. }
  98. }
  99. return oc1;
  100. }