DavidPagels/retro-pico-switch

c-buttons cancel each other

Closed this issue · 7 comments

Hi.
Don't know if this is how the NSO N64 controller also behaves on pc or not, i don't own a switch to test there, but only one c-button can be active at any given time, even if you press two c-buttons of different axes (c-down and c-left for example).
I'm using the usb version on a regular raspberry pico with an original n64 controller.

Since the project currently mimics a Switch Pro Controller, and that uses an analog stick for c button inputs, I have to translate c buttons to an analog stick output. I could've handle adjacent c-buttons, but what would I send if opposite buttons or 3+ c buttons are pressed?

i understand that c-buttons are working as the right analog, but X and Y axis button combinations should be able to be pressed together.
as for same axis c-buttons, there are 3 ways to handle that kind of situation:

  1. cancel out: if you press c-up and c-down, both would be ignored.
  2. second button is cancelled: if you press c-up and then c-down, c-up would register and c-down would be ignored.
  3. second button wins: if you press c-up and then c-down, c-up is ignored while c-down is pressed and only c-down is registered, when c-down is released, c-up is registered again.

i think the most accepted way is the second one, but to maintain current behavior the first option is best.

another solution would be to map c-left and c-down to Y and X respectively and leave c-up and c-right on the stick, this matches NSO mappings.
image

i managed to add the diagonals and found a solution for opposite directions by configuring c-up+down to be c-up and X and c-left+right to be c-right and Y.

first added the missing defines for the c-buttons in N64Controller.h:

#define N64_MASK_C_UP 0x8
#define N64_MASK_C_UPRIGHT 0x9
#define N64_MASK_C_RIGHT 0x1
#define N64_MASK_C_DOWNRIGHT 0x5
#define N64_MASK_C_DOWN 0x4
#define N64_MASK_C_DOWNLEFT 0x6
#define N64_MASK_C_LEFT 0x2
#define N64_MASK_C_UPLEFT 0xA
#define N64_MASK_C_UPDOWN 0xC
#define N64_MASK_C_LEFTRIGHT 0x3

then added the extra switches in N64Controller.cpp:

  switch (N64_MASK_C & _controllerState[1]) {
    case N64_MASK_C_UP:
      ry = SWITCH_JOYSTICK_MAX;
      break;
    case N64_MASK_C_DOWN:
      ry = SWITCH_JOYSTICK_MIN;
      break;
    case N64_MASK_C_LEFT:
      rx = SWITCH_JOYSTICK_MIN;
      break;
    case N64_MASK_C_RIGHT:
      rx = SWITCH_JOYSTICK_MAX;
      break;
    case N64_MASK_C_UPLEFT:
      rx = SWITCH_JOYSTICK_MIN;
      ry = SWITCH_JOYSTICK_MAX;
      break;
    case N64_MASK_C_DOWNLEFT:
      rx = SWITCH_JOYSTICK_MIN;
      ry = SWITCH_JOYSTICK_MIN;
      break;
    case N64_MASK_C_UPRIGHT:
      rx = SWITCH_JOYSTICK_MAX;
      ry = SWITCH_JOYSTICK_MAX;
      break;
    case N64_MASK_C_DOWNRIGHT:
      rx = SWITCH_JOYSTICK_MAX;
      ry = SWITCH_JOYSTICK_MIN;
      break;
    case N64_MASK_C_UPDOWN:
      ry = SWITCH_JOYSTICK_MAX;
      switchReport->buttons[0] = SWITCH_MASK_X;
      break;
    case N64_MASK_C_LEFTRIGHT:
      rx = SWITCH_JOYSTICK_MAX;
      switchReport->buttons[0] = SWITCH_MASK_Y;
      break;

like that, you have no conflicts and additionally you get access to the X and Y buttons.
i can send you a pull request with the changes if you like.

@DavidPagels, @Sakitoshi
I'm having issues with the C-Buttons and this fix isn't included in the latest release. Would it be possible to provide a compiled build with this fix in it? Thanks in advance!

@BSeraph i have it compiled on my repo https://github.com/Sakitoshi/retro-pico-switch/releases
i have been experimenting adding mario 64 all-stars compatibility and an analog stick curve better suited for gamecube style analog replacements. those hopefully will come soon™.

Thank you so much! I'm testing this on MiSTer FPGA, for N64 Controllers. The C-buttons are unuseable on it on the standard Right Stick mode, (for some reason they don't register at all) but they work perfectly via the Button Mode. Is there a way to make the Button mode the default mode, or does it have to reset everytime on boot?

i don't know how to make it persistent yet, but the default mode can be easily changed by modifying https://github.com/Sakitoshi/retro-pico-switch/blob/70d720f1ee5af70bfdc9371a5e0e856761d2b68c/include/N64Controller.h#L25 to 1 and compiling.