Bagaimana kurang tahu resolusi terminal?


12

Setiap kali seseorang menetapkan ukuran yang berbeda untuk konsol virtual, lessmengenali resolusi jendela (saya berasumsi bahwa ...); menurut itu, ia mengubah berapa banyak baris teks yang harus divisualisasikan. Bagaimana parameter itu dihitung?


Uhm ... ok, tapi di mana saya bisa menemukan prosedur yang dijalankan?
Giuseppe Crinò

Jawaban:


22

Jika Anda mencari cara untuk memeriksa dari skrip, Anda dapat melakukan salah satu dari ini:

  • Jalankan tput colsdan tput lines, seperti yang disarankan manatwork
  • periksa nilai $ LINES dan $ COLUMNS

Tetapi jika Anda menginginkan detailnya, ini dia:

Untuk terminal virtual (xterm, et al) ada ioctl()panggilan sistem yang akan memberi tahu Anda ukuran jendela itu. Jika bisa, lessgunakan panggilan ini. Selain itu, ketika Anda mengubah ukuran jendela, apa pun yang berjalan di jendela itu menerima SIGWINCHsinyal yang memberi lesstahu bahwa itu harus memeriksa ukuran jendela baru. Sebagai contoh, saya mulai lessmenjalankan (sebagai ID proses 16663), terhubung dengannya strace, dan mengubah ukuran jendela. Inilah yang saya lihat:

$ strace -p 16663
Process 16663 attached - interrupt to quit
read(3, 0xbfb1f10f, 1)                  = ? ERESTARTSYS (To be restarted)
--- SIGWINCH (Window changed) @ 0 (0) ---
rt_sigaction(SIGWINCH, {0x805cf10, [WINCH], SA_RESTART}, {0x805cf10, [WINCH], SA_RESTART}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
ioctl(1, SNDCTL_TMR_TIMEBASE or TCGETS, {B38400 opost isig -icanon -echo ...}) = 0
ioctl(1, SNDCTL_TMR_TIMEBASE or TCGETS, {B38400 opost isig -icanon -echo ...}) = 0
ioctl(1, TIOCGWINSZ, {ws_row=40, ws_col=80, ws_xpixel=0, ws_ypixel=0}) = 0
ioctl(2, TIOCGWINSZ, {ws_row=40, ws_col=80, ws_xpixel=0, ws_ypixel=0}) = 0

Ini juga apa tput colsdan tput lineslakukan di belakang layar, jika mereka bisa. Untuk info lebih lanjut tentang metode ini, lihat man tty-ioctldan cari TIOCGWINSZ.

Untuk terminal lain seperti yang terhubung ke port serial, tidak ada cara untuk mendapatkan info ini secara langsung. Dalam hal itu, lessmulailah mencari petunjuk dalam variabel lingkungan.

  • LINESdan COLUMNSakan sering diatur ke dimensi terminal. Bahkan, jika bashatau zshdapat menemukan dimensi terminal, ia akan secara otomatis mengatur variabel-variabel ini sendiri, untuk memudahkan program yang tidak terlalu pintar untuk melihat ukuran terminal. Namun, kebanyakan shell lain, termasuk dashdan tcsh, tidak mengatur variabel-variabel ini.
  • TERMbiasanya diatur ke tipe terminal, dalam hal ini basis data terminfo dapat berisi ukuran terminal yang diharapkan. Jika tput rowstidak dapat menggunakan IOCTL (misalnya, jika Anda terhubung melalui port serial), itu akan kembali ke nilai yang dicatat di sini. Untuk terminal yang ukurannya bisa berubah, ini hanya dugaan dan kemungkinan salah.

Untuk info lebih lanjut, lihat man tputperintah untuk mengendalikan terminal, dan man terminfountuk daftar hal-hal yang bisa Anda katakan kepada terminal.


Database terminfo tidak melakukan apa yang ditunjukkan di sini. Jawaban oleh @ warl0ck, yang berisi lebih sedikit informasi, lebih akurat.
Thomas Dickey

@ThomasDickey Anda benar; semua itu memiliki nilai yang diharapkan. Koreksi jawaban saya; Terima kasih.
Jander

7

Jika Anda melihat kode sumbernya, Anda akan tahu lesspanggilan ioctl()untuk mengambil ukuran jendela di Linux.

#ifdef TIOCGWINSZ
    {
        struct winsize w;
        if (ioctl(2, TIOCGWINSZ, &w) == 0)
        {
            if (w.ws_row > 0)
                sys_height = w.ws_row;
            if (w.ws_col > 0)
                sys_width = w.ws_col;
        }
    }
#else
#ifdef WIOCGETD
    {
        struct uwdata w;
        if (ioctl(2, WIOCGETD, &w) == 0)
        {
            if (w.uw_height > 0)
                sys_height = w.uw_height / w.uw_vs;
            if (w.uw_width > 0)
                sys_width = w.uw_width / w.uw_hs;
        }
    }
#endif

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.