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

Author Topic: Exceptions in SFML 3 ?  (Read 37118 times)

0 Members and 1 Guest are viewing this topic.

Silvah

  • Guest
Re: Exceptions in SFML 3 ?
« Reply #15 on: October 13, 2013, 05:55:30 pm »
Throw to code:
try
{
        tex.loadFromFile("pic.jpg");
}
catch(loadFromFileFailed& e)
{//by this point I am already kind of discouraged and want to go play with some other library that doesn't force exceptions
        return errcode::loadFromFileFailed;
}
 
definitely can't be faster
Of course it can be.

If the exception handling method is a so-called "free" exception handling, like DWARF2 or 64-bit SEH, then in the usual case, i.e. no exception is thrown, the cost of setting up a try/catch is zero. As in, no code has to be run, for all the stuff required is in the static data already.

On the other hand, the reverse conversion, if(result == ERROR) { throw something; }, requires a conditional branch. Yes, it may will be well-predicted, making it cheap, but even if it is, it will pollute the branch predictor history, possibly evicting a branch that occurs in the hot path from there. And sure, that hot branch will eventually get there back again, but for the first few times, it's more likely to be mispredicted. The cost of mispredictions is typically measured in tens of cycles, which sure doesn't sound like a lot, except it's already way more than the cost incurred by try/catch in the aforementioned case.

There's also the question of the callee detecting the error. Perhaps surprisingly, it's the same in both cases: it's if(someLowerLevelStuffResult == ERROR) { propagate the error to the caller; }. Given the usual behavior is for no error to occur, it's a simply a not taken branch.

Obviously, if the expected behavior is for an error to actually happen, then the above considerations don't apply, but something is probably amiss anyway.

on MinGW DW2 […] breaks winapi callbacks, SJLJ […] doesn't break callbacks.
It's the other way around. No, really. It's the other way around.

If one throws across callbacks while using DWARF2 unwinding, the unwinder has no idea whatsoever what to do with that foreign stack frame for which there are no unwind data available. So it calls std::terminate.

If one throws across callbacks while using setjmp/longjmp unwinding, the unwinder has no idea whatsoever about anything, its only job is to longjmp to the nearest matching handler. If there is a matching handler, it blindly longjmps to it, completely ignoring any possible cleanup code that the foreign code would otherwise execute. If the foreign code acquired some resources, they're leaked. If it held a lock, a deadlock awaits.

To sum up: with DWARF2, you get a loud immediate crash. With setjmp/longjmp, you get a silent corruption. I'd take the former over the latter any day.

To be completely safe, don't ever throw across foreign code.

EDIT: fixed a typo.
« Last Edit: October 13, 2013, 08:22:18 pm by Silvah »

FRex

  • Hero Member
  • *****
  • Posts: 1845
  • Back to C++ gamedev with SFML in May 2023
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #16 on: October 13, 2013, 06:40:27 pm »
Quote
Of course it can be.
Zero cost doesn't make it faster, just equal, I knew someone would come running with no cost argument or something so I wrote it "can't be faster" not "it's slower".

Quote
It's the other way around. No, really. It's the other way around.
No, it's not unless all these pages are horribly outdated, contain 100% false information and during last 2-4 years everything got put on it's head:
1. http://tdm-gcc.tdragon.net/quirks
2. http://www.mingw.org/wiki/GCCStatus
3. http://gcc.gnu.org/wiki/WindowsGCCImprovements
4. http://sourceforge.net/apps/trac/mingw-w64/wiki/Exception%20Handling

And here is what I wrote, in red you have link in which the same information is given:
Quote
DW2 is 32 bit only(1 and 4), bloats the executable(1 and 3), is much faster(1, 2 and 3) but breaks winapi callbacks(1, 3 and 4), SJLJ is way slower(1, 2 and 3), more space efficient(1 and 3) and doesn't break callbacks(1, 3 and 4).

Quote
If there is a matching handler, it blindly longjmps to it, completely ignoring any possible cleanup code that the foreign code would otherwise execute.
According to 3. it's `common` to throw in callback and catch in win event loop.

Quote
On the other hand, the reverse convertion, if(result == ERROR) { throw something; }, requires a conditional branch.
We are really getting into stupidly low level things now..
SFML would do such condition if it were to throw instead, stbi, ifstream, FILE * and GL all return error codes not throw. And SFML already has many branches, even in Texture.cpp itself, that are false for good data.
« Last Edit: October 13, 2013, 07:04:10 pm by FRex »
Back to C++ gamedev with SFML in May 2023

Silvah

  • Guest
Re: Exceptions in SFML 3 ?
« Reply #17 on: October 13, 2013, 08:34:02 pm »
Quote
It's the other way around. No, really. It's the other way around.
No, it's not unless all these pages are horribly outdated, contain 100% false information and during last 2-4 years everything got put on it's head:
1. http://tdm-gcc.tdragon.net/quirks
2. http://www.mingw.org/wiki/GCCStatus
3. http://gcc.gnu.org/wiki/WindowsGCCImprovements
4. http://sourceforge.net/apps/trac/mingw-w64/wiki/Exception%20Handling

And here is what I wrote, in red you have link in which the same information is given:
Quote
DW2 is 32 bit only(1 and 4), bloats the executable(1 and 3), is much faster(1, 2 and 3) but breaks winapi callbacks(1, 3 and 4), SJLJ is way slower(1, 2 and 3), more space efficient(1 and 3) and doesn't break callbacks(1, 3 and 4).
I only refuted the part about "breaking in presence of foreign frames", the rest may or may not be true, my argument is not concerned about that.

Quote
If there is a matching handler, it blindly longjmps to it, completely ignoring any possible cleanup code that the foreign code would otherwise execute.
According to 3. it's `common` to throw in callback and catch in win event loop.
This may or may not be true, but honestly, I don't understand how this relates to what I said.

Quote
Of course it can be.
Zero cost doesn't make it faster, just equal, I knew someone would come running with no cost argument or something so I wrote it "can't be faster" not "it's slower".
The following sentences tried to explain why zero cost makes it faster by virtue of the alternative incurring a cost.

Quote
On the other hand, the reverse convertion, if(result == ERROR) { throw something; }, requires a conditional branch.
We are really getting into stupidly low level things now..
It was you who started talking about low-level and mostly irrelevant (for most code, at least) things like the speed of exceptions, so you shouldn't be very surprised if people follow the same route in their arguments.

SFML would do such condition if it were to throw instead, stbi, ifstream, FILE * and GL all return error codes not throw.
But SFML has to if if it wants to return an error code too.

And SFML already has many branches, even in Texture.cpp itself, that are false for good data.
If that's the case, could you show they're not necessary, then file bugs or pull requests to remove them? But if they're part of the logic, then they're part of the logic.

If you disagree, that's fine. But it'd be kind of you to point out the parts I got wrong and why I am wrong instead of using sophistry.
« Last Edit: October 13, 2013, 08:37:51 pm by Silvah »

Nexus

  • SFML Team
  • Hero Member
  • *****
  • Posts: 6286
  • Thor Developer
    • View Profile
    • Bromeon
Re: Exceptions in SFML 3 ?
« Reply #18 on: October 13, 2013, 09:05:33 pm »
Error handling in SFML is hardly ever time-critical, and even if it were, other points such as user-friendlyness are certainly more relevant. I think we should focus again on design aspects rather than micro-optimization.

I mostly just said the whole "image loading" thing as a way of highlighting my attitude towards design and programming, namely I prefer very discrete responsibilities in code.
As mentioned, a separate loader would tear apart the implementation in many cases, which is not what I call well-distributed responsibilities.

If you look at the implementation of Texture.loadFromFile, it just calls through to sf::Image.
Yes, but look at other resource classes, for example sf::Font. Extracting loadFromFile() leads to another class that needs access to the same low-level library (freetype in this case). It is likely that both Font and FontLoader require common functionality, which leads to either further types that transport the information, or  the break of encapsulation through friendship, or both. There is additional code necessary to pass information from one object to the other, i.e. there is more code to test and maintain.

On the other hand, I see no advantage of separating the classes. Please name an actual one (not just from a theoretical OOD perspective) that would justify the big disadvantages, namely more complex API and implementation.
Zloxx II: action platformer
Thor Library: particle systems, animations, dot products, ...
SFML Game Development:

FRex

  • Hero Member
  • *****
  • Posts: 1845
  • Back to C++ gamedev with SFML in May 2023
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #19 on: October 13, 2013, 10:08:47 pm »
Quote
I only refuted the part about "breaking in presence of foreign frames", the rest may or may not be true, my argument is not concerned about that.
Me, GCC for Windows page, MinGw 64 wiki page and TDM quirks page all say that DW2 breaks them and SJLJ doesn't, you said it's other way around, you got this part wrong too.


Quote
But SFML has to if if it wants to return an error code too.
But you were complaining that throwing after checking error code is inefficient so that's why it should always throw, while SFML would do exactly same thing in a function one level lower on call stack -> check one of error codes and instead of returning false throw. Something at some point has to branch on error code from C to throw.


Quote
The following sentences tried to explain why zero cost makes it faster by virtue of the alternative incurring a cost.
Reread the point, it was about code->throw being nicer conversion to write than throw->code. Here is the point pasted so that you don't forget to actually read it when you start replying, like you forgot to read all linked pages apparently.
Quote
3.The fuss of converting error code to exception is way way lesser than fuss of converting exception into error code:


Quote
This may or may not be true, but honestly, I don't understand how this relates to what I said.
You said basically: "SJLJ sucks beacuse DW2 crashes loudly and SJLJ does stupid things silently and corrupts state" while GCC page says it's perfectly normal for people to do exactly that using SJLJ and that's why Windows is stuck with this slower model and TDM quotes better interoperability as reason for using SJLJ by default.


Quote
If that's the case, could you show they're not necessary, then file bugs or pull requests to remove them? But if they're part of the logic, then they're part of the logic.
These lines make no sense unless you want to pass negative offset of left corner and have it ignored silently, two checks that have yet to be true in my code ever(I guarantee I never in my life tried to load image with left or top being negative):
https://github.com/SFML/SFML/blob/master/src/SFML/Graphics/Texture.cpp#L213
They are probably there for idiots so it doesn't crash in release.


Quote
It was you who started talking about low-level and mostly irrelevant (for most code, at least) things like the speed of exceptions, so you shouldn't be very surprised if people follow the same route in their arguments.
No, it was TDM and GCC pages that say SJLJ is always slow and that DW2 is even slower when exceptions happen. You are getting into CPU instructions level issues and claiming that branching on error code before throw is slow except you didn't provide any evidence for your claim whatsoever.


Quote
But it'd be kind of you to point out the parts I got wrong and why I am wrong instead of using sophistry.
You are using sophistry and spewing bullshit, you first said that DW2 and SJLJ are other way around with regard to foreign frames which is debunked by TDM and GCC page.
Then you claim that SJLJ actually is bad for not crashing because it breaks the foreign clean up, which is debunked by GCC page and called common practice.
Then you claim that checking single error code that is almost never true is a costly branch, while SFML does branches that are almost never false already.
How linking to official GNU, MinGW and TDM pages is sophistry is really beyond me.
You have yet to provide a single link, documentation page or whatever to back up anything you said and you are calling me using official sources "sophistry".
IF as you said SJLJ craps on clean up of C foreign frames then go report the problem to Dragon so he can update TDM page AND find more recent GCC on Windows page that says that and then come back to me because I'm completely uninterested in "feelings" such as:
Quote
This may or may not be true
Quote
may or may not be true
aimed at GCC or TDM page without any backing information whatsoever coming from someone who just two posts above this one was completely wrong about which exception model actually breaks foreign frames and now claims that both actually do and no one at GCC, MinGW nor Dragon noticed.

Quote
break of encapsulation through friendship
Does it really? BS says It doesn't: http://www.stroustrup.com/bs_faq2.html#friend
« Last Edit: October 13, 2013, 10:24:56 pm by FRex »
Back to C++ gamedev with SFML in May 2023

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 10801
    • View Profile
    • development blog
    • Email
Re: Exceptions in SFML 3 ?
« Reply #20 on: October 13, 2013, 11:21:28 pm »
FRex and Silvah: Can we now return to a normal discussion and leave your personal feelings completely aside? You can still fight each other on your own private messages, but this near childish behavior and calling names won't help you, nor us, nor the discussion. Thank you!

Also a design discussion is about showing different opinions, possible dangers or problems as well as trying to find a general solution for the greater good. Thus it's important to give your opinion, but when doing so please keep in mind to not claim your opinion as "the truth" and "the right way" to go, thus kind of provoking fights rather than discussions (even implicitly!).
Side notes such as "everything-is-throwing-cause-modern-cpp-is-one-size-fits-all" are completely unnecessary and even though not intended can be seen as intimidating.
Thus keep it objective, fact based and try to hold your personal feelings back, that way we can actually get a good discussion going. :)

Now back to the topic

There have been a few arguments regarding C or binding usage. Those are valid points one has to think about, but SFML is a C++ library and we should be using C++'s full power and go with modern "patterns". Constantly thinking about how it would work in C or how C functions handle X or how bindings would work with it, doesn't yield many useful results to a C++ based discussion. Also keep in mind that a lot of other C++ features don't work with C and other bindings and yet we have a working CSFML and quite a few bindings to SFML.
I think the first iteration of the discussion should be about the C++ library SFML and only in a second or third instance one could think about what it means for all the existing and future bindings. So let us have a C++ rather than a C discussion! :)

Given that this discussion started from Tank's GDD article, it's interesting that nobody has really thought about what Tank actually said in the article. If we'd assume loadFromFile throws an exception, how can we prevent stepping into it? Do we have to implement our own exists() function, should SFML provide such a facility or do we ignore what Tank wrote and let everyone walk blindly into the exception?
Of course there are also other ways loadFromFile could fail, do we need facilities for that as well or do we just cover the most common one?
Maybe this goes a bit into the same direction as MorleyDev pointed out. The loadFromFile does essentially "too much".

Since some people rather want to stick with booleans, how would one fix the problem of not knowing what the error actually was about? Do you consider a enum with the different error and error codes to be a better design then?

And as a final note: Arguing about performance especially for such low-level functionalists seems rather ridiculous. Unless there are real benchmarks with function usage similar to how SFML would use exceptions/uses booleans this subject shouldn't really matter in such a discussion.

I'll also leave this here. It's not like we're the first one having such discussions. :D
« Last Edit: October 13, 2013, 11:35:15 pm by eXpl0it3r »
Official FAQ: https://www.sfml-dev.org/faq.php
Official Discord Server: https://discord.gg/nr4X7Fh
——————————————————————
Dev Blog: https://duerrenberger.dev/blog/

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: Exceptions in SFML 3 ?
« Reply #21 on: October 13, 2013, 11:25:50 pm »
Actually its more than 2 things that are done by the loadFromFile methods: access of the file system to get the file size, allocating memory for encoded data, loading the data, identify the data format and the size after decoding, allocating memory for decoded data, decoding, freeing memory from encoded data, using the data(upload to graphics card, creating glyphs and so on).
SFML hides memory allocation already for many things and I think that should be kept that way in the future, so that part can be ignored. Then there remain just loading, often decoding and using; and I think what can be easily done with a function needs no loader or decoder objects just to satisfy some OO extremists.
If those 3 responsibilities get split it would nicely separate concerns and the resource classes would stop needing to know how to access all kinds of other libraries. It could look like these (assuming its with exceptions):
sf::Buffer buf=sf::LoadFile("picture.png");
sf::Image img=sf::DecodeImage(buf);
sf::Texture tex(img);
 
sf::Texture tex(sf::DecodeImage(sf::LoadFile("picture.png")));
Then people could easily replace parts, for example:
FancyData data=fancyBufferedZipFileSystem.load("picture.png");
sf::Texture tex(sf::DecodeImage(data.ptr(),data.size()));
 
std::unique_ptr<uint8_t[]> bitmap=MyRaytracer.renderImage(x,y);
sf::Texture tex(sf::Image(x,y,bitmap.get()));
sf::Buffer buf=sf::LoadFile("picture.newformat");
MyBitmap bm=MyNewDecoder(buf.ptr(),buf.size());
sf::Texture tex(sf::Image(bm.x,bm.y,bm.ptr));
Maybe even add another variant of the Buffer?
sf::MemMapBuffer buf("picture.png");
sf::Texture tex(sf::DecodeImage(buf));
Another weird example for demonstration:
sf::Http h("http:://www.example.com");
sf::Http::Response response=h.sendRequest(sf::Http::Request("downloads/myshader.vs"));
if(response.getStatus!=sf::Http::Response::Ok)
  throw std::runtime_error("could not download vertex shader");
sf::Buffer vsbuf=response.getBody();
response=h.sendRequest(sf::Http::Request("downloads/myshader.fs"));
if(response.getStatus!=sf::Http::Response::Ok)
  throw std::runtime_error("could not download fragment shader");
sf::Buffer fsbuf=response.getBody();
sf::Shader shader(vsbuf,fsbuf);
Without exceptions that would all get longer and possibly loose the return values for getting something useful, but I think you can imagine the code yourself. Providing versions with and without exceptions shouldn't be all that difficult.
« Last Edit: October 13, 2013, 11:29:11 pm by wintertime »

Ixrec

  • Hero Member
  • *****
  • Posts: 1241
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #22 on: October 13, 2013, 11:53:48 pm »
Quote
Given that this discussion started from Tank's GDD article, it's interesting that nobody has really thought about what Tank actually said in the article. If we'd assume loadFromFile throws an exception, how can we prevent stepping into it? Do we have to implement our own exists() function, should SFML provide such a facility or do we ignore what Tank wrote and let everyone walk blindly into the exception?
Of course there are also other ways loadFromFile could fail, do we need facilities for that as well or do we just cover the most common one?

A lot of this didn't quite make sense to me, because having a non-throwing version of/option for the function (especially if the optional argument is an error struct) seems to be the obvious and complete answer to all of those questions.  Are you assuming we won't have such a thing?

Quote
Maybe this goes a bit into the same direction as MorleyDev pointed out. The loadFromFile does essentially "too much".

Well, let's try to get a bit more specific, since encapsulating all the annoying details for you is a big plus of OOP in general and libraries like SFML in particular.

The first few specific ideas regarding how to split it up have essentially been rejected in this thread already for splitting the API and implementation without any non-theoretical gain, so I'll ignore those.  wintertime's sf::Buffer idea at least seems like it might have a purpose.

Since it's already possible to load the sf::Image yourself and make the sf::Texture from that, instead of doing it all in a single sf::Texture.loadFromFile() call, I'll assume we don't really need to debate that split (no one's suggesting we *force* everyone to explicitly construct the Image themselves, right?).

So the question is whether splitting sf::Image into sf::Image and sf::Buffer gives any real benefits.  First, though I know very little about this low-level stuff, I have a hard time believing that you can load a file's data into a buffer with absolute zero awareness of the file's format, in which case you'd be splitting the implementation again.  And what would be the benefit of manipulating the buffer yourself?  Most of the examples wintertime gives seem like they should already possible with loadFromMemory and/or loadFromStream, so it seems like the only potential gain is some options for manual memory management.

Maybe you could argue that all of these functions shouldn't be part of the sf::Texture class because of the abstract design principles people have been citing, but I'm pretty sure that if you really follow those principles you just end up putting all of sf::Texture's functions into sf::TextureManager, leaving sf::Texture as nothing but a wrapper for an OpenGL cache ID (and sf::Image a wrapper for a Uint8*, etc), and at that point the new sf::TextureManager is identical to the old sf::Texture but with a longer name.
« Last Edit: October 13, 2013, 11:58:15 pm by Ixrec »

Hiura

  • SFML Team
  • Hero Member
  • *****
  • Posts: 4321
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #23 on: October 14, 2013, 12:04:44 am »
@wintertime: it's an interesting design, for sure. However, apart from a few extra constructors and a new interface with sf::Buffer, it feels a lot like the current loadFromMemory methods.

Sure, with exception,  you can know exactly which operation / object failed but it can also be done with different type of exception (e.g. sf::IOException, sf::FormatException, ...).

And without exception I feel the code will be bloated with if statement everywhere without a real advantage over the current model – even if the user know what failed he will have to suffer too much.



About exception VS return code, here are my quick thoughts.

With SFML 2 we have to use code like this:

sf::Resource x;
if (x.loadFromY(z)) { ... }

With exception we could directly load x in its constructor and therefore make things more readable (IMO).

sf::Resource x(z);

Where Resource is Image/Texture/Sound/......

(This was also mentioned by someone earlier:) If we have to load N resource, we have (usualy) only one try-catch whereas we would have N if statements.
SFML / OS X developer

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 10801
    • View Profile
    • development blog
    • Email
Re: Exceptions in SFML 3 ?
« Reply #24 on: October 14, 2013, 12:06:24 am »
A lot of this didn't quite make sense to me, because having a non-throwing version of/option for the function (especially if the optional argument is an error struct) seems to be the obvious and complete answer to all of those questions.  Are you assuming we won't have such a thing?
Never mind that, I should've looked at it again. :D
Quote from: GDD - Errors
The answer is simple: You can’t guarantee that between your checks and the actual call, the file will still be readable, because you don’t control it. Files live on a shared storage, a lot can happen in the meantime.

The first few specific ideas regarding how to split it up have essentially been rejected in this thread already for splitting the API and implementation without any non-theoretical gain, so I'll ignore those.  wintertime's sf::Buffer idea at least seems like it might have a purpose.
The question we'll eventually get back to will be: Is that still "simple" as in "Simple and Fast Multimedia Library"? How many more intermediate classes can we add to gain only a small bit of "better" design?
Don't get me wrong I like the idea and iirc we had some similar suggestions a year or so back.
Official FAQ: https://www.sfml-dev.org/faq.php
Official Discord Server: https://discord.gg/nr4X7Fh
——————————————————————
Dev Blog: https://duerrenberger.dev/blog/

Ixrec

  • Hero Member
  • *****
  • Posts: 1241
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #25 on: October 14, 2013, 12:17:06 am »
Yeah, that was the conclusion I came to in that post (same as you and Hiura it seems).  By "might have a purpose" I merely meant that it wasn't quite as straightforward a case as the sf::TextureLoader class proposed earlier.  That one obviously didn't add any useful functionality.

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: Exceptions in SFML 3 ?
« Reply #26 on: October 14, 2013, 12:23:45 am »
The idea is to make all resource classes simpler by cutting out the 6 loadFromMemory, loadFromFile and loadFromStream. The Buffer class would then also replace the weird self-defined stream classes and the file loading for all things would use it, which arguably would make it simpler.
DecodeImage would be a free function and the only one to know about the png, jpg and other libs and then Image needs only know about already decoded bitmaps. Maybe the other classes could also be simplified in that way.

MorleyDev

  • Full Member
  • ***
  • Posts: 219
  • "It is not enough for code to work."
    • View Profile
    • http://www.morleydev.co.uk/
Re: Exceptions in SFML 3 ?
« Reply #27 on: October 14, 2013, 12:26:01 am »
FYI I never proposed a TextureLoader, I was going more the ImageLoader/Load file and Decode way at the Image level.

I really should of thought of that splitting down to File -> Buffer -> Image, kicking myself for not when it's exactly where my thinking was heading and then I just couldn't finish it in a way I liked. But that way you presented, I like. It looks very nice and, I think, would read very well and be conceptually easy to understand.

For "simplicity" one could perhaps create a facade onto that system that unifies it for beginners, and when they need more complex solutions "Well, this actually uses these under the hood so all you need to do..." is always a nice thing to be able to say.

A benefit I kept thinking of and never bloody mentioned for some reason (sorry, it's been a long day xD) with an extensible design would be the ability to easily plug-in ones own loaders alongside the built-in ones for loading custom file types. An exposed loading system would be much easier for a user to extend.

Loading for images is, I believe, determined in the underlying libraries used in SFML by the "header bytes" of the files that image types have to identify them. A unified decoder you can add your own logic to would be very useful for people who want support for whatever types SFML does not provide support for.

However, I'm well aware all of these proposals would call for big changes in the underlying code for SFML. It's possible to instead write your own loader and call loadFromMemory/loadFromStream means it has solutions in the current way of doing thing.

Since the current way still works and can be made to work with others fine, it's arguable that it's not enough of a benefit to justify what could be a dramatic rewrite of the system.

But on the other other hand, writing a PhysFS File loader makes more sense to me than writing a PhysFS Stream as something to just drop into your code as a replacement for sf::LoadFile and have it just work...feels much simpler than having to go in, replace loadFromFile with loadFromStream and give loadFromStream the new stream you have to create.
« Last Edit: October 14, 2013, 12:44:55 am by MorleyDev »
UnitTest11 - A unit testing library in C++ written to take advantage of C++11.

All code is guilty until proven innocent, unworthy until tested, and pointless without singular and well-defined purpose.

Ixrec

  • Hero Member
  • *****
  • Posts: 1241
    • View Profile
    • Email
Re: Exceptions in SFML 3 ?
« Reply #28 on: October 14, 2013, 12:44:03 am »
I don't really see the problem with loadFromMemory/loadFromStream.  I never felt they were "straying from the way SFML wants you to do these things."  The whole reason they exist is to cover the odd cases where we want to get the data our own way; using them in those cases is exactly what SFML would want (if it was sentient).

Quote
The idea is to make all resource classes simpler by cutting out the 6 loadFromMemory, loadFromFile and loadFromStream. The Buffer class would then also replace the weird self-defined stream classes and the file loading for all things would use it, which arguably would make it simpler.

Wouldn't this be another case of splitting/duplication huge swaths of implementation details?

I guess you could argue the API is a bit simpler if you just use three overloads of sf::Texture instead of the three loadFromX methods, but that seems like hiding something from the end user you really shouldn't be hiding, and it'd probably be a little more confusing than having the explicit function names.

Nexus

  • SFML Team
  • Hero Member
  • *****
  • Posts: 6286
  • Thor Developer
    • View Profile
    • Bromeon
Re: Exceptions in SFML 3 ?
« Reply #29 on: October 14, 2013, 12:45:37 am »
The idea is to make all resource classes simpler by cutting out the 6 loadFromMemory, loadFromFile and loadFromStream.
But this "simpler" is very local, the usage is massively more complicated. Three or more classes to load an image is definitely not the solution. The 7z API is built like that: You have to work with buffers and low-level algorithms and need to know a lot about the non-documented implementation. That effectively makes 7z/LZMA the worst C++ API I have ever seen. If we go in that direction, we should still provide a high-level way to load an image in one function call. Most people don't care about decoding, buffers, file formats or anything like that.

The Buffer class would then also replace the weird self-defined stream classes and the file loading for all things would use it, which arguably would make it simpler.
But using fixed buffers, you lose the whole advantage of sf::InputStream, namely the streaming itself. Now it is possible to load music continuously in chunks from an archive, how would this work with the buffer API?

One possibility would be to adapt sf::InputStream to work with sf::Buffer instead of (void*, size_t) pairs. But then you still have the stream class, and everything is more complicated.
Zloxx II: action platformer
Thor Library: particle systems, animations, dot products, ...
SFML Game Development: