Quote Originally Posted by ghoul View Post
The warning has no implications on your side. To get around it you can cast your string to const char *
Code:
   if (strcmp((const char *)text.value, "xterm") != 0)
By the way should that be:

Code:
  if (strcmp((const char *)text.value, "xterm") == 0)
The signature mostly guides the API developers(strcmp in this case) into making sure the two strings are not modified from within the function/API.
This code worked fine. I thought it was something to do with casting but didn't know how. I've started reading 'C Primer Plus' to refresh my knowledge of C, so that should help with the common knowledge questions like like.

Code:
john.c
Try replacing lines 58 and 59 with this: Code: if (text.format != 8) printf("bad format\n"); else { char *v = text.value; while (*v) { if (strcmp(v, "xterm"); printf("xterm found\n"); v += strlen(v); } }
I'm liking this text.format variable to indicate bad format. Very nice.

The reason why I asked this question is to be able to tell if there's an open window on the screen (and to manipulate it if it meets the conditions) or to see if there are no windows open, and in that case just do nothing.

The program's objective is to continually poll the focused window, panel, and virtual keyboard, and to change the width of the virtual keyboard if the panel is up or the height/width of the focused application depending on if the keyboard or panel is up. This way, screen space is always be used as efficiently as possible, and the virtual keyboard never overlaps the windows. I have this working just fine with some inefficient code that calls external programs as marked within the code.

The efficient program works perfectly so long as there is always a window on the screen; else, the XResizeWindow() command tries to resize the root desktop (I presume), and thus ends in either a bad window error or creates a dead window on the screen, which stays there indefinitely.

focused.c
Code:
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <time.h>
#include <string.h>

// gcc -Wall focused.c -o focused -lX11 && focused

XTextProperty text;
char *name;

Window get_toplevel_parent(Display * display, Window window)
{
     Window parent;
     Window root;
     Window * children;
     unsigned int num_children;

     while (1) {

         if (0 == XQueryTree(display, window, &root,
                   &parent, &children, &num_children)) {

             fprintf(stderr, "XQueryTree error\n");
             abort();
         }

         if (children)
             XFree(children);
                  
         if (window == root || parent == root) {
 
             return window;

         } else {

            // better at grabbing window names
            XGetWMName(display, window, &text);

            window = parent;

            // worse at grabbing window names
            XFetchName(display, window, &name);
        } 
    }
}

int main(int argc, char *argv[]) {

   Display *display; // 800x480
   Window focus, toplevel_parent_of_focus, window, last_window;
   XWindowAttributes attr;
   int revert, winNum, winPid, winX, winY = 240;
   char pidline [64] = "";
   char command [64] = "";
   char winName [64] = "";

   FILE *fpid;

   display = XOpenDisplay(NULL);

   // svkbd = virtual keyboard
   // panel = vertical panel on right side of screen    
   int svkbd, last_svkbd = 0, panel, last_panel = 0, last_window_x = 0, last_window_y = 0, last_win_x = 0;

   while (1) {

      XGetInputFocus(display, &focus, &revert);
      toplevel_parent_of_focus = get_toplevel_parent(display, focus);

      // check if the virtual keyboard is on 
      pidline[0] = '\0';
      fpid = popen("pidof svkbd-en&", "r");
      if (fgets(pidline, 64, fpid) != 0)
         svkbd = 1;
      else
         svkbd = 0;
      pclose(fpid);

      // Check if panel is up
      pidline[0] = '\0';
      fpid = popen("pidof panel&", "r");
      if (fgets(pidline, 64, fpid) != 0)
         panel = 1;
      else
         panel = 0;
      pclose(fpid);

      // Get focused window
      window = (unsigned)toplevel_parent_of_focus;
      printf("Name: %s\n", (const char *)text.value);

      // Only execute if current changes will affect the virt. keyboard or focused app; don't try to change to the same size 
      if ((svkbd != last_svkbd || panel != last_panel || window != last_window || attr.width != last_window_x || attr.height != last_window_y) ) {

         // Working but inefficient code
 /*      printf("Change found: %s\n", command);
         pidline[0] = '\0';
         fpid = popen("xdotool getactivewindow; xdotool getwindowname $(xdotool getactivewindow) &", "r");
         fgets(pidline, 64, fpid);
         winNum = strtoul(pidline, NULL, 10);
         pidline[0] = '\0';
         fgets(pidline, 64, fpid);
         strcpy(winName, pidline);
         winName[strlen(winName) - 1 ] = '\0'; 
         printf("PID: %i name: '%s'\n", winNum, winName);
         pclose(fpid);

         // This seems to notice the desktop (which is apparently called 'Openbox' but can be different depending on what program is grabbing the screen name
         if (strcmp(winName, "Menu") != 0 &&
             strcmp(winName, "Openbox") != 0) {*/
 
            if (panel == 1)
               winX = 750; // panel = 50 wide (scr. 800-50)
            else
               winX = 800; // and screen is 800 wide

            if (svkbd == 1)
               winY = 240; // virt. keyboard is 240 high
            else
               winY = 480; // screen is 480 high

// Several attempts to stop desktop from getting through
// The code below must not be executed if no window is open in the window manager
            if (strcmp(winName, "Openbox") != 0 && text.format == 8 && text.value != NULL && strcmp((const char *)text.value, "") != 0 && strcmp((const char *)text.value, "(null)") != 0 && strcmp((const char *)text.value, "Openbox") != 0 && strcmp((const char *)text.value, "Menu") != 0) {

               // Working inefficient code to adjust wndw size
               /*snprintf(command, sizeof command, "xdotool windowsize %i %i %i", winNum, winX, winY); 
               fpid = popen(command, "r");
               pclose(fpid);*/

               // Effient but non-working code
               XGetWindowAttributes(display, toplevel_parent_of_focus, &attr);
               // I believe this func. might be causing the
               // bad window error when it is executed when no windows are up
               XResizeWindow(display, window, winX, winY); 
            }

            // only refresh virtual keyboard if size is to be changed
            if (svkbd == 1 && ((last_win_x != winX &&  last_svkbd == svkbd) || (last_svkbd != svkbd && panel == 1))) {

               // Will later use execl call but not apriority atm
               if (panel == 1) 
                  fpid = popen("killall svkbd-en; svkbd-en -d -g 750x240 &", "r");
               else            
                  fpid = popen("killall svkbd-en; svkbd-en -d -g 800x240 &", "r");

               pclose(fpid);
            //}
         }
      }

      last_svkbd = svkbd;
      last_panel = panel;
      last_window = window;
      last_window_x = attr.width;
      last_window_y = attr.height;
      last_win_x = winX;

      // sleep one sec (or less if needed) 
      usleep(1000000);

   }

   return 0;
}