- Home /
Accessing 'un-namespaced' class from UnityStandardAssets.Characters.ThirdPerson
I've never really had to deal with namespaces before, so excuse any ignorance that might be present here.
I'm writing a static camera system (kind of like you'd see in the old Resident Evil games) and I'm currently using Unity's Third Person Controller. I'm trying to modify ThirdPersonUserControl.cs for the needs of this system.
Basically, I want to subscribe it to a custom event so that every time my active camera changes, ThirdPersonUserControl will update its reference to the camera appropriately (as this reference is what allows for camera relative controls).
I have a class CameraMaster which contains the event I want to subscribe to, but I can't access it from ThirdPersonUserControl. I'm pretty sure this has something to do with namespacing, as ThirdPersonUserControl resides in the namespace UnityStandardAssets.Characters.ThirdPerson.
Every time I try to reference CameraMaster in ThirdPersonUserControl, I get the error message
The name 'CameraMaster' does not exist in the current context.
I've tried namespacing CameraMaster and putting in the appropriate using
statement in ThirdPersonUserControl, as well as putting CameraMaster in the same namespace. Nothing seems to have worked. I even tried using global::
.
I read in This Question that the problem was that the other class was in a plugins folder, however moving the scripts into the same directory also didn't work for me.
I know that there are other solutions to this problem (storing a reference to the ThirdPersonUserControl in CameraMaster and manually calling a function to do what I want, or even just moving a single camera to different locations, rather than having multiple cameras), however, for the purposes of learning, I really want to know how to access my CameraMaster class from ThirdPersonUserControl.
It's probably not relevant, but here is CameraMaster:
public class CameraMaster : MonoBehaviour {
[SerializeField]
private Camera startingCamera;
private static Camera[] cameras;
public delegate void CameraEventHandler(Camera cam);
public static event CameraEventHandler OnCameraChange;
void Start() {
cameras = GameObject.FindObjectsOfType<Camera>();
ShowCamera(startingCamera);
}
public static void ShowCamera(Camera cam) {
if (OnCameraChange != null) {
OnCameraChange(cam);
}
foreach (Camera camera in cameras)
camera.enabled = camera == cam;
}
}
And, for reference, here is ThirdPersonUserControl's class definition:
using System;
using UnityEngine;
using UnityStandardAssets.CrossPlatformInput;
namespace UnityStandardAssets.Characters.ThirdPerson {
[RequireComponent(typeof(ThirdPersonCharacter))]
public class ThirdPersonUserControl : MonoBehaviour {
Thanks for any help!
If Camera$$anonymous$$aster is not in a namespace, you don't need to do anything special to access it. Pleast post the line of code that actually generates the "The name 'Camera$$anonymous$$aster' does not exist in the current context" error.
Well I never even had a complete line that generated the error. I couldn't get past typing "Camera$$anonymous$$aster".
However, the actual line would look like this:
Camera$$anonymous$$aster.OnCameraChange += SetCamera;
And the SetCamera() function:
public void SetCamera(Camera cam) {
m_Cam = cam.transform;
}
Then I get the error:
The name `Camera$$anonymous$$aster' does not exist in the current context
$$anonymous$$y project directory, in case it's related to that:
Note that the line
Camera$$anonymous$$aster.OnCameraChange += SetCamera;
exists at the top of the Start method
Answer by villevli · Nov 21, 2016 at 05:50 PM
Make a copy of the ThirdPersonUserControl.cs and put it in your own scripts folder. Also change it to different namespace and add using UnityStandardAssets.Characters.ThirdPerson;
(not needed if you copied everything the script uses from UnityStandardAssets.Characters.ThirdPerson to your new namespace).
I don't usually modify Standard assets directly but copy them like this. If they get updated it's easy to import the new versions when you have not modified them in their original location.
This definitely solved the problem. Thank you. So far this is the best answer, but it still feels like a work around.
It's not a workaround. The problem is that the folder "Standard Assets" has a special meaning. It's a seperate compilation group which are compiled before your own "project" scripts.
See the SpecialFolders page as well as the script compilation order page. There's also a wiki page on that subject. Scripts inside the Standard Assets folder are considered "standard components" which can't reference anything outside the Standard Assets folder. They are compiled seperately and just "linked in". Normal "project" scripts can access classes defined inside Standard Assets but not the other way round.
In general it's better to have classes not too tightly bound to each other.
Answer by spraw · Nov 21, 2016 at 06:12 PM
https://docs.unity3d.com/Manual/ScriptCompileOrderFolders.html
Standard Assets get compiled first, which means that 'CameraMaster' does not exist when 'ThirdPersonUserControl' tries to access it.
A Standard Asset (A 3rd party library, framework, etc) is usually not meant to access or reference your own scripts. You should move the Standard Asset out of its special folder, as you are not using it as a Standard Asset, but as a modified base.
Answer by tanoshimi · Nov 21, 2016 at 06:13 PM
Your problem is unrelated to namespaces. The problem is that ThirdPersonUserControl is in the "Standard Assets" folder. All scripts placed in that folder are compiled in the first phase of compilation. Your CameraMaster script, however, is a regular user class which is not compiled until a later phase of compilation - more explanation at https://docs.unity3d.com/Manual/ScriptCompileOrderFolders.html. So, at the point that ThirdPersonUserControl is compiled, the reference to CameraMaster cannot be resolved, because that script isn't compiled until later.
Generally speaking, you shouldn't modify files in the standard assets for this reason. If you want to create your own modification based on a standard asset, copy it into a different scripts directory in your project.
Your answer
Follow this Question
Related Questions
third person camera 2 Answers
Problems with Camera (Camera keeps looking at the feet of my character) 1 Answer
Modify Standard Asset --> MultipurposeCameraRig (add manual rotation) 0 Answers
How to make camera position relative to a specific target. 1 Answer
ThirdPersonController/ThirdPersonAnimatorController Jitter when moving 1 Answer