[unix] 삭제시 텍스트 / 화면 깜박임 방지

내 스크립트는 다음과 같은 작업을 수행합니다.

while :;
   clear

   do_a_lot_of_output_here

   sleep 1
done

선명하고 출력 할 때 화면이 깜박이지 않도록하는 옵션이 있습니까? 나는 watch명령 에서처럼하고 싶지만 (하지만 작성되었습니다 C). 조언이 있습니까?

clear | hexdump -C

00000000  1b 5b 48 1b 5b 32 4a                              |.[H.[2J|
00000007

추신. 나는 bash단지 사용 하고 있습니다.



답변

스크립트가 전체 화면을 지우기 때문에 깜박임이 발생합니다. 기존 텍스트 위에 페인트하고 필요한 경우에만 지우면 깜박임이 없습니다.

예를 들면 다음과 같습니다.

#!/bin/sh
watchit() {
    HOME=$(tput cup 0 0)
    ED=$(tput ed)
    EL=$(tput el)
    ROWS=$(tput lines)
    COLS=$(tput cols)
    printf '%s%s' "$HOME" "$ED"
    while true
    do
        CMD="$@"
        ${SHELL:=sh} -c "$CMD" | head -n $ROWS | while IFS= read LINE; do
            printf '%-*.*s%s\n' $COLS $COLS "$LINE" "$EL"
        done
        printf '%s%s' "$ED" "$HOME"
        sleep 1
    done
}

watchit top -b -n 1

이렇게합니다 :

  • 화면에 맞는 주어진 명령의 출력을 인쇄합니다 (랩핑 또는 스크롤 없음).
  • 덮어 쓰지 않은 각 줄의 일부를 지우면서 기존 줄을 덮어 씁니다.
  • ed터미널 의 기능을 사용하여 현재 위치에서 화면 끝까지 인쇄합니다.

당신이 크기 조정 화면을 처리하기 원한다면, 당신이 할당을 움직일 수 ROWSCOLS외부 루프 내부에, 예를 들면,

#!/bin/sh
watchit() {
    HOME=$(tput cup 0 0)
    ED=$(tput ed)
    EL=$(tput el)
    printf '%s%s' "$HOME" "$ED"
    while true
    do
        ROWS=$(tput lines)
        COLS=$(tput cols)
        CMD="$@"
        ${SHELL:=sh} -c "$CMD" | head -n $ROWS | while IFS= read LINE; do
            printf '%-*.*s%s\n' $COLS $COLS "$LINE" "$EL"
        done
        printf '%s%s' "$ED" "$HOME"
        sleep 1
    done
}

watchit top -b -n 1

tput시스템에서 현재 화면 크기를 요청하기 때문 입니다.

더 읽을 거리 :


답변

깜박임을 방지하는 한 가지 방법은 화면을 지우고 다시 그리는 데 최소 시간이 걸리도록 화면을 지우기 전에 모든 출력을 얻는 것입니다. 이것은 이중 버퍼링의 개념과 유사합니다.

while :; do
   output=$(do_a_lot_of_output_here)
   clear
   echo "$output"
   sleep 1
done

이것은 깜박임을 완전히 제거하지는 않지만 내 경험에서 훨씬 덜 자주 발생합니다.


답변

루프 주변에서 매번 화면을 지우면 깜박임이 불가피합니다. 커서를 화면 상단으로 이동하고 대신 기존 출력의 일부를 덮어 쓸 수 있습니다.

# You may want to do this if your code is in a script.
unhide_cursor() {
    printf '\e[?25h'
}
trap unhide_cursor EXIT

# Hide the cursor (there is probably a much better way to do this)
printf '\e[?25l'
clear 
while true ; do
    # Move the cursor to the top of the screen but don't clear the screen
    printf '\033[;H' 
    do_a_lot_of_output_here
    sleep 1
done

이 스크립트는 출력이 줄어들면 아티팩트를 남깁니다. 또한 휴대하기가 쉽지 않습니다. urxvt, xterm 및 st로만 테스트했습니다.


답변

Cristian의 답변을 확장하여 콘솔 창이 명령 출력보다 작을 때 작동하는 다음 bash 기능을 만들었습니다.

function watcher()
{
    lines=$(tput lines)
    while true; do
        output="$($@ | head -n $lines)"
        clear
        echo -e "$output"
        sleep 2
    done
}

이를 통해 감시자에게 모든 명령을 전달할 수 있습니다. git을 사용하는 경우 다음을 사용하십시오 git config --global color.status always.

watcher git status

항상 업데이트중인 git 상태 출력을 표시합니다.


답변