Home > Mobile >  How to store a call to GameObject.transform.Translate in a variable, and invoke it?
How to store a call to GameObject.transform.Translate in a variable, and invoke it?

Time:05-03

How can I create a variable that holds a single call to Gameobject.transform.Translate, like below, because I have lots of if-else statements I need to put in?

var Trans = 
Gameobject.transform.Translate(screentouch.deltaPosition.x, screentouch.deltaPosition.x, 0);

if(a > 5){
  Trans
}else if (a  > 8){
  Trans
}

This code is obviously not correct - it generates a compiler error:

var Trans = 
Gameobject.transform.Translate(screentouch.deltaPosition.x, screentouch.deltaPosition.x, 0);

error: Cannot assign void to an implicitly - typed variable.

CodePudding user response:

It looks like you're trying to do something like this:

System.Action trans = () => { 
   Gameobject.transform.Translate(
       screentouch.deltaPosition.x, 
       screentouch.deltaPosition.x, // Are you sure you don't want y here?
       0
   );
};

The expression () => { ... } defines a lambda function, kind of a one-off, on-the-spot function that doesn't persist as a member of a class. The System.Action variable trans we store it in is a delegate type - similar to a "function pointer" or "closure" in other languages. It stores a reference to a function (and its corresponding this context) so later code can call that function by reference to the variable (just type trans()), without that code needing to know or care what function it's really calling.

The trouble is this isn't really appropriate for a game context because it allocates heap memory to hold the lambda function and the delegate - that's wasteful here. It slows down your code and can cause hitches when the garbage collector needs to run to clear out the junk. A little garbage isn't the end of the world, but we'd like to avoid allocating every frame if we can. Let's look at ways we can avoid the unnecessary allocation.

One way is to use a flag variable.

bool shouldMove = false;

if(a > 5){
  shouldMove = true;
}else if (a  > 8){
  shouldMove = true;
}

if (shouldMove) {
   Gameobject.transform.Translate(
       screentouch.deltaPosition.x, 
       screentouch.deltaPosition.x, // Still probably a y you want.
       0
   );
}

Or, depending on how complex your ifs get, you could even combine them like:

bool shouldMove = (a > 5) || (a > 8) || ...

...or maybe even a switch expression.

Another approach is to just define a helper function to handle this.

private void Move(GameObject go, Touch touch) {
    go.transform.Translate(
       screentouch.deltaPosition.x, 
       screentouch.deltaPosition.x, // Still betting it's y...
       0
   );
}

Then you have a simpler thing to type each time you want to move:

if(a > 5){
  Move(GameObject, screentouch);
}else if (a  > 8){
  Move(GameObject, screentouch);
}

But overall, I'd say if your code is getting so repetitive that you're looking to store functions in variables to streamline it, you might just be approaching this the wrong way, and we might be able to find neater ways to structure your code to achieve the same goal. Including more context about your use case in your question can help us find more elegant solutions.

  • Related