/*
 * a GUI application for displaying a console
 *	USER32 back end
 * Copyright 2001 Eric Pouech
 */

#include <stdio.h>
#include "winecon_user.h"

/* mapping console colors to RGB values */
COLORREF	WCUSER_ColorMap[16] = 
{
    RGB(0x00, 0x00, 0x00), RGB(0x00, 0x00, 0x80), RGB(0x00, 0x80, 0x00), RGB(0x00, 0x80, 0x80),
    RGB(0x80, 0x00, 0x00), RGB(0x80, 0x00, 0x80), RGB(0x80, 0x80, 0x00), RGB(0x80, 0x80, 0x80),
    RGB(0xC0, 0xC0, 0xC0), RGB(0x00, 0x00, 0xFF), RGB(0x00, 0xFF, 0x00), RGB(0x00, 0xFF, 0xFF),
    RGB(0xFF, 0x00, 0x00), RGB(0xFF, 0x00, 0xFF), RGB(0xFF, 0xFF, 0x00), RGB(0xFF, 0xFF, 0xFF),
};

/******************************************************************
 *		WCUSER_FillMemDC
 *
 * Fills the Mem DC with current cells values
 */
static void WCUSER_FillMemDC(const struct inner_data* data, int upd_tp, int upd_bm)
{
    unsigned		i, j, k;
    CHAR_INFO*		cell;
    HFONT		hOldFont;
    WORD		attr;
    WCHAR*		line;

    if (!(line = HeapAlloc(GetProcessHeap(), 0, data->curcfg.sb_width * sizeof(WCHAR))))
    {Trace(0, "OOM\n"); return;}

    hOldFont = SelectObject(PRIVATE(data)->hMemDC, PRIVATE(data)->hFont);
    for (j = upd_tp; j <= upd_bm; j++)
    {
	cell = &data->cells[j * data->curcfg.sb_width];
	for (i = 0; i < data->curcfg.win_width; i++)
	{
	    attr = cell[i].Attributes;
	    SetBkColor(PRIVATE(data)->hMemDC, WCUSER_ColorMap[attr & 0x0F]);
	    SetTextColor(PRIVATE(data)->hMemDC, WCUSER_ColorMap[(attr >> 4) & 0x0F]);
	    for (k = i; k < data->curcfg.win_width && cell[k].Attributes == attr; k++)
	    {
		line[k - i] = cell[k].Char.UnicodeChar;
	    }
	    TextOut(PRIVATE(data)->hMemDC, i * data->curcfg.cell_width, j * data->curcfg.cell_height, 
		    line, k - i);
	    i = k - 1;
	}
    }
    SelectObject(PRIVATE(data)->hMemDC, hOldFont);
    HeapFree(GetProcessHeap(), 0, line);
}

/******************************************************************
 *		WCUSER_NewBitmap
 *
 * Either the font geometry or the sb geometry has changed. we need to recreate the
 * bitmap geometry
 */
static void WCUSER_NewBitmap(struct inner_data* data, BOOL fill)
{
    HDC         hDC;
    HBITMAP	hnew, hold;

    if (!data->curcfg.sb_width || !data->curcfg.sb_height || !(hDC = GetDC(PRIVATE(data)->hWnd))) 
        return;
    hnew = CreateCompatibleBitmap(hDC, 
				  data->curcfg.sb_width  * data->curcfg.cell_width, 
				  data->curcfg.sb_height * data->curcfg.cell_height);
    ReleaseDC(PRIVATE(data)->hWnd, hDC);
    hold = SelectObject(PRIVATE(data)->hMemDC, hnew);

    if (PRIVATE(data)->hBitmap)
    {
	if (hold == PRIVATE(data)->hBitmap)
	    DeleteObject(PRIVATE(data)->hBitmap);
	else
	    Trace(0, "leak\n");
    }
    PRIVATE(data)->hBitmap = hnew;
    if (fill)
	WCUSER_FillMemDC(data, 0, data->curcfg.sb_height - 1);
}

/******************************************************************
 *		WCUSER_ResizeScreenBuffer
 *
 *
 */
static void WCUSER_ResizeScreenBuffer(struct inner_data* data)
{
    WCUSER_NewBitmap(data, FALSE);
}

/******************************************************************
 *		WCUSER_PosCursor
 *
 * Set a new position for the cursor
 */
static void	WCUSER_PosCursor(const struct inner_data* data)
{
    if (PRIVATE(data)->hWnd != GetFocus() || !data->curcfg.cursor_visible) return;

    SetCaretPos((data->cursor.X - data->curcfg.win_pos.X) * data->curcfg.cell_width, 
		(data->cursor.Y - data->curcfg.win_pos.Y) * data->curcfg.cell_height);
    ShowCaret(PRIVATE(data)->hWnd); 
}

/******************************************************************
 *		WCUSER_ShapeCursor
 *
 * Sets a new shape for the cursor
 */
void	WCUSER_ShapeCursor(struct inner_data* data, int size, int vis, BOOL force)
{
    if (force || size != data->curcfg.cursor_size)
    {
	if (data->curcfg.cursor_visible && PRIVATE(data)->hWnd == GetFocus()) DestroyCaret();
	if (PRIVATE(data)->cursor_bitmap) DeleteObject(PRIVATE(data)->cursor_bitmap);
	PRIVATE(data)->cursor_bitmap = (HBITMAP)0;
	if (size != 100)
	{
	    int		w16b; /* number of byets per row, aligned on word size */
	    BYTE*	ptr;
	    int		i, j, nbl;

	    w16b = ((data->curcfg.cell_width + 15) & ~15) / 8;
	    ptr = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, w16b * data->curcfg.cell_height);
	    if (!ptr) {Trace(0, "OOM\n"); return;}
	    nbl = max((data->curcfg.cell_height * size) / 100, 1);
	    for (j = data->curcfg.cell_height - nbl; j < data->curcfg.cell_height; j++)
	    {
		for (i = 0; i < data->curcfg.cell_width; i++)
		{
		    ptr[w16b * j + (i / 8)] |= 0x80 >> (i & 7);
		}
	    }
	    PRIVATE(data)->cursor_bitmap = CreateBitmap(data->curcfg.cell_width, 
                                               data->curcfg.cell_height, 1, 1, ptr);
	    HeapFree(GetProcessHeap(), 0, ptr);
	}
	data->curcfg.cursor_size = size;
	data->curcfg.cursor_visible = -1;
    }

    vis = (vis) ? TRUE : FALSE;
    if (force || vis != data->curcfg.cursor_visible)
    {
	data->curcfg.cursor_visible = vis;
	if (PRIVATE(data)->hWnd == GetFocus())
	{
	    if (vis)
	    {
		CreateCaret(PRIVATE(data)->hWnd, PRIVATE(data)->cursor_bitmap, 
                            data->curcfg.cell_width, data->curcfg.cell_height);
		WCUSER_PosCursor(data);
	    }
	    else
	    {
		DestroyCaret();
	    }
	}
    }
}

/******************************************************************
 *		INECON_ComputePositions
 *
 * Recomputes all the components (mainly scroll bars) positions
 */
void	WCUSER_ComputePositions(struct inner_data* data)
{
    RECT		r;
    int			dx, dy;

    /* compute window size from desired client size */
    r.left = r.top = 0;
    r.right = data->curcfg.win_width * data->curcfg.cell_width;
    r.bottom = data->curcfg.win_height * data->curcfg.cell_height;

    if (IsRectEmpty(&r))
    {
	ShowWindow(PRIVATE(data)->hWnd, SW_HIDE);
	return;
    }

    AdjustWindowRect(&r, GetWindowLong(PRIVATE(data)->hWnd, GWL_STYLE), FALSE);

    dx = dy = 0;
    if (data->curcfg.sb_width > data->curcfg.win_width)
    {
	dy = GetSystemMetrics(SM_CYHSCROLL);
	SetScrollRange(PRIVATE(data)->hWnd, SB_HORZ, 0, 
                       data->curcfg.sb_width - data->curcfg.win_width, FALSE);
	SetScrollPos(PRIVATE(data)->hWnd, SB_HORZ, 0, FALSE); /* FIXME */
	ShowScrollBar(PRIVATE(data)->hWnd, SB_HORZ, TRUE);
    }
    else
    {
	ShowScrollBar(PRIVATE(data)->hWnd, SB_HORZ, FALSE);
    }

    if (data->curcfg.sb_height > data->curcfg.win_height)
    {
	dx = GetSystemMetrics(SM_CXVSCROLL);
	SetScrollRange(PRIVATE(data)->hWnd, SB_VERT, 0, 
                       data->curcfg.sb_height - data->curcfg.win_height, FALSE);
	SetScrollPos(PRIVATE(data)->hWnd, SB_VERT, 0, FALSE); /* FIXME */
	ShowScrollBar(PRIVATE(data)->hWnd, SB_VERT, TRUE);
    }	
    else
    {
	ShowScrollBar(PRIVATE(data)->hWnd, SB_VERT, FALSE);
    }

    SetWindowPos(PRIVATE(data)->hWnd, 0, 0, 0, r.right - r.left + dx, r.bottom - r.top + dy,
		 SWP_NOMOVE|SWP_NOZORDER|SWP_SHOWWINDOW);
    WCUSER_ShapeCursor(data, data->curcfg.cursor_size, data->curcfg.cursor_visible, TRUE);
    WCUSER_PosCursor(data);
}

/******************************************************************
 *		WCUSER_SetTitle
 *
 * Sets the title to the wine console
 */
static void	WCUSER_SetTitle(const struct inner_data* data)
{
    WCHAR	buffer[256];	

    if (WINECON_GetConsoleTitle(data->hConIn, buffer, sizeof(buffer)))
	SetWindowText(PRIVATE(data)->hWnd, buffer);
}

/******************************************************************
 *		FontEqual
 *
 *
 */
BOOL WCUSER_AreFontsEqual(const struct config_data* config, const LOGFONT* lf)
{
    return lf->lfHeight == config->cell_height &&
        lf->lfWidth  == config->cell_width &&
        lf->lfWeight == config->font_weight &&
        !lf->lfItalic && !lf->lfUnderline && !lf->lfStrikeOut &&
        !lstrcmpW(lf->lfFaceName, config->face_name);
}

/******************************************************************
 *		CopyFont
 *
 *
 */
void WCUSER_CopyFont(struct config_data* config, const LOGFONT* lf)
{
    config->cell_width  = lf->lfWidth;
    config->cell_height = lf->lfHeight;
    config->font_weight  = lf->lfWeight;
    lstrcpyW(config->face_name, lf->lfFaceName);
}

/******************************************************************
 *		WCUSER_InitFont
 *
 * create a hFont from the settings saved in registry...
 * (called on init, assuming no font has been created before)
 */
BOOL	WCUSER_InitFont(struct inner_data* data)
{
    LOGFONT lf;
        
    lf.lfHeight        = -data->curcfg.cell_height;
    lf.lfWidth         = data->curcfg.cell_width;
    lf.lfEscapement    = 0;
    lf.lfOrientation   = 0;
    lf.lfWeight        = data->curcfg.font_weight;
    lf.lfItalic        = FALSE;
    lf.lfUnderline     = FALSE;
    lf.lfStrikeOut     = FALSE;
    lf.lfCharSet       = DEFAULT_CHARSET;
    lf.lfOutPrecision  = OUT_DEFAULT_PRECIS;
    lf.lfClipPrecision = CLIP_DEFAULT_PRECIS; 
    lf.lfQuality       = DEFAULT_QUALITY;
    lf.lfPitchAndFamily = FIXED_PITCH | FF_DONTCARE;
    lstrcpy(lf.lfFaceName, data->curcfg.face_name);
    PRIVATE(data)->hFont = CreateFontIndirect(&lf);
    if (!PRIVATE(data)->hFont) return FALSE;

    WCUSER_ComputePositions(data);
    WCUSER_NewBitmap(data, TRUE);
    InvalidateRect(PRIVATE(data)->hWnd, NULL, FALSE);
    UpdateWindow(PRIVATE(data)->hWnd);
    return TRUE;
}

/******************************************************************
 *		WCUSER_SetFont
 *
 * sets logfont as the new font for the console
 */
BOOL	WCUSER_SetFont(struct inner_data* data, const LOGFONT* logfont)
{
    if (WCUSER_AreFontsEqual(&data->curcfg, logfont)) return TRUE;
    if (PRIVATE(data)->hFont) DeleteObject(PRIVATE(data)->hFont);
    PRIVATE(data)->hFont = CreateFontIndirect(logfont);
    if (!PRIVATE(data)->hFont) {Trace(0, "wrong font\n");return FALSE;}
    WCUSER_CopyFont(&data->curcfg, logfont);

    WCUSER_ComputePositions(data);
    WCUSER_NewBitmap(data, TRUE);
    InvalidateRect(PRIVATE(data)->hWnd, NULL, FALSE);
    UpdateWindow(PRIVATE(data)->hWnd);
    return TRUE;
}

/******************************************************************
 *		WCUSER_GetCell
 *
 * Get a cell from the a relative coordinate in window (takes into
 * account the scrolling)
 */
static COORD	WCUSER_GetCell(const struct inner_data* data, LPARAM lParam)
{
    COORD	c;

    c.X = data->curcfg.win_pos.X + (short)LOWORD(lParam) / data->curcfg.cell_width;
    c.Y = data->curcfg.win_pos.Y + (short)HIWORD(lParam) / data->curcfg.cell_height;

    return c;
}

/******************************************************************
 *		WCUSER_GetSelectionRect
 *
 * Get the selection rectangle
 */
static void	WCUSER_GetSelectionRect(const struct inner_data* data, LPRECT r)
{
    r->left   = (min(PRIVATE(data)->selectPt1.X, PRIVATE(data)->selectPt2.X)    ) * data->curcfg.cell_width;
    r->top    = (min(PRIVATE(data)->selectPt1.Y, PRIVATE(data)->selectPt2.Y)    ) * data->curcfg.cell_height;
    r->right  = (max(PRIVATE(data)->selectPt1.X, PRIVATE(data)->selectPt2.X) + 1) * data->curcfg.cell_width;
    r->bottom = (max(PRIVATE(data)->selectPt1.Y, PRIVATE(data)->selectPt2.Y) + 1) * data->curcfg.cell_height;
}

/******************************************************************
 *		WCUSER_SetSelection
 *
 *
 */
static void	WCUSER_SetSelection(const struct inner_data* data, HDC hRefDC)
{
    HDC		hDC;
    RECT	r;

    WCUSER_GetSelectionRect(data, &r);
    hDC = hRefDC ? hRefDC : GetDC(PRIVATE(data)->hWnd);
    if (hDC)
    {
	if (PRIVATE(data)->hWnd == GetFocus() && data->curcfg.cursor_visible)
	    HideCaret(PRIVATE(data)->hWnd);
	InvertRect(hDC, &r);
	if (hDC != hRefDC)
	    ReleaseDC(PRIVATE(data)->hWnd, hDC);
	if (PRIVATE(data)->hWnd == GetFocus() && data->curcfg.cursor_visible)
	    ShowCaret(PRIVATE(data)->hWnd);
    }
}

/******************************************************************
 *		WCUSER_MoveSelection
 *
 *
 */
static void	WCUSER_MoveSelection(struct inner_data* data, COORD dst, BOOL final)
{
    RECT	r;
    HDC		hDC;

    WCUSER_GetSelectionRect(data, &r);
    hDC = GetDC(PRIVATE(data)->hWnd);
    if (hDC)
    {
	if (PRIVATE(data)->hWnd == GetFocus() && data->curcfg.cursor_visible)
	    HideCaret(PRIVATE(data)->hWnd);
	InvertRect(hDC, &r);
    }
    PRIVATE(data)->selectPt2 = dst;
    if (hDC)
    {
	WCUSER_GetSelectionRect(data, &r);
	InvertRect(hDC, &r);
	ReleaseDC(PRIVATE(data)->hWnd, hDC);
	if (PRIVATE(data)->hWnd == GetFocus() && data->curcfg.cursor_visible)
	    ShowCaret(PRIVATE(data)->hWnd);
    }
    if (final)
    {
	ReleaseCapture();
	PRIVATE(data)->hasSelection = TRUE;
    }
}

/******************************************************************
 *		WCUSER_CopySelectionToClipboard
 *
 * Copies the current selection into the clipboard
 */
static void	WCUSER_CopySelectionToClipboard(const struct inner_data* data)
{
    HANDLE	hMem;
    LPWSTR	p;
    unsigned	w, h;

    w = abs(PRIVATE(data)->selectPt1.X - PRIVATE(data)->selectPt2.X) + 2;
    h = abs(PRIVATE(data)->selectPt1.Y - PRIVATE(data)->selectPt2.Y) + 1;

    if (!OpenClipboard(PRIVATE(data)->hWnd)) return;
    EmptyClipboard();

    hMem = GlobalAlloc(GMEM_MOVEABLE, (w * h - 1) * sizeof(WCHAR));
    if (hMem && (p = GlobalLock(hMem)))
    {
	COORD	c;
	int	y;

	c.X = data->curcfg.win_pos.X + min(PRIVATE(data)->selectPt1.X, PRIVATE(data)->selectPt2.X);
	c.Y = data->curcfg.win_pos.Y + min(PRIVATE(data)->selectPt1.Y, PRIVATE(data)->selectPt2.Y);
	
	for (y = 0; y < h; y++, c.Y++)
	{
	    ReadConsoleOutputCharacter(data->hConOut, &p[y * w], w - 1, c, NULL);
	    if (y < h - 1) p[y * w + w - 1] = '\n';
	}
	GlobalUnlock(hMem);
	SetClipboardData(CF_UNICODETEXT, hMem);
    }
    CloseClipboard();
}

/******************************************************************
 *		WCUSER_PasteFromClipboard
 *
 *
 */
static void	WCUSER_PasteFromClipboard(struct inner_data* data)
{
    HANDLE	h;
    WCHAR*	ptr;

    if (!OpenClipboard(PRIVATE(data)->hWnd)) return;
    h = GetClipboardData(CF_UNICODETEXT);
    if (h && (ptr = GlobalLock(h)))
    {
	int		i, len = GlobalSize(h) / sizeof(WCHAR);
	INPUT_RECORD	ir[2];
	DWORD		n;
	SHORT		sh;

	ir[0].EventType = KEY_EVENT;
	ir[0].Event.KeyEvent.wRepeatCount = 0;
	ir[0].Event.KeyEvent.dwControlKeyState = 0;
	ir[0].Event.KeyEvent.bKeyDown = TRUE;

	/* generate the corresponding input records */
	for (i = 0; i < len; i++)
	{
	    /* FIXME: the modifying keys are not generated (shift, ctrl...) */
	    sh = VkKeyScan(ptr[i]);
	    ir[0].Event.KeyEvent.wVirtualKeyCode = LOBYTE(sh);
	    ir[0].Event.KeyEvent.wVirtualScanCode = MapVirtualKey(LOBYTE(sh), 0);
	    ir[0].Event.KeyEvent.uChar.UnicodeChar = ptr[i];
	    
	    ir[1] = ir[0];
	    ir[1].Event.KeyEvent.bKeyDown = FALSE;
	    
	    WriteConsoleInput(data->hConIn, ir, 2, &n);
	}
	GlobalUnlock(h);
    }
    CloseClipboard();
}

/******************************************************************
 *		Refresh
 *
 *
 */
static void WCUSER_Refresh(const struct inner_data* data, int tp, int bm)
{
    if (data->curcfg.win_pos.Y <= bm && data->curcfg.win_pos.Y + data->curcfg.win_height >= tp)
    {
	RECT	r;

	r.left   = 0;
	r.right  = data->curcfg.win_width * data->curcfg.cell_width;
	r.top    = (tp - data->curcfg.win_pos.Y) * data->curcfg.cell_height;
	r.bottom = (bm - data->curcfg.win_pos.Y + 1) * data->curcfg.cell_height;
	InvalidateRect(PRIVATE(data)->hWnd, &r, FALSE);
	WCUSER_FillMemDC(data, tp, bm);
	UpdateWindow(PRIVATE(data)->hWnd);
    }
}

/******************************************************************
 *		WCUSER_Paint
 *
 *
 */
static void	WCUSER_Paint(const struct inner_data* data)
{
    PAINTSTRUCT		ps;

    BeginPaint(PRIVATE(data)->hWnd, &ps);
    BitBlt(ps.hdc, 0, 0, 
           data->curcfg.win_width * data->curcfg.cell_width, 
           data->curcfg.win_height * data->curcfg.cell_height,
	   PRIVATE(data)->hMemDC, 
           data->curcfg.win_pos.X * data->curcfg.cell_width, 
           data->curcfg.win_pos.Y * data->curcfg.cell_height,
	   SRCCOPY);
    if (PRIVATE(data)->hasSelection)
	WCUSER_SetSelection(data, ps.hdc);
    EndPaint(PRIVATE(data)->hWnd, &ps);
}

/******************************************************************
 *		WCUSER_Scroll
 *
 *
 */
static void WCUSER_Scroll(struct inner_data* data, int pos, BOOL horz)
{
    if (horz)
    {
	SetScrollPos(PRIVATE(data)->hWnd, SB_HORZ, pos, TRUE);
	data->curcfg.win_pos.X = pos;
	InvalidateRect(PRIVATE(data)->hWnd, NULL, FALSE);
    }
    else
    {
	SetScrollPos(PRIVATE(data)->hWnd, SB_VERT, pos, TRUE);
	data->curcfg.win_pos.Y = pos;
    }
    InvalidateRect(PRIVATE(data)->hWnd, NULL, FALSE);
}

struct font_chooser {
    struct inner_data*	data;
    int			done;
};

/******************************************************************
 *		WCUSER_ValidateFontMetric
 *
 * Returns true if the font described in tm is usable as a font for the renderer
 */
BOOL	WCUSER_ValidateFontMetric(const struct inner_data* data, const TEXTMETRIC* tm)
{
    return tm->tmMaxCharWidth * data->curcfg.win_width < GetSystemMetrics(SM_CXSCREEN) &&
	tm->tmHeight * data->curcfg.win_height < GetSystemMetrics(SM_CYSCREEN) &&
	!tm->tmItalic && !tm->tmUnderlined && !tm->tmStruckOut;
}

/******************************************************************
 *		WCUSER_ValidateFont
 *
 * Returns true if the font family described in lf is usable as a font for the renderer
 */
BOOL	WCUSER_ValidateFont(const struct inner_data* data, const LOGFONT* lf)
{
    return (lf->lfPitchAndFamily & 3) == FIXED_PITCH && 
        (lf->lfPitchAndFamily & 0xF0) == FF_MODERN &&
        lf->lfCharSet != SYMBOL_CHARSET;
}

/******************************************************************
 *		get_first_font_enum_2
 *		get_first_font_enum
 *
 * Helper functions to get a decent font for the renderer
 */
static int CALLBACK get_first_font_enum_2(const LOGFONT* lf, const TEXTMETRIC* tm, 
					  DWORD FontType, LPARAM lParam)
{
    struct font_chooser*	fc = (struct font_chooser*)lParam;

    if (WCUSER_ValidateFontMetric(fc->data, tm))
    {
	WCUSER_SetFont(fc->data, lf);
	fc->done = 1;
	return 0;
    }
    return 1;
}

static int CALLBACK get_first_font_enum(const LOGFONT* lf, const TEXTMETRIC* tm, 
					DWORD FontType, LPARAM lParam)
{
    struct font_chooser*	fc = (struct font_chooser*)lParam;

    if (WCUSER_ValidateFont(fc->data, lf))
    {
	EnumFontFamilies(PRIVATE(fc->data)->hMemDC, lf->lfFaceName, get_first_font_enum_2, lParam);
	return !fc->done; /* we just need the first matching one... */
    }
    return 1;
}

/******************************************************************
 *		WCUSER_FillMenu
 *
 *
 */
static BOOL WCUSER_FillMenu(HMENU hMenu, BOOL sep)
{
    HMENU		hSubMenu;
    HINSTANCE		hInstance = GetModuleHandle(NULL);
    WCHAR		buff[256];

    if (!hMenu) return FALSE;

    /* FIXME: error handling & memory cleanup */
    hSubMenu = CreateMenu();
    if (!hSubMenu) return FALSE;

    LoadString(hInstance, IDS_MARK, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_MARK, buff);
    LoadString(hInstance, IDS_COPY, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_COPY, buff);
    LoadString(hInstance, IDS_PASTE, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_PASTE, buff);
    LoadString(hInstance, IDS_SELECTALL, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_SELECTALL, buff);
    LoadString(hInstance, IDS_SCROLL, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_SCROLL, buff);
    LoadString(hInstance, IDS_SEARCH, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hSubMenu, -1, MF_BYPOSITION|MF_STRING, IDS_SEARCH, buff);

    if (sep) InsertMenu(hMenu, -1, MF_BYPOSITION|MF_SEPARATOR, 0, NULL);
    LoadString(hInstance, IDS_EDIT, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hMenu, -1, MF_BYPOSITION|MF_STRING|MF_POPUP, (UINT_PTR)hSubMenu, buff);
    LoadString(hInstance, IDS_DEFAULT, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hMenu, -1, MF_BYPOSITION|MF_STRING, IDS_DEFAULT, buff);
    LoadString(hInstance, IDS_PROPERTY, buff, sizeof(buff) / sizeof(WCHAR));
    InsertMenu(hMenu, -1, MF_BYPOSITION|MF_STRING, IDS_PROPERTY, buff);

    return TRUE;
}

/******************************************************************
 *		WCUSER_Create
 *
 * Creates the window for the rendering
 */
static LRESULT WCUSER_Create(HWND hWnd, LPCREATESTRUCT lpcs)
{
    struct inner_data*	data;
    HMENU		hSysMenu;

    data = lpcs->lpCreateParams;
    SetWindowLong(hWnd, 0L, (DWORD)data);
    PRIVATE(data)->hWnd = hWnd;

    data->curcfg.cursor_size = 101; /* invalid value, will trigger a complete cleanup */

    hSysMenu = GetSystemMenu(hWnd, FALSE);
    if (!hSysMenu) return 0;
    PRIVATE(data)->hPopMenu = CreatePopupMenu();
    if (!PRIVATE(data)->hPopMenu) return 0;

    WCUSER_FillMenu(hSysMenu, TRUE);
    WCUSER_FillMenu(PRIVATE(data)->hPopMenu, FALSE);

    PRIVATE(data)->hMemDC = CreateCompatibleDC(0);
    if (!PRIVATE(data)->hMemDC) {Trace(0, "no mem dc\n");return 0;}

    return 0;
}

/******************************************************************
 *		WCUSER_SetMenuDetails
 *
 * Grays / ungrays the menu items according to their state
 */
static void	WCUSER_SetMenuDetails(const struct inner_data* data)
{
    HMENU		hMenu = GetSystemMenu(PRIVATE(data)->hWnd, FALSE);

    if (!hMenu) {Trace(0, "Issue in getting menu bits\n");return;}

    /* FIXME: set the various menu items to their state (if known) */
    EnableMenuItem(hMenu, IDS_DEFAULT, MF_BYCOMMAND|MF_GRAYED);

    EnableMenuItem(hMenu, IDS_MARK, MF_BYCOMMAND|MF_GRAYED);
    EnableMenuItem(hMenu, IDS_COPY, MF_BYCOMMAND|(PRIVATE(data)->hasSelection ? MF_ENABLED : MF_GRAYED));
    EnableMenuItem(hMenu, IDS_PASTE, 
		   MF_BYCOMMAND|(IsClipboardFormatAvailable(CF_UNICODETEXT) 
				 ? MF_ENABLED : MF_GRAYED));
    /* Select all: always active */
    EnableMenuItem(hMenu, IDS_SCROLL, MF_BYCOMMAND|MF_GRAYED);
    EnableMenuItem(hMenu, IDS_SEARCH, MF_BYCOMMAND|MF_GRAYED);
}

/******************************************************************
 *		WCUSER_GenerateKeyInputRecord
 *
 * generates input_record from windows WM_KEYUP/WM_KEYDOWN messages
 */
static void    WCUSER_GenerateKeyInputRecord(struct inner_data* data, BOOL down, 
                                             WPARAM wParam, LPARAM lParam, BOOL sys)
{
    INPUT_RECORD	ir;
    DWORD		n;
    WCHAR		buf[2];
    BYTE		keyState[256];
    static	WCHAR	last; /* keep last char seen as feed for key up message */

    ir.EventType = KEY_EVENT;
    ir.Event.KeyEvent.bKeyDown = down;
    ir.Event.KeyEvent.wRepeatCount = LOWORD(lParam);
    ir.Event.KeyEvent.wVirtualKeyCode = wParam;
    
    ir.Event.KeyEvent.wVirtualScanCode = HIWORD(lParam) & 0xFF;
    GetKeyboardState(keyState);
    
    ir.Event.KeyEvent.uChar.UnicodeChar = 0;
    ir.Event.KeyEvent.dwControlKeyState = 0;
    if (lParam & (1L << 24))		ir.Event.KeyEvent.dwControlKeyState |= ENHANCED_KEY;
    if (keyState[VK_SHIFT]    & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= SHIFT_PRESSED;
    if (keyState[VK_CONTROL]  & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= LEFT_CTRL_PRESSED; /* FIXME: gotta choose one */
    if (keyState[VK_LCONTROL] & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= LEFT_CTRL_PRESSED;
    if (keyState[VK_RCONTROL] & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= RIGHT_CTRL_PRESSED;
    if (sys)				ir.Event.KeyEvent.dwControlKeyState |= LEFT_ALT_PRESSED; /* FIXME: gotta choose one */
    if (keyState[VK_LMENU]    & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= LEFT_ALT_PRESSED;
    if (keyState[VK_RMENU]    & 0x80)	ir.Event.KeyEvent.dwControlKeyState |= RIGHT_ALT_PRESSED;
    if (keyState[VK_CAPITAL]  & 0x01)	ir.Event.KeyEvent.dwControlKeyState |= CAPSLOCK_ON;	    
    if (keyState[VK_NUMLOCK]  & 0x01)	ir.Event.KeyEvent.dwControlKeyState |= NUMLOCK_ON;
    if (keyState[VK_SCROLL]   & 0x01)	ir.Event.KeyEvent.dwControlKeyState |= SCROLLLOCK_ON;

    if (PRIVATE(data)->hasSelection && ir.Event.KeyEvent.dwControlKeyState == 0 && 
	ir.Event.KeyEvent.wVirtualKeyCode == VK_RETURN)
    {
	PRIVATE(data)->hasSelection = FALSE;
	WCUSER_SetSelection(data, 0);
	WCUSER_CopySelectionToClipboard(data);
	return;
    }
    
    if (!(ir.Event.KeyEvent.dwControlKeyState & ENHANCED_KEY))
    {
	if (down)
	{
	    switch (ToUnicode(wParam, HIWORD(lParam), keyState, buf, 2, 0))
	    {
	    case 2:
		/* FIXME... should generate two events... */
		/* fall thru */
	    case 1:	
		last = buf[0];
		break;
	    default:
		last = 0;
		break;
	    }
	}
	ir.Event.KeyEvent.uChar.UnicodeChar = last; /* FIXME HACKY... and buggy 'coz it should be a stack, not a single value */
	if (!down) last = 0;
    }

    WriteConsoleInput(data->hConIn, &ir, 1, &n);
}

/******************************************************************
 *		WCUSER_Proc
 *
 *
 */
static LRESULT CALLBACK WCUSER_Proc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
    struct inner_data*	data = (struct inner_data*)GetWindowLong(hWnd, 0);

    switch (uMsg)
    {
    case WM_CREATE:
        return WCUSER_Create(hWnd, (LPCREATESTRUCT)lParam);
    case WM_DESTROY:
	PRIVATE(data)->hWnd = 0;
	PostQuitMessage(0);
	break;
    case WM_PAINT:
	WCUSER_Paint(data);
	break;
    case WM_KEYDOWN:
    case WM_KEYUP:
	WCUSER_GenerateKeyInputRecord(data, uMsg == WM_KEYDOWN, wParam, lParam, FALSE);
	break;
    case WM_SYSKEYDOWN:
    case WM_SYSKEYUP:
	WCUSER_GenerateKeyInputRecord(data, uMsg == WM_SYSKEYDOWN, wParam, lParam, TRUE);
	break;
    case WM_LBUTTONDOWN:
	/* EPP if (wParam != MK_LBUTTON) */
	if (PRIVATE(data)->hasSelection)
	{
	    PRIVATE(data)->hasSelection = FALSE;
	}
	else
	{
	    PRIVATE(data)->selectPt1 = PRIVATE(data)->selectPt2 = WCUSER_GetCell(data, lParam);
	    SetCapture(PRIVATE(data)->hWnd);
	}
	WCUSER_SetSelection(data, 0);
	break;
    case WM_MOUSEMOVE:
	/* EPP if (wParam != MK_LBUTTON) */
        if (GetCapture() == PRIVATE(data)->hWnd)
	{
	    WCUSER_MoveSelection(data, WCUSER_GetCell(data, lParam), FALSE);
	}
	break;
    case WM_LBUTTONUP:
	/* EPP if (wParam != MK_LBUTTON) */
        if (GetCapture() == PRIVATE(data)->hWnd)
	{
	    WCUSER_MoveSelection(data, WCUSER_GetCell(data, lParam), TRUE);
	}
	break;
    case WM_SETFOCUS:
	if (data->curcfg.cursor_visible)
	{
	    CreateCaret(PRIVATE(data)->hWnd, PRIVATE(data)->cursor_bitmap, 
                        data->curcfg.cell_width, data->curcfg.cell_height); 
	    WCUSER_PosCursor(data);
	}
        break; 
    case WM_KILLFOCUS: 
	if (data->curcfg.cursor_visible)
	    DestroyCaret(); 
	break;
    case WM_HSCROLL: 
        {
	    int	pos = data->curcfg.win_pos.X;

	    switch (LOWORD(wParam)) 
	    { 
            case SB_PAGEUP: 	pos -= 8; 		break; 
            case SB_PAGEDOWN: 	pos += 8; 		break; 
            case SB_LINEUP: 	pos--;			break;
	    case SB_LINEDOWN: 	pos++;	 		break;
            case SB_THUMBTRACK: pos = HIWORD(wParam);	break;
            default: 					break;
	    } 
	    if (pos < 0) pos = 0;
	    if (pos > data->curcfg.sb_width - data->curcfg.win_width) 
                pos = data->curcfg.sb_width - data->curcfg.win_width;
	    if (pos != data->curcfg.win_pos.X)
	    {
		ScrollWindow(hWnd, (data->curcfg.win_pos.X - pos) * data->curcfg.cell_width, 0, 
                             NULL, NULL);
		data->curcfg.win_pos.X = pos;
		SetScrollPos(hWnd, SB_HORZ, pos, TRUE); 
		UpdateWindow(hWnd); 
		WCUSER_PosCursor(data);
		WINECON_NotifyWindowChange(data);
	    }
        } 
	break;
    case WM_VSCROLL: 
        {
	    int	pos = data->curcfg.win_pos.Y;

	    switch (LOWORD(wParam)) 
	    { 
            case SB_PAGEUP: 	pos -= 8; 		break; 
            case SB_PAGEDOWN: 	pos += 8; 		break; 
            case SB_LINEUP: 	pos--;			break;
	    case SB_LINEDOWN: 	pos++;	 		break;
            case SB_THUMBTRACK: pos = HIWORD(wParam);	break;
            default: 					break;
	    } 
	    if (pos < 0) pos = 0;
	    if (pos > data->curcfg.sb_height - data->curcfg.win_height) 
                pos = data->curcfg.sb_height - data->curcfg.win_height;
	    if (pos != data->curcfg.win_pos.Y)
	    {
		ScrollWindow(hWnd, 0, (data->curcfg.win_pos.Y - pos) * data->curcfg.cell_height, 
                             NULL, NULL);
		data->curcfg.win_pos.Y = pos;
		SetScrollPos(hWnd, SB_VERT, pos, TRUE); 
		UpdateWindow(hWnd); 
		WCUSER_PosCursor(data);
		WINECON_NotifyWindowChange(data);
	    }
        } 
	break;
    case WM_SYSCOMMAND:
	switch (wParam)
	{
	case IDS_DEFAULT:
	    WCUSER_GetProperties(data, FALSE);
	    break;
	case IDS_PROPERTY:
	    WCUSER_GetProperties(data, TRUE);
	    break;
	default: 
	    return DefWindowProc(hWnd, uMsg, wParam, lParam);
	}
	break;
    case WM_RBUTTONDOWN:
        if ((wParam & (MK_CONTROL|MK_SHIFT)) == data->curcfg.menu_mask)
        {
            RECT        r;

            GetWindowRect(hWnd, &r);
            TrackPopupMenu(PRIVATE(data)->hPopMenu, TPM_LEFTALIGN|TPM_TOPALIGN, 
                           r.left + LOWORD(lParam), r.top + HIWORD(lParam), 0, hWnd, NULL);
        }
	break;    
    case WM_COMMAND:
	switch (wParam)
	{
	case IDS_DEFAULT:
	    WCUSER_GetProperties(data, FALSE);
	    break;
	case IDS_PROPERTY:
	    WCUSER_GetProperties(data, TRUE);
	    break;
	case IDS_MARK:
	    goto niy;
	case IDS_COPY:
	    PRIVATE(data)->hasSelection = FALSE;
	    WCUSER_SetSelection(data, 0);
	    WCUSER_CopySelectionToClipboard(data);
	    break;
	case IDS_PASTE:
	    WCUSER_PasteFromClipboard(data);
	    break;
	case IDS_SELECTALL:
	    PRIVATE(data)->selectPt1.X = PRIVATE(data)->selectPt1.Y = 0;
	    PRIVATE(data)->selectPt2.X = (data->curcfg.sb_width - 1) * data->curcfg.cell_width;
	    PRIVATE(data)->selectPt2.Y = (data->curcfg.sb_height - 1) * data->curcfg.cell_height;
	    WCUSER_SetSelection(data, 0);
	    PRIVATE(data)->hasSelection = TRUE;
	    break;
	case IDS_SCROLL:
	case IDS_SEARCH:
	niy:
	    Trace(0, "unhandled yet command: %x\n", wParam);
	    break;
	default: 
	    return DefWindowProc(hWnd, uMsg, wParam, lParam);
	}
	break;
    case WM_INITMENUPOPUP:
	if (!HIWORD(lParam))	return DefWindowProc(hWnd, uMsg, wParam, lParam);
	WCUSER_SetMenuDetails(data);
	break;
    default:
	return DefWindowProc(hWnd, uMsg, wParam, lParam);
    }
    return 0;
}

/******************************************************************
 *		WCUSER_DeleteBackend
 *
 *
 */
void WCUSER_DeleteBackend(struct inner_data* data)
{
    if (!PRIVATE(data)) return;
    if (PRIVATE(data)->hWnd)		DestroyWindow(PRIVATE(data)->hWnd);
    if (PRIVATE(data)->hFont)		DeleteObject(PRIVATE(data)->hFont);
    if (PRIVATE(data)->cursor_bitmap)	DeleteObject(PRIVATE(data)->cursor_bitmap);
    if (PRIVATE(data)->hMemDC)		DeleteDC(PRIVATE(data)->hMemDC);
    if (PRIVATE(data)->hBitmap)		DeleteObject(PRIVATE(data)->hBitmap);
    HeapFree(GetProcessHeap(), 0, PRIVATE(data));
}

/******************************************************************
 *		WCUSER_MainLoop
 *
 *
 */
static int WCUSER_MainLoop(struct inner_data* data)
{
    MSG		msg;

    for (;;) 
    {
	switch (MsgWaitForMultipleObjects(1, &data->hSynchro, FALSE, INFINITE, QS_ALLINPUT))
	{
	case WAIT_OBJECT_0:
	    if (!WINECON_GrabChanges(data))
		PostQuitMessage(0);
	    break;
	case WAIT_OBJECT_0+1:
	    switch (GetMessage(&msg, 0, 0, 0))
	    {
	    case -1: /* the event handle became invalid, so exit */
		return -1;
	    case 0: /* WM_QUIT has been posted */
		return 0;
	    default:
		DispatchMessage(&msg);
		break;
	    }
	    break;
	default:
	    Trace(0, "got pb\n");
	    /* err */
	    break;
	}
    }	
}

/******************************************************************
 *		WCUSER_InitBackend
 *
 * Initialisation part II: creation of window.
 *
 */
BOOL WCUSER_InitBackend(struct inner_data* data)
{
    static WCHAR wClassName[] = {'W','i','n','e','C','o','n','s','o','l','e','C','l','a','s','s',0};

    WNDCLASS		wndclass;

    data->private = HeapAlloc(GetProcessHeap(), 0, sizeof(struct inner_data_user));
    if (!data->private) return FALSE;

    data->fnMainLoop = WCUSER_MainLoop;
    data->fnPosCursor = WCUSER_PosCursor;
    data->fnShapeCursor = WCUSER_ShapeCursor;
    data->fnComputePositions = WCUSER_ComputePositions;
    data->fnRefresh = WCUSER_Refresh;
    data->fnResizeScreenBuffer = WCUSER_ResizeScreenBuffer;
    data->fnSetTitle = WCUSER_SetTitle;
    data->fnScroll = WCUSER_Scroll;
    data->fnDeleteBackend = WCUSER_DeleteBackend;

    wndclass.style         = 0;
    wndclass.lpfnWndProc   = WCUSER_Proc;
    wndclass.cbClsExtra    = 0;
    wndclass.cbWndExtra    = sizeof(DWORD);
    wndclass.hInstance     = GetModuleHandle(NULL);
    wndclass.hIcon         = LoadIcon(0, IDI_WINLOGO);
    wndclass.hCursor       = LoadCursor(0, IDC_ARROW);
    wndclass.hbrBackground = GetStockObject(BLACK_BRUSH);
    wndclass.lpszMenuName  = NULL;
    wndclass.lpszClassName = wClassName;
  
    RegisterClass(&wndclass);

    CreateWindow(wndclass.lpszClassName, NULL,
		 WS_OVERLAPPED|WS_CAPTION|WS_SYSMENU|WS_THICKFRAME|WS_MINIMIZEBOX|WS_HSCROLL|WS_VSCROLL, 
		 CW_USEDEFAULT, CW_USEDEFAULT, 0, 0, 0, 0, wndclass.hInstance, data);   
    if (!PRIVATE(data)->hWnd) return FALSE;

    /* force update of current data */
    WINECON_GrabChanges(data);

    if (!WCUSER_InitFont(data))
    {
        struct font_chooser fc;
        /* try to find an acceptable font */
        fc.data = data;
        fc.done = 0;
        EnumFontFamilies(PRIVATE(data)->hMemDC, NULL, get_first_font_enum, (LPARAM)&fc);
        return fc.done;
    }
    return TRUE;
}



