/*
 * Scroll windows and DCs
 *
 * Copyright  David W. Metcalfe, 1993
 *
 */

#include <stdlib.h>
#include "windows.h"
#include "gdi.h"
#include "scroll.h"
#include "stddebug.h"
/* #define DEBUG_SCROLL */
#include "debug.h"


static int RgnType;


/*************************************************************************
 *             ScrollWindow         (USER.61)
 */

void ScrollWindow(HWND hwnd, short dx, short dy, LPRECT rect, LPRECT clipRect)
{
    HDC hdc;
    HRGN hrgnUpdate;
    RECT rc, cliprc;

    dprintf_scroll(stddeb,"ScrollWindow: dx=%d, dy=%d, rect=%d,%d,%d,%d\n", 
	   dx, dy, rect->left, rect->top, rect->right, rect->bottom);

    hdc = GetDC(hwnd);

    if (rect == NULL)
	GetClientRect(hwnd, &rc);
    else
	CopyRect(&rc, rect);
    if (clipRect == NULL)
	GetClientRect(hwnd, &cliprc);
    else
	CopyRect(&cliprc, clipRect);

    hrgnUpdate = CreateRectRgn(0, 0, 0, 0);
    ScrollDC(hdc, dx, dy, &rc, &cliprc, hrgnUpdate, NULL);
    InvalidateRgn(hwnd, hrgnUpdate, TRUE);
    ReleaseDC(hwnd, hdc);
}


/*************************************************************************
 *             ScrollDC         (USER.221)
 */

BOOL ScrollDC(HDC hdc, short dx, short dy, LPRECT rc, LPRECT cliprc,
	      HRGN hrgnUpdate, LPRECT rcUpdate)
{
    HRGN hrgnClip, hrgn1, hrgn2;
    POINT src, dest;
    short width, height;
    DC *dc = (DC *)GDI_GetObjPtr(hdc, DC_MAGIC);

    dprintf_scroll(stddeb, "ScrollDC: dx=%d, dy=%d, rc=%d,%d,%d,%d\n", dx, dy,
	   rc->left, rc->top, rc->right, rc->bottom);

    if (rc == NULL)
	return FALSE;

    if (cliprc)
    {
	hrgnClip = CreateRectRgnIndirect(cliprc);
	SelectClipRgn(hdc, hrgnClip);
    }

    if (dx > 0)
    {
	src.x = XDPTOLP(dc, rc->left);
	dest.x = XDPTOLP(dc, rc->left + abs(dx));
    }
    else
    {
	src.x = XDPTOLP(dc, rc->left + abs(dx));
	dest.x = XDPTOLP(dc, rc->left);
    }
    if (dy > 0)
    {
	src.y = YDPTOLP(dc, rc->top);
	dest.y = YDPTOLP(dc, rc->top + abs(dy));
    }
    else
    {
	src.y = YDPTOLP(dc, rc->top + abs(dy));
	dest.y = YDPTOLP(dc, rc->top);
    }

    width = rc->right - rc->left - abs(dx);
    height = rc->bottom - rc->top - abs(dy);

    if (!BitBlt(hdc, dest.x, dest.y, width, height, hdc, src.x, src.y, 
		SRCCOPY))
	return FALSE;

    if (hrgnUpdate)
    {
	if (dx > 0)
	    hrgn1 = CreateRectRgn(rc->left, rc->top, rc->left+dx, rc->bottom);
	else if (dx < 0)
	    hrgn1 = CreateRectRgn(rc->right+dx, rc->top, rc->right, 
				  rc->bottom);
	else
	    hrgn1 = CreateRectRgn(0, 0, 0, 0);

	if (dy > 0)
	    hrgn2 = CreateRectRgn(rc->left, rc->top, rc->right, rc->top+dy);
	else if (dy < 0)
	    hrgn2 = CreateRectRgn(rc->left, rc->bottom+dy, rc->right, 
				  rc->bottom);
	else
	    hrgn2 = CreateRectRgn(0, 0, 0, 0);

	RgnType = CombineRgn(hrgnUpdate, hrgn1, hrgn2, RGN_OR);
    }

    if (rcUpdate) GetRgnBox( hrgnUpdate, rcUpdate );
    return TRUE;
}


/*************************************************************************
 *             ScrollWindowEx       (USER.319)
 */

int ScrollWindowEx(HWND hwnd, short dx, short dy, LPRECT rect, LPRECT clipRect,
		   HRGN hrgnUpdate, LPRECT rcUpdate, WORD flags)
{
    HDC hdc;
    RECT rc, cliprc;

    dprintf_scroll(stddeb,"ScrollWindowEx: dx=%d, dy=%d, rect=%d,%d,%d,%d\n", 
	   dx, dy, rect->left, rect->top, rect->right, rect->bottom);

    hdc = GetDC(hwnd);

    if (rect == NULL)
	GetClientRect(hwnd, &rc);
    else
	CopyRect(&rc, rect);
    if (clipRect == NULL)
	GetClientRect(hwnd, &cliprc);
    else
	CopyRect(&cliprc, clipRect);

    ScrollDC(hdc, dx, dy, &rc, &cliprc, hrgnUpdate, rcUpdate);

    if (flags | SW_INVALIDATE)
    {
	RedrawWindow( hwnd, NULL, hrgnUpdate, RDW_INVALIDATE | RDW_ERASE |
                      ((flags & SW_ERASE) ? RDW_ERASENOW : 0));
    }

    ReleaseDC(hwnd, hdc);
    return RgnType;
}
