示例#1
0
文件: model.c 项目: jogi1/jsv
static qboolean Model_MapCreatePVS(struct map *map)
{
	unsigned char *visdata, *scan;
	struct dleaf *in;
	int p, i;

	map->vis_rowlongs = (map->visleafs + 31) >> 5;
	map->vis_rowbytes = map->vis_rowlongs * 4;
	map->pvs = (unsigned char *) calloc(map->vis_rowbytes * map->visleafs, sizeof(unsigned char));
	if (map->pvs == NULL)
		return false;

	if (map->header->lumps[LUMP_VISIBILITY].filelen == 0)
		return false;

	visdata = map->mod_base + map->header->lumps[LUMP_VISIBILITY].fileofs;

	in = (struct dleaf *)(map->mod_base + map->header->lumps[LUMP_LEAFS].fileofs);
	in++;
	scan = map->pvs;

	for (i=0; i<map->visleafs; i++, in++, scan += map->vis_rowbytes)
	{
		p = LittleLong(in->visofs);
		memcpy(scan, (p == -1) ? map->novis : DecompressVis (map, visdata + p), map->vis_rowbytes);
	}

	return true;
}
示例#2
0
文件: model.cpp 项目: RkShaRkz/Quake2
static void LoadQ1Vis(bspfile_t *f, byte *vis, int size)
{
	if (!size)
	{
		Com_DPrintf("No visinfo in map\n");
		f->numClusters = 1;				// required
		f->visRowSize  = 1;				// required
		f->visInfo     = NULL;
		return;
	}
	// NOTE: 'size' is ignored later

	// create dummy clusters: 1 cluster per 1 leaf
	f->numClusters = f->numLeafs;

	int rowSize;
	f->visRowSize = rowSize = (f->numClusters + 7) >> 3;
	byte *dst = new (f->extraChain) byte [rowSize * f->numClusters];
	f->visInfo = dst;

	// start from leaf #1 (leaf 0 is CONTENTS_SOLID and have no stored visinfo)
	for (int i = 1; i < f->numLeafs; i++, dst += rowSize)
		DecompressVis(dst, vis, f->leafs1[i].visofs, rowSize);
	Com_DPrintf("Decompressed vis: %d -> %d bytes\n", size, rowSize * f->numClusters);
}
示例#3
0
byte * dxModel::LeafPVS(mleaf_s *leaf)
{
    if (leaf == leafs)
    {
        return novis;
    }
    return DecompressVis(leaf->compressed_vis);
}
示例#4
0
void PvsForOrigin (vec3_t org, byte *pvs)
{
	dleaf_t	*leaf;

	if (!visdatasize)
	{
		memset (pvs, 255, (numleafs+7)/8 );
		return;
	}

	leaf = PointInLeaf (org);
	if (leaf->visofs == -1)
		Error ("leaf->visofs == -1");

	DecompressVis (&dvisdata[leaf->visofs], pvs);
}
示例#5
0
文件: model.cpp 项目: RkShaRkz/Quake2
static void LoadQ2Vis(bspfile_t *f, dBsp2Vis_t *vis, int size)
{
#if !LITTLE_ENDIAN
	if (size)		// should process this only when map have visibility data
	{
		LTL(vis->numClusters);
		int j = vis->numClusters;
		for (int i = 0; i < j ; i++)
		{
			LTL(vis->bitOfs[i][0]);
			LTL(vis->bitOfs[i][1]);
		}
	}
#endif

	if (!size)
	{
		Com_DPrintf("No visinfo in map\n");
		if (f->numClusters > 1)
		{
			if (developer->integer)
				appWPrintf("WARNING: map with cluster info but without visinfo\n");
		}
		f->numClusters = 1;				// required
		f->visRowSize  = 1;				// required
		f->visInfo     = NULL;
		return;
	}
	// NOTE: 'size' is ignored later

	int rowSize;
	f->visRowSize = rowSize = (f->numClusters + 7) >> 3;

	// decompress visinfo
	byte *dst = new (f->extraChain) byte [rowSize * f->numClusters];
	f->visInfo = dst;
	for (int i = 0; i < f->numClusters; i++, dst += rowSize)
		DecompressVis(dst, vis, vis->bitOfs[i][dBsp2Vis_t::PVS], rowSize);
	Com_DPrintf("Decompressed vis: %d -> %d bytes\n", size, rowSize * f->numClusters);
}
示例#6
0
文件: vvis.cpp 项目: chrizonix/RCBot2
static int CompressAndCrosscheckClusterVis( int clusternum )
{
    int		optimized = 0;
    byte	compressed[MAX_MAP_LEAFS/8];
//
// compress the bit string
//
    byte *uncompressed = uncompressedvis + clusternum*leafbytes;
    for ( int i = 0; i < portalclusters; i++ )
    {
        if ( i == clusternum )
            continue;

        if ( CheckBit( uncompressed, i ) )
        {
            byte *other = uncompressedvis + i*leafbytes;
            if ( !CheckBit( other, clusternum ) )
            {
                ClearBit( uncompressed, i );
                optimized++;
            }
        }
    }
    int numbytes = CompressVis( uncompressed, compressed );

    byte *dest = vismap_p;
    vismap_p += numbytes;

    if (vismap_p > vismap_end)
        Error ("Vismap expansion overflow");

    dvis->bitofs[clusternum][DVIS_PVS] = dest-vismap;

    memcpy( dest, compressed, numbytes );

    // check vis data
    DecompressVis( vismap + dvis->bitofs[clusternum][DVIS_PVS], compressed );

    return optimized;
}
示例#7
0
文件: vvis.cpp 项目: chrizonix/RCBot2
//-----------------------------------------------------------------------------
// Using the PVS, compute the visible fog volumes from each leaf
//-----------------------------------------------------------------------------
static void CalcVisibleFogVolumes()
{
    byte	uncompressed[MAX_MAP_LEAFS/8];

    int i, j, k;

    // Clear the contents flags for water testing
    for (i = 0; i < numleafs; ++i)
    {
        dleafs[i].contents &= ~CONTENTS_TESTFOGVOLUME;
        g_LeafMinDistToWater[i] = 65535;
    }

    for (i = 0; i < numleafs; ++i)
    {
        // If we've already discovered that this leaf needs testing,
        // no need to go through the work again...
        if (dleafs[i].contents & CONTENTS_TESTFOGVOLUME)
        {
            Assert((dleafs[i].contents & (CONTENTS_SLIME | CONTENTS_WATER)) == 0);
            continue;
        }

        // Don't bother checking fog volumes from solid leaves
        if (dleafs[i].contents & CONTENTS_SOLID)
            continue;

        // Look only for leaves which are visible from leaves that have fluid in them.
        if ( dleafs[i].leafWaterDataID == -1 )
            continue;

        // Don't bother about looking from CONTENTS_SLIME; we're not going to treat that as interesting.
        // because slime is opaque
        if ( dleafs[i].contents & CONTENTS_SLIME )
            continue;

        // First get the vis data..
        int cluster = dleafs[i].cluster;
        if (cluster < 0)
            continue;

        DecompressVis( &dvisdata[dvis->bitofs[cluster][DVIS_PVS]], uncompressed );

        // Iterate over all potentially visible clusters from this leaf
        for (j = 0; j < dvis->numclusters; ++j)
        {
            // Don't need to bother if this is the same as the current cluster
            if (j == cluster)
                continue;

            if ( !CheckBit( uncompressed, j ) )
                continue;

            // Found a visible cluster, now iterate over all leaves
            // inside that cluster
            for (k = 0; k < g_ClusterLeaves[j].leafCount; ++k)
            {
                int nClusterLeaf = g_ClusterLeaves[j].leafs[k];

                // Don't bother checking fog volumes from solid leaves
                if ( dleafs[nClusterLeaf].contents & CONTENTS_SOLID )
                    continue;

                // Don't bother checking from any leaf that's got fluid in it
                if ( dleafs[nClusterLeaf].leafWaterDataID != -1 )
                    continue;

                // Here, we've found a case where a non-liquid leaf is visible from a liquid leaf
                // So, in this case, we have to do the expensive test during rendering.
                dleafs[nClusterLeaf].contents |= CONTENTS_TESTFOGVOLUME;
            }
        }
    }
}
示例#8
0
文件: vvis.cpp 项目: chrizonix/RCBot2
static float CalcDistanceFromLeafToWater( int leafNum )
{
    byte	uncompressed[MAX_MAP_LEAFS/8];

    int j, k;

    // If we know that this one doesn't see a water surface then don't bother doing anything.
    if( ((dleafs[leafNum].contents & CONTENTS_TESTFOGVOLUME) == 0) && ( dleafs[leafNum].leafWaterDataID == -1 ) )
        return 65535; // FIXME: make a define for this.

    // First get the vis data..
    int cluster = dleafs[leafNum].cluster;
    if (cluster < 0)
        return 65535; // FIXME: make a define for this.

    DecompressVis( &dvisdata[dvis->bitofs[cluster][DVIS_PVS]], uncompressed );

    float minDist = 65535.0f; // FIXME: make a define for this.

    Vector leafMin, leafMax;

    leafMin[0] = ( float )dleafs[leafNum].mins[0];
    leafMin[1] = ( float )dleafs[leafNum].mins[1];
    leafMin[2] = ( float )dleafs[leafNum].mins[2];
    leafMax[0] = ( float )dleafs[leafNum].maxs[0];
    leafMax[1] = ( float )dleafs[leafNum].maxs[1];
    leafMax[2] = ( float )dleafs[leafNum].maxs[2];

    /*
    	CUtlVector<listplane_t> temp;

    	// build a convex solid out of the planes so that we can get at the triangles.
    	for( j = dleafs[i].firstleafbrush; j < dleafs[i].firstleafbrush + dleafs[i].numleafbrushes; j++ )
    	{
    		dbrush_t *pBrush = &dbrushes[j];
    		for( k = pBrush->firstside; k < pBrush->firstside + pBrush->numsides; k++ )
    		{
    			dbrushside_t *pside = dbrushsides + k;
    			dplane_t *pplane = dplanes + pside->planenum;
    			AddListPlane( &temp, pplane->normal[0], pplane->normal[1], pplane->normal[2], pplane->dist );
    		}
    		CPhysConvex *pConvex = physcollision->ConvexFromPlanes( (float *)temp.Base(), temp.Count(), VPHYSICS_MERGE );
    		ConvertConvexToCollide(  &pConvex,
    			temp.RemoveAll();
    	}
    */

    // Iterate over all potentially visible clusters from this leaf
    for (j = 0; j < dvis->numclusters; ++j)
    {
        // Don't need to bother if this is the same as the current cluster
        if (j == cluster)
            continue;

        // If the cluster isn't in our current pvs, then get out of here.
        if ( !CheckBit( uncompressed, j ) )
            continue;

        // Found a visible cluster, now iterate over all leaves
        // inside that cluster
        for (k = 0; k < g_ClusterLeaves[j].leafCount; ++k)
        {
            int nClusterLeaf = g_ClusterLeaves[j].leafs[k];

            // Don't bother testing the ones that don't see a water boundary.
            if( ((dleafs[nClusterLeaf].contents & CONTENTS_TESTFOGVOLUME) == 0) && ( dleafs[nClusterLeaf].leafWaterDataID == -1 ) )
                continue;

            // Find the minimum distance between each surface on the boundary of the leaf
            // that we have the pvs for and each water surface in the leaf that we are testing.
            int nFirstFaceID = dleafs[nClusterLeaf].firstleafface;
            for( int leafFaceID = 0; leafFaceID < dleafs[nClusterLeaf].numleaffaces; ++leafFaceID )
            {
                int faceID = dleaffaces[nFirstFaceID + leafFaceID];
                dface_t *pFace = &dfaces[faceID];
                if( pFace->texinfo == -1 )
                    continue;

                texinfo_t *pTexInfo = &texinfo[pFace->texinfo];
                if( pTexInfo->flags & SURF_WARP )
                {
                    // Woo hoo!!!  We found a water face.
                    // compare the bounding box of the face with the bounding
                    // box of the leaf that we are looking from and see
                    // what the closest distance is.
                    // FIXME: this could be a face/face distance between the water
                    // face and the bounding volume of the leaf.

                    // Get the bounding box of the face
                    Vector faceMin, faceMax;
                    GetBoundsForFace( faceID, faceMin, faceMax );
                    float dist = GetMinDistanceBetweenBoundingBoxes( leafMin, leafMax, faceMin, faceMax );
                    if( dist < minDist )
                    {
                        minDist = dist;
                    }
                }
            }
        }
    }
    return minDist;
}