evelynshilosky

InteractionSystem - Part 6.1

Mar 27th, 2025
289
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 12.32 KB | None | 0 0
  1. using UnityEngine;
  2. using System.Collections.Generic;
  3.  
  4. public class InteractionSystem : MonoBehaviour
  5. {
  6.     public Transform leftObjectHolder;
  7.     public Transform rightObjectHolder;
  8.     public LayerMask pickupLayer;
  9.     public float placementDistance = 5f;
  10.     public LayerMask placementLayerMask;
  11.     public float previewUpdateInterval = 0.1f;
  12.     public float placementHeightOffset = 0.1f;
  13.     public float rotationIncrement = 45f;
  14.     public Transform backpackWearPosition;
  15.  
  16.     private InventorySystem inventorySystem;
  17.     private PlayerMovement playerMovement;
  18.     private UIManager uiManager;
  19.     private bool isPrecisionDrop = false;
  20.     private Dictionary<GameObject, int> originalLayers = new Dictionary<GameObject, int>();
  21.     private float lastPreviewUpdateTime;
  22.     private bool isRotating = false;
  23.     private Vector3 currentRotation;
  24.     private List<GameObject> previewObjects = new List<GameObject>();
  25.     public Item currentBackpackItem;
  26.  
  27.     private void Start()
  28.     {
  29.         inventorySystem = InventorySystem.Instance;
  30.         playerMovement = GetComponent<PlayerMovement>();
  31.         uiManager = UIManager.Instance;
  32.         UpdateItemVisibility();
  33.     }
  34.  
  35.     private void Update()
  36.     {
  37.         if (isPrecisionDrop)
  38.         {
  39.             UpdatePlacementPreview();
  40.             HandleRotation();
  41.         }
  42.         else
  43.         {
  44.             ClearPreviewObjects();
  45.         }
  46.  
  47.         if (Input.GetKeyDown(KeyCode.E) && currentBackpackItem != null && !inventorySystem.IsBackpackEquipped)
  48.         {
  49.             WearBackpack();
  50.         }
  51.     }
  52.  
  53.     public void TryPickUpItem(InteractableObject interactable)
  54.     {
  55.         Item item = interactable.item;
  56.  
  57.         if (item.isBackpack && !inventorySystem.IsBackpackEquipped)
  58.         {
  59.             PickUpBackpack(item);
  60.         }
  61.         else
  62.         {
  63.             bool isLeftHand = inventorySystem.rightHandItem != null && inventorySystem.leftHandItem == null;
  64.             EquipItem(item, isLeftHand, item.isTwoHanded);
  65.             playerMovement.UpdateCarryingAnimations();
  66.         }
  67.     }
  68.  
  69.     private void PickUpBackpack(Item backpackItem)
  70.     {
  71.         bool isLeftHand = inventorySystem.rightHandItem != null && inventorySystem.leftHandItem == null;
  72.         EquipItem(backpackItem, isLeftHand, false);
  73.         currentBackpackItem = backpackItem;
  74.         uiManager.ShowBackpackPrompt(backpackItem);
  75.     }
  76.  
  77.     public void HandleBackpackPrompt(bool accepted)
  78.     {
  79.         if (accepted)
  80.         {
  81.             WearBackpack();
  82.         }
  83.         else
  84.         {
  85.             uiManager.UpdateBackpackPrompt();
  86.             // Don't close the prompt here
  87.         }
  88.     }
  89.  
  90.     public void WearBackpack()
  91.     {
  92.         if (currentBackpackItem != null)
  93.         {
  94.             bool wasLeftHand = inventorySystem.leftHandItem == currentBackpackItem;
  95.             inventorySystem.UnequipItem(wasLeftHand);
  96.  
  97.             currentBackpackItem.transform.SetParent(backpackWearPosition);
  98.             currentBackpackItem.transform.localPosition = Vector3.zero;
  99.             currentBackpackItem.transform.localRotation = Quaternion.identity;
  100.  
  101.             Destroy(currentBackpackItem.GetComponent<Rigidbody>());
  102.             MeshCollider meshCollider = currentBackpackItem.GetComponent<MeshCollider>();
  103.             if (meshCollider != null) meshCollider.enabled = false;
  104.  
  105.             inventorySystem.EquipBackpack(currentBackpackItem);
  106.             currentBackpackItem = null;
  107.  
  108.             uiManager.ClosePrompt();
  109.             playerMovement.UpdateCarryingAnimations();
  110.         }
  111.     }
  112.  
  113.     public void UnequipBackpack()
  114.     {
  115.         if (inventorySystem.IsBackpackEquipped)
  116.         {
  117.             Item backpack = inventorySystem.backpack;
  118.             inventorySystem.UnequipBackpack();
  119.  
  120.             MeshCollider meshCollider = backpack.GetComponent<MeshCollider>();
  121.             if (meshCollider != null) meshCollider.enabled = true;
  122.  
  123.             if (backpack.GetComponent<Rigidbody>() == null)
  124.             {
  125.                 backpack.gameObject.AddComponent<Rigidbody>();
  126.             }
  127.  
  128.             backpack.transform.SetParent(null);
  129.             backpack.transform.position = transform.position + transform.forward * 1.5f;
  130.  
  131.             playerMovement.UpdateCarryingAnimations();
  132.         }
  133.     }
  134.  
  135.     private void EquipItem(Item item, bool isLeftHand, bool isTwoHanded)
  136.     {
  137.         inventorySystem.EquipItem(item, isLeftHand, isTwoHanded);
  138.         UpdateItemPosition(item.gameObject, isLeftHand);
  139.         ChangeItemLayer(item.gameObject, pickupLayer);
  140.         playerMovement.UpdateCarryingAnimations();
  141.     }
  142.  
  143.     public void UpdateItemPosition(GameObject itemObject, bool isLeftHand)
  144.     {
  145.         Transform objectHolder = isLeftHand ? leftObjectHolder : rightObjectHolder;
  146.         Item item = itemObject.GetComponent<Item>();
  147.         Vector3 positionOffset = isLeftHand ? item.leftPositionOffset : item.rightPositionOffset;
  148.         Vector3 rotationOffset = isLeftHand ? item.leftRotationOffset : item.rightRotationOffset;
  149.  
  150.         itemObject.transform.SetParent(objectHolder);
  151.         itemObject.transform.localPosition = positionOffset;
  152.         itemObject.transform.localRotation = Quaternion.Euler(rotationOffset);
  153.     }
  154.  
  155.     private void UpdateItemVisibility()
  156.     {
  157.         if (inventorySystem.leftHandItem != null)
  158.         {
  159.             inventorySystem.leftHandItem.gameObject.SetActive(!isPrecisionDrop);
  160.         }
  161.         if (inventorySystem.rightHandItem != null)
  162.         {
  163.             inventorySystem.rightHandItem.gameObject.SetActive(!isPrecisionDrop);
  164.         }
  165.     }
  166.  
  167.     private void UpdatePlacementPreview()
  168.     {
  169.         if (Time.time - lastPreviewUpdateTime < previewUpdateInterval) return;
  170.  
  171.         lastPreviewUpdateTime = Time.time;
  172.  
  173.         RaycastHit hit;
  174.         if (Physics.Raycast(Camera.main.transform.position, Camera.main.transform.forward, out hit, placementDistance, placementLayerMask))
  175.         {
  176.             List<Item> itemsToPlace = new List<Item>();
  177.             if (inventorySystem.leftHandItem != null) itemsToPlace.Add(inventorySystem.leftHandItem);
  178.             if (inventorySystem.rightHandItem != null) itemsToPlace.Add(inventorySystem.rightHandItem);
  179.  
  180.             ClearPreviewObjects();
  181.  
  182.             Vector3 previewPosition = hit.point + hit.normal * (0.05f + placementHeightOffset);
  183.             Quaternion previewRotation = !isRotating ? Quaternion.LookRotation(hit.normal, Vector3.up) : Quaternion.Euler(currentRotation);
  184.  
  185.             for (int i = 0; i < itemsToPlace.Count; i++)
  186.             {
  187.                 GameObject previewObj = Instantiate(itemsToPlace[i].gameObject);
  188.                 Destroy(previewObj.GetComponent<Rigidbody>());
  189.                 Destroy(previewObj.GetComponent<Collider>());
  190.                 previewObj.AddComponent<Outline>();
  191.  
  192.                 previewObj.transform.position = previewPosition + Vector3.right * (i * 0.5f);
  193.                 previewObj.transform.rotation = previewRotation;
  194.  
  195.                 Outline outline = previewObj.GetComponent<Outline>();
  196.                 outline.OutlineMode = Outline.Mode.OutlineAll;
  197.                 outline.OutlineColor = Color.green;
  198.                 outline.OutlineWidth = 5f;
  199.  
  200.                 previewObjects.Add(previewObj);
  201.                 previewObj.SetActive(true);
  202.             }
  203.  
  204.             bool canPlace = !Physics.Raycast(previewPosition, Vector3.down, placementHeightOffset + 0.05f, placementLayerMask);
  205.             foreach (var obj in previewObjects)
  206.             {
  207.                 obj.GetComponent<Outline>().OutlineColor = canPlace ? Color.green : Color.red;
  208.             }
  209.         }
  210.         else
  211.         {
  212.             ClearPreviewObjects();
  213.         }
  214.     }
  215.  
  216.     private void HandleRotation()
  217.     {
  218.         if (Input.GetKeyDown(KeyCode.R))
  219.         {
  220.             isRotating = !isRotating;
  221.             if (isRotating)
  222.             {
  223.                 currentRotation = previewObjects[0].transform.rotation.eulerAngles;
  224.                 uiManager.ShowInventoryPrompt(null);
  225.                 uiManager.UpdatePromptText("Rotation mode enabled. Use Q/E to rotate horizontally, Z/C to rotate vertically.");
  226.                 uiManager.ShowOkayButton();
  227.             }
  228.             else
  229.             {
  230.                 uiManager.ShowInventoryPrompt(null);
  231.                 uiManager.UpdatePromptText("Rotation mode disabled.");
  232.                 uiManager.ShowOkayButton();
  233.             }
  234.         }
  235.  
  236.         if (isRotating && previewObjects.Count > 0)
  237.         {
  238.             if (Input.GetKeyDown(KeyCode.Q))
  239.             {
  240.                 currentRotation.y -= rotationIncrement;
  241.             }
  242.             else if (Input.GetKeyDown(KeyCode.E))
  243.             {
  244.                 currentRotation.y += rotationIncrement;
  245.             }
  246.             else if (Input.GetKeyDown(KeyCode.Z))
  247.             {
  248.                 currentRotation.x -= rotationIncrement;
  249.             }
  250.             else if (Input.GetKeyDown(KeyCode.C))
  251.             {
  252.                 currentRotation.x += rotationIncrement;
  253.             }
  254.  
  255.             foreach (var obj in previewObjects)
  256.             {
  257.                 obj.transform.rotation = Quaternion.Euler(currentRotation);
  258.             }
  259.         }
  260.     }
  261.  
  262.     public void DropItem(bool isLeftHand)
  263.     {
  264.         Item itemToDrop = isLeftHand ? inventorySystem.leftHandItem : inventorySystem.rightHandItem;
  265.         if (itemToDrop != null)
  266.         {
  267.             GameObject itemObject = itemToDrop.gameObject;
  268.             itemObject.transform.SetParent(null);
  269.  
  270.             Vector3 dropPosition;
  271.             if (isPrecisionDrop && previewObjects.Count > 0)
  272.             {
  273.                 int index = isLeftHand ? 0 : (previewObjects.Count > 1 ? 1 : 0);
  274.                 dropPosition = previewObjects[index].transform.position;
  275.                 itemObject.transform.position = dropPosition;
  276.                 itemObject.transform.rotation = previewObjects[index].transform.rotation;
  277.             }
  278.             else
  279.             {
  280.                 dropPosition = transform.position + transform.forward * 1f + transform.right * Random.Range(-0.5f, 0.5f);
  281.                 itemObject.transform.position = dropPosition;
  282.                 itemObject.transform.rotation = Random.rotation;
  283.             }
  284.  
  285.             itemObject.SetActive(true);
  286.  
  287.             Rigidbody rb = itemObject.GetComponent<Rigidbody>();
  288.             if (rb == null) rb = itemObject.AddComponent<Rigidbody>();
  289.             rb.isKinematic = false;
  290.             rb.useGravity = true;
  291.             rb.AddForce(Vector3.down * 2f, ForceMode.Impulse);
  292.  
  293.             inventorySystem.UnequipItem(isLeftHand);
  294.             RestoreOriginalLayer(itemObject);
  295.  
  296.             InteractableObject interactable = itemObject.GetComponent<InteractableObject>();
  297.             if (interactable != null)
  298.             {
  299.                 interactable.enabled = true;
  300.             }
  301.  
  302.             playerMovement.UpdateCarryingAnimations();
  303.         }
  304.  
  305.         ClearPreviewObjects();
  306.  
  307.         if (inventorySystem.leftHandItem == null && inventorySystem.rightHandItem == null)
  308.         {
  309.             isPrecisionDrop = false;
  310.             isRotating = false;
  311.         }
  312.  
  313.         UpdateItemVisibility();
  314.     }
  315.  
  316.     public void DropBothItems()
  317.     {
  318.         DropItem(true);
  319.         DropItem(false);
  320.     }
  321.  
  322.     public void ChangeItemLayer(GameObject itemObject, LayerMask newLayer)
  323.     {
  324.         if (!originalLayers.ContainsKey(itemObject))
  325.         {
  326.             originalLayers[itemObject] = itemObject.layer;
  327.         }
  328.         itemObject.layer = (int)Mathf.Log(newLayer.value, 2);
  329.     }
  330.  
  331.     private void RestoreOriginalLayer(GameObject itemObject)
  332.     {
  333.         if (originalLayers.ContainsKey(itemObject))
  334.         {
  335.             itemObject.layer = originalLayers[itemObject];
  336.             originalLayers.Remove(itemObject);
  337.         }
  338.     }
  339.  
  340.     public void TogglePrecisionDrop()
  341.     {
  342.         isPrecisionDrop = !isPrecisionDrop;
  343.         UpdateItemVisibility();
  344.         uiManager.ShowInventoryPrompt(null);
  345.         uiManager.UpdatePromptText(isPrecisionDrop ? "Precision drop enabled" : "Precision drop disabled");
  346.         uiManager.ShowOkayButton();
  347.     }
  348.  
  349.     private void ClearPreviewObjects()
  350.     {
  351.         foreach (var obj in previewObjects)
  352.         {
  353.             Destroy(obj);
  354.         }
  355.         previewObjects.Clear();
  356.     }
  357.  
  358.     public bool IsPrecisionDropEnabled()
  359.     {
  360.         return isPrecisionDrop;
  361.     }
  362. }
  363.  
Advertisement
Add Comment
Please, Sign In to add comment