1

The type needed has name stored in string so i can't use it as a type inside my code in order to find an object .

I tried various ways to use the string as a type in order to find the object needed but none of them worked.

levelN = "Level"+levelNumber;

First try:

var levelManager = FindObjectOfType< Type.GetType(levelN)>(); 

Second try:

var type = Type.GetType(levelN);

var levelManager = FindObjectOfType< type.GetType()>(); 

Third try:

var levelManager = FindObjectOfType< type>(); 

I created "type" which has the Type needed for the search of the object but when I used in my code an error appear (cs1525) on the first and the second. On the third try this shows up:

error CS0118: 'type' is a variable but is used like a type

Giulio Caccin
  • 2,962
  • 6
  • 36
  • 57
Seif Karoui
  • 126
  • 5
  • 1
    In the first try you are trying to find object which can be found by its component types(e.g MeshRenderer) but you are trying to find them by its name, that's incorrect – Chestera Jul 14 '19 at 20:00
  • 1
    There's two different things you need to do here. 1. get a `Type` from a `string` 2. use reflection to invoke generics with a `Type` at runtime Both of these things are possible (`Type.GetType()`, `MethodInfo.MakeGenericMethod`), but: are usually best avoided and don't work well on all platforms (especially things like unity). Can you not change what you need here, perhaps just *recognizing* some types and hard coding them? – Marc Gravell Jul 14 '19 at 20:02

1 Answers1

1

It's not entirely clear what you're asking, due to the lack of a good minimal, complete, and verifiable code example. In particular, while you say you want to retrieve an object by type, it's not clear from your post that there are in fact types having names like Level1, Level2, etc.

Assuming there are though, then you should just use the non-generic FindObjectByType(Type) overload, documented here: https://docs.unity3d.com/2018.4/Documentation/ScriptReference/Object.FindObjectOfType.html

Then you can pass an actual Type object, retrieved by calling Type.GetType(string). Pay close attention to the documentation though:

typeName String
The assembly-qualified name of the type to get. See AssemblyQualifiedName. If the type is in the currently executing assembly or in Mscorlib.dll, it is sufficient to supply the type name qualified by its namespace.

It's unlikely you can just pass e.g. the string "Level1" to the method.

Frankly, it would be much better for you to initialize your own Dictionary<string, object> table to look up the "level manager" objects. Assuming your "level manager" objects share a common base type, you can use that as the dictionary's value type, instead of object.

Presumably, this is something your code needs to do only infrequently. As long as this doesn't happen very often, it should be okay. Still, do note the guidance in the Unity3d documentation:

It is a general best practice to eliminate all usage of Object.Find and Object.FindObjectOfType in production code. As these APIs require Unity to iterate over all GameObjects and Components in memory, they rapidly become non-performant as the scope of a project grows.

Peter Duniho
  • 68,759
  • 7
  • 102
  • 136
  • My goal is that gameobjects can use the string so they can access the specific class of that level in which they exist to control variables like score in that level class. – Seif Karoui Jul 14 '19 at 22:44
  • @SeifKaroui Unless you need to have different member variable names for each 'class', I suggest the `Dictionary` style of saving unique information. Otherwise, create a base class, or use a `ScriptableObject` and save each level as its own instance. – Eliasar Jul 15 '19 at 19:32