libretro / mame2003-plus-libretro

Updated 2018 version of MAME (0.78) for libretro. with added game support plus many fixes and improvements
Other
189 stars 109 forks source link

input mapping discussion: phase 3 (three retropad modes!) #157

Closed markwkidd closed 6 years ago

markwkidd commented 6 years ago

I predict that the input mapping system is going to eventually be one of the big selling points of mame2003-plus. Things are going good.

After 76 messages and counting in the phase two discussion I'm starting a new issue now that we have a new input 'baseline' commited to the master branch.

Maybe some further tweaks are needed. Shall we talk about it?

One thought I had was to refactor the two new input options to be something like:

retropad_input: mame|modern|snes|disabled keyboard_input: disabled|enabled

I think that achieves the same functionality as retropad|mame_keyboard|simultaneous plus mame|modern|snes but does it in a more intuitive way.

Not for Phase 4: The libretro lightgun API is not actually mapped to the mame2003 lightgun interface -- lightgun functionality now is hackishly routed only through the MAME mouse interface. It apparently has consequences for people whose lightguns are emulating mice (like mine).

Addressing that might be Phase 6 or 7 at the earliest though. wertz is the one that knows most about it, and I'm really hoping they will contribute a PR. Talks are underway.

dankcushions commented 6 years ago

great! some inputty things that I can think of:

  1. lose the 'right stick to buttons' option for robotron (etc), and instead map those buttons do the retropad right analog stick via the API properly.
  2. draw up some nice diagrams of the control layouts for the wiki
  3. have a look into the analog mappings for things like super hang, outrun, etc. maybe map to right stick? I don't think libretro understands analog triggers yet (?).
  4. when I was looking around, it seems like we only support 4 players: https://github.com/libretro/mame2003-plus-libretro/blob/master/src/mame2003/mame2003.c#L1040 - but there's one game that supports more than 4 - 'Sprint 8' - https://github.com/libretro/mame2003-plus-libretro/blob/0a03a0d3016745c38128e2223a3b45a6124c5157/src/drivers/sprint8.c#L299 - but we might eventually backport other >4 player games, like xmen 6 player (currently at 'not working' state).
markwkidd commented 6 years ago

Those all look right to me.

The first one looked simplest so I did take a quick crack at a PR to remove the rstick-to-buttons option: https://github.com/libretro/mame2003-plus-libretro/pull/158

markwkidd commented 6 years ago

have a look into the analog mappings for things like super hang, outrun, etc. maybe map to right stick? I don't think libretro understands analog triggers yet (?).

I would like to see this question raised in the #programming discord channel. @dankcushions are you willing to, or would you prefer that I ask it? I've only looked at all of these new mapping options on paper so far, but there is at now more analog remapping support -- and joypad to keyboard support -- than in times past -- I don't know if that encompasses triggers as well.

If there still isn't trigger support, then there might also be some use for what we currently call simultaneous mode, because if a keyboard key can be mapped to the analog trigger, my understanding is that a retropad button can now be assigned to a virtual key for the RetroArch keyboard mapper. What I'm halfheartedly trying to describe is hacky as heck though - probably better at that point to just map to right stick.

dankcushions commented 6 years ago

you can ask about the triggers! we have analog stick support in mame2003 already for the left stick, so we should be able to do the same for the other axis and the right stick.

markwkidd commented 6 years ago

radius - Hidden Asbestos added the support for analog triggers radius - afaik it's just available in all buttons if the input driver supports it

I'll update if Hidden Asbestos has anything else to add

Edit: Here is the code evidently https://github.com/libretro/RetroArch/blob/master/libretro-common/include/libretro.h#L206

Edit: Here is an example implementation https://github.com/libretro/beetle-saturn-libretro/blob/a0a6dad8632ce5ff4049f8cd7b0e0d7b4c73f83c/input.cpp#L313

basically queries the input as analog first if the return val is zero then it queries as digital

example of get_analog_trigger : https://github.com/libretro/beetle-saturn-libretro/blob/a0a6dad8632ce5ff4049f8cd7b0e0d7b4c73f83c/input.cpp#L577

radius offered some 'shoddy' pseudocode: input_state_cb( player_index, RETRO_DEVICE_ANALOG, RETRO_DEVICE_INDEX_ANALOG_BUTTON, RETRO_DEVICE_ID_JOYPAD_L2 ) != 0 ? input_state_cb( player_index, RETRO_DEVICE_ANALOG, RETRO_DEVICE_INDEX_ANALOG_BUTTON, RETRO_DEVICE_ID_JOYPAD_L2 ) : input_state_cb( player_index, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L2 )

ghost commented 6 years ago

So idk if we should consider this a bug or a feature, but if a user has a core / game remap file, then that throws off all the changes attempted by the new RetroPad Layout setting. The best way I can describe is it seems that the changes are relative to the user's existing defaults instead of overriding them as an absolute.

I'm also not sure how I feel about the changes requiring a restart either instead of being instant. Part of me feels like this setting should just override RA's control settings for the game / core, and if you want custom controls, then it should probably require the user to set RetroPad Layout to maybe something like custom in addition to the options already outlined in the first post of this thread.

On the other side of the same coin, part of me can't help but feel like this feature is redundant / unnecessary because changing inputs isn't that difficult to begin with thanks to how RetroArch works, and even more so thanks to fr500's / Radius' work on the remapper overhaul. I'd instead prefer to see inputs that are exclusive to the MAME menu be added to the core remapper as a whole, but perhaps I should be tagging @fr500 for that one.

markwkidd commented 6 years ago

@SapphireTactician is there any way you could describe this in narrative terms to make sure folks know how to recreate the issue?

eg.. 1) Load metalslug, 2) use snes retropad layout, 3) change the layout, etc?

Others who know more about MAME controls may have an easier time following this but I'm trying to understand it with less background.

andres-asm commented 6 years ago

better pseudocode:

for (int player = 0; player < ARBITRARY_MAXIMUM_PLAYERS; player++)
{
   for (int button = 0; button <= RETRO_DEVICE_ID_JOYPAD_R3; button++)
   {
      int value = input_state_cb(player, RETRO_DEVICE_ANALOG, RETRO_DEVICE_INDEX_ANALOG_BUTTON, button) 
      if (value != 0)
      {
            do-stuff-with-analog-value
      }
      else if (input_state_cb(player, RETRO_DEVICE_JOYPAD, 0, button)
      {
            do-stuff
      }
   }
}
markwkidd commented 6 years ago

I wish everyone could be in discord right now because there has gotten to be a pretty extensive chat going with @fr500 who has done a lot of work with retroarch's input system over the years.

I'm minimally cleaning up the transcript to keep here for my future reference:

radius - Today at 9:48 PM so have two devices then arcade and gamepad that's all don't overdo it don't use core options for this it's terrible if you want more than one retropad layout just add one device subclass

so you know there are two different gamepads in libretro right? RETRO_DEVICE_JOYPAD and RETRO_DEVICE_ANALOG radius - Today at 9:52 PM then you should use RETRO_DEVICE_ANALOG because some other frontends actually comply with the API :stuck_out_tongue:

you can create an arbitrary amount of sub-gamepads like this #define RETRO_DEVICE_EXAMPLE RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_JOYPAD, 0) then when you set the ports instead of just RETRO_DEVICE_JOYPAD and RETRO_DEVICE_ANALOG you can do it like this

      { "Gamepad", RETRO_DEVICE_JOYPAD },
      { "Port Empty", RETRO_DEVICE_NONE },
      { "Gamepad 3 Button", RETRO_DEVICE_3B },
      { "Gamepad 6 Button", RETRO_DEVICE_6B },
};```

all of those are gamepads you can choce via gui
and you can change the map depending on which is selected
you can even set different devices based on the game
building the descriptors is tedious
but for a multi system emulator it's the only choice

right now you have this static map
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT,  "Joystick Left" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP,    "Joystick Up" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN,  "Joystick Down" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B,     "Button 1" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y,     "Button 2" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X,     "Button 3" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A,     "Button 4" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L,     "Button 5" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R,     "Button 6" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L2,     "Button 7" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R2,     "Button 8" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L3,     "Button 9" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R3,     "Button 10" },\
    { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT,   "Insert Coin" },\
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" },

> but you could have a file... say descriptors.h or something
> and have something like this
> pseudo again
> radius - Today at 9:57 PM

struct retro_input_descriptor capcom_fighter = { { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT, "Joystick Left" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP, "Joystick Up" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN, "Joystick Down" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B, "Weak Kick" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y, "Weak Punch" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X, "Mid Punch" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A, "Mid Kick" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L, "Strong Punch" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R, "Strong Kick" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Insert Coin" },\ { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" }, }



> then after loading the game you could do `environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, capcom_fighter);`
> or something like that
> that's just the descriptions of course, the corresponding button actions have to change too
> you have something like that already in retro_run as far as I can see
andres-asm commented 6 years ago

I edited the second code block a lot tho :P

markwkidd commented 6 years ago

(updated the second code block)

andres-asm commented 6 years ago

So here's my take on this. Don't overdo it, don't offer too much choice, let the frontend handle the heavy lifting.

That's what the frontend is for.

In my opinion you should have at most two "modes" let's call them gamepad and arcade (I would use just gamepad but I'm entertaining the choice you mentioned)

So first, let's create the devices:

#define RETRO_DEVICE_GAMEPAD_MODE RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_ANALOG, 0)
#define RETRO_DEVICE_ARCADE_MODE RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_ANALOG, 0)

So these devices will be the devices that can be plugged into the "virtual ports"

When you chose a device in the "Controls" gui it fires this function in the core:

void retro_set_controller_port_device(unsigned in_port, unsigned device)

Which you have stubbed at the moment. By choosing a device I mean this:

image

I don't know mame specific code but this function generally should work like this:

void retro_set_controller_port_device(unsigned port, unsigned device)
{
   if (port > PORTS_YOU_WANT_TO_SUPPORT)
      return;

   if (driver == DRIVER_NEOGEO && DEVICE == RETRO_DEVICE_GAMEPAD_MODE)
      cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, descriptors_neogeo_gamepad);
   if (driver == DRIVER_NEOGEO && DEVICE == RETRO_DEVICE_ARCADE_MODE)
      cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, descriptors_neogeo_arcade);    

   if (driver == DRIVER_CPS_FIGHTER && DEVICE == RETRO_DEVICE_GAMEPAD_MODE)
      cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, descriptors_cps_fighter_gamepad);    
   if (driver == DRIVER_CPS_FIGHTER && DEVICE == RETRO_DEVICE_ARCADE_MODE)
      cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, descriptors_cps_fighter_arcade);    

   /* etc etc etc */

}

This would be together with the descriptors thems-selves, if it was me I would put them in a descriptors.h file since it could become big


struct retro_input_descriptor neogeo_arcade = {
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT, "Joystick Left" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP, "Joystick Up" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN, "Joystick Down" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B, "A" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y, "B" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X, "C" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A, "D" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Insert Coin" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" },
}

struct retro_input_descriptor neogeo_gamepad = {
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT, "Joystick Left" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP, "Joystick Up" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN, "Joystick Down" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B, "A" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y, "C" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X, "B" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A, "D" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Insert Coin" },
   { INDEX, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" },
}

etc etc etc

And of course this has to be accompanied by the corresponding input logic that has this in mind, similar to the code blocks you have in place but that change depending on the driver, or game family or whatever you want to call it.

retro_run()
{
   stuff
   stuff
   stuff
   if (driver == DRIVER_NEOGEO && DEVICE == RETRO_DEVICE_GAMEPAD_MODE)
   {
      /* code to handle NEOGEO GAMEPAD*/
   }
   if (driver == DRIVER_NEOGEO && DEVICE == RETRO_DEVICE_ARCADE_MODE)
   {
      /* code to handle NEOGEO ARCADE*/
   }   
   etc etc etc

}

It's a long daunting task, but I think going this way would make the core feel like a proper libretro core, and not just MAME running inside RetroArch.

FWIW these are all just suggestions, and my take on the matter, I'm think most people aren't even aware that you can have all these features in a core working, it just takes a lot of code, but at least it's easy code.

ghost commented 6 years ago

i think we need a reset of some sort hacks like this

https://github.com/libretro/mame2003-plus-libretro/commit/8650b2e61cfc53e0078a4429ddec98f1bd366936#diff-c7698bf8bb6ee8a6035a02a296c7a9b4

https://github.com/libretro/mame2003-plus-libretro/commit/f209fb2accc9ace4c3c491f822faf7571666db8d#diff-c7698bf8bb6ee8a6035a02a296c7a9b4

are going to need to be reverted there is hacks on hacks everywhere in drivers and the input system dont be surprised when things dont work as expected

ghost commented 6 years ago

@markwkidd are we going to re-write the mame input system or use it if its going to be a re write someones going to to have to assign themselves to it. As far as i can see we just need to plug into it properly its something you might want to consider before going further. If we are going to use it i suggest we revert it back to the mame input code to the day it was added.

Please look at the original mame source in windows/input.c all we have to do is all the appropriate osd functions

for the lightgun is would suggest void osd_lightgun_read(int player,int deltax,int deltay)

andres-asm commented 6 years ago

I implemented an example now, for SF2:

Gamepad mode:

image

ghost commented 6 years ago

@fr500 is the code available for this ?

andres-asm commented 6 years ago

I'll post a diff shortly

ghost commented 6 years ago

sweet i am totally new to retroarch is still kinda building blocks for me.

ghost commented 6 years ago

@fr500 would it be anti retroarch approach to apply the retrorach input through the mame osd options (operation system dependent) instead of using the retro arch menus?

andres-asm commented 6 years ago

Well, it wouldn't play nice with netplay, it uses our API for syncing inputs. Actually that's one of the things I mentioned, the easiest route is for it to be all in mame OSD.

But a nice libretro core should use the libretro API for everything in my opinion, otherwise it's just as if it was a launcher and doesn't feel nicely integrated.

That's just my opinion though.

You guys can do whatever you feel like is better. (I think this idea is better)

andres-asm commented 6 years ago

So the code for the example:

diff --git a/src/libretro/libretro.c b/src/libretro/libretro.c
index 83ec990..1d985a6 100644
--- a/src/libretro/libretro.c
+++ b/src/libretro/libretro.c
@@ -35,6 +35,12 @@ retro_environment_t environ_cb = NULL;
 unsigned long lastled = 0;
 retro_set_led_state_t led_state_cb = NULL;

+#define RETRO_DEVICE_GAMEPAD RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_ANALOG, 0)
+#define RETRO_DEVICE_ARCADE  RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_ANALOG, 1)
+
+bool sf2 = false;
+bool gamepad = false;
+
 void retro_set_video_refresh(retro_video_refresh_t cb) { video_cb = cb; }
 void retro_set_audio_sample(retro_audio_sample_t cb) { }
 void retro_set_audio_sample_batch(retro_audio_sample_batch_t cb) { audio_batch_cb = cb; }
@@ -68,6 +74,18 @@ void retro_set_environment(retro_environment_t cb)
    };
    environ_cb = cb;

+   static const struct retro_controller_description controllers[] = {
+       {"Gamepad", RETRO_DEVICE_GAMEPAD},
+       {"Arcade Stick", RETRO_DEVICE_ARCADE},
+   };
+
+   static const struct retro_controller_info ports[] = {
+       { controllers, 2 },
+       { controllers, 2 },
+       { 0 },
+   };
+
+   cb(RETRO_ENVIRONMENT_SET_CONTROLLER_INFO, (void*)ports);
    cb(RETRO_ENVIRONMENT_SET_VARIABLES, (void*)vars);
 }

@@ -103,7 +121,7 @@ static int getDriverIndex(const char* aPath)
     memset(driverName, 0, sizeof(driverName));
     strncpy(driverName, last ? last + 1 : path, sizeof(driverName) - 1);
     free(path);
-    
+
     // Remove extension    
     firstDot = strchr(driverName, '.');

@@ -120,7 +138,7 @@ static int getDriverIndex(const char* aPath)
           return i;
        }
     }
-    
+
     return -1;
 }

@@ -509,7 +527,8 @@ bool retro_load_game(const struct retro_game_info *game)

     // Find game index
     driverIndex = getDriverIndex(game->path);
-    
+
+
     if(driverIndex)
     {
         int orientation;
@@ -584,7 +603,13 @@ bool retro_load_game(const struct retro_game_info *game)
         options.use_samples = samples;
         options.cheat = cheats;

-        environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, desc);
+        if (strstr(game->path, "sf2.zip"))
+        {
+            sf2 = true;
+        }
+
+        if (!sf2)
+           environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, desc);

         // Boot the emulator
         return run_game(driverIndex) == 0;
@@ -695,4 +720,60 @@ size_t retro_get_memory_size(unsigned type) {return 0;}
 bool retro_load_game_special(unsigned game_type, const struct retro_game_info *info, size_t num_info){return false;}
 void retro_cheat_reset(void){}
 void retro_cheat_set(unsigned unused, bool unused1, const char* unused2){}
-void retro_set_controller_port_device(unsigned in_port, unsigned device){}
+
+    static struct retro_input_descriptor cps_6button_arcade[] = {
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT, "Joystick Left" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP, "Joystick Up" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN, "Joystick Down" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B, "Weak Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y, "Weak Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X, "Medium Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A, "Medium Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R, "Strong Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R2, "Strong Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Coin" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" },
+        { 0 }
+    };
+
+    static struct retro_input_descriptor cps_6button_gamepad[] = {
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT, "Joystick Left" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT, "Joystick Right" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP, "Joystick Up" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN, "Joystick Down" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B, "Weak Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y, "Weak Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X, "Medium Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A, "Medium Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L, "Strong Punch" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R, "Strong Kick" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Coin" },
+        { 0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" },
+        { 0 }
+    };
+
+    static struct retro_input_descriptor empty[] = {
+        { 0 }
+    };
+
+void retro_set_controller_port_device(unsigned in_port, unsigned device)
+{
+   environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, empty);
+   if (sf2 && in_port == 0)
+   {
+       if (device == RETRO_DEVICE_GAMEPAD)
+       {
+          environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, cps_6button_gamepad);
+       }
+       else if (device == RETRO_DEVICE_ARCADE)
+       {
+          environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, cps_6button_arcade);
+       } 
+       else
+          environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, empty);
+   }
+   else
+       environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, empty);
+
+}

It only checks for sf2 (quick hack) and only sets the descriptions, it's not actually changing the input logic, should be enough to get you guys started if you chose to go this route.

diff.txt

ghost commented 6 years ago

@fr500 really appreciate you taking the time to help us here personally i want to do the osd approach to get it working then make something more in line with full integration. Will see what the others say

andres-asm commented 6 years ago

People on discord say they prefer not using the OSD. I honestly think if we're settling for the OSD... may as well use standalone.

You lose all the RetroArch features by going that route too. (as of 1.7.2, unmapping of buttons, multiple buttons for one action, digital to analog, analog to digital, and in the future, combos, granular turbo per-button)

andres-asm commented 6 years ago

Also the OSD approach means digging into mame's internals, the libretro approach doesn't, you shouldn't have to change much to get it to work and you can have analog buttons too nowadays.

andres-asm commented 6 years ago

That's it for me tonight tho, have fun!

ghost commented 6 years ago

cheers mr fr500 I guess someones going to have to re write the mame input system to handle driver macros if we go the other route.

andres-asm commented 6 years ago

Not sure what you mean with that

ghost commented 6 years ago

mames input system basically reads joysticks available at os/keyboards at os level set buttons and controls with flags in the drivers. the osd functions in this case would hook to retroarch devices. ie digital hat or analogue ect

ghost commented 6 years ago

I think all we have to do is all the analog information to the joystickinfo will need to look into that part a lot more again thats just the logic part really

ie superhangon that was pointed out earlier

INPUT_PORTS_START( shangon ) PORT_START / Steering / PORT_ANALOG( 0xff, 0x7f, IPT_AD_STICK_X | IPF_REVERSE | IPF_CENTER , 100, 3, 0x42, 0xbd )

ifdef HANGON_DIGITAL_CONTROLS

PORT_START / Buttons / PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 )

else

PORT_START / Accel / Decel / PORT_ANALOG( 0xff, 0x1, IPT_AD_STICK_Y | IPF_CENTER | IPF_REVERSE, 100, 16, 1, 0xa2 )

endif

we haven mapped any analogue joystick stuff at all that in itself is probably why

dankcushions commented 6 years ago

@sapphiretactician

I'm also not sure how I feel about the changes requiring a restart

they don’t?

i agree with @FR500 that we should use be device subclass for our two types. i think gamepad and arcade is a bad name though - SNES and modern is more descriptive. also i’d be tempted to lose the mame legacy mode as it doesn’t seem to have a utility.

dankcushions commented 6 years ago

we haven mapped any analogue joystick stuff at all that in itself is probably why

yes we have - IPT_AD_STICK_X is hooked up, just not Y.

dankcushions commented 6 years ago

@grant2258

i think we need a reset of some sort hacks like this

8650b2e#diff-c7698bf8bb6ee8a6035a02a296c7a9b4

this one could use revisiting using the new mouse device code but i think it's useful and it doesn't really mess with any mame input code.

f209fb2#diff-c7698bf8bb6ee8a6035a02a296c7a9b4

agreed - this one should be reverted and I think following my pad changes the JOYSTICKRIGHT_LEFT (etc) stuff should be hooked up correctly anyway.

dankcushions commented 6 years ago

Ok just to pre-empt someone coding the @fr500 changes, as I want a break for now :) ...

I think they're good but I think how we should implement them is: 1) Implement my modern, SNES and 'MAME Legacy' layouts as device subclasses, so they can be selected via Retroarch. 2) Get rid of the now redundant retropad_layouts core option. 3) enjoy...

i think hooking up per game descriptors for games like sf2 could come later. keep it simple for now. this issue is already spiraling out into a bunch of different things :)

dankcushions commented 6 years ago

one thing to be mindful of - currently the MAME osd menu displays the retropad bindings. eg, it will tell you that 'Button 3' is hooked up to 'Retropad B' or whatever. with my current change, when you change the layout core option it updates the osd with the new Retropad associations, which is important until we're ready to let go of the OSD input menus.

is there a callback for when the device type changes that we can use to trigger these same updates?

ghost commented 6 years ago

is the analogue hooked up to emit directions I must be going blind the problem is when we are discussing things code is changing we should point out when changing code off our own backs. Like the tab menu changes and adding the restart option. I personally think we should be putting a pr in so we dont mess with each others code if multiple people are working on it. I do tend to agree with @dankcushions you do one or the other through mame osd or through retroatch no hybrid in betweens its too messy and spirals things to be more complicated than they need to be. Maybe spiral off an input branch so the mainline version is usable changing like this multiple times a day will put people off using it if its changing like this on a daily basis if people want to test the new input stuff all they need to do is checkout the branch

ghost commented 6 years ago

So idk if we should consider this a bug or a feature, but if a user has a core / game remap file, then that throws off all the changes attempted by the new RetroPad Layout setting. The best way I can describe is it seems that the changes are relative to the user's existing defaults instead of overriding them as an absolute.

I'm also not sure how I feel about the changes requiring a restart either instead of being instant. Part of me feels like this setting should just override RA's control settings for the game / core, and if you want custom controls, then it should probably require the user to set RetroPad Layout to maybe something like custom in addition to the options already outlined in the first post of this thread.

On the other side of the same coin, part of me can't help but feel like this feature is redundant / unnecessary because changing inputs isn't that difficult to begin with thanks to how RetroArch works, and even more so thanks to fr500's / Radius' work on the remapper overhaul. I'd instead prefer to see inputs that are exclusive to the MAME menu be added to the core remapper as a whole, but perhaps I should be tagging @fr500 for that one.

mame input has always been easy to change through mame if you want a retroarch env your going to have to talk to mark or dank about libretro rewrite.

Maybe there should be two versions mame running in libretro (which is what we have not cleanly though) and mame libretro full integration.

markwkidd commented 6 years ago

The two modes are mame_keyboard and retropad -- they don't work perfectly yet, but that's the system.

mame_keyboard is generally fine. retropad is still very much a work in progress.

ghost commented 6 years ago

i think there needs to be stability for people using this core though a input testing branch would be ideal it means users can still use the core and we can do what we need to. Then just bring it in when its done.

markwkidd commented 6 years ago

I agree, a separate branch would be better.

Could we settle on one baseline retropad profile for now, and then move our testing of other approaches to a branch?

On Sun, Apr 29, 2018 at 11:38 AM, grant2258 notifications@github.com wrote:

i think there needs to be stability for people using this core though a input testing branch would be ideal it means user can still use the core and we can do what we need to

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/libretro/mame2003-plus-libretro/issues/157#issuecomment-385260018, or mute the thread https://github.com/notifications/unsubscribe-auth/ASphdtecWOVGRm9l_CT1F831FBPMfQRVks5ttd5ZgaJpZM4TrjoK .

-- Mark W. Kidd http://facebook.com/markwkidd (606)536-0115

ghost commented 6 years ago

well id like to help with @SapphireTactician with his issue before we branch off if thats ok with you? I get the feeling his problems might be coming from the old mame cfg dir settings for the snes pad we had before

markwkidd commented 6 years ago

fine by me. I'm going to be on the road for the next three days so other than maybe simple things I really need to keep my hands off of the code

On Sun, Apr 29, 2018 at 11:43 AM, grant2258 notifications@github.com wrote:

well id like to help with @SapphireTactician https://github.com/SapphireTactician with his issue before we branch off if thats ok with you? I get the feeling his problems might be coming from the old mame cfg dir settings for the snes pad we had before

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/libretro/mame2003-plus-libretro/issues/157#issuecomment-385260357, or mute the thread https://github.com/notifications/unsubscribe-auth/ASphdh0F-gvTbcAnopx3t6rPO5Q0ZCM7ks5ttd-rgaJpZM4TrjoK .

-- Mark W. Kidd http://facebook.com/markwkidd (606)536-0115

ghost commented 6 years ago

no need to keep your hands off anything mark if we have a base line :D. I wish i had more time to be on the road. My guess is no one is going to want to pick this up anyway. Im fine with branching off right now tbh just wanna make sure @SapphireTactician doesnt remain in limbo on this issue

ghost commented 6 years ago

@markwkidd @dankcushions i think that issue was resolved how do you two feel about how things are now. If anything you feel needs change before branching off please feel free to do so then we work on a testing branch with pr style adding

ghost commented 6 years ago

Sorry about keeping you all waiting. I haven't been well lately and took a nap. @grant2258 What problem of mine are we talking about?

andres-asm commented 6 years ago

I don't know what the conclusion is, anyway I just wanted to give you some pointers. Let me know if I can be of any help

ghost commented 6 years ago

@fr500 you have been of great help thanks we will get there hopefully if not we know where to ask :D. I myself want to familiarize myself with libretro and its innner workings. Im going to go back to the very first release and start plugging in my own code to see how it all fits together before contributing to this. When i say osd i mean the functions mame calls for video updates and sound updates and input updates ect. Not actually using osd code to use these functions but call the retroarch from them routines

ghost commented 6 years ago

You know my first outlook was retroarch was a front end to launch emulators. It seems a very invasive front end if all these working contents we already have to be changed or be partially working to fit an idealism. It's like saying with mame in windows you can't have the tab menu displayed unless you goto a menu and call it there. This seems to be trickling down to every feature now it's like it's the ultimate sin it to use the menu. I'll help with general it's fixes or bugs can't say I'm a big fan of breaking things that already work.

ghost commented 6 years ago

I have nothing against the tab menu. I just want the frontend to tie into it so that anything the tab menu can modify, the front-end can as well. And each can reflect the changes of the other. There's no reason why they both can't co-exist and do the same things. @grant2258

As I've said before, all I ever wanted is the ability to map the service buttons from the front-end as well.

markwkidd commented 6 years ago

I would say that mame is a frontend and emulator package. When you add a libretro front end, which is be required in some form to execute libretro cores. That leads to 2 frontends.

If not the benefit of all possible libretro frontends, including retroarch as just one, then why not use the original xmame or another source port of mame 0.78.

On Mon, Apr 30, 2018, 12:13 PM grant2258 notifications@github.com wrote:

You know my first outlook was retroarch was a front end to launch emulators. It seems a very invasive front end if all these working contents we already have to be changed or be partially working to fit an idealism. It's like saying with mame in windows you can't have the tab menu displayed unless you goto a menu and call it there. This seems to be trickling down to every feature now it's like it's the ultimate sin it to use the menu. I'll help with general it's fixes or bugs can't say I'm a big fan of breaking things that already work.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/libretro/mame2003-plus-libretro/issues/157#issuecomment-385448259, or mute the thread https://github.com/notifications/unsubscribe-auth/ASphdtrzqZOu7q3oeQnFDwiQKxc9F3Tdks5ttzhFgaJpZM4TrjoK .

ghost commented 6 years ago

I am beginning to think a standalone for mame2003 would be a good idea as well. Again it's just a person al thought mame is designed in such a way that's not a good fit for idealism but to work on many systems . I thought haze was harsh on his comments about retroarch in regards to mame but I can somewhat agree with what he says I don't agree with all of it though. Personally I would go for a sdl port for mame2003-plus have the best of both worlds