更改未在ncurses的字段中显示 [英] changes not showing in field in ncurses
问题描述
我有一个ncurses程序,它是一个登录菜单,我使用字段来输入用户名和密码.
问题是,当我在字段中键入内容时,字符会注册,但不会显示在终端中.换句话说,如果您执行代码打击并键入内容,您将无法在终端中看到它,但是如果按F2键,您可能会看到字符已注册.
这是我的代码:
test.cpp
I have a ncurses program which is a login menu and I use field for username and password.
The problem is that when I type something in the fields, characters register but do not show in terminal. In other word if you execute the code blow and type something, you won't be able to see it in terminal but if you push F2, you could see that the characters were registered.
Here is my code:
test.cpp
#include <curses.h>
#include <form.h>
#include <menu.h>
#include <string>
#include <cstring>
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
class WelcomeMenu {
private:
int _row; // number of rows of the terminal
int _col; // number of columns of the terminal
public:
WelcomeMenu();
~WelcomeMenu();
void welcomeBox();
void loginMenu();
void registerMenu();
};
WelcomeMenu::WelcomeMenu(){
initscr();
noecho();
cbreak();
keypad(stdscr, true);
int row, col;
getmaxyx(stdscr,row,col); /* get the number of rows and columns */
this->_row = row; this->_col = col;
loginMenu();
}
WelcomeMenu::~WelcomeMenu(){
refresh();
endwin();
}
/*
* This is useful because ncurses fill fields blanks with spaces.
*/
char* trim_whitespaces(char *str)
{
char *end;
// trim leading space
while(isspace(*str))
str++;
if(*str == 0) // all spaces?
return str;
// trim trailing space
end = str + strnlen(str, 128) - 1;
while(end > str && isspace(*end))
end--;
// write new null terminator
*(end+1) = '\0';
return str;
}
void WelcomeMenu::loginMenu(){
// erase();
FORM *form;
FIELD *fields[5];
WINDOW *win_body, *win_form;
int ch;
win_body = newwin(24, 80, 0, 0);
assert(win_body != NULL);
box(win_body, 0, 0);
win_form = derwin(win_body, 20, 78, 3, 1);
assert(win_form != NULL);
box(win_form, 0, 0);
mvwprintw(win_body, 1, 2, "Press F1 to quit and F2 to print fields content");
fields[0] = new_field(1, 10, 0, 0, 0, 0);
fields[1] = new_field(1, 40, 0, 15, 0, 0);
fields[2] = new_field(1, 10, 2, 0, 0, 0);
fields[3] = new_field(1, 40, 2, 15, 0, 0);
fields[4] = NULL;
assert(fields[0] != NULL && fields[1] != NULL && fields[2] != NULL && fields[3] != NULL);
set_field_buffer(fields[0], 0, "Username: ");
set_field_buffer(fields[1], 0, "username");
set_field_buffer(fields[2], 0, "Password: ");
set_field_buffer(fields[3], 0, "password");
set_field_opts(fields[0], O_VISIBLE | O_PUBLIC | O_AUTOSKIP);
set_field_opts(fields[1], O_VISIBLE | O_PUBLIC | O_EDIT | O_ACTIVE);
set_field_opts(fields[2], O_VISIBLE | O_PUBLIC | O_AUTOSKIP);
set_field_opts(fields[3], O_VISIBLE | O_PUBLIC | O_EDIT | O_ACTIVE);
set_field_back(fields[1], A_UNDERLINE);
set_field_back(fields[3], A_UNDERLINE);
form = new_form(fields);
assert(form != NULL);
set_form_win(form, win_form);
set_form_sub(form, derwin(win_form, 18, 76, 1, 1));
post_form(form);
refresh();
wrefresh(win_body);
wrefresh(win_form);
while ((ch = getch()) != KEY_F(1)){
switch (ch) {
case KEY_F(2):
// Or the current field buffer won't be sync with what is displayed
form_driver(form, REQ_NEXT_FIELD);
form_driver(form, REQ_PREV_FIELD);
move(LINES-3, 2);
for (int i = 0; fields[i]; i++) {
printw("%s", trim_whitespaces(field_buffer(fields[i], 0)));
if (field_opts(fields[i]) & O_ACTIVE)
printw("\"\t");
else
printw(": \"");
}
refresh();
pos_form_cursor(form);
break;
case KEY_DOWN:
form_driver(form, REQ_NEXT_FIELD);
form_driver(form, REQ_END_LINE);
break;
case KEY_UP:
form_driver(form, REQ_PREV_FIELD);
form_driver(form, REQ_END_LINE);
break;
case KEY_LEFT:
form_driver(form, REQ_PREV_CHAR);
break;
case KEY_RIGHT:
form_driver(form, REQ_NEXT_CHAR);
break;
// Delete the char before cursor
case KEY_BACKSPACE:
case 127:
form_driver(form, REQ_DEL_PREV);
break;
// Delete the char under the cursor
case KEY_DC:
form_driver(form, REQ_DEL_CHAR);
break;
default:
form_driver(form, ch);
break;
}
}
wrefresh(win_form);
unpost_form(form);
free_form(form);
free_field(fields[0]);
free_field(fields[1]);
free_field(fields[2]);
free_field(fields[3]);
delwin(win_form);
delwin(win_body);
}
int main(){
WelcomeMenu * myConWin = new WelcomeMenu();
delete myConWin;
return 0;
}
您可以像这样编译它: g ++ -inccurses -lform test.cpp
you can compile it like: g++ -lncurses -lform test.cpp
预先感谢您的回复
推荐答案
该示例的基本问题是它不提供显示字符的功能.在ncurses中,可以使用 form_driver 代码>
函数:
The basic problem with the example is that it does not provide for displaying the characters. In ncurses, that would be done using the form_driver
function:
form_driver
Once a form has been posted (displayed), you should funnel input events
to it through form_driver. This routine has three major input cases:
o The input is a form navigation request. Navigation request codes
are constants defined in <form.h>, which are distinct from the key-
and character codes returned by wgetch(3x).
o The input is a printable character. Printable characters (which
must be positive, less than 256) are checked according to the pro-
gram's locale settings.
o The input is the KEY_MOUSE special key associated with an mouse
event.
让程序使用 form_driver
会涉及到程序的一些重组,将切换语句移动到可以从表单驱动器调用的函数中.
Making your program use form_driver
would involve some reorganization of the program, moving that switch-statement into a function which can be called from the form-driver.
ncurses示例包括一些使用 form_driver的示例
.您可能想通读测试代码,看看
The ncurses examples include a few using form_driver
. You might want to read through the test-code, seeing how the basic loop
while (!finished) {
switch (form_driver(form, c = form_virtualize(form, w))) {
case E_OK:
MvAddStr(5, 57, field_buffer(secure, 1));
clrtoeol();
refresh();
break;
case E_UNKNOWN_COMMAND:
finished = my_form_driver(form, c);
break;
default:
beep();
break;
}
使用其 form_virtualize
函数读取字符(或表单请求).您未看到的可打印字符由 form_driver
处理,后者会更新表单上的当前字段.您可以像 form_virtualize
一样操作字段缓冲区并执行其他特殊操作,但是更新表单中的字段是为什么要使用 form_driver
的原因
uses its form_virtualize
function to read characters (or form-requests). The printable characters that you are (not) seeing are handled by form_driver
which updates the current field on the form. You can manipulate the field-buffer and do other special things as done in form_virtualize
, but updating fields in the form is why you would use form_driver
.
这篇关于更改未在ncurses的字段中显示的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!