Main Page | Class Hierarchy | Alphabetical List | Data Structures | Directories | File List | Data Fields | Globals

Brush.cpp File Reference

#include "stdafx.h"
#include <assert.h>
#include "qe3.h"
#include "winding.h"

Include dependency graph for Brush.cpp:

Include dependency graph

Go to the source code of this file.

Defines

#define INTERSECT_EPSILON   0.1
#define INTERSECT_EPSILON   0.1
#define MAX_MOVE_FACES   64
#define MAX_MOVE_FACES   64
#define MAX_MOVE_FACES   64
#define POINT_EPSILON   0.3
#define POINT_EPSILON   0.3

Functions

int AddPlanept (float *f)
void Brush_AddToList (brush_t *b, brush_t *list)
brush_tBrush_Alloc ()
face_tBrush_BestSplitFace (brush_t *b)
void Brush_Build (brush_t *b, bool bSnap, bool bMarkMap, bool bConvert)
void Brush_BuildWindings (brush_t *b, bool bSnap)
void Brush_Center (brush_t *b, vec3_t vNewCenter)
brush_tBrush_Clone (brush_t *b)
int Brush_Convex (brush_t *b)
brush_tBrush_Create (vec3_t mins, vec3_t maxs, texdef_t *texdef)
brush_tBrush_CreatePyramid (vec3_t mins, vec3_t maxs, texdef_t *texdef)
void Brush_Draw (brush_t *b)
void Brush_DrawFacingAngle (brush_t *b, entity_t *e)
void Brush_DrawXY (brush_t *b, int nViewType)
void Brush_FitTexture (brush_t *b, int nHeight, int nWidth)
void Brush_Free (brush_t *b, bool bRemoveNode)
brush_tBrush_FullClone (brush_t *b)
const char * Brush_GetKeyValue (brush_t *b, const char *pKey)
int Brush_InsertVertexBetween (brush_t *b, vec3_t p1, vec3_t p2)
brush_tBrush_MakeConvexBrushes (brush_t *b)
void Brush_MakeFacePlanes (brush_t *b)
winding_tBrush_MakeFaceWinding (brush_t *b, face_t *face)
void Brush_MakeSided (int sides)
void Brush_MakeSidedCone (int sides)
void Brush_MakeSidedSphere (int sides)
int Brush_MemorySize (brush_t *b)
void Brush_Move (brush_t *b, const vec3_t move, bool bSnap)
int Brush_MoveVertex (brush_t *b, vec3_t vertex, vec3_t delta, vec3_t end, bool bSnap)
int Brush_MoveVertex_old1 (brush_t *b, vec3_t vertex, vec3_t delta, vec3_t end, bool bSnap)
int Brush_MoveVertex_old2 (brush_t *b, vec3_t vertex, vec3_t delta, vec3_t end, bool bSnap)
const char * Brush_Name (brush_t *b)
brush_tBrush_Parse (void)
face_tBrush_Point (vec3_t origin, brush_t *b)
void Brush_Print (brush_t *b)
face_tBrush_Ray (vec3_t origin, vec3_t dir, brush_t *b, float *dist)
void Brush_RemoveEmptyFaces (brush_t *b)
void Brush_RemoveFromList (brush_t *b)
void Brush_ResetFaceOriginals (brush_t *b)
void Brush_Resize (brush_t *b, vec3_t vMin, vec3_t vMax)
void Brush_Rotate (brush_t *b, vec3_t vAngle, vec3_t vOrigin, bool bBuild)
void Brush_SelectFaceForDragging (brush_t *b, face_t *f, qboolean shear)
void Brush_SetEpair (brush_t *b, const char *pKey, const char *pValue)
void Brush_SetTexture (brush_t *b, texdef_t *texdef, brushprimit_texdef_t *brushprimit_texdef, bool bFitScale, IPluginTexdef *pTexdef)
void Brush_SideSelect (brush_t *b, vec3_t origin, vec3_t dir, qboolean shear)
void Brush_SnapPlanepts (brush_t *b)
void Brush_SnapToGrid (brush_t *pb)
void Brush_SplitBrushByFace (brush_t *in, face_t *f, brush_t **front, brush_t **back)
void Brush_Write (brush_t *b, CMemFile *pMemFile)
void Brush_Write (brush_t *b, FILE *f)
void Clamp (float &f, int nClamp)
qboolean ClipLineToFace (vec3_t p1, vec3_t p2, face_t *f)
void DrawBrushEntityName (brush_t *b)
void DrawLight (brush_t *b)
void EmitTextureCoordinates (float *xyzst, qtexture_t *q, face_t *f)
face_tFace_Alloc (void)
face_tFace_Clone (face_t *f)
void Face_Draw (face_t *f)
void Face_FitTexture (face_t *face, int nHeight, int nWidth)
void Face_Free (face_t *f)
face_tFace_FullClone (face_t *f)
void Face_MakePlane (face_t *f)
int Face_MemorySize (face_t *f)
void Face_MoveTexture (face_t *f, vec3_t delta)
void Face_SetColor (brush_t *b, face_t *f, float fCurveColor)
void Face_TextureVectors (face_t *f, float STfromXYZ[2][4])
void FacingVectors (entity_t *e, vec3_t forward, vec3_t right, vec3_t up)
eclass_tHasModel (brush_t *b)
bool PaintedModel (brush_t *b, bool bOkToTexture)
void PrintPlane (plane_t *p)
void PrintVector (vec3_t v)
void PrintWinding (winding_t *w)
void WINAPI QERApp_MapPrintf_FILE (char *text,...)
void WINAPI QERApp_MapPrintf_MEMFILE (char *text,...)
void SetFaceTexdef (brush_t *b, face_t *f, texdef_t *texdef, brushprimit_texdef_t *brushprimit_texdef, bool bFitScale, IPluginTexdef *pPlugTexdef)
float SetShadeForPlane (plane_t *p)
void TextureAxisFromPlane (plane_t *pln, vec3_t xv, vec3_t yv)

Variables

vec3_t baseaxis [18]
bool g_bDoIt = false
bool g_bInPaintedModel = false
FILEg_File
int g_nBrushId = 0
CMemFile * g_pMemFile
float lightaxis [3] = {0.6, 0.8, 1.0}
float shift [2]
vec3_t vecs [2]


Define Documentation

#define INTERSECT_EPSILON   0.1
 

Definition at line 1125 of file Brush.cpp.

#define INTERSECT_EPSILON   0.1
 

Definition at line 1125 of file Brush.cpp.

#define MAX_MOVE_FACES   64
 

Definition at line 1318 of file Brush.cpp.

#define MAX_MOVE_FACES   64
 

Definition at line 1318 of file Brush.cpp.

#define MAX_MOVE_FACES   64
 

Definition at line 1318 of file Brush.cpp.

#define POINT_EPSILON   0.3
 

Definition at line 1126 of file Brush.cpp.

#define POINT_EPSILON   0.3
 

Definition at line 1126 of file Brush.cpp.


Function Documentation

int AddPlanept float *  f  ) 
 

Definition at line 2987 of file Brush.cpp.

References QEGlobals_t::d_move_points, QEGlobals_t::d_num_move_points, g_qeglobals, and i.

Referenced by Brush_SelectFaceForDragging(), SelectFaceEdge(), and SelectVertex().

02988 {
02989     int     i;
02990 
02991     for (i=0 ; i<g_qeglobals.d_num_move_points ; i++)
02992         if (g_qeglobals.d_move_points[i] == f)
02993             return 0;
02994     g_qeglobals.d_move_points[g_qeglobals.d_num_move_points++] = f;
02995     return 1;
02996 }

void Brush_AddToList brush_t b,
brush_t list
 

Definition at line 2807 of file Brush.cpp.

References b, brush_t, DispatchRadiantMsg(), Error(), brush_s::next, Patch_Select(), brush_s::patchBrush, brush_s::pPatch, brush_s::prev, brush_s::pTerrain, RADIANT_SELECTION, selected_brushes, Terrain_Select(), and brush_s::terrainBrush.

Referenced by AddBrushForPatch(), AddBrushForTerrain(), AddProp(), AddRegionBrushes(), Brush_CopyList(), Brush_MakeSided(), Brush_MakeSidedCone(), Brush_MakeSidedSphere(), CPlugInManager::CommitBrushHandleToMap(), CXYWnd::Copy(), CopyAndSelect(), CopyToMap(), CreateEntityBrush(), CreateEntityFromName(), CreateSmartBrush(), CSG_MakeHollow(), CSG_Merge(), CSG_Subtract(), Map_ApplyRegion(), Map_RegionOff(), CXYWnd::NewBrushDrag(), CMainFrame::OnCreate(), CXYWnd::Paste(), CXYWnd::ProduceSplitLists(), QERApp_CreateBrush(), Select_AllOfType(), Select_Brush(), Select_Clone(), Select_CompleteTall(), Select_Inside(), Select_PartialTall(), Select_Ray(), Select_Touching(), SelectBrush(), Undo_AddBrush(), Undo_AddBrushList(), Undo_Redo(), and Undo_Undo().

02808 {
02809     if (b->next || b->prev)
02810         Error ("Brush_AddToList: allready linked");
02811     
02812     if (list == &selected_brushes || list == &active_brushes)
02813     {
02814         if (b->patchBrush && list == &selected_brushes)
02815         {
02816             Patch_Select(b->pPatch);
02817         }
02818         if (b->terrainBrush && list == &selected_brushes) {
02819             Terrain_Select(b->pTerrain);
02820         }
02821     }
02822     b->next = list->next;
02823     list->next->prev = b;
02824     list->next = b;
02825     b->prev = list;
02826     
02827     // TTimo messaging
02828     DispatchRadiantMsg( RADIANT_SELECTION );    
02829 }

Here is the call graph for this function:

brush_t* Brush_Alloc  ) 
 

Definition at line 46 of file Brush.cpp.

References b, brush_t, and qmalloc().

Referenced by Brush_Clone(), Brush_Create(), Brush_CreatePyramid(), Brush_FullClone(), Brush_MakeSided(), Brush_MakeSidedCone(), Brush_MakeSidedSphere(), Brush_Merge(), Brush_MergeList(), Brush_Parse(), and CPlugInManager::CreateBrushHandle().

00047 {
00048   brush_t *b = (brush_t*)qmalloc(sizeof(brush_t));
00049   return b;
00050 }

Here is the call graph for this function:

face_t* Brush_BestSplitFace brush_t b  ) 
 

Definition at line 751 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, plane_t::dist, f, face_t, face_s::face_winding, face_s::next, plane_t::normal, face_s::plane, value, Winding_Free(), Winding_IsTiny(), and Winding_SplitEpsilon().

Referenced by Brush_MakeConvexBrushes().

00752 {
00753     face_t *face, *f, *bestface;
00754     winding_t *front, *back;
00755     int splits, tinywindings, value, bestvalue;
00756 
00757     bestvalue = 999999;
00758     bestface = NULL;
00759     for (face = b->brush_faces; face; face = face->next)
00760     {
00761         splits = 0;
00762         tinywindings = 0;
00763         for (f = b->brush_faces; f; f = f->next)
00764         {
00765             if (f == face) continue;
00766             //
00767             Winding_SplitEpsilon(f->face_winding, face->plane.normal, face->plane.dist, 0.1, &front, &back);
00768 
00769             if (!front)
00770             {
00771                 Winding_Free(back);
00772             }
00773             else if (!back)
00774             {
00775                 Winding_Free(front);
00776             }
00777             else
00778             {
00779                 splits++;
00780                 if (Winding_IsTiny(front)) tinywindings++;
00781                 if (Winding_IsTiny(back)) tinywindings++;
00782             }
00783         }
00784         if (splits)
00785         {
00786             value = splits + 50 * tinywindings;
00787             if (value < bestvalue)
00788             {
00789                 bestvalue = value;
00790                 bestface = face;
00791             }
00792         }
00793     }
00794     return bestface;
00795 }

Here is the call graph for this function:

void Brush_Build brush_t b,
bool  bSnap,
bool  bMarkMap,
bool  bConvert
 

Definition at line 643 of file Brush.cpp.

References b, QEGlobals_t::bNeedConvert, Brush_BuildWindings(), brush_t, QEGlobals_t::d_select_mode, g_qeglobals, Group_AddToProperGroup(), QEGlobals_t::m_bBrushPrimitMode, Patch_BuildPoints(), sel_vertex, SetupVertexSelection(), Sys_MarkMapModified(), and Sys_Printf().

Referenced by AddBrushForPatch(), AddBrushForTerrain(), AddProp(), AddRegionBrushes(), Brush_FullClone(), Brush_MakeSided(), Brush_MakeSidedCone(), Brush_MakeSidedSphere(), Brush_Move(), Brush_RebuildBrush(), Brush_Resize(), Brush_Rotate(), Brush_SetTexture(), Brush_SnapToGrid(), Brush_SplitBrushByFace(), CPlugInManager::CommitBrushHandleToMap(), CPlugInManager::CommitEntityHandleToMap(), CXYWnd::Copy(), CopyAndSelect(), CopyBrush(), CopyToMap(), CreateEntityBrush(), CreateEntityFromName(), CreateSmartBrush(), Drag_Begin(), Entity_Create(), Entity_Parse(), FindReplaceTextures(), Map_BuildBrushData(), Map_ImportBuffer(), MoveSelection(), CXYWnd::NewBrushDrag(), CMainFrame::OnBrushFlipx(), CMainFrame::OnBrushFlipy(), CMainFrame::OnCreate(), CXYWnd::Paste(), QERApp_BuildBrush(), QERApp_BuildBrush2(), QERApp_CreateBrush(), QERApp_SetFaceInfo(), RotateTextures(), Select_ApplyMatrix(), Select_Clone(), Select_FitTexture(), Select_RotateTexture(), Select_Scale(), Select_ScaleTexture(), Select_SetTexture(), Select_ShiftTexture(), and Select_Ungroup().

00644 {
00645     bool        bLocalConvert;
00646 
00647 #ifdef _DEBUG
00648     if (!g_qeglobals.m_bBrushPrimitMode && bConvert)
00649         Sys_Printf("Warning : conversion from brush primitive to old brush format not implemented\n");
00650 #endif
00651 
00652     // if bConvert is set and g_qeglobals.bNeedConvert is not, that just means we need convert for this brush only
00653     if (bConvert && !g_qeglobals.bNeedConvert)
00654     {
00655         bLocalConvert = true;
00656         g_qeglobals.bNeedConvert = true;
00657     }
00658 
00659     /*
00660     ** build the windings and generate the bounding box
00661     */
00662     Brush_BuildWindings(b, bSnap);
00663 
00664     Patch_BuildPoints (b);
00665 
00666     /*
00667     ** move the points and edges if in select mode
00668     */
00669     if (g_qeglobals.d_select_mode == sel_vertex || g_qeglobals.d_select_mode == sel_edge)
00670         SetupVertexSelection ();
00671 
00672     if (b->itemOwner == NULL)
00673       Group_AddToProperGroup(b);
00674 
00675     if (bMarkMap)
00676     {
00677         Sys_MarkMapModified();
00678     }
00679 
00680     if (bLocalConvert)
00681         g_qeglobals.bNeedConvert = false;
00682 }

Here is the call graph for this function:

void Brush_BuildWindings brush_t b,
bool  bSnap
 

Definition at line 3150 of file Brush.cpp.

References b, QEGlobals_t::bNeedConvert, brush_s::brush_faces, Brush_MakeFacePlanes(), Brush_MakeFaceWinding(), Brush_SnapPlanepts(), brush_t, face_s::d_texture, EmitBrushPrimitTextureCoordinates(), EmitTextureCoordinates(), Face_SetColor(), face_t, face_s::face_winding, FaceToBrushPrimitFace(), free(), g_qeglobals, i, j, QEGlobals_t::m_bBrushPrimitMode, brush_s::maxs, brush_s::mins, texdef_t::name, face_s::next, winding_t::numpoints, winding_t::points, face_s::texdef, Texture_ForName(), v, vec_t, and w.

Referenced by Brush_Build(), Brush_Merge(), and Brush_MergeList().

03151 {
03152     winding_t *w;
03153     face_t    *face;
03154     vec_t      v;
03155 
03156     if (bSnap)
03157         Brush_SnapPlanepts( b );
03158 
03159     // clear the mins/maxs bounds
03160     b->mins[0] = b->mins[1] = b->mins[2] = 99999;
03161     b->maxs[0] = b->maxs[1] = b->maxs[2] = -99999;
03162 
03163     Brush_MakeFacePlanes (b);
03164 
03165     face = b->brush_faces;
03166 
03167     float fCurveColor = 1.0;
03168 
03169     for ( ; face ; face=face->next)
03170     {
03171         int i, j;
03172         free(face->face_winding);
03173         w = face->face_winding = Brush_MakeFaceWinding (b, face);
03174         face->d_texture = Texture_ForName( face->texdef.name );
03175 
03176         if (!w)
03177             continue;
03178     
03179         for (i=0 ; i<w->numpoints ; i++)
03180         {
03181             // add to bounding box
03182             for (j=0 ; j<3 ; j++)
03183             {
03184                 v = w->points[i][j];
03185                 if (v > b->maxs[j])
03186                     b->maxs[j] = v;
03187                 if (v < b->mins[j])
03188                     b->mins[j] = v;
03189             }
03190         }
03191         // setup s and t vectors, and set color
03192         //if (!g_PrefsDlg.m_bGLLighting)
03193     //{
03194           Face_SetColor (b, face, fCurveColor);
03195     //}
03196 
03197         fCurveColor -= .10;
03198         if (fCurveColor <= 0)
03199             fCurveColor = 1.0;
03200 
03201         // computing ST coordinates for the windings
03202         if (g_qeglobals.m_bBrushPrimitMode)
03203         {
03204             if (g_qeglobals.bNeedConvert)
03205             {
03206                 // we have parsed old brushes format and need conversion
03207                 // convert old brush texture representation to new format
03208                 FaceToBrushPrimitFace(face);
03209 #ifdef _DEBUG
03210                 // use old texture coordinates code to check against
03211                 for (i=0 ; i<w->numpoints ; i++)
03212                     EmitTextureCoordinates( w->points[i], face->d_texture, face);
03213 #endif
03214             }
03215             // use new texture representation to compute texture coordinates
03216             // in debug mode we will check against old code and warn if there are differences
03217             EmitBrushPrimitTextureCoordinates(face,w);
03218         }
03219         else
03220         {
03221             for (i=0 ; i<w->numpoints ; i++)
03222                 EmitTextureCoordinates( w->points[i], face->d_texture, face);
03223         }
03224     }
03225 }

Here is the call graph for this function:

void Brush_Center brush_t b,
vec3_t  vNewCenter
 

Definition at line 3285 of file Brush.cpp.

References abs(), b, Brush_Move(), brush_t, j, brush_s::maxs, brush_s::mins, vec3_t, and VectorSubtract.

03286 {
03287   vec3_t vMid;
03288   // get center of the brush
03289   for (int j = 0; j < 3; j++)
03290   {
03291     vMid[j] = b->mins[j] + abs((b->maxs[j] - b->mins[j]) * 0.5);
03292   }
03293   // calc distance between centers
03294   VectorSubtract(vNewCenter, vMid, vMid);
03295   Brush_Move(b, vMid, true);
03296 
03297 }

Here is the call graph for this function:

brush_t* Brush_Clone brush_t b  ) 
 

Definition at line 2619 of file Brush.cpp.

References b, Brush_Alloc(), brush_s::brush_faces, Brush_RemoveFromList(), brush_t, Entity_UnlinkBrush(), f, Face_Clone(), face_t, g_nBrushId, n, face_s::next, brush_s::numberId, brush_s::owner, p, Patch_Duplicate(), brush_s::patchBrush, brush_s::pPatch, patchMesh_t::pSymbiot, terrainMesh_t::pSymbiot, brush_s::pTerrain, Terrain_Duplicate(), and brush_s::terrainBrush.

Referenced by Brush_SplitBrushByFace(), CXYWnd::Copy(), CopyBrush(), CXYWnd::Paste(), and Select_Clone().

02620 {
02621     brush_t *n = NULL;
02622     face_t  *f, *nf;
02623 
02624     if (b->patchBrush)
02625     {
02626         patchMesh_t *p = Patch_Duplicate(b->pPatch);
02627         Brush_RemoveFromList(p->pSymbiot);
02628         Entity_UnlinkBrush(p->pSymbiot);
02629         n = p->pSymbiot;
02630     }
02631     else if (b->terrainBrush)
02632     {
02633         terrainMesh_t *p = Terrain_Duplicate(b->pTerrain);
02634         Brush_RemoveFromList(p->pSymbiot);
02635         Entity_UnlinkBrush(p->pSymbiot);
02636         n = p->pSymbiot;
02637     }
02638     else
02639     {
02640     n = Brush_Alloc();
02641       n->numberId = g_nBrushId++;
02642         n->owner = b->owner;
02643         for (f=b->brush_faces ; f ; f=f->next)
02644         {
02645             nf = Face_Clone( f );
02646             nf->next = n->brush_faces;
02647             n->brush_faces = nf;
02648         }
02649     }
02650 
02651     return n;
02652 }

Here is the call graph for this function:

int Brush_Convex brush_t b  ) 
 

Definition at line 837 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, plane_t::dist, face_t, face_s::face_winding, face_s::next, plane_t::normal, face_s::plane, and Winding_PlanesConcave().

00838 {
00839     face_t *face1, *face2;
00840 
00841     for (face1 = b->brush_faces; face1; face1 = face1->next)
00842     {
00843         if (!face1->face_winding) continue;
00844         for (face2 = b->brush_faces; face2; face2 = face2->next)
00845         {
00846             if (face1 == face2) continue;
00847             if (!face2->face_winding) continue;
00848             if (Winding_PlanesConcave(face1->face_winding, face2->face_winding,
00849                                         face1->plane.normal, face2->plane.normal,
00850                                         face1->plane.dist, face2->plane.dist))
00851             {
00852                 return false;
00853             }
00854         }
00855     }
00856     return true;
00857 }

Here is the call graph for this function:

brush_t* Brush_Create vec3_t  mins,
vec3_t  maxs,
texdef_t texdef
 

Definition at line 2210 of file Brush.cpp.

References b, Brush_Alloc(), brush_s::brush_faces, brush_t, texdef_t::contents, Error(), f, Face_Alloc(), face_t, texdef_t::flags, g_qeglobals, i, j, QEGlobals_t::m_bBrushPrimitMode, face_s::next, face_s::planepts, texdef_t::rotate, texdef_t::scale, texdef_t::shift, Sys_Printf(), face_s::texdef, vec3_t, and VectorCopy.

Referenced by AddBrushForPatch(), AddBrushForTerrain(), AddProp(), AddRegionBrushes(), Brush_CreatePyramid(), Brush_Resize(), CPlugInManager::CommitEntityHandleToMap(), CreateEntityBrush(), CreateEntityFromName(), CreateSmartBrush(), Entity_Create(), Entity_Parse(), CXYWnd::NewBrushDrag(), CMainFrame::OnCreate(), and QERApp_CreateBrush().

02211 {
02212     int     i, j;
02213     vec3_t  pts[4][2];
02214     face_t  *f;
02215     brush_t *b;
02216 
02217     // brush primitive mode : convert texdef to brushprimit_texdef ?
02218     // most of the time texdef is empty
02219     if (g_qeglobals.m_bBrushPrimitMode)
02220     {
02221         // check texdef is empty .. if there are cases it's not we need to write some conversion code
02222         if (texdef->shift[0]!=0 || texdef->shift[1]!=0 || texdef->scale[0]!=0 || texdef->scale[1]!=0 || texdef->rotate!=0)
02223             Sys_Printf("Warning : non-zero texdef detected in Brush_Create .. need brush primitive conversion\n");
02224     }
02225 
02226     for (i=0 ; i<3 ; i++)
02227     {
02228         if (maxs[i] < mins[i])
02229             Error ("Brush_InitSolid: backwards");
02230     }
02231 
02232     b = Brush_Alloc();
02233     
02234     pts[0][0][0] = mins[0];
02235     pts[0][0][1] = mins[1];
02236     
02237     pts[1][0][0] = mins[0];
02238     pts[1][0][1] = maxs[1];
02239     
02240     pts[2][0][0] = maxs[0];
02241     pts[2][0][1] = maxs[1];
02242     
02243     pts[3][0][0] = maxs[0];
02244     pts[3][0][1] = mins[1];
02245     
02246     for (i=0 ; i<4 ; i++)
02247     {
02248         pts[i][0][2] = mins[2];
02249         pts[i][1][0] = pts[i][0][0];
02250         pts[i][1][1] = pts[i][0][1];
02251         pts[i][1][2] = maxs[2];
02252     }
02253 
02254     for (i=0 ; i<4 ; i++)
02255     {
02256         f = Face_Alloc();
02257         f->texdef = *texdef;
02258         f->texdef.flags &= ~SURF_KEEP;
02259         f->texdef.contents &= ~CONTENTS_KEEP;
02260         f->next = b->brush_faces;
02261         b->brush_faces = f;
02262         j = (i+1)%4;
02263 
02264         VectorCopy (pts[j][1], f->planepts[0]);
02265         VectorCopy (pts[i][1], f->planepts[1]);
02266         VectorCopy (pts[i][0], f->planepts[2]);
02267     }
02268     
02269     f = Face_Alloc();
02270     f->texdef = *texdef;
02271     f->texdef.flags &= ~SURF_KEEP;
02272     f->texdef.contents &= ~CONTENTS_KEEP;
02273     f->next = b->brush_faces;
02274     b->brush_faces = f;
02275 
02276     VectorCopy (pts[0][1], f->planepts[0]);
02277     VectorCopy (pts[1][1], f->planepts[1]);
02278     VectorCopy (pts[2][1], f->planepts[2]);
02279 
02280     f = Face_Alloc();
02281     f->texdef = *texdef;
02282     f->texdef.flags &= ~SURF_KEEP;
02283     f->texdef.contents &= ~CONTENTS_KEEP;
02284     f->next = b->brush_faces;
02285     b->brush_faces = f;
02286 
02287     VectorCopy (pts[2][0], f->planepts[0]);
02288     VectorCopy (pts[1][0], f->planepts[1]);
02289     VectorCopy (pts[0][0], f->planepts[2]);
02290 
02291     return b;
02292 }

Here is the call graph for this function:

brush_t* Brush_CreatePyramid vec3_t  mins,
vec3_t  maxs,
texdef_t texdef
 

Definition at line 2302 of file Brush.cpp.

References b, bottom, Brush_Alloc(), Brush_Create(), brush_s::brush_faces, brush_t, texdef_t::contents, Error(), f, Face_Alloc(), face_t, texdef_t::flags, i, j, face_s::next, face_s::planepts, Q_rint(), face_s::texdef, top, vec3_t, and VectorCopy.

02303 {
02304     //++timo handle new brush primitive ? return here ??
02305     return Brush_Create(mins, maxs, texdef);
02306 
02307     for (int i=0 ; i<3 ; i++)
02308         if (maxs[i] < mins[i])
02309             Error ("Brush_InitSolid: backwards");
02310 
02311     brush_t* b = Brush_Alloc();
02312 
02313     vec3_t corners[4];
02314 
02315     float fMid = Q_rint(mins[2] + (Q_rint((maxs[2] - mins[2]) / 2)));
02316 
02317     corners[0][0] = mins[0];
02318     corners[0][1] = mins[1];
02319     corners[0][2] = fMid;
02320 
02321     corners[1][0] = mins[0];
02322     corners[1][1] = maxs[1];
02323     corners[1][2] = fMid;
02324 
02325     corners[2][0] = maxs[0];
02326     corners[2][1] = maxs[1];
02327     corners[2][2] = fMid;
02328 
02329     corners[3][0] = maxs[0];
02330     corners[3][1] = mins[1];
02331     corners[3][2] = fMid;
02332 
02333     vec3_t top, bottom;
02334 
02335     top[0] = Q_rint(mins[0] + ((maxs[0] - mins[0]) / 2));
02336     top[1] = Q_rint(mins[1] + ((maxs[1] - mins[1]) / 2));
02337     top[2] = Q_rint(maxs[2]);
02338 
02339     VectorCopy(top, bottom);
02340     bottom[2] = mins[2];
02341 
02342     // sides
02343     for (i = 0; i < 4; i++)
02344     {
02345         face_t* f = Face_Alloc();
02346         f->texdef = *texdef;
02347         f->texdef.flags &= ~SURF_KEEP;
02348         f->texdef.contents &= ~CONTENTS_KEEP;
02349         f->next = b->brush_faces;
02350         b->brush_faces = f;
02351         int j = (i+1)%4;
02352 
02353         VectorCopy (top, f->planepts[0]);
02354         VectorCopy (corners[i], f->planepts[1]);
02355         VectorCopy(corners[j], f->planepts[2]);
02356 
02357         f = Face_Alloc();
02358         f->texdef = *texdef;
02359         f->texdef.flags &= ~SURF_KEEP;
02360         f->texdef.contents &= ~CONTENTS_KEEP;
02361         f->next = b->brush_faces;
02362         b->brush_faces = f;
02363 
02364         VectorCopy (bottom, f->planepts[2]);
02365         VectorCopy (corners[i], f->planepts[1]);
02366         VectorCopy(corners[j], f->planepts[0]);
02367     }
02368 
02369     return b;
02370 }

Here is the call graph for this function:

void Brush_Draw brush_t b  ) 
 

Definition at line 3920 of file Brush.cpp.

References b, qtexture_s::bFromShader, brush_s::bModelFailed, Brush_DrawFacingAngle(), brush_s::brush_faces, brush_t, CCamWnd::Camera(), IPluginEntity::CamRender(), cd_texture, face_s::d_color, QEGlobals_t::d_savedinfo, face_s::d_texture, camera_t::draw_mode, DrawLight(), entity_s::eclass, SavedInfo_t::exclude, face_t, face_s::face_winding, eclass_s::fixedsize, texdef_t::flags, qtexture_s::fTrans, g_pParentWnd, g_PrefsDlg, g_qeglobals, CMainFrame::GetCamera(), brush_s::hiddenBrush, i, CPrefsDlg::m_bGLLighting, CPrefsDlg::m_bNewLightDraw, texdef_t::name, face_s::next, plane_t::normal, eclass_s::nShowFlags, winding_t::numpoints, order, brush_s::owner, PaintedModel(), Patch_DrawCam(), brush_s::patchBrush, face_s::plane, winding_t::points, brush_s::pPatch, entity_s::pPlugEnt, brush_s::pTerrain, qglBegin, qglBindTexture, qglColor3fv, qglColor4f, qglDisable, qglEnable, qglEnd, qglNormal3fv, qglTexCoord2fv, qglVertex3fv, qtexture_t, strstr(), Terrain_DrawCam(), brush_s::terrainBrush, face_s::texdef, qtexture_s::texture_number, and w.

Referenced by CCamWnd::Cam_Draw().

03921 {
03922     face_t          *face;
03923     int             i, order;
03924     qtexture_t      *prev = 0;
03925     winding_t *w;
03926 
03927     if ( b->owner && ( b->owner->eclass->nShowFlags & ECLASS_PLUGINENTITY ) )
03928     {
03929         b->owner->pPlugEnt->CamRender();
03930         return;
03931     }
03932     
03933     // (TTimo) NOTE: added by build 173, I check after pPlugEnt so it doesn't interfere ?
03934     if (b->hiddenBrush)
03935     {
03936         return;
03937     }
03938 
03939     if (b->patchBrush)
03940     {
03941         //Patch_DrawCam(b->nPatchID);
03942         Patch_DrawCam(b->pPatch);
03943         //if (!g_bPatchShowBounds)
03944         return;
03945     }
03946     
03947     if (b->terrainBrush)
03948     {
03949         Terrain_DrawCam(b->pTerrain);
03950         return;
03951     }
03952 
03953     int nDrawMode = g_pParentWnd->GetCamera()->Camera().draw_mode;
03954     
03955     if (b->owner->eclass->fixedsize)
03956     {
03957         
03958         if (!(g_qeglobals.d_savedinfo.exclude & EXCLUDE_ANGLES) && (b->owner->eclass->nShowFlags & ECLASS_ANGLE))
03959         {
03960             Brush_DrawFacingAngle(b, b->owner);
03961         }
03962         
03963         if (g_PrefsDlg.m_bNewLightDraw && (b->owner->eclass->nShowFlags & ECLASS_LIGHT))
03964         {
03965             DrawLight(b);
03966             return;
03967         }
03968         if (nDrawMode == cd_texture || nDrawMode == cd_light)
03969             qglDisable (GL_TEXTURE_2D);
03970         
03971         // if we are wireframing models
03972         bool bp = (b->bModelFailed) ? false : PaintedModel(b, true);
03973         
03974         if (nDrawMode == cd_texture || nDrawMode == cd_light)
03975             qglEnable (GL_TEXTURE_2D);
03976         
03977         if (bp)
03978             return;
03979     }
03980     
03981     // guarantee the texture will be set first
03982     prev = NULL;
03983     for (face = b->brush_faces,order = 0 ; face ; face=face->next, order++)
03984     {
03985         w = face->face_winding;
03986         if (!w)
03987         {
03988             continue;       // freed face
03989         }
03990         
03991         if (g_qeglobals.d_savedinfo.exclude & EXCLUDE_CAULK)
03992         {
03993             if (strstr(face->texdef.name, "caulk"))
03994             {
03995                 continue;
03996             }
03997         }
03998         
03999 #if 0
04000         if (b->alphaBrush)
04001         {
04002             if (!(face->texdef.flags & SURF_ALPHA))
04003                 continue;
04004             //--qglPushAttrib(GL_ALL_ATTRIB_BITS);
04005             qglDisable(GL_CULL_FACE);
04006             //--qglTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
04007             //--qglBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
04008             //--qglDisable(GL_DEPTH_TEST);
04009             //--qglBlendFunc (GL_SRC_ALPHA, GL_DST_ALPHA);
04010             //--qglEnable (GL_BLEND);
04011         }
04012 #endif
04013         
04014         if ((nDrawMode == cd_texture || nDrawMode == cd_light) && face->d_texture != prev)
04015         {
04016             // set the texture for this face
04017             prev = face->d_texture;
04018             qglBindTexture( GL_TEXTURE_2D, face->d_texture->texture_number );
04019         }
04020         
04021         
04022         
04023         if (!b->patchBrush)
04024         {
04025             if (face->texdef.flags & SURF_TRANS33) 
04026                 qglColor4f ( face->d_color[0], face->d_color[1], face->d_color[2], 0.33 );
04027             else if ( face->texdef.flags & SURF_TRANS66) 
04028                 qglColor4f ( face->d_color[0], face->d_color[1], face->d_color[2], 0.66 );
04029             else
04030                 qglColor3fv( face->d_color );
04031         }
04032         else
04033         {
04034             qglColor4f ( face->d_color[0], face->d_color[1], face->d_color[2], 0.13 );
04035         }
04036         
04037         // shader drawing stuff
04038         if (face->d_texture->bFromShader)
04039         {
04040             // setup shader drawing
04041             qglColor4f ( face->d_color[0], face->d_color[1], face->d_color[2], face->d_texture->fTrans );
04042             
04043         }
04044         
04045         // draw the polygon
04046         
04047         //if (nDrawMode == cd_light)
04048         //{
04049         if (g_PrefsDlg.m_bGLLighting)
04050         {
04051             qglNormal3fv(face->plane.normal);
04052         }
04053         //}
04054         
04055         qglBegin(GL_POLYGON);
04056         //if (nDrawMode == cd_light)
04057         
04058         for (i=0 ; i<w->numpoints ; i++)
04059         {
04060             if (nDrawMode == cd_texture || nDrawMode == cd_light)
04061                 qglTexCoord2fv( &w->points[i][3] );
04062             qglVertex3fv(w->points[i]);
04063         }
04064         qglEnd();
04065     }
04066     
04067 #if 0
04068     if (b->alphaBrush)
04069     {
04070         //--qglPopAttrib();
04071         qglEnable(GL_CULL_FACE);
04072         //--qglDisable (GL_BLEND);
04073         //--qglTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
04074     }
04075 #endif
04076     
04077     if (b->owner->eclass->fixedsize && (nDrawMode == cd_texture || nDrawMode == cd_light))
04078         qglEnable (GL_TEXTURE_2D);
04079     
04080     qglBindTexture( GL_TEXTURE_2D, 0 );
04081 }

Here is the call graph for this function:

void Brush_DrawFacingAngle brush_t b,
entity_t e
 

Definition at line 3768 of file Brush.cpp.

References b, brush_t, entity_t::brushes, e, FacingVectors(), brush_s::maxs, bspbrush_s::maxs, bspbrush_s::mins, qglBegin, qglColor4f, qglEnd, qglLineWidth, qglVertex3fv, right, up, vec3_t, VectorAdd, VectorMA, and VectorScale.

Referenced by Brush_Draw().

03769 {
03770     vec3_t  forward, right, up;
03771     vec3_t  endpoint, tip1, tip2;
03772     vec3_t  start;
03773     float   dist;
03774 
03775     VectorAdd(e->brushes.onext->mins, e->brushes.onext->maxs, start);
03776     VectorScale(start, 0.5, start);
03777     dist = (b->maxs[0] - start[0]) * 2.5;
03778 
03779     FacingVectors (e, forward, right, up);
03780     VectorMA (start, dist, forward, endpoint);
03781 
03782     dist = (b->maxs[0] - start[0]) * 0.5;
03783     VectorMA (endpoint, -dist, forward, tip1);
03784     VectorMA (tip1, -dist, up, tip1);
03785     VectorMA (tip1, 2*dist, up, tip2);
03786 
03787     qglColor4f (1, 1, 1, 1);
03788     qglLineWidth (4);
03789     qglBegin (GL_LINES);
03790     qglVertex3fv (start);
03791     qglVertex3fv (endpoint);
03792     qglVertex3fv (endpoint);
03793     qglVertex3fv (tip1);
03794     qglVertex3fv (endpoint);
03795     qglVertex3fv (tip2);
03796     qglEnd ();
03797     qglLineWidth (1);
03798 }

Here is the call graph for this function:

void Brush_DrawXY brush_t b,
int  nViewType
 

Definition at line 4097 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, DrawBrushEntityName(), entity_s::eclass, face_t, face_s::face_winding, eclass_s::fixedsize, g_PrefsDlg, brush_s::hiddenBrush, i, CPrefsDlg::m_bNewLightDraw, brush_s::maxs, brush_s::mins, face_s::next, plane_t::normal, eclass_s::nShowFlags, winding_t::numpoints, order, brush_s::owner, PaintedModel(), Patch_DrawXY(), brush_s::patchBrush, face_s::plane, winding_t::points, brush_s::pPatch, brush_s::pTerrain, qglBegin, qglEnd, qglPolygonMode, qglVertex3fv, Terrain_DrawXY(), brush_s::terrainBrush, vec3_t, VectorCopy, and w.

Referenced by CXYWnd::XY_Draw().

04098 {
04099     face_t *face;
04100     int     order;
04101     winding_t *w;
04102     int        i;
04103 
04104     if (b->hiddenBrush)
04105     {
04106         return;
04107     }
04108 
04109     if (b->patchBrush)
04110     {
04111         //Patch_DrawXY(b->nPatchID);
04112         Patch_DrawXY(b->pPatch);
04113         if (!g_bPatchShowBounds)
04114             return;
04115     }
04116 
04117     if (b->terrainBrush)
04118     {
04119         Terrain_DrawXY(b->pTerrain, b->owner);
04120     }
04121                      
04122 
04123     if (b->owner->eclass->fixedsize)
04124     {
04125         if (g_PrefsDlg.m_bNewLightDraw && (b->owner->eclass->nShowFlags & ECLASS_LIGHT))
04126         {
04127             vec3_t vCorners[4];
04128             float fMid = b->mins[2] + (b->maxs[2] - b->mins[2]) / 2;
04129 
04130             vCorners[0][0] = b->mins[0];
04131             vCorners[0][1] = b->mins[1];
04132             vCorners[0][2] = fMid;
04133 
04134             vCorners[1][0] = b->mins[0];
04135             vCorners[1][1] = b->maxs[1];
04136             vCorners[1][2] = fMid;
04137 
04138             vCorners[2][0] = b->maxs[0];
04139             vCorners[2][1] = b->maxs[1];
04140             vCorners[2][2] = fMid;
04141 
04142             vCorners[3][0] = b->maxs[0];
04143             vCorners[3][1] = b->mins[1];
04144             vCorners[3][2] = fMid;
04145 
04146             vec3_t vTop, vBottom;
04147 
04148             vTop[0] = b->mins[0] + ((b->maxs[0] - b->mins[0]) / 2);
04149             vTop[1] = b->mins[1] + ((b->maxs[1] - b->mins[1]) / 2);
04150             vTop[2] = b->maxs[2];
04151 
04152             VectorCopy(vTop, vBottom);
04153             vBottom[2] = b->mins[2];
04154 
04155             qglPolygonMode (GL_FRONT_AND_BACK, GL_LINE);
04156             qglBegin(GL_TRIANGLE_FAN);
04157             qglVertex3fv(vTop);
04158             qglVertex3fv(vCorners[0]);
04159             qglVertex3fv(vCorners[1]);
04160             qglVertex3fv(vCorners[2]);
04161             qglVertex3fv(vCorners[3]);
04162             qglVertex3fv(vCorners[0]);
04163             qglEnd();
04164             qglBegin(GL_TRIANGLE_FAN);
04165             qglVertex3fv(vBottom);
04166             qglVertex3fv(vCorners[0]);
04167             qglVertex3fv(vCorners[3]);
04168             qglVertex3fv(vCorners[2]);
04169             qglVertex3fv(vCorners[1]);
04170             qglVertex3fv(vCorners[0]);
04171             qglEnd();
04172             DrawBrushEntityName (b);
04173             return;
04174         }
04175         else if (b->owner->eclass->nShowFlags & ECLASS_MISCMODEL)
04176         {
04177             if (PaintedModel(b, false))
04178             return;
04179         }
04180     }
04181 
04182     for (face = b->brush_faces,order = 0 ; face ; face=face->next, order++)
04183     {
04184         // only draw polygons facing in a direction we care about
04185     if (nViewType == XY)
04186     {
04187           if (face->plane.normal[2] <= 0)
04188               continue;
04189     }
04190     else
04191     {
04192       if (nViewType == XZ)
04193       {
04194         if (face->plane.normal[1] <= 0)
04195           continue;
04196       }
04197       else 
04198       {
04199         if (face->plane.normal[0] <= 0)
04200           continue;
04201       }
04202     }
04203 
04204         w = face->face_winding;
04205         if (!w)
04206             continue;
04207 
04208     //if (b->alphaBrush && !(face->texdef.flags & SURF_ALPHA))
04209     //  continue;
04210 
04211         // draw the polygon
04212         qglBegin(GL_LINE_LOOP);
04213     for (i=0 ; i<w->numpoints ; i++)
04214           qglVertex3fv(w->points[i]);
04215         qglEnd();
04216     }
04217 
04218     DrawBrushEntityName (b);
04219 
04220 }

Here is the call graph for this function:

void Brush_FitTexture brush_t b,
int  nHeight,
int  nWidth
 

Definition at line 4585 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, Face_FitTexture(), face_t, and face_s::next.

Referenced by Select_FitTexture().

04586 {
04587     face_t *face;
04588 
04589     for (face = b->brush_faces ; face ; face=face->next)
04590   {
04591     Face_FitTexture( face, nHeight, nWidth );
04592   }
04593 }

Here is the call graph for this function:

void Brush_Free brush_t b,
bool  bRemoveNode
 

Definition at line 2510 of file Brush.cpp.

References b, brush_s::brush_faces, Brush_RemoveFromList(), brush_t, Entity_UnlinkBrush(), epair_t, brush_s::epairs, f, Face_Free(), face_t, free(), Group_RemoveBrush(), epair_s::key, next, face_s::next, epair_s::next, brush_s::next, brush_s::onext, Patch_Delete(), brush_s::patchBrush, brush_s::pPatch, brush_s::pTerrain, Terrain_Delete(), brush_s::terrainBrush, and epair_s::value.

Referenced by AddProp(), Brush_MakeConvexBrushes(), Brush_MakeSided(), Brush_MakeSidedCone(), Brush_MakeSidedSphere(), Brush_MergeListPairs(), Brush_SplitBrushByFace(), Brush_Subtract(), CleanList(), CPlugInManager::Cleanup(), CreateEntityFromName(), CSG_MakeHollow(), CSG_Merge(), CSG_Subtract(), Entity_Free(), Entity_Parse(), Map_BuildBrushData(), Map_Free(), CXYWnd::NewBrushDrag(), CMainFrame::OnDestroy(), QERApp_DeletePatch(), RemoveRegionBrushes(), Select_Delete(), Undo_Clear(), Undo_ClearRedo(), and Undo_FreeFirstUndo().

02511 {
02512     face_t  *f, *next;
02513     epair_t *ep, *enext;
02514 
02515     // remove from group
02516     if (bRemoveNode)
02517         Group_RemoveBrush(b);
02518 
02519     // free the patch if it's there
02520     if (b->patchBrush)
02521     {
02522         Patch_Delete(b->pPatch);
02523     }
02524 
02525     if( b->terrainBrush )
02526     {
02527         Terrain_Delete( b->pTerrain );
02528     }
02529 
02530     // free faces
02531     for (f=b->brush_faces ; f ; f=next)
02532     {
02533         next = f->next;
02534         Face_Free( f );
02535     }
02536 
02537     //Timo : free brush epairs
02538     for (ep = b->epairs ; ep ; ep=enext )
02539     {
02540         enext = ep->next;
02541         free (ep->key);
02542         free (ep->value);
02543         free (ep);
02544     }
02545 
02546     // unlink from active/selected list
02547     if (b->next)
02548         Brush_RemoveFromList (b);
02549 
02550     // unlink from entity list
02551     if (b->onext)
02552         Entity_UnlinkBrush (b);
02553 
02554     free (b);
02555 }

Here is the call graph for this function:

brush_t* Brush_FullClone brush_t b  ) 
 

Definition at line 2663 of file Brush.cpp.

References b, Brush_Alloc(), Brush_Build(), brush_s::brush_faces, Brush_RemoveFromList(), brush_t, face_s::d_texture, EmitBrushPrimitTextureCoordinates(), EmitTextureCoordinates(), Entity_UnlinkBrush(), f, f2(), Face_FullClone(), Face_SetColor(), face_t, face_s::face_winding, g_nBrushId, g_qeglobals, j, QEGlobals_t::m_bBrushPrimitMode, brush_s::maxs, brush_s::mins, n, face_s::next, brush_s::numberId, winding_t::numpoints, face_s::original, brush_s::owner, p, Patch_Duplicate(), brush_s::patchBrush, winding_t::points, brush_s::pPatch, patchMesh_t::pSymbiot, terrainMesh_t::pSymbiot, brush_s::pTerrain, Terrain_Duplicate(), brush_s::terrainBrush, and VectorCopy.

Referenced by Undo_AddBrush(), and Undo_AddBrushList().

02664 {
02665     brush_t *n = NULL;
02666     face_t *f, *nf, *f2, *nf2;
02667     int j;
02668 
02669     if (b->patchBrush)
02670     {
02671         patchMesh_t *p = Patch_Duplicate(b->pPatch);
02672         Brush_RemoveFromList(p->pSymbiot);
02673         Entity_UnlinkBrush(p->pSymbiot);
02674         n = p->pSymbiot;
02675         n->owner = b->owner;
02676         Brush_Build(n);
02677     }
02678     else if (b->terrainBrush)
02679     {
02680         terrainMesh_t *p = Terrain_Duplicate(b->pTerrain);
02681         Brush_RemoveFromList(p->pSymbiot);
02682         Entity_UnlinkBrush(p->pSymbiot);
02683         n = p->pSymbiot;
02684         n->owner = b->owner;
02685         Brush_Build(n);
02686     }
02687     else
02688     {
02689     n = Brush_Alloc();
02690     n->numberId = g_nBrushId++;
02691         n->owner = b->owner;
02692         VectorCopy(b->mins, n->mins);
02693         VectorCopy(b->maxs, n->maxs);
02694         //
02695         for (f = b->brush_faces; f; f = f->next)
02696         {
02697             if (f->original) continue;
02698             nf = Face_FullClone(f);
02699             nf->next = n->brush_faces;
02700             n->brush_faces = nf;
02701             //copy all faces that have the original set to this face
02702             for (f2 = b->brush_faces; f2; f2 = f2->next)
02703             {
02704                 if (f2->original == f)
02705                 {
02706                     nf2 = Face_FullClone(f2);
02707                     nf2->next = n->brush_faces;
02708                     n->brush_faces = nf2;
02709                     //set original
02710                     nf2->original = nf;
02711                 }
02712             }
02713         }
02714         for (nf = n->brush_faces; nf; nf = nf->next)
02715         {
02716             Face_SetColor(n, nf, 1.0);
02717             if (nf->face_winding)
02718       {
02719         if (g_qeglobals.m_bBrushPrimitMode)
02720                 EmitBrushPrimitTextureCoordinates(nf,nf->face_winding);
02721         else
02722         {
02723                   for (j = 0; j < nf->face_winding->numpoints; j++)
02724                     EmitTextureCoordinates(nf->face_winding->points[j], nf->d_texture, nf);
02725         }
02726       }
02727         }
02728   }
02729     return n;
02730 }

Here is the call graph for this function:

const char* Brush_GetKeyValue brush_t b,
const char *  pKey
 

Definition at line 1902 of file Brush.cpp.

References b, brush_t, brush_s::epairs, g_qeglobals, QEGlobals_t::m_bBrushPrimitMode, Patch_GetKeyValue(), brush_s::patchBrush, brush_s::pPatch, brush_s::pTerrain, Sys_Printf(), Terrain_GetKeyValue(), brush_s::terrainBrush, and ValueForKey().

Referenced by Group_AddToItem(), and Group_AddToProperGroup().

01903 {
01904     if (g_qeglobals.m_bBrushPrimitMode)
01905     {
01906     if (b->patchBrush)
01907     {
01908       return Patch_GetKeyValue(b->pPatch, pKey);
01909     }
01910     else if (b->terrainBrush)
01911     {
01912       return Terrain_GetKeyValue(b->pTerrain, pKey);
01913     }
01914     else
01915     {
01916           return ValueForKey(b->epairs, pKey);
01917     }
01918     }
01919     else
01920     {
01921         Sys_Printf("Can only set brush/patch key/values in Brush primitive mode\n");
01922     }
01923   return "";
01924 }

Here is the call graph for this function:

int Brush_InsertVertexBetween brush_t b,
vec3_t  p1,
vec3_t  p2
 

Definition at line 1598 of file Brush.cpp.

References b, brush_t, face_t, w, and Winding_InsertPoint().

01599 {
01600     face_t *face;
01601     winding_t *w, *neww;
01602     vec3_t point;
01603     int i, insert;
01604 
01605     if (Point_Equal(p1, p2, 0.4))
01606         return false;
01607     VectorAdd(p1, p2, point);
01608     VectorScale(point, 0.5, point);
01609     insert = false;
01610     //the end point may not be the same as another vertex
01611     for (face = b->brush_faces; face; face = face->next)
01612     {
01613         w = face->face_winding;
01614         if (!w) continue;
01615         neww = NULL;
01616         for (i = 0; i < w->numpoints; i++)
01617         {
01618             if (!Point_Equal(w->points[i], p1, 0.1))
01619                 continue;
01620             if (Point_Equal(w->points[(i+1) % w->numpoints], p2, 0.1))
01621             {
01622                 neww = Winding_InsertPoint(w, point, (i+1) % w->numpoints);
01623                 break;
01624             }
01625             else if (Point_Equal(w->points[(i-1+w->numpoints) % w->numpoints], p2, 0.3))
01626             {
01627                 neww = Winding_InsertPoint(w, point, i);
01628                 break;
01629             }
01630         }
01631         if (neww)
01632         {
01633             Winding_Free(face->face_winding);
01634             face->face_winding = neww;
01635             insert = true;
01636         }
01637     }
01638     return insert;
01639 }

Here is the call graph for this function:

brush_t* Brush_MakeConvexBrushes brush_t b  ) 
 

Definition at line 809 of file Brush.cpp.

References b, Brush_BestSplitFace(), Brush_Free(), Brush_SplitBrushByFace(), brush_t, face_t, and brush_s::next.

00810 {
00811     brush_t *front, *back, *end;
00812     face_t *face;
00813 
00814     b->next = NULL;
00815     face = Brush_BestSplitFace(b);
00816     if (!face) return b;
00817     Brush_SplitBrushByFace(b, face, &front, &back);
00818     //this should never happen
00819     if (!front && !back) return b;
00820     Brush_Free(b);
00821     if (!front)
00822         return Brush_MakeConvexBrushes(back);
00823     b = Brush_MakeConvexBrushes(front);
00824     if (back)
00825     {
00826         for (end = b; end->next; end = end->next);
00827         end->next = Brush_MakeConvexBrushes(back);
00828     }
00829     return b;
00830 }

Here is the call graph for this function:

void Brush_MakeFacePlanes brush_t b  ) 
 

Definition at line 473 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, f, Face_MakePlane(), face_t, and face_s::next.

Referenced by Brush_BuildWindings().

00474 {
00475     face_t  *f;
00476 
00477     for (f=b->brush_faces ; f ; f=f->next)
00478     {
00479         Face_MakePlane (f);
00480     }
00481 }

Here is the call graph for this function:

winding_t* Brush_MakeFaceWinding brush_t b,
face_t face
 

Definition at line 564 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, plane_t::dist, DotProduct, fabs(), face_t, free(), face_s::next, plane_t::normal, face_s::plane, printf(), qboolean, vec3_origin, VectorSubtract, w, Winding_BaseForPlane(), and Winding_Clip().

Referenced by Brush_BuildWindings(), Brush_SelectFaceForDragging(), MakeFace(), SelectFaceEdge(), and SelectVertex().

00565 {
00566     winding_t   *w;
00567     face_t      *clip;
00568     plane_t         plane;
00569     qboolean        past;
00570 
00571     // get a poly that covers an effectively infinite area
00572     w = Winding_BaseForPlane (&face->plane);
00573 
00574     // chop the poly by all of the other faces
00575     past = false;
00576     for (clip = b->brush_faces ; clip && w ; clip=clip->next)
00577     {
00578         if (clip == face)
00579         {
00580             past = true;
00581             continue;
00582         }
00583         if (DotProduct (face->plane.normal, clip->plane.normal) > 0.999
00584             && fabs(face->plane.dist - clip->plane.dist) < 0.01 )
00585         {   // identical plane, use the later one
00586             if (past)
00587             {
00588                 free (w);
00589                 return NULL;
00590             }
00591             continue;
00592         }
00593 
00594         // flip the plane, because we want to keep the back side
00595         VectorSubtract (vec3_origin,clip->plane.normal, plane.normal);
00596         plane.dist = -clip->plane.dist;
00597         
00598         w = Winding_Clip (w, &plane, false);
00599         if (!w)
00600             return w;
00601     }
00602     
00603     if (w->numpoints < 3)
00604     {
00605         free(w);
00606         w = NULL;
00607     }
00608 
00609     if (!w)
00610         printf ("unused plane\n");
00611 
00612     return w;
00613 }

Here is the call graph for this function:

void Brush_MakeSided int  sides  ) 
 

Definition at line 2382 of file Brush.cpp.

References CMainFrame::ActiveXY(), b, Brush_AddToList(), Brush_Alloc(), Brush_Build(), brush_s::brush_faces, Brush_Free(), brush_t, cos(), QEGlobals_t::d_texturewin, Entity_LinkBrush(), f, Face_Alloc(), face_t, floor(), g_pParentWnd, g_qeglobals, CXYWnd::GetViewType(), i, MAX_POINTS_ON_WINDING, brush_s::maxs, brush_s::mins, brush_s::next, face_s::next, face_s::planepts, QE_SingleBrush(), selected_brushes, sin(), sv, Sys_Printf(), Sys_Status(), Sys_UpdateWindows(), texturewin_t::texdef, face_s::texdef, vec3_t, VectorCopy, W_ALL, width, world_entity, XY, XZ, and YZ.

Referenced by CMainFrame::OnBrush3sided(), CMainFrame::OnBrush4sided(), CMainFrame::OnBrush5sided(), CMainFrame::OnBrush6sided(), CMainFrame::OnBrush7sided(), CMainFrame::OnBrush8sided(), CMainFrame::OnBrush9sided(), and SidesDlgProc().

02383 {
02384     int     i, axis;
02385     vec3_t  mins, maxs;
02386     brush_t *b;
02387     texdef_t    *texdef;
02388     face_t  *f;
02389     vec3_t  mid;
02390     float   width;
02391     float   sv, cv;
02392 
02393     if (sides < 3)
02394     {
02395         Sys_Status ("Bad sides number", 0);
02396         return;
02397     }
02398 
02399     if (sides >= MAX_POINTS_ON_WINDING-4)
02400     {
02401         Sys_Printf("too many sides.\n");
02402         return;
02403     }
02404 
02405     if (!QE_SingleBrush ())
02406     {
02407         Sys_Status ("Must have a single brush selected", 0 );
02408         return;
02409     }
02410 
02411     b = selected_brushes.next;
02412     VectorCopy (b->mins, mins);
02413     VectorCopy (b->maxs, maxs);
02414     texdef = &g_qeglobals.d_texturewin.texdef;
02415 
02416     Brush_Free (b);
02417 
02418     if (g_pParentWnd->ActiveXY())
02419     {
02420         switch(g_pParentWnd->ActiveXY()->GetViewType())
02421         {
02422             case XY: axis = 2; break;
02423             case XZ: axis = 1; break;
02424             case YZ: axis = 0; break;
02425         }
02426     }
02427     else
02428     {
02429         axis = 2;
02430     }
02431 
02432     // find center of brush
02433     width = 8;
02434     for (i = 0; i < 3; i++)
02435     {
02436         mid[i] = (maxs[i] + mins[i]) * 0.5;
02437         if (i == axis) continue;
02438         if ((maxs[i] - mins[i]) * 0.5 > width)
02439             width = (maxs[i] - mins[i]) * 0.5;
02440     }
02441 
02442     b = Brush_Alloc();
02443         
02444     // create top face
02445     f = Face_Alloc();
02446     f->texdef = *texdef;
02447     f->next = b->brush_faces;
02448     b->brush_faces = f;
02449 
02450     f->planepts[2][(axis+1)%3] = mins[(axis+1)%3]; f->planepts[2][(axis+2)%3] = mins[(axis+2)%3]; f->planepts[2][axis] = maxs[axis];
02451     f->planepts[1][(axis+1)%3] = maxs[(axis+1)%3]; f->planepts[1][(axis+2)%3] = mins[(axis+2)%3]; f->planepts[1][axis] = maxs[axis];
02452     f->planepts[0][(axis+1)%3] = maxs[(axis+1)%3]; f->planepts[0][(axis+2)%3] = maxs[(axis+2)%3]; f->planepts[0][axis] = maxs[axis];
02453 
02454     // create bottom face
02455     f = Face_Alloc();
02456     f->texdef = *texdef;
02457     f->next = b->brush_faces;
02458     b->brush_faces = f;
02459 
02460     f->planepts[0][(axis+1)%3] = mins[(axis+1)%3]; f->planepts[0][(axis+2)%3] = mins[(axis+2)%3]; f->planepts[0][axis] = mins[axis];
02461     f->planepts[1][(axis+1)%3] = maxs[(axis+1)%3]; f->planepts[1][(axis+2)%3] = mins[(axis+2)%3]; f->planepts[1][axis] = mins[axis];
02462     f->planepts[2][(axis+1)%3] = maxs[(axis+1)%3]; f->planepts[2][(axis+2)%3] = maxs[(axis+2)%3]; f->planepts[2][axis] = mins[axis];
02463 
02464     for (i=0 ; i<sides ; i++)
02465     {
02466         f = Face_Alloc();
02467         f->texdef = *texdef;
02468         f->next = b->brush_faces;
02469         b->brush_faces = f;
02470 
02471         sv = sin (i*3.14159265*2/sides);
02472         cv = cos (i*3.14159265*2/sides);
02473 
02474         f->planepts[0][(axis+1)%3] = floor(mid[(axis+1)%3]+width*cv+0.5);
02475         f->planepts[0][(axis+2)%3] = floor(mid[(axis+2)%3]+width*sv+0.5);
02476         f->planepts[0][axis] = mins[axis];
02477 
02478         f->planepts[1][(axis+1)%3] = f->planepts[0][(axis+1)%3];
02479         f->planepts[1][(axis+2)%3] = f->planepts[0][(axis+2)%3];
02480         f->planepts[1][axis] = maxs[axis];
02481 
02482         f->planepts[2][(axis+1)%3] = floor(f->planepts[0][(axis+1)%3] - width*sv + 0.5);
02483         f->planepts[2][(axis+2)%3] = floor(f->planepts[0][(axis+2)%3] + width*cv + 0.5);
02484         f->planepts[2][axis] = maxs[axis];
02485     }
02486 
02487     Brush_AddToList (b, &selected_brushes);
02488 
02489     Entity_LinkBrush (world_entity, b);
02490 
02491     Brush_Build( b );
02492 
02493     Sys_UpdateWindows (W_ALL);
02494 }

Here is the call graph for this function:

void Brush_MakeSidedCone int  sides  ) 
 

Definition at line 4290 of file Brush.cpp.

References b, Brush_AddToList(), Brush_Alloc(), Brush_Build(), brush_s::brush_faces, Brush_Free(), brush_t, cos(), QEGlobals_t::d_texturewin, Entity_LinkBrush(), f, Face_Alloc(), face_t, floor(), g_qeglobals, i, brush_s::maxs, brush_s::mins, brush_s::next, face_s::next, face_s::planepts, QE_SingleBrush(), selected_brushes, sin(), sv, Sys_Status(), Sys_UpdateWindows(), texturewin_t::texdef, face_s::texdef, vec3_t, VectorCopy, W_ALL, width, and world_entity.

Referenced by SidesDlgProc().

04291 {
04292     int     i;
04293     vec3_t  mins, maxs;
04294     brush_t *b;
04295     texdef_t    *texdef;
04296     face_t  *f;
04297     vec3_t  mid;
04298     float   width;
04299     float   sv, cv;
04300 
04301     if (sides < 3)
04302     {
04303         Sys_Status ("Bad sides number", 0);
04304         return;
04305     }
04306 
04307     if (!QE_SingleBrush ())
04308     {
04309         Sys_Status ("Must have a single brush selected", 0 );
04310         return;
04311     }
04312 
04313     b = selected_brushes.next;
04314     VectorCopy (b->mins, mins);
04315     VectorCopy (b->maxs, maxs);
04316     texdef = &g_qeglobals.d_texturewin.texdef;
04317 
04318     Brush_Free (b);
04319 
04320     // find center of brush
04321     width = 8;
04322     for (i=0 ; i<2 ; i++)
04323     {
04324         mid[i] = (maxs[i] + mins[i])*0.5;
04325         if (maxs[i] - mins[i] > width)
04326             width = maxs[i] - mins[i];
04327     }
04328     width /= 2;
04329 
04330     b = Brush_Alloc();
04331 
04332     // create bottom face
04333     f = Face_Alloc();
04334     f->texdef = *texdef;
04335     f->next = b->brush_faces;
04336     b->brush_faces = f;
04337 
04338     f->planepts[0][0] = mins[0];f->planepts[0][1] = mins[1];f->planepts[0][2] = mins[2];
04339     f->planepts[1][0] = maxs[0];f->planepts[1][1] = mins[1];f->planepts[1][2] = mins[2];
04340     f->planepts[2][0] = maxs[0];f->planepts[2][1] = maxs[1];f->planepts[2][2] = mins[2];
04341 
04342     for (i=0 ; i<sides ; i++)
04343     {
04344         f = Face_Alloc();
04345         f->texdef = *texdef;
04346         f->next = b->brush_faces;
04347         b->brush_faces = f;
04348 
04349         sv = sin (i*3.14159265*2/sides);
04350         cv = cos (i*3.14159265*2/sides);
04351 
04352 
04353         f->planepts[0][0] = floor(mid[0]+width*cv+0.5);
04354         f->planepts[0][1] = floor(mid[1]+width*sv+0.5);
04355         f->planepts[0][2] = mins[2];
04356 
04357         f->planepts[1][0] = mid[0];
04358         f->planepts[1][1] = mid[1];
04359         f->planepts[1][2] = maxs[2];
04360 
04361         f->planepts[2][0] = floor(f->planepts[0][0] - width * sv + 0.5);
04362         f->planepts[2][1] = floor(f->planepts[0][1] + width * cv + 0.5);
04363         f->planepts[2][2] = maxs[2];
04364 
04365     }
04366 
04367     Brush_AddToList (b, &selected_brushes);
04368 
04369     Entity_LinkBrush (world_entity, b);
04370 
04371     Brush_Build( b );
04372 
04373     Sys_UpdateWindows (W_ALL);
04374 }

Here is the call graph for this function:

void Brush_MakeSidedSphere int  sides  ) 
 

Definition at line 4384 of file Brush.cpp.

References b, Brush_AddToList(), Brush_Alloc(), Brush_Build(), brush_s::brush_faces, Brush_Free(), brush_t, QEGlobals_t::d_texturewin, Entity_LinkBrush(), f, Face_Alloc(), face_t, g_qeglobals, i, j, k, brush_s::maxs, brush_s::mins, brush_s::next, face_s::next, p, face_s::planepts, Q_PI, QE_SingleBrush(), selected_brushes, Sys_Status(), Sys_UpdateWindows(), t, texturewin_t::texdef, face_s::texdef, vec3_t, VectorAdd, VectorCopy, VectorPolar(), W_ALL, and world_entity.

Referenced by SidesDlgProc().

04385 {
04386     int     i,j;
04387     vec3_t  mins, maxs;
04388     brush_t *b;
04389     texdef_t    *texdef;
04390     face_t  *f;
04391     vec3_t  mid;
04392 
04393     if (sides < 4)
04394     {
04395         Sys_Status ("Bad sides number", 0);
04396         return;
04397     }
04398 
04399     if (!QE_SingleBrush ())
04400     {
04401         Sys_Status ("Must have a single brush selected", 0 );
04402         return;
04403     }
04404 
04405     b = selected_brushes.next;
04406     VectorCopy (b->mins, mins);
04407     VectorCopy (b->maxs, maxs);
04408     texdef = &g_qeglobals.d_texturewin.texdef;
04409 
04410     Brush_Free (b);
04411 
04412     // find center of brush
04413     float radius = 8;
04414     for (i=0 ; i<2 ; i++)
04415     {
04416         mid[i] = (maxs[i] + mins[i])*0.5;
04417         if (maxs[i] - mins[i] > radius)
04418             radius = maxs[i] - mins[i];
04419     }
04420     radius /= 2;
04421 
04422     b = Brush_Alloc();
04423 
04424     float dt = float(2 * Q_PI / sides);
04425     float dp = float(Q_PI / sides);
04426   float t,p;
04427     for(i=0; i <= sides-1; i++)
04428   {
04429         for(j=0;j <= sides-2; j++)
04430         {
04431             t = i * dt;
04432             p = float(j * dp - Q_PI / 2);
04433 
04434       f = Face_Alloc();
04435         f->texdef = *texdef;
04436         f->next = b->brush_faces;
04437         b->brush_faces = f;
04438 
04439       VectorPolar(f->planepts[0], radius, t, p);
04440       VectorPolar(f->planepts[1], radius, t, p + dp);
04441       VectorPolar(f->planepts[2], radius, t + dt, p + dp);
04442 
04443       for (int k = 0; k < 3; k++)
04444         VectorAdd(f->planepts[k], mid, f->planepts[k]);
04445         }
04446   }
04447 
04448   p = float((sides - 1) * dp - Q_PI / 2);
04449     for(i = 0; i <= sides-1; i++)
04450     {
04451         t = i * dt;
04452 
04453     f = Face_Alloc();
04454       f->texdef = *texdef;
04455       f->next = b->brush_faces;
04456       b->brush_faces = f;
04457 
04458     VectorPolar(f->planepts[0], radius, t, p);
04459     VectorPolar(f->planepts[1], radius, t + dt, p + dp);
04460     VectorPolar(f->planepts[2], radius, t + dt, p);
04461 
04462     for (int k = 0; k < 3; k++)
04463       VectorAdd(f->planepts[k], mid, f->planepts[k]);
04464     }
04465 
04466     Brush_AddToList (b, &selected_brushes);
04467 
04468     Entity_LinkBrush (world_entity, b);
04469 
04470     Brush_Build( b );
04471 
04472     Sys_UpdateWindows (W_ALL);
04473 }

Here is the call graph for this function:

int Brush_MemorySize brush_t b  ) 
 

Definition at line 2580 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, epair_t, brush_s::epairs, f, Face_MemorySize(), face_t, epair_s::key, face_s::next, epair_s::next, Patch_MemorySize(), brush_s::patchBrush, brush_s::pPatch, brush_s::pTerrain, Terrain_MemorySize(), brush_s::terrainBrush, and epair_s::value.

Referenced by Undo_AddBrush(), Undo_AddBrushList(), Undo_Clear(), Undo_FreeFirstUndo(), Undo_Redo(), and Undo_Undo().

02581 {
02582     face_t  *f;
02583     epair_t *ep;
02584     int size = 0;
02585 
02586     //
02587     if (b->patchBrush)
02588     {
02589         size += Patch_MemorySize(b->pPatch);
02590     }
02591     if (b->terrainBrush)
02592     {
02593         size += Terrain_MemorySize(b->pTerrain);
02594     }
02595     //
02596     for (f = b->brush_faces; f; f = f->next)
02597     {
02598         size += Face_MemorySize(f);
02599     }
02600     //
02601     for (ep = b->epairs; ep; ep = ep->next )
02602     {
02603         size += _msize(ep->key);
02604         size += _msize(ep->value);
02605         size += _msize(ep);
02606     }
02607     size += _msize(b);
02608     return size;
02609 }

Here is the call graph for this function:

void Brush_Move brush_t b,
const vec3_t  move,
bool  bSnap
 

Definition at line 4227 of file Brush.cpp.

References b, Brush_Build(), brush_s::brush_faces, brush_t, entity_s::eclass, f, Face_MoveTexture(), face_t, eclass_s::fixedsize, g_PrefsDlg, i, CPrefsDlg::m_bTextureLock, move(), face_s::next, entity_s::origin, brush_s::owner, Patch_Move(), brush_s::patchBrush, face_s::planepts, brush_s::pPatch, brush_s::pTerrain, Terrain_Move(), brush_s::terrainBrush, vec3_t, VectorAdd, and VectorCopy.

Referenced by Brush_Center(), MoveHold(), Select_Clone(), and Select_Move().

04228 {
04229   int i;
04230   face_t *f;
04231 
04232   for (f=b->brush_faces ; f ; f=f->next)
04233   {
04234     vec3_t vTemp;
04235     VectorCopy(move, vTemp);
04236 
04237     if (g_PrefsDlg.m_bTextureLock)
04238       Face_MoveTexture(f, vTemp);
04239     
04240     for (i=0 ; i<3 ; i++)
04241       VectorAdd (f->planepts[i], move, f->planepts[i]);
04242   }
04243   Brush_Build( b, bSnap );
04244 
04245 
04246   if (b->patchBrush)
04247   {
04248     //Patch_Move(b->nPatchID, move);
04249     Patch_Move(b->pPatch, move);
04250   }
04251 
04252   if (b->terrainBrush)
04253   {
04254     Terrain_Move(b->pTerrain, move);
04255   }
04256 
04257 
04258   // PGM - keep the origin vector up to date on fixed size entities.
04259   if(b->owner->eclass->fixedsize)
04260   {
04261     VectorAdd(b->owner->origin, move, b->owner->origin);
04262       //VectorAdd(b->maxs, b->mins, b->owner->origin);
04263       //VectorScale(b->owner->origin, 0.5, b->owner->origin);
04264   }
04265 }

Here is the call graph for this function:

int Brush_MoveVertex brush_t b,
vec3_t  vertex,
vec3_t  delta,
vec3_t  end,
bool  bSnap
 

Definition at line 1320 of file Brush.cpp.

References b, brush_t, face_t, g_qeglobals, VectorCopy, and w.

Referenced by MoveSelection().

01321 {
01322     face_t *f, *face, *newface, *lastface, *nextface;
01323     face_t *movefaces[MAX_MOVE_FACES];
01324     int movefacepoints[MAX_MOVE_FACES];
01325     winding_t *w, tmpw;
01326     vec3_t start, mid;
01327     plane_t plane;
01328     int i, j, k, nummovefaces, result, done;
01329     float dot, front, back, frac, smallestfrac;
01330 
01331     result = true;
01332     //
01333     tmpw.numpoints = 3;
01334     tmpw.maxpoints = 3;
01335     VectorCopy(vertex, start);
01336     VectorAdd(vertex, delta, end);
01337     //snap or not?
01338     if (bSnap)
01339         for (i = 0; i < 3; i++)
01340             end[i] = floor(end[i] / g_qeglobals.d_gridsize + 0.5) * g_qeglobals.d_gridsize;
01341     //
01342     VectorCopy(end, mid);
01343     //if the start and end are the same
01344     if (Point_Equal(start, end, 0.3)) return false;
01345     //the end point may not be the same as another vertex
01346     for (face = b->brush_faces; face; face = face->next)
01347     {
01348         w = face->face_winding;
01349         if (!w) continue;
01350         for (i = 0; i < w->numpoints; i++)
01351         {
01352             if (Point_Equal(w->points[i], end, 0.3))
01353             {
01354                 VectorCopy(vertex, end);
01355                 return false;
01356             }
01357         }
01358     }
01359     //
01360     done = false;
01361     while(!done)
01362     {
01363         //chop off triangles from all brush faces that use the to be moved vertex
01364         //store pointers to these chopped off triangles in movefaces[]
01365         nummovefaces = 0;
01366         for (face = b->brush_faces; face; face = face->next)
01367         {
01368             w = face->face_winding;
01369             if (!w) continue;
01370             for (i = 0; i < w->numpoints; i++)
01371             {
01372                 if (Point_Equal(w->points[i], start, 0.2))
01373                 {
01374                     if (face->face_winding->numpoints <= 3)
01375                     {
01376                         movefacepoints[nummovefaces] = i;
01377                         movefaces[nummovefaces++] = face;
01378                         break;
01379                     }
01380                     dot = DotProduct(end, face->plane.normal) - face->plane.dist;
01381                     //if the end point is in front of the face plane
01382                     if (dot > 0.1)
01383                     {
01384                         //fanout triangle subdivision
01385                         for (k = i; k < i + w->numpoints-3; k++)
01386                         {
01387                             VectorCopy(w->points[i], tmpw.points[0]);
01388                             VectorCopy(w->points[(k+1) % w->numpoints], tmpw.points[1]);
01389                             VectorCopy(w->points[(k+2) % w->numpoints], tmpw.points[2]);
01390                             //
01391                             newface = Face_Clone(face);
01392                             //get the original
01393                             for (f = face; f->original; f = f->original) ;
01394                             newface->original = f;
01395                             //store the new winding
01396                             if (newface->face_winding) Winding_Free(newface->face_winding);
01397                             newface->face_winding = Winding_Clone(&tmpw);
01398                             //get the texture
01399                             newface->d_texture = Texture_ForName( newface->texdef.name );
01400                             //add the face to the brush
01401                             newface->next = b->brush_faces;
01402                             b->brush_faces = newface;
01403                             //add this new triangle to the move faces
01404                             movefacepoints[nummovefaces] = 0;
01405                             movefaces[nummovefaces++] = newface;
01406                         }
01407                         //give the original face a new winding
01408                         VectorCopy(w->points[(i-2+w->numpoints) % w->numpoints], tmpw.points[0]);
01409                         VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[1]);
01410                         VectorCopy(w->points[i], tmpw.points[2]);
01411                         Winding_Free(face->face_winding);
01412                         face->face_winding = Winding_Clone(&tmpw);
01413                         //add the original face to the move faces
01414                         movefacepoints[nummovefaces] = 2;
01415                         movefaces[nummovefaces++] = face;
01416                     }
01417                     else
01418                     {
01419                         //chop a triangle off the face
01420                         VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[0]);
01421                         VectorCopy(w->points[i], tmpw.points[1]);
01422                         VectorCopy(w->points[(i+1) % w->numpoints], tmpw.points[2]);
01423                         //remove the point from the face winding
01424                         Winding_RemovePoint(w, i);
01425                         //get texture crap right
01426                         Face_SetColor(b, face, 1.0);
01427                         for (j = 0; j < w->numpoints; j++)
01428                             EmitTextureCoordinates(w->points[j], face->d_texture, face);
01429                         //make a triangle face
01430                         newface = Face_Clone(face);
01431                         //get the original
01432                         for (f = face; f->original; f = f->original) ;
01433                         newface->original = f;
01434                         //store the new winding
01435                         if (newface->face_winding) Winding_Free(newface->face_winding);
01436                         newface->face_winding = Winding_Clone(&tmpw);
01437                         //get the texture
01438                         newface->d_texture = Texture_ForName( newface->texdef.name );
01439                         //add the face to the brush
01440                         newface->next = b->brush_faces;
01441                         b->brush_faces = newface;
01442                         //
01443                         movefacepoints[nummovefaces] = 1;
01444                         movefaces[nummovefaces++] = newface;
01445                     }
01446                     break;
01447                 }
01448             }
01449         }
01450         //now movefaces contains pointers to triangle faces that
01451         //contain the to be moved vertex
01452         //
01453         done = true;
01454         VectorCopy(end, mid);
01455         smallestfrac = 1;
01456         for (face = b->brush_faces; face; face = face->next)
01457         {
01458             //check if there is a move face that has this face as the original
01459             for (i = 0; i < nummovefaces; i++)
01460             {
01461                 if (movefaces[i]->original == face) break;
01462             }
01463             if (i >= nummovefaces) continue;
01464             //check if the original is not a move face itself
01465             for (j = 0; j < nummovefaces; j++)
01466             {
01467                 if (face == movefaces[j]) break;
01468             }
01469             //if the original is not a move face itself
01470             if (j >= nummovefaces)
01471             {
01472                 memcpy(&plane, &movefaces[i]->original->plane, sizeof(plane_t));
01473             }
01474             else
01475             {
01476                 k = movefacepoints[j];
01477                 w = movefaces[j]->face_winding;
01478                 VectorCopy(w->points[(k+1)%w->numpoints], tmpw.points[0]);
01479                 VectorCopy(w->points[(k+2)%w->numpoints], tmpw.points[1]);
01480                 //
01481                 k = movefacepoints[i];
01482                 w = movefaces[i]->face_winding;
01483                 VectorCopy(w->points[(k+1)%w->numpoints], tmpw.points[2]);
01484                 if (!Plane_FromPoints(tmpw.points[0], tmpw.points[1], tmpw.points[2], &plane))
01485                 {
01486                     VectorCopy(w->points[(k+2)%w->numpoints], tmpw.points[2]);
01487                     if (!Plane_FromPoints(tmpw.points[0], tmpw.points[1], tmpw.points[2], &plane))
01488                         //this should never happen otherwise the face merge did a crappy job a previous pass
01489                         continue;
01490                 }
01491             }
01492             //now we've got the plane to check agains
01493             front = DotProduct(start, plane.normal) - plane.dist;
01494             back = DotProduct(end, plane.normal) - plane.dist;
01495             //if the whole move is at one side of the plane
01496             if (front < 0.01 && back < 0.01) continue;
01497             if (front > -0.01 && back > -0.01) continue;
01498             //if there's no movement orthogonal to this plane at all
01499             if (fabs(front-back) < 0.001) continue;
01500             //ok first only move till the plane is hit
01501             frac = front/(front-back);
01502             if (frac < smallestfrac)
01503             {
01504                 mid[0] = start[0] + (end[0] - start[0]) * frac;
01505                 mid[1] = start[1] + (end[1] - start[1]) * frac;
01506                 mid[2] = start[2] + (end[2] - start[2]) * frac;
01507                 smallestfrac = frac;
01508             }
01509             //
01510             done = false;
01511         }
01512 
01513         //move the vertex
01514         for (i = 0; i < nummovefaces; i++)
01515         {
01516             //move vertex to end position
01517             VectorCopy(mid, movefaces[i]->face_winding->points[movefacepoints[i]]);
01518             //create new face plane
01519             for (j = 0; j < 3; j++)
01520             {
01521                 VectorCopy(movefaces[i]->face_winding->points[j], movefaces[i]->planepts[j]);
01522             }
01523             Face_MakePlane(movefaces[i]);
01524             if (VectorLength(movefaces[i]->plane.normal) < 0.1)
01525                 result = false;
01526         }
01527         //if the brush is no longer convex
01528         if (!result || !Brush_Convex(b))
01529         {
01530             for (i = 0; i < nummovefaces; i++)
01531             {
01532                 //move the vertex back to the initial position
01533                 VectorCopy(start, movefaces[i]->face_winding->points[movefacepoints[i]]);
01534                 //create new face plane
01535                 for (j = 0; j < 3; j++)
01536                 {
01537                     VectorCopy(movefaces[i]->face_winding->points[j], movefaces[i]->planepts[j]);
01538                 }
01539                 Face_MakePlane(movefaces[i]);
01540             }
01541             result = false;
01542             VectorCopy(start, end);
01543             done = true;
01544         }
01545         else
01546         {
01547             VectorCopy(mid, start);
01548         }
01549         //get texture crap right
01550         for (i = 0; i < nummovefaces; i++)
01551         {
01552             Face_SetColor(b, movefaces[i], 1.0);
01553             for (j = 0; j < movefaces[i]->face_winding->numpoints; j++)
01554                 EmitTextureCoordinates(movefaces[i]->face_winding->points[j], movefaces[i]->d_texture, movefaces[i]);
01555         }
01556 
01557         //now try to merge faces with their original faces
01558         lastface = NULL;
01559         for (face = b->brush_faces; face; face = nextface)
01560         {
01561             nextface = face->next;
01562             if (!face->original)
01563             {
01564                 lastface = face;
01565                 continue;
01566             }
01567             if (!Plane_Equal(&face->plane, &face->original->plane, false))
01568             {
01569                 lastface = face;
01570                 continue;
01571             }
01572             w = Winding_TryMerge(face->face_winding, face->original->face_winding, face->plane.normal, true);
01573             if (!w)
01574             {
01575                 lastface = face;
01576                 continue;
01577             }
01578             Winding_Free(face->original->face_winding);
01579             face->original->face_winding = w;
01580             //get texture crap right
01581             Face_SetColor(b, face->original, 1.0);
01582             for (j = 0; j < face->original->face_winding->numpoints; j++)
01583                 EmitTextureCoordinates(face->original->face_winding->points[j], face->original->d_texture, face->original);
01584             //remove the face that was merged with the original
01585             if (lastface) lastface->next = face->next;
01586             else b->brush_faces = face->next;
01587             Face_Free(face);
01588         }
01589     }
01590     return result;
01591 }

int Brush_MoveVertex_old1 brush_t b,
vec3_t  vertex,
vec3_t  delta,
vec3_t  end,
bool  bSnap
 

Definition at line 880 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, QEGlobals_t::d_gridsize, face_t, floor(), g_qeglobals, i, winding_t::maxpoints, face_s::next, winding_t::numpoints, POINT_EPSILON, Point_Equal(), VectorAdd, and w.

00881 {
00882     face_t *f, *face, *newface, *lastface, *nextface;
00883     face_t *movefaces[MAX_MOVE_FACES];
00884     int movefacepoints[MAX_MOVE_FACES];
00885     winding_t *w, tmpw;
00886     int i, j, k, nummovefaces, result;
00887     float dot;
00888 
00889     result = false;
00890     //
00891     tmpw.numpoints = 3;
00892     tmpw.maxpoints = 3;
00893     VectorAdd(vertex, delta, end);
00894     //snap or not?
00895     if (bSnap)
00896         for (i = 0; i < 3; i++)
00897             end[i] = floor(end[i] / g_qeglobals.d_gridsize + 0.5) * g_qeglobals.d_gridsize;
00898     //chop off triangles from all brush faces that use the to be moved vertex
00899     //store pointers to these chopped off triangles in movefaces[]
00900     nummovefaces = 0;
00901     for (face = b->brush_faces; face; face = face->next)
00902     {
00903         w = face->face_winding;
00904         if (!w) continue;
00905         for (i = 0; i < w->numpoints; i++)
00906         {
00907             if (Point_Equal(w->points[i], vertex, POINT_EPSILON))
00908             {
00909                 if (face->face_winding->numpoints <= 3)
00910                 {
00911                     movefacepoints[nummovefaces] = i;
00912                     movefaces[nummovefaces++] = face;
00913                     break;
00914                 }
00915                 dot = DotProduct(end, face->plane.normal) - face->plane.dist;
00916                 //if the end point is in front of the face plane
00917                 if (dot > 0.1)
00918                 {
00919                     //fanout triangle subdivision
00920                     for (k = i; k < i + w->numpoints-3; k++)
00921                     {
00922                         VectorCopy(w->points[i], tmpw.points[0]);
00923                         VectorCopy(w->points[(k+1) % w->numpoints], tmpw.points[1]);
00924                         VectorCopy(w->points[(k+2) % w->numpoints], tmpw.points[2]);
00925                         //
00926                         newface = Face_Clone(face);
00927                         //get the original
00928                         for (f = face; f->original; f = f->original) ;
00929                         newface->original = f;
00930                         //store the new winding
00931                         if (newface->face_winding) Winding_Free(newface->face_winding);
00932                         newface->face_winding = Winding_Clone(&tmpw);
00933                         //get the texture
00934                         newface->d_texture = Texture_ForName( newface->texdef.name );
00935                         //add the face to the brush
00936                         newface->next = b->brush_faces;
00937                         b->brush_faces = newface;
00938                         //add this new triangle to the move faces
00939                         movefacepoints[nummovefaces] = 0;
00940                         movefaces[nummovefaces++] = newface;
00941                     }
00942                     //give the original face a new winding
00943                     VectorCopy(w->points[(i-2+w->numpoints) % w->numpoints], tmpw.points[0]);
00944                     VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[1]);
00945                     VectorCopy(w->points[i], tmpw.points[2]);
00946                     Winding_Free(face->face_winding);
00947                     face->face_winding = Winding_Clone(&tmpw);
00948                     //add the original face to the move faces
00949                     movefacepoints[nummovefaces] = 2;
00950                     movefaces[nummovefaces++] = face;
00951                 }
00952                 else
00953                 {
00954                     //chop a triangle off the face
00955                     VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[0]);
00956                     VectorCopy(w->points[i], tmpw.points[1]);
00957                     VectorCopy(w->points[(i+1) % w->numpoints], tmpw.points[2]);
00958                     //remove the point from the face winding
00959                     Winding_RemovePoint(w, i);
00960                     //get texture crap right
00961                     Face_SetColor(b, face, 1.0);
00962                     for (j = 0; j < w->numpoints; j++)
00963                         EmitTextureCoordinates(w->points[j], face->d_texture, face);
00964                     //make a triangle face
00965                     newface = Face_Clone(face);
00966                     //get the original
00967                     for (f = face; f->original; f = f->original) ;
00968                     newface->original = f;
00969                     //store the new winding
00970                     if (newface->face_winding) Winding_Free(newface->face_winding);
00971                     newface->face_winding = Winding_Clone(&tmpw);
00972                     //get the texture
00973                     newface->d_texture = Texture_ForName( newface->texdef.name );
00974                     //add the face to the brush
00975                     newface->next = b->brush_faces;
00976                     b->brush_faces = newface;
00977                     //
00978                     movefacepoints[nummovefaces] = 1;
00979                     movefaces[nummovefaces++] = newface;
00980                 }
00981                 break;
00982             }
00983         }
00984     }
00985     //now movefaces contains pointers to triangle faces that
00986     //contain the to be moved vertex
00987 
00988     //check if the move is valid
00989     int l;
00990     vec3_t p1, p2;
00991     winding_t *w2;
00992     plane_t plane;
00993 
00994     face = NULL;
00995     VectorCopy(vertex, tmpw.points[1]);
00996     VectorCopy(end, tmpw.points[2]);
00997     for (face = b->brush_faces; face; face = face->next)
00998     {
00999         for (i = 0; i < nummovefaces; i++)
01000         {
01001             if (face == movefaces[i])
01002                 break;
01003         }
01004         if (i < nummovefaces)
01005             continue;
01006         //the delta vector may not intersect with any of the not move faces
01007         if (Winding_VectorIntersect(face->face_winding, &face->plane, vertex, end, INTERSECT_EPSILON))
01008             break;
01009         //if the end point of the to be moved vertex is near this not move face
01010         if (abs(DotProduct(face->plane.normal, end) - face->plane.dist) < 0.5)
01011         {
01012             //the end point may not be inside or very close to the not move face winding
01013             if (Winding_PointInside(face->face_winding, &face->plane, end, 0.5))
01014                 break;
01015         }
01016         for (i = 0; i < nummovefaces; i++)
01017         {
01018             w = movefaces[i]->face_winding;
01019             j = movefacepoints[i];
01020             for (k = -1; k <= 1; k += 2)
01021             {
01022                 //check if the new edge will not intersect with the not move face
01023                 VectorCopy(w->points[(j + k + w->numpoints) % w->numpoints], tmpw.points[0]);
01024                 if (Winding_VectorIntersect(face->face_winding, &face->plane, tmpw.points[0], end, INTERSECT_EPSILON))
01025                 {
01026                     //ok the new edge instersects with the not move face
01027                     //we can't perform the vertex movement
01028                     //break;
01029                 }
01030                 //check if the not move face intersects the "movement winding"
01031                 Winding_Plane(&tmpw, plane.normal, &plane.dist);
01032                 w2 = face->face_winding;
01033                 for (l = 0; l < w2->numpoints; l++)
01034                 {
01035                     VectorCopy(w2->points[l], p1);
01036                     if (Point_Equal(p1, tmpw.points[0], POINT_EPSILON)) continue;
01037                     VectorCopy(w2->points[(l+1) % w2->numpoints], p2);
01038                     if (Point_Equal(p2, tmpw.points[0], POINT_EPSILON)) continue;
01039                     if (Winding_VectorIntersect(&tmpw, &plane, p1, p2, INTERSECT_EPSILON))
01040                         break;
01041                 }
01042                 if (l < w2->numpoints)
01043                 {
01044                     //ok this not move face intersects the "movement winding"
01045                     //we can't perform the vertex movement
01046                     break;
01047                 }
01048             }
01049             if (k <= 1) break;
01050         }
01051         if (i < nummovefaces)
01052             break;
01053     }
01054     if (!face)
01055     {
01056         //ok the move was valid
01057         //now move all the vertexes of the movefaces
01058         for (i = 0; i < nummovefaces; i++)
01059         {
01060             VectorCopy(end, movefaces[i]->face_winding->points[movefacepoints[i]]);
01061             //create new face plane
01062             for (j = 0; j < 3; j++)
01063             {
01064                 VectorCopy(movefaces[i]->face_winding->points[j], movefaces[i]->planepts[j]);
01065             }
01066             Face_MakePlane(movefaces[i]);
01067         }
01068         result = true;
01069     }
01070     //get texture crap right
01071     for (i = 0; i < nummovefaces; i++)
01072     {
01073         Face_SetColor(b, movefaces[i], 1.0);
01074         for (j = 0; j < movefaces[i]->face_winding->numpoints; j++)
01075             EmitTextureCoordinates(movefaces[i]->face_winding->points[j], movefaces[i]->d_texture, movefaces[i]);
01076     }
01077 
01078     //now try to merge faces with their original faces
01079     lastface = NULL;
01080     for (face = b->brush_faces; face; face = nextface)
01081     {
01082         nextface = face->next;
01083         if (!face->original)
01084         {
01085             lastface = face;
01086             continue;
01087         }
01088         if (!Plane_Equal(&face->plane, &face->original->plane, false))
01089         {
01090             lastface = face;
01091             continue;
01092         }
01093         w = Winding_TryMerge(face->face_winding, face->original->face_winding, face->plane.normal, true);
01094         if (!w)
01095         {
01096             lastface = face;
01097             continue;
01098         }
01099         Winding_Free(face->original->face_winding);
01100         face->original->face_winding = w;
01101         //get texture crap right
01102         Face_SetColor(b, face->original, 1.0);
01103         for (j = 0; j < face->original->face_winding->numpoints; j++)
01104             EmitTextureCoordinates(face->original->face_winding->points[j], face->original->d_texture, face->original);
01105         //remove the face that was merged with the original
01106         if (lastface) lastface->next = face->next;
01107         else b->brush_faces = face->next;
01108         Face_Free(face);
01109     }
01110     return result;
01111 }

Here is the call graph for this function:

int Brush_MoveVertex_old2 brush_t b,
vec3_t  vertex,
vec3_t  delta,
vec3_t  end,
bool  bSnap
 

Definition at line 1128 of file Brush.cpp.

References b, brush_t, face_t, g_qeglobals, VectorAdd, and w.

01129 {
01130     face_t *f, *face, *newface, *lastface, *nextface;
01131     face_t *movefaces[MAX_MOVE_FACES];
01132     int movefacepoints[MAX_MOVE_FACES];
01133     winding_t *w, tmpw;
01134     int i, j, k, nummovefaces, result;
01135     float dot;
01136 
01137     result = true;
01138     //
01139     tmpw.numpoints = 3;
01140     tmpw.maxpoints = 3;
01141     VectorAdd(vertex, delta, end);
01142     //snap or not?
01143     if (bSnap)
01144         for (i = 0; i < 3; i++)
01145             end[i] = floor(end[i] / g_qeglobals.d_gridsize + 0.5) * g_qeglobals.d_gridsize;
01146     //chop off triangles from all brush faces that use the to be moved vertex
01147     //store pointers to these chopped off triangles in movefaces[]
01148     nummovefaces = 0;
01149     for (face = b->brush_faces; face; face = face->next)
01150     {
01151         w = face->face_winding;
01152         if (!w) continue;
01153         for (i = 0; i < w->numpoints; i++)
01154         {
01155             if (Point_Equal(w->points[i], vertex, POINT_EPSILON))
01156             {
01157                 if (face->face_winding->numpoints <= 3)
01158                 {
01159                     movefacepoints[nummovefaces] = i;
01160                     movefaces[nummovefaces++] = face;
01161                     break;
01162                 }
01163                 dot = DotProduct(end, face->plane.normal) - face->plane.dist;
01164                 //if the end point is in front of the face plane
01165                 if (dot > 0.1)
01166                 {
01167                     //fanout triangle subdivision
01168                     for (k = i; k < i + w->numpoints-3; k++)
01169                     {
01170                         VectorCopy(w->points[i], tmpw.points[0]);
01171                         VectorCopy(w->points[(k+1) % w->numpoints], tmpw.points[1]);
01172                         VectorCopy(w->points[(k+2) % w->numpoints], tmpw.points[2]);
01173                         //
01174                         newface = Face_Clone(face);
01175                         //get the original
01176                         for (f = face; f->original; f = f->original) ;
01177                         newface->original = f;
01178                         //store the new winding
01179                         if (newface->face_winding) Winding_Free(newface->face_winding);
01180                         newface->face_winding = Winding_Clone(&tmpw);
01181                         //get the texture
01182                         newface->d_texture = Texture_ForName( newface->texdef.name );
01183                         //add the face to the brush
01184                         newface->next = b->brush_faces;
01185                         b->brush_faces = newface;
01186                         //add this new triangle to the move faces
01187                         movefacepoints[nummovefaces] = 0;
01188                         movefaces[nummovefaces++] = newface;
01189                     }
01190                     //give the original face a new winding
01191                     VectorCopy(w->points[(i-2+w->numpoints) % w->numpoints], tmpw.points[0]);
01192                     VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[1]);
01193                     VectorCopy(w->points[i], tmpw.points[2]);
01194                     Winding_Free(face->face_winding);
01195                     face->face_winding = Winding_Clone(&tmpw);
01196                     //add the original face to the move faces
01197                     movefacepoints[nummovefaces] = 2;
01198                     movefaces[nummovefaces++] = face;
01199                 }
01200                 else
01201                 {
01202                     //chop a triangle off the face
01203                     VectorCopy(w->points[(i-1+w->numpoints) % w->numpoints], tmpw.points[0]);
01204                     VectorCopy(w->points[i], tmpw.points[1]);
01205                     VectorCopy(w->points[(i+1) % w->numpoints], tmpw.points[2]);
01206                     //remove the point from the face winding
01207                     Winding_RemovePoint(w, i);
01208                     //get texture crap right
01209                     Face_SetColor(b, face, 1.0);
01210                     for (j = 0; j < w->numpoints; j++)
01211                         EmitTextureCoordinates(w->points[j], face->d_texture, face);
01212                     //make a triangle face
01213                     newface = Face_Clone(face);
01214                     //get the original
01215                     for (f = face; f->original; f = f->original) ;
01216                     newface->original = f;
01217                     //store the new winding
01218                     if (newface->face_winding) Winding_Free(newface->face_winding);
01219                     newface->face_winding = Winding_Clone(&tmpw);
01220                     //get the texture
01221                     newface->d_texture = Texture_ForName( newface->texdef.name );
01222                     //add the face to the brush
01223                     newface->next = b->brush_faces;
01224                     b->brush_faces = newface;
01225                     //
01226                     movefacepoints[nummovefaces] = 1;
01227                     movefaces[nummovefaces++] = newface;
01228                 }
01229                 break;
01230             }
01231         }
01232     }
01233     //now movefaces contains pointers to triangle faces that
01234     //contain the to be moved vertex
01235 
01236     //move the vertex
01237     for (i = 0; i < nummovefaces; i++)
01238     {
01239         //move vertex to end position
01240         VectorCopy(end, movefaces[i]->face_winding->points[movefacepoints[i]]);
01241         //create new face plane
01242         for (j = 0; j < 3; j++)
01243         {
01244             VectorCopy(movefaces[i]->face_winding->points[j], movefaces[i]->planepts[j]);
01245         }
01246         Face_MakePlane(movefaces[i]);
01247     }
01248     //if the brush is no longer convex
01249     if (!Brush_Convex(b))
01250     {
01251         for (i = 0; i < nummovefaces; i++)
01252         {
01253             //move the vertex back to the initial position
01254             VectorCopy(vertex, movefaces[i]->face_winding->points[movefacepoints[i]]);
01255             //create new face plane
01256             for (j = 0; j < 3; j++)
01257             {
01258                 VectorCopy(movefaces[i]->face_winding->points[j], movefaces[i]->planepts[j]);
01259             }
01260             Face_MakePlane(movefaces[i]);
01261         }
01262         result = false;
01263     }
01264     //get texture crap right
01265     for (i = 0; i < nummovefaces; i++)
01266     {
01267         Face_SetColor(b, movefaces[i], 1.0);
01268         for (j = 0; j < movefaces[i]->face_winding->numpoints; j++)
01269             EmitTextureCoordinates(movefaces[i]->face_winding->points[j], movefaces[i]->d_texture, movefaces[i]);
01270     }
01271 
01272     //now try to merge faces with their original faces
01273     lastface = NULL;
01274     for (face = b->brush_faces; face; face = nextface)
01275     {
01276         nextface = face->next;
01277         if (!face->original)
01278         {
01279             lastface = face;
01280             continue;
01281         }
01282         if (!Plane_Equal(&face->plane, &face->original->plane, false))
01283         {
01284             lastface = face;
01285             continue;
01286         }
01287         w = Winding_TryMerge(face->face_winding, face->original->face_winding, face->plane.normal, true);
01288         if (!w)
01289         {
01290             lastface = face;
01291             continue;
01292         }
01293         Winding_Free(face->original->face_winding);
01294         face->original->face_winding = w;
01295         //get texture crap right
01296         Face_SetColor(b, face->original, 1.0);
01297         for (j = 0; j < face->original->face_winding->numpoints; j++)
01298             EmitTextureCoordinates(face->original->face_winding->points[j], face->original->d_texture, face->original);
01299         //remove the face that was merged with the original
01300         if (lastface) lastface->next = face->next;
01301         else b->brush_faces = face->next;
01302         Face_Free(face);
01303     }
01304     return result;
01305 }

const char* Brush_Name brush_t b  ) 
 

Definition at line 34 of file Brush.cpp.

References b, Brush_SetEpair(), brush_t, g_nBrushId, g_qeglobals, QEGlobals_t::m_bBrushPrimitMode, brush_s::numberId, and sprintf().

00035 {
00036   static char cBuff[1024];
00037     b->numberId = g_nBrushId++;
00038     if (g_qeglobals.m_bBrushPrimitMode)
00039   {
00040     sprintf(cBuff, "Brush %i", b->numberId);
00041     Brush_SetEpair(b, "Name", cBuff);
00042   }
00043   return cBuff;
00044 }

Here is the call graph for this function:

brush_t* Brush_Parse void   ) 
 

Definition at line 1666 of file Brush.cpp.

References atof(), atoi, b, QEGlobals_t::bNeedConvert, QEGlobals_t::bOldBrushes, QEGlobals_t::bPrimitBrushes, Brush_Alloc(), brush_s::brush_faces, brush_t, BrushPrimit_Parse(), QEGlobals_t::bSurfacePropertiesPlugin, texdef_t::contents, qtexture_s::contents, QEGlobals_t::d_parsed_brushes, face_s::d_texture, f, Face_Alloc(), face_t, texdef_t::flags, qtexture_s::flags, free(), g_qeglobals, GETPLUGINTEXDEF, GetToken(), i, j, QEGlobals_t::m_bBrushPrimitMode, texdef_t::name, face_s::next, Patch_Parse(), face_s::planepts, texdef_t::rotate, texdef_t::scale, texdef_t::SetName(), texdef_t::shift, strcmp(), Sys_Printf(), Terrain_Parse(), face_s::texdef, Texture_ForName(), TokenAvailable(), texdef_t::value, qtexture_s::value, and Warning().

Referenced by Entity_Parse().

01667 {
01668     brush_t     *b;
01669     face_t      *f;
01670     int         i,j;
01671     
01672     g_qeglobals.d_parsed_brushes++;
01673     b = Brush_Alloc();
01674 
01675     do
01676     {
01677         if (!GetToken (true))
01678             break;
01679         if (!strcmp (token, "}") )
01680             break;
01681         
01682         // handle "Brush" primitive
01683         if (strcmpi(token, "brushDef") == 0)
01684         {
01685             // Timo parsing new brush format
01686             g_qeglobals.bPrimitBrushes=true;
01687             // check the map is not mixing the two kinds of brushes
01688             if (g_qeglobals.m_bBrushPrimitMode)
01689             {
01690                 if (g_qeglobals.bOldBrushes)
01691                     Sys_Printf("Warning : old brushes and brush primitive in the same file are not allowed ( Brush_Parse )\n");
01692             }
01693             //++Timo write new brush primitive -> old conversion code for Q3->Q2 conversions ?
01694             else
01695                 Sys_Printf("Warning : conversion code from brush primitive not done ( Brush_Parse )\n");
01696             
01697             BrushPrimit_Parse(b);
01698             if (b == NULL)
01699             {
01700                 Warning ("parsing brush primitive");
01701                 return NULL;
01702             }
01703             else
01704             {
01705                 continue;
01706             }
01707         }
01708         if ( strcmpi( token, "terrainDef" ) == 0 )
01709         {
01710             free (b);
01711 
01712             b = Terrain_Parse();
01713             if (b == NULL)
01714             {
01715                 Warning ("parsing terrain/brush");
01716                 return NULL;
01717             }
01718             else
01719             {
01720                 continue;
01721             }
01722         }
01723         if (strcmpi(token, "patchDef2") == 0 || strcmpi(token, "patchDef3") == 0)
01724         {
01725             free (b);
01726             
01727             // double string compare but will go away soon
01728             b = Patch_Parse(strcmpi(token, "patchDef2") == 0);
01729             if (b == NULL)
01730             {
01731                 Warning ("parsing patch/brush");
01732                 return NULL;
01733             }
01734             else
01735             {
01736                 continue;
01737             }
01738             // handle inline patch
01739         }
01740         else
01741         {
01742             // Timo parsing old brush format
01743             g_qeglobals.bOldBrushes=true;
01744             if (g_qeglobals.m_bBrushPrimitMode)
01745             {
01746                 // check the map is not mixing the two kinds of brushes
01747                 if (g_qeglobals.bPrimitBrushes)
01748                     Sys_Printf("Warning : old brushes and brush primitive in the same file are not allowed ( Brush_Parse )\n");
01749                 // set the "need" conversion flag
01750                 g_qeglobals.bNeedConvert=true;
01751             }
01752             
01753             f = Face_Alloc();
01754             
01755             // add the brush to the end of the chain, so
01756             // loading and saving a map doesn't reverse the order
01757             
01758             f->next = NULL;
01759             if (!b->brush_faces)
01760             {
01761                 b->brush_faces = f;
01762             }
01763             else
01764             {
01765                 face_t *scan;
01766                 for (scan=b->brush_faces ; scan->next ; scan=scan->next)
01767                     ;
01768                 scan->next = f;
01769             }
01770             
01771             // read the three point plane definition
01772             for (i=0 ; i<3 ; i++)
01773             {
01774                 if (i != 0)
01775                     GetToken (true);
01776                 if (strcmp (token, "(") )
01777                 {
01778                     Warning ("parsing brush");
01779                     return NULL;
01780                 }
01781                 
01782                 for (j=0 ; j<3 ; j++)
01783                 {
01784                     GetToken (false);
01785                     f->planepts[i][j] = atof(token);
01786                 }
01787                 
01788                 GetToken (false);
01789                 if (strcmp (token, ")") )
01790                 {
01791                     Warning ("parsing brush");
01792                     return NULL;
01793                 }
01794             }
01795         }
01796 
01797         // Timo
01798         // if we have a surface plugin, we'll call the plugin parsing
01799         if (g_qeglobals.bSurfacePropertiesPlugin)
01800         {
01801             GETPLUGINTEXDEF(f)->ParseTexdef();
01802         }
01803         else
01804         {
01805             
01806             // read the texturedef
01807             GetToken (false);
01808             f->texdef.SetName(token);
01809             if (token[0] == '(')
01810             {
01811                 int i = 32;
01812             }
01813             GetToken (false);
01814             f->texdef.shift[0] = atoi(token);
01815             GetToken (false);
01816             f->texdef.shift[1] = atoi(token);
01817             GetToken (false);
01818             f->texdef.rotate = atoi(token); 
01819             GetToken (false);
01820             f->texdef.scale[0] = atof(token);
01821             GetToken (false);
01822             f->texdef.scale[1] = atof(token);
01823                         
01824             // the flags and value field aren't necessarily present
01825             f->d_texture = Texture_ForName( f->texdef.name );
01826             f->texdef.flags = f->d_texture->flags;
01827             f->texdef.value = f->d_texture->value;
01828             f->texdef.contents = f->d_texture->contents;
01829             
01830             if (TokenAvailable ())
01831             {
01832                 GetToken (false);
01833                 f->texdef.contents = atoi(token);
01834                 GetToken (false);
01835                 f->texdef.flags = atoi(token);
01836                 GetToken (false);
01837                 f->texdef.value = atoi(token);
01838             }
01839             
01840         }
01841     } while (1);
01842     
01843     return b;
01844 }

Here is the call graph for this function:

face_t* Brush_Point vec3_t  origin,
brush_t b
 

Definition at line 2788 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, plane_t::dist, DotProduct, f, face_t, face_s::next, plane_t::normal, and face_s::plane.

02789 {
02790     face_t  *f;
02791     float   d1;
02792 
02793     for (f=b->brush_faces ; f ; f=f->next)
02794     {
02795         d1 = DotProduct (origin, f->plane.normal) - f->plane.dist;
02796         if (d1 > 0)
02797         {
02798             return NULL;    // point is on front side of face
02799         }
02800     }
02801 
02802     return b->brush_faces;
02803 }

void Brush_Print brush_t b  ) 
 

Definition at line 4269 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, f, face_t, face_s::next, face_s::planepts, and Sys_Printf().

Referenced by CMainFrame::OnSelectionPrint().

04270 {
04271   int nFace = 0;
04272   for (face_t* f = b->brush_faces ; f ; f=f->next)
04273   {
04274     Sys_Printf("Face %i\n", nFace++);
04275     Sys_Printf("%f %f %f\n", f->planepts[0][0], f->planepts[0][1], f->planepts[0][2]);
04276     Sys_Printf("%f %f %f\n", f->planepts[1][0], f->planepts[1][1], f->planepts[1][2]);
04277     Sys_Printf("%f %f %f\n", f->planepts[2][0], f->planepts[2][1], f->planepts[2][2]);
04278   }
04279  }

Here is the call graph for this function:

face_t* Brush_Ray vec3_t  origin,
vec3_t  dir,
brush_t b,
float *  dist
 

Definition at line 2741 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, plane_t::dist, DotProduct, f, face_t, i, face_s::next, plane_t::normal, p2, face_s::plane, vec3_t, VectorCopy, and VectorSubtract.

Referenced by CCamWnd::Cam_ChangeFloor(), Test_Ray(), and Z_Draw().

02742 {
02743     face_t  *f, *firstface;
02744     vec3_t  p1, p2;
02745     float   frac, d1, d2;
02746     int     i;
02747 
02748     VectorCopy (origin, p1);
02749     for (i=0 ; i<3 ; i++)
02750         p2[i] = p1[i] + dir[i]*16384;
02751 
02752     for (f=b->brush_faces ; f ; f=f->next)
02753     {
02754         d1 = DotProduct (p1, f->plane.normal) - f->plane.dist;
02755         d2 = DotProduct (p2, f->plane.normal) - f->plane.dist;
02756         if (d1 >= 0 && d2 >= 0)
02757         {
02758             *dist = 0;
02759             return NULL;    // ray is on front side of face
02760         }
02761         if (d1 <=0 && d2 <= 0)
02762             continue;
02763     // clip the ray to the plane
02764         frac = d1 / (d1 - d2);
02765         if (d1 > 0)
02766         {
02767             firstface = f;
02768             for (i=0 ; i<3 ; i++)
02769                 p1[i] = p1[i] + frac *(p2[i] - p1[i]);
02770         }
02771         else
02772         {
02773             for (i=0 ; i<3 ; i++)
02774                 p2[i] = p1[i] + frac *(p2[i] - p1[i]);
02775         }
02776     }
02777 
02778     // find distance p1 is along dir
02779     VectorSubtract (p1, origin, p1);
02780     d1 = DotProduct (p1, dir);
02781 
02782     *dist = d1;
02783 
02784     return firstface;
02785 }

void Brush_RemoveEmptyFaces brush_t b  ) 
 

Definition at line 3234 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, f, Face_Free(), face_t, face_s::face_winding, next, and face_s::next.

Referenced by Brush_SplitBrushByFace().

03235 {
03236     face_t  *f, *next;
03237 
03238     f = b->brush_faces;
03239     b->brush_faces = NULL;
03240 
03241     for ( ; f ; f=next)
03242     {
03243         next = f->next;
03244         if (!f->face_winding)
03245             Face_Free (f);
03246         else
03247         {
03248             f->next = b->brush_faces;
03249             b->brush_faces = f;
03250         }
03251 
03252     }
03253 }

Here is the call graph for this function:

void Brush_RemoveFromList brush_t b  ) 
 

Definition at line 2831 of file Brush.cpp.

References b, brush_t, Error(), brush_s::next, Patch_Deselect(), brush_s::patchBrush, brush_s::pPatch, brush_s::prev, brush_s::pTerrain, Terrain_Deselect(), and brush_s::terrainBrush.

Referenced by Brush_Clone(), Brush_CopyList(), Brush_Free(), Brush_FullClone(), Brush_Resize(), CSG_Merge(), CSG_Subtract(), Map_ApplyRegion(), Map_RegionOff(), CXYWnd::ProduceSplitLists(), Select_AllOfType(), Select_Brush(), Select_Clone(), Select_CompleteTall(), Select_Inside(), Select_PartialTall(), Select_Ray(), Select_Touching(), SelectBrush(), Undo_Redo(), and Undo_Undo().

02832 {
02833     if (!b->next || !b->prev)
02834         Error ("Brush_RemoveFromList: not linked");
02835     
02836     if (b->patchBrush)
02837     {
02838         Patch_Deselect(b->pPatch);
02839         //Patch_Deselect(b->nPatchID);
02840     }
02841     if (b->terrainBrush)
02842     {
02843         Terrain_Deselect(b->pTerrain);
02844     }
02845 
02846     b->next->prev = b->prev;
02847     b->prev->next = b->next;
02848     b->next = b->prev = NULL;
02849 }

Here is the call graph for this function:

void Brush_ResetFaceOriginals brush_t b  ) 
 

Definition at line 1647 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, face_t, face_s::next, and face_s::original.

Referenced by MoveSelection().

01648 {
01649     face_t *face;
01650 
01651     for (face = b->brush_faces; face; face = face->next)
01652     {
01653         face->original = NULL;
01654     }
01655 }

void Brush_Resize brush_t b,
vec3_t  vMin,
vec3_t  vMax
 

Definition at line 3300 of file Brush.cpp.

References b, Brush_Build(), Brush_Create(), brush_s::brush_faces, Brush_RemoveFromList(), brush_t, f, Face_Free(), face_t, free(), brush_s::next, face_s::next, next, and face_s::texdef.

Referenced by HasModel().

03301 {
03302   brush_t *b2 = Brush_Create(vMin, vMax, &b->brush_faces->texdef);
03303 
03304   face_t *next;
03305     for (face_t *f=b->brush_faces ; f ; f=next)
03306     {
03307         next = f->next;
03308         Face_Free( f );
03309     }
03310 
03311   b->brush_faces = b2->brush_faces;
03312 
03313     // unlink from active/selected list
03314     if (b2->next)
03315   Brush_RemoveFromList (b2);
03316   free(b2);
03317   Brush_Build(b, true);
03318 }

Here is the call graph for this function:

void Brush_Rotate brush_t b,
vec3_t  vAngle,
vec3_t  vOrigin,
bool  bBuild
 

Definition at line 3270 of file Brush.cpp.

References b, Brush_Build(), brush_s::brush_faces, brush_t, f, face_t, i, face_s::next, face_s::planepts, and VectorRotate().

Referenced by CPlugInManager::CommitEntityHandleToMap(), Entity_Parse(), and TrackMD3Angles().

03271 {
03272     for (face_t* f=b->brush_faces ; f ; f=f->next)
03273     {
03274         for (int i=0 ; i<3 ; i++)
03275         {
03276             VectorRotate(f->planepts[i], vAngle, vOrigin, f->planepts[i]);
03277         }
03278     }
03279     if (bBuild)
03280     {
03281         Brush_Build(b, false, false);
03282     }
03283 }

Here is the call graph for this function:

void Brush_SelectFaceForDragging brush_t b,
face_t f,
qboolean  shear
 

Definition at line 3006 of file Brush.cpp.

References AddPlanept(), b, brush_s::brush_faces, Brush_MakeFaceWinding(), brush_t, c, d, plane_t::dist, DotProduct, entity_s::eclass, f, f2(), fabs(), face_t, eclass_s::fixedsize, free(), i, brush_s::next, face_s::next, plane_t::normal, winding_t::numpoints, ON_EPSILON, brush_s::owner, face_s::plane, face_s::planepts, winding_t::points, selected_brushes, VectorCopy, and w.

Referenced by Brush_SideSelect(), and Drag_Setup().

03007 {
03008     int     i;
03009     face_t  *f2;
03010     winding_t   *w;
03011     float   d;
03012     brush_t *b2;
03013     int     c;
03014 
03015     if (b->owner->eclass->fixedsize)
03016         return;
03017 
03018     c = 0;
03019     for (i=0 ; i<3 ; i++)
03020         c += AddPlanept (f->planepts[i]);
03021     if (c == 0)
03022         return;     // allready completely added
03023 
03024     // select all points on this plane in all brushes the selection
03025     for (b2=selected_brushes.next ; b2 != &selected_brushes ; b2 = b2->next)
03026     {
03027         if (b2 == b)
03028             continue;
03029         for (f2=b2->brush_faces ; f2 ; f2=f2->next)
03030         {
03031             for (i=0 ; i<3 ; i++)
03032                 if (fabs(DotProduct(f2->planepts[i], f->plane.normal)
03033                 -f->plane.dist) > ON_EPSILON)
03034                     break;
03035             if (i==3)
03036             {   // move this face as well
03037                 Brush_SelectFaceForDragging (b2, f2, shear);
03038                 break;
03039             }
03040         }
03041     }
03042 
03043 
03044     // if shearing, take all the planes adjacent to 
03045     // selected faces and rotate their points so the
03046     // edge clipped by a selcted face has two of the points
03047     if (!shear)
03048         return;
03049 
03050     for (f2=b->brush_faces ; f2 ; f2=f2->next)
03051     {
03052         if (f2 == f)
03053             continue;
03054         w = Brush_MakeFaceWinding (b, f2);
03055         if (!w)
03056             continue;
03057 
03058         // any points on f will become new control points
03059         for (i=0 ; i<w->numpoints ; i++)
03060         {
03061             d = DotProduct (w->points[i], f->plane.normal) 
03062                 - f->plane.dist;
03063             if (d > -ON_EPSILON && d < ON_EPSILON)
03064                 break;
03065         }
03066 
03067         //
03068         // if none of the points were on the plane,
03069         // leave it alone
03070         //
03071         if (i != w->numpoints)
03072         {
03073             if (i == 0)
03074             {   // see if the first clockwise point was the
03075                 // last point on the winding
03076                 d = DotProduct (w->points[w->numpoints-1]
03077                     , f->plane.normal) - f->plane.dist;
03078                 if (d > -ON_EPSILON && d < ON_EPSILON)
03079                     i = w->numpoints - 1;
03080             }
03081 
03082             AddPlanept (f2->planepts[0]);
03083 
03084             VectorCopy (w->points[i], f2->planepts[0]);
03085             if (++i == w->numpoints)
03086                 i = 0;
03087             
03088             // see if the next point is also on the plane
03089             d = DotProduct (w->points[i]
03090                 , f->plane.normal) - f->plane.dist;
03091             if (d > -ON_EPSILON && d < ON_EPSILON)
03092                 AddPlanept (f2->planepts[1]);
03093 
03094             VectorCopy (w->points[i], f2->planepts[1]);
03095             if (++i == w->numpoints)
03096                 i = 0;
03097 
03098             // the third point is never on the plane
03099 
03100             VectorCopy (w->points[i], f2->planepts[2]);
03101         }
03102 
03103         free(w);
03104     }
03105 }

Here is the call graph for this function:

void Brush_SetEpair brush_t b,
const char *  pKey,
const char *  pValue
 

Definition at line 1874 of file Brush.cpp.

References b, brush_t, brush_s::epairs, g_qeglobals, QEGlobals_t::m_bBrushPrimitMode, Patch_SetEpair(), brush_s::patchBrush, brush_s::pPatch, brush_s::pTerrain, SetKeyValue(), Sys_Printf(), Terrain_SetEpair(), and brush_s::terrainBrush.

Referenced by Brush_Name(), Select_AddToGroup(), and Select_Name().

01875 {
01876     if (g_qeglobals.m_bBrushPrimitMode)
01877     {
01878     if (b->patchBrush)
01879     {
01880       Patch_SetEpair(b->pPatch, pKey, pValue);
01881     }
01882     else if (b->terrainBrush)
01883     {
01884       Terrain_SetEpair(b->pTerrain, pKey, pValue);
01885     }
01886     else
01887     {
01888           SetKeyValue(b->epairs, pKey, pValue);
01889     }
01890     }
01891     else
01892     {
01893         Sys_Printf("Can only set key/values in Brush primitive mode\n");
01894     }
01895 }

Here is the call graph for this function:

void Brush_SetTexture brush_t b,
texdef_t texdef,
brushprimit_texdef_t brushprimit_texdef,
bool  bFitScale,
IPluginTexdef pTexdef
 

Definition at line 2938 of file Brush.cpp.

References b, bFitScale, Brush_Build(), brush_s::brush_faces, brush_t, brushprimit_texdef, brushprimit_texdef_t, f, face_t, face_s::next, Patch_SetTexture(), brush_s::patchBrush, brush_s::pPatch, brush_s::pTerrain, SetFaceTexdef(), Terrain_SetTexture(), and brush_s::terrainBrush.

Referenced by Drag_Begin(), and Select_SetTexture().

02939 {
02940     for (face_t* f = b->brush_faces ; f ; f = f->next) 
02941     {
02942         SetFaceTexdef (b, f, texdef, brushprimit_texdef, bFitScale, pTexdef);
02943     }
02944     Brush_Build( b );
02945     if (b->patchBrush)
02946     {
02947         //++timo clean
02948 //      Sys_Printf("WARNING: Brush_SetTexture needs surface plugin code for patches\n");
02949         Patch_SetTexture(b->pPatch, texdef, pTexdef );
02950     }
02951     if (b->terrainBrush)
02952     {
02953         Terrain_SetTexture(b->pTerrain, texdef);
02954     }
02955 
02956 }

Here is the call graph for this function:

void Brush_SideSelect brush_t b,
vec3_t  origin,
vec3_t  dir,
qboolean  shear
 

Definition at line 3115 of file Brush.cpp.

References b, brush_s::brush_faces, Brush_SelectFaceForDragging(), brush_t, ClipLineToFace(), f, f2(), face_t, face_s::next, p2, vec3_t, VectorCompare(), VectorCopy, and VectorMA.

Referenced by Drag_Setup().

03117 {
03118     face_t  *f, *f2;
03119     vec3_t  p1, p2;
03120 
03121   //if (b->patchBrush)
03122   //  return;
03123     //Patch_SideSelect(b->nPatchID, origin, dir);
03124     for (f=b->brush_faces ; f ; f=f->next)
03125     {
03126         VectorCopy (origin, p1);
03127         VectorMA (origin, 16384, dir, p2);
03128 
03129         for (f2=b->brush_faces ; f2 ; f2=f2->next)
03130         {
03131             if (f2 == f)
03132                 continue;
03133             ClipLineToFace (p1, p2, f2);
03134         }
03135 
03136         if (f2)
03137             continue;
03138 
03139         if (VectorCompare (p1, origin))
03140             continue;
03141         if (ClipLineToFace (p1, p2, f))
03142             continue;
03143 
03144         Brush_SelectFaceForDragging (b, f, shear);
03145     }
03146 
03147     
03148 }

Here is the call graph for this function:

void Brush_SnapPlanepts brush_t b  ) 
 

Definition at line 620 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, f, face_t, floor(), g_PrefsDlg, i, j, CPrefsDlg::m_bNoClamp, face_s::next, and face_s::planepts.

Referenced by Brush_BuildWindings().

00621 {
00622     int     i, j;
00623     face_t  *f;
00624 
00625   if (g_PrefsDlg.m_bNoClamp)
00626     return;
00627 
00628     for (f=b->brush_faces ; f; f=f->next)
00629         for (i=0 ; i<3 ; i++)
00630             for (j=0 ; j<3 ; j++)
00631                 f->planepts[i][j] = floor (f->planepts[i][j] + 0.5);
00632 }

Here is the call graph for this function:

void Brush_SnapToGrid brush_t pb  ) 
 

Definition at line 3255 of file Brush.cpp.

References Brush_Build(), brush_s::brush_faces, brush_t, QEGlobals_t::d_gridsize, f, face_t, floor(), g_qeglobals, i, j, face_s::next, and face_s::planepts.

Referenced by Select_SnapToGrid().

03256 {
03257     for (face_t *f = pb->brush_faces ; f; f = f->next)
03258     {
03259         for (int i = 0 ;i < 3 ;i++)
03260         {
03261             for (int j = 0 ;j < 3 ; j++)
03262             {
03263                 f->planepts[i][j] = floor (f->planepts[i][j] / g_qeglobals.d_gridsize + 0.5) * g_qeglobals.d_gridsize;
03264             }
03265         }
03266     }
03267     Brush_Build(pb);
03268 }

Here is the call graph for this function:

void Brush_SplitBrushByFace brush_t in,
face_t f,
brush_t **  front,
brush_t **  back
 

Definition at line 692 of file Brush.cpp.

References b, Brush_Build(), Brush_Clone(), brush_s::brush_faces, Brush_Free(), Brush_RemoveEmptyFaces(), brush_t, Entity_LinkBrush(), f, Face_Clone(), face_t, in, face_s::next, brush_s::owner, face_s::planepts, face_s::texdef, vec3_t, and VectorCopy.

Referenced by Brush_MakeConvexBrushes(), Brush_Subtract(), CSG_MakeHollow(), CXYWnd::ProduceSplitLists(), and CXYWnd::ProduceSplits().

00693 {
00694     brush_t *b;
00695     face_t  *nf;
00696     vec3_t  temp;
00697 
00698     b = Brush_Clone (in);
00699     nf = Face_Clone (f);
00700 
00701     nf->texdef = b->brush_faces->texdef;
00702     nf->next = b->brush_faces;
00703     b->brush_faces = nf;
00704 
00705     Brush_Build( b );
00706     Brush_RemoveEmptyFaces ( b );
00707     if ( !b->brush_faces )
00708     {   // completely clipped away
00709         Brush_Free (b);
00710         *back = NULL;
00711     }
00712     else
00713     {
00714         Entity_LinkBrush (in->owner, b);
00715         *back = b;
00716     }
00717 
00718     b = Brush_Clone (in);
00719     nf = Face_Clone (f);
00720     // swap the plane winding
00721     VectorCopy (nf->planepts[0], temp);
00722     VectorCopy (nf->planepts[1], nf->planepts[0]);
00723     VectorCopy (temp, nf->planepts[1]);
00724 
00725     nf->texdef = b->brush_faces->texdef;
00726     nf->next = b->brush_faces;
00727     b->brush_faces = nf;
00728 
00729     Brush_Build( b );
00730     Brush_RemoveEmptyFaces ( b );
00731     if ( !b->brush_faces )
00732     {   // completely clipped away
00733         Brush_Free (b);
00734         *front = NULL;
00735     }
00736     else
00737     {
00738         Entity_LinkBrush (in->owner, b);
00739         *front = b;
00740     }
00741 }

Here is the call graph for this function:

void Brush_Write brush_t b,
CMemFile *  pMemFile
 

Definition at line 2077 of file Brush.cpp.

References b, brush_s::brush_faces, brush_t, face_s::brushprimit_texdef, QEGlobals_t::bSurfacePropertiesPlugin, texdef_t::contents, brushprimit_texdef_s::coords, epair_t, brush_s::epairs, face_t, texdef_t::flags, g_pMemFile, g_qeglobals, GETPLUGINTEXDEF, i, j, epair_s::key, QEGlobals_t::m_bBrushPrimitMode, MemFile_fprintf(), texdef_t::name, epair_s::next, face_s::next, Patch_Write(), brush_s::patchBrush, face_s::pData, face_s::planepts, pname, brush_s::pPatch, brush_s::pTerrain, QERApp_MapPrintf_MEMFILE(), texdef_t::rotate, texdef_t::scale, texdef_t::shift, strlen(), Sys_Printf(), Terrain_Write(), brush_s::terrainBrush, face_s::texdef, epair_s::value, and texdef_t::value.

Referenced by Entity_Write(), and Entity_WriteSelected().

02078 {
02079     epair_t *ep;
02080     face_t  *fa;
02081     char *pname;
02082     int     i;
02083     
02084     if (b->patchBrush)
02085     {
02086         Patch_Write(b->pPatch, pMemFile);
02087         return;
02088     }
02089     if (b->terrainBrush)
02090     {
02091         Terrain_Write(b->pTerrain, pMemFile);
02092         return;
02093     }
02094     //++timo NOTE: it's not very difficult to add since the surface properties plugin
02095     // writes throught a printf-style function prototype
02096     if (g_qeglobals.bSurfacePropertiesPlugin)
02097     {
02098         Sys_Printf("WARNING: Brush_Write to a CMemFile and Surface Properties plugin not done\n");
02099     }
02100     if (g_qeglobals.m_bBrushPrimitMode)
02101     {
02102         // brush primitive format
02103         MemFile_fprintf (pMemFile, "{\nBrushDef\n{\n");
02104         // brush epairs
02105         if (b->epairs)
02106             for( ep = b->epairs ; ep ; ep=ep->next )
02107                 MemFile_fprintf (pMemFile, "\"%s\" \"%s\"\n", ep->key, ep->value );
02108         for (fa=b->brush_faces ; fa ; fa=fa->next)
02109         {
02110             // save planepts
02111             for (i=0 ; i<3 ; i++)
02112             {
02113                 MemFile_fprintf(pMemFile, "( ");
02114                 for (int j = 0; j < 3; j++)
02115                     if (fa->planepts[i][j] == static_cast<int>(fa->planepts[i][j]))
02116                         MemFile_fprintf(pMemFile, "%i ", static_cast<int>(fa->planepts[i][j]));
02117                     else
02118                         MemFile_fprintf(pMemFile, "%f ", fa->planepts[i][j]);
02119                 MemFile_fprintf(pMemFile, ") ");
02120             }
02121             // save texture coordinates
02122             MemFile_fprintf(pMemFile,"( ( ");
02123             for (i=0 ; i<3 ; i++)
02124                 if (fa->brushprimit_texdef.coords[0][i] == static_cast<int>(fa->brushprimit_texdef.coords[0][i]))
02125                     MemFile_fprintf(pMemFile,"%i ",static_cast<int>(fa->brushprimit_texdef.coords[0][i]));
02126                 else
02127                     MemFile_fprintf(pMemFile,"%f ",fa->brushprimit_texdef.coords[0][i]);
02128             MemFile_fprintf(pMemFile,") ( ");
02129             for (i=0 ; i<3 ; i++)
02130                 if (fa->brushprimit_texdef.coords[1][i] == static_cast<int>(fa->brushprimit_texdef.coords[1][i]))
02131                     MemFile_fprintf(pMemFile,"%i ",static_cast<int>(fa->brushprimit_texdef.coords[1][i]));
02132                 else
02133                     MemFile_fprintf(pMemFile,"%f ",fa->brushprimit_texdef.coords[1][i]);
02134             MemFile_fprintf(pMemFile,") ) ");
02135             // save texture attribs
02136       char *pName = strlen(fa->texdef.name) > 0 ? fa->texdef.name : "unnamed";
02137             MemFile_fprintf(pMemFile, "%s ", pName);
02138             MemFile_fprintf(pMemFile, "%i %i %i\n", fa->texdef.contents, fa->texdef.flags, fa->texdef.value);
02139         }
02140         MemFile_fprintf (pMemFile, "}\n}\n");
02141     }
02142     else
02143     {
02144         // old brushes format
02145         // also handle surface properties plugin
02146         MemFile_fprintf (pMemFile, "{\n");
02147         for (fa=b->brush_faces ; fa ; fa=fa->next)
02148         {
02149             for (i=0 ; i<3 ; i++)
02150             {
02151                 MemFile_fprintf(pMemFile, "( ");
02152                 for (int j = 0; j < 3; j++)
02153                 {
02154                     if (fa->planepts[i][j] == static_cast<int>(fa->planepts[i][j]))
02155                         MemFile_fprintf(pMemFile, "%i ", static_cast<int>(fa->planepts[i][j]));
02156                     else
02157                         MemFile_fprintf(pMemFile, "%f ", fa->planepts[i][j]);
02158                 }
02159                 MemFile_fprintf(pMemFile, ") ");
02160             }
02161             
02162             if (g_qeglobals.bSurfacePropertiesPlugin)
02163             {
02164                 g_pMemFile = pMemFile;
02165 #ifdef _DEBUG
02166                 if (!fa->pData)
02167                     Sys_Printf("ERROR: unexpected IPluginTexdef* is NULL in Brush_Write\n");
02168                 else
02169 #endif
02170                 GETPLUGINTEXDEF(fa)->WriteTexdef( QERApp_MapPrintf_MEMFILE );
02171             }
02172             else
02173             {
02174                 pname = fa->texdef.name;
02175                 if (pname[0] == 0)
02176                     pname = "unnamed";
02177                 
02178                 MemFile_fprintf (pMemFile, "%s %i %i %i ", pname,
02179                     (int)fa->texdef.shift[0], (int)fa->texdef.shift[1],
02180                     (int)fa->texdef.rotate);
02181                 
02182                 if (fa->texdef.scale[0] == (int)fa->texdef.scale[0])
02183                     MemFile_fprintf (pMemFile, "%i ", (int)fa->texdef.scale[0]);
02184                 else
02185                     MemFile_fprintf (pMemFile, "%f ", (float)fa->texdef.scale[0]);
02186                 if (fa->texdef.scale[1] == (int)fa->texdef.scale[1])
02187                     MemFile_fprintf (pMemFile, "%i", (int)fa->texdef.scale[1]);
02188                 else
02189                     MemFile_fprintf (pMemFile, "%f", (float)fa->texdef.scale[1]);
02190                 
02191                 MemFile_fprintf (pMemFile, " %i %i %i", fa->texdef.contents, fa->texdef.flags, fa->texdef.value);
02192             }
02193             MemFile_fprintf (pMemFile, "\n");
02194         }
02195         MemFile_fprintf (pMemFile, "}\n");
02196     }
02197     
02198     
02199 }

Here is the call graph for this function:

void Brush_Write brush_t b,
FILE f
 

Definition at line 1932 of file Brush.cpp.

01933 {
01934     epair_t *ep;
01935     face_t  *fa;
01936     char    *pname;
01937     int     i;
01938     
01939     if (b->patchBrush)
01940     {
01941         Patch_Write(b->pPatch, f);
01942         return;
01943     }
01944     if ( b->pTerrain )
01945     {
01946         Terrain_Write(b->pTerrain, f);
01947         return;
01948     }
01949     if (g_qeglobals.m_bBrushPrimitMode)
01950     {
01951         // save brush primitive format
01952         fprintf (f, "{\nbrushDef\n{\n");
01953         // brush epairs
01954         if (b->epairs)
01955             for (ep = b->epairs ; ep ; ep=ep->next)
01956                 fprintf (f, "\"%s\" \"%s\"\n", ep->key, ep->value);
01957         for (fa=b->brush_faces ; fa ; fa=fa->next)
01958         {
01959             // save planepts
01960             for (i=0 ; i<3 ; i++)
01961             {
01962                 fprintf(f, "( ");
01963                 for (int j = 0; j < 3; j++)
01964                     if (fa->planepts[i][j] == static_cast<int>(fa->planepts[i][j]))
01965                         fprintf(f, "%i ", static_cast<int>(fa->planepts[i][j]));
01966                     else
01967                         fprintf(f, "%f ", fa->planepts[i][j]);
01968                 fprintf(f, ") ");
01969             }
01970             // save texture coordinates
01971             fprintf(f,"( ( ");
01972             for (i=0 ; i<3 ; i++)
01973                 if (fa->brushprimit_texdef.coords[0][i] == static_cast<int>(fa->brushprimit_texdef.coords[0][i]))
01974                     fprintf(f,"%i ",static_cast<int>(fa->brushprimit_texdef.coords[0][i]));
01975                 else
01976                     fprintf(f,"%f ",fa->brushprimit_texdef.coords[0][i]);
01977             fprintf(f,") ( ");
01978             for (i=0 ; i<3 ; i++)
01979                 if (fa->brushprimit_texdef.coords[1][i] == static_cast<int>(fa->brushprimit_texdef.coords[1][i]))
01980                     fprintf(f,"%i ",static_cast<int>(fa->brushprimit_texdef.coords[1][i]));
01981                 else
01982                     fprintf(f,"%f ",fa->brushprimit_texdef.coords[1][i]);
01983             fprintf(f,") ) ");
01984             // save texture attribs
01985             //++timo surface properties plugin not implemented for brush primitives
01986             if (g_qeglobals.bSurfacePropertiesPlugin)
01987                 Sys_Printf("WARNING: surface properties plugin not supported with brush primitives (yet)\n");
01988 
01989       char *pName = strlen(fa->texdef.name) > 0 ? fa->texdef.name : "unnamed";
01990             fprintf(f, "%s ", pName );
01991             fprintf(f, "%i %i %i\n", fa->texdef.contents, fa->texdef.flags, fa->texdef.value);
01992         }
01993         fprintf (f, "}\n}\n");
01994     }
01995     else
01996     {
01997         fprintf (f, "{\n");
01998         for (fa=b->brush_faces ; fa ; fa=fa->next)
01999         {
02000             for (i=0 ; i<3 ; i++)
02001             {
02002                 fprintf(f, "( ");
02003                 for (int j = 0; j < 3; j++)
02004                 {
02005                     if (fa->planepts[i][j] == static_cast<int>(fa->planepts[i][j]))
02006                         fprintf(f, "%i ", static_cast<int>(fa->planepts[i][j]));
02007                     else
02008                         fprintf(f, "%f ", fa->planepts[i][j]);
02009                 }
02010                 fprintf(f, ") ");
02011             }
02012             
02013             if (g_qeglobals.bSurfacePropertiesPlugin)
02014             {
02015                 g_File = f;
02016 #ifdef _DEBUG
02017                 if (!fa->pData)
02018                     Sys_Printf("ERROR: unexpected IPluginTexdef* is NULL in Brush_Write\n");
02019                 else
02020 #endif
02021                 GETPLUGINTEXDEF(fa)->WriteTexdef( QERApp_MapPrintf_FILE );
02022             }
02023             else
02024             {
02025                 pname = fa->texdef.name;
02026                 if (pname[0] == 0)
02027                     pname = "unnamed";
02028                 
02029                 fprintf (f, "%s %i %i %i ", pname,
02030                     (int)fa->texdef.shift[0], (int)fa->texdef.shift[1],
02031                     (int)fa->texdef.rotate);
02032                 
02033                 if (fa->texdef.scale[0] == (int)fa->texdef.scale[0])
02034                     fprintf (f, "%i ", (int)fa->texdef.scale[0]);
02035                 else
02036                     fprintf (f, "%f ", (float)fa->texdef.scale[0]);
02037                 if (fa->texdef.scale[1] == (int)fa->texdef.scale[1])
02038                     fprintf (f, "%i", (int)fa->texdef.scale[1]);
02039                 else
02040                     fprintf (f, "%f", (float)fa->texdef.scale[1]);
02041                 
02042                 fprintf (f, " %i %i %i", fa->texdef.contents, fa->texdef.flags, fa->texdef.value);
02043             }
02044             fprintf (f, "\n");
02045         }
02046         fprintf (f, "}\n");
02047     }
02048 }

void Clamp float &  f,
int  nClamp
 

Definition at line 257 of file Brush.cpp.

References f.

Referenced by AbsoluteToLocal(), and Face_MoveTexture().

00258 {
00259   float fFrac = f - static_cast<int>(f);
00260   f = static_cast<int>(f) % nClamp;
00261   f += fFrac;
00262 }

qboolean ClipLineToFace vec3_t  p1,
vec3_t  p2,
face_t f
 

Definition at line 2959 of file Brush.cpp.

References plane_t::dist, DotProduct, f, face_t, i, plane_t::normal, p2, face_s::plane, qboolean, and v.

Referenced by Brush_SideSelect().

02960 {
02961     float   d1, d2, fr;
02962     int     i;
02963     float   *v;
02964 
02965     d1 = DotProduct (p1, f->plane.normal) - f->plane.dist;
02966     d2 = DotProduct (p2, f->plane.normal) - f->plane.dist;
02967 
02968     if (d1 >= 0 && d2 >= 0)
02969         return false;       // totally outside
02970     if (d1 <= 0 && d2 <= 0)
02971         return true;        // totally inside
02972 
02973     fr = d1 / (d1 - d2);
02974 
02975     if (d1 > 0)
02976         v = p1;
02977     else
02978         v = p2;
02979 
02980     for (i=0 ; i<3 ; i++)
02981         v[i] = p1[i] + fr*(p2[i] - p1[i]);
02982 
02983     return true;
02984 }

void DrawBrushEntityName brush_t b  ) 
 

Definition at line 488 of file Brush.cpp.

References a, b, brush_t, entity_s::brushes, c, cos(), QEGlobals_t::d_savedinfo, SavedInfo_t::exclude, FloatForKey(), g_qeglobals, i, brush_s::maxs, brush_s::mins, name, brush_s::onext, brush_s::owner, Q_PI, qglBegin, qglCallLists, qglEnd, qglRasterPos3f, qglVertex3fv, s, SavedInfo_t::show_names, sin(), strlen(), and ValueForKey().

Referenced by Brush_DrawXY().

00489 {
00490     char    *name;
00491     //float a, s, c;
00492     //vec3_t    mid;
00493     //int       i;
00494 
00495     if (!b->owner)
00496         return;     // during contruction
00497 
00498     if (b->owner == world_entity)
00499         return;
00500 
00501     if (b != b->owner->brushes.onext)
00502         return; // not key brush
00503 
00504 // MERGEME
00505 #if 0
00506     if (!(g_qeglobals.d_savedinfo.exclude & EXCLUDE_ANGLES))
00507     {
00508         // draw the angle pointer
00509         a = FloatForKey (b->owner, "angle");
00510         if (a)
00511         {
00512             s = sin (a/180*Q_PI);
00513             c = cos (a/180*Q_PI);
00514             for (i=0 ; i<3 ; i++)
00515                 mid[i] = (b->mins[i] + b->maxs[i])*0.5; 
00516 
00517             qglBegin (GL_LINE_STRIP);
00518             qglVertex3fv (mid);
00519             mid[0] += c*8;
00520             mid[1] += s*8;
00521             mid[2] += s*8;
00522             qglVertex3fv (mid);
00523             mid[0] -= c*4;
00524             mid[1] -= s*4;
00525             mid[2] -= s*4;
00526             mid[0] -= s*4;
00527             mid[1] += c*4;
00528             mid[2] += c*4;
00529             qglVertex3fv (mid);
00530             mid[0] += c*4;
00531             mid[1] += s*4;
00532             mid[2] += s*4;
00533             mid[0] += s*4;
00534             mid[1] -= c*4;
00535             mid[2] -= c*4;
00536             qglVertex3fv (mid);
00537             mid[0] -= c*4;
00538             mid[1] -= s*4;
00539             mid[2] -= s*4;
00540             mid[0] += s*4;
00541             mid[1] -= c*4;
00542             mid[2] -= c*4;
00543             qglVertex3fv (mid);
00544             qglEnd ();
00545         }
00546     }
00547 #endif
00548 
00549     if (g_qeglobals.d_savedinfo.show_names)
00550     {
00551         name = ValueForKey (b->owner, "classname");
00552         qglRasterPos3f (b->mins[0]+4, b->mins[1]+4, b->mins[2]+4);
00553         qglCallLists (strlen(name), GL_UNSIGNED_BYTE, name);
00554     }
00555 }

Here is the call graph for this function:

void DrawLight brush_t b  ) 
 

Definition at line 3800 of file Brush.cpp.

References b, brush_t, GetVectorForKey(), i, brush_s::maxs, brush_s::mins, n, entity_s::origin, brush_s::owner, qglBegin, qglColor3f, qglEnd, qglVertex3fv, sscanf(), ValueForKey(), vec3_t, VectorAdd, VectorCopy, and VectorSubtract.

Referenced by Brush_Draw().

03801 {
03802     vec3_t vTriColor;
03803     bool bTriPaint = false;
03804 
03805   vTriColor[0] = vTriColor[2] = 1.0;
03806   vTriColor[1]  = 1.0;
03807   bTriPaint = true;
03808   CString strColor = ValueForKey(b->owner, "_color");
03809   if (strColor.GetLength() > 0)
03810   {
03811     float fR, fG, fB;
03812       int n = sscanf(strColor,"%f %f %f", &fR, &fG, &fB);
03813     if (n == 3)
03814     {
03815       vTriColor[0] = fR;
03816       vTriColor[1] = fG;
03817       vTriColor[2] = fB;
03818     }
03819   }
03820   qglColor3f(vTriColor[0], vTriColor[1], vTriColor[2]);
03821 
03822   vec3_t vCorners[4];
03823   float fMid = b->mins[2] + (b->maxs[2] - b->mins[2]) / 2;
03824 
03825   vCorners[0][0] = b->mins[0];
03826   vCorners[0][1] = b->mins[1];
03827   vCorners[0][2] = fMid;
03828 
03829   vCorners[1][0] = b->mins[0];
03830   vCorners[1][1] = b->maxs[1];
03831   vCorners[1][2] = fMid;
03832 
03833   vCorners[2][0] = b->maxs[0];
03834   vCorners[2][1] = b->maxs[1];
03835   vCorners[2][2] = fMid;
03836 
03837   vCorners[3][0] = b->maxs[0];
03838   vCorners[3][1] = b->mins[1];
03839   vCorners[3][2] = fMid;
03840 
03841   vec3_t vTop, vBottom;
03842 
03843   vTop[0] = b->mins[0] + ((b->maxs[0] - b->mins[0]) / 2);
03844   vTop[1] = b->mins[1] + ((b->maxs[1] - b->mins[1]) / 2);
03845   vTop[2] = b->maxs[2];
03846 
03847   VectorCopy(vTop, vBottom);
03848   vBottom[2] = b->mins[2];
03849 
03850   vec3_t vSave;
03851   VectorCopy(vTriColor, vSave);
03852 
03853   qglBegin(GL_TRIANGLE_FAN);
03854   qglVertex3fv(vTop);
03855   for (int i = 0; i <= 3; i++)
03856   {
03857     vTriColor[0] *= 0.95;
03858     vTriColor[1] *= 0.95;
03859     vTriColor[2] *= 0.95;
03860     qglColor3f(vTriColor[0], vTriColor[1], vTriColor[2]);
03861     qglVertex3fv(vCorners[i]);
03862   }
03863   qglVertex3fv(vCorners[0]);
03864   qglEnd();
03865   
03866   VectorCopy(vSave, vTriColor);
03867   vTriColor[0] *= 0.95;
03868   vTriColor[1] *= 0.95;
03869   vTriColor[2] *= 0.95;
03870 
03871   qglBegin(GL_TRIANGLE_FAN);
03872   qglVertex3fv(vBottom);
03873   qglVertex3fv(vCorners[0]);
03874   for (i = 3; i >= 0; i--)
03875   {
03876     vTriColor[0] *= 0.95;
03877     vTriColor[1] *= 0.95;
03878     vTriColor[2] *= 0.95;
03879     qglColor3f(vTriColor[0], vTriColor[1], vTriColor[2]);
03880     qglVertex3fv(vCorners[i]);
03881   }
03882   qglEnd();
03883 
03884   // check for DOOM lights
03885   CString str = ValueForKey(b->owner, "light_right");
03886   if (str.GetLength() > 0) {
03887     vec3_t vRight, vUp, vTarget, vTemp;
03888     GetVectorForKey (b->owner, "light_right", vRight);
03889     GetVectorForKey (b->owner, "light_up", vUp);
03890     GetVectorForKey (b->owner, "light_target", vTarget);
03891 
03892     qglColor3f(0, 1, 0);
03893         qglBegin(GL_LINE_LOOP);
03894     VectorAdd(vTarget, b->owner->origin, vTemp);
03895     VectorAdd(vTemp, vRight, vTemp);
03896     VectorAdd(vTemp, vUp, vTemp);
03897     qglVertex3fv(b->owner->origin);
03898     qglVertex3fv(vTemp);
03899     VectorAdd(vTarget, b->owner->origin, vTemp);
03900     VectorAdd(vTemp, vUp, vTemp);
03901     VectorSubtract(vTemp, vRight, vTemp);
03902     qglVertex3fv(b->owner->origin);
03903     qglVertex3fv(vTemp);
03904     VectorAdd(vTarget, b->owner->origin, vTemp);
03905     VectorAdd(vTemp, vRight, vTemp);
03906     VectorSubtract(vTemp, vUp, vTemp);
03907     qglVertex3fv(b->owner->origin);
03908     qglVertex3fv(vTemp);
03909     VectorAdd(vTarget, b->owner->origin, vTemp);
03910     VectorSubtract(vTemp, vUp, vTemp);
03911     VectorSubtract(vTemp, vRight, vTemp);
03912     qglVertex3fv(b->owner->origin);
03913     qglVertex3fv(vTemp);
03914     qglEnd();
03915 
03916   }
03917 
03918 }

Here is the call graph for this function:

void EmitTextureCoordinates float *  xyzst,
qtexture_t q,
face_t f
 

Definition at line 457 of file Brush.cpp.

References DotProduct, f, face_t, Face_TextureVectors(), and qtexture_t.

Referenced by Brush_BuildWindings(), Brush_FullClone(), FaceToBrushPrimitFace(), and Patch_CapTexture().

00458 {
00459     float   STfromXYZ[2][4];
00460 
00461     Face_TextureVectors (f,  STfromXYZ);
00462     xyzst[3] = DotProduct (xyzst, STfromXYZ[0]) + STfromXYZ[0][3];
00463     xyzst[4] = DotProduct (xyzst, STfromXYZ[1]) + STfromXYZ[1][3];
00464 }

Here is the call graph for this function:

face_t* Face_Alloc void   ) 
 

Definition at line 169 of file Brush.cpp.

References QEGlobals_t::bSurfacePropertiesPlugin, f, face_t, g_qeglobals, g_SurfaceTable, _QERPlugSurfaceTable::m_pfnTexdefAlloc, and qmalloc().

Referenced by CPlugInManager::AddFaceToBrushHandle(), Brush_Create(), Brush_CreatePyramid(), Brush_MakeSided(), Brush_MakeSidedCone(), Brush_MakeSidedSphere(), Brush_Merge(), Brush_MergeList(), Brush_Parse(), Brush_RebuildBrush(), BrushPrimit_Parse(), Face_Clone(), Face_FullClone(), and QERApp_AddFaceData().

00170 {
00171     face_t *f = (face_t*)qmalloc( sizeof( *f ) );
00172     
00173     if (g_qeglobals.bSurfacePropertiesPlugin)
00174         f->pData = static_cast<void *>( g_SurfaceTable.m_pfnTexdefAlloc( f ) );
00175 
00176     return f;
00177 }

Here is the call graph for this function:

face_t* Face_Clone face_t f  ) 
 

Definition at line 216 of file Brush.cpp.

References f, Face_Alloc(), face_t, memcpy(), n, face_s::planepts, and face_s::texdef.

Referenced by Brush_Clone(), and Brush_SplitBrushByFace().

00217 {
00218     face_t  *n;
00219 
00220     n = Face_Alloc();
00221     n->texdef = f->texdef;
00222 
00223     memcpy (n->planepts, f->planepts, sizeof(n->planepts));
00224 
00225     // all other fields are derived, and will be set by Brush_Build
00226     return n;
00227 }

Here is the call graph for this function:

void Face_Draw face_t f  ) 
 

Definition at line 4085 of file Brush.cpp.

References f, face_t, face_s::face_winding, i, winding_t::numpoints, winding_t::points, qglBegin, qglEnd, and qglVertex3fv.

Referenced by CCamWnd::Cam_Draw().

04086 {
04087     int i;
04088 
04089     if ( f->face_winding == 0 )
04090         return;
04091     qglBegin( GL_POLYGON );
04092     for ( i = 0 ; i < f->face_winding->numpoints; i++)
04093         qglVertex3fv( f->face_winding->points[i] );
04094     qglEnd();
04095 }

void Face_FitTexture face_t face,
int  nHeight,
int  nWidth
 

Definition at line 4475 of file Brush.cpp.

References AddPointToBounds(), ClearBounds(), cos(), face_s::d_texture, DotProduct, face_t, face_s::face_winding, height, qtexture_s::height, i, winding_t::numpoints, face_s::plane, winding_t::points, texdef_t::rotate, s, texdef_t::scale, texdef_t::shift, sin(), t, face_s::texdef, TextureAxisFromPlane(), vec3_t, vecs, w, width, and qtexture_s::width.

Referenced by Brush_FitTexture(), and Select_FitTexture().

04476 {
04477   winding_t *w;
04478   vec3_t   mins,maxs;
04479   int i;
04480   float width, height, temp;
04481   float rot_width, rot_height;
04482   float cosv,sinv,ang;
04483   float min_t, min_s, max_t, max_s;
04484   float s,t;
04485     vec3_t  vecs[2];
04486   vec3_t   coords[4];
04487     texdef_t    *td;
04488 
04489   if (nHeight < 1)
04490   {
04491     nHeight = 1;
04492   }
04493   if (nWidth < 1)
04494   {
04495     nWidth = 1;
04496   }
04497 
04498   ClearBounds (mins, maxs);
04499 
04500     td = &face->texdef;
04501     w = face->face_winding;
04502     if (!w)
04503     {
04504     return;
04505     }
04506   for (i=0 ; i<w->numpoints ; i++)
04507   {
04508     AddPointToBounds( w->points[i], mins, maxs );
04509   }
04510    // 
04511    // get the current angle
04512    //
04513     ang = td->rotate / 180 * Q_PI;
04514     sinv = sin(ang);
04515     cosv = cos(ang);
04516 
04517     // get natural texture axis
04518     TextureAxisFromPlane(&face->plane, vecs[0], vecs[1]);
04519 
04520   min_s = DotProduct( mins, vecs[0] );
04521   min_t = DotProduct( mins, vecs[1] );
04522   max_s = DotProduct( maxs, vecs[0] );
04523   max_t = DotProduct( maxs, vecs[1] );
04524   width = max_s - min_s;
04525   height = max_t - min_t;
04526   coords[0][0] = min_s;
04527   coords[0][1] = min_t;
04528   coords[1][0] = max_s;
04529   coords[1][1] = min_t;
04530   coords[2][0] = min_s;
04531   coords[2][1] = max_t;
04532   coords[3][0] = max_s;
04533   coords[3][1] = max_t;
04534   min_s = min_t = 99999;
04535   max_s = max_t = -99999;
04536   for (i=0; i<4; i++)
04537   {
04538     s = cosv * coords[i][0] - sinv * coords[i][1];
04539       t = sinv * coords[i][0] + cosv * coords[i][1];
04540     if (i&1)
04541     {
04542       if (s > max_s) 
04543       {
04544         max_s = s;
04545       }
04546     }
04547     else
04548     {
04549       if (s < min_s) 
04550       {
04551         min_s = s;
04552       }
04553       if (i<2)
04554       {
04555         if (t < min_t) 
04556         {
04557           min_t = t;
04558         }
04559       }
04560       else
04561       {
04562         if (t > max_t) 
04563         {
04564           max_t = t;
04565         }
04566       }
04567     }
04568   }
04569   rot_width =  (max_s - min_s);
04570   rot_height = (max_t - min_t);
04571   td->scale[0] = -(rot_width/((float)(face->d_texture->width*nWidth)));
04572   td->scale[1] = -(rot_height/((float)(face->d_texture->height*nHeight)));
04573 
04574   td->shift[0] = min_s/td->scale[0];
04575   temp = (int)(td->shift[0] / (face->d_texture->width*nWidth));
04576   temp = (temp+1)*face->d_texture->width*nWidth;
04577   td->shift[0] = (int)(temp - td->shift[0])%(face->d_texture->width*nWidth);
04578 
04579   td->shift[1] = min_t/td->scale[1];
04580   temp = (int)(td->shift[1] / (face->d_texture->height*nHeight));
04581   temp = (temp+1)*(face->d_texture->height*nHeight);
04582   td->shift[1] = (int)(temp - td->shift[1])%(face->d_texture->height*nHeight);
04583 }

Here is the call graph for this function:

void Face_Free face_t f  ) 
 

Definition at line 184 of file Brush.cpp.

References assert, QEGlobals_t::bSurfacePropertiesPlugin, f, face_t, face_s::face_winding, free(), g_qeglobals, GETPLUGINTEXDEF, face_s::pData, Sys_Printf(), face_s::texdef, and texdef_t::~texdef_t().

Referenced by Brush_Free(), Brush_RebuildBrush(), Brush_RemoveEmptyFaces(), Brush_Resize(), and QERApp_DeleteFace().

00185 {
00186     assert( f != 0 );
00187 
00188     if ( f->face_winding )
00189     {
00190         free( f->face_winding );
00191         f->face_winding = 0;
00192     }
00193 
00194     if (g_qeglobals.bSurfacePropertiesPlugin)
00195     {
00196 #ifdef _DEBUG
00197         if ( !f->pData )
00198         {
00199             Sys_Printf("WARNING: unexpected IPluginTexdef is NULL in Face_Free\n");
00200         }
00201         else
00202 #endif
00203         GETPLUGINTEXDEF(f)->DecRef();
00204     }
00205 
00206     f->texdef.~texdef_t();;
00207 
00208     free( f );
00209 }

Here is the call graph for this function:

face_t* Face_FullClone face_t f  ) 
 

Definition at line 236 of file Brush.cpp.

References face_s::d_texture, f, Face_Alloc(), face_t, face_s::face_winding, memcpy(), n, texdef_t::name, face_s::plane, face_s::planepts, face_s::texdef, Texture_ForName(), and Winding_Clone().

Referenced by Brush_FullClone().

00237 {
00238     face_t  *n;
00239 
00240     n = Face_Alloc();
00241     n->texdef = f->texdef;
00242     memcpy(n->planepts, f->planepts, sizeof(n->planepts));
00243     memcpy(&n->plane, &f->plane, sizeof(plane_t));
00244     if (f->face_winding)
00245         n->face_winding = Winding_Clone(f->face_winding);
00246     else
00247         n->face_winding = NULL;
00248     n->d_texture = Texture_ForName( n->texdef.name );
00249     return n;
00250 }

Here is the call graph for this function:

void Face_MakePlane face_t f  ) 
 

Definition at line 432 of file Brush.cpp.

References CrossProduct(), plane_t::dist, DotProduct, f, face_t, j, plane_t::normal, face_s::plane, face_s::planepts, printf(), vec3_origin, vec3_t, VectorCompare(), and VectorNormalize().

Referenced by Brush_MakeFacePlanes().

00433 {
00434     int     j;
00435     vec3_t  t1, t2, t3;
00436 
00437     // convert to a vector / dist plane
00438     for (j=0 ; j<3 ; j++)
00439     {
00440         t1[j] = f->planepts[0][j] - f->planepts[1][j];
00441         t2[j] = f->planepts[2][j] - f->planepts[1][j];
00442         t3[j] = f->planepts[1][j];
00443     }
00444     
00445     CrossProduct(t1,t2, f->plane.normal);
00446     if (VectorCompare (f->plane.normal, vec3_origin))
00447         printf ("WARNING: brush plane with no normal\n");
00448     VectorNormalize (f->plane.normal);
00449     f->plane.dist = DotProduct (t3, f->plane.normal);
00450 }

Here is the call graph for this function:

int Face_MemorySize face_t f  ) 
 

Definition at line 2562 of file Brush.cpp.

References f, face_t, and face_s::face_winding.

Referenced by Brush_MemorySize().

02563 {
02564     int size = 0;
02565 
02566     if (f->face_winding)
02567     {
02568         size += _msize(f->face_winding);
02569     }
02570     //f->texdef.~texdef_t();;
02571     size += _msize(f);
02572     return size;
02573 }

void Face_MoveTexture face_t f,
vec3_t  delta
 

Definition at line 269 of file Brush.cpp.

References c, Clamp(), cos(), face_s::d_texture, DotProduct, f, Face_MoveTexture_BrushPrimit(), face_t, g_qeglobals, qtexture_s::height, QEGlobals_t::m_bBrushPrimitMode, face_s::plane, texdef_t::rotate, s, texdef_t::scale, texdef_t::shift, sin(), face_s::texdef, TextureAxisFromPlane(), vec3_t, and qtexture_s::width.

Referenced by Brush_Move().

00270 {
00271     vec3_t vX, vY;
00272 /*
00273 #ifdef _DEBUG
00274     if (g_PrefsDlg.m_bBrushPrimitMode)
00275         Sys_Printf("Warning : Face_MoveTexture not done in brush primitive mode\n");
00276 #endif
00277 */
00278     if (g_qeglobals.m_bBrushPrimitMode)
00279         Face_MoveTexture_BrushPrimit( f, delta );
00280     else
00281     {
00282         TextureAxisFromPlane(&f->plane, vX, vY);
00283 
00284         vec3_t vDP, vShift;
00285         vDP[0] = DotProduct(delta, vX);
00286         vDP[1] = DotProduct(delta, vY);
00287 
00288         double fAngle = f->texdef.rotate  / 180 * Q_PI;
00289         double c = cos(fAngle);
00290         double s = sin(fAngle);
00291 
00292         vShift[0] = vDP[0] * c - vDP[1] * s;
00293         vShift[1] = vDP[0] * s + vDP[1] * c;
00294 
00295         if (!f->texdef.scale[0])
00296             f->texdef.scale[0] = 1;
00297         if (!f->texdef.scale[1])
00298             f->texdef.scale[1] = 1;
00299 
00300         f->texdef.shift[0] -= vShift[0] / f->texdef.scale[0];
00301         f->texdef.shift[1] -= vShift[1] / f->texdef.scale[1];
00302   
00303         // clamp the shifts
00304         Clamp(f->texdef.shift[0], f->d_texture->width);
00305         Clamp(f->texdef.shift[1], f->d_texture->height);
00306     }
00307 }

Here is the call graph for this function:

void Face_SetColor brush_t b,
face_t f,
float  fCurveColor
 

Definition at line 314 of file Brush.cpp.

References b, brush_t, CCamWnd::Camera(), cd_texture, qtexture_s::color, face_s::d_color, face_s::d_texture, camera_t::draw_mode, entity_s::eclass, f, face_t, eclass_s::fixedsize, g_pParentWnd, CMainFrame::GetCamera(), brush_s::owner, face_s::plane, q, qtexture_t, and SetShadeForPlane().

Referenced by Brush_BuildWindings(), and Brush_FullClone().

00315 {
00316     float   shade;
00317     qtexture_t *q;
00318 
00319     q = f->d_texture;
00320 
00321     // set shading for face
00322     shade = SetShadeForPlane (&f->plane);
00323     if (g_pParentWnd->GetCamera()->Camera().draw_mode == cd_texture && !b->owner->eclass->fixedsize)
00324     {
00325         //if (b->curveBrush)
00326         //  shade = fCurveColor;
00327         f->d_color[0] = 
00328         f->d_color[1] = 
00329         f->d_color[2] = shade;
00330     }
00331     else
00332     {
00333         f->d_color[0] = shade*q->color[0];
00334         f->d_color[1] = shade*q->color[1];
00335         f->d_color[2] = shade*q->color[2];
00336     }
00337 }

Here is the call graph for this function:

void Face_TextureVectors face_t f,
float  STfromXYZ[2][4]
 

Definition at line 345 of file Brush.cpp.

References QEGlobals_t::bNeedConvert, cos(), face_s::d_texture, f, face_t, g_PrefsDlg, g_qeglobals, qtexture_s::height, i, j, QEGlobals_t::m_bBrushPrimitMode, CPrefsDlg::m_bHiColorTextures, memset(), face_s::plane, q, qtexture_t, texdef_t::rotate, texdef_t::scale, texdef_t::shift, sin(), sv, Sys_Printf(), face_s::texdef, TextureAxisFromPlane(), tv(), vec3_t, and qtexture_s::width.

Referenced by EmitTextureCoordinates().

00346 {
00347     vec3_t      pvecs[2];
00348     int         sv, tv;
00349     float       ang, sinv, cosv;
00350     float       ns, nt;
00351     int         i,j;
00352     qtexture_t *q;
00353     texdef_t    *td;
00354 
00355 #ifdef _DEBUG
00356     //++timo when playing with patches, this sometimes get called and the Warning is displayed
00357     // find some way out ..
00358     if (g_qeglobals.m_bBrushPrimitMode && !g_qeglobals.bNeedConvert)
00359         Sys_Printf("Warning : illegal call of Face_TextureVectors in brush primitive mode\n");
00360 #endif
00361 
00362     td = &f->texdef;
00363     q = f->d_texture;
00364 
00365     memset (STfromXYZ, 0, 8*sizeof(float));
00366 
00367     if (!td->scale[0])
00368         td->scale[0] = (g_PrefsDlg.m_bHiColorTextures) ? 0.5 : 1;
00369     if (!td->scale[1])
00370         td->scale[1] = (g_PrefsDlg.m_bHiColorTextures) ? 0.5 : 1;
00371 
00372     // get natural texture axis
00373     TextureAxisFromPlane(&f->plane, pvecs[0], pvecs[1]);
00374 
00375     // rotate axis
00376     if (td->rotate == 0)
00377         { sinv = 0 ; cosv = 1; }
00378     else if (td->rotate == 90)
00379         { sinv = 1 ; cosv = 0; }
00380     else if (td->rotate == 180)
00381         { sinv = 0 ; cosv = -1; }
00382     else if (td->rotate == 270)
00383         { sinv = -1 ; cosv = 0; }
00384     else
00385     {   
00386         ang = td->rotate / 180 * Q_PI;
00387         sinv = sin(ang);
00388         cosv = cos(ang);
00389     }
00390 
00391     if (pvecs[0][0])
00392         sv = 0;
00393     else if (pvecs[0][1])
00394         sv = 1;
00395     else
00396         sv = 2;
00397                 
00398     if (pvecs[1][0])
00399         tv = 0;
00400     else if (pvecs[1][1])
00401         tv = 1;
00402     else
00403         tv = 2;
00404                     
00405     for (i=0 ; i<2 ; i++) {
00406         ns = cosv * pvecs[i][sv] - sinv * pvecs[i][tv];
00407         nt = sinv * pvecs[i][sv] +  cosv * pvecs[i][tv];
00408         STfromXYZ[i][sv] = ns;
00409         STfromXYZ[i][tv] = nt;
00410     }
00411 
00412     // scale
00413     for (i=0 ; i<2 ; i++)
00414         for (j=0 ; j<3 ; j++)
00415             STfromXYZ[i][j] = STfromXYZ[i][j] / td->scale[i];
00416 
00417     // shift
00418     STfromXYZ[0][3] = td->shift[0];
00419     STfromXYZ[1][3] = td->shift[1];
00420 
00421     for (j=0 ; j<4 ; j++) {
00422         STfromXYZ[0][j] /= q->width;
00423         STfromXYZ[1][j] /= q->height;
00424     }
00425 }

Here is the call graph for this function:

void FacingVectors entity_t e,
vec3_t  forward,
vec3_t  right,
vec3_t  up
 

Definition at line 3746 of file Brush.cpp.

References AngleVectors(), e, IntForKey(), right, up, vec3_t, and VectorSet.

Referenced by Brush_DrawFacingAngle().

03747 {
03748     int         angleVal;
03749     vec3_t      angles;
03750 
03751     angleVal = IntForKey(e, "angle");
03752     if (angleVal == -1)             // up
03753     {
03754         VectorSet(angles, 270, 0, 0);
03755     }
03756     else if(angleVal == -2)     // down
03757     {
03758         VectorSet(angles, 90, 0, 0);
03759     }
03760     else
03761     {
03762         VectorSet(angles, 0, angleVal, 0);
03763     }
03764 
03765     AngleVectors(angles, forward, right, up);
03766 }

Here is the call graph for this function:

eclass_t* HasModel brush_t b  ) 
 

Definition at line 3321 of file Brush.cpp.

References b, brush_s::bModelFailed, Brush_Resize(), brush_t, e, entity_s::eclass, Eclass_hasModel(), eclass_t, GetCachedModel(), entity_s::md3Class, eclass_s::nShowFlags, NULL, entity_s::origin, brush_s::owner, strlen(), ValueForKey(), vec3_t, and VectorAdd.

Referenced by PaintedModel().

03322 {
03323   vec3_t vMin, vMax;
03324   vMin[0] = vMin[1] = vMin[2] = 9999;
03325   vMax[0] = vMax[1] = vMax[2] = -9999;
03326 
03327   if (b->owner->md3Class != NULL)
03328   {
03329     return b->owner->md3Class;
03330   }
03331 
03332   if (Eclass_hasModel(b->owner->eclass, vMin, vMax))
03333   {
03334     return b->owner->eclass;
03335   }
03336 
03337   eclass_t *e = NULL;
03338   // FIXME: entity needs to track whether a cache hit failed and not ask again
03339   if (b->owner->eclass->nShowFlags & ECLASS_MISCMODEL)
03340   {
03341     char *pModel = ValueForKey(b->owner, "model");
03342     if (pModel != NULL && strlen(pModel) > 0)
03343     {
03344       e = GetCachedModel(b->owner, pModel, vMin, vMax);
03345       if (e != NULL)
03346       {
03347         // we need to scale the brush to the proper size based on the model load
03348         // recreate brush just like in load/save
03349 
03350             VectorAdd (vMin, b->owner->origin, vMin);
03351             VectorAdd (vMax, b->owner->origin, vMax);
03352 
03353         Brush_Resize(b, vMin, vMax);
03354 
03355 /*
03356         //
03357         vec3_t vTemp, vTemp2;
03358         VectorSubtract(b->maxs, b->mins, vTemp);
03359         VectorSubtract(vMax, vMin, vTemp2);
03360         for (int i = 0; i < 3; i++)
03361         {
03362           if (vTemp[i] != 0)
03363           {
03364             vTemp2[i] /= vTemp[i];
03365           }
03366         }
03367         vec3_t vMid, vMid2;
03368         vMid[0] = vMid[1] = vMid[2] = 0.0;
03369         vMid2[0] = vMid2[1] = vMid2[2] = 0.0;
03370 
03371         for (int j = 0; j < 3; j++)
03372         {
03373           vMid2[j] = b->mins[j] + abs((b->maxs[j] - b->mins[j]) * 0.5);
03374         }
03375 
03376         //VectorSubtract(vMid2, vMid, vMid2);
03377 
03378             for (face_t* f=b->brush_faces ; f ; f=f->next)
03379             {
03380                 for (int i=0 ; i<3 ; i++)
03381                 {
03382 
03383             // scale
03384             VectorSubtract(f->planepts[i], vMid2, f->planepts[i]);
03385             f->planepts[i][0] *= vTemp2[0];
03386             f->planepts[i][1] *= vTemp2[1];
03387             f->planepts[i][2] *= vTemp2[2];
03388             VectorAdd(f->planepts[i], vMid2, f->planepts[i]);
03389           }
03390         }
03391 
03392         //Brush_Center(b, b->owner->origin);
03393 
03394         //Brush_SnapToGrid(b);
03395 /*
03396         float a = FloatForKey (b->owner, "angle");
03397         if (a)
03398         {
03399           vec3_t vAngle;
03400           vAngle[0] = vAngle[1] = 0;
03401           vAngle[2] = a;
03402           Brush_Rotate(b, vAngle, b->owner->origin);
03403         }
03404         else
03405         {
03406           Brush_Build(b, true);
03407 */
03408 //        }
03409 
03410         b->bModelFailed = false;
03411       }
03412       else
03413       {
03414         b->bModelFailed = true;
03415       }
03416     } 
03417   }
03418   return e;
03419 }

Here is the call graph for this function:

bool PaintedModel brush_t b,
bool  bOkToTexture
 

Definition at line 3423 of file Brush.cpp.

References a, b, brush_s::bModelFailed, brush_t, c, eclass_s::color, cos(), eclass_t, ENTITY_BOX, ENTITY_WIREFRAME, entitymodel, FloatForKey(), g_bDoIt, g_bInPaintedModel, g_PrefsDlg, HasModel(), i, IsBrushSelected(), j, CPrefsDlg::m_nEntityShowState, brush_s::maxs, brush_s::mins, eclass_s::model, entitymodel_t::nTextureBind, entitymodel_t::nTriCount, entity_s::origin, brush_s::owner, Patch_FromTriangle(), entitymodel_t::pNext, entitymodel_t::pTriList, Q_PI, qglBegin, qglBindTexture, qglColor3f, qglColor3fv, qglDisable, qglEnable, qglEnd, qglPointSize, qglPolygonMode, qglPopAttrib, qglPushAttrib, qglTexCoord2f, qglVertex3f, qglVertex3fv, s, sin(), trimodel_t::st, trimodel_t::v, v, vec3_t, vec5_t, VectorAdd, VectorClear, VectorCopy, VectorScale, entity_s::vRotation, x, x2, y, y2, and z.

Referenced by Brush_Draw(), and Brush_DrawXY().

03424 {
03425     if (g_bInPaintedModel)
03426     { 
03427       return true;
03428     }
03429     
03430     if (g_PrefsDlg.m_nEntityShowState == ENTITY_BOX || b->bModelFailed)
03431     {
03432       return false;
03433     }
03434     else if (!IsBrushSelected(b) && (g_PrefsDlg.m_nEntityShowState & ENTITY_SELECTED_ONLY))
03435     {
03436         return false;
03437     }
03438 
03439     g_bInPaintedModel = true;
03440     bool bReturn = false;
03441 
03442     eclass_t *pEclass = HasModel(b);
03443 
03444     if (pEclass)
03445     {
03446       qglPushAttrib(GL_ALL_ATTRIB_BITS);
03447       entitymodel *model = pEclass->model;
03448 
03449 
03450       float a = FloatForKey (b->owner, "angle");
03451       while (model != NULL)
03452       {
03453         if (bOkToTexture == false || g_PrefsDlg.m_nEntityShowState & ENTITY_WIREFRAME || model->nTextureBind == -1) // skinned
03454         {
03455             qglDisable( GL_CULL_FACE );
03456             qglPolygonMode (GL_FRONT_AND_BACK, GL_LINE);
03457             qglDisable(GL_TEXTURE_2D);
03458           qglColor3fv(pEclass->color);
03459         }
03460         else
03461         {
03462           qglColor3f(1, 1, 1);
03463           qglEnable(GL_TEXTURE_2D);
03464             qglBindTexture( GL_TEXTURE_2D, model->nTextureBind );
03465         }
03466         vec3_t v;
03467         
03468         int i,j;
03469         VectorAdd(b->maxs, b->mins, v);
03470         VectorScale(v, 0.5, v);
03471         VectorCopy(b->owner->origin, v);
03472 
03473           
03474         //for (i = 0; i < 3; i++)
03475         //{
03476         //  v[i] -= (pEclass->mins[i] - b->mins[i]);
03477         //}
03478 
03479         //if (model->nModelPosition)
03480         //{
03481               //v[2] = b->mins[2] - (pEclass->mins[2]);
03482         //}
03483 
03484         float s, c;
03485           if (a)
03486         {
03487               s = sin (a/180*Q_PI);
03488               c = cos (a/180*Q_PI);
03489         }
03490 
03491         vec3_t vSin;
03492         vec3_t vCos;
03493         VectorClear(vSin);
03494         VectorClear(vCos);
03495         for ( j = 0; j < 3; j++)
03496         {
03497           if (b->owner->vRotation[j])
03498           {
03499             vSin[j] = sin(b->owner->vRotation[j]/180*Q_PI);
03500             vCos[j] = cos(b->owner->vRotation[j]/180*Q_PI);
03501           }
03502         }
03503 
03504 
03505           qglBegin (GL_TRIANGLES);
03506 
03507         vec5_t vTest[3];
03508         for (i = 0; i < model->nTriCount; i++)
03509         {
03510           for (j = 0; j < 3; j++)
03511           {
03512 #if 1
03513             float x = model->pTriList[i].v[j][0] + v[0];
03514             float y = model->pTriList[i].v[j][1] + v[1];
03515             if (a)
03516             {
03517               float x2 = (((x - v[0]) * c) - ((y - v[1]) * s)) + v[0];
03518               float y2 = (((x - v[0]) * s) + ((y - v[1]) * c)) + v[1];
03519               x = x2;
03520               y = y2;
03521             }
03522             //qglTexCoord2f (pEclass->pTriList[i].st[j][0] / pEclass->nSkinWidth, pEclass->pTriList[i].st[j][1] / pEclass->nSkinHeight);
03523             qglTexCoord2f (model->pTriList[i].st[j][0], model->pTriList[i].st[j][1]);
03524             qglVertex3f(x, y, model->pTriList[i].v[j][2] + v[2]);
03525 #else
03526             float x = model->pTriList[i].v[j][0] + v[0];
03527             float y = model->pTriList[i].v[j][1] + v[1];
03528             float z = model->pTriList[i].v[j][2] + v[2];
03529 
03530             if (b->owner->vRotation[0])
03531             {
03532               float y2 = (((y - v[1]) * vCos[0]) - ((z - v[2]) * vSin[0])) + v[1];
03533               float z2 = (((y - v[1]) * vSin[0]) + ((z - v[2]) * vCos[0])) + v[2];
03534               y = y2;
03535               z = z2;
03536             }
03537             if (b->owner->vRotation[1])
03538             {
03539               float z2 = (((z - v[2]) * vCos[1]) - ((x - v[0]) * vSin[1])) + v[2];
03540               float x2 = (((z - v[2]) * vSin[1]) + ((x - v[0]) * vCos[1])) + v[0];
03541               x = x2;
03542               z = z2;
03543             }
03544             if (b->owner->vRotation[2])
03545             {
03546               float x2 = (((x - v[0]) * vCos[2]) - ((y - v[1]) * vSin[2])) + v[0];
03547               float y2 = (((x - v[0]) * vSin[2]) + ((y - v[1]) * vCos[2])) + v[1];
03548               x = x2;
03549               y = y2;
03550             }
03551             qglTexCoord2f (model->pTriList[i].st[j][0], model->pTriList[i].st[j][1]);
03552             qglVertex3f(x, y, z);
03553 #endif
03554             if (g_bDoIt)
03555             {
03556               vTest[j][0] = x;
03557               vTest[j][1] = y;
03558               vTest[j][2] = model->pTriList[i].v[j][2] + v[2];
03559               vTest[j][3] = model->pTriList[i].st[j][0];
03560               vTest[j][4] = model->pTriList[i].st[j][1];
03561             }
03562 
03563           }
03564           if (g_bDoIt)
03565           {
03566             Patch_FromTriangle(vTest[0], vTest[1], vTest[2]);
03567           }
03568         }
03569         qglEnd();
03570         if (g_PrefsDlg.m_nEntityShowState & ENTITY_WIREFRAME)   // skinned
03571         {
03572           qglEnable(GL_CULL_FACE );
03573           qglEnable(GL_TEXTURE_2D);
03574             qglPolygonMode (GL_FRONT_AND_BACK, GL_FILL);
03575         }
03576         else
03577         {
03578             qglDisable(GL_TEXTURE_2D);
03579         }
03580         model = model->pNext;
03581       }
03582 
03583       if (g_bDoIt)
03584       {
03585         g_bDoIt = false;
03586       }
03587 
03588       vec3_t vColor;
03589       VectorScale(pEclass->color, 0.50, vColor);
03590 
03591       vec3_t vCenter, vMin, vMax;
03592       VectorCopy(b->owner->origin, vCenter);
03593 
03594           qglColor3fv(vColor);
03595       qglPointSize(4);
03596 
03597       qglBegin(GL_POINTS);
03598       qglVertex3fv(b->owner->origin);
03599       qglEnd();
03600 
03601       qglBegin(GL_LINES);
03602       vCenter[0] -= 8;
03603       qglVertex3fv(vCenter);
03604       vCenter[0] += 16;
03605       qglVertex3fv(vCenter);
03606       vCenter[0] -= 8;
03607       vCenter[1] -= 8;
03608       qglVertex3fv(vCenter);
03609       vCenter[1] += 16;
03610       qglVertex3fv(vCenter);
03611       vCenter[1] -= 8;
03612       vCenter[2] -= 8;
03613       qglVertex3fv(vCenter);
03614       vCenter[2] += 16;
03615       qglVertex3fv(vCenter);
03616       vCenter[2] -= 8;
03617       qglEnd();
03618 
03619       VectorCopy(vCenter, vMin);
03620       VectorCopy(vCenter, vMax);
03621       vMin[0] -= 4;
03622       vMin[1] -= 4;
03623       vMin[2] -= 4;
03624       vMax[0] += 4;
03625       vMax[1] += 4;
03626       vMax[2] += 4;
03627 
03628             qglBegin(GL_LINE_LOOP);
03629           qglVertex3f(vMin[0],vMin[1],vMin[2]);
03630           qglVertex3f(vMax[0],vMin[1],vMin[2]);
03631           qglVertex3f(vMax[0],vMax[1],vMin[2]);
03632           qglVertex3f(vMin[0],vMax[1],vMin[2]);
03633             qglEnd();
03634             
03635             qglBegin(GL_LINE_LOOP);
03636             qglVertex3f(vMin[0],vMin[1],vMax[2]);
03637               qglVertex3f(vMax[0],vMin[1],vMax[2]);
03638               qglVertex3f(vMax[0],vMax[1],vMax[2]);
03639               qglVertex3f(vMin[0],vMax[1],vMax[2]);
03640             qglEnd();
03641 
03642             qglBegin(GL_LINES);
03643             qglVertex3f(vMin[0],vMin[1],vMin[2]);
03644               qglVertex3f(vMin[0],vMin[1],vMax[2]);
03645               qglVertex3f(vMin[0],vMax[1],vMax[2]);
03646               qglVertex3f(vMin[0],vMax[1],vMin[2]);
03647               qglVertex3f(vMax[0],vMin[1],vMin[2]);
03648               qglVertex3f(vMax[0],vMin[1],vMax[2]);
03649               qglVertex3f(vMax[0],vMax[1],vMax[2]);
03650               qglVertex3f(vMax[0],vMax[1],vMin[2]);
03651             qglEnd();
03652 
03653 
03654         if (g_PrefsDlg.m_nEntityShowState & ENTITY_BOXED)
03655         {
03656             qglColor3fv(pEclass->color);
03657 
03658         vec3_t mins, maxs;
03659         VectorCopy(b->mins, mins);
03660         VectorCopy(b->maxs, maxs);
03661 /*
03662         if (a)
03663         {
03664           vec3_t vAngle;
03665           vAngle[0] = vAngle[1] = 0;
03666           vAngle[2] = a;
03667           VectorRotate(mins, vAngle, b->owner->origin, mins);
03668           VectorRotate(maxs, vAngle, b->owner->origin, maxs);
03669         }
03670 */
03671             qglBegin(GL_LINE_LOOP);
03672           qglVertex3f(mins[0],mins[1],mins[2]);
03673           qglVertex3f(maxs[0],mins[1],mins[2]);
03674           qglVertex3f(maxs[0],maxs[1],mins[2]);
03675           qglVertex3f(mins[0],maxs[1],mins[2]);
03676             qglEnd();
03677             
03678             qglBegin(GL_LINE_LOOP);
03679             qglVertex3f(mins[0],mins[1],maxs[2]);
03680               qglVertex3f(maxs[0],mins[1],maxs[2]);
03681               qglVertex3f(maxs[0],maxs[1],maxs[2]);
03682               qglVertex3f(mins[0],maxs[1],maxs[2]);
03683             qglEnd();
03684 
03685             qglBegin(GL_LINES);
03686             qglVertex3f(mins[0],mins[1],mins[2]);
03687               qglVertex3f(mins[0],mins[1],maxs[2]);
03688               qglVertex3f(mins[0],maxs[1],maxs[2]);
03689               qglVertex3f(mins[0],maxs[1],mins[2]);
03690               qglVertex3f(maxs[0],mins[1],mins[2]);
03691               qglVertex3f(maxs[0],mins[1],maxs[2]);
03692               qglVertex3f(maxs[0],maxs[1],maxs[2]);
03693               qglVertex3f(maxs[0],maxs[1],mins[2]);
03694             qglEnd();
03695       }
03696         qglPopAttrib();
03697       bReturn = true;
03698     }
03699     else
03700     {
03701       b->bModelFailed = true;
03702     }
03703 
03704   g_bInPaintedModel = false;
03705   return bReturn;
03706 }

Here is the call graph for this function:

void PrintPlane plane_t p  ) 
 

Definition at line 65 of file Brush.cpp.

References plane_t::dist, plane_t::normal, p, and printf().

00066 {
00067   printf ("(%5.2f, %5.2f, %5.2f) : %5.2f\n",  p->normal[0],  p->normal[1], 
00068   p->normal[2],  p->dist);
00069 }

Here is the call graph for this function:

void PrintVector vec3_t  v  ) 
 

Definition at line 71 of file Brush.cpp.

References printf(), and v.

00072 {
00073   printf ("(%5.2f, %5.2f, %5.2f)\n",  v[0],  v[1], v[2]);
00074 }

Here is the call graph for this function:

void PrintWinding winding_t w  ) 
 

Definition at line 55 of file Brush.cpp.

References i, winding_t::numpoints, winding_t::points, printf(), and w.

00056 {
00057     int     i;
00058     
00059     printf ("-------------\n");
00060     for (i=0 ; i<w->numpoints ; i++)
00061         printf ("(%5.2f, %5.2f, %5.2f)\n", w->points[i][0]
00062         , w->points[i][1], w->points[i][2]);
00063 }

Here is the call graph for this function:

void WINAPI QERApp_MapPrintf_FILE char *  text,
  ...
 

Definition at line 1855 of file Brush.cpp.

References fprintf(), g_File, va_end, va_list, va_start, and vsprintf().

Referenced by Brush_Write(), and Patch_Write().

01856 {
01857     va_list argptr;
01858     char    buf[32768];
01859 
01860     va_start (argptr,text);
01861     vsprintf (buf, text,argptr);
01862     va_end (argptr);
01863 
01864     fprintf( g_File, buf );
01865 }

Here is the call graph for this function:

void WINAPI QERApp_MapPrintf_MEMFILE char *  text,
  ...
 

Definition at line 2059 of file Brush.cpp.

References g_pMemFile, MemFile_fprintf(), va_end, va_list, va_start, and vsprintf().

Referenced by Brush_Write().

02060 {
02061     va_list argptr;
02062     char    buf[32768];
02063 
02064     va_start (argptr,text);
02065     vsprintf (buf, text,argptr);
02066     va_end (argptr);
02067 
02068     MemFile_fprintf( g_pMemFile, buf );
02069 }

Here is the call graph for this function:

void SetFaceTexdef brush_t b,
face_t f,
texdef_t texdef,
brushprimit_texdef_t brushprimit_texdef,
bool  bFitScale,
IPluginTexdef pPlugTexdef
 

Definition at line 2867 of file Brush.cpp.

References AbsoluteToLocal(), b, brush_s::brush_faces, brush_t, brushprimit_texdef, face_s::brushprimit_texdef, brushprimit_texdef_t, QEGlobals_t::bSurfacePropertiesPlugin, ComputeAbsolute(), texdef_t::contents, ConvertTexMatWithQTexture(), f, face_t, texdef_t::flags, g_qeglobals, g_SurfaceTable, GETPLUGINTEXDEF, IPluginTexdef::Hook(), QEGlobals_t::m_bBrushPrimitMode, _QERPlugSurfaceTable::m_pfnTexdefAlloc, texdef_t::name, face_s::next, NULL, p2, face_s::pData, face_s::plane, pPlugTexdef, texdef_t::scale, Sys_Printf(), face_s::texdef, Texture_ForName(), vec3_t, VectorAdd, VectorNormalize(), VectorScale, and VectorSubtract.

Referenced by Brush_SetTexture(), Drag_Begin(), and Select_SetTexture().

02867                                                                                                                                                    {
02868     int     oldFlags;
02869     int     oldContents;
02870     face_t  *tf;
02871 
02872     oldFlags = f->texdef.flags;
02873     oldContents = f->texdef.contents;
02874     if (g_qeglobals.m_bBrushPrimitMode)
02875     {
02876         f->texdef = *texdef;
02877         ConvertTexMatWithQTexture( brushprimit_texdef, NULL, &f->brushprimit_texdef, Texture_ForName( f->texdef.name ) );
02878     }
02879     else
02880         if (bFitScale)
02881         {
02882             f->texdef = *texdef;
02883             // fit the scaling of the texture on the actual plane
02884             vec3_t p1,p2,p3; // absolute coordinates
02885             // compute absolute coordinates
02886             ComputeAbsolute(f,p1,p2,p3);
02887             // compute the scale
02888             vec3_t vx,vy;
02889             VectorSubtract(p2,p1,vx);
02890             VectorNormalize(vx);
02891             VectorSubtract(p3,p1,vy);
02892             VectorNormalize(vy);
02893             // assign scale
02894             VectorScale(vx,texdef->scale[0],vx);
02895             VectorScale(vy,texdef->scale[1],vy);
02896             VectorAdd(p1,vx,p2);
02897             VectorAdd(p1,vy,p3);
02898             // compute back shift scale rot
02899             AbsoluteToLocal(f->plane,f,p1,p2,p3);
02900         }
02901         else
02902             f->texdef = *texdef;
02903     f->texdef.flags = (f->texdef.flags & ~SURF_KEEP) | (oldFlags & SURF_KEEP);
02904     f->texdef.contents = (f->texdef.contents & ~CONTENTS_KEEP) | (oldContents & CONTENTS_KEEP);
02905 
02906     // surface plugin
02907     if (g_qeglobals.bSurfacePropertiesPlugin)
02908     {
02909 #ifdef _DEBUG
02910         if (!f->pData)
02911             Sys_Printf("ERROR: unexpected IPluginTexdef* is NULL in SetFaceTexdef\n");
02912         else
02913 #endif
02914             GETPLUGINTEXDEF(f)->DecRef();
02915         IPluginTexdef *pTexdef = NULL;
02916         if ( pPlugTexdef )
02917         {
02918             pTexdef = pPlugTexdef->Copy();
02919             pTexdef->Hook( f );
02920         }
02921         else
02922             pTexdef = g_SurfaceTable.m_pfnTexdefAlloc( f );
02923         f->pData = pTexdef;
02924     }
02925 
02926     // if this is a curve face, set all other curve faces to the same texdef
02927     if (f->texdef.flags & SURF_CURVE) 
02928     {
02929         for (tf = b->brush_faces ; tf ; tf = tf->next) 
02930         {
02931             if (tf->texdef.flags & SURF_CURVE) 
02932                 tf->texdef = f->texdef;
02933         }
02934     }
02935 }

Here is the call graph for this function:

float SetShadeForPlane plane_t p  ) 
 

Definition at line 135 of file Brush.cpp.

References f, fabs(), i, lightaxis, plane_t::normal, and p.

Referenced by Face_SetColor().

00136 {
00137     int     i;
00138     float   f;
00139 
00140     // axial plane
00141     for (i=0 ; i<3 ; i++)
00142         if (fabs(p->normal[i]) > 0.9)
00143         {
00144             f = lightaxis[i];
00145             return f;
00146         }
00147 
00148     // between two axial planes
00149     for (i=0 ; i<3 ; i++)
00150         if (fabs(p->normal[i]) < 0.1)
00151         {
00152             f = (lightaxis[(i+1)%3] + lightaxis[(i+2)%3])/2;
00153             return f;
00154         }
00155 
00156     // other
00157     f= (lightaxis[0] + lightaxis[1] + lightaxis[2]) / 3;
00158     return f;
00159 }

Here is the call graph for this function:

void TextureAxisFromPlane plane_t pln,
vec3_t  xv,
vec3_t  yv
 

Definition at line 101 of file Brush.cpp.

References baseaxis, DotProduct, i, plane_t::normal, vec_t, and VectorCopy.

Referenced by AbsoluteToLocal(), ComputeAbsolute(), Face_FitTexture(), Face_MoveTexture(), Face_TextureVectors(), QuakeTextureVecs(), TexinfoForBrushTexture(), and WriteMapBrush().

00102 {
00103     int     bestaxis;
00104     float   dot,best;
00105     int     i;
00106     
00107     best = 0;
00108     bestaxis = 0;
00109     
00110     for (i=0 ; i<6 ; i++)
00111     {
00112         dot = DotProduct (pln->normal, baseaxis[i*3]);
00113         if (dot > best)
00114         {
00115             best = dot;
00116             bestaxis = i;
00117         }
00118     }
00119     
00120     VectorCopy (baseaxis[bestaxis*3+1], xv);
00121     VectorCopy (baseaxis[bestaxis*3+2], yv);
00122 }


Variable Documentation

vec3_t baseaxis[18]
 

Initial value:

{
{0,0,1}, {1,0,0}, {0,-1,0},         
{0,0,-1}, {1,0,0}, {0,-1,0},        
{1,0,0}, {0,1,0}, {0,0,-1},         
{-1,0,0}, {0,1,0}, {0,0,-1},        
{0,1,0}, {1,0,0}, {0,0,-1},         
{0,-1,0}, {1,0,0}, {0,0,-1}         
}

Definition at line 91 of file Brush.cpp.

bool g_bDoIt = false [static]
 

Definition at line 3422 of file Brush.cpp.

Referenced by PaintedModel().

bool g_bInPaintedModel = false [static]
 

Definition at line 3421 of file Brush.cpp.

Referenced by PaintedModel().

FILE* g_File
 

Definition at line 1854 of file Brush.cpp.

Referenced by Brush_Write(), Patch_Write(), and QERApp_MapPrintf_FILE().

int g_nBrushId = 0
 

Definition at line 32 of file Brush.cpp.

Referenced by Brush_Clone(), Brush_FullClone(), Brush_Name(), and CPlugInManager::CreateBrushHandle().

CMemFile* g_pMemFile
 

Definition at line 2058 of file Brush.cpp.

Referenced by Brush_Write(), and QERApp_MapPrintf_MEMFILE().

float lightaxis[3] = {0.6, 0.8, 1.0}
 

Definition at line 126 of file Brush.cpp.

Referenced by SetShadeForPlane().

float shift[2]
 

Definition at line 162 of file Brush.cpp.

Referenced by EmitTerrainVerts(), EmitTerrainVerts2(), FakeTexCoordsToTexMat(), texdef_t::operator=(), ParseRawBrush(), QuakeTextureVecs(), R_ColorShiftLightingBytes(), R_SetColorMappings(), Select_RotateTexture(), Select_ScaleTexture(), Terrain_ParseFace(), TexinfoForBrushTexture(), TexMatToFakeTexCoords(), and WriteMapBrush().

vec3_t vecs[2]
 

Definition at line 161 of file Brush.cpp.

Referenced by AddSkyPolygon(), AllocateLightmapForSurface(), ClipSkyPolygon(), EmitTerrainVerts(), EmitTerrainVerts2(), Face_FitTexture(), HL_SwapBSPFile(), HL_TextureBrushes(), Q1_SwapBSPFile(), Q1_TextureBrushes(), Q2_CreateMapTexinfo(), Q2_SwapBSPFile(), QuakeTextureVecs(), Sin_CreateMapTexinfo(), Sin_SwapBSPFile(), TexinfoForBrushTexture(), tv(), VL_FloodLight(), VS_FloodLight(), and WriteMapBrush().


Generated on Thu Aug 25 17:23:42 2005 for Quake III Arena by  doxygen 1.3.9.1