SFML community forums

General => SFML development => Topic started by: eXpl0it3r on March 08, 2017, 12:58:37 pm

Title: sf::Time & sf::Clock vs C++11 chrono
Post by: eXpl0it3r on March 08, 2017, 12:58:37 pm
Info & Rules (http://en.sfml-dev.org/forums/index.php?topic=21541.0) about this sub-forum

With C++11 (http://en.sfml-dev.org/forums/index.php?topic=21571.0) we finally got access to <chrono> a native and thus cross-platform C++ standard library timing and clock functionalities.

SFML 2.x and earlier has introduced its own sf::Clock and later sf::Time classes to deal with time dependent functionalities internally but also as library features, useful in pretty much any application.

Questions are now:
For comparison here are two simple clock example as one can probably find in many games. Let us know if you think there are better examples/implementations to show the API differences.

(click to show/hide)

(click to show/hide)


Summary
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Jonny on March 08, 2017, 02:17:31 pm
chrono functionality with SFML interface would be ideal ;)

I like the power/flexibility of chrono, but it can often be quite verbose and lacks simplicity for common tasks. If I had to choose I'd say remove the SFML classes (ultimately it's one less thing to maintain and allows development to focus on other new features).
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Mario on March 08, 2017, 02:27:23 pm
I'd vote for thin wrappers, i.e. existing SFML class around the standard library stuff. Why? Because of simplicity. It's very unlikely this would cause any significant maintenance overhead, but at the same time it makes usage so much simpler, because SFML's interface is far less elaborate/flexible and hides lots of optional complexity.

<chrono> has a higher entry level/knowledge requirement compared to sf::Clock.

Also keep in mind that nobody is forced to use these classes. if you need more control, e.g. to pick your timer class/accuracy, nobody stops you from using <chrono> directly, but especially from a newbie friendly approach, it's far better to offer a thin wrapper that's both easy to understand and use. Especially considering they're not really "off-topic" for SFML's scope.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 08, 2017, 06:21:25 pm
I usually think it's better to use standard stuff, because it is more flexible, robust, documented, used, etc. and people don't have to learn yet another xyz class which just works for this specific framework. And we can focus on the real value of SFML (multimedia abstractions) rather than thin wrappers provided for pure convenience.

But I have to admit that std::chrono makes things more verbose and confusing than needed... So here is my suggestion:

sf::Time looks much better than the standard equivalent (either verbose templates everywhere, or std::chrono::nanoseconds which looks confusing). So I'd keep it. With additional conversions to and from std::chrono::duration, if possible.

sf::Clock doesn't deserve to exist compared to a standard clock::now() (yes, don't be afraid to typedef those long standard clock types). But it's convenient because it returns that sf::Time that I want to keep in the API. So let's make it more useful! Everyone wants a pausable clock, let's do it. Maybe we can even find other good ideas in the long list of suggestions/implementations available.

PS: here is the standard example using less verbose syntax (let's not make it more complicated than it is ;))

(click to show/hide)
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Lin on March 09, 2017, 05:51:46 am
I'd like SFML to keep its own clock wrapper because I use the C binding of SFML, and removal of it would require me to use another library or do an extra step to link <chrono> in my project.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 09, 2017, 06:32:27 am
Quote
I'd like SFML to keep its own clock wrapper because I use the C binding of SFML
Bindings should not interfere in the design choices for the core libraries. If feature xxx is standard in C++ but not in yyy language, then SFML should not be concerned about it ;)
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: binary1248 on March 09, 2017, 07:23:39 am
That is where lists like these come in handy:

https://github.com/nothings/single_file_libs
https://github.com/fffaraz/awesome-cpp
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Hiura on March 09, 2017, 11:14:31 am
sf::Time looks much better than the standard equivalent (either verbose templates everywhere, or std::chrono::nanoseconds which looks confusing). So I'd keep it. With additional conversions to and from std::chrono::duration, if possible.

I think it's really important to have something easy to use for the various part of SFML that deal with duration. But providing something specific to SFML also has the downside to make it harder to use with other STL features.

But is the STL version really that verbose or confusing? I mean, its API looks very similar to SFML's. We could simply use an alias in the sf namespace to represent time duration.

(click to show/hide)

Disclaimer: I haven't used this API yet actually, so if I missed something more complex than that, let me know.


By the way, is std::chrono::duration<float> a number of seconds?
Yes, the default ratio for time duration is one, which is expressed in seconds. Also relevant for the curious among us: http://en.cppreference.com/w/cpp/chrono/treat_as_floating_point
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 09, 2017, 11:23:08 am
Quote
We could simply use an alias in the sf namespace to represent time duration
I can imagine a few drawbacks:
1. Nothing, in your function that takes a sf::Time, indicates that you work with nanoseconds; in the end you'll constantly go see that typedef to know what sf::Time is
2. You're not showing conversion from sf::Time to something else than nanoseconds; this is where std::chrono is quite verbose
3. "5s" is okay, but what about 3.2 seconds? its creation will be more verbose, and you'll end up with a duration<float> that will no longer be implicitly convertible to sf::Time (you'll have to duration_cast)
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Hiura on March 09, 2017, 12:26:05 pm
I see now what you meant! It's indeed not as simple as I initially thought.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Elias Daler on March 10, 2017, 09:09:12 am
I completely agree with idea of having sf::Clock, but implementing it with <chrono>.

What if sf::Time just stored time in std::chrono::nanoseconds and had all the same functions like asSeconds(), asMilliseconds() and just used duration_cast in implementations? We may also add some user-defined literals like "s", "ms" and then we'd be able to write:
music.setPlayingOffset(500ms);

sf::Time may also have implicit constructors which accept std::chrono::nanoseconds, std::chrono::milliseconds, std::chrono::seconds so that conversions from standard library things to sf::Time are possible.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 10, 2017, 09:22:10 am
Quote
What if sf::Time just stored time in std::chrono::nanoseconds and had all the same functions like asSeconds(), asMilliseconds() and just used duration_cast in implementations?
That was the implicit plan :)

Quote
We may also add some user-defined literals like "s", "ms" and then we'd be able to write
Quote
sf::Time may also have implicit constructors which accept std::chrono::nanoseconds, std::chrono::milliseconds, std::chrono::seconds so that conversions from standard library things to sf::Time are possible
Implicit constructors already allow to write "music.setPlayingOffset(500ms), no need to define our own user-literal suffixes.
Also, we may not need as many constructors. Anything with integer representation and higher period can be implicitly converted to std::chrono::microseconds, and same for a duration<float, seconds>. Or if it doesn't work too well, we can have a single templated constructor and use duration_cast to get microseconds.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Elias Daler on March 10, 2017, 09:28:32 am
That's good to know, just makes everything simpler for implementation.  ;D
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: MrOnlineCoder on March 10, 2017, 08:38:31 pm
I love sf::Clock more that that chrono, that casts,declartions are not so great as usage of Clock, IMO.  I agree with Mario, Clock is more friendly, I think.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: jill on March 12, 2017, 02:03:25 am
Both are very great api. I prefer learn both of them. sf::Clock & sf::Time means more sfml-native and more object-oriented. And std::chrono means portable: it can be used not only in sfml, but also many other apis(Saying these words is embarrassed in sfml community ;D), so std::chrono is: learn only once and use anywhere. So,  I prefer learn both.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: JayhawkZombie on March 13, 2017, 03:31:07 pm
If my input is of any use:

We all use std::chrono for our internal timing, but it's not far off from sf::Clock.
Sort of like:

CurrFrameStart = std::chrono::high_resolution_clock::now();
TickDelta = std::chrono::duration<double, std::milli>(CurrFrameStart - LastFrameStart).count();

I'd argue that SFML's timing libraries are easier to use, and certainly less verbose, but I see no reason SFML couldn't wrap the C++11 implementation.  It would allow, like Laurent said, conversion between representations, and you'd have access to the system's highest resolution clock if needed.
It would also strip off some more platform-dependent code (and remove that oh-so-beautiful "isWindowsXpOrOlder" check), at least for compilers that support the C++11 standard chrono addition (though I've yet to encounter one that doesn't).
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 13, 2017, 03:34:24 pm
Of course, the implied goal is to remove all that ugly OS-specific stuff when a standard implementation exists. We don't want to re-invent std::chrono from scratch.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: korczurekk on March 14, 2017, 07:57:08 pm
Well, if there still will be sf::Time in SFML3 it would be quite important to provide method like asStandardDuration() (in addition to asSeconds() etc.) so it wouldn't be a problem to get it work with stuff like std::this_thread::sleep_for(). I fear that making new sf::Time compatible with std::chrono can cause code to be huge and, as far as I know, we don't want it to happen. At least I don't.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: Laurent on March 14, 2017, 08:00:26 pm
Quote
Well, if there still will be sf::Time in SFML3 it would be quite important to provide method like asStandardDuration() (in addition to asSeconds() etc.) so it wouldn't be a problem to get it work with stuff like std::this_thread::sleep_for()
It was already said at least twice ;)
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: korczurekk on March 14, 2017, 08:04:56 pm
Quote
Well, if there still will be sf::Time in SFML3 it would be quite important to provide method like asStandardDuration() (in addition to asSeconds() etc.) so it wouldn't be a problem to get it work with stuff like std::this_thread::sleep_for()
It was already said at least twice ;)
I also read trough it twice and still didn't notice that. ;-; Well, that's my opinion, at least you know what folks think.
Title: Re: sf::Time & sf::Clock vs C++11 chrono
Post by: aggsol on March 23, 2018, 04:48:45 pm
I vote for complete removal including sf::Time. As the example from JayhawkZombie shows there is so little gained from keeping sf::Time. It is IMO not worth the overhead. The additional verbosity and relying on the standard will lower the entry barrier of SFML und will introduce beginners  to more std functions.