char request_char(const buffer * const b, const char * const prompt, const char default_value) { set_attr(0); print_prompt(prompt); if (default_value) output_char(default_value, 0, false); move_cursor(b->cur_y, b->cur_x); while(true) { int c; input_class ic; do c = get_key_code(); while(c > 0xFF || (ic = CHAR_CLASS(c)) == IGNORE || ic == INVALID); switch(ic) { case ALPHA: return (char)localised_up_case[(unsigned char)c]; case RETURN: return (char)localised_up_case[(unsigned char)default_value]; default: break; } } }
int request_strings(req_list *rlp0, int n) { assert(rlp0->cur_entries > 0); int ne_lines0 = 0, ne_columns0 = 0; bool reordered = false; max_names_per_line = max_names_per_col = x = y = page = fuzz_len = 0; if ( ! request_strings_init(rlp0) ) return ERROR; const int dx = rl.max_entry_len + 1 + (rl.suffix ? 1 : 0); while(true) { if (ne_lines0 != ne_lines || ne_columns0 != ne_columns) { if (ne_lines0 && ne_columns0 ) n = PXY2N(page,x,y); if (!(max_names_per_line = ne_columns / dx)) max_names_per_line = 1; max_names_per_col = ne_lines - 1; names_per_page = max_names_per_line * max_names_per_col; ne_lines0 = ne_lines; ne_columns0 = ne_columns; page = N2P(n); x = N2X(n); y = N2Y(n); print_strings(); print_message(NULL); } n = PXY2N(page,x,y); assert(fuzz_len >= 0); fuzz_len = min(fuzz_len, strlen(rl.entries[n])); move_cursor(y, x * dx + fuzz_len); int c; input_class ic; do c = get_key_code(); while((ic = CHAR_CLASS(c)) == IGNORE || ic == INVALID); switch(ic) { case ALPHA: if (n >= rl.cur_entries) n = rl.cur_entries - 1; c = localised_up_case[(unsigned char)c]; fuzz_forward( c ); break; case TAB: if (! rlp0->ignore_tab) { n = request_strings_cleanup(reordered); if (n >= rlp0->cur_entries) return ERROR; else return -n - 2; } break; case RETURN: n = request_strings_cleanup(reordered); if (n >= rlp0->cur_entries) return ERROR; else return n; case COMMAND: if (c < 0) c = -c - 1; const int a = parse_command_line(key_binding[c], NULL, NULL, false); if (a >= 0) { switch(a) { case BACKSPACE_A: fuzz_back(); break; case MOVERIGHT_A: request_move_right(); break; case MOVELEFT_A: request_move_left(); break; case MOVESOL_A: request_move_to_sol(); break; case MOVEEOL_A: request_move_to_eol(); break; case TOGGLESEOL_A: if (x != 0) x = 0; else request_move_to_eol(); break; case LINEUP_A: request_move_up(); break; case LINEDOWN_A: request_move_down(); break; case MOVEINCUP_A: request_move_inc_up(); break; case MOVEINCDOWN_A: request_move_inc_down(); break; case PAGEUP_A: case PREVPAGE_A: request_prev_page(); break; case PAGEDOWN_A: case NEXTPAGE_A: request_next_page(); break; case MOVESOF_A: request_move_to_sof(); break; case MOVEEOF_A: request_move_to_eof(); break; case TOGGLESEOF_A: request_toggle_seof(); break; case NEXTWORD_A: request_move_next(); break; case PREVWORD_A: request_move_previous(); break; case NEXTDOC_A: reordered |= request_reorder(1); break; case PREVDOC_A: reordered |= request_reorder(-1); break; case INSERT_A: case DELETECHAR_A: prune = !prune; break; case CLOSEDOC_A: case ESCAPE_A: case QUIT_A: case SELECTDOC_A: request_strings_cleanup(reordered); return -1; } } break; default: break; } } }
char *request(const char *prompt, const char * const default_string, const bool alpha_allowed, const int completion_type, const bool prefer_utf8) { set_attr(0); input_buffer[pos = len = offset = 0] = 0; encoding = ENC_ASCII; x = start_x = print_prompt(prompt); init_history(); if (default_string) { strncpy(input_buffer, default_string, MAX_INPUT_LINE_LEN); len = strlen(input_buffer); encoding = detect_encoding(input_buffer, len); input_refresh(); } bool first_char_typed = true, last_char_completion = false, selection = false; while(true) { assert(input_buffer[len] == 0); move_cursor(ne_lines - 1, x); int c; input_class ic; do c = get_key_code(); while((ic = CHAR_CLASS(c)) == IGNORE); /* ISO 10646 characters *above 256* can be added only to UTF-8 lines, or ASCII lines (making them, of course, UTF-8). */ if (ic == ALPHA && c > 0xFF && encoding != ENC_ASCII && encoding != ENC_UTF8) ic = INVALID; if (ic != TAB) last_char_completion = false; if (ic == TAB && !completion_type) ic = ALPHA; switch(ic) { case INVALID: alert(); break; case ALPHA: if (first_char_typed) { input_buffer[len = 0] = 0; clear_to_eol(); } if (encoding == ENC_ASCII && c > 0x7F) encoding = prefer_utf8 || c > 0xFF ? ENC_UTF8 : ENC_8_BIT; int c_len = encoding == ENC_UTF8 ? utf8seqlen(c) : 1; int c_width = output_width(c); assert(c_len > 0); if (len <= MAX_INPUT_LINE_LEN - c_len && (alpha_allowed || (c < 0x100 && isxdigit(c)) || c=='X' || c=='x')) { memmove(&input_buffer[pos + c_len], &input_buffer[pos], len - pos + 1); if (c_len == 1) input_buffer[pos] = c; else utf8str(c, &input_buffer[pos]); len += c_len; move_cursor(ne_lines - 1, x); if (x < ne_columns - c_width) { if (pos == len - c_len) output_char(c, 0, encoding); else if (char_ins_del_ok) insert_char(c, 0, encoding); else input_refresh(); } input_move_right(true); } break; case RETURN: selection = true; break; case TAB: if (completion_type == COMPLETE_FILE || completion_type == COMPLETE_SYNTAX) { bool quoted = false; char *prefix, *completion, *p; if (len && input_buffer[len - 1] == '"') { input_buffer[len - 1] = 0; if (prefix = strrchr(input_buffer, '"')) { quoted = true; prefix++; } else input_buffer[len - 1] = '"'; } if (!quoted) { prefix = strrchr(input_buffer, ' '); if (prefix) prefix++; else prefix = input_buffer; } if (last_char_completion || completion_type == COMPLETE_SYNTAX) { if (completion_type == COMPLETE_FILE ) completion = p = request_files(prefix, true); else completion = p = request_syntax(prefix, true); reset_window(); if (completion) { if (*completion) selection = true; else completion++; } } else { if (completion_type == COMPLETE_FILE ) completion = p = complete_filename(prefix); else completion = p = request_syntax(prefix, true); last_char_completion = true; if (!completion) alert(); } if (completion && (prefix - input_buffer) + strlen(completion) + 1 < MAX_INPUT_LINE_LEN) { const encoding_type completion_encoding = detect_encoding(completion, strlen(completion)); if (encoding == ENC_ASCII || completion_encoding == ENC_ASCII || encoding == completion_encoding) { strcpy(prefix, completion); if (quoted) strcat(prefix, "\""); len = strlen(input_buffer); pos = offset = 0; x = start_x; if (encoding == ENC_ASCII) encoding = completion_encoding; input_move_to_eol(); if (quoted) input_move_left(false); input_refresh(); } else alert(); } else if (quoted) strcat(prefix, "\""); free(p); } break; case COMMAND: if (c < 0) c = -c - 1; const int a = parse_command_line(key_binding[c], NULL, NULL, false); if (a >= 0) { switch(a) { case LINEUP_A: case LINEDOWN_A: case MOVESOF_A: case MOVEEOF_A: case PAGEUP_A: case PAGEDOWN_A: case NEXTPAGE_A: case PREVPAGE_A: if (history_buff) { switch(a) { case LINEUP_A: line_up(history_buff); break; case LINEDOWN_A: line_down(history_buff); break; case MOVESOF_A: move_to_sof(history_buff); break; case MOVEEOF_A: move_to_bof(history_buff); break; case PAGEUP_A: case PREVPAGE_A: prev_page(history_buff); break; case PAGEDOWN_A: case NEXTPAGE_A: next_page(history_buff); break; } /* In some cases, the default displayed on the command line will be the same as the first history item. In that case we skip it. */ if (first_char_typed == true && a == LINEUP_A && history_buff->cur_line_desc->line && !strncmp(history_buff->cur_line_desc->line, input_buffer, history_buff->cur_line_desc->line_len)) line_up(history_buff); if (history_buff->cur_line_desc->line) { strncpy(input_buffer, history_buff->cur_line_desc->line, min(history_buff->cur_line_desc->line_len,MAX_INPUT_LINE_LEN)); input_buffer[min(history_buff->cur_line_desc->line_len,MAX_INPUT_LINE_LEN)] = 0; len = strlen(input_buffer); encoding = detect_encoding(input_buffer, len); } else { input_buffer[len = 0] = 0; encoding = ENC_ASCII; } x = start_x; pos = 0; offset = 0; input_refresh(); } break; case MOVELEFT_A: input_move_left(true); break; case MOVERIGHT_A: input_move_right(true); break; case BACKSPACE_A: if (pos == 0) break; input_move_left(true); case DELETECHAR_A: if (len > 0 && pos < len) { int c_len = encoding == ENC_UTF8 ? utf8len(input_buffer[pos]) : 1; int c_width = get_char_width(&input_buffer[pos], encoding); memmove(&input_buffer[pos], &input_buffer[pos + c_len], len - pos - c_len + 1); len -= c_len; if (input_buffer_is_ascii()) encoding = ENC_ASCII; if (char_ins_del_ok) { int i, j; move_cursor(ne_lines - 1, x); delete_chars(c_width); for(i = x, j = pos; j < len && i + get_char_width(&input_buffer[j], encoding) < ne_columns - c_width; i += get_char_width(&input_buffer[j], encoding), j = next_pos(input_buffer, j, encoding)); if (j < len) { move_cursor(ne_lines - 1, i); while(j < len && i + get_char_width(&input_buffer[j], encoding) < ne_columns) { output_char(get_char(&input_buffer[j], encoding), 0, encoding); i += get_char_width(&input_buffer[j], encoding); j = next_pos(input_buffer, j, encoding); } } } else input_refresh(); } break; case DELETELINE_A: move_cursor(ne_lines - 1, start_x); clear_to_eol(); input_buffer[len = pos = offset = 0] = 0; encoding = ENC_ASCII; x = start_x; break; case DELETEEOL_A: input_buffer[len = pos] = 0; clear_to_eol(); if (input_buffer_is_ascii()) encoding = ENC_ASCII; break; case MOVEINCUP_A: if (x != start_x) { pos = offset; x = start_x; break; } case MOVESOL_A: input_move_to_sol(); break; case MOVEINCDOWN_A: { int i, j; for(i = x, j = pos; j < len && i + get_char_width(&input_buffer[j], encoding) < ne_columns; i += get_char_width(&input_buffer[j], encoding), j = next_pos(input_buffer, j, encoding)); if (j != pos && j < len) { pos = j; x = i; break; } } case MOVEEOL_A: input_move_to_eol(); break; case TOGGLESEOL_A: case TOGGLESEOF_A: if (pos != 0) input_move_to_sol(); else input_move_to_eol(); break; case PREVWORD_A: input_prev_word(); break; case NEXTWORD_A: input_next_word(); break; case REFRESH_A: input_refresh(); break; case PASTE_A: input_paste(); break; case AUTOCOMPLETE_A: input_autocomplete(); break; case ESCAPE_A: return NULL; default: break; } } break; default: break; } if (selection) { const line_desc * const last = (line_desc *)history_buff->line_desc_list.tail_pred->prev; assert(input_buffer[len] == 0); if (history_buff->num_lines == 0 || len != last->line_len || strncmp(input_buffer, last->line, last->line_len)) add_to_history(input_buffer); return input_buffer; } first_char_typed = false; } }
int main(int argc, char **argv) { char *locale = setlocale(LC_ALL, ""); for(int i = 0; i < 256; i++) localised_up_case[i] = toupper(i); if (locale) { struct re_pattern_buffer re_pb; struct re_registers re_reg; memset(&re_pb, 0, sizeof re_pb); memset(&re_reg, 0, sizeof re_reg); re_pb.translate = localised_up_case; re_compile_pattern(LOCALE_REGEX, strlen(LOCALE_REGEX), &re_pb); if (re_search(&re_pb, locale, strlen(locale), 0, strlen(locale), &re_reg) >= 0) { if (re_reg.start[1] >= 0) io_utf8 = true; } free(re_reg.start); free(re_reg.end); } bool no_config = false; char *macro_name = NULL, *key_bindings_name = NULL, *menu_conf_name = NULL, *startup_prefs_name = DEF_PREFS_NAME; char * const skiplist = calloc(argc, 1); if (!skiplist) exit(1); /* We need this many flags. */ for(int i = 1; i < argc; i++) { if (argv[i][0] == '-' && (!strcmp(&argv[i][1], "h") || !strcmp(&argv[i][1], "-help" "\0" VERSION_STRING))) { puts(ARG_HELP); exit(0); } /* Special arguments start with two dashes. If we find one, we cancel its entry in argv[], so that it will be skipped when opening the specified files. The only exception is +N for skipping to the N-th line. */ if (argv[i][0] == '-' && argv[i][1] == '-') { if (!argv[i][2]) i++; /* You can use "--" to force the next token to be a filename */ else if (!strcmp(&argv[i][2], "noconfig") || !strcmp(&argv[i][2], "no-config")) { no_config = true; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "noansi") || !strcmp(&argv[i][2], "no-ansi")) { ansi = false; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "no-syntax")) { do_syntax = false; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "prefs")) { if (i < argc-1) { startup_prefs_name = argv[i+1]; skiplist[i] = skiplist[i+1] = 1; /* argv[i] = argv[i+1] = NULL; */ } } else if (!strcmp(&argv[i][2], "ansi")) { ansi = true; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "utf8")) { io_utf8 = true; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "no-utf8")) { io_utf8 = false; skiplist[i] = 1; /* argv[i] = NULL; */ } else if (!strcmp(&argv[i][2], "macro")) { if (i < argc-1) { macro_name = argv[i+1]; skiplist[i] = skiplist[i+1] = 1; /* argv[i] = argv[i+1] = NULL; */ } } else if (!strcmp(&argv[i][2], "keys")) { if (i < argc-1) { key_bindings_name = argv[i+1]; skiplist[i] = skiplist[i+1] = 1; /* argv[i] = argv[i+1] = NULL; */ } } else if (!strcmp(&argv[i][2], "menus")) { if (i < argc-1) { menu_conf_name = argv[i+1]; skiplist[i] = skiplist[i+1] = 1; /* argv[i] = argv[i+1] = NULL; */ } } } } #ifdef NE_TEST /* Dump the builtin menu and key bindings to compare to doc/default.menus and doc/default.keys. */ int dump_config(void); dump_config(); #endif /* Unless --noconfig was specified, we try to configure the menus and the keyboard. Note that these functions can exit() on error. */ if (!no_config) { get_menu_configuration(menu_conf_name); get_key_bindings(key_bindings_name); } /* If we cannot even create a buffer, better go... */ if (!new_buffer()) exit(1); /* Now that key_bindings are loaded, try to fix up the message for NOT_FOUND. */ { char *repeat_last_keystroke, *new_not_found; if ((repeat_last_keystroke = find_key_strokes(REPEATLAST_A, 1))) { if ((new_not_found = malloc(39+strlen(repeat_last_keystroke)))) { strcat(strcat(strcpy(new_not_found, "Not Found. (RepeatLast with "), repeat_last_keystroke), " to wrap.)"); error_msg[NOT_FOUND] = new_not_found; } free(repeat_last_keystroke); } } clear_buffer(cur_buffer); /* The INT_MAX clip always exists, and it is used by the Through command. */ clip_desc * const cd = alloc_clip_desc(INT_MAX, 0); if (!cd) exit(1); add_head(&clips, &cd->cd_node); /* General terminfo and cursor motion initalization. From here onwards, we cannot exit() lightly. */ term_init(); /* We will be always using the last line for the status bar. */ set_terminal_window(ne_lines-1); /* We read in all the key capabilities. */ read_key_capabilities(); /* Some initializations of other modules... */ re_set_syntax( RE_CONTEXT_INDEP_ANCHORS | RE_CONTEXT_INDEP_OPS | RE_HAT_LISTS_NOT_NEWLINE | RE_NEWLINE_ALT | RE_NO_BK_PARENS | RE_NO_BK_VBAR | RE_NO_EMPTY_RANGES ); bool first_file = true; load_virtual_extensions(); load_auto_prefs(cur_buffer, startup_prefs_name); buffer *stdin_buffer = NULL; if (!isatty(fileno(stdin))) { first_file = false; const int error = load_fd_in_buffer(cur_buffer, fileno(stdin)); print_error(error); stdin_buffer = cur_buffer; if (!(freopen("/dev/tty", "r", stdin))) { fprintf(stderr, "Cannot reopen input tty\n"); abort(); } } /* The terminal is prepared for interactive I/O. */ set_interactive_mode(); clear_entire_screen(); /* This function sets fatal_code() as signal interrupt handler for all the dangerous signals (SIGILL, SIGSEGV etc.). */ set_fatal_code(); if (argc > 1) { /* The first file opened does not need a NEWDOC_A action. Note that file loading can be interrupted (wildcarding can sometimes produce unwanted results). */ uint64_t first_line = 0, first_col = 0; bool binary = false, skip_plus = false, read_only = false; stop = false; for(int i = 1; i < argc && !stop; i++) { if (argv[i] && !skiplist[i]) { if (argv[i][0] == '+' && !skip_plus) { /* looking for "+", or "+N" or "+N,M" */ uint64_t tmp_l = INT64_MAX, tmp_c = 0; char *d; errno = 0; if (argv[i][1]) { if (isdigit((unsigned char)argv[i][1])) { tmp_l = strtoll(argv[i]+1, &d, 10); if (!errno) { if (*d) { /* separator between N and M */ if (isdigit((unsigned char)d[1])) { tmp_c = strtoll(d+1, &d, 10); if (*d) errno = ERANGE; } else errno = ERANGE; } } } else errno = ERANGE; } if (!errno) { first_line = tmp_l; first_col = tmp_c; } else { skip_plus = true; i--; } } else if (!strcmp(argv[i], "--binary")) { binary = true; } else if (!strcmp(argv[i], "--read-only") || !strcmp(argv[i], "--readonly") || !strcmp(argv[i], "--ro")) { read_only = true; } else { if (!strcmp(argv[i], "-") && stdin_buffer) { stdin_buffer->opt.binary = binary; if (read_only) stdin_buffer->opt.read_only = read_only; if (first_line) do_action(stdin_buffer, GOTOLINE_A, first_line, NULL); if (first_col) do_action(stdin_buffer, GOTOCOLUMN_A, first_col, NULL); stdin_buffer = NULL; } else { if (!strcmp(argv[i], "--")) i++; if (!first_file) do_action(cur_buffer, NEWDOC_A, -1, NULL); else first_file = false; cur_buffer->opt.binary = binary; if (i < argc) do_action(cur_buffer, OPEN_A, 0, str_dup(argv[i])); if (first_line) do_action(cur_buffer, GOTOLINE_A, first_line, NULL); if (first_col) do_action(cur_buffer, GOTOCOLUMN_A, first_col, NULL); if (read_only) cur_buffer->opt.read_only = read_only; } first_line = first_col = 0; skip_plus = binary = read_only = false; } } } free(skiplist); /* This call makes current the first specified file. It is called only if more than one buffer exist. */ if (get_nth_buffer(1)) do_action(cur_buffer, NEXTDOC_A, -1, NULL); } /* We delay updates. In this way the macro activity does not cause display activity. */ reset_window(); delay_update(); if (macro_name) do_action(cur_buffer, MACRO_A, -1, str_dup(macro_name)); else if (first_file) { /* If there is no file to load, and no macro to execute, we display the "NO WARRANTY" message. */ about(); } while(true) { /* If we are displaying the "NO WARRANTY" info, we should not refresh the window now */ if (!displaying_info) { refresh_window(cur_buffer); if (cur_buffer->opt.automatch) automatch_bracket(cur_buffer, true); } draw_status_bar(); move_cursor(cur_buffer->cur_y, cur_buffer->cur_x); int c = get_key_code(); if (window_changed_size) { print_error(do_action(cur_buffer, REFRESH_A, 0, NULL)); window_changed_size = displaying_info = false; cur_buffer->automatch.shown = 0; } if (c == INVALID_CHAR) continue; /* Window resizing. */ const input_class ic = CHAR_CLASS(c); if (displaying_info) { refresh_window(cur_buffer); displaying_info = false; } if (cur_buffer->automatch.shown) automatch_bracket(cur_buffer, false); switch(ic) { case INVALID: print_error(INVALID_CHARACTER); break; case ALPHA: print_error(do_action(cur_buffer, INSERTCHAR_A, c, NULL)); break; case TAB: print_error(do_action(cur_buffer, INSERTTAB_A, 1, NULL)); break; case RETURN: print_error(do_action(cur_buffer, INSERTLINE_A, -1, NULL)); break; case COMMAND: if (c < 0) c = -c - 1; if (key_binding[c]) print_error(execute_command_line(cur_buffer, key_binding[c])); break; default: break; } } }
NS_IMETHODIMP nsUnicodeToJamoTTF::Convert(const PRUnichar * aSrc, PRInt32 * aSrcLength, char * aDest, PRInt32 * aDestLength) { nsresult rv = NS_OK; mByteOff = 0; // This should never happen, but it happens under MS Windows, somehow... if (mJamoCount > mJamosMaxLength) { NS_WARNING("mJamoCount > mJamoMaxLength on entering Convert()"); Reset(); } for (PRInt32 charOff = 0; charOff < *aSrcLength; charOff++) { PRUnichar ch = aSrc[charOff]; // Syllable boundary check. Ref. : Unicode 3.2 section 3.11 if (mJamoCount != 0 && gIsBoundary[CHAR_CLASS(mJamos[mJamoCount - 1])][CHAR_CLASS(ch)]) { composeHangul(aDest); mJamoCount = 0; } // Ignore tone marks other than the first in a sequence of tone marks. else if (mJamoCount != 0 && IS_TONE(mJamos[mJamoCount - 1]) && IS_TONE(ch)) { --mJamoCount; composeHangul(aDest); mJamoCount = 0; // skip over tone marks from the second on in a series. while (IS_TONE(ch) && ++charOff < *aSrcLength) ch = aSrc[charOff]; if (!IS_TONE(ch)) { mJamos[mJamoCount++] = ch; continue; } else break; } if (mJamoCount == mJamosMaxLength) { mJamosMaxLength++; if (mJamos == mJamosStatic) { mJamos = (PRUnichar *) PR_Malloc(sizeof(PRUnichar) * mJamosMaxLength); if (!mJamos) return NS_ERROR_OUT_OF_MEMORY; memcpy(mJamos, mJamosStatic, sizeof(PRUnichar) * mJamoCount); } else { mJamos = (PRUnichar *) PR_Realloc(mJamos, sizeof(PRUnichar) * mJamosMaxLength); if (!mJamos) return NS_ERROR_OUT_OF_MEMORY; } } mJamos[mJamoCount++] = ch; } if (mJamoCount != 0) composeHangul(aDest); mJamoCount = 0; *aDestLength = mByteOff; return rv; }
/* If mark_char is not '\0', we bold names ending with it. */ int request_strings(const char * const * const _entries, const int _num_entries, int n, const int _max_name_len, int _mark_char) { action a; input_class ic; int c, i, ne_lines0, ne_columns0; assert(_num_entries > 0); ne_lines0 = ne_columns0 = max_names_per_line = max_names_per_col = x = y = page = 0; entries = _entries; num_entries = _num_entries; max_name_len = _max_name_len + 1; mark_char = _mark_char; while(TRUE) { if (ne_lines0 != ne_lines || ne_columns0 != ne_columns) { if (ne_lines0 && ne_columns0 ) n = PXY2N(page,x,y); if (!(max_names_per_line = ne_columns / (max_name_len))) max_names_per_line = 1; max_names_per_col = ne_lines - 1; names_per_page = max_names_per_line * max_names_per_col; ne_lines0 = ne_lines; ne_columns0 = ne_columns; page = N2P(n); x = N2X(n); y = N2Y(n); print_strings(); print_message(NULL); } move_cursor(y, x * max_name_len); do c = get_key_code(); while((ic = CHAR_CLASS(c)) == IGNORE || ic == INVALID); n = PXY2N(page,x,y); switch(ic) { case ALPHA: if (n >= num_entries) n = num_entries - 1; c = localised_up_case[(unsigned char)c]; for(i = 1; i < num_entries; i++) if (localised_up_case[(unsigned char)entries[(n + i) % num_entries][0]] == c) { normalize((n + i) % num_entries); break; } break; case TAB: if (n >= num_entries) return ERROR; else return -n - 2; case RETURN: if (n >= num_entries) return ERROR; else return n; case COMMAND: if (c < 0) c = -c - 1; if ((a = parse_command_line(key_binding[c], NULL, NULL, FALSE))>=0) { switch(a) { case MOVERIGHT_A: request_move_right(); break; case MOVELEFT_A: request_move_left(); break; case MOVESOL_A: request_move_to_sol(); break; case MOVEEOL_A: request_move_to_eol(); break; case TOGGLESEOL_A: if (x != 0) x = 0; else request_move_to_eol(); break; case LINEUP_A: request_move_up(); break; case LINEDOWN_A: request_move_down(); break; case MOVEINCUP_A: request_move_inc_up(); break; case MOVEINCDOWN_A: request_move_inc_down(); break; case PAGEUP_A: case PREVPAGE_A: request_prev_page(); break; case PAGEDOWN_A: case NEXTPAGE_A: request_next_page(); break; case MOVESOF_A: request_move_to_sof(); break; case MOVEEOF_A: request_move_to_eof(); break; case TOGGLESEOF_A: request_toggle_seof(); break; case ESCAPE_A: return -1; } } break; default: break; } } }