1 #include "cmd-visual/cmd-visuals.h"
2 #include "cmd-visual/cmd-draw.h"
3 #include "core/asking-player.h"
4 #include "core/visuals-reseter.h"
5 #include "flavor/flavor-describer.h"
6 #include "flavor/object-flavor-types.h"
7 #include "flavor/object-flavor.h"
8 #include "game-option/special-options.h"
9 #include "io/files-util.h"
10 #include "io/input-key-acceptor.h"
11 #include "io/read-pref-file.h"
12 #include "knowledge/knowledge-features.h"
13 #include "knowledge/knowledge-items.h"
14 #include "knowledge/knowledge-monsters.h"
15 #include "knowledge/lighting-level-table.h"
16 #include "main/sound-of-music.h"
17 #include "monster-race/monster-race.h"
18 #include "object/object-kind.h"
19 #include "system/monster-race-definition.h"
20 #include "system/object-type-definition.h"
21 #include "system/player-type-definition.h"
22 #include "term/screen-processor.h"
23 #include "term/term-color-types.h"
24 #include "util/angband-files.h"
25 #include "util/int-char-converter.h"
26 #include "view/display-messages.h"
29 * @brief キャラクタのビジュアルIDを変更する際の対象指定関数
30 * @param i 指定対象となるキャラクタコード
31 * @param num 指定されたビジュアルIDを返す参照ポインタ
32 * @param max ビジュアルIDの最大数
33 * @return 指定が実際に行われた場合TRUE、キャンセルされた場合FALSE
35 static bool cmd_visuals_aux(int i, IDX *num, IDX max)
39 sprintf(str, "%d", *num);
40 if (!get_string(format("Input new number(0-%d): ", max - 1), str, 4)) {
44 IDX tmp = (IDX)strtol(str, nullptr, 0);
45 if (tmp >= 0 && tmp < max) {
48 } else if (isupper(i)) {
49 *num = (*num + max - 1) % max;
51 *num = (*num + 1) % max;
58 * @brief キャラクタの変更メニュー表示
59 * @param choice_msg 選択メッセージ
61 static void print_visuals_menu(concptr choice_msg)
63 prt(_("[ 画面表示の設定 ]", "Interact with Visuals"), 1, 0);
64 prt(_("(0) ユーザー設定ファイルのロード", "(0) Load a user pref file"), 3, 5);
65 prt(_("(1) モンスターの 色/文字 をファイルに書き出す", "(1) Dump monster attr/chars"), 4, 5);
66 prt(_("(2) アイテムの 色/文字 をファイルに書き出す", "(2) Dump object attr/chars"), 5, 5);
67 prt(_("(3) 地形の 色/文字 をファイルに書き出す", "(3) Dump feature attr/chars"), 6, 5);
68 prt(_("(4) モンスターの 色/文字 を変更する (数値操作)", "(4) Change monster attr/chars (numeric operation)"), 7, 5);
69 prt(_("(5) アイテムの 色/文字 を変更する (数値操作)", "(5) Change object attr/chars (numeric operation)"), 8, 5);
70 prt(_("(6) 地形の 色/文字 を変更する (数値操作)", "(6) Change feature attr/chars (numeric operation)"), 9, 5);
71 prt(_("(7) モンスターの 色/文字 を変更する (シンボルエディタ)", "(7) Change monster attr/chars (visual mode)"), 10, 5);
72 prt(_("(8) アイテムの 色/文字 を変更する (シンボルエディタ)", "(8) Change object attr/chars (visual mode)"), 11, 5);
73 prt(_("(9) 地形の 色/文字 を変更する (シンボルエディタ)", "(9) Change feature attr/chars (visual mode)"), 12, 5);
74 prt(_("(R) 画面表示方法の初期化", "(R) Reset visuals"), 13, 5);
75 prt(format(_("コマンド: %s", "Command: %s"), choice_msg ? choice_msg : _("", "")), 15, 0);
79 * Interact with "visuals"
81 void do_cmd_visuals(PlayerType *player_ptr)
83 FILE *auto_dump_stream;
86 bool need_redraw = false;
87 concptr empty_symbol = "<< ? >>";
89 empty_symbol = "<< ?? >>";
95 print_visuals_menu(nullptr);
103 prt(_("コマンド: ユーザー設定ファイルのロード", "Command: Load a user pref file"), 15, 0);
104 prt(_("ファイル: ", "File: "), 17, 0);
105 sprintf(tmp, "%s.prf", player_ptr->base_name);
106 if (!askfor(tmp, 70)) {
110 (void)process_pref_file(player_ptr, tmp, true);
115 static concptr mark = "Monster attr/chars";
116 prt(_("コマンド: モンスターの[色/文字]をファイルに書き出します", "Command: Dump monster attr/chars"), 15, 0);
117 prt(_("ファイル: ", "File: "), 17, 0);
118 sprintf(tmp, "%s.prf", player_ptr->base_name);
119 if (!askfor(tmp, 70)) {
123 path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
124 if (!open_auto_dump(&auto_dump_stream, buf, mark)) {
128 auto_dump_printf(auto_dump_stream, _("\n# モンスターの[色/文字]の設定\n\n", "\n# Monster attr/char definitions\n\n"));
129 for (const auto &[r_idx, r_ref] : r_info) {
130 if (r_ref.name.empty()) {
134 auto_dump_printf(auto_dump_stream, "# %s\n", r_ref.name.c_str());
135 auto_dump_printf(auto_dump_stream, "R:%d:0x%02X/0x%02X\n\n", r_ref.idx, (byte)(r_ref.x_attr), (byte)(r_ref.x_char));
138 close_auto_dump(&auto_dump_stream, mark);
139 msg_print(_("モンスターの[色/文字]をファイルに書き出しました。", "Dumped monster attr/chars."));
143 static concptr mark = "Object attr/chars";
144 prt(_("コマンド: アイテムの[色/文字]をファイルに書き出します", "Command: Dump object attr/chars"), 15, 0);
145 prt(_("ファイル: ", "File: "), 17, 0);
146 sprintf(tmp, "%s.prf", player_ptr->base_name);
147 if (!askfor(tmp, 70)) {
151 path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
152 if (!open_auto_dump(&auto_dump_stream, buf, mark)) {
156 auto_dump_printf(auto_dump_stream, _("\n# アイテムの[色/文字]の設定\n\n", "\n# Object attr/char definitions\n\n"));
157 for (const auto &k_ref : k_info) {
158 if (k_ref.name.empty()) {
162 std::string o_name("");
163 GAME_TEXT char_o_name[MAX_NLEN]{};
165 o_name = strip_name(k_ref.idx);
168 dummy.prep(k_ref.idx);
169 describe_flavor(player_ptr, char_o_name, &dummy, OD_FORCE_FLAVOR);
173 o_name = char_o_name;
176 auto_dump_printf(auto_dump_stream, "# %s\n", o_name.data());
177 auto_dump_printf(auto_dump_stream, "K:%d:0x%02X/0x%02X\n\n", (int)k_ref.idx, (byte)(k_ref.x_attr), (byte)(k_ref.x_char));
180 close_auto_dump(&auto_dump_stream, mark);
181 msg_print(_("アイテムの[色/文字]をファイルに書き出しました。", "Dumped object attr/chars."));
185 static concptr mark = "Feature attr/chars";
186 prt(_("コマンド: 地形の[色/文字]をファイルに書き出します", "Command: Dump feature attr/chars"), 15, 0);
187 prt(_("ファイル: ", "File: "), 17, 0);
188 sprintf(tmp, "%s.prf", player_ptr->base_name);
189 if (!askfor(tmp, 70)) {
193 path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
194 if (!open_auto_dump(&auto_dump_stream, buf, mark)) {
198 auto_dump_printf(auto_dump_stream, _("\n# 地形の[色/文字]の設定\n\n", "\n# Feature attr/char definitions\n\n"));
199 for (const auto &f_ref : f_info) {
200 if (f_ref.name.empty()) {
203 if (f_ref.mimic != f_ref.idx) {
207 auto_dump_printf(auto_dump_stream, "# %s\n", (f_ref.name.c_str()));
208 auto_dump_printf(auto_dump_stream, "F:%d:0x%02X/0x%02X:0x%02X/0x%02X:0x%02X/0x%02X\n\n", f_ref.idx, (byte)(f_ref.x_attr[F_LIT_STANDARD]),
209 (byte)(f_ref.x_char[F_LIT_STANDARD]), (byte)(f_ref.x_attr[F_LIT_LITE]), (byte)(f_ref.x_char[F_LIT_LITE]),
210 (byte)(f_ref.x_attr[F_LIT_DARK]), (byte)(f_ref.x_char[F_LIT_DARK]));
213 close_auto_dump(&auto_dump_stream, mark);
214 msg_print(_("地形の[色/文字]をファイルに書き出しました。", "Dumped feature attr/chars."));
219 static concptr choice_msg = _("モンスターの[色/文字]を変更します", "Change monster attr/chars");
220 static MonsterRaceId r = r_info.begin()->second.idx;
221 prt(format(_("コマンド: %s", "Command: %s"), choice_msg), 15, 0);
223 auto *r_ptr = &r_info[r];
227 TERM_COLOR da = r_ptr->d_attr;
228 byte dc = r_ptr->d_char;
229 TERM_COLOR ca = r_ptr->x_attr;
230 byte cc = r_ptr->x_char;
232 term_putstr(5, 17, -1, TERM_WHITE, format(_("モンスター = %d, 名前 = %-40.40s", "Monster = %d, Name = %-40.40s"), r, r_ptr->name.c_str()));
233 term_putstr(10, 19, -1, TERM_WHITE, format(_("初期値 色 / 文字 = %3u / %3u", "Default attr/char = %3u / %3u"), da, dc));
234 term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
235 term_queue_bigchar(43, 19, da, dc, 0, 0);
236 term_putstr(10, 20, -1, TERM_WHITE, format(_("現在値 色 / 文字 = %3u / %3u", "Current attr/char = %3u / %3u"), ca, cc));
237 term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
238 term_queue_bigchar(43, 20, ca, cc, 0, 0);
239 term_putstr(0, 22, -1, TERM_WHITE, _("コマンド (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ", "Command (n/N/^N/a/A/^A/c/C/^C/v/V/^V): "));
246 c = 'a' + i - KTRL('A');
247 } else if (isupper(i)) {
257 if (!cmd_visuals_aux(i, &num, static_cast<IDX>(r_info.size()))) {
261 r = i2enum<MonsterRaceId>(num);
262 } while (r_info[r].name.empty());
267 t = (int)r_ptr->x_attr;
268 (void)cmd_visuals_aux(i, &t, 256);
269 r_ptr->x_attr = (byte)t;
273 t = (int)r_ptr->x_char;
274 (void)cmd_visuals_aux(i, &t, 256);
275 r_ptr->x_char = (byte)t;
279 do_cmd_knowledge_monsters(player_ptr, &need_redraw, true, r);
281 print_visuals_menu(choice_msg);
289 static concptr choice_msg = _("アイテムの[色/文字]を変更します", "Change object attr/chars");
291 prt(format(_("コマンド: %s", "Command: %s"), choice_msg), 15, 0);
293 auto *k_ptr = &k_info[k];
297 TERM_COLOR da = k_ptr->d_attr;
298 auto dc = k_ptr->d_char;
299 TERM_COLOR ca = k_ptr->x_attr;
300 auto cc = k_ptr->x_char;
302 term_putstr(5, 17, -1, TERM_WHITE,
304 _("アイテム = %d, 名前 = %-40.40s", "Object = %d, Name = %-40.40s"), k, (!k_ptr->flavor ? k_ptr->name : k_ptr->flavor_name).c_str()));
305 term_putstr(10, 19, -1, TERM_WHITE, format(_("初期値 色 / 文字 = %3d / %3d", "Default attr/char = %3d / %3d"), da, dc));
306 term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
307 term_queue_bigchar(43, 19, da, dc, 0, 0);
308 term_putstr(10, 20, -1, TERM_WHITE, format(_("現在値 色 / 文字 = %3d / %3d", "Current attr/char = %3d / %3d"), ca, cc));
309 term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
310 term_queue_bigchar(43, 20, ca, cc, 0, 0);
311 term_putstr(0, 22, -1, TERM_WHITE, _("コマンド (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ", "Command (n/N/^N/a/A/^A/c/C/^C/v/V/^V): "));
319 c = 'a' + i - KTRL('A');
320 } else if (isupper(i)) {
330 if (!cmd_visuals_aux(i, &k, static_cast<IDX>(k_info.size()))) {
334 } while (k_info[k].name.empty());
339 t = (int)k_ptr->x_attr;
340 (void)cmd_visuals_aux(i, &t, 256);
341 k_ptr->x_attr = (byte)t;
345 t = (int)k_ptr->x_char;
346 (void)cmd_visuals_aux(i, &t, 256);
347 k_ptr->x_char = (byte)t;
351 do_cmd_knowledge_objects(player_ptr, &need_redraw, true, k);
353 print_visuals_menu(choice_msg);
361 static concptr choice_msg = _("地形の[色/文字]を変更します", "Change feature attr/chars");
363 static IDX lighting_level = F_LIT_STANDARD;
364 prt(format(_("コマンド: %s", "Command: %s"), choice_msg), 15, 0);
366 auto *f_ptr = &f_info[f];
370 TERM_COLOR da = f_ptr->d_attr[lighting_level];
371 byte dc = f_ptr->d_char[lighting_level];
372 TERM_COLOR ca = f_ptr->x_attr[lighting_level];
373 byte cc = f_ptr->x_char[lighting_level];
376 term_putstr(5, 17, -1, TERM_WHITE,
377 format(_("地形 = %d, 名前 = %s, 明度 = %s", "Terrain = %d, Name = %s, Lighting = %s"), f, (f_ptr->name.c_str()),
378 lighting_level_str[lighting_level]));
379 term_putstr(10, 19, -1, TERM_WHITE, format(_("初期値 色 / 文字 = %3d / %3d", "Default attr/char = %3d / %3d"), da, dc));
380 term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
381 term_queue_bigchar(43, 19, da, dc, 0, 0);
382 term_putstr(10, 20, -1, TERM_WHITE, format(_("現在値 色 / 文字 = %3d / %3d", "Current attr/char = %3d / %3d"), ca, cc));
383 term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
384 term_queue_bigchar(43, 20, ca, cc, 0, 0);
385 term_putstr(0, 22, -1, TERM_WHITE,
386 _("コマンド (n/N/^N/a/A/^A/c/C/^C/l/L/^L/d/D/^D/v/V/^V): ", "Command (n/N/^N/a/A/^A/c/C/^C/l/L/^L/d/D/^D/v/V/^V): "));
394 c = 'a' + i - KTRL('A');
395 } else if (isupper(i)) {
405 if (!cmd_visuals_aux(i, &f, static_cast<IDX>(f_info.size()))) {
409 } while (f_info[f].name.empty() || (f_info[f].mimic != f));
414 t = (int)f_ptr->x_attr[lighting_level];
415 (void)cmd_visuals_aux(i, &t, 256);
416 f_ptr->x_attr[lighting_level] = (byte)t;
420 t = (int)f_ptr->x_char[lighting_level];
421 (void)cmd_visuals_aux(i, &t, 256);
422 f_ptr->x_char[lighting_level] = (byte)t;
426 (void)cmd_visuals_aux(i, &lighting_level, F_LIT_MAX);
429 apply_default_feat_lighting(f_ptr->x_attr, f_ptr->x_char);
433 do_cmd_knowledge_features(&need_redraw, true, f, &lighting_level);
435 print_visuals_menu(choice_msg);
443 do_cmd_knowledge_monsters(player_ptr, &need_redraw, true);
446 do_cmd_knowledge_objects(player_ptr, &need_redraw, true, -1);
449 IDX lighting_level = F_LIT_STANDARD;
450 do_cmd_knowledge_features(&need_redraw, true, -1, &lighting_level);
455 reset_visuals(player_ptr);
456 msg_print(_("画面上の[色/文字]を初期値にリセットしました。", "Visual attr/char tables reset."));
469 do_cmd_redraw(player_ptr);