xash3d-fwgs/engine/client/vgui/vgui_clip.cpp

110 lines
3.6 KiB
C++
Raw Normal View History

/*
vgui_clip.cpp - clip in 2D space
Copyright (C) 2011 Uncle Mike
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
*/
#include "common.h"
#include "vgui_draw.h"
#include "wrect.h"
//-----------------------------------------------------------------------------
// For simulated scissor tests...
//-----------------------------------------------------------------------------
static wrect_t g_ScissorRect;
static qboolean g_bScissor = false;
//-----------------------------------------------------------------------------
// Enable/disable scissoring...
//-----------------------------------------------------------------------------
void EnableScissor( qboolean enable )
{
g_bScissor = enable;
}
void SetScissorRect( int left, int top, int right, int bottom )
{
// Check for a valid rectangle...
Assert( left <= right );
Assert( top <= bottom );
g_ScissorRect.left = left;
g_ScissorRect.top = top;
g_ScissorRect.right = right;
g_ScissorRect.bottom = bottom;
}
//-----------------------------------------------------------------------------
// Purpose: Used for clipping, produces an interpolated texture coordinate
//-----------------------------------------------------------------------------
inline float InterpTCoord( float val, float mins, float maxs, float tMin, float tMax )
{
float flPercent;
if( mins != maxs )
flPercent = (float)(val - mins) / (maxs - mins);
else flPercent = 0.5f;
return tMin + (tMax - tMin) * flPercent;
}
//-----------------------------------------------------------------------------
// Purpose: Does a scissor clip of the input rectangle.
// Returns false if it is completely clipped off.
//-----------------------------------------------------------------------------
qboolean ClipRect( const vpoint_t &inUL, const vpoint_t &inLR, vpoint_t *pOutUL, vpoint_t *pOutLR )
{
if( g_bScissor )
{
// pick whichever left side is larger
if( g_ScissorRect.left > inUL.point[0] )
pOutUL->point[0] = g_ScissorRect.left;
else
pOutUL->point[0] = inUL.point[0];
// pick whichever right side is smaller
if( g_ScissorRect.right <= inLR.point[0] )
pOutLR->point[0] = g_ScissorRect.right;
else
pOutLR->point[0] = inLR.point[0];
// pick whichever top side is larger
if( g_ScissorRect.top > inUL.point[1] )
pOutUL->point[1] = g_ScissorRect.top;
else
pOutUL->point[1] = inUL.point[1];
// pick whichever bottom side is smaller
if( g_ScissorRect.bottom <= inLR.point[1] )
pOutLR->point[1] = g_ScissorRect.bottom;
else
pOutLR->point[1] = inLR.point[1];
// Check for non-intersecting
if(( pOutUL->point[0] > pOutLR->point[0] ) || ( pOutUL->point[1] > pOutLR->point[1] ))
{
return false;
}
pOutUL->coord[0] = InterpTCoord(pOutUL->point[0], inUL.point[0], inLR.point[0], inUL.coord[0], inLR.coord[0] );
pOutLR->coord[0] = InterpTCoord(pOutLR->point[0], inUL.point[0], inLR.point[0], inUL.coord[0], inLR.coord[0] );
pOutUL->coord[1] = InterpTCoord(pOutUL->point[1], inUL.point[1], inLR.point[1], inUL.coord[1], inLR.coord[1] );
pOutLR->coord[1] = InterpTCoord(pOutLR->point[1], inUL.point[1], inLR.point[1], inUL.coord[1], inLR.coord[1] );
}
else
{
*pOutUL = inUL;
*pOutLR = inLR;
}
return true;
}