/*
 * Add the default or a custom menu depending on the class match
 */
void
SetupSysMenu (unsigned long hwndIn)
{
  HWND    hwnd;
  HMENU	  sys;
  int     i;
  WindowPtr pWin;
  char *res_name, *res_class;

  hwnd = (HWND)hwndIn;
  if (!hwnd)
    return;

  pWin = GetProp (hwnd, WIN_WINDOW_PROP);
  
  sys = GetSystemMenu (hwnd, FALSE);
  if (!sys)
    return;

  if (pWin)
    {
      /* First see if there's a class match... */
      if (winMultiWindowGetClassHint (pWin, &res_name, &res_class))
	{
	  for (i=0; i<pref.sysMenuItems; i++)
	    {
	      if (!strcmp(pref.sysMenu[i].match, res_name) ||
		  !strcmp(pref.sysMenu[i].match, res_class) ) 
		{
		  free(res_name);
		  free(res_class);
  
		  MakeMenu (pref.sysMenu[i].menuName, sys,
			    pref.sysMenu[i].menuPos==AT_START?0:-1);
		  return;
		}
	    }
	  
	  /* No match, just free alloc'd strings */
	  free(res_name);
	  free(res_class);
	} /* Found wm_class */
    } /* if pwin */

  /* Fallback to system default */
  if (pref.defaultSysMenuName[0])
    {
      if (pref.defaultSysMenuPos==AT_START)
	MakeMenu (pref.defaultSysMenuName, sys, 0);
      else
	MakeMenu (pref.defaultSysMenuName, sys, -1);
    }
}
/*
 * Check for a match of the window class to one specified in the
 * ICONS{} section in the prefs file, and load the icon from a file
 */
HICON
winOverrideIcon (unsigned long longWin)
{
  WindowPtr pWin = (WindowPtr) longWin;
  char *res_name, *res_class;
  int i;
  HICON hicon;
  char *wmName;

  if (pWin==NULL)
    return 0;

  /* If we can't find the class, we can't override from default! */
  if (!winMultiWindowGetClassHint (pWin, &res_name, &res_class))
    return 0;

  winMultiWindowGetWMName (pWin, &wmName);
  
  for (i=0; i<pref.iconItems; i++) {
    if (!strcmp(pref.icon[i].match, res_name) ||
	!strcmp(pref.icon[i].match, res_class) ||
	(wmName && strstr(wmName, pref.icon[i].match))) 
      {
	free (res_name);
	free (res_class);
	free(wmName);

	if (pref.icon[i].hicon)
	  return pref.icon[i].hicon;

       hicon = LoadImageComma (pref.icon[i].iconFile, 0, 0, LR_DEFAULTSIZE);
       if (hicon==NULL)
         ErrorF ("winOverrideIcon: LoadImageComma(%s) failed\n",
                  pref.icon[i].iconFile);

	pref.icon[i].hicon = hicon;
	return hicon;
      }
  }
  
  /* Didn't find the icon, fail gracefully */
  free (res_name);
  free (res_class);
  free(wmName);

  return 0;
}
/*
 * Check for a match of the window class to one specified in the
 * STYLES{} section in the prefs file, and return the style type
 */
unsigned long
winOverrideStyle (unsigned long longpWin)
{
  WindowPtr pWin = (WindowPtr) longpWin;
  char *res_name, *res_class;
  int i;
  char *wmName;

  if (pWin==NULL)
    return STYLE_NONE;

  /* If we can't find the class, we can't override from default! */
  if (!winMultiWindowGetClassHint (pWin, &res_name, &res_class))
    return STYLE_NONE;

  winMultiWindowGetWMName (pWin, &wmName);

  for (i=0; i<pref.styleItems; i++) {
    if (!strcmp(pref.style[i].match, res_name) ||
	!strcmp(pref.style[i].match, res_class) ||
	(wmName && strstr(wmName, pref.style[i].match)))
      {
	free (res_name);
	free (res_class);
	free(wmName);

	if (pref.style[i].type)
	  return pref.style[i].type;
      }
  }

  /* Didn't find the style, fail gracefully */
  free (res_name);
  free (res_class);
  free(wmName);

  return STYLE_NONE;
}
void
winCreateWindowsWindow (WindowPtr pWin)
{
  int                   iX, iY;
  int			iWidth;
  int			iHeight;
  HWND			hWnd;
  WNDCLASSEX		wc;
  winWindowPriv(pWin);
  HICON			hIcon;
  HICON			hIconSmall;
#define CLASS_NAME_LENGTH 512
  char                  pszClass[CLASS_NAME_LENGTH], pszWindowID[12];
  char                  *res_name, *res_class, *res_role;
  static int		s_iWindowID = 0;
  winPrivScreenPtr	pScreenPriv = pWinPriv->pScreenPriv;
  WinXSizeHints         hints;

#if CYGMULTIWINDOW_DEBUG
  ErrorF ("winCreateWindowsWindow - pWin: %08x\n", pWin);
#endif

  iX = pWin->drawable.x + GetSystemMetrics (SM_XVIRTUALSCREEN);
  iY = pWin->drawable.y + GetSystemMetrics (SM_YVIRTUALSCREEN);

  /* Default positions if none specified */
  if (!winMultiWindowGetWMNormalHints(pWin, &hints))
    hints.flags = 0;
  if ( !(hints.flags & (USPosition|PPosition)) &&
       !winMultiWindowGetTransientFor (pWin, NULL) &&
       !pWin->overrideRedirect )
    {
      iX = CW_USEDEFAULT;
      iY = CW_USEDEFAULT;
    }

  iWidth = pWin->drawable.width;
  iHeight = pWin->drawable.height;

  winSelectIcons(pWin, &hIcon, &hIconSmall); 

  /* Set standard class name prefix so we can identify window easily */
  strncpy (pszClass, WINDOW_CLASS_X, sizeof(pszClass));

  if (winMultiWindowGetClassHint (pWin, &res_name, &res_class))
    {
      strncat (pszClass, "-", 1);
      strncat (pszClass, res_name, CLASS_NAME_LENGTH - strlen (pszClass));
      strncat (pszClass, "-", 1);
      strncat (pszClass, res_class, CLASS_NAME_LENGTH - strlen (pszClass));
      
      /* Check if a window class is provided by the WM_WINDOW_ROLE property,
       * if not use the WM_CLASS information.
       * For further information see:
       * http://tronche.com/gui/x/icccm/sec-5.html
       */ 
      if (winMultiWindowGetWindowRole (pWin, &res_role) )
	{
	  strcat (pszClass, "-");
	  strcat (pszClass, res_role);
	  free (res_role);
	}

      free (res_name);
      free (res_class);
    }

  /* Add incrementing window ID to make unique class name */
  snprintf (pszWindowID, sizeof(pszWindowID), "-%x", s_iWindowID++);
  pszWindowID[sizeof(pszWindowID)-1] = 0;
  strcat (pszClass, pszWindowID);

#if CYGMULTIWINDOW_DEBUG
  ErrorF ("winCreateWindowsWindow - Creating class: %s\n", pszClass);
#endif

  /* Setup our window class */
  wc.cbSize = sizeof(wc);
  wc.style = CS_HREDRAW | CS_VREDRAW;
  wc.lpfnWndProc = winTopLevelWindowProc;
  wc.cbClsExtra = 0;
  wc.cbWndExtra = 0;
  wc.hInstance = g_hInstance;
  wc.hIcon = hIcon;
  wc.hIconSm = hIconSmall;
  wc.hCursor = 0;
  wc.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH);
  wc.lpszMenuName = NULL;
  wc.lpszClassName = pszClass;
  RegisterClassEx (&wc);

  /* Create the window */
  /* Make it OVERLAPPED in create call since WS_POPUP doesn't support */
  /* CW_USEDEFAULT, change back to popup after creation */
  hWnd = CreateWindowExA (WS_EX_TOOLWINDOW,	/* Extended styles */
			  pszClass,		/* Class name */
			  WINDOW_TITLE_X,	/* Window name */
			  WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN | WS_CLIPSIBLINGS,
			  iX,			/* Horizontal position */
			  iY,			/* Vertical position */
			  iWidth,		/* Right edge */ 
			  iHeight,		/* Bottom edge */
			  (HWND) NULL,		/* No parent or owner window */
			  (HMENU) NULL,		/* No menu */
			  GetModuleHandle (NULL), /* Instance handle */
			  pWin);		/* ScreenPrivates */
  if (hWnd == NULL)
    {
      ErrorF ("winCreateWindowsWindow - CreateWindowExA () failed: %d\n",
	      (int) GetLastError ());
    }
 
  /* Change style back to popup, already placed... */
  SetWindowLong (hWnd, GWL_STYLE, WS_POPUP | WS_CLIPCHILDREN | WS_CLIPSIBLINGS);
  SetWindowPos (hWnd, 0, 0, 0, 0, 0,
		SWP_FRAMECHANGED | SWP_NOZORDER | SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
  /* Make sure it gets the proper system menu for a WS_POPUP, too */
  GetSystemMenu (hWnd, TRUE);

  pWinPriv->hWnd = hWnd;

  /* Cause any .XWinrc menus to be added in main WNDPROC */
  PostMessage (hWnd, WM_INIT_SYS_MENU, 0, 0);
  
  SetProp (pWinPriv->hWnd, WIN_WID_PROP, (HANDLE) winGetWindowID(pWin));

  /* Flag that this Windows window handles its own activation */
  SetProp (pWinPriv->hWnd, WIN_NEEDMANAGE_PROP, (HANDLE) 0);

  /* Call engine-specific create window procedure */
  (*pScreenPriv->pwinFinishCreateWindowsWindow) (pWin);
}