Fractal Softworks Forum

Please login or register.

Login with username, password and session length

Author Topic: ShieldAPI isWithinArc()  (Read 3086 times)

xenoargh

  • Admiral
  • *****
  • Posts: 5078
  • naively breaking things!
    • View Profile
ShieldAPI isWithinArc()
« on: April 28, 2016, 06:14:52 PM »

It's currently returning true only when the point is within about half of the true arc, with Beam impacts.  Hits out to the edges return false.

This is probably causing a bunch of weird issues in the main game, too, if it's being used there.
Logged
Please check out my SS projects :)
Xeno's Mod Pack

Alex

  • Administrator
  • Admiral
  • *****
  • Posts: 24143
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #1 on: April 28, 2016, 06:28:03 PM »

Hmm - It's used everywhere, so I kind of doubt it could be that broken.

To clarify what it does: it checks whether the vector from the shield's center to the parameter passed in to this method is within the current shield arc. If the shield is off, it returns false.
Logged

xenoargh

  • Admiral
  • *****
  • Posts: 5078
  • naively breaking things!
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #2 on: April 28, 2016, 09:15:14 PM »

It only gets half the arc, when tested here with a BeamAPI's .getTo().  But there are some other wrinkles I found when I was testing all of this out.

I'm also having some real problems with didDamageThisFrame() with WeaponAPIs that are isBurstBeam, which is returning true even when the Beam is not, actually, in contact with the shield that frame.

This code, on the other hand, is pretty much good:
Code: java
    public static boolean isWithinShieldArc(ShipAPI ship, Vector2f point)
    {
Vector2f shipLoc = ship.getLocation();
float shieldRange = ship.getShield().getRadius() + 45f;
if(MathUtils.getDistanceSquared(shipLoc, point) > shieldRange * shieldRange) return false;

float shieldAngle = ship.getShield().getFacing();
float shieldArc = ship.getShield().getArc() / 2f;

        // Check if weapon is aimed at any part of the target
        Vector2f endArcLeft = MathUtils.getPointOnCircumference(shipLoc, shieldRange, shieldAngle - shieldArc);
        Vector2f endArcRight = MathUtils.getPointOnCircumference(shipLoc, shieldRange, shieldAngle + shieldArc);
        float radSquared = shieldRange * shieldRange;

        boolean partiallyInArc = (Line2D
                .ptSegDistSq(
                        shipLoc.x,
                        shipLoc.y,
                        endArcLeft.x,
                        endArcLeft.y,
                        point.x,
                        point.y) <= radSquared)
                || (Line2D
                .ptSegDistSq(
                        shipLoc.x,
                        shipLoc.y,
                        endArcRight.x,
                        endArcRight.y,
                        point.x,
                        point.y) <= radSquared);
        return partiallyInArc;
    }

Note the fudge-factor 45f in the distance check; it's necessary for isBurstBeam weapons, as they don't appear to be following the rest of the rules; the actual getTo() Vector2f is not actually in contact with the Shield, but can be some distance away, yet it's doing damage that frame.  I'm guessing that has to do with burst-beams needing a little help under the hood to deal with their beam-speeds, etc., but it produced some unexpected behaviors here.
Logged
Please check out my SS projects :)
Xeno's Mod Pack

Alex

  • Administrator
  • Admiral
  • *****
  • Posts: 24143
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #3 on: April 28, 2016, 09:29:28 PM »

Hmm - this probably has more to do with beam.getTo() returning bad results. It's possible it's returning a point pre-that-frame's collision check, i.e. one that hasn't been shortened to hit the shield yet, but could be beyond it (and thus possibly outside the arc). Would cause bigger problems with faster beams, which might also explain what you're seeing with burst beams, since those tend to be faster.
Logged

xenoargh

  • Admiral
  • *****
  • Posts: 5078
  • naively breaking things!
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #4 on: April 28, 2016, 09:39:53 PM »

That makes sense.  I've also found another case like that, where a Burst Beam with a high beam speed actually can penetrate a shield. 

Got it largely fixed, now that I know what I'm looking for; covering all edge cases (like, really fast Beams like the Guardian) might be a bit tricky, though; I guess I can offset the target's center point by the beam's speed, but that sounds like a kludge that will break if getTo() gives good results later.
Logged
Please check out my SS projects :)
Xeno's Mod Pack

Alex

  • Administrator
  • Admiral
  • *****
  • Posts: 24143
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #5 on: April 28, 2016, 09:44:40 PM »

Yeah, sorry about the mess :) One of those things where it's tricky to get the ordering right (i.e. moving where the script effect is called to be after getTo() is set might break something else) so touching it would require, well... actually looking at it quite a bit.
Logged

xenoargh

  • Admiral
  • *****
  • Posts: 5078
  • naively breaking things!
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #6 on: April 29, 2016, 08:26:29 AM »

Hey, no probs; this is one of those funny things where it's literally just the one weird edge case, y'know?
Logged
Please check out my SS projects :)
Xeno's Mod Pack

Alex

  • Administrator
  • Admiral
  • *****
  • Posts: 24143
    • View Profile
Re: ShieldAPI isWithinArc()
« Reply #7 on: April 29, 2016, 09:46:35 AM »

Games are built one weird edge case at a time, I say!
Logged