mirror of
https://github.com/NohamR/Reclass.git
synced 2026-05-10 19:59:21 +00:00
Shadcn-style command row: pill chips, chevron breadcrumbs, left-elide
- Add ROUNDBOX pill indicators behind editable SRC and ADDR spans - Switch breadcrumb separator from > to › (U+203A) - Collapse deep paths (>4 parts) with ellipsis - Left-elide breadcrumb path to keep current selection visible - Clear base-addr indicator before repainting (prevents smear) - Wire pill + addr decorators into setCommandRowText refresh
This commit is contained in:
@@ -24,6 +24,12 @@ static QString elide(QString s, int max) {
|
|||||||
return s.left(max - 1) + QChar(0x2026);
|
return s.left(max - 1) + QChar(0x2026);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static QString elideLeft(const QString& s, int max) {
|
||||||
|
if (s.size() <= max) return s;
|
||||||
|
if (max <= 1) return QStringLiteral("\u2026").left(max);
|
||||||
|
return QStringLiteral("\u2026") + s.right(max - 1);
|
||||||
|
}
|
||||||
|
|
||||||
static QString crumbFor(const rcx::NodeTree& t, uint64_t nodeId) {
|
static QString crumbFor(const rcx::NodeTree& t, uint64_t nodeId) {
|
||||||
QStringList parts;
|
QStringList parts;
|
||||||
QSet<uint64_t> seen;
|
QSet<uint64_t> seen;
|
||||||
@@ -37,7 +43,9 @@ static QString crumbFor(const rcx::NodeTree& t, uint64_t nodeId) {
|
|||||||
cur = n.parentId;
|
cur = n.parentId;
|
||||||
}
|
}
|
||||||
std::reverse(parts.begin(), parts.end());
|
std::reverse(parts.begin(), parts.end());
|
||||||
return parts.join(QStringLiteral(" > "));
|
if (parts.size() > 4)
|
||||||
|
parts = {parts.front(), QStringLiteral("\u2026"), parts[parts.size() - 2], parts.back()};
|
||||||
|
return parts.join(QStringLiteral(" \u203A "));
|
||||||
}
|
}
|
||||||
|
|
||||||
// ── RcxDocument ──
|
// ── RcxDocument ──
|
||||||
@@ -814,7 +822,7 @@ void RcxController::updateCommandRow() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
QString row = QStringLiteral(" * SRC: %1 : %2 %3")
|
QString row = QStringLiteral(" * SRC: %1 : %2 %3")
|
||||||
.arg(elide(src, 40), elide(addr, 24), elide(path, 120));
|
.arg(elide(src, 40), elide(addr, 24), elideLeft(path, 120));
|
||||||
|
|
||||||
for (auto* ed : m_editors)
|
for (auto* ed : m_editors)
|
||||||
ed->setCommandRowText(row);
|
ed->setCommandRowText(row);
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ static constexpr int IND_EDITABLE = 8;
|
|||||||
static constexpr int IND_HEX_DIM = 9;
|
static constexpr int IND_HEX_DIM = 9;
|
||||||
static constexpr int IND_BASE_ADDR = 10; // Green color for base address
|
static constexpr int IND_BASE_ADDR = 10; // Green color for base address
|
||||||
static constexpr int IND_HOVER_SPAN = 11; // Blue text on hover (link-like)
|
static constexpr int IND_HOVER_SPAN = 11; // Blue text on hover (link-like)
|
||||||
|
static constexpr int IND_CMD_PILL = 12; // Rounded chip behind command row spans
|
||||||
|
|
||||||
// Footer selection ID: set high bit to distinguish footer-only selections from node selections
|
// Footer selection ID: set high bit to distinguish footer-only selections from node selections
|
||||||
static constexpr uint64_t kFooterIdBit = 0x8000000000000000ULL;
|
static constexpr uint64_t kFooterIdBit = 0x8000000000000000ULL;
|
||||||
@@ -151,6 +152,16 @@ void RcxEditor::setupScintilla() {
|
|||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,
|
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,
|
||||||
IND_HOVER_SPAN, QColor("#3d9c8a"));
|
IND_HOVER_SPAN, QColor("#3d9c8a"));
|
||||||
|
|
||||||
|
// Command-row pill background (shadcn-ish chip)
|
||||||
|
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETSTYLE,
|
||||||
|
IND_CMD_PILL, 7 /*INDIC_ROUNDBOX*/);
|
||||||
|
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,
|
||||||
|
IND_CMD_PILL, QColor("#2a2a2a"));
|
||||||
|
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETALPHA,
|
||||||
|
IND_CMD_PILL, (long)90);
|
||||||
|
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICSETUNDER,
|
||||||
|
IND_CMD_PILL, (long)1);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void RcxEditor::setupLexer() {
|
void RcxEditor::setupLexer() {
|
||||||
@@ -301,6 +312,7 @@ void RcxEditor::applyDocument(const ComposeResult& result) {
|
|||||||
applyFoldLevels(result.meta);
|
applyFoldLevels(result.meta);
|
||||||
applyHexDimming(result.meta);
|
applyHexDimming(result.meta);
|
||||||
applyBaseAddressColoring(result.meta);
|
applyBaseAddressColoring(result.meta);
|
||||||
|
applyCommandRowPills();
|
||||||
|
|
||||||
// Reset hint line - applySelectionOverlay will repaint indicators
|
// Reset hint line - applySelectionOverlay will repaint indicators
|
||||||
m_hintLine = -1;
|
m_hintLine = -1;
|
||||||
@@ -517,18 +529,32 @@ static QString getLineText(QsciScintilla* sci, int line) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void RcxEditor::applyBaseAddressColoring(const QVector<LineMeta>& meta) {
|
void RcxEditor::applyBaseAddressColoring(const QVector<LineMeta>& meta) {
|
||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_SETINDICATORCURRENT, IND_BASE_ADDR);
|
if (meta.isEmpty() || meta[0].lineKind != LineKind::CommandRow) return;
|
||||||
// Color the ADDR span on CommandRow (line 0)
|
|
||||||
if (!meta.isEmpty() && meta[0].lineKind == LineKind::CommandRow) {
|
clearIndicatorLine(IND_BASE_ADDR, 0);
|
||||||
QString lineText = getLineText(m_sci, 0);
|
QString lineText = getLineText(m_sci, 0);
|
||||||
ColumnSpan span = commandRowAddrSpan(lineText);
|
ColumnSpan span = commandRowAddrSpan(lineText);
|
||||||
if (span.valid) {
|
if (span.valid)
|
||||||
long posA = posFromCol(m_sci, 0, span.start);
|
fillIndicatorCols(IND_BASE_ADDR, 0, span.start, span.end);
|
||||||
long posB = posFromCol(m_sci, 0, span.end);
|
|
||||||
if (posB > posA)
|
|
||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_INDICATORFILLRANGE, posA, posB - posA);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RcxEditor::applyCommandRowPills() {
|
||||||
|
if (m_meta.isEmpty() || m_meta[0].lineKind != LineKind::CommandRow) return;
|
||||||
|
|
||||||
|
constexpr int line = 0;
|
||||||
|
QString t = getLineText(m_sci, line);
|
||||||
|
|
||||||
|
clearIndicatorLine(IND_CMD_PILL, line);
|
||||||
|
|
||||||
|
auto fillPadded = [&](ColumnSpan s) {
|
||||||
|
if (!s.valid) return;
|
||||||
|
int a = qMax(0, s.start - 1);
|
||||||
|
int b = qMin(t.size(), s.end + 1);
|
||||||
|
fillIndicatorCols(IND_CMD_PILL, line, a, b);
|
||||||
|
};
|
||||||
|
|
||||||
|
fillPadded(commandRowSrcSpan(t));
|
||||||
|
fillPadded(commandRowAddrSpan(t));
|
||||||
}
|
}
|
||||||
|
|
||||||
// ── Shared inline-edit shutdown ──
|
// ── Shared inline-edit shutdown ──
|
||||||
@@ -1563,6 +1589,8 @@ void RcxEditor::setCommandRowText(const QString& line) {
|
|||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_SETCURRENTPOS, savedPos);
|
m_sci->SendScintilla(QsciScintillaBase::SCI_SETCURRENTPOS, savedPos);
|
||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_SETANCHOR, savedAnchor);
|
m_sci->SendScintilla(QsciScintillaBase::SCI_SETANCHOR, savedAnchor);
|
||||||
m_sci->SendScintilla(QsciScintillaBase::SCI_COLOURISE, start, start + utf8.size());
|
m_sci->SendScintilla(QsciScintillaBase::SCI_COLOURISE, start, start + utf8.size());
|
||||||
|
applyBaseAddressColoring(m_meta);
|
||||||
|
applyCommandRowPills();
|
||||||
}
|
}
|
||||||
|
|
||||||
void RcxEditor::setEditorFont(const QString& fontName) {
|
void RcxEditor::setEditorFont(const QString& fontName) {
|
||||||
|
|||||||
@@ -115,6 +115,7 @@ private:
|
|||||||
void applyFoldLevels(const QVector<LineMeta>& meta);
|
void applyFoldLevels(const QVector<LineMeta>& meta);
|
||||||
void applyHexDimming(const QVector<LineMeta>& meta);
|
void applyHexDimming(const QVector<LineMeta>& meta);
|
||||||
void applyBaseAddressColoring(const QVector<LineMeta>& meta);
|
void applyBaseAddressColoring(const QVector<LineMeta>& meta);
|
||||||
|
void applyCommandRowPills();
|
||||||
|
|
||||||
void commitInlineEdit();
|
void commitInlineEdit();
|
||||||
int editEndCol() const;
|
int editEndCol() const;
|
||||||
|
|||||||
Reference in New Issue
Block a user