mirror of
https://github.com/fastfetch-cli/fastfetch.git
synced 2026-10-30 00:37:23 +01:00
Using EWMH to detect WM in X11 sessions
This commit is contained in:
@@ -266,6 +266,13 @@ static void getWMProtocolNameFromEnv(FFDisplayServerResult* result)
|
||||
return;
|
||||
}
|
||||
|
||||
env = getenv("DISPLAY");
|
||||
if(env != NULL && *env != '\0')
|
||||
{
|
||||
ffStrbufSetS(&result->wmProtocolName, FF_DISPLAYSERVER_PROTOCOL_X11);
|
||||
return;
|
||||
}
|
||||
|
||||
env = getenv("TERM");
|
||||
if(env != NULL && *env != '\0')
|
||||
{
|
||||
@@ -308,7 +315,7 @@ static void getFromProcDir(const FFinstance* instance, FFDisplayServerResult* re
|
||||
if(result->wmPrettyName.length == 0)
|
||||
applyPrettyNameIfWM(result, processName.chars);
|
||||
|
||||
if(result->deProcessName.length > 0 && result->wmPrettyName.length > 0)
|
||||
if(result->dePrettyName.length > 0 && result->wmPrettyName.length > 0)
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -324,6 +331,19 @@ void ffdsDetectWMDE(const FFinstance* instance, FFDisplayServerResult* result)
|
||||
if(result->wmProtocolName.length == 0)
|
||||
getWMProtocolNameFromEnv(result);
|
||||
|
||||
//We don't want to detect anything in TTY
|
||||
if(ffStrbufIgnCaseCompS(&result->wmProtocolName, FF_DISPLAYSERVER_PROTOCOL_TTY) == 0)
|
||||
return;
|
||||
|
||||
//If we found the processName via display server, use it.
|
||||
//This will set the pretty name if it is a known WM, otherwise the prettyName to the processName
|
||||
if(result->wmProcessName.length > 0)
|
||||
{
|
||||
applyPrettyNameIfWM(result, result->wmProcessName.chars);
|
||||
if(result->wmPrettyName.length == 0)
|
||||
ffStrbufSet(&result->wmPrettyName, &result->wmProcessName);
|
||||
}
|
||||
|
||||
const char* env = parseEnv();
|
||||
|
||||
//Connecting to a display server only gives WM results, not DE results.
|
||||
|
||||
@@ -3,6 +3,70 @@
|
||||
#ifdef FF_HAVE_X11
|
||||
#include <X11/Xlib.h>
|
||||
|
||||
typedef struct X11PropertyData
|
||||
{
|
||||
FF_LIBRARY_SYMBOL(XInternAtom)
|
||||
FF_LIBRARY_SYMBOL(XGetWindowProperty)
|
||||
} X11PropertyData;
|
||||
|
||||
static unsigned char* x11GetProperty(X11PropertyData* data, Display* display, Window window, const char* request)
|
||||
{
|
||||
Atom requestAtom = data->ffXInternAtom(display, request, False);
|
||||
if(requestAtom == None)
|
||||
return NULL;
|
||||
|
||||
Atom actualType;
|
||||
unsigned long unused;
|
||||
unsigned char* result = NULL;
|
||||
|
||||
data->ffXGetWindowProperty(
|
||||
display,
|
||||
window,
|
||||
requestAtom,
|
||||
0,
|
||||
64,
|
||||
False,
|
||||
AnyPropertyType,
|
||||
&actualType,
|
||||
(int*) &unused,
|
||||
&unused,
|
||||
&unused,
|
||||
&result
|
||||
);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static void x11DetectWMFromEWMH(X11PropertyData* data, Display* display, FFDisplayServerResult* result)
|
||||
{
|
||||
if(result->wmProcessName.length > 0)
|
||||
return;
|
||||
|
||||
Window root = DefaultRootWindow(display);
|
||||
if(root == None)
|
||||
return;
|
||||
|
||||
unsigned char* wmWindowID = x11GetProperty(data, display, root, "_NET_SUPPORTING_WM_CHECK");
|
||||
if(wmWindowID == NULL)
|
||||
return;
|
||||
|
||||
Window wmWindow = *(Window*) wmWindowID;
|
||||
if(wmWindow == None)
|
||||
return;
|
||||
|
||||
unsigned char* wmName = x11GetProperty(data, display, wmWindow, "_NET_WM_NAME");
|
||||
if(wmName == NULL)
|
||||
wmName = x11GetProperty(data, display, wmWindow, "WM_NAME");
|
||||
if(wmName == NULL)
|
||||
return;
|
||||
|
||||
const char* wmNameString = (const char*) wmName;
|
||||
if(*wmNameString == '\0')
|
||||
return;
|
||||
|
||||
ffStrbufSetS(&result->wmProcessName, wmNameString);
|
||||
}
|
||||
|
||||
static void x11AddScreenAsResult(FFlist* results, Screen* screen, uint32_t refreshRate)
|
||||
{
|
||||
if(WidthOfScreen(screen) == 0 || HeightOfScreen(screen) == 0)
|
||||
@@ -20,6 +84,10 @@ void ffdsConnectXlib(const FFinstance* instance, FFDisplayServerResult* result)
|
||||
FF_LIBRARY_LOAD_SYMBOL(x11, XOpenDisplay,)
|
||||
FF_LIBRARY_LOAD_SYMBOL(x11, XCloseDisplay,)
|
||||
|
||||
X11PropertyData propertyData;
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(x11, propertyData.ffXInternAtom, XInternAtom,)
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(x11, propertyData.ffXGetWindowProperty, XGetWindowProperty,)
|
||||
|
||||
Display* display = ffXOpenDisplay(x11);
|
||||
if(display == NULL)
|
||||
{
|
||||
@@ -30,6 +98,8 @@ void ffdsConnectXlib(const FFinstance* instance, FFDisplayServerResult* result)
|
||||
for(int i = 0; i < ScreenCount(display); i++)
|
||||
x11AddScreenAsResult(&result->resolutions, ScreenOfDisplay(display, i), 0);
|
||||
|
||||
x11DetectWMFromEWMH(&propertyData, display, result);
|
||||
|
||||
ffXCloseDisplay(display);
|
||||
dlclose(x11);
|
||||
|
||||
@@ -216,6 +286,10 @@ void ffdsConnectXrandr(const FFinstance* instance, FFDisplayServerResult* result
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(xrandr, data.ffXRRFreeMonitors, XRRFreeMonitors,);
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(xrandr, data.ffXRRFreeScreenConfigInfo, XRRFreeScreenConfigInfo,);
|
||||
|
||||
X11PropertyData propertyData;
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(xrandr, propertyData.ffXInternAtom, XInternAtom,)
|
||||
FF_LIBRARY_LOAD_SYMBOL_ADRESS(xrandr, propertyData.ffXGetWindowProperty, XGetWindowProperty,)
|
||||
|
||||
data.display = ffXOpenDisplay(NULL);
|
||||
if(data.display == NULL)
|
||||
{
|
||||
@@ -228,6 +302,8 @@ void ffdsConnectXrandr(const FFinstance* instance, FFDisplayServerResult* result
|
||||
for(int i = 0; i < ScreenCount(data.display); i++)
|
||||
xrandrHandleScreen(&data, ScreenOfDisplay(data.display, i));
|
||||
|
||||
x11DetectWMFromEWMH(&propertyData, data.display, result);
|
||||
|
||||
ffXCloseDisplay(data.display);
|
||||
dlclose(xrandr);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user