In x11, GetDisplayDPI can give incorrect or unusable DPI information. Using XGetDefaults to get the Xft DPI if it's available and returning that. This could allow you to figure out DPI scale.

This commit is contained in:
Kyle Schaefer 2021-03-22 11:22:31 -07:00 committed by Sam Lantinga
parent 6a2af48ad7
commit c289bad900
2 changed files with 33 additions and 0 deletions

View File

@ -345,6 +345,29 @@ SetXRandRDisplayName(Display *dpy, Atom EDID, char *name, const size_t namelen,
#endif
}
static int
GetXftDPI(Display* dpy)
{
char* xdefault_resource;
int xft_dpi, err;
xdefault_resource = X11_XGetDefault(dpy, "Xft", "dpi");
if(!xdefault_resource) {
return 0;
}
/*
* It's possible for SDL_atoi to call strtol, if it fails due to a
* overflow or an underflow, it will return LONG_MAX or LONG_MIN and set
* errno to ERANGE. So we need to check for this so we dont get crazy dpi
* values
*/
xft_dpi = SDL_atoi(xdefault_resource);
err = errno;
return err == ERANGE ? 0 : xft_dpi;
}
static int
X11_InitModes_XRandR(_THIS)
@ -417,6 +440,7 @@ X11_InitModes_XRandR(_THIS)
RRMode modeID;
RRCrtc output_crtc;
XRRCrtcInfo *crtc;
float xft_dpi;
/* The primary output _should_ always be sorted first, but just in case... */
if ((looking_for_primary && (res->outputs[output] != primary)) ||
@ -471,6 +495,14 @@ X11_InitModes_XRandR(_THIS)
displaydata->hdpi = display_mm_width ? (((float) mode.w) * 25.4f / display_mm_width) : 0.0f;
displaydata->vdpi = display_mm_height ? (((float) mode.h) * 25.4f / display_mm_height) : 0.0f;
displaydata->ddpi = SDL_ComputeDiagonalDPI(mode.w, mode.h, ((float) display_mm_width) / 25.4f,((float) display_mm_height) / 25.4f);
/* if xft dpi is available we will use this over xrandr */
xft_dpi = (float)GetXftDPI(dpy);
if(xft_dpi > 0) {
displaydata->hdpi = xft_dpi;
displaydata->vdpi = xft_dpi;
}
displaydata->scanline_pad = scanline_pad;
displaydata->x = display_x;
displaydata->y = display_y;

View File

@ -138,6 +138,7 @@ SDL_X11_SYM(int,XWarpPointer,(Display* a,Window b,Window c,int d,int e,unsigned
SDL_X11_SYM(int,XWindowEvent,(Display* a,Window b,long c,XEvent* d),(a,b,c,d),return)
SDL_X11_SYM(Status,XWithdrawWindow,(Display* a,Window b,int c),(a,b,c),return)
SDL_X11_SYM(VisualID,XVisualIDFromVisual,(Visual* a),(a),return)
SDL_X11_SYM(char*,XGetDefault,(Display* a,char* b, char* c),(a,b,c),return)
#if SDL_VIDEO_DRIVER_X11_CONST_PARAM_XEXTADDDISPLAY
SDL_X11_SYM(XExtDisplayInfo*,XextAddDisplay,(XExtensionInfo* a,Display* b,_Xconst char* c,XExtensionHooks* d,int e,XPointer f),(a,b,c,d,e,f),return)
#else