mirror of
https://github.com/ENSL/NS.git
synced 2024-12-11 13:22:03 +00:00
444 lines
14 KiB
C++
444 lines
14 KiB
C++
|
//========= Copyright <20> 1996-2002, Valve LLC, All rights reserved. ============
|
|||
|
//
|
|||
|
// Purpose:
|
|||
|
//
|
|||
|
// $NoKeywords: $
|
|||
|
//=============================================================================
|
|||
|
|
|||
|
// vgui_SpectatorPanel.cpp: implementation of the SpectatorPanel class.
|
|||
|
//
|
|||
|
//////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
#include "hud.h"
|
|||
|
#include "cl_util.h"
|
|||
|
#include "const.h"
|
|||
|
#include "entity_state.h"
|
|||
|
#include "cl_entity.h"
|
|||
|
#include "pm_shared.h"
|
|||
|
#include "vgui_TeamFortressViewport.h"
|
|||
|
#include "vgui_SpectatorPanel.h"
|
|||
|
#include "vgui_scorepanel.h"
|
|||
|
#include "mod/AvHOverviewControl.h"
|
|||
|
|
|||
|
|
|||
|
#define BANNER_WIDTH 256
|
|||
|
#define BANNER_HEIGHT 64
|
|||
|
|
|||
|
|
|||
|
#define OPTIONS_BUTTON_X 96
|
|||
|
#define CAMOPTIONS_BUTTON_X 200
|
|||
|
|
|||
|
|
|||
|
class Spectator_CheckButtonHandler : public ICheckButton2Handler
|
|||
|
{
|
|||
|
|
|||
|
public:
|
|||
|
|
|||
|
Spectator_CheckButtonHandler(SpectatorPanel * panel)
|
|||
|
{
|
|||
|
m_pFather = panel;
|
|||
|
}
|
|||
|
|
|||
|
virtual void StateChanged(CCheckButton2* pButton)
|
|||
|
{
|
|||
|
m_pFather->StateChanged(pButton);
|
|||
|
}
|
|||
|
|
|||
|
private:
|
|||
|
|
|||
|
SpectatorPanel * m_pFather;
|
|||
|
|
|||
|
};
|
|||
|
|
|||
|
//////////////////////////////////////////////////////////////////////
|
|||
|
// Construction/Destruction
|
|||
|
//////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
SpectatorPanel::SpectatorPanel(int x,int y,int wide,int tall) : Panel(x,y,wide,tall)
|
|||
|
{
|
|||
|
m_overviewButton = NULL;
|
|||
|
m_autoDirectorButton = NULL;
|
|||
|
m_firstPersonButton = NULL;
|
|||
|
m_overviewControl = NULL;
|
|||
|
}
|
|||
|
|
|||
|
SpectatorPanel::~SpectatorPanel()
|
|||
|
{
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
void SpectatorPanel::StateChanged(CCheckButton2* pButton)
|
|||
|
{
|
|||
|
bool theOverviewMode = false;
|
|||
|
if(m_overviewButton)
|
|||
|
{
|
|||
|
theOverviewMode = m_overviewButton->IsChecked();
|
|||
|
}
|
|||
|
gHUD.m_Spectator.SetOverviewMode(theOverviewMode);
|
|||
|
|
|||
|
int theMode = OBS_NONE;
|
|||
|
|
|||
|
if (m_firstPersonButton->IsChecked())
|
|||
|
{
|
|||
|
theMode = OBS_IN_EYE;
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
theMode = OBS_CHASE_LOCKED;
|
|||
|
}
|
|||
|
|
|||
|
gHUD.m_Spectator.SetMode(theMode);
|
|||
|
|
|||
|
if (m_autoDirectorButton != NULL)
|
|||
|
{
|
|||
|
if (m_autoDirectorButton->IsChecked())
|
|||
|
{
|
|||
|
gEngfuncs.Cvar_SetValue("spec_autodirector", 1);
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
gEngfuncs.Cvar_SetValue("spec_autodirector", 0);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
Update(); // Update so that the components reflect the new state.
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
void SpectatorPanel::ActionSignal(int cmd)
|
|||
|
{
|
|||
|
|
|||
|
switch (cmd)
|
|||
|
{
|
|||
|
/*
|
|||
|
case SPECTATOR_PANEL_CMD_NONE : break;
|
|||
|
*/
|
|||
|
|
|||
|
case SPECTATOR_PANEL_CMD_PLAYERS :
|
|||
|
gViewPort->UpdatePlayerMenu();
|
|||
|
gViewPort->ShowCommandMenu(gViewPort->m_SpectatorPlayerMenu);
|
|||
|
break;
|
|||
|
|
|||
|
case SPECTATOR_PANEL_CMD_NEXTPLAYER : gHUD.m_Spectator.FindNextPlayer(true);
|
|||
|
break;
|
|||
|
|
|||
|
case SPECTATOR_PANEL_CMD_PREVPLAYER : gHUD.m_Spectator.FindNextPlayer(false);
|
|||
|
break;
|
|||
|
|
|||
|
/*
|
|||
|
case SPECTATOR_PANEL_CMD_HIDEMENU : ShowMenu(false);
|
|||
|
break;
|
|||
|
|
|||
|
case SPECTATOR_PANEL_CMD_CAMERA : gViewPort->ShowCommandMenu( gViewPort->m_SpectatorCameraMenu );
|
|||
|
break;
|
|||
|
|
|||
|
*/
|
|||
|
default : gEngfuncs.Con_DPrintf("Unknown SpectatorPanel ActionSingal %i.\n",cmd); break;
|
|||
|
}
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
void SpectatorPanel::Initialize()
|
|||
|
{
|
|||
|
int x,y,wide,tall;
|
|||
|
|
|||
|
getBounds(x,y,wide,tall);
|
|||
|
|
|||
|
CSchemeManager * pSchemes = gViewPort->GetSchemeManager();
|
|||
|
|
|||
|
|
|||
|
int colorR = 128 / gHUD.GetGammaSlope();
|
|||
|
int colorG = 128 / gHUD.GetGammaSlope();
|
|||
|
int colorB = 128 / gHUD.GetGammaSlope();
|
|||
|
|
|||
|
int armedColorR = 255 / gHUD.GetGammaSlope();
|
|||
|
int armedColorG = 255 / gHUD.GetGammaSlope();
|
|||
|
int armedColorB = 255 / gHUD.GetGammaSlope();
|
|||
|
|
|||
|
|
|||
|
SchemeHandle_t hSmallScheme = pSchemes->getSchemeHandle( /*"Team Info Text"*/ "PieMenuScheme" );
|
|||
|
Font* font = pSchemes->getFont(hSmallScheme);
|
|||
|
|
|||
|
//m_TopBorder = new CTransparentPanel(64, 0, 0, ScreenWidth, YRES(PANEL_HEIGHT));
|
|||
|
m_TopBorder = new CTransparentPanel(1, 0, ScreenHeight() - YRES(32), ScreenWidth(), YRES(SPECTATOR_PANEL_HEIGHT));
|
|||
|
m_TopBorder->setParent(this);
|
|||
|
|
|||
|
m_BottomBorder = new CTransparentPanel(1, 0, ScreenHeight() - YRES(32), ScreenWidth(), YRES(SPECTATOR_PANEL_HEIGHT));
|
|||
|
m_BottomBorder->setParent(this);
|
|||
|
|
|||
|
setPaintBackgroundEnabled(false);
|
|||
|
|
|||
|
m_ExtraInfo = new Label( "Extra Info", 0, 0, wide, YRES(SPECTATOR_PANEL_HEIGHT) );
|
|||
|
m_ExtraInfo->setParent(m_TopBorder);
|
|||
|
m_ExtraInfo->setFont( font );
|
|||
|
|
|||
|
m_ExtraInfo->setPaintBackgroundEnabled(false);
|
|||
|
m_ExtraInfo->setFgColor( 143, 143, 54, 0 );
|
|||
|
m_ExtraInfo->setContentAlignment( vgui::Label::a_west );
|
|||
|
|
|||
|
|
|||
|
|
|||
|
m_TimerImage = new CImageLabel( "timer", 0, 0, 14, 14 );
|
|||
|
m_TimerImage->setParent(m_TopBorder);
|
|||
|
|
|||
|
m_TopBanner = new CImageLabel( "banner", 0, 0, XRES(BANNER_WIDTH), YRES(BANNER_HEIGHT) );
|
|||
|
m_TopBanner->setParent(this);
|
|||
|
|
|||
|
m_CurrentTime = new Label( "00:00", 0, 0, wide, YRES(SPECTATOR_PANEL_HEIGHT) );
|
|||
|
m_CurrentTime->setParent(m_TopBorder);
|
|||
|
m_CurrentTime->setFont( pSchemes->getFont(hSmallScheme) );
|
|||
|
m_CurrentTime->setPaintBackgroundEnabled(false);
|
|||
|
m_CurrentTime->setFgColor( 143, 143, 54, 0 );
|
|||
|
m_CurrentTime->setContentAlignment( vgui::Label::a_west );
|
|||
|
|
|||
|
m_Separator = new Panel( 0, 0, XRES( 64 ), YRES( 96 ));
|
|||
|
m_Separator->setParent( m_TopBorder );
|
|||
|
m_Separator->setFgColor( 59, 58, 34, 48 );
|
|||
|
m_Separator->setBgColor( 59, 58, 34, 48 );
|
|||
|
|
|||
|
for ( int j= 0; j < TEAM_NUMBER; j++ )
|
|||
|
{
|
|||
|
m_TeamScores[j] = new Label( " ", 0, 0, wide, YRES(SPECTATOR_PANEL_HEIGHT) );
|
|||
|
m_TeamScores[j]->setParent( m_TopBorder );
|
|||
|
m_TeamScores[j]->setFont( pSchemes->getFont(hSmallScheme) );
|
|||
|
m_TeamScores[j]->setPaintBackgroundEnabled(false);
|
|||
|
m_TeamScores[j]->setFgColor( 143, 143, 54, 0 );
|
|||
|
m_TeamScores[j]->setContentAlignment( vgui::Label::a_west );
|
|||
|
m_TeamScores[j]->setVisible ( false );
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
m_PrevPlayerButton= new ColorButton("<", XRES(390 - 20 - 4), YRES(6), XRES(20), YRES(20), false, false );
|
|||
|
m_PrevPlayerButton->setParent( m_BottomBorder );
|
|||
|
m_PrevPlayerButton->setContentAlignment( vgui::Label::a_center );
|
|||
|
m_PrevPlayerButton->setBoundKey( (char)255 ); // special no bound to avoid leading spaces in name
|
|||
|
m_PrevPlayerButton->addActionSignal( new CSpectatorHandler_Command(this,SPECTATOR_PANEL_CMD_PREVPLAYER) );
|
|||
|
m_PrevPlayerButton->setUnArmedBorderColor ( colorR, colorG, colorB, 0 );
|
|||
|
m_PrevPlayerButton->setArmedBorderColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
m_PrevPlayerButton->setUnArmedColor ( colorR, colorG, colorB, 0 );
|
|||
|
m_PrevPlayerButton->setArmedColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
|
|||
|
m_NextPlayerButton= new ColorButton(">", XRES(390 + 200 + 4), YRES(6), XRES(20), YRES(20), false, false );
|
|||
|
m_NextPlayerButton->setParent( m_BottomBorder );
|
|||
|
m_NextPlayerButton->setContentAlignment( vgui::Label::a_center );
|
|||
|
m_NextPlayerButton->setBoundKey( (char)255 ); // special no bound to avoid leading spaces in name
|
|||
|
m_NextPlayerButton->addActionSignal( new CSpectatorHandler_Command(this,SPECTATOR_PANEL_CMD_NEXTPLAYER) );
|
|||
|
m_NextPlayerButton->setUnArmedBorderColor ( colorR, colorG, colorB, 0 );
|
|||
|
m_NextPlayerButton->setArmedBorderColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
m_NextPlayerButton->setUnArmedColor ( colorR, colorG, colorB, 0);
|
|||
|
m_NextPlayerButton->setArmedColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
|
|||
|
// Initialize the bottom title.
|
|||
|
|
|||
|
m_BottomMainLabel = new ColorButton( "Spectator Bottom", XRES(390), YRES(6), XRES(200), YRES(20), false, false );
|
|||
|
m_BottomMainLabel->setFont(font);
|
|||
|
m_BottomMainLabel->setParent(m_BottomBorder);
|
|||
|
m_BottomMainLabel->setContentAlignment( vgui::Label::a_center );
|
|||
|
m_BottomMainLabel->addActionSignal( new CSpectatorHandler_Command(this,SPECTATOR_PANEL_CMD_PLAYERS) );
|
|||
|
|
|||
|
m_BottomMainLabel->setUnArmedBorderColor ( colorR, colorG, colorB, 0);
|
|||
|
m_BottomMainLabel->setArmedBorderColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
m_BottomMainLabel->setUnArmedColor ( colorR, colorG, colorB, 0);
|
|||
|
m_BottomMainLabel->setArmedColor ( armedColorR, armedColorR, armedColorR, 0);
|
|||
|
|
|||
|
|
|||
|
|
|||
|
m_menuVisible = true;
|
|||
|
|
|||
|
m_insetVisible = false;
|
|||
|
|
|||
|
m_ExtraInfo->setVisible( false );
|
|||
|
m_Separator->setVisible( false );
|
|||
|
m_TimerImage->setVisible( false );
|
|||
|
|
|||
|
m_TopBorder->setVisible(true);
|
|||
|
m_BottomBorder->setVisible( true );
|
|||
|
|
|||
|
m_overviewButton = new CCheckButton2();
|
|||
|
m_overviewButton->setFont(font);
|
|||
|
m_overviewButton->setParent( m_BottomBorder );
|
|||
|
m_overviewButton->SetText("Overview");
|
|||
|
m_overviewButton->setPos(XRES(10), YRES(6));
|
|||
|
m_overviewButton->setSize(XRES(100), YRES(20));
|
|||
|
m_overviewButton->SetImages("gfx/vgui/640_checkset.tga", "gfx/vgui/640_checkunset.tga");
|
|||
|
m_overviewButton->SetHandler(new Spectator_CheckButtonHandler(this));
|
|||
|
m_overviewButton->SetTextColor(colorR, colorG, colorB, 0);
|
|||
|
|
|||
|
m_firstPersonButton = new CCheckButton2();
|
|||
|
m_firstPersonButton->setFont(font);
|
|||
|
m_firstPersonButton->setParent( m_BottomBorder );
|
|||
|
m_firstPersonButton->SetText("First person");
|
|||
|
m_firstPersonButton->setPos(XRES(10 + 100), YRES(6));
|
|||
|
m_firstPersonButton->setSize(XRES(100), YRES(20));
|
|||
|
m_firstPersonButton->SetImages("gfx/vgui/640_checkset.tga", "gfx/vgui/640_checkunset.tga");
|
|||
|
m_firstPersonButton->SetHandler(new Spectator_CheckButtonHandler(this));
|
|||
|
m_firstPersonButton->SetTextColor(colorR, colorG, colorB, 0);
|
|||
|
|
|||
|
m_autoDirectorButton = new CCheckButton2();
|
|||
|
m_autoDirectorButton->setFont(font);
|
|||
|
m_autoDirectorButton->setParent( m_BottomBorder );
|
|||
|
m_autoDirectorButton->SetText("Auto-director");
|
|||
|
m_autoDirectorButton->setPos(XRES(10 + 200), YRES(6));
|
|||
|
m_autoDirectorButton->setSize(XRES(100), YRES(20));
|
|||
|
m_autoDirectorButton->SetImages("gfx/vgui/640_checkset.tga", "gfx/vgui/640_checkunset.tga");
|
|||
|
m_autoDirectorButton->SetHandler(new Spectator_CheckButtonHandler(this));
|
|||
|
m_autoDirectorButton->SetTextColor(colorR, colorG, colorB, 0);
|
|||
|
|
|||
|
|
|||
|
/*
|
|||
|
m_OverviewData.insetWindowX = 4; // upper left corner
|
|||
|
m_OverviewData.insetWindowY = 4 + SPECTATOR_PANEL_HEIGHT;
|
|||
|
m_OverviewData.insetWindowHeight = 180;
|
|||
|
m_OverviewData.insetWindowWidth = 240;
|
|||
|
|
|||
|
|
|||
|
theDrawInfo.mX = XRES(m_OverviewData.insetWindowX + m_OverviewData.insetWindowWidth + 4);
|
|||
|
theDrawInfo.mY = YRES(SPECTATOR_PANEL_HEIGHT + 4);
|
|||
|
theDrawInfo.mWidth = ScreenWidth() - theDrawInfo.mX - XRES(4);
|
|||
|
theDrawInfo.mHeight = ScreenHeight() - YRES(SPECTATOR_PANEL_HEIGHT + 4) - theDrawInfo.mY;
|
|||
|
*/
|
|||
|
|
|||
|
int theX = XRES(4 + 240 + 4);
|
|||
|
int theY = YRES(SPECTATOR_PANEL_HEIGHT + 4);
|
|||
|
int theWidth = ScreenWidth() - theX - XRES(4);
|
|||
|
int theHeight = ScreenHeight() - YRES(SPECTATOR_PANEL_HEIGHT + 4) - theY;
|
|||
|
|
|||
|
m_overviewControl = new AvHOverviewControl;
|
|||
|
m_overviewControl->setPos(theX, theY);
|
|||
|
m_overviewControl->setSize(theWidth, theHeight);
|
|||
|
m_overviewControl->setParent(this);
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
void SpectatorPanel::ShowMenu(bool isVisible)
|
|||
|
{
|
|||
|
|
|||
|
if ( !isVisible )
|
|||
|
{
|
|||
|
gViewPort->HideCommandMenu();
|
|||
|
}
|
|||
|
|
|||
|
m_menuVisible = isVisible;
|
|||
|
|
|||
|
gViewPort->UpdateCursorState();
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
void SpectatorPanel::EnableInsetView(bool isEnabled)
|
|||
|
{
|
|||
|
|
|||
|
|
|||
|
int x = gHUD.m_Spectator.m_OverviewData.insetWindowX;
|
|||
|
int y = gHUD.m_Spectator.m_OverviewData.insetWindowY;
|
|||
|
int wide = gHUD.m_Spectator.m_OverviewData.insetWindowWidth;
|
|||
|
int tall = gHUD.m_Spectator.m_OverviewData.insetWindowHeight;
|
|||
|
int offset = x + wide + 2;
|
|||
|
|
|||
|
if ( isEnabled )
|
|||
|
{
|
|||
|
// short black bar to see full inset
|
|||
|
m_TopBorder->setBounds( XRES(offset), 0, XRES(640 - offset ), YRES(SPECTATOR_PANEL_HEIGHT) );
|
|||
|
|
|||
|
if ( gEngfuncs.IsSpectateOnly() )
|
|||
|
{
|
|||
|
m_TopBanner->setVisible( true );
|
|||
|
m_TopBanner->setPos( XRES(offset), 0 );
|
|||
|
}
|
|||
|
else
|
|||
|
m_TopBanner->setVisible( false );
|
|||
|
|
|||
|
}
|
|||
|
else
|
|||
|
{
|
|||
|
// full black bar, no inset border
|
|||
|
// show banner only in real HLTV mode
|
|||
|
if ( gEngfuncs.IsSpectateOnly() )
|
|||
|
{
|
|||
|
m_TopBanner->setVisible( true );
|
|||
|
m_TopBanner->setPos( 0,0 );
|
|||
|
}
|
|||
|
else
|
|||
|
m_TopBanner->setVisible( false );
|
|||
|
|
|||
|
m_TopBorder->setBounds( 0, 0, ScreenWidth(), YRES(SPECTATOR_PANEL_HEIGHT) );
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
m_insetVisible = isEnabled;
|
|||
|
|
|||
|
Update();
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
void SpectatorPanel::Update()
|
|||
|
{
|
|||
|
|
|||
|
// Update the check boxes.
|
|||
|
m_overviewButton->SetChecked(gHUD.m_Spectator.IsInOverviewMode());
|
|||
|
m_overviewButton->setVisible(gHUD.GetIsNSMode());
|
|||
|
|
|||
|
m_firstPersonButton->SetChecked(g_iUser1 == OBS_IN_EYE);
|
|||
|
|
|||
|
m_autoDirectorButton->SetChecked(CVAR_GET_FLOAT("spec_autodirector") != 0);
|
|||
|
m_autoDirectorButton->setVisible(gEngfuncs.IsSpectateOnly());
|
|||
|
|
|||
|
m_overviewControl->setVisible(gHUD.m_Spectator.IsInOverviewMode());
|
|||
|
|
|||
|
int iTextWidth, iTextHeight;
|
|||
|
int iTimeHeight, iTimeWidth;
|
|||
|
int offset,j;
|
|||
|
|
|||
|
// TODO Max: Figure out what this is for.
|
|||
|
|
|||
|
if ( m_insetVisible )
|
|||
|
offset = gHUD.m_Spectator.m_OverviewData.insetWindowX + gHUD.m_Spectator.m_OverviewData.insetWindowWidth + 2;
|
|||
|
else
|
|||
|
offset = 0;
|
|||
|
|
|||
|
//bool visible = gHUD.m_Spectator.m_drawstatus->value != 0;
|
|||
|
bool visible = true;
|
|||
|
|
|||
|
m_ExtraInfo->setVisible( visible );
|
|||
|
m_TimerImage->setVisible( visible );
|
|||
|
m_CurrentTime->setVisible( visible );
|
|||
|
m_Separator->setVisible( visible );
|
|||
|
|
|||
|
for ( j= 0; j < TEAM_NUMBER; j++ )
|
|||
|
m_TeamScores[j]->setVisible( visible );
|
|||
|
|
|||
|
if ( !visible )
|
|||
|
return;
|
|||
|
|
|||
|
m_ExtraInfo->getTextSize( iTextWidth, iTextHeight );
|
|||
|
m_CurrentTime->getTextSize( iTimeWidth, iTimeHeight );
|
|||
|
|
|||
|
iTimeWidth += XRES ( 14 ); // +timer icon
|
|||
|
iTimeWidth += ( 4-(iTimeWidth%4) );
|
|||
|
|
|||
|
if ( iTimeWidth > iTextWidth )
|
|||
|
iTextWidth = iTimeWidth;
|
|||
|
|
|||
|
int xPos = ScreenWidth() - ( iTextWidth + XRES ( 4 + offset ) );
|
|||
|
|
|||
|
m_ExtraInfo->setBounds( xPos, YRES( 1 ), iTextWidth, iTextHeight );
|
|||
|
|
|||
|
m_TimerImage->setBounds( xPos, YRES( 2 ) + iTextHeight , XRES(14), YRES(14) );
|
|||
|
|
|||
|
m_CurrentTime->setBounds( xPos + XRES ( 14 + 1 ), YRES( 2 ) + iTextHeight , iTimeWidth, iTimeHeight );
|
|||
|
|
|||
|
m_Separator->setPos( ScreenWidth() - ( iTextWidth + XRES ( 4+2+4+offset ) ) , YRES( 1 ) );
|
|||
|
m_Separator->setSize( XRES( 4 ), YRES( SPECTATOR_PANEL_HEIGHT - 2 ) );
|
|||
|
|
|||
|
for ( j= 0; j < TEAM_NUMBER; j++ )
|
|||
|
{
|
|||
|
int iwidth, iheight;
|
|||
|
|
|||
|
m_TeamScores[j]->getTextSize( iwidth, iheight );
|
|||
|
m_TeamScores[j]->setBounds( ScreenWidth() - ( iTextWidth + XRES ( 4+2+4+2+offset ) + iwidth ), YRES( 1 ) + ( iheight * j ), iwidth, iheight );
|
|||
|
}
|
|||
|
|
|||
|
}
|