JackBoosY
In src/video/winrt/SDL_winrtgamebar.cpp line 55:
virtual HRESULT STDMETHODCALLTYPE add_VisibilityChanged(
__FIEventHandler_1_IInspectable *handler,
Windows::Foundation::EventRegistrationToken *token) = 0;
The macro __FIEventHandler_1_IInspectable defined in windows.fondation.h(Windows10 SDK 10.0.17763.0) line 3576:
#define __FIVector_1_Windows__CFoundation__CPoint ABI::Windows::Foundation::Collections::__FIVector_1_Windows__CFoundation__CPoint_t
but no longer exists in Windows 10 SDK 10.0.19041.0.
After searching this macro in the sdk include path, I found that it was defined in many header files. But it should be replaced in windows.system.h .
On some systems, GetClipCursor() impacts performance when called frequently, so only call it every once in a while to make sure we haven't lost our capture.
Manuel Alfayate Corchete
I'm trying to build SDL2 with threads support here in GNU/Linux, both X86 and ARM, and it does not seem to be possible ATM:
/home/manuel/src/SDLLLL/src/core/linux/SDL_threadprio.c:233:26: error: 'rtkit_max_realtime_priority' undeclared (first use in this function)
Manuel Alfayate Corchete
This patch is needed so programs that do this work as expected:
1) Start in a different video mode than the mode used by the system and then...
2) Try to go fullscreen with the mode originally used by the system via SetWindowFullScreen() with the SDL_WINDOW_FULLSCREEN_DESKTOP flag.
An example would be pt2-clone in https://github.com/8bitbubsy/pt2-clone.
This program does this:
Starts with:
video.window = SDL_CreateWindow("", SDL_WINDOWPOS_CENTERED,
SDL_WINDOWPOS_CENTERED, screenW, screenH, windowFlags);
and then, *IF* the user has configured it in fullscreen mode in its .ini, it tries to go fullscreen with the desktop mode:
SDL_SetWindowFullscreen(video.window, SDL_WINDOW_FULLSCREEN_DESKTOP);
This sequence of operations is currently failing because SDL_SetDisplayModeForDisplay() in SDL_video.c fails because display->desktop_mode is not being initialized with its correct value: SetDisplayMode() in SDL_kmsdrmvideo.c will not be able to set the mode because it detects the mode to have a driverdata of 0x0 ("if (!modedata)") and rightfully returns an error.
So, the included patch fixes this small problem, and programs that first change the video mode and then try to go fullscreen with the system video mode will now work.
The patch simply fixes an small omission, but its really needed now that dynamic video mode changing was implemented on the KMSDRM backend.
Ryan C. Gordon
As discussed here:
https://discourse.libsdl.org/t/question-about-implementation-of-sdl-updatewindowsurfacerects/27561
"As you can see this function [WIN_UpdateWindowFramebuffer, in src/video/windows/SDL_windowsframebuffer.c] calls BitBlt on entire screen, even though it accepts the rects. Rects variable is not even used in this function at all. Now my question is why is that the case?"
Anthony Pesch
I was looking into my own input bug and noticed an issue in the HIDAPI code while looking over it. I don't have a controller that goes down this path to test and try to provoke the issue, but it looks pretty straight forward.
The memmove to shift the joystick id array on disconnect isn't scaling the size by sizeof(SDL_JoystickID), likely corrupting the ids on disconnect.
It currently behaves like a locking key which is pressed
when Caps Lock is enabled and released when disabled. This
means that apps that trigger events on Caps Lock key down will
only fire these events every other time Caps Lock is pressed.
Lacky
It looks like refactoring of SDL2 internal API has broken SDL_RenderFillRect for DirectFB. In new version function SDL_RenderFillRect returns 0, but rectangle is not visible.
Replacing "count" with "len" in the argument list for SDL_memcpy in DirectFB_QueueFillRects fixes problem.
Jan Bujak
I wrote a new driver for my gamepad on Linux. I'd like SDL to support it out-of-box, as currently it just treats it as a generic joystick instead of a gamepad. From what I can see the only way to do that is to either 1) pick one of the already supported controllers' PID, VID and button layouts and have my driver send that (effectively lying that it's something else), or 2) submit a preconfigured, hardcoded mapping to SDL.
Both of those, in my opinion, are silly when we already have the Linux Gamepad Specification which standarizes this:
https://www.kernel.org/doc/html/v4.15/input/gamepad.html
Unfortunately SDL doesn't make use of it currently. So I've took it upon myself to add it; patch is in the attachments.
Basically what the patch does is that if SDL finds no built-it controller mappings for a given joystick it then asks the joystick backend to autodetect it, and that uses the relevant evdev bits to figure out which button/axis is which. (See the specs for more details.)
With this patch applied my own driver for my controller works out-of-box with SDL with no extra configuration and is correctly recognized as a gamepad; this is also going to be the case for any other driver which follows the Linux Gamepad Specification.
Arithmatic operations promote Uint8 to signed int. If the top bit of a
Uint8 is set, and it is left shifted 24 places, then the result is not
representable in a signed 32 bit int. This would be undefined behaviour
on systems where int is 32 bits.
It makes it clearer who owns the memory, and more reasonable to free it on
failure in the creating function.
(and, of course, pacifies static analysis.)
Manuel Alfayate Corchete
On the KMSDRM backend, there is no such thing as a desktop, yet some programs could (and DO) use SDL_GetGlobalMouseState().
So I think its good idea that, in KMSDRM, it returns the same mouse coordinates anyway as SDL_GetMouseState() would return. There is nothing else it could return, as far as I can understand, since there is no desktop anyway.
This small patch does precisely that.
Manuel Alfayate Corchete
The KMSDRM backend was doing things wrong because of some small (but important) misconceptions on how KMS/DRM works: to implement a largely broken non-vsync refresh mechanism, the SwapWindow() function was issuing new pageflips before previous ones had completed, thus causing EBUSY returns, buffer mismanagement, etc... resulting in general breakage on vsync disabling from apps, that would not allow vsync to work again without KMSDRM video re-initialization.
To further clarify, on most DRM drivers async pageflips are NOT working nowadays, so all issued pageflips will complete on next VBLANK, NOT ASAP (calling drmModePageFlip() with the DRM_MODE_PAGE_FLIP_ASYNC flag will return error).
The old code was assuming that can just issue a synchronous (=on VBLANK) pageflip and then pass a 0 timeout to the pull() function so we do not wait for the pageflip event, thinking that this will lead to correct non-vsynced screen updates from the program: That is plain wrong.
Each pageflip has to be waite before issuing a new one, ALWAYS. And if we do not support ASYNC pageflips on the DRM driver level, then we are forced to wait for the next VBLANK. There is no way around it.
I have also added many comments on the KMSDRM code. This is needed for future reference for me or others who may need to look at this code: KMS/DRM terminology regarding what SYNC and ASYNC mean in pageflip terms, and where to do certain things and why, is not trivial. It is not desirable or possible to invest time on researching the same concepts every time there is need to dive into this code. So please leave all these comments in the patch.
1. Comment that SDL_SetThreadPriority will make any necessary system changes when applying priority.
2. Add a hint to override SDL's default behavior for scheduler policy.
3. Modify the pthreads SDL_SetThreadPriority so that instead of just using the current thread scheduler policy it will change it to a policy that should work best for the requested priority.
4. Add hint checks in SDL_SetThreadPriority so that #3 can be overridden if desired.
5. Modify the Linux SDL_SetThreadPriority so that in the case that policy, either by SDL defaults or from the hint, is a realtime policy it uses the realtime rtkit API.
6. Prior to calling rtkit on Linux make the necessary thread state changes that rtkit requires. Currently this is done every time as it isn't expected that SDL_SetThreadPriority will be called repeatedly for a thread.
michaeljosephmaltese
Display ends up taking only 1/4 of the screen area. It needs to call "setWantsBestResolutionOpenGLSurface:highdpi", like when creating a window the normal way.
wengxt
Due to the new major fcitx version is coming close, the existing code need to be ported to use new Fcitx dbus interface.
The new dbus interface is supported by both fcitx 4 and 5, and has a good side effect, which is that it will work with flatpak for free. Also the patch remove the dependency on fcitx header. Instead, it just hardcodes a few enum value in the code so need to handle the different header for fcitx4 or 5.
meyraud705
'SDL_Windows::driverdata' of a Wayland window is allocated by calloc in 'Wayland_CreateWindow' but freed by SDL_free in 'Wayland_DestroyWindow'.
meyraud705
I see how the documentation is confusing. I think that the choice of the axis is an implementation detail. The documentation should state the goal of this value, so I propose this wording:
"Use this value to play an effect on the steering wheel axis. This provides
better compatibility across platforms and devices as SDL will guess the
correct axis."
Value could even be renamed 'SDL_HAPTIC_STEERING_AXIS'.
For Linux, sending an effect on the X axis with a Logitech wheel works. Others brands don't have driver for Linux as far as I know.
This is only supported on PulseAudio. You can set a description when opening
your audio device that will show up in pauvcontrol, which lets you set
per-stream volume levels.
Fixes Bugzilla #4801.
dark_sylinc
Trying to build SDL with VS2019 using CMake will encounter a linking error
More specifically:
1>SDL_string.obj : error LNK2019: unresolved external symbol memset referenced in function SDL_vsnprintf_REAL
* 8BitDo N30 Pro 2
* 8BitDo SN30 Gamepad
* 8BitDo SN30 Pro+
* 8BitDo Zero 2
* SZMY-POWER PC Gamepad
* ThrustMaster eSwap PRO Controller
* ZEROPLUS P4 Wired Gamepad
In additional, all 8BitDo controllers use SDL_HINT_GAMECONTROLLER_USE_BUTTON_LABELS to have the correct mapping based on user preferences.
This patch removes deferred error string formatting: now we do it during
SDL_SetError(), so there's no limit on printf-style arguments used.
Also removes stub for managing error string translations; we don't have the
facilities to maintain that and the way we set arbitrary error strings
doesn't really make this practical anyhow.
Since the final error string is set right away and unique to the thread,
we no longer need a static buffer for legacy SDL_GetError(), and we don't
have to allocate 5x 128-byte argument fields per-thread. Also, since we now
use SDL_vsnprintf instead of parsing the format string ourselves, there's a
lot of code deleted and we have access to more robust formatting powers now.
This does mean the final error strings can't be more than 128 bytes, down
from the theoretical maximum of around 768, but I think this is probably okay.
They might truncate but they will always be null-terminated!
Fixes Bugzilla #5092.
The joystick layer can't necessarily give us perfect centering, but we know
that the game controller level has logical absolute idle positions that have
nothing to do with the physical device.
So send game controller events to make it look like the device is completely
untouched before sending the final removal event.
This driver supports the Razer Atrox Arcade Stick
Some of the quirks of this driver, inherent in Windows Gaming Input:
* There will never appear to be controllers connected at startup. You must support hot-plugging in order to see these controllers.
* You can't read the state of the guide button
* You can't get controller events in the background
meyraud705
On line 220 of SDL_hidapi_xbox360.c https://hg.libsdl.org/SDL/file/4608f0e6e8e3/src/joystick/hidapi/SDL_hidapi_xbox360.c#l220
if (!XINPUTGETSTATE(user_index, &xinput_state[user_index].state) == ERROR_SUCCESS) {
logical not is only applied to the left hand side of this comparison.
I think you mean:
if (XINPUTGETSTATE(user_index, &xinput_state[user_index].state) != ERROR_SUCCESS) {
On Raspberry Pi 3 via the VC4 driver in firmware KMS mode, none of the
found configs match the desired format, causing the function to fall through
without any config being selected.
Fix by first iterating over the found configs, and if no match exists,
don't exclude the non-matching configs. This should fix RPI3 and possibly other
targets without breaking targets that have a matching native format (such as RPI4).
This allows you to bind surfaceless contexts on a background thread to, for
example, load assets in a separate context, for platforms that have different
requirements about sharing surfaces, etc.
Martin's notes on the matter:
"Here's a patch that enables passing NULL windows to SDL_GL_MakeCurrent, if
the involved APIs allow it. Currently, this is only the case for EGL, and
even then only if some specific extensions are present (which they usually
are).
If "surfaceless" contexts are not supported, SDL_GL_MakeCurrent continues to
generate an error (albeit with a more specific error message than it used to),
so this should not break anything that wasn't broken before."
(Please see https://bugzilla.libsdl.org/show_bug.cgi?id=3695 for more
discussion.)
Fixes Bugzilla #3695.
This behavior matches SDL_RecreateWindow and makes it less likely that
another piece of code (e.g. a DestroyWindowFramebuffer implementation)
will attempt to use or free the stale surface pointer.
From hmk:
"When scaling is enabled (e.g. via SDL_RenderSetLogicalSize, size not equal
to window size), mouse motion events are also scaled. Small motions are
rounded up (SDL_max() when the value after scaling is less than 1), while
larger motions are truncated by the floating point -> integer conversion.
https://hg.libsdl.org/SDL/file/b18197f9bf9d/src/render/SDL_render.c#l658
The end result feels something like mouse reverse mouse acceleration + angle
snapping at low speeds, but less consistent (amount of truncation & rounding
depends on how fast the mouse is moved) and potentially much worse if the
scaling factor is large. This pretty much makes it useless for anything
where you need precise mouse aiming (think of games). I suspect this is why
aiming gets so terrible in some games that let you use scaling to reduce the
render resolution (e.g. Ion Fury).
With 4x4 scaling, I can reproduce a situation where it takes three fast flicks
of the mouse across the pad to undo one slow sweep across the pad. In other
words, extreme reverse acceleration. This does not happen when scaling is
disabled.
Furthermore, any game that uses relative mouse motion events for 3D camera
rotation probably wants the raw mouse deltas and not a value that depends on
scaling and resolution and rounding and truncation. Ideal camera rotation
just takes mouse input, multiplies it by sensitivity, and adds it to the
angle-in-radians or whatever measure is used for yaw & pitch. Pixels and
screen resolution or window dimensions should not be a part of the equation
at all, even if it could be implemented without rounding errors.
[...]
This [patch] completely eliminates angle snapping for me, and makes
sensitivity consistent. In other words, it's completely usable for, say,
aiming in a first person shooter."
Partially fixes Bugzilla #4811.
Caleb Cornett's comments:
"A few weeks ago, Alex added a partial Metal API to SDL2:
https://hg.libsdl.org/SDL/rev/22c8e7cd8d38
I noticed it was missing a few features that would help Metal become a
first-class citizen in SDL, so I went ahead and wrote them! Here are the new
APIs:
1. SDL_WINDOW_METAL flag for SDL_CreateWindow(). This allows the programmer
to specify that they intend to create a window for use with SDL_MetalView.
The flag is used to ensure correct usage of the API and to prevent
accidentally defaulting to OpenGL on iOS.
2. SDL_Metal_GetLayer(). This function takes a SDL_MetalView and returns a
pointer to the view's backing CAMetalLayer. This simplifies things
considerably, since in the current version of the SDL_Metal API the
programmer is required to bridge-cast a SDL_MetalView handle to an NSView or
UIView (depending on the platform) and then extract the layer from there.
SDL_Metal_GetLayer automatically handles all of that, making the operation
simple and cross-platform.
3. SDL_Metal_GetDrawableSize(). This function already exists in the current
SDL_Metal API (and is used behind-the-scenes for SDL_Vulkan_GetDrawableSize
on Apple platforms) but was not publicly exposed. My patch exposes this
function for public use. It works just like you'd expect.
Tested on macOS 10.14 and iOS 12.4."
Fixes Bugzilla #4796.
This does not account for scrollbars nor margins. But is much better then returning the full display size when not running fullscreen, but for example in an iframe.
The first terminator is for input parameters. The second terminator was for the
output parameters.
If an error occurs when calling MakeThreadHighPriority(), e.g. a bad thread id,
then the reply from connection_send_with_reply_and_block() will be null.
Anthony Pesch's notes on his patch:
"Currently, the WASAPI backend creates a stream in shared mode and sets the
device's callback size to be half of the shared stream's total buffer size.
This works, but doesn't coordinate will with the actual hardware. The hardware
will raise an interrupt after every period which in turn will signal the
object being waited on inside of WaitDevice. From my empirical testing, the
callback size was often larger than the period size and not a multiple of it,
which resulted in poor latency when trying to time an application based on the
audio callback. The reason for this looked something like:
* The device's callback would be called and and the audio buffer was filled.
* WaitDevice would be called.
* The hardware would raise an interrupt after one period.
* WaitDevice would resume, see that a a full callback had not been played and
then wait again.
* The hardware would raise an interrupt after another period.
* WaitDevice would resume, see that a full callback + some extra amount had
been played and then it would again call our callback and this process would
repeat.
The effect of this is that the pacing between subsequent callbacks is poor -
sometimes it's called very quickly, sometimes it's called very late.
By matching the callback's size to the stream's period size, the pacing of
calls to the user callback is improved substantially. I didn't write an actual
test for this, but my use case for this was my Dreamcast emulator
(https://redream.io) which uses the audio callback to help drive the emulation
speed. Without this change and with the default shared stream buffer (which
has a period of ~10ms) I would get frame times that were between ~3-30
milliseconds; after this change I get frame times of ~11-22 milliseconds.
Note, this patch also has a change that removes passing a duration to the
Initialize call. It seems that the default duration used (when 0 is passed)
does typically match up with the duration returned by GetDevicePeriod, however
the Initialize docs say:
> To set the buffer to the minimum size required by the engine thread, the
> client should call Initialize with the hnsBufferDuration parameter set to 0.
> Following the Initialize call, the client can get the size of the resulting
> buffer by calling IAudioClient::GetBufferSize.
This change isn't strictly required, but I made it to hopefully rule out
another source of unexpected latency."
Fixes Bugzilla #4592.
If called from background threads, use Grand Central Dispatch to use the
main thread instead. On the main thread, just call them directly.
Fixes Bugzilla #4932.
The warnings were produced by GCC 9.2.x for x86_64-linux-gnu or
i386-pc-msdosdjgpp targets.
Most of the fixes involve changing the type of a variable rather than
the format specifier. For many of the affected test conuter variables,
a basic int seems sufficient.
Some format specifier warnings still remain for cases where changing
type or casting seemed inappropriate. Those warnings will probably
require some new format specifier macros (e.g. SDL_PRIu32).
Jason
In iOS, URL Events trigger the DropFile event. I would also expect the same event to be fired on the macOS platform but this is not implemented at all in the AppDelegate.
Konrad
It appears that I cannot use SDL_RenderReadPixels on a bound framebuffer (SDL_Texture set as render target) as it simply results in gibberish data. However, drawing that framebuffer into the default target (window surface) does render it correctly. Other backends (OpenGL, software, Direct3D) do work fine.
It looks to me like D3D11_RenderReadPixels just gets the general backbuffer and not the current render target and its backbuffer.
Here is the patch which actually fetches the current render target and its underlying ID3D11Resource which is ID3D11Texture2D.
There are multiple SDL APIs that internally sink into dbus calls, e.g. battery
status, thread priority. If those calls happen in different threads simultaneously
it can result in dbus crashes.
To abide by dbus's multithreading guidelines we must call dbus_threads_init_default()
to enable dbus's internal locking mechanisms:
https://dbus.freedesktop.org/doc/api/html/group__DBusThreads.html#gac7b8a7001befc3eaa8c6b043151008dc
Additionally, access to a DBusMessage must be synchronized between threads.
SDL was already abiding that guideline as the DBusMessage structs aren't shared.
The following email from the dbus mailing list hints that arbitrating access to
the DBusConnection on the SDL may also be required:
https://lists.freedesktop.org/archives/dbus/2017-September/017306.html
Currently the message is double terminated, which results in SDL_DBus_CallMethodInternal()
incorrectly assuming that the other party is always returning true.
I'm not super familiar with dbus, so I'm not sure if this could also be the cause of this bug:
https://github.com/ValveSoftware/steam-for-linux/issues/6901
So if you go into System Preferences on a MacBook and toggle between a pair of
connected bluetooth headphones and built-in internal speakers, SDL will
switch the device it is playing sound through, to match this setting, on the
fly.
Likewise if the default output device is a USB thing and is unplugged; as the
default device changes at the system level, SDL will pick this up and carry
on with the new default. This is different from our unplug detection for
specific devices, as in those cases we want to send the app a disconnect
notification, instead of migrating transparently as we now do for default
devices.
Note that this should also work for capture devices; if the device changes,
SDL will start recording from the new default.
Fixes Bugzilla #4851.
This avoids the need to malloc something extra, use a semaphore, etc, and
fixes Emscripten with pthreads support, which might not spin up a web worker
until after SDL_CreateThread returns and thus can't wait on a semaphore at
this point in any case.
Fixes Bugzilla #5064.
Build is broken without EGL since version 2.0.12 and
https://hg.libsdl.org/SDL/rev/72cc4740dec2:
/home/giuliobenetti/autobuild/run/instance-1/output-1/build/sdl2-2.0.12/src/video/kmsdrm/SDL_kmsdrmvideo.c: In function 'KMSDRM_CreateSurfaces':
/home/giuliobenetti/autobuild/run/instance-1/output-1/build/sdl2-2.0.12/src/video/kmsdrm/SDL_kmsdrmvideo.c:394:5: error: unknown type name 'EGLContext'
EGLContext egl_context;
^
Fixes:
- http://autobuild.buildroot.org/results/fafd20a01591032662f9ca025fcea3478239cf3c
Signed-off-by: Fabrice Fontaine <fontaine.fabrice@gmail.com>
Build with directfb is broken due to a spurious '}' and a missing 'E'
since version 2.0.12 and https://hg.libsdl.org/SDL/rev/4c2dcf490cba:
/home/buildroot/autobuild/run/instance-2/output-1/build/sdl2-2.0.12/src/video/directfb/SDL_DirectFB_render.c: In function 'SetBlendMode':
/home/buildroot/autobuild/run/instance-2/output-1/build/sdl2-2.0.12/src/video/directfb/SDL_DirectFB_render.c:202:9: error: case label not within a switch statement
202 | case SDL_BLENDMODE_MUL:
| ^~~~
/home/buildroot/autobuild/run/instance-2/output-1/build/sdl2-2.0.12/src/video/directfb/SDL_DirectFB_render.c:205:67: error: 'DSBF_DSTCOLOR' undeclared (first use in this function); did you mean 'DSBF_DESTCOLOR'?
205 | SDL_DFB_CHECK(destsurf->SetSrcBlendFunction(destsurf, DSBF_DSTCOLOR));
| ^~~~~~~~~~~~~
Fixes:
- http://autobuild.buildroot.org/results/83ccefee68c2800c0544e6f40fa8bc8ee6b67b77
Signed-off-by: Fabrice Fontaine <fontaine.fabrice@gmail.com>
Andrei Kortunov
Hello. I try to implement an application for Android, which uses a new sensors API from 2.0.9 to control a camera rotation via built-in gyroscope, using the code from the test/testsensor.c as an example.
Gyroscope input itself works well, but an interval between SDL_SENSORUPDATE events is about 200ms (the SENSOR_DELAY_NORMAL, I believe), when I need the interval about 20-40ms (the SENSOR_DELAY_GAME or SENSOR_DELAY_FASTEST).
If a driver's implementation of CreateWindowFramebuffer sets the window
surface, use that rather than overwriting it. A driver may set the window
surface if data cannot be passed via the CreateWindowFramebuffer output
parameters (e.g. surface palette colors).
Otherwise our cached state goes out of sync when updating a texture. Since
these state changes aren't necessary, they were removed instead of updating
the cached state.
Fixes Bugzilla #4998.
bluenaxela+sdl
I've noticed that the Switch Pro Controller hidapi driver does not report battery levels when connected via Bluetooth, despite having code for setting joystick->epowerlevel.
This is caused by the driver always using k_eSwitchInputReportIDs_SimpleControllerState via Bluetooth. Using that mode means that the state reports you get back from the controller do not include battery state. Not using the full controller state over Bluetooth effectively makes this driver's support for setting joystick->epowerlevel entirely pointless, only ever reporting SDL_JOYSTICK_POWER_WIRED.
Is there a reason this was set to only use SimpleControllerState via Bluetooth?
I've attached a patch I'm using to allow getting battery level for the Switch Pro Controller.
A couple notes about this patch:
1) It changes LoadStickCalibration to accept the input_mode that is selected, because that's really what should determine what is used for stick extents, since stick extents differ between the modes.
2) In my patch I only use FullControllerState when the vid/pid matches the official Switch Pro Controller, as a cautionary measure in case some third-party controllers have problems with FullControllerState mode via Bluetooth (I noticed a HORI Wireless Switch Pad I had seemed to not read controller calibration correctly for stick extents. Maybe it's calibration data was uninitialized on account of having never been used with a Switch? I'm unsure, though if that guess is right maybe SDL2 should be detecting an uninitiated calibration state and using some sensible defaults)
There are a number of poorly behaved HID devices that time out on attempts to
read various strings. Rather than end up on an endless treadmill of blacklisting
broken devices, reduce our risk by only querying devices that are gamepads.
SDL_hidapijoystick.c already checks these same usages, so we shouldn't
exclude any working HID devices (caveat below).
This also makes HidP_GetPreparsedData() and HidP_GetCaps() failure skip
the device entirely, but that seems desired. If a device can't even return basic
top-level collection data properly, we want nothing to do with that broken device.
If we do find devices that work with HIDAPI joystick and fail these calls, we can
add an exception via VID+PID matching.
bluenaxela+sdl
The HORI Wireless Switch Pad does not properly connect via bluetooth. I did some debugging and found that the code that tries to control the Home LED causes this controller to disconnect.
This results in a dlsym() call, which causes Emscripten to panic if the game
wasn't explicitly built dlopen support. eglGetProcAddress works just fine on
this platform, so just let that codepath handle it.
This is a multi-part fix, and is the 2nd attempt at a fix for Bug 5034. Here
are the problems being addressed:
1. On macOS 10.14.x and earlier, trying to call IOHIDDeviceUnscheduleFromRunLoop
without a prior, paired call to IOHIDDeviceScheduleWithRunLoop, appears to
lead to a crash. A per-device flag has been added to make sure that these
calls are paired.
2. DARWIN_JoystickDetect was free'ing its SDL_joystick's hwdata field
(via FreeDevice) without setting it to NULL, and DARWIN_JoystickRumble wasn't
checking for a NULL hwdata. FreeDevice will now set hwdata to NULL and
DARWIN_JoystickRumble will check for a NULL hwdata.
meyraud705
Added Linux implementation, otherwise you get "Unsupported direction type" error.
Added documentation to explain why one would use SDL_HAPTIC_FIRST_AXIS.
Mathieu Laurendeau
Consider a device supporting effects on multiple axes.
There's currently no way to play effects against a single-axis direction.
A device supporting effects against X and Y may not allow to play effects with a two-axis direction coordinate, even if one of the coordinates is null.
My current (ugly) work around for this is to add a direction type SDL_HAPTIC_X_FORCE to play effects against a X-axis only direction (patch attached).
This issue impacted two GIMX users using the following wheels:
- Leo Bodnar SimSteering force feedback wheel
- Accuforce direct drive wheel
Playing constant/spring/damper effects against a X-axis direction worked well for the first wheel, but not for the second one.
A better strategy seems to play the effects against the first axis reported by the DirectInput enumeration.
This strategy also works with Logitech wheels (at least the DFGT).
It's been more than a year that I have the latest patch (playing effects against the first axis only) in the GIMX software. It's being used by thousands of people, mostly for adapting their FFB wheel to the PS4. I had no report that proves this strategy to be wrong.
Jimb Esser
Add new RawInput controller API, and improved correlation with XInput/WGI
Reorder joystick init so drivers can ask the others if they handle a device reliably
Do not poll disconnected XInput devices (major perf issue)
Fix various cases where incorrect correlation could happen
Simple mechanism for propagating unhandled Guide button presses even before guaranteed correlation
Correlate by axis motion as well as button presses
Fix failing to zero other trigger
Fix SDL_HINT_JOYSTICK_HIDAPI not working if set before calling SDL_Init()
Add missing device to device names
Disable RawInput if we have a mismatch of XInput-capable but not RawInput-capable devices
Updated to SDL 2.0.13 code with the following notes:
New HID driver: xbox360w - no idea what that is, hopefully urelated
SDL_hidapijoystick.c had been refactored to couple data handling logic with device opening logic and device lists caused some problems, yields slightly uglier integration than previously when the 360 HID device driver was just handling the data.
SDL_hidapijoystick.c now often pulls the device off of the joystick_hwdata structure for some rumble logic, but it appears that code path is never reached, so probably not a problem.
Looks like joystick_hwdata was refactored to not include a mutex in other drivers, maintainers may want to do the same refactor here if that's useful for some reason.
Something changed in how devices get names, so getting generic names.
Had to fix a (new?) bug where removing an XInput controller caused existing controllers (that moved to a new XInput index) to get identified as 0x045e/0x02fd ("it's probably Bluetooth" in code), rendering the existing HIDAPI_IsDevicePresent and new RAWINPUT_IsDevicePresent unreliable.
Jimb Esser
Add new RawInput controller API, and improved correlation with XInput/WGI
Reorder joystick init so drivers can ask the others if they handle a device reliably
Do not poll disconnected XInput devices (major perf issue)
Fix various cases where incorrect correlation could happen
Simple mechanism for propagating unhandled Guide button presses even before guaranteed correlation
Correlate by axis motion as well as button presses
Fix failing to zero other trigger
Fix SDL_HINT_JOYSTICK_HIDAPI not working if set before calling SDL_Init()
Add missing device to device names
Disable RawInput if we have a mismatch of XInput-capable but not RawInput-capable devices
Updated to SDL 2.0.13 code with the following notes:
New HID driver: xbox360w - no idea what that is, hopefully urelated
SDL_hidapijoystick.c had been refactored to couple data handling logic with device opening logic and device lists caused some problems, yields slightly uglier integration than previously when the 360 HID device driver was just handling the data.
SDL_hidapijoystick.c now often pulls the device off of the joystick_hwdata structure for some rumble logic, but it appears that code path is never reached, so probably not a problem.
Looks like joystick_hwdata was refactored to not include a mutex in other drivers, maintainers may want to do the same refactor here if that's useful for some reason.
Something changed in how devices get names, so getting generic names.
Had to fix a (new?) bug where removing an XInput controller caused existing controllers (that moved to a new XInput index) to get identified as 0x045e/0x02fd ("it's probably Bluetooth" in code), rendering the existing HIDAPI_IsDevicePresent and new RAWINPUT_IsDevicePresent unreliable.
Malte Kie?ling
I get a build error in SDL_sysjoystick.c:74 for the merged patch, but its nothing to sweat about, just -Werror=declaration-after-statement doing its usual stuff.
David Ludwig
I have created a new driver for SDL's Joystick and Game-Controller subsystem: a Virtual driver. This driver allows one to create a software-based joystick, which to SDL applications will look and react like a real joystick, but whose state can be set programmatically. A primary use case for this is to help enable developers to add touch-screen joysticks to their apps.
The driver comes with a set of new, public APIs, with functions to attach and detach joysticks, set virtual-joystick state, and to determine if a joystick is a virtual-one.
Use of virtual joysticks goes as such:
1. Attach one or more virtual joysticks by calling SDL_JoystickAttachVirtual. If successful, this returns the virtual-device's joystick-index.
2. Open the virtual joysticks (using indicies returned by SDL_JoystickAttachVirtual).
3. Call any of the SDL_JoystickSetVirtual* functions when joystick-state changes. Please note that virtual-joystick state will only get applied on the next call to SDL_JoystickUpdate, or when pumping or polling for SDL events (via SDL_PumpEvents or SDL_PollEvent).
Here is a listing of the new, public APIs, at present and subject to change:
------------------------------------------------------------
/**
* Attaches a new virtual joystick.
* Returns the joystick's device index, or -1 if an error occurred.
*/
extern DECLSPEC int SDLCALL SDL_JoystickAttachVirtual(SDL_JoystickType type, int naxes, int nballs, int nbuttons, int nhats);
/**
* Detaches a virtual joystick
* Returns 0 on success, or -1 if an error occurred.
*/
extern DECLSPEC int SDLCALL SDL_JoystickDetachVirtual(int device_index);
/**
* Indicates whether or not a virtual-joystick is at a given device index.
*/
extern DECLSPEC SDL_bool SDLCALL SDL_JoystickIsVirtual(int device_index);
/**
* Set values on an opened, virtual-joystick's controls.
* Returns 0 on success, -1 on error.
*/
extern DECLSPEC int SDLCALL SDL_JoystickSetVirtualAxis(SDL_Joystick * joystick, int axis, Sint16 value);
extern DECLSPEC int SDLCALL SDL_JoystickSetVirtualBall(SDL_Joystick * joystick, int ball, Sint16 xrel, Sint16 yrel);
extern DECLSPEC int SDLCALL SDL_JoystickSetVirtualButton(SDL_Joystick * joystick, int button, Uint8 value);
extern DECLSPEC int SDLCALL SDL_JoystickSetVirtualHat(SDL_Joystick * joystick, int hat, Uint8 value);
------------------------------------------------------------
Miscellaneous notes on the initial patch, which are also subject to change:
1. no test code is present in SDL, yet. This should, perhaps, change. Initial development was done with an ImGui-based app, which potentially is too thick for use in SDL-official. If tests are to be added, what kind of tests? Automated? Graphical?
2. virtual game controllers can be created by calling SDL_JoystickAttachVirtual with a joystick-type of SDL_JOYSTICK_TYPE_GAME_CONTROLLER, with naxes (num axes) set to SDL_CONTROLLER_AXIS_MAX, and with nbuttons (num buttons) set to SDL_CONTROLLER_BUTTON_MAX. When updating their state, values of type SDL_GameControllerAxis or SDL_GameControllerButton can be casted to an int and used for the control-index (in calls to SDL_JoystickSetVirtual* functions).
3. virtual joysticks' guids are mostly all-zeros with the exception of the last two bytes, the first of which is a 'v', to indicate that the guid is a virtual one, and the second of which is a SDL_JoystickType that has been converted into a Uint8.
4. virtual joysticks are ONLY turned into virtual game-controllers if and when their joystick-type is set to SDL_JOYSTICK_TYPE_GAMECONTROLLER. This is controlled by having SDL's default list of game-controllers have a single entry for a virtual game controller (of guid, "00000000000000000000000000007601", which is subject to the guid-encoding described above).
5. regarding having to call SDL_JoystickUpdate, either directly or indirectly via SDL_PumpEvents or SDL_PollEvents, before new virtual-joystick state becomes active (as specified via SDL_JoystickSetVirtual* function-calls), this was done to match behavior found in SDL's other joystick drivers, almost all of which will only update SDL-state during SDL_JoystickUpdate.
6. the initial patch is based off of SDL 2.0.12
7. the virtual joystick subsystem is disabled by default. It should be possible to enable it by building with SDL_JOYSTICK_VIRTUAL=1
Questions, comments, suggestions, or bug reports very welcome!
Ethan Lee
Basically replicating the solution of the Switch Controller's button label issue. Physical layout should take priority unless it's explicitly requested by the user or application!
ciremo6483
In `SDL_iconv_string` the `while (inbytesleft > 0)` loop can end up in a state where it never terminates because the library `iconv` function called from `SDL_iconv` doesn't consume any bytes.
This happened when a `WCHAR_T` input string was being converted to `UTF-8` but contained invalid characters. It would first It would first skip a few bytes due to `case SDL_ICONV_EILSEQ` but when there were 3 bytes remaining of `inbytesleft` `iconv` just didn't consume anything more (but didn't throw an error either).
It just so happens that the Microsoft Classic IntelliMouse `product_string` contains such invalid characters (`"Microsoft? Classic IntelliMouse?"`), meaning the function would get stuck with said mouse plugged in.
A fix for this would be to check if `inbytesleft` was unchanged after an iteration and in that case either decrement the counter like when `SDL_ICONV_EILSEQ` is returned or simply break the loop.
cmediaplayer
Hi, i already mentioned in the SDL discourse a bug that recreating of a texture occours pixel shader problem on direct3d renderer. There is no problem for direct3d11. You can see the issue by using my app named C Media Player which is available for Windows for free using my web site www.cmediaplayer.com. Just follow the steps:
*Open a media file
*When playing the file change the scale quality under the video menu.
*You will see the problem.
Prior to this fix, we would hit the existing_instance >= 0 case and move the joystick
again to a different index than the one requested by the caller. It also breaks the assumption
that a SDL_JoystickID is only present in SDL_joystick_players at one location.
Anthony Pesch
I was just communicating with one of the Retropie developers regarding this.
This change removed the forced window focus change on creation (3534cb3793) as part of the change no longer assumes there's only a single window being created. This was perhaps an over-aggressive removal.
Due to that change, joystick events are only received if SDL_SetKeyboardFocus is called explicitly, or if the app has specified SDL_HINT_JOYSTICK_ALLOW_BACKGROUND_EVENTS.
I think that part of my change should be reverted to continue setting mouse / keyboard focus to the window being created. If SDL_WINDOW_INPUT_FOCUS is to be used as an input flag the code could be conditional, but that would still leave existing software broken.
The 8BitDo SF30 Pro Gamepad will generate a single motor pulse for each rumble message, so we need to do this frequently to have continous rumble on this device.