summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChris Davis <cd.rattan@gmail.com>2014-07-28 23:04:10 -0700
committerMichael Adam <obnox@samba.org>2014-10-01 14:32:09 +0200
commitc272178ccc6bb2f3b4a6621ef463489741c7e040 (patch)
treef69b089ec9ce2458bed554633b42977c1e04e224
parentcc22cb5cd44fdcc078211d2b82502ca219b1e928 (diff)
downloadsamba-c272178ccc6bb2f3b4a6621ef463489741c7e040.tar.gz
samba-c272178ccc6bb2f3b4a6621ef463489741c7e040.tar.xz
samba-c272178ccc6bb2f3b4a6621ef463489741c7e040.zip
regedit: use pad as a canvas for dialogs
Drawing in a pad allows the dialog to maintain the same size even when the terminal window is shrunk to some awkwardly small size. It also helps avoid hacks needed to update positions of subwindows when the panel is moved. Signed-off-by: Chris Davis <cd.rattan@gmail.com> Reviewed-by: Andreas Schneider <asn@samba.org> Reviewed-by: Michael Adam <obnox@samba.org>
-rw-r--r--source3/utils/regedit_dialog.c79
-rw-r--r--source3/utils/regedit_dialog.h1
2 files changed, 57 insertions, 23 deletions
diff --git a/source3/utils/regedit_dialog.c b/source3/utils/regedit_dialog.c
index 3cef7a06d6..d8ffa9f750 100644
--- a/source3/utils/regedit_dialog.c
+++ b/source3/utils/regedit_dialog.c
@@ -343,6 +343,11 @@ WERROR dialog_create(struct dialog *dia)
/* create window for dialog */
nlines += 4;
ncols += 6;
+ dia->pad = newpad(nlines, ncols);
+ if (dia->pad == NULL) {
+ rv = WERR_NOMEM;
+ goto fail;
+ }
dia->centered = false;
if (dia->y < 0 || dia->x < 0) {
dia->centered = true;
@@ -360,18 +365,19 @@ WERROR dialog_create(struct dialog *dia)
}
/* setup color and border */
- wbkgdset(dia->window, ' ' | COLOR_PAIR(dia->color));
- wclear(dia->window);
- mvwhline(dia->window, 1, 2, 0, ncols - 4);
- mvwhline(dia->window, nlines - 2, 2, 0, ncols - 4);
- mvwvline(dia->window, 2, 1, 0, nlines - 4);
- mvwvline(dia->window, 2, ncols - 2, 0, nlines - 4);
- mvwaddch(dia->window, 1, 1, ACS_ULCORNER);
- mvwaddch(dia->window, 1, ncols - 2, ACS_URCORNER);
- mvwaddch(dia->window, nlines - 2, 1, ACS_LLCORNER);
- mvwaddch(dia->window, nlines - 2, ncols - 2, ACS_LRCORNER);
+ getmaxyx(dia->pad, nlines, ncols);
+ wbkgdset(dia->pad, ' ' | COLOR_PAIR(dia->color));
+ wclear(dia->pad);
+ mvwhline(dia->pad, 1, 2, 0, ncols - 4);
+ mvwhline(dia->pad, nlines - 2, 2, 0, ncols - 4);
+ mvwvline(dia->pad, 2, 1, 0, nlines - 4);
+ mvwvline(dia->pad, 2, ncols - 2, 0, nlines - 4);
+ mvwaddch(dia->pad, 1, 1, ACS_ULCORNER);
+ mvwaddch(dia->pad, 1, ncols - 2, ACS_URCORNER);
+ mvwaddch(dia->pad, nlines - 2, 1, ACS_LLCORNER);
+ mvwaddch(dia->pad, nlines - 2, ncols - 2, ACS_LRCORNER);
col = ncols / 2 - MIN(strlen(dia->title) + 2, ncols) / 2;
- mvwprintw(dia->window, 1, col, " %s ", dia->title);
+ mvwprintw(dia->pad, 1, col, " %s ", dia->title);
/* create subwindows for each section */
row = 2;
@@ -389,7 +395,7 @@ WERROR dialog_create(struct dialog *dia)
break;
}
- section->window = derwin(dia->window, section->nlines,
+ section->window = subpad(dia->pad, section->nlines,
section->ncols, row, col);
if (section->window == NULL) {
rv = WERR_NOMEM;
@@ -410,15 +416,30 @@ fail:
void dialog_show(struct dialog *dia)
{
- struct dialog_section *section;
+ int nlines, ncols;
+ int pad_y, pad_x;
+ int y, x;
+ int rv;
+ touchwin(dia->pad);
+ getmaxyx(dia->window, nlines, ncols);
+ getmaxyx(dia->pad, pad_y, pad_x);
+ y = 0;
+ if (pad_y > nlines) {
+ y = (pad_y - nlines) / 2;
+ }
+ x = 0;
+ if (pad_x > ncols) {
+ x = (pad_x - ncols) / 2;
+ }
+ rv = copywin(dia->pad, dia->window, y, x, 0, 0,
+ nlines - 1, ncols - 1, false);
+ SMB_ASSERT(rv == OK);
+
+ getyx(dia->pad, pad_y, pad_x);
+ wmove(dia->window, pad_y - y, pad_x - x);
touchwin(dia->window);
wnoutrefresh(dia->window);
- section = dia->head_section;
- do {
- wnoutrefresh(section->window);
- section = section->next;
- } while (section != dia->head_section);
}
void dialog_destroy(struct dialog *dia)
@@ -448,9 +469,16 @@ static int dialog_getch(struct dialog *dia)
c = regedit_getch();
if (c == KEY_RESIZE) {
int nlines, ncols, y, x;
+ int pad_nlines, pad_ncols;
+ int win_nlines, win_ncols;
- getmaxyx(dia->window, nlines, ncols);
+ getmaxyx(dia->window, win_nlines, win_ncols);
+ getmaxyx(dia->pad, pad_nlines, pad_ncols);
getbegyx(dia->window, y, x);
+
+ nlines = pad_nlines;
+ ncols = pad_ncols;
+
if (dia->centered) {
center_above_window(&nlines, &ncols, &y, &x);
} else {
@@ -469,6 +497,10 @@ static int dialog_getch(struct dialog *dia)
}
}
}
+ if (nlines != win_nlines || ncols != win_ncols) {
+ wresize(dia->window, nlines, ncols);
+ replace_panel(dia->panel, dia->window);
+ }
move_panel(dia->panel, y, x);
}
@@ -542,6 +574,7 @@ void dialog_modal_loop(struct dialog *dia, WERROR *err,
enum dialog_action *action)
{
do {
+ dialog_show(dia);
update_panels();
doupdate();
} while (dialog_handle_input(dia, err, action));
@@ -649,10 +682,10 @@ static WERROR hsep_create(struct dialog *dia, struct dialog_section *section)
/* change the border characters around this section to
tee chars */
getparyx(section->window, y, x);
- mvwaddch(dia->window, y, x - 1, ACS_HLINE);
- mvwaddch(dia->window, y, x - 2, ACS_LTEE);
- mvwaddch(dia->window, y, x + section->ncols, ACS_HLINE);
- mvwaddch(dia->window, y, x + section->ncols + 1, ACS_RTEE);
+ mvwaddch(dia->pad, y, x - 1, ACS_HLINE);
+ mvwaddch(dia->pad, y, x - 2, ACS_LTEE);
+ mvwaddch(dia->pad, y, x + section->ncols, ACS_HLINE);
+ mvwaddch(dia->pad, y, x + section->ncols + 1, ACS_RTEE);
}
return WERR_OK;
diff --git a/source3/utils/regedit_dialog.h b/source3/utils/regedit_dialog.h
index c0d89ff3ec..18b9b98fb5 100644
--- a/source3/utils/regedit_dialog.h
+++ b/source3/utils/regedit_dialog.h
@@ -35,6 +35,7 @@ typedef bool (*dialog_submit_cb)(struct dialog *, struct dialog_section *,
struct dialog {
char *title;
WINDOW *window;
+ WINDOW *pad;
PANEL *panel;
int x;
int y;