/*******************************************************************************
 * Copyright (c) 2000, 2008 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.swt.widgets;

import org.eclipse.swt.*;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.Point;

import intrinsic.Function;
import intrinsic.flash.events.*;
import intrinsic.flash.display.*;
import intrinsic.mx.controls.RadioButton;
import intrinsic.mx.controls.RadioButtonGroup;
import intrinsic.mx.core.UIComponent;

public class Button extends Control {
	String text = "";
	org.eclipse.swt.graphics.Image image;

public Button (Composite parent, int style) {
	super (parent, checkStyle (style));
}

public void addSelectionListener (SelectionListener listener) {
	checkWidget ();
	if (listener == null) error (SWT.ERROR_NULL_ARGUMENT);
	TypedListener typedListener = new TypedListener (listener);
	addListener (SWT.Selection,typedListener);
	addListener (SWT.DefaultSelection,typedListener);
}

static int checkStyle (int style) {
	style = checkBits (style, SWT.PUSH, SWT.ARROW, SWT.CHECK, SWT.RADIO, SWT.TOGGLE, /*COMMAND_LINK ? SWT.COMMAND : */0);
	if ((style & (SWT.PUSH | SWT.TOGGLE)) != 0) {
		return checkBits (style, SWT.CENTER, SWT.LEFT, SWT.RIGHT, 0, 0, 0);
	}
	if ((style & (SWT.CHECK | SWT.RADIO)) != 0) {
		return checkBits (style, SWT.LEFT, SWT.RIGHT, SWT.CENTER, 0, 0, 0);
	}
	if ((style & SWT.ARROW) != 0) {
		style |= SWT.NO_FOCUS;
		return checkBits (style, SWT.UP, SWT.DOWN, SWT.LEFT, SWT.RIGHT, 0, 0);
	}
	return style;
}

void clickHandler(MouseEvent event) {
	sendSelection ();
}

native Function clickHandlerFunction ()/*{
	return clickHandler__Lflash_events_MouseEvent_2;
}*/;

Point computeNativeSize (UIComponent widget, int wHint, int hHint, boolean changed) {
	double oldWidth = widget.width, oldHeight = widget.height;
	widget.width = Double.NaN;
	widget.height = Double.NaN;
	//widget.validateProperties();
	widget.validateSize();
	int width = wHint == SWT.DEFAULT ? (int)widget.measuredWidth : wHint;
	int height = hHint == SWT.DEFAULT ? (int)widget.measuredHeight : hHint;
	widget.width = oldWidth;
	widget.height = oldHeight;
	return new Point (width, height);
}

void createHandle () {
	intrinsic.mx.controls.Button widget;
	if ((style & SWT.RADIO) != 0) {
		RadioButton button = new intrinsic.mx.controls.RadioButton();
		widget = button;
		if (parent.group == null) parent.group = new RadioButtonGroup(); 
		button.group = parent.group;
		widget.setStyle("paddingTop", 0);
		widget.setStyle("paddingBottom", 0);
	} else if ((style & SWT.CHECK) != 0) {
		widget = new intrinsic.mx.controls.CheckBox();
		widget.setStyle("paddingTop", 0);
		widget.setStyle("paddingBottom", 0);
	} else {
		widget = new intrinsic.mx.controls.Button();
		if ((style & SWT.TOGGLE) != 0) widget.toggle = true;
	}
	object = widget;
}

public int getAlignment () {
	checkWidget ();
	if ((style & SWT.ARROW) != 0) {
		if ((style & SWT.UP) != 0) return SWT.UP;
		if ((style & SWT.DOWN) != 0) return SWT.DOWN;
		if ((style & SWT.LEFT) != 0) return SWT.LEFT;
		if ((style & SWT.RIGHT) != 0) return SWT.RIGHT;
		return SWT.UP;
	}
	if ((style & SWT.LEFT) != 0) return SWT.LEFT;
	if ((style & SWT.CENTER) != 0) return SWT.CENTER;
	if ((style & SWT.RIGHT) != 0) return SWT.RIGHT;
	return SWT.LEFT;
}

String getNameText() {
	return getText ();
}

Image _getImage(DisplayObjectContainer item) {
	return image;
}

public org.eclipse.swt.graphics.Image getImage () {
	checkWidget ();
	return image;
}

public boolean getSelection () {
	checkWidget ();
	if ((style & (SWT.CHECK | SWT.RADIO | SWT.TOGGLE)) == 0) return false;
	return ((intrinsic.mx.controls.Button)object).selected;
}

public String getText () {
	checkWidget ();
	if ((style & SWT.ARROW) != 0) return "";
	return text;
}

void hookEvents (){
	super.hookEvents();
	object.addEventListener(MouseEvent.CLICK, clickHandlerFunction ());
}

void releaseWidget () {
	super.releaseWidget ();
	text = null;
	image = null;
}

public void removeSelectionListener (SelectionListener listener) {
	checkWidget ();
	if (listener == null) error (SWT.ERROR_NULL_ARGUMENT);
	if (eventTable == null) return;
	eventTable.unhook (SWT.Selection, listener);
	eventTable.unhook (SWT.DefaultSelection,listener);	
}

void selectRadio () {
	/*
	* This code is intentionally commented.  When two groups
	* of radio buttons with the same parent are separated by
	* another control, the correct behavior should be that
	* the two groups act independently.  This is consistent
	* with radio tool and menu items.  The commented code
	* implements this behavior.
	*/
//	int index = 0;
//	Control [] children = parent._getChildren ();
//	while (index < children.length && children [index] != this) index++;
//	int i = index - 1;
//	while (i >= 0 && children [i].setRadioSelection (false)) --i;
//	int j = index + 1;
//	while (j < children.length && children [j].setRadioSelection (false)) j++;
//	setSelection (true);
	Control [] children = parent._getChildren ();
	for (int i=0; i<children.length; i++) {
		Control child = children [i];
		if (this != child) child.setRadioSelection (false);
	}
	setSelection (true);
}

void sendSelection () {
//	if ((style & (SWT.CHECK | SWT.TOGGLE)) != 0) {
//		setSelection (!getSelection ());
//	} else {
//		if ((style & SWT.RADIO) != 0) {
//			if ((parent.getStyle () & SWT.NO_RADIO_GROUP) != 0) {
//				setSelection (!getSelection ());
//			} else {
//				selectRadio ();
//			}
//		}
//	}
	postEvent (SWT.Selection);
}

public void setAlignment (int alignment) {
	checkWidget ();
	if ((style & SWT.ARROW) != 0) {
		if ((style & (SWT.UP | SWT.DOWN | SWT.LEFT | SWT.RIGHT)) == 0) return; 
		style &= ~(SWT.UP | SWT.DOWN | SWT.LEFT | SWT.RIGHT);
		style |= alignment & (SWT.UP | SWT.DOWN | SWT.LEFT | SWT.RIGHT);
	} else {
		if ((alignment & (SWT.LEFT | SWT.RIGHT | SWT.CENTER)) == 0) return;
		style &= ~(SWT.LEFT | SWT.RIGHT | SWT.CENTER);
		style |= alignment & (SWT.LEFT | SWT.RIGHT | SWT.CENTER);
	}
}

public void setImage (org.eclipse.swt.graphics.Image image) {
	checkWidget ();
	if (image != null && image.isDisposed()) error(SWT.ERROR_INVALID_ARGUMENT);
	if ((style & SWT.ARROW) != 0) return;
	this.image = image;
	if (image == null) {
		object.clearStyle("icon");
	} else {
		object.setStyle("icon", SWTBitmapAsset.getClazz());
	}
}

boolean setRadioSelection (boolean value) {
	if ((style & SWT.RADIO) == 0) return false;
	if (getSelection () != value) {
		setSelection (value);
		postEvent (SWT.Selection);
	}
	return true;
}

public void setSelection (boolean selected) {
	checkWidget ();
	if ((style & (SWT.CHECK | SWT.RADIO | SWT.TOGGLE)) == 0) return;
	((intrinsic.mx.controls.Button)object).selected = selected;
}

public void setText (String string) {
	checkWidget ();
	if (string == null) error (SWT.ERROR_NULL_ARGUMENT);
	if ((style & SWT.ARROW) != 0) return;
	text = string;
	((intrinsic.mx.controls.Button)object).label = fixMnemonic (string);
}

}
