2

I'm creating an AI Director and need a way to change when the AI needs to pressure the player and when they need to move away. I've got a TArray of Objects and am checking the distance from the player. I'd like to either get the largest distance or the smallest distance.

I know this doesn't work:

operator comparer = PlayerTensionLevel > BackstageThreshold ? > : <;

Both of the variables used in the one line Bool are floats. I'm hoping that the comparer can be used in a situation like:

if(DistanceSquared(objectA, objectB) comparer _currentThresholdDistance){
    _currentObject = objectA;
    _currentThresholdDistance = DistanceSquared(objectA, objectB);
}
John Kugelman
  • 349,597
  • 67
  • 533
  • 578
Paul Brown
  • 21
  • 2

2 Answers2

2

You can compute with bool! If you aren’t concerned with differing behavior for ties, you can just write

if((DistanceSquared(objectA, objectB) > _currentThresholdDistance) ==
   (PlayerTensionLevel > BackstageThreshold)) …

(Technically, the extra parentheses here are unnecessary, but it’s probably not reasonable to expect the reader to know that relational operators have higher precedence than equality operators.)

Davis Herring
  • 36,443
  • 4
  • 48
  • 76
0

As already mentioned in @SamVarshavchik's comment above,
You can use std::function and assign it to either std::less or std::greater based on PlayerTensionLevel and BackstageThreshold.

After you determine the comparator you can use it against the current values of _currentThresholdDistance and the the squared distance between the objects (here I just used dist2 to represent it).

#include <iostream>
#include <functional>

std::function<bool(float a, float b)>
     GetComp(float PlayerTensionLevel, float BackstageThreshold)
{
    if (PlayerTensionLevel > BackstageThreshold) {
        return std::less<float>{};
    }
    return std::greater<float>{};
}

int main() {
    float _currentThresholdDistance = 1;
    float dist2 = 2;

    float PlayerTensionLevel = 100;
    float BackstageThreshold;

    BackstageThreshold = 101;
    std::cout << GetComp(PlayerTensionLevel, BackstageThreshold)
                        (dist2, _currentThresholdDistance) << std::endl;

    BackstageThreshold = 99;
    std::cout << GetComp(PlayerTensionLevel, BackstageThreshold)
                        (dist2, _currentThresholdDistance) << std::endl;
}

Output:

1
0
wohlstad
  • 12,661
  • 10
  • 26
  • 39
  • To add to this, Unreal has its own `TLess` and `TGreater` templated predicates, which is advised to use when writing Unreal specific code. – goose_lake Jan 24 '23 at 11:46
  • 1
    @goose_lake my solution can be easily adapted to use `TLess` etc. if needed - just replace `std::less` etc. with it in `GetComp` . – wohlstad Jan 24 '23 at 11:48