main.lua 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180
  1. -- This demo renders four examples of mesh drawing:
  2. -- A plain mesh (one triangle, white)
  3. -- A mesh with a vertex map (a cube, magenta)
  4. -- An instanced mesh with its size controlled by gl_InstanceID and an equation (512 cubes animated, cyan)
  5. -- An instanced mesh with its size controlled by an attached attribute (512 cubes with random sizes, yellow)
  6. local fragmentShader = require("shader")
  7. local mesh1, mesh2, mesh4
  8. local mesh4Instance
  9. local mesh1Program, mesh3Program, mesh4Program
  10. local gridSize = 8
  11. local gridSizeCubed = gridSize*gridSize*gridSize
  12. -- Call this function with a string containing a glsl function preTransform()
  13. -- Which maps world space coordinates to world space coordinates.
  14. local function makeShader(prefix)
  15. return lovr.graphics.newShader(prefix .. [[
  16. out vec3 lightDirection;
  17. out vec3 normalDirection;
  18. vec3 lightPosition = vec3(10, 10, 3);
  19. vec4 position(mat4 projection, mat4 transform, vec4 _vertex) {
  20. vec4 vertex = preTransform(_vertex);
  21. vec4 vVertex = transform * vertex;
  22. vec4 vLight = lovrView * vec4(lightPosition, 1.);
  23. lightDirection = normalize(vec3(vLight - vVertex));
  24. normalDirection = normalize(lovrNormalMatrix * lovrNormal);
  25. return projection * transform * vertex;
  26. }
  27. ]], fragmentShader)
  28. end
  29. -- This "standard" program is the same as the standard light shader from the other examples-- it does nothing.
  30. local mesh1Program = makeShader("vec4 preTransform(vec4 v) { return v; }")
  31. local animate = 0
  32. function lovr.load()
  33. lovr.graphics.setCullingEnabled(true)
  34. -- mesh1Program()
  35. mesh1 = lovr.graphics.newMesh({{ 'lovrPosition', 'float', 3 }, { 'lovrNormal', 'float', 3 }}, 3, 'triangles')
  36. mesh1:setVertices({{0,0,0, 0,0,1}, {1,0,0, 0,0,1}, {0,1,0, 0,0,1}}) -- A triangle
  37. mesh2 = lovr.graphics.newMesh({{ 'lovrPosition', 'float', 3 }, { 'lovrNormal', 'float', 3 }}, 24, 'triangles')
  38. local mesh2Vertices = { -- Coordinates for mesh 2 (a cube)
  39. {0,0,0, 0,0,-1}, -- Face front
  40. {0,1,0, 0,0,-1},
  41. {1,1,0, 0,0,-1},
  42. {1,0,0, 0,0,-1},
  43. {1,1,0, 0,1,0}, -- Face top
  44. {0,1,0, 0,1,0},
  45. {0,1,1, 0,1,0},
  46. {1,1,1, 0,1,0},
  47. {1,0,0, 1,0,0}, -- Face right
  48. {1,1,0, 1,0,0},
  49. {1,1,1, 1,0,0},
  50. {1,0,1, 1,0,0},
  51. {0,0,0, -1,0,0}, -- Face left
  52. {0,0,1, -1,0,0},
  53. {0,1,1, -1,0,0},
  54. {0,1,0, -1,0,0},
  55. {1,1,1, 0,0,1}, -- Face back
  56. {0,1,1, 0,0,1},
  57. {0,0,1, 0,0,1},
  58. {1,0,1, 0,0,1},
  59. {0,0,0, 0,-1,0}, -- Face bottom
  60. {1,0,0, 0,-1,0},
  61. {1,0,1, 0,-1,0},
  62. {0,0,1, 0,-1,0}
  63. }
  64. -- This cube covers the space 0..1, so it's centered at (0.5, 0.5, 0.5).
  65. -- Edit the first three coordinates of each vertex to center it at (0,0,0):
  66. for _, v in ipairs(mesh2Vertices) do
  67. for i=1,3 do
  68. v[i] = v[i] - 0.5
  69. end
  70. end
  71. mesh2:setVertices(mesh2Vertices)
  72. local mesh2Indexes = { -- Indexes for mesh 2
  73. 1, 2, 3, 1, 3, 4, -- Face front
  74. 5, 6, 7, 5, 7, 8, -- Face top
  75. 9, 10, 11, 9, 11, 12, -- Face right
  76. 13, 14, 15, 13, 15, 16, -- Face left
  77. 17, 18, 19, 17, 19, 20, -- Face back
  78. 21, 22, 23, 21, 23, 24, -- Face bottom
  79. }
  80. mesh2:setVertexMap(mesh2Indexes)
  81. mesh3Program = makeShader([[
  82. uniform int gridSize;
  83. uniform float animate;
  84. vec4 preTransform(vec4 v) {
  85. int x = gl_InstanceID % gridSize;
  86. int y = (gl_InstanceID / gridSize) % gridSize;
  87. int z = (gl_InstanceID / gridSize) / gridSize;
  88. float cubeSize = (sin(x + y + z + animate) + 1) / 2;
  89. return v * vec4(cubeSize,cubeSize,cubeSize,1) + vec4(x,y,z,0) - vec4(gridSize, gridSize, gridSize, 0)/2;
  90. }
  91. ]])
  92. mesh3Program:send("gridSize", gridSize)
  93. mesh4Program = makeShader([[
  94. uniform int gridSize;
  95. in float cubeSize;
  96. vec4 preTransform(vec4 v) {
  97. int x = gl_InstanceID % gridSize;
  98. int y = (gl_InstanceID / gridSize) % gridSize;
  99. int z = (gl_InstanceID / gridSize) / gridSize;
  100. return v * vec4(cubeSize,cubeSize,cubeSize,1) + vec4(x,y,z,0) - vec4(gridSize, gridSize, gridSize, 0)/2;
  101. }
  102. ]])
  103. mesh4Program:send("gridSize", gridSize)
  104. mesh4 = lovr.graphics.newMesh({}, 24, 'triangles')
  105. mesh4Instance = lovr.graphics.newMesh({{'cubeSize', 'float', 1}}, gridSizeCubed, 'points')
  106. local mesh4Vertices = {}
  107. for i=1,gridSizeCubed do
  108. table.insert(mesh4Vertices, {math.random()})
  109. end
  110. mesh4Instance:setVertices(mesh4Vertices)
  111. mesh4:setVertexMap(mesh2Indexes)
  112. mesh4:attachAttributes(mesh2)
  113. mesh4:attachAttributes(mesh4Instance, 1)
  114. end
  115. function lovr.update(dt)
  116. animate = animate + dt/math.pi*2
  117. end
  118. function lovr.draw(eye)
  119. lovr.graphics.setShader(mesh1Program)
  120. lovr.graphics.push()
  121. lovr.graphics.setColor(1,1,1)
  122. lovr.graphics.translate(0, 0, -2)
  123. mesh1:draw(0,0,0)
  124. lovr.graphics.pop()
  125. lovr.graphics.push()
  126. lovr.graphics.setColor(1,0,1)
  127. lovr.graphics.rotate(1 * math.pi/2, 0, 1, 0)
  128. lovr.graphics.translate(0, 0, -2)
  129. mesh2:draw(0,0,0)
  130. lovr.graphics.pop()
  131. lovr.graphics.setShader(mesh3Program)
  132. lovr.graphics.setColor(0,1,1)
  133. lovr.graphics.push()
  134. lovr.graphics.rotate(2 * math.pi/2, 0, 1, 0)
  135. lovr.graphics.translate(0, 0, -2)
  136. lovr.graphics.scale(1/gridSize)
  137. mesh3Program:send("animate", animate)
  138. mesh2:drawInstanced(gridSizeCubed, 0,0,0)
  139. lovr.graphics.pop()
  140. lovr.graphics.setShader(mesh4Program)
  141. lovr.graphics.setColor(1,1,0)
  142. lovr.graphics.push()
  143. lovr.graphics.rotate(3 * math.pi/2, 0, 1, 0)
  144. lovr.graphics.translate(0, 0, -2)
  145. lovr.graphics.scale(1/gridSize)
  146. mesh4:drawInstanced(gridSizeCubed, 0,0,0)
  147. lovr.graphics.pop()
  148. end