class CraftingLogicController extends CraftingMainLogicController
{
	default m_maxIngredientCount = 5;
	private editable var m_ingredientsWeaponContainer : inkCompoundRef;
	private editable var m_itemPreviewContainer : inkWidgetRef;
	private editable var m_weaponPreviewContainer : inkWidgetRef;
	private editable var m_garmentPreviewContainer : inkWidgetRef;
	private editable var m_perkNotificationContainer : inkWidgetRef;
	private editable var m_perkNotificationText : inkTextRef;
	private var m_itemTooltipController : weak< AGenericTooltipController >;
	private var m_quickHackTooltipController : weak< AGenericTooltipController >;
	private var m_tooltipData : ATooltipData;
	private var m_ingredientWeaponController : weak< InventoryWeaponDisplayController >;
	private var m_ingredientClothingController : weak< InventoryWeaponDisplayController >;
	private var m_selectedItemGameData : gameItemData;
	private var m_quantityPickerPopupToken : inkGameNotificationToken;
	private var m_playerCraftBook : weak< CraftBook >;
	private var m_hasSpawnedQuickHackTooltip : Bool;
	private var m_timeUntilReset : Float;
	default m_timeUntilReset = 1;

	public override function Init( craftingGameController : weak< CraftingMainGameController > )
	{
		super.Init( craftingGameController );
		m_playerCraftBook = m_craftingSystem.GetPlayerCraftBook();
		SetCraftingButton( "UI-Crafting-CraftItem" );
	}

	private const function IsCurrentSelectedRecipeValid() : Bool
	{
		var data : array< IScriptable >;
		var i : Int32;
		data = m_dataSource.GetArray();
		for( i = 0; i < data.Size(); i += 1 )
		{
			if( ( ( RecipeData )( data[ i ] ) ).id == m_selectedRecipe.id )
			{
				return true;
			}
		}
		return false;
	}

	public override function RefreshListViewContent( optional inventoryItemData : InventoryItemData )
	{
		m_dataSource.Clear();
		m_dataSource.Reset( GetRecipesList() );
		if( !( IsCurrentSelectedRecipeValid() ) )
		{
			m_selectedRecipe = NULL;
		}
		UpdateRecipePreviewPanel( m_selectedRecipe );
	}

	protected override function SetupIngredientWidgets()
	{
		AsyncSpawnFromLocal( inkCompoundRef.Get( m_ingredientsWeaponContainer ), 'ingredientWeapon', this, 'OnWeaponControllerSpawned' );
		AsyncSpawnFromLocal( inkCompoundRef.Get( m_ingredientsListContainer ), 'ingredientClothes', this, 'OnClothingControllerSpawned' );
		inkCompoundRef.SetVisible( m_ingredientsWeaponContainer, false );
		super.SetupIngredientWidgets();
	}

	protected event OnWeaponControllerSpawned( widget : inkWidget, userData : IScriptable )
	{
		var buttonController : weak< inkButtonController >;
		m_ingredientWeaponController = ( ( InventoryWeaponDisplayController )( widget.GetControllerByType( 'InventoryWeaponDisplayController' ) ) );
		buttonController = ( ( inkButtonController )( m_ingredientWeaponController.GetRootWidget().GetControllerByType( 'inkButtonController' ) ) );
		buttonController.SetEnabled( false );
	}

	protected event OnClothingControllerSpawned( widget : inkWidget, userData : IScriptable )
	{
		m_ingredientClothingController = ( ( InventoryWeaponDisplayController )( widget.GetControllerByType( 'InventoryWeaponDisplayController' ) ) );
	}

	protected override function SetupFilters()
	{
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.AllCount ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.RangedWeapons ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.MeleeWeapons ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.Consumables ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.Grenades ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.Attachments ) ) );
		m_filters.PushBack( ( ( Int32 )( ItemFilterCategory.Programs ) ) );
		super.SetupFilters();
	}

	protected override function UpdateItemPreview( craftableController : CraftableItemLogicController )
	{
		var selectedRecipe : RecipeData;
		m_progressButtonController.Reset();
		selectedRecipe = ( ( RecipeData )( ( ( IScriptable )( craftableController.GetData() ) ) ) );
		UpdateRecipePreviewPanel( selectedRecipe );
	}

	private function UpdateRecipePreviewPanel( selectedRecipe : RecipeData )
	{
		var isWeapon : Bool;
		var previewEvent : CraftingItemPreviewEvent;
		var buttonState : EProgressBarState;
		m_selectedRecipe.isSelected = false;
		if( selectedRecipe == NULL )
		{
			inkWidgetRef.SetVisible( m_itemDetailsContainer, false );
			return;
		}
		inkWidgetRef.SetVisible( m_itemDetailsContainer, true );
		DryMakeItem( selectedRecipe );
		isWeapon = InventoryItemData.IsWeapon( m_selectedItemData );
		inkWidgetRef.SetVisible( m_weaponPreviewContainer, isWeapon );
		inkWidgetRef.SetVisible( m_itemPreviewContainer, !( isWeapon ) );
		if( m_selectedRecipe.id != selectedRecipe.id )
		{
			previewEvent = new CraftingItemPreviewEvent;
			previewEvent.itemID = ( ( isWeapon ) ? ( m_selectedItemGameData.GetID() ) : ( ItemID.None() ) );
			QueueEvent( previewEvent );
		}
		m_selectedRecipe = selectedRecipe;
		m_selectedRecipe.isSelected = true;
		SetupIngredients( m_craftingSystem.GetItemCraftingCost( m_selectedItemGameData ), 1 );
		UpdateTooltipData();
		SetQualityHeader();
		m_playerCraftBook.SetRecipeInspected( m_selectedRecipe.id.GetID() );
		m_isCraftable = m_craftingSystem.CanItemBeCrafted( m_selectedItemGameData );
		buttonState = ( ( m_isCraftable ) ? ( EProgressBarState.Available ) : ( EProgressBarState.Blocked ) );
		m_progressButtonController.SetAvaibility( buttonState );
		inkTextRef.SetVisible( m_blockedText, !( m_isCraftable ) );
		if( !( m_isCraftable ) )
		{
			SetNotification( false );
		}
	}

	private function DryMakeItem( selectedRecipe : RecipeData )
	{
		var craftedItemID : ItemID;
		var itemData : gameItemData;
		var item : InventoryItemData;
		var player : weak< PlayerPuppet >;
		var itemModParams : ItemModParams;
		player = m_craftingGameController.GetPlayer();
		craftedItemID = ItemID.FromTDBID( selectedRecipe.id.GetID() );
		itemModParams.itemID = craftedItemID;
		itemModParams.quantity = 1;
		itemData = Inventory.CreateItemData( itemModParams, player );
		CraftingSystem.SetItemLevel( player, itemData );
		CraftingSystem.MarkItemAsCrafted( player, itemData );
		itemData.SetDynamicTag( 'SkipActivityLog' );
		item = m_craftingGameController.GetInventoryManager().GetInventoryItemDataForDryItem( itemData );
		m_selectedItemGameData = itemData;
		m_selectedItemData = item;
	}

	private function GetMinimalInvetoryItemData() : MinimalItemTooltipData
	{
		var data : MinimalItemTooltipData;
		var statusManager : UIInventoryItemStatsManager;
		var itemRecord : weak< Item_Record >;
		var itemCategory : gamedataItemCategory;
		var itemType : gamedataItemType;
		data = m_inventoryManager.GetMinimalTooltipDataForInventoryItem( m_selectedItemData, false, NULL, false, false );
		itemType = InventoryItemData.GetItemType( m_selectedItemData );
		itemRecord = TweakDBInterface.GetItemRecord( ItemID.GetTDBID( InventoryItemData.GetID( m_selectedItemData ) ) );
		itemCategory = itemRecord.ItemCategory().Type();
		if( itemCategory != gamedataItemCategory.Weapon )
		{
			statusManager = UIInventoryItemStatsManager.FromMinimalItemTooltipDataToTooltipStats( data );
			data.GetStatsManager().SetTooltipsStats( statusManager.TooltipStats );
		}
		if( RPGManager.IsScopeAttachment( itemType ) || RPGManager.IsMuzzleAttachment( itemType ) )
		{
			HideMods( data );
		}
		data.ammoCount = GameInstance.GetTransactionSystem( m_Game ).GetItemQuantity( m_Player, InventoryItemData.GetID( m_selectedItemData ) );
		data.displayContext = InventoryTooltipDisplayContext.Crafting;
		return data;
	}

	private function HideMods( data : MinimalItemTooltipData )
	{
		data.mods.Clear();
	}

	private function UpdateTooltipData()
	{
		var isQuickHack : Bool;
		isQuickHack = IsQuickHackItem();
		if( isQuickHack )
		{
			if( ( m_quickHackTooltipController == NULL ) && !( m_hasSpawnedQuickHackTooltip ) )
			{
				AsyncSpawnFromExternal( inkWidgetRef.Get( m_tooltipContainer ), R"base\gameplay\gui\common\tooltip\programtooltip.inkwidget", 'programTooltip', this, 'OnQuickHackTooltipSpawned' );
				m_hasSpawnedQuickHackTooltip = true;
				return;
			}
			EnableQuickHackTooltip();
			return;
		}
		if( ( m_itemTooltipController == NULL ) && !( m_hasSpawnedTooltip ) )
		{
			SpawnItemTooltipAsync( inkWidgetRef.Get( m_tooltipContainer ), this, 'OnItemTooltipSpawned' );
			m_hasSpawnedTooltip = true;
			return;
		}
		EnableMainTooltip();
	}

	protected event OnItemTooltipSpawned( widget : inkWidget, userData : IScriptable )
	{
		m_itemTooltipController = ( ( AGenericTooltipController )( widget.GetController() ) );
		EnableMainTooltip();
	}

	protected event OnQuickHackTooltipSpawned( widget : inkWidget, userData : IScriptable )
	{
		m_quickHackTooltipController = ( ( AGenericTooltipController )( widget.GetController() ) );
		EnableQuickHackTooltip();
	}

	private function EnableQuickHackTooltip()
	{
		ToggleMainTooltip( false );
		ToggleQuickHackTooltip( true );
	}

	private function EnableMainTooltip()
	{
		ToggleMainTooltip( true );
		ToggleQuickHackTooltip( false );
	}

	private function ToggleMainTooltip( isEnabled : Bool )
	{
		if( m_itemTooltipController != NULL )
		{
			m_tooltipData = GetMinimalInvetoryItemData();
			m_itemTooltipController.SetData( m_tooltipData );
			m_itemTooltipController.GetRootWidget().SetVisible( isEnabled );
		}
	}

	private function ToggleQuickHackTooltip( isEnabled : Bool )
	{
		if( m_quickHackTooltipController != NULL )
		{
			m_tooltipData = GetQuickHackTooltipData( m_selectedRecipe, m_selectedItemData, m_selectedItemGameData );
			m_quickHackTooltipController.SetData( m_tooltipData );
			m_quickHackTooltipController.GetRootWidget().SetVisible( isEnabled );
		}
	}

	private function SetQualityHeader()
	{
		var rarityLabel, iconicLabel, plusLabel : String;
		var qualityName : CName;
		var isIconic : Bool;
		var isPlus : Float;
		var quality : gamedataQuality;
		var rarityItemType : RarityItemType;
		var itemData : weak< gameItemData >;
		iconicLabel = GetLocalizedText( UIItemsHelper.QualityToDefaultString( gamedataQuality.Iconic ) );
		itemData = InventoryItemData.GetGameItemData( m_selectedItemData );
		if( itemData.HasTag( 'ChimeraMod' ) )
		{
			quality = gamedataQuality.Iconic;
			plusLabel = iconicLabel;
		}
		else
		{
			isIconic = RPGManager.IsItemIconic( itemData );
			isPlus = RPGManager.GetItemPlus( itemData );
			quality = GetQuality();
			rarityItemType = UIItemsHelper.ItemTypeToRarity( InventoryItemData.GetItemType( m_selectedItemData ), itemData );
			rarityLabel = GetLocalizedText( UIItemsHelper.QualityToDefaultString( quality, rarityItemType ) );
			plusLabel = rarityLabel;
			if( isPlus >= 2.0 )
			{
				plusLabel += "++";
			}
			else if( isPlus >= 1.0 )
			{
				plusLabel += "+";
			}
			if( isIconic )
			{
				plusLabel += ( " / " + iconicLabel );
			}
		}
		inkTextRef.SetText( m_itemQuality, plusLabel );
		qualityName = UIItemsHelper.QualityEnumToName( quality );
		inkTextRef.SetState( m_itemQuality, qualityName );
		inkTextRef.SetText( m_itemName, m_selectedRecipe.label );
		inkTextRef.SetState( m_itemName, qualityName );
	}

	private function SetNotification( isQuickHack : Bool )
	{
		var levelParams : inkTextParams;
		var levelRequired : Int32;
		var playerLevel : Float;
		var quality : gamedataQuality;
		var hasAmmoCap : Bool;
		var hasEnoughIngredients : Bool;
		if( isQuickHack )
		{
			inkTextRef.SetText( m_blockedText, "LocKey#78498" );
			m_notificationType = UIMenuNotificationType.CraftingQuickhack;
			return;
		}
		quality = GetQuality();
		levelRequired = GetMinimumLevelRequiredByQuality( quality );
		playerLevel = m_craftingGameController.GetPlayerLevel();
		if( playerLevel < ( ( Float )( levelRequired ) ) )
		{
			levelParams = new inkTextParams;
			levelParams.AddNumber( "int_0", levelRequired );
			inkTextRef.SetText( m_blockedText, "LocKey#87105", levelParams );
			m_notificationType = UIMenuNotificationType.PlayerReqLevelToLow;
			return;
		}
		hasEnoughIngredients = m_craftingSystem.EnoughIngredientsForCrafting( InventoryItemData.GetGameItemData( m_selectedItemData ) );
		if( !( hasEnoughIngredients ) )
		{
			inkTextRef.SetText( m_blockedText, "LocKey#42797" );
			m_notificationType = UIMenuNotificationType.CraftingNotEnoughMaterial;
			return;
		}
		hasAmmoCap = HasAmmoCap();
		if( hasAmmoCap )
		{
			inkTextRef.SetText( m_blockedText, "LocKey#81496" );
			m_notificationType = UIMenuNotificationType.CraftingAmmoCap;
			return;
		}
	}

	private function HasAmmoCap() : Bool
	{
		var itemData : weak< gameItemData >;
		var maxCraftingAmount : Int32;
		itemData = InventoryItemData.GetGameItemData( m_selectedItemData );
		maxCraftingAmount = m_craftingSystem.GetMaxCraftingAmount( itemData );
		return maxCraftingAmount == 0;
	}

	private function GetQuality() : gamedataQuality
	{
		var qualityName : CName;
		qualityName = InventoryItemData.GetQuality( m_selectedItemData );
		return UIItemsHelper.QualityNameToEnum( qualityName );
	}

	private static function GetMinimumLevelRequiredByQuality( quality : gamedataQuality ) : Int32
	{
		switch( quality )
		{
			case gamedataQuality.Uncommon:
				return 1;
			case gamedataQuality.Rare:
				return 1;
			case gamedataQuality.Epic:
				return 1;
			case gamedataQuality.Legendary:
				return 1;
			default:
				return 1;
		}
	}

	private function SetupIngredients( const ingredient : ref< array< IngredientData > >, itemAmount : Int32 )
	{
		var i, ingredientCount : Int32;
		var controller : weak< IngredientListItemLogicController >;
		var data : IngredientData;
		var itemData : InventoryItemData;
		var isInInventory : Bool;
		ingredientCount = ingredient.Size();
		inkCompoundRef.SetVisible( m_ingredientsWeaponContainer, false );
		m_ingredientClothingController.GetRootWidget().SetVisible( false );
		for( i = 0; i < ingredientCount; i += 1 )
		{
			data = ingredient[ i ];
			itemData = GetInventoryItemDataFromRecord( data.id );
			controller = m_ingredientsControllerList[ i ];
			if( RPGManager.IsItemWeapon( InventoryItemData.GetID( itemData ) ) )
			{
				inkCompoundRef.SetVisible( m_ingredientsWeaponContainer, true );
				m_ingredientWeaponController.Setup( itemData );
				controller.SetUnusedState();
				isInInventory = RPGManager.HasItem( m_craftingGameController.GetPlayer(), ItemID.GetTDBID( InventoryItemData.GetID( itemData ) ) );
				m_ingredientWeaponController.GetRootWidget().SetState( ( ( isInInventory ) ? ( 'Default' ) : ( 'Unavailable' ) ) );
				continue;
			}
			if( RPGManager.IsItemClothing( InventoryItemData.GetID( itemData ) ) )
			{
				m_ingredientClothingController.GetRootWidget().SetVisible( true );
				m_ingredientClothingController.Setup( itemData );
				isInInventory = RPGManager.HasItem( m_craftingGameController.GetPlayer(), ItemID.GetTDBID( InventoryItemData.GetID( itemData ) ) );
				m_ingredientClothingController.GetRootWidget().SetState( ( ( isInInventory ) ? ( 'Default' ) : ( 'Unavailable' ) ) );
				controller.SetUnusedState();
				continue;
			}
			controller.SetupData( ingredient[ i ], m_tooltipsManager, itemAmount );
		}
		for( i = ingredientCount; i < m_maxIngredientCount; i += 1 )
		{
			controller = m_ingredientsControllerList[ i ];
			controller.SetUnusedState();
		}
	}

	protected event OnDisplayHoverOver( hoverOverEvent : ItemDisplayHoverOverEvent )
	{
		var tooltipData : MaterialTooltipData;
		tooltipData = new MaterialTooltipData;
		if( hoverOverEvent.display.GetDisplayContext() == ItemDisplayContext.None )
		{
			tooltipData.Title = GetLocalizedText( InventoryItemData.GetName( hoverOverEvent.itemData ) );
			m_tooltipsManager.ShowTooltipAtWidget( 'materialTooltip', hoverOverEvent.widget, tooltipData, gameuiETooltipPlacement.RightTop, true );
		}
	}

	public override function OnChangeTab( isCurrent : Bool )
	{
		super.OnChangeTab( isCurrent );
		m_quantityPickerPopupToken = NULL;
		m_selectedRecipe = NULL;
	}

	private function OpenQuantityPicker( const itemData : ref< InventoryItemData >, maxQuantity : Int32 )
	{
		var data : QuantityPickerPopupData;
		data = new QuantityPickerPopupData;
		data.notificationName = 'base\gameplay\gui\widgets\notifications\item_quantity_picker.inkwidget';
		data.isBlocking = true;
		data.useCursor = true;
		data.queueName = 'modal_popup';
		data.maxValue = maxQuantity;
		data.gameItemData = itemData;
		data.actionType = QuantityPickerActionType.Craft;
		data.sendQuantityChangedEvent = true;
		m_quantityPickerPopupToken = m_craftingGameController.ShowGameNotification( data );
		if( m_quantityPickerPopupToken )
		{
			m_quantityPickerPopupToken.RegisterListener( this, 'OnQuantityPickerEvent' );
		}
		m_buttonHintsController.Hide();
	}

	protected event OnQuantityPickerEvent( data : inkGameNotificationData )
	{
		var closeData : QuantityPickerPopupCloseData;
		var quantityData : PickerChoosenQuantityChangedEvent;
		closeData = ( ( QuantityPickerPopupCloseData )( data ) );
		quantityData = ( ( PickerChoosenQuantityChangedEvent )( data ) );
		if( closeData != NULL )
		{
			m_quantityPickerPopupToken = NULL;
			if( closeData.choosenQuantity != -1 )
			{
				CraftItem( m_selectedRecipe, closeData.choosenQuantity );
				m_buttonHintsController.Show();
			}
		}
		if( quantityData != NULL )
		{
			SetupIngredients( m_craftingSystem.GetItemCraftingCost( m_selectedItemGameData ), quantityData.choosenQuantity );
		}
	}

	protected event OnHoldFinished( evt : ProgressBarFinishedProccess )
	{
		var quantity : Int32;
		if( !( m_isPanelOpen ) )
		{
			return false;
		}
		PlaySound( 'Item', 'OnCrafted' );
		PlayRumble( RumbleStrength.Heavy, RumbleType.Pulse, RumblePosition.Right );
		if( ( ( m_selectedRecipe.id.TagsContains( 'Consumable' ) && !( m_selectedRecipe.id.TagsContains( 'Medical' ) ) ) || m_selectedRecipe.id.TagsContains( 'Ammo' ) ) || InventoryItemData.GetItemType( m_selectedRecipe.inventoryItem ) == gamedataItemType.Gen_CraftingMaterial )
		{
			quantity = m_craftingSystem.GetMaxCraftingAmount( InventoryItemData.GetGameItemData( m_selectedItemData ) );
			if( m_selectedRecipe.id.TagsContains( 'Ammo' ) && ( quantity == 0 ) )
			{
				return false;
			}
			if( quantity > 1 )
			{
				OpenQuantityPicker( m_selectedItemData, quantity );
				return true;
			}
		}
		if( m_selectedRecipe.id.TagsContains( 'Ammo' ) )
		{
			CraftItem( m_selectedRecipe, 1 );
		}
		else
		{
			CraftItem( m_selectedRecipe, m_selectedRecipe.amount );
		}
	}

	protected override function SetItemButtonHintsHoverOver( evt : inkPointerEvent )
	{
		if( m_isCraftable )
		{
			m_buttonHintsController.AddButtonHint( 'craft_item', GetLocalizedText( "UI-Crafting-hold_to_craft" ) );
		}
	}

	private function GetRecipesList() : array< IScriptable >
	{
		var itemRecordList : array< weak< Item_Record > >;
		var itemRecord : weak< Item_Record >;
		var i : Int32;
		var recipeDataList : array< IScriptable >;
		var recipeData : RecipeData;
		m_playerCraftBook.HideRecipesForOwnedItems();
		itemRecordList = m_playerCraftBook.GetCraftableItems();
		for( i = 0; i < itemRecordList.Size(); i += 1 )
		{
			itemRecord = itemRecordList[ i ];
			if( itemRecord )
			{
				recipeData = m_craftingSystem.GetRecipeData( itemRecord );
				recipeData.isNew = m_playerCraftBook.IsRecipeNew( recipeData.id.GetID() );
				recipeData.isCraftable = m_craftingSystem.CanItemBeCrafted( itemRecord );
				recipeData.inventoryItem = m_inventoryManager.GetInventoryItemDataFromItemRecord( recipeData.id );
				InventoryItemData.SetQuality( recipeData.inventoryItem, UIItemsHelper.QualityEnumToName( itemRecord.Quality().Type() ) );
				m_inventoryManager.GetOrCreateInventoryItemSortData( recipeData.inventoryItem, m_craftingGameController.GetScriptableSystem() );
				recipeDataList.PushBack( recipeData );
			}
		}
		return recipeDataList;
	}

	private function GetInventoryItemDataFromRecord( itemRecord : Item_Record ) : InventoryItemData
	{
		var itemData : InventoryItemData;
		itemData = m_inventoryManager.GetInventoryItemDataFromItemRecord( itemRecord );
		m_inventoryManager.GetOrCreateInventoryItemSortData( itemData, m_craftingGameController.GetScriptableSystem() );
		return itemData;
	}

	private function GetQuickHackTooltipData( recipeData : RecipeData, inventoryItemData : InventoryItemData, gameData : gameItemData ) : ATooltipData
	{
		var tooltipData : InventoryTooltipData;
		tooltipData = InventoryTooltipData.FromRecipeAndItemData( m_craftingGameController.GetPlayer().GetGame(), recipeData, inventoryItemData, inventoryItemData, gameData );
		InventoryItemData.SetGameItemData( tooltipData.inventoryItemData, gameData );
		if( InventoryItemData.GetItemType( inventoryItemData ) == gamedataItemType.Prt_Program )
		{
			tooltipData.quickhackData = m_inventoryManager.GetQuickhackTooltipData( ItemID.GetTDBID( InventoryItemData.GetID( inventoryItemData ) ) );
		}
		return tooltipData;
	}

	private function IsQuickHackItem() : Bool
	{
		return m_selectedItemData.ItemType == gamedataItemType.Prt_Program;
	}

	private function CraftItem( selectedRecipe : RecipeData, amount : Int32 )
	{
		var craftItemRequest : CraftItemRequest;
		if( selectedRecipe.label != "" )
		{
			craftItemRequest = new CraftItemRequest;
			craftItemRequest.target = m_craftingGameController.GetPlayer();
			craftItemRequest.itemRecord = selectedRecipe.id;
			craftItemRequest.amount = amount;
			if( selectedRecipe.id.TagsContains( 'Ammo' ) )
			{
				craftItemRequest.bulletAmount = selectedRecipe.amount;
			}
			m_craftingSystem.QueueRequest( craftItemRequest );
		}
		if( ( m_selectedRecipe.id.TagsContains( 'Medical' ) || m_selectedRecipe.id.TagsContains( 'Grenade' ) ) || ( m_selectedRecipe.id.TagsContains( 'CraftableIconic' ) && !( m_selectedRecipe.id.TagsContains( 'Haunted_Gun' ) ) ) )
		{
			DelayedReset.CreateAndDispatch( this, m_Player, m_timeUntilReset );
		}
	}

	public function ResetViewDelayed()
	{
		inkWidgetRef.SetVisible( m_itemDetailsContainer, false );
		m_selectedRecipe = NULL;
	}

	protected event OnItemDisplayHoverOver( evt : ItemDisplayHoverOverEvent )
	{
		if( !( InventoryItemData.IsEmpty( evt.itemData ) ) )
		{
			m_playerCraftBook.SetRecipeInspected( ItemID.GetTDBID( InventoryItemData.GetID( evt.itemData ) ) );
		}
	}

	protected event OnUninitialize()
	{
		if( m_selectedItemGameData )
		{
			m_selectedItemGameData = NULL;
		}
		super.OnUninitialize();
	}

}

class DelayedReset extends DelayCallback
{
	private var m_controller : weak< CraftingLogicController >;

	public static function CreateAndDispatch( controller : weak< CraftingLogicController >, player : weak< PlayerPuppet >, time : Float )
	{
		var callback : DelayedReset;
		callback = new DelayedReset;
		callback.m_controller = controller;
		GameInstance.GetDelaySystem( player.GetGame() ).DelayCallback( callback, time, false );
	}

	public override function Call()
	{
		m_controller.ResetViewDelayed();
	}

}

