Learning CMake - Part 1 - The Basics

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
welcome developers i'm currently in the early stages of developing my next indie game the colon case in good old c plus so far this game makes use of two third-party libraries the first is sfml a cross-platform multimedia library that i'm using to assist with graphics and sound the second is json cpp which i'm using to load and parse json files for my game's data as my c plus project gets larger and with the desire to port it to multiple platforms it's becoming more of a priority for me to invest some time into learning about c plus build systems this is where cmake comes in cmake seems to be the most actively supported software used to help automate the build process for c plus programmers in this series i'll be stepping through the process of converting my existing code base from a visual studio solution to a cmake configuration script i have several specific goals in mind first is to make it easier to be able to port the project from windows to other operating systems or even from visual studio to other development environments the second is to make it easier to bring in third-party dependencies such as the aforementioned sfml and json cpp in the future i may be looking to integrate my games with the likes of steam discord or twitch or i may want to tap into ffmpeg or another library to play video cut scenes each new library added to a project introduces its own challenges which i'm hoping cmake will help to mitigate in this video i'm going to work through some of the basics on how to use cmake and some of its basic features these are the steps i'll be going through you can use the time index in the description to skip around i use visual studio community 2019 edition and i keep it up to date with the latest version you could download and install cmake separately but if you go to tools then get tools and features you'll find a cmake tools for windows option normally applications or libraries you create in visual studio have their own proprietary project format an sln file is a visual studio solution which is kind of a container for a related projects and a vcx proj file is a visual studio project but with the cmake tools installed a visual studio provides direct support for creating and building projects based on cmake scripts instead when creating a new project you can choose the cmake project template this will produce a shell project that includes a starter cmake lists text file this contains the script cmake will use to generate your build files i'm actually going to scrub the shell project that visual studio created as i think it might be instructive to start from scratch instead i've created a git repository called cmake testing grounds this is a public repo that you can find on my github account i found the official cmake tutorial to be quite good but i'll be doing things here just a little bit differently or out of order first i'll be creating an empty folder in my repo learning cmake and a part 1 folder inside that and we'll open that folder in visual studio and now i'll create a cmake list's text file this must be named exactly like this case sensitive visual studio brings up a cmake overview page which i'm going to ignore for the purpose of this video before setting up the cmake list file i'll create a main cpp program that will just print a basic greeting hello cmake now in c make lists we'll have three statements c make minimum required indicates the minimum version of c make for our project this can be the latest version or an earlier version if you have a specific reason to make your project backwards compatible project is used to give your project a name and version and add executable defines your target executable file name and the list of source files note that when you save the cmakelist's text file visual studio creates a folder named out with a subfolder named build this is where all of the build files will be produced by cmake the compiler and the linker from here you can right-click on the cmakelist's text file and tell it to build or tell it to run the debug configuration where we see the results of the program i'm also going to add two set statements to specify the c plus plus language standard if you're as old as i am you might have been surprised to discover that c plus has been going through a three-year improvement cycle since 2011. for this example i'll set the standard to version 11 and make this version of the c plus plus compiler required for my game the colon case i've updated the standard to 17 as i wanted to use the new cross platform file system features on a day-to-day basis i'll be continuing to build and debug my applications from inside visual studio when i reach certain milestones however i also want to be able to build from the command line this will give me the flexibility to work within any development environment and using any c plus compiler under tools then command line you can find the developer command prompt this opens a windows command prompt with the initial directory being the root folder of our project we can run cmake-version to verify that cmake exists if we run cmake-help and pipe it to more we see the various options we can pass in at the bottom of the help information we see the list of generators that are available visual studio 2019 is the default targeting a 64-bit windows environment i'll create a separate build folder to keep the build artifacts from the command line separate from those generated from within visual studio i'm also going to create a win64 folder under that representing the default architecture from this folder we'll run cmake-s indicate the source's two directories back and dash b with a dot to indicate that the current folder is where we want the build artifacts cmake does its thing to create the visual studio solution and project files i refer to this as the generator step as it doesn't actually invoke the compiler or linker yet but instead generates the project files we can now run cmake dash dash build dot to invoke the visual studio c plus compiler in linker to produce a debug executable if we hop into the debug folder for a moment we can run our program if we wanted to produce a release executable we can instead run cmake dash dash build dot dash dash config release and here's the much smaller executable with no debug information let's say we had a reason to want to support 32-bit windows environments we can go back to the build folder and create a separate win32 folder from here we can run cmake-a win32 dash s two folders back for the source dash b dot this creates a visual studio solution in project files that will target 32-bit windows instead as before we can now build the debug executable [Music] and the release executable i also have the mingw compiler installed which uses the more standardized makefiles as its build script i'll create a separate mingw folder from here we can run cmake g mingw make files dash s two folders back for the source dash b dot and we see here the make file running cmake dash dash build dot creates an executable by invoking g plus plus instead in the solution explorer view you'll notice that we have tons of files in the build folder there are also files in the out folder but visual studio hides those because it knows they aren't part of your source code switching to the get changes view you can now see all of them along with a dot vs folder which stores workspace settings we're going to want a git ignore file so that we only commit our source code doing a google search for visual studio git ignore we can find a suggested git ignore file as we can see it's quite the beefy file because we're separating our build results into a specific folder the get ignore file we'll need will be much simpler i'll go ahead and create the dot get ignore file and just add three lines the dot vs folder the out folder and the build folder now when we switch back to the git changes view we only see our git ignore file in the project source i'll go ahead and commit these files and push to the origin you can find the cmake testing grounds repository on my github account if you're involved in game development it's almost certain you'll have a collection of resource files such as images or sounds that you'll need to include in your release i'm going to create a resources folder and add a mock resource file here called greeting.txt hello cmake from our resource file now we can update our main function to read the greeting from our resource file instead we'll need the f stream and string headers to get access to file streams and strings we can open the file using a relative path we'll use the getline function to read the first line into a string and send that to the output or if the file was not opened we'll output an error message if we try running our program now it will output the error because it can't find the resource file we need to tell cmake to copy the resources folder to the target directory cmake provides a set of built-in command line tools as shown here with the dash e option in the cmake documentation you can see the full list of available commands by running cmake dash e you can also run these tools from within the cmake list script using the add custom command statement it must be placed after the add executable statement because we'll be referencing the learn cmake part 1 target that it defines the post build identifier tells cmake to run this command after the executable has been built the dollar cmake command variable is just indicating that it's running one of the built-in cmake commands you could also run a custom command here such as a custom build tool the command we want is named copy directory we'll take the contents of the resources folder from the root source directory and copy it into the resources folder of the target the dollar with less than and greater than delimiters is called a generator expression the target file dir identifier is considered a target dependent query now when we run our program we successfully see the greeting from our resource file the cmake tutorial includes a section where a header file is configured with the project's version information defined in the cmake lists file i'm not sure how i feel about the practice of configuring source files my personal preference would be to configure a resource file that the application loads in i'm going to create a configure folder and add a file named about.txt here this will contain two lines the first line will identify the version and the second line will identify the build time the at symbols are used to delimit variables that will be replaced during the generator step when running the cmake next we can update the main function to accept a v option to print version information this code will check if the first argument is dash v if so it will read the about.txt file line by line pulling out the version and build values into strings and then sending this information to the standard output if the user was requesting version information we won't print the greeting and finally we can update the cmakelist's text file to determine the bill date and time and to make sure the about.txt file gets copied to the target resources folder the string statement can be used to build a timestamp i split this into two variables named bill date and build time the configure file statement will take the given source file and copy it into the given location in the target it will also replace all of the variables with the corresponding values if we build and run the program at this point we get our usual greeting to see the dash v option we'll have to open up a command prompt we navigate to the output folder and run the program to check its version if we tell visual studio to build again you might be expecting the build time to get updated it does not cmake actually caches all of the information during the generator step only refreshing it if the cmakelist's text file changes you can force cmake to regenerate its cache by right clicking on the cmake lists file and choosing generate cache when running with the dash v option again we now see the build time update i'm actually going to update the project version to 1.1 at this point note that because this involves saving a change to cmake lists simply building will update the output when we run with the dash v option again i came across an interesting alternative for the build date over on stack overflow user d burnett suggests using cmake to create a separate cmake script file adding a custom target to run that script and then adding the custom target as a dependency of the executable target doing it this way bypasses the c make cash as this is my first rodeo with cmake i'm not quite as clear why the extra effort is really worth it i feel like any time i plan on putting out an actual release i'd be performing a clean build from the command line the cache won't come into play at that point i'm a big believer in writing automated tests even for projects with a single developer cmake comes with automated testing support with its companion c test tool the enable testing statement in your cmake lists file is required the add test statement will add a test to be run each test must be given a name which identifies it in the output as well as a command to run which will typically be a target previously identified by an add executable statement without additional information about each test c-test assumes that simply running with a return value of zero passes the test the set test's properties statement can be used to provide further requirements for the test to pass for my example i'll add a test named greeting test that runs our learn cmake part 1 executable this will pass if the output is exactly hello cmake from our resource file i'll also add a test named version test that runs with the dash v option this will pass if the output starts with the text version followed by our project's major and minor version numbers separated by a dot in visual studio you can right-click on the cmakelists.txt file and choose run tests on the command line you can navigate to your build folder and simply run c test running c test dash n gives a list of tests without actually running them while c test vv provides verbose test output for my upcoming game the colon case i've been writing automated tests in separate projects currently my tests are written as c plus functions that return true if the test passes the main function for these test projects runs each test wrapped in an assert macro call now that i'm learning cmake it appears that i'll have to refactor this approach i'm either going to have to write each test as its own executable or come up with a way of bootstrapping each test into a single executable that accepts a test name as an input parameter i'd be very curious to see how others are organizing their test projects github provides a feature called github actions which can be used to automatically build and test your projects on your repository page you'll find a tab labeled actions if you don't have any actions set up yet you'll see a page like this with some suggested workflows if you have a cmakelist.txt file you should see the cmake-based projects workflow as a suggestion initiating this will start you off with a template cmake yaml file in a special folder named dot github workflows i'm going to keep the file as is for the moment but place it on a branch until the workflow actually passes based on the contents of the script it's likely i'll have to update it to point at the correct folder i was under the impression i'd need to add extra steps to build and test but i later discovered that the scroll bars in the editor weren't showing me the entire file for some reason after a few failed attempts i finally fixed up all the places i needed to edit to pass the configure step however i came across a compilation error related to the stir comp function since the github action is running by default in ubuntu using regular makefiles this exposes a difference between it and the visual studio environment i needed to add the c-string header to ensure cross-platform compatibility once that was fixed i finally got my first successful build it should be noted that you can modify the environment for your workflows or even include multiple environments on the github hosted runners help page you can find the list of available environments and supported software github also provides a status badge feature for your workflows you can add this to your repositories readme file and there it is telling us that our little greeting example is passing hooray and that's it for part one of my cmake guide next up i'll be looking at converting some of the existing code base for the colon case to build using cmake this will involve organizing source code into subfolders building static libraries and managing dependencies stay tuned to riley entertainment games for more game development guides or head on over to my main riley entertainment channel for regular gaming content
Info
Channel: Riley Entertainment Games
Views: 14,937
Rating: undefined out of 5
Keywords: cmake tutorial, github actions, learning cmake, ctest tutorial
Id: lZ4VytXLNSo
Channel Id: undefined
Length: 19min 7sec (1147 seconds)
Published: Wed Mar 24 2021
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.