Aguardar que uma janela X apareça / desapareça (de uma maneira sã)

9

Dentro de um script de shell, eu preciso esperar por uma janela que tenha uma string em seu título para aparecer, fazer alguma ação, e então esperar que ela desapareça, e fazer alguma outra ação.

Até ontem, eu tinha esse código simples. O problema é que o disco não pode ser colocado em um estado de economia de energia enquanto o script é executado, e pode ser por muitas horas:

while :; do
    until wmctrl -l | grep -q "$string"; do   # until
        sleep 0.5
    done
    : do action 1

    while wmctrl -l | grep -q "$string"; do   # while
        sleep 0.5
    done
    : do action 2
done

Como decidi que o código mencionado estava ativamente ativando o disco, examinei a documentação de algumas ferramentas de linha de comando e decidi que xdotool aguardasse a exibição da janela e xprop descobrir quando a janela janela desapareceu:

while :; do
    # we use 'until' because sometimes xdotool just crashes
    until xdotool search -sync -all -onlyvisible -pid $pid -name "$string"; do
        :
    done

    # xdotool isn't trustworthy either, so check again
    wmctrl -l | grep -q "$string" ||
        continue

    : do action 1

    xprop -spy -root _NET_CLIENT_LIST_STACKING | while read line; do
        if [[ ! ${_line:-} || $_line = $line ]]; then
            _line=$line
            continue
        else
            _line=$line
            if wmctrl -l | grep -q "$string"; then
                continue
            else
                : do action 2
                break
            fi
        fi
    done
done

Agora tenho dois novos problemas com o código acima:

  • O xdotool não apenas trava e dá resultados estranhos, como eu já trabalhei antes, mas também suga cerca de 15% da CPU enquanto aguarda a janela para aparecer. Então, isso significa que me livrei de código simples que desperta o disco, para escrever código que fica perdendo a CPU por horas, e minha intenção era economizar energia em primeiro lugar.
  • xprop -spy me notificará sempre que eu mudar o foco (que eu tenho contornado através de $_line ) ou criar e destruir janelas. Isso acorda o disco com mais frequência do que xdotool.

Estou procurando um programa simples que aguarde até que a janela com o título $string apareça ou desapareça. Pode ser uma ferramenta de linha de comando existente, um script python, código C compilável ..., mas eu deveria ser capaz de integrá-lo de alguma forma ao meu script (mesmo que ele apenas grave algumas informações em um fifo)!

    
por Teresa e Junior 07.05.2013 / 21:39

2 respostas

3

Isso deve dar a você todas as atividades do sistema de arquivos (OK: mais. O que eu esqueci? Sockets?) que incluem gravações:

strace -f command 2>&1 | 
  grep -e '^open.*O_CREAT' \
    -e ^write   \
    -e ^mkdir   \
    -e ^rmdir   \
    -e ^unlink  \
    -e ^rename  \
    -e ^chmod   \
    -e ^link    \
    -e ^symlink \
    -e ^mknod

Com esta informação, um ambiente chroot funcional pode ser criado no tmpfs (como uma ação de último recurso; talvez symlinks para tmpfs sejam suficientes). Se o programa for iniciado em um chroot de RAM, ele não terá a chance de ativar o disco diretamente. Nenhuma gravação em sua hierarquia de sistema de arquivos é gravada em disco.

    
por 07.05.2013 / 22:44
5

Pode ser mais simples, e mais confiável, confiar em seu gerenciador de janelas ou X11 para lidar com isso escrevendo um aplicativo X11 "real".

O que você quer do shell é algo que se registra com o gerenciador de janelas e espera por um tipo de evento desejado antes de retornar ao shell ... ele é muito mais fácil de carregar se você puder evitar o loop dentro do shell. (Seu until xdotool... causa carga porque não há atraso (suspensão) dentro do loop).

Ah ... aparentemente xdotool tinha esse recurso adicionado há mais de um ano --sync . Isso não está disponível na minha distribuição Linux atual (Debian Squeeze), então eu não tentei.

O desenvolvedor xdotool responde a uma pergunta semelhante à sua: link

    
por 07.05.2013 / 23:45