Contents |
Отладка, чтение и написание исходного кода — это то, на что у Вас будет уходить основное время при разработке программного обеспечения. С этой целью KDevelop предоставляет Вам множество различных возможностей в изучении исходного кода и более продуктивном его написании. В следующих разделах рассказывается что KDevelop является не только редактором исходного кода — он скорее является системой управления исходным кодом, которая даёт Вам различные представления информации о содержимом файлов с исходным кодом, которые в совокупности представляют собой сеансы.
Для работы с проектами в KDevelop используются инструменты. Инструмент обеспечивает некоторое представление объекта с которым предназначен работать или действий, которые могут быть выполнены над ним. Инструменты представлены в виде кнопок, находящихся по краю окна (вертикально по левому или правому краям, либо горизонтально по нижнему краю). При нажатии на такую кнопку, в главном окне открывается служебная панель с инструментом. Если же нажать на эту кнопку снова — панель скроется.
| Примечание |
|---|
| Чтобы скрыть служебную панель можно также нажать кнопку в правой части заголовка панели. Однако, по крайней мере в последних версиях KDevelop 4.2.x, это так же приведёт к исчезновению кнопки, представляющую инструмент на границе окна. Как вернуть потерянную кнопку обратно, равно как и кнопку любого другого инструмента, описано ниже. Данное поведение описано в отчёте об ошибках bug 270018 |
Изображение, приведённое выше, показывает служебные панели, расположенные по левому и правому краям. Панель Classes (Классы в русском переводе) открыта слева, а панель Snippets (Фрагменты в русском переводе) — справа от редактора исходного кода, размещённого в середине. На практике Вы вероятнее всего будете пользоваться преимущественно панелями Классы и Навигация по коду, открытыми слева. Остальные панели вероятнее всего будут открываться на время необходимое для работы с ними, оставляя в основное рабочее время всё свободное пространство редактору кода.
Когда Вы запустите KDevelop, Вы должны увидеть кнопку панели инструментов . Нажав её, откроется окно панели, которая снизу отобразит проекты открытые в существующей сессии, а сверху иерархию директорий и файлов открытых проектов.
Есть много иных служебных панелей которые можно использовать в KDevelop, кнопки которых не все изначально присутствуют на границах главного окна. Чтобы добавить интересующую панель следует выбрать пункт меню . Вот некоторые из тех, что могут оказаться полезными:
#include line, it shows information about the file you are including such as what classes are declared in that file; if you are on an empty line at file scope, it shows the classes and functions declared and defined in the current file (all as links: clicking on them brings you to the point in the file where the declaration or definition actually is); if you are in a function definition, it shows where the declaration is and offers a list of places where the function is used.
for (typename Triangulation< dim>::active_cell_iterator cell
= triangulation.begin_active();
cell != triangulation.end();
++cell)./configure).
A complete list of tools and views is given here.
For many programmers, vertical screen space is the most important. To this end, you can arrange your tool views at the left and right margin of the window: to move a tool, click on its symbol with the right mouse button and select a new position for it.
KDevelop understands source code, and as a consequence it is really good at providing you information about variables or functions that may appear in your program. For example, here is a snapshot of working with a piece of code and hovering the mouse over the symbol cell in line 1316 (if you are working keyboard oriented, you can achieve the same effect by holding down the Alt key for a while):
KDevelop shows me a tooltip that includes the type of the variable (here: DoFHandler<dim>active_cell_iterator), where this variable is declared (the container, which here is the surrounding function get_maximal_velocity since it is a local variable), what it is (a variable, not a function, class or namespace) and where it is declared (in line 1314, just a few lines up in the code).
In the current context, the symbol over which the mouse was hovering has no associated documentation. In this example, had the mouse hovered over the symbol get_this_mpi_process in line 1318, the outcome would have been this:
Here, KDevelop has cross-referenced the declaration from an entirely different file (utilities.h, which in fact even resides in a different project of the same session) together with the doxygen-style comment that accompanies the declaration there.
What makes these tooltips even more useful is that they are dynamic: I can click on the container to get information about the context in which the variable is declared (i.e. about the namespace System, such as where it is declared, defined, used, or what its documentation is) and I can click on the blue links that will reset the cursor position to the location of the declaration of the Symbol (e.g. in utilities.h, line 289) or give me a list of places where this symbol is used in the current file or throughout all the projects of the current session. The latter is often useful if you want to explore how, for example, a particular function is used in a large code basis.
| Note |
|---|
| The information in a tooltip is fleeting — it depends on you holding the Alt key down or hovering your mouse. If you want a more permanent place for it, open the Code Browser tool view in one of the sub-windows. For example, here the cursor is on the same function as in the example above, and the tool view on the left presents the same kind of information as in the tooltip before: Moving the cursor around on the right changes the information presented on the left. What's more, clicking on the button at the top right allows you to lock this information, making it independent of the cursor movement while you explore the information presented there. |
| Note |
|---|
| This sort of context information is available in many other places in KDevelop, not just in the source editor. For example, holding down the Alt key in a completion list (e.g. when doing a quick-open) also yields context information about the current symbol. |
The next level up is to obtain information about the entire source file you are currently working on. To this end, position the cursor at file scope in the current file and look at the what the Code Browser tool view shows:
Here, it shows a list of namespaces, classes and functions declared or defined in the current file, giving you an overview of what's happening in this file and a means to jump directly to any of these declarations or definitions without scrolling up and down in the file or searching for a particular symbol.
| Note |
|---|
| The information shown for file scope is the same as presented in the "Outline" mode discussed below for navigating source code; the difference is that outline mode is only a temporary tooltip. |
There are many ways to obtain information about an entire project (or, in fact, about all projects in a session). This sort of information is typically provided through various tool views. For example, the Classes tool view provides a tree structure of all classes and surrounding namespaces for all projects in a session, together with the member functions and variables of each of these classes:
Hovering over an entry provides again information about the symbol, its location of declaration and definition, and its uses. Double-clicking on an entry in this tree view opens an editor window at the location where the symbol is declared or defined.
But there are other ways of looking at global information. For example, the Documents tool provides a view of a project in terms of the kinds of files or other documents this project is comprised of:
In the previous section, we have discussed exploring source code, i.e. getting information about symbols, files and projects. The next step is then to jump around your source base, i.e. to navigate in it. There are again various levels at which this is possible: local, within a file, and within a project.
| Note |
|---|
| Many of the ways to navigate through code are accessible from the menu in the KDevelop main window. |
KDevelop is much more than an editor, but it is also a source editor. As such, you can of course move the cursor up, down, left or right in a source file. You can also use the PageUp and PageDown keys, and all the other commands you are used from any useful editor.
At the file scope, KDevelop offers many possible ways to navigate through source code. For example:
As mentioned in other places, KDevelop does not usually consider individual source files but rather looks at projects as a whole (or, rather, at all projects that are part of the current session). As a consequence, it offers many possibilities for navigating through entire projects. Some of these are derived from what we have already discussed in the section on Exploring source code while others are genuinely different. The common theme is that these navigation features are based on a semantic understanding of the code, i.e. they offer you something that requires parsing entire projects and connecting data. The following list shows some ways how to navigate through source code that is scattered throughout a potentially very large number of files:
| Note |
|---|
| Jumping to the declaration of a symbol is something that does not only work when placing the cursor on the name of the function you are currently implementing. Rather, it also works for other symbols: Putting the cursor on a (local, global, or member) variable and jumping to its declaration also transports you to its location of declaration. Similarly, you can place the cursor on the name of a class, for example in a variable of function declaration, and jump to the location of its declaration. |
| Note |
|---|
| To see the list of all uses of a name through which these commands cycle, place the cursor onto it and open the Code Browser tool view or press and hold the Alt button. This is explained in more detail in the section on Exploring code. |
Because KDevelop understands your projects' source code, it can assist in writing more code. The following outlines some of the ways in which it does that.
Probably the most useful of all features in writing new code is auto-completion. Consider, for example, the following piece of code:
class Car { // ... public: std::string get_color () const; }; void foo() { Car my_ride; // ...do something with this variable... std::string color = my_ride.ge
In the last line, KDevelop will remember that the variable my_ride is of type Car, and will automatically offer to complete the name of the member function ge as get_color. In fact, all you have to do is to keep typing until the auto-completion feature has reduced the number of matches to one, and then hit the Enter key:
Note that you can click on the tool-tip to get more information about the function apart from its return type and whether it is public:
Auto-completion can save you a lot of typing if your project uses long variable and function names; furthermore, it avoids mis-spelling names (and the resulting compiler errors) and it makes it much simpler to remember the exact names of functions; for example, if all of your getters start with get_, then the auto-completion feature will be able to only present you a list of possible getters when you have typed the first four letters, likely reminding you in the process which of the functions is the correct one. Note that for auto-completion to work, neither the declaration of the Car class nor of the my_ride variable need to be in the same file as where you are currently writing code. KDevelop simply has to know that these classes and variables are connected, i.e. the files in which these connections are made need to be part of the project you are currently working on.
| Note |
|---|
| KDevelop doesn't always know when to assist you in completing code. If the auto-completion tooltip doesn't automatically open, hit Ctrl + Space to open a list of completions manually. In general, in order for auto-completion to work, KDevelop needs to parse your source files. This happens in the background for all files that are part of the projects of the current session after you start KDevelop, as well as while after you stop typing for a fraction of a second (the delay can be configured). |
| Note |
|---|
| KDevelop only parses files that it considers source code, as determined by the MIME-type of the file. This type isn't set before the first time a file is saved; consequently, creating a new file and starting to write code in it will not trigger parsing for auto-completion until after it is saved for the first time. |
| Note |
|---|
| As in the previous note, for auto-completion to work, KDevelop must be able to find declarations in header files. For this, it searches in a number of default paths. If it doesn't automatically find a header file, it will underline the name of a header file in red; in that case, right click on it to tell KDevelop explicitly where to find these files and the information they provide. |
KDevelop has a wizard for adding new classes. To add a new class, select to get the following dialog box:
Here, we have entered the new class's name Bus (you can also enter here which other classes this class should be derived from). The next page of the dialog allows us to select the standard member functions we will need:
Here, we want a default constructor, a copy constructor, and a destructor. After the following pages of the dialog that allow you to select a license header and the location for the new files, KDevelop will generate two new tabs with the header and source files:
The header file already has include guards and the new class has all the member functions we selected. The next two steps would be to document the class and its member functions and to implement them. We will discuss aids for documenting classes and functions below. To implement the special functions already added, simply go to the tab where the skeleton of functions are already provided:
To add new member functions, go back to the tab and add the name of a function. For example, let us add this:
Note how I have already started with the implementation. However, in many coding styles, the function shouldn't be implemented in the header file but rather in the corresponding .cpp file. To this end, locate the cursor on the name of the function and select or hit Ctrl + Alt + S. This remove the code between curly braces from the header file (and replaces it by a semicolon as necessary to terminate the function declaration) and moves it into the source file:
Note how I have just started typing and that I meant to imply that the students variable should probably be a member variable of class Bus but that I haven't yet added it. Note also how KDevelop underlines it to make clear that it doesn't know anything about the variable. But this problem can be solved: Clicking on the variable name yields the following tooltip:
(The same can be achieved by right clicking on it and selecting .) Let me select "3 - private unsigned int" (either by mouse, or by hitting Alt + 3) and then see how it comes out in the header file:
It is worth noting that KDevelop extracts the type of the variable to be declared from the expression used to initialize it. For example, if we had written the addition in the following rather dubious way, it would had suggested to declare the variable as type double:
As a final point: The method using does not always insert the new member function where you may want it. For example, you may want it to be marked as inline and place it at the bottom of the header file. In a case like this, write the declaration and the start writing the definition of the function like this:
KDevelop automatically offers all possible completions of what might come here. Selecting one of the two add_students entries yields the following code that already fills in the complete argument list:
| Note |
|---|
| The fact that the tooltip shows the same function twice is fixed in KDevelop 4.2.2 and later. |
| Note |
|---|
In the example, accepting one of the choices the auto-completion tool offers yields the correct signature but unfortunately deletes the inline marker already written. This has been reported as KDevelop Bug 274245. |
Good code is well documented, both at the level of the implementation of algorithms within in functions as well as at the level of the interface — i.e., classes, (member and global) functions, and (member or global) variables need to be documented to explain their intent, possible values of arguments, pre- and postconditions, etc. As far as documenting the interface is concerned, doxygen has become the de facto standard for formatting comments that can then be extracted and displayed on searchable webpages.
KDevelop supports this style of comments by providing a short cut to generate the framework of comments that document a class or member function. For example, assume you have already written this code:
class Car { public: std::string get_color () const; };
You now want to add documentation to both the class and the member function. To this end, move the cursor onto the first line and select or hit Alt + Shift + D. KDevelop will respond with the following:
The cursor is already in the grayed out area for you to fill in the short description (after the doxygen keyword @brief) of this class. You can then continue to add documentation to this comment that gives a more detailed overview of what the class does:
While the editor is inside the comment, the comment text is highlighted in green (the highlighting disappears once you move the cursor out of the comment). When you get to the end of a line, hit Enter and KDevelop will automatically start a new line that starts with an asterisk and place the cursor one character indented.
Now let's document the member function, again by putting the cursor on the line of the declaration and selecting or hitting Alt + Shift + D:
Again, KDevelop automatically generates the skeleton of a comment, including documentation for the function itself, as well as its return type. In the current case, the name of the function is pretty much self-explanatory, but oftentimes function arguments may not be and should be documented individually. To illustrate this, let's consider a slightly more interesting function and the comment KDevelop automatically generates:
Here, the suggested comment already contains all the Doxygen fields for the individual parameters, for example.
Sometimes, one wants to rename a function, class or variable. For example, let's say we already have this:
We then realize that we're unhappy with the name remove_students and would have rather called it, say, throw_out_students. We could do a search-replace for the name, but this has two drawbacks:
Both these problems can be solved by moving the cursor on any of the occurrences of the name of the function and selecting (or right clicking on the name and selecting ). This brings up a dialog box where you can enter the new name of the function and where you can also see all the places where the function is actually used:
Most projects have pieces of code that one frequently has to write in source code. Examples are: for compiler writers, a loop over all instructions; for user interface writers, checks that user input is valid and if not to open an error box; in the project of the author of these lines, it would be code of the kind
for (typename Triangulation<dim,spacedim>::active_cell_iterator cell = triangulation.begin_active(); cell != triangulation.end(); ++cell) ... do something with the cell ...
Rather than typing this kind of text over and over again (with all the concomitant typos one introduces), the Snippets tool of KDevelop can help here. To this end, open the tool view (see Tools and views if the corresponding button isn't already on the perimeter of your window). Then click on the "Add repository" button (a slight misnomer — it allows you to create a named collection of snippets for source codes of a particular kind, e.g. C++ sources) and create an empty repository. Then click
to add a snippet, to get a dialog like the following:
| Note |
|---|
| The name of a snippet may not have spaces or other special characters because it must look like a normal function or variable name (for reasons that will become clear in the next paragraph). If the name of the snippet does contain spaces, the button will become inactive without any further explanation. This has been reported as KDevelop bug 274299. |
To use a snippet so defined, when you are editing code, you can just type the name of the snippet like you would any other function or variable name. This name will become available for auto-completion — which means that there is no harm in using a long and descriptive name for a snippet such as the one above — and when you accept the suggestion of the auto-completion tooltip (for example by just hitting Enter), the already entered part of the snippets' name will be replaced by the full expansion of the snippet and will be properly indented:
Note that for this to work, the Snippets tool view need not be open or visible: you only ever need the tool view to define new snippets. An alternative, if less convenient, way to expand a snippet is to simply click on it in the respective tool view.
| Note |
|---|
| Snippets are much more powerful than just explained. For a full description of what you can do with them, see the detailed documentation of the Snippets tool. |
If you've gotten this far, take a look at the upper right of the KDevelop main window: As shown in the picture, you will see that there are three modes KDevelop can be in: (the mode we discuss in the current chapter on working with source code), (see Debugging programs) and (see Working with version control systems).
Each mode has its own set of tools that are stacked around the perimeter, and each mode also has a working set of currently open files and documents. Furthermore, each such working set is associated with a current session, i.e. we have the relationship shown above. Note that the files in the working set come from the same session, but they may come from different projects that are part of the same session.
If you open KDevelop the first time, the working set is empty — there are no open files. But as you open files for editing (or debugging, or reviewing in the other modes) your working set grows. The fact that your working set is non-empty is indicated by a symbol in the tab, as shown below. You will notice that whenever you close KDevelop and later start it again, the working set is saved and restored, i.e. you get the same set of open files.
If you hover your mouse over the symbol for the working set, you get a tooltip that shows you which files are currently open in this working set (here: the step-32.cc and step-1.cc files). Clicking on the red minus sign closes the tab for the corresponding file. Maybe more importantly, clicking on the correspondingly named button allows you to close the entire working set at once (i.e. to close all currently open files). The point about closing a working set, however, is that it doesn't just close all files, it actually saves the working set and opens a new, still empty one. You can see this here:
Note the two symbols to the left of the three mode tabs (the heart and the unidentifiable symbol to its left). Each of these two symbols represents a saved working set, in addition to the currently open working set. If you hover your mouse over the heart symbol, you'll get something like this:
It shows you that the corresponding working set contains two files and their corresponding project names: Makefile and changes.h. Clicking will close and save the current working set (which as shown here has the files tria.h and tria.cc open) and instead open the selected working set. You can also permanently delete a working set, which removes it from the set of saved working sets.
KDevelop's editor follows the standard keyboard shortcuts for all usual editing operations. However, it also supports a number of more advanced operations when editing source code, some of which are bound to particular key combinations. The following are frequently particularly helpful:
| Jumping around in code | |
|---|---|
| Ctrl+Alt+O | Quick open file: enter part of a filename and select among all the files in the current session's projects' directory trees that match the string; the file will then be opened |
| Ctrl+Alt+C | Quick open class: enter part of a class name and select among all class names that match; the cursor will then jump to the class declaration |
| Ctrl+Alt+M | Quick open function: enter part of a (member) function name and select among all names that match; note that the list shows both declarations and definitions and the cursor will then jump to the selected item |
| Ctrl+Alt+Q | Universal quick open: type anything (file name, class name, function name) and get a list of anything that matches to select from |
| Ctrl+Alt+N | Outline: Provide a list of all things that are happening in this file, e.g. class declarations and function definitions |
| Ctrl+, | Jump to definition of a function if the cursor is currently on a function declaration |
| Ctrl+. | Jump to declaration of a function or variable if the cursor is currently in a function definition |
| Ctrl+Alt+PageDown | Jump to next function |
| Ctrl+Alt+PageUp | Jump to previous function |
| Ctrl+G | Goto line |
| Searching and replacing | |
| Ctrl+F | Find |
| F3 | Find next |
| Ctrl+R | Replace |
| Ctrl+Alt+F | Find-Replace in multiple files |
| Other things | |
| Ctrl+_ | Collapse one level: remove this block from view, for example if you want to focus on the bigger picture within a function |
| Ctrl++ | Expand one level: undo the collapsing |
| Ctrl+D | Comment out selected text or current line |
| Ctrl+Shift+D | Comment in selected text or current line |
| Alt+Shift+D | Document the current function. If the cursor is on a function or class declaration then hitting this key will create a doxygen-style comment pre-populated with a listing of all parameters, return values, etc. |
| Ctrl+T | Transpose the current and the previous character |
| Ctrl+K | Delete the current line (note: this is not just emacs' "delete from here to the end of the line") |