Class ModifierChords

java.lang.Object
frc.spectrumLib.gamepads.ModifierChords

public final class ModifierChords extends Object
Buttons shared between bare bindings and modifier chords (LB + A, RT + X, ...), resolved as one answer from the buttons held. Press and release order cannot matter, and at most one of the group's triggers is true at a time, so their edge bindings cannot race.

While any modifier in the group is held, the group's buttons belong to the chords: every bare binding is off, and the first chord whose modifier and button are held (and that is enabled) is on. Otherwise the first bare binding whose button is held is on. "First" is the order the bindings were made, so make the one that should win first.

A bare binding waits settleSeconds before it counts, so a button pressed just before the modifier, or let go just after it, does not blip the bare action. Chords act at once. Going from a bare binding to a later one does not wait: that only happens by letting go of the first button with the second still held.

A bare press let go before the settle time is a tap, not a mistake, unless a modifier touched it: it plays late, settleSeconds after it was pressed, for as long as it was held. A chord that starts before it plays cancels it. A press that begins when the modifier is let go (the tail of a chord) is not a tap.

Bind the rising edges of the chord and bare triggers, and the "nothing held" action to the falling edge of any(). An onFalse on each trigger would race the next one's onTrue.

Only the face-button side is handled: the modifiers' own bindings (LT alone to intake, LT + LB to eject) are untouched.

Reads the clock and the buttons, both AdvantageKit inputs, so it replays exactly. Its triggers poll it several times a loop, so only the first call at a new timestamp advances it: the clock must be the robot clock, which is pinned per loop.

  • Field Details

    • DEFAULT_SETTLE_SECONDS

      public static final double DEFAULT_SETTLE_SECONDS
      Longer than every face-button lead in 3847's 2026 practice chords (112 chords, longest 0.079 s), and than 97% of chord releases in Spectrum's 2023-2026 logs. A longer wait delays every bare press for the few chords left.
      See Also:
  • Constructor Details

    • ModifierChords

      public ModifierChords(DoubleSupplier clockSeconds, double settleSeconds)
      Parameters:
      clockSeconds - the robot clock, pinned per loop (Timer::getTimestamp)
      settleSeconds - how long a bare button must be held, with no modifier, before it counts; 0 to act at once
  • Method Details

    • chord

      public Trigger chord(BooleanSupplier modifier, BooleanSupplier button)
      Parameters:
      modifier - a bumper, a trigger, or a combination such as bothBumpers
      button - the button pressed with it
      Returns:
      true while this chord is the group's answer
    • chord

      public Trigger chord(BooleanSupplier modifier, BooleanSupplier button, BooleanSupplier enabled)
      A chord that only acts while enabled (teleop, say). While disabled its modifier still keeps the bare bindings off.
      Parameters:
      modifier - a bumper, a trigger, or a combination such as bothBumpers
      button - the button pressed with it
      enabled - whether the chord may act
      Returns:
      true while this chord is the group's answer
    • bare

      public Trigger bare(BooleanSupplier button)
      Parameters:
      button - a button that also takes part in chords
      Returns:
      true while button is the group's answer: held, with no modifier, past the settle time, or a tap of it playing late
    • any

      public Trigger any()
      Returns:
      true while any of the group's bindings is the answer; its falling edge is "nothing held"