* Slightly alter the semantics of the input gathering function to take the

menu item it's associated with rather than an input string. This allows it
  to calculate the position to start the input at, as well as the correct
  line to place it on. The previous solution always put the input at the
  center line, which happened to be the right place by happy coincidence
  unless one also had the menu items for viewing/saving the debug syslog
  present.
* Implement input buffer scrolling, and consequently lift the previous size
  limit on user input (it is now only limited by the size of the passed in
  buffer).
* Implement parsing of the input buffer to allow it to handle comma-separated
  options. Thus, one can now input things like "disable_smp true, serial_debug_output false"
  and it will be handled properly.



git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@41706 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Rene Gollent 2011-05-24 03:21:51 +00:00
parent c05a3fa6a7
commit 8837310ce7
9 changed files with 90 additions and 38 deletions

View File

@ -68,7 +68,7 @@ class MenuItem;
extern void platform_add_menus(Menu *menu);
extern void platform_update_menu_item(Menu *menu, MenuItem *item);
extern void platform_run_menu(Menu *menu);
extern size_t platform_get_user_input_text(Menu *menu, const char *prompt,
extern size_t platform_get_user_input_text(Menu *menu, MenuItem *item,
char *buffer, size_t bufferSize);
#endif

View File

@ -12,7 +12,7 @@ class MenuItem;
void platform_generic_update_text_menu_item(Menu* menu, MenuItem* item);
void platform_generic_run_text_menu(Menu* menu);
size_t platform_generic_get_user_input_text(Menu* menu, const char* prompt,
size_t platform_generic_get_user_input_text(Menu* menu, MenuItem* item,
char* buffer, size_t bufferSize);
#endif /* GENERIC_TEXT_MENU_H */

View File

@ -523,18 +523,35 @@ debug_menu_display_syslog(Menu* menu, MenuItem* item)
static bool
debug_menu_add_advanced_option(Menu* menu, MenuItem* item)
{
char buffer[128];
const char* prompt = "Option: ";
char buffer[256];
size_t size = platform_get_user_input_text(menu, prompt, buffer,
size_t size = platform_get_user_input_text(menu, item, buffer,
sizeof(buffer) - 1);
if (size > 0) {
buffer[size] = '\n';
char* token = NULL;
char *bufferOffset = buffer;
char *separator = NULL;
uint32 pos = strlen(sSafeModeOptionsBuffer);
if (pos + size < sizeof(sSafeModeOptionsBuffer))
strlcat(sSafeModeOptionsBuffer, buffer,
sizeof(sSafeModeOptionsBuffer));
do {
token = bufferOffset;
separator = strchr(bufferOffset, ',');
if (separator != NULL) {
*separator = '\0';
bufferOffset = separator + 1;
} else {
token = bufferOffset;
bufferOffset = NULL;
}
uint32 length = strlen(token) + 1;
if (pos + length < sizeof(sSafeModeOptionsBuffer)) {
strlcat(sSafeModeOptionsBuffer, token,
sizeof(sSafeModeOptionsBuffer));
sSafeModeOptionsBuffer[pos + length - 1] = '\n';
pos += length;
} else
break;
} while (token != NULL);
}
return true;

View File

@ -51,7 +51,7 @@ platform_add_menus(Menu *menu)
}
void
void
platform_update_menu_item(Menu *menu, MenuItem *item)
{
platform_generic_update_text_menu_item(menu, item);
@ -65,9 +65,9 @@ platform_run_menu(Menu *menu)
}
size_t
platform_get_user_input_text(Menu* menu, const char* prompt, char *buffer,
platform_get_user_input_text(Menu *menu, MenuItem *item, char *buffer,
size_t bufferSize)
{
return platform_generic_get_user_input_text(menu, prompt, buffer,
return platform_generic_get_user_input_text(menu, item, buffer,
bufferSize);
}

View File

@ -67,9 +67,9 @@ platform_run_menu(Menu *menu)
size_t
platform_get_user_input_text(Menu* menu, const char* prompt, char *buffer,
platform_get_user_input_text(Menu *menu, MenuItem *item, char *buffer,
size_t bufferSize)
{
return platform_generic_get_user_input_text(menu, prompt, buffer,
return platform_generic_get_user_input_text(menu, item, buffer,
bufferSize);
}

View File

@ -114,9 +114,9 @@ platform_run_menu(Menu* menu)
size_t
platform_get_user_input_text(Menu* menu, const char* prompt, char* buffer,
platform_get_user_input_text(Menu* menu, MenuItem* item, char* buffer,
size_t bufferSize)
{
return platform_generic_get_user_input_text(menu, prompt, buffer,
return platform_generic_get_user_input_text(menu, item, buffer,
bufferSize);
}

View File

@ -513,15 +513,20 @@ platform_generic_run_text_menu(Menu *menu)
size_t
platform_generic_get_user_input_text(Menu* menu, const char* prompt,
char* buffer, size_t bufferSize)
platform_generic_get_user_input_text(Menu* menu, MenuItem* item, char* buffer,
size_t bufferSize)
{
size_t pos = 0;
memset(buffer, 0, bufferSize);
int32 promptLength = strlen(prompt);
int32 line = console_height() / 2;
int32 promptLength = strlen(item->Label()) + 2;
int32 line = menu->IndexOf(item) - sMenuOffset;
if (line < 0 || line >= menu_height())
return 0;
line += kFirstLine;
console_set_cursor(kOffsetX, line);
int32 x = kOffsetX + 1;
console_set_cursor(0, line);
console_set_color(kSelectedItemColor, kSelectedItemBackgroundColor);
@ -529,12 +534,15 @@ platform_generic_get_user_input_text(Menu* menu, const char* prompt,
console_set_color(kTextColor, kBackgroundColor);
console_set_cursor(0, line);
print_spacing(x);
printf(prompt);
printf(item->Label());
printf(": ");
x += promptLength;
console_set_color(kSelectedItemColor, kSelectedItemBackgroundColor);
console_show_cursor();
console_set_cursor(x, line);
int32 scrollOffset = 0;
bool doScroll = false;
int key = 0;
size_t dataLength = 0;
while (true) {
@ -546,35 +554,62 @@ platform_generic_get_user_input_text(Menu* menu, const char* prompt,
{
switch (key) {
case TEXT_CONSOLE_KEY_LEFT:
if (pos != 0)
if (pos > 0)
pos--;
else if (scrollOffset > 0) {
scrollOffset--;
doScroll = true;
}
break;
case TEXT_CONSOLE_KEY_RIGHT:
if (pos < dataLength)
pos++;
if (pos < dataLength) {
if (x + (int32)pos == console_width() - 1) {
scrollOffset++;
doScroll = true;
} else
pos++;
}
break;
default:
break;
}
} else if (key == TEXT_CONSOLE_KEY_BACKSPACE) {
if (pos != 0) {
pos--;
if (pos != 0 || scrollOffset > 0) {
if (pos > 0)
pos--;
else if (scrollOffset > 0)
scrollOffset--;
dataLength--;
buffer[pos] = '\0';
int32 offset = pos + scrollOffset;
memmove(buffer + offset, buffer + offset + 1, dataLength - offset);
console_set_cursor(x + pos, line);
printf(" ");
putchar(' ');
// if this was a mid-line backspace, the line will need to be redrawn
if (pos + scrollOffset < dataLength)
doScroll = true;
}
// only accept printable ascii characters
} else if (key > 32 || key == TEXT_CONSOLE_KEY_SPACE) {
// don't allow the input to exceed either the buffer size
// or screen width
// TODO: support scrolling the line to allow larger inputs
if (x < (console_width() - 1) && pos < (bufferSize - 1)) {
buffer[pos++] = key;
printf("%c", key);
if (pos < (bufferSize - 1)) {
buffer[pos + scrollOffset] = key;
if (x + (int32)pos < console_width() - 1) {
putchar(key);
pos++;
} else {
scrollOffset++;
doScroll = true;
}
dataLength++;
}
}
if (doScroll) {
console_set_cursor(x, line);
for (int32 i = x; i < console_width() - 1; i++)
putchar(buffer[scrollOffset + i - x]);
doScroll = false;
}
console_set_cursor(x + pos, line);
}

View File

@ -40,9 +40,9 @@ platform_run_menu(Menu *menu)
size_t
platform_get_user_input_text(Menu *menu, const char *prompt, char *buffer,
platform_get_user_input_text(Menu *menu, MenuItem *item, char *buffer,
size_t bufferSize)
{
return platform_generic_get_user_input_text(menu, prompt, buffer,
return platform_generic_get_user_input_text(menu, item, buffer,
bufferSize);
}

View File

@ -75,8 +75,8 @@ platform_run_menu(Menu *menu)
void
platform_get_user_input_text(Menu *menu, const char *prompt, char *buffer,
platform_get_user_input_text(Menu *menu, MenuItem *item, char *buffer,
size_t bufferSize)
{
platform_generic_get_user_input_text(menu, prompt, buffer, bufferSize);
platform_generic_get_user_input_text(menu, item, buffer, bufferSize);
}