/*** * * Copyright (C) 2002 The Wastes Project, All Rights Reserved. * * This product contains software technology from Valve Software, LLC, * Copyright © 1996-2001, Valve LLC, All rights reserved. * * Use, distribution, and modification of this source code and/or resulting * object code is restricted to non-commercial enhancements to products from * The Wastes Project. All other use, distribution, or modification is prohibited * without written permission from The Wastes Project. * ***/ #include "VGUI_TextImage.h" #include "hud.h" #include "cl_util.h" #include "tw_vgui.h" #include "vgui_TheWastesViewport.h" #include "tw_common.h" #include #define INFO_PANEL_X XRES(236) #define INFO_PANEL_Y YRES(188) #define INFO_PANEL_SIZE_X XRES(328) #define INFO_PANEL_SIZE_Y YRES(220) #define IMAGE_PANEL_X XRES(236) #define IMAGE_PANEL_Y YRES(34) #define IMAGE_PANEL_SIZE_X XRES(328) #define IMAGE_PANEL_SIZE_Y YRES(76) #define LIST_BUTTON_X XRES(68) #define LIST_BUTTON_Y YRES(34) #define MAIN_BUTTON_X XRES(68) #define MAIN_BUTTON_Y YRES(416) #define BUTTON_SIZE_X XRES(160) //#define BUTTON_SIZE_Y YRES(30) // Important: // join_game -> join this game // setweapons -> set weapons command, 5 arguments like setweapons -1 -1 -1 -1 -1 // setrandom -> random weaps // unsetrandom -> non random weaps // spectate -> spectate this game class CItemList; /* ========== CInformationPanel ========== */ class CInformationPanel : public CTransparentPanel { public: CInformationPanel( int x, int y, int wide, int tall ); void SetInfo( char *pszClassname ); private: ScrollPanel *m_pScrollPanel; TextPanel *m_pTextPanel; CImageLabel *m_pImageLabel; char m_szClassname[128]; }; /* ========== CItemSelectionPanel ========== */ class CItemSelectionPanel : public CMenuPanel { public: CItemSelectionPanel(int x,int y,int wide,int tall); ~CItemSelectionPanel(); void paintBackground(); void SetInfo(char *pszClassname); void SetImage( char *pszClassname, int iIndex ); void AddItem( playeritemlist_t *pList, int iSlot, int iIndex ); void SendItems(); private: CImageLabel *m_pImageLabels[5]; CItemList *m_pItemList; CInformationPanel *m_pInformationPanel; int m_iWeaponIndices[5]; }; /* ========== CItemSelectionPanel_Create Used by external modules to spawn this item selection code ========== */ CMenuPanel *CItemSelectionPanel_Create(int x,int y,int wide,int tall) { return new CItemSelectionPanel(x,y,wide,tall); } /* ========== CItemListHandler_NewItemList ========== */ enum e_itemcategories { ITEM_MELEE = 0, ITEM_SIDEARMS, ITEM_PRIMARY, ITEM_UNIQUE, ITEM_EXPLOSIVES, ITEM_BACK, }; class CItemListHandler_NewItemList : public ActionSignal { public: CItemListHandler_NewItemList(int iCategory,CItemList *pItemList); virtual void actionPerformed(Panel *panel); private: int m_iCategory; CItemList *m_pOldItemList; }; /* ========== CHandler_SendChanges ========== */ class CHandler_SendChanges : public ActionSignal { public: CHandler_SendChanges(CItemSelectionPanel *pPanel) { m_pInfoPanel = pPanel; } virtual void actionPerformed(Panel *panel) { m_pInfoPanel->SendItems(); } private: CItemSelectionPanel *m_pInfoPanel; }; /* ========== CItemButtonHandler_SetItem ========== */ class CItemButtonHandler_SetItem : public ActionSignal { public: CItemButtonHandler_SetItem( playeritemlist_t *pList, int iSlot, int iIndex, CItemSelectionPanel *pPanel) : m_pList( pList ), m_iWeaponIndex( iIndex ), m_iWeaponSlot( iSlot ), m_pPanel( pPanel ) { } virtual void actionPerformed(Panel *panel) { m_pPanel->AddItem( m_pList, m_iWeaponSlot, m_iWeaponIndex ); } private: CItemSelectionPanel *m_pPanel; playeritemlist_t *m_pList; int m_iWeaponIndex; int m_iWeaponSlot; }; /* ========== CommandButtonShaded ========== */ class CommandButtonShaded : public CommandButton { public: CommandButtonShaded(const char *text,int x,int y,int wide,int tall,bool bNoHighlight); void paint(); }; CommandButtonShaded::CommandButtonShaded(const char *text,int x,int y,int wide,int tall,bool bNoHighlight = 0) : CommandButton(text,x,y,wide,tall,bNoHighlight) { } void CommandButtonShaded::paint() { if(!isArmed()) { drawSetColor(TW_PANEL_BG_RGBA); drawFilledRect(0,0,_size[0],_size[1]); } CommandButton::paint(); } /* ========== ItemButtonShaded ========== */ class ItemButtonShaded : public CommandButtonShaded { public: ItemButtonShaded(const char *classname,int x,int y,int wide,int tall,bool bNoHighlight); void setParent(Panel *newParent); void paint(); private: char m_szClassname[128]; }; ItemButtonShaded::ItemButtonShaded(const char *classname,int x,int y,int wide,int tall,bool bNoHighlight = 0) : CommandButtonShaded(classname,x,y,wide,tall,bNoHighlight) { char szRealText[128]; strcpy(m_szClassname,classname); // Localize the text on the buttons sprintf(szRealText,"#ItemList_%s",classname); setText(CHudTextMessage::BufferedLocaliseTextString(szRealText)); } void ItemButtonShaded::setParent(Panel *newParent) { CommandButtonShaded::setParent(newParent); } void ItemButtonShaded::paint() { CommandButtonShaded::paint(); if(isArmed()) { CItemSelectionPanel *pPanel = (CItemSelectionPanel*)getParent(); if(pPanel != NULL) pPanel->SetInfo(m_szClassname); } } /* ========== CItemList Base class to show vgui buttons pertaining to categories of weapons ========== */ class CItemList { public: CItemList(CItemSelectionPanel *pPanel, playeritemlist_t *pList, int iSlot, int iNextSlot ) : m_pParentPanel( pPanel ), m_pItemArray( pList ), m_iSlot( iSlot ), m_iNextSlot( iNextSlot ) { } virtual ~CItemList() { for( int i = 0;i < m_ItemButtons.size();i++ ) { m_pParentPanel->removeChild( m_ItemButtons[i] ); } } void BuildButtons() { int iButtonPosY = LIST_BUTTON_Y; for( int i = 0;i < m_pItemArray->size; i++ ) { playeritem_t *pItem = &m_pItemArray->array[i]; ItemButtonShaded *newButton; newButton = new ItemButtonShaded( pItem->weapon_classname, LIST_BUTTON_X, iButtonPosY, BUTTON_SIZE_X, BUTTON_SIZE_Y ); newButton->setParent( m_pParentPanel ); newButton->addActionSignal( new CItemButtonHandler_SetItem( m_pItemArray, m_iSlot, i, m_pParentPanel ) ); newButton->addActionSignal( new CItemListHandler_NewItemList(m_iNextSlot,this) ); m_ItemButtons.push_back( newButton ); iButtonPosY += BUTTON_SIZE_Y + YRES(8); } CommandButtonShaded *backButton; backButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Back"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); backButton->setParent( m_pParentPanel ); backButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_BACK,this)); m_ItemButtons.push_back( backButton ); m_iNumButtons = ++i; } playeritemlist_t *m_pItemArray; int m_iSlot,m_iNextSlot; CItemSelectionPanel *m_pParentPanel; public: std::vector m_ItemButtons; int m_iNumButtons; }; class CMainCategories : public CItemList { public: CMainCategories(CItemSelectionPanel *pPanel, playeritemlist_t *pList ) : CItemList(pPanel, pList, -1, -1) { int iButtonPosY = LIST_BUTTON_Y; m_pMeleeButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Melee"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); m_pMeleeButton->setParent(m_pParentPanel); m_pMeleeButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_MELEE,this)); iButtonPosY += BUTTON_SIZE_Y + YRES(8); m_pSidearmsButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Sidearms"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); m_pSidearmsButton->setParent(m_pParentPanel); m_pSidearmsButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_SIDEARMS,this)); iButtonPosY += BUTTON_SIZE_Y + YRES(8); m_pSecondaryButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Secondary"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); m_pSecondaryButton->setParent(m_pParentPanel); m_pSecondaryButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_PRIMARY,this)); iButtonPosY += BUTTON_SIZE_Y + YRES(8); m_pExplosivesButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Explosives"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); m_pExplosivesButton->setParent(m_pParentPanel); m_pExplosivesButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_EXPLOSIVES,this)); // No uniques for now :| /* iButtonPosY += BUTTON_SIZE_Y + YRES(8); m_pUniqueButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#ItemList_Unique"),LIST_BUTTON_X,iButtonPosY,BUTTON_SIZE_X,BUTTON_SIZE_Y); m_pUniqueButton->setParent(m_pParentPanel); m_pUniqueButton->addActionSignal(new CItemListHandler_NewItemList(ITEM_UNIQUE,this)); */ iButtonPosY += BUTTON_SIZE_Y + YRES(8); } ~CMainCategories() { m_pParentPanel->removeChild(m_pMeleeButton); m_pParentPanel->removeChild(m_pSidearmsButton); m_pParentPanel->removeChild(m_pSecondaryButton); m_pParentPanel->removeChild(m_pExplosivesButton); // m_pParentPanel->removeChild(m_pUniqueButton); } private: CommandButtonShaded *m_pMeleeButton; CommandButtonShaded *m_pSidearmsButton; CommandButtonShaded *m_pSecondaryButton; CommandButtonShaded *m_pExplosivesButton; // CommandButtonShaded *m_pUniqueButton; }; /* CItemSelectionPanel methods */ CItemSelectionPanel::CItemSelectionPanel(int x,int y,int wide,int tall) : CMenuPanel(100,false,x,y,wide,tall) { memset( m_iWeaponIndices, -1, sizeof( m_iWeaponIndices ) ); // Start up selection images for(int i = 0;i < 5;i++) { m_pImageLabels[i] = new CImageLabel("",0,0); m_pImageLabels[i]->setParent(this); m_pImageLabels[i]->setVisible(false); } // Load the item manager m_pItemList = new CMainCategories(this, NULL ); // Information Panel m_pInformationPanel = new CInformationPanel(INFO_PANEL_X,INFO_PANEL_Y,INFO_PANEL_SIZE_X,INFO_PANEL_SIZE_Y); m_pInformationPanel->setParent(this); m_pInformationPanel->setVisible(true); int iButtonPosX = MAIN_BUTTON_X; CommandButtonShaded *pOkButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#Menu_JoinGame"), iButtonPosX, MAIN_BUTTON_Y, BUTTON_SIZE_X, BUTTON_SIZE_Y ); pOkButton->setParent(this); // pOkButton->addActionSignal(new CMenuHandler_TextWindow(HIDE_TEXTWINDOW)); pOkButton->addActionSignal(new CHandler_SendChanges(this)); iButtonPosX += XRES(168); CommandButtonShaded *pRandomButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#Menu_Random"), iButtonPosX,MAIN_BUTTON_Y, BUTTON_SIZE_X, BUTTON_SIZE_Y ); pRandomButton->setParent(this); pRandomButton->addActionSignal(new CMenuHandler_TextWindow(HIDE_TEXTWINDOW)); pRandomButton->addActionSignal(new CMenuHandler_StringCommand("setrandom")); pRandomButton->addActionSignal(new CMenuHandler_StringCommand("join_game")); iButtonPosX += XRES(168); CommandButtonShaded *pSpectateButton = new CommandButtonShaded(CHudTextMessage::BufferedLocaliseTextString("#Menu_Spectate"), iButtonPosX, MAIN_BUTTON_Y, BUTTON_SIZE_X,BUTTON_SIZE_Y ); pSpectateButton->setParent(this); pSpectateButton->addActionSignal(new CMenuHandler_TextWindow(HIDE_TEXTWINDOW)); pSpectateButton->addActionSignal(new CMenuHandler_StringCommand("spectate")); } CItemSelectionPanel::~CItemSelectionPanel() { delete m_pItemList; for( int i = 0;i < 5;i++ ) delete m_pImageLabels[i]; } void CItemSelectionPanel::SetInfo(char *pszClassname) { m_pInformationPanel->SetInfo(pszClassname); } void CItemSelectionPanel::SetImage(char *pszClassname,int iIndex) { // Show image char szImageName[128]; sprintf(szImageName,"inv_%s",pszClassname); m_pImageLabels[iIndex]->NewImage(szImageName); m_pImageLabels[iIndex]->setVisible(true); m_pImageLabels[iIndex]->setImageColor(Color(255,255,255,160)); // Slightly faded // Set image bounds int x, y; int w,h; w = m_pImageLabels[iIndex]->getImageWide(); h = m_pImageLabels[iIndex]->getImageTall(); switch( iIndex ) { case 0: x = IMAGE_PANEL_X; y = IMAGE_PANEL_Y; break; case 1: x = IMAGE_PANEL_X; y = IMAGE_PANEL_Y + h + YRES(8); break; case 2: x = IMAGE_PANEL_X + w + XRES(8); y = IMAGE_PANEL_Y; break; case 3: case 4: x = IMAGE_PANEL_X + w + XRES(8); y = IMAGE_PANEL_Y + h + YRES(8); break; } m_pImageLabels[iIndex]->setPos( x, y ); } void CItemSelectionPanel::paintBackground() { drawSetColor(TW_PANEL_BORDER_RGBA); drawOutlinedRect(0,0,_size[0],_size[1]); } void CItemSelectionPanel::AddItem( playeritemlist_t *pList, int iSlot, int iIndex ) { m_iWeaponIndices[iSlot] = iIndex; SetImage( pList->array[iIndex].weapon_classname, iSlot ); } void CItemSelectionPanel::SendItems() { // Must have a melee or backup weapon to spawn. if( m_iWeaponIndices[0] == -1 ) { gEngfuncs.pfnCenterPrint( "Must choose a melee weapon" ); return; } gViewPort->HideTopMenu(); char szText[64]; sprintf( szText, "setweapons %i %i %i %i %i", m_iWeaponIndices[0], m_iWeaponIndices[1], m_iWeaponIndices[2], m_iWeaponIndices[3], m_iWeaponIndices[4] ); gEngfuncs.pfnClientCmd( "unsetrandom" ); gEngfuncs.pfnClientCmd( szText ); gEngfuncs.pfnClientCmd( "join_game" ); } /* CInformationPanel methods */ CInformationPanel::CInformationPanel(int x,int y,int wide,int tall) : CTransparentPanel(0,x,y,wide,tall) { memset( m_szClassname, 0, sizeof( m_szClassname ) ); m_pImageLabel = new CImageLabel("",0,0); m_pImageLabel->setParent(this); m_pImageLabel->setVisible(false); // Get the scheme used for the Titles CSchemeManager *pSchemes = gViewPort->GetSchemeManager(); // schemes SchemeHandle_t hTitleScheme = pSchemes->getSchemeHandle( "Title Font" ); SchemeHandle_t hMOTDText = pSchemes->getSchemeHandle( "Briefing Text" ); // color schemes int r, g, b, a; m_pScrollPanel = new CTFScrollPanel(XRES(16),YRES(16), wide - XRES(32), tall - YRES(32)); m_pScrollPanel->setParent(this); // force scrollbars on to set clientClip m_pScrollPanel->setScrollBarAutoVisible(false, false); m_pScrollPanel->setScrollBarVisible(true, true); m_pScrollPanel->validate(); m_pTextPanel = new TextPanel("",0,0,64,64); m_pTextPanel->setParent(m_pScrollPanel->getClient()); // Set font m_pTextPanel->setFont(pSchemes->getFont(hMOTDText)); pSchemes->getFgColor(hMOTDText,r,g,b,a); m_pTextPanel->setFgColor(r,g,b,a); pSchemes->getBgColor(hMOTDText,r,g,b,a); m_pTextPanel->setBgColor(r,g,b,a); } void CInformationPanel::SetInfo( char *pszClassname ) { // Dont update if we are already showing info if( strcmp( pszClassname, m_szClassname ) == 0 ) return; strcpy( m_szClassname, pszClassname ); // Show image char szImageName[128]; sprintf(szImageName,"info_%s",pszClassname); m_pImageLabel->NewImage(szImageName); m_pImageLabel->setVisible(true); m_pImageLabel->setImageColor(Color(255,255,255,160)); // Slightly faded // Set image bounds int w,h; getSize(w,h); m_pImageLabel->setPos(w/2 - m_pImageLabel->getImageWide()/2,h/2 - m_pImageLabel->getImageTall()/2); // Set text char szLocalizedClass[128]; sprintf(szLocalizedClass,"#Information_%s",pszClassname); m_pTextPanel->setText(CHudTextMessage::BufferedLocaliseTextString(szLocalizedClass)); // Get the total size of the MOTD text and resize the text panel int iScrollSizeX, iScrollSizeY; // First, set the size so that the client's width is correct at least because the // width is critical for getting the "wrapped" size right. // You'll see a horizontal scroll bar if there is a single word that won't wrap in the // specified width. m_pTextPanel->getTextImage()->setSize(m_pScrollPanel->getClientClip()->getWide(), m_pScrollPanel->getClientClip()->getTall()); m_pTextPanel->getTextImage()->getTextSizeWrapped( iScrollSizeX, iScrollSizeY ); // Now resize the textpanel to fit the scrolled size m_pTextPanel->setSize( iScrollSizeX , iScrollSizeY ); //turn the scrollbars back into automode m_pScrollPanel->setScrollBarAutoVisible(true, true); m_pScrollPanel->setScrollBarVisible(false, false); m_pScrollPanel->validate(); } /* CItemListHandler_NewItemList methods */ CItemListHandler_NewItemList::CItemListHandler_NewItemList(int iCategory,CItemList *pItemList) { m_iCategory = iCategory; m_pOldItemList = pItemList; } void CItemListHandler_NewItemList::actionPerformed(Panel *panel) { CItemSelectionPanel *pParent = m_pOldItemList->m_pParentPanel; delete m_pOldItemList; switch( m_iCategory ) { case ITEM_MELEE: m_pOldItemList = new CItemList( pParent, &g_MeleeItems, ITEM_MELEE, ITEM_SIDEARMS ); m_pOldItemList->BuildButtons(); break; case ITEM_SIDEARMS: m_pOldItemList = new CItemList( pParent, &g_SidearmItems, ITEM_SIDEARMS, ITEM_PRIMARY ); m_pOldItemList->BuildButtons(); break; case ITEM_PRIMARY: m_pOldItemList = new CItemList( pParent, &g_PrimaryItems, ITEM_PRIMARY, ITEM_EXPLOSIVES ); m_pOldItemList->BuildButtons(); break; /* case ITEM_UNIQUE: m_pOldItemList = new CItemList( pParent, &g_UniqueItems, 3 ); m_pOldItemList->BuildButtons(); break;*/ case ITEM_EXPLOSIVES: m_pOldItemList = new CItemList( pParent, &g_OtherItems, ITEM_EXPLOSIVES, ITEM_BACK ); m_pOldItemList->BuildButtons(); break; case ITEM_BACK: m_pOldItemList = new CMainCategories( pParent, NULL ); break; } }