Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mouse bug... #454

Open
seleuco opened this issue Feb 11, 2024 · 9 comments
Open

Mouse bug... #454

seleuco opened this issue Feb 11, 2024 · 9 comments

Comments

@seleuco
Copy link

seleuco commented Feb 11, 2024

@ToddLa

Hi todd.

I have been updating the Android MAME port so that it works with the latest pc desktop version version

https://github.com/seleuco/MAME4droid-2024/tree/main

I started the development using your OSD modifications (libmame 250)since you have done a magnificent job and it has sense to start with.

When I implemented the mouse support I went crazy because you have a bug that makes the mouse seem to work but it is not really working it well.

Specifically, when mame invokes void ios_osd_interface::input_update(bool relative_reset) the relative_reset parameter indicates that this is when the relative data (the mouse) must be polled, therefore it must be passed to do the effective polling:

m_callbacks.input_poll(relative_reset,&g_input, sizeof(g_input));

....

   if(relative_reset) {
        for (int i = 0; i < MYOSD_NUM_MICE; i++) {
            input->mouse_status[i] = mouse_status[i];

            input->mouse_x[i] = mouse_x[i] * 512;
            input->mouse_y[i] = mouse_y[i] * 512;

            pthread_mutex_lock(&mouse_mutex);

            mouse_x[i] = 0;
            mouse_y[i] = 0;

            pthread_mutex_unlock(&mouse_mutex);
        }
    }

I hope this helps if you still maintain the iOS port, which is great :)

@ToddLa
Copy link
Collaborator

ToddLa commented Feb 21, 2024

Thanks! I did not fully understand how MAME handles relative devices, I will update next time we do a release.

@ToddLa
Copy link
Collaborator

ToddLa commented Feb 21, 2024

My MAME OSD, assumes the client will do all the rendering (on iOS we use Metal)

Did you do that on Android, or did you put back the option to render to a bitmap?

@seleuco
Copy link
Author

seleuco commented Feb 21, 2024

Yeah. I know you do all the rendering on the client. At the moment I make a bitmap although later in the client I apply shaders and I support a lot of glsl shaders. In any case this approach has clear disadvantages with artwork of course.

I want to try to get bgfx running at some point, which would be better than reinventing the wheel but so far renderer has been fast developed and works fast and well.

I also wanted to respect MAME UI unlike you on iOS because on Android there are already great third-party frontends with which I integrate. I have tried to enhance the MAME UI with media scraping and including resources such as history data and mame info which authors has given permission to me. Also I made it touch enabled, so by default you have an experience very similar to the PC experience, which I like.

Ahhh. One important thing mame Devs have fixed discrete sound bug in a recent commit. Al least works fine on my arm64 build without numprocessors setted to one. That is important because improves performance in threaded rendering like the one on namco system 22 which run full speed on my device.

It is curious but my port has not any issue with sound. I have seen you have been struggling with sound issues on iOS devices. In fact, I'm running in a low latency path mode so buffering is setted to 2/3 frames and there is not any underun.

@ToddLa
Copy link
Collaborator

ToddLa commented Feb 21, 2024

YES audio bug fixed! I have bang'd my head trying to work around that. Setting num-cpu to one killed me!

Thanks

@ToddLa
Copy link
Collaborator

ToddLa commented Feb 21, 2024

Yea hires artwork looks great when you handle the render, and vector games can draw nice hires lines

@ToddLa
Copy link
Collaborator

ToddLa commented Apr 22, 2024

FYI I did an update to my MAME fork to MAME 264....

I am looking at the mouse issue now, and have a question...

Wouldn't relative-reset make more sense like this....

for (int i = 0; i < MYOSD_NUM_MICE; i++) {
  input->mouse_status[i] = mouse_status[i];

  input->mouse_x[i] = mouse_x[i] * 512;
  input->mouse_y[i] = mouse_y[i] * 512;

  if(relative_reset) { 
    pthread_mutex_lock(&mouse_mutex);
    mouse_x[i] = 0;
    mouse_y[i] = 0;
    pthread_mutex_unlock(&mouse_mutex);
  }
}

@ToddLa
Copy link
Collaborator

ToddLa commented Apr 22, 2024

I have never gotten the MAME "DOS" UX to use the mouse, maybe this change will fix it!!

Also the relative-reset flag was added relatively recently, thanks for letting me know about it!

@seleuco
Copy link
Author

seleuco commented Apr 23, 2024

FYI I did an update to my MAME fork to MAME 264....

I am looking at the mouse issue now, and have a question...

Wouldn't relative-reset make more sense like this....

for (int i = 0; i < MYOSD_NUM_MICE; i++) {
  input->mouse_status[i] = mouse_status[i];

  input->mouse_x[i] = mouse_x[i] * 512;
  input->mouse_y[i] = mouse_y[i] * 512;

  if(relative_reset) { 
    pthread_mutex_lock(&mouse_mutex);
    mouse_x[i] = 0;
    mouse_y[i] = 0;
    pthread_mutex_unlock(&mouse_mutex);
  }
}

Empirically, it is working correctly for me.

If you look at https://github.com/mamedev/mame/blob/master/src/osd/modules/input/input_rawinput.cpp

at the poll interval, if the relative_reset is set, then they exchange the mouse data an set it to zero the member one

`

  virtual void poll(bool relative_reset) override
{
	rawinput_device::poll(relative_reset);
	if (relative_reset)
	{
		m_mouse.lX = std::exchange(m_x, 0);
		m_mouse.lY = std::exchange(m_y, 0);
		m_mouse.lV = std::exchange(m_v, 0);
		m_mouse.lH = std::exchange(m_h, 0);
	}
}

`

@seleuco
Copy link
Author

seleuco commented Apr 23, 2024

I have never gotten the MAME "DOS" UX to use the mouse, maybe this change will fix it!!

Also the relative-reset flag was added relatively recently, thanks for letting me know about it!

Making the mouse to work correctly is more important than it seems because there are artworks that are clickable.. :)

For the mouse to work in the UI and in the artwork, mouse events must be injected directly. It doesn't work like it does with games.

look at here:

https://github.com/seleuco/MAME4droid-2024/blob/main/src/osd/myosd/myosdmain.cpp

`
extern "C" void myosd_pushEvent(myosd_inputevent event)
{
if(osdInterface!= nullptr && osdInterface->isMachine() && osdInterface->target()!= nullptr) {

    switch(event.type) {
        case event.MYOSD_KEY_EVENT:
            osdInterface->machine().ui_input().push_char_event(osdInterface->target(), event.data.key_char);
            break;
        case event.MYOSD_MOUSE_MOVE_EVENT:
            osdInterface->machine().ui_input().push_mouse_move_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        case event.MYOSD_MOUSE_BT1_DBLCLK:
            osdInterface->machine().ui_input().push_mouse_double_click_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        case event.MYOSD_MOUSE_BT1_DOWN:
            osdInterface->machine().ui_input().push_mouse_down_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        case event.MYOSD_MOUSE_BT1_UP:
            osdInterface->machine().ui_input().push_mouse_up_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        case event.MYOSD_MOUSE_BT2_DOWN:
            osdInterface->machine().ui_input().push_mouse_rdown_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        case event.MYOSD_MOUSE_BT2_UP:
            osdInterface->machine().ui_input().push_mouse_rup_event(osdInterface->target(), event.data.mouse_data.x, event.data.mouse_data.y);
            break;
        default:
            osd_printf_error("has unknown myosd event type (%u)\n",event.type);
    }

}

}
`

and here:

https://github.com/seleuco/MAME4droid-2024/blob/main/src/osd/myosd/myosd-droid.cpp

`
int myosd_droid_setMouseData(int i, int mouseAction, int button, float cx, float cy) {

if(mouseAction == com_seleuco_mame4droid_Emulator_MOUSE_MOVE)
{
    cur_x_mouse = MAX(0, MIN(cx + cur_x_mouse, myosd_droid_video_width));
    cur_y_mouse = MAX(0, MIN(cy + cur_y_mouse, myosd_droid_video_height));

    myosd_inputevent ev;
    ev.type = ev.MYOSD_MOUSE_MOVE_EVENT;
    ev.data.mouse_data.x = cur_x_mouse;
    ev.data.mouse_data.y = cur_y_mouse;
    myosd_pushEvent(ev);

    if(!myosd_droid_inMenu) {
        pthread_mutex_lock(&mouse_mutex);

        mouse_x[i] += cx;
        mouse_y[i] += cy;

        pthread_mutex_unlock(&mouse_mutex);
   }
}
else if(mouseAction == com_seleuco_mame4droid_Emulator_MOUSE_MOVE_POINTER)
{
    cur_x_mouse = cx;
    cur_y_mouse = cy;

    myosd_inputevent ev;
    ev.type = ev.MYOSD_MOUSE_MOVE_EVENT;
    ev.data.mouse_data.x = cur_x_mouse;
    ev.data.mouse_data.y = cur_y_mouse;
    myosd_pushEvent(ev);
}
else if(mouseAction == com_seleuco_mame4droid_Emulator_MOUSE_BTN_DOWN)
{
    myosd_inputevent ev;
    ev.data.mouse_data.x = cur_x_mouse;
    ev.data.mouse_data.y = cur_y_mouse;

    if(button==1) {

        ev.type = ev.MYOSD_MOUSE_BT1_DOWN;
        myosd_pushEvent(ev);

        static float last_click_x = 0;
        static float last_click_y = 0;
        static std::chrono::steady_clock::time_point last_click_time = std::chrono::steady_clock::time_point::min();

        auto double_click_speed = std::chrono::milliseconds(250);
        auto const click = std::chrono::steady_clock::now();

        int offsetX = 4;
        int offsetY = 4;
        if(cx != -1 && cy != -1) {
            offsetX = cx;
            offsetY = cy;
            double_click_speed = std::chrono::milliseconds(400);
        }

        if (click < (last_click_time + double_click_speed)
            && (cur_x_mouse >= (last_click_x - offsetX) && cur_x_mouse <= (last_click_x + offsetX))
            && (cur_y_mouse >= (last_click_y - offsetY) && cur_y_mouse <= (last_click_y + offsetY)))
        {
            last_click_time = std::chrono::time_point<std::chrono::steady_clock>::min();
            ev.type = ev.MYOSD_MOUSE_BT1_DBLCLK;
            myosd_pushEvent(ev);
            __android_log_print(ANDROID_LOG_DEBUG, "libMAME4droid.so", "MOUSEB PULSO BT1 DBLCLK!!!!");
        }
        else
        {
            last_click_time = click;
            last_click_x = cur_x_mouse;
            last_click_y = cur_y_mouse;
        }

        mouse_status[i] |= MYOSD_A;
        __android_log_print(ANDROID_LOG_DEBUG, "libMAME4droid.so", "MOUSEB PULSO BT1!");
    }
    else if(button == 2)
    {
        ev.type = ev.MYOSD_MOUSE_BT2_DOWN;
        myosd_pushEvent(ev);
        mouse_status[i] |= MYOSD_B;
    }
    else if(button == 3)
    {
        mouse_status[i] |= MYOSD_C;
    }
}
else if(mouseAction == com_seleuco_mame4droid_Emulator_MOUSE_BTN_UP)
{
    myosd_inputevent ev;
    ev.data.mouse_data.x = cur_x_mouse;
    ev.data.mouse_data.y = cur_y_mouse;

    if(button==1)
    {
        ev.type = ev.MYOSD_MOUSE_BT1_UP;
        myosd_pushEvent(ev);
        mouse_status[i] &= ~MYOSD_A;
    }
    else if(button==2)
    {
        ev.type = ev.MYOSD_MOUSE_BT2_UP;
        myosd_pushEvent(ev);
        mouse_status[i] &= ~MYOSD_B;
    }
    else if(button==3)
    {
        mouse_status[i] &= ~MYOSD_C;
    }
}

return 1;

}
`

Also keyboard has to be inyected ....

Anyway i think that @cuavas has changed a lot of this in a recent commit because it has added some type of touch support. I will dig on it when they launch 0.265

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants