A Simple VSCode Setup for C++ Developers
As a software developer, I’ve tried different integrated development environment (IDE) and text editors for code development (vim, Emacs, Sublime Text, etc). Out of the ones I’ve tried, Microsoft Visual Studio Code (VSCode) stands out among the rest as a flexible and lightweight editor. What’s great about VSCode is its extensibility with various plug-ins from the Extension Marketplace. Did I also mention that it’s free AND is updated every month!?
As a developer whose primary coding language is C++ I find VSCode provides all the tools, e.g. gdb debugger, and features, e.g. IntelliSense, that ease the development process. However, when I first started using the editor, online search turns up articles that focuses more on what extensions to use, which for a beginner, blindly installing them can quickly bloat up the editor and makes it difficult to configure the extensions to be useful.
In this article, I’m going to focus on 4 topics to help the uninitiated set up their VSCode environment for coding in C++:
- Set up VSCode workspace
- Set up debugger settings
- Set up build instructions
- Essential extensions for code development
Set Up VSCode Workspace
VSCode uses the workspace concept to apply custom settings and allow the user to specify commands that only apply to the codes in that workspace. The codes DO NOT have to be physically in the same folder!
A workspace and its settings are represented by a .code-workspace
file in the directory. When you add this folder into the workspace (right-click on the Explorer window and select Add folder to Workspace), VSCode will search for the file and establish the workspace.
In the above screenshot, I placed my .code-workspace
in the Coding_Workspace
folder which contains several git repos. These subfolders are also added into the workspace using Add folder to Workspace to create a multi-root workspace. This is extremely useful when you are working on multiple repos and want to specify commands for specific repos. This will be more apparent when I explain how to setup build instructions.
If you are starting from scratch, simply open a new VSCode window. Select Add workspace folder on the Welcome screen. Choose a folder you want to make as your workspace. Select File > Save Workspace As and the .code-workspace
file will be automatically created with minimum settings filled out. When you add other folders into the workspace, this file will be automatically updated by VSCode with the name of the folder so it can be used to create specific instructions for files in that folder only.
Another thing VSCode will do when you first create a workspace is creating a .vscode
folder. This folder is where local settings and instructions are stored.
Two files you should pay special attention to are tasks.json
and launch.json
. The first specifies build instructions. The second specifies settings for the debug environment.
Set Up Build Instructions
VSCode supports custom tasks that simplify your development process and reduce typing and memorization. These tasks can also be chained together to form more complex build or run tasks.
All of the custom tasks are stored in tasks.json
in .vscode
sub-folder. Each can be specified in a comma separated list surrounded by braces {}
as shown in the figure below.
Single Task
Each tasks have properties for the user to define. Here we only focus on what I think are essential. For a comprehensive list, refer to the link in the footnote¹.
label
: This is a string to help you identify what this task will do. It is also use as the name in the drop down menu when choosing Tasks: Run Task in the Command Palette (Ctrl+Shift+P
).type
: The type of command that is being executed. Supportsshell
orprocess
.command
: The command that you want VSCode to execute.args
: Array of comma separated arguments you want to pass to the command. For example,-DCMAKE_BUILD_TYPE=Debug
to tell CMake to generate makefile with debug flags.group
: The group you want VSCode to organize this task in. Supportsbuild
,test
, andnone
.
group
also supports making the task a default when using the keyboard shortcut Ctrl+Shift+B
. To do this, instead of specifying one of the 3 options above, in braces {}
specify the following properties:
kind
:build
,test
,none
.isDefault
:true
,false
.
If all of your tasks has the property isDefault
set to true then the shortcut will open a drop-down menu for you to choose which to execute.
NOTE: There is another property presentation
that allows you to manipulate the output of the tasks. By default, it is set to always start a new terminal and print to it (for more information refer to the footnote¹).
You can see in the figure above that I use {workspaceFolder:pcl}
in args
and cwd
. Remember when I talked about the multi-root workspace? This allows me to execute the CMake command in the pcl
folder itself and not having to worry about relative or absolute paths. VSCode automatically expands the expression; in my case, ~/Code_Workspace/pcl/
.
In addition to workspaceFolder
VSCode predefines other variables that can be used to generalize settings that require paths. Please see the footnote⁴ for more details.
Chaining Tasks
Another powerful feature of specifying your tasks in tasks.json
is it allows you to chain the single tasks together. To do this simply create a new task with the following properties:
label
: Specify a unique name for the taskdependsOn
: Array of comma-separated labels of the single taskdependsOrder
: Specify the order in which the task will be executed. The current task will be executed last and each task must return before the next executes. Supportssequence
.
This feature is useful for chaining build tasks together or build and run unit tests combo.
Set Up Debugger Settings
In my opinion this is a powerful feature that makes VSCode standout among other text editors. Similar to tasks, users can setup their debug environment in launch.json
in a comma-separated list as seen in the screenshot below.
Each debug session supports many properties. The list below is not comprehensive and focuses on ones that I think are essential. For the full list, please refer to the footnotes² ³.
name
: Unique name that differentiate the debug tasks from one another.type
: The type of debugger to use. If you installed the C/C++ extension thencppdbg
is available. A few others shipped with the editor arenode
,php
,go
for other programming languages.request
:launch
a new process orattach
to a running process. Ifattach
is chosen, the debug window will show a drop-down menu of running process with IDs to choose from.program
: path to the executable you want to debug.args
: comma-separated list of arguments to pass to the executable.stopAtEntry
: true or false whether the debugger will break at the entry of the code.cwd
: the working directory to find dependencies. Setting to${workspaceFolder}
is the standard.externalConsole
: true or false whether to launch the debug terminal in an external console.MIMode
: This is specific to C/C++ extension and is required. Supportsgdb
orlldb
.setupCommands
: This is specific to C/C++ extension and is option. The setting in the figure above suffices.preLaunchTask
: A comma-separated list of task names fromtasks.json
to run before launching the debugger. For example, building the code in debug mode before debugging.postDebugTask
: A comma-separated list of task names fromtasks.json
to run after the debug session. Can be used to clean up temporary files.
You may notice from the screenshot that I’ve again use ${workspaceFolder:pcl}
for cwd
and program
. This tells VSCode that I want the debugger, in this case gdb,
to latch on to an executable test
in the pcl
folder in my workspace and make the that folder the root directory when running the debugger.
Note: If you find the list of properties to set daunting, no worries, VSCode will show available options when you press “
when editing the .json
files!
Essential Extensions For Code Development
And finally, the following is a list of extensions I found useful and think are essential for C++ developers:
- C/C++
- Clang-Format
- CMake
- Docker
- GitLens
- Git History
- Git Extension Pack
- Github Pull Requests and Issues
- vscode-icons
Note: If you are working with ROS and your primary OS is Linux. I recommend also downloading the ROS extension.
The list is not extensive and may not include other extensions that other developers may find helpful. I recommend sticking with those listed above for a few weeks before browsing through the marketplace (you can definitely get loss in that place!).
Each of these extension provide commands that can be accessed through the Command Palette. You can start typing what you want to achieve and VSCode will slowly narrow down the options. Not only that, the displayed commands are sorted by recently used.
For extensions dealing with code repositories like Git, they allow the user to choose the repository the selected command should apply to.
Some other extensions, like C/C++, do not add executable commands but rather optional settings that can enhance the editor even more. For example, C/C++ syntax highlighting.
Summary
In this article, I have shown how to set up VSCode workspace and settings to aid in C++ development. This is what I’ve found working for me and have been helping me immensely in my coding journey and I hope it can do the same for you.
For ROS developers, I recommend reading the following articles on how to set up VSCode to integrate ROS workflow into your development and testing:
Happy coding!