Compiling SFML with CMake
Introduction
Well, ok, the title of this tutorial is not completely right. You will not compile SFML with CMake, because CMake is not a compiler. So... what is CMake?
CMake is an open-source meta build system. Instead of building SFML, it builds what builds SFML: Visual studio solutions, Code::Blocks workspaces, Linux makefiles, XCode projects, ... in fact it can generate the makefiles or projects for the OS and compiler of your choice. It is similar to autoconf/automake or premake -- for those who are already familiar with these tools.
CMake is widely used, by well-known projects such as Blender, Boost, KDE, or Ogre. You can read more about CMake on its official website or on the wikipedia page.
So, as you've probably understood, this tutorial is made of two main sections: generating the build files with CMake, and then building SFML with your preferred compiler.
Installing dependencies
SFML depends on a few other libraries, so before starting to compile you must have their development files installed.
On Windows and Mac OS X, all the needed dependencies are provided directly with SFML, so you don't have to download/install anything. Compilation will work out of the box.
On Linux however, nothing is provided and SFML relies on your own installation of the libraries it depends on. Here is a list of what you need to install before compiling SFML:
- pthread
- opengl
- xlib
- xrandr
- freetype
- glew
- jpeg
- sndfile
- openal
The exact name of the packages depend on each distribution. And don't forget to install the development version of these packages.
Configuring your SFML build
This step consists of creating the projects/makefiles that will finally compile SFML. Basically it consists of choosing what to build, how to build it and where. Plus a few other options so that you can create the perfect build that suits your needs -- we'll see that in detail later.
The first thing to choose is where the projects/makefiles and object files (files resulting from the compilation process) will be created. You can generate them directly in the source tree (ie. the SFML root directory), but it will then be polluted with a lot of garbage: a complete hierarchy of build files, object files, etc. The cleanest solution is to generate them in a completely separate folder so that you can keep your SFML directory clean. Using separate folders will also make it easier to have multiple different builds (static, dynamic, debug, release, ...).
Now that you've chosen the build directory, there's one more thing to do before you can run CMake. When CMake configures your project, it tests the availability of the compiler (and checks its version as well). As a consequence, the compiler executable must be available when CMake is run. This is not a problem for Linux and Mac OS X users, since the compilers are installed in a standard path and are always globally available, but on Windows you may have to add the directory of your compiler in the PATH environment variable, so that CMake can find it automatically. This is especially important when you have several compilers installed, or multiple versions of the same compiler.
On Windows, if you want to use gcc (MinGW), you can temporarily add the MinGW\bin directory to the PATH and then run cmake from the command shell:
> set PATH=%PATH%;your_mingw_folder\bin
> cmake
With Visual C++, you can either run CMake from the "Visual Studio command prompt" available from the start menu, or call the vcvars32.bat file of your Visual Studio installation; it will setup the environment variables properly.
> your_visual_studio_folder\VC\bin\vcvars32.bat
> cmake
Now you are ready to run CMake. In fact there are three different ways to run it:
- cmake-gui
This is a graphical interface that allows you to configure everything with buttons and text fields; this is probably the easiest solution for beginners and people who don't want to deal with the command line; it's also very convenient to see and edit the build options. - cmake -i
This is the command line interactive invocation, you will be prompted to fill every build option explicitly; this is a good option to start with the command line, since you probably don't remember all the options that are available, and don't know which ones are relevant. - cmake
This is the direct invocation, you must put all the options and their values directly.
In this tutorial I will focus on cmake-gui, as this is most likely what beginners will use. I assume that people who use the command line can learn the syntax from the CMake manual. Except the screenshots and the "click there" stuff, all the explanations below still applies (options are the same).
Here is what cmake-gui looks like:
Here are the first steps to perform:
- Tell CMake where the source code of SFML is (this must be the root folder of the SFML hierarchy, where the first CMakeLists.txt file is).
- Choose where you want the projects/makefiles to be generated (if the directory doesn't exist, CMake will create it).
- Click the "Configure" button
If this is the first time that you run CMake in this directory (or if you cleared the cache), cmake-gui will ask you to choose the generator. In other words, this is where you select your compiler/IDE.
For example, to generate a Visual Studio 10 solution, you must choose "Visual Studio 10".
To generate makefiles usable with Visual C++, select "NMake makefiles". To create makefiles usable with MinGW (gcc), select "MinGW makefiles". It
is generally easier to generate makefiles rather than IDE projects: you can then compile with a single command, or even gather multiple
compilations in a single script. Since you will only compile, not edit source files, IDE projects are generally useless.
Moreover, the installation process (described later in this document) may not work with the "Xcode" generator; therefore it is higthly
recommended to use the "Makefile" generator on Mac OS X.
Always keep the "Use default native compilers" option, you don't need to care about the three others.
After selecting the generator, CMake will run a lot of tests to check various things of your compilation environment: compiler path, standard headers, SFML dependencies, etc. If everything is ok, it should finish with the "Configuring done" message. If something goes wrong, read the error(s) carefully. Maybe your compiler is not accessible (see above), or one external dependency is missing.
After configuring is done, a lot of options appear in the central part of the window. CMake has many options, but most of them have the
right default value. Many of them are not even meant to be changed, they are just there to show you what CMake automatically found.
Here are the few relevant options that you may have to care about when configuring your SFML build:
| Variable | Meaning |
|---|---|
CMAKE_BUILD_TYPE |
This option selects the build type. Relevant values are "Debug" and "Release" (there are other types such as "RelWithDebInfo" or "MinSizeRel", but they are not really configured in the SFML makefiles). Note that if you generate a workspace for an IDE that supports multiple configurations, such as Visual Studio, this option is ignored and you automatically get all the available build types in it. |
CMAKE_INSTALL_PREFIX |
This is the install path. By default, it is defined to the most natural path according to the OS ("/usr/local" for Linux and Mac OS X, "C:\Program Files" for Windows, etc.). Installing files after compiling is not mandatory, you can use the binaries directly from where they are compiled, but it may be a better solution to install them properly so that you don't have all the garbage files produced by the compilation. |
CMAKE_INSTALL_FRAMEWORK_PREFIX |
This is the install path for frameworks. By default, it is defined to the root library,
i.e. /Library/Frameworks folder. As stated for CMAKE_INSTALL_PREFIX it is not mandatory to install files
after compiling, but it is cleaner to install them. This path is used to install on your system sndfile.framework (a required dependency not provided by Apple) and SFML as frameworks if BUILD_FRAMEWORKS is selected. |
BUILD_SHARED_LIBS |
This boolean option controls whether you build the dynamic (shared) libraries of SFML, or the static ones. This option is not compatible with SFML_USE_STATIC_STD_LIBS, they are mutually exclusive. |
SFML_BUILD_FRAMEWORKS |
This boolean option controls whether you build SFML as
framework bundles
or as
dylib binaries.
Building frameworks requires BUILD_SHARED_LIBS to be selected. It is recommended to use SFML as frameworks when releasing your applications to the public. However, SFML cannot be built in debug as frameworks; use instead dylibs. |
SFML_BUILD_EXAMPLES |
This boolean option controls whether you build the SFML examples or not. |
SFML_BUILD_DOC |
This boolean option controls whether you generate the SFML documentation or not. Note that the
doxygen tool must be installed and accessible, otherwise
enabling this option will produce an error. On Mac OS X you can either install the classic-Unix doxygen binary into /usr/bin or any similar directory, or install Doxygen.app into any "Applications" folder, e.g. ~/Applications. |
SFML_USE_STATIC_STD_LIBS |
This boolean option selects the version of the standard C/C++ library which is linked to SFML. TRUE statically links the standard libraries, which means that SFML is self-contained and doesn't depend on the compiler's specific DLLs. FALSE (the default) dynamically links the standard libraries, which means that SFML depends on the compiler's DLLs (msvcrxx.dll/msvcpxx.dll for Visual C++, libgcc_s_xxx-1.dll/libstdc++-6.dll for gcc). Be careful, this setting must match your own projects settings, otherwise you may experience crashes. This option is not compatible with BUILD_SHARED_LIBS, they are mutually exclusive. |
CMAKE_OSX_ARCHITECTURES |
This setting specifies for which architectures SFML should be compiled. The recommended value is "i386;x86_64" to generate universal binaries for both 32 and 64 bits systems. |
SFML_INSTALL_XCODE4_TEMPLATES |
This boolean option controls whether cmake will install the Xcode 4 templates on your system or not. More information about these templates is given in the "Getting started" tutorial for Mac OS X. |
SFML_INSTALL_PKGCONFIG_FILES |
This boolean option controls whether cmake will install the pkg-config files on your system or not. pkg-config is a tool that provides a unified interface for querying installed libraries. |
After everything is configured, click the "Configure" button once again: the options background should become white, and the "Generate" button should become available. Click it to finally create the chosen makefiles/projects.
CMake creates a cache for every project. Therefore, if you decide to come back later, you'll find your options back and you'll be able to change them, then reconfigure and generate the updated makefiles/projects.
C++11 and Mac OS X
If you want to use C++11 features in your application on Mac OS X, you have to use clang (Apple's official compiler) and libc++. Moreover, you also need to build SFML with these tools to workaround any incompatibility between standard libraries and compilers.
Here are the settings to use to build SFML with clang and libc++:
- Choose "Specify native compilers" rather than "Use default native compilers" when you select the generator
CMAKE_CXX_COMPILERset to /usr/bin/clang++ (see screenshot)CMAKE_C_COMPILERset to /usr/bin/clang (see screenshot)CMAKE_CXX_FLAGSandCMAKE_C_FLAGSset to "-stdlib=libc++"
Building SFML
Let's start this new section with good news: you won't have to go through the configure step anymore, even if you update your working copy of SFML. CMake is smart, it adds a custom step to the generated makefiles/projects, that automatically regenerates the build files whenever something changes.
You're now ready to compile SFML. Of course, how to do it depends on what makefiles/projects you've generated. If you created a project/solution/workspace, open it with your IDE and compile like any other project. I won't show you the details here, there are too many different IDEs and I assume that you know yours enough to do this simple task.
If you generated a makefile, open a command shell and execute the make command corresponding to your environment. For example, run "nmake" if
you generated a NMake (Visual C++) makefile, "mingw32-make" if you generated a MinGW (gcc) makefile, or simply "make" if you generated a Linux
makefile.
Note: on Windows, the make program (nmake or mingw32-make) may not be accessible. If it's the case, don't forget to add it to your PATH
environment variable; see the explanations at the beginning of the "Configuring your SFML build" section for more details.
By default, everything will be compiled (all the SFML libraries, as well as all the examples if you enabled the SFML_BUILD_EXAMPLES option).
If you want to compile only a single SFML library or example, you can select a different target. You can also choose to clean or install the compiled
files, with the corresponding targets.
Here are all the targets that are available, depending on the configure options that you chose:
| Target | Meaning |
|---|---|
all |
This is the default target, it is used if no target is explicitly specified. It builds all the targets that produce a binary (sfml libraries and examples). |
sfml‑system |
Builds the corresponding SFML library. The "sfml-main" target is available only on Windows systems. |
cocoa |
Builds the corresponding SFML example. These targets are available only if the SFML_BUILD_EXAMPLES option is enabled. Note that some of the
targets are available only on a certain OS ("cocoa" is available on Mac OS X, "win32" on Windows, "X11" on Linux, etc.).
|
doc |
Generates the API documentation. This target is available only if the SFML_BUILD_DOC option is enabled.
|
clean |
Removes all the object files produced by a previous compilation. You generally don't need to invoke this target, except when you want to recompile SFML completely (some updates may mess up with object files already compiled, and cleaning everything is the only solution). |
install |
Installs SFML to the path defined in the CMAKE_INSTALL_PREFIX and CMAKE_INSTALL_FRAMEWORK_PREFIX options. It copies the
SFML libraries and headers, as well as examples and documentation if the SFML_BUILD_EXAMPLES and SFML_BUILD_DOC options are enabled.
After installing, you get a clean distribution of SFML, just as if you had downloaded the SDK or installed it from the system repositories.
|
If you use an IDE, a target is simply a project. To build a target, select the corresponding project and compile it (even "clean" or
"install" must be compiled to be executed -- don't be confused by the fact that no source code is actually compiled).
If you use a makefile, pass the name of the target to the make command to build this target. Examples: "nmake doc", "mingw32-make install",
"make sfml-network".
Now you should have successfully compiled SFML. Congratulations!
