- Home /
KEEP INSTANTIATE PREFAB ONMOUSEDOWN
Hi, I have been looking for the solution to keep a prefab dragging for a long time. If i drag a gameobject through a viewportPos, the gameobject will be destroyed and instantiate a prefab at mouse position. While my mouse still down, i would like to keep the prefab dragging. Is there solution for doing that??? here is my script:
public void OnDrag(PointerEventData eventData)
{
Vector2 item_world_position = Camera.main.ScreenToWorldPoint(Input.mousePosition);
transform.position = item_world_position;
var viewportPos = Camera.main.WorldToViewportPoint(transform.position);
if (viewportPos.y > 0.165)
{
// Get the prefab to instantiate
Transform itemprefab = itemBeingDragged.GetComponent<InventoryItem>().item_prefab;
// Instantiate it to world position
Instantiate(itemprefab, item_world_position, Quaternion.identity);
itemprefab.transform.SetParent(GameObject.FindGameObjectWithTag("GroundedItem").transform, true);
Destroy(itemBeingDragged);
Destroy(itemBeingDragged.transform.parent.gameObject);
}
}
Answer by Piyush_Pandey · Sep 05, 2018 at 12:49 PM
It can be done this way.
Add the script [i will call it the First ] to the gameobject you drag through viewport.
Add a Spawned script to the object you want to spawn
Warning: You are destroying the First script after the new object is spawned. If you do that, it will not work. I will recommend you to disable it til you are holding the new Spawned object. Once you do the mouse up on the new Spawned object, then destroy First.
------------------EDIT--------------------------
So i made a sample project of this scenario, tested it and it works. I would recommend you also to make a simple sample project with one UI image object in the scene, and one UI image prefab which spawns. As i am not aware of all the details of the project requirements, once you get a hold of the concept, you can add your custom functionality.
First script.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
public class First : MonoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler
{
public GameObject itemprefab;
private Spawned _spawnedScript;
public static GameObject itemBeingDragged;
private Transform thisObjectTransform;
private Transform spawnedItemParent;//parent of the spawned item
private Transform mainCamTrans;
private Camera mainCamScript;
private Vector2 item_world_position;
private Vector3 viewportPos;
Vector3 startPosition;
Transform startParent;
PointerEventData data;
void Start()
{
//caching for optimisation
spawnedItemParent = GameObject.Find("Canvas").transform;//not recommended method. Must be cached from some manager script
mainCamScript = Camera.main;
mainCamTrans = Camera.main.transform;
thisObjectTransform = transform;
item_world_position = Vector2.zero;
viewportPos = Vector3.zero;
}
public void OnBeginDrag(PointerEventData beginData)
{
//pass the BEGIN pointer event data to the new spawnned object
if (_spawnedScript != null)//null till the object is spawned
{
_spawnedScript.OnBeginDrag(beginData);
}
itemBeingDragged = gameObject;
startPosition = thisObjectTransform.position;
startParent = thisObjectTransform.parent;
}
public void OnDrag(PointerEventData duringData)
{
//pass the DRAG pointer event data to the new spawnned object
if (_spawnedScript != null)
{
_spawnedScript.OnDrag(duringData);
}
item_world_position = mainCamScript.ScreenToViewportPoint(new Vector3(duringData.position.x , duringData.position.y , mainCamTrans.position.z));
thisObjectTransform.position = item_world_position;
viewportPos = mainCamScript.WorldToViewportPoint(thisObjectTransform.position);
if (viewportPos.y > 0.165 && _spawnedScript==null)
{
GameObject go = Instantiate(itemprefab, spawnedItemParent);
go.transform.position = item_world_position;
_spawnedScript = go.GetComponent<Spawned>();
/*
* Sorry i forgot to warn you that disabling the FIRST script will disable the pointer system
* I would recommend to make its color to "Clear" so that it is not visible.
* We will disable/destroy it when the player performs mouse up
*/
itemBeingDragged.GetComponent<Image>().color = Color.clear;
}
}
public void OnEndDrag(PointerEventData endData)
{
//pass the END pointer event data to the new spawnned object
if (_spawnedScript != null)
{
_spawnedScript.OnEndDrag(endData);
/*
* Here we will disable/destroy this script.
* Make sure that it is after we have passed on the pointer data
*/
// itemBeingDragged.SetActive(false);
Debug.Log("First objtect destruction");
Destroy(this.gameObject);
}
itemBeingDragged = null;
if (thisObjectTransform.parent == startParent)
{
thisObjectTransform.position = startPosition;
}
}
}
Spawned script.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
//This is the new spawned object
public class Spawned : MonoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler
{
Vector2 temp;
void Start()
{
temp = Vector2.zero;//cache for optimisation
}
public void OnBeginDrag(PointerEventData beginData)
{
//give the object the touch/mouse position
//vector3 should not be used else it will give Z depth to the object
temp = Camera.main.ScreenToWorldPoint(beginData.position);
transform.position = temp;
}
public void OnDrag(PointerEventData duringData)
{
//give the object the touch/mouse position
//vector3 should not be used else it will give Z depth to the object
temp = Camera.main.ScreenToWorldPoint(duringData.position);
transform.position = temp;
}
public void OnEndDrag(PointerEventData endData)
{
//give the object the touch/mouse position
//vector3 should not be used else it will give Z depth to the object
temp = Camera.main.ScreenToWorldPoint(endData.position);
transform.position = temp;
}
}
Thank you for your helping! Unity informs me that I have problems with these line in my script: _spawnedScript.OnBeginDrag(beginData); _spawnedScript.OnDrag(duringData); _spawnedScript.OnEndDrag(endData);
I also can't drag both gameobject and prefab.
i have edited my answer, please check it out and let me know.
Here is my full script for the First and Spawned: First:
using System.Collections;
using UnityEngine;
using UnityEngine.EventSystems;
//This is the first object that we dragged
public class First : $$anonymous$$onoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler
{
public GameObject itemprefab;
private Spawned _spawnedScript;
public static GameObject itemBeingDragged;
Vector3 startPosition;
Transform startParent;
PointerEventData data;
/*
* Instantiation code here
* Cache the Spawned script as it is going to be used in 3 places
*
*/
/*
The below three functions pass the data to the new spawned object
*/
public void OnBeginDrag(PointerEventData beginData)
{
//pass the BEGIN pointer event data to the new spawnned object
_spawnedScript.OnBeginDrag(beginData);
/*.
* rest of your code
*
* ......*/
itemBeingDragged = gameObject;
startPosition = transform.position;
startParent = transform.parent;
GetComponent<CanvasGroup>().blocksRaycasts = false;
}
public void OnDrag(PointerEventData duringData)
{
//pass the DRAG pointer event data to the new spawnned object
_spawnedScript.OnDrag(duringData);
/*.
* rest of your code
* ......*/
Vector2 item_world_position = Camera.main.ScreenToWorldPoint(Input.mousePosition);
transform.position = item_world_position;
var viewportPos = Camera.main.WorldToViewportPoint(transform.position);
if (viewportPos.y > 0.165)
{
// Get the prefab to instantiate
Transform itemprefab = itemBeingDragged.GetComponent<InventoryItem>().item_prefab;
// Instantiate it to world position
Instantiate(itemprefab, item_world_position, Quaternion.identity);
itemprefab.transform.SetParent(GameObject.FindGameObjectWithTag("GroundedItem").transform, true);
itemBeingDragged.gameObject.SetActive(false);
}
}
public void OnEndDrag(PointerEventData endData)
{
//pass the END pointer event data to the new spawnned object
_spawnedScript.OnEndDrag(endData);
/*.
* rest of your code
* ......*/
{
itemBeingDragged = null;
GetComponent<CanvasGroup>().blocksRaycasts = true;
if (transform.parent == startParent)
{
transform.position = startPosition;
}
}
}
}
and the Spawned: using System.Collections; using UnityEngine; using UnityEngine.EventSystems;
//This is the new spawned object
public class Spawned : $$anonymous$$onoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler
{
public void OnBeginDrag(PointerEventData beginData)
{
//give the object the touch/mouse position
transform.position = Camera.main.ScreenToWorldPoint(Input.mousePosition);
}
public void OnDrag(PointerEventData duringData)
{
//give the object the touch/mouse position
transform.position = Camera.main.ScreenToWorldPoint(Input.mousePosition);
}
public void OnEndDrag(PointerEventData endData)
{
//give the object the touch/mouse position
transform.position = Camera.main.ScreenToWorldPoint(Input.mousePosition);
}
}
Your answer
Follow this Question
Related Questions
Unable to make 2D enemy zigzag : Top Down View 1 Answer
Multiple Cars not working 1 Answer
Distribute terrain in zones 3 Answers
My script only partially works 2 Answers