gametechmods

Robot Arena => Modifications => Topic started by: Urjak on August 21, 2012, 05:23:05 PM

Title: Removing the reversal of direction when inverted in AI.
Post by: Urjak on August 21, 2012, 05:23:05 PM
Hello,

I have found myself needing an AI which does not change drive direction when the chassis is inverted. Does anyone know if and how such a change would be possible?


Thanks in advance for any responses.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Sage on August 21, 2012, 05:28:36 PM
I wonder... if maybe you could set invertibility to NO? Would it still try to move?
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: nicsan2009 on August 21, 2012, 05:36:57 PM
I wonder... if maybe you could set invertibility to NO? Would it still try to move?
I think it goes full on retard and just spins aimlessly.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on August 21, 2012, 05:41:44 PM

Is the robot a double wedge or something? If so, I remember Joe saying that the AI needed might be in the stock BBEANS pack somewhere...
I looked and it isn't there.

I had an idea, not sure how it would be done in the python file, but taking the code used for when a robot reverses itself in SwitchDirRam and putting it under InvertHandler might work. I think JoeBlo gave me that idea, I'll look into it...


Edit: Yeah I really have no idea what to edit and where, I'm scared of breaking something. I'll let Joe and the other greats do this stuff.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Urjak on August 21, 2012, 05:57:19 PM
The robot itself is a crawler, such that the relative orientation of the chassis is irrelevant to its movement. And yes, when invertability is set to False, then the bot does not attempt to move.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: 123savethewhales on August 21, 2012, 11:55:23 PM
I ask the same question when making those torque reaction vs, apparently you can't do it.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Urjak on August 22, 2012, 12:31:06 AM
I ask the same question when making those torque reaction vs, apparently you can't do it.


You mean its actually hard coded into the .exe?
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on August 22, 2012, 03:04:50 PM
I ask the same question when making those torque reaction vs, apparently you can't do it.


You mean its actually hard coded into the .exe?

I think it's possible, but i need someone that knows what they're doing in python to clarify.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Urjak on August 22, 2012, 03:09:18 PM
I ask the same question when making those torque reaction vs, apparently you can't do it.


You mean its actually hard coded into the .exe?

I think it's possible, but i need someone that knows what they're doing in python to clarify.

I dropped a PM to Clickbeetle to see if he knows.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on August 22, 2012, 03:10:58 PM
Well SwitchDirRam basically does that when it loses weapons, so I bet it's possible to do that when inverted.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Naryar on August 22, 2012, 03:28:38 PM
If I remember correctly, one of the stock bots had different controls for normal and inverted driving. Dunno if the game detects the inverted controls or not, but it may be worth trying.

Edit : Nope it's not coal miner.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Trovaner on August 23, 2012, 07:08:01 PM
It isn't hard-coded into the EXE so this is completely fix-able. All you need to do is override the SuperAI's "Throttle" and "Turn" methods by including your own version inside of your AI.py (don't edit the actual SuperAI's code inside of the AI/__init__.py).

Code: (OmniReversible.py) [Select]
from __future__ import generators
import plus
import AI
import Gooey
import Tactics

class OmniReversible(AI.SuperAI):
    "Omni strategy that doesn't switch directions when inverted"
    name = "OmniReversible"
   
    def __init__(self, **args):
        AI.SuperAI.__init__(self, **args)
       
        self.zone = "weapon"
        self.triggers = ["Fire"]
        self.trigger2 = ["Srimech"]
        self.reloadTime = 0
        self.reloadDelay = 3
        self.escapeDuration = int(2/self.tickInterval) #2 seconds
       
        self.spin_range = 3.0
       
        if 'range' in args:
            self.spin_range = args.get('range')
       
        if 'triggers' in args: self.triggers = args['triggers']
        if 'reload' in args: self.reloadDelay = args['reload']
        if 'escapeDuration' in args: self.escapeDuration = int(args['escapeDuration']/self.tickInterval)
       
        self.triggerIterator = iter(self.triggers)
       
        self.tactics.append(Tactics.Engage(self))

    def Activate(self, active):
        if active:
            if AI.SuperAI.debugging:
                self.debug = Gooey.Plain("watch", 0, 75, 100, 75)
                tbox = self.debug.addText("line0", 0, 0, 100, 15)
                tbox.setText("Throttle")
                tbox = self.debug.addText("line1", 0, 15, 100, 15)
                tbox.setText("Turning")
                tbox = self.debug.addText("line2", 0, 30, 100, 15)
                tbox.setText("")
                tbox = self.debug.addText("line3", 0, 45, 100, 15)
                tbox.setText("")
           
            self.RegisterSmartZone(self.zone, 1)
       
        return AI.SuperAI.Activate(self, active)

    def Tick(self):
        # fire weapon
        if self.weapons:
           
            # spin up depending on enemy's range
            enemy, range = self.GetNearestEnemy()
           
            if enemy is not None and range < self.spin_range:
                self.Input("Spin", 0, 1)
            elif self.GetInputStatus("Spin", 0) != 0:
                self.Input("Spin", 0, 0)
           
            targets = [x for x in self.sensors.itervalues() if x.contacts > 0 \
                and not plus.isDefeated(x.robot)]
           
            # slight delay between firing
            if self.reloadTime > 0: self.reloadTime -= 1
           
            if len(targets) > 0 and self.reloadTime <= 0:
                try:
                    trigger = self.triggerIterator.next()
                except StopIteration:
                    self.triggerIterator = iter(self.triggers)
                    trigger = self.triggerIterator.next()
               
                self.Input(trigger, 0, 1)
                self.reloadTime = self.reloadDelay
       
        return AI.SuperAI.Tick(self)

    def InvertHandler(self):
        # fire all weapons once per second (until we're upright!)
        while 1:
            for trigger in self.trigger2:
                self.Input(trigger, 0, 1)
           
            for i in range(0, 8):
                yield 0

    def LostComponent(self, id):
        # if we lose all our weapons, stop using the Engage tactic and switch to Shove
        if id in self.weapons: self.weapons.remove(id)
       
        if not self.weapons:
            tactic = [x for x in self.tactics if x.name == "Engage"]
            if len(tactic) > 0:
                self.tactics.remove(tactic[0])
               
                self.tactics.append(Tactics.Shove(self))
                self.tactics.append(Tactics.Charge(self))
       
        return AI.SuperAI.LostComponent(self, id)

    def Throttle(self, throttle):
        # if we're car steering and we're not moving much, throttle up
        if self.bCarSteering and self.last_turn_throttle != 0:
            speed = self.GetSpeed()
            if speed > 0 and speed < self.top_speed / 3: throttle = self.last_throttle + 10
            elif speed < 0 and speed > -self.top_speed / 3: throttle = self.last_throttle - 10
       
        throttle = min(max(throttle, -100), 100)
       
        self.set_throttle = throttle
        self.Input('Forward', 0, throttle)
        self.DebugString(0, "Throttle = " + str(int(throttle)))

    def Turn(self, turning):
        if self.bInvertible and self.IsUpsideDown(): turning = -turning
        turning = min(max(turning, -100), 100)
       
        self.set_turn_throttle = turning
        self.Input('LeftRight', 0, -turning)
        self.Input('LeftRight', 1, turning)
        self.DebugString(1, "Turning = " + str(int(turning)))

    def StuckHandler(self):
        "This generator is called when the bot is almost immobile."
        while 1:
            # back up for 2 seconds (will stop once we're not immobile)
            for i in range(0, self.escapeDuration):
                self.Throttle(-100)
                yield 0
            # go forward for 2 seconds
            for i in range(0, self.escapeDuration):
                self.Throttle(100)
                yield 0

    def DebugString(self, id, string):
        if self.debug:
            if id == 0: self.debug.get("line0").setText(string)
            elif id == 1: self.debug.get("line1").setText(string)
            elif id == 2: self.debug.get("line2").setText(string)
            elif id == 3: self.debug.get("line3").setText(string)

AI.register(OmniReversible)

Edit: Everything is fixed now. By request, I also added a binding called "escapeDuration" so that you can set how long the AI should attempt to move in any one direction when it is being counted out. The default behavior was and is to move backwards for 2 seconds then forward for 2 seconds then repeat.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Urjak on August 23, 2012, 07:53:35 PM
Trov, you are a godsend. The bot works flawlessly now! Many thanks to you.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on August 24, 2012, 12:54:07 PM
Yes! Thanks Trov!
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Trovaner on August 25, 2012, 10:21:21 AM
It appears to be working correctly now.
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on August 26, 2012, 03:56:13 PM
Trov, can you make an OmniRam variant? I need it for LDAI.


edit: It works, but when the bot is inverted it drives into the wall as if there were a nose issue...
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Trovaner on September 07, 2012, 09:22:02 PM
WHAT HAVE I DONE


(https://gametechmods.com/uploads/images/61717bigwheel.jpg)


^That battle was AI'd.  Happened the first time I tried it.


So... as you can see, I made a .py for Big Wheel.  It was actually pretty easy; you just need to delete that line in def Throttle (I was wrong about def Turning though, you need to leave that as is).


*LINK* (https://gametechmods.com/uploads/files/TRFBD.zip)


Then I just added a feature where you can make it spin continuously when the opponent is in range (so it won't stop dead still when the opponent is right under it).  Also, you can put 'SpinCycle':x in Bindings to make it spin back and forth for x/2 ticks in each direction when the opponent is in range (so in theory, it would drive back and forth over opponents and trample them, but in practice it seems to work better in just one direction).  Just make a new analog control named "Spin" to make the AI do that.


Now I hope I don't regret unleashing this scourge upon the tournament scene...  :frown:

Does Click's version work?
Title: Re: Removing the reversal of direction when inverted in AI.
Post by: Badnik96 on September 08, 2012, 06:39:51 PM
Nope, still drives into the wall.