debugdraw: Added texture quad rendering.
This commit is contained in:
Родитель
93b2dee899
Коммит
25a6a6c4a2
|
@ -12,6 +12,19 @@
|
|||
|
||||
#include <bx/uint32_t.h>
|
||||
|
||||
void imageCheckerboard(void* _dst, uint32_t _width, uint32_t _height, uint32_t _step, uint32_t _0, uint32_t _1)
|
||||
{
|
||||
uint32_t* dst = (uint32_t*)_dst;
|
||||
for (uint32_t yy = 0; yy < _height; ++yy)
|
||||
{
|
||||
for (uint32_t xx = 0; xx < _width; ++xx)
|
||||
{
|
||||
uint32_t abgr = ( (xx/_step)&1) ^ ( (yy/_step)&1) ? _1 : _0;
|
||||
*dst++ = abgr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class DebugDrawApp : public entry::AppI
|
||||
{
|
||||
void init(int _argc, char** _argv) BX_OVERRIDE
|
||||
|
@ -46,10 +59,17 @@ class DebugDrawApp : public entry::AppI
|
|||
cameraSetVerticalAngle(0.0f);
|
||||
|
||||
ddInit();
|
||||
|
||||
uint8_t data[32*32*4];
|
||||
imageCheckerboard(data, 32, 32, 4, 0xff808080, 0xffc0c0c0);
|
||||
|
||||
m_sprite = ddCreateSprite(32, 32, data);
|
||||
}
|
||||
|
||||
virtual int shutdown() BX_OVERRIDE
|
||||
{
|
||||
ddDestroy(m_sprite);
|
||||
|
||||
ddShutdown();
|
||||
|
||||
cameraDestroy();
|
||||
|
@ -180,8 +200,8 @@ class DebugDrawApp : public entry::AppI
|
|||
ddDrawCircle(normal, center, 1.0f, 0.5f + bx::fsin(time*10.0f) );
|
||||
ddPop();
|
||||
|
||||
ddSetSpin(time);
|
||||
ddDrawQuad(normal, center, 2.0f);
|
||||
//ddSetSpin(time);
|
||||
ddDrawQuad(m_sprite, normal, center, 2.0f);
|
||||
}
|
||||
ddPop();
|
||||
|
||||
|
@ -256,6 +276,7 @@ class DebugDrawApp : public entry::AppI
|
|||
}
|
||||
|
||||
entry::MouseState m_mouseState;
|
||||
SpriteHandle m_sprite;
|
||||
|
||||
int64_t m_timeOffset;
|
||||
|
||||
|
|
|
@ -6,11 +6,13 @@
|
|||
#include <bgfx/bgfx.h>
|
||||
#include <bgfx/embedded_shader.h>
|
||||
#include "debugdraw.h"
|
||||
#include "../packrect.h"
|
||||
|
||||
#include <bx/fpumath.h>
|
||||
#include <bx/radixsort.h>
|
||||
#include <bx/uint32_t.h>
|
||||
#include <bx/crtimpl.h>
|
||||
#include <bx/handlealloc.h>
|
||||
|
||||
struct DebugVertex
|
||||
{
|
||||
|
@ -320,6 +322,50 @@ static const bgfx::EmbeddedShader s_embeddedShaders[] =
|
|||
BGFX_EMBEDDED_SHADER_END()
|
||||
};
|
||||
|
||||
#define SPRITE_TEXTURE_SIZE 1024
|
||||
|
||||
template<uint16_t MaxHandlesT = 256, uint16_t TextureSizeT = 1024>
|
||||
struct SpriteT
|
||||
{
|
||||
SpriteT()
|
||||
: m_ra(TextureSizeT, TextureSizeT)
|
||||
{
|
||||
}
|
||||
|
||||
SpriteHandle create(uint16_t _width, uint16_t _height)
|
||||
{
|
||||
SpriteHandle handle = { bx::HandleAlloc::invalid };
|
||||
|
||||
if (m_handleAlloc.getNumHandles() < m_handleAlloc.getMaxHandles() )
|
||||
{
|
||||
Pack2D pack;
|
||||
if (m_ra.find(_width, _height, pack) )
|
||||
{
|
||||
handle.idx = m_handleAlloc.alloc();
|
||||
m_pack[handle.idx] = pack;
|
||||
}
|
||||
}
|
||||
|
||||
return handle;
|
||||
}
|
||||
|
||||
void destroy(SpriteHandle _sprite)
|
||||
{
|
||||
const Pack2D& pack = m_pack[_sprite.idx];
|
||||
m_ra.clear(pack);
|
||||
m_handleAlloc.free(_sprite.idx);
|
||||
}
|
||||
|
||||
const Pack2D& get(SpriteHandle _sprite) const
|
||||
{
|
||||
return m_pack[_sprite.idx];
|
||||
}
|
||||
|
||||
bx::HandleAllocT<MaxHandlesT> m_handleAlloc;
|
||||
Pack2D m_pack[MaxHandlesT];
|
||||
RectPack2DT<256> m_ra;
|
||||
};
|
||||
|
||||
struct DebugDraw
|
||||
{
|
||||
DebugDraw()
|
||||
|
@ -384,7 +430,7 @@ struct DebugDraw
|
|||
|
||||
u_params = bgfx::createUniform("u_params", bgfx::UniformType::Vec4, 4);
|
||||
s_texColor = bgfx::createUniform("s_texColor", bgfx::UniformType::Int1);
|
||||
m_texture = bgfx::createTexture2D(2048, 2048, false, 1, bgfx::TextureFormat::BGRA8);
|
||||
m_texture = bgfx::createTexture2D(SPRITE_TEXTURE_SIZE, SPRITE_TEXTURE_SIZE, false, 1, bgfx::TextureFormat::BGRA8);
|
||||
|
||||
void* vertices[Mesh::Count] = {};
|
||||
uint16_t* indices[Mesh::Count] = {};
|
||||
|
@ -691,6 +737,7 @@ struct DebugDraw
|
|||
m_pos = 0;
|
||||
m_indexPos = 0;
|
||||
m_vertexPos = 0;
|
||||
m_posQuad = 0;
|
||||
}
|
||||
|
||||
void shutdown()
|
||||
|
@ -706,6 +753,33 @@ struct DebugDraw
|
|||
bgfx::destroyTexture(m_texture);
|
||||
}
|
||||
|
||||
SpriteHandle createSprite(uint16_t _width, uint16_t _height, const void* _data)
|
||||
{
|
||||
SpriteHandle handle = m_sprite.create(_width, _height);
|
||||
|
||||
if (isValid(handle) )
|
||||
{
|
||||
const Pack2D& pack = m_sprite.get(handle);
|
||||
bgfx::updateTexture2D(
|
||||
m_texture
|
||||
, 0
|
||||
, 0
|
||||
, pack.m_x
|
||||
, pack.m_y
|
||||
, pack.m_width
|
||||
, pack.m_height
|
||||
, bgfx::copy(_data, pack.m_width*pack.m_height*4)
|
||||
);
|
||||
}
|
||||
|
||||
return handle;
|
||||
}
|
||||
|
||||
void destroy(SpriteHandle _handle)
|
||||
{
|
||||
m_sprite.destroy(_handle);
|
||||
}
|
||||
|
||||
void begin(uint8_t _viewId)
|
||||
{
|
||||
BX_CHECK(State::Count == m_state);
|
||||
|
@ -735,6 +809,7 @@ struct DebugDraw
|
|||
{
|
||||
BX_CHECK(0 == m_stack, "Invalid stack %d.", m_stack);
|
||||
|
||||
flushQuad();
|
||||
flush();
|
||||
|
||||
m_state = State::Count;
|
||||
|
@ -790,8 +865,6 @@ struct DebugDraw
|
|||
|
||||
void setState(bool _depthTest, bool _depthWrite, bool _clockwise)
|
||||
{
|
||||
flush();
|
||||
|
||||
const uint64_t depthTest = m_depthTestLess
|
||||
? BGFX_STATE_DEPTH_TEST_LESS
|
||||
: BGFX_STATE_DEPTH_TEST_GREATER
|
||||
|
@ -1291,6 +1364,94 @@ struct DebugDraw
|
|||
close();
|
||||
}
|
||||
|
||||
void drawQuad(SpriteHandle _handle, const float* _normal, const float* _center, float _size)
|
||||
{
|
||||
if (m_posQuad == BX_COUNTOF(m_cacheQuad) )
|
||||
{
|
||||
flushQuad();
|
||||
}
|
||||
|
||||
const Attrib& attrib = m_attrib[m_stack];
|
||||
|
||||
float udir[3];
|
||||
float vdir[3];
|
||||
|
||||
bx::vec3TangentFrame(_normal, udir, vdir, attrib.m_spin);
|
||||
|
||||
const Pack2D& pack = m_sprite.get(_handle);
|
||||
const float invTextureSize = 1.0f/SPRITE_TEXTURE_SIZE;
|
||||
const float us = pack.m_x * invTextureSize;
|
||||
const float vs = pack.m_y * invTextureSize;
|
||||
const float ue = (pack.m_x + pack.m_width ) * invTextureSize;
|
||||
const float ve = (pack.m_y + pack.m_height) * invTextureSize;
|
||||
|
||||
const float aspectRatio = float(pack.m_width)/float(pack.m_height);
|
||||
const float halfExtentU = aspectRatio*_size*0.5f;
|
||||
const float halfExtentV = 1.0f/aspectRatio*_size*0.5f;
|
||||
|
||||
float umin[3];
|
||||
bx::vec3Mul(umin, udir, -halfExtentU);
|
||||
|
||||
float umax[3];
|
||||
bx::vec3Mul(umax, udir, halfExtentU);
|
||||
|
||||
float vmin[3];
|
||||
bx::vec3Mul(vmin, vdir, -halfExtentV);
|
||||
|
||||
float vmax[3];
|
||||
bx::vec3Mul(vmax, vdir, halfExtentV);
|
||||
|
||||
DebugUvVertex* vertex = &m_cacheQuad[m_posQuad];
|
||||
m_posQuad += 4;
|
||||
|
||||
float pt[3];
|
||||
float tmp[3];
|
||||
bx::vec3Add(tmp, umin, vmin);
|
||||
bx::vec3Add(pt, _center, tmp);
|
||||
vertex->m_x = pt[0];
|
||||
vertex->m_y = pt[1];
|
||||
vertex->m_z = pt[2];
|
||||
vertex->m_u = us;
|
||||
vertex->m_v = vs;
|
||||
vertex->m_abgr = attrib.m_abgr;
|
||||
++vertex;
|
||||
|
||||
bx::vec3Add(tmp, umax, vmin);
|
||||
bx::vec3Add(pt, _center, tmp);
|
||||
vertex->m_x = pt[0];
|
||||
vertex->m_y = pt[1];
|
||||
vertex->m_z = pt[2];
|
||||
vertex->m_u = ue;
|
||||
vertex->m_v = vs;
|
||||
vertex->m_abgr = attrib.m_abgr;
|
||||
++vertex;
|
||||
|
||||
bx::vec3Add(tmp, umin, vmax);
|
||||
bx::vec3Add(pt, _center, tmp);
|
||||
vertex->m_x = pt[0];
|
||||
vertex->m_y = pt[1];
|
||||
vertex->m_z = pt[2];
|
||||
vertex->m_u = us;
|
||||
vertex->m_v = ve;
|
||||
vertex->m_abgr = attrib.m_abgr;
|
||||
++vertex;
|
||||
|
||||
bx::vec3Add(tmp, umax, vmax);
|
||||
bx::vec3Add(pt, _center, tmp);
|
||||
vertex->m_x = pt[0];
|
||||
vertex->m_y = pt[1];
|
||||
vertex->m_z = pt[2];
|
||||
vertex->m_u = ue;
|
||||
vertex->m_v = ve;
|
||||
vertex->m_abgr = attrib.m_abgr;
|
||||
++vertex;
|
||||
}
|
||||
|
||||
void drawQuad(bgfx::TextureHandle _handle, const float* _normal, const float* _center, float _size)
|
||||
{
|
||||
BX_UNUSED(_handle, _normal, _center, _size);
|
||||
}
|
||||
|
||||
void drawCone(const float* _from, const float* _to, float _radius)
|
||||
{
|
||||
const Attrib& attrib = m_attrib[m_stack];
|
||||
|
@ -1710,6 +1871,48 @@ private:
|
|||
}
|
||||
}
|
||||
|
||||
void flushQuad()
|
||||
{
|
||||
if (0 != m_posQuad)
|
||||
{
|
||||
const uint32_t numIndices = m_posQuad/4*6;
|
||||
if (bgfx::checkAvailTransientBuffers(m_posQuad, DebugUvVertex::ms_decl, numIndices) )
|
||||
{
|
||||
bgfx::TransientVertexBuffer tvb;
|
||||
bgfx::allocTransientVertexBuffer(&tvb, m_posQuad, DebugUvVertex::ms_decl);
|
||||
memcpy(tvb.data, m_cacheQuad, m_posQuad * DebugUvVertex::ms_decl.m_stride);
|
||||
|
||||
bgfx::TransientIndexBuffer tib;
|
||||
bgfx::allocTransientIndexBuffer(&tib, numIndices);
|
||||
uint16_t* indices = (uint16_t*)tib.data;
|
||||
for (uint16_t ii = 0, num = m_posQuad/4; ii < num; ++ii)
|
||||
{
|
||||
uint16_t startVertex = ii*4;
|
||||
indices[0] = startVertex+0;
|
||||
indices[1] = startVertex+1;
|
||||
indices[2] = startVertex+2;
|
||||
indices[3] = startVertex+1;
|
||||
indices[4] = startVertex+3;
|
||||
indices[5] = startVertex+2;
|
||||
indices += 6;
|
||||
}
|
||||
|
||||
const Attrib& attrib = m_attrib[m_stack];
|
||||
|
||||
bgfx::setVertexBuffer(&tvb);
|
||||
bgfx::setIndexBuffer(&tib);
|
||||
bgfx::setState(0
|
||||
| (attrib.m_state & ~BGFX_STATE_CULL_MASK)
|
||||
);
|
||||
bgfx::setTransform(m_mtx);
|
||||
bgfx::setTexture(0, s_texColor, m_texture);
|
||||
bgfx::submit(m_viewId, m_program[Program::FillTexture]);
|
||||
}
|
||||
|
||||
m_posQuad = 0;
|
||||
}
|
||||
}
|
||||
|
||||
struct State
|
||||
{
|
||||
enum Enum
|
||||
|
@ -1726,11 +1929,16 @@ private:
|
|||
static const uint32_t stackSize = 16;
|
||||
BX_STATIC_ASSERT(cacheSize >= 3, "Cache must be at least 3 elements.");
|
||||
DebugVertex m_cache[cacheSize+1];
|
||||
uint32_t m_mtx;
|
||||
uint16_t m_indices[cacheSize*2];
|
||||
uint16_t m_pos;
|
||||
uint16_t m_indexPos;
|
||||
uint16_t m_vertexPos;
|
||||
|
||||
static const uint32_t cacheQuadSize = 1024;
|
||||
DebugUvVertex m_cacheQuad[cacheQuadSize];
|
||||
uint16_t m_posQuad;
|
||||
|
||||
uint32_t m_mtx;
|
||||
uint8_t m_viewId;
|
||||
uint8_t m_stack;
|
||||
bool m_depthTestLess;
|
||||
|
@ -1752,7 +1960,10 @@ private:
|
|||
State::Enum m_state;
|
||||
|
||||
Mesh m_mesh[Mesh::Count];
|
||||
|
||||
|
||||
typedef SpriteT<256, SPRITE_TEXTURE_SIZE> Sprite;
|
||||
Sprite m_sprite;
|
||||
|
||||
bgfx::UniformHandle s_texColor;
|
||||
bgfx::TextureHandle m_texture;
|
||||
bgfx::ProgramHandle m_program[Program::Count];
|
||||
|
@ -1776,6 +1987,16 @@ void ddShutdown()
|
|||
s_dd.shutdown();
|
||||
}
|
||||
|
||||
SpriteHandle ddCreateSprite(uint16_t _width, uint16_t _height, const void* _data)
|
||||
{
|
||||
return s_dd.createSprite(_width, _height, _data);
|
||||
}
|
||||
|
||||
void ddDestroy(SpriteHandle _handle)
|
||||
{
|
||||
s_dd.destroy(_handle);
|
||||
}
|
||||
|
||||
void ddBegin(uint8_t _viewId)
|
||||
{
|
||||
s_dd.begin(_viewId);
|
||||
|
@ -1911,6 +2132,16 @@ void ddDrawQuad(const float* _normal, const float* _center, float _size)
|
|||
s_dd.drawQuad(_normal, _center, _size);
|
||||
}
|
||||
|
||||
void ddDrawQuad(SpriteHandle _handle, const float* _normal, const float* _center, float _size)
|
||||
{
|
||||
s_dd.drawQuad(_handle, _normal, _center, _size);
|
||||
}
|
||||
|
||||
void ddDrawQuad(bgfx::TextureHandle _handle, const float* _normal, const float* _center, float _size)
|
||||
{
|
||||
s_dd.drawQuad(_handle, _normal, _center, _size);
|
||||
}
|
||||
|
||||
void ddDrawCone(const void* _from, const void* _to, float _radius)
|
||||
{
|
||||
s_dd.drawCone(_from, _to, _radius);
|
||||
|
|
|
@ -21,12 +21,22 @@ struct Axis
|
|||
};
|
||||
};
|
||||
|
||||
struct SpriteHandle { uint16_t idx; };
|
||||
|
||||
inline bool isValid(SpriteHandle _handle) { return _handle.idx != UINT16_MAX; }
|
||||
|
||||
///
|
||||
void ddInit(bool _depthTestLess = true, bx::AllocatorI* _allocator = NULL);
|
||||
|
||||
///
|
||||
void ddShutdown();
|
||||
|
||||
///
|
||||
SpriteHandle ddCreateSprite(uint16_t _width, uint16_t _height, const void* _data);
|
||||
|
||||
///
|
||||
void ddDestroy(SpriteHandle _handle);
|
||||
|
||||
///
|
||||
void ddBegin(uint8_t _viewId);
|
||||
|
||||
|
@ -108,6 +118,12 @@ void ddDrawCircle(Axis::Enum _axis, float _x, float _y, float _z, float _radius,
|
|||
///
|
||||
void ddDrawQuad(const float* _normal, const float* _center, float _size);
|
||||
|
||||
///
|
||||
void ddDrawQuad(SpriteHandle _handle, const float* _normal, const float* _center, float _size);
|
||||
|
||||
///
|
||||
void ddDrawQuad(bgfx::TextureHandle _handle, const float* _normal, const float* _center, float _size);
|
||||
|
||||
///
|
||||
void ddDrawCone(const void* _from, const void* _to, float _radius);
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче