* bobToolz::Vis Viewer repair (shows current vis cluster brush drawsurfaces in green and rest visible ones in other colours for Q3 and Wolf/QL .bsp):

don't crash on bsp w/o vis
		don't crash with origin in the void (includes inside of structural brush)(do reset)
		grab point to analyse from camera position with nothing selected; grab from any objects selection too
		fix rendering issues
		read surfaces written by q3map2 correctly + faster rendering code
		print number of loaded drawsurfaces to console for evaluation of optimization done
		fix a couple of of leaks and crashes after new/delete
This commit is contained in:
Garux 2019-03-07 00:50:25 +03:00
parent af720a7f32
commit 4382b5f6d9
10 changed files with 149 additions and 149 deletions

View File

@ -30,7 +30,6 @@
#include "str.h"
#include "DPoint.h"
#include "DWinding.h"
#include "misc.h"
#include "funchandlers.h"
@ -50,6 +49,8 @@ DVisDrawer::~DVisDrawer(){
GlobalShaderCache().detachRenderable( *this );
destroyShaders();
ClearPoints();
g_VisView = NULL;
}
@ -62,13 +63,15 @@ const char* g_state_wireframe = "$bobtoolz/visdrawer/wireframe";
void DVisDrawer::constructShaders(){
OpenGLState state;
GlobalOpenGLStateLibrary().getDefaultState( state );
state.m_sort = OpenGLState::eSortOverlayFirst;
state.m_state = RENDER_COLOURWRITE | RENDER_DEPTHWRITE | RENDER_COLOURCHANGE;
state.m_linewidth = 1;
GlobalOpenGLStateLibrary().insert( g_state_wireframe, state );
GlobalOpenGLStateLibrary().getDefaultState( state );
state.m_state = RENDER_FILL | RENDER_BLEND | RENDER_COLOURWRITE | RENDER_COLOURCHANGE | RENDER_SMOOTH | RENDER_DEPTHWRITE;
state.m_depthfunc = GL_LEQUAL;
state.m_state = RENDER_FILL | RENDER_BLEND | RENDER_COLOURWRITE | RENDER_COLOURCHANGE | RENDER_DEPTHTEST;
GlobalOpenGLStateLibrary().insert( g_state_solid, state );
@ -84,21 +87,15 @@ void DVisDrawer::destroyShaders(){
}
void DVisDrawer::render( RenderStateFlags state ) const {
//bleh
std::list<DWinding *>::const_iterator l = m_list->begin();
for (; l != m_list->end(); l++ )
{
DWinding* w = *l;
glColor4f( w->clr[0], w->clr[1], w->clr[2], 0.5f );
glBegin( GL_POLYGON );
for ( int i = 0; i < w->numpoints; i++ ) {
glVertex3f( ( w->p[i] )[0], ( w->p[i] )[1], ( w->p[i] )[2] );
}
glEnd();
glEnable( GL_POLYGON_OFFSET_FILL );
for( const auto surf : *m_list ){
const DMetaSurf& s = *surf;
glColor4f( s.colour[0], s.colour[1], s.colour[2], 0.5f );
glVertexPointer( 3, GL_FLOAT, sizeof( vec3_t ), s.verts );
glDrawElements( GL_TRIANGLES, GLsizei( s.indicesN ), GL_UNSIGNED_INT, s.indices );
}
glDisable( GL_POLYGON_OFFSET_FILL );
glColor4f( 1, 1, 1, 1 );
}
void DVisDrawer::renderWireframe( Renderer& renderer, const VolumeTest& volume ) const {
@ -122,17 +119,17 @@ void DVisDrawer::renderSolid( Renderer& renderer, const VolumeTest& volume ) con
renderer.addRenderable( *this, g_matrix4_identity );
}
void DVisDrawer::SetList( std::list<DWinding*> *pointList ){
if ( m_list ) {
ClearPoints();
}
void DVisDrawer::SetList( DMetaSurfaces* pointList ){
ClearPoints();
m_list = pointList;
}
void DVisDrawer::ClearPoints(){
std::list<DWinding *>::const_iterator deadPoint = m_list->begin();
for (; deadPoint != m_list->end(); deadPoint++ )
delete *deadPoint;
m_list->clear();
if ( m_list ) {
for ( auto deadPoint : *m_list )
delete deadPoint;
m_list->clear();
delete m_list;
m_list = 0;
}
}

View File

@ -32,8 +32,28 @@
#include <list>
#include "renderable.h"
#include "irender.h"
#include "mathlib.h"
#include "DWinding.h"
class DMetaSurf
{
public:
DMetaSurf() = delete;
DMetaSurf( int numverts, int numindices ){
verts = new vec3_t[numverts];
indices = new unsigned int[numindices];
indicesN = numindices;
}
~DMetaSurf(){
delete[] verts;
delete[] indices;
}
vec3_t* verts;
unsigned int* indices;
int indicesN;
vec3_t colour;
};
typedef std::list<DMetaSurf*> DMetaSurfaces;
class DVisDrawer : public Renderable, public OpenGLRenderable
{
@ -44,11 +64,11 @@ DVisDrawer();
virtual ~DVisDrawer();
protected:
std::list<DWinding*>* m_list;
DMetaSurfaces* m_list;
int refCount;
public:
void ClearPoints();
void SetList( std::list<DWinding*>* pointList );
void SetList( DMetaSurfaces* pointList );
void render( RenderStateFlags state ) const;
void renderSolid( Renderer& renderer, const VolumeTest& volume ) const;

View File

@ -8,21 +8,23 @@ int numleafs;
int numleafsurfaces;
int numVisBytes;
int numDrawVerts;
int numDrawVertsIndices;
int numDrawSurfaces;
int numbrushes;
int numbrushsides;
int numleafbrushes;
byte *visBytes = NULL;
dnode_t *dnodes = NULL;
dplane_t *dplanes = NULL;
dleaf_t *dleafs = NULL;
byte *visBytes = NULL;
dnode_t *dnodes = NULL;
dplane_t *dplanes = NULL;
dleaf_t *dleafs = NULL;
qdrawVert_t *drawVerts = NULL;
dsurface_t *drawSurfaces = NULL;
int *dleafsurfaces = NULL;
dbrush_t *dbrushes = NULL;
dbrushside_t *dbrushsides = NULL;
int *dleafbrushes = NULL;
int *drawVertsIndices = NULL;
dsurface_t *drawSurfaces = NULL;
int *dleafsurfaces = NULL;
dbrush_t *dbrushes = NULL;
dbrushside_t *dbrushsides = NULL;
int *dleafbrushes = NULL;
#define BSP_IDENT ( ( 'P' << 24 ) + ( 'S' << 16 ) + ( 'B' << 8 ) + 'I' )
#define Q3_BSP_VERSION 46
@ -159,7 +161,7 @@ void SwapBSPFile( void ) {
}
// drawindexes
// SwapBlock( (int *)drawIndexes, numDrawIndexes * sizeof( drawIndexes[0] ) );
SwapBlock( (int *)drawVertsIndices, numDrawVertsIndices * sizeof( drawVertsIndices[0] ) );
// drawsurfs
SwapBlock( (int *)drawSurfaces, numDrawSurfaces * sizeof( drawSurfaces[0] ) );
@ -218,18 +220,19 @@ bool LoadBSPFile( const char *filename ) {
return false;
}
numbrushsides = CopyLump( header, LUMP_BRUSHES, (void**)&dbrushsides, sizeof( dbrushside_t ) );
numbrushes = CopyLump( header, LUMP_BRUSHES, (void**)&dbrushes, sizeof( dbrush_t ) );
numplanes = CopyLump( header, LUMP_PLANES, (void**)&dplanes, sizeof( dplane_t ) );
numleafs = CopyLump( header, LUMP_LEAFS, (void**)&dleafs, sizeof( dleaf_t ) );
numnodes = CopyLump( header, LUMP_NODES, (void**)&dnodes, sizeof( dnode_t ) );
numDrawVerts = CopyLump( header, LUMP_DRAWVERTS, (void**)&drawVerts, sizeof( qdrawVert_t ) );
numDrawSurfaces = CopyLump( header, LUMP_SURFACES, (void**)&drawSurfaces, sizeof( dsurface_t ) );
numleafsurfaces = CopyLump( header, LUMP_LEAFSURFACES, (void**)&dleafsurfaces, sizeof( int ) );
numVisBytes = CopyLump( header, LUMP_VISIBILITY, (void**)&visBytes, 1 );
numleafbrushes = CopyLump( header, LUMP_LEAFBRUSHES, (void**)&dleafbrushes, sizeof( int ) );
numbrushsides = CopyLump( header, LUMP_BRUSHES, (void**)&dbrushsides, sizeof( dbrushside_t ) );
numbrushes = CopyLump( header, LUMP_BRUSHES, (void**)&dbrushes, sizeof( dbrush_t ) );
numplanes = CopyLump( header, LUMP_PLANES, (void**)&dplanes, sizeof( dplane_t ) );
numleafs = CopyLump( header, LUMP_LEAFS, (void**)&dleafs, sizeof( dleaf_t ) );
numnodes = CopyLump( header, LUMP_NODES, (void**)&dnodes, sizeof( dnode_t ) );
numDrawVerts = CopyLump( header, LUMP_DRAWVERTS, (void**)&drawVerts, sizeof( qdrawVert_t ) );
numDrawVertsIndices = CopyLump( header, LUMP_DRAWINDEXES, (void**)&drawVertsIndices, sizeof( int ) );
numDrawSurfaces = CopyLump( header, LUMP_SURFACES, (void**)&drawSurfaces, sizeof( dsurface_t ) );
numleafsurfaces = CopyLump( header, LUMP_LEAFSURFACES, (void**)&dleafsurfaces, sizeof( int ) );
numVisBytes = CopyLump( header, LUMP_VISIBILITY, (void**)&visBytes, 1 );
numleafbrushes = CopyLump( header, LUMP_LEAFBRUSHES, (void**)&dleafbrushes, sizeof( int ) );
delete header; // everything has been copied out
delete[] header; // everything has been copied out
// swap everything
SwapBSPFile();
@ -238,34 +241,16 @@ bool LoadBSPFile( const char *filename ) {
}
void FreeBSPData(){
if ( visBytes ) {
delete visBytes;
}
if ( dnodes ) {
delete dnodes;
}
if ( dplanes ) {
delete dplanes;
}
if ( dleafs ) {
delete dleafs;
}
if ( drawVerts ) {
delete drawVerts;
}
if ( drawSurfaces ) {
delete drawSurfaces;
}
if ( dleafsurfaces ) {
delete dleafsurfaces;
}
if ( dleafbrushes ) {
delete dleafbrushes;
}
if ( dbrushes ) {
delete dbrushes;
}
if ( dbrushsides ) {
delete dbrushsides;
}
#define DEL( a ) delete[] a; a = 0;
DEL( visBytes );
DEL( dnodes );
DEL( dplanes );
DEL( dleafs );
DEL( drawVerts );
DEL( drawVertsIndices );
DEL( drawSurfaces );
DEL( dleafsurfaces );
DEL( dleafbrushes );
DEL( dbrushes );
DEL( dbrushsides );
}

View File

@ -108,7 +108,7 @@ typedef enum {
#define MAX_MAP_VISIBILITY 0x200000
#define MAX_MAP_NODES 0x20000
#define MAX_MAP_PLANES 0x20000
#define MAX_MAP_PLANES 0x100000
#define MAX_MAP_LEAFS 0x20000
extern int numVisBytes;
@ -116,6 +116,7 @@ extern int numleafs;
extern int numplanes;
extern int numnodes;
extern int numDrawVerts;
extern int numDrawVertsIndices;
extern int numDrawSurfaces;
extern int numleafsurfaces;
extern int numbrushes;
@ -127,6 +128,7 @@ extern dplane_t *dplanes;
extern dleaf_t *dleafs;
extern byte *visBytes;
extern qdrawVert_t *drawVerts;
extern int *drawVertsIndices;
extern dsurface_t *drawSurfaces;
extern int *dleafsurfaces;
extern dbrush_t *dbrushes;

View File

@ -588,40 +588,6 @@ void DoSplitPatchRows() {
}
void DoVisAnalyse(){
char filename[1024];
if ( GlobalSelectionSystem().countSelected() == 0 ) {
globalErrorStream() << "bobToolz VisAnalyse: Invalid number of objects selected, choose 1 only.\n";
if ( g_VisView ) {
delete g_VisView;
return;
}
}
// ensure we have something selected
if ( GlobalSelectionSystem().countSelected() != 1 ) {
//DoMessageBox("Invalid number of objects selected, choose 1 only", "Error", eMB_OK);
globalErrorStream() << "bobToolz VisAnalyse: Invalid number of objects selected, choose 1 only.\n";
return;
}
scene::Instance& brush = GlobalSelectionSystem().ultimateSelected();
//ensure we have a brush selected
if ( !Node_isBrush( brush.path().top() ) ) {
//DoMessageBox("No brush selected, select ONLY one brush", "Error", eMB_OK);
globalErrorStream() << "bobToolz VisAnalyse: No brush selected, select ONLY 1 brush.\n";
return;
}
DBrush orgBrush;
orgBrush.LoadFromBrush( brush, false );
orgBrush.BuildBounds();
vec3_t origin;
origin[0] = ( orgBrush.bbox_max[0] + orgBrush.bbox_min[0] ) / 2.f;
origin[1] = ( orgBrush.bbox_max[1] + orgBrush.bbox_min[1] ) / 2.f;
origin[2] = ( orgBrush.bbox_max[2] + orgBrush.bbox_min[2] ) / 2.f;
const char* rad_filename = GlobalRadiant().getMapName();
if ( !rad_filename ) {
//DoMessageBox("An ERROR occurred while trying\n to get the map filename", "Error", eMB_OK);
@ -629,18 +595,31 @@ void DoVisAnalyse(){
return;
}
char filename[1024];
strcpy( filename, rad_filename );
char* ext = strrchr( filename, '.' ) + 1;
strcpy( ext, "bsp" ); // rename the extension
std::list<DWinding*> *pointList = BuildTrace( filename, origin );
vec3_t origin;
if ( GlobalSelectionSystem().countSelected() == 0 ) {
memcpy( origin, GlobalRadiant().Camera_getOrigin().data(), 3 * sizeof ( ( ( Vector3* ) ( 0 ) ) -> x() ) );
}
else{
memcpy( origin, GlobalSelectionSystem().getBoundsSelected().origin.data(), 3 * sizeof ( ( ( Vector3* ) ( 0 ) ) -> x() ) );
}
DMetaSurfaces* pointList = BuildTrace( filename, origin );
if( pointList && pointList->size() )
globalOutputStream() << "bobToolz VisAnalyse: " << pointList->size() << " drawsurfaces loaded\n";
if ( !g_VisView ) {
g_VisView = new DVisDrawer;
}
g_VisView->SetList( pointList );
SceneChangeNotify();
}
void DoTrainPathPlot() {

View File

@ -24,7 +24,7 @@ Files Contained In This Package:
Readme.txt --- This file.
Changelog.txt --- Version information.
bobToolz.dll --- The plugin itsself.
bobToolz.dll --- The plugin itself.
bt/*.txt --- A few text files required by the plugin.

View File

@ -4,8 +4,8 @@
#include "visfind.h"
#include "dialogs/dialogs-gtk.h"
#include "DWinding.h"
#include "bsploader.h"
#include "DVisDrawer.h"
#include <list>
@ -127,9 +127,7 @@ int bsp_countclusters_mask( byte *bitvector, byte *maskvector, int length ){
return( c );
}
void AddCluster( std::list<DWinding*> *pointlist, dleaf_t *cl, bool* repeatlist, vec3_t clr ){
DWinding* w;
void AddCluster( DMetaSurfaces* pointlist, dleaf_t *cl, bool* repeatlist, const vec3_t clr ){
int* leafsurf = &dleafsurfaces[cl->firstLeafSurface];
for ( int k = 0; k < cl->numLeafSurfaces; k++, leafsurf++ )
{
@ -147,20 +145,15 @@ void AddCluster( std::list<DWinding*> *pointlist, dleaf_t *cl, bool* repeatli
DoMessageBox( "Warning", "Warning", eMB_OK );
}
w = new DWinding();
w->AllocWinding( surf->numVerts );
DMetaSurf* meta = new DMetaSurf( surf->numVerts, surf->numIndexes );
for ( int l = 0; l < surf->numVerts; l++, vert++ )
{
( w->p[l] )[0] = vert->xyz[0];
( w->p[l] )[1] = vert->xyz[1];
( w->p[l] )[2] = vert->xyz[2];
for ( int l = 0; l < surf->numIndexes; ++l )
meta->indices[l] = drawVertsIndices[ surf->firstIndex + l ];
for ( int l = 0; l < surf->numVerts; ++l, ++vert )
VectorCopy( vert->xyz, meta->verts[l] );
VectorCopy( clr, meta->colour );
w->clr[0] = clr[0];
w->clr[1] = clr[1];
w->clr[2] = clr[2];
}
pointlist->push_back( w );
pointlist->push_back( meta );
repeatlist[*leafsurf] = true;
}
@ -171,22 +164,14 @@ void AddCluster( std::list<DWinding*> *pointlist, dleaf_t *cl, bool* repeatli
CreateTrace
=============
*/
std::list<DWinding*> *CreateTrace( dleaf_t *leaf, int c, vis_header *header, byte *visdata, byte *seen ){
DMetaSurfaces *CreateTrace( dleaf_t *leaf, int c, vis_header *header, byte *visdata, byte *seen ){
byte *vis;
int i, j, clusterNum;
std::list<DWinding*> *pointlist = new std::list<DWinding*>;
DMetaSurfaces* pointlist = new DMetaSurfaces;
bool* repeatlist = new bool[numDrawSurfaces];
dleaf_t *cl;
vec3_t clrRnd[5] = {
{0.f, 0.f, 1.f},
{0.f, 1.f, 1.f},
{1.f, 0.f, 0.f},
{1.f, 0.f, 1.f},
{1.f, 1.f, 0.f},
};
vec3_t clrGreen = {0.f, 1.f, 0.f};
const vec3_t clrGreen = {0.f, 1.f, 0.f};
memset( repeatlist, 0, sizeof( bool ) * numDrawSurfaces );
@ -203,7 +188,16 @@ std::list<DWinding*> *CreateTrace( dleaf_t *leaf, int c, vis_header *header, byt
cl = &( dleafs[bsp_leafnumforcluster( clusterNum )] );
if ( ( *( vis + i ) & ( 1 << j ) ) && ( *( seen + i ) & ( 1 << j ) ) && ( leaf->area == cl->area ) ) {
AddCluster( pointlist, cl, repeatlist, clrRnd[rand() % 5] );
vec3_t clr;
do {
VectorSet( clr,
( rand() % 256 ) / 255.f,
( rand() % 256 ) / 255.f,
( rand() % 256 ) / 255.f );
}while( ( clr[0] + clr[2] < clr[1] * 1.5f ) || //too green
( clr[0] < .3 && clr[1] < .3 && clr[2] < .3 ) ); //too dark
AddCluster( pointlist, cl, repeatlist, clr );
}
clusterNum++;
}
@ -221,7 +215,7 @@ std::list<DWinding*> *CreateTrace( dleaf_t *leaf, int c, vis_header *header, byt
setup for CreateTrace
=============
*/
std::list<DWinding*> *TraceCluster( int leafnum ){
DMetaSurfaces* TraceCluster( int leafnum ){
byte seen[( MAX_MAP_LEAFS / 8 ) + 1];
vis_header *vheader;
byte *visdata;
@ -238,14 +232,26 @@ std::list<DWinding*> *TraceCluster( int leafnum ){
return CreateTrace( leaf, leaf->cluster, vheader, visdata, seen );
}
std::list<DWinding *>* BuildTrace( char* filename, vec3_t v_origin ){
DMetaSurfaces* BuildTrace( char* filename, vec3_t v_origin ){
if ( !LoadBSPFile( filename ) ) {
return NULL;
}
if( numVisBytes == 0 ){
FreeBSPData();
globalErrorStream() << "bobToolz VisAnalyse: Bsp has no visibility data!\n";
return 0;
}
int leafnum = bsp_leafnumfororigin( v_origin );
std::list<DWinding*> *pointlist = TraceCluster( leafnum );
if( dleafs[leafnum].cluster == -1 ){
FreeBSPData();
globalErrorStream() << "bobToolz VisAnalyse: Point of interest is in the void!\n";
return 0;
}
DMetaSurfaces* pointlist = TraceCluster( leafnum );
FreeBSPData();

View File

@ -2,6 +2,7 @@
#include <list>
#include "mathlib.h"
class DWinding;
class DMetaSurf;
typedef std::list<DMetaSurf*> DMetaSurfaces;
std::list<DWinding*> *BuildTrace( char* filename, vec3_t v_origin );
DMetaSurfaces* BuildTrace( char* filename, vec3_t v_origin );

View File

@ -149,6 +149,9 @@ struct _QERFuncTable_1
void ( *XYWindowMouseDown_disconnect )( MouseEventHandlerId id );
VIEWTYPE ( *XYWindow_getViewType )();
Vector3 ( *XYWindow_windowToWorld )( const WindowVector& position );
Vector3 ( *Camera_getOrigin )();
const char* ( *TextureBrowser_getSelectedShader )( );
// GTK+ functions

View File

@ -109,6 +109,10 @@ Vector3 XYWindow_windowToWorld( const WindowVector& position ){
return result;
}
Vector3 Camera_getOrigin(){
return Camera_getOrigin( *g_pParentWnd->GetCamWnd() );
}
class RadiantCoreAPI
{
_QERFuncTable_1 m_radiantcore;
@ -149,6 +153,9 @@ RadiantCoreAPI(){
m_radiantcore.XYWindowMouseDown_disconnect = XYWindowMouseDown_disconnect;
m_radiantcore.XYWindow_getViewType = XYWindow_getViewType;
m_radiantcore.XYWindow_windowToWorld = XYWindow_windowToWorld;
m_radiantcore.Camera_getOrigin = Camera_getOrigin;
m_radiantcore.TextureBrowser_getSelectedShader = TextureBrowser_GetSelectedShader;
m_radiantcore.m_pfnMessageBox = &gtk_MessageBox;