// ---------------------------------------------------------------------------
// 
//   Lily Engine alpha
// 
//   Copyright (c) 2010 Clifford Jolly
//     http://cliffjolly.com
//     cliff@cliffjolly.com
// 
// ---------------------------------------------------------------------------
// 
//   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
// -------------------------- END HEADER -------------------------------------

#include "../hacks/winhacks.h"

#include <GL/gl.h>

#include "widgetalignedbox.h"

WidgetAlignedBox::WidgetAlignedBox(void) {
	hAlign = 0;
	vAlign = 0;
    vStretch = false;
    hStretch = false;
}

WidgetAlignedBox::~WidgetAlignedBox(void) {
	
}


void WidgetAlignedBox::draw(void) {

	WidgetSingleParent::draw();
	
	if(child) {
		glPushMatrix();

		float realOffsetX = getOffsetX();
		float realOffsetY = getOffsetY();

#ifdef WIDGET_SNAP_TO_PIXELS
        realOffsetX = int(realOffsetX + 0.5);
        realOffsetY = int(realOffsetY + 0.5);
#endif

		glTranslatef(realOffsetX, realOffsetY, 0);

		pushClipArea(0, 0, child->getWidth(), child->getHeight());

		child->draw();
		
		popClipArea();
		
		glPopMatrix();
	}
	
}

float WidgetAlignedBox::getMinHeight(void) {
	float childSize = child ? child->getMinHeight() : 0;
	float mySize    = WidgetSingleParent::getMinHeight();
	return mySize > childSize ? mySize : childSize;
}

float WidgetAlignedBox::getMinWidth(void) {
	float childSize = child ? child->getMinWidth() : 0;
	float mySize    = WidgetSingleParent::getMinWidth();
	return mySize > childSize ? mySize : childSize;
}

void WidgetAlignedBox::setWidth(float newWidth) {
	WidgetSingleParent::setWidth(newWidth);
	if(child) child->setWidth(hStretch ? width : 0);
}

void WidgetAlignedBox::setHeight(float newHeight) {
	WidgetSingleParent::setHeight(newHeight);
	if(child) child->setHeight(vStretch ? height : 0);
}

bool WidgetAlignedBox::handleEvent(const WidgetEvent *event) {

	bool ret = WidgetSingleParent::handleEvent(event);
	
	float oldOffsetX = debugDrawOffsetX;
	float oldOffsetY = debugDrawOffsetY;
	
	// Copy the whole event so whatever we don't change is sane.
	WidgetEvent shiftedEvent = *event;
	
	if(event->type == WIDGETEVENT_MOUSEMOTION ||
		event->type == WIDGETEVENT_MOUSEDOWN ||
		event->type == WIDGETEVENT_MOUSEUP) {
		
		if(child) {
			
			float realOffsetX = getOffsetX();
			float realOffsetY = getOffsetY();
		
			shiftedEvent.mouse.x -= realOffsetX;
			shiftedEvent.mouse.y -= realOffsetY;
			debugDrawOffsetX += realOffsetX;
			debugDrawOffsetY += realOffsetY;
		
			ret |= child->handleEvent(&shiftedEvent);
		}
		
	} else {

		// I don't know what this is. Just pass it along.
		if(child) ret |= child->handleEvent(&shiftedEvent);
		
	}	
	
	debugDrawOffsetX = oldOffsetX;
	debugDrawOffsetY = oldOffsetY;

	return ret;
}

float WidgetAlignedBox::getOffsetX(void) {
	// Left
	if(hAlign < 0) {
		return 0;
	}
	
	// Right
	if(hAlign > 0) {
		return getWidth() - (child ? (child->getWidth()) : 0);
	}

	// Centered.
	return (getWidth() / 2.0) - (child ? (child->getWidth() / 2.0) : 0);
}

float WidgetAlignedBox::getOffsetY(void) {
	// Top
	if(vAlign < 0) {
		return 0;
	}
	
	// Bottom
	if(vAlign > 0) {
		return getHeight() - (child ? (child->getHeight()) : 0);
	}

	// Centered.
	return (getHeight() / 2.0) - (child ? (child->getHeight() / 2.0) : 0);
}

void WidgetAlignedBox::setHAlign(int hAlign) {
	this->hAlign = hAlign;
}

void WidgetAlignedBox::setVAlign(int vAlign) {
	this->vAlign = vAlign;
}

int WidgetAlignedBox::getHAlign(void) {
	return hAlign;
}

int WidgetAlignedBox::getVAlign(void) {
	return vAlign;
}

void WidgetAlignedBox::setVStretch(bool vStretch) {
    this->vStretch = vStretch;
}

bool WidgetAlignedBox::getVStretch(void) {
    return vStretch;
}

void WidgetAlignedBox::setHStretch(bool hStretch) {
    this->hStretch = hStretch;
}

bool WidgetAlignedBox::getHStretch(void) {
    return hStretch;
}
