Fixed bug 4883 - Add approximation for display DPI on iOS Aaron Barany There appears to be no way to directly access the display DPI on iOS, so as an approximation the DPI for the iPhone 1 is used as a base value and is multiplied by the screen's scale. This should at least give a ballpark number for the various screen scales. (based on https://stackoverflow.com/questions/25756087/detecting-iphone-6-6-screen-sizes-in-point-values it appears that both 2x and 3x are used) I have updated the patch to use a table of current devices and use a computation as a fallback. I have also updated the fallback computation to be more accurate.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222
diff --git a/src/video/uikit/SDL_uikitmodes.h b/src/video/uikit/SDL_uikitmodes.h
index d6faa11..cab8185 100644
--- a/src/video/uikit/SDL_uikitmodes.h
+++ b/src/video/uikit/SDL_uikitmodes.h
@@ -27,7 +27,10 @@
@interface SDL_DisplayData : NSObject
+- (instancetype)init;
+
@property (nonatomic, strong) UIScreen *uiscreen;
+@property (nonatomic) float screenDPI;
@end
@@ -41,6 +44,7 @@ extern SDL_bool UIKit_IsDisplayLandscape(UIScreen *uiscreen);
extern int UIKit_InitModes(_THIS);
extern void UIKit_GetDisplayModes(_THIS, SDL_VideoDisplay * display);
+extern int UIKit_GetDisplayDPI(_THIS, SDL_VideoDisplay * display, float * ddpi, float * hdpi, float * vdpi);
extern int UIKit_SetDisplayMode(_THIS, SDL_VideoDisplay * display, SDL_DisplayMode * mode);
extern void UIKit_QuitModes(_THIS);
extern int UIKit_GetDisplayUsableBounds(_THIS, SDL_VideoDisplay * display, SDL_Rect * rect);
diff --git a/src/video/uikit/SDL_uikitmodes.m b/src/video/uikit/SDL_uikitmodes.m
index be34b06..2b40dbb 100644
--- a/src/video/uikit/SDL_uikitmodes.m
+++ b/src/video/uikit/SDL_uikitmodes.m
@@ -27,9 +27,150 @@
#include "../../events/SDL_events_c.h"
+#import <sys/utsname.h>
+
@implementation SDL_DisplayData
+- (instancetype)initWithScreen:(UIScreen*)screen
+{
+ if (self = [super init]) {
+ self.uiscreen = screen;
+
+ /*
+ * A well up to date list of device info can be found here:
+ * https://github.com/lmirosevic/GBDeviceInfo/blob/master/GBDeviceInfo/GBDeviceInfo_iOS.m
+ */
+ NSDictionary* devices = @{
+ @"iPhone1,1": @163,
+ @"iPhone1,2": @163,
+ @"iPhone2,1": @163,
+ @"iPhone3,1": @326,
+ @"iPhone3,2": @326,
+ @"iPhone3,3": @326,
+ @"iPhone4,1": @326,
+ @"iPhone5,1": @326,
+ @"iPhone5,2": @326,
+ @"iPhone5,3": @326,
+ @"iPhone5,4": @326,
+ @"iPhone6,1": @326,
+ @"iPhone6,2": @326,
+ @"iPhone7,1": @401,
+ @"iPhone7,2": @326,
+ @"iPhone8,1": @326,
+ @"iPhone8,2": @401,
+ @"iPhone8,4": @326,
+ @"iPhone9,1": @326,
+ @"iPhone9,2": @401,
+ @"iPhone9,3": @326,
+ @"iPhone9,4": @401,
+ @"iPhone10,1": @326,
+ @"iPhone10,2": @401,
+ @"iPhone10,3": @458,
+ @"iPhone10,4": @326,
+ @"iPhone10,5": @401,
+ @"iPhone10,6": @458,
+ @"iPhone11,2": @458,
+ @"iPhone11,4": @458,
+ @"iPhone11,6": @458,
+ @"iPhone11,8": @326,
+ @"iPhone12,1": @326,
+ @"iPhone12,3": @458,
+ @"iPhone12,5": @458,
+ @"iPad1,1": @132,
+ @"iPad2,1": @132,
+ @"iPad2,2": @132,
+ @"iPad2,3": @132,
+ @"iPad2,4": @132,
+ @"iPad2,5": @163,
+ @"iPad2,6": @163,
+ @"iPad2,7": @163,
+ @"iPad3,1": @264,
+ @"iPad3,2": @264,
+ @"iPad3,3": @264,
+ @"iPad3,4": @264,
+ @"iPad3,5": @264,
+ @"iPad3,6": @264,
+ @"iPad4,1": @264,
+ @"iPad4,2": @264,
+ @"iPad4,3": @264,
+ @"iPad4,4": @326,
+ @"iPad4,5": @326,
+ @"iPad4,6": @326,
+ @"iPad4,7": @326,
+ @"iPad4,8": @326,
+ @"iPad4,9": @326,
+ @"iPad5,1": @326,
+ @"iPad5,2": @326,
+ @"iPad5,3": @264,
+ @"iPad5,4": @264,
+ @"iPad6,3": @264,
+ @"iPad6,4": @264,
+ @"iPad6,7": @264,
+ @"iPad6,8": @264,
+ @"iPad6,11": @264,
+ @"iPad6,12": @264,
+ @"iPad7,1": @264,
+ @"iPad7,2": @264,
+ @"iPad7,3": @264,
+ @"iPad7,4": @264,
+ @"iPad7,5": @264,
+ @"iPad7,6": @264,
+ @"iPad7,11": @264,
+ @"iPad7,12": @264,
+ @"iPad8,1": @264,
+ @"iPad8,2": @264,
+ @"iPad8,3": @264,
+ @"iPad8,4": @264,
+ @"iPad8,5": @264,
+ @"iPad8,6": @264,
+ @"iPad8,7": @264,
+ @"iPad8,8": @264,
+ @"iPad11,1": @326,
+ @"iPad11,2": @326,
+ @"iPad11,3": @326,
+ @"iPad11,4": @326,
+ @"iPod1,1": @163,
+ @"iPod2,1": @163,
+ @"iPod3,1": @163,
+ @"iPod4,1": @326,
+ @"iPod5,1": @326,
+ @"iPod7,1": @326,
+ @"iPod9,1": @326,
+ };
+
+ struct utsname systemInfo;
+ uname(&systemInfo);
+ NSString* deviceName =
+ [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
+ id foundDPI = devices[deviceName];
+ if (foundDPI) {
+ self.screenDPI = (float)[foundDPI integerValue];
+ } else {
+ /*
+ * Estimate the DPI based on the screen scale multiplied by the base DPI for the device
+ * type (e.g. based on iPhone 1 and iPad 1)
+ */
+ #if __IPHONE_OS_VERSION_MIN_REQUIRED >= 80000
+ float scale = (float)screen.nativeScale;
+ #else
+ float scale = (float)screen.scale;
+ #endif
+ float defaultDPI;
+ if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
+ defaultDPI = 132.0f;
+ } else if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone) {
+ defaultDPI = 163.0f;
+ } else {
+ defaultDPI = 160.0f;
+ }
+ self.screenDPI = scale * defaultDPI;
+ }
+ }
+ return self;
+}
+
@synthesize uiscreen;
+@synthesize screenDPI;
@end
@@ -153,14 +294,12 @@ UIKit_AddDisplay(UIScreen *uiscreen)
display.current_mode = mode;
/* Allocate the display data */
- SDL_DisplayData *data = [[SDL_DisplayData alloc] init];
+ SDL_DisplayData *data = [[SDL_DisplayData alloc] initWithScreen:uiscreen];
if (!data) {
UIKit_FreeDisplayModeData(&display.desktop_mode);
return SDL_OutOfMemory();
}
- data.uiscreen = uiscreen;
-
display.driverdata = (void *) CFBridgingRetain(data);
SDL_AddVideoDisplay(&display);
@@ -244,6 +383,27 @@ UIKit_GetDisplayModes(_THIS, SDL_VideoDisplay * display)
}
int
+UIKit_GetDisplayDPI(_THIS, SDL_VideoDisplay * display, float * ddpi, float * hdpi, float * vdpi)
+{
+ @autoreleasepool {
+ SDL_DisplayData *data = (__bridge SDL_DisplayData *) display->driverdata;
+ float dpi = data.screenDPI;
+
+ if (ddpi) {
+ *ddpi = dpi * (float)SDL_sqrt(2.0);
+ }
+ if (hdpi) {
+ *hdpi = dpi;
+ }
+ if (vdpi) {
+ *vdpi = dpi;
+ }
+ }
+
+ return 0;
+}
+
+int
UIKit_SetDisplayMode(_THIS, SDL_VideoDisplay * display, SDL_DisplayMode * mode)
{
@autoreleasepool {