SpriteBatchBase.h 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. // Copyright (c) 2008-2023 the Urho3D project
  2. // License: MIT
  3. // Класс SpriteBatch разбит на части для более легкого восприятия кода
  4. #pragma once
  5. #include "../Core/Object.h"
  6. #include "../Graphics/Graphics.h"
  7. #include "../GraphicsAPI/IndexBuffer.h"
  8. #include "../GraphicsAPI/ShaderVariation.h"
  9. #include "../GraphicsAPI/Texture2D.h"
  10. #include "../GraphicsAPI/VertexBuffer.h"
  11. namespace Urho3D
  12. {
  13. /// @nobindtemp
  14. class URHO3D_API SpriteBatchBase : public Object
  15. {
  16. URHO3D_OBJECT(SpriteBatchBase, Object);
  17. // ============================ Пакетный рендеринг треугольников ============================
  18. private:
  19. // Максимальное число треугольников в порции
  20. inline static constexpr i32 MAX_TRIANGLES_IN_PORTION = 600;
  21. // Число вершин в треугольнике
  22. inline static constexpr i32 VERTICES_PER_TRIANGLE = 3;
  23. // Атрибуты вершин треугольников
  24. struct TVertex
  25. {
  26. Vector3 position_;
  27. u32 color_; // Цвет в формате 0xAABBGGRR
  28. };
  29. // Текущая порция треугольников
  30. TVertex tVertices_[MAX_TRIANGLES_IN_PORTION * VERTICES_PER_TRIANGLE];
  31. // Число вершин в массиве tVertices_
  32. i32 tNumVertices_ = 0;
  33. // Шейдеры для рендеринга треугольников. Инициализируются в конструкторе
  34. ShaderVariation* tVertexShader_;
  35. ShaderVariation* tPixelShader_;
  36. // Вершинный буфер для треугольников (индексный буфер не используется)
  37. SharedPtr<VertexBuffer> tVertexBuffer_;
  38. protected:
  39. // Данные для функции AddTriangle().
  40. // Заполняем заранее выделенную память, вместо передачи кучи аргументов в функцию
  41. struct
  42. {
  43. TVertex v0_, v1_, v2_;
  44. } triangle_;
  45. // Добавляет 3 вершины в массив tVertices_. Вызывает Flush(), если массив полон.
  46. // Перед вызовом этой функции необходимо заполнить структуру triangle_
  47. void AddTriangle();
  48. public:
  49. /// Указывает цвет для следующих треугольников (в формате 0xAABBGGRR)
  50. void SetShapeColor(u32 color);
  51. /// Указывает цвет для следующих треугольников
  52. void SetShapeColor(const Color& color);
  53. // ============================ Пакетный рендеринг четырехугольников ============================
  54. private:
  55. // Максимальное число четырёхугольников в порции
  56. inline static constexpr i32 MAX_QUADS_IN_PORTION = 500;
  57. // Четырёхугольник состоит из двух треугольников, а значит у него 6 вершин.
  58. // То есть каждый четырёхугольник занимает 6 элементов в индексном буфере
  59. inline static constexpr i32 INDICES_PER_QUAD = 6;
  60. // Две вершины четырёхугольника идентичны для обоих треугольников, поэтому
  61. // в вершинном буфере каждый четырёхугольник занимает 4 элемента
  62. inline static constexpr i32 VERTICES_PER_QUAD = 4;
  63. // Атрибуты вершин четырёхугольников
  64. struct QVertex
  65. {
  66. Vector3 position_;
  67. u32 color_; // Цвет в формате 0xAABBGGRR
  68. Vector2 uv_;
  69. };
  70. // Текущая порция четырёхугольников
  71. QVertex qVertices_[MAX_QUADS_IN_PORTION * VERTICES_PER_QUAD];
  72. // Число вершин в массиве qVertices_
  73. i32 qNumVertices_ = 0;
  74. // Текущая текстура
  75. Texture2D* qCurrentTexture_ = nullptr;
  76. // Текущие шейдеры
  77. ShaderVariation* qCurrentVS_ = nullptr;
  78. ShaderVariation* qCurrentPS_ = nullptr;
  79. // Буферы
  80. SharedPtr<IndexBuffer> qIndexBuffer_;
  81. SharedPtr<VertexBuffer> qVertexBuffer_;
  82. protected:
  83. // Данные для функции AddQuad().
  84. // Заполняем заранее выделенную память, вместо передачи кучи аргументов в функцию
  85. struct
  86. {
  87. Texture2D* texture_;
  88. ShaderVariation* vs_;
  89. ShaderVariation* ps_;
  90. QVertex v0_, v1_, v2_, v3_;
  91. } quad_;
  92. // Добавляет 4 вершины в массив quads_.
  93. // Если массив полон или требуемые шейдеры или текстура отличаются от текущих, то автоматически
  94. // происходит вызов функции Flush() (то есть начинается новая порция).
  95. // Перед вызовом этой функции необходимо заполнить структуру quad_
  96. void AddQuad();
  97. // ============================ Общее ============================
  98. private:
  99. void UpdateViewProjMatrix();
  100. IntRect GetViewportRect();
  101. protected:
  102. // Кешируем доступ к подсистеме. Инициализируется в конструкторе
  103. Graphics* graphics_ = nullptr;
  104. public:
  105. // Режим наложения
  106. BlendMode blendMode_ = BLEND_ALPHA;
  107. // Если использовать CMP_LESSEQUAL, то будет учитываться содержимое буфера глубины
  108. // (но сам SpriteBatch ничего не пишет в буфер глубины).
  109. // При CMP_ALWAYS каждый выводимый спрайт будет перекрывать прежде отрисованные пиксели
  110. CompareMode compareMode_ = CMP_ALWAYS;
  111. // Если определена камера, то SpriteBatch рисует в мировых координатах
  112. Camera* camera_ = nullptr;
  113. // Размеры виртуального экрана. Если одна из координат <= 0, то используются реальные размеры экрана
  114. IntVector2 virtualScreenSize_ = IntVector2(0, 0);
  115. bool VirtualScreenUsed() const { return virtualScreenSize_.x_ > 0 && virtualScreenSize_.y_ > 0; }
  116. // Конструктор
  117. SpriteBatchBase(Context* context);
  118. // Рендерит накопленную геометрию (то есть текущую порцию)
  119. void Flush();
  120. // Переводит реальные координаты в виртуальные. Используется для курсора мыши
  121. Vector2 GetVirtualPos(const Vector2& realPos);
  122. };
  123. } // namespace Urho3D