The detail pane's Parameters section is now an editable form: each parameter is a type-hinted input field (string / number / json, optional marked), and a live "Builds" preview shows the command being assembled. String values are auto-quoted; a required field left empty keeps its placeholder and disables "Insert & run"; trailing empty optionals are omitted. Insert and Insert & run now use the assembled command (not just the template), so Insert & run works for parameterized commands once the required fields are filled — destructive commands still confirm first. Param fields reset when the selected command changes or the modal opens. Keyboard nav (Up/Down/Enter) is scoped to the search box so typing in a field doesn't move the selection. A best-effort parseParamSpecs turns the human-readable param templates into fields; JSON-array params (z_sendmany, createrawtransaction) surface as a single "json" field the user pastes into. Adds the console_ref_builds label + 8 translations. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
202 lines
8.8 KiB
C++
202 lines
8.8 KiB
C++
// DragonX Wallet - ImGui Edition
|
|
// Copyright 2024-2026 The Hush Developers
|
|
// Released under the GPLv3
|
|
|
|
#pragma once
|
|
|
|
#include "console_channel.h"
|
|
#include "console_model.h"
|
|
#include "console_scroll_controller.h"
|
|
#include "console_selection_controller.h"
|
|
#include "console_text_layout.h"
|
|
#include "../layout.h"
|
|
#include "../../daemon/embedded_daemon.h"
|
|
#include "../../daemon/xmrig_manager.h"
|
|
#include "../../rpc/rpc_client.h"
|
|
#include "../../rpc/rpc_worker.h"
|
|
|
|
#include <string>
|
|
#include <vector>
|
|
#include <deque>
|
|
#include <mutex>
|
|
|
|
namespace dragonx {
|
|
namespace ui {
|
|
|
|
class ConsoleCommandExecutor;
|
|
struct ConsoleLogFilterCaps;
|
|
struct ConsoleCommandEntry;
|
|
|
|
/**
|
|
* @brief Console tab — a rich terminal shared by the full-node and lite variants.
|
|
*
|
|
* The command execution + log sources are provided by a ConsoleCommandExecutor, so this
|
|
* one widget serves both dragonxd (RPC) and the lite backend.
|
|
*/
|
|
class ConsoleTab {
|
|
public:
|
|
ConsoleTab();
|
|
~ConsoleTab();
|
|
|
|
/**
|
|
* @brief Render the console tab against a backend executor.
|
|
*/
|
|
void render(ConsoleCommandExecutor& exec);
|
|
|
|
/**
|
|
* @brief Render the RPC Command Reference popup at top-level scope.
|
|
* Must be called outside any child window so the modal blocks all input.
|
|
*/
|
|
void renderCommandsPopupModal();
|
|
|
|
// Debug/UI-sweep hook: force the RPC command-reference popup open/closed so the full UI sweep
|
|
// can capture it (the popup is otherwise opened only by a toolbar button).
|
|
void sweepSetCommandsPopup(bool open) { show_commands_popup_ = open; }
|
|
|
|
/**
|
|
* @brief Add a line to the console output
|
|
*/
|
|
void addLine(const std::string& line, ConsoleChannel channel = ConsoleChannel::None);
|
|
void addRpcTraceLine(const std::string& source, const std::string& method);
|
|
|
|
/**
|
|
* @brief Clear console output
|
|
*/
|
|
void clear();
|
|
|
|
// Scanline effect toggle (set from settings)
|
|
static bool s_scanline_enabled;
|
|
|
|
// Console output zoom factor (1.0 = default caption font size)
|
|
static float s_console_zoom;
|
|
|
|
// Draw the per-line left color accent bars (channel-colored). Toggled from the toolbar.
|
|
static bool s_line_accents_enabled;
|
|
|
|
// Color output text per channel. When false the console is monochrome text. Toolbar-toggled.
|
|
static bool s_line_text_color_enabled;
|
|
|
|
// Show/hide daemon output messages
|
|
static bool s_daemon_messages_enabled;
|
|
|
|
// Show only error messages (filter toggle)
|
|
static bool s_errors_only_enabled;
|
|
|
|
// Show app RPC calls made through RPCClient (method/source only)
|
|
static bool s_rpc_trace_enabled;
|
|
|
|
// Show "[app] ..." wallet log lines
|
|
static bool s_app_messages_enabled;
|
|
|
|
/// Refresh console text colors for current theme (call after theme switch)
|
|
static void refreshColors();
|
|
|
|
// Colors — follow active theme (public for use by notification forwarding)
|
|
static ImU32 COLOR_COMMAND;
|
|
static ImU32 COLOR_RESULT;
|
|
static ImU32 COLOR_ERROR;
|
|
static ImU32 COLOR_DAEMON;
|
|
static ImU32 COLOR_INFO;
|
|
static ImU32 COLOR_RPC;
|
|
|
|
private:
|
|
// Text color for a channel, resolved from the current theme (COLOR_* + material). Each
|
|
// line stores only its semantic ConsoleChannel (in ConsoleModel); the text color and
|
|
// the left accent-bar color are both derived from it at draw time.
|
|
ImU32 channelTextColor(ConsoleChannel channel) const;
|
|
// Saturated accent color for a channel — the left accent-bar color, also used to tint the
|
|
// matching toolbar filter toggle. 0 for channels that get no accent (result/JSON/None).
|
|
static ImU32 channelAccentColor(ConsoleChannel channel);
|
|
|
|
// Drain the thread-safe ingest queue into the visible model (once per frame, main
|
|
// thread), applying the line cap + selection/scroll bookkeeping for the new lines.
|
|
void drainModel();
|
|
|
|
// Format a completed command result (JSON role -> channel) into console lines.
|
|
void addFormattedResult(const std::string& result, bool is_error);
|
|
void renderStatusHeader(ConsoleCommandExecutor& exec);
|
|
void renderCommandsPopup();
|
|
void renderCommandDetail(const ConsoleCommandEntry& cmd, const char* catLabel); // right pane
|
|
void insertCommandToInput(const ConsoleCommandEntry& cmd); // fill input + close the modal
|
|
|
|
// renderToolbar() draws the top bar; these are its sub-steps:
|
|
void renderToolbar(ConsoleCommandExecutor& exec);
|
|
void drawToolbarStatus(ConsoleCommandExecutor& exec); // backend status dot + label
|
|
void drawLogFilterToggles(const ConsoleLogFilterCaps& caps); // color-coded filter checkboxes
|
|
void drawFilterInput(); // text filter + match count
|
|
void drawZoomControls(); // zoom -/+ buttons
|
|
|
|
// renderInput() draws the command line; dispatch is factored out:
|
|
void renderInput(ConsoleCommandExecutor& exec);
|
|
// Echo + handle a submitted command line (built-ins + submit). True if non-empty/handled.
|
|
bool submitConsoleCommand(ConsoleCommandExecutor& exec, const std::string& cmd);
|
|
|
|
// renderOutput() orchestrates the scrollable output area; these are its sub-steps:
|
|
void renderOutput();
|
|
void computeVisibleLines(bool& hasTextFilter, std::string& filterLower); // -> visible_indices_
|
|
void handleOutputInteraction(ImVec2 mousePos, bool mouseInOutput); // wheel/selection/keys
|
|
void drawVisibleLines(float padX, float lineHeight, bool hasTextFilter,
|
|
const std::string& filterLower); // bars/guides/highlight/text
|
|
void drawNewOutputIndicator(); // jump-to-bottom pill
|
|
void drawOutputContextMenu(); // right-click menu
|
|
|
|
// Map a screen point to a raw {line, col} position via this frame's wrapped layout.
|
|
// (View-side because it needs layout_ + output_origin_; feeds the selection controller.)
|
|
ConsoleTextPos screenToTextPos(ImVec2 screen_pos) const;
|
|
|
|
// The current selection's text (via selection_ over the visible model). "" if inactive.
|
|
std::string selectedText() const;
|
|
|
|
// Thread-safe line store: producers on any thread call model_.ingest(); the main
|
|
// thread drains it once per frame in render(). The visible deque is main-thread-only.
|
|
ConsoleModel model_;
|
|
std::vector<std::string> command_history_;
|
|
int history_index_ = -1;
|
|
char input_buffer_[4096] = {0};
|
|
bool stop_confirm_pending_ = false; // 'stop' typed once, awaiting a confirming second 'stop'
|
|
// (log-ingestion cursors + result queue moved to the ConsoleCommandExecutor)
|
|
|
|
// Auto-scroll state machine (pin-to-bottom, wheel-up cooldown, new-line backlog count).
|
|
ConsoleScrollController scroll_;
|
|
|
|
// Text-selection state + logic (anchor/caret, ordering, extraction, eviction shift).
|
|
ConsoleSelectionController selection_;
|
|
float output_scroll_y_ = 0.0f; // Track scroll position for selection
|
|
ImVec2 output_origin_ = {0, 0}; // Top-left of output area
|
|
float output_line_height_ = 0.0f; // Text line height (for scanline alignment)
|
|
|
|
struct ScanlineRow {
|
|
float yTop = 0.0f;
|
|
float yBot = 0.0f;
|
|
int rowIndex = 0;
|
|
};
|
|
std::vector<ScanlineRow> scanline_rows_;
|
|
|
|
// Output filter
|
|
char filter_text_[128] = {0};
|
|
mutable int filter_match_count_ = 0; // lines matching the text filter (for the toolbar)
|
|
std::string context_token_; // hash/address under the cursor at right-click
|
|
mutable std::vector<int> visible_indices_; // Cached for selection mapping
|
|
bool folding_active_ = true; // fold UI shown only in the unfiltered (foldable) view
|
|
bool has_text_filter_ = false; // computed once per frame (before the toolbar draws it)
|
|
std::string filter_lower_; // lowercased filter needle for match highlighting
|
|
|
|
// Wrap layout for the visible lines (segments + per-line heights + cumulative Y),
|
|
// recomputed each frame by the pure BuildConsoleLayout (console_text_layout.h) and
|
|
// consumed by the renderer + hit-testing.
|
|
mutable ConsoleLayout layout_;
|
|
|
|
// Commands popup (RPC command explorer)
|
|
bool show_commands_popup_ = false;
|
|
char command_search_[128] = {0}; // RPC-reference search filter (cleared when the modal opens)
|
|
int cmd_sel_cat_ = -1; // detail-pane selection: category index into consoleCommandCategories()
|
|
int cmd_sel_idx_ = -1; // detail-pane selection: command index within that category
|
|
std::string pending_submit_; // command to run next frame (deferred so the modal needs no executor)
|
|
const ConsoleCommandEntry* run_confirm_cmd_ = nullptr; // destructive "Insert & run" awaiting confirmation
|
|
char cmd_param_bufs_[6][256] = {{0}}; // parameter-builder input fields
|
|
const ConsoleCommandEntry* cmd_param_owner_ = nullptr; // command the param buffers currently hold
|
|
};
|
|
|
|
} // namespace ui
|
|
} // namespace dragonx
|