Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 25 additions & 1 deletion packages/bruno-app/src/components/CodeMirrorSearch/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,31 @@ const CodeMirrorSearch = forwardRef(({ visible, editor, onClose }, ref) => {
editor.addLineClass(currentLine, 'wrap', 'cm-search-line-highlight');
searchLineHighlight.current = currentLine;

editor.scrollIntoView(matches[matchIndex].from, 100);
// previous line of code
// editor.scrollIntoView(matches[matchIndex].from, 100);

// This is the part we are fixing for issue #7875.
// Before, CodeMirror only scrolled enough to make the match visible,
// which often placed the result near the bottom of the JSON viewport.
// Now we calculate the matched line position and force it closer to
// the vertical centre, giving users better JSON context above and below.
const activeMatch = matches[matchIndex];
const scroller = editor.getScrollerElement();
const lineHeight = editor.defaultTextHeight();

// CodeMirror's heightAtLine gives us the vertical position of the line
// inside the full editor document, not just the visible screen.
const matchTop = editor.heightAtLine(activeMatch.from.line, 'local');

// We subtract half the viewport height, then add a few line heights so
// the highlighted line is visually centred instead of being too high.
const targetScrollTop = Math.max(
0,
matchTop - scroller.clientHeight / 2 + lineHeight * 3
);
// my line of work ends here
editor.scrollTo(null, targetScrollTop);
Comment on lines +159 to +174
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🌐 Web query:

In CodeMirror 5, what is the difference between heightAtLine(line, 'local')andcharCoords(pos, 'local'), and which API reflects the actual vertical position of a match inside a wrapped line?

💡 Result:

In CodeMirror 5, heightAtLine(line, "local") and charCoords(pos, "local") both accept "local" as the coordinate reference mode, but they answer different geometry questions: 1) heightAtLine(line, "local") - Returns the y position (height from the top of the editor viewport) of the top of the given logical line. - It’s line-level and based on CodeMirror’s internal measurement model for line heights (which can be approximated when the line has not actually been rendered due to viewport/lazy rendering) [1]. - For wrapped lines, this is about the logical line’s top (not a specific visual wrap “sub-line”), so it does not directly tell you where a particular wrapped segment starts/ends. 2) charCoords(pos, "local") - Returns the rectangle for a specific character position in the document, including top/bottom in the chosen coordinate system (here, "local") [2][3]. - Because it’s character-based, it reflects the actual layout of the visual line wrapping for that position (including which wrapped segment the character is on). Which API reflects the actual vertical position of a match inside a wrapped line? - Use charCoords(pos, "local") for match rendering/positioning. Since matches are character ranges (positions) and wrapping is visual/segment-based, the character rectangle returned by charCoords is the API that corresponds to the actual on-screen vertical placement of the match within wrapped lines [2][3]. Important nuance about "local" - There have been historical issues where charCoords(..., "local") could be inconsistent/off by padding (and related fixes landed) [4]. So if you’re comparing to other local measurements (or doing pixel-perfect positioning), you should validate against getScrollInfo()/wrapper padding in your exact setup—but the character-based nature of charCoords remains what makes it the correct choice for “vertical position of a match inside a wrapped line.” [4][2]

Citations:


Use charCoords() to reflect the actual position of wrapped matches.

heightAtLine() returns only the logical line's top, which doesn't account for the actual vertical position of a match within a wrapped line. charCoords() is character-position aware and reflects the true on-screen placement.

🔧 Suggested change
-      const matchTop = editor.heightAtLine(activeMatch.from.line, 'local');
+      const matchTop = editor.charCoords(activeMatch.from, 'local').top;
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/bruno-app/src/components/CodeMirrorSearch/index.js` around lines 159
- 174, The current centering uses editor.heightAtLine(activeMatch.from.line,
'local') which ignores wrapped-line offsets; replace that with
editor.charCoords(activeMatch.from, 'local') and use coords.top (the actual
on-screen Y for the match) when computing targetScrollTop so wrapped matches are
centered correctly; update the code that defines matchTop (or remove it) to call
editor.charCoords(activeMatch.from, 'local') and use the returned .top value in
the existing centering calculation before calling editor.scrollTo.


editor.setSelection(matches[matchIndex].from, matches[matchIndex].to);
} catch (e) {
console.error('Search error:', e);
Expand Down