4
\$\begingroup\$

I want to use Instantiate(item, new Vector3(...), Quaternion.identity) to land an item at the position that was clicked. My game is using a third-person view (example).

This is the code that I think I should be using:

if(Input.GetKeyDown(KeyCode.Mouse0) && cur_items > 0){
    Instantiate(item, object_pos, Quaternion.identity);
    cur_items--;
}

mouse_pos = Input.mousePosition;
object_pos = Camera.main.WorldToScreenPoint(mouse_pos);

What am I doing wrong?

\$\endgroup\$
4
  • \$\begingroup\$ Do you want to keep your Z axis Common? or Do you want depth also? like instantiating an object somewhere far away in the background? either case it should be Camera.main.ScreenToWorldPoint \$\endgroup\$ May 24, 2014 at 10:16
  • \$\begingroup\$ Can you clarify what you're having trouble with? Is it instantiating an object at a specific position, or the physics of moving an item towards a position? \$\endgroup\$
    – House
    May 24, 2014 at 13:23
  • \$\begingroup\$ @Byte56 Sorry I wasn't very specific. The problem is with the physics of moving the item to the position. The item instantiates as it should, just not where it should. \$\endgroup\$
    – eren_tetik
    May 24, 2014 at 13:30
  • \$\begingroup\$ Your comment makes it sound like both. You say physics, and also say it instantiates at the wrong position. \$\endgroup\$
    – House
    May 24, 2014 at 13:36

3 Answers 3

3
\$\begingroup\$

First of all you need to determine how would you determine z-axis. If you want the z to be constant, just change the position after instantiating or while instantiating. Another way would be to casting a ray from camera, and instantiating the object at ray hit position. Something like below -

if(Input.GetMouseDown(0)){
    Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
    RayCastHit hit;
    if (Physics.Raycast(ray, out hit, 100)) {
        Instantiate(item, hit.point, Quaternion.identity);
    }
}

JS Version(untested)

if(Input.GetMouseDown(0)){
    var ray:Ray = Camera.main.ScreenPointToRay(Input.mousePosition);
    var hit:RayCastHit;
    if (Physics.Raycast(ray, hit, 100)) {
        Instantiate(item, hit.point, Quaternion.identity);
    }
}

PS: LVBen got a point that using hit.transform.position will give weird results. It's upto you if you want to use it or not. hit.point will be the better option anyways.

\$\endgroup\$
3
  • \$\begingroup\$ I tried this but I'm getting a couple errors: i.imgur.com/xp0dzv5.png i.imgur.com/BQKQVap.png \$\endgroup\$
    – eren_tetik
    May 25, 2014 at 4:40
  • 1
    \$\begingroup\$ I'd recommend to use hit.point instead of hit.transform.position, because it will create the object exactly where you click instead of at the origin of the object that was clicked on. For example, if you clicked on a very large terrain, your code would cause the object to always appear at the same spot (the terrain's origin), no matter what part of the terrain that you clicked on, and it would likely be nowhere near where you clicked. \$\endgroup\$
    – LVBen
    May 25, 2014 at 18:45
  • \$\begingroup\$ @eren_trigger My code was in C#. I've put a JS version there, although it's untested but it should work. \$\endgroup\$
    – noob
    May 25, 2014 at 23:30
3
\$\begingroup\$

It should be Camera.main.ScreenToWorldPoint(mouse_pos); and it should come before instantiating the object

\$\endgroup\$
3
  • \$\begingroup\$ I did this but the items now instantiate at some weird positions. EDIT - i.imgur.com/IyNSfut.png \$\endgroup\$
    – eren_tetik
    May 24, 2014 at 14:40
  • \$\begingroup\$ I cant get a clear picture.. may be your viewport may be big thats why its instantiating at those positions. is it instantiating where you click or somewhere totally elsewhere? \$\endgroup\$ May 25, 2014 at 9:45
  • \$\begingroup\$ I'm clicking where I want it to instantiate. I click somewhere on the plane hoping the item will instantiate there, but it seems to spawn somewhere beyond the plane. Sorry I can't explain it clearly \$\endgroup\$
    – eren_tetik
    May 25, 2014 at 12:38
0
\$\begingroup\$

You could use a Ray. This is how I am doing it on my current project:

Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit rayHit;
if (Physics.Raycast(ray, out rayHit))
{
    // ... instantiate object here
    newObject.transform.position = rayHit.point;
}

That will instantiate an object at the point where the ray collides with an object. All of my meshes have the origin at the bottom, so my new objects will appear exactly on top of whichever object is beneath the mouse.

\$\endgroup\$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .