1 #include "core/show-file.h"
2 #include "core/asking-player.h"
3 #include "io/files-util.h"
4 #include "io/input-key-acceptor.h"
5 #include "main/sound-of-music.h"
6 #include "system/angband-version.h"
7 #include "system/player-type-definition.h"
8 #include "term/gameterm.h"
9 #include "term/screen-processor.h"
10 #include "term/term-color-types.h"
11 #include "util/angband-files.h"
12 #include "util/int-char-converter.h"
13 #include "util/string-processor.h"
14 #include "view/display-messages.h"
17 * @brief ファイル内容の一行をコンソールに出力する
18 * Display single line of on-line help file
24 * You can insert some special color tag to change text color.
26 * WHITETEXT [[[[y|SOME TEXT WHICH IS DISPLAYED IN YELLOW| WHITETEXT
27 * A colored segment is between "[[[[y|" and the last "|".
28 * You can use any single character in place of the "|".
32 static void show_file_aux_line(concptr str, int cy, concptr shower)
36 byte textcolor = TERM_WHITE;
37 byte focuscolor = TERM_YELLOW;
43 ptr = angband_strstr(lcstr, shower);
44 textcolor = (ptr == nullptr) ? TERM_L_DARK : TERM_WHITE;
50 static const char tag_str[] = "[[[[";
51 byte color = textcolor;
53 for (int i = 0; str[i];) {
54 int len = strlen(&str[i]);
55 int showercol = len + 1;
56 int bracketcol = len + 1;
59 ptr = angband_strstr(&lcstr[i], shower);
61 showercol = ptr - &lcstr[i];
64 ptr = in_tag ? angband_strchr(&str[i], in_tag) : angband_strstr(&str[i], tag_str);
66 bracketcol = ptr - &str[i];
67 if (bracketcol < endcol)
69 if (showercol < endcol)
72 term_addstr(endcol, color, &str[i]);
76 if (shower && endcol == showercol) {
77 int showerlen = strlen(shower);
78 term_addstr(showerlen, focuscolor, &str[i]);
84 if (endcol != bracketcol)
94 i += sizeof(tag_str) - 1;
95 color = color_char_to_attr(str[i]);
96 if (color == 255 || str[i + 1] == '\0') {
98 term_addstr(-1, color, tag_str);
99 cx += sizeof(tag_str) - 1;
108 term_erase(cx, cy, 255);
112 * @brief ファイル内容をコンソールに出力する
113 * Recursive file perusal.
114 * @param player_ptr プレイヤーへの参照ポインタ
115 * @param show_version TRUEならばコンソール上にゲームのバージョンを表示する
116 * @param name ファイル名の文字列
117 * @param what 内容キャプションの文字列
122 * Process various special text in the input file, including
123 * the "menu" structures used by the "help file" system.
124 * Return FALSE on 'q' to exit from a deep, otherwise TRUE.
128 bool show_file(PlayerType *player_ptr, bool show_version, concptr name, concptr what, int line, BIT_FLAGS mode)
131 term_get_size(&wid, &hgt);
134 strcpy(finder_str, "");
137 strcpy(shower_str, "");
139 char caption[1024 + 256];
143 for (int i = 0; i < 68; i++) {
148 strcpy(filename, name);
149 int n = strlen(filename);
151 concptr tag = nullptr;
152 for (int i = 0; i < n; i++) {
153 if (filename[i] == '#') {
155 tag = filename + i + 1;
164 strcpy(caption, what);
166 fff = angband_fopen(path, "r");
170 sprintf(caption, _("ヘルプ・ファイル'%s'", "Help file '%s'"), name);
171 path_build(path, sizeof(path), ANGBAND_DIR_HELP, name);
172 fff = angband_fopen(path, "r");
176 sprintf(caption, _("スポイラー・ファイル'%s'", "Info file '%s'"), name);
177 path_build(path, sizeof(path), ANGBAND_DIR_INFO, name);
178 fff = angband_fopen(path, "r");
182 path_build(path, sizeof(path), ANGBAND_DIR, name);
184 for (int i = 0; path[i]; i++)
186 path[i] = PATH_SEP[0];
188 sprintf(caption, _("スポイラー・ファイル'%s'", "Info file '%s'"), name);
189 fff = angband_fopen(path, "r");
193 msg_format(_("'%s'をオープンできません。", "Cannot open '%s'."), name);
205 bool reverse = (line < 0);
208 if (angband_fgets(fff, buf, sizeof(buf)))
210 if (!prefix(str, "***** ")) {
215 if ((str[6] == '[') && isalpha(str[7])) {
216 int k = str[7] - 'A';
218 if ((str[8] == ']') && (str[9] == ' ')) {
219 memcpy(hook[k], str + 10, 31);
229 size_t len = strlen(str);
230 if (str[len - 1] == '>') {
232 if (tag && streq(str + 7, tag))
240 line = ((size - 1) / rows) * rows;
244 concptr find = nullptr;
245 concptr shower = nullptr;
247 if (line >= size - rows)
254 fff = angband_fopen(path, "r");
261 while (next < line) {
262 if (angband_fgets(fff, buf, sizeof(buf)))
264 if (prefix(buf, "***** "))
270 for (row_count = 0; row_count < rows;) {
274 if (angband_fgets(fff, buf, sizeof(buf)))
276 if (prefix(buf, "***** "))
279 if (find && !row_count) {
283 if (!angband_strstr(lc_buf, find))
288 show_file_aux_line(str, row_count + 2, shower);
292 while (row_count < rows) {
293 term_erase(0, row_count + 2, 255);
304 prt(format(_("[変愚蛮怒 %d.%d.%d, %s, %d/%d]", "[Hengband %d.%d.%d, %s, Line %d/%d]"), FAKE_VER_MAJOR - 10, FAKE_VER_MINOR, FAKE_VER_PATCH, caption,
311 prt(format("[%s]", title), 0, 0);
313 prt(format(_("[%s, %d/%d]", "[%s, Line %d/%d]"), caption, line, size), 0, 0);
317 prt(_("[キー:(?)ヘルプ (ESC)終了]", "[Press ESC to exit.]"), hgt - 1, 0);
321 prt("[キー:(RET/スペース)↑ (-)↓ (?)ヘルプ (ESC)終了]", hgt - 1, 0);
323 prt("[キー:(RET/スペース)↓ (-)↑ (?)ヘルプ (ESC)終了]", hgt - 1, 0);
325 prt("[Press Return, Space, -, =, /, |, or ESC to exit.]", hgt - 1, 0);
329 skey = inkey_special(true);
332 if (strcmp(name, _("jhelpinfo.txt", "helpinfo.txt")) != 0)
333 show_file(player_ptr, true, _("jhelpinfo.txt", "helpinfo.txt"), nullptr, 0, mode);
336 prt(_("強調: ", "Show: "), hgt - 1, 0);
339 strcpy(back_str, shower_str);
340 if (askfor(shower_str, 80)) {
342 str_tolower(shower_str);
347 strcpy(shower_str, back_str);
352 prt(_("検索: ", "Find: "), hgt - 1, 0);
353 strcpy(back_str, finder_str);
354 if (askfor(finder_str, 80)) {
359 str_tolower(finder_str);
364 strcpy(finder_str, back_str);
369 prt(_("行: ", "Goto Line: "), hgt - 1, 0);
382 line = ((size - 1) / rows) * rows;
387 prt(_("ファイル・ネーム: ", "Goto File: "), hgt - 1, 0);
388 strcpy(tmp, _("jhelp.hlp", "help.hlp"));
390 if (askfor(tmp, 80)) {
391 if (!show_file(player_ptr, true, tmp, nullptr, 0, mode))
399 line = line + (reverse ? rows : -rows);
412 line = line + (reverse ? -1 : 1);
430 line = line + (reverse ? -rows : rows);
442 if (!(skey & SKEY_MASK) && isalpha(skey))
445 if ((key > -1) && hook[key][0]) {
446 /* Recurse on that file */
447 if (!show_file(player_ptr, true, hook[key], nullptr, 0, mode))
455 char xtmp[sizeof(caption) + 128];
459 if (!get_string(_("ファイル名: ", "File name: "), xtmp, 80))
462 path_build(buff, sizeof(buff), ANGBAND_DIR_USER, xtmp);
464 /* Hack -- Re-Open the file */
465 fff = angband_fopen(path, "r");
467 ffp = angband_fopen(buff, "w");
470 msg_print(_("ファイルを開けません。", "Failed to open file."));
475 sprintf(xtmp, "%s: %s", player_ptr->name, what ? what : caption);
476 angband_fputs(ffp, xtmp, 80);
477 angband_fputs(ffp, "\n", 80);
479 while (!angband_fgets(fff, buff, sizeof(buff)))
480 angband_fputs(ffp, buff, 80);
483 fff = angband_fopen(path, "r");
486 if ((skey == ESCAPE) || (skey == '<'))
489 if (skey == KTRL('q'))
497 return (skey != 'q');
501 * Convert string to lower case
503 void str_tolower(char *str)
505 for (; *str; str++) {
512 *str = (char)tolower(*str);