camera.ScreenToWorldPoint() question Non-connected GameObject

I’ve looked and looked, and drove myself bonkers trying to get this to work correctly.
I found a question titled similarly to mine, but it dealt with a camera that was attached to the component.

I’m trying to do approximately the same thing, but I’m referencing a camera that’s not attached to the object.

The object moves, the game camera (tagged “MainCamera”) is stationary so I didn’t want to attach it as a component. Here’s my attempt to code the scenario:

//Inspector Variables
var mainCamera = Camera;
var mousePosition;

function Start () 
{
var mainCamera = GameObject.FindWithTag ("MainCamera");
{

function Update()
{
 if (Input.GetButtonDown("Fire1"))
   { 
   mousePosition = mainCamera.ScreenToWorldPoint(Input.mousePosition); //Line 40

    print(mousePosition);
   }
}

(I’ve removed everything not related to the issue I’m having.)

The error I’m getting (as soon as I press the mouse button) is:

InvalidCastException: Cannot cast from
source type to destination type.
(wrapper dynamic-method)
UnityEngine.Camera.Camera$ScreenToWorldPoint$UnityEngine.Vector3
(object,object) <IL 0x00001,
0x0002f>
Boo.Lang.Runtime.RuntimeServices.Invoke
(object,string,object) <IL 0x0004c,
0x00125>
UnityScript.Lang.UnityRuntimeServices.Invoke
(object,string,object,System.Type)
<IL 0x00018, 0x000a9>
ScriptEnemyCube.Update () (at
Assets/ScriptEnemyCube.js:40)

(Line 40 is noted in the code above)

I put a print(mainCamera) in two positions in the script to test it (after removing the offending lines 40 & 41). One in the start function immediately after the variable is re-declared:

The log says:

Main Camera (UnityEngine.GameObject)

This is Correct, and represents the name of the object I was looking for.

The other one I placed into the Update function:
The log says:

UnityEngine.Camera

I can see that the variable isn’t carrying into the Update function from the start function. Everything I can find regarding the “find with tag” is that it should go into the Start Function, and I don’t know how to pass the value along to where I need it.

I assume that’s what the problem is here?

Honestly, I don’t think I even need to FIND the camera to begin with… I know where it is, what’s it’s named, etc. I just don’t know how to hardcode that info directly, rather than have it go looking for it.

Can anyone suggest a fix for this, or explain what I’m doing wrong? I’m not used to programming in javascript, and am new to Unity 3d.

If it’s too complicated to explain, I understand, just lemme’ know, and I’ll go bury myself in more tutorials. Thanks for your time.


Thanks! I’ll be able to test it the moment I get home.

Everything I’d read had suggested that “var” was optional, and was implied whether you added it or not. So when used within a function, it actually creates a “local” variable that’s only good within the function it was called. That’s kinda’ important, thanks for making me aware of that.

I definately should have given types for the variables, I was a little confused by the wording of one of the tuts I’d looked at earlier, and some of the error messages I was getting. I thought perhaps I was using the wrong type, so I was trying to let the system pick the appropriate one for me.

(The bracket was just a typo when I put it up in here.)

I’m telling you, I spent 4 hours on this stupid thing… tweaking this and tweaking that, and trying not to use a raycast from the mouse to do the same thing, because I wanted to successfully call another gameobject and use it.

EDITED: There are several minor errors in this script. The error found in line 40 was not generated there, but in Start: when you placed var before mainCamera, a temporary variable with this name was created inside Start - it disappeared as soon as Start ended, so the public variable mainCamera declared at the beginning of your script was not ever set. Another detail: always declare the variable type, unless you initialize it with a value of well defined type. If you write var pos = Vector3.zero;, Unity knows pos is a Vector3. If you just write var pos;, Unity uses a variant type, which takes more time to be processed and may render errors sometimes. The type is specially important to distinguish between int and float: this is by far the most commom error. If you write var t = 0;, Unity assumes t is int, and you may get in trouble if adding float values to it - specially Time.deltaTime, which is a small float value. To get rid of these errors, write var t = 0.0; or var t: float = 0;. To finish this brief explanation, variable declared outside any function have script scope, what means they are known by everybody inside the script, and live while the script is alive. Variable defined inside functions have local scope: they are known only inside the function, and their contents are lost when the function returns.

//Inspector Variables
var mainCamera: Camera; // define the variable type this way
var mousePosition: Vector3; // never let a variable untyped

function Start () 
{ // the var keyword would create a new mainCamera temporary variable
  // doesn't use it since you want to use the public mainCamera variable
    mainCamera = GameObject.FindWithTag ("MainCamera");
} // <- this bracket was turned to the wrong side!

function Update()
{
  if (Input.GetButtonDown("Fire1"))
  { // line 40 had no errors! the error cause was in Start
    mousePosition = mainCamera.ScreenToWorldPoint(Input.mousePosition); //Line 40
    // print wants strings; convert ints, floats, vectors etc. to strings using
    // .ToString(), or concatenating with strings (kind of "Num "+i)
    print(mousePosition.ToString()); 
  }
}