/* wvstbar.c
 * author: jody glasser (jglas@tdycont.com)
 *
 * $Id: wvstbar.c 1.6 1997/02/08 11:03:29 dumoulin Exp $
 */

#include <windows.h>
#include <windowsx.h>
#include "wvglob.h"
#include "winvn.h"
#include <commctrl.h>
#include <stdarg.h>
#include "visualstylesxp.h"

/*
   These are the popups defined in the menus in winvn.rc
   Any changes to the menu definitions will require
   corresponding changes in this module.

   main window popups:     Group Window popups:    Article Window popups:
   Network                 Articles                File
   Group                   Sort                    Edit
   Utilities               Search                  Search
   Batch Send                                   View
   Config                                          Respond
   Configure Fonts
   Configure Color
   Window
   Close
   Minimize
   Help

 */


/* structure to associate popup handles to identifiers */
typedef struct popupid 
{
  HMENU hMenu;                  /* menu handle */
  int ID;                       /* corresponding identifier */
} POPUPID;

static POPUPID PopupTable[MAXPOPUPS];
static int NumPopups;
static int GroupPopupBase;
static int ArtPopupBase;

/*
 ** StatBarMainPopups
 *
 *  PARAMETERS:   none
 *
 *  CALLED:       once after creation of main window
 *
 *  DESCRIPTION:  gets HMENUs associated with the main window
 *                popups and associates them with predefined
 *                identifiers to be used in stringtable lookups
 *                to provide status bar text
 *
 *  RETURNS:      nothing
 *
 */
void StatBarMainPopups ()
{
	HMENU hMenu;
	int i;

	hMenu = GetMenu (NetDoc.hWndFrame);
	i = 0;

	/* top level menus */
	PopupTable[i].ID = IDM_NETWORK_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);
	i++;
	PopupTable[i].ID = IDM_GROUP_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);
	i++;
	PopupTable[i].ID = IDM_UTILITIES_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);
	i++;
	PopupTable[i].ID = IDM_CONFIG_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);
	i++;
	PopupTable[i].ID = IDM_WINDOW_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);
	i++;
	PopupTable[i].ID = IDM_HELP_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, i);

	/* nested sub-menus */
	i++;
	PopupTable[i].ID = IDM_BATCH_MENU;
	PopupTable[i].hMenu = GetSubMenu (PopupTable[2].hMenu, 3);
	i++;
	PopupTable[i].ID = IDM_FONT_MENU;
	PopupTable[i].hMenu = GetSubMenu (PopupTable[3].hMenu, 13);
	i++;
	PopupTable[i].ID = IDM_COLOR_MENU;
	PopupTable[i].hMenu = GetSubMenu (PopupTable[3].hMenu, 14);
	i++;
	PopupTable[i].ID = IDM_CLOSE_MENU;
	PopupTable[i].hMenu = GetSubMenu (PopupTable[4].hMenu, 1);
	i++;
	PopupTable[i].ID = IDM_MINIMIZE_MENU;
	PopupTable[i].hMenu = GetSubMenu (PopupTable[4].hMenu, 2);

	NumPopups = i + 1;
	GroupPopupBase = NumPopups;
}

/*
 ** StatBarGroupPopups
 *
 *  PARAMETERS:   TypDoc *MyDoc
 *
 *  CALLED:       whenever group window gets the focus
 *
 *  DESCRIPTION:  gets HMENUs associated with the current group window
 *                popups and associates them with predefined
 *                identifiers to be used in stringtable lookups
 *                to provide status bar text
 *
 *  RETURNS:      nothing
 *
 */
void StatBarGroupPopups (TypDoc * MyDoc)
{
	HMENU hMenu;
	int i, j;

	hMenu = GetMenu (MyDoc->hWndFrame);
	i = GroupPopupBase;
	j = 0;

	PopupTable[i].ID = IDM_ARTICLE_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_SORT_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_SEARCH_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;

	if (NumPopups < i) 
	{
		NumPopups = i;
		ArtPopupBase = i;
	}
}

/*
 ** StatBarArtPopups
 *
 *  PARAMETERS:   TypDoc *MyDoc
 *
 *  CALLED:       whenever article window gets the focus
 *
 *  DESCRIPTION:  gets HMENUs associated with the current article window
 *                popups and associates them with predefined
 *                identifiers to be used in stringtable lookups
 *                to provide status bar text
 *
 *  RETURNS:      nothing
 *
 */
void StatBarArtPopups (TypDoc * MyDoc)
{
	HMENU hMenu;
	int i, j;

	hMenu = GetMenu (MyDoc->hWndFrame);
	i = ArtPopupBase;
	j = 0;

	PopupTable[i].ID = IDM_FILE_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_EDIT_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_ARTSEARCH_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_VIEW_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	j++;
	PopupTable[i].ID = IDM_RESPOND_MENU;
	PopupTable[i].hMenu = GetSubMenu (hMenu, j);
	i++;
	if (NumPopups < i) 
	{
		NumPopups = i;
	}
}


/* Initialize the variables with Status Bar element sizes  */
/* call once at initialization                             */
void InitStatBar (STATUSPAINT * StatbarPntData)
{
	HDC hDC;
	TEXTMETRIC tm;
	HANDLE hOldFont;
	SIZE sz, sz2;

	StatbarPntData->dyBorder = GetSystemMetrics (SM_CYBORDER);
	StatbarPntData->dyBorderx2 = StatbarPntData->dyBorder * 2;
	StatbarPntData->dyBorderx3 = StatbarPntData->dyBorder * 3;
	StatbarPntData->dyBorderx4 = StatbarPntData->dyBorder * 4;
	StatbarPntData->dyBorderx8 = StatbarPntData->dyBorder * 8;
	StatbarPntData->dyBorderx9 = StatbarPntData->dyBorder * 9;
	StatbarPntData->dyBorderx10 = StatbarPntData->dyBorder * 10;
	StatbarPntData->dxResize = ::GetSystemMetrics(SM_CXVSCROLL);

	hDC = GetDC (NULL);
/* 
   char          szHelv[] = "Helv";
   int           Fntheight;                  // Height of the font
   Fntheight = MulDiv(-10, GetDeviceCaps(hDC, LOGPIXELSY), 72);
   StatbarPntData->hFontStatbar = hWinVnFont;
   ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,
   DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, szHelv);
 */
	StatbarPntData->hFontStatbar = hWinVnFont;
	hOldFont = SelectObject (hDC, StatbarPntData->hFontStatbar);
	GetTextMetrics (hDC, &tm);
	GetTextExtentPoint(hDC, "CAPS", 4, &sz);
	GetTextExtentPoint(hDC, "DHE-RSA-AES256-SHA", 18, &sz2);
	
	SelectObject (hDC, hOldFont);
	ReleaseDC (NULL, hDC);

	StatbarPntData->dyStatbar = tm.tmHeight + tm.tmExternalLeading + (7 * StatbarPntData->dyBorder);
	/* sb eliminated */
	StatbarPntData->dxStates = tm.tmMaxCharWidth * 3;
	StatbarPntData->dxStates = sz.cx + 2;

	StatbarPntData->dxCommMsg = sz2.cx + 2;
													  
	StatBarMainPopups ();
}


void SetNumLockText (HWND hwnd)
{
	RECT rc, rcTemp, rcTemp2;
	HDC hdc;
	int NumLockLeft;
	char szString[6];
	static int nLastState = FALSE;
	static HWND hLastWnd;
	HANDLE hOldFont;

	/* Num Lock Text */
	if (GetKeyState (VK_NUMLOCK) & 0x0001) 
	{
		if (nLastState == TRUE && hwnd == hLastWnd)
			return;
		nLastState = TRUE;
		hLastWnd = hwnd;
		strcpy (szString, "NUM");
	}
	else 
	{
		if (nLastState == FALSE && hwnd == hLastWnd)
			return;
		nLastState = FALSE;
		hLastWnd = hwnd;
		strcpy (szString, "");
	}

	// Is stat bar stuff initialized ? if not then don't draw text
	//
	if (StatbarPntData.dyStatbar) 
	{
		hdc = GetDC (hwnd);

		GetClientRect (hwnd, &rc);
		rc.top = rc.bottom - StatbarPntData.dyStatbar;
		NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;

		hOldFont = SelectObject (hdc, StatbarPntData.hFontStatbar);
		SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
		SetBkColor (hdc, GetSysColor (COLOR_BTNFACE));

		rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
		rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
		rcTemp.left = NumLockLeft;
		rcTemp.right = rcTemp.left + StatbarPntData.dxStates - StatbarPntData.dyBorder;

		rcTemp2 = rcTemp;

		ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
					ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) szString,
					lstrlen ((LPSTR) szString), NULL);

		SelectObject (hdc, hOldFont);
		ReleaseDC (hwnd, hdc);
	}

	return;
}

void SetCapsLockText (HWND hwnd)
{
	RECT rc, rcTemp, rcTemp2;
	HDC hdc;
	int CapLockLeft;
	int NumLockLeft;
	int ConnLeft;
	char szString[6];
	static int nLastState = FALSE;
	static HWND hLastWnd;
	HANDLE hOldFont;

	/* Caps Lock Text */
	if (GetKeyState (VK_CAPITAL) & 0x0001) 
	{
		if (nLastState == TRUE && hwnd == hLastWnd)
			return;
		nLastState = TRUE;
		hLastWnd = hwnd;
		strcpy (szString, "CAPS");
	}
	else 
	{
		if (nLastState == FALSE && hwnd == hLastWnd)
			return;
		nLastState = FALSE;
		hLastWnd = hwnd;
		strcpy (szString, "");
	}
	// Is stat bar stuff initialized ? if not then don't draw text
	//
	if (StatbarPntData.dyStatbar) 
	{
		hdc = GetDC (hwnd);

		GetClientRect (hwnd, &rc);
		rc.top = rc.bottom - StatbarPntData.dyStatbar;
		NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;
		CapLockLeft = NumLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxStates;
		ConnLeft = 	CapLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxCommMsg;

		hOldFont = SelectObject (hdc, StatbarPntData.hFontStatbar);
		SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
		SetBkColor (hdc, GetSysColor (COLOR_BTNFACE));

		rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
		rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
		rcTemp.left = CapLockLeft;
		rcTemp.right = rcTemp.left + StatbarPntData.dxStates - StatbarPntData.dyBorder;

		rcTemp2 = rcTemp;

		ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
					ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) szString,
					lstrlen ((LPSTR) szString), NULL);

		SelectObject (hdc, hOldFont);
		ReleaseDC (hwnd, hdc);
	}

	return;
}

void SetConnectionText (HWND hwnd, LPSTR lpszConnText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg)
{
	RECT rc, rcTemp, rcTemp2;
	HDC hdc;
	int CapLockLeft;
	int NumLockLeft;
	int CommLeft;
	HANDLE hOldFont = NULL;
	if (permflg)
		strntcpy (MyDoc->szStatCommText, lpszConnText, MAXSTATCOMMTEXT - 1);

	if (redrawflg && (MyDoc && MyDoc->nStatBarCommPanel) ) 
	{
		hdc = GetDC (hwnd);

		GetClientRect (hwnd, &rc);
		rc.top = rc.bottom - StatbarPntData.dyStatbar;

		rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
		rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
		rcTemp.left = StatbarPntData.dyBorderx9;
		NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;
		CapLockLeft = NumLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxStates;
		CommLeft = 	CapLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxCommMsg;

		rcTemp.right = CommLeft - StatbarPntData.dyBorderx9;
		rcTemp.right = CommLeft - StatbarPntData.dyBorderx9 - StatbarPntData.dyBorder;

		rcTemp2 = rcTemp;

		//PaintStatbarText(hdc, rcTemp, lpszConnText, MyDoc);
		if (StatbarPntData.dyStatbar) 
		{

			hOldFont = SelectObject (hdc, StatbarPntData.hFontStatbar);
			SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
			SetBkColor (hdc, GetSysColor (COLOR_BTNFACE));

			rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
			rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
			rcTemp.left = CommLeft;
			rcTemp.right = rcTemp.left + StatbarPntData.dxCommMsg - StatbarPntData.dyBorder;

			rcTemp2 = rcTemp;

			ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
						ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) lpszConnText,
						lstrlen ((LPSTR) lpszConnText), NULL);

			SelectObject (hdc, hOldFont);
		}

		ReleaseDC(hwnd, hdc);
	}
	return;
}



#define STATUSSIZE 1024
void WVArgXSetStatbarText (HWND hwnd, UINT IDlpszStatBarText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg, ...)
{
	va_list vargs;
	char far *pFormat = NULL;
	char far *pMesg = NULL;
	int  nStrLen = 0;

	pMesg = (char far *)GlobalAllocPtr (GMEM_MOVEABLE, STATUSSIZE * sizeof (char));
	pFormat = (char far *)GlobalAllocPtr (GMEM_MOVEABLE, STATUSSIZE * sizeof (char) * 2);

	if (pFormat && pMesg) 
	{
		*pMesg = '\0';
		nStrLen = LoadString(hInst, IDlpszStatBarText, pFormat, STATUSSIZE);

		if (nStrLen && nStrLen < STATUSSIZE) 
		{
			va_start( vargs, permflg );
			_vsnprintf( pMesg, STATUSSIZE, pFormat, vargs );
			va_end( vargs );        
		}
		SetStatbarText (hwnd, pMesg, MyDoc, redrawflg, permflg);
  
	}
	if (pFormat)
	GlobalFreePtr(pFormat);

	if (pMesg)
	GlobalFreePtr(pMesg);

}


void WVArg2SetStatbarText (HWND hwnd, UINT IDlpszStatBarText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg,
                      const char far *psubst1,const char far *psubst2)
{
	char *buf;
	char *msg;

	if ((buf = (char *) GlobalAllocPtr (GMEM_MOVEABLE,  2 * MAXSTATBARTEXT * sizeof (char))) == NULL) 
	{
		WVMessageBox (hwnd, IDS_STBAR_MEM_ERROR, IDS_STBAR_MEM_FAIL, MB_OK | MB_ICONSTOP);
		return;
	}
	msg = buf + MAXSTATBARTEXT;
	if (LoadString (hInst, IDlpszStatBarText, buf, MAXSTATBARTEXT) != 0) 
	{
		_snprintf(msg, MAXSTATBARTEXT*2, buf, psubst1, psubst2);
		SetStatbarText (hwnd, msg, MyDoc, redrawflg, permflg);
	}
	GlobalFreePtr(buf);
}

void WVArgSetStatbarText (HWND hwnd, UINT IDlpszStatBarText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg,
                     const char far *psubst)
{
	char *buf;
	char *msg;

	if ((buf = (char *) GlobalAllocPtr (GMEM_MOVEABLE,  2 * MAXSTATBARTEXT * sizeof (char))) == NULL) 
	{
		WVMessageBox (hwnd, IDS_STBAR_MEM_ERROR, IDS_STBAR_MEM_FAIL, MB_OK | MB_ICONSTOP);
		return;
	}
	msg = buf + MAXSTATBARTEXT;
	if (LoadString (hInst, IDlpszStatBarText, buf, MAXSTATBARTEXT) != 0) 
	{
		_snprintf(msg, MAXSTATBARTEXT*2, buf, psubst);
		SetStatbarText (hwnd, msg, MyDoc, redrawflg, permflg);
	}
	GlobalFreePtr(buf);
}

void WVSetStatbarText (HWND hwnd, UINT IDlpszStatBarText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg)
{
	char *buf;

	if ((buf = (char *) GlobalAllocPtr (GMEM_MOVEABLE,  MAXSTATBARTEXT * sizeof (char))) == NULL) 
	{
		WVMessageBox (hwnd, IDS_STBAR_MEM_ERROR, IDS_STBAR_MEM_FAIL, MB_OK | MB_ICONSTOP);
		return;
	}

	if (LoadString (hInst, IDlpszStatBarText, buf, MAXSTATBARTEXT) != 0)
		SetStatbarText (hwnd, buf, MyDoc, redrawflg, permflg);

	GlobalFreePtr(buf);
}


void SetStatbarText (HWND hwnd, LPSTR lpszStatBarText, TypDoc * MyDoc, BOOL redrawflg, BOOL permflg)
{
	RECT rc, rcTemp, rcTemp2;
	HDC hdc;
	int CapLockLeft;
	int NumLockLeft;
	int CommLeft;
	BOOL bShowComm = (MyDoc && MyDoc->nStatBarCommPanel) ? 1 : 0;
	if (permflg)
		strntcpy (MyDoc->szStatBarText, lpszStatBarText, MAXSTATBARTEXT - 1);

	/* if no status bar text, set StatBarPercent = 0 */
	if (strlen(MyDoc->szStatBarText) == 0)
		MyDoc->StatBarPercent = 0;

	if (redrawflg) 
	{
		hdc = GetDC (hwnd);

		GetClientRect (hwnd, &rc);
		rc.top = rc.bottom - StatbarPntData.dyStatbar;

		rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
		rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
		rcTemp.left = StatbarPntData.dyBorderx9;
		NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;
		CapLockLeft = NumLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxStates;
		CommLeft = 	CapLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxCommMsg;
		if (!bShowComm)
			CommLeft = CapLockLeft;

		rcTemp.right = CommLeft - StatbarPntData.dyBorderx9;
		rcTemp.right = CommLeft - StatbarPntData.dyBorderx9 - StatbarPntData.dyBorder;

		rcTemp2 = rcTemp;

		PaintStatbarText(hdc, rcTemp, lpszStatBarText, MyDoc);
		ReleaseDC(hwnd, hdc);
	}
	return;
}

void SetStatbarPercent(HWND hwnd, int StatBarPercent, TypDoc * MyDoc, BOOL redrawflg)
{
   RECT rc, rcTemp, rcTemp2;
   HDC hdc;
   int CapLockLeft;
   int NumLockLeft;
   int CommLeft;
   int i, j;
   BOOL bShowComm = (MyDoc && MyDoc->nStatBarCommPanel) ? 1 : 0;

   /* ensure that percentages are within range */
   if (StatBarPercent > 100)
      StatBarPercent = 100;
   else if (StatBarPercent < 0)
      StatBarPercent = 0;

   if (MyDoc && MyDoc->StatBarPercent > 100)
      MyDoc->StatBarPercent = 100;
   else if (MyDoc && MyDoc->StatBarPercent < 0)
      MyDoc->StatBarPercent = 0;

   if (redrawflg) 
   {
      hdc = GetDC(hwnd);

      GetClientRect(hwnd, &rc);
      rc.top = rc.bottom - StatbarPntData.dyStatbar;

      rcTemp.top = rc.top + StatbarPntData.dyBorder * 4;
      rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
      rcTemp.left = StatbarPntData.dyBorderx9;

      NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;
      CapLockLeft = NumLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxStates;
	  CommLeft = CapLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxCommMsg;
	  if (!bShowComm)
		CommLeft = CapLockLeft; 

      rcTemp.right = CommLeft - StatbarPntData.dyBorderx9;
      rcTemp.right = CommLeft - StatbarPntData.dyBorderx9 - StatbarPntData.dyBorder;

      rcTemp2 = rcTemp;
      i = MulDiv(rcTemp.right - rcTemp.left, MyDoc->StatBarPercent, 100) + rcTemp.left;
      j = MulDiv(rcTemp.right - rcTemp.left, StatBarPercent, 100) + rcTemp.left;
      if (j > i + 1) 
	  {
         rcTemp.left = i;
         rcTemp.right = j;
         InvertRect(hdc, &rcTemp);
         MyDoc->StatBarPercent = StatBarPercent;
      }
      else if (j < i) 
	  {
         MyDoc->StatBarPercent = StatBarPercent;
         PaintStatbarText(hdc, rcTemp, MyDoc->szStatBarText, MyDoc);
      }
      ReleaseDC(hwnd, hdc);
   }
   else
      MyDoc->StatBarPercent = StatBarPercent;

   return;
}

void PaintStatbarText(HDC hdc, RECT rcTemp, LPSTR lpszStatBarText, TypDoc * MyDoc)
{
	RECT rcTemp2;
	HANDLE hOldFont;
	rcTemp2 = rcTemp;

	hOldFont = SelectObject (hdc, StatbarPntData.hFontStatbar);
	SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
	SetBkColor (hdc, GetSysColor (COLOR_BTNFACE));

	ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
				ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, lpszStatBarText,
				lstrlen (lpszStatBarText), NULL);
	SelectObject (hdc, hOldFont);
	if (MyDoc->StatBarPercent > 0) 
	{
		rcTemp.right = MulDiv (rcTemp.right - rcTemp.left, MyDoc->StatBarPercent, 100) + rcTemp.left;
		InvertRect(hdc, &rcTemp);
	}
  return;
}

void PaintStatbar (HWND hwnd, HDC hdc, TypDoc * MyDoc)
{
	RECT rc, rcTemp, rcTemp2;
	HBRUSH hBrush;
	int CapLockLeft;
	int NumLockLeft;
	int CommLeft;
	char szString[6];
	HANDLE hOldFont;
	BOOL bShowComm = (MyDoc && MyDoc->nStatBarCommPanel) ? 1 : 0;


	GetClientRect (hwnd, &rc);

	rc.top = rc.bottom - StatbarPntData.dyStatbar;
	NumLockLeft = rc.right - StatbarPntData.dxResize - StatbarPntData.dxStates;
	CapLockLeft = NumLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxStates;
	CommLeft = CapLockLeft - StatbarPntData.dyBorderx3 - StatbarPntData.dxCommMsg;
	if (!bShowComm)
		CommLeft = CapLockLeft;	

	/* draw the frame */

	/* Border color */

	hBrush = CreateSolidBrush (GetSysColor (COLOR_BTNFACE));

	/* top and bottom border */

	/* Top */

	rcTemp = rc;
	rcTemp.bottom = rcTemp.top + StatbarPntData.dyBorderx3;
	rcTemp.top += StatbarPntData.dyBorderx2;
	FillRect (hdc, &rcTemp, hBrush);

	/* Bottom */

	rcTemp = rc;
	rcTemp.top = rcTemp.bottom - StatbarPntData.dyBorderx2;
	FillRect (hdc, &rcTemp, hBrush);

	/* left and right border */

	/* Left */

	rcTemp = rc;
	rcTemp.right = StatbarPntData.dyBorderx8;
	rcTemp.top += StatbarPntData.dyBorderx2;
	FillRect (hdc, &rcTemp, hBrush);

	/* Bar between status and comm stat Area */
	rcTemp.right = CommLeft;
	rcTemp.left = rcTemp.right - StatbarPntData.dyBorderx10;
	FillRect (hdc, &rcTemp, hBrush);

	/* bar between comm stat & caps */
	if (bShowComm)
	{
		rcTemp.right = CapLockLeft;
		rcTemp.left = rcTemp.right - StatbarPntData.dyBorderx10;
		FillRect (hdc, &rcTemp, hBrush);
	}

	/* Bar between Caps Lock and Num Lock Area */
	rcTemp.right = NumLockLeft;
	rcTemp.left = rcTemp.right - StatbarPntData.dyBorderx4;
	FillRect (hdc, &rcTemp, hBrush);




	/* Right */
	rcTemp.right = rc.right;
	rcTemp.left = rcTemp.right - StatbarPntData.dxResize;//StatbarPntData.dyBorderx10;
	FillRect (hdc, &rcTemp, hBrush);

	DeleteObject (hBrush);

	/* Shadow color */

	hBrush = CreateSolidBrush (GetSysColor (COLOR_BTNSHADOW));

	/* Top and left shadow */

	rcTemp = rc;
	rcTemp.top = rc.top + StatbarPntData.dyBorderx3;
	rcTemp.bottom = rcTemp.top + StatbarPntData.dyBorder;

	/* Top of Status */
	rcTemp.left = StatbarPntData.dyBorderx8;
	rcTemp.right = CommLeft - StatbarPntData.dyBorderx9;
	FillRect (hdc, &rcTemp, hBrush);

	/*top of CommStat */
	if (bShowComm)
	{
		rcTemp.left = CommLeft - StatbarPntData.dyBorder;
		rcTemp.right = rcTemp.left + StatbarPntData.dxCommMsg;
		FillRect (hdc, &rcTemp, hBrush);
	}

	/* Top of Caps Lock */
	rcTemp.left = CapLockLeft - StatbarPntData.dyBorder;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates;
	FillRect (hdc, &rcTemp, hBrush);

	/* Top of Num Lock  */
	rcTemp.left = NumLockLeft - StatbarPntData.dyBorder;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates;
	FillRect (hdc, &rcTemp, hBrush);

	/* Left */
	rcTemp = rc;
	rcTemp.top += StatbarPntData.dyBorderx3;
	rcTemp.bottom -= StatbarPntData.dyBorderx2;

	/* Left of bar */
	rcTemp.left = StatbarPntData.dyBorderx8;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	/* Left on Bar between status and comm stat Area */
	if (bShowComm)
	{
		rcTemp.left = CommLeft - StatbarPntData.dyBorder;
		rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
		FillRect (hdc, &rcTemp, hBrush);
	}
	rcTemp.left = CapLockLeft - StatbarPntData.dyBorder;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);


	/* Left on Bar between Caps Lock and Num Lock Area */
	rcTemp.left = NumLockLeft - StatbarPntData.dyBorder;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	DeleteObject (hBrush);

	hBrush = CreateSolidBrush (GetSysColor (COLOR_BTNHIGHLIGHT));

	/* Right, top and bottom hilight */

	rcTemp = rc;
	rcTemp.top = rc.bottom - StatbarPntData.dyBorderx3;
	rcTemp.bottom = rcTemp.top + StatbarPntData.dyBorder;


	/* Bottom of status */
	rcTemp.left = StatbarPntData.dyBorderx8;
	rcTemp.right = CommLeft - StatbarPntData.dyBorderx9;
	FillRect (hdc, &rcTemp, hBrush);

	/* bottom of comm status */
	if (bShowComm)
	{
		rcTemp.left = CommLeft;
		rcTemp.right = rcTemp.left + StatbarPntData.dxCommMsg;
		FillRect (hdc, &rcTemp, hBrush);
	}


	/* Bottom of caps lock */
	rcTemp.left = CapLockLeft;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates;
	FillRect (hdc, &rcTemp, hBrush);

	/* Bottom of num lock */
	rcTemp.left = NumLockLeft;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates;
	FillRect (hdc, &rcTemp, hBrush);

	rcTemp = rc;
	rcTemp.top += StatbarPntData.dyBorderx3;
	rcTemp.bottom -= StatbarPntData.dyBorderx2;

	/* Right of status */
	rcTemp.left = CommLeft - StatbarPntData.dyBorderx9;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	/* right of comm stat */
	if (bShowComm)
	{
		rcTemp.left = CapLockLeft - StatbarPntData.dyBorderx3;
		rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
		FillRect (hdc, &rcTemp, hBrush);
	}
	
	
	/* Right of caps lock */
	rcTemp.left = NumLockLeft - StatbarPntData.dyBorderx3;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	/* Right of num lock */
	rcTemp.left = rc.right - StatbarPntData.dxResize;//StatbarPntData.dyBorderx9;
	rcTemp.right = rcTemp.left + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	/* Across the top */
	rcTemp = rc;
	rcTemp.top += StatbarPntData.dyBorder;
	rcTemp.bottom = rcTemp.top + StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);

	DeleteObject (hBrush);

	/* solid black line across top */

	hBrush = CreateSolidBrush (GetSysColor (COLOR_WINDOWTEXT));
	rcTemp = rc;
	rcTemp.bottom = rcTemp.top;
	rcTemp.bottom += StatbarPntData.dyBorder;
	FillRect (hdc, &rcTemp, hBrush);
	DeleteObject (hBrush);

	/* now the text, with the button face background */

	hOldFont = SelectObject (hdc, StatbarPntData.hFontStatbar);
	SetTextColor (hdc, GetSysColor (COLOR_BTNTEXT));
	SetBkColor (hdc, GetSysColor (COLOR_BTNFACE));

	/* status Text */
	rcTemp.top = rc.top + (StatbarPntData.dyBorder * 4);
	rcTemp.bottom = rc.bottom - StatbarPntData.dyBorderx3;
	rcTemp.left = StatbarPntData.dyBorderx9;
	rcTemp.right = CommLeft - StatbarPntData.dyBorderx10;

	PaintStatbarText(hdc, rcTemp, MyDoc->szStatBarText, MyDoc);

	if (bShowComm)
	{
		rcTemp.left = CommLeft;
		rcTemp.right = rcTemp.left + StatbarPntData.dxCommMsg - StatbarPntData.dyBorder;

		rcTemp2 = rcTemp;

		ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
				  ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) MyDoc->szStatCommText,
				  lstrlen ((LPSTR) MyDoc->szStatCommText), NULL);
	}


	/* Caps Lock Text */
	if (GetKeyState (VK_CAPITAL) & 0x0001)
		strcpy (szString, "CAPS");
	else
		strcpy (szString, "");

	rcTemp.left = CapLockLeft;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates - StatbarPntData.dyBorder;

	rcTemp2 = rcTemp;

	ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
			  ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) szString,
			  lstrlen ((LPSTR) szString), NULL);

	/* Num Lock Text */
	if (GetKeyState (VK_NUMLOCK) & 0x0001)
		strcpy (szString, "NUM");
	else
		strcpy (szString, "");

	rcTemp.left = NumLockLeft;
	rcTemp.right = rcTemp.left + StatbarPntData.dxStates - StatbarPntData.dyBorder;

	rcTemp2 = rcTemp;

	ExtTextOut (hdc, rcTemp.left + StatbarPntData.dyBorderx2, rcTemp.top,
			  ETO_OPAQUE | ETO_CLIPPED, &rcTemp2, (LPSTR) szString,
			  lstrlen ((LPSTR) szString), NULL);

	SelectObject (hdc, hOldFont);

	rcTemp = rc;
	rcTemp.top += StatbarPntData.dyBorderx3; 
	rcTemp.left = rcTemp.right - StatbarPntData.dxResize;
	rcTemp.bottom = rcTemp.top + StatbarPntData.dxResize;
	if( g_xpStyle.IsThemeActive() )   
	{   
		HTHEME hTheme = NULL;   
		hTheme = g_xpStyle.OpenThemeData( hwnd, L"SCROLLBAR" );
		
		   
		HRESULT hr;  
		hr = g_xpStyle.DrawThemeBackground( hTheme, hdc, SBP_SIZEBOX, SZB_RIGHTALIGN, &rcTemp, NULL);   
		hr = g_xpStyle.CloseThemeData( hTheme );   

	}   
	else   
	{   
		DrawFrameControl( hdc, &rcTemp, DFC_SCROLL, DFCS_SCROLLSIZEGRIP );

	}
}

/*
*  StatusBarProc() -
*
*      Processes the status bar stuff for all windows
*
*       Returns:    TRUE,   if the message has been processed
*                   FALSE,  if the calling Window Proc should continue processing
*/
BOOL StatusBarProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam, TypDoc * MyDoc)
{
  HWND hFrameWnd;
  char szStatBarText[256];
  int i;
#ifdef _WIN32
  HMENU hMenu;
#endif
#ifdef COMMCTRL
  LPTOOLTIPTEXT lpToolTipText;
  static char   szBuffer[64];
  TBNOTIFY FAR *ptbn;
#endif

  hFrameWnd = GetParent (hWnd);
  if (hFrameWnd == NULL)
    hFrameWnd = hWnd;

  switch (message) 
  {

  case WM_SETFOCUS:
    SetCapsLockText (hFrameWnd);
    SetNumLockText (hFrameWnd);
    break;

  case WM_KEYUP:
    break;

  case WM_KEYDOWN:
      if (wParam == VK_CAPITAL)
        SetCapsLockText (hFrameWnd);
      else if (wParam == VK_NUMLOCK)
        SetNumLockText (hFrameWnd);
    break;

  case WM_MENUSELECT:
#ifdef _WIN32
    if (HIWORD (wParam) == 0xFFFF && (HMENU) lParam == NULL) 
	{
#else
    if (LOWORD (lParam) == 0xFFFF && HIWORD (lParam) == 0) 
	{
#endif
      SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
      return(TRUE);
    }
#ifdef _WIN32
    if (HIWORD (wParam) & MF_POPUP) 
	{
#else
    if (LOWORD (lParam) & MF_POPUP) 
	{
#endif
      for (i = 0; i < NumPopups; i++) 
	  {
#ifdef _WIN32
        hMenu = GetSubMenu ((HMENU) lParam, LOWORD (wParam));
        if (PopupTable[i].hMenu == hMenu) 
		{
#else
        if ((UINT) PopupTable[i].hMenu == (UINT) LOWORD (wParam)) 
		{
#endif
          if (LoadString (hInst, PopupTable[i].ID, szStatBarText, 255) != 0)
            SetStatbarText (hFrameWnd, szStatBarText, MyDoc, TRUE, FALSE);
          else
            SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
          return(TRUE);
        }
      }
      SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
      return(TRUE);
    }
    if (LOWORD (wParam)) 
	{
      if (LoadString (hInst, LOWORD (wParam), szStatBarText, 255) != 0)
        SetStatbarText (hFrameWnd, szStatBarText, MyDoc, TRUE, FALSE);
      else
        SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
    }
    else
      SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
    return(TRUE);
    break;

#ifdef COMMCTRL
  case WM_NOTIFY:
    switch (((LPNMHDR) lParam)->code) 
    { 
      case TTN_NEEDTEXT: 
        lpToolTipText = (LPTOOLTIPTEXT)lParam;
        if (lpToolTipText->hdr.code == TTN_NEEDTEXT)
        {
          LoadString(hInst,
                   lpToolTipText->hdr.idFrom,   // string ID == command ID
                   szBuffer,
                   sizeof(szBuffer));

          lpToolTipText->lpszText = szBuffer;
        }
        break;

      case TBN_BEGINDRAG: 
        ptbn = (TBNOTIFY FAR *) lParam;
        LoadString(hInst,
                   ptbn->iItem,
                   szBuffer,
                   sizeof(szBuffer));
        SetStatbarText (hFrameWnd, szBuffer, MyDoc, TRUE, FALSE);
        break;

      case TBN_ENDDRAG: 
        SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
        break;
    }
    break;
#else
  case WM_COMMAND:
    switch (HIWORD (lParam)) 
	{
    case TBN_BEGINDRAG:
      if (LOWORD (lParam)) 
	  {
        if (LoadString (hInst, LOWORD (lParam), szStatBarText, 255) != 0)
      {
          SetStatbarText (hFrameWnd, szStatBarText, MyDoc, TRUE, FALSE);
      }
      }
      return(TRUE);
      break;
    case TBN_ENDDRAG:
      SetStatbarText (hFrameWnd, MyDoc->szStatBarText, MyDoc, TRUE, FALSE);
      return(TRUE);
      break;
    }
    break;
#endif


  case WM_ENTERIDLE:
    break;
  }
  return(FALSE);
}
