summaryrefslogtreecommitdiff
path: root/plugins/MirandaG15/src
diff options
context:
space:
mode:
authorRobert Pösel <robyer@seznam.cz>2013-10-29 18:17:04 +0000
committerRobert Pösel <robyer@seznam.cz>2013-10-29 18:17:04 +0000
commit4d01f5f5096cb4d22c4a7ba17cc82977c7f5f19b (patch)
tree9353d79ddff12a1c2ced3e300d61a516f2572fb5 /plugins/MirandaG15/src
parent2307fd7414d16d4ff936607a215e9a2ca0294741 (diff)
Adopted MirandaG15 plugin
First compilable version and 32-bit only. git-svn-id: http://svn.miranda-ng.org/main/trunk@6681 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c
Diffstat (limited to 'plugins/MirandaG15/src')
-rw-r--r--plugins/MirandaG15/src/CAppletManager.cpp1960
-rw-r--r--plugins/MirandaG15/src/CAppletManager.h193
-rw-r--r--plugins/MirandaG15/src/CChatScreen.cpp800
-rw-r--r--plugins/MirandaG15/src/CChatScreen.h113
-rw-r--r--plugins/MirandaG15/src/CConfig.cpp970
-rw-r--r--plugins/MirandaG15/src/CConfig.h166
-rw-r--r--plugins/MirandaG15/src/CContactList.cpp1174
-rw-r--r--plugins/MirandaG15/src/CContactList.h145
-rw-r--r--plugins/MirandaG15/src/CContactlistScreen.cpp315
-rw-r--r--plugins/MirandaG15/src/CContactlistScreen.h62
-rw-r--r--plugins/MirandaG15/src/CCreditsScreen.cpp266
-rw-r--r--plugins/MirandaG15/src/CCreditsScreen.h53
-rw-r--r--plugins/MirandaG15/src/CEvent.h71
-rw-r--r--plugins/MirandaG15/src/CEventLog.cpp120
-rw-r--r--plugins/MirandaG15/src/CEventLog.h46
-rw-r--r--plugins/MirandaG15/src/CEventScreen.cpp239
-rw-r--r--plugins/MirandaG15/src/CEventScreen.h51
-rw-r--r--plugins/MirandaG15/src/CIRCConnection.h12
-rw-r--r--plugins/MirandaG15/src/CIRCHistory.h23
-rw-r--r--plugins/MirandaG15/src/CNotificationScreen.cpp374
-rw-r--r--plugins/MirandaG15/src/CNotificationScreen.h95
-rw-r--r--plugins/MirandaG15/src/CProtocolData.h13
-rw-r--r--plugins/MirandaG15/src/CScreen.cpp180
-rw-r--r--plugins/MirandaG15/src/CScreen.h47
-rw-r--r--plugins/MirandaG15/src/CScreensaverScreen.cpp200
-rw-r--r--plugins/MirandaG15/src/CScreensaverScreen.h51
-rw-r--r--plugins/MirandaG15/src/Miranda.cpp223
-rw-r--r--plugins/MirandaG15/src/Miranda.h4
-rw-r--r--plugins/MirandaG15/src/StdAfx.h53
-rw-r--r--plugins/MirandaG15/src/m_metacontacts.h166
30 files changed, 8185 insertions, 0 deletions
diff --git a/plugins/MirandaG15/src/CAppletManager.cpp b/plugins/MirandaG15/src/CAppletManager.cpp
new file mode 100644
index 0000000000..8eb965f0a3
--- /dev/null
+++ b/plugins/MirandaG15/src/CAppletManager.cpp
@@ -0,0 +1,1960 @@
+#include "stdafx.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+#include "m_system.h"
+
+// specifies how long contact status notifications are ignored after signon
+#define PROTOCOL_NOTIFY_DELAY 1500
+
+//########################################################################
+// functions
+//########################################################################
+
+//************************************************************************
+// returns the AppletManager's instance
+//************************************************************************
+CAppletManager *CAppletManager::GetInstance()
+{
+ return (CAppletManager*)CLCDOutputManager::GetInstance();
+}
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CAppletManager::CAppletManager()
+{
+ m_uiTimer = NULL;
+ m_pLastScreen = NULL;
+
+
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CAppletManager::~CAppletManager()
+{
+
+}
+
+//************************************************************************
+// Initializes the AppletManager
+//************************************************************************
+bool CAppletManager::Initialize(tstring strAppletName)
+{
+ if(!CLCDOutputManager::Initialize(strAppletName))
+ return false;
+
+ GetLCDConnection()->Connect(CConfig::GetIntSetting(DEVICE));
+
+ // set the volumewheel hook
+ SetVolumeWheelHook();
+
+ // initialize the screens
+ m_NotificationScreen.Initialize();
+ m_EventScreen.Initialize();
+ m_ContactlistScreen.Initialize();
+ m_ChatScreen.Initialize();
+ m_CreditsScreen.Initialize();
+ m_ScreensaverScreen.Initialize();
+
+ // add the screens to the list
+ AddScreen(&m_NotificationScreen);
+ AddScreen(&m_EventScreen);
+ AddScreen(&m_ContactlistScreen);
+ AddScreen(&m_ChatScreen);
+ AddScreen(&m_CreditsScreen);
+ AddScreen(&m_ScreensaverScreen);
+
+ // activate the event screen
+ ActivateScreen(&m_EventScreen);
+
+ // hook the neccessary events
+ m_hMIHookMessageWindowEvent = HookEvent(ME_MSG_WINDOWEVENT,CAppletManager::HookMessageWindowEvent);
+ m_hMIHookEventAdded = HookEvent(ME_DB_EVENT_ADDED, CAppletManager::HookEventAdded);
+ m_hMIHookStatusChanged = HookEvent(ME_DB_CONTACT_SETTINGCHANGED, CAppletManager::HookStatusChanged);
+ m_hMIHookProtoAck = HookEvent(ME_PROTO_ACK, CAppletManager::HookProtoAck);
+ m_hMIHookContactDeleted = HookEvent(ME_DB_CONTACT_DELETED, CAppletManager::HookContactDeleted);
+ m_hMIHookContactAdded = HookEvent(ME_DB_CONTACT_ADDED, CAppletManager::HookContactAdded);
+ m_hMIHookSettingChanged = HookEvent(ME_DB_CONTACT_SETTINGCHANGED,CAppletManager::HookSettingChanged);
+ m_hMIHookContactIsTyping = HookEvent(ME_PROTO_CONTACTISTYPING,CAppletManager::HookContactIsTyping);
+
+ // enumerate protocols
+ int iCount;
+ int iProtoCount = 0;
+ PROTOACCOUNT **ppAccounts;
+ CProtocolData *pProtoData = NULL;
+ CIRCConnection *pIRCConnection = NULL;
+
+ CallService(MS_PROTO_ENUMACCOUNTS,(WPARAM)&iCount,(LPARAM)&ppAccounts);
+ for(int i=0;i<iCount;i++)
+ {
+ /**if(ppProtocolDescriptor[i]->type != PROTOTYPE_PROTOCOL)
+ continue;**/
+ if (ppAccounts[i]->bIsEnabled == 0)
+ continue;
+
+ iProtoCount++;
+ pProtoData = new CProtocolData();
+ pProtoData->iStatus = ID_STATUS_OFFLINE;
+ pProtoData->strProtocol = toTstring(ppAccounts[i]->szModuleName);
+ pProtoData->lTimeStamp = 0;
+
+ // try to create an irc connection for that protocol (will fail if it is no irc protocol)
+ pIRCConnection = CreateIRCConnection(pProtoData->strProtocol);
+
+ m_vProtocolData.push_back(pProtoData);
+ }
+
+ // load status bitmaps
+ m_ahStatusBitmaps[0] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_OFFLINE),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[1] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_ONLINE),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[2] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_AWAY),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[3] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_NA),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[4] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_OCCUPIED),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[5] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_DND),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[6] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_INVISIBLE),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ m_ahStatusBitmaps[7] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_STATUS_FFC),
+ IMAGE_BITMAP,5, 5, LR_MONOCHROME);
+ // Load event bitmaps
+ m_ahEventBitmaps[0] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_MSG),
+ IMAGE_BITMAP,6, 6, LR_MONOCHROME);
+ m_ahEventBitmaps[1] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_CON),
+ IMAGE_BITMAP,6, 6, LR_MONOCHROME);
+ m_ahEventBitmaps[2] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_USER),
+ IMAGE_BITMAP,6, 6, LR_MONOCHROME);
+ m_ahEventBitmaps[3] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_INFO),
+ IMAGE_BITMAP,6, 6, LR_MONOCHROME);
+
+ m_ahLargeEventBitmaps[0] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_MSG_LARGE),
+ IMAGE_BITMAP,8, 8, LR_MONOCHROME);
+ m_ahLargeEventBitmaps[1] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_CON_LARGE),
+ IMAGE_BITMAP,8, 8, LR_MONOCHROME);
+ m_ahLargeEventBitmaps[2] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_USER_LARGE),
+ IMAGE_BITMAP,8, 8, LR_MONOCHROME);
+ m_ahLargeEventBitmaps[3] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(IDB_EVENT_INFO_LARGE),
+ IMAGE_BITMAP,8, 8, LR_MONOCHROME);
+
+
+ // start the update timer
+ m_uiTimer = SetTimer(0,0,1000/10,CAppletManager::UpdateTimer);
+
+
+
+ return true;
+}
+
+//************************************************************************
+// Deinitializes the AppletManager
+//************************************************************************
+bool CAppletManager::Shutdown()
+{
+ if(!IsInitialized())
+ return false;
+
+ // stop the update timer
+ KillTimer(0,m_uiTimer);
+
+ // delete status bitmaps
+ for(int i=0;i<8;i++)
+ DeleteObject(m_ahStatusBitmaps[i]);
+
+ // delete event bitmaps
+ for(int i=0;i<8;i++)
+ {
+ DeleteObject(m_ahLargeEventBitmaps[i]);
+ DeleteObject(m_ahEventBitmaps[i]);
+ }
+
+ // unhook the events
+ UnhookEvent(m_hMIHookMessageWindowEvent);
+ UnhookEvent(m_hMIHookEventAdded);
+ UnhookEvent(m_hMIHookStatusChanged);
+ UnhookEvent(m_hMIHookProtoAck);
+ UnhookEvent(m_hMIHookContactDeleted);
+ UnhookEvent(m_hMIHookContactAdded);
+ UnhookEvent(m_hMIHookSettingChanged);
+
+ // unhook all irc protocols, and delete the classes
+ vector<CIRCConnection*>::iterator iter = m_vIRCConnections.begin();
+ while(iter != m_vIRCConnections.end())
+ {
+ UnhookEvent((*iter)->hEventHook);
+ delete *iter;
+ iter++;
+ }
+ m_vIRCConnections.clear();
+
+ // Deinitialize the screens
+ m_NotificationScreen.Shutdown();
+ m_EventScreen.Shutdown();
+ m_ContactlistScreen.Shutdown();
+ m_ChatScreen.Shutdown();
+ m_CreditsScreen.Shutdown();
+ m_ScreensaverScreen.Shutdown();
+
+ // deinitialize the configuration manager
+ CConfig::Shutdown();
+
+ // delete the protocol information
+ CProtocolData *pProtoData;
+ for(int i=0;i<m_vProtocolData.size();i++)
+ {
+ pProtoData = m_vProtocolData[i];
+ delete pProtoData;
+ }
+ m_vProtocolData.clear();
+
+ // deinitialize the outputmanager
+ if(!CLCDOutputManager::Shutdown())
+ return false;
+ return true;
+}
+
+//************************************************************************
+// Translates the specified string, and inserts the parameters
+//************************************************************************
+tstring CAppletManager::TranslateString(TCHAR *szString,...)
+{
+ TCHAR out[1024];
+ TCHAR *szTranslatedString = TranslateTS(szString);
+
+ va_list body;
+ va_start(body, szString);
+ _vstprintf(out, szTranslatedString, body);
+ va_end(body);
+ return out;
+}
+
+//************************************************************************
+// checks if the patched IRC protocol is in place
+//************************************************************************
+bool CAppletManager::IsIRCHookEnabled()
+{
+ if(m_vIRCConnections.size() == NULL)
+ return false;
+ return true;
+}
+
+//************************************************************************
+// returns the informations structure for the specified protocol
+//************************************************************************
+CProtocolData* CAppletManager::GetProtocolData(tstring strProtocol)
+{
+ for(int i=0;i<m_vProtocolData.size();i++)
+ {
+ if(m_vProtocolData[i]->strProtocol == strProtocol)
+ return m_vProtocolData[i];
+ }
+ return NULL;
+}
+
+//************************************************************************
+// Updates the AppletManager
+//************************************************************************
+bool CAppletManager::Update()
+{
+ if(!CLCDOutputManager::Update())
+ return false;
+
+ // Update Messagejobs
+ UpdateMessageJobs();
+
+ // Screensaver detection
+ BOOL bActive = false;
+ SystemParametersInfo(SPI_GETSCREENSAVERRUNNING, 0, &bActive, 0);
+ if(bActive != m_bScreensaver)
+ {
+ if(CConfig::GetBoolSetting(SCREENSAVER_LOCK)) {
+ if(!m_bScreensaver) {
+ ActivateScreensaverScreen();
+ } else {
+ ActivateEventScreen();
+ }
+ }
+ if(CConfig::GetBoolSetting(CONTROL_BACKLIGHTS)) {
+ if(GetLCDConnection() &&
+ GetLCDConnection()->GetConnectionType() == TYPE_LOGITECH)
+ {
+ CLCDConnectionLogitech *pLCDConnection = (CLCDConnectionLogitech*)GetLCDConnection();
+
+ // Screensaver starts
+ if(!m_bScreensaver)
+ {
+ m_G15LightStatus = pLCDConnection->GetLightStatus();
+ pLCDConnection->SetLCDBacklight(LCD_OFF);
+ pLCDConnection->SetKBDBacklight(KBD_OFF);
+ pLCDConnection->SetMKeyLight(0,0,0,0);
+ }
+ // Screensaver ends
+ else
+ {
+ SG15LightStatus currentStatus = pLCDConnection->GetLightStatus();
+
+ if(currentStatus.eLCDBrightness == LCD_OFF)
+ pLCDConnection->SetLCDBacklight(m_G15LightStatus.eLCDBrightness);
+ if(currentStatus.eKBDBrightness == KBD_OFF)
+ pLCDConnection->SetKBDBacklight(m_G15LightStatus.eKBDBrightness);
+ if(!currentStatus.bMRKey && !currentStatus.bMKey[0] && !currentStatus.bMKey[1]
+ && !currentStatus.bMKey[2])
+ pLCDConnection->SetMKeyLight(m_G15LightStatus.bMKey[0],m_G15LightStatus.bMKey[1],m_G15LightStatus.bMKey[2],m_G15LightStatus.bMRKey);
+ }
+ }
+ }
+ m_bScreensaver = bActive;
+ }
+
+ return true;
+}
+
+//************************************************************************
+// Called when the active screen has expired
+//************************************************************************
+void CAppletManager::OnScreenExpired(CLCDScreen *pScreen)
+{
+ // If the notification screen has expired, activate the last active screen
+ if(pScreen == (CLCDScreen*)&m_NotificationScreen)
+ {
+ ActivateScreen(m_pLastScreen);
+ if(CConfig::GetBoolSetting(TRANSITIONS))
+ m_pGfx->StartTransition();
+ }
+}
+
+//************************************************************************
+// the update timer's callback function
+//************************************************************************
+VOID CALLBACK CAppletManager::UpdateTimer(HWND hwnd,UINT uMsg,UINT_PTR idEvent,DWORD dwTime)
+{
+ CAppletManager::GetInstance()->Update();
+}
+
+//************************************************************************
+// applies the volumewheel setting
+//************************************************************************
+void CAppletManager::SetVolumeWheelHook()
+{
+ // Set the volumewheel hook
+ if(GetLCDConnection() && GetLCDConnection()->GetConnectionType() == TYPE_LOGITECH)
+ {
+ CLCDConnectionLogitech *pLCDConnection = (CLCDConnectionLogitech*)GetLCDConnection();
+ if(pLCDConnection->GetConnectionState() == CONNECTED)
+ pLCDConnection->SetVolumeWheelHook(CConfig::GetBoolSetting(HOOK_VOLUMEWHEEL));
+ }
+}
+
+//************************************************************************
+// Called when the connection state has changed
+//************************************************************************
+void CAppletManager::OnConnectionChanged(int iConnectionState)
+{
+ if(iConnectionState == CONNECTED)
+ {
+ SetVolumeWheelHook();
+ }
+ CConfig::OnConnectionChanged();
+}
+
+//************************************************************************
+// called when the plugin's configuration has changed
+//************************************************************************
+void CAppletManager::OnConfigChanged()
+{
+ GetLCDConnection()->Connect(CConfig::GetIntSetting(DEVICE));
+
+ m_pGfx->StartTransition(TRANSITION_MORPH);
+
+ // Set the volumewheel hook
+ SetVolumeWheelHook();
+ // send the event to all screens
+ m_NotificationScreen.OnConfigChanged();
+ m_ChatScreen.OnConfigChanged();
+ m_EventScreen.OnConfigChanged();
+ m_ContactlistScreen.OnConfigChanged();
+ m_CreditsScreen.OnConfigChanged();
+}
+//************************************************************************
+// activate a screen
+//************************************************************************
+void CAppletManager::ActivateScreen(CScreen *pScreen) {
+ if(GetActiveScreen() && GetActiveScreen() != &m_NotificationScreen) {
+ m_pLastScreen = (CScreen*)GetActiveScreen();
+ }
+
+ CLCDOutputManager::ActivateScreen(pScreen);
+}
+
+//************************************************************************
+// activates the previous screen
+//************************************************************************
+void CAppletManager::ActivatePreviousScreen() {
+ if(m_pLastScreen) {
+ ActivateScreen(m_pLastScreen);
+ }
+}
+
+//************************************************************************
+// activates the credits screen
+//************************************************************************
+void CAppletManager::ActivateScreensaverScreen()
+{
+ m_ScreensaverScreen.Reset();
+ ActivateScreen(&m_ScreensaverScreen);
+}
+
+//************************************************************************
+// activates the credits screen
+//************************************************************************
+void CAppletManager::ActivateCreditsScreen()
+{
+ m_CreditsScreen.Reset();
+ ActivateScreen(&m_CreditsScreen);
+}
+
+//************************************************************************
+// activates the event screen
+//************************************************************************
+void CAppletManager::ActivateEventScreen()
+{
+ m_ChatScreen.SetContact(NULL);
+ ActivateScreen(&m_EventScreen);
+
+ if(CConfig::GetBoolSetting(TRANSITIONS))
+ m_pGfx->StartTransition();
+}
+
+//************************************************************************
+// activates the contactlist screen
+//************************************************************************
+void CAppletManager::ActivateCListScreen()
+{
+ m_ChatScreen.SetContact(NULL);
+ m_ContactlistScreen.ResetPosition();
+ ActivateScreen(&m_ContactlistScreen);
+
+ if(CConfig::GetBoolSetting(TRANSITIONS))
+ m_pGfx->StartTransition();
+}
+
+//************************************************************************
+// activates the chat screen
+//************************************************************************
+bool CAppletManager::ActivateChatScreen(HANDLE hContact)
+{
+ if(!m_ChatScreen.SetContact(hContact))
+ return false;
+
+ m_ContactlistScreen.OnSessionOpened(hContact);
+ ActivateScreen(&m_ChatScreen);
+
+ if(CConfig::GetBoolSetting(TRANSITIONS))
+ m_pGfx->StartTransition();
+ return true;
+}
+
+//************************************************************************
+// returns the contacts displayname
+//************************************************************************
+tstring CAppletManager::GetContactDisplayname(HANDLE hContact,bool bShortened)
+{
+ if(!bShortened || !CConfig::GetBoolSetting(NOTIFY_NICKCUTOFF))
+ return (TCHAR*)CallService(MS_CLIST_GETCONTACTDISPLAYNAME, (WPARAM)hContact, GCDNF_TCHAR);
+
+ tstring strNick = GetContactDisplayname(hContact,false);
+ if(strNick.length() > CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET))
+ return strNick.erase(CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET)) + _T("...");
+
+ return strNick;
+}
+
+//************************************************************************
+// returns the contacts group
+//************************************************************************
+tstring CAppletManager::GetContactGroup(HANDLE hContact)
+{
+ DBVARIANT dbv;
+ int res = db_get_ts(hContact, "CList", "Group", &dbv);
+
+ tstring strGroup = _T("");
+ if(!res)
+ strGroup = dbv.ptszVal;
+
+ db_free(&dbv);
+ return strGroup;
+}
+
+//************************************************************************
+// returns the bitmap for the specified event
+//************************************************************************
+HBITMAP CAppletManager::GetEventBitmap(EventType eType, bool bLarge)
+{
+ switch(eType)
+ {
+ case EVENT_MSG_RECEIVED:
+ case EVENT_MSG_SENT:
+ case EVENT_IRC_RECEIVED:
+ case EVENT_IRC_SENT:
+ if(bLarge)
+ return m_ahLargeEventBitmaps[0];
+ else
+ return m_ahEventBitmaps[0];
+ case EVENT_PROTO_STATUS:
+ case EVENT_PROTO_CONNECTED:
+ case EVENT_PROTO_DISCONNECTED:
+ if(bLarge)
+ return m_ahLargeEventBitmaps[1];
+ else
+ return m_ahEventBitmaps[1];
+ case EVENT_STATUS:
+ case EVENT_SIGNED_ON:
+ case EVENT_SIGNED_OFF:
+ if(bLarge)
+ return m_ahLargeEventBitmaps[2];
+ else
+ return m_ahEventBitmaps[2];
+ default:
+ if(bLarge)
+ return m_ahLargeEventBitmaps[3];
+ else
+ return m_ahEventBitmaps[3];
+ }
+}
+
+//************************************************************************
+// returns the bitmap for the specified status
+//************************************************************************
+HBITMAP CAppletManager::GetStatusBitmap(int iStatus)
+{
+ switch(iStatus)
+ {
+ case ID_STATUS_OFFLINE:
+ return m_ahStatusBitmaps[0];
+ case ID_STATUS_ONLINE:
+ return m_ahStatusBitmaps[1];
+ case ID_STATUS_NA:
+ return m_ahStatusBitmaps[3];
+ case ID_STATUS_OCCUPIED:
+ return m_ahStatusBitmaps[4];
+ case ID_STATUS_DND:
+ return m_ahStatusBitmaps[5];
+ case ID_STATUS_INVISIBLE:
+ return m_ahStatusBitmaps[6];
+ case ID_STATUS_FREECHAT:
+ return m_ahStatusBitmaps[7];
+ case ID_STATUS_AWAY:
+ default:
+ return m_ahStatusBitmaps[2];
+ }
+}
+//************************************************************************
+// returns a formatted timestamp string
+//************************************************************************
+tstring CAppletManager::GetFormattedTimestamp(tm *tm_time)
+{
+ time_t now;
+ tm tm_now;
+ time(&now);
+ localtime_s(&tm_now,&now);
+
+ TCHAR buffer[128];
+ setlocale( LC_ALL, "" );
+
+ if(tm_time->tm_mday != tm_now.tm_mday || tm_time->tm_mon != tm_now.tm_mon)
+ {
+ if(CConfig::GetBoolSetting(TIMESTAMP_SECONDS))
+ _tcsftime(buffer,128,_T("[%x %H:%M:%S]"),tm_time);
+ else
+ _tcsftime(buffer,128,_T("[%x %H:%M]"),tm_time);
+ }
+ else
+ {
+ if(CConfig::GetBoolSetting(TIMESTAMP_SECONDS))
+ _tcsftime(buffer,128,_T("[%H:%M:%S]"),tm_time);
+ else
+ _tcsftime(buffer,128,_T("[%H:%M]"),tm_time);
+ }
+
+ return toTstring(buffer);
+}
+
+//************************************************************************
+// called to process the specified event
+//************************************************************************
+void CAppletManager::HandleEvent(CEvent *pEvent)
+{
+ TRACE(_T("<< Event: %i\n"),(int)pEvent->eType);
+
+ // check if the event's timestamp needs to be set
+ if(!pEvent->bTime)
+ {
+ time_t now;
+ time(&now);
+ localtime_s(&pEvent->Time,&now);
+ }
+ // check wether the event needs notification
+
+ // check for protocol filters
+ if(pEvent->hContact != NULL && pEvent->eType != EVENT_CONTACT_ADDED)
+ {
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)pEvent->hContact, 0);
+ if(szProto == NULL || !CConfig::GetProtocolNotificationFilter(toTstring(szProto)))
+ pEvent->bNotification = false;
+ }
+ pEvent->bLog = pEvent->bNotification;
+
+ if(CAppletManager::IsSubContact(pEvent->hContact))
+ {
+ pEvent->bLog = false;
+ pEvent->bNotification = false;
+ }
+
+ // if the applet is in foreground, skip notifications for the chatsession contact
+ if(pEvent->hContact && GetLCDConnection()->IsForeground() && pEvent->hContact == m_ChatScreen.GetContact() &&
+ (!m_ChatScreen.IsInputActive() || !CConfig::GetBoolSetting(NOTIFY_NO_SKIP_REPLY)))
+ {
+ if(pEvent->eType == EVENT_STATUS && CConfig::GetBoolSetting(NOTIFY_SKIP_STATUS))
+ pEvent->bNotification = false;
+ if( pEvent->eType == EVENT_SIGNED_ON && CConfig::GetBoolSetting(NOTIFY_SKIP_SIGNON))
+ pEvent->bNotification = false;
+ if(pEvent->eType == EVENT_SIGNED_OFF && CConfig::GetBoolSetting(NOTIFY_SKIP_SIGNOFF))
+ pEvent->bNotification = false;
+ if((pEvent->eType == EVENT_IRC_RECEIVED || pEvent->eType == EVENT_MSG_RECEIVED) && CConfig::GetBoolSetting(NOTIFY_SKIP_MESSAGES))
+ pEvent->bNotification = false;
+ }
+
+ // send the event to all screens
+ m_NotificationScreen.OnEventReceived(pEvent);
+ m_ChatScreen.OnEventReceived(pEvent);
+ m_EventScreen.OnEventReceived(pEvent);
+ m_ContactlistScreen.OnEventReceived(pEvent);
+
+ // activate notification screen if neccessary (and screensaverscreen is not active)
+ if(pEvent->bNotification)
+ {
+ if(GetActiveScreen() != (CLCDScreen*)&m_NotificationScreen && GetActiveScreen() != (CLCDScreen*)&m_ScreensaverScreen)
+ {
+ m_NotificationScreen.SetAlert(true);
+ m_NotificationScreen.SetExpiration(CConfig::GetIntSetting(NOTIFY_DURATION)*1000);
+ ActivateScreen(&m_NotificationScreen);
+
+ if(GetLCDConnection()->IsForeground() && CConfig::GetBoolSetting(TRANSITIONS))
+ m_pGfx->StartTransition();
+ }
+ }
+}
+
+bool CAppletManager::IsUtfSendAvailable(HANDLE hContact) {
+ char* szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM) hContact, 0);
+ if ( szProto == NULL )
+ return FALSE;
+
+ return ( CallProtoService(szProto, PS_GETCAPS, PFLAGNUM_4, 0) & PF4_IMSENDUTF ) ? TRUE : FALSE;
+}
+
+//************************************************************************
+// returns the contacts message service name
+//************************************************************************
+char *CAppletManager::GetMessageServiceName(HANDLE hContact,bool bIsUnicode)
+{
+ if(g_bUnicode) {
+ char szServiceName[100];
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM) hContact, 0);
+
+ if(szProto == NULL)
+ return NULL;
+
+ if (!bIsUnicode)
+ return PSS_MESSAGE;
+
+ _snprintf(szServiceName, sizeof(szServiceName), "%s%sW", szProto, PSS_MESSAGE);
+ if (ServiceExists(szServiceName))
+ return PSS_MESSAGE "W";
+ } else {
+ return PSS_MESSAGE;
+ }
+}
+
+//************************************************************************
+// updates all pending message jobs
+//************************************************************************
+void CAppletManager::UpdateMessageJobs()
+{
+ list<SMessageJob*>::iterator iter = m_MessageJobs.begin();
+ while(iter != m_MessageJobs.end())
+ {
+ // TODO: Fertigstellen
+ if((*iter)->dwTimestamp + 15*1000 < GetTickCount())
+ {
+ CEvent Event;
+
+ Event.eType = EVENT_MESSAGE_ACK;
+ Event.hValue = (*iter)->hEvent;
+ Event.hContact = (*iter)->hContact;
+ Event.iValue = ACKRESULT_FAILED;
+ Event.strValue = TranslateString(_T("Timeout: No response from contact/server"));
+
+ HandleEvent(&Event);
+
+ SMessageJob *pJob = *iter;
+ m_MessageJobs.erase(iter);
+ free(pJob->pcBuffer);
+ delete(pJob);
+ break;
+ }
+ iter++;
+ }
+}
+
+//************************************************************************
+// adds a message job to the list
+//************************************************************************
+void CAppletManager::AddMessageJob(SMessageJob *pJob)
+{
+ m_MessageJobs.push_back(pJob);
+}
+
+//************************************************************************
+// finishes a message job
+//************************************************************************
+void CAppletManager::FinishMessageJob(SMessageJob *pJob)
+{
+ list<SMessageJob*>::iterator iter = m_MessageJobs.begin();
+ while(iter != m_MessageJobs.end())
+ {
+ if((*iter) == pJob)
+ {
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)pJob->hContact, 0);
+ tstring strProto = toTstring(szProto);
+ CIRCConnection *pIRCCon = GetIRCConnection(strProto);
+
+ // Only add the message to the history if the contact isn't an irc chatroom
+ if(!(pIRCCon && db_get_b(pJob->hContact, szProto, "ChatRoom", 0) != 0))
+ {
+ // Add the message to the database
+ DBEVENTINFO dbei = { 0 };
+ dbei.cbSize = sizeof(dbei);
+ dbei.eventType = EVENTTYPE_MESSAGE;
+ dbei.flags = DBEF_SENT;
+ dbei.szModule = szProto;
+ dbei.timestamp = time(NULL);
+ // Check if protocoll is valid
+ if(dbei.szModule == NULL)
+ return;
+
+ if(pJob->dwFlags & PREF_UTF) {
+ dbei.flags |= DBEF_UTF;
+ }
+
+ dbei.cbBlob = pJob->iBufferSize;
+ dbei.pBlob = (PBYTE) pJob->pcBuffer;
+
+ db_event_add(pJob->hContact, &dbei);
+ }
+ SMessageJob *pJob = *iter;
+ m_MessageJobs.erase(iter);
+ free(pJob->pcBuffer);
+ delete(pJob);
+ return;
+ }
+ }
+}
+
+//************************************************************************
+// cancels a message job
+//************************************************************************
+void CAppletManager::CancelMessageJob(SMessageJob *pJob)
+{
+ list<SMessageJob*>::iterator iter = m_MessageJobs.begin();
+ while(iter != m_MessageJobs.end())
+ {
+ if((*iter) == pJob)
+ {
+ SMessageJob *pJob = *iter;
+ m_MessageJobs.erase(iter);
+ free(pJob->pcBuffer);
+ delete(pJob);
+ return;
+ }
+ }
+}
+
+//************************************************************************
+// returns wether or not a contact is a subcontact
+//************************************************************************
+bool CAppletManager::IsSubContact(HANDLE hContact)
+{
+ if(!db_get_b(0, "MetaContacts", "Enabled", 1))
+ return false;
+ bool bIsSubcontact = db_get_b(hContact,"MetaContacts","IsSubcontact",0);
+ return bIsSubcontact;
+ // HANDLE hMetaContact = (HANDLE)CallService(MS_MC_GETMETACONTACT, (WPARAM)hContact, NULL);
+ // return hMetaContact != NULL;
+}
+
+//************************************************************************
+// sends typing notifications to the specified contact
+//************************************************************************
+void CAppletManager::SendTypingNotification(HANDLE hContact,bool bEnable)
+{
+ DWORD protoStatus;
+ DWORD protoCaps;
+ DWORD typeCaps;
+
+ if (!hContact)
+ return;
+
+ // Don't send to protocols who don't support typing
+ // Don't send to users who are unchecked in the typing notification options
+ // Don't send to protocols that are offline
+ // Don't send to users who are not visible and
+ // Don't send to users who are not on the visible list when you are in invisible mode.
+ if (!db_get_b(hContact, "SRMsg", "SupportTyping", db_get_b(NULL, "SRMsg", "DefaultTyping", 1)))
+ return;
+
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+ if (!szProto)
+ return;
+
+ protoStatus = CallProtoService(szProto, PS_GETSTATUS, 0, 0);
+ protoCaps = CallProtoService(szProto, PS_GETCAPS, PFLAGNUM_1, 0);
+ typeCaps = CallProtoService(szProto, PS_GETCAPS, PFLAGNUM_4, 0);
+
+ if (!(typeCaps & PF4_SUPPORTTYPING))
+ return;
+ if (protoStatus < ID_STATUS_ONLINE)
+ return;
+ if (protoCaps & PF1_VISLIST && db_get_w(hContact, szProto, "ApparentMode", 0) == ID_STATUS_OFFLINE)
+ return;
+ if (protoCaps & PF1_INVISLIST && protoStatus == ID_STATUS_INVISIBLE && db_get_w(hContact, szProto, "ApparentMode", 0) != ID_STATUS_ONLINE)
+ return;
+ if (db_get_b(hContact, "CList", "NotOnList", 0)
+ && !db_get_b(NULL, "SRMsg", "UnknownTyping", 1))
+ return;
+ // End user check
+ CallService(MS_PROTO_SELFISTYPING, (WPARAM) hContact, bEnable?PROTOTYPE_SELFTYPING_ON:PROTOTYPE_SELFTYPING_OFF);
+}
+
+//************************************************************************
+// sends a message to the specified contact
+//************************************************************************
+HANDLE CAppletManager::SendMessageToContact(HANDLE hContact,tstring strMessage)
+{
+ string strAscii = toNarrowString(strMessage);
+ int bufSize = lstrlenA(strAscii.c_str())+1;
+ SMessageJob *pJob = new SMessageJob();
+ pJob->dwTimestamp = GetTickCount();
+ pJob->hContact = hContact;
+
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+ tstring strProto = toTstring(szProto);
+
+ CIRCConnection *pIRCCon = CAppletManager::GetInstance()->GetIRCConnection(strProto);
+
+ if(pIRCCon && db_get_b(hContact, szProto, "ChatRoom", 0) != 0)
+ {
+ GCDEST gcd = {0};
+ GCEVENT gce = {0};
+
+ DBVARIANT dbv;
+ if (!db_get((HANDLE)hContact, szProto, "Nick", &dbv) && dbv.type == DBVT_ASCIIZ )
+ gcd.pszID = dbv.pszVal;
+ else
+ return NULL;
+
+ string strID = string(gcd.pszID) + " - " + toNarrowString(pIRCCon->strNetwork).c_str();
+ gcd.pszID = (char*)strID.c_str();
+ gcd.pszModule = szProto;
+ gcd.iType = GC_EVENT_SENDMESSAGE;
+
+ gce.cbSize = sizeof(GCEVENT);
+ gce.pDest = &gcd;
+ gce.pszStatus = "";
+ // gce.bAddToLog = true;
+ gce.pszUserInfo = NULL;
+
+ gce.pszText = (char *)strAscii.c_str();
+
+ gce.dwItemData = NULL;
+ gce.time = time(NULL);
+ gce.bIsMe = true;
+
+ CallService(MS_GC_EVENT, NULL, (LPARAM) &gce);
+
+ pJob->hEvent = NULL;
+ }
+ else
+ {
+ DWORD pref = 0;
+ bool bIsUnicode = false;
+ if(CAppletManager::IsUtfSendAvailable(pJob->hContact)) {
+ pref = PREF_UTF;
+ char* szMsgUtf = NULL;
+ #if defined( _UNICODE )
+ szMsgUtf = mir_utf8encodeW( strMessage.c_str());
+ #else
+ int codepage = CallService( MS_LANGPACK_GETCODEPAGE, 0, 0 );
+ szMsgUtf = mir_utf8encodecp(strMessage.c_str(), codepage);
+ #endif
+
+ pJob->iBufferSize = strlen(szMsgUtf)+1;
+ pJob->pcBuffer = (char *)malloc(pJob->iBufferSize);
+ pJob->dwFlags = PREF_UTF;
+
+ memcpy(pJob->pcBuffer,szMsgUtf,pJob->iBufferSize);
+ mir_free(szMsgUtf);
+ } else {
+
+#ifdef _UNICODE
+ bIsUnicode = !IsUnicodeAscii(strMessage.c_str(),lstrlen(strMessage.c_str()));
+#endif
+ if(bIsUnicode) {
+ pref = PREF_UNICODE;
+ pJob->iBufferSize = bufSize * (sizeof(TCHAR) + 1);
+ } else {
+ pJob->iBufferSize = bufSize;
+ }
+ pJob->pcBuffer = (char *)malloc(pJob->iBufferSize);
+ memcpy(pJob->pcBuffer,strAscii.c_str(),bufSize);
+
+ if(bIsUnicode) {
+ memcpy(&pJob->pcBuffer[bufSize],strMessage.c_str(),bufSize*sizeof(TCHAR));
+ }
+ }
+ char *szService = CAppletManager::GetMessageServiceName(pJob->hContact,bIsUnicode);
+
+ if(szService == NULL)
+ {
+ free(pJob->pcBuffer);
+ pJob->pcBuffer == NULL;
+ return NULL;
+ }
+ pJob->hEvent = (HANDLE) CallContactService(pJob->hContact, szService , pref, (LPARAM)pJob->pcBuffer );
+ CAppletManager::GetInstance()->AddMessageJob(pJob);
+ }
+
+
+ return pJob->hEvent;
+}
+
+//************************************************************************
+// check if a contacts message window is opened
+//************************************************************************
+bool CAppletManager::IsMessageWindowOpen(HANDLE hContact)
+{
+ MessageWindowInputData mwid;
+ mwid.cbSize = sizeof(MessageWindowInputData);
+ mwid.hContact = hContact;
+ mwid.uFlags = MSG_WINDOW_UFLAG_MSG_BOTH;
+
+ MessageWindowData mwd;
+ mwd.cbSize = sizeof(MessageWindowData);
+ CallService(MS_MSG_GETWINDOWDATA,(WPARAM)&mwid,(LPARAM)&mwd);
+ if(mwd.uState & MSG_WINDOW_STATE_EXISTS)
+ return true;
+ return false;
+}
+
+//************************************************************************
+// marks the given message as read
+//************************************************************************
+void CAppletManager::MarkMessageAsRead(HANDLE hContact,HANDLE hEvent)
+{
+ db_event_markRead(hContact, hEvent);
+ CallService(MS_CLIST_REMOVEEVENT, (WPARAM)hContact, (LPARAM)hEvent);
+}
+
+//************************************************************************
+// translates the given database event
+//************************************************************************
+bool CAppletManager::TranslateDBEvent(CEvent *pEvent,WPARAM wParam, LPARAM lParam)
+{
+ HANDLE hContact = (HANDLE)wParam;
+ HANDLE hdbevent = (HANDLE)lParam;
+
+
+ // Create struct for dbevent
+ DBEVENTINFO dbevent;
+ ZeroMemory(&dbevent, sizeof(dbevent));
+ //dbevent.flags |= PREF_UNICODE;
+ dbevent.cbSize = sizeof(dbevent);
+ dbevent.cbBlob = db_event_getBlobSize(hdbevent);
+ if(dbevent.cbBlob == -1) // hdbevent is invalid
+ {
+ return false;
+ }
+ dbevent.pBlob = (PBYTE)malloc(dbevent.cbBlob);
+ if(db_event_get(hdbevent, &dbevent) != 0)
+ {
+ free(dbevent.pBlob);
+ return false;
+ }
+
+ pEvent->dwFlags = dbevent.flags;
+ pEvent->hContact = hContact;
+ pEvent->hValue = hdbevent;
+
+ time_t timestamp = (time_t)dbevent.timestamp;
+ localtime_s(&pEvent->Time,&timestamp);
+ pEvent->bTime = true;
+ /*
+ if(dbevent.eventType == EVENTTYPE_MESSAGE && dbevent.flags & DBEF_READ) {
+ free(dbevent.pBlob);
+ return false;
+ }
+ */
+ // Skip events from the user except for messages
+ if(dbevent.eventType != EVENTTYPE_MESSAGE && (dbevent.flags & DBEF_SENT))
+ {
+ free(dbevent.pBlob);
+ return false;
+ }
+
+ int msglen = 0;
+
+ tstring strName = CAppletManager::GetContactDisplayname(hContact,true);
+
+ switch(dbevent.eventType)
+ {
+ case EVENTTYPE_MESSAGE:
+ msglen = strlen((char *) dbevent.pBlob) + 1;
+#ifdef _UNICODE
+ if (dbevent.flags & DBEF_UTF) {
+ pEvent->strValue = Utf8_Decode((char*)dbevent.pBlob);
+ } else if ((int) dbevent.cbBlob == msglen*3){
+ pEvent->strValue = (TCHAR *) & dbevent.pBlob[msglen];
+ } else {
+ pEvent->strValue = toTstring((char*)dbevent.pBlob);
+ }
+#else
+ pEvent->strValue = toTstring((char*)dbevent.pBlob);
+#endif
+ pEvent->eType = (dbevent.flags & DBEF_SENT) ? EVENT_MSG_SENT:EVENT_MSG_RECEIVED;
+ if(pEvent->eType == EVENT_MSG_RECEIVED)
+ {
+ pEvent->dwFlags = MSG_UNREAD;
+ if(CConfig::GetBoolSetting(NOTIFY_MESSAGES))
+ pEvent->bNotification = true;
+ }
+
+ pEvent->strDescription = strName + _T(": ") +pEvent->strValue;
+ pEvent->strSummary = TranslateString(_T("New message from %s"),strName.c_str());
+ break;
+ case EVENTTYPE_URL:
+ if(CConfig::GetBoolSetting(NOTIFY_URL))
+ pEvent->bNotification = true;
+
+ pEvent->eType = EVENT_URL;
+ pEvent->strDescription = TranslateString(_T("Incoming URL from %s"),strName.c_str());
+ break;
+ case EVENTTYPE_CONTACTS:
+ if(CConfig::GetBoolSetting(NOTIFY_CONTACTS))
+ pEvent->bNotification = true;
+
+ pEvent->strDescription = TranslateString(_T("Incoming contacts from %s"),strName.c_str());
+ pEvent->eType = EVENT_CONTACTS;
+ break;
+ case EVENTTYPE_ADDED:
+ if(CConfig::GetBoolSetting(NOTIFY_CONTACTS))
+ pEvent->bNotification = true;
+
+ pEvent->strDescription = TranslateString(_T("You were added by %s"),strName.c_str());
+ pEvent->eType = EVENT_ADDED;
+ break;
+ case EVENTTYPE_AUTHREQUEST:
+ if(CConfig::GetBoolSetting(NOTIFY_CONTACTS))
+ pEvent->bNotification = true;
+
+ pEvent->strDescription = TranslateString(_T("Incoming Authrequest!"));
+ pEvent->eType = EVENT_AUTHREQUEST;
+ break;
+ case EVENTTYPE_FILE:
+ if(CConfig::GetBoolSetting(NOTIFY_FILE))
+ pEvent->bNotification = true;
+
+ pEvent->strDescription = TranslateString(_T("Incoming file from %s"),strName.c_str());
+ pEvent->eType = EVENT_FILE;
+ break;
+ default:
+ return false;
+ break;
+ }
+
+ if(CConfig::GetBoolSetting(NOTIFY_SHOWPROTO))
+ {
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)pEvent->hContact, 0);
+ pEvent->strDescription = _T("(")+toTstring(szProto)+_T(") ") + pEvent->strDescription;
+ }
+
+ // Clean up
+ free(dbevent.pBlob);
+ return true;
+}
+
+//************************************************************************
+// removes IRC formatting tags from the string
+//************************************************************************
+tstring CAppletManager::StripIRCFormatting(tstring strText)
+{
+ tstring::size_type End=0,Start=0;
+ tstring strEntity = _T("");
+ tstring strReplace = _T("");
+ tstring::size_type len = strText.length();
+
+ int i = 0;
+ while(i < strText.length())
+ {
+ Start = strText.find(_T("%"),i);
+ if(Start != string::npos && Start < strText.length() - 1)
+ {
+ strEntity = strText[Start+1];
+ if(strEntity == _T("%"))
+ {
+ strText.replace(Start,2,_T("%"));
+ i = Start +1;
+ }
+ /*
+ else if(strEntity == _T("b") || strEntity == _T("B") ||
+ strEntity == _T("i") || strEntity == _T("I") ||
+ strEntity ==_T("u") || strEntity == _T("U") ||
+ strEntity == _T("C") ||strEntity == _T("F"))
+ {
+ strText.erase(Start,2);
+ i = Start;
+ }
+ */
+ else if(strEntity == _T("c") || strEntity == _T("f"))
+ {
+ strText.erase(Start,4);
+ i = Start;
+ }
+ else
+ {
+ strText.erase(Start,2);
+ i = Start;
+ }
+ }
+ else
+ break;
+ }
+
+ return strText;
+}
+
+//************************************************************************
+// returns the IRC connection class for the specified protocol
+//************************************************************************
+CIRCConnection *CAppletManager::GetIRCConnection(tstring strProtocol)
+{
+ vector<CIRCConnection*>::iterator iter = m_vIRCConnections.begin();
+ while(iter != m_vIRCConnections.end())
+ {
+ if((*iter)->strProtocol == strProtocol)
+ return *iter;
+ iter++;
+ }
+ return NULL;
+}
+
+//************************************************************************
+// creates the IRC connection class for the specified protocol
+//************************************************************************
+CIRCConnection *CAppletManager::CreateIRCConnection(tstring strProtocol)
+{
+ char buffer[128];
+ sprintf(buffer,"%s/HookableEvents",toNarrowString(strProtocol).c_str());
+
+ // try to hook the events
+ HANDLE hEventHook = HookEvent(buffer,CAppletManager::HookChatInbound);
+ // if the hook could not be established, the protocol is not an IRC instance
+ if(!hEventHook)
+ return NULL;
+
+ TRACE(_T("Patched IRC-Connection found: %s\n"),strProtocol.c_str());
+ CIRCConnection *pIRCCon = new CIRCConnection();
+ pIRCCon->strProtocol = strProtocol;
+ pIRCCon->hEventHook = hEventHook;
+ pIRCCon->strNetwork = _T("");
+
+ m_vIRCConnections.push_back(pIRCCon);
+
+ return pIRCCon;
+}
+
+//************************************************************************
+// returns the history class for the specified IRC channel
+//************************************************************************
+CIRCHistory *CAppletManager::GetIRCHistory(HANDLE hContact)
+{
+ list<CIRCHistory*>::iterator iter = m_LIRCHistorys.begin();
+ while(iter != m_LIRCHistorys.end())
+ {
+ if((*iter)->hContact == hContact)
+ return *iter;
+ iter++;
+ }
+ return NULL;
+}
+
+CIRCHistory *CAppletManager::GetIRCHistoryByName(tstring strProtocol,tstring strChannel)
+{
+ list<CIRCHistory*>::iterator iter = m_LIRCHistorys.begin();
+ while(iter != m_LIRCHistorys.end())
+ {
+ if((*iter)->strChannel == strChannel && (*iter)->strProtocol == strProtocol)
+ return *iter;
+ iter++;
+ }
+ return NULL;
+}
+
+//************************************************************************
+// deletes the history class for the specified IRC channel
+//************************************************************************
+void CAppletManager::DeleteIRCHistory(HANDLE hContact)
+{
+ list<CIRCHistory*>::iterator iter = m_LIRCHistorys.begin();
+ while(iter != m_LIRCHistorys.end())
+ {
+ if((*iter)->hContact == hContact)
+ {
+ CIRCHistory *pHistory = *iter;
+ pHistory->LMessages.clear();
+ pHistory->LUsers.clear();
+
+ m_LIRCHistorys.erase(iter);
+
+ delete pHistory;
+
+ return;
+ }
+ iter++;
+ }
+}
+
+//************************************************************************
+// creates a history class for the specified IRC channel
+//************************************************************************
+CIRCHistory *CAppletManager::CreateIRCHistory(HANDLE hContact,tstring strChannel)
+{
+ char *szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+ if(!szProto)
+ return NULL;
+
+ CIRCHistory *pHistory = GetIRCHistoryByName(toTstring(szProto),strChannel);
+ if(pHistory)
+ {
+ pHistory->hContact = hContact;
+ return pHistory;
+ }
+
+ pHistory = new CIRCHistory();
+ pHistory->hContact = hContact;
+ pHistory->strChannel = strChannel;
+ pHistory->strProtocol = toTstring(szProto);
+
+ m_LIRCHistorys.push_back(pHistory);
+
+ return pHistory;
+}
+
+CIRCHistory *CAppletManager::CreateIRCHistoryByName(tstring strProtocol,tstring strChannel)
+{
+ CIRCHistory *pHistory = GetIRCHistoryByName(strProtocol,strChannel);
+ if(pHistory)
+ return pHistory;
+
+ pHistory = new CIRCHistory();
+ pHistory->hContact = NULL;
+ pHistory->strChannel = strChannel;
+ pHistory->strProtocol = strProtocol;
+
+ m_LIRCHistorys.push_back(pHistory);
+
+ return pHistory;
+}
+
+//########################################################################
+// hook functions
+//########################################################################
+
+//************************************************************************
+// inbound chat event hook function
+//************************************************************************
+int CAppletManager::HookChatInbound(WPARAM wParam,LPARAM lParam)
+{
+ GCEVENT *gce = (GCEVENT*)lParam;
+ GCDEST *gcd = (GCDEST*)gce->pDest;
+
+ if(gce == NULL || gcd == NULL)
+ TRACE(_T("<< [%s] skipping invalid IRC event\n"));
+
+ TRACE(_T("<< [%s:%s] IRC event %04X\n"),toTstring(gcd->pszModule).c_str(),toTstring(gcd->pszID).c_str(),gcd->iType);
+
+ // get the matching irc connection entry
+ CIRCConnection *pIRCCon = CAppletManager::GetInstance()->GetIRCConnection(toTstring(gcd->pszModule));
+ if(!pIRCCon)
+ {
+ TRACE(_T("<< [%s] IRC connection not found, skipping event\n"),toTstring(gcd->pszModule).c_str());
+ return 0;
+ }
+
+ // fetch the network name
+ if(gcd->iType == GC_EVENT_CHANGESESSIONAME)
+ {
+ if(!_tcsicmp(gcd->ptszID,_T("Network log")))
+ {
+ pIRCCon->strNetwork = toTstring(gce->ptszText);
+ TRACE(_T("\t Found network identifier: %s\n"),pIRCCon->strNetwork.c_str());
+ return 0;
+ }
+ }
+
+ CEvent Event;
+ if(gce->bIsMe)
+ Event.eType = EVENT_IRC_SENT;
+ else
+ Event.eType = EVENT_IRC_RECEIVED;
+ Event.iValue = gcd->iType;
+ Event.hValue = (HANDLE)lParam;
+
+ CIRCHistory *pHistory = NULL;
+ if(gcd->ptszID)
+ {
+ tstring strChannel = toTstring(gcd->ptszID);
+ tstring::size_type pos = strChannel.find('-');
+ if(pos != tstring::npos)
+ strChannel = strChannel.substr(0,pos-1);
+ else
+ {
+ if(_tcsicmp(gcd->ptszID,_T("Network log")))
+ TRACE(_T("\t WARNING: ignoring unknown event!\n"));
+ return 0;
+ }
+ pHistory = CAppletManager::GetInstance()->GetIRCHistoryByName(pIRCCon->strProtocol,strChannel);
+ if(!pHistory)
+ {
+ if(gcd->iType == GC_EVENT_JOIN)
+ {
+ pHistory = CAppletManager::GetInstance()->CreateIRCHistoryByName(pIRCCon->strProtocol,strChannel);
+ if(pHistory)
+ pHistory->LUsers.push_back(toTstring(gce->ptszNick));
+ }
+ return 0;
+ }
+ Event.hContact = pHistory->hContact;
+ }
+ else if(gcd->iType != GC_EVENT_INFORMATION)
+ {
+ TRACE(_T("\t WARNING: ignoring unknown event!\n"));
+ return 0;
+ }
+ else
+ Event.hContact = NULL;
+
+ // Ignore events from hidden chatrooms, except for join events
+ if(gcd->ptszID != NULL && db_get_b(Event.hContact,"CList","Hidden",0))
+ {
+ if(gcd->iType == GC_EVENT_JOIN && pHistory)
+ pHistory->LUsers.push_back(toTstring(gce->ptszNick));
+
+ TRACE(_T("\t Chatroom is hidden, skipping event!\n"));
+ return 0;
+ }
+
+ tstring strText = StripIRCFormatting(toTstring(gce->ptszText));
+ tstring strNick = toTstring(gce->ptszNick);
+ tstring strStatus = toTstring(gce->ptszStatus);
+
+ if(CConfig::GetBoolSetting(NOTIFY_NICKCUTOFF) && strNick.length() > CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET))
+ strNick = strNick.erase(CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET)) + _T("...");
+
+ TRACE(_T("\t Handling event...\t"));
+
+ switch(gcd->iType)
+ {
+ case GC_EVENT_INFORMATION:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_CHANNEL))
+ Event.bNotification = true;
+
+ if(strText.find(_T("CTCP")) == 0)
+ Event.strValue = _T("--> ") + strText;
+ else
+ Event.strValue = strText;
+
+ break;
+ case GC_EVENT_ACTION:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_EMOTES))
+ Event.bNotification = true;
+ Event.strValue = strNick + _T(" ") + strText;
+ break;
+ case GC_EVENT_MESSAGE:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_MESSAGES))
+ Event.bNotification = true;
+ Event.strValue = strNick + _T(": ") + strText;
+ break;
+ case GC_EVENT_JOIN:
+ // Add the user to the list
+ pHistory->LUsers.push_back(toTstring(gce->ptszNick));
+
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_USERS))
+ Event.bNotification = true;
+ // Skip join event for user
+ if(gce->bIsMe)
+ return 0;
+ Event.strValue = TranslateString(_T("%s has joined the channel"),strNick.c_str());
+
+ break;
+ case GC_EVENT_PART:
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_USERS))
+ Event.bNotification = true;
+ tstring strFullNick = toTstring(gce->ptszNick);
+ Event.strValue = TranslateString(strText.empty()?_T("%s has left"):_T("%s has left: %s"),strNick.c_str(),strText.c_str());
+ if(pHistory)
+ {
+ // Remove the user from the list
+ list<tstring>::iterator iter = pHistory->LUsers.begin();
+ while(iter != pHistory->LUsers.end())
+ {
+ if((*iter) == strFullNick)
+ {
+ pHistory->LUsers.erase(iter);
+ break;
+ }
+ iter++;
+ }
+ }
+ break;
+ }
+ case GC_EVENT_QUIT:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_USERS))
+ Event.bNotification = true;
+ Event.strValue = TranslateString(strText.empty()?_T("%s has disconnected"):_T("%s has disconnected: %s"),strNick.c_str(),strText.c_str());
+ break;
+ case GC_EVENT_KICK:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_USERS))
+ Event.bNotification = true;
+ Event.strValue = TranslateString(_T("%s has kicked %s: %s"),strStatus.c_str(),strNick.c_str(),strText.c_str());
+ break;
+ case GC_EVENT_NICK:
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_USERS))
+ Event.bNotification = true;
+ tstring strFullNick = toTstring(gce->ptszNick);
+
+ if(CConfig::GetBoolSetting(NOTIFY_NICKCUTOFF) && strText.length() > CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET))
+ strText = strText.erase(CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET)) + _T("...");
+
+ Event.strValue = TranslateString(_T("%s is now known as %s"),strNick.c_str(),strText.c_str());
+ if(pHistory)
+ {
+ // change the nick in the userlist
+ list<tstring>::iterator iter = pHistory->LUsers.begin();
+ while(iter != pHistory->LUsers.end())
+ {
+ if((*iter) == strFullNick)
+ (*iter) = strText;
+ iter++;
+ }
+ }
+ break;
+ }
+ case GC_EVENT_NOTICE:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_NOTICES))
+ Event.bNotification = true;
+ Event.strValue = TranslateString(_T("Notice from %s: %s"),strNick.c_str(),strText.c_str());
+ break;
+ case GC_EVENT_TOPIC:
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_CHANNEL))
+ Event.bNotification = true;
+ Event.strValue = TranslateString(_T("Topic is now '%s' (set by %s)"),strText.c_str(),strNick.c_str());
+ break;
+ case GC_EVENT_ADDSTATUS:
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_STATUS))
+ Event.bNotification = true;
+ tstring strNick2 = toTstring(gce->ptszStatus);
+ if(CConfig::GetBoolSetting(NOTIFY_NICKCUTOFF) && strNick2.length() > CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET))
+ strNick2 = strNick2.erase(CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET)) + _T("...");
+
+ Event.strValue = TranslateString(_T("%s enables '%s' for %s"),strText.c_str(),strNick2.c_str(),strNick.c_str());
+ break;
+ }
+ case GC_EVENT_REMOVESTATUS:
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_IRC_STATUS))
+ Event.bNotification = true;
+ tstring strNick2 = toTstring(gce->ptszStatus);
+ if(CConfig::GetBoolSetting(NOTIFY_NICKCUTOFF) && strNick2.length() > CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET))
+ strNick2 = strNick2.erase(CConfig::GetIntSetting(NOTIFY_NICKCUTOFF_OFFSET)) + _T("...");
+
+ Event.strValue = TranslateString(_T("%s disables '%s' for %s"),strText.c_str(),strNick2.c_str(),strNick.c_str());
+ break;
+ }
+ default:
+ TRACE(_T("OK!\n"));
+ return 0;
+ }
+ if(gce->bIsMe || gcd->ptszID == NULL)
+ Event.bNotification = false;
+
+ // set the event's timestamp
+ Event.bTime = true;
+ time_t now;
+ time(&now);
+ localtime_s(&Event.Time,&now);
+
+ SIRCMessage IRCMsg;
+ IRCMsg.bIsMe = gce->bIsMe;
+ IRCMsg.strMessage = Event.strValue;
+ IRCMsg.Time = Event.Time;
+
+ if(pHistory)
+ {
+ pHistory->LMessages.push_back(IRCMsg);
+
+ // Limit the size to the session logsize
+ if(pHistory->LMessages.size() > CConfig::GetIntSetting(SESSION_LOGSIZE))
+ pHistory->LMessages.pop_front();
+ }
+ else if(gce->ptszNick && gcd->iType == GC_EVENT_QUIT)
+ {
+ tstring strNick = toTstring(gce->ptszNick);
+
+ if(!CAppletManager::GetInstance()->m_LIRCHistorys.empty())
+ {
+ list<CIRCHistory*>::iterator iter = CAppletManager::GetInstance()->m_LIRCHistorys.begin();
+ list<tstring>::iterator nickiter;
+ while(iter != CAppletManager::GetInstance()->m_LIRCHistorys.end())
+ {
+ nickiter = (*iter)->LUsers.begin();
+ while(nickiter != (*iter)->LUsers.end())
+ {
+ if((*nickiter) == strNick)
+ {
+ (*iter)->LMessages.push_back(IRCMsg);
+ // Limit the size to the session logsize
+ if((*iter)->LMessages.size() > CConfig::GetIntSetting(SESSION_LOGSIZE))
+ (*iter)->LMessages.pop_front();
+
+ (*iter)->LUsers.erase(nickiter);
+
+ Event.hContact = (*iter)->hContact;
+ tstring strName = CAppletManager::GetContactDisplayname((*iter)->hContact,true);
+ Event.strDescription = strName + _T(" - ")+Event.strValue;
+ Event.strSummary = _T("(") + toTstring(gcd->pszModule) + _T(") ")+strName;
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ break;
+ }
+ nickiter++;
+ }
+ iter++;
+ }
+ }
+ TRACE(_T("OK!\n"));
+ return 0;
+ }
+ else if(gcd->ptszID != NULL)
+ {
+ TRACE(_T("OK!\n"));
+ return 0;
+ }
+
+ if(pHistory)
+ {
+ tstring strChannel = pHistory->strChannel;
+ if(CConfig::GetBoolSetting(NOTIFY_CHANNELCUTOFF) && strNick.length() > CConfig::GetIntSetting(NOTIFY_CHANNELCUTOFF_OFFSET)) {
+ strChannel = strChannel.erase(CConfig::GetIntSetting(NOTIFY_CHANNELCUTOFF_OFFSET)) + _T("...");
+ }
+ Event.strDescription = strChannel + _T(" - ")+Event.strValue;
+ Event.strSummary = _T("(") + toTstring(gcd->pszModule) + _T(") ")+pHistory->strChannel;
+ }
+ else
+ Event.strDescription = Event.strValue;
+
+ TRACE(_T("OK!\n"));
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+
+ return 0;
+}
+
+//************************************************************************
+// message window event hook function
+//************************************************************************
+int CAppletManager::HookMessageWindowEvent(WPARAM wParam, LPARAM lParam)
+{
+ MessageWindowEventData *mwed = (MessageWindowEventData*)lParam;
+ CEvent Event;
+
+ Event.eType = EVENT_MESSAGEWINDOW;
+ Event.hContact = mwed->hContact;
+ Event.iValue = mwed->uType;
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+
+ return 0;
+}
+
+
+//************************************************************************
+// contact typing notification hook function
+//************************************************************************
+int CAppletManager::HookContactIsTyping(WPARAM wParam, LPARAM lParam)
+{
+ HANDLE hContact = (HANDLE)wParam;
+ int iState = (int)lParam;
+
+ CEvent Event;
+
+ Event.eType = EVENT_TYPING_NOTIFICATION;
+ Event.hContact = hContact;
+ Event.iValue = iState;
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ return 0;
+}
+
+//************************************************************************
+// new event hook function
+//************************************************************************
+int CAppletManager::HookEventAdded(WPARAM wParam, LPARAM lParam)
+{
+ CEvent Event;
+
+ if(CAppletManager::TranslateDBEvent(&Event,wParam,lParam))
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+
+ return 0;
+}
+
+//************************************************************************
+// contact status change hook function
+//************************************************************************
+int CAppletManager::HookStatusChanged(WPARAM wParam, LPARAM lParam)
+{
+ DBCONTACTWRITESETTING *cws = (DBCONTACTWRITESETTING*)lParam;
+
+ if ((wParam == 0) || (strcmp(cws->szSetting,"Status") != NULL))
+ return 0;
+
+
+ // Prepare message and append to queue
+ CEvent Event;
+ Event.hContact = (HANDLE)wParam;
+ int iStatus = cws->value.wVal;
+ Event.iValue = iStatus;
+
+ int iOldStatus = CAppletManager::GetInstance()->m_ContactlistScreen.GetContactStatus(Event.hContact);
+
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)Event.hContact, 0);
+ tstring strProto = toTstring(szProto);
+
+ CProtocolData *pProtocolData = CAppletManager::GetInstance()->GetProtocolData(toTstring(szProto));
+ if(pProtocolData == NULL)
+ return false;
+
+ // Fetch the contacts name
+ tstring strName = CAppletManager::GetContactDisplayname(Event.hContact,true);
+
+ // Get status String
+ Event.strValue = toTstring((char *) CallService(MS_CLIST_GETSTATUSMODEDESCRIPTION, iStatus, 0));
+
+ // check if this is an irc protocol
+ CIRCConnection *pIRCCon = CAppletManager::GetInstance()->GetIRCConnection(strProto);
+
+ // Contact signed on
+ if(iOldStatus == ID_STATUS_OFFLINE && iStatus != ID_STATUS_OFFLINE)
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_SIGNOFF))
+ Event.bNotification = true;
+
+ Event.eType = EVENT_SIGNED_ON;
+ if(pIRCCon && db_get_b(Event.hContact, szProto, "ChatRoom", 0) != 0)
+ {
+ Event.strDescription = TranslateString(_T("Joined %s"),strName.c_str());
+
+ DBVARIANT dbv;
+ if (db_get_ts(Event.hContact, szProto, "Nick", &dbv))
+ return 0;
+ CAppletManager::GetInstance()->CreateIRCHistory(Event.hContact,dbv.ptszVal);
+ db_free(&dbv);
+ }
+ else
+ Event.strDescription = TranslateString(_T("%s signed on (%s)"),strName.c_str(),Event.strValue.c_str());
+ }
+ // Contact signed off
+ else if(iStatus == ID_STATUS_OFFLINE && iOldStatus != ID_STATUS_OFFLINE)
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_SIGNON))
+ Event.bNotification = true;
+
+ Event.eType = EVENT_SIGNED_OFF;
+ if(pIRCCon && db_get_b(Event.hContact, szProto, "ChatRoom", 0) != 0)
+ {
+ Event.strDescription = TranslateString(_T("Left %s"),strName.c_str());
+ // delete IRC-Channel history
+ CAppletManager::GetInstance()->DeleteIRCHistory(Event.hContact);
+ }
+ else
+ Event.strDescription = TranslateString(_T("%s signed off"),strName.c_str());
+ }
+ // Contact changed status
+ else if(iStatus != iOldStatus)
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_STATUS))
+ Event.bNotification = true;
+
+ Event.eType = EVENT_STATUS;
+ Event.strDescription = TranslateString(_T("%s is now %s"),strName.c_str(),Event.strValue.c_str());
+ }
+ // ignore remaining events
+ else
+ return 0;
+
+ if(CConfig::GetBoolSetting(NOTIFY_SHOWPROTO))
+ Event.strDescription = _T("(")+strProto+_T(") ") + Event.strDescription;
+
+
+
+ Event.strSummary = TranslateString(_T("Contactlist event"));
+
+ // Block notifications after connecting/disconnecting
+ if(pProtocolData->iStatus == ID_STATUS_OFFLINE ||
+ pProtocolData->lTimeStamp + PROTOCOL_NOTIFY_DELAY > GetTickCount())
+ Event.bNotification = false;
+
+ //CAppletManager::GetInstance()->ActivateNotificationScreen(&Event);
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+
+ return 0;
+}
+
+//************************************************************************
+// protocoll ack hook function
+//************************************************************************
+int CAppletManager::HookProtoAck(WPARAM wParam, LPARAM lParam)
+{
+ ACKDATA *pAck = (ACKDATA *) lParam;
+
+ if(lParam == 0)
+ return 0;
+
+ // Prepare message and append to queue
+ CEvent Event;
+
+ // Message job handling
+ if(pAck->type == ACKTYPE_MESSAGE)
+ {
+ list<SMessageJob*>::iterator iter = CAppletManager::GetInstance()->m_MessageJobs.begin();
+ while(iter != CAppletManager::GetInstance()->m_MessageJobs.end())
+ {
+ if((*iter)->hEvent == pAck->hProcess && (*iter)->hContact == pAck->hContact)
+ {
+ Event.eType = EVENT_MESSAGE_ACK;
+ Event.hValue = pAck->hProcess;
+ Event.hContact = pAck->hContact;
+ Event.iValue = pAck->result;
+ if(pAck->lParam != 0)
+ Event.strValue = toTstring((char*)pAck->lParam);
+ else
+ Event.strValue = _T("");
+
+ if(Event.iValue == ACKRESULT_SUCCESS)
+ CAppletManager::GetInstance()->FinishMessageJob((*iter));
+ else
+ CAppletManager::GetInstance()->CancelMessageJob((*iter));
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+
+ return 0;
+ }
+ iter++;
+ }
+ }
+ // protocol status changes
+ else if(pAck->type == ACKTYPE_STATUS && pAck->result == ACKRESULT_SUCCESS)
+ {
+ int iOldStatus = (int)pAck->hProcess;
+ int iNewStatus = pAck->lParam;
+
+ tstring strProto = toTstring(pAck->szModule);
+
+ // ignore metacontacts status changes
+ if(toLower(strProto) == _T("metacontacts"))
+ return 0;
+
+ CProtocolData *pProtoData = CAppletManager::GetInstance()->GetProtocolData(strProto);
+ if(pProtoData == NULL)
+ return 0;
+
+ if(iNewStatus == ID_STATUS_CONNECTING)
+ return 0;
+
+ if(iNewStatus == ID_STATUS_OFFLINE)
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_PROTO_SIGNOFF))
+ Event.bNotification = true;
+ Event.eType = EVENT_PROTO_DISCONNECTED;
+ }
+ else if(iNewStatus != ID_STATUS_OFFLINE && iOldStatus == ID_STATUS_CONNECTING)
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_PROTO_SIGNON))
+ Event.bNotification = true;
+ Event.eType = EVENT_PROTO_CONNECTED;
+ }
+ else
+ {
+ if(CConfig::GetBoolSetting(NOTIFY_PROTO_STATUS))
+ Event.bNotification = true;
+ Event.eType = EVENT_PROTO_STATUS;
+ }
+
+ // Skip connecting status
+ if(iNewStatus == ID_STATUS_CONNECTING)
+ return 0;
+
+ pProtoData->iStatus = iNewStatus;
+
+ Event.iValue = iNewStatus;
+ Event.strValue = strProto;
+
+ // set the event description / summary
+ tstring strStatus = toTstring((char *) CallService(MS_CLIST_GETSTATUSMODEDESCRIPTION, iNewStatus, 0));
+ Event.strDescription = _T("(") + Event.strValue + _T(") ")+ TranslateString(_T("You are now %s"),strStatus.c_str());
+ Event.strSummary = TranslateString(_T("Protocol status change"));
+
+ if(Event.eType != EVENT_PROTO_STATUS)
+ pProtoData->lTimeStamp = GetTickCount();
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ //CAppletManager::GetInstance()->ActivateNotificationScreen(&Event);
+ }
+
+ return 0;
+}
+
+//************************************************************************
+// contact added hook function
+//************************************************************************
+int CAppletManager::HookContactAdded(WPARAM wParam, LPARAM lParam)
+{
+ CEvent Event;
+ Event.eType = EVENT_CONTACT_ADDED;
+ Event.hContact = (HANDLE)wParam;
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ return 0;
+}
+
+//************************************************************************
+// contact deleted hook function
+//************************************************************************
+int CAppletManager::HookContactDeleted(WPARAM wParam, LPARAM lParam)
+{
+ CEvent Event;
+ Event.eType = EVENT_CONTACT_DELETED;
+ Event.hContact = (HANDLE)wParam;
+ Event.bNotification = CConfig::GetBoolSetting(NOTIFY_CONTACTS);
+ Event.bLog = Event.bNotification;
+
+ tstring strName = CAppletManager::GetContactDisplayname(Event.hContact,true);
+
+ Event.strDescription = TranslateString(_T("%s was deleted from contactlist!"),strName.c_str());
+
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ return 0;
+}
+
+//************************************************************************
+// setting changed hook function
+//************************************************************************
+int CAppletManager::HookSettingChanged(WPARAM wParam,LPARAM lParam)
+{
+ DBCONTACTWRITESETTING *dbcws = (DBCONTACTWRITESETTING*)lParam;
+
+ CEvent Event;
+ Event.hContact = (HANDLE)wParam;
+
+ if(!lstrcmpA(dbcws->szModule,"MetaContacts"))
+ {
+ //if(!lstrcmpA(dbcws->szSetting,"Enabled")) {
+ // CAppletManager::GetInstance()->OnConfigChanged();
+ // return 0;
+ //} else
+ if(!lstrcmpA(dbcws->szSetting,"IsSubcontact")) {
+ Event.eType = EVENT_CONTACT_GROUP;
+ DBVARIANT dbv;
+ int res = db_get_ts((HANDLE)wParam, "CList", "Group", &dbv);
+ if(!res)
+ Event.strValue = dbv.ptszVal;
+ db_free(&dbv);
+ } else {
+ return 0;
+ }
+ }
+ else if(!lstrcmpA(dbcws->szSetting,"Nick") || !lstrcmpA(dbcws->szSetting,"MyHandle"))
+ {
+ DBVARIANT dbv={0};
+ // if the protocol nick has changed, check if a custom handle is set
+ if(!lstrcmpA(dbcws->szSetting,"Nick"))
+ {
+ if (!db_get_ts(Event.hContact, "CList", "MyHandle", &dbv))
+ {
+ // handle found, ignore this event
+ if(dbv.pszVal && strlen(dbv.pszVal)>0)
+ return 0;
+ }
+ db_free(&dbv);
+ }
+
+ Event.eType = EVENT_CONTACT_NICK;
+ if(dbcws->value.type != DBVT_DELETED && dbcws->value.pszVal && strlen(dbcws->value.pszVal)>0)
+ {
+#ifdef _UNICODE
+ if(dbcws->value.type == DBVT_UTF8)
+ Event.strValue = Utf8_Decode(dbcws->value.pszVal);
+ else
+#endif
+ Event.strValue = toTstring(dbcws->value.pszVal);
+ }
+ else
+ {
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)Event.hContact, 0);
+ if (db_get_ts(Event.hContact, szProto, "Nick", &dbv))
+ return 0;
+ Event.strValue = dbv.ptszVal;
+ db_free(&dbv);
+ }
+ }
+ else if(!lstrcmpA(dbcws->szModule,"CList"))
+ {
+ if(!lstrcmpA(dbcws->szSetting,"Hidden"))
+ {
+ Event.eType = EVENT_CONTACT_HIDDEN;
+ Event.iValue = db_get_b((HANDLE)wParam,"CList","Hidden",0);
+ }
+ else if(!lstrcmpA(dbcws->szSetting,"Group"))
+ {
+ Event.eType = EVENT_CONTACT_GROUP;
+ DBVARIANT dbv;
+ int res = db_get_ts((HANDLE)wParam, "CList", "Group", &dbv);
+ if(!res)
+ Event.strValue = dbv.ptszVal;
+ db_free(&dbv);
+ }
+ else
+ return 0;
+ }
+ else
+ return 0;
+ CAppletManager::GetInstance()->HandleEvent(&Event);
+ return 0;
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CAppletManager.h b/plugins/MirandaG15/src/CAppletManager.h
new file mode 100644
index 0000000000..dee9b96a9e
--- /dev/null
+++ b/plugins/MirandaG15/src/CAppletManager.h
@@ -0,0 +1,193 @@
+#ifndef _COUTPUTMANAGER_H_
+#define _COUTPUTMANAGER_H_
+
+#include "CLCDOutputManager.h"
+
+#include "CProtocolData.h"
+#include "CIRCHistory.h"
+#include "CIRCConnection.h"
+
+#include "CNotificationScreen.h"
+#include "CEventScreen.h"
+#include "CContactlistScreen.h"
+#include "CChatScreen.h"
+#include "CCreditsScreen.h"
+#include "CScreensaverScreen.h"
+
+#include "CLCDConnectionLogitech.h"
+
+struct SMessageJob
+{
+ HANDLE hEvent;
+ HANDLE hContact;
+ DWORD dwFlags;
+ char *pcBuffer;
+ int iBufferSize;
+ DWORD dwTimestamp;
+};
+
+class CAppletManager : public CLCDOutputManager
+{
+public:
+ // returns the AppletManager's instance
+ static CAppletManager *GetInstance();
+
+ // Constructor
+ CAppletManager();
+ // Destructor
+ ~CAppletManager();
+
+ // Initializes the AppletManager
+ bool Initialize(tstring strAppletName);
+ // Deinitializes the AppletManager
+ bool Shutdown();
+ // Updates the AppletManager
+ bool Update();
+
+ // the update timer's callback function
+ static VOID CALLBACK UpdateTimer(HWND hwnd,UINT uMsg,UINT_PTR idEvent,DWORD dwTime);
+
+ // called when the plugin's configuration has changed
+ void OnConfigChanged();
+
+ // called to process the specified event
+ void HandleEvent(CEvent *pEvent);
+
+ // screen activation functions
+ void ActivatePreviousScreen();
+ void ActivateScreensaverScreen();
+ void ActivateCreditsScreen();
+ void ActivateEventScreen();
+ void ActivateCListScreen();
+ bool ActivateChatScreen(HANDLE hContact);
+
+ // hook functions
+ static int HookMessageWindowEvent(WPARAM wParam, LPARAM lParam);
+ static int HookContactIsTyping(WPARAM wParam, LPARAM lParam);
+ static int HookEventAdded(WPARAM wParam, LPARAM lParam);
+ static int HookStatusChanged(WPARAM wParam, LPARAM lParam);
+ static int HookProtoAck(WPARAM wParam, LPARAM lParam);
+ static int HookContactAdded(WPARAM wParam, LPARAM lParam);
+ static int HookContactDeleted(WPARAM wParam, LPARAM lParam);
+ static int HookSettingChanged(WPARAM wParam,LPARAM lParam);
+ static int HookChatInbound(WPARAM wParam,LPARAM lParam);
+
+ // check if a contacts message window is opened
+ static bool IsMessageWindowOpen(HANDLE hContact);
+ // marks the given event as read
+ static void MarkMessageAsRead(HANDLE hContact,HANDLE hEvent);
+ // translates the given database event
+ static bool TranslateDBEvent(CEvent *pEvent,WPARAM wParam, LPARAM lParam);
+ // sends a message to the specified contact
+ static HANDLE SendMessageToContact(HANDLE hContact,tstring strMessage);
+ // sends typing notifications to the specified contact
+ static void SendTypingNotification(HANDLE hContact,bool bEnable);
+
+ // returns the contacts message service name
+ static char *GetMessageServiceName(HANDLE hContact,bool bIsUnicode);
+ static bool IsUtfSendAvailable(HANDLE hContact);
+ // returns a formatted timestamp string
+ static tstring GetFormattedTimestamp(tm *time);
+
+ // returns wether or not a contact is a subcontact
+ static bool IsSubContact(HANDLE hContact);
+ // returns the contacts group
+ static tstring GetContactGroup(HANDLE hContact);
+ // returns the contacts displayname
+ static tstring GetContactDisplayname(HANDLE hContact,bool bShortened=false);
+
+ // returns the history class for the specified IRC channel
+ CIRCHistory *GetIRCHistory(HANDLE hContact);
+ CIRCHistory *GetIRCHistoryByName(tstring strProtocol,tstring strChannel);
+
+ // returns the IRC connection class for the specified protocol
+ CIRCConnection *GetIRCConnection(tstring strProtocol);
+ // creates the IRC connection class for the specified protocol
+ CIRCConnection *CreateIRCConnection(tstring strProtocol);
+
+ // returns the bitmap for the specified status
+ HBITMAP GetStatusBitmap(int iStatus);
+ // returns the bitmap for the specified event
+ HBITMAP GetEventBitmap(EventType eType, bool bLarge = false);
+
+ // checks if the patched IRC protocol is in place
+ bool IsIRCHookEnabled();
+
+ static tstring TranslateString(TCHAR *szString,...);
+
+private:
+ list<CIRCHistory*> m_LIRCHistorys;
+ // deletes the history class for the specified IRC channel
+ void DeleteIRCHistory(HANDLE hContact);
+ // creates a history class for the specified IRC channel
+ CIRCHistory *CreateIRCHistory(HANDLE hContact,tstring strChannel);
+ CIRCHistory *CreateIRCHistoryByName(tstring strProtocol,tstring strChannel);
+
+ // activate a screen
+ void ActivateScreen(CScreen *pScreen);
+
+ // applies the volumewheel setting
+ void SetVolumeWheelHook();
+
+ // Called when the connection state has changed
+ void OnConnectionChanged(int iConnectionState);
+ // Called when the active screen has expired
+ void OnScreenExpired(CLCDScreen *pScreen);
+
+ // updates all pending message jobs
+ void UpdateMessageJobs();
+ // adds a message job to the list
+ void AddMessageJob(SMessageJob *pJob);
+ // finishes a message job
+ void FinishMessageJob(SMessageJob *pJob);
+ // cancels a message job
+ void CancelMessageJob(SMessageJob *pJob);
+
+ // removes a message job from the list
+
+ // strip IRC formatting
+ static tstring StripIRCFormatting(tstring strText);
+
+ // Light status
+ SG15LightStatus m_G15LightStatus;
+
+ list<SMessageJob*> m_MessageJobs;
+
+ // update timer handle
+ UINT m_uiTimer;
+
+ // screens
+ CNotificationScreen m_NotificationScreen;
+ CEventScreen m_EventScreen;
+ CContactlistScreen m_ContactlistScreen;
+ CChatScreen m_ChatScreen;
+ CCreditsScreen m_CreditsScreen;
+ CScreensaverScreen m_ScreensaverScreen;
+
+ // protocol data
+ vector<CProtocolData*> m_vProtocolData;
+ CProtocolData* GetProtocolData(tstring strProtocol);
+
+ // hook handles
+ HANDLE m_hMIHookMessageWindowEvent;
+ HANDLE m_hMIHookContactIsTyping;
+ HANDLE m_hMIHookEventAdded;
+ HANDLE m_hMIHookStatusChanged;
+ HANDLE m_hMIHookProtoAck;
+ HANDLE m_hMIHookSettingChanged;
+ HANDLE m_hMIHookContactDeleted;
+ HANDLE m_hMIHookContactAdded;
+
+ vector<CIRCConnection*> m_vIRCConnections;
+
+ // last active screen
+ CScreen *m_pLastScreen;
+
+ bool m_bScreensaver;
+
+ HBITMAP m_ahStatusBitmaps[8];
+ HBITMAP m_ahEventBitmaps[4];
+ HBITMAP m_ahLargeEventBitmaps[4];
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CChatScreen.cpp b/plugins/MirandaG15/src/CChatScreen.cpp
new file mode 100644
index 0000000000..dc87294e26
--- /dev/null
+++ b/plugins/MirandaG15/src/CChatScreen.cpp
@@ -0,0 +1,800 @@
+#include "stdafx.h"
+#include "CChatScreen.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CChatScreen::CChatScreen()
+{
+ m_bTyping = false;
+ m_hContact = NULL;
+ m_bHideTitle = false;
+ m_bHideLabels = false;
+
+ m_dwMaximizedTimer = 0;
+ m_bMaximizedTimer = false;
+ m_bCloseTimer = false;
+ m_dwCloseTimer = 0;
+
+ m_eReplyState = REPLY_STATE_NONE;
+ m_iStatus = ID_STATUS_OFFLINE;
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CChatScreen::~CChatScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CChatScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_InfoText.Initialize();
+ m_UserName.Initialize();
+ m_UserStatus.Initialize();
+ m_UserProto.Initialize();
+ m_Input.Initialize();
+ m_TextLog.Initialize();
+ m_Scrollbar.Initialize();
+
+ UpdateObjects();
+ // other attributes
+ m_InfoText.SetAlignment(DT_CENTER);
+ m_InfoText.SetWordWrap(TRUE);
+ m_InfoText.SetText(_T(""));
+ m_InfoText.Show(0);
+
+ m_UserName.SetAlignment(DT_CENTER);
+ m_UserName.SetWordWrap(TRUE);
+ m_UserName.SetText(_T("Proto"));
+
+
+ m_UserStatus.SetAlignment(DT_LEFT);
+ m_UserStatus.SetWordWrap(TRUE);
+ m_UserStatus.SetText(_T("Status"));
+
+
+ m_UserProto.SetAlignment(DT_RIGHT);
+ m_UserProto.SetWordWrap(TRUE);
+ m_UserProto.SetText(_T("User"));
+
+ m_Input.Show(0);
+
+
+
+ m_TextLog.Show(1);
+
+
+
+ m_TextLog.SetScrollbar(&m_Scrollbar);
+
+ AddObject(&m_Scrollbar);
+ AddObject(&m_TextLog);
+ AddObject(&m_Input);
+ AddObject(&m_InfoText);
+ AddObject(&m_UserName);
+ AddObject(&m_UserStatus);
+ AddObject(&m_UserProto);
+
+
+ SetButtonBitmap(0,IDB_UP);
+ SetButtonBitmap(1,IDB_DOWN);
+ SetButtonBitmap(2,IDB_HISTORY);
+ SetButtonBitmap(3,IDB_REPLY);
+
+ return true;
+}
+
+//************************************************************************
+// Shutdown the screen
+//************************************************************************
+bool CChatScreen::Shutdown()
+{
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// update's the screens objects ( sizes, fonts etc)
+//************************************************************************
+void CChatScreen::UpdateObjects()
+{
+ m_bHideTitle = false;
+ m_bHideLabels = !CConfig::GetBoolSetting(SHOW_LABELS);
+
+ if(IsMaximized())
+ {
+ if(!m_bHideTitle && !CConfig::GetBoolSetting(MAXIMIZED_TITLE))
+ m_bHideTitle = true;
+
+ if(!m_bHideLabels && !CConfig::GetBoolSetting(MAXIMIZED_LABELS))
+ m_bHideLabels = true;
+ }
+
+ // Fonts
+ m_TextLog.SetFont(CConfig::GetFont(FONT_SESSION));
+ m_Input.SetFont(CConfig::GetFont(FONT_SESSION));
+ m_InfoText.SetFont(CConfig::GetFont(FONT_SESSION));
+
+ m_UserName.SetFont(CConfig::GetFont(FONT_TITLE));
+ m_UserStatus.SetFont(CConfig::GetFont(FONT_TITLE));
+ m_UserProto.SetFont(CConfig::GetFont(FONT_TITLE));
+
+ int w = GetWidth() - 8;
+ // Sizes
+ m_UserName.SetSize(w*0.4, CConfig::GetFontHeight(FONT_TITLE));
+ m_UserStatus.SetSize(w*0.25, CConfig::GetFontHeight(FONT_TITLE));
+ m_UserProto.SetSize(w*0.3, CConfig::GetFontHeight(FONT_TITLE));
+
+ int iHeight =GetHeight();
+ iHeight -= m_bHideTitle?0:CConfig::GetFontHeight(FONT_TITLE)+2;
+ iHeight -= m_bHideLabels?0:5;
+
+ m_Input.SetSize(GetWidth()-5, iHeight);
+ m_TextLog.SetSize(GetWidth()-5, iHeight);
+
+ m_InfoText.SetSize(160, 28);
+ m_InfoText.SetOrigin(0,(iHeight-CConfig::GetFontHeight(FONT_SESSION))/2);
+
+ // Origins
+
+ m_UserName.SetOrigin(8+w*0.25, 0);
+ m_UserStatus.SetOrigin(8, 0);
+ m_UserProto.SetOrigin(GetWidth()-w*0.3, 0);
+
+ m_TextLog.SetOrigin(0, m_bHideTitle?0:CConfig::GetFontHeight(FONT_TITLE)+2);
+ m_Input.SetOrigin(0,m_bHideTitle?0:CConfig::GetFontHeight(FONT_TITLE)+2);
+
+ m_InfoText.SetOrigin(0, 10);
+
+ m_UserName.Show(!m_bHideTitle);
+ m_UserStatus.Show(!m_bHideTitle);
+ m_UserProto.Show(!m_bHideTitle);
+
+ m_Scrollbar.SetOrigin(GetWidth()-4,(m_bHideTitle?0:CConfig::GetFontHeight(FONT_TITLE)+2));
+ m_Scrollbar.SetSize(4,iHeight);
+
+ // other options
+ m_TextLog.SetLogSize(CConfig::GetIntSetting(SESSION_LOGSIZE));
+
+ m_Input.SetBreakKeys(CConfig::GetBoolSetting(SESSION_SENDRETURN)?KEYS_RETURN:KEYS_CTRL_RETURN);
+ m_Input.ShowSymbols(CConfig::GetBoolSetting(SESSION_SYMBOLS));
+
+ ShowButtons(!m_bHideLabels);
+}
+
+//************************************************************************
+// update's the screens title labels
+//************************************************************************
+void CChatScreen::UpdateLabels()
+{
+ tstring strNickname = CAppletManager::GetContactDisplayname(m_hContact);
+ char *szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO,(UINT)m_hContact,0);
+ char *szStatus = NULL;
+ m_iStatus = ID_STATUS_OFFLINE;
+
+ tstring strProto = _T("");
+ tstring strStatus = _T("");
+ if(szProto != NULL)
+ {
+ strProto = _T("(") + toTstring(szProto) + _T(")");
+ m_iStatus = db_get_w(m_hContact,szProto,"Status",ID_STATUS_OFFLINE);
+ }
+
+ szStatus = (char *) CallService(MS_CLIST_GETSTATUSMODEDESCRIPTION, m_iStatus, 0);
+ if(szStatus != NULL)
+ strStatus = toTstring(szStatus);
+
+ m_UserName.SetText(strNickname.c_str());
+ m_UserStatus.SetText(strStatus.c_str());
+
+ if(m_bContactTyping && CConfig::GetBoolSetting(SESSION_SHOWTYPING))
+ m_UserProto.SetText(CAppletManager::TranslateString(_T("typing..")));
+ else
+ m_UserProto.SetText(strProto.c_str());
+}
+
+// returns wether the input mode is active
+bool CChatScreen::IsInputActive()
+{
+ if(m_eReplyState != REPLY_STATE_NONE)
+ return true;
+ else
+ return false;
+}
+
+//************************************************************************
+// returns the chat contact
+//************************************************************************
+HANDLE CChatScreen::GetContact()
+{
+ return m_hContact;
+}
+
+//************************************************************************
+// sets the screen's chat contact
+//************************************************************************
+bool CChatScreen::SetContact(HANDLE hContact)
+{
+ if(hContact == NULL)
+ {
+ m_hContact = NULL;
+ return true;
+ }
+
+ // Check if the contact is valid
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)hContact, 0);
+ m_strProto = toTstring(szProto);
+
+ CIRCConnection *pIRCCon = CAppletManager::GetInstance()->GetIRCConnection(m_strProto);
+ if(pIRCCon)
+ m_bIRCProtocol = true;
+ else
+ m_bIRCProtocol = false;
+
+
+ if(!szProto)
+ return false;
+
+ if(m_eReplyState != REPLY_STATE_NONE)
+ DeactivateMessageMode();
+ else if(IsMaximized())
+ Minimize();
+
+ m_bContactTyping = false;
+ m_hContact = hContact;
+ m_TextLog.ClearLog();
+ UpdateLabels();
+
+ LoadHistory();
+
+ return true;
+}
+
+//************************************************************************
+// loads the contacts history
+//************************************************************************
+void CChatScreen::LoadHistory()
+{
+ if(!m_hContact)
+ return;
+
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)m_hContact, 0);
+
+ if(m_bIRCProtocol && db_get_b(m_hContact, szProto, "ChatRoom", 0) != 0)
+ {
+ if(!CAppletManager::GetInstance()->IsIRCHookEnabled())
+ {
+ time_t now;
+ tm tm_now;
+ time(&now);
+ localtime_s(&tm_now,&now);
+
+ AddIncomingMessage(CAppletManager::TranslateString(_T("IRC-Chatroom support is disabled!\nYou need to install the patched IRC.dll (see the readme) to use IRC-Chatrooms on the LCD")),&tm_now,true);
+ }
+ else
+ {
+ CIRCHistory *pHistory = CAppletManager::GetInstance()->GetIRCHistory(m_hContact);
+ if(pHistory)
+ {
+ list<SIRCMessage>::iterator iter = pHistory->LMessages.begin();
+ while(iter != pHistory->LMessages.end())
+ {
+ if((*iter).bIsMe)
+ AddOutgoingMessage((*iter).strMessage,&((*iter).Time),true);
+ else
+ AddIncomingMessage((*iter).strMessage,&((*iter).Time),true);
+ iter++;
+ }
+ }
+ }
+ }
+ else
+ {
+ // Get last events from database
+ CEvent Event;
+ list<HANDLE> LHandles;
+ HANDLE hEvent = db_event_last(m_hContact);
+ HANDLE hUnread = db_event_firstUnread(m_hContact);
+
+ if(CConfig::GetBoolSetting(SESSION_LOADDB))
+ {
+ while(hEvent != NULL && hUnread != NULL)
+ {
+ LHandles.push_front(hEvent);
+ if(CConfig::GetBoolSetting(SESSION_LOADDB) && *(LHandles.begin()) == hUnread)
+ break;
+ hEvent = db_event_prev(hEvent);
+ }
+ }
+ else
+ {
+ for (int i = CConfig::GetIntSetting(SESSION_LOGSIZE); i > 0 && hEvent!=NULL; i--)
+ {
+ LHandles.push_front(hEvent);
+ hEvent = db_event_prev(hEvent);
+ }
+ }
+
+ bool bRead = true;
+ while(!(LHandles.empty()))
+ {
+ if(CAppletManager::TranslateDBEvent(&Event,(LPARAM)m_hContact,(WPARAM)*(LHandles.begin())))
+ {
+ if(Event.hValue == hUnread)
+ bRead = false;
+ if(Event.eType == EVENT_MSG_RECEIVED)
+ {
+ AddIncomingMessage(Event.strValue,&Event.Time);
+ if(!bRead && CConfig::GetBoolSetting(SESSION_MARKREAD) && !CAppletManager::IsMessageWindowOpen(m_hContact))
+ CAppletManager::MarkMessageAsRead(m_hContact,Event.hValue);
+ }
+ else
+ AddOutgoingMessage(Event.strValue,&Event.Time);
+
+ }
+ LHandles.pop_front();
+ }
+ }
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CChatScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ if(CConfig::GetBoolSetting(SESSION_CLOSE)) {
+ if(!CAppletManager::GetInstance()->GetLCDConnection()->IsForeground()) {
+ if(!m_bCloseTimer && CConfig::GetIntSetting(SESSION_CLOSETIMER) != 0) {
+ m_bCloseTimer = true;
+ m_dwCloseTimer = GetTickCount();
+ } else if(CConfig::GetIntSetting(SESSION_CLOSETIMER) == 0 || GetTickCount() - m_dwCloseTimer >= CConfig::GetIntSetting(SESSION_CLOSETIMER)) {
+ m_bCloseTimer = false;
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ return true;
+ }
+ }
+ }
+
+ if(m_bMaximizedTimer && m_dwMaximizedDuration != INFINITE)
+ {
+ if(m_dwMaximizedTimer + m_dwMaximizedDuration <= GetTickCount())
+ Minimize();
+ }
+
+ if(m_eReplyState == REPLY_STATE_INPUT && !m_Input.IsInputActive())
+ SendCurrentMessage();
+
+ // Handle Typing notifications
+ if(IsInputActive())
+ {
+ if(m_Input.GetLastInputTime() + 10000 <= GetTickCount())
+ {
+ if(m_bTyping)
+ {
+ m_bTyping = false;
+ CAppletManager::GetInstance()->SendTypingNotification(m_hContact,0);
+ }
+ }
+ else if(CConfig::GetBoolSetting(SESSION_SENDTYPING) && !m_bTyping)
+ {
+ m_bTyping = true;
+ CAppletManager::GetInstance()->SendTypingNotification(m_hContact,1);
+ }
+ }
+ else if(m_bTyping)
+ {
+ m_bTyping = false;
+ CAppletManager::GetInstance()->SendTypingNotification(m_hContact,0);
+ }
+
+ return true;
+}
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CChatScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ if(!m_bHideTitle)
+ {
+ int iTitleHeight = CConfig::GetFontHeight(FONT_TITLE)+1;
+ pGfx->DrawLine(0,iTitleHeight<6?6:iTitleHeight,GetWidth(),iTitleHeight<6?6:iTitleHeight);
+ int iOffset = (iTitleHeight-5)/2;
+ pGfx->DrawBitmap(1,iOffset,5,5,CAppletManager::GetInstance()->GetStatusBitmap(m_iStatus));
+ }
+
+ return true;
+}
+
+//************************************************************************
+// Adds an outgoing message to the log
+//************************************************************************
+void CChatScreen::AddOutgoingMessage(tstring strMessage,tm *time,bool bIRC)
+{
+ tstring strPrefix = bIRC?_T(""):_T(">> ");
+ if(CConfig::GetBoolSetting(SESSION_TIMESTAMPS))
+ strPrefix += CAppletManager::GetFormattedTimestamp(time) + _T(" ");
+
+ // adjust the scroll mode
+ m_TextLog.SetAutoscrollMode(SCROLL_LINE);
+
+ // add the message
+ m_TextLog.AddText(strPrefix + strMessage,true);
+
+}
+
+//************************************************************************
+// Adds an incoming message to the log
+//************************************************************************
+void CChatScreen::AddIncomingMessage(tstring strMessage,tm *time,bool bIRC)
+{
+ tstring strPrefix = bIRC?_T(""):_T("<< ");
+ if(CConfig::GetBoolSetting(SESSION_TIMESTAMPS))
+ strPrefix += CAppletManager::GetFormattedTimestamp(time) + _T(" ");
+
+
+ // adjust the scroll mode
+ EScrollMode eMode;
+ switch(CConfig::GetIntSetting(SESSION_AUTOSCROLL))
+ {
+ case SESSION_AUTOSCROLL_NONE: eMode = SCROLL_NONE; break;
+ case SESSION_AUTOSCROLL_FIRST: eMode = SCROLL_MESSAGE; break;
+ case SESSION_AUTOSCROLL_LAST: eMode = SCROLL_LINE; break;
+ }
+ m_TextLog.SetAutoscrollMode(eMode);
+
+ // add the message
+ m_TextLog.AddText(strPrefix + strMessage);
+}
+
+//************************************************************************
+// activates the input mode
+//************************************************************************
+void CChatScreen::ActivateMessageMode()
+{
+ m_InfoText.Show(0);
+ m_TextLog.Show(0);
+ m_TextLog.SetScrollbar(NULL);
+ m_Input.SetScrollbar(&m_Scrollbar);
+
+ if(m_eReplyState != REPLY_STATE_FAILED)
+ m_Input.Reset();
+
+ m_Input.Show(1);
+ m_Input.ActivateInput();
+
+ m_eReplyState = REPLY_STATE_INPUT;
+
+ SetButtonBitmap(2,IDB_BACK);
+ SetButtonBitmap(3,IDB_SEND);
+
+ if(CConfig::GetBoolSetting(SESSION_REPLY_MAXIMIZED))
+ Maximize();
+ else
+ Minimize();
+}
+
+//************************************************************************
+// sends the message
+//************************************************************************
+void CChatScreen::SendCurrentMessage()
+{
+ if(m_Input.GetText().empty())
+ {
+ DeactivateMessageMode();
+ return;
+ }
+ ASSERT(m_eReplyState == REPLY_STATE_INPUT);
+
+ m_eReplyState = REPLY_STATE_SENDING;
+
+ m_Input.DeactivateInput();
+
+ m_InfoText.SetText(CAppletManager::TranslateString(_T("Sending message...")));
+ m_InfoText.Show(1);
+ m_Input.Show(0);
+
+ m_hMessage = CAppletManager::SendMessageToContact(m_hContact,m_Input.GetText());
+ if(m_hMessage == NULL)
+ {
+ DeactivateMessageMode();
+ return;
+ }
+ SetButtonBitmap(2,NULL);
+ SetButtonBitmap(3,NULL);
+}
+
+//************************************************************************
+// invalidates the message mode
+//************************************************************************
+void CChatScreen::InvalidateMessageMode(tstring strError)
+{
+ m_eReplyState = REPLY_STATE_FAILED;
+
+ m_InfoText.SetText(strError);
+
+ SetButtonBitmap(2,IDB_BACK);
+ SetButtonBitmap(3,IDB_SEND);
+
+ if(IsMaximized())
+ Minimize();
+}
+
+//************************************************************************
+// deactivates the input mode
+//************************************************************************
+void CChatScreen::DeactivateMessageMode()
+{
+ m_Input.Reset();
+
+ m_Input.SetScrollbar(NULL);
+ m_TextLog.SetScrollbar(&m_Scrollbar);
+
+ m_TextLog.Show(1);
+ m_InfoText.Show(0);
+ m_Input.Show(0);
+
+ m_Input.DeactivateInput();
+
+ m_eReplyState = REPLY_STATE_NONE;
+
+ SetButtonBitmap(2,IDB_HISTORY);
+ SetButtonBitmap(3,IDB_REPLY);
+
+ if(IsMaximized())
+ Minimize();
+}
+
+//************************************************************************
+// maximizes the content object
+//************************************************************************
+void CChatScreen::Maximize(DWORD dwTimer)
+{
+ m_bMaximizedTimer = true;
+ m_dwMaximizedTimer = GetTickCount();
+ m_dwMaximizedDuration = dwTimer;
+ UpdateObjects();
+}
+
+//************************************************************************
+// minimizes the content object
+//************************************************************************
+void CChatScreen::Minimize()
+{
+ m_bMaximizedTimer = false;
+ m_dwMaximizedTimer = 0;
+ UpdateObjects();
+}
+
+//************************************************************************
+// returns wether the content is maximized
+//************************************************************************
+bool CChatScreen::IsMaximized()
+{
+ return m_bMaximizedTimer;
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CChatScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+ UpdateObjects();
+}
+
+//************************************************************************
+// Called when the applet's configuration has changed
+//************************************************************************
+void CChatScreen::OnConfigChanged()
+{
+ CScreen::OnConfigChanged();
+
+ UpdateObjects();
+
+ m_TextLog.ClearLog();
+ LoadHistory();
+}
+
+//************************************************************************
+// Called when an event is received
+//************************************************************************
+void CChatScreen::OnEventReceived(CEvent *pEvent)
+{
+ // only let events for this contact pass
+ if(pEvent->hContact != m_hContact &&
+ // expect for IRC events without a contact -> global notifications
+ !((pEvent->eType == EVENT_IRC_SENT || pEvent->eType == EVENT_IRC_RECEIVED) && pEvent->hContact == NULL))
+ return;
+
+ switch(pEvent->eType)
+ {
+ case EVENT_MESSAGE_ACK:
+ if(pEvent->hValue != m_hMessage)
+ return;
+
+ if(pEvent->iValue == ACKRESULT_SUCCESS)
+ DeactivateMessageMode();
+ else
+ InvalidateMessageMode(pEvent->strValue.empty()?CAppletManager::TranslateString(_T("Could not send the message!")):pEvent->strValue);
+ break;
+ case EVENT_IRC_SENT:
+ // Add the message to the log
+ AddOutgoingMessage(pEvent->strValue,&pEvent->Time,true);
+ break;
+ case EVENT_IRC_RECEIVED:
+ // Add the message to the log
+ AddIncomingMessage(pEvent->strValue,&pEvent->Time,true);
+ break;
+ case EVENT_MSG_RECEIVED:
+ // mark it as read if required
+ if(CConfig::GetBoolSetting(SESSION_MARKREAD) && !CAppletManager::IsMessageWindowOpen(m_hContact))
+ CAppletManager::MarkMessageAsRead(m_hContact,pEvent->hValue);
+ // Add the message to the log
+ AddIncomingMessage(pEvent->strValue,&pEvent->Time);
+ break;
+ case EVENT_MSG_SENT:
+ // Add the message to the log
+ AddOutgoingMessage(pEvent->strValue,&pEvent->Time);
+ break;
+ case EVENT_CONTACT_HIDDEN:
+ // contact is set to hidden
+ if(pEvent->iValue == 1)
+ {
+ // Close the chat screen if the contact is an irc chatroom
+ if(!(m_bIRCProtocol && db_get_b(pEvent->hContact, toNarrowString(m_strProto).c_str(), "ChatRoom", 0) != 0))
+ break;
+ }
+ else
+ break;
+ case EVENT_CONTACT_DELETED:
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ break;
+ case EVENT_TYPING_NOTIFICATION:
+ m_bContactTyping = pEvent->iValue != 0;
+ UpdateLabels();
+ break;
+ case EVENT_STATUS:
+ case EVENT_CONTACT_NICK:
+ case EVENT_SIGNED_OFF:
+ case EVENT_SIGNED_ON:
+ UpdateLabels();
+ break;
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CChatScreen::OnLCDButtonDown(int iButton)
+{
+ switch(m_eReplyState)
+ {
+ case REPLY_STATE_NONE:
+ if(iButton == LGLCDBUTTON_CANCEL) {
+ CAppletManager::GetInstance()->ActivatePreviousScreen();
+ } else if(iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_MENU)
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ // enter reply mode
+ else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK)
+ ActivateMessageMode();
+ else {
+ bool bRes = false;
+ if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ bRes = m_TextLog.ScrollUp();
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ bRes = m_TextLog.ScrollDown();
+ }
+
+ if(bRes && CConfig::GetBoolSetting(SESSION_SCROLL_MAXIMIZED)) {
+ Maximize(5000);
+ }
+ }
+ break;
+ case REPLY_STATE_FAILED:
+ if(iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_CANCEL) {
+ DeactivateMessageMode();
+ } else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) {
+ ActivateMessageMode();
+ } else if(iButton == LGLCDBUTTON_CANCEL) {
+ DeactivateMessageMode();
+ CAppletManager::GetInstance()->ActivatePreviousScreen();
+ } else if(iButton == LGLCDBUTTON_MENU) {
+ DeactivateMessageMode();
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ }
+ break;
+ case REPLY_STATE_SENDING:
+ break;
+ case REPLY_STATE_INPUT:
+ if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_Input.ScrollLine(0);
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_Input.ScrollLine(1);
+ // send the message
+ } else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) {
+ SendCurrentMessage();
+ // cancel message mode
+ } else if(iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_CANCEL) {
+ DeactivateMessageMode();
+ }
+ break;
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CChatScreen::OnLCDButtonRepeated(int iButton)
+{
+ switch(m_eReplyState)
+ {
+ case REPLY_STATE_NONE:
+ if(iButton < 2)
+ {
+ bool bRes = false;
+ if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ bRes = m_TextLog.ScrollUp();
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ bRes = m_TextLog.ScrollDown();
+ }
+
+ if(bRes && CConfig::GetBoolSetting(SESSION_SCROLL_MAXIMIZED))
+ Maximize(5000);
+ }
+ break;
+ case REPLY_STATE_INPUT:
+ if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_Input.ScrollLine(0);
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_Input.ScrollLine(1);
+ }
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CChatScreen::OnLCDButtonUp(int iButton)
+{
+
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CChatScreen::OnActivation()
+{
+ m_bCloseTimer = false;
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CChatScreen::OnDeactivation()
+{
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CChatScreen::OnExpiration()
+{
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CChatScreen.h b/plugins/MirandaG15/src/CChatScreen.h
new file mode 100644
index 0000000000..7af002e46c
--- /dev/null
+++ b/plugins/MirandaG15/src/CChatScreen.h
@@ -0,0 +1,113 @@
+#ifndef _CCHATSCREEN_H_
+#define _CCHATSCREEN_H_
+
+#include "CScreen.h"
+
+#include "CLCDLabel.h"
+#include "CLCDTextLog.h"
+#include "CLCDInput.h"
+
+class CChatScreen : public CScreen
+{
+public:
+ // Constructor
+ CChatScreen();
+ // Destructor
+ ~CChatScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when an event is received
+ void OnEventReceived(CEvent *pEvent);
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+ // Called when the applet's configuration has changed
+ void OnConfigChanged();
+ // Called when the screen size has changed
+ void OnSizeChanged();
+
+ // Set's the chat contact
+ bool SetContact(HANDLE hContact);
+ // returns the chat contact
+ HANDLE GetContact();
+
+ // returns wether the input mode is active
+ bool IsInputActive();
+protected:
+ // loads the contacts history
+ void LoadHistory();
+
+ // Adds an outgoing message to the log
+ void AddOutgoingMessage(tstring strMessage,tm *time,bool bIRC = false);
+ // Adds an incoming message to the log
+ void AddIncomingMessage(tstring strMessage,tm *time,bool bIRC = false);
+
+ // maximizes the content object
+ void Maximize(DWORD dwTimer=INFINITE);
+ // minimizes the content object
+ void Minimize();
+ // returns wether the content is maximized
+ bool IsMaximized();
+
+ // activates the input mode
+ void ActivateMessageMode();
+ // deactivates the input mode
+ void DeactivateMessageMode();
+ // sends the message
+ void SendCurrentMessage();
+ // invalidates the message mode
+ void InvalidateMessageMode(tstring strError);
+
+ // update's the screens objects ( sizes, fonts etc)
+ void UpdateObjects();
+ // update's the screens title labels
+ void UpdateLabels();
+
+ bool m_bHideLabels,m_bHideTitle;
+ bool m_bMaximizedTimer;
+
+ bool m_bContactTyping;
+ bool m_bTyping;
+
+ enum { REPLY_STATE_NONE,REPLY_STATE_INPUT,REPLY_STATE_SENDING,REPLY_STATE_FAILED} m_eReplyState;
+ DWORD m_dwCloseTimer;
+ bool m_bCloseTimer;
+ DWORD m_dwMaximizedTimer;
+ DWORD m_dwMaximizedDuration;
+
+ HANDLE m_hContact;
+ HANDLE m_hMessage;
+
+ int m_iStatus;
+
+ CLCDLabel m_UserProto;
+ CLCDLabel m_UserName;
+ CLCDLabel m_UserStatus;
+ CLCDLabel m_InfoText;
+
+ CLCDInput m_Input;
+ CLCDTextLog m_TextLog;
+ CLCDBar m_Scrollbar;
+
+ tstring m_strProto;
+ bool m_bIRCProtocol;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CConfig.cpp b/plugins/MirandaG15/src/CConfig.cpp
new file mode 100644
index 0000000000..76cfc68444
--- /dev/null
+++ b/plugins/MirandaG15/src/CConfig.cpp
@@ -0,0 +1,970 @@
+#include "StdAfx.h"
+#include "Miranda.h"
+#include "CConfig.h"
+
+#include "CAppletManager.h"
+
+#define FONTF_BOLD 1
+#define FONTF_ITALIC 2
+
+HANDLE CConfig::m_hOptionsInitHook = NULL;
+bool CConfig::m_bInitializingDialog = false;
+bool CConfig::m_abBoolSettings[BOOL_SETTINGS];
+int CConfig::m_aiIntSettings[INT_SETTINGS];
+LOGFONT CConfig::m_logfont[FONT_SETTINGS];
+LOGFONT CConfig::m_templogfont[FONT_SETTINGS];
+HANDLE CConfig::m_hSampleFont[FONT_SETTINGS];
+TEXTMETRIC CConfig::m_tmFontInfo[FONT_SETTINGS];
+vector<CProtoFilter*> CConfig::m_ProtoList;
+HWND CConfig::hDeviceBox = NULL;
+
+void CConfig::Initialize()
+{
+ CConfig::LoadSettings();
+ m_hOptionsInitHook = HookEvent(ME_OPT_INITIALISE, CConfig::InitOptionsDialog);
+
+}
+
+void CConfig::Shutdown()
+{
+ if(m_hSampleFont)
+ DeleteObject(m_hSampleFont);
+ UnhookEvent(m_hOptionsInitHook);
+}
+
+void CConfig::LoadSettings()
+{
+ m_abBoolSettings[SKIP_DRIVER_ERROR] = db_get_dw(NULL, "MirandaG15", "SkipDriverError",0);
+
+ m_abBoolSettings[SCREENSAVER_LOCK] = db_get_dw(NULL, "MirandaG15", "ScreensaverLock",1);
+ m_abBoolSettings[NOTIFY_SHOWPROTO] = db_get_dw(NULL, "MirandaG15", "NotifyShowProto",0);
+ m_abBoolSettings[NOTIFY_NICKCUTOFF] = db_get_dw(NULL, "MirandaG15", "NotifyNickCutoff",0);
+ m_abBoolSettings[NOTIFY_CHANNELCUTOFF] = db_get_dw(NULL, "MirandaG15", "NotifyChannelCutoff",0);
+
+ m_abBoolSettings[TRANSITIONS] = db_get_dw(NULL, "MirandaG15", "Transitions",0);
+ m_abBoolSettings[TIMESTAMP_SECONDS] = db_get_dw(NULL, "MirandaG15", "TimestampSeconds",0);
+ m_abBoolSettings[SESSION_TIMESTAMPS] = db_get_dw(NULL, "MirandaG15", "SessionTimestamps",0);
+ m_abBoolSettings[NOTIFY_TIMESTAMPS] = db_get_dw(NULL, "MirandaG15", "NotifyTimestamps",0);
+
+ m_abBoolSettings[CONTROL_BACKLIGHTS] = db_get_dw(NULL, "MirandaG15", "ControlBacklights",0);
+ m_abBoolSettings[HOOK_VOLUMEWHEEL] = db_get_dw(NULL, "MirandaG15", "HookVolumeWheel",0);
+
+ m_abBoolSettings[CLIST_SELECTION] = db_get_dw(NULL, "MirandaG15", "CListSelection",1);
+ m_abBoolSettings[CLIST_COLUMNS] = db_get_dw(NULL, "MirandaG15", "CListColumns",0);
+ m_abBoolSettings[CLIST_HIDEOFFLINE] = db_get_dw(NULL, "MirandaG15", "CListHideOffline",1);
+ m_abBoolSettings[CLIST_USEIGNORE] = db_get_dw(NULL, "MirandaG15", "CListUseIgnore",1);
+ m_abBoolSettings[CLIST_USEGROUPS] = db_get_dw(NULL, "MirandaG15", "CListUseGroups",1);
+ m_abBoolSettings[CLIST_SHOWPROTO] = db_get_dw(NULL, "MirandaG15", "CListShowProto",1);
+ m_abBoolSettings[CLIST_DRAWLINES] = db_get_dw(NULL, "MirandaG15", "CListDrawLines",1);
+ m_abBoolSettings[CLIST_COUNTERS] = db_get_dw(NULL, "MirandaG15", "CListCounters",1);
+ m_abBoolSettings[CLIST_POSITION] = db_get_dw(NULL, "MirandaG15", "CListPosition",0);
+
+ m_abBoolSettings[NOTIFY_IRC_MESSAGES] = db_get_dw(NULL, "MirandaG15", "NotifyIRCMessages", 1);
+ m_abBoolSettings[NOTIFY_IRC_USERS] = db_get_dw(NULL, "MirandaG15", "NotifyIRCUsers", 0);
+ m_abBoolSettings[NOTIFY_IRC_EMOTES] = db_get_dw(NULL, "MirandaG15", "NotifyIRCEmotes", 0);
+ m_abBoolSettings[NOTIFY_IRC_NOTICES] = db_get_dw(NULL, "MirandaG15", "NotifyIRCNotices", 1);
+ m_abBoolSettings[NOTIFY_IRC_CHANNEL] = db_get_dw(NULL, "MirandaG15", "NotifyIRCChannel", 0);
+ m_abBoolSettings[NOTIFY_IRC_STATUS] = db_get_dw(NULL, "MirandaG15", "NotifyIRCStatus", 0);
+
+ m_abBoolSettings[NOTIFY_PROTO_STATUS] = db_get_dw(NULL, "MirandaG15", "NotifyProtoStatus", 0);
+ m_abBoolSettings[NOTIFY_PROTO_SIGNON] = db_get_dw(NULL, "MirandaG15", "NotifyProtoSignOn", 1);
+ m_abBoolSettings[NOTIFY_PROTO_SIGNOFF] =db_get_dw(NULL, "MirandaG15", "NotifyProtoSignOff", 1);
+ m_abBoolSettings[NOTIFY_MESSAGES] = db_get_dw(NULL, "MirandaG15", "NotifyMessages", 1);
+ m_abBoolSettings[NOTIFY_SIGNON] = db_get_dw(NULL, "MirandaG15", "NotifySignOn", 1);
+ m_abBoolSettings[NOTIFY_SIGNOFF] = db_get_dw(NULL, "MirandaG15", "NotifySignOff", 1);
+ m_abBoolSettings[NOTIFY_STATUS] = db_get_dw(NULL, "MirandaG15", "NotifyStatus", 0);
+ m_abBoolSettings[NOTIFY_SKIP_MESSAGES] =db_get_dw(NULL, "MirandaG15", "NotifySkipMessages", 1);
+ m_abBoolSettings[NOTIFY_SKIP_SIGNON] = db_get_dw(NULL, "MirandaG15", "NotifySkipSignOn", 0);
+ m_abBoolSettings[NOTIFY_SKIP_SIGNOFF] = db_get_dw(NULL, "MirandaG15", "NotifySkipSignOff", 0);
+ m_abBoolSettings[NOTIFY_SKIP_STATUS] = db_get_dw(NULL, "MirandaG15", "NotifySkipStatus", 1);
+ m_abBoolSettings[NOTIFY_NO_SKIP_REPLY] = db_get_dw(NULL, "MirandaG15", "NotifyNoSkipReply",1);
+ m_abBoolSettings[NOTIFY_URL] = db_get_dw(NULL, "MirandaG15", "NotifyURL", 1);
+ m_abBoolSettings[NOTIFY_FILE] = db_get_dw(NULL, "MirandaG15", "NotifyFile", 1);
+ m_abBoolSettings[NOTIFY_CONTACTS] = db_get_dw(NULL, "MirandaG15", "NotifyContacts", 1);
+
+ m_abBoolSettings[SESSION_SCROLL_MAXIMIZED] = db_get_dw(NULL, "MirandaG15", "SessionScrollMaximized", 1);
+ m_abBoolSettings[SESSION_REPLY_MAXIMIZED] = db_get_dw(NULL, "MirandaG15", "SessionReplyMaximized", 1);
+ m_abBoolSettings[SESSION_LOADDB] = db_get_dw(NULL, "MirandaG15", "SessionLoadDB", 0);
+ m_abBoolSettings[SESSION_MARKREAD] = db_get_dw(NULL, "MirandaG15", "SessionMarkRead", 1);
+ m_abBoolSettings[SESSION_SENDRETURN] = db_get_dw(NULL, "MirandaG15", "SessionSendReturn",0);
+ m_abBoolSettings[SESSION_SHOWTYPING] = db_get_dw(NULL, "MirandaG15", "SessionShowTyping",1);
+ m_abBoolSettings[SESSION_SENDTYPING] = db_get_dw(NULL, "MirandaG15", "SessionSendTyping",1);
+ m_abBoolSettings[SESSION_SYMBOLS] = db_get_dw(NULL, "MirandaG15", "SessionSymbols",0);
+ m_abBoolSettings[SESSION_CLOSE] = db_get_dw(NULL, "MirandaG15", "SessionClose",1);
+
+ m_abBoolSettings[SHOW_LABELS] = db_get_dw(NULL, "MirandaG15", "ShowLabels", 1);
+ m_abBoolSettings[MAXIMIZED_TITLE] = db_get_dw(NULL, "MirandaG15", "MaximizedTitle", 0);
+ m_abBoolSettings[MAXIMIZED_LABELS] = db_get_dw(NULL, "MirandaG15", "MaximizedLabels", 1);
+
+ m_aiIntSettings[NOTIFY_CHANNELCUTOFF_OFFSET] = db_get_dw(NULL, "MirandaG15", "NotifyChannelCutoffOffset", 10);
+ m_aiIntSettings[NOTIFY_NICKCUTOFF_OFFSET] = db_get_dw(NULL, "MirandaG15", "NotifyNickCutoffOffset", 10);
+ m_aiIntSettings[NOTIFY_DURATION] = db_get_dw(NULL, "MirandaG15", "NotifyDuration", 4);
+ m_aiIntSettings[NOTIFY_LOGSIZE] = db_get_dw(NULL, "MirandaG15", "NotifyLogSize", 10);
+ m_aiIntSettings[SESSION_LOGSIZE] = db_get_dw(NULL, "MirandaG15", "SessionLogSize", 10);
+ m_aiIntSettings[SESSION_AUTOSCROLL] = db_get_dw(NULL, "MirandaG15", "SessionAutoScroll", SESSION_AUTOSCROLL_FIRST);
+ m_aiIntSettings[SESSION_CLOSETIMER] = db_get_dw(NULL, "MirandaG15", "SessionCloseTimer", 15);
+ m_aiIntSettings[NOTIFY_TITLE] = db_get_dw(NULL, "MirandaG15", "NotifyTitle", NOTIFY_TITLE_NAME);
+ m_aiIntSettings[CLIST_GA] = db_get_dw(NULL, "MirandaG15", "CListGA",CLIST_GA_NONE);
+ m_aiIntSettings[DEVICE] = db_get_dw(NULL, "MirandaG15", "Device",0);
+
+ for(int i=0;i<FONT_SETTINGS;i++)
+ LoadFontSettings(i);
+
+ // Load protocol specific settings
+ int iCount;
+ int iProtoCount = 0;
+ PROTOACCOUNT **ppAccounts;
+ CProtoFilter *pProtoFilter;
+ tstring strSetting;
+
+ CallService(MS_PROTO_ENUMACCOUNTS,(WPARAM)&iCount,(LPARAM)&ppAccounts);
+ for(int i=0;i<iCount;i++)
+ {
+ /*if(ppProtocolDescriptor[i]->type != PROTOTYPE_PROTOCOL)
+ continue;*/
+ if (ppAccounts[i]->bIsEnabled == 0)
+ continue;
+
+ iProtoCount++;
+ pProtoFilter = new CProtoFilter();
+ pProtoFilter->strName = toTstring(ppAccounts[i]->szModuleName);
+
+ strSetting = _T("ProtoFilter_") + pProtoFilter->strName;
+ pProtoFilter->bNotificationFilter = db_get_dw(NULL,"MirandaG15",toNarrowString(strSetting).c_str(),1);
+ strSetting = _T("ProtoCListFilter_") + pProtoFilter->strName;
+ pProtoFilter->bContactlistFilter = db_get_dw(NULL,"MirandaG15",toNarrowString(strSetting).c_str(),1);
+ m_ProtoList.push_back(pProtoFilter);
+ }
+}
+
+void CConfig::SaveSettings()
+{
+ db_set_dw(NULL, "MirandaG15", "SkipDriverError", m_abBoolSettings[SKIP_DRIVER_ERROR]);
+
+ db_set_dw(NULL, "MirandaG15", "ScreensaverLock", m_abBoolSettings[SCREENSAVER_LOCK]);
+ db_set_dw(NULL, "MirandaG15", "NotifyShowProto", m_abBoolSettings[NOTIFY_SHOWPROTO]);
+ db_set_dw(NULL, "MirandaG15", "NotifyChannelCutoff", m_abBoolSettings[NOTIFY_CHANNELCUTOFF]);
+ db_set_dw(NULL, "MirandaG15", "NotifyNickCutoff", m_abBoolSettings[NOTIFY_NICKCUTOFF]);
+ db_set_dw(NULL, "MirandaG15", "Transitions", m_abBoolSettings[TRANSITIONS]);
+ db_set_dw(NULL, "MirandaG15", "TimestampSeconds", m_abBoolSettings[TIMESTAMP_SECONDS]);
+ db_set_dw(NULL, "MirandaG15", "SessionTimestamps", m_abBoolSettings[SESSION_TIMESTAMPS]);
+ db_set_dw(NULL, "MirandaG15", "NotifyTimestamps", m_abBoolSettings[NOTIFY_TIMESTAMPS]);
+
+ db_set_dw(NULL, "MirandaG15", "ControlBacklights", m_abBoolSettings[CONTROL_BACKLIGHTS]);
+ db_set_dw(NULL, "MirandaG15", "HookVolumeWheel", m_abBoolSettings[HOOK_VOLUMEWHEEL]);
+
+ db_set_dw(NULL, "MirandaG15", "CListSelection", m_abBoolSettings[CLIST_SELECTION]);
+ db_set_dw(NULL, "MirandaG15", "CListColumns", m_abBoolSettings[CLIST_COLUMNS]);
+ db_set_dw(NULL, "MirandaG15", "CListHideOffline", m_abBoolSettings[CLIST_HIDEOFFLINE]);
+ db_set_dw(NULL, "MirandaG15", "CListUseIgnore", m_abBoolSettings[CLIST_USEIGNORE]);
+ db_set_dw(NULL, "MirandaG15", "CListUseGroups", m_abBoolSettings[CLIST_USEGROUPS]);
+ db_set_dw(NULL, "MirandaG15", "CListShowProto", m_abBoolSettings[CLIST_SHOWPROTO]);
+ db_set_dw(NULL, "MirandaG15", "CListDrawLines", m_abBoolSettings[CLIST_DRAWLINES]);
+ db_set_dw(NULL, "MirandaG15", "CListCounters", m_abBoolSettings[CLIST_COUNTERS]);
+ db_set_dw(NULL, "MirandaG15", "CListPosition", m_abBoolSettings[CLIST_POSITION]);
+
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCMessages", m_abBoolSettings[NOTIFY_IRC_MESSAGES]);
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCUsers", m_abBoolSettings[NOTIFY_IRC_USERS]);
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCEmotes", m_abBoolSettings[NOTIFY_IRC_EMOTES]);
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCNotices", m_abBoolSettings[NOTIFY_IRC_NOTICES]);
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCChannel", m_abBoolSettings[NOTIFY_IRC_CHANNEL]);
+ db_set_dw(NULL, "MirandaG15", "NotifyIRCStatus", m_abBoolSettings[NOTIFY_IRC_STATUS]);
+
+ db_set_dw(NULL, "MirandaG15", "NotifyProtoStatus", m_abBoolSettings[NOTIFY_PROTO_STATUS]);
+ db_set_dw(NULL, "MirandaG15", "NotifyProtoSignOn", m_abBoolSettings[NOTIFY_PROTO_SIGNON]);
+ db_set_dw(NULL, "MirandaG15", "NotifyProtoSignOff",m_abBoolSettings[NOTIFY_PROTO_SIGNOFF]);
+ db_set_dw(NULL, "MirandaG15", "NotifyMessages", m_abBoolSettings[NOTIFY_MESSAGES]);
+ db_set_dw(NULL, "MirandaG15", "NotifySignOn", m_abBoolSettings[NOTIFY_SIGNON]);
+ db_set_dw(NULL, "MirandaG15", "NotifySignOff", m_abBoolSettings[NOTIFY_SIGNOFF]);
+ db_set_dw(NULL, "MirandaG15", "NotifyStatus", m_abBoolSettings[NOTIFY_STATUS]);
+ db_set_dw(NULL, "MirandaG15", "NotifySkipMessages", m_abBoolSettings[NOTIFY_SKIP_MESSAGES]);
+ db_set_dw(NULL, "MirandaG15", "NotifySkipSignOn", m_abBoolSettings[NOTIFY_SKIP_SIGNON]);
+ db_set_dw(NULL, "MirandaG15", "NotifySkipSignOff", m_abBoolSettings[NOTIFY_SKIP_SIGNOFF]);
+ db_set_dw(NULL, "MirandaG15", "NotifySkipStatus", m_abBoolSettings[NOTIFY_SKIP_STATUS]);
+ db_set_dw(NULL, "MirandaG15", "NotifyNoSkipReply", m_abBoolSettings[NOTIFY_NO_SKIP_REPLY]);
+ db_set_dw(NULL, "MirandaG15", "NotifyURL", m_abBoolSettings[NOTIFY_URL]);
+ db_set_dw(NULL, "MirandaG15", "NotifyFile", m_abBoolSettings[NOTIFY_FILE]);
+ db_set_dw(NULL, "MirandaG15", "NotifyContacts", m_abBoolSettings[NOTIFY_CONTACTS]);
+
+ db_set_dw(NULL, "MirandaG15", "SessionScrollMaximized",m_abBoolSettings[SESSION_SCROLL_MAXIMIZED]);
+ db_set_dw(NULL, "MirandaG15", "SessionReplyMaximized",m_abBoolSettings[SESSION_REPLY_MAXIMIZED]);
+ db_set_dw(NULL, "MirandaG15", "SessionShowTyping", m_abBoolSettings[SESSION_SHOWTYPING]);
+ db_set_dw(NULL, "MirandaG15", "SessionSendTyping", m_abBoolSettings[SESSION_SENDTYPING]);
+ db_set_dw(NULL, "MirandaG15", "SessionLoadDB", m_abBoolSettings[SESSION_LOADDB]);
+ db_set_dw(NULL, "MirandaG15", "SessionSendReturn", m_abBoolSettings[SESSION_SENDRETURN]);
+ db_set_dw(NULL, "MirandaG15", "SessionMarkRead", m_abBoolSettings[SESSION_MARKREAD]);
+ db_set_dw(NULL, "MirandaG15", "SessionSymbols", m_abBoolSettings[SESSION_SYMBOLS]);
+ db_set_dw(NULL, "MirandaG15", "SessionClose", m_abBoolSettings[SESSION_CLOSE]);
+
+ db_set_dw(NULL, "MirandaG15", "ShowLabels", m_abBoolSettings[SHOW_LABELS]);
+ db_set_dw(NULL, "MirandaG15", "MaximizedTitle", m_abBoolSettings[MAXIMIZED_TITLE]);
+ db_set_dw(NULL, "MirandaG15", "MaximizedLabels", m_abBoolSettings[MAXIMIZED_LABELS]);
+
+ db_set_dw(NULL, "MirandaG15", "NotifyChannelCutoffOffset", m_aiIntSettings[NOTIFY_CHANNELCUTOFF_OFFSET]);
+ db_set_dw(NULL, "MirandaG15", "NotifyNickCutoffOffset", m_aiIntSettings[NOTIFY_NICKCUTOFF_OFFSET]);
+ db_set_dw(NULL, "MirandaG15", "NotifyDuration", m_aiIntSettings[NOTIFY_DURATION]);
+ db_set_dw(NULL, "MirandaG15", "NotifyLogSize", m_aiIntSettings[NOTIFY_LOGSIZE]);
+ db_set_dw(NULL, "MirandaG15", "SessionLogSize", m_aiIntSettings[SESSION_LOGSIZE]);
+ db_set_dw(NULL, "MirandaG15", "NotifyTitle", m_aiIntSettings[NOTIFY_TITLE]);
+ db_set_dw(NULL, "MirandaG15", "SessionAutoScroll", m_aiIntSettings[SESSION_AUTOSCROLL]);
+ db_set_dw(NULL, "MirandaG15", "SessionCloseTimer", m_aiIntSettings[SESSION_CLOSETIMER]);
+ db_set_dw(NULL, "MirandaG15", "CListGA", m_aiIntSettings[CLIST_GA]);
+ db_set_dw(NULL, "MirandaG15", "Device", m_aiIntSettings[DEVICE]);
+
+ // Save font settings
+ for(int i=0;i<FONT_SETTINGS;i++)
+ SaveFontSettings(i);
+
+ // save protocol specific settings
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ tstring strSetting = _T("");
+ while(iter != m_ProtoList.end())
+ {
+ strSetting = _T("ProtoFilter_") + (*iter)->strName;
+ db_set_dw(NULL, "MirandaG15", toNarrowString(strSetting).c_str(),(*iter)->bNotificationFilter);
+ strSetting = _T("ProtoCListFilter_") + (*iter)->strName;
+ db_set_dw(NULL, "MirandaG15", toNarrowString(strSetting).c_str(),(*iter)->bContactlistFilter);
+ iter++;
+ }
+
+ // Notify OutputManager of configuration change
+ if(CAppletManager::GetInstance()->IsInitialized())
+ CAppletManager::GetInstance()->OnConfigChanged();
+}
+
+void CConfig::UpdateFontSettings(int iFont)
+{
+ if(m_hSampleFont[iFont])
+ DeleteObject(m_hSampleFont[iFont]);
+ m_hSampleFont[iFont] = CreateFontIndirect(&m_logfont[iFont]);
+ HDC hDC = CreateCompatibleDC(NULL);
+ SelectObject(hDC, m_hSampleFont[iFont]);
+ GetTextMetrics(hDC,&m_tmFontInfo[iFont]);
+ DeleteObject(hDC);
+}
+
+void CConfig::OnConnectionChanged() {
+ FillDeviceBox(CConfig::hDeviceBox);
+}
+
+int CConfig::InitOptionsDialog(WPARAM wParam, LPARAM lParam)
+{
+ OPTIONSDIALOGPAGE odp;
+ ZeroMemory(&odp, sizeof(odp));
+ odp.cbSize = sizeof(odp);
+ odp.position = 847000000;
+ odp.hInstance = hInstance;
+ odp.pszGroup = "MirandaG15";
+ odp.flags = ODPF_BOLDGROUPS;
+
+ // ---------------------
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_FONTS);
+ odp.pszTitle = "Appearance";
+ odp.pszGroup = "MirandaG15";
+ odp.pfnDlgProc = CConfig::AppearanceDlgProc;
+
+ Options_AddPage(wParam, &odp);
+
+ // ---------------------
+
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_NOTIFICATIONS);
+ odp.pszTitle = "Notifications";
+ odp.pfnDlgProc = CConfig::NotificationsDlgProc;
+
+ Options_AddPage(wParam, &odp);
+
+ // ---------------------
+
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_CHAT);
+ odp.pszTitle = "Chatsessions";
+ odp.pfnDlgProc = CConfig::ChatDlgProc;
+
+ Options_AddPage(wParam, &odp);
+
+ // ---------------------
+
+ odp.pszTemplate = MAKEINTRESOURCEA(IDD_CLIST);
+ odp.pszTitle = "Contactlist";
+ odp.pfnDlgProc = CConfig::ContactlistDlgProc;
+
+ Options_AddPage(wParam, &odp);
+ return 0;
+}
+
+void CConfig::SaveFontSettings(int iFont)
+{
+ if(iFont > FONT_SETTINGS -1 || iFont < 0)
+ return;
+
+ char szSetting[128];
+
+ // Height
+ sprintf(szSetting,"Font%dHeight",iFont);
+ db_set_b(NULL, "MirandaG15", szSetting, m_logfont[iFont].lfHeight);
+ // Style
+ int style = 0;
+ if(m_logfont[iFont].lfWeight == FW_BOLD)
+ style |= FONTF_BOLD;
+ if(m_logfont[iFont].lfItalic)
+ style |= FONTF_ITALIC;
+ sprintf(szSetting,"Font%dStyle",iFont);
+ db_set_b(NULL, "MirandaG15", szSetting, style);
+ // Charset
+ sprintf(szSetting,"Font%dCharset",iFont);
+ db_set_b(NULL, "MirandaG15", szSetting, m_logfont[iFont].lfCharSet);
+ // Name
+ sprintf(szSetting,"Font%dName",iFont);
+ db_set_ts(NULL, "MirandaG15", szSetting, m_logfont[iFont].lfFaceName);
+
+ UpdateFontSettings(iFont);
+}
+
+void CConfig::LoadFontSettings(int iFont)
+{
+ if(iFont > FONT_SETTINGS -1 || iFont < 0)
+ return;
+
+ char szSetting[128];
+
+ // Fixed Values
+ m_logfont[iFont].lfOutPrecision = OUT_DEFAULT_PRECIS;
+ m_logfont[iFont].lfClipPrecision = CLIP_DEFAULT_PRECIS;
+ m_logfont[iFont].lfQuality = DEFAULT_QUALITY;
+ m_logfont[iFont].lfPitchAndFamily = DEFAULT_PITCH | FF_DONTCARE;
+ // Height
+ sprintf(szSetting,"Font%dHeight",iFont);
+ m_logfont[iFont].lfHeight = (char) db_get_b(NULL, "MirandaG15", szSetting, -MulDiv(6, 96, 72));
+ // Style
+ sprintf(szSetting,"Font%dStyle",iFont);
+ int style = db_get_b(NULL, "MirandaG15", szSetting, 0);
+ m_logfont[iFont].lfWeight = style & FONTF_BOLD ? FW_BOLD : FW_NORMAL;
+ m_logfont[iFont].lfItalic = style & FONTF_ITALIC ? 1 : 0;
+ // Charset
+ sprintf(szSetting,"Font%dCharset",iFont);
+ m_logfont[iFont].lfCharSet = db_get_b(NULL, "MirandaG15", szSetting, DEFAULT_CHARSET);
+ // Name
+ sprintf(szSetting,"Font%dName",iFont);
+ DBVARIANT dbv;
+ if (db_get_ts(NULL, "MirandaG15", szSetting, &dbv))
+ lstrcpy(m_logfont[iFont].lfFaceName,_T("Small Fonts"));
+ else {
+ lstrcpy(m_logfont[iFont].lfFaceName, dbv.ptszVal);
+ db_free(&dbv);
+ }
+
+ UpdateFontSettings(iFont);
+}
+
+LOGFONT &CConfig::GetFont(int iFont)
+{
+ return m_logfont[iFont];
+}
+
+int CConfig::GetFontHeight(int iFont)
+{
+ return m_tmFontInfo[iFont].tmHeight;
+}
+
+int CConfig::GetSampleField(int iFont)
+{
+ switch(iFont)
+ {
+ case 0: return IDC_SAMPLE1;
+ case 1: return IDC_SAMPLE2;
+ case 2: return IDC_SAMPLE3;
+ case 3: return IDC_SAMPLE4;
+ case 4: return IDC_SAMPLE5;
+ };
+ return 0;
+}
+
+INT_PTR CALLBACK CConfig::AppearanceDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+ char buf[128];
+
+ switch (uMsg)
+ {
+ case WM_INITDIALOG:
+ {
+ m_bInitializingDialog = true;
+
+ // Translate the dialog
+ TranslateDialogDefault(hwndDlg);
+
+ CheckDlgButton(hwndDlg, IDC_SKIP_DRIVER_ERROR, m_abBoolSettings[SKIP_DRIVER_ERROR] ? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_SCREENSAVER_LOCK, m_abBoolSettings[SCREENSAVER_LOCK] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_TRANSITIONS, m_abBoolSettings[TRANSITIONS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CONTROL_BACKLIGHTS, m_abBoolSettings[CONTROL_BACKLIGHTS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SHOW_LABELS, m_abBoolSettings[SHOW_LABELS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_HOOK_VOLUMEWHEEL, m_abBoolSettings[HOOK_VOLUMEWHEEL] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_TIMESTAMP_SECONDS, m_abBoolSettings[TIMESTAMP_SECONDS] ? BST_CHECKED : BST_UNCHECKED);
+
+ for(int i=0;i<FONT_SETTINGS;i++)
+ {
+ m_templogfont[i] = m_logfont[i];
+ SendDlgItemMessage(hwndDlg,CConfig::GetSampleField(i),WM_SETFONT,(WPARAM)m_hSampleFont[i],(LPARAM)true);
+ }
+
+ // fill device box
+ CConfig::hDeviceBox = GetDlgItem(hwndDlg,IDC_DEVICE);
+ FillDeviceBox(CConfig::hDeviceBox);
+
+ m_bInitializingDialog = false;
+ break;
+ }
+ case WM_NOTIFY:
+ {
+ switch (((LPNMHDR)lParam)->code)
+ {
+ case PSN_APPLY:
+ {
+ m_abBoolSettings[SKIP_DRIVER_ERROR] = IsDlgButtonChecked(hwndDlg,IDC_SKIP_DRIVER_ERROR) == BST_CHECKED ? true : false;
+
+ m_abBoolSettings[SCREENSAVER_LOCK] = IsDlgButtonChecked(hwndDlg,IDC_SCREENSAVER_LOCK) == BST_CHECKED ? true : false;
+ m_abBoolSettings[TRANSITIONS] = IsDlgButtonChecked(hwndDlg,IDC_TRANSITIONS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SHOW_LABELS] = IsDlgButtonChecked(hwndDlg,IDC_SHOW_LABELS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CONTROL_BACKLIGHTS] = IsDlgButtonChecked(hwndDlg,IDC_CONTROL_BACKLIGHTS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[HOOK_VOLUMEWHEEL] = IsDlgButtonChecked(hwndDlg,IDC_HOOK_VOLUMEWHEEL) == BST_CHECKED ? true : false;
+ m_abBoolSettings[TIMESTAMP_SECONDS] = IsDlgButtonChecked(hwndDlg,IDC_TIMESTAMP_SECONDS) == BST_CHECKED ? true : false;
+ m_aiIntSettings[DEVICE] = SendDlgItemMessage(hwndDlg,IDC_DEVICE,CB_GETCURSEL ,0,0);
+
+ for(int i=0;i<FONT_SETTINGS;i++)
+ m_logfont[i] = m_templogfont[i];
+
+ CConfig::SaveSettings();
+ SendMessage(hwndDlg, WM_INITDIALOG, 0, 0);
+ break;
+ }
+ }
+ break;
+ }
+ case WM_COMMAND:
+ {
+ if(LOWORD(wParam) == IDC_CREDITS)
+ {
+ CAppletManager::GetInstance()->ActivateCreditsScreen();
+ break;
+ }
+
+ int iFont = LOWORD(wParam);
+ switch(iFont)
+ {
+ case IDC_CHOOSEFONT1: iFont = 0; break;
+ case IDC_CHOOSEFONT2: iFont = 1; break;
+ case IDC_CHOOSEFONT3: iFont = 2; break;
+ case IDC_CHOOSEFONT4: iFont = 3; break;
+ case IDC_CHOOSEFONT5: iFont = 4; break;
+ default: iFont = -1;
+ };
+
+ if(iFont >= 0)
+ {
+ CHOOSEFONT cf = { 0 };
+ cf.lStructSize = sizeof(cf);
+ cf.hwndOwner = hwndDlg;
+ cf.lpLogFont = &m_templogfont[iFont];
+ cf.Flags = CF_FORCEFONTEXIST | CF_INITTOLOGFONTSTRUCT | CF_SCREENFONTS;
+ if (ChooseFont(&cf))
+ {
+ if(m_hSampleFont[iFont])
+ DeleteObject(m_hSampleFont[iFont]);
+ m_hSampleFont[iFont] = CreateFontIndirect(&m_templogfont[iFont]);
+ SendDlgItemMessage(hwndDlg,CConfig::GetSampleField(iFont),WM_SETFONT,(WPARAM)m_hSampleFont[iFont],(LPARAM)true);
+ TRACE(_T("Font selected!"));
+ }
+ }
+ if(LOWORD(wParam) == IDC_DEVICE && SendDlgItemMessage(hwndDlg,IDC_DEVICE,CB_GETCURSEL ,0,0) != m_aiIntSettings[DEVICE]) {
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+
+ // Activate the apply button
+ if (!m_bInitializingDialog && ((HIWORD(wParam) == EN_CHANGE) || (HIWORD(wParam) == BN_CLICKED))) {
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+ break;
+ }
+ }
+ return 0;
+}
+
+INT_PTR CALLBACK CConfig::ChatDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+ char buf[128];
+
+ switch (uMsg)
+ {
+ case WM_INITDIALOG:
+ {
+ m_bInitializingDialog = true;
+
+ // Translate the dialog
+ TranslateDialogDefault(hwndDlg);
+
+ CheckDlgButton(hwndDlg, IDC_MAXIMIZED_TITLE, m_abBoolSettings[MAXIMIZED_TITLE] ? BST_UNCHECKED : BST_CHECKED);
+ CheckDlgButton(hwndDlg, IDC_MAXIMIZED_LABELS, m_abBoolSettings[MAXIMIZED_LABELS] ? BST_UNCHECKED : BST_CHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_REPLY_MAXIMIZED, m_abBoolSettings[SESSION_REPLY_MAXIMIZED]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SCROLL_MAXIMIZED, m_abBoolSettings[SESSION_SCROLL_MAXIMIZED]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SHOWTYPING, m_abBoolSettings[SESSION_SHOWTYPING]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SENDTYPING, m_abBoolSettings[SESSION_SENDTYPING]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_LOADDB, m_abBoolSettings[SESSION_LOADDB]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_MARKREAD, m_abBoolSettings[SESSION_MARKREAD]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SYMBOLS, m_abBoolSettings[SESSION_SYMBOLS]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_TIMESTAMPS, m_abBoolSettings[SESSION_TIMESTAMPS]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_CLOSE, m_abBoolSettings[SESSION_CLOSE]? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_SESSION_SENDRETURN, m_abBoolSettings[SESSION_SENDRETURN]? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_SESSION_SCROLLNONE, m_aiIntSettings[SESSION_AUTOSCROLL] == SESSION_AUTOSCROLL_NONE? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SCROLLFIRST, m_aiIntSettings[SESSION_AUTOSCROLL] == SESSION_AUTOSCROLL_FIRST? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_SESSION_SCROLLLAST, m_aiIntSettings[SESSION_AUTOSCROLL] == SESSION_AUTOSCROLL_LAST? BST_CHECKED : BST_UNCHECKED);
+
+ itoa(m_aiIntSettings[SESSION_LOGSIZE], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_SESSION_LOGSIZE, buf);
+
+ itoa(m_aiIntSettings[SESSION_CLOSETIMER], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_SESSION_CLOSETIMER, buf);
+
+ m_bInitializingDialog = false;
+ break;
+ }
+ case WM_NOTIFY:
+ {
+ switch (((LPNMHDR)lParam)->code)
+ {
+ case PSN_APPLY:
+ {
+ m_abBoolSettings[SESSION_SCROLL_MAXIMIZED] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_SCROLL_MAXIMIZED) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_REPLY_MAXIMIZED] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_REPLY_MAXIMIZED) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_SHOWTYPING] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_SHOWTYPING) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_SENDTYPING] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_SENDTYPING) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_LOADDB] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_LOADDB) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_SENDRETURN] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_SENDRETURN) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_MARKREAD] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_MARKREAD) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_SYMBOLS] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_SYMBOLS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_TIMESTAMPS] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_TIMESTAMPS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[SESSION_CLOSE] = IsDlgButtonChecked(hwndDlg,IDC_SESSION_CLOSE) == BST_CHECKED ? true : false;
+
+ if(IsDlgButtonChecked(hwndDlg,IDC_SESSION_SCROLLNONE) == BST_CHECKED)
+ m_aiIntSettings[SESSION_AUTOSCROLL] = SESSION_AUTOSCROLL_NONE;
+ else if(IsDlgButtonChecked(hwndDlg,IDC_SESSION_SCROLLFIRST) == BST_CHECKED)
+ m_aiIntSettings[SESSION_AUTOSCROLL] = SESSION_AUTOSCROLL_FIRST;
+ else
+ m_aiIntSettings[SESSION_AUTOSCROLL] = SESSION_AUTOSCROLL_LAST;
+
+ m_abBoolSettings[MAXIMIZED_TITLE] = IsDlgButtonChecked(hwndDlg,IDC_MAXIMIZED_TITLE) == BST_UNCHECKED ? true : false;
+ m_abBoolSettings[MAXIMIZED_LABELS] = IsDlgButtonChecked(hwndDlg,IDC_MAXIMIZED_LABELS) == BST_UNCHECKED ? true : false;
+
+ GetDlgItemTextA(hwndDlg,IDC_SESSION_LOGSIZE,buf,256);
+ m_aiIntSettings[SESSION_LOGSIZE] = atoi(buf) > 0 ? atoi(buf):1;
+
+ GetDlgItemTextA(hwndDlg,IDC_SESSION_CLOSETIMER,buf,256);
+ m_aiIntSettings[SESSION_CLOSETIMER] = atoi(buf) >= 0 ? atoi(buf):1;
+
+ CConfig::SaveSettings();
+ SendMessage(hwndDlg, WM_INITDIALOG, 0, 0);
+ break;
+ }
+ }
+ break;
+ }
+ case WM_COMMAND:
+ {
+ // Activate the apply button
+ if (!m_bInitializingDialog && ((HIWORD(wParam) == EN_CHANGE) || (HIWORD(wParam) == BN_CLICKED)))
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+
+ break;
+ }
+ }
+ return 0;
+}
+
+INT_PTR CALLBACK CConfig::NotificationsDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+ char buf[128];
+
+ switch (uMsg)
+ {
+ case WM_INITDIALOG:
+ {
+ m_bInitializingDialog = true;
+
+ // Translate the dialog
+ TranslateDialogDefault(hwndDlg);
+
+ // Initialize the protocol filter list
+ SetWindowLong(GetDlgItem(hwndDlg,IDC_PROTOCOLS),GWL_STYLE,GetWindowLong(GetDlgItem(hwndDlg,IDC_PROTOCOLS),GWL_STYLE)|TVS_NOHSCROLL);
+ int iRes = 0;
+
+ HIMAGELIST himlCheckBoxes;
+ himlCheckBoxes=ImageList_Create(GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON),ILC_COLOR32|ILC_MASK,2,2);
+ iRes = ImageList_AddIcon(himlCheckBoxes,LoadIcon(hInstance,MAKEINTRESOURCE(IDI_NOTICK)));
+ iRes = ImageList_AddIcon(himlCheckBoxes,LoadIcon(hInstance,MAKEINTRESOURCE(IDI_TICK)));
+ TreeView_SetImageList(GetDlgItem(hwndDlg,IDC_PROTOCOLS),himlCheckBoxes,TVSIL_NORMAL);
+
+ FillTree(GetDlgItem(hwndDlg,IDC_PROTOCOLS));
+
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_TIMESTAMPS, m_abBoolSettings[NOTIFY_TIMESTAMPS] ? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SHOWPROTO, m_abBoolSettings[NOTIFY_SHOWPROTO] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_CHANNELCUTOFF, m_abBoolSettings[NOTIFY_CHANNELCUTOFF] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_NICKCUTOFF, m_abBoolSettings[NOTIFY_NICKCUTOFF] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_MESSAGES, m_abBoolSettings[NOTIFY_IRC_MESSAGES] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_USERS, m_abBoolSettings[NOTIFY_IRC_USERS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_EMOTES, m_abBoolSettings[NOTIFY_IRC_EMOTES] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_NOTICES, m_abBoolSettings[NOTIFY_IRC_NOTICES] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_CHANNEL, m_abBoolSettings[NOTIFY_IRC_CHANNEL] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_IRC_STATUS, m_abBoolSettings[NOTIFY_IRC_STATUS] ? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_PROTO_STATUS, m_abBoolSettings[NOTIFY_PROTO_STATUS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_PROTO_SIGNON, m_abBoolSettings[NOTIFY_PROTO_SIGNON] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_PROTO_SIGNOFF, m_abBoolSettings[NOTIFY_PROTO_SIGNOFF] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SIGNON, m_abBoolSettings[NOTIFY_SIGNON] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SIGNOFF, m_abBoolSettings[NOTIFY_SIGNOFF] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_STATUS, m_abBoolSettings[NOTIFY_STATUS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_MESSAGES, m_abBoolSettings[NOTIFY_MESSAGES] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_FILE, m_abBoolSettings[NOTIFY_FILE] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_CONTACTS, m_abBoolSettings[NOTIFY_CONTACTS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_URL, m_abBoolSettings[NOTIFY_URL] ? BST_CHECKED : BST_UNCHECKED);
+
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_NO_SKIP_REPLY, m_abBoolSettings[NOTIFY_NO_SKIP_REPLY] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SKIP_SIGNON, m_abBoolSettings[NOTIFY_SKIP_SIGNON] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SKIP_SIGNOFF, m_abBoolSettings[NOTIFY_SKIP_SIGNOFF] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SKIP_STATUS, m_abBoolSettings[NOTIFY_SKIP_STATUS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_SKIP_MESSAGES, m_abBoolSettings[NOTIFY_SKIP_MESSAGES] ? BST_CHECKED : BST_UNCHECKED);
+
+ itoa(m_aiIntSettings[NOTIFY_CHANNELCUTOFF_OFFSET], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_NOTIFY_CHANNELCUTOFF_OFFSET, buf);
+
+ itoa(m_aiIntSettings[NOTIFY_NICKCUTOFF_OFFSET], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_NOTIFY_NICKCUTOFF_OFFSET, buf);
+
+ itoa(m_aiIntSettings[NOTIFY_LOGSIZE], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_NOTIFY_LOGSIZE, buf);
+
+ itoa(m_aiIntSettings[NOTIFY_DURATION], buf, 10);
+ SetDlgItemTextA(hwndDlg, IDC_NOTIFY_DURATION, buf);
+
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_TITLEHIDE, m_aiIntSettings[NOTIFY_TITLE] == NOTIFY_TITLE_HIDE? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_TITLENAME, m_aiIntSettings[NOTIFY_TITLE] == NOTIFY_TITLE_NAME? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_NOTIFY_TITLEINFO, m_aiIntSettings[NOTIFY_TITLE] == NOTIFY_TITLE_INFO? BST_CHECKED : BST_UNCHECKED);
+
+ m_bInitializingDialog = false;
+ break;
+ }
+ case WM_NOTIFY:
+ {
+ if(((LPNMHDR)lParam)->idFrom == IDC_PROTOCOLS)
+ {
+ if(((LPNMHDR)lParam)->code != NM_CLICK)
+ return 0;
+
+ TVHITTESTINFO hti;
+ hti.pt.x=(short)LOWORD(GetMessagePos());
+ hti.pt.y=(short)HIWORD(GetMessagePos());
+ ScreenToClient(((LPNMHDR)lParam)->hwndFrom,&hti.pt);
+ if(TreeView_HitTest(((LPNMHDR)lParam)->hwndFrom,&hti))
+ if(hti.flags&TVHT_ONITEMICON) {
+ TVITEM tvi;
+ tvi.mask=TVIF_HANDLE|TVIF_IMAGE|TVIF_SELECTEDIMAGE;
+ tvi.hItem=hti.hItem;
+ TreeView_GetItem(((LPNMHDR)lParam)->hwndFrom,&tvi);
+ tvi.iImage=tvi.iSelectedImage=!tvi.iImage;
+ ((CProtoFilter *)tvi.lParam)->bTempNotificationFilter=tvi.iImage;
+ TreeView_SetItem(((LPNMHDR)lParam)->hwndFrom,&tvi);
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+
+ }
+ break;
+ }
+ switch (((LPNMHDR)lParam)->code)
+ {
+ case PSN_APPLY:
+ {
+ m_abBoolSettings[NOTIFY_TIMESTAMPS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_TIMESTAMPS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_CHANNELCUTOFF] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_CHANNELCUTOFF) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_NICKCUTOFF] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_NICKCUTOFF) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SHOWPROTO] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SHOWPROTO) == BST_CHECKED ? true : false;
+
+ m_abBoolSettings[NOTIFY_IRC_MESSAGES] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_MESSAGES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_IRC_USERS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_USERS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_IRC_EMOTES] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_EMOTES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_IRC_NOTICES] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_NOTICES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_IRC_CHANNEL] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_CHANNEL) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_IRC_STATUS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_IRC_STATUS) == BST_CHECKED ? true : false;
+
+ m_abBoolSettings[NOTIFY_PROTO_STATUS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_PROTO_STATUS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_PROTO_SIGNON] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_PROTO_SIGNON) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_PROTO_SIGNOFF] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_PROTO_SIGNOFF) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_MESSAGES] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_MESSAGES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SIGNON] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SIGNON) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SIGNOFF] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SIGNOFF) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_STATUS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_STATUS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_URL] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_URL) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_FILE] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_FILE) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_CONTACTS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_CONTACTS) == BST_CHECKED ? true : false;
+
+ m_abBoolSettings[NOTIFY_NO_SKIP_REPLY] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_NO_SKIP_REPLY) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SKIP_MESSAGES] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SKIP_MESSAGES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SKIP_SIGNON] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SKIP_SIGNON) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SKIP_SIGNOFF] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SKIP_SIGNOFF) == BST_CHECKED ? true : false;
+ m_abBoolSettings[NOTIFY_SKIP_STATUS] = IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_SKIP_STATUS) == BST_CHECKED ? true : false;
+
+ GetDlgItemTextA(hwndDlg,IDC_NOTIFY_CHANNELCUTOFF_OFFSET,buf,256);
+ m_aiIntSettings[NOTIFY_CHANNELCUTOFF_OFFSET] = atoi(buf) > 0 ? atoi(buf):1;
+
+ GetDlgItemTextA(hwndDlg,IDC_NOTIFY_NICKCUTOFF_OFFSET,buf,256);
+ m_aiIntSettings[NOTIFY_NICKCUTOFF_OFFSET] = atoi(buf) > 0 ? atoi(buf):1;
+
+ GetDlgItemTextA(hwndDlg,IDC_NOTIFY_DURATION,buf,256);
+ m_aiIntSettings[NOTIFY_DURATION] = atoi(buf) > 0 ? atoi(buf):1;
+
+ GetDlgItemTextA(hwndDlg,IDC_NOTIFY_LOGSIZE,buf,256);
+ m_aiIntSettings[NOTIFY_LOGSIZE] = atoi(buf) > 0 ? atoi(buf):1;
+
+ if(IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_TITLEHIDE) == BST_CHECKED)
+ m_aiIntSettings[NOTIFY_TITLE] = NOTIFY_TITLE_HIDE;
+ else if(IsDlgButtonChecked(hwndDlg,IDC_NOTIFY_TITLENAME) == BST_CHECKED)
+ m_aiIntSettings[NOTIFY_TITLE] = NOTIFY_TITLE_NAME;
+ else
+ m_aiIntSettings[NOTIFY_TITLE] = NOTIFY_TITLE_INFO;
+
+ // apply all contactlist protocol filters
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ while(iter != m_ProtoList.end())
+ {
+ (*iter)->bNotificationFilter = (*iter)->bTempNotificationFilter;
+ iter++;
+ }
+
+ CConfig::SaveSettings();
+ SendMessage(hwndDlg, WM_INITDIALOG, 0, 0);
+ break;
+ }
+ }
+ break;
+ }
+ case WM_COMMAND:
+ {
+ // Activate the apply button
+ if (!m_bInitializingDialog && ((HIWORD(wParam) == EN_CHANGE) || (HIWORD(wParam) == BN_CLICKED)))
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+
+ break;
+ }
+ }
+ return 0;
+}
+
+INT_PTR CALLBACK CConfig::ContactlistDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+ char buf[128];
+
+ switch (uMsg)
+ {
+ case WM_INITDIALOG:
+ {
+ m_bInitializingDialog = true;
+
+ // Translate the dialog
+ TranslateDialogDefault(hwndDlg);
+
+ // Initialize the protocol filter list
+ SetWindowLong(GetDlgItem(hwndDlg,IDC_CLIST_PROTOFILTER),GWL_STYLE,GetWindowLong(GetDlgItem(hwndDlg,IDC_CLIST_PROTOFILTER),GWL_STYLE)|TVS_NOHSCROLL);
+ int iRes = 0;
+
+ HIMAGELIST himlCheckBoxes;
+ himlCheckBoxes=ImageList_Create(GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON),ILC_COLOR32|ILC_MASK,2,2);
+ iRes = ImageList_AddIcon(himlCheckBoxes,LoadIcon(hInstance,MAKEINTRESOURCE(IDI_NOTICK)));
+ iRes = ImageList_AddIcon(himlCheckBoxes,LoadIcon(hInstance,MAKEINTRESOURCE(IDI_TICK)));
+ TreeView_SetImageList(GetDlgItem(hwndDlg,IDC_CLIST_PROTOFILTER),himlCheckBoxes,TVSIL_NORMAL);
+
+ FillTree(GetDlgItem(hwndDlg,IDC_CLIST_PROTOFILTER),true);
+
+ CheckDlgButton(hwndDlg, IDC_CLIST_SELECTION, m_abBoolSettings[CLIST_SELECTION] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_COLUMNS, m_abBoolSettings[CLIST_COLUMNS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_HIDEOFFLINE, m_abBoolSettings[CLIST_HIDEOFFLINE] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_USEIGNORE, m_abBoolSettings[CLIST_USEIGNORE] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_USEGROUPS, m_abBoolSettings[CLIST_USEGROUPS] ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_SHOWPROTO, m_abBoolSettings[CLIST_SHOWPROTO]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_DRAWLINES, m_abBoolSettings[CLIST_DRAWLINES]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_POSITION, m_abBoolSettings[CLIST_POSITION]? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hwndDlg, IDC_CLIST_COUNTERS, m_abBoolSettings[CLIST_COUNTERS]? BST_CHECKED : BST_UNCHECKED);
+
+ if(m_aiIntSettings[CLIST_GA] == CLIST_GA_NONE)
+ CheckDlgButton(hwndDlg, IDC_CLIST_GA_NONE, BST_CHECKED);
+ else if(m_aiIntSettings[CLIST_GA] == CLIST_GA_COLLAPSE)
+ CheckDlgButton(hwndDlg, IDC_CLIST_GA_COLLAPSE, BST_CHECKED);
+ else
+ CheckDlgButton(hwndDlg, IDC_CLIST_GA_EXPAND, BST_CHECKED);
+
+ m_bInitializingDialog = false;
+ break;
+ }
+ case WM_NOTIFY:
+ {
+ if(((LPNMHDR)lParam)->idFrom == IDC_CLIST_PROTOFILTER)
+ {
+ if(((LPNMHDR)lParam)->code != NM_CLICK)
+ return 0;
+
+ TVHITTESTINFO hti;
+ hti.pt.x=(short)LOWORD(GetMessagePos());
+ hti.pt.y=(short)HIWORD(GetMessagePos());
+ ScreenToClient(((LPNMHDR)lParam)->hwndFrom,&hti.pt);
+ if(TreeView_HitTest(((LPNMHDR)lParam)->hwndFrom,&hti))
+ if(hti.flags&TVHT_ONITEMICON) {
+ TVITEM tvi;
+ tvi.mask=TVIF_HANDLE|TVIF_IMAGE|TVIF_SELECTEDIMAGE;
+ tvi.hItem=hti.hItem;
+ TreeView_GetItem(((LPNMHDR)lParam)->hwndFrom,&tvi);
+ tvi.iImage=tvi.iSelectedImage=!tvi.iImage;
+ ((CProtoFilter *)tvi.lParam)->bTempContactlistFilter=tvi.iImage;
+ TreeView_SetItem(((LPNMHDR)lParam)->hwndFrom,&tvi);
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+ }
+ break;
+ }
+ switch (((LPNMHDR)lParam)->code)
+ {
+ case PSN_APPLY:
+ {
+ m_abBoolSettings[CLIST_SELECTION] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_SELECTION) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_COLUMNS] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_COLUMNS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_HIDEOFFLINE] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_HIDEOFFLINE) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_USEGROUPS] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_USEGROUPS) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_USEIGNORE] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_USEIGNORE) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_SHOWPROTO] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_SHOWPROTO) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_DRAWLINES] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_DRAWLINES) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_POSITION] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_POSITION) == BST_CHECKED ? true : false;
+ m_abBoolSettings[CLIST_COUNTERS] = IsDlgButtonChecked(hwndDlg,IDC_CLIST_COUNTERS) == BST_CHECKED ? true : false;
+
+ if(IsDlgButtonChecked(hwndDlg,IDC_CLIST_GA_NONE) == BST_CHECKED)
+ m_aiIntSettings[CLIST_GA] = CLIST_GA_NONE;
+ else if(IsDlgButtonChecked(hwndDlg,IDC_CLIST_GA_COLLAPSE) == BST_CHECKED)
+ m_aiIntSettings[CLIST_GA] = CLIST_GA_COLLAPSE;
+ else
+ m_aiIntSettings[CLIST_GA] = CLIST_GA_EXPAND;
+
+ // apply all contactlist protocol filters
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ while(iter != m_ProtoList.end())
+ {
+ (*iter)->bContactlistFilter = (*iter)->bTempContactlistFilter;
+ iter++;
+ }
+ CConfig::SaveSettings();
+ SendMessage(hwndDlg, WM_INITDIALOG, 0, 0);
+ break;
+ }
+ }
+ break;
+ }
+ case WM_COMMAND:
+ {
+ // Activate the apply button
+ if (!m_bInitializingDialog && ((HIWORD(wParam) == EN_CHANGE) || (HIWORD(wParam) == BN_CLICKED)))
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0);
+
+ break;
+ }
+ }
+ return 0;
+}
+
+
+bool CConfig::GetProtocolContactlistFilter(tstring strProtocol)
+{
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ while(iter != m_ProtoList.end())
+ {
+ if((*iter)->strName == strProtocol)
+ return (*iter)->bContactlistFilter;
+ iter++;
+ }
+ return false;
+}
+
+bool CConfig::GetProtocolNotificationFilter(tstring strProtocol)
+{
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ while(iter != m_ProtoList.end())
+ {
+ if((*iter)->strName == strProtocol)
+ return (*iter)->bNotificationFilter;
+ iter++;
+ }
+ return false;
+}
+
+bool CConfig::GetBoolSetting(int iSetting)
+{
+ if(iSetting >= 0 && iSetting < BOOL_SETTINGS)
+ return m_abBoolSettings[iSetting];
+ return false;
+}
+
+int CConfig::GetIntSetting(int iSetting)
+{
+ if(iSetting >= 0 && iSetting < INT_SETTINGS)
+ return m_aiIntSettings[iSetting];
+ return false;
+}
+
+void CConfig::ClearTree(HWND hTree)
+{
+ TreeView_DeleteAllItems(hTree);
+}
+
+void CConfig::FillDeviceBox(HWND hBox) {
+ CLCDConnection *connection = CAppletManager::GetInstance()->GetLCDConnection();
+ CLCDDevice *device = NULL;
+ int i = 0;
+ SendMessage(hBox,CB_RESETCONTENT,0,0);
+
+ while((device = connection->GetAttachedDevice(i++)) != NULL) {
+ SendMessage(hBox,CB_ADDSTRING,0,(LPARAM)device->GetDisplayName().c_str());
+ }
+
+ if(i == 1) {
+ SendMessage(hBox,CB_ADDSTRING,0,(LPARAM)_T("No device attached"));
+ }
+
+ int iDevice = CConfig::GetIntSetting(DEVICE);
+ if( iDevice >= i)
+ iDevice = 0;
+
+ SendMessage(hBox,CB_SETCURSEL ,iDevice,0);
+}
+
+void CConfig::FillTree(HWND hTree,bool bCList)
+{
+ TreeView_DeleteAllItems(hTree);
+
+ TVINSERTSTRUCT tvis;
+ tvis.hParent=NULL;
+ tvis.hInsertAfter=TVI_LAST;
+ tvis.item.mask=TVIF_PARAM|TVIF_TEXT|TVIF_IMAGE|TVIF_SELECTEDIMAGE;
+
+ vector<CProtoFilter*>::iterator iter = m_ProtoList.begin();
+ while(iter != m_ProtoList.end())
+ {
+ tvis.item.lParam=(LPARAM)(*iter);
+ tvis.item.pszText= (LPTSTR)(*iter)->strName.c_str();
+ if(!bCList)
+ {
+ tvis.item.iImage= (*iter)->bNotificationFilter;
+ (*iter)->bTempNotificationFilter = (*iter)->bNotificationFilter;
+ }
+ else
+ {
+ tvis.item.iImage= (*iter)->bContactlistFilter;
+ (*iter)->bTempContactlistFilter = (*iter)->bContactlistFilter;
+ }
+ tvis.item.iSelectedImage= tvis.item.iImage;
+
+ TreeView_InsertItem(hTree,&tvis);
+ iter++;
+ }
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CConfig.h b/plugins/MirandaG15/src/CConfig.h
new file mode 100644
index 0000000000..e35b68f772
--- /dev/null
+++ b/plugins/MirandaG15/src/CConfig.h
@@ -0,0 +1,166 @@
+#ifndef _CCONFIG_H_
+#define _CCONFIG_H_
+
+// Tabs
+#define TAB_OPTIONS 0
+#define TAB_NOTIFICATIONS 1
+#define TAB_CHAT 2
+#define TAB_CLIST 3
+
+// Fonts
+#define FONT_LOG 0
+#define FONT_SESSION 1
+#define FONT_CLIST 2
+#define FONT_TITLE 3
+#define FONT_NOTIFICATION 4
+
+#define FONT_SETTINGS 5
+
+// Bool settings
+#define CLIST_HIDEOFFLINE 0
+#define NOTIFY_MESSAGES 1
+#define NOTIFY_SIGNON 2
+#define NOTIFY_SIGNOFF 3
+#define NOTIFY_STATUS 4
+#define SESSION_LOADDB 5
+#define SHOW_LABELS 6
+#define SESSION_MARKREAD 7
+#define NOTIFY_CONTACTS 8
+#define NOTIFY_FILE 9
+#define NOTIFY_URL 10
+#define SESSION_SENDRETURN 11
+#define NOTIFY_PROTO_STATUS 12
+#define SESSION_SHOWTYPING 13
+#define SESSION_SENDTYPING 14
+#define SESSION_SCROLL_MAXIMIZED 15
+#define SESSION_REPLY_MAXIMIZED 16
+#define MAXIMIZED_TITLE 17
+#define MAXIMIZED_LABELS 18
+#define CLIST_USEGROUPS 19
+#define CLIST_USEIGNORE 20
+#define NOTIFY_PROTO_SIGNON 21
+#define NOTIFY_PROTO_SIGNOFF 22
+#define CLIST_SHOWPROTO 23
+#define SESSION_SYMBOLS 24
+#define CLIST_COUNTERS 24
+#define CLIST_DRAWLINES 25
+#define CLIST_POSITION 26
+#define CONTROL_BACKLIGHTS 28
+#define HOOK_VOLUMEWHEEL 29
+#define NOTIFY_SKIP_MESSAGES 30
+#define NOTIFY_SKIP_STATUS 31
+#define NOTIFY_SKIP_SIGNON 32
+#define NOTIFY_SKIP_SIGNOFF 33
+#define SESSION_TIMESTAMPS 34
+#define NOTIFY_TIMESTAMPS 35
+#define TIMESTAMP_SECONDS 36
+#define NOTIFY_IRC_MESSAGES 37
+#define NOTIFY_IRC_USERS 38
+#define NOTIFY_IRC_EMOTES 39
+#define NOTIFY_IRC_NOTICES 40
+#define NOTIFY_IRC_CHANNEL 41
+#define NOTIFY_IRC_STATUS 42
+#define CLIST_COLUMNS 43
+#define TRANSITIONS 44
+#define NOTIFY_NICKCUTOFF 45
+#define NOTIFY_SHOWPROTO 46
+#define NOTIFY_NO_SKIP_REPLY 47
+#define CLIST_SELECTION 48
+#define NOTIFY_CHANNELCUTOFF 49
+#define SCREENSAVER_LOCK 50
+#define SESSION_CLOSE 52
+#define SKIP_DRIVER_ERROR 53
+
+#define BOOL_SETTINGS 54
+
+// Int Settings
+#define SESSION_LOGSIZE 0
+#define NOTIFY_LOGSIZE 1
+#define NOTIFY_DURATION 2
+#define NOTIFY_TITLE 3
+#define SESSION_AUTOSCROLL 4
+#define CLIST_GA 5
+#define NOTIFY_NICKCUTOFF_OFFSET 6
+#define DEVICE 7
+#define NOTIFY_CHANNELCUTOFF_OFFSET 8
+#define SESSION_CLOSETIMER 9
+
+#define INT_SETTINGS 10
+
+// Enums
+#define CLIST_GA_NONE 0
+#define CLIST_GA_EXPAND 1
+#define CLIST_GA_COLLAPSE 2
+
+#define NOTIFY_TITLE_HIDE 0
+#define NOTIFY_TITLE_INFO 1
+#define NOTIFY_TITLE_NAME 2
+
+#define SESSION_AUTOSCROLL_NONE 0
+#define SESSION_AUTOSCROLL_FIRST 1
+#define SESSION_AUTOSCROLL_LAST 2
+
+struct CProtoFilter
+{
+ tstring strName;
+ bool bNotificationFilter;
+ bool bContactlistFilter;
+
+ bool bTempNotificationFilter;
+ bool bTempContactlistFilter;
+};
+
+class CConfig
+{
+public:
+ static void Initialize();
+ static void Shutdown();
+
+ static void LoadSettings();
+ static void SaveSettings();
+
+ // InitDialogHook Callback
+ static int InitOptionsDialog(WPARAM wParam, LPARAM lParam);
+ // OnConnectionChanged
+ static void OnConnectionChanged();
+
+ // Dialog WndProc
+ static INT_PTR CALLBACK AppearanceDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
+ static INT_PTR CALLBACK ChatDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
+ static INT_PTR CALLBACK NotificationsDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
+ static INT_PTR CALLBACK ContactlistDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
+
+ static bool GetBoolSetting(int iSetting);
+ static int GetIntSetting(int iSetting);
+ static bool GetProtocolNotificationFilter(tstring strProtocol);
+ static bool GetProtocolContactlistFilter(tstring strProtocol);
+
+ static LOGFONT &GetFont(int iFont);
+ static int GetFontHeight(int iFont);
+private:
+ static int GetSampleField(int iFont);
+ static void ClearTree(HWND hTree);
+ static void FillTree(HWND hTree,bool bCList=false);
+ static void FillDeviceBox(HWND hBox);
+
+ static HWND hDeviceBox;
+ static vector<CProtoFilter*> m_ProtoList;
+
+ static HANDLE m_hSampleFont[FONT_SETTINGS];
+ static TEXTMETRIC m_tmFontInfo[FONT_SETTINGS];
+ static LOGFONT m_logfont[FONT_SETTINGS];
+ static LOGFONT m_templogfont[FONT_SETTINGS];
+
+ static void LoadFontSettings(int iFont);
+ static void SaveFontSettings(int iFont);
+
+ static void UpdateFontSettings(int iFont);
+
+ static bool m_abBoolSettings[BOOL_SETTINGS];
+ static int m_aiIntSettings[INT_SETTINGS];
+ static bool m_bInitializingDialog;
+ static HANDLE m_hOptionsInitHook;
+
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CContactList.cpp b/plugins/MirandaG15/src/CContactList.cpp
new file mode 100644
index 0000000000..c2ba33e529
--- /dev/null
+++ b/plugins/MirandaG15/src/CContactList.cpp
@@ -0,0 +1,1174 @@
+#include "stdafx.h"
+#include "CContactList.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+const int aiStatusPriority[] = { 0, // ID_STATUS_OFFLINE 40071
+ 9, // ID_STATUS_ONLINE 40072
+ 8, // ID_STATUS_AWAY 40073
+ 1, // ID_STATUS_DND 40074
+ 7, // ID_STATUS_NA 40075
+ 6, // ID_STATUS_OCCUPIED 40076
+ 10, // ID_STATUS_FREECHAT 40077
+ 9, // ID_STATUS_INVISIBLE 40078
+ 8, // ID_STATUS_ONTHEPHONE 40079
+ 8 // ID_STATUS_OUTTOLUNCH 40080
+ };
+
+//************************************************************************
+// constructor
+//************************************************************************
+CContactList::CContactList()
+{
+ m_bUseGroups = false;
+ m_bUseMetaContacts = false;
+ m_dwLastScroll = 0;
+}
+
+//************************************************************************
+// destructor
+//************************************************************************
+CContactList::~CContactList()
+{
+}
+
+//************************************************************************
+// initializes the list
+//************************************************************************
+bool CContactList::Initialize()
+{
+ if(!CLCDList<CContactListEntry*,CContactListGroup*>::Initialize())
+ return false;
+
+ InitializeGroupObjects();
+
+ RefreshList();
+
+ return true;
+}
+
+//************************************************************************
+// deinitializes the list
+//************************************************************************
+bool CContactList::Shutdown()
+{
+ if(!CLCDList<CContactListEntry*,CContactListGroup*>::Shutdown())
+ return false;
+
+ UninitializeGroupObjects();
+
+ return false;
+}
+
+
+
+//************************************************************************
+// returns the contacts ccontactlistentry class
+//************************************************************************
+CContactListEntry *CContactList::GetContactData(CListEntry<CContactListEntry*,CContactListGroup*> *pEntry)
+{
+ if(pEntry->GetType() == ITEM)
+ return ((CListItem<CContactListEntry*,CContactListGroup*>*)pEntry)->GetItemData();
+ else
+ return ((CListContainer<CContactListEntry*,CContactListGroup*>*)pEntry)->GetGroupData()->pContactListEntry;
+}
+
+
+
+//************************************************************************
+// returns the contacts group path
+//************************************************************************
+tstring CContactList::GetContactGroupPath(HANDLE hContact)
+{
+ tstring strGroup = _T("");
+ if(db_get_b(0, "MetaContacts", "Enabled", 1) && CAppletManager::IsSubContact(hContact))
+ {
+ HANDLE hMetaContact = (HANDLE)CallService(MS_MC_GETMETACONTACT, (WPARAM)hContact, NULL);
+ if(CConfig::GetBoolSetting(CLIST_USEGROUPS))
+ strGroup = CAppletManager::GetContactGroup(hMetaContact);
+
+ tstring strMetaName = CAppletManager::GetContactDisplayname(hMetaContact);
+ strGroup += (strGroup.empty()?_T(""):_T("\\"))+ strMetaName;
+ }
+ else
+ strGroup = CAppletManager::GetContactGroup(hContact);
+ return strGroup;
+}
+
+//************************************************************************
+// adds a contact to the list
+//************************************************************************
+void CContactList::AddContact(HANDLE hContact)
+{
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = NULL;
+
+ tstring strName = CAppletManager::GetContactDisplayname(hContact);
+ char *szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO,(UINT)hContact,0);
+
+ tstring strGroup = GetContactGroupPath(hContact);
+ // ignore contacts without a valid protocoll
+ if(szProto == NULL)
+ return;
+
+ int iStatus = db_get_w(hContact,szProto,"Status",ID_STATUS_OFFLINE);
+ char *szStatus = (char *) CallService(MS_CLIST_GETSTATUSMODEDESCRIPTION, iStatus, 0);
+
+ CContactListEntry *psContact = new CContactListEntry();
+
+ psContact->strName = strName;
+ psContact->iMessages = 0;
+ psContact->hHandle = hContact;
+
+ psContact->iStatus = iStatus;
+
+ if(szStatus != NULL)
+ psContact->strStatus =toTstring(szStatus);
+ psContact->strProto = toTstring(szProto);
+
+ // check wether the contact should be listed
+ if(!IsVisible(psContact)) {
+ delete psContact;
+ return;
+ }
+
+ // Don't add metacontacts as contacts
+ if(!stricmp(szProto,"MetaContacts"))
+ {
+ if(!CConfig::GetBoolSetting(CLIST_USEGROUPS))
+ strGroup = _T("");
+ strGroup += (strGroup.empty()?_T(""):_T("\\"))+psContact->strName;
+ pGroup = GetGroupByString(strGroup);
+ if(pGroup == NULL)
+ pGroup = AddGroupByString(strGroup);
+ pGroup->GetGroupData()->hMetaContact = hContact;
+ pGroup->GetGroupData()->pContactListEntry = psContact;
+
+ pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)pGroup->GetParent();
+ if(pGroup->GetType() != ROOT && iStatus != ID_STATUS_OFFLINE)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,1);
+
+ pGroup->sort(CContactList::CompareEntries);
+
+ // check that all subcontacts exist
+ int numContacts = CallService(MS_MC_GETNUMCONTACTS,(WPARAM)hContact,0);
+ HANDLE hSubContact = NULL;
+ for(int i=0;i<numContacts;i++) {
+ hSubContact = (HANDLE *) CallService(MS_MC_GETSUBCONTACT, (WPARAM)hContact, (LPARAM)i);
+ RemoveContact(hSubContact);
+ AddContact(hSubContact);
+ }
+ return;
+ } else if(CAppletManager::IsSubContact(hContact)) {
+ HANDLE hMetaContact = (HANDLE *) CallService(MS_MC_GETMETACONTACT, (WPARAM)hContact, 0);
+ // check that the metacontact exists
+ if(!FindContact(hMetaContact)) {
+ AddContact(hMetaContact);
+ }
+ }
+
+ CListItem<CContactListEntry*,CContactListGroup*> *pItem = NULL;
+ if((!CAppletManager::IsSubContact(hContact) && !CConfig::GetBoolSetting(CLIST_USEGROUPS)) || strGroup.empty())
+ {
+ pItem = AddItem(psContact);
+ ((CListContainer<CContactListEntry*,CContactListGroup*>*)this)->sort(CContactList::CompareEntries);
+ }
+ else
+ {
+ pGroup = GetGroupByString(strGroup);
+ if(pGroup == NULL) {
+ pGroup = AddGroupByString(strGroup);
+ }
+ pItem = pGroup->AddItem(psContact);
+
+ if(!CAppletManager::IsSubContact(hContact) && iStatus != ID_STATUS_OFFLINE)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,1);
+
+ pGroup->sort(CContactList::CompareEntries);
+ }
+
+ UpdateMessageCounter((CListEntry<CContactListEntry*,CContactListGroup*>*)pItem);
+}
+
+//************************************************************************
+// returns wether a contact should be listed or not
+//************************************************************************
+bool CContactList::IsVisible(CContactListEntry *pEntry) {
+ if(!pEntry) {
+ return false;
+ }
+
+ if(pEntry->strProto != _T("MetaContacts")) {
+ if(pEntry->iStatus == ID_STATUS_OFFLINE && CConfig::GetBoolSetting(CLIST_HIDEOFFLINE)) {
+ return false;
+ }
+ } else {
+ if(pEntry->iStatus == ID_STATUS_OFFLINE) {
+ DWORD dwNumContacts = (DWORD)CallService(MS_MC_GETNUMCONTACTS,(WPARAM)pEntry->hHandle,0);
+ HANDLE hSubContact = NULL;
+ char *szProto;
+ for(int i=0;i<dwNumContacts;i++) {
+ hSubContact = (HANDLE)CallService(MS_MC_GETSUBCONTACT,(WPARAM)pEntry->hHandle,i);
+ szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO,(UINT)hSubContact,0);
+ if(db_get_w(hSubContact,szProto,"Status",ID_STATUS_OFFLINE) != ID_STATUS_OFFLINE) {
+ return true;
+ }
+ }
+ }
+ }
+
+ if(pEntry->iMessages > 0)
+ return true;
+
+ if(CConfig::GetBoolSetting(CLIST_USEIGNORE)) {
+ if(db_get_b(pEntry->hHandle,"CList","Hidden",0))
+ return false;
+ else if(CAppletManager::IsSubContact(pEntry->hHandle)) {
+ HANDLE hMetaContact = (HANDLE) CallService(MS_MC_GETMETACONTACT, (WPARAM)pEntry->hHandle, 0);
+ if(db_get_b(hMetaContact,"CList","Hidden",0)) {
+ return false;
+ }
+ }
+ }
+
+
+ if(!CConfig::GetProtocolContactlistFilter(pEntry->strProto))
+ return false;
+
+ if(CConfig::GetBoolSetting(CLIST_HIDEOFFLINE) && pEntry->iStatus == ID_STATUS_OFFLINE)
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// removes a contact from the list
+//************************************************************************
+void CContactList::RemoveContact(HANDLE hContact) {
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = NULL;
+
+ ///tstring strGroup = GetContactGroupPath(hContact);
+
+ CListEntry<CContactListEntry*,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ if(!pContactEntry) {
+ return;
+ }
+
+ if( !CConfig::GetBoolSetting(CLIST_USEGROUPS)){
+ if(pContactEntry->GetType() == ITEM)
+ RemoveItem(((CListItem<CContactListEntry*,CContactListGroup*>*)pContactEntry)->GetItemData());
+ else
+ RemoveGroup(((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry)->GetGroupData());
+ } else {
+ pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent();
+ ASSERT(pGroup != NULL);
+
+ CContactListEntry *pEntry = GetContactData(pContactEntry);
+ if(!pEntry) {
+ return;
+ }
+ // Update the contacts group if it has one
+ if(pGroup->GetType() != ROOT)
+ {
+ if(!CAppletManager::IsSubContact(hContact) && pEntry->iStatus != ID_STATUS_OFFLINE)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,-1);
+
+ if(!CAppletManager::IsSubContact(hContact) && pEntry->iMessages > 0)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,0,-pEntry->iMessages);
+ }
+
+ if(pContactEntry->GetType() == ITEM)
+ pGroup->RemoveItem(((CListItem<CContactListEntry*,CContactListGroup*>*)pContactEntry)->GetItemData());
+ else {
+ pGroup->RemoveGroup(((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry)->GetGroupData());
+ // Reenumerate all subcontacts (maybe MetaContacts was disabled
+ int numContacts = CallService(MS_MC_GETNUMCONTACTS,(WPARAM)hContact,0);
+ HANDLE hSubContact = NULL;
+ for(int i=0;i<numContacts;i++) {
+ hSubContact = (HANDLE *) CallService(MS_MC_GETSUBCONTACT,(WPARAM)hContact, (LPARAM)i);
+ if(!FindContact(hSubContact)) {
+ AddContact(hSubContact);
+ }
+ }
+ }
+
+ CListContainer<CContactListEntry*,CContactListGroup*> *pParent = (CListContainer<CContactListEntry*,CContactListGroup*>*)pGroup->GetParent();
+ while(pParent != NULL && pGroup->IsEmpty() && !pGroup->GetGroupData()->hMetaContact)
+ {
+ pParent->RemoveGroup(pGroup->GetGroupData());
+ pGroup = pParent;
+ pParent = (CListContainer<CContactListEntry*,CContactListGroup*>*)pGroup->GetParent();
+ }
+ }
+}
+
+//************************************************************************
+// get group by string
+//************************************************************************
+CListContainer<CContactListEntry*,CContactListGroup*> *CContactList::GetGroupByString(tstring strGroup)
+{
+ tstring strParse = strGroup;
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)this;
+ tstring::size_type pos;
+ while((pos = strParse.find('\\')) != tstring::npos )
+ {
+ strGroup = strParse.substr(0,pos);
+ strParse = strParse.substr(pos+1);
+
+ pGroup = FindGroupInGroup(strGroup,pGroup);
+ if(pGroup == NULL)
+ return NULL;
+ }
+ pGroup = FindGroupInGroup(strParse,pGroup);
+ return pGroup;
+}
+
+//************************************************************************
+// Adds a group
+//************************************************************************
+CListContainer<CContactListEntry*,CContactListGroup*> *CContactList::AddGroupByString(tstring strGroup)
+{
+ tstring strParse = strGroup;
+ tstring strPath = _T("");
+
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)this;
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup2 = NULL;
+ tstring::size_type pos;
+ while((pos = strParse.find('\\')) != tstring::npos )
+ {
+ strGroup = strParse.substr(0,pos);
+ strParse = strParse.substr(pos+1);
+ strPath += strGroup;
+
+ if(pGroup2 = FindGroupInGroup(strGroup,pGroup))
+ pGroup = pGroup2;
+ else
+ {
+ CContactListGroup *pGroupObject = GetGroupObjectByPath(strPath);
+ if(!pGroupObject)
+ pGroupObject = CreateGroupObjectByPath(strPath);
+ pGroup2 = pGroup->InsertGroup(pGroup->begin(),pGroupObject);
+ pGroup->sort(CContactList::CompareEntries);
+ pGroup = pGroup2;
+ }
+ ASSERT(pGroup != NULL);
+ strPath += _T("\\");
+ }
+ strPath += strParse;
+ if(pGroup2 = FindGroupInGroup(strParse,pGroup))
+ return pGroup2;
+ else
+ {
+ CContactListGroup *pGroupObject = GetGroupObjectByPath(strPath);
+ if(!pGroupObject)
+ pGroupObject = CreateGroupObjectByPath(strPath);
+ pGroup2 = pGroup->InsertGroup(pGroup->begin(),pGroupObject);
+ pGroup->sort(CContactList::CompareEntries);
+ return pGroup2;
+ }
+}
+
+//************************************************************************
+// returns the contact's status
+//************************************************************************
+int CContactList::GetContactStatus(HANDLE hContact)
+{
+ CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ if(!pContactEntry)
+ return ID_STATUS_OFFLINE;
+
+
+ CContactListEntry *pEntry = GetContactData(pContactEntry);
+ if(!pEntry) {
+ return ID_STATUS_OFFLINE;
+ }
+ return pEntry->iStatus;
+}
+
+
+
+//************************************************************************
+// Called to delete the specified item
+//************************************************************************
+void CContactList::DeleteItem(CContactListEntry *pEntry)
+{
+ delete pEntry;
+}
+
+//************************************************************************
+// Called to delete the specified group
+//************************************************************************
+void CContactList::DeleteGroup(CContactListGroup *pGroup)
+{
+}
+
+//************************************************************************
+// Called to draw the specified entry
+//************************************************************************
+void CContactList::DrawEntry(CLCDGfx *pGfx,CContactListEntry *pEntry,bool bSelected)
+{
+ if(pEntry == NULL) {
+ return;
+ }
+
+ int iOffset = 0;
+ tstring strText = _T("");
+ if(pEntry->iMessages > 0)
+ {
+ strText = _T("[");
+ strText += pEntry->strMessages;
+ strText += _T("]");
+ }
+ strText += pEntry->strName;
+
+ if(CConfig::GetBoolSetting(CLIST_SHOWPROTO) && !CConfig::GetBoolSetting(CLIST_COLUMNS))
+ {
+ int w = pGfx->GetClipWidth();
+ pGfx->DrawText(w-w*0.3,0,w*0.3,pEntry->strProto);
+ pGfx->DrawText(8,0,w*0.7-8,strText);
+ }
+ else
+ pGfx->DrawText(8,0,pGfx->GetClipWidth()-8,strText);
+
+
+ pGfx->DrawBitmap(1,ceil((pGfx->GetClipHeight()-5)/2.0f),5,5,CAppletManager::GetInstance()->GetStatusBitmap(pEntry->iStatus));
+
+ if(bSelected && (GetTickCount() - m_dwLastScroll < 1000 || !CConfig::GetBoolSetting(CLIST_SELECTION)))
+ {
+ RECT invert = { 0,0,GetWidth(),m_iFontHeight};
+ InvertRect(pGfx->GetHDC(), &invert);
+ }
+}
+
+//************************************************************************
+// Called to draw the specified group
+//************************************************************************
+void CContactList::DrawGroup(CLCDGfx *pGfx,CContactListGroup *pGroup,bool bOpen,bool bSelected)
+{
+ if(pGroup == NULL || ( pGroup->hMetaContact && pGroup->pContactListEntry == NULL)) {
+ return;
+ }
+
+ char num[10],num2[10];
+ itoa(pGroup->iMembers,num,10);
+ itoa(pGroup->iOnline,num2,10);
+
+ int iEvents = pGroup->iEvents;
+ tstring strText = pGroup->strName;
+
+ if(!pGroup->hMetaContact)
+ {
+ if(CConfig::GetBoolSetting(CLIST_COUNTERS))
+ strText = strText + _T(" (") + toTstring(num2).c_str()+ _T("/") + toTstring(num).c_str() + _T(")");
+ }
+ else
+ {
+ pGfx->DrawBitmap(8,ceil((pGfx->GetClipHeight()-5)/2.0f),5,5,CAppletManager::GetInstance()->GetStatusBitmap(pGroup->pContactListEntry->iStatus));
+ iEvents += pGroup->pContactListEntry->iMessages;
+ }
+
+ if(iEvents != 0)
+ {
+ itoa(iEvents,num,10);
+ strText = _T("[") + toTstring(num) + _T("]") + strText;
+ }
+
+ int iOffset = !pGroup->hMetaContact?m_iFontHeight*0.8:m_iFontHeight*0.8+8;
+ pGfx->DrawText(iOffset,0,pGfx->GetClipWidth()-iOffset,strText.c_str());
+
+ if(bOpen)
+ pGfx->DrawText(1,0,_T("-"));
+ else
+ pGfx->DrawText(1,0,_T("+"));
+
+ if(bSelected && (GetTickCount() - m_dwLastScroll < 1000|| !CConfig::GetBoolSetting(CLIST_SELECTION)))
+ {
+ RECT invert2 = { 0,0,GetWidth(),m_iFontHeight};
+ InvertRect(pGfx->GetHDC(),&invert2);
+ }
+}
+
+
+//************************************************************************
+// Called to compare two entrys
+//************************************************************************
+bool CContactList::CompareEntries(CListEntry<CContactListEntry*,CContactListGroup*> *pLeft,CListEntry<CContactListEntry*,CContactListGroup*> *pRight)
+{
+ CContactListEntry *pLeftEntry = GetContactData(pLeft);
+ CContactListEntry *pRightEntry = GetContactData(pRight);
+
+ if(pLeftEntry && pRightEntry)
+ {
+ int iLeftMessages = pLeftEntry->iMessages;
+ int iRightMessages = pRightEntry->iMessages;
+
+ if(pLeft->GetType() == CONTAINER)
+ iLeftMessages += ((CListContainer<CContactListEntry*,CContactListGroup*>*)pLeft)->GetGroupData()->iEvents;
+ if(pRight->GetType() == CONTAINER)
+ iRightMessages += ((CListContainer<CContactListEntry*,CContactListGroup*>*)pRight)->GetGroupData()->iEvents;
+
+ if (!iRightMessages && iLeftMessages)
+ return true;
+ else if (iRightMessages && !iLeftMessages)
+ return false;
+ else if (iLeftMessages && iRightMessages)
+ return (iLeftMessages > iRightMessages);
+ else if(pLeftEntry->iStatus != pRightEntry->iStatus)
+ return (aiStatusPriority[pLeftEntry->iStatus - ID_STATUS_OFFLINE] > aiStatusPriority[pRightEntry->iStatus - ID_STATUS_OFFLINE]);
+ else
+ return _tcsicmp(pLeftEntry->strName.c_str(),pRightEntry->strName.c_str())<0;
+ }
+ else if(pLeft->GetType() == ITEM && pRight->GetType() == CONTAINER)
+ return false;
+ else if(pLeft->GetType() == CONTAINER && pRight->GetType() == ITEM)
+ return true;
+ else if(pLeft->GetType() == CONTAINER && pRight->GetType() == CONTAINER)
+ {
+ CContactListGroup *pGroup1 = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pLeft)->GetGroupData();
+ CContactListGroup *pGroup2 = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pRight)->GetGroupData();
+
+ if (!pGroup2->iEvents && pGroup1->iEvents)
+ return true;
+ else if (pGroup2->iEvents && !pGroup1->iEvents)
+ return false;
+ else if (pGroup1->iEvents && pGroup2->iEvents)
+ return (pGroup1->iEvents > pGroup2->iEvents);
+ else
+ return _tcsicmp(pGroup1->strName.c_str(),pGroup2->strName.c_str())<0;
+ }
+}
+
+//************************************************************************
+// refreshes the list
+//************************************************************************
+void CContactList::RefreshList()
+{
+ if(db_get_b(NULL,"MetaContacts","Enabled",1) != m_bUseMetaContacts ||
+ CConfig::GetBoolSetting(CLIST_USEGROUPS) != m_bUseGroups)
+ {
+ InitializeGroupObjects();
+ Clear();
+ }
+ m_bUseGroups = CConfig::GetBoolSetting(CLIST_USEGROUPS);
+ m_bUseMetaContacts = db_get_b(NULL,"MetaContacts","Enabled",1);
+
+ CListEntry<CContactListEntry*,CContactListGroup*> *pContactEntry = NULL;
+ HANDLE hContact = db_find_first();
+ while(hContact != NULL)
+ {
+ pContactEntry = FindContact(hContact);
+ if(!pContactEntry)
+ AddContact(hContact);
+ else if(pContactEntry && !IsVisible(GetContactData(pContactEntry)))
+ RemoveContact(hContact);
+ hContact = db_find_next(hContact);
+ }
+}
+
+//************************************************************************
+// set the contactlists font
+//************************************************************************
+bool CContactList::SetFont(LOGFONT &lf)
+{
+ if(!CLCDList::SetFont(lf))
+ return false;
+
+ SetEntryHeight(m_iFontHeight<5?5:m_iFontHeight);
+
+ return true;
+}
+
+//************************************************************************
+// called when the configuration has changed
+//************************************************************************
+void CContactList::OnConfigChanged()
+{
+ RefreshList();
+}
+
+
+//************************************************************************
+// returns the entry for the specified group name
+//************************************************************************
+CListContainer<CContactListEntry*,CContactListGroup*> *CContactList::FindGroup(tstring strGroup)
+{
+ return FindGroupInGroup(strGroup,(CListContainer<CContactListEntry*,CContactListGroup*>*)this);
+}
+
+//************************************************************************
+// returns the entry for the specified group name
+//************************************************************************
+CListContainer<CContactListEntry*,CContactListGroup*> *CContactList::FindGroupInGroup(tstring strGroup,CListContainer<CContactListEntry*,CContactListGroup*> *pGroup)
+{
+ CListContainer<CContactListEntry*,CContactListGroup*>::iterator iter = pGroup->begin();
+ CListContainer<CContactListEntry*,CContactListGroup*> *pItem = NULL;
+ while(!pGroup->empty() && iter != pGroup->end())
+ {
+ if((*iter)->GetType() == CONTAINER)
+ {
+ pItem = (CListContainer<CContactListEntry*,CContactListGroup*>*)*iter;
+ if(pItem->GetGroupData()->strName == strGroup)
+ return pItem;
+
+ //pItem = FindGroupInGroup(strGroup,(CListContainer<CContactListEntry*,CContactListGroup*> *)*iter);
+ //if(pItem)
+ // return pItem;
+ }
+ iter++;
+ }
+ return NULL;
+}
+
+//************************************************************************
+// returns the entry for the specified handle
+//************************************************************************
+CListEntry<CContactListEntry*,CContactListGroup*> *CContactList::FindContact(HANDLE hContact)
+{
+ if(hContact == NULL)
+ return NULL;
+
+ return FindContactInGroup(hContact,(CListContainer<CContactListEntry*,CContactListGroup*>*)this);
+}
+
+//************************************************************************
+// returns the entry for the specified handle
+//************************************************************************
+CListEntry<CContactListEntry*,CContactListGroup*> *CContactList::FindContactInGroup(HANDLE hContact,CListContainer<CContactListEntry*,CContactListGroup*> *pGroup)
+{
+ if(hContact == NULL)
+ return NULL;
+
+ CListItem<CContactListEntry*,CContactListGroup*> *pItemEntry = NULL;
+ CListEntry<CContactListEntry*,CContactListGroup*> *pEntry = NULL;
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroupEntry = NULL;
+ CListContainer<CContactListEntry*,CContactListGroup*>::iterator iter = pGroup->begin();
+ while(iter != pGroup->end())
+ {
+ if((*iter)->GetType() == ITEM)
+ {
+ pItemEntry = (CListItem<CContactListEntry*,CContactListGroup*>*)*iter;
+ if(pItemEntry->GetItemData()->hHandle == hContact)
+ return *iter;
+ }
+ else
+ {
+ pGroupEntry = (CListContainer<CContactListEntry*,CContactListGroup*> *)*iter;
+ if(pGroupEntry->GetGroupData()->hMetaContact == hContact)
+ return *iter;
+
+ pEntry = FindContactInGroup(hContact,pGroupEntry);
+ if(pEntry)
+ return pEntry;
+ }
+ iter++;
+ }
+ return NULL;
+}
+
+
+//************************************************************************
+// called when a contacts hidden flag has changed
+//************************************************************************
+void CContactList::OnContactHiddenChanged(HANDLE hContact, bool bHidden)
+{
+ CListEntry<CContactListEntry*,CContactListGroup*> *pContactEntry = FindContact(hContact);
+
+ if(!pContactEntry && !bHidden)
+ {
+ AddContact(hContact);
+ return;
+ }
+ else if(!pContactEntry)
+ return;
+
+ if(!IsVisible(GetContactData(pContactEntry)))
+ RemoveContact(hContact);
+}
+
+//************************************************************************
+// called when a contacts nickname has changed
+//************************************************************************
+void CContactList::OnContactNickChanged(HANDLE hContact, tstring strNick)
+{
+ CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ if(!pContactEntry)
+ return;
+
+ if(pContactEntry->GetType() == CONTAINER)
+ {
+ CListContainer *pGroup = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry);
+ pGroup->GetGroupData()->strName = strNick;
+ tstring strPath = GetContactGroupPath(hContact);
+ pGroup->GetGroupData()->strPath = strPath + (strPath.empty()?_T(""):_T("\\")) + strNick;
+ }
+
+ CContactListEntry* pEntry = GetContactData(pContactEntry);
+ if(!pEntry) {
+ return;
+ }
+
+ pEntry->strName = strNick;
+ ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent())->sort(CContactList::CompareEntries);
+}
+
+//************************************************************************
+// called when a contacts status has changed
+//************************************************************************
+void CContactList::OnStatusChange(HANDLE hContact,int iStatus)
+{
+ // find the entry in the list
+ CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ if(!pContactEntry)
+ {
+ AddContact(hContact);
+ return;
+ }
+
+
+ CContactListEntry *pItemData = GetContactData(pContactEntry);
+ if(!pItemData) {
+ return;
+ }
+ // get the old status
+ int iOldStatus = pItemData->iStatus;
+
+ // Update the list entry
+ char *szStatus = (char *) CallService(MS_CLIST_GETSTATUSMODEDESCRIPTION, iStatus, 0);
+ if(szStatus != NULL)
+ pItemData->strStatus =toTstring(szStatus);
+
+ pItemData->iStatus = iStatus;
+
+ // update the contacts group
+ CListContainer<CContactListEntry*,CContactListGroup*>* pGroup = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent());
+ if(pGroup->GetType() != ROOT)
+ {
+ if(!CAppletManager::IsSubContact(hContact) && iStatus == ID_STATUS_OFFLINE && iOldStatus != ID_STATUS_OFFLINE)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,-1);
+
+ else if(!CAppletManager::IsSubContact(hContact) && iStatus != ID_STATUS_OFFLINE && iOldStatus == ID_STATUS_OFFLINE)
+ ChangeGroupObjectCounters(pGroup->GetGroupData()->strPath,0,1);
+ }
+
+ // check if the entry is still visible
+ if(!IsVisible(pItemData))
+ {
+ RemoveContact(hContact);
+ return;
+ }
+
+ // sort the list
+ pGroup->sort(CContactList::CompareEntries);
+
+}
+
+
+
+//************************************************************************
+// called when the contacts message count has changed
+//************************************************************************
+void CContactList::OnMessageCountChanged(HANDLE hContact)
+{
+ CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ if(!pContactEntry)
+ {
+ AddContact(hContact);
+ return;
+ }
+
+ UpdateMessageCounter(pContactEntry);
+
+ if(!IsVisible(GetContactData(pContactEntry)))
+ RemoveContact(hContact);
+ ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent())->sort(CContactList::CompareEntries);
+
+}
+
+//************************************************************************
+// called when a contact has been added
+//************************************************************************
+void CContactList::OnContactAdded(HANDLE hContact)
+{
+ // Update the list
+ AddContact(hContact);
+
+ // increase the membercount of the new group, and check if it needs to be created
+ tstring strGroup = GetContactGroupPath(hContact);
+ if(!strGroup.empty())
+ {
+ CContactListGroup *pGroup = GetGroupObjectByPath(strGroup);
+ if(!pGroup)
+ pGroup = CreateGroupObjectByPath(strGroup);
+
+ if(!CAppletManager::IsSubContact(hContact))
+ ChangeGroupObjectCounters(strGroup,1);
+ }
+}
+
+//************************************************************************
+// called when a contact has been deleted
+//************************************************************************
+void CContactList::OnContactDeleted(HANDLE hContact)
+{
+ // Update the list
+ RemoveContact(hContact);
+
+ // Decrease the membercount of the old group, and check if it needs to be deleted
+ int res = 0;
+ tstring strGroup = GetContactGroupPath(hContact);
+ if(!strGroup.empty())
+ {
+ CContactListGroup *pGroup = GetGroupObjectByPath(strGroup);
+
+
+ if(!CAppletManager::IsSubContact(hContact))
+ ChangeGroupObjectCounters(strGroup,-1);
+
+ if(pGroup->iMembers <= 0)
+ DeleteGroupObjectByPath(pGroup->strPath);
+ }
+}
+
+//************************************************************************
+// called when a contacts group has changed
+//************************************************************************
+void CContactList::OnContactGroupChanged(HANDLE hContact,tstring strGroup)
+{
+ bool bMetaContact = false;
+
+
+ strGroup = GetContactGroupPath(hContact);
+
+ // Decrease the membercount of the old group
+ CListEntry<CContactListEntry *,CContactListGroup*> *pContactEntry = FindContact(hContact);
+ CContactListGroup *pOldGroup = NULL;
+ // If the contactentry was not found, try adding the contact (metacontacts fix)
+ if(!pContactEntry) {
+ return;
+ }
+ if(pContactEntry->GetType() == CONTAINER)
+ bMetaContact = true;
+
+
+ CListContainer<CContactListEntry*,CContactListGroup*>* pContainer = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent());
+ // Update the contacts group if it has one
+ if(pContainer->GetType() != ROOT)
+ {
+ pOldGroup = pContainer->GetGroupData();
+ if(!CAppletManager::IsSubContact(hContact))
+ ChangeGroupObjectCounters(pOldGroup->strPath,-1);
+ }
+
+ // increase the membercount of the new group, and check if it needs to be created
+ if(!strGroup.empty())
+ {
+ CContactListGroup *pGroup = GetGroupObjectByPath(strGroup);
+ if(!pGroup)
+ pGroup = CreateGroupObjectByPath(strGroup);
+ if(!CAppletManager::IsSubContact(hContact))
+ ChangeGroupObjectCounters(strGroup,1);
+ }
+
+ // move subcontacts
+ if(pContactEntry->GetType() == CONTAINER)
+ {
+ CListContainer<CContactListEntry*,CContactListGroup*> *pGroup = (CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry;
+ CListContainer<CContactListEntry*,CContactListGroup*>::iterator iter = pGroup->begin();
+ while(!pGroup->empty())
+ {
+ iter = pGroup->begin();
+ if((*iter)->GetType() == ITEM)
+ OnContactGroupChanged(GetContactData(*iter)->hHandle,_T(""));
+ bool b = pGroup->empty();
+ int i = pGroup->size();
+ Sleep(1);
+ }
+ }
+
+ // update the list
+ RemoveContact(hContact);
+ AddContact(hContact);
+
+ if(bMetaContact)
+ {
+ tstring strName = CAppletManager::GetContactDisplayname(hContact);
+ tstring strPath = _T("");
+ if(pOldGroup)
+ strPath += pOldGroup->strPath;
+ strPath += (strPath.empty()?_T(""):_T("\\")) + strName;
+ DeleteGroupObjectByPath(strPath);
+ }
+
+ // check if the old group ( if it exists ) needs to be deleted
+ if(pOldGroup && !pOldGroup->hMetaContact && pOldGroup->iMembers <= 0 && pOldGroup->iGroups <= 0)
+ DeleteGroupObjectByPath(pOldGroup->strPath);
+}
+
+//************************************************************************
+// updates the message count for the specified contact
+//************************************************************************
+void CContactList::UpdateMessageCounter(CListEntry<CContactListEntry*,CContactListGroup*> *pContactEntry)
+{
+ CContactListEntry *pEntry = GetContactData(pContactEntry);
+ if(!pEntry) {
+ return;
+ }
+ int iOldMessages = pEntry->iMessages;
+
+ bool bSort = false;
+ HANDLE hEvent= NULL;
+
+ hEvent = db_event_firstUnread(pEntry->hHandle);
+ if(CAppletManager::IsMessageWindowOpen(pEntry->hHandle) || (hEvent == NULL && pEntry->iMessages > 0))
+ {
+ pEntry->iMessages = 0;
+ bSort = true;
+ }
+ else
+ {
+ pEntry->iMessages = 0;
+ HANDLE hLastEvent = db_event_last(pEntry->hHandle);
+ while(hLastEvent != NULL && hEvent != NULL)
+ {
+ pEntry->iMessages++;
+ if(hLastEvent == hEvent)
+ break;
+ hLastEvent = db_event_prev(hLastEvent);
+ }
+ }
+ if(pEntry->iMessages >= 100)
+ pEntry->strMessages = _T(">99");
+ else
+ {
+ char buffer[8];
+ buffer[0] = 0;
+ itoa(pEntry->iMessages,buffer,10);
+ pEntry->strMessages = toTstring(buffer);
+ }
+
+ CListContainer<CContactListEntry*,CContactListGroup*>* pContainer = ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContactEntry->GetParent());
+ // Update the contacts group if it has one
+ if(pContainer->GetType() != ROOT)
+ {
+ // Update the groups event count
+ if(iOldMessages != 0 && pEntry->iMessages == 0)
+ ChangeGroupObjectCounters(pContainer->GetGroupData()->strPath,0,0,-1);
+ else if(iOldMessages == 0 && pEntry->iMessages != 0)
+ ChangeGroupObjectCounters(pContainer->GetGroupData()->strPath,0,0,1);
+ else
+ return;
+
+ // sort the groups parent
+ ((CListContainer<CContactListEntry*,CContactListGroup*>*)pContainer->GetParent())->sort(CContactList::CompareEntries);
+ }
+}
+
+//************************************************************************
+// changes the groups membercount
+//************************************************************************
+void CContactList::ChangeGroupObjectCounters(tstring strGroup,int iMembers,int iOnline,int iEvents)
+{
+ CContactListGroup* pGroup = GetGroupObjectByPath(strGroup);
+ if(!pGroup)
+ return;
+
+ pGroup->iMembers += iMembers;
+ pGroup->iOnline += iOnline;
+ pGroup->iEvents += iEvents;
+
+ tstring strParse = pGroup->strPath;
+ tstring::size_type pos;
+
+ while((pos = strParse.rfind('\\')) != tstring::npos )
+ {
+ strParse = strParse.substr(0,pos);
+
+ pGroup = GetGroupObjectByPath(strParse);
+ if(!pGroup)
+ break;
+ pGroup->iMembers += iMembers;
+ pGroup->iOnline += iOnline;
+ pGroup->iEvents += iEvents;
+ }
+}
+
+//************************************************************************
+// uninitializes the group objects
+//************************************************************************
+void CContactList::UninitializeGroupObjects()
+{
+ vector<CContactListGroup*>::iterator iter = m_Groups.begin();
+ while(iter != m_Groups.end())
+ {
+ delete (*iter);
+ iter++;
+ }
+ m_Groups.clear();
+}
+
+//************************************************************************
+// initializes the group objects
+//************************************************************************
+void CContactList::InitializeGroupObjects()
+{
+ UninitializeGroupObjects();
+
+ int res = 0;
+ CContactListGroup *pGroup = NULL;
+
+ HANDLE hContact = db_find_first();
+ HANDLE hMetaContact = NULL;
+ char *szProto = NULL;
+ while(hContact != NULL)
+ {
+ tstring strGroup = GetContactGroupPath(hContact);
+ szProto = (char*)CallService(MS_PROTO_GETCONTACTBASEPROTO,(UINT)hContact,0);
+ if(szProto && db_get_b(NULL,"MetaContacts","Enabled",1) && !stricmp(szProto,"MetaContacts"))
+ {
+ tstring strName = CAppletManager::GetContactDisplayname(hContact);
+ tstring strPath = _T("");
+ if(CConfig::GetBoolSetting(CLIST_USEGROUPS))
+ strPath += strGroup;
+ strPath += (strPath.empty()?_T(""):_T("\\")) + strName;
+
+ pGroup = CreateGroupObjectByPath(strPath);
+ pGroup->hMetaContact = hContact;
+
+ if(!strGroup.empty())
+ ChangeGroupObjectCounters(strGroup,1);
+ }
+ // If the contact has no group, continue
+ else if(!strGroup.empty() && CConfig::GetBoolSetting(CLIST_USEGROUPS))
+ {
+ pGroup = GetGroupObjectByPath(strGroup);
+
+ // create the group
+ if(!pGroup)
+ pGroup = CreateGroupObjectByPath(strGroup);
+
+ // update it's counters
+ if(!CAppletManager::IsSubContact(hContact))
+ ChangeGroupObjectCounters(strGroup,1);
+ }
+
+ hContact = db_find_next(hContact);
+ }
+}
+
+//************************************************************************
+// get group object by string
+//************************************************************************
+CContactListGroup *CContactList::GetGroupObjectByPath(tstring strPath)
+{
+ ASSERT(!strPath.empty());
+
+ CContactListGroup *pGroup = NULL;
+ vector<CContactListGroup*>::iterator iter = m_Groups.begin();
+ for(;iter != m_Groups.end();iter++)
+ {
+ if((*iter)->strPath == strPath)
+ {
+ pGroup = *iter;
+ break;
+ }
+ }
+ return pGroup;
+}
+
+//************************************************************************
+// creates a group object by string
+//************************************************************************
+CContactListGroup *CContactList::CreateGroupObjectByPath(tstring strPath)
+{
+ ASSERT(!strPath.empty());
+
+ CContactListGroup *pNewGroup = new CContactListGroup();
+ CContactListGroup *pParentGroup = NULL;
+
+ tstring strParsePath = _T("");
+ tstring strName = strPath;
+ tstring::size_type pos;
+
+ while((pos = strName.find('\\')) != tstring::npos )
+ {
+ strParsePath += strName.substr(0,pos);
+ strName = strName.substr(pos+1);
+
+ pParentGroup = GetGroupObjectByPath(strParsePath);
+ if(!pParentGroup)
+ pParentGroup = CreateGroupObjectByPath(strParsePath);
+ strParsePath += _T("\\");
+ }
+
+ if(pParentGroup)
+ pParentGroup->iGroups++;
+
+ pNewGroup->strName = strName;
+ pNewGroup->strPath = strPath;
+ pNewGroup->iMembers = 0;
+ pNewGroup->iOnline = 0;
+ pNewGroup->iGroups = 0;
+ pNewGroup->iEvents = 0;
+ pNewGroup->hMetaContact = NULL;
+ pNewGroup->pContactListEntry = NULL;
+
+ m_Groups.push_back(pNewGroup);
+
+ return pNewGroup;
+}
+
+//************************************************************************
+// deletes a group object by string
+//************************************************************************
+void CContactList::DeleteGroupObjectByPath(tstring strPath)
+{
+ ASSERT(!strPath.empty());
+
+ CContactListGroup *pParentGroup = NULL;
+ vector<CContactListGroup*>::iterator iter = m_Groups.begin();
+ for(iter = m_Groups.begin();iter != m_Groups.end();iter++)
+ {
+ if((*iter)->strPath == strPath)
+ {
+ CContactListGroup *pGroup = *iter;
+ m_Groups.erase(iter);
+ if(pGroup->pContactListEntry)
+ {
+ DeleteEntry(pGroup->pContactListEntry);
+ }
+ delete pGroup;
+
+ tstring strParse = strPath;
+ tstring::size_type pos = strParse.rfind('\\');
+ if(pos != tstring::npos )
+ {
+ strParse = strParse.substr(0,pos);
+ pParentGroup = GetGroupObjectByPath(strParse);
+ pParentGroup->iGroups--;
+ if(pParentGroup->iMembers <= 0 && pParentGroup->iGroups <= 0)
+ DeleteGroupObjectByPath(strParse);
+ }
+ return;
+ }
+ }
+}
+
+void CContactList::SetPosition(CListEntry<CContactListEntry*,CContactListGroup*> *pEntry)
+{
+ CLCDList<CContactListEntry*,CContactListGroup*>::SetPosition(pEntry);
+}
+
+bool CContactList::ScrollUp()
+{
+ m_dwLastScroll = GetTickCount();
+ return CLCDList<CContactListEntry*,CContactListGroup*>::ScrollUp();
+}
+
+bool CContactList::ScrollDown()
+{
+ m_dwLastScroll = GetTickCount();
+ return CLCDList<CContactListEntry*,CContactListGroup*>::ScrollDown();
+}
+
+void CContactList::ShowSelection() {
+ m_dwLastScroll = GetTickCount();
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CContactList.h b/plugins/MirandaG15/src/CContactList.h
new file mode 100644
index 0000000000..75b129f8fc
--- /dev/null
+++ b/plugins/MirandaG15/src/CContactList.h
@@ -0,0 +1,145 @@
+#ifndef _CCONTACTLIST_H_
+#define _CCONTACTLIST_H_
+
+#include "CLCDList.h"
+
+class CContactListEntry
+{
+public:
+ int iMessages;
+ tstring strMessages;
+ HANDLE hHandle;
+ tstring strName;
+ tstring strProto;
+ tstring strStatus;
+ int iStatus;
+};
+
+class CContactListGroup
+{
+public:
+ tstring strName;
+ tstring strPath;
+ int iMembers;
+ int iGroups;
+ int iOnline;
+ int iEvents;
+
+ HANDLE hMetaContact;
+ CContactListEntry *pContactListEntry;
+};
+
+class CContactList : public CLCDList<CContactListEntry*,CContactListGroup*>
+{
+public:
+ // constructor
+ CContactList();
+ // destructor
+ ~CContactList();
+
+ // initializes the list
+ bool Initialize();
+ // deinitializes the list
+ bool Shutdown();
+
+ // called when a contact has been added
+ void OnContactAdded(HANDLE hContact);
+ // called when a contact has been deleted
+ void OnContactDeleted(HANDLE hContact);
+ // called when the configuration has changed
+ void OnConfigChanged();
+ // called when a contacts group has changed
+ void OnContactGroupChanged(HANDLE hContact,tstring strGroup);
+ // called when a contacts hidden flag has changed
+ void OnContactHiddenChanged(HANDLE hContact, bool bVisibility);
+ // called when a contacts nickname has changed
+ void OnContactNickChanged(HANDLE hContact, tstring strNick);
+ // called when a contacts status has changed
+ void OnStatusChange(HANDLE hContact,int iStatus);
+ // called when the contacts message count has changed
+ void OnMessageCountChanged(HANDLE hContact);
+ // returns the contact's status
+ int GetContactStatus(HANDLE hContact);
+
+ // Called to compare two entrys
+ static bool CompareEntries(CListEntry<CContactListEntry*,CContactListGroup*> *pLeft,CListEntry<CContactListEntry*,CContactListGroup*> *pRight);
+
+ void SetPosition(CListEntry<CContactListEntry*,CContactListGroup*> *pEntry);
+ bool ScrollUp();
+ bool ScrollDown();
+ void ShowSelection();
+
+ bool SetFont(LOGFONT &lf);
+protected:
+ // returns the contacts group path
+ tstring GetContactGroupPath(HANDLE hContact);
+
+ // adds a contact to the list
+ void AddContact(HANDLE hContact);
+ // removes a contact from the list
+ void RemoveContact(HANDLE hContact);
+
+ // uninitializes the group objects
+ void UninitializeGroupObjects();
+
+ // initializes the group objects
+ void InitializeGroupObjects();
+ // get group object by string
+ CContactListGroup *GetGroupObjectByPath(tstring strPath);
+ // creates a group object by string
+ CContactListGroup *CreateGroupObjectByPath(tstring strPath);
+ // deletes a group object by string
+ void DeleteGroupObjectByPath(tstring strPath);
+
+ // changes the groups membercount
+ void ChangeGroupObjectCounters(tstring strGroup,int iMembers,int iOnline=0,int iEvents=0);
+
+ // returns wether a contact should be listed or not
+ bool IsVisible(CContactListEntry *pEntry);
+
+ // sorts all entries of a group
+ void SortGroup(CListContainer<CContactListEntry*,CContactListGroup*> *pGroup);
+
+ // tries to find a contact in the specified group
+ CListEntry<CContactListEntry*,CContactListGroup*> *FindContactInGroup(HANDLE hContact,CListContainer<CContactListEntry*,CContactListGroup*> *pGroup);
+
+ // tries to find a group in the specified group
+ CListContainer<CContactListEntry*,CContactListGroup*> *FindGroupInGroup(tstring strGroup,CListContainer<CContactListEntry*,CContactListGroup*> *pGroup);
+
+ // Adds a group
+ CListContainer<CContactListEntry*,CContactListGroup*> *AddGroupByString(tstring strGroup);
+ // get group by string
+ CListContainer<CContactListEntry*,CContactListGroup*> *GetGroupByString(tstring strGroup);
+
+ // updates the message counter for the specified entry
+ void UpdateMessageCounter(CListEntry<CContactListEntry*,CContactListGroup*> *pContactEntry);
+ // refreshes the list
+ void RefreshList();
+
+ // returns the entry for the specified handle
+ CListEntry<CContactListEntry*,CContactListGroup*> *FindContact(HANDLE hContact);
+
+ // returns the entry for the specified group name
+ CListContainer<CContactListEntry*,CContactListGroup*> *FindGroup(tstring strGroup);
+
+ // returns the contacts ccontactlistentry class
+ static CContactListEntry *GetContactData(CListEntry<CContactListEntry*,CContactListGroup*> *pEntry);
+
+ // Called to delete the specified item
+ void DeleteItem(CContactListEntry *pEntry);
+ // Called to delete the specified group
+ void DeleteGroup(CContactListGroup* pGroup);
+ // Called to draw the specified group
+ void DrawGroup(CLCDGfx *pGfx,CContactListGroup* pGroup,bool bOpen,bool bSelected);
+ // Called to draw the specified entry
+ void DrawEntry(CLCDGfx *pGfx,CContactListEntry *pEntry,bool bSelected);
+
+ bool m_bUseGroups;
+ bool m_bUseMetaContacts;
+ vector<CContactListGroup*> m_Groups;
+ DWORD m_dwLastScroll;
+
+ HBITMAP m_ahBitmaps[8];
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CContactlistScreen.cpp b/plugins/MirandaG15/src/CContactlistScreen.cpp
new file mode 100644
index 0000000000..b9cbebf5b2
--- /dev/null
+++ b/plugins/MirandaG15/src/CContactlistScreen.cpp
@@ -0,0 +1,315 @@
+#include "stdafx.h"
+#include "CContactlistScreen.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CContactlistScreen::CContactlistScreen()
+{
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CContactlistScreen::~CContactlistScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CContactlistScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_ContactList.Initialize();
+ m_ContactList.SetOrigin(0, 0);
+ m_ContactList.SetSize(GetWidth()-5, GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+ m_ContactList.SetFont(CConfig::GetFont(FONT_CLIST));
+ m_ContactList.SetDrawTreeLines(CConfig::GetBoolSetting(CLIST_DRAWLINES));
+ m_ContactList.SetColumns(CConfig::GetBoolSetting(CLIST_COLUMNS)?2:1);
+
+ AddObject(&m_ContactList);
+
+ m_Scrollbar.Initialize();
+ m_Scrollbar.SetOrigin(GetWidth()-4,0);
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+ m_ContactList.SetScrollbar(&m_Scrollbar);
+
+ AddObject(&m_Scrollbar);
+
+ SetButtonBitmap(0,IDB_UP);
+ SetButtonBitmap(1,IDB_DOWN);
+ SetButtonBitmap(2,IDB_HISTORY);
+ SetButtonBitmap(3,IDB_CHAT);
+
+ return true;
+}
+
+//************************************************************************
+// Shutdown the screen
+//************************************************************************
+bool CContactlistScreen::Shutdown()
+{
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CContactlistScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CContactlistScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// returns the online status of the specified contact
+//************************************************************************
+int CContactlistScreen::GetContactStatus(HANDLE hContact)
+{
+ return m_ContactList.GetContactStatus(hContact);
+}
+
+//************************************************************************
+// resets the position of the contactlist
+//************************************************************************
+void CContactlistScreen::ResetPosition()
+{
+ // collapse all groups if setting is active
+ switch(CConfig::GetIntSetting(CLIST_GA))
+ {
+ case CLIST_GA_COLLAPSE:
+ m_ContactList.CollapseAll();
+ break;
+ case CLIST_GA_EXPAND:
+ m_ContactList.ExpandAll();
+ break;
+ }
+
+ // select the first item if setting is active
+ if(CConfig::GetBoolSetting(CLIST_POSITION))
+ m_ContactList.SetPosition(m_ContactList.GetFirstEntry());
+
+ UpdateUseSoftkeyLabel();
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CContactlistScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+
+ m_ContactList.OnConfigChanged();
+ m_ContactList.SetSize(GetWidth()-5, GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+
+ m_Scrollbar.SetOrigin(GetWidth()-4,0);
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CContactlistScreen::OnConfigChanged()
+{
+ CScreen::OnConfigChanged();
+
+ m_ContactList.OnConfigChanged();
+ m_ContactList.SetDrawTreeLines(CConfig::GetBoolSetting(CLIST_DRAWLINES));
+ m_ContactList.SetSize(GetWidth()-5, GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+ m_ContactList.SetFont(CConfig::GetFont(FONT_CLIST));
+ m_ContactList.SetColumns(CConfig::GetBoolSetting(CLIST_COLUMNS)?2:1);
+
+ m_Scrollbar.SetOrigin(GetWidth()-4,0);
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+}
+
+//************************************************************************
+// Called when an event is received
+//************************************************************************
+void CContactlistScreen::OnEventReceived(CEvent *pEvent)
+{
+ int iStatus = 0;
+ switch(pEvent->eType)
+ {
+ case EVENT_SIGNED_ON:
+ case EVENT_SIGNED_OFF:
+ case EVENT_STATUS:
+ m_ContactList.OnStatusChange(pEvent->hContact,pEvent->iValue);
+ break;
+ case EVENT_CONTACT_NICK:
+ m_ContactList.OnContactNickChanged(pEvent->hContact,pEvent->strValue);
+ break;
+ case EVENT_CONTACT_ADDED:
+ m_ContactList.OnContactAdded(pEvent->hContact);
+ break;
+ case EVENT_CONTACT_DELETED:
+ m_ContactList.OnContactDeleted(pEvent->hContact);
+ break;
+ case EVENT_MSG_RECEIVED:
+ case EVENT_MESSAGEWINDOW:
+ m_ContactList.OnMessageCountChanged(pEvent->hContact);
+ break;
+ case EVENT_CONTACT_HIDDEN:
+ m_ContactList.OnContactHiddenChanged(pEvent->hContact,pEvent->iValue);
+ break;
+ case EVENT_CONTACT_GROUP:
+ m_ContactList.OnContactGroupChanged(pEvent->hContact,pEvent->strValue);
+ break;
+ }
+}
+
+//************************************************************************
+// Called when a chat session was opened
+//************************************************************************
+void CContactlistScreen::OnSessionOpened(HANDLE hContact)
+{
+ m_ContactList.OnMessageCountChanged(hContact);
+}
+
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CContactlistScreen::OnLCDButtonDown(int iButton)
+{
+ m_bLongPress = false;
+ if(iButton == LGLCDBUTTON_CANCEL) {
+ CAppletManager::GetInstance()->ActivatePreviousScreen();
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_ContactList.ScrollDown();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_ContactList.ScrollUp();
+ } else if(iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_MENU) {
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ return;
+ } else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) {
+ CListEntry<CContactListEntry*,CContactListGroup*> *pEntry = m_ContactList.GetSelectedEntry();
+ if(!pEntry)
+ return;
+ if(pEntry->GetType() == CONTAINER) {
+ CListContainer<CContactListEntry*,CContactListGroup*> *pContainer = (CListContainer<CContactListEntry*,CContactListGroup*>*)pEntry;
+ if(pContainer->GetGroupData()->hMetaContact == NULL) {
+ pContainer->ToggleOpen();
+ }
+ } else if(pEntry->GetType() == ITEM)
+ {
+ CContactListEntry *pContact = ((CListItem<CContactListEntry*,CContactListGroup*>*)pEntry)->GetItemData();
+ if(!pContact->hHandle)
+ return;
+ CAppletManager::GetInstance()->ActivateChatScreen(pContact->hHandle);
+ return;
+ }
+ }
+
+ UpdateUseSoftkeyLabel();
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CContactlistScreen::OnLCDButtonRepeated(int iButton)
+{
+ m_bLongPress = true;
+ if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_ContactList.ScrollDown();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_ContactList.ScrollUp();
+ } else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) {
+ UpdateUseSoftkeyLabel();
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CContactlistScreen::OnLCDButtonUp(int iButton)
+{
+ if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) {
+ m_ContactList.ShowSelection();
+
+ CListEntry<CContactListEntry*,CContactListGroup*> *pEntry = m_ContactList.GetSelectedEntry();
+ if(!pEntry)
+ return;
+ if(pEntry->GetType() == CONTAINER) {
+ CListContainer<CContactListEntry*,CContactListGroup*> *pContainer = (CListContainer<CContactListEntry*,CContactListGroup*>*)pEntry;
+ if(pContainer->GetGroupData()->hMetaContact != NULL) {
+ if(m_bLongPress) {
+ pContainer->ToggleOpen();
+ } else {
+ CAppletManager::GetInstance()->ActivateChatScreen(pContainer->GetGroupData()->hMetaContact);
+ }
+ }
+ }
+ }
+ m_bLongPress = false;
+ UpdateUseSoftkeyLabel();
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CContactlistScreen::OnActivation()
+{
+
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CContactlistScreen::OnDeactivation()
+{
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CContactlistScreen::OnExpiration()
+{
+}
+
+//************************************************************************
+// updates the use softkey label
+//************************************************************************
+void CContactlistScreen::UpdateUseSoftkeyLabel()
+{
+ CListEntry<CContactListEntry*,CContactListGroup*> *pEntry = m_ContactList.GetSelectedEntry();
+ if(!pEntry)
+ return;
+
+ if(pEntry->GetType() == CONTAINER)
+ {
+ CListContainer<CContactListEntry*,CContactListGroup*> *pContainer = (CListContainer<CContactListEntry*,CContactListGroup*>*)pEntry;
+ if(pContainer->GetGroupData()->hMetaContact == NULL || m_bLongPress) {
+ if(((CListContainer<CContactListEntry*,CContactListGroup*>*)pEntry)->IsOpen())
+ SetButtonBitmap(3,IDB_MINUS);
+ else
+ SetButtonBitmap(3,IDB_PLUS);
+ } else {
+ SetButtonBitmap(3,IDB_CHAT);
+ }
+ }
+ else
+ {
+ SetButtonBitmap(3,IDB_CHAT);
+ }
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CContactlistScreen.h b/plugins/MirandaG15/src/CContactlistScreen.h
new file mode 100644
index 0000000000..3b9a5f6f95
--- /dev/null
+++ b/plugins/MirandaG15/src/CContactlistScreen.h
@@ -0,0 +1,62 @@
+#ifndef _CCONTACTLISTSCREEN_H_
+#define _CCONTACTLISTSCREEN_H_
+
+#include "CScreen.h"
+#include "CContactList.h"
+#include "CLCDBar.h"
+
+class CContactlistScreen : public CScreen
+{
+public:
+ // Constructor
+ CContactlistScreen();
+ // Destructor
+ ~CContactlistScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // resets the position of the contactlist
+ void ResetPosition();
+
+ // returns the online status of the specified contact
+ int GetContactStatus(HANDLE hContact);
+
+ // Called when a chat session was opened
+ void OnSessionOpened(HANDLE hContact);
+
+ // Called when the configuration has changed
+ void OnConfigChanged();
+ // Called when the screen size has changed
+ void OnSizeChanged();
+ // Called when an event is received
+ void OnEventReceived(CEvent *pEvent);
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+
+private:
+ // updates the use softkey label
+ void UpdateUseSoftkeyLabel();
+
+ CContactList m_ContactList;
+ CLCDBar m_Scrollbar;
+ bool m_bLongPress;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CCreditsScreen.cpp b/plugins/MirandaG15/src/CCreditsScreen.cpp
new file mode 100644
index 0000000000..5c3cd9669b
--- /dev/null
+++ b/plugins/MirandaG15/src/CCreditsScreen.cpp
@@ -0,0 +1,266 @@
+#include "stdafx.h"
+#include "CCreditsScreen.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CCreditsScreen::CCreditsScreen()
+{
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CCreditsScreen::~CCreditsScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CCreditsScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_Label.Initialize();
+
+ m_Label.SetAlignment(DT_CENTER);
+ m_Label.SetWordWrap(TRUE);
+ m_Label.SetText(_T(""));
+ m_Label.SetFontFaceName(_T("Microsoft Sans Serif"));
+ m_Label.SetFontPointSize(10);
+ m_Label.SetFontWeight(FW_BOLD);
+
+ m_Label2.Initialize();
+
+ AddObject(&m_Label);
+ AddObject(&m_Label2);
+ return true;
+}
+
+//************************************************************************
+// Shutdown the scren
+//************************************************************************
+bool CCreditsScreen::Shutdown()
+{
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CCreditsScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ DWORD dwTimeElapsed = GetTickCount() - m_dwActivation;
+ int iOldPosition = m_iPosition;
+
+ if(dwTimeElapsed > m_dwDuration)
+ {
+ m_dwDuration = 4000;
+ m_Label.SetText(_T(""));
+ m_Label2.SetText(_T(""));
+ switch(m_iPosition)
+ {
+ case 0:
+ m_Label.SetText(_T("MirandaG15"));
+ m_Label2.SetText(_T("2008 by Martin Kleinhans"));
+ m_dwDuration = 2500;
+ break;
+ case 1:
+ m_Label.SetSize(GetWidth(),GetHeight());
+ m_Label.SetText(_T("Special thanks to:"));
+ m_dwDuration = 2000;
+ break;
+ case 2:
+ m_Label.SetSize(GetWidth(),25);
+ m_Label.SetText(_T("Shere Khan\n"));
+ m_Label2.SetText(_T("Concept, Ideas, Testing"));
+ m_dwDuration = 2500;
+ break;
+ case 3:
+ m_Label.SetSize(GetWidth(),25);
+ m_Label.SetText(_T("Tauu and Cloonix\n"));
+ m_Label2.SetText(_T("Ideas, Testing"));
+ m_dwDuration = 2500;
+ break;
+ case 4:
+ m_Label.SetSize(GetWidth(),GetHeight());
+ m_Label.SetFontPointSize(10);
+ m_Label.SetFontWeight(FW_BOLD);
+ m_Label.SetText(_T("Betatesters:"));
+ m_dwDuration = 2000;
+ break;
+ case 5:
+ m_Label.SetSize(GetWidth(),25);
+ m_Label2.SetFontPointSize(10);
+ m_Label2.SetFontWeight(FW_BOLD);
+ m_Label.SetText(_T("Cyberz"));
+ m_Label2.SetText(_T("Cimlite"));
+ m_dwDuration = 2000;
+ break;
+ case 6:
+ m_Label.SetText(_T("Vullcan"));
+ m_Label2.SetText(_T("Snake"));
+ m_dwDuration = 2000;
+ break;
+ case 7:
+ m_Label.SetText(_T("Wiebbe"));
+ m_Label2.SetText(_T("Maluku"));
+ m_dwDuration = 2000;
+ break;
+ case 8:
+ m_Label.SetText(_T("lastwebpage"));
+ m_dwDuration = 2000;
+ break;
+ case 9:
+ m_Label.SetSize(GetWidth(),GetHeight());
+ m_Label.SetText(_T("Additional thanks to:"));
+ m_dwDuration = 2000;
+ break;
+ case 10:
+ m_Label.SetSize(GetWidth(),25);
+ m_Label2.SetFontPointSize(8);
+ m_Label2.SetFontWeight(FW_NORMAL);
+ m_Label.SetText(_T("Everyone"));
+ m_Label2.SetText(_T("on G15Forums.com"));
+ m_dwDuration = 2000;
+ break;
+ case 11:
+ m_Label.SetText(_T("Everyone else"));
+ m_Label2.SetText(_T("for feedback and suggestions"));
+ m_dwDuration = 2000;
+ break;
+ case 12:
+ m_Label.SetFontPointSize(10);
+ m_Label.SetFontWeight(FW_BOLD);
+ m_Label.SetSize(GetWidth(),25);
+ m_Label.SetText(_T("Logitech"));
+ m_Label2.SetText(_T("for obvious reasons"));
+ m_dwDuration = 2000;
+ break;
+ case 13:
+ m_Label.SetSize(GetWidth(),10);
+ m_Label.SetText(_T("You can contact me at:"));
+ m_Label2.SetSize(GetWidth(),33);
+ m_Label2.SetOrigin(0,10);
+ m_Label2.SetFontPointSize(8);
+ m_Label2.SetText(_T("mail@mkleinhans.de\nwww.mkleinhans.de"));
+ m_dwDuration = 2500;
+ break;
+ default:
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ return true;
+ }
+ m_iPosition++;
+ CAppletManager::GetInstance()->StartTransition(TRANSITION_MORPH);
+ }
+
+ if(m_iPosition != iOldPosition)
+ m_dwActivation = GetTickCount();
+ return true;
+}
+
+//************************************************************************
+// Resets the credits screens state
+//************************************************************************
+void CCreditsScreen::Reset()
+{
+ m_dwActivation = GetTickCount();
+ m_dwDuration = 0;
+
+ m_iPosition = 0;
+
+ CAppletManager::GetInstance()->GetLCDConnection()->SetAsForeground(true);
+
+ m_Label2.SetAlignment(DT_CENTER);
+ m_Label2.SetWordWrap(TRUE);
+ m_Label2.SetText(_T(""));
+ m_Label2.SetFontFaceName(_T("Microsoft Sans Serif"));
+ m_Label2.SetFontPointSize(8);
+
+ m_Label.SetOrigin(0,0);
+ m_Label.SetSize(GetWidth(),20);
+
+ m_Label2.SetOrigin(0,23);
+ m_Label2.SetSize(GetWidth(),20);
+}
+
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CCreditsScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CCreditsScreen::OnConfigChanged()
+{
+ CLCDScreen::OnSizeChanged();
+ CScreen::OnConfigChanged();
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CCreditsScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+}
+
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CCreditsScreen::OnLCDButtonDown(int iButton)
+{
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CCreditsScreen::OnLCDButtonRepeated(int iButton)
+{
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CCreditsScreen::OnLCDButtonUp(int iButton)
+{
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CCreditsScreen::OnActivation()
+{
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CCreditsScreen::OnDeactivation()
+{
+ CAppletManager::GetInstance()->GetLCDConnection()->SetAsForeground(false);
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CCreditsScreen::OnExpiration()
+{
+}
diff --git a/plugins/MirandaG15/src/CCreditsScreen.h b/plugins/MirandaG15/src/CCreditsScreen.h
new file mode 100644
index 0000000000..3873fc2c79
--- /dev/null
+++ b/plugins/MirandaG15/src/CCreditsScreen.h
@@ -0,0 +1,53 @@
+#ifndef _CCREDITSSCREEN_H_
+#define _CCREDITSSCREEN_H_
+
+#include "CScreen.h"
+#include "CLCDLabel.h"
+
+class CCreditsScreen : public CScreen
+{
+public:
+ // Constructor
+ CCreditsScreen();
+ // Destructor
+ ~CCreditsScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when the configuration has changed
+ void OnConfigChanged();
+ // Called when the screen size has changed
+ void OnSizeChanged();
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+
+ // Resets the credits screens state
+ void Reset();
+private:
+
+ CLCDLabel m_Label;
+ CLCDLabel m_Label2;
+
+ DWORD m_dwActivation;
+ DWORD m_dwDuration;
+ int m_iPosition;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CEvent.h b/plugins/MirandaG15/src/CEvent.h
new file mode 100644
index 0000000000..cf23af037e
--- /dev/null
+++ b/plugins/MirandaG15/src/CEvent.h
@@ -0,0 +1,71 @@
+#ifndef _CEVENT_H_
+#define _CEVENT_H_
+
+enum EventType { EVENT_MSG_RECEIVED = 0,
+ EVENT_MSG_SENT = 3,
+ EVENT_MESSAGE_ACK = 4,
+ EVENT_STATUS = 1,
+ EVENT_MSG_ACK = 2,
+
+ EVENT_URL = 5,
+ EVENT_FILE = 6,
+ EVENT_AUTHREQUEST = 7,
+ EVENT_CONTACTS = 8,
+ EVENT_ADDED = 9,
+
+ EVENT_CONTACT_ADDED = 10,
+ EVENT_CONTACT_DELETED = 11,
+ EVENT_CONTACT_NICK = 12,
+ EVENT_CONTACT_HIDDEN = 13,
+ EVENT_CONTACT_GROUP = 14,
+
+ EVENT_SIGNED_ON = 15,
+ EVENT_SIGNED_OFF = 16,
+
+ EVENT_PROTO_STATUS = 17,
+ EVENT_PROTO_CONNECTED = 18,
+ EVENT_PROTO_DISCONNECTED = 19,
+
+ EVENT_TYPING_NOTIFICATION = 20,
+ EVENT_MESSAGEWINDOW = 21,
+ EVENT_IRC_SENT = 22,
+ EVENT_IRC_RECEIVED = 23};
+
+#define MSG_READ 0
+#define MSG_UNREAD 1
+
+class CEvent
+{
+public:
+ CEvent()
+ {
+ bTime = false;
+ dwFlags = NULL;
+ hContact = NULL;
+ bNotification = false;
+ bLog = true;
+ strDescription = _T("");
+
+ iValue = NULL;
+ hValue = NULL;
+ strValue = _T("");
+ }
+
+ enum EventType eType;
+ DWORD dwFlags;
+ HANDLE hContact;
+ tm Time;
+ bool bTime;
+
+ bool bNotification;
+ bool bLog;
+
+ tstring strDescription;
+ tstring strSummary;
+
+ HANDLE hValue;
+ int iValue;
+ tstring strValue;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CEventLog.cpp b/plugins/MirandaG15/src/CEventLog.cpp
new file mode 100644
index 0000000000..dd82d923f4
--- /dev/null
+++ b/plugins/MirandaG15/src/CEventLog.cpp
@@ -0,0 +1,120 @@
+#include "stdafx.h"
+#include "CEventLog.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// constructor
+//************************************************************************
+CEventLog::CEventLog()
+{
+ m_dwLastScroll = 0;
+}
+
+//************************************************************************
+// destructor
+//************************************************************************
+CEventLog::~CEventLog()
+{
+
+}
+
+//************************************************************************
+// deinitializes the list
+//************************************************************************
+bool CEventLog::Shutdown()
+{
+ if(!CLCDList<CEventLogEntry*>::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// initializes the list
+//************************************************************************
+bool CEventLog::Initialize()
+{
+ if(!CLCDList<CEventLogEntry*>::Initialize())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Called to set the objects font
+//************************************************************************
+bool CEventLog::SetFont(LOGFONT &lf)
+{
+ if(!CLCDList<CEventLogEntry*>::SetFont(lf))
+ return false;
+
+ SetEntryHeight(m_iFontHeight<6?6:m_iFontHeight);
+
+ return true;
+}
+
+//************************************************************************
+// adds an entry to the list
+//************************************************************************
+CListItem<CEventLogEntry*> *CEventLog::AddItem(CEventLogEntry *pEntry)
+{
+ CListItem<CEventLogEntry*> *pItem = CLCDList<CEventLogEntry*>::AddItem(pEntry);
+ if(GetEntryCount() > CConfig::GetIntSetting(NOTIFY_LOGSIZE))
+ RemoveItem(((CListItem<CEventLogEntry*>*)GetFirstEntry())->GetItemData());
+
+ if(GetTickCount() - m_dwLastScroll > 10000)
+ SetPosition(pItem);
+ return pItem;
+}
+
+//************************************************************************
+// Called to delete the specified entry
+//************************************************************************
+void CEventLog::DeleteEntry(CEventLogEntry *pEntry)
+{
+ delete pEntry;
+}
+
+//************************************************************************
+// Called to draw the specified entry
+//************************************************************************
+void CEventLog::DrawEntry(CLCDGfx *pGfx,CEventLogEntry *pEntry,bool bSelected)
+{
+ SelectObject(pGfx->GetHDC(),m_hFont);
+
+ bool bLargeIcons = GetEntryHeight() > 8;
+ int iOffset = (m_iFontHeight-(bLargeIcons?8:6))/2;
+ HBITMAP hBitmap = CAppletManager::GetInstance()->GetEventBitmap(pEntry->eType,bLargeIcons);
+ pGfx->DrawBitmap(0,iOffset<0?0:iOffset,bLargeIcons?8:6,bLargeIcons?8:6,hBitmap);
+
+ iOffset = bLargeIcons?10:7;
+ if(CConfig::GetBoolSetting(NOTIFY_TIMESTAMPS))
+ pGfx->DrawText(iOffset,0,pGfx->GetClipWidth()-iOffset,pEntry->strTimestamp + pEntry->strValue);
+ else
+ pGfx->DrawText(iOffset,0,pGfx->GetClipWidth()-iOffset,pEntry->strValue);
+
+ if(bSelected && GetTickCount() - m_dwLastScroll < 1000)
+ {
+ RECT invert = { 0,0,GetWidth(),m_iFontHeight};
+ InvertRect(pGfx->GetHDC(),&invert);
+ }
+}
+
+
+void CEventLog::SetPosition(CListEntry<CEventLogEntry*> *pEntry)
+{
+ CLCDList<CEventLogEntry*>::SetPosition(pEntry);
+}
+
+bool CEventLog::ScrollUp()
+{
+ m_dwLastScroll = GetTickCount();
+ return CLCDList<CEventLogEntry*>::ScrollUp();
+}
+
+bool CEventLog::ScrollDown()
+{
+ m_dwLastScroll = GetTickCount();
+ return CLCDList<CEventLogEntry*>::ScrollDown();
+}
diff --git a/plugins/MirandaG15/src/CEventLog.h b/plugins/MirandaG15/src/CEventLog.h
new file mode 100644
index 0000000000..e5953f92c7
--- /dev/null
+++ b/plugins/MirandaG15/src/CEventLog.h
@@ -0,0 +1,46 @@
+#ifndef _CEVENTLOG_H_
+#define _CEVENTLOG_H_
+
+#include "CLCDList.h"
+
+class CEventLogEntry
+{
+public:
+ HANDLE hContact;
+ tstring strValue;
+ tstring strTimestamp;
+ tm Time;
+ EventType eType;
+};
+
+class CEventLog : public CLCDList<CEventLogEntry*>
+{
+public:
+ // constructor
+ CEventLog();
+ // destructor
+ ~CEventLog();
+
+ // initializes the list
+ bool Initialize();
+ // deinitializes the list
+ bool Shutdown();
+ // adds an entry to the list
+ CListItem<CEventLogEntry*> *AddItem(CEventLogEntry *);
+
+ void SetPosition(CListEntry<CEventLogEntry*> *pEntry);
+ bool ScrollUp();
+ bool ScrollDown();
+
+ bool SetFont(LOGFONT &lf);
+
+protected:
+ // Called to delete the specified entry
+ void DeleteEntry(CEventLogEntry *pEntry);
+ // Called to draw the specified entry
+ void DrawEntry(CLCDGfx *pGfx,CEventLogEntry *pEntry,bool bSelected);
+
+ DWORD m_dwLastScroll;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CEventScreen.cpp b/plugins/MirandaG15/src/CEventScreen.cpp
new file mode 100644
index 0000000000..cda38b07b4
--- /dev/null
+++ b/plugins/MirandaG15/src/CEventScreen.cpp
@@ -0,0 +1,239 @@
+#include "stdafx.h"
+#include "CEventScreen.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CEventScreen::CEventScreen()
+{
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CEventScreen::~CEventScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CEventScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_EventLog.Initialize();
+ m_EventLog.SetOrigin(0,0);
+ m_EventLog.SetSize(GetWidth()-5,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+ m_EventLog.SetFont(CConfig::GetFont(FONT_LOG));
+
+ AddObject(&m_EventLog);
+
+ m_Scrollbar.Initialize();
+ m_Scrollbar.SetOrigin(GetWidth()-4,0);
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+ m_EventLog.SetScrollbar(&m_Scrollbar);
+
+ AddObject(&m_Scrollbar);
+
+ SetButtonBitmap(0,IDB_UP);
+ SetButtonBitmap(1,IDB_DOWN);
+ SetButtonBitmap(2,IDB_CLIST);
+ SetButtonBitmap(3,NULL);
+
+ return true;
+}
+
+//************************************************************************
+// Shutdown the screen
+//************************************************************************
+bool CEventScreen::Shutdown()
+{
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CEventScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CEventScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CEventScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+
+ m_EventLog.SetFont(CConfig::GetFont(FONT_LOG));
+ m_EventLog.SetSize(GetWidth()-5,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+
+ m_Scrollbar.SetOrigin(GetWidth()-4,0);
+
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CEventScreen::OnConfigChanged()
+{
+ CScreen::OnConfigChanged();
+
+ m_EventLog.SetFont(CConfig::GetFont(FONT_LOG));
+ m_EventLog.SetSize(GetWidth()-5,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?6:0));
+
+ // Update all timestamps
+ list<CListEntry<CEventLogEntry*>*>::iterator iter = m_EventLog.begin();
+ CListItem<CEventLogEntry*> *pItem = NULL;
+ while(iter != m_EventLog.end())
+ {
+ pItem = static_cast<CListItem<CEventLogEntry*>*>(*iter);
+ pItem->GetItemData()->strTimestamp = CAppletManager::GetFormattedTimestamp(&pItem->GetItemData()->Time) + _T(" ");
+ iter++;
+ }
+
+ m_Scrollbar.SetSize(4,GetHeight()-(CConfig::GetBoolSetting(SHOW_LABELS)?5:0));
+}
+
+//************************************************************************
+// Called when an event is received
+//************************************************************************
+void CEventScreen::OnEventReceived(CEvent *pEvent)
+{
+ // check if the event needs to be listed
+ if(!pEvent->bLog)
+ return;
+
+ // create a list entry structure
+ CEventLogEntry *pEntry = new CEventLogEntry();
+ pEntry->hContact = pEvent->hContact;
+ pEntry->eType = pEvent->eType;
+
+ pEntry->Time = pEvent->Time;
+ pEntry->strTimestamp = CAppletManager::GetFormattedTimestamp(&pEvent->Time) + _T(" ");
+ pEntry->strValue = pEvent->strDescription;
+
+ // add it to the list and scroll to it
+ m_EventLog.AddItem(pEntry);
+
+ UpdateChatButton();
+}
+
+//************************************************************************
+// Updates the 4th softkey label
+//************************************************************************
+void CEventScreen::UpdateChatButton()
+{
+ CListEntry<CEventLogEntry*> *pItem = m_EventLog.GetSelectedEntry();
+ if(!pItem || pItem->GetType() != ITEM)
+ return;
+ CEventLogEntry *pEntry = ((CListItem<CEventLogEntry*>*)pItem)->GetItemData();
+ if(pEntry->hContact)
+ SetButtonBitmap(3,IDB_CHAT);
+ else
+ SetButtonBitmap(3,NULL);
+}
+
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CEventScreen::OnLCDButtonDown(int iButton)
+{
+ if(iButton == LGLCDBUTTON_CANCEL) {
+ CAppletManager::GetInstance()->ActivatePreviousScreen();
+ } else if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_EventLog.ScrollDown();
+ UpdateChatButton();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_EventLog.ScrollUp();
+ UpdateChatButton();
+ } else if(iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_MENU) {
+ CAppletManager::GetInstance()->ActivateCListScreen();
+ } else if(iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK)
+ {
+ CListEntry<CEventLogEntry*> *pItem = m_EventLog.GetSelectedEntry();
+ if(!pItem || pItem->GetType() != ITEM)
+ return;
+ CEventLogEntry *pEntry = ((CListItem<CEventLogEntry*>*)pItem)->GetItemData();
+
+ if(!pEntry->hContact)
+ return;
+
+ // if the contact is an irc chatroom, check if it is hidden (user left the channel)
+ char *szProto = (char *) CallService(MS_PROTO_GETCONTACTBASEPROTO, (WPARAM)pEntry->hContact, 0);
+ CIRCConnection *pIRCCon = CAppletManager::GetInstance()->GetIRCConnection(toTstring(szProto));
+
+ if(pIRCCon && db_get_b(pEntry->hContact, szProto, "ChatRoom", 0) != 0 &&
+ db_get_b((HANDLE)pEntry->hContact,"CList","Hidden",0))
+ return;
+
+ CAppletManager::GetInstance()->ActivateChatScreen(pEntry->hContact);
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CEventScreen::OnLCDButtonRepeated(int iButton)
+{
+ if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_EventLog.ScrollDown();
+ UpdateChatButton();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_EventLog.ScrollUp();
+ UpdateChatButton();
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CEventScreen::OnLCDButtonUp(int iButton)
+{
+
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CEventScreen::OnActivation()
+{
+
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CEventScreen::OnDeactivation()
+{
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CEventScreen::OnExpiration()
+{
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CEventScreen.h b/plugins/MirandaG15/src/CEventScreen.h
new file mode 100644
index 0000000000..e2eeccc24c
--- /dev/null
+++ b/plugins/MirandaG15/src/CEventScreen.h
@@ -0,0 +1,51 @@
+#ifndef _CEVENTSCREEN_H_
+#define _CEVENTSCREEN_H_
+
+#include "CScreen.h"
+#include "CEventLog.h"
+#include "CLCDBar.h"
+
+class CEventScreen : public CScreen
+{
+public:
+ // Constructor
+ CEventScreen();
+ // Destructor
+ ~CEventScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when the configuration has changed
+ void OnConfigChanged();
+ // Called when the screen size has changed
+ void OnSizeChanged();
+ // Called when an event is received
+ void OnEventReceived(CEvent *pEvent);
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+
+private:
+ void UpdateChatButton();
+
+ CEventLog m_EventLog;
+ CLCDBar m_Scrollbar;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CIRCConnection.h b/plugins/MirandaG15/src/CIRCConnection.h
new file mode 100644
index 0000000000..4067941cea
--- /dev/null
+++ b/plugins/MirandaG15/src/CIRCConnection.h
@@ -0,0 +1,12 @@
+#ifndef _CIRCCONNECTION_H_
+#define _CIRCCONNECTION_H_
+
+class CIRCConnection
+{
+public:
+ HANDLE hEventHook;
+ tstring strProtocol;
+ tstring strNetwork;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CIRCHistory.h b/plugins/MirandaG15/src/CIRCHistory.h
new file mode 100644
index 0000000000..299a80544b
--- /dev/null
+++ b/plugins/MirandaG15/src/CIRCHistory.h
@@ -0,0 +1,23 @@
+#ifndef _CIRCHISTORY_H_
+#define _CIRCHISTORY_H_
+
+struct SIRCMessage
+{
+ tm Time;
+ bool bIsMe;
+ tstring strMessage;
+};
+
+
+class CIRCHistory
+{
+public:
+ tstring strChannel;
+ tstring strProtocol;
+ HANDLE hContact;
+ list<SIRCMessage> LMessages;
+ list<tstring> LUsers;
+};
+
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CNotificationScreen.cpp b/plugins/MirandaG15/src/CNotificationScreen.cpp
new file mode 100644
index 0000000000..d950eccac8
--- /dev/null
+++ b/plugins/MirandaG15/src/CNotificationScreen.cpp
@@ -0,0 +1,374 @@
+#include "stdafx.h"
+#include "CNotificationScreen.h"
+#include "CConfig.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CNotificationScreen::CNotificationScreen()
+{
+ m_pEntry = NULL;
+ //m_bMessageMode = false;
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CNotificationScreen::~CNotificationScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CNotificationScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_EventText.Initialize();
+ m_MessageText.Initialize();
+ m_TitleText.Initialize();
+ m_Scrollbar.Initialize();
+ m_Timestamp.Initialize();
+ //m_Input.Initialize();
+ //m_Input.Show(0);
+
+ m_TitleText.SetText(_T("Miranda-IM"));
+ m_TitleText.SetAlignment(DT_LEFT);
+
+ m_Timestamp.SetAlignment(DT_RIGHT);
+
+ m_EventText.SetAlignment(DT_CENTER);
+ m_EventText.SetWordWrap(TRUE);
+
+ m_MessageText.SetScrollbar(&m_Scrollbar);
+
+ UpdateObjects();
+
+ AddObject(&m_Scrollbar);
+ AddObject(&m_EventText);
+ AddObject(&m_MessageText);
+ AddObject(&m_TitleText);
+ AddObject(&m_Timestamp);
+ //AddObject(&m_Input);
+
+ SetButtonBitmap(0,IDB_UP);
+ SetButtonBitmap(1,IDB_DOWN);
+
+ return true;
+}
+
+//************************************************************************
+// Shutdown the screen
+//************************************************************************
+bool CNotificationScreen::Shutdown()
+{
+ CNotificationEntry *pEntry = NULL;
+ while(!m_LNotifications.empty())
+ {
+ pEntry = *(m_LNotifications.begin());
+ m_LNotifications.pop_front();
+ delete pEntry;
+ }
+
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CNotificationScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CNotificationScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ if(CConfig::GetIntSetting(NOTIFY_TITLE) != NOTIFY_TITLE_HIDE)
+ {
+ int iTitleHeight = CConfig::GetFontHeight(FONT_TITLE);
+ pGfx->DrawLine(0,iTitleHeight < 7?7:iTitleHeight,GetWidth(),iTitleHeight < 7?7:iTitleHeight);
+ if(m_pEntry)
+ {
+ int iOffset = (iTitleHeight-(iTitleHeight>8?8:6))/2;
+ HBITMAP hBitmap = CAppletManager::GetInstance()->GetEventBitmap(m_pEntry->eType,iTitleHeight>8);
+ pGfx->DrawBitmap(0,iOffset,iTitleHeight>8?8:6,iTitleHeight>8?8:6,hBitmap);
+ }
+ }
+ return true;
+}
+
+//************************************************************************
+// displays the specified notification
+//************************************************************************
+void CNotificationScreen::DisplayNotification(CNotificationEntry *pEntry)
+{
+ if(m_pEntry != NULL)
+ delete m_pEntry;
+
+
+ tstring strTime = CAppletManager::GetFormattedTimestamp(&pEntry->Time);
+
+ m_pEntry = pEntry;
+ if(CConfig::GetIntSetting(NOTIFY_TITLE) == NOTIFY_TITLE_NAME || pEntry->strTitle.empty())
+ m_TitleText.SetText(_T("Miranda-IM"));
+ else
+ m_TitleText.SetText(pEntry->strTitle);
+
+ if(CConfig::GetBoolSetting(NOTIFY_TIMESTAMPS))
+ m_Timestamp.SetText(strTime);
+ else
+ m_Timestamp.SetText(_T(""));
+
+
+ if(pEntry->hContact)
+ SetButtonBitmap(3,IDB_CHAT);
+ else
+ SetButtonBitmap(3,NULL);
+
+ if(pEntry->bMessage)
+ {
+ SetButtonBitmap(0,IDB_UP);
+ SetButtonBitmap(1,IDB_DOWN);
+
+ m_MessageText.Show(1);
+ m_Scrollbar.Show(1);
+ m_EventText.Show(0);
+ m_MessageText.SetText(pEntry->strText.c_str());
+ }
+ else
+ {
+ SetButtonBitmap(0,NULL);
+ SetButtonBitmap(1,NULL);
+
+ m_Scrollbar.Show(0);
+ m_MessageText.Show(0);
+ m_EventText.Show(1);
+ m_EventText.SetText(pEntry->strText.c_str());
+ }
+}
+
+//************************************************************************
+// updates all objects
+//************************************************************************
+void CNotificationScreen::UpdateObjects()
+{
+ int iHeight = GetHeight() - (CConfig::GetBoolSetting(SHOW_LABELS)?6:0);
+ int iOrigin = 0;
+
+ if(CConfig::GetIntSetting(NOTIFY_TITLE) == NOTIFY_TITLE_HIDE)
+ {
+ m_TitleText.Show(false);
+ m_Timestamp.Show(false);
+ }
+ else
+ {
+ iOrigin = CConfig::GetFontHeight(FONT_TITLE);
+ iHeight -= iOrigin;
+ m_Timestamp.Show(true);
+ m_TitleText.Show(true);
+ }
+
+
+ m_MessageText.SetFont(CConfig::GetFont(FONT_NOTIFICATION));
+ m_TitleText.SetFont(CConfig::GetFont(FONT_TITLE));
+ m_EventText.SetFont(CConfig::GetFont(FONT_NOTIFICATION));
+ m_Timestamp.SetFont(CConfig::GetFont(FONT_TITLE));
+
+ m_Timestamp.SetSize((GetWidth()/3),CConfig::GetFontHeight(FONT_TITLE));
+ m_Timestamp.SetOrigin((GetWidth()/3)*2,0);
+
+ m_TitleText.SetSize(((GetWidth()/3)*2) -5,CConfig::GetFontHeight(FONT_TITLE));
+ m_TitleText.SetOrigin(9,0);
+
+ m_EventText.SetOrigin(0,iOrigin + 1);
+ m_EventText.SetSize(GetWidth()-4, iHeight);
+
+ m_MessageText.SetOrigin(0, iOrigin+1);
+ m_MessageText.SetSize(GetWidth()-4, iHeight);
+
+ //m_Input.SetOrigin(0, iOrigin+1);
+ //m_Input.SetSize(GetWidth()-4, iHeight);
+
+ m_Scrollbar.SetOrigin(GetWidth()-4,iOrigin+1);
+ m_Scrollbar.SetSize(4,iHeight);
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CNotificationScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+
+ UpdateObjects();
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CNotificationScreen::OnConfigChanged()
+{
+ CScreen::OnConfigChanged();
+
+ UpdateObjects();
+}
+
+//************************************************************************
+// Called when an event is received
+//************************************************************************
+void CNotificationScreen::OnEventReceived(CEvent *pEvent)
+{
+ // check wether this events needs notification
+ if(!pEvent->bNotification)
+ return;
+
+ CNotificationEntry *pEntry = new CNotificationEntry();
+ pEntry->eType = pEvent->eType;
+ pEntry->strTitle = pEvent->strSummary;
+ if(pEvent->eType == EVENT_MSG_RECEIVED ||
+ (pEvent->eType == EVENT_IRC_RECEIVED && (pEvent->iValue == GC_EVENT_MESSAGE || pEvent->iValue == GC_EVENT_NOTICE)))
+ {
+ pEntry->bMessage = true;
+ tstring strUser = CAppletManager::GetContactDisplayname(pEvent->hContact);
+
+ if(CConfig::GetIntSetting(NOTIFY_TITLE) == NOTIFY_TITLE_INFO)
+ pEntry->strText = pEvent->strValue;
+ else
+ pEntry->strText = strUser + (pEvent->eType == EVENT_IRC_RECEIVED?_T(" - "):_T(": "))+ pEvent->strValue;
+ }
+ else
+ {
+ pEntry->bMessage = false;
+ if(CConfig::GetIntSetting(NOTIFY_TITLE) == NOTIFY_TITLE_INFO && pEvent->eType == EVENT_IRC_RECEIVED )
+ pEntry->strText = pEvent->strValue;
+ else
+ pEntry->strText = pEvent->strDescription;
+ }
+
+ pEntry->hContact = pEvent->hContact;
+ pEntry->Time = pEvent->Time;
+
+ if(m_pEntry)
+ {
+ m_LNotifications.push_back(pEntry);
+ SetButtonBitmap(2,IDB_NEXT);
+ }
+ else
+ {
+ DisplayNotification(pEntry);
+ SetButtonBitmap(2,NULL);
+ }
+}
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CNotificationScreen::OnLCDButtonDown(int iButton)
+{
+ CScreen::OnLCDButtonDown(iButton);
+
+ if((iButton == LGLCDBUTTON_BUTTON2 || iButton == LGLCDBUTTON_RIGHT) && m_LNotifications.size() >= 1)
+ {
+ CNotificationEntry *pEntry = *(m_LNotifications.begin());
+ m_LNotifications.pop_front();
+
+ if(m_LNotifications.size() >= 1)
+ SetButtonBitmap(2,IDB_NEXT);
+ else
+ SetButtonBitmap(2,NULL);
+
+ DisplayNotification(pEntry);
+ SetExpiration(CConfig::GetIntSetting(NOTIFY_DURATION)*1000);
+ }
+ else if((iButton == LGLCDBUTTON_BUTTON3 || iButton == LGLCDBUTTON_OK) && m_pEntry && m_pEntry->hContact)
+ {
+ SetExpiration(0);
+
+ CLCDConnection *pLCDCon = CAppletManager::GetInstance()->GetLCDConnection();
+ pLCDCon->SetAsForeground(1);
+ pLCDCon->SetAsForeground(0);
+ CAppletManager::GetInstance()->ActivateChatScreen(m_pEntry->hContact);
+ } else if(!m_MessageText.IsVisible()) {
+ SetExpiration(0);
+ } else {
+ if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_MessageText.ScrollDown();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_MessageText.ScrollUp();
+ }
+ SetExpiration(CConfig::GetIntSetting(NOTIFY_DURATION)*1000);
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CNotificationScreen::OnLCDButtonRepeated(int iButton)
+{
+ CScreen::OnLCDButtonDown(iButton);
+ if(m_MessageText.IsVisible()) {
+ if(iButton == LGLCDBUTTON_BUTTON1 || iButton == LGLCDBUTTON_DOWN) {
+ m_MessageText.ScrollDown();
+ } else if(iButton == LGLCDBUTTON_BUTTON0 || iButton == LGLCDBUTTON_UP) {
+ m_MessageText.ScrollUp();
+ }
+ SetExpiration(CConfig::GetIntSetting(NOTIFY_DURATION)*1000);
+ }
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CNotificationScreen::OnLCDButtonUp(int iButton)
+{
+
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CNotificationScreen::OnActivation()
+{
+
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CNotificationScreen::OnDeactivation()
+{
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CNotificationScreen::OnExpiration()
+{
+ // clear the cached events
+ CNotificationEntry *pEntry = NULL;
+ while(!m_LNotifications.empty())
+ {
+ pEntry = *(m_LNotifications.begin());
+ m_LNotifications.pop_front();
+ delete pEntry;
+ }
+ // reset the object's content
+ m_EventText.SetText(_T(""));
+ m_MessageText.SetText(_T(""));
+
+ m_pEntry = NULL;
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CNotificationScreen.h b/plugins/MirandaG15/src/CNotificationScreen.h
new file mode 100644
index 0000000000..837398238a
--- /dev/null
+++ b/plugins/MirandaG15/src/CNotificationScreen.h
@@ -0,0 +1,95 @@
+#ifndef _CNOTIFICATIONSCREEN_H_
+#define _CNOTIFICATIONSCREEN_H_
+
+#include "CScreen.h"
+#include "CLCDLabel.h"
+#include "CLCDTextLog.h"
+#include "CLCDBar.h"
+#include "CLCDInput.h"
+
+class CNotificationEntry
+{
+public:
+ bool bMessage;
+ tm Time;
+ tstring strText;
+ tstring strTitle;
+ HANDLE hContact;
+ EventType eType;
+};
+
+class CNotificationScreen : public CScreen
+{
+public:
+ // Constructor
+ CNotificationScreen();
+ // Destructor
+ ~CNotificationScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when the screen size has changed
+ void OnSizeChanged();
+ // Called when the configuration has changed
+ void OnConfigChanged();
+ // Called when an event is received
+ void OnEventReceived(CEvent *pEvent);
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+private:
+ /*
+ // activates the input box
+ void ActivateMessageMode();
+ // deactivates the input box
+ void DeactivateMessageMode();
+ // sends the message
+ void SendCurrentMessage();
+ // invalidates the message
+ void InvalidateMessageMode(tstring strMessage);
+ */
+
+ // displays the specified notification
+ void DisplayNotification(CNotificationEntry *pEntry);
+ // updates all objects
+ void UpdateObjects();
+
+ // cached notifications
+ list<CNotificationEntry*> m_LNotifications;
+
+ // objects
+ CLCDLabel m_EventText;
+ CLCDTextLog m_MessageText;
+ CLCDLabel m_TitleText;
+ CLCDLabel m_Timestamp;
+ CLCDBar m_Scrollbar;
+ //CLCDInput m_Input;
+
+ // Contact off the current event
+ CNotificationEntry *m_pEntry;
+
+ // message mode variables
+ /*
+ bool m_bMessageMode;
+ enum { REPLY_STATE_NONE,REPLY_STATE_INPUT,REPLY_STATE_SENDING,REPLY_STATE_FAILED} m_eReplyState;
+ HANDLE m_hMessage;
+ */
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CProtocolData.h b/plugins/MirandaG15/src/CProtocolData.h
new file mode 100644
index 0000000000..cd2282377d
--- /dev/null
+++ b/plugins/MirandaG15/src/CProtocolData.h
@@ -0,0 +1,13 @@
+#ifndef _CPROTOCLDATA_H_INCLUDED_
+#define _CPROTOCLDATA_H_INCLUDED_
+
+class CProtocolData
+{
+public:
+ tstring strProtocol;
+ int iStatus;
+ int iDesiredStatus;
+ long lTimeStamp;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CScreen.cpp b/plugins/MirandaG15/src/CScreen.cpp
new file mode 100644
index 0000000000..1759fa9686
--- /dev/null
+++ b/plugins/MirandaG15/src/CScreen.cpp
@@ -0,0 +1,180 @@
+#include "stdafx.h"
+#include "CScreen.h"
+#include "CConfig.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CScreen::CScreen()
+{
+ m_bHideButtons = false;
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CScreen::~CScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CScreen::Initialize()
+{
+ if(!CLCDScreen::Initialize())
+ return false;
+
+ // initialize the four button labels
+ for (int i = 0; i < 4; i++)
+ {
+ m_aButtons[i].Initialize();
+ m_aButtons[i].SetSize(17, 3);
+ m_aButtons[i].Show(0);
+ m_abShowButtons[i] = false;
+ m_ahBitmaps[i] = NULL;
+ if(GetWidth() == 160) {
+ m_aButtons[i].SetOrigin(10+i*29+(i/2)*36, GetHeight()-3);
+ } else {
+ m_aButtons[i].SetOrigin((280/4)*(i+0.5f) + (i/2)*40, GetHeight()-3);
+ }
+ AddObject(&m_aButtons[i]);
+ }
+
+ /*
+ m_Clock.Initialize();
+
+ m_Clock.SetOrigin(68,0);
+ m_Clock.SetSize(40,2);
+ m_Clock.SetText(_T("23:00 - "));
+
+ m_Clock.SetFontFaceName(_T("Small Fonts"));//Digital Limit 3õ3 C"));
+ m_Clock.SetFontPointSize(10);
+ //m_Clock.SetFont(CConfig::GetFont(FONT_CLIST));
+
+ AddObject(&m_Clock);
+ */
+ return true;
+}
+
+//************************************************************************
+// Shutdown the scren
+//************************************************************************
+bool CScreen::Shutdown()
+{
+ if(!CLCDScreen::Shutdown())
+ return false;
+
+ for(int i=0; i < 4; i++)
+ if(m_ahBitmaps[i] != NULL)
+ DeleteObject(m_ahBitmaps[i]);
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CScreen::Update()
+{
+ if(!CLCDScreen::Update())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CLCDScreen::Draw(pGfx))
+ return false;
+
+ for(int i=0;i<4;i++)
+ if(m_aButtons[i].IsVisible())
+ {
+ pGfx->DrawLine(0,GetHeight()-5,GetWidth(),GetHeight()-5);
+ break;
+ }
+
+ return true;
+}
+
+//************************************************************************
+// Set the specified button label
+//************************************************************************
+void CScreen::SetButtonBitmap(int iButton, int iBitmap)
+{
+ if(iButton <0 || iButton > 3)
+ return;
+ if(iBitmap == 0)
+ {
+ m_aButtons[iButton].Show(0);
+ m_abShowButtons[iButton] = false;
+ }
+ else
+ {
+ if(m_ahBitmaps[iButton] != NULL)
+ DeleteObject(m_ahBitmaps[iButton]);
+
+ m_ahBitmaps[iButton] = (HBITMAP)LoadImage(hInstance, MAKEINTRESOURCE(iBitmap),
+ IMAGE_BITMAP,17, 3, LR_MONOCHROME);
+ m_aButtons[iButton].SetBitmap(m_ahBitmaps[iButton]);
+
+ if(CConfig::GetBoolSetting(SHOW_LABELS))
+ m_aButtons[iButton].Show(1);
+ m_abShowButtons[iButton] = true;
+ }
+}
+
+//************************************************************************
+// shows/hides the buttons
+//************************************************************************
+void CScreen::ShowButtons(bool bShow)
+{
+ m_bHideButtons = !bShow;
+ UpdateButtons();
+}
+
+//************************************************************************
+// Update the buttons
+//************************************************************************
+void CScreen::UpdateButtons()
+{
+ for (int i = 0; i < 4; i++)
+ {
+ if(GetWidth() == 160) {
+ m_aButtons[i].SetOrigin(10+i*29+(i/2)*36, GetHeight()-3);
+ } else {
+ m_aButtons[i].SetOrigin((280/4)*(i+0.5f) + (i/2)*40, GetHeight()-3);
+ }
+
+ if(m_abShowButtons[i])
+ m_aButtons[i].Show(CConfig::GetBoolSetting(SHOW_LABELS) && !m_bHideButtons);
+ }
+}
+
+//************************************************************************
+// Called when an event is received
+//************************************************************************
+void CScreen::OnEventReceived(CEvent *pEvent)
+{
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CScreen::OnConfigChanged()
+{
+ UpdateButtons();
+}
+
+//************************************************************************
+// Called when the screens size has changed
+//************************************************************************
+void CScreen::OnSizeChanged() {
+ CLCDScreen::OnSizeChanged();
+
+ UpdateButtons();
+} \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CScreen.h b/plugins/MirandaG15/src/CScreen.h
new file mode 100644
index 0000000000..53b05a96e3
--- /dev/null
+++ b/plugins/MirandaG15/src/CScreen.h
@@ -0,0 +1,47 @@
+#ifndef _CSCREEN_H_
+#define _CSCREEN_H_
+
+#include "CLCDScreen.h"
+#include "CLCDBitmap.h"
+//#include "CLCDLabel.h"
+
+class CScreen : public CLCDScreen
+{
+public:
+ // Constructor
+ CScreen();
+ // Destructor
+ ~CScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when an event is received
+ virtual void OnEventReceived(CEvent *pEvent);
+ // Called when the configuration has changed
+ virtual void OnConfigChanged();
+ // Called when the screens size has changed
+ virtual void OnSizeChanged();
+protected:
+ // Set the specified button label
+ void SetButtonBitmap(int iButton, int iBitmap);
+ // Hide/Show the buttons
+ void ShowButtons(bool bShow);
+private:
+ //CLCDLabel m_Clock;
+
+ CLCDBitmap m_aButtons[4];
+ HBITMAP m_ahBitmaps[4];
+ bool m_abShowButtons[4];
+ bool m_bHideButtons;
+
+ void UpdateButtons();
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/CScreensaverScreen.cpp b/plugins/MirandaG15/src/CScreensaverScreen.cpp
new file mode 100644
index 0000000000..6c8a915a49
--- /dev/null
+++ b/plugins/MirandaG15/src/CScreensaverScreen.cpp
@@ -0,0 +1,200 @@
+#include "stdafx.h"
+#include "CScreensaverScreen.h"
+#include "CAppletManager.h"
+
+//************************************************************************
+// Constructor
+//************************************************************************
+CScreensaverScreen::CScreensaverScreen()
+{
+}
+
+//************************************************************************
+// Destructor
+//************************************************************************
+CScreensaverScreen::~CScreensaverScreen()
+{
+}
+
+//************************************************************************
+// Initializes the screen
+//************************************************************************
+bool CScreensaverScreen::Initialize()
+{
+ if(!CScreen::Initialize())
+ return false;
+
+ m_Label.Initialize();
+ m_Label2.Initialize();
+
+ m_Label.SetAlignment(DT_CENTER);
+ m_Label.SetWordWrap(TRUE);
+ m_Label.SetText(_T("Screensaver is active"));
+ m_Label.SetFontFaceName(_T("Microsoft Sans Serif"));
+ m_Label.SetFontPointSize(10);
+ m_Label.SetFontWeight(FW_BOLD);
+
+ m_Label2.SetAlignment(DT_CENTER);
+ m_Label2.SetWordWrap(TRUE);
+ m_Label2.SetText(_T(""));
+ m_Label2.SetFontFaceName(_T("Microsoft Sans Serif"));
+ m_Label2.SetFontPointSize(8);
+
+ m_Label.SetOrigin(0,0);
+ m_Label.SetSize(GetWidth(),20);
+
+ m_Label2.SetOrigin(0,23);
+ m_Label2.SetSize(GetWidth(),20);
+
+
+
+ AddObject(&m_Label);
+ AddObject(&m_Label2);
+
+ return true;
+}
+
+//************************************************************************
+// Shutdown the scren
+//************************************************************************
+bool CScreensaverScreen::Shutdown()
+{
+ if(!CScreen::Shutdown())
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Updates the screen
+//************************************************************************
+bool CScreensaverScreen::Update()
+{
+ if(!CScreen::Update())
+ return false;
+
+ DWORD dwTimeElapsed = GetTickCount() - m_dwActivation;
+ int iOldPosition = m_iPosition;
+
+ if(dwTimeElapsed > m_dwDuration)
+ {
+ m_dwDuration = 4000;
+ m_Label.SetText(_T(""));
+ m_Label2.SetText(_T(""));
+ switch(m_iPosition)
+ {
+ case 0:
+ m_Label.SetFontPointSize(8);
+ m_Label.SetText(_T("MirandaG15"));
+ m_Label2.SetText(_T("Screensaver is active"));
+ m_dwDuration = 1800;
+ break;
+ case 1:
+ m_Label.SetFontPointSize(11);
+ m_Label.SetText(_T("MirandaG15"));
+ m_Label2.SetText(_T("Applet locked"));
+ m_dwDuration = 1800;
+ m_iPosition = -1;
+ break;
+
+ default:
+ CAppletManager::GetInstance()->ActivateEventScreen();
+ return true;
+ }
+ m_iPosition++;
+ CAppletManager::GetInstance()->StartTransition(TRANSITION_MORPH);
+ }
+
+ if(m_iPosition != iOldPosition)
+ m_dwActivation = GetTickCount();
+
+ return true;
+}
+
+//************************************************************************
+// Resets the credits screens state
+//************************************************************************
+void CScreensaverScreen::Reset()
+{
+ m_dwDuration = 0;
+ m_iPosition = 0;
+
+ m_Label.SetFontPointSize(10);
+
+ m_Label.SetText(_T(""));
+ m_Label2.SetText(_T(""));
+
+ CAppletManager::GetInstance()->GetLCDConnection()->SetAsForeground(true);
+}
+
+
+//************************************************************************
+// Draws the screen
+//************************************************************************
+bool CScreensaverScreen::Draw(CLCDGfx *pGfx)
+{
+ if(!CScreen::Draw(pGfx))
+ return false;
+
+ return true;
+}
+
+//************************************************************************
+// Called when the configuration has changed
+//************************************************************************
+void CScreensaverScreen::OnConfigChanged()
+{
+ CScreen::OnConfigChanged();
+}
+
+//************************************************************************
+// Called when the screen size has changed
+//************************************************************************
+void CScreensaverScreen::OnSizeChanged()
+{
+ CScreen::OnSizeChanged();
+}
+
+//************************************************************************
+// Called when an LCD-button is pressed
+//************************************************************************
+void CScreensaverScreen::OnLCDButtonDown(int iButton)
+{
+}
+
+//************************************************************************
+// Called when an LCD-button event is repeated
+//************************************************************************
+void CScreensaverScreen::OnLCDButtonRepeated(int iButton)
+{
+}
+
+//************************************************************************
+// Called when an LCD-button is released
+//************************************************************************
+void CScreensaverScreen::OnLCDButtonUp(int iButton)
+{
+}
+
+//************************************************************************
+// Called when the screen is activated
+//************************************************************************
+void CScreensaverScreen::OnActivation()
+{
+}
+
+//************************************************************************
+// Called when the screen is deactivated
+//************************************************************************
+void CScreensaverScreen::OnDeactivation()
+{
+ CAppletManager::GetInstance()->GetLCDConnection()->SetAsForeground(false);
+ CAppletManager::GetInstance()->StartTransition(TRANSITION_MORPH);
+}
+
+//************************************************************************
+// Called when the screen has expired
+//************************************************************************
+void CScreensaverScreen::OnExpiration()
+{
+}
diff --git a/plugins/MirandaG15/src/CScreensaverScreen.h b/plugins/MirandaG15/src/CScreensaverScreen.h
new file mode 100644
index 0000000000..19592a204b
--- /dev/null
+++ b/plugins/MirandaG15/src/CScreensaverScreen.h
@@ -0,0 +1,51 @@
+#ifndef _CSCREENSAVERSSCREEN_H_
+#define _CSCREENSAVERSSCREEN_H_
+
+#include "CScreen.h"
+#include "CLCDLabel.h"
+
+class CScreensaverScreen : public CScreen
+{
+public:
+ // Constructor
+ CScreensaverScreen();
+ // Destructor
+ ~CScreensaverScreen();
+
+ // Initializes the screen
+ bool Initialize();
+ // Shutdown the scren
+ bool Shutdown();
+ // Updates the screen
+ bool Update();
+ // Draws the screen
+ bool Draw(CLCDGfx *pGfx);
+
+ // Called when the configuration has changed
+ void OnConfigChanged();
+ // Called when the screen size has changed
+ void OnSizeChanged();
+ // Called when an LCD-button is pressed
+ void OnLCDButtonDown(int iButton);
+ // Called when an LCD-button event is repeated
+ void OnLCDButtonRepeated(int iButton);
+ // Called when an LCD-button is released
+ void OnLCDButtonUp(int iButton);
+ // Called when the screen is activated
+ void OnActivation();
+ // Called when the screen is deactivated
+ void OnDeactivation();
+ // Called when the screen has expired
+ void OnExpiration();
+
+ // Resets the credits screens state
+ void Reset();
+private:
+
+ CLCDLabel m_Label,m_Label2;
+ DWORD m_dwActivation;
+ DWORD m_dwDuration;
+ int m_iPosition;
+};
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/Miranda.cpp b/plugins/MirandaG15/src/Miranda.cpp
new file mode 100644
index 0000000000..6776c397ef
--- /dev/null
+++ b/plugins/MirandaG15/src/Miranda.cpp
@@ -0,0 +1,223 @@
+
+/*
+ * Miranda IM LCD Plugin
+ * Displays incoming text messages on an LCD.
+ *
+ * Copyright (c) 2003 Martin Rubli, mrubli@gmx.net
+ *
+ ******************************************************************************
+ * This file is part of Miranda IM LCD Plugin.
+ *
+ * Miranda IM LCD Plugin 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 2 of the License, or (at
+ * your option) any later version.
+ *
+ * Miranda IM LCD Plugin 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.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with Miranda IM LCD Plugin; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ ******************************************************************************
+ *
+ * Miranda.cpp: Miranda plugin initialisation
+ */
+
+/*
+ * TODO:
+
+*/
+/*
+ * CHANGES:
+ */
+/*
+ * KNOWN BUGS:
+ *
+ */
+
+/*
+ * IDEAS:
+ *
+ */
+
+#ifdef _DEBUG
+ #include <crtdbg.h>
+ #define _CRTDBG_MAP_ALLOC
+#endif
+
+#include "StdAfx.h"
+
+#include "CAppletManager.h"
+#include "CConfig.h"
+
+#include "m_system.h"
+
+// SETTINGS
+#define LCD_FPS 10
+
+//************************************************************************
+// Variables
+//************************************************************************
+bool g_bInitialized;
+bool g_bUnicode;
+// AppletManager object
+ CAppletManager* g_AppletManager;
+
+// Plugin Information
+
+HINSTANCE hInstance;
+int hLangpack;
+
+// Initialization Hook
+static HANDLE hMIHookModulesLoaded;
+
+// {58D63981-14C1-4099-A3F7-F4FAA4C8FC59}
+#define MIID_G15APPLET { 0x58d63981, 0x14c1, 0x4099, { 0xa3, 0xf7, 0xf4, 0xfa, 0xa4, 0xc8, 0xfc, 0x59 } }
+
+static const MUUID interfaces[] = {MIID_G15APPLET, MIID_LAST};
+
+static PLUGININFOEX pluginInfo = {
+ sizeof(PLUGININFOEX),
+ APP_NAME,
+ PLUGIN_MAKE_VERSION(0,1,2,0),
+ "Provides an interface to use Miranda from the LCD of various Logitech devices",
+ "Martin Kleinhans",
+ "mail@mkleinhans.de",
+ "© 2009 Martin Kleinhans",
+ "http://www.mkleinhans.de",
+ 0, // not transient
+ // {798221E1-E47A-4dc8-9077-1E576F9C4307}
+ { 0x798221e1, 0xe47a, 0x4dc8, { 0x90, 0x77, 0x1e, 0x57, 0x6f, 0x9c, 0x43, 0x7 } }
+};
+
+// Function Prototypes
+int Init(WPARAM,LPARAM);
+void UnInit();
+
+
+
+//************************************************************************
+// Exported Functions
+//************************************************************************
+extern "C" {
+ __declspec(dllexport) const MUUID * MirandaPluginInterfaces(void)
+ {
+ return interfaces;
+ }
+
+ __declspec(dllexport) PLUGININFOEX* MirandaPluginInfoEx(DWORD mirandaVersion)
+ {
+ // Are we running under Unicode Windows version ?
+ g_bUnicode = (GetVersion() & 0x80000000) == 0;
+ if (g_bUnicode) {
+ pluginInfo.flags = 1; // UNICODE_AWARE
+ }
+ return &pluginInfo;
+ }
+
+
+ // Called by Miranda to load the plugin.
+ // We defer initialization until Miranda's module loading process completed and return 0 to
+ // mark success, everything else will cause the plugin to be freed right away.
+ int __declspec(dllexport) Load()
+ {
+ g_bInitialized = false;
+ InitDebug();
+ TRACE(_T("Plugin loaded\n"));
+ // Schedule actual initialization for later
+ // (We don't really need the handle but want to be able to release it properly later ...)
+ hMIHookModulesLoaded = HookEvent(ME_SYSTEM_MODULESLOADED, Init);
+ if(hMIHookModulesLoaded == 0)
+ {
+ tstring text = _T("Failed to initialize the Applet.\nThe plugin will not be loaded. ");
+ tstring title = _T(APP_SHORTNAME);
+ MessageBox(NULL, text.c_str(), title.c_str(), MB_OK | MB_ICONEXCLAMATION);
+ return 1;
+ }
+ return 0;
+ }
+
+ // Called by Miranda when the plugin should unload itself.
+ int __declspec(dllexport) Unload(void)
+ {
+ if(!g_bInitialized) {
+ TRACE(_T("ERROR: Unload requested, but plugin is not initialized?!\n"));
+ return 0;
+ }
+ TRACE(_T("-------------------------------------------\nUnloading started\n"));
+ UnInit();
+ TRACE(_T("Unloading successful\n"));
+ TRACE(_T("Cleaning up: "));
+ UnhookEvent(hMIHookModulesLoaded); // just to be really correct ...
+ UnInitDebug();
+ TRACE(_T("OK!\n"));
+ return 0;
+ }
+}
+
+//************************************************************************
+// DllMain
+//
+// EntryPoint of the DLL
+//************************************************************************
+BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
+{
+
+ hInstance = hinstDLL;
+ return TRUE;
+}
+
+//************************************************************************
+// Init
+//
+// Called after Miranda has finished loading all modules
+// This is where the main plugin initialization happens and the
+// connection to the LCD is established,
+//************************************************************************
+int Init(WPARAM wParam,LPARAM lParam)
+{
+ g_AppletManager = new CAppletManager();
+ // Memoryleak Detection
+ #ifdef _DEBUG
+ _CrtSetDbgFlag( _CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
+
+ #endif
+
+ // set up the LCD context as non-autostart, non-persist, callbacked
+ CConfig::Initialize();
+
+ // Initialize the output object
+ if(!g_AppletManager->Initialize(toTstring(APP_SHORTNAME)))
+ {
+ if(CConfig::GetBoolSetting(SKIP_DRIVER_ERROR)) {
+ tstring text = _T("Failed to initialize the LCD connection\n Make sure you have the newest Logitech drivers installed (>=1.03).\n");
+ tstring title = _T(APP_SHORTNAME);
+ MessageBox(NULL, text.c_str(), title.c_str(), MB_OK | MB_ICONEXCLAMATION);
+ }
+
+ TRACE(_T("Initialization failed!.\n"));
+ return 0;
+ }
+
+ g_bInitialized = true;
+ TRACE(_T("Initialization completed successfully.\n-------------------------------------------\n"));
+ return 0;
+}
+//************************************************************************
+// UnInit
+//
+// Called when the plugin is about to be unloaded
+//************************************************************************
+void UnInit(void)
+{
+ g_AppletManager->Shutdown();
+ delete g_AppletManager;
+ UnhookEvent(hMIHookModulesLoaded);
+
+//#ifdef _DEBUG
+// _CrtDumpMemoryLeaks();
+//#endif
+}
diff --git a/plugins/MirandaG15/src/Miranda.h b/plugins/MirandaG15/src/Miranda.h
new file mode 100644
index 0000000000..851da133cb
--- /dev/null
+++ b/plugins/MirandaG15/src/Miranda.h
@@ -0,0 +1,4 @@
+extern HINSTANCE hInstance;
+extern char *MsgServiceName(HANDLE hContact,bool bIsUnicode);
+extern bool g_bUnicode;
+
diff --git a/plugins/MirandaG15/src/StdAfx.h b/plugins/MirandaG15/src/StdAfx.h
new file mode 100644
index 0000000000..c03f576c95
--- /dev/null
+++ b/plugins/MirandaG15/src/StdAfx.h
@@ -0,0 +1,53 @@
+#ifndef _STDAFX_H_
+#define _STDAFX_H_
+
+#define APP_NAME "MirandaG15"
+#define APP_SHORTNAME "MirandaG15"
+
+/* Common header files */
+#include <assert.h>
+
+#define _WIN32_WINNT 0x0500 // Needed for waitable timers
+#include <Windows.h>
+#include <CommCtrl.h>
+#include <tchar.h>
+#include <time.h>
+#include <string>
+#include <vector>
+#include <queue>
+#include <list>
+
+using namespace std;
+
+#include <newpluginapi.h>
+
+#include <m_message.h>
+#include <m_protomod.h>
+#include <m_protosvc.h>
+#include <m_database.h>
+#include <m_options.h>
+#include <m_clist.h>
+#include <m_protocols.h>
+#include <m_skin.h>
+#include <m_clui.h>
+#include <m_chat.h>
+#include <m_idle.h>
+#include <m_metacontacts.h>
+#include <m_langpack.h>
+
+//#define IDF_ISIDLE 0x1 // idle has become active (if not set, inactive)
+#define IDF_SHORT 0x2 // short idle mode
+#define IDF_LONG 0x4 // long idle mode
+//#define IDF_PRIVACY 0x8 // if set, the information provided shouldn't be given to third parties.
+#define IDF_ONFORCE 0x10
+
+#define ASSERT assert
+
+#include "LCDFramework.h"
+
+#include "Miranda.h"
+#include "CEvent.h"
+
+#include "../resource.h"
+
+#endif \ No newline at end of file
diff --git a/plugins/MirandaG15/src/m_metacontacts.h b/plugins/MirandaG15/src/m_metacontacts.h
new file mode 100644
index 0000000000..9f348bd2c6
--- /dev/null
+++ b/plugins/MirandaG15/src/m_metacontacts.h
@@ -0,0 +1,166 @@
+/*
+
+Miranda IM: the free IM client for Microsoft* Windows*
+
+Copyright © 2004 Universite Louis PASTEUR, STRASBOURG.
+Copyright © 2004 Scott Ellis (www.scottellis.com.au mail@scottellis.com.au)
+
+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 2
+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.
+
+You should have received a copy of the GNU General Public License
+along with this program; if not, write to the Free Software
+Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+*/
+
+#ifndef M_METACONTACTS_H__
+#define M_METACONTACTS_H__ 1
+
+#ifndef MIID_METACONTACTS
+#define MIID_METACONTACTS {0xc0325019, 0xc1a7, 0x40f5, { 0x83, 0x65, 0x4f, 0x46, 0xbe, 0x21, 0x86, 0x3e}}
+#endif
+
+//get the handle for a contact's parent metacontact
+//wParam=(HANDLE)hSubContact
+//lParam=0
+//returns a handle to the parent metacontact, or null if this contact is not a subcontact
+#define MS_MC_GETMETACONTACT "MetaContacts/GetMeta"
+
+//gets the handle for the default contact
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns a handle to the default contact, or null on failure
+#define MS_MC_GETDEFAULTCONTACT "MetaContacts/GetDefault"
+
+//gets the contact number for the default contact
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns a DWORD contact number, or -1 on failure
+#define MS_MC_GETDEFAULTCONTACTNUM "MetaContacts/GetDefaultNum"
+
+//gets the handle for the 'most online' contact
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns a handle to the 'most online' contact
+#define MS_MC_GETMOSTONLINECONTACT "MetaContacts/GetMostOnline"
+
+//gets the number of subcontacts for a metacontact
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns a DWORD representing the number of subcontacts for the given metacontact
+#define MS_MC_GETNUMCONTACTS "MetaContacts/GetNumContacts"
+
+//gets the handle of a subcontact, using the subcontact's number
+//wParam=(HANDLE)hMetaContact
+//lParam=(DWORD)contact number
+//returns a handle to the specified subcontact
+#define MS_MC_GETSUBCONTACT "MetaContacts/GetSubContact"
+
+//sets the default contact, using the subcontact's contact number
+//wParam=(HANDLE)hMetaContact
+//lParam=(DWORD)contact number
+//returns 0 on success
+#define MS_MC_SETDEFAULTCONTACTNUM "MetaContacts/SetDefault"
+
+//sets the default contact, using the subcontact's handle
+//wParam=(HANDLE)hMetaContact
+//lParam=(HANDLE)hSubcontact
+//returns 0 on success
+#define MS_MC_SETDEFAULTCONTACT "MetaContacts/SetDefaultByHandle"
+
+//forces the metacontact to send using a specific subcontact, using the subcontact's contact number
+//wParam=(HANDLE)hMetaContact
+//lParam=(DWORD)contact number
+//returns 0 on success
+#define MS_MC_FORCESENDCONTACTNUM "MetaContacts/ForceSendContact"
+
+//forces the metacontact to send using a specific subcontact, using the subcontact's handle
+//wParam=(HANDLE)hMetaContact
+//lParam=(HANDLE)hSubcontact
+//returns 0 on success (will fail if 'force default' is in effect)
+#define MS_MC_FORCESENDCONTACT "MetaContacts/ForceSendContactByHandle"
+
+//'unforces' the metacontact to send using a specific subcontact
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns 0 on success (will fail if 'force default' is in effect)
+#define MS_MC_UNFORCESENDCONTACT "MetaContacts/UnforceSendContact"
+
+//'forces' or 'unforces' (i.e. toggles) the metacontact to send using it's default contact
+// overrides (and clears) 'force send' above, and will even force use of offline contacts
+// will send ME_MC_FORCESEND or ME_MC_UNFORCESEND event
+//wParam=(HANDLE)hMetaContact
+//lParam=0
+//returns 1(true) or 0(false) representing new state of 'force default'
+#define MS_MC_FORCEDEFAULT "MetaContacts/ForceSendDefault"
+
+// method to get state of 'force' for a metacontact
+// wParam=(HANDLE)hMetaContact
+// lParam= (DWORD)&contact_number or NULL
+//
+// if lparam supplied, the contact_number of the contatct 'in force' will be copied to the address it points to,
+// or if none is in force, the value (DWORD)-1 will be copied
+// (v0.8.0.8+ returns 1 if 'force default' is true with *lParam == default contact number, else returns 0 with *lParam as above)
+#define MS_MC_GETFORCESTATE "MetaContacts/GetForceState"
+
+// fired when a metacontact's default contact changes (fired upon creation of metacontact also, when default is initially set)
+// wParam=(HANDLE)hMetaContact
+// lParam=(HANDLE)hDefaultContact
+#define ME_MC_DEFAULTTCHANGED "MetaContacts/DefaultChanged"
+
+// fired when a metacontact's subcontacts change (fired upon creation of metacontact, when contacts are added or removed, and when
+// contacts are reordered) - a signal to re-read metacontact data
+// wParam=(HANDLE)hMetaContact
+// lParam=0
+#define ME_MC_SUBCONTACTSCHANGED "MetaContacts/SubcontactsChanged"
+
+// fired when a metacontact is forced to send using a specific subcontact
+// wParam=(HANDLE)hMetaContact
+// lParam=(HANDLE)hForceContact
+#define ME_MC_FORCESEND "MetaContacts/ForceSend"
+
+// fired when a metacontact is 'unforced' to send using a specific subcontact
+// wParam=(HANDLE)hMetaContact
+// lParam=0
+#define ME_MC_UNFORCESEND "MetaContacts/UnforceSend"
+
+// method to get protocol name - used to be sure you're dealing with a "real" metacontacts plugin :)
+// wParam=lParam=0
+#define MS_MC_GETPROTOCOLNAME "MetaContacts/GetProtoName"
+
+
+// added 0.9.5.0 (22/3/05)
+// wParam=(HANDLE)hContact
+// lParam=0
+// convert a given contact into a metacontact
+#define MS_MC_CONVERTTOMETA "MetaContacts/ConvertToMetacontact"
+
+// added 0.9.5.0 (22/3/05)
+// wParam=(HANDLE)hContact
+// lParam=(HANDLE)hMeta
+// add an existing contact to a metacontact
+#define MS_MC_ADDTOMETA "MetaContacts/AddToMetacontact"
+
+// added 0.9.5.0 (22/3/05)
+// wParam=0
+// lParam=(HANDLE)hContact
+// remove a contact from a metacontact
+#define MS_MC_REMOVEFROMMETA "MetaContacts/RemoveFromMetacontact"
+
+
+// added 0.9.13.2 (6/10/05)
+// wParam=(BOOL)disable
+// lParam=0
+// enable/disable the 'hidden group hack' - for clists that support subcontact hiding using 'IsSubcontact' setting
+// should be called once in the clist 'onmodulesloaded' event handler (which, since it's loaded after the db, will be called
+// before the metacontact onmodulesloaded handler where the subcontact hiding is usually done)
+#define MS_MC_DISABLEHIDDENGROUP "MetaContacts/DisableHiddenGroup"
+
+#endif