MyStudio IDE: How Goto Line feature works
Hello,
I'd recently implemented "Goto Line" feature on my side project, MyStudio IDE and here's how I did it.
Background:
As a part of building essential features for an IDE, "Goto Line" seemed like an easy milestone.
There may be other ways to accomplish this but here's how I did it.
UI Goals:
Show a UI widget, "Line X, Column Y" to the bottom-right on the application's status bar.
Clicking on it should spawn a dialog with an input field to enter two types of data:
- a line number
- a key:pair of line number and column. Ex: 4:2 (line number 4, column number 2)
User can initiate the request by either pressing Enter key or clicking on OK button of the dialog.
This indicator should be visible ONLY when we have an open file.
It should also respond to keyboard shortcut
Ctrl+G
when request is valid.
UI Design:
Indicator UI:
Dialog:
Implementation:
I looked at gedit and KWrite and decided to use GtkButton
as the line indicator widget instead of GtkLabel
.
We start by initializing status bar UI and storing references to button and input field of dialog from main_window.ui
(Glade resource file) from Builder
object.
Feature 1: Changes to cursor position should update line indicator
TextBuffer
of GtkSourceView
instance (text editor widget) has a connect_cursor_position_notify
callback, also called a 'signal' in GTK terminlogy.
This callback, as the name suggests, is triggered each time cursor position changes and it returns a reference to TextBuffer
instance.
I wrote fetch_line_number_by_buffer function to fetch the current line number and column number as a Tuple.
With this info, we call the update function that does some sanity checks before updating the UI widget.
TextBuffer returns a zero-based number for the line numbers which is why we need to adjust the values as required before updating the indicator.
Feature 2: Jump to given line number & update indicator
Just like before, we need access to TextBuffer
to change the cursor's position for a given text editor instance.
I wrote the jump_to_line_with_editor function that takes 3 parameters - line number, column number and aGtkSourceView
(text editor) instance.
Inside this function, we get access to TextIter object of the TextBuffer
for a given line number AFTER decrement it by 1.
The line - 1
is necessary because TextBuffer assumes given line number will start from zero.
Later, we set the column number (after decrement by 1, ofcourse!) to this TextIter
object and use TextBuffer
's place_cursor
function to update the UI.
We don't have to validate the user input here as this is handled by text editor instance. For example, if user provides a line number greater than total lines of an open file, it will simply go to the last line.
End Result:
Thanks for reading! Leave a comment down below on your thoughts or any ideas for this.
Don't forget to give it a like to this post seen to your right :)
You can @ me on Twitter