class GenericMessageNotification extends inkGameController
{
	private editable var m_title : inkTextRef;
	private editable var m_message : inkTextRef;
	private editable var m_buttonConfirm : inkWidgetRef;
	private editable var m_buttonCancel : inkWidgetRef;
	private editable var m_buttonOk : inkWidgetRef;
	private editable var m_buttonYes : inkWidgetRef;
	private editable var m_buttonNo : inkWidgetRef;
	private editable var m_root : inkWidgetRef;
	private editable var m_background : inkWidgetRef;
	private editable var m_buttonHintsRoot : inkWidgetRef;
	private var m_buttonHintsController : weak< ButtonHints >;
	private var m_data : GenericMessageNotificationData;
	private var m_isNegativeHovered : Bool;
	private var m_isPositiveHovered : Bool;
	private editable var m_libraryPath : inkWidgetLibraryReference;

	protected event OnInitialize()
	{
		inkWidgetRef.SetVisible( m_root, true );
		inkWidgetRef.SetVisible( m_background, true );
		RegisterToGlobalInputCallback( 'OnPostOnPress', this, 'OnHandlePressInput' );
		m_data = ( ( GenericMessageNotificationData )( GetRootWidget().GetUserData( 'GenericMessageNotificationData' ) ) );
		inkWidgetRef.RegisterToCallback( m_buttonConfirm, 'OnRelease', this, 'OnConfirmClick' );
		inkWidgetRef.RegisterToCallback( m_buttonCancel, 'OnRelease', this, 'OnCancelClick' );
		inkWidgetRef.RegisterToCallback( m_buttonOk, 'OnRelease', this, 'OnOkClick' );
		inkWidgetRef.RegisterToCallback( m_buttonYes, 'OnRelease', this, 'OnYesClick' );
		inkWidgetRef.RegisterToCallback( m_buttonNo, 'OnRelease', this, 'OnNoClick' );
		inkWidgetRef.RegisterToCallback( m_buttonConfirm, 'OnHoverOver', this, 'OnPositiveHoverOver' );
		inkWidgetRef.RegisterToCallback( m_buttonCancel, 'OnHoverOver', this, 'OnNegativeHoverOver' );
		inkWidgetRef.RegisterToCallback( m_buttonOk, 'OnHoverOver', this, 'OnPositiveHoverOver' );
		inkWidgetRef.RegisterToCallback( m_buttonYes, 'OnHoverOver', this, 'OnPositiveHoverOver' );
		inkWidgetRef.RegisterToCallback( m_buttonNo, 'OnHoverOver', this, 'OnNegativeHoverOver' );
		inkWidgetRef.RegisterToCallback( m_buttonConfirm, 'OnHoverOut', this, 'OnPositiveHoverOut' );
		inkWidgetRef.RegisterToCallback( m_buttonCancel, 'OnHoverOut', this, 'OnNegativeHoverOut' );
		inkWidgetRef.RegisterToCallback( m_buttonOk, 'OnHoverOut', this, 'OnPositiveHoverOut' );
		inkWidgetRef.RegisterToCallback( m_buttonYes, 'OnHoverOut', this, 'OnPositiveHoverOut' );
		inkWidgetRef.RegisterToCallback( m_buttonNo, 'OnHoverOut', this, 'OnNegativeHoverOut' );
		inkTextRef.SetText( m_title, m_data.title );
		inkTextRef.SetText( m_message, m_data.message );
		inkWidgetRef.SetVisible( m_buttonConfirm, false );
		inkWidgetRef.SetVisible( m_buttonCancel, false );
		inkWidgetRef.SetVisible( m_buttonOk, false );
		inkWidgetRef.SetVisible( m_buttonYes, false );
		inkWidgetRef.SetVisible( m_buttonNo, false );
		switch( m_data.type )
		{
			case GenericMessageNotificationType.OK:
				inkWidgetRef.SetVisible( m_buttonOk, true );
			break;
			case GenericMessageNotificationType.Confirm:
				inkWidgetRef.SetVisible( m_buttonConfirm, true );
			break;
			case GenericMessageNotificationType.Cancel:
				inkWidgetRef.SetVisible( m_buttonCancel, true );
			break;
			case GenericMessageNotificationType.ConfirmCancel:
				inkWidgetRef.SetVisible( m_buttonConfirm, true );
			inkWidgetRef.SetVisible( m_buttonCancel, true );
			break;
			case GenericMessageNotificationType.YesNo:
				inkWidgetRef.SetVisible( m_buttonYes, true );
			inkWidgetRef.SetVisible( m_buttonNo, true );
		}
		PlayLibraryAnimation( 'vendor_popup_sell_junk_intro' );
		PlayLibraryAnimation( 'intro' );
	}

	protected event OnUninitialize()
	{
		UnregisterFromGlobalInputCallback( 'OnPostOnPress', this, 'OnHandlePressInput' );
	}

	private function AddButtonHints( actionName : CName, const label : ref< String > )
	{
		var buttonHint : LabelInputDisplayController;
		buttonHint = ( ( LabelInputDisplayController )( SpawnFromExternal( inkWidgetRef.Get( m_buttonHintsRoot ), inkWidgetLibraryResource.GetPath( m_libraryPath.widgetLibrary ), m_libraryPath.widgetItem ).GetController() ) );
		buttonHint.SetInputActionLabel( actionName, label );
	}

	protected event OnHandlePressInput( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'proceed' ) && !( m_isNegativeHovered ) )
		{
			if( m_data.type == GenericMessageNotificationType.OK )
			{
				Close( GenericMessageNotificationResult.OK );
			}
			else if( m_data.type == GenericMessageNotificationType.Confirm )
			{
				Close( GenericMessageNotificationResult.Confirm );
			}
			else if( m_data.type == GenericMessageNotificationType.ConfirmCancel )
			{
				Close( GenericMessageNotificationResult.Confirm );
			}
			else if( m_data.type == GenericMessageNotificationType.YesNo )
			{
				Close( GenericMessageNotificationResult.Yes );
			}
		}
		else if( evt.IsAction( 'cancel' ) || ( evt.IsAction( 'proceed' ) && m_isNegativeHovered ) )
		{
			if( m_data.type == GenericMessageNotificationType.Cancel )
			{
				Close( GenericMessageNotificationResult.Cancel );
			}
			else if( m_data.type == GenericMessageNotificationType.ConfirmCancel )
			{
				Close( GenericMessageNotificationResult.Cancel );
			}
			else if( m_data.type == GenericMessageNotificationType.YesNo )
			{
				Close( GenericMessageNotificationResult.No );
			}
		}
	}

	protected event OnConfirmClick( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'click' ) )
		{
			Close( GenericMessageNotificationResult.Confirm );
		}
	}

	protected event OnCancelClick( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'click' ) )
		{
			Close( GenericMessageNotificationResult.Cancel );
		}
	}

	protected event OnOkClick( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'click' ) )
		{
			Close( GenericMessageNotificationResult.OK );
		}
	}

	protected event OnYesClick( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'click' ) )
		{
			Close( GenericMessageNotificationResult.Yes );
		}
	}

	protected event OnNoClick( evt : inkPointerEvent )
	{
		if( evt.IsAction( 'click' ) )
		{
			Close( GenericMessageNotificationResult.No );
		}
	}

	protected event OnPositiveHoverOver( evt : inkPointerEvent )
	{
		m_isPositiveHovered = true;
	}

	protected event OnNegativeHoverOver( evt : inkPointerEvent )
	{
		m_isNegativeHovered = true;
	}

	protected event OnPositiveHoverOut( evt : inkPointerEvent )
	{
		m_isPositiveHovered = false;
	}

	protected event OnNegativeHoverOut( evt : inkPointerEvent )
	{
		m_isNegativeHovered = false;
	}


	private var m_closeData : GenericMessageNotificationCloseData;

	private function Close( result : GenericMessageNotificationResult )
	{
		m_closeData = new GenericMessageNotificationCloseData;
		m_closeData.identifier = m_data.identifier;
		m_closeData.result = result;
		PlaySound( 'Button', 'OnPress' );
		PlayLibraryAnimation( 'outro' );
		m_data.token.TriggerCallback( m_closeData );
	}

	protected event OnCloseAnimationFinished( proxy : inkAnimProxy ) {}

	private static function GetBaseData() : GenericMessageNotificationData
	{
		var data : GenericMessageNotificationData;
		data = new GenericMessageNotificationData;
		data.notificationName = 'base\gameplay\gui\widgets\notifications\generic_fullscreen_message_notification.inkwidget';
		data.isBlocking = true;
		data.useCursor = true;
		data.queueName = 'modal_popup';
		return data;
	}

	public static function Show( controller : worlduiIGameController, const title : ref< String >, const message : ref< String > ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.title = title;
		data.message = message;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, identifier : Int32, const title : ref< String >, const message : ref< String > ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.title = title;
		data.message = message;
		data.identifier = identifier;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, const message : ref< String > ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.message = message;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, identifier : Int32, const message : ref< String > ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.message = message;
		data.identifier = identifier;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, const title : ref< String >, const message : ref< String >, type : GenericMessageNotificationType ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.title = title;
		data.message = message;
		data.type = type;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, identifier : Int32, const title : ref< String >, const message : ref< String >, type : GenericMessageNotificationType ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.title = title;
		data.message = message;
		data.identifier = identifier;
		data.type = type;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, const message : ref< String >, type : GenericMessageNotificationType ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.message = message;
		data.type = type;
		return controller.ShowGameNotification( data );
	}

	public static function Show( controller : worlduiIGameController, identifier : Int32, const message : ref< String >, type : GenericMessageNotificationType ) : inkGameNotificationToken
	{
		var data : GenericMessageNotificationData;
		data = GetBaseData();
		data.message = message;
		data.identifier = identifier;
		data.type = type;
		return controller.ShowGameNotification( data );
	}

}

class GenericMessageNotificationData extends inkGameNotificationData
{
	var identifier : Int32;
	var type : GenericMessageNotificationType;
	var title : String;
	var message : String;
}

class GenericMessageNotificationCloseData extends inkGameNotificationData
{
	var identifier : Int32;
	var result : GenericMessageNotificationResult;
}

enum GenericMessageNotificationType
{
	OK = 0,
	Confirm = 1,
	Cancel = 2,
	ConfirmCancel = 3,
	YesNo = 4,
}

enum GenericMessageNotificationResult
{
	Cancel = 0,
	Confirm = 1,
	OK = 2,
	Yes = 3,
	No = 4,
}

