(C++) chatQue class [v0.1 OLD]

Post those lines of code you feel like sharing or find what you require for your project here; or simply use them as tutorials.
Locked
Rambus
Posts: 96
Joined: Thu Nov 24, 2005 4:56 pm
Location: Canada
Contact:

(C++) chatQue class [v0.1 OLD]

Post by Rambus »

ChatQue is a object for simulating half-life style chat display capable of custom colors, fading away, shadows and any custom font.

The latest version of the code is available at:
www.g0dsoft.com/irrlicht/chatQue/

Image

Example Usage

Code: Select all

//Init code
ChatQue que(device,rect<s32>(0,0,100,100),5000,true,500);
que.addMessage(L"Hello world!");
//que.setDebug(true); //Usefull for visualising the draw surface.
//Just befor you call driver->endScene();
que.draw();
chatQue.h

Code: Select all

/*
chatQue is copyright g0dsoft 2006
Version: 0.1
Code by: Mark Laprairie
Contact: webmaster@g0dsoft.com
Url: www.g0dsoft.com

chatQue.h
ChatQue is a object for simulating half-life style chat display
capable of colors, fading away, shadows and any custom font.

Example usage
ChatQue que(device,rect<s32>(0,0,100,100),5000,true,500);
que.addMessage(L"Hello world!");
//Just befor you call driver->endScene();
que.draw();

ToDo:
     -Length clipping for text that leaves the rect.
     -Word wrapping.
(If you make these changes,  make sure to tell me!)

*/

#ifndef __CHATQUE_H__
#define __CHATQUE_H__

#define CHATQUE_STRINGLENGTH 240

#include <irrlicht.h>
#include <list>

using namespace irr;
using namespace core;
using namespace scene;
using namespace video;
using namespace io;
using namespace gui;

using namespace std;

class ChatQue {
public:
    //Constructor
    ChatQue(IrrlichtDevice * device,const core::rect<s32> drawArea,float textLife = 5000, bool setFade = false, float fadeTime = 1000.00, bool setShadows = true);
    ~ChatQue();
    //Main Functions
    void addMessage(const wchar_t* text,SColor chatColor = SColor(255,255,255,255),SColor chatColorShadow = SColor(255,0,0,0));

    void addMessage(wchar_t* text,SColor chatColor = SColor(255,255,255,255),SColor chatColorShadow = SColor(255,0,0,0));
    void addMessage(core::stringw text,SColor chatColor = SColor(255,255,255,255),SColor chatColorShadow = SColor(255,0,0,0));

    void draw();
    
    void setFade(bool setFade = true);
    void setRect(const core::rect<s32> drawArea);
    void setFadeTime(float fadeTime = 1000.00);
    void setFont(irr::gui::IGUIFont* font);
    void setMaxLines(unsigned short maxLines);
    void setShadows(bool setShadows = true);
    void setVisible(bool setVisible = true);
    void setLife(float setLife = 1000);
    void setDebug(bool setDebug = true);
    
protected: 
    //Helper functions
    void chatQue_calculateRect(const core::rect<s32> drawArea);
    void chatQue_calculateFontHeight(irr::gui::IGUIFont* font);
    void chatQue_calculateMaxLines();
    
    struct chatQueMessage{
        wchar_t message[CHATQUE_STRINGLENGTH];
        SColor chatColor;
        SColor chatColorShadow;
        SColor chatColorFade;
        SColor chatColorShadowFade;
        float created;
        float fade;
        bool chatQue_memoryManaged;
    };  
    
    //Rect replacment
    unsigned int m_xWidth;
    unsigned int m_yHeight;
    unsigned int m_y;
    unsigned int m_x; 
    //Font height
    unsigned short m_fontHeight;
    
    IrrlichtDevice* chatQue_device;
    bool chatQue_fade;
    bool chatQue_shadows;
    bool chatQue_visible;
    bool chatQue_debug;
    float chatQue_fadeTime;
    float chatQue_life;
    unsigned short chatQue_maxLines;
    std::list<chatQueMessage> chatQue_list;
    IGUIFont* chatQue_font;
};

#endif //chatque.h

chatQue.cpp

Code: Select all

/*
chatQue is copyright g0dsoft 2006
Version: 0.1
Code by: Mark Laprairie
Contact: webmaster@g0dsoft.com
Url: www.g0dsoft.com

chatQue.cpp
ChatQue is a object for simulating half-life style chat display
capable of colors, fading away, shadows and any custom font.

Example usage
ChatQue que(device,rect<s32>(0,0,100,100),5000,true,500);
que.addMessage(L"Hello world!");
//Just befor you call driver->endScene();
que.draw();

ToDo:
     -Length clipping for text that leaves the rect.
     -Word wrapping.
*/

#include "chatQue.h"

ChatQue::ChatQue(IrrlichtDevice * device,const core::rect<s32> drawArea,float textLife,bool setFade, float fadeTime, bool setShadows)
{
     chatQue_device = device;
     chatQue_fade = setFade;
     m_fontHeight = 0;
     chatQue_calculateRect(drawArea);
     chatQue_font = device->getGUIEnvironment()->getBuiltInFont();
     setFont(chatQue_font);
     chatQue_life = textLife;
     chatQue_visible = true;
     chatQue_debug = false;
     chatQue_fadeTime = fadeTime;
}

ChatQue::~ChatQue()
{
   std::list<chatQueMessage>::iterator iter;
   for (iter=chatQue_list.begin(); iter != chatQue_list.end(); iter++)
   {     
         if(iter->chatQue_memoryManaged == true)
            delete iter->message;
   }
   chatQue_list.erase(chatQue_list.begin(),chatQue_list.end());
}

void ChatQue::addMessage(wchar_t* text, SColor chatColor, SColor chatColorShadow)
{
   addMessage((const wchar_t*) text,chatColor,chatColorShadow);
}

void ChatQue::addMessage(core::stringw text, SColor chatColor, SColor chatColorShadow)
{
   addMessage((const wchar_t*) text.c_str(),chatColor,chatColorShadow);
}

void ChatQue::addMessage(const wchar_t* text, SColor chatColor, SColor chatColorShadow)
{
     chatQueMessage lmsg;
     wcscpy(lmsg.message,text);
     lmsg.chatColor = chatColor;
     lmsg.chatColorShadow = chatColorShadow;
     lmsg.fade = 0;
     lmsg.chatQue_memoryManaged = false;
     lmsg.created = chatQue_device->getTimer()->getTime();
     chatQue_list.push_front(lmsg);
}

void ChatQue::draw()
{
   //Debug
   if(chatQue_debug && chatQue_visible)
     chatQue_device->getVideoDriver()->draw2DRectangle(video::SColor(100,155,155,255),
          core::rect<s32>(m_x, m_y - m_yHeight,m_x + m_xWidth,m_y));    
   //Main Update/Draw
   std::list<chatQueMessage>::iterator iter;
   unsigned short count = 0;
   unsigned int m_y_tmp = m_y;
   u32 l_time = chatQue_device->getTimer()->getTime();
   for (iter=chatQue_list.begin(); iter != chatQue_list.end(); iter++)
   { 
      //Max lines means no fade, special case delete
      if(count > chatQue_maxLines){
         if(iter->chatQue_memoryManaged == true)
            delete iter->message;
         chatQue_list.erase(iter,chatQue_list.end());
         return;
      }
      //Update
      if((iter->created + chatQue_life) < l_time){
         if(chatQue_fade){
             if(iter->fade == 0){
                 iter->fade = l_time;
                 iter->chatColorFade = iter->chatColor;
                 iter->chatColorShadowFade = iter->chatColorShadow;
             }
             //Fade code
             f32 l_alpha = (   (f32)(l_time - iter->fade)/(f32)chatQue_fadeTime );
             iter->chatColor = iter->chatColorFade.getInterpolated(SColor(0,0,0,0),1-l_alpha);
             iter->chatColorShadow = iter->chatColorShadowFade.getInterpolated(SColor(0,0,0,0),1-l_alpha);
         }
         if( ((l_time - iter->fade) >= chatQue_fadeTime) || !chatQue_fade ){
             if(iter->chatQue_memoryManaged == true)
                delete iter->message;
             chatQue_list.erase(iter,chatQue_list.end());
             return;
         }
      } 
      //Draw
      if (chatQue_visible){
          if (chatQue_font){
             if (chatQue_shadows)
                 chatQue_font->draw(iter->message,
                   core::rect<s32>(m_x + 1,m_y_tmp - m_fontHeight+ 1,m_x+m_xWidth + 1,m_y_tmp + 1),
                   iter->chatColorShadow);        
             
             chatQue_font->draw(iter->message,
               core::rect<s32>(m_x,m_y_tmp - m_fontHeight,m_x+m_xWidth,m_y_tmp),
               iter->chatColor);    
             m_y_tmp -= m_fontHeight;
          }
      }
      count++;
   }
}

//!-- Start Helpers

void ChatQue::chatQue_calculateRect(const core::rect<s32> drawArea)
{
   m_xWidth  = drawArea.getWidth();
   m_yHeight = drawArea.getHeight();
   position2d<s32> l_positionTmp = drawArea.LowerRightCorner;
   m_y = l_positionTmp.Y;
   l_positionTmp = drawArea.UpperLeftCorner;
   m_x = l_positionTmp.X;  
}

void ChatQue::chatQue_calculateFontHeight(irr::gui::IGUIFont* font)
{
     dimension2d<s32> l_fontHeight = chatQue_font->getDimension(L"|");
     m_fontHeight = l_fontHeight.Height;   
}

void ChatQue::chatQue_calculateMaxLines()
{
     chatQue_maxLines = ((m_yHeight - m_fontHeight) / m_fontHeight);     
}

//!-- End Helpers

void ChatQue::setFade(bool setFade)
{
     chatQue_fade = setFade;
}

void ChatQue::setRect(const core::rect<s32> drawArea)
{
     chatQue_calculateRect(drawArea);
}

void ChatQue::setFadeTime(float fadeTime)
{
     chatQue_fadeTime = fadeTime;
}

void ChatQue::setFont(irr::gui::IGUIFont* font)
{    
     chatQue_font = font;
     chatQue_calculateFontHeight(font);
     chatQue_calculateMaxLines();
}

void ChatQue::setLife(float setLife)
{
     chatQue_life = setLife;
}

void ChatQue::setShadows(bool setShadows)
{
     chatQue_shadows = setShadows;
}

void ChatQue::setVisible(bool setVisible)
{
     chatQue_visible = setVisible;
}

void ChatQue::setDebug(bool setDebug)
{
     chatQue_debug = setDebug;
}
Last edited by Rambus on Fri Sep 22, 2006 11:54 pm, edited 1 time in total.
Phxx
Posts: 13
Joined: Wed May 10, 2006 7:55 pm

Post by Phxx »

Awesome, i've always liked the half-life / counter-strike chat :)
stodge
Posts: 216
Joined: Fri Dec 05, 2003 5:57 pm

Post by stodge »

Two things:

1) What's the license?
2) You might want to change addMessage to pop old messages when a set maximum is reached. This would avoid hogging too much memory. You could implement setMaximumSize(int size), with -1 disabling the feature.

Looks good - good job!
hybrid
Admin
Posts: 14143
Joined: Wed Apr 19, 2006 9:20 pm
Location: Oldenburg(Oldb), Germany
Contact:

Post by hybrid »

I'd suggest to inherit from IGUIElement to allow automatic render within gui->drawAll()
And what's the benefit over the other chat classes?
Rambus
Posts: 96
Joined: Thu Nov 24, 2005 4:56 pm
Location: Canada
Contact:

Post by Rambus »

Stodge-
1) What's the license?
Free, Free, no Credit, Free

2) You might want to change addMessage to pop old messages when a set maximum is reached. This would avoid hogging too much memory. You could implement setMaximumSize(int size), with -1 disabling the feature.

MaxLines is calculated based on how many lines will fit in your rendering box (Set on object creation). So if a pile of messages hit the screen at once, ones that get pushed too far up are deleted (I think this is the best solution for minimum client involvement)

I don't know why it's missing from the code, but note that their is a
function in the header void setMaxLines(unsigned short maxLines); to set this manually. I will add the implementation in a few days when I post a new version.

hybrid-
I'll look into making it a IGUIElement. (Thanks for the idea)
There is no chat class like this: This is a simple chat class for replicating Starcraft/warcraft/half-life chat display. Something I needed, and I'm sure other irrlicht users would love.

After talking to some users in #irrlicht, I have added even more functionality to this class while keeping it super easy to use.
-Word Wrap,
-Recalculate rendering box,
-Rainbow text,
-and a bunch more.

Hopefully you guys like this!
stodge
Posts: 216
Joined: Fri Dec 05, 2003 5:57 pm

Post by stodge »

P.S. Que is spelt Queue. :wink:
hybrid
Admin
Posts: 14143
Joined: Wed Apr 19, 2006 9:20 pm
Location: Oldenburg(Oldb), Germany
Contact:

Post by hybrid »

I'm not into this game suff that much, so I can only assess differences if you name it. The other two chats I meant are Acki's GUI extensions and "the other one" I don't remember now.
Rambus
Posts: 96
Joined: Thu Nov 24, 2005 4:56 pm
Location: Canada
Contact:

Post by Rambus »

@stodge- I know, I use que as shorthand- if a bunch of people have a problem with that I will change it.

Sorry hybrid,
basically (from what I know about their gui extensions) they are modified list boxes, allowing for color and possibly a few extra features.
(I could be wrong about this, I havent used them)

The benefits of using my chatQue, is that there is no scroll bar,No item selection or any other features generally not used in halflife/starcraft.

-It can be added with out recompiling the irrlicht source.
-Special effects (shadows, fade, rainbow render)
-Removes items automatically.

My chatQue is basically defined by a draw area and a font.
It automatically does everything else for you.
The text will never leave the draw area (in the next version anyways)
If text is up on screen for too long, it will be removed.
If text is pushed above the box it will be removed
If it goes past the right bound of the box, it will be truncated or wrapped into two/three/etc lines.

If that really didn't help you visualize the differences I don't know what else to say, play starcraft/half-life and see how their chat works.

P.S. I will post the new version in 3 days from today.
CmdKewin
Posts: 29
Joined: Thu Aug 17, 2006 1:49 pm

Post by CmdKewin »

Nice Class, really nice :)

I changed it a bit (mainly remaning stuff), and added a Console_backColor parameter (and relative get/set methods).

Next thing on my list is a Console_Dump function.
bitplane
Admin
Posts: 3204
Joined: Mon Mar 28, 2005 3:45 am
Location: England
Contact:

Post by bitplane »

lock requested by Rambus, new version on the way :)
Submit bugs/patches to the tracker!
Need help right now? Visit the chat room
Locked