Автоматически делать снимок экрана с x сервером, если содержимое окна меняется - PullRequest
5 голосов
/ 29 января 2011

Я ищу способ автоматически сделать скриншот моего X-сервера, если окно создано или содержимое окна изменилось.

В настоящее время я достигаю этого, слушая события X11, но сообщается не обо всех изменениях.

Ответы [ 2 ]

5 голосов
/ 29 января 2011

Посмотрите на XDamageNotifyEvent, XDamageQueryExtension, XDamageCreate, XDamageSubtract из расширения Damage. Это расширение используется для отслеживания изменения содержимого окна. http://www.freedesktop.org/wiki/Software/XDamage

Хорошим источником примера кода будет все, что делает миниатюры окон. Кроме того, любой оконный менеджер композитинга (Compiz, некоторые разновидности metacity и т. Д.) Будет содержать код отслеживания повреждений.

Без расширения, вы в основном должны опрашивать (обновлять содержимое окна за тайм-аут).

2 голосов
/ 31 августа 2015

Я знаю, что этот пост довольно мертв. И все же документация по X11 ужасна, и мне потребовалось много времени, чтобы заставить XDamage работать в любом случае. Итак, вот пример, который будет выводить строку на консоль каждый раз, когда изменяется корневое окно X11, на основе документации, упомянутой в посте Havoc, и свободно на основе этой ссылки :

#include <stdio.h>
#include <stdlib.h>
#include <X11/extensions/Xdamage.h>
#include <X11/Xlib.h>
#include <signal.h>

int endnow = 0;

void cleanup(int SIGNUM){
    endnow = 1;
}

int main(){
    Display *display;
    display = XOpenDisplay(":0");
    if(!display){
        perror("could not open display");
        exit(1);
    }
    Window root = DefaultRootWindow(display);        

    int damage_event, damage_error, test;

    //this line is necessary to initialize things
    test = XDamageQueryExtension(display, &damage_event, &damage_error);
    /*The "event" output is apparently the integer that appears in the
    Xevent.type field when XNextEvent returns an XDamage event */
    printf("test = %d, event = %d, error = %d\n",test,damage_event, damage_error);

    //This is the handler for the XDamage interface
    //See the XDamage documentation for more damage report levels
    // http://www.freedesktop.org/wiki/Software/XDamage
    Damage damage = XDamageCreate(display, root, XDamageReportNonEmpty);

    signal(SIGINT,cleanup);

    // XCloseDisplay(display);
    while(endnow == 0){
        XEvent event;
        XNextEvent(display,&event);
        printf("event.type = %d\n",event.type);
        //this line resets the XDamage handler
        XDamageSubtract(display,damage,None,None);
    }
    XCloseDisplay(display);
    printf("done\n");
    exit(0);
}

Естественно, если вы запустите это с консоли на том же экране, что и ваш дисплей :0, каждая напечатанная строка будет активироваться сама по себе, и будет немного нестабильна. Но это хорошая демонстрация, если вы запускаете его с терминала ssh на другом компьютере.

...