Ticket #4256: scrollbars_improvements.patch

File scrollbars_improvements.patch, 20.8 KB (added by kybl, 14 months ago)

Patch

  • lib/widget/listbox.c

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget/listbox.c b/lib/widget/listbox.c
    a b  
    8585 
    8686/* --------------------------------------------------------------------------------------------- */ 
    8787 
    88 static void 
    89 listbox_drawscroll (WListbox * l) 
    90 { 
    91     Widget *w = WIDGET (l); 
    92     int max_line = w->lines - 1; 
    93     int line = 0; 
    94     int i; 
    95     int length; 
    96  
    97     /* Are we at the top? */ 
    98     widget_gotoyx (w, 0, w->cols); 
    99     if (l->top == 0) 
    100         tty_print_one_vline (TRUE); 
    101     else 
    102         tty_print_char ('^'); 
    103  
    104     length = g_queue_get_length (l->list); 
    105  
    106     /* Are we at the bottom? */ 
    107     widget_gotoyx (w, max_line, w->cols); 
    108     if (l->top + w->lines == length || w->lines >= length) 
    109         tty_print_one_vline (TRUE); 
    110     else 
    111         tty_print_char ('v'); 
    112  
    113     /* Now draw the nice relative pointer */ 
    114     if (!g_queue_is_empty (l->list)) 
    115         line = 1 + ((l->pos * (w->lines - 2)) / length); 
    116  
    117     for (i = 1; i < max_line; i++) 
    118     { 
    119         widget_gotoyx (w, i, w->cols); 
    120         if (i != line) 
    121             tty_print_one_vline (TRUE); 
    122         else 
    123             tty_print_char ('*'); 
    124     } 
    125 } 
    126  
    127 /* --------------------------------------------------------------------------------------------- */ 
    128  
    12988static void 
    13089listbox_draw (WListbox * l, gboolean focused) 
    13190{ 
     
    183142 
    184143    l->cursor_y = sel_line; 
    185144 
    186     if (l->scrollbar && length > w->lines) 
     145    if (l->draw_scrollbar) 
    187146    { 
    188147        tty_setcolor (normalc); 
    189         listbox_drawscroll (l); 
     148        scrollbar_set_state (l->scrollbar, w->y - 1, w->x + w->cols - 1, w->lines + 2, g_queue_get_length (l->list), w->lines, l->top); 
     149        WIDGET (l->scrollbar)->callback (WIDGET (l->scrollbar), NULL, MSG_DRAW, 0, NULL); 
    190150    } 
    191151} 
    192152 
     
    440400static inline void 
    441401listbox_destroy (WListbox * l) 
    442402{ 
     403    widget_destroy (WIDGET (l->scrollbar)); 
    443404    listbox_remove_list (l); 
    444405} 
    445406 
     
    564525    l->deletable = deletable; 
    565526    l->callback = callback; 
    566527    l->allow_duplicates = TRUE; 
    567     l->scrollbar = !mc_global.tty.slow_terminal; 
     528    l->draw_scrollbar = !mc_global.tty.slow_terminal; 
     529    l->scrollbar = scrollbar_new (y, x + width - 1, height, TRUE); 
    568530 
    569531    return l; 
    570532} 
  • lib/widget/Makefile.am

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget/Makefile.am b/lib/widget/Makefile.am
    a b  
    2424        quick.c quick.h \ 
    2525        radio.c radio.h \ 
    2626        rect.c rect.h \ 
     27        scrollbar.c scrollbar.h \ 
    2728        widget-common.c widget-common.h \ 
    2829        wtools.c wtools.h 
    2930 
  • doc/man/mc.1.in

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/doc/man/mc.1.in b/doc/man/mc.1.in
    a b  
    19891989.I Show free space. 
    19901990If enabled, free space and total space of current file system is shown 
    19911991at the bottom frame of panel. Enabled by default. 
     1992.PP 
     1993.I Panel scrollbars. 
     1994Show scrollbars in main panels (on the right side). Enabled by default. 
    19921995.\"NODE "    Panel options" 
    19931996.SH "    Panel options" 
    19941997.B Main panel options 
  • lib/widget/listbox.h

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget/listbox.h b/lib/widget/listbox.h
    a b  
    4848    int pos;                    /* The current element displayed */ 
    4949    int top;                    /* The first element displayed */ 
    5050    gboolean allow_duplicates;  /* Do we allow duplicates on the list? */ 
    51     gboolean scrollbar;         /* Draw a scrollbar? */ 
     51    gboolean draw_scrollbar;    /* Draw a scrollbar? */ 
     52    WScrollbar *scrollbar;      /* Scrollbar widget */ 
    5253    gboolean deletable;         /* Can list entries be deleted? */ 
    5354    lcback_fn callback;         /* The callback function */ 
    5455    int cursor_x, cursor_y;     /* Cache the values */ 
  • src/filemanager/panel.h

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/src/filemanager/panel.h b/src/filemanager/panel.h
    a b  
    105105 
    106106    dir_list dir;               /* Directory contents */ 
    107107    struct stat dir_stat;       /* Stat of current dir: used by execute () */ 
     108    WScrollbar *scrollbar;      /* scrollbar of panel */ 
    108109 
    109110    vfs_path_t *cwd_vpath;      /* Current Working Directory */ 
    110111    vfs_path_t *lwd_vpath;      /* Last Working Directory */ 
  • src/filemanager/layout.h

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/src/filemanager/layout.h b/src/filemanager/layout.h
    a b  
    4646extern int output_start_y; 
    4747extern gboolean xterm_title; 
    4848extern gboolean free_space; 
     49extern gboolean panel_scrollbars; 
    4950extern gboolean nice_rotating_dash; 
    5051 
    5152extern int ok_to_refresh; 
  • src/setup.c

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/src/setup.c b/src/setup.c
    a b  
    274274    { "command_prompt", &command_prompt }, 
    275275    { "menubar_visible", &menubar_visible }, 
    276276    { "free_space", &free_space }, 
     277    { "panel_scrollbars", &panel_scrollbars }, 
    277278    { "horizontal_split", &panels_layout.horizontal_split }, 
    278279    { "vertical_equal", &panels_layout.vertical_equal }, 
    279280    { "horizontal_equal", &panels_layout.horizontal_equal }, 
  • lib/widget.h

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget.h b/lib/widget.h
    a b  
    2929#include "lib/widget/gauge.h" 
    3030#include "lib/widget/groupbox.h" 
    3131#include "lib/widget/label.h" 
     32#include "lib/widget/scrollbar.h" 
    3233#include "lib/widget/listbox.h" 
    3334#include "lib/widget/menu.h" 
    3435#include "lib/widget/radio.h" 
  • src/filemanager/layout.c

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/src/filemanager/layout.c b/src/filemanager/layout.c
    a b  
    100100/* Set to show free space on device assigned to current directory */ 
    101101gboolean free_space = TRUE; 
    102102 
     103/* Set to show scrollbars on main panels */ 
     104gboolean panel_scrollbars = TRUE; 
     105 
    103106/* The starting line for the output of the subprogram */ 
    104107int output_start_y = 0; 
    105108 
     
    133136    gboolean message_visible; 
    134137    gboolean xterm_title; 
    135138    gboolean free_space; 
     139    gboolean panel_scrollbars; 
    136140    int output_lines; 
    137141} layout_t; 
    138142 
     
    176180    { N_("&Keybar visible"), &mc_global.keybar_visible, NULL }, 
    177181    { N_("H&intbar visible"), &mc_global.message_visible, NULL }, 
    178182    { N_("&XTerm window title"), &xterm_title, NULL }, 
    179     { N_("&Show free space"), &free_space, NULL } 
     183    { N_("&Show free space"), &free_space, NULL }, 
     184    { N_("&Panel scrollbars"), &panel_scrollbars, NULL } 
    180185    /* *INDENT-ON* */ 
    181186}; 
    182187 
     
    466471                xterm_title = check_options[5].widget->state; 
    467472            else if (sender == WIDGET (check_options[6].widget)) 
    468473                free_space = check_options[6].widget->state; 
     474            else if (sender == WIDGET (check_options[7].widget)) 
     475                panel_scrollbars = check_options[7].widget->state; 
    469476            else 
    470477                ok = FALSE; 
    471478 
     
    678685    old_layout.message_visible = mc_global.message_visible; 
    679686    old_layout.xterm_title = xterm_title; 
    680687    old_layout.free_space = free_space; 
     688    old_layout.panel_scrollbars = panel_scrollbars; 
    681689    old_layout.output_lines = -1; 
    682690 
    683691    _output_lines = output_lines; 
     
    696704    mc_global.message_visible = old_layout.message_visible; 
    697705    xterm_title = old_layout.xterm_title; 
    698706    free_space = old_layout.free_space; 
     707    panel_scrollbars = old_layout.panel_scrollbars; 
    699708    output_lines = old_layout.output_lines; 
    700709 
    701710    panels_layout = old_panels_layout; 
  • src/filemanager/panel.c

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/src/filemanager/panel.c b/src/filemanager/panel.c
    a b  
    12581258{ 
    12591259    const Widget *w = CONST_WIDGET (panel); 
    12601260    gchar *tmp; 
     1261    int lines; 
    12611262 
    12621263    set_colors (panel); 
    12631264    tty_draw_box (w->y, w->x, w->lines, w->cols, FALSE); 
     1265    lines = panel_lines (panel); 
    12641266 
    12651267    if (panels_options.show_mini_info) 
    12661268    { 
    12671269        int y; 
    12681270 
    1269         y = panel_lines (panel) + 2; 
     1271        y = lines + 2; 
    12701272 
    12711273        widget_gotoyx (w, y, 0); 
    12721274        tty_print_alt_char (ACS_LTEE, FALSE); 
     
    12741276        tty_print_alt_char (ACS_RTEE, FALSE); 
    12751277    } 
    12761278 
     1279    if (panel_scrollbars) { 
     1280        scrollbar_set_state (panel->scrollbar, w->y + 1, w->x + w->cols - 1, lines + 2, panel->dir.len, 
     1281                             lines * panel->list_cols, panel->top_file); 
     1282    } 
     1283 
    12771284    widget_gotoyx (w, 0, 1); 
    12781285    tty_print_string (panel_history_prev_item_char); 
    12791286 
     
    13141321    { 
    13151322        if (panel->marked == 0) 
    13161323        { 
    1317             /* Show size of curret file in the bottom of panel */ 
     1324            /* Show size of current file in the bottom of panel */ 
    13181325            if (S_ISREG (panel->dir.list[panel->selected].st.st_mode)) 
    13191326            { 
    13201327                char buffer[BUF_SMALL]; 
     
    36483655        mc_event_add (h->event_group, MCEVENT_HISTORY_LOAD, panel_load_history, w, NULL); 
    36493656        /* subscribe to "history_save" event */ 
    36503657        mc_event_add (h->event_group, MCEVENT_HISTORY_SAVE, panel_save_history, w, NULL); 
     3658        panel->scrollbar = scrollbar_new (w->y + 1, w->x + w->cols - 1, w->lines, FALSE); 
     3659        return MSG_HANDLED; 
     3660 
     3661    case MSG_RESIZE: 
     3662        widget_default_callback (w, NULL, MSG_RESIZE, 0, data); 
     3663        if (panel->scrollbar != NULL) 
     3664            WIDGET (panel->scrollbar)->callback (WIDGET (panel->scrollbar), NULL, MSG_RESIZE, 0, NULL); 
    36513665        return MSG_HANDLED; 
    36523666 
    36533667    case MSG_DRAW: 
    36543668        /* Repaint everything, including frame and separator */ 
    36553669        widget_erase (w); 
    36563670        show_dir (panel); 
     3671        mini_info_separator (panel); 
    36573672        panel_print_header (panel); 
    36583673        adjust_top_file (panel); 
    36593674        paint_dir (panel); 
    3660         mini_info_separator (panel); 
    36613675        display_mini_info (panel); 
     3676 
     3677        if (panel_scrollbars) 
     3678            WIDGET (panel->scrollbar)->callback (WIDGET (panel->scrollbar), NULL, MSG_DRAW, 0, NULL); 
     3679 
    36623680        panel->dirty = FALSE; 
    36633681        return MSG_HANDLED; 
    36643682 
     
    37063724        mc_event_del (h->event_group, MCEVENT_HISTORY_LOAD, panel_load_history, w); 
    37073725        /* unsubscribe from "history_save" event */ 
    37083726        mc_event_del (h->event_group, MCEVENT_HISTORY_SAVE, panel_save_history, w); 
     3727        widget_destroy (WIDGET (panel->scrollbar)); 
    37093728        panel_destroy (panel); 
    37103729        free_my_statfs (); 
    37113730        return MSG_HANDLED; 
  • new file lib/widget/scrollbar.c

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget/scrollbar.c b/lib/widget/scrollbar.c
    new file mode 100644
    - +  
     1/* 
     2   Widgets for the Midnight Commander 
     3 
     4   Copyright (C) 2021 
     5   Free Software Foundation, Inc. 
     6 
     7   This file is part of the Midnight Commander. 
     8 
     9   The Midnight Commander is free software: you can redistribute it 
     10   and/or modify it under the terms of the GNU General Public License as 
     11   published by the Free Software Foundation, either version 3 of the License, 
     12   or (at your option) any later version. 
     13 
     14   The Midnight Commander is distributed in the hope that it will be useful, 
     15   but WITHOUT ANY WARRANTY; without even the implied warranty of 
     16   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
     17   GNU General Public License for more details. 
     18 
     19   You should have received a copy of the GNU General Public License 
     20   along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     21 */ 
     22 
     23/** \file scrollbar.c 
     24 *  \brief Source: WScrollbar widget 
     25 */ 
     26 
     27#include <config.h> 
     28 
     29#include <stdarg.h> 
     30#include <stdlib.h> 
     31#include <string.h> 
     32 
     33#include "lib/global.h" 
     34 
     35#include "lib/tty/tty.h" 
     36#include "lib/tty/color.h" 
     37#include "lib/skin.h" 
     38#include "lib/strutil.h" 
     39#include "lib/widget.h" 
     40 
     41/*** global variables ****************************************************************************/ 
     42 
     43/*** file scope macro definitions ****************************************************************/ 
     44 
     45/*** file scope type declarations ****************************************************************/ 
     46 
     47/*** file scope variables ************************************************************************/ 
     48 
     49/*** file scope functions ************************************************************************/ 
     50 
     51static cb_ret_t 
     52scrollbar_callback (Widget * w, Widget * sender, widget_msg_t msg, int parm, void *data) 
     53{ 
     54    WScrollbar *s = SCROLLBAR (w); 
     55 
     56    switch (msg) 
     57    { 
     58    case MSG_RESIZE: 
     59        { 
     60            widget_default_callback (w, NULL, MSG_RESIZE, 0, data); 
     61            return MSG_HANDLED; 
     62        } 
     63 
     64    case MSG_DRAW: 
     65        { 
     66            int scrollbar_values_per_char; 
     67            int scrollbar_values_total; 
     68            int scrollbox_length; 
     69            int top_possibilities; 
     70            int scrollbox_pos_start; 
     71            int i; 
     72            int scrollbar_position; 
     73 
     74            if (s->data_items <= s->data_visible_items) 
     75                return MSG_HANDLED; 
     76 
     77            /* Are we at the top? */ 
     78            widget_gotoyx (w, 0, 0); 
     79            if (s->data_visible_start_position == 0) 
     80                tty_print_string (mc_global.tty.ugly_line_drawing ? "" : "△"); 
     81            else 
     82                tty_print_string (mc_global.tty.ugly_line_drawing ? "^" : "▲"); 
     83 
     84            /* Are we at the bottom? */ 
     85            widget_gotoyx (w, w->lines - 1, 0); 
     86            if (s->data_visible_start_position + s->data_visible_items >= s->data_items) 
     87                tty_print_string (mc_global.tty.ugly_line_drawing ? "" : "▽"); 
     88            else 
     89                tty_print_string (mc_global.tty.ugly_line_drawing ? "v" : "▼"); 
     90 
     91            if (w->lines <= 2)           /* there is no enough space for actual scrollbar */ 
     92                return MSG_HANDLED; 
     93 
     94            /* Now draw the nice relative pointer */ 
     95            scrollbar_values_per_char = (s->has_subchars && !mc_global.tty.ugly_line_drawing ? 2 : 1); 
     96            scrollbar_values_total = (w->lines - 2) * scrollbar_values_per_char; 
     97            scrollbox_length = MAX (1, scrollbar_values_total * s->data_visible_items / s->data_items); 
     98            top_possibilities = s->data_items - s->data_visible_items + 1; 
     99            scrollbox_pos_start = (2 * s->data_visible_start_position * (scrollbar_values_total - scrollbox_length) 
     100                    / (top_possibilities - 1) + 1) / 2; 
     101 
     102            for (i = 0; i < w->lines - 2; i++) 
     103            { 
     104                widget_gotoyx (w, i + 1, 0); 
     105                scrollbar_position = i * scrollbar_values_per_char; 
     106 
     107                if (scrollbar_values_per_char == 2 
     108                        && scrollbar_position + 1 == scrollbox_pos_start) 
     109                    tty_print_string ("▄"); 
     110                else if (scrollbar_values_per_char == 2 
     111                        && scrollbar_position >= scrollbox_pos_start 
     112                        && scrollbar_position + 1 == scrollbox_pos_start + scrollbox_length) 
     113                    tty_print_string ("▀"); 
     114                else if (scrollbar_position >= scrollbox_pos_start 
     115                        && scrollbar_position + scrollbar_values_per_char <= scrollbox_pos_start + scrollbox_length) 
     116                    tty_print_string (mc_global.tty.ugly_line_drawing ? "#" : (s->has_subchars ? "█" : "▓")); 
     117                else 
     118                    tty_print_string (s->has_subchars || mc_global.tty.ugly_line_drawing ? " " : "░"); 
     119            } 
     120 
     121            return MSG_HANDLED; 
     122        } 
     123 
     124    default: 
     125        return widget_default_callback (w, sender, msg, parm, data); 
     126    } 
     127} 
     128 
     129/* --------------------------------------------------------------------------------------------- */ 
     130/*** public functions ****************************************************************************/ 
     131/* --------------------------------------------------------------------------------------------- */ 
     132 
     133WScrollbar * 
     134scrollbar_new (int y, int x, int lines, gboolean has_subchars) 
     135{ 
     136    WScrollbar *scrollbar; 
     137    Widget *w; 
     138 
     139    scrollbar = g_new (WScrollbar, 1); 
     140    w = WIDGET (scrollbar); 
     141    widget_init (w, y, x, lines, 1, scrollbar_callback, NULL); 
     142 
     143    scrollbar->has_subchars = has_subchars; 
     144    scrollbar->data_items = 0; 
     145    scrollbar->data_visible_items = 0; 
     146    scrollbar->data_visible_start_position = 0; 
     147 
     148    return scrollbar; 
     149} 
     150 
     151/* --------------------------------------------------------------------------------------------- */ 
     152 
     153void 
     154scrollbar_set_state(WScrollbar * scrollbar, int y, int x, int lines, int data_length, 
     155                    int data_visible_length, int data_position) 
     156{ 
     157    Widget *w = WIDGET (scrollbar); 
     158 
     159    w->y = y; 
     160    w->x = x; 
     161    w->lines = lines; 
     162    scrollbar->data_items = data_length; 
     163    scrollbar->data_visible_items = data_visible_length; 
     164    scrollbar->data_visible_start_position = data_position; 
     165 
     166    widget_draw (w); 
     167} 
     168 
     169/* --------------------------------------------------------------------------------------------- */ 
  • new file lib/widget/scrollbar.h

    IDEA additional info:
    Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP
    <+>UTF-8
    diff --git a/lib/widget/scrollbar.h b/lib/widget/scrollbar.h
    new file mode 100644
    - +  
     1 
     2/** \file scrollbar.h 
     3 *  \brief Header: WScrollbar widget 
     4 */ 
     5 
     6#ifndef MC__WIDGET_SCROLLBAR_H 
     7#define MC__WIDGET_SCROLLBAR_H 
     8 
     9/*** typedefs(not structures) and defined constants **********************************************/ 
     10 
     11#define SCROLLBAR(x) ((WScrollbar *)(x)) 
     12 
     13/*** enums ***************************************************************************************/ 
     14 
     15/*** structures declarations (and typedefs of structures)*****************************************/ 
     16 
     17typedef struct 
     18{ 
     19    Widget widget; 
     20    gboolean has_subchars;   /* if uses sub-characters (2 states per character). Also, this 
     21                                turns off scrollbar background */ 
     22    int data_items;         /* how many items are in the background data */ 
     23    int data_visible_items; /* how many items from data are actually visible */ 
     24    int data_visible_start_position;       /* position of first visible item in data */ 
     25} WScrollbar; 
     26 
     27/*** global variables defined in .c file *********************************************************/ 
     28 
     29/*** declarations of public functions ************************************************************/ 
     30 
     31WScrollbar *scrollbar_new (int y, int x, int height, gboolean has_subchars); 
     32void scrollbar_set_state (WScrollbar * scrollbar, int y, int x, int lines, int data_length, 
     33                          int data_visible_length, int data_position); 
     34 
     35/*** inline functions ****************************************************************************/ 
     36 
     37#endif /* MC__WIDGET_SCROLLBAR_H */