From e6d1ba2a17a7e157d5aa36957f16842ac17cba89 Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Sat, 17 Jun 2023 00:52:40 -0700
Subject: [PATCH] Added the concept of display natural orientation
Also renamed SDL_GetDisplayOrientation() SDL_GetDisplayCurrentOrientation()
The natural orientation of the primary display is the frame of reference for accelerometer and gyro sensor readings.
---
.../main/java/org/libsdl/app/SDLActivity.java | 65 ++++++++++++-------
.../main/java/org/libsdl/app/SDLSurface.java | 32 ++++-----
build-scripts/SDL_migration.cocci | 5 ++
docs/README-migration.md | 1 +
include/SDL3/SDL_oldnames.h | 2 +
include/SDL3/SDL_sensor.h | 4 +-
include/SDL3/SDL_video.h | 15 ++++-
src/core/android/SDL_android.c | 54 ++++++++++++---
src/core/android/SDL_android.h | 3 +-
src/dynapi/SDL_dynapi.sym | 3 +-
src/dynapi/SDL_dynapi_overrides.h | 3 +-
src/dynapi/SDL_dynapi_procs.h | 3 +-
src/events/SDL_displayevents.c | 4 +-
src/test/SDL_test_common.c | 9 ++-
src/video/SDL_sysvideo.h | 3 +-
src/video/SDL_video.c | 23 ++++++-
src/video/android/SDL_androidvideo.c | 3 +-
src/video/uikit/SDL_uikitmodes.m | 11 ++++
src/video/wayland/SDL_waylandvideo.c | 7 +-
src/video/windows/SDL_windowsmodes.c | 32 ++++++---
20 files changed, 208 insertions(+), 74 deletions(-)
diff --git a/android-project/app/src/main/java/org/libsdl/app/SDLActivity.java b/android-project/app/src/main/java/org/libsdl/app/SDLActivity.java
index 629dabb16802..30a3fe1a8467 100644
--- a/android-project/app/src/main/java/org/libsdl/app/SDLActivity.java
+++ b/android-project/app/src/main/java/org/libsdl/app/SDLActivity.java
@@ -193,7 +193,7 @@ public static void debugSource(int sources, String prefix) {
protected static final int SDL_ORIENTATION_PORTRAIT = 3;
protected static final int SDL_ORIENTATION_PORTRAIT_FLIPPED = 4;
- protected static int mCurrentOrientation;
+ protected static int mCurrentRotation;
protected static Locale mCurrentLocale;
// Handle the state of the native layer
@@ -437,9 +437,9 @@ public void onClick(DialogInterface dialog,int id) {
mLayout.addView(mSurface);
// Get our current screen orientation and pass it down.
- mCurrentOrientation = SDLActivity.getCurrentOrientation();
- // Only record current orientation
- SDLActivity.onNativeOrientationChanged(mCurrentOrientation);
+ SDLActivity.nativeSetNaturalOrientation(SDLActivity.getNaturalOrientation());
+ mCurrentRotation = SDLActivity.getCurrentRotation();
+ SDLActivity.onNativeRotationChanged(mCurrentRotation);
try {
if (Build.VERSION.SDK_INT < 24 /* Android 7.0 (N) */) {
@@ -543,33 +543,47 @@ protected void onStart() {
}
}
- public static int getCurrentOrientation() {
+ public static int getNaturalOrientation() {
int result = SDL_ORIENTATION_UNKNOWN;
Activity activity = (Activity)getContext();
- if (activity == null) {
- return result;
- }
- Display display = activity.getWindowManager().getDefaultDisplay();
-
- switch (display.getRotation()) {
- case Surface.ROTATION_0:
- result = SDL_ORIENTATION_PORTRAIT;
- break;
-
- case Surface.ROTATION_90:
+ if (activity != null) {
+ Configuration config = activity.getResources().getConfiguration();
+ Display display = activity.getWindowManager().getDefaultDisplay();
+ int rotation = display.getRotation();
+ if (((rotation == Surface.ROTATION_0 || rotation == Surface.ROTATION_180) &&
+ config.orientation == Configuration.ORIENTATION_LANDSCAPE) ||
+ ((rotation == Surface.ROTATION_90 || rotation == Surface.ROTATION_270) &&
+ config.orientation == Configuration.ORIENTATION_PORTRAIT)) {
result = SDL_ORIENTATION_LANDSCAPE;
- break;
+ } else {
+ result = SDL_ORIENTATION_PORTRAIT;
+ }
+ }
+ return result;
+ }
- case Surface.ROTATION_180:
- result = SDL_ORIENTATION_PORTRAIT_FLIPPED;
- break;
+ public static int getCurrentRotation() {
+ int result = 0;
- case Surface.ROTATION_270:
- result = SDL_ORIENTATION_LANDSCAPE_FLIPPED;
- break;
+ Activity activity = (Activity)getContext();
+ if (activity != null) {
+ Display display = activity.getWindowManager().getDefaultDisplay();
+ switch (display.getRotation()) {
+ case Surface.ROTATION_0:
+ result = 0;
+ break;
+ case Surface.ROTATION_90:
+ result = 90;
+ break;
+ case Surface.ROTATION_180:
+ result = 180;
+ break;
+ case Surface.ROTATION_270:
+ result = 270;
+ break;
+ }
}
-
return result;
}
@@ -987,7 +1001,8 @@ public static native void onNativeTouch(int touchDevId, int pointerFingerId,
public static native String nativeGetHint(String name);
public static native boolean nativeGetHintBoolean(String name, boolean default_value);
public static native void nativeSetenv(String name, String value);
- public static native void onNativeOrientationChanged(int orientation);
+ public static native void nativeSetNaturalOrientation(int orientation);
+ public static native void onNativeRotationChanged(int rotation);
public static native void nativeAddTouch(int touchId, String name);
public static native void nativePermissionResult(int requestCode, boolean result);
public static native void onNativeLocaleChanged();
diff --git a/android-project/app/src/main/java/org/libsdl/app/SDLSurface.java b/android-project/app/src/main/java/org/libsdl/app/SDLSurface.java
index a14234309ca5..c4c14491455c 100644
--- a/android-project/app/src/main/java/org/libsdl/app/SDLSurface.java
+++ b/android-project/app/src/main/java/org/libsdl/app/SDLSurface.java
@@ -325,36 +325,36 @@ public void onSensorChanged(SensorEvent event) {
// Since we may have an orientation set, we won't receive onConfigurationChanged events.
// We thus should check here.
- int newOrientation;
+ int newRotation;
float x, y;
switch (mDisplay.getRotation()) {
+ case Surface.ROTATION_0:
+ default:
+ x = event.values[0];
+ y = event.values[1];
+ newRotation = 0;
+ break;
case Surface.ROTATION_90:
x = -event.values[1];
y = event.values[0];
- newOrientation = SDLActivity.SDL_ORIENTATION_LANDSCAPE;
- break;
- case Surface.ROTATION_270:
- x = event.values[1];
- y = -event.values[0];
- newOrientation = SDLActivity.SDL_ORIENTATION_LANDSCAPE_FLIPPED;
+ newRotation = 90;
break;
case Surface.ROTATION_180:
x = -event.values[0];
y = -event.values[1];
- newOrientation = SDLActivity.SDL_ORIENTATION_PORTRAIT_FLIPPED;
+ newRotation = 180;
break;
- case Surface.ROTATION_0:
- default:
- x = event.values[0];
- y = event.values[1];
- newOrientation = SDLActivity.SDL_ORIENTATION_PORTRAIT;
+ case Surface.ROTATION_270:
+ x = event.values[1];
+ y = -event.values[0];
+ newRotation = 270;
break;
}
- if (newOrientation != SDLActivity.mCurrentOrientation) {
- SDLActivity.mCurrentOrientation = newOrientation;
- SDLActivity.onNativeOrientationChanged(newOrientation);
+ if (newRotation != SDLActivity.mCurrentRotation) {
+ SDLActivity.mCurrentRotation = newRotation;
+ SDLActivity.onNativeRotationChanged(newRotation);
}
SDLActivity.onNativeAccel(-x / SensorManager.GRAVITY_EARTH,
diff --git a/build-scripts/SDL_migration.cocci b/build-scripts/SDL_migration.cocci
index 99d9c0487eba..a9afa8082639 100644
--- a/build-scripts/SDL_migration.cocci
+++ b/build-scripts/SDL_migration.cocci
@@ -2668,3 +2668,8 @@ typedef SDL_cond, SDL_Condition;
- SDL_TLSCleanup
+ SDL_CleanupTLS
(...)
+@@
+@@
+- SDL_GetDisplayOrientation
++ SDL_GetDisplayCurrentOrientation
+ (...)
diff --git a/docs/README-migration.md b/docs/README-migration.md
index 6d649e52ae86..6199d7a935b5 100644
--- a/docs/README-migration.md
+++ b/docs/README-migration.md
@@ -1139,6 +1139,7 @@ The SDL_WINDOW_TOOLTIP and SDL_WINDOW_POPUP_MENU window flags are now supported
The following functions have been renamed:
* SDL_GetClosestDisplayMode() => SDL_GetClosestFullscreenDisplayMode()
+* SDL_GetDisplayOrientation() => SDL_GetDisplayCurrentOrientation()
* SDL_GetPointDisplayIndex() => SDL_GetDisplayForPoint()
* SDL_GetRectDisplayIndex() => SDL_GetDisplayForRect()
* SDL_GetWindowDisplayIndex() => SDL_GetDisplayForWindow()
diff --git a/include/SDL3/SDL_oldnames.h b/include/SDL3/SDL_oldnames.h
index 9378a9c90c33..a79f0cec8e37 100644
--- a/include/SDL3/SDL_oldnames.h
+++ b/include/SDL3/SDL_oldnames.h
@@ -466,6 +466,7 @@
/* ##SDL_video.h */
#define SDL_GetClosestDisplayMode SDL_GetClosestFullscreenDisplayMode
+#define SDL_GetDisplayOrientation SDL_GetDisplayCurrentOrientation
#define SDL_GetPointDisplayIndex SDL_GetDisplayForPoint
#define SDL_GetRectDisplayIndex SDL_GetDisplayForRect
#define SDL_GetWindowDisplayIndex SDL_GetDisplayForWindow
@@ -902,6 +903,7 @@
/* ##SDL_video.h */
#define SDL_GetClosestDisplayMode SDL_GetClosestDisplayMode_renamed_SDL_GetClosestFullscreenDisplayMode
+#define SDL_GetDisplayOrientation SDL_GetDisplayOrientation_renamed_SDL_GetDisplayCurrentOrientation
#define SDL_GetPointDisplayIndex SDL_GetPointDisplayIndex_renamed_SDL_GetDisplayForPoint
#define SDL_GetRectDisplayIndex SDL_GetRectDisplayIndex_renamed_SDL_GetDisplayForRect
#define SDL_GetWindowDisplayIndex SDL_GetWindowDisplayIndex_renamed_SDL_GetDisplayForWindow
diff --git a/include/SDL3/SDL_sensor.h b/include/SDL3/SDL_sensor.h
index dda75f036505..1b806953381a 100644
--- a/include/SDL3/SDL_sensor.h
+++ b/include/SDL3/SDL_sensor.h
@@ -96,7 +96,7 @@ typedef enum
*
* The axis data is not changed when the device is rotated.
*
- * \sa SDL_GetDisplayOrientation()
+ * \sa SDL_GetDisplayCurrentOrientation()
*/
#define SDL_STANDARD_GRAVITY 9.80665f
@@ -120,7 +120,7 @@ typedef enum
*
* The axis data is not changed when the device is rotated.
*
- * \sa SDL_GetDisplayOrientation()
+ * \sa SDL_GetDisplayCurrentOrientation()
*/
/* Function prototypes */
diff --git a/include/SDL3/SDL_video.h b/include/SDL3/SDL_video.h
index c6f6fa15067b..664777e8cdad 100644
--- a/include/SDL3/SDL_video.h
+++ b/include/SDL3/SDL_video.h
@@ -394,6 +394,19 @@ extern DECLSPEC int SDLCALL SDL_GetDisplayBounds(SDL_DisplayID displayID, SDL_Re
*/
extern DECLSPEC int SDLCALL SDL_GetDisplayUsableBounds(SDL_DisplayID displayID, SDL_Rect *rect);
+/**
+ * Get the orientation of a display when it is unrotated.
+ *
+ * \param displayID the instance ID of the display to query
+ * \returns The SDL_DisplayOrientation enum value of the display, or
+ * `SDL_ORIENTATION_UNKNOWN` if it isn't available.
+ *
+ * \since This function is available since SDL 3.0.0.
+ *
+ * \sa SDL_GetDisplays
+ */
+extern DECLSPEC SDL_DisplayOrientation SDLCALL SDL_GetDisplayNaturalOrientation(SDL_DisplayID displayID);
+
/**
* Get the orientation of a display.
*
@@ -405,7 +418,7 @@ extern DECLSPEC int SDLCALL SDL_GetDisplayUsableBounds(SDL_DisplayID displayID,
*
* \sa SDL_GetDisplays
*/
-extern DECLSPEC SDL_DisplayOrientation SDLCALL SDL_GetDisplayOrientation(SDL_DisplayID displayID);
+extern DECLSPEC SDL_DisplayOrientation SDLCALL SDL_GetDisplayCurrentOrientation(SDL_DisplayID displayID);
/**
* Get the content scale of a display.
diff --git a/src/core/android/SDL_android.c b/src/core/android/SDL_android.c
index 8238979c3cbd..1d3909b6938f 100644
--- a/src/core/android/SDL_android.c
+++ b/src/core/android/SDL_android.c
@@ -155,10 +155,14 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetenv)(
JNIEnv *env, jclass cls,
jstring name, jstring value);
-JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeOrientationChanged)(
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetNaturalOrientation)(
JNIEnv *env, jclass cls,
jint orientation);
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeRotationChanged)(
+ JNIEnv *env, jclass cls,
+ jint rotation);
+
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeAddTouch)(
JNIEnv *env, jclass cls,
jint touchId, jstring name);
@@ -202,7 +206,8 @@ static JNINativeMethod SDLActivity_tab[] = {
{ "nativeGetHint", "(Ljava/lang/String;)Ljava/lang/String;", SDL_JAVA_INTERFACE(nativeGetHint) },
{ "nativeGetHintBoolean", "(Ljava/lang/String;Z)Z", SDL_JAVA_INTERFACE(nativeGetHintBoolean) },
{ "nativeSetenv", "(Ljava/lang/String;Ljava/lang/String;)V", SDL_JAVA_INTERFACE(nativeSetenv) },
- { "onNativeOrientationChanged", "(I)V", SDL_JAVA_INTERFACE(onNativeOrientationChanged) },
+ { "nativeSetNaturalOrientation", "(I)V", SDL_JAVA_INTERFACE(nativeSetNaturalOrientation) },
+ { "onNativeRotationChanged", "(I)V", SDL_JAVA_INTERFACE(onNativeRotationChanged) },
{ "nativeAddTouch", "(ILjava/lang/String;)V", SDL_JAVA_INTERFACE(nativeAddTouch) },
{ "nativePermissionResult", "(IZ)V", SDL_JAVA_INTERFACE(nativePermissionResult) },
{ "nativeAllowRecreateActivity", "()Z", SDL_JAVA_INTERFACE(nativeAllowRecreateActivity) },
@@ -369,7 +374,8 @@ static jmethodID midHapticRun;
static jmethodID midHapticStop;
/* Accelerometer data storage */
-static SDL_DisplayOrientation displayOrientation;
+static SDL_DisplayOrientation displayNaturalOrientation;
+static SDL_DisplayOrientation displayCurrentOrientation;
static float fLastAccelerometer[3];
static SDL_bool bHasNewData;
@@ -934,17 +940,44 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeResize)(
SDL_UnlockMutex(Android_ActivityMutex);
}
-JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeOrientationChanged)(
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetNaturalOrientation)(
JNIEnv *env, jclass jcls,
jint orientation)
+{
+ displayNaturalOrientation = (SDL_DisplayOrientation)orientation;
+}
+
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeRotationChanged)(
+ JNIEnv *env, jclass jcls,
+ jint rotation)
{
SDL_LockMutex(Android_ActivityMutex);
- displayOrientation = (SDL_DisplayOrientation)orientation;
+ if (displayNaturalOrientation == SDL_ORIENTATION_LANDSCAPE) {
+ rotation += 90;
+ }
+
+ switch (rotation % 360) {
+ case 0:
+ displayCurrentOrientation = SDL_ORIENTATION_PORTRAIT;
+ break;
+ case 90:
+ displayCurrentOrientation = SDL_ORIENTATION_LANDSCAPE;
+ break;
+ case 180:
+ displayCurrentOrientation = SDL_ORIENTATION_PORTRAIT_FLIPPED;
+ break;
+ case 270:
+ displayCurrentOrientation = SDL_ORIENTATION_LANDSCAPE_FLIPPED;
+ break;
+ default:
+ displayCurrentOrientation = SDL_ORIENTATION_UNKNOWN;
+ break;
+ }
if (Android_Window) {
SDL_VideoDisplay *display = SDL_GetVideoDisplay(SDL_GetPrimaryDisplay());
- SDL_SendDisplayEvent(display, SDL_EVENT_DISPLAY_ORIENTATION, orientation);
+ SDL_SendDisplayEvent(display, SDL_EVENT_DISPLAY_ORIENTATION, displayCurrentOrientation);
}
SDL_UnlockMutex(Android_ActivityMutex);
@@ -1706,9 +1739,14 @@ int Android_JNI_OpenAudioDevice(int iscapture, int device_id, SDL_AudioSpec *spe
return 0;
}
-SDL_DisplayOrientation Android_JNI_GetDisplayOrientation(void)
+SDL_DisplayOrientation Android_JNI_GetDisplayNaturalOrientation(void)
+{
+ return displayNaturalOrientation;
+}
+
+SDL_DisplayOrientation Android_JNI_GetDisplayCurrentOrientation(void)
{
- return displayOrientation;
+ return displayCurrentOrientation;
}
void *Android_JNI_GetAudioBuffer(void)
diff --git a/src/core/android/SDL_android.h b/src/core/android/SDL_android.h
index 3e318ac9edb8..a245af980058 100644
--- a/src/core/android/SDL_android.h
+++ b/src/core/android/SDL_android.h
@@ -43,7 +43,8 @@ extern void Android_JNI_HideTextInput(void);
extern SDL_bool Android_JNI_IsScreenKeyboardShown(void);
extern ANativeWindow *Android_JNI_GetNativeWindow(void);
-extern SDL_DisplayOrientation Android_JNI_GetDisplayOrientation(void);
+extern SDL_DisplayOrientation Android_JNI_GetDisplayNaturalOrientation(void);
+extern SDL_DisplayOrientation Android_JNI_GetDisplayCurrentOrientation(void);
/* Audio support */
extern void Android_DetectDevices(void);
diff --git a/src/dynapi/SDL_dynapi.sym b/src/dynapi/SDL_dynapi.sym
index d10df5474325..b06d9f1afa74 100644
--- a/src/dynapi/SDL_dynapi.sym
+++ b/src/dynapi/SDL_dynapi.sym
@@ -166,7 +166,7 @@ SDL3_0.0.0 {
SDL_GetDisplayForPoint;
SDL_GetDisplayForRect;
SDL_GetDisplayName;
- SDL_GetDisplayOrientation;
+ SDL_GetDisplayCurrentOrientation;
SDL_GetDisplayUsableBounds;
SDL_GetError;
SDL_GetErrorMsg;
@@ -866,6 +866,7 @@ SDL3_0.0.0 {
SDL_hid_get_report_descriptor;
SDL_HasWindowSurface;
SDL_DestroyWindowSurface;
+ SDL_GetDisplayNaturalOrientation;
# extra symbols go here (don't modify this line)
local: *;
};
diff --git a/src/dynapi/SDL_dynapi_overrides.h b/src/dynapi/SDL_dynapi_overrides.h
index c3635845fecc..6a5ad66de2c6 100644
--- a/src/dynapi/SDL_dynapi_overrides.h
+++ b/src/dynapi/SDL_dynapi_overrides.h
@@ -190,7 +190,7 @@
#define SDL_GetDisplayForPoint SDL_GetDisplayForPoint_REAL
#define SDL_GetDisplayForRect SDL_GetDisplayForRect_REAL
#define SDL_GetDisplayName SDL_GetDisplayName_REAL
-#define SDL_GetDisplayOrientation SDL_GetDisplayOrientation_REAL
+#define SDL_GetDisplayCurrentOrientation SDL_GetDisplayCurrentOrientation_REAL
#define SDL_GetDisplayUsableBounds SDL_GetDisplayUsableBounds_REAL
#define SDL_GetError SDL_GetError_REAL
#define SDL_GetErrorMsg SDL_GetErrorMsg_REAL
@@ -892,3 +892,4 @@
#define SDL_hid_get_report_descriptor SDL_hid_get_report_descriptor_REAL
#define SDL_HasWindowSurface SDL_HasWindowSurface_REAL
#define SDL_DestroyWindowSurface SDL_DestroyWindowSurface_REAL
+#define SDL_GetDisplayNaturalOrientation SDL_GetDisplayNaturalOrientation_REAL
diff --git a/src/dynapi/SDL_dynapi_procs.h b/src/dynapi/SDL_dynapi_procs.h
index 5bbe6227b32b..7557f35cec89 100644
--- a/src/dynapi/SDL_dynapi_procs.h
+++ b/src/dynapi/SDL_dynapi_procs.h
@@ -265,7 +265,7 @@ SDL_DYNAPI_PROC(int,SDL_GetDisplayBounds,(SDL_DisplayID a, SDL_Rect *b),(a,b),re
SDL_DYNAPI_PROC(SDL_DisplayID,SDL_GetDisplayForPoint,(const SDL_Point *a),(a),return)
SDL_DYNAPI_PROC(SDL_DisplayID,SDL_GetDisplayForRect,(const SDL_Rect *a),(a),return)
SDL_DYNAPI_PROC(const char*,SDL_GetDisplayName,(SDL_DisplayID a),(a),return)
-SDL_DYNAPI_PROC(SDL_DisplayOrientation,SDL_GetDisplayOrientation,(SDL_DisplayID a),(a),return)
+SDL_DYNAPI_PROC(SDL_DisplayOrientation,SDL_GetDisplayCurrentOrientation,(SDL_DisplayID a),(a),return)
SDL_DYNAPI_PROC(int,SDL_GetDisplayUsableBounds,(SDL_DisplayID a, SDL_Rect *b),(a,b),return)
SDL_DYNAPI_PROC(const char*,SDL_GetError,(void),(),return)
SDL_DYNAPI_PROC(char*,SDL_GetErrorMsg,(char *a, int b),(a,b),return)
@@ -937,3 +937,4 @@ SDL_DYNAPI_PROC(SDL_hid_device_info*,SDL_hid_get_device_info,(SDL_hid_device *a)
SDL_DYNAPI_PROC(int,SDL_hid_get_report_descriptor,(SDL_hid_device *a, unsigned char *b, size_t c),(a,b,c),return)
SDL_DYNAPI_PROC(SDL_bool,SDL_HasWindowSurface,(SDL_Window *a),(a),return)
SDL_DYNAPI_PROC(int,SDL_DestroyWindowSurface,(SDL_Window *a),(a),return)
+SDL_DYNAPI_PROC(SDL_DisplayOrientation,SDL_GetDisplayNaturalOrientation,(SDL_DisplayID a),(a),return)
diff --git a/src/events/SDL_displayevents.c b/src/events/SDL_displayevents.c
index 803d24d4318c..edccb033f624 100644
--- a/src/events/SDL_displayevents.c
+++ b/src/events/SDL_displayevents.c
@@ -33,10 +33,10 @@ int SDL_SendDisplayEvent(SDL_VideoDisplay *display, SDL_EventType displayevent,
}
switch (displayevent) {
case SDL_EVENT_DISPLAY_ORIENTATION:
- if (data1 == SDL_ORIENTATION_UNKNOWN || data1 == display->orientation) {
+ if (data1 == SDL_ORIENTATION_UNKNOWN || data1 == display->current_orientation) {
return 0;
}
- display->orientation = (SDL_DisplayOrientation)data1;
+ display->current_orientation = (SDL_DisplayOrientation)data1;
break;
default:
break;
diff --git a/src/test/SDL_test_common.c b/src/test/SDL_test_common.c
index d77b65212dd7..3e5e370f7d8f 100644
--- a/src/test/SDL_test_common.c
+++ b/src/test/SDL_test_common.c
@@ -2464,8 +2464,13 @@ void SDLTest_CommonDrawWindowInfo(SDL_Renderer *renderer, SDL_Window *window, fl
textY += lineHeight;
}
- (void)SDL_snprintf(text, sizeof(text), "SDL_GetDisplayOrientation: ");
- SDLTest_PrintDisplayOrientation(text, sizeof(text), SDL_GetDisplayOrientation(windowDisplayID));
+ (void)SDL_snprintf(text, sizeof(text), "SDL_GetDisplayNaturalOrientation: ");
+ SDLTest_PrintDisplayOrientation(text, sizeof(text), SDL_GetDisplayNaturalOrientation(windowDisplayID));
+ SDLTest_DrawString(renderer, 0.0f, textY, text);
+ textY += lineHeight;
+
+ (void)SDL_snprintf(text, sizeof(text), "SDL_GetDisplayCurrentOrientation: ");
+ SDLTest_PrintDisplayOrientation(text, sizeof(text), SDL_GetDisplayCurrentOrientation(windowDisplayID));
SDLTest_DrawString(renderer, 0.0f, textY, text);
textY += lineHeight;
diff --git a/src/video/SDL_sysvideo.h b/src/video/SDL_sysvideo.h
index 9da28a1c3526..db67e46af1f5 100644
--- a/src/video/SDL_sysvideo.h
+++ b/src/video/SDL_sysvideo.h
@@ -145,7 +145,8 @@ struct SDL_VideoDisplay
SDL_DisplayMode *fullscreen_modes;
SDL_DisplayMode desktop_mode;
const SDL_DisplayMode *current_mode;
- SDL_DisplayOrientation orientation;
+ SDL_DisplayOrientation natural_orientation;
+ SDL_DisplayOrientation current_orientation;
float content_scale;
SDL_Window *fullscreen_window;
diff --git a/src/video/SDL_video.c b/src/video/SDL_video.c
index 925b411e0e47..e211f5ad424a 100644
--- a/src/video/SDL_video.c
+++ b/src/video/SDL_video.c
@@ -889,13 +889,32 @@ int SDL_GetDisplayUsableBounds(SDL_DisplayID displayID, SDL_Rect *rect)
return SDL_GetDisplayBounds(displayID, rect);
}
-SDL_DisplayOrientation SDL_GetDisplayOrientation(SDL_DisplayID displayID)
+SDL_DisplayOrientation SDL_GetDisplayNaturalOrientation(SDL_DisplayID displayID)
{
SDL_VideoDisplay *display = SDL_GetVideoDisplay(displayID);
CHECK_DISPLAY_MAGIC(display, SDL_ORIENTATION_UNKNOWN);
- return display->orientation;
+ if (display->natural_orientation != SDL_ORIENTATION_UNKNOWN) {
+ return display->natural_orientation;
+ } else {
+ /* Default to landscape if the driver hasn't set it */
+ return SDL_ORIENTATION_LANDSCAPE;
+ }
+}
+
+SDL_DisplayOrientation SDL_GetDisplayCurrentOrientation(SDL_DisplayID displayID)
+{
+ SDL_VideoDisplay *display = SDL_GetVideoDisplay(displayID);
+
+ CHECK_DISPLAY_MAGIC(display, SDL_ORIENTATION_UNKNOWN);
+
+ if (display->current_orientation != SDL_ORIENTATION_UNKNOWN) {
+ return display->current_orientation;
+ } else {
+ /* Default to landscape if the driver hasn't set it */
+ return SDL_ORIENTATION_LANDSCAPE;
+ }
}
void SDL_SetDisplayContentScale(SDL_VideoDisplay *display, float scale)
diff --git a/src/video/android/SDL_androidvideo.c b/src/video/android/SDL_androidvideo.c
index 7804fe9de2df..021607ce5d3a 100644
--- a/src/video/android/SDL_androidvideo.c
+++ b/src/video/android/SDL_androidvideo.c
@@ -189,7 +189,8 @@ int Android_VideoInit(SDL_VideoDevice *_this)
return -1;
}
display = SDL_GetVideoDisplay(displayID);
- display->orientation = Android_JNI_GetDisplayOrientation();
+ display->natural_orientation = Android_JNI_GetDisplayNaturalOrientation();
+ display->current_orientation = Android_JNI_GetDisplayCurrentOrientation();
display->content_scale = Android_ScreenDensity;
Android_InitTouch();
diff --git a/src/video/uikit/SDL_uikitmodes.m b/src/video/uikit/SDL_uikitmodes.m
index 220589d10b33..3ce798102255 100644
--- a/src/video/uikit/SDL_uikitmodes.m
+++ b/src/video/uikit/SDL_uikitmodes.m
@@ -220,6 +220,17 @@ int UIKit_AddDisplay(UIScreen *uiscreen, SDL_bool send_event)
}
SDL_zero(display);
+#if !TARGET_OS_TV
+ if (uiscreen == [UIScreen mainScreen]) {
+ /* The natural orientation (used by sensors) is portrait */
+ display.natural_orientation = SDL_ORIENTATION_PORTRAIT;
+ } else
+#endif
+ if (UIKit_IsDisplayLandscape(uiscreen)) {
+ display.natural_orientation = SDL_ORIENTATION_LANDSCAPE;
+ } else {
+ display.natural_orientation = SDL_ORIENTATION_PORTRAIT;
+ }
display.desktop_mode = mode;
/* Allocate the display data */
diff --git a/src/video/wayland/SDL_waylandvideo.c b/src/video/wayland/SDL_waylandvideo.c
index ba6aecf31f4a..79358c23bbc6 100644
--- a/src/video/wayland/SDL_waylandvideo.c
+++ b/src/video/wayland/SDL_waylandvideo.c
@@ -594,7 +594,12 @@ static void display_handle_done(void *data,
if (driverdata->display == 0) {
/* First time getting display info, create the VideoDisplay */
SDL_bool send_event = driverdata->videodata->initializing ? SDL_FALSE : SDL_TRUE;
- driverdata->placeholder.orientation = driverdata->orientation;
+ if (driverdata->physical_width >= driverdata->physical_height) {
+ driverdata->placeholder.natural_orientation = SDL_ORIENTATION_LANDSCAPE;
+ } else {
+ driverdata->placeholder.natural_orientation = SDL_ORIENTATION_PORTRAIT;
+ }
+ driverdata->placeholder.current_orientation = driverdata->orientation;
driverdata->placeholder.driverdata = driverdata;
driverdata->display = SDL_AddVideoDisplay(&driverdata->placeholder, send_event);
SDL_free(driverdata->placeholder.name);
diff --git a/src/video/windows/SDL_windowsmodes.c b/src/video/windows/SDL_windowsmodes.c
index 05f3e1d64934..018f0e13c526 100644
--- a/src/video/windows/SDL_windowsmodes.c
+++ b/src/video/windows/SDL_windowsmodes.c
@@ -102,7 +102,7 @@ static void WIN_UpdateDisplayMode(SDL_VideoDevice *_this, LPCWSTR deviceName, DW
}
}
-static SDL_DisplayOrientation WIN_GetDisplayOrientation(DEVMODE *mode)
+static SDL_DisplayOrientation WIN_GetNaturalOrientation(DEVMODE *mode)
{
int width = mode->dmPelsWidth;
int height = mode->dmPelsHeight;
@@ -115,6 +115,15 @@ static SDL_DisplayOrientation WIN_GetDisplayOrientation(DEVMODE *mode)
}
if (width >= height) {
+ return SDL_ORIENTATION_LANDSCAPE;
+ } else {
+ return SDL_ORIENTATION_PORTRAIT;
+ }
+}
+
+static SDL_DisplayOrientation WIN_GetDisplayOrientation(DEVMODE *mode)
+{
+ if (WIN_GetNaturalOrientation(mode) == SDL_ORIENTATION_LANDSCAPE) {
switch (mode->dmDisplayOrientation) {
case DMDO_DEFAULT:
return SDL_ORIENTATION_LANDSCAPE;
@@ -182,7 +191,7 @@ static float WIN_GetContentScale(SDL_VideoDevice *_this, HMONITOR hMonitor)
return dpi / 96.0f;
}
-static SDL_bool WIN_GetDisplayMode(SDL_VideoDevice *_this, HMONITOR hMonitor, LPCWSTR deviceName, DWORD index, SDL_DisplayMode *mode, SDL_DisplayOrientation *orientation)
+static SDL_bool WIN_GetDisplayMode(SDL_VideoDevice *_this, HMONITOR hMonitor, LPCWSTR deviceName, DWORD index, SDL_DisplayMode *mode, SDL_DisplayOrientation *natural_orientation, SDL_DisplayOrientation *current_orientation)
{
SDL_DisplayModeData *data;
DEVMODE devmode;
@@ -210,8 +219,11 @@ static SDL_bool WIN_GetDisplayMode(SDL_VideoDevice *_this, HMONITOR hMonitor, LP
/* Fill in the mode information */
WIN_UpdateDisplayMode(_this, deviceName, index, mode);
- if (orientation) {
- *orientation = WIN_GetDisplayOrientation(&devmode);
+ if (natural_orientation) {
+ *natural_orientation = WIN_GetNaturalOrientation(&devmode);
+ }
+ if (current_orientation) {
+ *current_orientation = WIN_GetDisplayOrientation(&devmode);
}
return SDL_TRUE;
@@ -324,14 +336,15 @@ static void WIN_AddDisplay(SDL_VideoDevice *_this, HMONITOR hMonitor, const MONI
SDL_VideoDisplay display;
SDL_DisplayData *displaydata;
SDL_DisplayMode mode;
- SDL_DisplayOrientation orientation;
+ SDL_DisplayOrientation natural_orientation;
+ SDL_DisplayOrientation current_orientation;
float content_scale = WIN_GetContentScale(_this, hMonitor);
#ifdef DEBUG_MODES
SDL_Log("Display: %s\n", WIN_StringToUTF8W(info->szDevice));
#endif
- if (!WIN_GetDisplayMode(_this, hMonitor, info->szDevice, ENUM_CURRENT_SETTINGS, &mode, &orientation)) {
+ if (!WIN_GetDisplayMode(_this, hMonitor, info->szDevice, ENUM_CURRENT_SETTINGS, &mode, &natural_orientation, ¤t_orientation)) {
return;
}
@@ -371,7 +384,7 @@ static void WIN_AddDisplay(SDL_VideoDevice *_this, HMONITOR hMonitor, const MONI
if (moved || changed_bounds) {
SDL_SendDisplayEvent(existing_display, SDL_EVENT_DISPLAY_MOVED, 0);
}
- SDL_SendDisplayEvent(existing_display, SDL_EVENT_DISPLAY_ORIENTATION, orientation);
+ SDL_SendDisplayEvent(existing_display, SDL_EVENT_DISPLAY_ORIENTATION, current_orientation);
SDL_SetDisplayContentScale(existing_display, content_scale);
}
goto done;
@@ -398,7 +411,8 @@ static void WIN_AddDisplay(SDL_VideoDevice *_this, HMONITOR hMonitor, const MONI
}
display.desktop_mode = mode;
- display.orientation = orientation;
+ display.natural_orientation = natural_orientation;
+ display.current_orientation = current_orientation;
display.content_scale = content_scale;
display.device = _this;
display.driverdata = displaydata;
@@ -514,7 +528,7 @@ int WIN_GetDisplayModes(SDL_VideoDevice *_this, SDL_VideoDisplay *display)
SDL_DisplayMode mode;
for (i = 0;; ++i) {
- if (!WIN_GetDisplayMode(_this, data->MonitorHandle, data->DeviceName, i, &mode, NULL)) {
+ if (!WIN_GetDisplayMode(_this, data->MonitorHandle, data->DeviceName, i, &mode, NULL, NULL)) {
break;
}
if (SDL_ISPIXELFORMAT_INDEXED(mode.format)) {
(Patch may be truncated, please check the link at the top of this post.)