LIBS: updated sdl2
parent
99bfd08f9a
commit
106e6d7295
|
@ -174,7 +174,7 @@ macro(CheckPulseAudio)
|
|||
set(SDL_AUDIO_DRIVER_PULSEAUDIO_DYNAMIC "\"${PULSE_SIMPLE_LIB_SONAME}\"")
|
||||
set(HAVE_PULSEAUDIO_SHARED TRUE)
|
||||
else()
|
||||
list(APPEND EXTRA_LDFLAGS ${PKG_sPULSEAUDIO_LDFLAGS})
|
||||
list(APPEND EXTRA_LDFLAGS ${PKG_PULSEAUDIO_LDFLAGS})
|
||||
endif()
|
||||
set(HAVE_SDL_AUDIO TRUE)
|
||||
endif()
|
||||
|
@ -467,6 +467,8 @@ macro(CheckX11)
|
|||
else()
|
||||
list(APPEND EXTRA_LIBS ${X11_LIB} ${XEXT_LIB})
|
||||
endif()
|
||||
else()
|
||||
list(APPEND EXTRA_LIBS ${X11_LIB} ${XEXT_LIB})
|
||||
endif()
|
||||
|
||||
set(CMAKE_REQUIRED_LIBRARIES ${X11_LIB} ${X11_LIB})
|
||||
|
|
|
@ -869,8 +869,9 @@ extern DECLSPEC int SDLCALL SDL_GameControllerRumble(SDL_GameController *gamecon
|
|||
* calling it with 0 intensity stops any rumbling.
|
||||
*
|
||||
* Note that this is rumbling of the _triggers_ and not the game controller as
|
||||
* a whole. The first controller to offer this feature was the PlayStation 5's
|
||||
* DualShock 5.
|
||||
* a whole. This is currently only supported on Xbox One controllers. If you
|
||||
* want the (more common) whole-controller rumble, use
|
||||
* SDL_GameControllerRumble() instead.
|
||||
*
|
||||
* \param gamecontroller The controller to vibrate
|
||||
* \param left_rumble The intensity of the left trigger rumble motor, from 0
|
||||
|
|
|
@ -625,6 +625,21 @@ extern "C" {
|
|||
*/
|
||||
#define SDL_HINT_JOYSTICK_HIDAPI_GAMECUBE "SDL_JOYSTICK_HIDAPI_GAMECUBE"
|
||||
|
||||
/**
|
||||
* \brief A variable controlling whether "low_frequency_rumble" and "high_frequency_rumble" is used to implement
|
||||
* the GameCube controller's 3 rumble modes, Stop(0), Rumble(1), and StopHard(2)
|
||||
* this is useful for applications that need full compatibility for things like ADSR envelopes.
|
||||
* Stop is implemented by setting "low_frequency_rumble" to "0" and "high_frequency_rumble" ">0"
|
||||
* Rumble is both at any arbitrary value,
|
||||
* StopHard is implemented by setting both "low_frequency_rumble" and "high_frequency_rumble" to "0"
|
||||
*
|
||||
* This variable can be set to the following values:
|
||||
* "0" - Normal rumble behavior is behavior is used (default)
|
||||
* "1" - Proper GameCube controller rumble behavior is used
|
||||
*
|
||||
*/
|
||||
#define SDL_HINT_JOYSTICK_GAMECUBE_RUMBLE_BRAKE "SDL_JOYSTICK_GAMECUBE_RUMBLE_BRAKE"
|
||||
|
||||
/**
|
||||
* \brief A variable controlling whether Switch Joy-Cons should be treated the same as Switch Pro Controllers when using the HIDAPI driver.
|
||||
*
|
||||
|
|
|
@ -829,9 +829,9 @@ extern DECLSPEC int SDLCALL SDL_JoystickRumble(SDL_Joystick *joystick, Uint16 lo
|
|||
* Each call to this function cancels any previous trigger rumble effect, and
|
||||
* calling it with 0 intensity stops any rumbling.
|
||||
*
|
||||
* Note that this function is for _trigger_ rumble; the first joystick to
|
||||
* support this was the PlayStation 5's DualShock 5 controller. If you want
|
||||
* the (more common) whole-controller rumble, use SDL_JoystickRumble()
|
||||
* Note that this is rumbling of the _triggers_ and not the game controller as
|
||||
* a whole. This is currently only supported on Xbox One controllers. If you
|
||||
* want the (more common) whole-controller rumble, use SDL_JoystickRumble()
|
||||
* instead.
|
||||
*
|
||||
* \param joystick The joystick to vibrate
|
||||
|
|
|
@ -271,6 +271,10 @@ extern DECLSPEC void SDLCALL SDL_StopTextInput(void);
|
|||
/**
|
||||
* Set the rectangle used to type Unicode text inputs.
|
||||
*
|
||||
* Note: If you want use system native IME window, try to set hint
|
||||
* **SDL_HINT_IME_SHOW_UI** to **1**, otherwise this function won't give you
|
||||
* any feedback.
|
||||
*
|
||||
* \param rect the SDL_Rect structure representing the rectangle to receive
|
||||
* text (ignored if NULL)
|
||||
*
|
||||
|
|
|
@ -407,6 +407,7 @@ openslES_CreatePCMPlayer(_THIS)
|
|||
{
|
||||
struct SDL_PrivateAudioData *audiodata = this->hidden;
|
||||
SLDataFormat_PCM format_pcm;
|
||||
SLAndroidDataFormat_PCM_EX format_pcm_ex;
|
||||
SLresult result;
|
||||
int i;
|
||||
|
||||
|
@ -414,30 +415,30 @@ openslES_CreatePCMPlayer(_THIS)
|
|||
it can be done as described here:
|
||||
https://developer.android.com/ndk/guides/audio/opensl/android-extensions.html#floating-point
|
||||
*/
|
||||
#if 1
|
||||
/* Just go with signed 16-bit audio as it's the most compatible */
|
||||
this->spec.format = AUDIO_S16SYS;
|
||||
#else
|
||||
SDL_AudioFormat test_format;
|
||||
for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
|
||||
if (SDL_AUDIO_ISSIGNED(test_format) && SDL_AUDIO_ISINT(test_format)) {
|
||||
break;
|
||||
if(SDL_GetAndroidSDKVersion() >= 21) {
|
||||
SDL_AudioFormat test_format;
|
||||
for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
|
||||
if (SDL_AUDIO_ISSIGNED(test_format)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!test_format) {
|
||||
/* Didn't find a compatible format : */
|
||||
LOGI( "No compatible audio format, using signed 16-bit audio" );
|
||||
test_format = AUDIO_S16SYS;
|
||||
if (!test_format) {
|
||||
/* Didn't find a compatible format : */
|
||||
LOGI( "No compatible audio format, using signed 16-bit audio" );
|
||||
test_format = AUDIO_S16SYS;
|
||||
}
|
||||
this->spec.format = test_format;
|
||||
} else {
|
||||
/* Just go with signed 16-bit audio as it's the most compatible */
|
||||
this->spec.format = AUDIO_S16SYS;
|
||||
}
|
||||
this->spec.format = test_format;
|
||||
#endif
|
||||
|
||||
/* Update the fragment size as size in bytes */
|
||||
SDL_CalculateAudioSpec(&this->spec);
|
||||
|
||||
LOGI("Try to open %u hz %u bit chan %u %s samples %u",
|
||||
this->spec.freq, SDL_AUDIO_BITSIZE(this->spec.format),
|
||||
LOGI("Try to open %u hz %s %u bit chan %u %s samples %u",
|
||||
this->spec.freq, SDL_AUDIO_ISFLOAT(this->spec.format) ? "float" : "pcm", SDL_AUDIO_BITSIZE(this->spec.format),
|
||||
this->spec.channels, (this->spec.format & 0x1000) ? "BE" : "LE", this->spec.samples);
|
||||
|
||||
/* configure audio source */
|
||||
|
@ -488,7 +489,19 @@ openslES_CreatePCMPlayer(_THIS)
|
|||
break;
|
||||
}
|
||||
|
||||
SLDataSource audioSrc = { &loc_bufq, &format_pcm };
|
||||
if(SDL_AUDIO_ISFLOAT(this->spec.format)) {
|
||||
/* Copy all setup into PCM EX structure */
|
||||
format_pcm_ex.formatType = SL_ANDROID_DATAFORMAT_PCM_EX;
|
||||
format_pcm_ex.endianness = format_pcm.endianness;
|
||||
format_pcm_ex.channelMask = format_pcm.channelMask;
|
||||
format_pcm_ex.numChannels = format_pcm.numChannels;
|
||||
format_pcm_ex.sampleRate = format_pcm.samplesPerSec;
|
||||
format_pcm_ex.bitsPerSample = format_pcm.bitsPerSample;
|
||||
format_pcm_ex.containerSize = format_pcm.containerSize;
|
||||
format_pcm_ex.representation = SL_ANDROID_PCM_REPRESENTATION_FLOAT;
|
||||
}
|
||||
|
||||
SLDataSource audioSrc = { &loc_bufq, SDL_AUDIO_ISFLOAT(this->spec.format) ? (void*)&format_pcm_ex : (void*)&format_pcm };
|
||||
|
||||
/* configure audio sink */
|
||||
SLDataLocator_OutputMix loc_outmix = { SL_DATALOCATOR_OUTPUTMIX, outputMixObject };
|
||||
|
|
|
@ -394,6 +394,7 @@ typedef struct {
|
|||
unsigned int text_len;
|
||||
keysym_t composebuffer[2];
|
||||
unsigned char composelen;
|
||||
int type;
|
||||
} SDL_WSCONS_input_data;
|
||||
|
||||
static SDL_WSCONS_input_data* inputs[4] = {NULL, NULL, NULL, NULL};
|
||||
|
@ -432,6 +433,7 @@ static SDL_WSCONS_input_data* SDL_WSCONS_Init_Keyboard(const char* dev)
|
|||
RETIFIOCTLERR(ioctl(input->fd, WSKBDIO_GETLEDS, &input->ledstate));
|
||||
input->origledstate = input->ledstate;
|
||||
RETIFIOCTLERR(ioctl(input->fd, WSKBDIO_GETENCODING, &input->encoding));
|
||||
RETIFIOCTLERR(ioctl(input->fd, WSKBDIO_GTYPE, &input->type));
|
||||
#ifdef WSKBDIO_SETVERSION
|
||||
RETIFIOCTLERR(ioctl(input->fd, WSKBDIO_SETVERSION, &version));
|
||||
#endif
|
||||
|
@ -725,7 +727,12 @@ static void updateKeyboard(SDL_WSCONS_input_data* input)
|
|||
}
|
||||
break;
|
||||
}
|
||||
Translate_to_keycode(input, type, events[i].value);
|
||||
|
||||
if (input->type == WSKBD_TYPE_USB && events[i].value <= 0xE7)
|
||||
SDL_SendKeyboardKey(type == WSCONS_EVENT_KEY_DOWN ? SDL_PRESSED : SDL_RELEASED, (SDL_Scancode)events[i].value);
|
||||
else
|
||||
Translate_to_keycode(input, type, events[i].value);
|
||||
|
||||
if (type == WSCONS_EVENT_KEY_UP) continue;
|
||||
|
||||
if (IS_ALTGR_MODE && !IS_CONTROL_HELD)
|
||||
|
|
|
@ -206,11 +206,28 @@ SDL_LogEvent(const SDL_Event *event)
|
|||
SDL_EVENT_CASE(SDL_APP_DIDENTERBACKGROUND) break;
|
||||
SDL_EVENT_CASE(SDL_APP_WILLENTERFOREGROUND) break;
|
||||
SDL_EVENT_CASE(SDL_APP_DIDENTERFOREGROUND) break;
|
||||
SDL_EVENT_CASE(SDL_LOCALECHANGED) break;
|
||||
SDL_EVENT_CASE(SDL_KEYMAPCHANGED) break;
|
||||
SDL_EVENT_CASE(SDL_CLIPBOARDUPDATE) break;
|
||||
SDL_EVENT_CASE(SDL_RENDER_TARGETS_RESET) break;
|
||||
SDL_EVENT_CASE(SDL_RENDER_DEVICE_RESET) break;
|
||||
|
||||
SDL_EVENT_CASE(SDL_DISPLAYEVENT) {
|
||||
char name2[64];
|
||||
switch (event->display.event) {
|
||||
case SDL_DISPLAYEVENT_NONE: SDL_strlcpy(name2, "SDL_DISPLAYEVENT_NONE (THIS IS PROBABLY A BUG!)", sizeof(name2)); break;
|
||||
#define SDL_DISPLAYEVENT_CASE(x) case x: SDL_strlcpy(name2, #x, sizeof (name2)); break
|
||||
SDL_DISPLAYEVENT_CASE(SDL_DISPLAYEVENT_ORIENTATION);
|
||||
SDL_DISPLAYEVENT_CASE(SDL_DISPLAYEVENT_CONNECTED);
|
||||
SDL_DISPLAYEVENT_CASE(SDL_DISPLAYEVENT_DISCONNECTED);
|
||||
#undef SDL_DISPLAYEVENT_CASE
|
||||
default: SDL_strlcpy(name2, "UNKNOWN (bug? fixme?)", sizeof(name2)); break;
|
||||
}
|
||||
SDL_snprintf(details, sizeof (details), " (timestamp=%u display=%u event=%s data1=%d)",
|
||||
(uint) event->display.timestamp, (uint) event->display.display, name2, (int) event->display.data1);
|
||||
break;
|
||||
}
|
||||
|
||||
SDL_EVENT_CASE(SDL_WINDOWEVENT) {
|
||||
char name2[64];
|
||||
switch(event->window.event) {
|
||||
|
@ -232,6 +249,8 @@ SDL_LogEvent(const SDL_Event *event)
|
|||
SDL_WINDOWEVENT_CASE(SDL_WINDOWEVENT_CLOSE);
|
||||
SDL_WINDOWEVENT_CASE(SDL_WINDOWEVENT_TAKE_FOCUS);
|
||||
SDL_WINDOWEVENT_CASE(SDL_WINDOWEVENT_HIT_TEST);
|
||||
SDL_WINDOWEVENT_CASE(SDL_WINDOWEVENT_ICCPROF_CHANGED);
|
||||
SDL_WINDOWEVENT_CASE(SDL_WINDOWEVENT_DISPLAY_CHANGED);
|
||||
#undef SDL_WINDOWEVENT_CASE
|
||||
default: SDL_strlcpy(name2, "UNKNOWN (bug? fixme?)", sizeof (name2)); break;
|
||||
}
|
||||
|
@ -660,7 +679,7 @@ static int
|
|||
SDL_PeepEventsInternal(SDL_Event * events, int numevents, SDL_eventaction action,
|
||||
Uint32 minType, Uint32 maxType, SDL_bool include_sentinel)
|
||||
{
|
||||
int i, used;
|
||||
int i, used, sentinels_expected = 0;
|
||||
|
||||
/* Don't look after we've quit */
|
||||
if (!SDL_AtomicGet(&SDL_EventQ.active)) {
|
||||
|
@ -723,8 +742,15 @@ SDL_PeepEventsInternal(SDL_Event * events, int numevents, SDL_eventaction action
|
|||
}
|
||||
if (type == SDL_POLLSENTINEL) {
|
||||
/* Special handling for the sentinel event */
|
||||
if (!include_sentinel || SDL_AtomicGet(&SDL_sentinel_pending) > 0) {
|
||||
/* Skip it, we don't want to include it or there's another one pending */
|
||||
if (!include_sentinel) {
|
||||
/* Skip it, we don't want to include it */
|
||||
continue;
|
||||
}
|
||||
if (!events || action != SDL_GETEVENT) {
|
||||
++sentinels_expected;
|
||||
}
|
||||
if (SDL_AtomicGet(&SDL_sentinel_pending) > sentinels_expected) {
|
||||
/* Skip it, there's another one pending */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
@ -991,6 +1017,7 @@ SDL_WaitEventTimeout(SDL_Event * event, int timeout)
|
|||
SDL_Window *wakeup_window;
|
||||
Uint32 start, expiration;
|
||||
SDL_bool include_sentinel = (timeout == 0) ? SDL_TRUE : SDL_FALSE;
|
||||
int result;
|
||||
|
||||
/* If there isn't a poll sentinel event pending, pump events and add one */
|
||||
if (SDL_AtomicGet(&SDL_sentinel_pending) == 0) {
|
||||
|
@ -998,33 +1025,34 @@ SDL_WaitEventTimeout(SDL_Event * event, int timeout)
|
|||
}
|
||||
|
||||
/* First check for existing events */
|
||||
switch (SDL_PeepEventsInternal(event, 1, SDL_GETEVENT, SDL_FIRSTEVENT, SDL_LASTEVENT, include_sentinel)) {
|
||||
case -1:
|
||||
result = SDL_PeepEventsInternal(event, 1, SDL_GETEVENT, SDL_FIRSTEVENT, SDL_LASTEVENT, include_sentinel);
|
||||
if (result < 0) {
|
||||
return 0;
|
||||
case 0:
|
||||
}
|
||||
if (include_sentinel) {
|
||||
if (event) {
|
||||
if (event->type == SDL_POLLSENTINEL) {
|
||||
/* Reached the end of a poll cycle, and not willing to wait */
|
||||
return 0;
|
||||
}
|
||||
} else {
|
||||
/* Need to peek the next event to check for sentinel */
|
||||
SDL_Event dummy;
|
||||
|
||||
if (SDL_PeepEventsInternal(&dummy, 1, SDL_PEEKEVENT, SDL_FIRSTEVENT, SDL_LASTEVENT, SDL_TRUE) &&
|
||||
dummy.type == SDL_POLLSENTINEL) {
|
||||
SDL_PeepEventsInternal(&dummy, 1, SDL_GETEVENT, SDL_POLLSENTINEL, SDL_POLLSENTINEL, SDL_TRUE);
|
||||
/* Reached the end of a poll cycle, and not willing to wait */
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (result == 0) {
|
||||
if (timeout == 0) {
|
||||
/* No events available, and not willing to wait */
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
if (include_sentinel) {
|
||||
if (event) {
|
||||
if (event->type == SDL_POLLSENTINEL) {
|
||||
/* Reached the end of a poll cycle, and not willing to wait */
|
||||
return 0;
|
||||
}
|
||||
} else {
|
||||
/* Need to peek the next event to check for sentinel */
|
||||
SDL_Event dummy;
|
||||
|
||||
if (SDL_PeepEventsInternal(&dummy, 1, SDL_PEEKEVENT, SDL_FIRSTEVENT, SDL_LASTEVENT, SDL_TRUE) &&
|
||||
dummy.type == SDL_POLLSENTINEL) {
|
||||
/* Reached the end of a poll cycle, and not willing to wait */
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
/* Has existing events */
|
||||
return 1;
|
||||
}
|
||||
|
|
|
@ -867,10 +867,14 @@ SDL_SendKeyboardText(const char *text)
|
|||
posted = 0;
|
||||
if (SDL_GetEventState(SDL_TEXTINPUT) == SDL_ENABLE) {
|
||||
SDL_Event event;
|
||||
size_t i = 0, length = SDL_strlen(text);
|
||||
|
||||
event.text.type = SDL_TEXTINPUT;
|
||||
event.text.windowID = keyboard->focus ? keyboard->focus->id : 0;
|
||||
SDL_utf8strlcpy(event.text.text, text, SDL_arraysize(event.text.text));
|
||||
posted = (SDL_PushEvent(&event) > 0);
|
||||
while (i < length) {
|
||||
i += SDL_utf8strlcpy(event.text.text, text + i, SDL_arraysize(event.text.text));
|
||||
posted |= (SDL_PushEvent(&event) > 0);
|
||||
}
|
||||
}
|
||||
return (posted);
|
||||
}
|
||||
|
|
|
@ -259,7 +259,7 @@ static int get_string_property(IOHIDDeviceRef device, CFStringRef prop, wchar_t
|
|||
|
||||
buf[0] = 0;
|
||||
|
||||
if (str) {
|
||||
if (str && CFGetTypeID(str) == CFStringGetTypeID()) {
|
||||
len --;
|
||||
|
||||
CFIndex str_len = CFStringGetLength(str);
|
||||
|
@ -298,7 +298,7 @@ static int get_string_property_utf8(IOHIDDeviceRef device, CFStringRef prop, cha
|
|||
|
||||
buf[0] = 0;
|
||||
|
||||
if (str) {
|
||||
if (str && CFGetTypeID(str) == CFStringGetTypeID()) {
|
||||
len--;
|
||||
|
||||
CFIndex str_len = CFStringGetLength(str);
|
||||
|
@ -326,10 +326,7 @@ static int get_string_property_utf8(IOHIDDeviceRef device, CFStringRef prop, cha
|
|||
|
||||
static int get_serial_number(IOHIDDeviceRef device, wchar_t *buf, size_t len)
|
||||
{
|
||||
// This crashes on M1 Macs, tracked by radar bug 79667729
|
||||
//return get_string_property(device, CFSTR(kIOHIDSerialNumberKey), buf, len);
|
||||
buf[0] = 0;
|
||||
return 0;
|
||||
return get_string_property(device, CFSTR(kIOHIDSerialNumberKey), buf, len);
|
||||
}
|
||||
|
||||
static int get_manufacturer_string(IOHIDDeviceRef device, wchar_t *buf, size_t len)
|
||||
|
@ -557,6 +554,7 @@ struct hid_device_info HID_API_EXPORT *hid_enumerate(unsigned short vendor_id,
|
|||
continue;
|
||||
}
|
||||
|
||||
#if 0 // Prefer direct HID support as that has extended functionality
|
||||
#if defined(SDL_JOYSTICK_MFI)
|
||||
// We want to prefer Game Controller support where available,
|
||||
// as Apple will likely be requiring that for supported devices.
|
||||
|
@ -564,6 +562,7 @@ struct hid_device_info HID_API_EXPORT *hid_enumerate(unsigned short vendor_id,
|
|||
if (IOS_SupportedHIDDevice(dev)) {
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
dev_vid = get_vendor_id(dev);
|
||||
|
|
|
@ -1882,7 +1882,7 @@ SDL_GetJoystickGameControllerType(const char *name, Uint16 vendor, Uint16 produc
|
|||
0x12ab, /* Unknown */
|
||||
0x1430, /* RedOctane */
|
||||
0x146b, /* BigBen */
|
||||
0x1532, /* Razer Sabertooth */
|
||||
0x1532, /* Razer */
|
||||
0x15e4, /* Numark */
|
||||
0x162e, /* Joytech */
|
||||
0x1689, /* Razer Onza */
|
||||
|
@ -1911,7 +1911,7 @@ SDL_GetJoystickGameControllerType(const char *name, Uint16 vendor, Uint16 produc
|
|||
0x0738, /* Mad Catz */
|
||||
0x0e6f, /* PDP */
|
||||
0x0f0d, /* Hori */
|
||||
0x1532, /* Razer Wildcat */
|
||||
0x1532, /* Razer */
|
||||
0x20d6, /* PowerA */
|
||||
0x24c6, /* PowerA */
|
||||
0x2e24, /* Hyperkin */
|
||||
|
@ -1944,6 +1944,9 @@ SDL_GetJoystickGameControllerType(const char *name, Uint16 vendor, Uint16 produc
|
|||
} else if (vendor == 0x0001 && product == 0x0001) {
|
||||
type = SDL_CONTROLLER_TYPE_UNKNOWN;
|
||||
|
||||
} else if (vendor == USB_VENDOR_MICROSOFT && product == USB_PRODUCT_XBOX_ONE_XINPUT_CONTROLLER) {
|
||||
type = SDL_CONTROLLER_TYPE_XBOXONE;
|
||||
|
||||
} else if ((vendor == USB_VENDOR_AMAZON && product == USB_PRODUCT_AMAZON_LUNA_CONTROLLER) ||
|
||||
(vendor == BLUETOOTH_VENDOR_AMAZON && product == BLUETOOTH_PRODUCT_LUNA_CONTROLLER)) {
|
||||
type = SDL_CONTROLLER_TYPE_AMAZON_LUNA;
|
||||
|
@ -2443,6 +2446,8 @@ SDL_bool SDL_ShouldIgnoreJoystick(const char *name, SDL_JoystickGUID guid)
|
|||
MAKE_VIDPID(0x04d9, 0x8009), /* OBINLB USB-HID Keyboard (Anne Pro II) */
|
||||
MAKE_VIDPID(0x04d9, 0xa292), /* OBINLB USB-HID Keyboard (Anne Pro II) */
|
||||
MAKE_VIDPID(0x04d9, 0xa293), /* OBINLB USB-HID Keyboard (Anne Pro II) */
|
||||
MAKE_VIDPID(0x1532, 0x0266), /* Razer Huntman V2 Analog, non-functional DInput device */
|
||||
MAKE_VIDPID(0x1532, 0x0282), /* Razer Huntman Mini Analog, non-functional DInput device */
|
||||
MAKE_VIDPID(0x26ce, 0x01a2), /* ASRock LED Controller */
|
||||
};
|
||||
|
||||
|
|
|
@ -53,6 +53,7 @@ typedef struct {
|
|||
/* Without this variable, hid_write starts to lag a TON */
|
||||
SDL_bool rumbleUpdate;
|
||||
SDL_bool m_bUseButtonLabels;
|
||||
SDL_bool useRumbleBrake;
|
||||
} SDL_DriverGameCube_Context;
|
||||
|
||||
static SDL_bool
|
||||
|
@ -92,6 +93,14 @@ static void SDLCALL SDL_GameControllerButtonReportingHintChanged(void *userdata,
|
|||
ctx->m_bUseButtonLabels = SDL_GetStringBoolean(hint, SDL_TRUE);
|
||||
}
|
||||
|
||||
static void SDLCALL SDL_JoystickGameCubeRumbleBrakeHintChanged(void *userdata, const char *name, const char *oldValue, const char *hint)
|
||||
{
|
||||
if (hint) {
|
||||
SDL_DriverGameCube_Context *ctx = (SDL_DriverGameCube_Context *)userdata;
|
||||
ctx->useRumbleBrake = SDL_GetStringBoolean(hint, SDL_FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
static Uint8 RemapButton(SDL_DriverGameCube_Context *ctx, Uint8 button)
|
||||
{
|
||||
if (!ctx->m_bUseButtonLabels) {
|
||||
|
@ -142,6 +151,7 @@ HIDAPI_DriverGameCube_InitDevice(SDL_HIDAPI_Device *device)
|
|||
ctx->joysticks[2] = -1;
|
||||
ctx->joysticks[3] = -1;
|
||||
ctx->rumble[0] = rumbleMagic;
|
||||
ctx->useRumbleBrake = SDL_FALSE;
|
||||
|
||||
if (device->vendor_id != USB_VENDOR_NINTENDO) {
|
||||
ctx->pc_mode = SDL_TRUE;
|
||||
|
@ -195,6 +205,8 @@ HIDAPI_DriverGameCube_InitDevice(SDL_HIDAPI_Device *device)
|
|||
}
|
||||
}
|
||||
|
||||
SDL_AddHintCallback(SDL_HINT_JOYSTICK_GAMECUBE_RUMBLE_BRAKE,
|
||||
SDL_JoystickGameCubeRumbleBrakeHintChanged, ctx);
|
||||
SDL_AddHintCallback(SDL_HINT_GAMECONTROLLER_USE_BUTTON_LABELS,
|
||||
SDL_GameControllerButtonReportingHintChanged, ctx);
|
||||
|
||||
|
@ -439,12 +451,22 @@ HIDAPI_DriverGameCube_RumbleJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *jo
|
|||
for (i = 0; i < MAX_CONTROLLERS; i += 1) {
|
||||
if (joystick->instance_id == ctx->joysticks[i]) {
|
||||
if (ctx->wireless[i]) {
|
||||
return SDL_SetError("Ninteno GameCube WaveBird controllers do not support rumble");
|
||||
return SDL_SetError("Nintendo GameCube WaveBird controllers do not support rumble");
|
||||
}
|
||||
if (!ctx->rumbleAllowed[i]) {
|
||||
return SDL_SetError("Second USB cable for WUP-028 not connected");
|
||||
}
|
||||
val = (low_frequency_rumble > 0 || high_frequency_rumble > 0);
|
||||
if (ctx->useRumbleBrake) {
|
||||
if (low_frequency_rumble == 0 && high_frequency_rumble > 0) {
|
||||
val = 0; /* if only low is 0 we want to do a regular stop*/
|
||||
} else if (low_frequency_rumble == 0 && high_frequency_rumble == 0) {
|
||||
val = 2; /* if both frequencies are 0 we want to do a hard stop */
|
||||
} else {
|
||||
val = 1; /* normal rumble */
|
||||
}
|
||||
} else {
|
||||
val = (low_frequency_rumble > 0 || high_frequency_rumble > 0);
|
||||
}
|
||||
if (val != ctx->rumble[i + 1]) {
|
||||
ctx->rumble[i + 1] = val;
|
||||
ctx->rumbleUpdate = SDL_TRUE;
|
||||
|
@ -522,6 +544,8 @@ HIDAPI_DriverGameCube_FreeDevice(SDL_HIDAPI_Device *device)
|
|||
|
||||
SDL_DelHintCallback(SDL_HINT_GAMECONTROLLER_USE_BUTTON_LABELS,
|
||||
SDL_GameControllerButtonReportingHintChanged, ctx);
|
||||
SDL_DelHintCallback(SDL_HINT_JOYSTICK_GAMECUBE_RUMBLE_BRAKE,
|
||||
SDL_JoystickGameCubeRumbleBrakeHintChanged, ctx);
|
||||
|
||||
SDL_LockMutex(device->dev_lock);
|
||||
{
|
||||
|
|
|
@ -69,6 +69,9 @@ static NSString *GCInputXboxShareButton = @"Button Share";
|
|||
#if !((__IPHONE_OS_VERSION_MAX_ALLOWED >= 130000) || (__APPLETV_OS_VERSION_MAX_ALLOWED >= 130000) || (__MAC_OS_VERSION_MAX_ALLOWED >= 1500000))
|
||||
@property(nonatomic, readonly) NSString *productCategory;
|
||||
#endif
|
||||
#if !((__IPHONE_OS_VERSION_MAX_ALLOWED >= 140500) || (__APPLETV_OS_VERSION_MAX_ALLOWED >= 140500) || (__MAC_OS_X_VERSION_MAX_ALLOWED >= 110300))
|
||||
@property(class, nonatomic, readwrite) BOOL shouldMonitorBackgroundEvents;
|
||||
#endif
|
||||
@end
|
||||
@interface GCExtendedGamepad (SDL)
|
||||
#if !((__IPHONE_OS_VERSION_MAX_ALLOWED >= 121000) || (__APPLETV_OS_VERSION_MAX_ALLOWED >= 121000) || (__MAC_OS_VERSION_MAX_ALLOWED >= 1401000))
|
||||
|
@ -572,6 +575,10 @@ IOS_JoystickInit(void)
|
|||
return 0;
|
||||
}
|
||||
|
||||
if (@available(macOS 11.3, iOS 14.5, tvOS 14.5, *)) {
|
||||
GCController.shouldMonitorBackgroundEvents = YES;
|
||||
}
|
||||
|
||||
/* For whatever reason, this always returns an empty array on
|
||||
macOS 11.0.1 */
|
||||
for (GCController *controller in [GCController controllers]) {
|
||||
|
|
|
@ -1147,7 +1147,8 @@ SDL_DINPUT_JoystickQuit(void)
|
|||
}
|
||||
|
||||
if (coinitialized) {
|
||||
WIN_CoUninitialize();
|
||||
/* Workaround for CoUninitialize() crash in NotifyInitializeSpied() */
|
||||
/*WIN_CoUninitialize();*/
|
||||
coinitialized = SDL_FALSE;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -657,7 +657,8 @@ RAWINPUT_QuitWindowsGamingInput(RAWINPUT_DeviceContext *ctx)
|
|||
__x_ABI_CWindows_CGaming_CInput_CIGamepadStatics_Release(wgi_state.gamepad_statics);
|
||||
wgi_state.gamepad_statics = NULL;
|
||||
}
|
||||
WIN_CoUninitialize();
|
||||
/* Workaround for CoUninitialize() crash in NotifyInitializeSpied() */
|
||||
/*WIN_CoUninitialize();*/
|
||||
wgi_state.initialized = SDL_FALSE;
|
||||
}
|
||||
}
|
||||
|
@ -921,9 +922,12 @@ RAWINPUT_IsDevicePresent(Uint16 vendor_id, Uint16 product_id, Uint16 version, co
|
|||
return SDL_TRUE;
|
||||
}
|
||||
|
||||
/* The Xbox 360 wireless controller shows up as product 0 in WGI */
|
||||
/* The Xbox 360 wireless controller shows up as product 0 in WGI.
|
||||
Try to match it to a Raw Input device via name or known product ID. */
|
||||
if (vendor_id == device->vendor_id && product_id == 0 &&
|
||||
name && SDL_strstr(device->name, name) != NULL) {
|
||||
((name && SDL_strstr(device->name, name) != NULL) ||
|
||||
(device->vendor_id == USB_VENDOR_MICROSOFT &&
|
||||
device->product_id == USB_PRODUCT_XBOX360_XUSB_CONTROLLER))) {
|
||||
return SDL_TRUE;
|
||||
}
|
||||
|
||||
|
|
|
@ -256,7 +256,8 @@ SDL_CleanupDeviceNotification(SDL_DeviceNotificationData *data)
|
|||
UnregisterClass(data->wincl.lpszClassName, data->wincl.hInstance);
|
||||
|
||||
if (data->coinitialized == S_OK) {
|
||||
WIN_CoUninitialize();
|
||||
/* Workaround for CoUninitialize() crash in NotifyInitializeSpied() */
|
||||
/*WIN_CoUninitialize();*/
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -71,7 +71,9 @@ typedef struct
|
|||
IDirect3DSurface9 *defaultRenderTarget;
|
||||
IDirect3DSurface9 *currentRenderTarget;
|
||||
void* d3dxDLL;
|
||||
#if SDL_HAVE_YUV
|
||||
LPDIRECT3DPIXELSHADER9 shaders[NUM_SHADERS];
|
||||
#endif
|
||||
LPDIRECT3DVERTEXBUFFER9 vertexBuffers[8];
|
||||
size_t vertexBufferSize[8];
|
||||
int currentVertexBuffer;
|
||||
|
@ -95,6 +97,7 @@ typedef struct
|
|||
D3D_TextureRep texture;
|
||||
D3DTEXTUREFILTERTYPE scaleMode;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
/* YV12 texture support */
|
||||
SDL_bool yuv;
|
||||
D3D_TextureRep utexture;
|
||||
|
@ -102,6 +105,7 @@ typedef struct
|
|||
Uint8 *pixels;
|
||||
int pitch;
|
||||
SDL_Rect locked_rect;
|
||||
#endif
|
||||
} D3D_TextureData;
|
||||
|
||||
typedef struct
|
||||
|
@ -534,7 +538,7 @@ D3D_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
if (D3D_CreateTextureRep(data->device, &texturedata->texture, usage, texture->format, PixelFormatToD3DFMT(texture->format), texture->w, texture->h) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texture->format == SDL_PIXELFORMAT_YV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_IYUV) {
|
||||
texturedata->yuv = SDL_TRUE;
|
||||
|
@ -547,6 +551,7 @@ D3D_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -563,7 +568,7 @@ D3D_RecreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
if (D3D_RecreateTextureRep(data->device, &texturedata->texture) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata->yuv) {
|
||||
if (D3D_RecreateTextureRep(data->device, &texturedata->utexture) < 0) {
|
||||
return -1;
|
||||
|
@ -573,6 +578,7 @@ D3D_RecreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -590,7 +596,7 @@ D3D_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if (D3D_UpdateTextureRep(data->device, &texturedata->texture, rect->x, rect->y, rect->w, rect->h, pixels, pitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata->yuv) {
|
||||
/* Skip to the correct offset into the next texture */
|
||||
pixels = (const void*)((const Uint8*)pixels + rect->h * pitch);
|
||||
|
@ -605,6 +611,7 @@ D3D_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -647,7 +654,7 @@ D3D_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if (!texturedata) {
|
||||
return SDL_SetError("Texture is not currently available");
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
texturedata->locked_rect = *rect;
|
||||
|
||||
if (texturedata->yuv) {
|
||||
|
@ -663,7 +670,9 @@ D3D_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
(void *) ((Uint8 *) texturedata->pixels + rect->y * texturedata->pitch +
|
||||
rect->x * SDL_BYTESPERPIXEL(texture->format));
|
||||
*pitch = texturedata->pitch;
|
||||
} else {
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
RECT d3drect;
|
||||
D3DLOCKED_RECT locked;
|
||||
HRESULT result;
|
||||
|
@ -696,14 +705,17 @@ D3D_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
if (!texturedata) {
|
||||
return;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata->yuv) {
|
||||
const SDL_Rect *rect = &texturedata->locked_rect;
|
||||
void *pixels =
|
||||
(void *) ((Uint8 *) texturedata->pixels + rect->y * texturedata->pitch +
|
||||
rect->x * SDL_BYTESPERPIXEL(texture->format));
|
||||
D3D_UpdateTexture(renderer, texture, rect, pixels, texturedata->pitch);
|
||||
} else {
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
IDirect3DTexture9_UnlockRect(texturedata->texture.staging, 0);
|
||||
texturedata->texture.dirty = SDL_TRUE;
|
||||
if (data->drawstate.texture == texture) {
|
||||
|
@ -711,10 +723,6 @@ D3D_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
data->drawstate.shader = NULL;
|
||||
IDirect3DDevice9_SetPixelShader(data->device, NULL);
|
||||
IDirect3DDevice9_SetTexture(data->device, 0, NULL);
|
||||
if (texturedata->yuv) {
|
||||
IDirect3DDevice9_SetTexture(data->device, 1, NULL);
|
||||
IDirect3DDevice9_SetTexture(data->device, 2, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -946,7 +954,7 @@ SetupTextureState(D3D_RenderData *data, SDL_Texture * texture, LPDIRECT3DPIXELSH
|
|||
if (BindTextureRep(data->device, &texturedata->texture, 0) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata->yuv) {
|
||||
switch (SDL_GetYUVConversionModeForResolution(texture->w, texture->h)) {
|
||||
case SDL_YUV_CONVERSION_JPEG:
|
||||
|
@ -972,6 +980,7 @@ SetupTextureState(D3D_RenderData *data, SDL_Texture * texture, LPDIRECT3DPIXELSH
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -982,18 +991,22 @@ SetDrawState(D3D_RenderData *data, const SDL_RenderCommand *cmd)
|
|||
const SDL_BlendMode blend = cmd->data.draw.blend;
|
||||
|
||||
if (texture != data->drawstate.texture) {
|
||||
#if SDL_HAVE_YUV
|
||||
D3D_TextureData *oldtexturedata = data->drawstate.texture ? (D3D_TextureData *) data->drawstate.texture->driverdata : NULL;
|
||||
D3D_TextureData *newtexturedata = texture ? (D3D_TextureData *) texture->driverdata : NULL;
|
||||
#endif
|
||||
LPDIRECT3DPIXELSHADER9 shader = NULL;
|
||||
|
||||
/* disable any enabled textures we aren't going to use, let SetupTextureState() do the rest. */
|
||||
if (texture == NULL) {
|
||||
IDirect3DDevice9_SetTexture(data->device, 0, NULL);
|
||||
}
|
||||
#if SDL_HAVE_YUV
|
||||
if ((!newtexturedata || !newtexturedata->yuv) && (oldtexturedata && oldtexturedata->yuv)) {
|
||||
IDirect3DDevice9_SetTexture(data->device, 1, NULL);
|
||||
IDirect3DDevice9_SetTexture(data->device, 2, NULL);
|
||||
}
|
||||
#endif
|
||||
if (texture && SetupTextureState(data, texture, &shader) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
@ -1010,10 +1023,12 @@ SetDrawState(D3D_RenderData *data, const SDL_RenderCommand *cmd)
|
|||
} else if (texture) {
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *) texture->driverdata;
|
||||
UpdateDirtyTexture(data->device, &texturedata->texture);
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata->yuv) {
|
||||
UpdateDirtyTexture(data->device, &texturedata->utexture);
|
||||
UpdateDirtyTexture(data->device, &texturedata->vtexture);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (blend != data->drawstate.blend) {
|
||||
|
@ -1353,10 +1368,12 @@ D3D_DestroyTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
renderdata->drawstate.shader = NULL;
|
||||
IDirect3DDevice9_SetPixelShader(renderdata->device, NULL);
|
||||
IDirect3DDevice9_SetTexture(renderdata->device, 0, NULL);
|
||||
#if SDL_HAVE_YUV
|
||||
if (data->yuv) {
|
||||
IDirect3DDevice9_SetTexture(renderdata->device, 1, NULL);
|
||||
IDirect3DDevice9_SetTexture(renderdata->device, 2, NULL);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (!data) {
|
||||
|
@ -1364,9 +1381,11 @@ D3D_DestroyTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
}
|
||||
|
||||
D3D_DestroyTextureRep(&data->texture);
|
||||
#if SDL_HAVE_YUV
|
||||
D3D_DestroyTextureRep(&data->utexture);
|
||||
D3D_DestroyTextureRep(&data->vtexture);
|
||||
SDL_free(data->pixels);
|
||||
#endif
|
||||
SDL_free(data);
|
||||
texture->driverdata = NULL;
|
||||
}
|
||||
|
@ -1388,12 +1407,14 @@ D3D_DestroyRenderer(SDL_Renderer * renderer)
|
|||
IDirect3DSurface9_Release(data->currentRenderTarget);
|
||||
data->currentRenderTarget = NULL;
|
||||
}
|
||||
#if SDL_HAVE_YUV
|
||||
for (i = 0; i < SDL_arraysize(data->shaders); ++i) {
|
||||
if (data->shaders[i]) {
|
||||
IDirect3DPixelShader9_Release(data->shaders[i]);
|
||||
data->shaders[i] = NULL;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
/* Release all vertex buffers */
|
||||
for (i = 0; i < SDL_arraysize(data->vertexBuffers); ++i) {
|
||||
if (data->vertexBuffers[i]) {
|
||||
|
@ -1666,7 +1687,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
|
||||
/* Set up parameters for rendering */
|
||||
D3D_InitRenderState(data);
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (caps.MaxSimultaneousTextures >= 3) {
|
||||
int i;
|
||||
for (i = 0; i < SDL_arraysize(data->shaders); ++i) {
|
||||
|
@ -1680,7 +1701,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_IYUV;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
data->drawstate.blend = SDL_BLENDMODE_INVALID;
|
||||
|
||||
return renderer;
|
||||
|
|
|
@ -91,7 +91,7 @@ typedef struct
|
|||
int lockedTexturePositionX;
|
||||
int lockedTexturePositionY;
|
||||
D3D11_FILTER scaleMode;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
/* YV12 texture support */
|
||||
SDL_bool yuv;
|
||||
ID3D11Texture2D *mainTextureU;
|
||||
|
@ -107,6 +107,7 @@ typedef struct
|
|||
Uint8 *pixels;
|
||||
int pitch;
|
||||
SDL_Rect locked_rect;
|
||||
#endif
|
||||
} D3D11_TextureData;
|
||||
|
||||
/* Blend mode data */
|
||||
|
@ -1116,7 +1117,7 @@ D3D11_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
D3D11_DestroyTexture(renderer, texture);
|
||||
return WIN_SetErrorFromHRESULT(SDL_COMPOSE_ERROR("ID3D11Device1::CreateTexture2D"), result);
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texture->format == SDL_PIXELFORMAT_YV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_IYUV) {
|
||||
textureData->yuv = SDL_TRUE;
|
||||
|
@ -1165,7 +1166,7 @@ D3D11_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return WIN_SetErrorFromHRESULT(SDL_COMPOSE_ERROR("ID3D11Device1::CreateTexture2D"), result);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
resourceViewDesc.Format = textureDesc.Format;
|
||||
resourceViewDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
|
||||
resourceViewDesc.Texture2D.MostDetailedMip = 0;
|
||||
|
@ -1179,7 +1180,7 @@ D3D11_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
D3D11_DestroyTexture(renderer, texture);
|
||||
return WIN_SetErrorFromHRESULT(SDL_COMPOSE_ERROR("ID3D11Device1::CreateShaderResourceView"), result);
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (textureData->yuv) {
|
||||
result = ID3D11Device_CreateShaderResourceView(rendererData->d3dDevice,
|
||||
(ID3D11Resource *)textureData->mainTextureU,
|
||||
|
@ -1232,7 +1233,7 @@ D3D11_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return WIN_SetErrorFromHRESULT(SDL_COMPOSE_ERROR("ID3D11Device1::CreateRenderTargetView"), result);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1250,6 +1251,7 @@ D3D11_DestroyTexture(SDL_Renderer * renderer,
|
|||
SAFE_RELEASE(data->mainTextureResourceView);
|
||||
SAFE_RELEASE(data->mainTextureRenderTargetView);
|
||||
SAFE_RELEASE(data->stagingTexture);
|
||||
#if SDL_HAVE_YUV
|
||||
SAFE_RELEASE(data->mainTextureU);
|
||||
SAFE_RELEASE(data->mainTextureResourceViewU);
|
||||
SAFE_RELEASE(data->mainTextureV);
|
||||
|
@ -1257,6 +1259,7 @@ D3D11_DestroyTexture(SDL_Renderer * renderer,
|
|||
SAFE_RELEASE(data->mainTextureNV);
|
||||
SAFE_RELEASE(data->mainTextureResourceViewNV);
|
||||
SDL_free(data->pixels);
|
||||
#endif
|
||||
SDL_free(data);
|
||||
texture->driverdata = NULL;
|
||||
}
|
||||
|
@ -1357,7 +1360,7 @@ D3D11_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if (D3D11_UpdateTextureInternal(rendererData, textureData->mainTexture, SDL_BYTESPERPIXEL(texture->format), rect->x, rect->y, rect->w, rect->h, srcPixels, srcPitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (textureData->yuv) {
|
||||
/* Skip to the correct offset into the next texture */
|
||||
srcPixels = (const void*)((const Uint8*)srcPixels + rect->h * srcPitch);
|
||||
|
@ -1381,6 +1384,7 @@ D3D11_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1448,7 +1452,7 @@ D3D11_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if (!textureData) {
|
||||
return SDL_SetError("Texture is not currently available");
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (textureData->yuv || textureData->nv12) {
|
||||
/* It's more efficient to upload directly... */
|
||||
if (!textureData->pixels) {
|
||||
|
@ -1465,7 +1469,7 @@ D3D11_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
*pitch = textureData->pitch;
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
if (textureData->stagingTexture) {
|
||||
return SDL_SetError("texture is already locked");
|
||||
}
|
||||
|
@ -1529,7 +1533,7 @@ D3D11_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
if (!textureData) {
|
||||
return;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (textureData->yuv || textureData->nv12) {
|
||||
const SDL_Rect *rect = &textureData->locked_rect;
|
||||
void *pixels =
|
||||
|
@ -1538,7 +1542,7 @@ D3D11_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
D3D11_UpdateTexture(renderer, texture, rect, pixels, textureData->pitch);
|
||||
return;
|
||||
}
|
||||
|
||||
#endif
|
||||
/* Commit the pixel buffer's changes back to the staging texture: */
|
||||
ID3D11DeviceContext_Unmap(rendererData->d3dContext,
|
||||
(ID3D11Resource *)textureData->stagingTexture,
|
||||
|
@ -1981,7 +1985,7 @@ D3D11_SetCopyState(SDL_Renderer * renderer, const SDL_RenderCommand *cmd, const
|
|||
default:
|
||||
return SDL_SetError("Unknown scale mode: %d\n", textureData->scaleMode);
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (textureData->yuv) {
|
||||
ID3D11ShaderResourceView *shaderResources[] = {
|
||||
textureData->mainTextureResourceView,
|
||||
|
@ -2032,7 +2036,7 @@ D3D11_SetCopyState(SDL_Renderer * renderer, const SDL_RenderCommand *cmd, const
|
|||
SDL_arraysize(shaderResources), shaderResources, textureSampler, matrix);
|
||||
|
||||
}
|
||||
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
return D3D11_SetDrawState(renderer, cmd, rendererData->pixelShaders[SHADER_RGB],
|
||||
1, &textureData->mainTextureResourceView, textureSampler, matrix);
|
||||
}
|
||||
|
@ -2341,6 +2345,7 @@ D3D11_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
|
||||
data = (D3D11_RenderData *) SDL_calloc(1, sizeof(*data));
|
||||
if (!data) {
|
||||
SDL_free(renderer);
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -1886,9 +1886,10 @@ static struct
|
|||
{
|
||||
const void *shader_data;
|
||||
SIZE_T shader_size;
|
||||
} D3D11_shaders[] = {
|
||||
} D3D11_shaders[NUM_SHADERS] = {
|
||||
{ D3D11_PixelShader_Colors, sizeof(D3D11_PixelShader_Colors) },
|
||||
{ D3D11_PixelShader_Textures, sizeof(D3D11_PixelShader_Textures) },
|
||||
#if SDL_HAVE_YUV
|
||||
{ D3D11_PixelShader_YUV_JPEG, sizeof(D3D11_PixelShader_YUV_JPEG) },
|
||||
{ D3D11_PixelShader_YUV_BT601, sizeof(D3D11_PixelShader_YUV_BT601) },
|
||||
{ D3D11_PixelShader_YUV_BT709, sizeof(D3D11_PixelShader_YUV_BT709) },
|
||||
|
@ -1898,6 +1899,7 @@ static struct
|
|||
{ D3D11_PixelShader_NV21_JPEG, sizeof(D3D11_PixelShader_NV21_JPEG) },
|
||||
{ D3D11_PixelShader_NV21_BT601, sizeof(D3D11_PixelShader_NV21_BT601) },
|
||||
{ D3D11_PixelShader_NV21_BT709, sizeof(D3D11_PixelShader_NV21_BT709) },
|
||||
#endif
|
||||
};
|
||||
|
||||
int D3D11_CreateVertexShader(ID3D11Device1 *d3dDevice, ID3D11VertexShader **vertexShader, ID3D11InputLayout **inputLayout)
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
typedef enum {
|
||||
SHADER_SOLID,
|
||||
SHADER_RGB,
|
||||
#if SDL_HAVE_YUV
|
||||
SHADER_YUV_JPEG,
|
||||
SHADER_YUV_BT601,
|
||||
SHADER_YUV_BT709,
|
||||
|
@ -34,6 +35,7 @@ typedef enum {
|
|||
SHADER_NV21_JPEG,
|
||||
SHADER_NV21_BT601,
|
||||
SHADER_NV21_BT709,
|
||||
#endif
|
||||
NUM_SHADERS
|
||||
} D3D11_Shader;
|
||||
|
||||
|
|
|
@ -167,11 +167,12 @@ typedef struct METAL_ShaderPipelines
|
|||
@property (nonatomic, retain) id<MTLTexture> mtltexture_uv;
|
||||
@property (nonatomic, retain) id<MTLSamplerState> mtlsampler;
|
||||
@property (nonatomic, assign) SDL_MetalFragmentFunction fragmentFunction;
|
||||
#if SDL_HAVE_YUV
|
||||
@property (nonatomic, assign) BOOL yuv;
|
||||
@property (nonatomic, assign) BOOL nv12;
|
||||
@property (nonatomic, assign) size_t conversionBufferOffset;
|
||||
#endif
|
||||
@property (nonatomic, assign) BOOL hasdata;
|
||||
|
||||
@property (nonatomic, retain) id<MTLBuffer> lockedbuffer;
|
||||
@property (nonatomic, assign) SDL_Rect lockedrect;
|
||||
@end
|
||||
|
@ -605,14 +606,14 @@ METAL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
mtltexdesc.usage = MTLTextureUsageShaderRead;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
id<MTLTexture> mtltexture = [data.mtldevice newTextureWithDescriptor:mtltexdesc];
|
||||
if (mtltexture == nil) {
|
||||
return SDL_SetError("Texture allocation failed");
|
||||
}
|
||||
|
||||
id<MTLTexture> mtltexture_uv = nil;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
BOOL yuv = (texture->format == SDL_PIXELFORMAT_IYUV) || (texture->format == SDL_PIXELFORMAT_YV12);
|
||||
BOOL nv12 = (texture->format == SDL_PIXELFORMAT_NV12) || (texture->format == SDL_PIXELFORMAT_NV21);
|
||||
|
||||
|
@ -637,7 +638,7 @@ METAL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return SDL_SetError("Texture allocation failed");
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
METAL_TextureData *texturedata = [[METAL_TextureData alloc] init];
|
||||
if (texture->scaleMode == SDL_ScaleModeNearest) {
|
||||
texturedata.mtlsampler = data.mtlsamplernearest;
|
||||
|
@ -646,7 +647,7 @@ METAL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
}
|
||||
texturedata.mtltexture = mtltexture;
|
||||
texturedata.mtltexture_uv = mtltexture_uv;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
texturedata.yuv = yuv;
|
||||
texturedata.nv12 = nv12;
|
||||
|
||||
|
@ -656,10 +657,12 @@ METAL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
texturedata.fragmentFunction = SDL_METAL_FRAGMENT_NV12;
|
||||
} else if (texture->format == SDL_PIXELFORMAT_NV21) {
|
||||
texturedata.fragmentFunction = SDL_METAL_FRAGMENT_NV21;
|
||||
} else {
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
texturedata.fragmentFunction = SDL_METAL_FRAGMENT_COPY;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (yuv || nv12) {
|
||||
size_t offset = 0;
|
||||
SDL_YUV_CONVERSION_MODE mode = SDL_GetYUVConversionModeForResolution(texture->w, texture->h);
|
||||
|
@ -671,7 +674,7 @@ METAL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
}
|
||||
texturedata.conversionBufferOffset = offset;
|
||||
}
|
||||
|
||||
#endif
|
||||
texture->driverdata = (void*)CFBridgingRetain(texturedata);
|
||||
|
||||
#if !__has_feature(objc_arc)
|
||||
|
@ -785,7 +788,7 @@ METAL_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if (METAL_UpdateTextureInternal(renderer, texturedata, texturedata.mtltexture, *rect, 0, pixels, pitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata.yuv) {
|
||||
int Uslice = texture->format == SDL_PIXELFORMAT_YV12 ? 1 : 0;
|
||||
int Vslice = texture->format == SDL_PIXELFORMAT_YV12 ? 0 : 1;
|
||||
|
@ -815,7 +818,7 @@ METAL_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
texturedata.hasdata = YES;
|
||||
|
||||
return 0;
|
||||
|
@ -896,10 +899,12 @@ METAL_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
}
|
||||
|
||||
*pitch = SDL_BYTESPERPIXEL(texture->format) * rect->w;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata.yuv || texturedata.nv12) {
|
||||
buffersize = ((*pitch) * rect->h) + (2 * (*pitch + 1) / 2) * ((rect->h + 1) / 2);
|
||||
} else {
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
buffersize = (*pitch) * rect->h;
|
||||
}
|
||||
|
||||
|
@ -953,7 +958,7 @@ METAL_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
destinationSlice:0
|
||||
destinationLevel:0
|
||||
destinationOrigin:MTLOriginMake(rect.x, rect.y, 0)];
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata.yuv) {
|
||||
int Uslice = texture->format == SDL_PIXELFORMAT_YV12 ? 1 : 0;
|
||||
int Vslice = texture->format == SDL_PIXELFORMAT_YV12 ? 0 : 1;
|
||||
|
@ -993,7 +998,7 @@ METAL_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
destinationLevel:0
|
||||
destinationOrigin:MTLOriginMake(UVrect.x, UVrect.y, 0)];
|
||||
}
|
||||
|
||||
#endif
|
||||
[blitcmd endEncoding];
|
||||
|
||||
[data.mtlcmdbuffer commit];
|
||||
|
@ -1313,10 +1318,12 @@ SetCopyState(SDL_Renderer *renderer, const SDL_RenderCommand *cmd, const size_t
|
|||
}
|
||||
|
||||
[data.mtlcmdencoder setFragmentTexture:texturedata.mtltexture atIndex:0];
|
||||
#if SDL_HAVE_YUV
|
||||
if (texturedata.yuv || texturedata.nv12) {
|
||||
[data.mtlcmdencoder setFragmentTexture:texturedata.mtltexture_uv atIndex:1];
|
||||
[data.mtlcmdencoder setFragmentBuffer:data.mtlbufconstants offset:texturedata.conversionBufferOffset atIndex:1];
|
||||
}
|
||||
#endif
|
||||
statecache->texture = texture;
|
||||
}
|
||||
return SDL_TRUE;
|
||||
|
|
|
@ -1690,6 +1690,32 @@ GL_SetVSync(SDL_Renderer * renderer, const int vsync)
|
|||
return retval;
|
||||
}
|
||||
|
||||
static SDL_bool
|
||||
GL_IsProbablyAccelerated(const GL_RenderData *data)
|
||||
{
|
||||
/*const char *vendor = (const char *) data->glGetString(GL_VENDOR);*/
|
||||
const char *renderer = (const char *) data->glGetString(GL_RENDERER);
|
||||
|
||||
#ifdef __WINDOWS__
|
||||
if (SDL_strcmp(renderer, "GDI Generic") == 0) {
|
||||
return SDL_FALSE; /* Microsoft's fallback software renderer. Fix your system! */
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef __APPLE__
|
||||
if (SDL_strcmp(renderer, "Apple Software Renderer") == 0) {
|
||||
return SDL_FALSE; /* (a probably very old) Apple software-based OpenGL. */
|
||||
}
|
||||
#endif
|
||||
|
||||
if (SDL_strcmp(renderer, "Software Rasterizer") == 0) {
|
||||
return SDL_FALSE; /* (a probably very old) Software Mesa, or some other generic thing. */
|
||||
}
|
||||
|
||||
/* !!! FIXME: swrast? llvmpipe? softpipe? */
|
||||
|
||||
return SDL_TRUE;
|
||||
}
|
||||
|
||||
static SDL_Renderer *
|
||||
GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
||||
|
@ -1700,6 +1726,8 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
Uint32 window_flags;
|
||||
int profile_mask = 0, major = 0, minor = 0;
|
||||
SDL_bool changed_window = SDL_FALSE;
|
||||
const char *hint;
|
||||
SDL_bool non_power_of_two_supported = SDL_FALSE;
|
||||
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, &profile_mask);
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, &major);
|
||||
|
@ -1758,7 +1786,7 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
renderer->GL_BindTexture = GL_BindTexture;
|
||||
renderer->GL_UnbindTexture = GL_UnbindTexture;
|
||||
renderer->info = GL_RenderDriver.info;
|
||||
renderer->info.flags = SDL_RENDERER_ACCELERATED;
|
||||
renderer->info.flags = 0; /* will set some flags below. */
|
||||
renderer->driverdata = data;
|
||||
renderer->window = window;
|
||||
|
||||
|
@ -1782,6 +1810,10 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
goto error;
|
||||
}
|
||||
|
||||
if (GL_IsProbablyAccelerated(data)) {
|
||||
renderer->info.flags |= SDL_RENDERER_ACCELERATED;
|
||||
}
|
||||
|
||||
#ifdef __MACOSX__
|
||||
/* Enable multi-threaded rendering */
|
||||
/* Disabled until Ryan finishes his VBO/PBO code...
|
||||
|
@ -1815,15 +1847,37 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
data->glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS_ARB);
|
||||
}
|
||||
|
||||
hint = SDL_getenv("GL_ARB_texture_non_power_of_two");
|
||||
if (!hint || *hint != '0') {
|
||||
SDL_bool isGL2 = SDL_FALSE;
|
||||
const char *verstr = (const char *)data->glGetString(GL_VERSION);
|
||||
if (verstr) {
|
||||
char verbuf[16];
|
||||
char *ptr;
|
||||
SDL_strlcpy(verbuf, verstr, sizeof (verbuf));
|
||||
ptr = SDL_strchr(verbuf, '.');
|
||||
if (ptr) {
|
||||
*ptr = '\0';
|
||||
if (SDL_atoi(verbuf) >= 2) {
|
||||
isGL2 = SDL_TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (isGL2 || SDL_GL_ExtensionSupported("GL_ARB_texture_non_power_of_two")) {
|
||||
non_power_of_two_supported = SDL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
data->textype = GL_TEXTURE_2D;
|
||||
if (SDL_GL_ExtensionSupported("GL_ARB_texture_non_power_of_two")) {
|
||||
if (non_power_of_two_supported) {
|
||||
data->GL_ARB_texture_non_power_of_two_supported = SDL_TRUE;
|
||||
data->glGetIntegerv(GL_MAX_TEXTURE_SIZE, &value);
|
||||
renderer->info.max_texture_width = value;
|
||||
renderer->info.max_texture_height = value;
|
||||
} else if (SDL_GL_ExtensionSupported("GL_ARB_texture_rectangle") ||
|
||||
SDL_GL_ExtensionSupported("GL_EXT_texture_rectangle")) {
|
||||
data->GL_ARB_texture_rectangle_supported = SDL_TRUE;
|
||||
data->textype = GL_TEXTURE_RECTANGLE_ARB;
|
||||
}
|
||||
if (data->GL_ARB_texture_rectangle_supported) {
|
||||
data->glGetIntegerv(GL_MAX_RECTANGLE_TEXTURE_SIZE_ARB, &value);
|
||||
renderer->info.max_texture_width = value;
|
||||
renderer->info.max_texture_height = value;
|
||||
|
@ -1848,7 +1902,7 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
}
|
||||
SDL_LogInfo(SDL_LOG_CATEGORY_RENDER, "OpenGL shaders: %s",
|
||||
data->shaders ? "ENABLED" : "DISABLED");
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
/* We support YV12 textures using 3 textures and a shader */
|
||||
if (data->shaders && data->num_texture_units >= 3) {
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_YV12;
|
||||
|
@ -1856,7 +1910,7 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV12;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV21;
|
||||
}
|
||||
|
||||
#endif
|
||||
#ifdef __MACOSX__
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_UYVY;
|
||||
#endif
|
||||
|
|
|
@ -284,7 +284,7 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
" gl_FragColor = texture2D(tex0, v_texCoord) * v_color;\n"
|
||||
"}"
|
||||
},
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
/* SHADER_YUV_JPEG */
|
||||
{
|
||||
/* vertex shader */
|
||||
|
@ -384,6 +384,7 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
BT709_SHADER_CONSTANTS
|
||||
NV21_SHADER_BODY
|
||||
},
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
};
|
||||
|
||||
static SDL_bool
|
||||
|
|
|
@ -32,6 +32,7 @@ typedef enum {
|
|||
SHADER_SOLID,
|
||||
SHADER_RGB,
|
||||
SHADER_RGBA,
|
||||
#if SDL_HAVE_YUV
|
||||
SHADER_YUV_JPEG,
|
||||
SHADER_YUV_BT601,
|
||||
SHADER_YUV_BT709,
|
||||
|
@ -43,6 +44,7 @@ typedef enum {
|
|||
SHADER_NV21_JPEG,
|
||||
SHADER_NV21_BT601,
|
||||
SHADER_NV21_BT709,
|
||||
#endif
|
||||
NUM_SHADERS
|
||||
} GL_Shader;
|
||||
|
||||
|
|
|
@ -561,6 +561,7 @@ GLES2_SelectProgram(GLES2_RenderData *data, GLES2_ImageSource source, int w, int
|
|||
case GLES2_IMAGESOURCE_TEXTURE_BGR:
|
||||
ftype = GLES2_SHADER_FRAGMENT_TEXTURE_BGR;
|
||||
break;
|
||||
#if SDL_HAVE_YUV
|
||||
case GLES2_IMAGESOURCE_TEXTURE_YUV:
|
||||
switch (SDL_GetYUVConversionModeForResolution(w, h)) {
|
||||
case SDL_YUV_CONVERSION_JPEG:
|
||||
|
@ -617,6 +618,7 @@ GLES2_SelectProgram(GLES2_RenderData *data, GLES2_ImageSource source, int w, int
|
|||
goto fault;
|
||||
}
|
||||
break;
|
||||
#endif /* SDL_HAVE_YUV */
|
||||
case GLES2_IMAGESOURCE_TEXTURE_EXTERNAL_OES:
|
||||
ftype = GLES2_SHADER_FRAGMENT_TEXTURE_EXTERNAL_OES;
|
||||
break;
|
||||
|
@ -1018,6 +1020,7 @@ SetCopyState(SDL_Renderer *renderer, const SDL_RenderCommand *cmd, void *vertice
|
|||
break;
|
||||
}
|
||||
break;
|
||||
#if SDL_HAVE_YUV
|
||||
case SDL_PIXELFORMAT_IYUV:
|
||||
case SDL_PIXELFORMAT_YV12:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_YUV;
|
||||
|
@ -1028,6 +1031,7 @@ SetCopyState(SDL_Renderer *renderer, const SDL_RenderCommand *cmd, void *vertice
|
|||
case SDL_PIXELFORMAT_NV21:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_NV21;
|
||||
break;
|
||||
#endif
|
||||
case SDL_PIXELFORMAT_EXTERNAL_OES:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_EXTERNAL_OES;
|
||||
break;
|
||||
|
@ -1051,6 +1055,7 @@ SetCopyState(SDL_Renderer *renderer, const SDL_RenderCommand *cmd, void *vertice
|
|||
case SDL_PIXELFORMAT_BGR888:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_BGR;
|
||||
break;
|
||||
#if SDL_HAVE_YUV
|
||||
case SDL_PIXELFORMAT_IYUV:
|
||||
case SDL_PIXELFORMAT_YV12:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_YUV;
|
||||
|
@ -1061,6 +1066,7 @@ SetCopyState(SDL_Renderer *renderer, const SDL_RenderCommand *cmd, void *vertice
|
|||
case SDL_PIXELFORMAT_NV21:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_NV21;
|
||||
break;
|
||||
#endif
|
||||
case SDL_PIXELFORMAT_EXTERNAL_OES:
|
||||
sourceType = GLES2_IMAGESOURCE_TEXTURE_EXTERNAL_OES;
|
||||
break;
|
||||
|
@ -1364,6 +1370,7 @@ GLES2_CreateTexture(SDL_Renderer *renderer, SDL_Texture *texture)
|
|||
format = GL_RGBA;
|
||||
type = GL_UNSIGNED_BYTE;
|
||||
break;
|
||||
#if SDL_HAVE_YUV
|
||||
case SDL_PIXELFORMAT_IYUV:
|
||||
case SDL_PIXELFORMAT_YV12:
|
||||
case SDL_PIXELFORMAT_NV12:
|
||||
|
@ -1371,6 +1378,7 @@ GLES2_CreateTexture(SDL_Renderer *renderer, SDL_Texture *texture)
|
|||
format = GL_LUMINANCE;
|
||||
type = GL_UNSIGNED_BYTE;
|
||||
break;
|
||||
#endif
|
||||
#ifdef GL_TEXTURE_EXTERNAL_OES
|
||||
case SDL_PIXELFORMAT_EXTERNAL_OES:
|
||||
format = GL_NONE;
|
||||
|
@ -2129,11 +2137,12 @@ GLES2_CreateRenderer(SDL_Window *window, Uint32 flags)
|
|||
renderer->SetVSync = GLES2_SetVSync;
|
||||
renderer->GL_BindTexture = GLES2_BindTexture;
|
||||
renderer->GL_UnbindTexture = GLES2_UnbindTexture;
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_YV12;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_IYUV;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV12;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV21;
|
||||
#endif
|
||||
#ifdef GL_TEXTURE_EXTERNAL_OES
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_EXTERNAL_OES;
|
||||
#endif
|
||||
|
|
|
@ -121,6 +121,8 @@ static const Uint8 GLES2_Fragment_TextureBGR[] = " \
|
|||
} \
|
||||
";
|
||||
|
||||
#if SDL_HAVE_YUV
|
||||
|
||||
#define JPEG_SHADER_CONSTANTS \
|
||||
"// YUV offset \n" \
|
||||
"const vec3 offset = vec3(0, -0.501960814, -0.501960814);\n" \
|
||||
|
@ -299,6 +301,7 @@ static const Uint8 GLES2_Fragment_TextureNV21BT709[] = \
|
|||
BT709_SHADER_CONSTANTS \
|
||||
NV21_SHADER_BODY \
|
||||
;
|
||||
#endif
|
||||
|
||||
/* Custom Android video format texture */
|
||||
static const Uint8 GLES2_Fragment_TextureExternalOES[] = " \
|
||||
|
@ -335,6 +338,7 @@ const Uint8 *GLES2_GetShader(GLES2_ShaderType type)
|
|||
return GLES2_Fragment_TextureRGB;
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_BGR:
|
||||
return GLES2_Fragment_TextureBGR;
|
||||
#if SDL_HAVE_YUV
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_YUV_JPEG:
|
||||
return GLES2_Fragment_TextureYUVJPEG;
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_YUV_BT601:
|
||||
|
@ -357,6 +361,7 @@ const Uint8 *GLES2_GetShader(GLES2_ShaderType type)
|
|||
return GLES2_Fragment_TextureNV21BT601;
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_NV21_BT709:
|
||||
return GLES2_Fragment_TextureNV21BT709;
|
||||
#endif
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_EXTERNAL_OES:
|
||||
return GLES2_Fragment_TextureExternalOES;
|
||||
default:
|
||||
|
|
|
@ -34,6 +34,7 @@ typedef enum
|
|||
GLES2_SHADER_FRAGMENT_TEXTURE_ARGB,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_BGR,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_RGB,
|
||||
#if SDL_HAVE_YUV
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_YUV_JPEG,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_YUV_BT601,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_YUV_BT709,
|
||||
|
@ -45,6 +46,7 @@ typedef enum
|
|||
GLES2_SHADER_FRAGMENT_TEXTURE_NV21_JPEG,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_NV21_BT601,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_NV21_BT709,
|
||||
#endif
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_EXTERNAL_OES,
|
||||
GLES2_SHADER_COUNT
|
||||
} GLES2_ShaderType;
|
||||
|
|
|
@ -139,11 +139,11 @@ SDLgfx_rotozoomSurfaceSizeTrig(int width, int height, double angle, const SDL_FP
|
|||
rotate(0.5, height - 0.5, sinangle, cosangle, center, &x2, &y2);
|
||||
rotate(width - 0.5, height - 0.5, sinangle, cosangle, center, &x3, &y3);
|
||||
|
||||
minx = SDL_floor( SDL_min( SDL_min(x0, x1), SDL_min(x2, x3) ) );
|
||||
maxx = SDL_ceil( SDL_max( SDL_max(x0, x1), SDL_max(x2, x3) ) );
|
||||
minx = (int)SDL_floor( SDL_min( SDL_min(x0, x1), SDL_min(x2, x3) ) );
|
||||
maxx = (int)SDL_ceil( SDL_max( SDL_max(x0, x1), SDL_max(x2, x3) ) );
|
||||
|
||||
miny = SDL_floor( SDL_min( SDL_min(y0, y1), SDL_min(y2, y3) ) );
|
||||
maxy = SDL_ceil( SDL_max( SDL_max(y0, y1), SDL_max(y2, y3) ) );
|
||||
miny = (int)SDL_floor( SDL_min( SDL_min(y0, y1), SDL_min(y2, y3) ) );
|
||||
maxy = (int)SDL_ceil( SDL_max( SDL_max(y0, y1), SDL_max(y2, y3) ) );
|
||||
|
||||
rect_dest->w = maxx - minx;
|
||||
rect_dest->h = maxy - miny;
|
||||
|
@ -249,6 +249,7 @@ Assumes dst surface was allocated with the correct dimensions.
|
|||
\param flipx Flag indicating horizontal mirroring should be applied.
|
||||
\param flipy Flag indicating vertical mirroring should be applied.
|
||||
\param smooth Flag indicating anti-aliasing should be used.
|
||||
\param dst_rect destination coordinates
|
||||
\param center true center.
|
||||
*/
|
||||
static void
|
||||
|
@ -283,8 +284,8 @@ transformSurfaceRGBA(SDL_Surface * src, SDL_Surface * dst, int isin, int icos,
|
|||
int x;
|
||||
double src_x = (rect_dest->x + 0 + 0.5 - center->x);
|
||||
double src_y = (rect_dest->y + y + 0.5 - center->y);
|
||||
int sdx = (icos * src_x - isin * src_y) + cx - fp_half;
|
||||
int sdy = (isin * src_x + icos * src_y) + cy - fp_half;
|
||||
int sdx = (int)((icos * src_x - isin * src_y) + cx - fp_half);
|
||||
int sdy = (int)((isin * src_x + icos * src_y) + cy - fp_half);
|
||||
for (x = 0; x < dst->w; x++) {
|
||||
int dx = (sdx >> 16);
|
||||
int dy = (sdy >> 16);
|
||||
|
@ -339,8 +340,8 @@ transformSurfaceRGBA(SDL_Surface * src, SDL_Surface * dst, int isin, int icos,
|
|||
int x;
|
||||
double src_x = (rect_dest->x + 0 + 0.5 - center->x);
|
||||
double src_y = (rect_dest->y + y + 0.5 - center->y);
|
||||
int sdx = (icos * src_x - isin * src_y) + cx - fp_half;
|
||||
int sdy = (isin * src_x + icos * src_y) + cy - fp_half;
|
||||
int sdx = (int)((icos * src_x - isin * src_y) + cx - fp_half);
|
||||
int sdy = (int)((isin * src_x + icos * src_y) + cy - fp_half);
|
||||
for (x = 0; x < dst->w; x++) {
|
||||
int dx = (sdx >> 16);
|
||||
int dy = (sdy >> 16);
|
||||
|
@ -369,29 +370,35 @@ Assumes dst surface was allocated with the correct dimensions.
|
|||
|
||||
\param src Source surface.
|
||||
\param dst Destination surface.
|
||||
\param cx Horizontal center coordinate.
|
||||
\param cy Vertical center coordinate.
|
||||
\param isin Integer version of sine of angle.
|
||||
\param icos Integer version of cosine of angle.
|
||||
\param flipx Flag indicating horizontal mirroring should be applied.
|
||||
\param flipy Flag indicating vertical mirroring should be applied.
|
||||
\param dst_rect destination coordinates
|
||||
\param center true center.
|
||||
*/
|
||||
static void
|
||||
transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int isin, int icos, int flipx, int flipy)
|
||||
transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int isin, int icos, int flipx, int flipy,
|
||||
const SDL_Rect *rect_dest,
|
||||
const SDL_FPoint *center)
|
||||
{
|
||||
int x, y, dx, dy, xd, yd, sdx, sdy, ax, ay;
|
||||
int sw, sh;
|
||||
int cx, cy;
|
||||
tColorY *pc;
|
||||
int gap;
|
||||
const int fp_half = (1<<15);
|
||||
int y;
|
||||
|
||||
/*
|
||||
* Variable setup
|
||||
*/
|
||||
xd = ((src->w - dst->w) << 15);
|
||||
yd = ((src->h - dst->h) << 15);
|
||||
ax = (cx << 16) - (icos * cx);
|
||||
ay = (cy << 16) - (isin * cx);
|
||||
sw = src->w - 1;
|
||||
sh = src->h - 1;
|
||||
pc = (tColorY*) dst->pixels;
|
||||
gap = dst->pitch - dst->w;
|
||||
cx = (int)(center->x * 65536.0);
|
||||
cy = (int)(center->y * 65536.0);
|
||||
|
||||
/*
|
||||
* Clear surface to colorkey
|
||||
*/
|
||||
|
@ -400,15 +407,17 @@ transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int isin
|
|||
* Iterate through destination surface
|
||||
*/
|
||||
for (y = 0; y < dst->h; y++) {
|
||||
dy = cy - y;
|
||||
sdx = (ax + (isin * dy)) + xd;
|
||||
sdy = (ay - (icos * dy)) + yd;
|
||||
int x;
|
||||
double src_x = (rect_dest->x + 0 + 0.5 - center->x);
|
||||
double src_y = (rect_dest->y + y + 0.5 - center->y);
|
||||
int sdx = (int)((icos * src_x - isin * src_y) + cx - fp_half);
|
||||
int sdy = (int)((isin * src_x + icos * src_y) + cy - fp_half);
|
||||
for (x = 0; x < dst->w; x++) {
|
||||
dx = (sdx >> 16);
|
||||
dy = (sdy >> 16);
|
||||
int dx = (sdx >> 16);
|
||||
int dy = (sdy >> 16);
|
||||
if ((unsigned)dx < (unsigned)src->w && (unsigned)dy < (unsigned)src->h) {
|
||||
if (flipx) dx = (src->w-1)-dx;
|
||||
if (flipy) dy = (src->h-1)-dy;
|
||||
if (flipx) dx = sw - dx;
|
||||
if (flipy) dy = sh- dy;
|
||||
*pc = *((tColorY *)src->pixels + src->pitch * dy + dx);
|
||||
}
|
||||
sdx += icos;
|
||||
|
@ -424,7 +433,7 @@ transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int isin
|
|||
\brief Rotates and zooms a surface with different horizontal and vertival scaling factors and optional anti-aliasing.
|
||||
|
||||
Rotates a 32-bit or 8-bit 'src' surface to newly created 'dst' surface.
|
||||
'angle' is the rotation in degrees, 'centerx' and 'centery' the rotation center. If 'smooth' is set
|
||||
'angle' is the rotation in degrees, 'center' the rotation center. If 'smooth' is set
|
||||
then the destination 32-bit surface is anti-aliased. 8-bit surfaces must have a colorkey. 32-bit
|
||||
surfaces must have a 8888 layout with red, green, blue and alpha masks (any ordering goes).
|
||||
The blend mode of the 'src' surface has some effects on generation of the 'dst' surface: The NONE
|
||||
|
@ -467,7 +476,6 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int smooth, int flipx, int
|
|||
colorKeyAvailable = SDL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
/* This function requires a 32-bit surface or 8-bit surface with a colorkey */
|
||||
is8bit = src->format->BitsPerPixel == 8 && colorKeyAvailable;
|
||||
if (!(is8bit || (src->format->BitsPerPixel == 32 && src->format->Amask)))
|
||||
|
@ -481,12 +489,14 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int smooth, int flipx, int
|
|||
rz_dst = NULL;
|
||||
if (is8bit) {
|
||||
/* Target surface is 8 bit */
|
||||
rz_dst = SDL_CreateRGBSurface(0, rect_dest->w, rect_dest->h + GUARD_ROWS, 8, 0, 0, 0, 0);
|
||||
rz_dst = SDL_CreateRGBSurfaceWithFormat(0, rect_dest->w, rect_dest->h + GUARD_ROWS, 8, src->format->format);
|
||||
if (rz_dst != NULL) {
|
||||
for (i = 0; i < src->format->palette->ncolors; i++) {
|
||||
rz_dst->format->palette->colors[i] = src->format->palette->colors[i];
|
||||
if (src->format->palette) {
|
||||
for (i = 0; i < src->format->palette->ncolors; i++) {
|
||||
rz_dst->format->palette->colors[i] = src->format->palette->colors[i];
|
||||
}
|
||||
rz_dst->format->palette->ncolors = src->format->palette->ncolors;
|
||||
}
|
||||
rz_dst->format->palette->ncolors = src->format->palette->ncolors;
|
||||
}
|
||||
} else {
|
||||
/* Target surface is 32 bit with source RGBA ordering */
|
||||
|
@ -547,8 +557,8 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int smooth, int flipx, int
|
|||
if(angle90 >= 0) {
|
||||
transformSurfaceY90(src, rz_dst, angle90, flipx, flipy);
|
||||
} else {
|
||||
transformSurfaceY(src, rz_dst, rect_dest->w/2, rect_dest->h/2, (int)sangleinv, (int)cangleinv,
|
||||
flipx, flipy);
|
||||
transformSurfaceY(src, rz_dst, (int)sangleinv, (int)cangleinv,
|
||||
flipx, flipy, rect_dest, center);
|
||||
}
|
||||
} else {
|
||||
/* Call the 32-bit transformation routine to do the rotation */
|
||||
|
|
|
@ -217,7 +217,7 @@ VITA_GXM_CreateRenderer(SDL_Window *window, Uint32 flags)
|
|||
|
||||
data = (VITA_GXM_RenderData *) SDL_calloc(1, sizeof(VITA_GXM_RenderData));
|
||||
if (!data) {
|
||||
VITA_GXM_DestroyRenderer(renderer);
|
||||
SDL_free(renderer);
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
}
|
||||
|
@ -226,7 +226,9 @@ VITA_GXM_CreateRenderer(SDL_Window *window, Uint32 flags)
|
|||
renderer->SupportsBlendMode = VITA_GXM_SupportsBlendMode;
|
||||
renderer->CreateTexture = VITA_GXM_CreateTexture;
|
||||
renderer->UpdateTexture = VITA_GXM_UpdateTexture;
|
||||
#if SDL_HAVE_YUV
|
||||
renderer->UpdateTextureYUV = VITA_GXM_UpdateTextureYUV;
|
||||
#endif
|
||||
renderer->LockTexture = VITA_GXM_LockTexture;
|
||||
renderer->UnlockTexture = VITA_GXM_UnlockTexture;
|
||||
renderer->SetTextureScaleMode = VITA_GXM_SetTextureScaleMode;
|
||||
|
|
|
@ -641,19 +641,16 @@ SDL_utf8strlcpy(SDL_OUT_Z_CAP(dst_bytes) char *dst, const char *src, size_t dst_
|
|||
size_t bytes = SDL_min(src_bytes, dst_bytes - 1);
|
||||
size_t i = 0;
|
||||
unsigned char trailing_bytes = 0;
|
||||
if (bytes)
|
||||
{
|
||||
|
||||
if (bytes) {
|
||||
unsigned char c = (unsigned char)src[bytes - 1];
|
||||
if (UTF8_IsLeadByte(c))
|
||||
if (UTF8_IsLeadByte(c)) {
|
||||
--bytes;
|
||||
else if (UTF8_IsTrailingByte(c))
|
||||
{
|
||||
for (i = bytes - 1; i != 0; --i)
|
||||
{
|
||||
} else if (UTF8_IsTrailingByte(c)) {
|
||||
for (i = bytes - 1; i != 0; --i) {
|
||||
c = (unsigned char)src[i];
|
||||
trailing_bytes = UTF8_TrailingBytes(c);
|
||||
if (trailing_bytes)
|
||||
{
|
||||
if (trailing_bytes) {
|
||||
if (bytes - i != trailing_bytes + 1)
|
||||
bytes = i;
|
||||
|
||||
|
@ -664,6 +661,7 @@ SDL_utf8strlcpy(SDL_OUT_Z_CAP(dst_bytes) char *dst, const char *src, size_t dst_
|
|||
SDL_memcpy(dst, src, bytes);
|
||||
}
|
||||
dst[bytes] = '\0';
|
||||
|
||||
return bytes;
|
||||
}
|
||||
|
||||
|
|
|
@ -128,8 +128,6 @@ static VideoBootStrap *bootstrap[] = {
|
|||
NULL
|
||||
};
|
||||
|
||||
static SDL_VideoDevice *_this = NULL;
|
||||
|
||||
#define CHECK_WINDOW_MAGIC(window, retval) \
|
||||
if (!_this) { \
|
||||
SDL_UninitializedVideo(); \
|
||||
|
@ -172,129 +170,58 @@ typedef struct {
|
|||
int bytes_per_pixel;
|
||||
} SDL_WindowTextureData;
|
||||
|
||||
static SDL_bool
|
||||
ShouldUseTextureFramebuffer()
|
||||
{
|
||||
const char *hint;
|
||||
|
||||
/* If there's no native framebuffer support then there's no option */
|
||||
if (!_this->CreateWindowFramebuffer) {
|
||||
return SDL_TRUE;
|
||||
}
|
||||
|
||||
/* If this is the dummy driver there is no texture support */
|
||||
if (_this->is_dummy) {
|
||||
return SDL_FALSE;
|
||||
}
|
||||
|
||||
/* See if the user or application wants a specific behavior */
|
||||
hint = SDL_GetHint(SDL_HINT_FRAMEBUFFER_ACCELERATION);
|
||||
if (hint) {
|
||||
if (*hint == '0' || SDL_strcasecmp(hint, "false") == 0) {
|
||||
return SDL_FALSE;
|
||||
} else {
|
||||
return SDL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
/* Each platform has different performance characteristics */
|
||||
#if defined(__WIN32__)
|
||||
/* GDI BitBlt() is way faster than Direct3D dynamic textures right now.
|
||||
*/
|
||||
return SDL_FALSE;
|
||||
|
||||
#elif defined(__MACOSX__)
|
||||
/* Mac OS X uses OpenGL as the native fast path (for cocoa and X11) */
|
||||
return SDL_TRUE;
|
||||
|
||||
#elif defined(__LINUX__)
|
||||
/* Properly configured OpenGL drivers are faster than MIT-SHM */
|
||||
#if SDL_VIDEO_OPENGL
|
||||
/* Ugh, find a way to cache this value! */
|
||||
{
|
||||
SDL_Window *window;
|
||||
SDL_GLContext context;
|
||||
SDL_bool hasAcceleratedOpenGL = SDL_FALSE;
|
||||
|
||||
window = SDL_CreateWindow("OpenGL test", -32, -32, 32, 32, SDL_WINDOW_OPENGL|SDL_WINDOW_HIDDEN);
|
||||
if (window) {
|
||||
context = SDL_GL_CreateContext(window);
|
||||
if (context) {
|
||||
const GLubyte *(APIENTRY * glGetStringFunc) (GLenum);
|
||||
const char *vendor = NULL;
|
||||
|
||||
glGetStringFunc = SDL_GL_GetProcAddress("glGetString");
|
||||
if (glGetStringFunc) {
|
||||
vendor = (const char *) glGetStringFunc(GL_VENDOR);
|
||||
}
|
||||
/* Add more vendors here at will... */
|
||||
if (vendor &&
|
||||
(SDL_strstr(vendor, "ATI Technologies") ||
|
||||
SDL_strstr(vendor, "NVIDIA"))) {
|
||||
hasAcceleratedOpenGL = SDL_TRUE;
|
||||
}
|
||||
SDL_GL_DeleteContext(context);
|
||||
}
|
||||
SDL_DestroyWindow(window);
|
||||
}
|
||||
return hasAcceleratedOpenGL;
|
||||
}
|
||||
#elif SDL_VIDEO_OPENGL_ES || SDL_VIDEO_OPENGL_ES2
|
||||
/* Let's be optimistic about this! */
|
||||
return SDL_TRUE;
|
||||
#else
|
||||
return SDL_FALSE;
|
||||
#endif
|
||||
|
||||
#else
|
||||
/* Play it safe, assume that if there is a framebuffer driver that it's
|
||||
optimized for the current platform.
|
||||
*/
|
||||
return SDL_FALSE;
|
||||
#endif
|
||||
}
|
||||
|
||||
static int
|
||||
SDL_CreateWindowTexture(SDL_VideoDevice *unused, SDL_Window * window, Uint32 * format, void ** pixels, int *pitch)
|
||||
SDL_CreateWindowTexture(SDL_VideoDevice *_this, SDL_Window * window, Uint32 * format, void ** pixels, int *pitch)
|
||||
{
|
||||
SDL_WindowTextureData *data;
|
||||
SDL_RendererInfo info;
|
||||
SDL_WindowTextureData *data = SDL_GetWindowData(window, SDL_WINDOWTEXTUREDATA);
|
||||
int i;
|
||||
|
||||
data = SDL_GetWindowData(window, SDL_WINDOWTEXTUREDATA);
|
||||
if (!data) {
|
||||
SDL_Renderer *renderer = NULL;
|
||||
int i;
|
||||
const char *hint = SDL_GetHint(SDL_HINT_FRAMEBUFFER_ACCELERATION);
|
||||
|
||||
/* Check to see if there's a specific driver requested */
|
||||
if (hint && *hint != '0' && *hint != '1' &&
|
||||
const SDL_bool specific_accelerated_renderer = (
|
||||
hint && *hint != '0' && *hint != '1' &&
|
||||
SDL_strcasecmp(hint, "true") != 0 &&
|
||||
SDL_strcasecmp(hint, "false") != 0 &&
|
||||
SDL_strcasecmp(hint, "software") != 0) {
|
||||
SDL_strcasecmp(hint, "software") != 0
|
||||
);
|
||||
|
||||
/* Check to see if there's a specific driver requested */
|
||||
if (specific_accelerated_renderer) {
|
||||
for (i = 0; i < SDL_GetNumRenderDrivers(); ++i) {
|
||||
SDL_RendererInfo info;
|
||||
SDL_GetRenderDriverInfo(i, &info);
|
||||
if (SDL_strcasecmp(info.name, hint) == 0) {
|
||||
renderer = SDL_CreateRenderer(window, i, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!renderer) {
|
||||
if (!renderer || (SDL_GetRendererInfo(renderer, &info) == -1)) {
|
||||
if (renderer) { SDL_DestroyRenderer(renderer); }
|
||||
return SDL_SetError("Requested renderer for " SDL_HINT_FRAMEBUFFER_ACCELERATION " is not available");
|
||||
}
|
||||
/* if it was specifically requested, even if SDL_RENDERER_ACCELERATED isn't set, we'll accept this renderer. */
|
||||
} else {
|
||||
for (i = 0; i < SDL_GetNumRenderDrivers(); ++i) {
|
||||
SDL_RendererInfo info;
|
||||
SDL_GetRenderDriverInfo(i, &info);
|
||||
if (SDL_strcmp(info.name, "software") != 0) {
|
||||
renderer = SDL_CreateRenderer(window, i, 0);
|
||||
if (renderer) {
|
||||
break;
|
||||
if (renderer && (SDL_GetRendererInfo(renderer, &info) == 0) && (info.flags & SDL_RENDERER_ACCELERATED)) {
|
||||
break; /* this will work. */
|
||||
}
|
||||
if (renderer) { /* wasn't accelerated, etc, skip it. */
|
||||
SDL_DestroyRenderer(renderer);
|
||||
renderer = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!renderer) {
|
||||
return SDL_SetError("No hardware accelerated renderers available");
|
||||
}
|
||||
}
|
||||
if (!renderer) {
|
||||
return SDL_SetError("No hardware accelerated renderers available");
|
||||
}
|
||||
|
||||
SDL_assert(renderer != NULL); /* should have explicitly checked this above. */
|
||||
|
||||
/* Create the data after we successfully create the renderer (bug #1116) */
|
||||
data = (SDL_WindowTextureData *)SDL_calloc(1, sizeof(*data));
|
||||
|
@ -305,6 +232,10 @@ SDL_CreateWindowTexture(SDL_VideoDevice *unused, SDL_Window * window, Uint32 * f
|
|||
SDL_SetWindowData(window, SDL_WINDOWTEXTUREDATA, data);
|
||||
|
||||
data->renderer = renderer;
|
||||
} else {
|
||||
if (SDL_GetRendererInfo(data->renderer, &info) == -1) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Free any old texture and pixel data */
|
||||
|
@ -315,23 +246,14 @@ SDL_CreateWindowTexture(SDL_VideoDevice *unused, SDL_Window * window, Uint32 * f
|
|||
SDL_free(data->pixels);
|
||||
data->pixels = NULL;
|
||||
|
||||
{
|
||||
SDL_RendererInfo info;
|
||||
Uint32 i;
|
||||
/* Find the first format without an alpha channel */
|
||||
*format = info.texture_formats[0];
|
||||
|
||||
if (SDL_GetRendererInfo(data->renderer, &info) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Find the first format without an alpha channel */
|
||||
*format = info.texture_formats[0];
|
||||
|
||||
for (i = 0; i < info.num_texture_formats; ++i) {
|
||||
if (!SDL_ISPIXELFORMAT_FOURCC(info.texture_formats[i]) &&
|
||||
!SDL_ISPIXELFORMAT_ALPHA(info.texture_formats[i])) {
|
||||
*format = info.texture_formats[i];
|
||||
break;
|
||||
}
|
||||
for (i = 0; i < (int) info.num_texture_formats; ++i) {
|
||||
if (!SDL_ISPIXELFORMAT_FOURCC(info.texture_formats[i]) &&
|
||||
!SDL_ISPIXELFORMAT_ALPHA(info.texture_formats[i])) {
|
||||
*format = info.texture_formats[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -364,6 +286,8 @@ SDL_CreateWindowTexture(SDL_VideoDevice *unused, SDL_Window * window, Uint32 * f
|
|||
return 0;
|
||||
}
|
||||
|
||||
static SDL_VideoDevice *_this = NULL;
|
||||
|
||||
static int
|
||||
SDL_UpdateWindowTexture(SDL_VideoDevice *unused, SDL_Window * window, const SDL_Rect * rects, int numrects)
|
||||
{
|
||||
|
@ -413,28 +337,6 @@ SDL_DestroyWindowTexture(SDL_VideoDevice *unused, SDL_Window * window)
|
|||
SDL_free(data);
|
||||
}
|
||||
|
||||
|
||||
/* This will switch the video backend from using a software surface to
|
||||
using a GPU texture through the 2D render API, if we think this would
|
||||
be more efficient. This only checks once, on demand. */
|
||||
static void
|
||||
PrepareWindowFramebuffer()
|
||||
{
|
||||
/* Add the renderer framebuffer emulation if desired */
|
||||
if (_this->checked_texture_framebuffer) {
|
||||
return;
|
||||
}
|
||||
|
||||
_this->checked_texture_framebuffer = SDL_TRUE;
|
||||
|
||||
if (ShouldUseTextureFramebuffer()) {
|
||||
_this->CreateWindowFramebuffer = SDL_CreateWindowTexture;
|
||||
_this->UpdateWindowFramebuffer = SDL_UpdateWindowTexture;
|
||||
_this->DestroyWindowFramebuffer = SDL_DestroyWindowTexture;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
cmpmodes(const void *A, const void *B)
|
||||
{
|
||||
|
@ -2549,20 +2451,58 @@ SDL_SetWindowFullscreen(SDL_Window * window, Uint32 flags)
|
|||
static SDL_Surface *
|
||||
SDL_CreateWindowFramebuffer(SDL_Window * window)
|
||||
{
|
||||
Uint32 format;
|
||||
void *pixels;
|
||||
int pitch;
|
||||
Uint32 format = 0;
|
||||
void *pixels = NULL;
|
||||
int pitch = 0;
|
||||
int bpp;
|
||||
Uint32 Rmask, Gmask, Bmask, Amask;
|
||||
SDL_bool created_framebuffer = SDL_FALSE;
|
||||
|
||||
PrepareWindowFramebuffer();
|
||||
/* This will switch the video backend from using a software surface to
|
||||
using a GPU texture through the 2D render API, if we think this would
|
||||
be more efficient. This only checks once, on demand. */
|
||||
if (!_this->checked_texture_framebuffer) {
|
||||
SDL_bool attempt_texture_framebuffer = SDL_TRUE;
|
||||
|
||||
if (!_this->CreateWindowFramebuffer || !_this->UpdateWindowFramebuffer) {
|
||||
return NULL;
|
||||
if (_this->is_dummy) { /* dummy driver never has GPU support, of course. */
|
||||
attempt_texture_framebuffer = SDL_FALSE;
|
||||
}
|
||||
|
||||
#if defined(__WIN32__) /* GDI BitBlt() is way faster than Direct3D dynamic textures right now. (!!! FIXME: is this still true?) */
|
||||
else if ((_this->CreateWindowFramebuffer != NULL) && (SDL_strcmp(_this->name, "windows") == 0)) {
|
||||
attempt_texture_framebuffer = SDL_FALSE;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (attempt_texture_framebuffer) {
|
||||
if (SDL_CreateWindowTexture(_this, window, &format, &pixels, &pitch) == -1) {
|
||||
/* !!! FIXME: if this failed halfway (made renderer, failed to make texture, etc),
|
||||
!!! FIXME: we probably need to clean this up so it doesn't interfere with
|
||||
!!! FIXME: a software fallback at the system level (can we blit to an
|
||||
!!! FIXME: OpenGL window? etc). */
|
||||
} else {
|
||||
/* future attempts will just try to use a texture framebuffer. */
|
||||
/* !!! FIXME: maybe we shouldn't override these but check if we used a texture
|
||||
!!! FIXME: framebuffer at the right places; is it feasible we could have an
|
||||
!!! FIXME: accelerated OpenGL window and a second ends up in software? */
|
||||
_this->CreateWindowFramebuffer = SDL_CreateWindowTexture;
|
||||
_this->UpdateWindowFramebuffer = SDL_UpdateWindowTexture;
|
||||
_this->DestroyWindowFramebuffer = SDL_DestroyWindowTexture;
|
||||
created_framebuffer = SDL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
_this->checked_texture_framebuffer = SDL_TRUE; /* don't check this again. */
|
||||
}
|
||||
|
||||
if (_this->CreateWindowFramebuffer(_this, window, &format, &pixels, &pitch) < 0) {
|
||||
return NULL;
|
||||
if (!created_framebuffer) {
|
||||
if (!_this->CreateWindowFramebuffer || !_this->UpdateWindowFramebuffer) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (_this->CreateWindowFramebuffer(_this, window, &format, &pixels, &pitch) < 0) {
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
if (window->surface) {
|
||||
|
|
|
@ -43,6 +43,7 @@ static int Emscripten_VideoInit(_THIS);
|
|||
static int Emscripten_SetDisplayMode(_THIS, SDL_VideoDisplay * display, SDL_DisplayMode * mode);
|
||||
static void Emscripten_VideoQuit(_THIS);
|
||||
static int Emscripten_GetDisplayUsableBounds(_THIS, SDL_VideoDisplay * display, SDL_Rect * rect);
|
||||
static int Emscripten_GetDisplayDPI(_THIS, SDL_VideoDisplay * display, float * ddpi, float * hdpi, float * vdpi);
|
||||
|
||||
static int Emscripten_CreateWindow(_THIS, SDL_Window * window);
|
||||
static void Emscripten_SetWindowSize(_THIS, SDL_Window * window);
|
||||
|
@ -82,6 +83,7 @@ Emscripten_CreateDevice(int devindex)
|
|||
device->VideoInit = Emscripten_VideoInit;
|
||||
device->VideoQuit = Emscripten_VideoQuit;
|
||||
device->GetDisplayUsableBounds = Emscripten_GetDisplayUsableBounds;
|
||||
device->GetDisplayDPI = Emscripten_GetDisplayDPI;
|
||||
device->SetDisplayMode = Emscripten_SetDisplayMode;
|
||||
|
||||
|
||||
|
@ -182,6 +184,27 @@ Emscripten_GetDisplayUsableBounds(_THIS, SDL_VideoDisplay * display, SDL_Rect *
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
Emscripten_GetDisplayDPI(_THIS, SDL_VideoDisplay * display, float * ddpi_out, float * hdpi_out, float * vdpi_out)
|
||||
{
|
||||
const float dpi_reference = 96.0f;
|
||||
float dpi;
|
||||
|
||||
dpi = (float)emscripten_get_device_pixel_ratio() * dpi_reference;
|
||||
|
||||
if (ddpi_out) {
|
||||
*ddpi_out = dpi;
|
||||
}
|
||||
if (hdpi_out) {
|
||||
*hdpi_out = dpi;
|
||||
}
|
||||
if (vdpi_out) {
|
||||
*vdpi_out = dpi;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
Emscripten_PumpEvents(_THIS)
|
||||
{
|
||||
|
|
|
@ -67,7 +67,6 @@ RISCOS_PollKeyboard(_THIS)
|
|||
|
||||
/* Check for key presses */
|
||||
while (key < 0xff) {
|
||||
SDL_bool already_pressed = SDL_FALSE;
|
||||
key = _kernel_osbyte(121, key + 1, 0) & 0xff;
|
||||
switch (key) {
|
||||
case 255:
|
||||
|
@ -83,22 +82,16 @@ RISCOS_PollKeyboard(_THIS)
|
|||
break;
|
||||
|
||||
default:
|
||||
/* Do we already know of this key? */
|
||||
SDL_SendKeyboardKey(SDL_PRESSED, SDL_RISCOS_translate_keycode(key));
|
||||
|
||||
/* Record the press so we can detect release later. */
|
||||
for (i = 0; i < RISCOS_MAX_KEYS_PRESSED; i++) {
|
||||
if (driverdata->key_pressed[i] == key) {
|
||||
already_pressed = SDL_TRUE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!already_pressed) {
|
||||
SDL_SendKeyboardKey(SDL_PRESSED, SDL_RISCOS_translate_keycode(key));
|
||||
/* Record the press so we can detect release later. */
|
||||
for (i = 0; i < RISCOS_MAX_KEYS_PRESSED; i++) {
|
||||
if (driverdata->key_pressed[i] == 255) {
|
||||
driverdata->key_pressed[i] = key;
|
||||
break;
|
||||
}
|
||||
if (driverdata->key_pressed[i] == 255) {
|
||||
driverdata->key_pressed[i] = key;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -51,16 +51,17 @@ static const TCHAR *SDL_HelperWindowClassName = TEXT("SDLHelperWindowInputCatche
|
|||
static const TCHAR *SDL_HelperWindowName = TEXT("SDLHelperWindowInputMsgWindow");
|
||||
static ATOM SDL_HelperWindowClass = 0;
|
||||
|
||||
/* For borderless Windows, still want the following flags:
|
||||
/* For borderless Windows, still want the following flag:
|
||||
- WS_MINIMIZEBOX: window will respond to Windows minimize commands sent to all windows, such as windows key + m, shaking title bar, etc.
|
||||
Additionally, non-fullscreen windows can add:
|
||||
- WS_CAPTION: this seems to enable the Windows minimize animation
|
||||
- WS_SYSMENU: enables system context menu on task bar
|
||||
- WS_MINIMIZEBOX: window will respond to Windows minimize commands sent to all windows, such as windows key + m, shaking title bar, etc.
|
||||
This will also cause the task bar to overlap the window and other windowed behaviors, so only use this for windows that shouldn't appear to be fullscreen
|
||||
*/
|
||||
|
||||
#define STYLE_BASIC (WS_CLIPSIBLINGS | WS_CLIPCHILDREN)
|
||||
#define STYLE_FULLSCREEN (WS_POPUP)
|
||||
#define STYLE_BORDERLESS (WS_POPUP)
|
||||
#define STYLE_FULLSCREEN (WS_POPUP | WS_MINIMIZEBOX)
|
||||
#define STYLE_BORDERLESS (WS_POPUP | WS_MINIMIZEBOX)
|
||||
#define STYLE_BORDERLESS_WINDOWED (WS_POPUP | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX)
|
||||
#define STYLE_NORMAL (WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX)
|
||||
#define STYLE_RESIZABLE (WS_THICKFRAME | WS_MAXIMIZEBOX)
|
||||
|
|
Loading…
Reference in New Issue