TextBox addText() gets increasingly slow [solved, workaround]

Started by syndicatedragon, 24 July 2013, 22:09:56

syndicatedragon

I'm trying to use a TextBox as a console but it seems like every time I call addText() it takes longer and longer for it to finish. This is with git-master downloaded this afternoon (7/24). Is this a known issue?

texus

Yes, TextBox is extremely slow and it is planned to be rewritten before v0.6 is finished.

Try using ChatBox instead for a console.
Then you could use an EditBox to type a new line.

ChatBox will be slow on linux with sfml 2.0, but there is no problem on windows or when using the github version of sfml.

syndicatedragon

OK, I'll give that a shot. Thanks for your reply and continued work on TGUI. :)

syndicatedragon

Before I had this which builds and works fine (except for the aforementioned slowness):
tgui::TextBox::Ptr tb(GameEngine::get()._gui, "console");
tb->load("Resources/TGUI/objects/Black.conf");
tb->disable();
tb->setPosition(0,450);
tb->setSize(800,150);
tb->setText(_consoleOutput);
tb->setTextSize(8);


I replaced it with this and now I get link errors. Any ideas what am I doing wrong?

tgui::ChatBox::Ptr tb(GameEngine::get()._gui, "console");
tb->load("Resources/TGUI/objects/Black.conf");
tb->setPosition(0,450);
tb->setSize(800,150);
tb->addLine("Welcome!", sf::Color::White);
tb->setTextSize(8);


errors:


1>PlayingState.obj : error LNK2019: unresolved external symbol "__declspec(dllimport) public: __thiscall tgui::SharedWidgetPtr<class tgui::ChatBox>::~SharedWidgetPtr<class tgui::ChatBox>(void)" (__imp_??1?$SharedWidgetPtr@VChatBox@tgui@@@tgui@@QAE@XZ) referenced in function "public: virtual void __thiscall PlayingState::init(void)" (?init@PlayingState@@UAEXXZ)
1>PlayingState.obj : error LNK2019: unresolved external symbol "__declspec(dllimport) public: class tgui::ChatBox * __thiscall tgui::SharedWidgetPtr<class tgui::ChatBox>::operator->(void)const " (__imp_??C?$SharedWidgetPtr@VChatBox@tgui@@@tgui@@QBEPAVChatBox@1@XZ) referenced in function "public: virtual void __thiscall PlayingState::init(void)" (?init@PlayingState@@UAEXXZ)
1>PlayingState.obj : error LNK2019: unresolved external symbol "__declspec(dllimport) public: __thiscall tgui::SharedWidgetPtr<class tgui::ChatBox>::SharedWidgetPtr<class tgui::ChatBox>(class tgui::Container &,class sf::String const &)" (__imp_??0?$SharedWidgetPtr@VChatBox@tgui@@@tgui@@QAE@AAVContainer@1@ABVString@sf@@@Z) referenced in function "public: virtual void __thiscall PlayingState::init(void)" (?init@PlayingState@@UAEXXZ)

texus

That is really strange.

I'm going to sleep now, but tomorrow I'll see if I can get a windows up and running to test this myself.

In the meantime you could try to link statically and see if it makes any difference.

texus

The problem only occurs with dynamic linking on windows.
So as a temporary workaround you can just use static linking.

I'll continue searching for the problem, but so far I have absolutely no idea what could be causing this error.

syndicatedragon

This isn't your problem, but I'm having some trouble with static linking and maybe you can spot my mistake.

I rebuilt tgui and got tgui-s-d.lib. I changed my Linker->Input list to the -s-d versions of both SFML and TGUI. I changed C++->Code Generation->Runtime Library to Multi-threaded Debug. I rebuilt the solution but I get a bunch of link errors for all of the SFML and TGUI functions that I call. They look like the errors I posted above, and it looks like it's still looking for a dll? Here's an example. Did I miss some step in order for static linking to work?

1>Actor.obj : error LNK2019: unresolved external symbol "__declspec(dllimport) public: virtual __thiscall sf::ConvexShape::~ConvexShape(void)" (__imp_??1ConvexShape@sf@@UAE@XZ) referenced in function __unwindfunclet$??0Actor@@QAE@XZ$0

texus

#7
I think you forgot to define SFML_STATIC.

QuoteI changed C++->Code Generation->Runtime Library to Multi-threaded Debug
You shouldn't touch this option. It is only needed when linking to the STL libraries statically, which you normally don't do.

syndicatedragon

Hmm. Defining SFML_STATIC and rebuilding allows it to link now. Unfortunately it crashes as soon as I start debugging.
Unhandled exception at 0x7c90100b in rl01_sfml.exe: 0xC0000005: Access violation reading location 0x00000014.The call stack is
> ntdll.dll!7c90100b()
> rl01_sfml.exe!sf::priv::MutexImpl::lock()  Line 52 + 0xc bytes C++

This kind of seems like an SFML problem? I guess I'll try building my own static SFML next (I've been using the pre-built libraries). Question: when building TGUI should the "TGUI_USE_STATIC_STD_LIBS" be checked when building for static SFML?

Thanks for all of your help so far

texus

#9
QuoteQuestion: when building TGUI should the "TGUI_USE_STATIC_STD_LIBS" be checked when building for static SFML?
Normally no.

If you use the precompiled sfml library then you must leave this unchecked.

This is about building static std libraries. If you check it when building tgui then it should also be checked in sfml (which isn't the case in the sfml that you download from the site). And only then you have to change the "Code Generation->Runtime Library" option in visual studio.
I prefer linux for this because there it doesn't matter how libs are compiled, but on windows these 3 options have to match each other (or you will get errors or crashes).

So if you had this option checked then it might be the reason for the crash.

syndicatedragon

I'm pretty sure that I didn't check that box, but I'll build again to be sure. At any rate, I took TGUI out of my build and it still crashes when using the static SFML libraries. So... I guess I will try to build my own SFML and see if that makes any difference. I'll check over on the SFML forums too.

texus

I found the problem that caused the errors with dynamic linking.

But I now hate windows even more than before.
The whole issue had nothing to do with ChatBox. After searching for the difference between TextBox and ChatBox I came to the simple conclusion: there wasn't any difference in the way they were used. In the end it turned out that you may not use "__declspec(dllimport)" for template classes (but have to do this for all other classes).
Where did I read that when searching info about dllexport and dllimport? Right, nowhere.

But anyway, I removed one word from my code and now using dlls should be possible again.

syndicatedragon

Ugh. Well, good job figuring that one out. That knowledge might come in handy in the future for me as well.

Also, I figured out my problem with the SFML static libs. I was using a sf::RenderWindow in a singleton class and apparently you can't use an instance of that class in a static/global context. I still have no idea why it works with the dynamic libs but I guess a redesign of my code is in order. Here's the thread if you're interested:

https://en.sfml-dev.org/forums/index.php?topic=12380.0

Thanks for you help!