Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: Help understanding the tutorials?  (Read 6013 times)

0 Members and 1 Guest are viewing this topic.

man with shell

  • Newbie
  • *
  • Posts: 2
    • View Profile
Help understanding the tutorials?
« on: March 14, 2012, 05:34:55 am »
The tutorials are extremely unhelpful and unclear. Is it possible someone could write a coherent expanation of how to install SFML for use with Code::Blocks?

For an example of the uselessness of the tutorial, note this line:

"If you linked against the dynamic versions of the SFML libraries, donc forget to copy the corresponding DLLs (sfml-system.dll in this case) to your executable's directory, or to a directory contained in the PATH environment variable."

My executable's directory? I haven't made an executable yet; first I have to have code that compiles, THEN I have an executable. And what is this "PATH environment variable"?

Tutorials are supposed to be written for people who don't already know these things.

At present, I believe I have followed the tutorial as well as I can. I have added the "lib" and "include" directories under the "Search Directories" tab, and I have added the item "-lsfml-system-s" to the "Other linker options" list in the "Project build options" window. I used "-s" because I did not understand the instructions for using the dynamic libraries.

The code of my project in its entirety:

Code: [Select]
#include <SFML/System.hpp>
#include <iostream>

int main()
{
    sf::Clock Clock;
    while (Clock.GetElapsedTime() < 5.f)
    {
        std::cout << Clock.GetElapsedTime() << std::endl;
        sf::Sleep(0.5f);
    }

    return 0;
}



The errors:
Quote
undefined reference to `sf::Clock::GetElapsedTime() const
undefined reference to `sf::Sleep(float)
undefined reference to `sf::Clock::GetElapsedTime() const
undefined reference to `sf::Clock::Clock()


Please help?

Laurent

  • Administrator
  • Hero Member
  • *****
  • Posts: 32498
    • View Profile
    • SFML's website
    • Email
Help understanding the tutorials?
« Reply #1 on: March 14, 2012, 08:19:10 am »
Quote
My executable's directory? I haven't made an executable yet; first I have to have code that compiles

The code is given above. Then you have the compiler and linker flags. And finally, after I said "your code should now compile fine", I tell you to copy the DLLs. So what's wrong?

Quote
And what is this "PATH environment variable"?

Google it. Unless you think that it is unhelpful and stupid as well.

Quote
Tutorials are supposed to be written for people who don't already know these things.

Tutorials are supposed to teach how to use SFML. They won't teach you how to use computers. If you want to program without knowing how to use Windows, man you're doing it wrong.

Quote
I used "-s" because I did not understand the instructions for using the dynamic libraries.

There's a screenshot, I don't know how to make it clearer.

Quote
The errors:
undefined reference to `sf::Clock::GetElapsedTime() const
undefined reference to `sf::Sleep(float)
undefined reference to `sf::Clock::GetElapsedTime() const
undefined reference to `sf::Clock::Clock()

Can you show us your code::blocks project file?

PS: sorry for being rude, but it was really not the right day for posting such a message...
Laurent Gomila - SFML developer

Bigz

  • Full Member
  • ***
  • Posts: 154
    • View Profile
    • Bigz.fr
Help understanding the tutorials?
« Reply #2 on: March 14, 2012, 10:11:20 am »
One of the most valuable quality of a developer is humility, which you definitly don't have. Before criticize a tutorial (which is really helpful and clear in my opinion), try to get some help in a polite way if you have a lack of knowledge about fundamental things. Hopefully, Laurent is really nice and will always help a user who needs it.

Anyway, it seems that you are using the SFML 1.6 with the libs given with it. So you probably missed something with the linking of those libs. Or you are compiling your project with another compiler than gcc4.4.x (which is the version used to compile the SFML 1.6 libs)

VPellen

  • Newbie
  • *
  • Posts: 14
    • View Profile
Help understanding the tutorials?
« Reply #3 on: March 14, 2012, 12:36:26 pm »
Your problem is not really with SFML, in this case, your problem is that you don't seem to have a solid grasp of the compilation and linking process, so you don't know how to set things up.

This isn't really your fault. Compilation and linking is something I've never in my life seen a really good explanation of, and I think it's something that we don't learn early enough. So I'll attempt to do so here. I'll also try and explain the bugs you're encountering.

Enjoy.

----------------------------------------------------

Let's start abstract. What is a computer program?

A computer program is a file like any other. It's a string of data. Fundamentally, all computer files are exactly the same - There's no real difference between a text file and a music file and an executable file. Zeroes and ones are zeroes and ones. The distinction is in how that data is interpreted. Computer programs are strings of data designed to be interpreted as machine instructions. Data commands. Really raw instructions that your computer can follow. But it's not the code you write. The code you write is far, far different. If you've ever tried to open an executable in a text editor, this is something you can probably understand.

So, question. How does C++ code get converted into that raw binary machine code? How does hello_world.cpp become hello_world.exe?

The most common answer is "A program called a compiler turns your code into an executable". It's also, sadly, a misleading answer. It's not really a lie, it just leaves out a lot of important details. In some languages, you don't need to really know the details. C++, you do need to know the details.

First, I want to draw a distinction between an IDE and a Compiler Suite. An IDE is something like Code Blocks; Effectively little more than a glorified text editor. It has useful features like code highlighting and project management and all that jazz, but it doesn't make programs.

A Compiler Suite is something different. The keyword there is suite. Most people understand a compiler to be a single indivisible entity: A sort of black box where you put code in one end and executables pop out the other end. This is not how it actually works. Turning your source into a working binary is a multi-step process. The "correct" term for this is called the Build Process.

I'll try and break down the Build Process into its relevant steps.

The first step is called preprocessing. You know those #include lines? Those are preprocessor directives. An #include directive effectively copy-pastes code from one file into another. When you #include <iostream>, you could effectively take out that line and copy-paste the entire contents of the iostream header into your file, and it'd work exactly the same. The preprocessor is dumb. It's essentially a text filtering stage. But it's the first major step in the process.

The second major step is the actual compilation. This is where your preprocessed code actually gets converted into binary code. But that binary code, and this is the important part, is not actually your exe. What you get instead are object files, little packages of binary code. You generally get one for every source code file you have, every cpp file. But not header files. Header files exist purely to be copy-pasted into other files. They don't get compiled in and of themselves. Most of the errors you get when you build a program are in the compile stage. If you leave out a semicolon somewhere, it's the compiler that bitches at you.

Now, the final step is the most critical. It's called linking.

When you write a computer program, in 99.999% of cases, you're using code written by other people at some point. When you use cout, or vectors, or strings, or all of the other functions that "Come with" C++, you're making use of the "Standard Library". When you want to use SFML's functions for creating a window or drawing an image or (my personal favourite) sending data over a network, you're using the "Simple Fast Media Library". The key repeating word there is Library.

The binary code that your compiler outputs when it builds your program, that's the binary for the code you wrote. But what about the binary code for the stuff everybody else wrote?

The purpose of the linker is to gather up various bits of machine code, various object files and libraries, and stick them all together. This process is called linking, and the result is an executable file that you can actually run.

So you already know where your machine code is. It's the object file your compiler produces. So where is everybody else's machine code?

Well, that depends. Let me draw a distinction here between Dynamic Libraries and Static Libraries. A static library is object code (binary code) that's directly linked into your executable. When you link your program with a Static Library, all of that library's machine code is right there in the executable. SFML's static lib files are called lib-sfml-library.a, with "library" being replaced with "graphics" or "network" or "audio" or some such.

Dynamic Linking is different. See, programmers are smart. Once upon a time, somebody realized that, really, there's some machine code that's going to be used by a lot of people. When you print text on the screen, you're probably not the only program that needs that functionality. When you draw images on the screen, you're not the only program that needs that functionality. Indeed, there's a whole ton of functionality that's used by a lot of programs! A Dynamic Library is effectively this. It's a file which is actually a lot like an executable - It's binary code which is run when needed, and many programs can use it.

So where ARE these files? These are Dynamically Linked Library files. The acronym for that is DLL, and you're probably familiar with them. They're all over the place. The place you see them most is probably in your windows/system32 folder. That makes sense - There's certain binary code that a lot of windows programs use! It makes sense to put them all in one place. SFML's library files are sfml-library.dll, with, again, library usually being graphics or network or audio or system or what have you.

So now, let's steer back to your particular issue. Let's take your questions one by one.

The reason it says "your executable's directory" is because, if you link your program with dynamic libraries.. your program needs to know where those dynamic libraries are! It can't just go over your entire computer and look in every folder for sfml-system.dll. So it looks in a few key places. The first place it looks is in the folder with your executable. Actually, when you run the program from codeblocks, you're usually running the executable from your PROJECT'S folder, so that's where it'll look first. Incidentally, codeblocks has a special name for the location of your Project's folder - They call it your PATH variable. A path is another name for a string representing a folder on your computer. C:\ is a path. C:\Windows\system32 is a path. C:\Documents and Settings\VPellen\My Documents\Project Dream is a path. If that's confusing, let me know, I'll try and reiterate.

Oh, and, incidentally, there are certain folders which all the executables on your computer look in for DLLs, like your windows folder and your system32 and a few others. Those folders are defined in the Path environment variable on your computer - NOT to be confused with the Path environment variable in codeblocks, although they're called "path" for the same reason. You can modify your computer's Path environment variable in your computer's system properties, but DON'T DO THAT UNLESS YOU KNOW WHAT YOU'RE DOING - imagine what would happen if suddenly none of your programs could access all the DLLs in your system32 folder. It wouldn't be pretty.

Now, you're getting undefined reference errors. Those are linker errors. Effectively, your linker is saying "Hey, I was told to expect to find binary code for the function sf::Clock::GetElapsedTime() and a few other things, but I can't find them! That's not cool." So it spits out an error and tells you it can't link your program together.

My guess is that your search directories aren't defined properly.

When you list search directories, there are multiple tabs, for your compiler and your linker. Your compiler search directories should be the include directories for the libraries you want, because it's your compiler that uses the #include directive and such. Your linker search directories should be the lib directory, because that's where the libraries are contained.

Now there's another gotcha - Codeblocks has different "build targets". often, you want multiple "builds" of your program - a normal super fast build for when you publish your program, and a slower build called a "debug build" that lets you use debugging tools to help get rid of bugs in your program. When you're defining your include and lib directories, make sure you do it right for ALL THE BUILD TARGETS YOU NEED, not just one.

The only other thing that could be biting you in the ass is the -lsfml-system-s command - That SHOULD link your libraries, but again, make sure that it's in A: The linker options, and B: That it's set for the right target.

Tutorials are a lovely thing, but the problem is that they're often more concerned with results than education. I hope my rambling rant has been educational. If not, let me know and I'll try and clarify some things.

I'll probably go over this a few times and correct some typos, but I'll put it up now in case it's useful.

Good luck.

Laurent

  • Administrator
  • Hero Member
  • *****
  • Posts: 32498
    • View Profile
    • SFML's website
    • Email
Help understanding the tutorials?
« Reply #4 on: March 14, 2012, 01:04:29 pm »
Would be great to:
- add a little abstraction to make it applicable to any OS
- put it somewhere on a website

... so that we could say "hey, read this first" everytime a beginner has configuration issues :)
Laurent Gomila - SFML developer

VPellen

  • Newbie
  • *
  • Posts: 14
    • View Profile
Help understanding the tutorials?
« Reply #5 on: March 14, 2012, 01:23:08 pm »
I'll happily write you up a clean tutorial if you want, but it'd fundamentally be a language/computer science intuition tutorial rather than a "how to get things running" tutorial. Also, if I were to explain the intuition, I'd probably make a completely separate tutorial on codeblocks because it's very, very separate from the intuition.

Unless you mean I should make my own website. In which case.. well, hell, I could, but I don't know.

You know, really, your tutorial on how to compile SFML shouldn't even be necessary. It should be enough to say "Here's where the libs are, here's where the includes are, off you go son". Compiling the libs from source should be a process even a beginning programmer is capable of. But people come here and they want to understand how to make a program with SFML, and they're confused, and so they nag you and ask you to make a tutorial.

But this isn't their fault, really. Beginner tutorials on how to program in C++ are really, really fundamentally stupid. The first thing they teach is always "okay, here's a preamble on how to set up a compiler so that you can start fiddling with hello world". That's not a good attitude. We're afraid of scaring them off, that if we talk about linkers and compilers that they'll run screaming for the hills, but I'm not sure I believe that. I think everybody who's ever made a computer program has had some fundamental interest in how things work. I also don't think that the compilation and linking process is actually pretty bloody simple when you break it down.

You know it wasn't until a couple of years ago that I actually grasped linking - It wasn't that it was some hard to understand process, it's that I fundamentally didn't understand how building programs worked. I assumed the compilation process was some arcane witchery that I could never grasp or understand without a ton of hardcore reading. I wish somebody had taught me how bloody simple it was sooner. It might've saved me hours of grief with linker errors.

Laurent

  • Administrator
  • Hero Member
  • *****
  • Posts: 32498
    • View Profile
    • SFML's website
    • Email
Help understanding the tutorials?
« Reply #6 on: March 14, 2012, 01:46:58 pm »
Quote
I'll happily write you up a clean tutorial if you want, but it'd fundamentally be a language/computer science intuition tutorial rather than a "how to get things running" tutorial

How to get things running is explained in my own tutorials. What we'd need is really something that explains how things work with very simple words, just like you did above.

When beginners post on this forum to say "hey, I have linker errors", or "xxx DLL cannot be found", we answer by saying "add this linker flag" or "copy this file there", everything works and everyone's happy.
But it's not a good solution, they'd better read what you've just explained, so that the next time they use a library, they wouldn't go through the same "getting started tutorials + beginners posts on the forum" process again.
Laurent Gomila - SFML developer

man with shell

  • Newbie
  • *
  • Posts: 2
    • View Profile
Help understanding the tutorials?
« Reply #7 on: March 14, 2012, 09:38:36 pm »
I acknowledge that my first post was unfair. So, of course, I'm not upset about any rudeness.

For my part, I spent some six hours trying to make this stuff work, and ultimately, I was unable to compile the most basic program. This was somewhat humiliating for a person who has written working games in C++. I hope you will pardon my frustration.

In substantive response to Laurent, what I did not understand is that the DLLs are not needed until after compiling is complete. I thought this DLL copying was another step that needed to come before compiling (after all, it said, "Don't forget" like it's something that I should have done by now).

This post by VPellen is spectacular. I really appreciate the information.

EDIT:

I have fixed the problem. It's something I don't really understand; I'll try to explain it.

Yesterday, I thought I had to put the DLLs in the directory with my executable. I didn't have an executable yet, but I knew which directory Code::Blocks was going to put it in when I pushed "Build and Run". So I copied the DLLs to that target directory.

When I deleted those DLLs, the code ran fine. No more problems.

Again, I appreciate your time and effort.

VPellen

  • Newbie
  • *
  • Posts: 14
    • View Profile
Help understanding the tutorials?
« Reply #8 on: March 14, 2012, 11:20:10 pm »
If I had to guess, I'd say that somewhere along the way some settings got misplaced or fiddled with and then at some point you did multiple steps at once and one of them happened to inadvertently clear up the issue. Either way, good to hear you got things running.

zalkore

  • Newbie
  • *
  • Posts: 4
    • View Profile
    • Email
Re: Help understanding the tutorials?
« Reply #9 on: January 02, 2013, 10:05:00 am »
I know this is an older thread but seeing as how I was having trouble with this same issue (and this post was among the top google results) I thought I'd post my solution. The cause for the error is slightly different than the OP but still, might help.

In the Project Build Options under Linker Settings, I had the dependencies in the wrong order.  Changing these into the correct ordered fixed my errors.

Pretty simple oversight heh.

p.s.
Excellent explanation VPellen, thank you.
"I'm crazy, and I'm right"