pipeline.cpp 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. /*
  2. * Copyright (c) 2012-2021 Daniele Bartolini et al.
  3. * License: https://github.com/dbartolini/crown/blob/master/LICENSE
  4. */
  5. #include "core/types.h"
  6. #include "device/pipeline.h"
  7. #include "world/shader_manager.h"
  8. #include <bx/math.h>
  9. namespace crown
  10. {
  11. /*
  12. * Copyright 2011-2017 Branimir Karadzic. All rights reserved.
  13. * License: https://github.com/bkaradzic/bgfx#license-bsd-2-clause
  14. */
  15. struct PosTexCoord0Vertex
  16. {
  17. float m_x;
  18. float m_y;
  19. float m_z;
  20. float m_u;
  21. float m_v;
  22. static void init()
  23. {
  24. ms_layout
  25. .begin()
  26. .add(bgfx::Attrib::Position, 3, bgfx::AttribType::Float)
  27. .add(bgfx::Attrib::TexCoord0, 2, bgfx::AttribType::Float)
  28. .end();
  29. }
  30. static bgfx::VertexLayout ms_layout;
  31. };
  32. bgfx::VertexLayout PosTexCoord0Vertex::ms_layout;
  33. /*
  34. * Copyright 2011-2017 Branimir Karadzic. All rights reserved.
  35. * License: https://github.com/bkaradzic/bgfx#license-bsd-2-clause
  36. */
  37. void screenSpaceQuad(float _textureWidth, float _textureHeight, float _texelHalf, bool _originBottomLeft, float _width = 1.0f, float _height = 1.0f)
  38. {
  39. if (3 == bgfx::getAvailTransientVertexBuffer(3, PosTexCoord0Vertex::ms_layout) )
  40. {
  41. bgfx::TransientVertexBuffer tvb;
  42. bgfx::allocTransientVertexBuffer(&tvb, 3, PosTexCoord0Vertex::ms_layout);
  43. PosTexCoord0Vertex* vertex = (PosTexCoord0Vertex*)tvb.data;
  44. const float minx = -_width;
  45. const float maxx = _width;
  46. const float miny = _height;
  47. const float maxy = -_height;
  48. const float texelHalfW = _texelHalf/_textureWidth;
  49. const float texelHalfH = _texelHalf/_textureHeight;
  50. const float minu = -1.0f + texelHalfW;
  51. const float maxu = 1.0f + texelHalfH;
  52. const float zz = 0.0f;
  53. float minv = texelHalfH;
  54. float maxv = 2.0f + texelHalfH;
  55. if (_originBottomLeft)
  56. {
  57. float temp = minv;
  58. minv = maxv;
  59. maxv = temp;
  60. minv -= 1.0f;
  61. maxv -= 1.0f;
  62. }
  63. vertex[0].m_x = maxx;
  64. vertex[0].m_y = maxy;
  65. vertex[0].m_z = zz;
  66. vertex[0].m_u = maxu;
  67. vertex[0].m_v = maxv;
  68. vertex[1].m_x = maxx;
  69. vertex[1].m_y = miny;
  70. vertex[1].m_z = zz;
  71. vertex[1].m_u = maxu;
  72. vertex[1].m_v = minv;
  73. vertex[2].m_x = minx;
  74. vertex[2].m_y = miny;
  75. vertex[2].m_z = zz;
  76. vertex[2].m_u = minu;
  77. vertex[2].m_v = minv;
  78. bgfx::setVertexBuffer(0, &tvb);
  79. }
  80. }
  81. Pipeline::Pipeline()
  82. : _frame_buffer(BGFX_INVALID_HANDLE)
  83. {
  84. for (u32 i = 0; i < countof(_buffers); ++i)
  85. _buffers[i] = BGFX_INVALID_HANDLE;
  86. }
  87. void Pipeline::create(uint16_t width, uint16_t height)
  88. {
  89. PosTexCoord0Vertex::init();
  90. _tex_color = bgfx::createUniform("s_texColor", bgfx::UniformType::Sampler);
  91. reset(width, height);
  92. }
  93. void Pipeline::destroy()
  94. {
  95. bgfx::destroy(_frame_buffer);
  96. bgfx::destroy(_buffers[1]);
  97. bgfx::destroy(_buffers[0]);
  98. bgfx::destroy(_tex_color);
  99. }
  100. void Pipeline::reset(u16 width, u16 height)
  101. {
  102. for (u32 i = 0; i < countof(_buffers); ++i)
  103. {
  104. if (bgfx::isValid(_buffers[i]))
  105. bgfx::destroy(_buffers[i]);
  106. }
  107. _buffers[0] = bgfx::createTexture2D(width
  108. , height
  109. , false
  110. , 1
  111. , bgfx::TextureFormat::BGRA8
  112. , BGFX_TEXTURE_RT
  113. );
  114. _buffers[1] = bgfx::createTexture2D(width
  115. , height
  116. , false
  117. , 1
  118. , bgfx::TextureFormat::D24S8
  119. , BGFX_TEXTURE_RT
  120. );
  121. if (bgfx::isValid(_frame_buffer))
  122. bgfx::destroy(_frame_buffer);
  123. _frame_buffer = bgfx::createFrameBuffer(countof(_buffers), _buffers);
  124. }
  125. void Pipeline::render(ShaderManager& sm, StringId32 program, uint8_t view, uint16_t width, uint16_t height)
  126. {
  127. const bgfx::Caps* caps = bgfx::getCaps();
  128. f32 ortho[16];
  129. bx::mtxOrtho(ortho, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, 100.0f, 0.0f, caps->homogeneousDepth);
  130. bgfx::setViewRect(view, 0, 0, width, height);
  131. bgfx::setViewTransform(view, NULL, ortho);
  132. const u32 samplerFlags = 0
  133. | BGFX_SAMPLER_MIN_POINT
  134. | BGFX_SAMPLER_MAG_POINT
  135. | BGFX_SAMPLER_MIP_POINT
  136. | BGFX_SAMPLER_U_CLAMP
  137. | BGFX_SAMPLER_V_CLAMP
  138. ;
  139. bgfx::setTexture(0, _tex_color, _buffers[0], samplerFlags);
  140. screenSpaceQuad(width, height, 0.0f, caps->originBottomLeft);
  141. sm.submit(program, view, 0, UINT64_MAX);
  142. }
  143. } // namespace crown