private void SetHoverItem(RPGItem item, string price, int fromPanel) { hoverFromPanel = fromPanel; if (item == null) { if (Event.current.type == EventType.repaint && !hoverDetected) { hoverItem = null; hoverItemPrice = null; } } else { if (hoverItem == null) hoverSkip = true; hoverDetected = true; hoverItem = item; hoverItemPrice = price; GUI.tooltip = ""; } }
protected override void OnItemTargeted(bool becomeTargeted, RPGItem item) { UpdateSelectionRing(3, becomeTargeted, item.transform); }
// ================================================================================================================ #region Bag panel private void DrawBag() { if (!gui.plrMoveBag) UniRPGGlobal.GUIConsumedInput = true; if (ShowRightPopMenu >= 0) GUI.enabled = false; GUI.BeginGroup(r[1], gui.bagPanelName, GUI.skin.window); { if (GUI.Button(new Rect(r[1].width - gui.WindowCloseButton.fixedWidth - GUI.skin.window.padding.right, GUI.skin.window.padding.top + GUI.skin.window.contentOffset.y, gui.WindowCloseButton.fixedWidth, gui.WindowCloseButton.fixedHeight), GUIContent.none, gui.WindowCloseButton)) { PlayButtonFX(); showBag = false; } Rect rect = new Rect(GUI.skin.window.padding.left, GUI.skin.window.padding.top, r[1].width - GUI.skin.window.padding.left - GUI.skin.window.padding.right, r[1].height - GUI.skin.window.padding.top - GUI.skin.window.padding.bottom - gui.BagCurrencyLabel.fixedHeight - gui.BagCurrencyLabel.margin.top - gui.BagCurrencyLabel.margin.bottom); Rect rButton = new Rect(0, 0, gui.ListButton.fixedHeight, gui.ListButton.fixedHeight); int countOver = (int)Mathf.Floor((r[1].width - GUI.skin.verticalScrollbar.fixedWidth) / gui.bagIconWidth); r[5] = new Rect(0, 0, r[1].width - GUI.skin.verticalScrollbar.fixedWidth, gui.bagIconWidth * (UniRPGGlobal.Player.Actor.bagSize / countOver)); scroll[2] = GUI.BeginScrollView(rect, scroll[2], r[5]); { for (int i = 0; i < UniRPGGlobal.Player.Actor.bagSize; i++) { if (i < UniRPGGlobal.Player.Actor.bag.Count) { if (UniRPGGlobal.Player.Actor.bag[i] != null && UniRPGGlobal.Player.Actor.bag[i].item != null) { if (GUI.Button(rButton, new GUIContent(UniRPGGlobal.Player.Actor.bag[i].item.icon[0] == null ? gui.txNoIcon : UniRPGGlobal.Player.Actor.bag[i].item.icon[0], i.ToString()), gui.ListButton)) { PlayButtonFX(); ShowRightPopMenu = i; //rPopMenu = new Rect(r[1].x + rButton.x + rect.x, r[1].y + rButton.y + rect.y - scroll[2].y, 200, 135); } if (GUI.tooltip == i.ToString() && ShowRightPopMenu == -1) SetHoverItem(UniRPGGlobal.Player.Actor.bag[i].item, "Value: " + UniRPGGlobal.Player.Actor.bag[i].item.price, 2); if (UniRPGGlobal.Player.Actor.bag[i].stack > 1) GUI.Label(rButton, UniRPGGlobal.Player.Actor.bag[i].stack.ToString(), gui.BagStackLabel); } else GUI.Button(rButton, GUIContent.none, gui.ListButton); } else GUI.Button(rButton, GUIContent.none, gui.ListButton); rButton.x += gui.bagIconWidth; if ((rButton.x + gui.bagIconWidth) > r[5].width) { rButton.x = 0; rButton.y += gui.bagIconWidth; } } } GUI.EndScrollView(); rect.y += rect.height + gui.BagCurrencyLabel.margin.top; rect.height = gui.BagCurrencyLabel.fixedHeight; GUI.Box(rect, UniRPGGlobal.DB.currency + ": " + UniRPGGlobal.Player.Actor.currency, gui.BagCurrencyLabel); } GUI.EndGroup(); if (!showOptions) GUI.enabled = true; int cnt = 4; if (popMenuHelperItem != null) { cnt = popMenuHelperStrings.Length + 1; } else if (popMenuHelperItem2 != null) { cnt = gui.actionSlotsCount + 1; } if (ShowRightPopMenu >= 0) { GUILayout.BeginArea(rPopMenu, GUI.skin.box); { if (popMenuHelperItem != null) { for (int i = 0; i < popMenuHelperStrings.Length; i++) { if (GUILayout.Button(popMenuHelperStrings[i])) { PlayButtonFX(); int slot = UniRPGGlobal.DB.equipSlots.IndexOf(popMenuHelperStrings[i]); if (slot >= 0) { // check if equip slot is a valid target if (UniRPGGlobal.Player.Actor.CanEquip(slot, popMenuHelperItem)) { bool failed = false; // remove item from bag UniRPGGlobal.Player.Actor.RemoveFromBag(ShowRightPopMenu, 1); // get the old item that will be removed from equip slot (if any) RPGItem oldItem = UniRPGGlobal.Player.Actor.GetEquippedItem(slot); if (oldItem != null) { // and try to place the old item in the bag if (!UniRPGGlobal.Player.Actor.AddToBag(oldItem, 1)) { failed = true; } } if (!failed) { // so far so good, now equip the item (which will also cause the old equipped item to be actually unequipped) if (!UniRPGGlobal.Player.Actor.Equip(slot, popMenuHelperItem)) { failed = true; } } if (failed) { // put the item back in bag (equip failed) UniRPGGlobal.Player.Actor.AddToBag(popMenuHelperItem, 1); } popMenuHelperItem = null; ShowRightPopMenu = -1; GUIUtility.ExitGUI(); return; } } } } if (GUILayout.Button("Cancel")) { PlayButtonFX(); popMenuHelperItem = null; ShowRightPopMenu = -1; } } else if (popMenuHelperItem2 != null) { scroll[3] = GUILayout.BeginScrollView(scroll[3]); { if (GUILayout.Button("Cancel")) { PlayButtonFX(); popMenuHelperItem2 = null; ShowRightPopMenu = -1; } for (int i = 0; i < gui.actionSlotsCount; i++) { if (GUILayout.Button("Slot " + (i + 1))) { PlayButtonFX(); UniRPGGlobal.Player.Actor.SetActionSlot(i, popMenuHelperItem2); popMenuHelperItem2 = null; ShowRightPopMenu = -1; } } } GUILayout.EndScrollView(); } else { if (GUILayout.Button("Use")) { // get the item PlayButtonFX(); RPGItem item = UniRPGGlobal.Player.Actor.GetBagItem(ShowRightPopMenu); if (item != null) { if (item.equipWhenUseFromBag) { // can be equipped by player? if ((item.equipTargetMask & UniRPGGlobal.Target.Player) != 0 && item.validEquipSlots.Count > 0) { popRectCalced = false; popMenuHelperItem = item; popMenuHelperStrings = new string[item.validEquipSlots.Count]; for (int i = 0; i < item.validEquipSlots.Count; i++) { popMenuHelperStrings[i] = UniRPGGlobal.DB.equipSlots[item.validEquipSlots[i]]; } } } else { UniRPGGlobal.Player.Actor.UseBagItem(ShowRightPopMenu); ShowRightPopMenu = -1; } } } if (GUILayout.Button("Slot")) { PlayButtonFX(); RPGItem item = UniRPGGlobal.Player.Actor.GetBagItem(ShowRightPopMenu); if (item != null) { //if (false == item.equipWhenUseFromBag) //{ // items that can't be equipped but are used from bag can be placed onto slot popRectCalced = false; popMenuHelperItem2 = item; //} } } if (GUILayout.Button("Destroy")) { PlayButtonFX(); UniRPGGlobal.Player.Actor.RemoveFromBag(ShowRightPopMenu, 1); ShowRightPopMenu = -1; } if (GUILayout.Button("Cancel")) { PlayButtonFX(); ShowRightPopMenu = -1; } } } GUILayout.EndArea(); } CalcPopMenuRect(cnt, ShowRightPopMenu, popMenuHelperItem != null || popMenuHelperItem2 != null); if (hoverFromPanel == 2) DrawHoverItemInfo(); }
/// <summary> /// Tell UniRPG that you want it to recreate this item in the world when /// the player loads or re-enters the same scene. UniRPG will not /// save the item if it becomes null before saving is requested /// </summary> public static void RegisterItemForAutoSaving(RPGItem item) { if (!itemsRegedForAutoSaving.Contains(item)) { item.IsPersistent = false; itemsRegedForAutoSaving.Add(item); } }
/// <summary> /// Tell UniRPG that you do not want this item to be restored when loading happens. /// Only works for items that where registered with RegisterItemForAutoSaving. /// </summary> public static void RemoveItemFromAutoSaving(RPGItem item) { itemsRegedForAutoSaving.Remove(item); }
/// <summary> /// place item in specified slot. return false if the slot is occupied. /// will only allow count>1 if the item can stack /// </summary> public bool SetBagSlot(RPGItem item, int slot, int count) { CheckBagSize(); // again, cant depend on slot being null (see reason inside AddToBag() comments) if (bag[slot] != null) { if (bag[slot].stack != 0) return false; } int added = count; bag[slot] = new BagSlot(); bag[slot].item = item; bag[slot].stack = count; // check if stack size allowed if (bag[slot].stack > item.maxStack) { added -= (bag[slot].stack - item.maxStack); bag[slot].stack = item.maxStack; } for (int i = 0; i < added; i++) { UniRPGGameController.ExecuteActions(bag[slot].item.onAddedToBag, bag[slot].item.gameObject, null, gameObject, null, null, false); } return true; }
protected virtual void OnItemTargeted(bool becomeTargeted, RPGItem item) { }
/// <summary> /// add the item to the first open bag slot. will auto stack if item can stack /// will add as many copies of item as possible as indicated by count /// </summary> public bool AddToBag(RPGItem item, int count) { return AddToBag(item, count, false); }
/// <summary> /// add the item to the first open bag slot. will auto stack if item can stack</summary> /// will add as many copies of item as possible as indicated by count /// If autoIncSize=true then will increase the bagSize if too small to hold new item (usefull for shopkeeper's bags which dont need set size) /// </summary> public bool AddToBag(RPGItem item, int count, bool autoIncSize) { if (count <= 0 || item == null) return false; //bool allGood = false; CheckBagSize(); // 1st check if item can stack and if same type in bag if (item.maxStack > 1) { foreach (BagSlot slot in bag) { if (count <= 0) break; if (slot == null) continue; if (slot.stack == 0) continue; if (slot.item == item && slot.stack < item.maxStack) { // found a spot where item can be placed int canTake = item.maxStack - slot.stack; if (count >= canTake) { count -= canTake; slot.stack += canTake; UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //allGood = true; } else { slot.stack += count; count = 0; UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //allGood = true; break; } } } } // find open slot(s) to place the item into if (count > 0) { for (int slot = 0; slot < bag.Count; slot++) { if (count <= 0) break; // cant use null to check if slot is empty cause unity's serialize seems to be creating empty objects for me // so i cant be sure that empty slots will be null, but I can do next best thing and check stack if (bag[slot] != null) { if (bag[slot].stack != 0) continue; } bag[slot] = new BagSlot(); bag[slot].item = item; if (item.maxStack > 1) { if (count >= item.maxStack) { count -= item.maxStack; bag[slot].stack = item.maxStack; UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //allGood = true; } else { bag[slot].stack = count; count = 0; UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //allGood = true; break; } } else { bag[slot].stack = 1; count--; UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //allGood = true; } } if (autoIncSize && count > 0) { bagSize++; // simply add a slot and call Add again since it will make call to CheckBagSize(); AddToBag(item, count, autoIncSize); } } //if (allGood) //{ // UniRPGGameController.ExecuteActions(item.onAddedToBag, item.gameObject, null, gameObject, null, null, false); //} return (count <= 0); }
/// <summary>Find the first slot that contains a copy of the item. return -1 if none found.</summary> public int FindInBag(RPGItem item) { if (item == null) return -1; if (bag.Count == 0) return -1; for (int i = 0; i < bag.Count; i++) { if (bag[i].item == null) continue; if (bag[i].item.prefabId == item.prefabId) return i; } return -1; }
public bool BagContains(RPGItem item) { if (item == null) return false; if (bag.Count == 0) return false; for (int i = 0; i < bag.Count; i++) { if (bag[i].item == null) continue; if (bag[i].item.prefabId == item.prefabId) return true; } return false; }
/// <summary>Return true if the bag has enough space for the indicated item</summary> public bool BagHasSpaceForItem(RPGItem item) { if (item == null) return false; CheckBagSize(); // 1st check if item can stack and if same type in bag if (item.maxStack > 1) { foreach (BagSlot slot in bag) { if (slot == null) continue; if (slot.stack == 0) continue; if (slot.item == item && slot.stack < item.maxStack) { // found a spot where item can be placed int canTake = item.maxStack - slot.stack; if (canTake > 0) return true; } } } // find open slot(s) to place the item into for (int slot = 0; slot < bag.Count; slot++) { if (bag[slot] == null) return true; if (bag[slot].stack <= 0) return true; } return false; }
public void EquipVisibleItem(int slot, RPGItem item) { Transform t = mountPoints[slot]; if (t != null) { GameObject go = (GameObject)Object.Instantiate(item.gameObject); if (go.GetComponent<Collider>() != null) Destroy(go.GetComponent<Collider>()); if (go.GetComponent<Rigidbody>() != null) Destroy(go.GetComponent<Rigidbody>()); Destroy(go.GetComponent<RPGItem>()); go.transform.parent = t; go.transform.localPosition = Vector3.zero; go.transform.localRotation = Quaternion.identity; } }
/// <summary> /// equip the item to the slot. will do CheckEquipSlotsSize() 1st. return false if equip failed, for example from state preventing equip. /// NOTE that this function will unequip an item in the target slot but will NOT put that item in the bag. you must do that manually. /// NOTE Do not call this from editor scripts. The editor has its own Equip/UnEquip functions in ActorInspector /// </summary> public bool Equip(int slot, RPGItem item) { if (!CanEquip(slot, item)) return false; // attempt equip CheckEquipSlotsSize(UniRPGGlobal.DB); if (slot >= 0 && slot < equipped.Count) { // 1st "unequip" whatever might be in the slot if (equipped[slot] != null) UnEquip(slot); // now equip equipped[slot] = item; // show the visible model if there is a transform marked with slot name in the character EquipVisibleItem(slot, item); // run the equip action of the item UniRPGGameController.ExecuteActions(item.onEquipActions, item.gameObject, null, null, gameObject, null, false); return true; } return false; }
/// <summary>return true if item can be equipped to the slot</summary> public bool CanEquip(int slot, RPGItem item) { if (!item.validEquipSlots.Contains(slot)) return false; // check states (check if equip on this slot allowed) foreach (RPGState state in states) { if (state == null) continue; if (state.effect == RPGState.Effect.PreventEquipSlot) { if (state.slot == slot) { #if UNITY_EDITOR Debug.LogWarning("State prevents equipping an item to this slot."); #endif return false; } } } return true; }
/// <summary>Put the Item in the slot</summary> public bool SetActionSlot(int slot, RPGItem item) { if (item == null) return false; if (slot < 0 || slot >= actionSlots.Count) return false; actionSlots[slot].SetAsItem(item); return true; }