Reputation: 249
I have found nerve wracking issue which I seem to be unable to solve.
SceneSettings::SceneSettings()
{
unsigned int w = (ConfigurationManager::GetInstance().GetWidth() >> 1) - 80;
unsigned int h = (ConfigurationManager::GetInstance().GetHeight() >> 1) - 50;
std::vector< std::string > menu_items;
menu_items.push_back("Graphic Settings");
menu_items.push_back("Sound Settings");
menu_items.push_back("Game Settings");
menu_items.push_back("Back");
Label* aux = NULL;
for ( unsigned int i = 0; i < menu_items.size(); i++ )
{
aux = new Label(menu_items[i], w, h);
items.push_back(aux);
aux = NULL;
aux = new Label(menu_items[i], w, h);
aux->SetColor(255, 0, 0);
hover_section.push_back(aux);
hover.push_back(false);
aux = NULL;
h += 25;
}
}
SceneSettings::~SceneSettings()
{
for (unsigned int i = 0; i < items.size(); i++)
{
delete items[i];
delete hover_section[i];
}
items.clear();
hover_section.clear();
}
void SceneSettings::Draw()
{
for ( unsigned int i = 0; i < items.size(); i++ )
{
if (hover[i])
hover_section[i]->Draw();
else
items[i]->Draw();
}
}
void SceneSettings::HandleEvents(SDL_Event& event)
{
switch(event.type)
{
case SDL_MOUSEMOTION :
{
int x = event.motion.x;
int y = event.motion.y;
for ( unsigned int i = 0; i < items.size(); i++ )
hover[i] = items[i]->GetIsInLabel(x, y);
} break;
}
}
Now what it does is, that first label "Graphic Settings" is not displayed. (not invisible, just plainly not visible)
items are defined as:
std::vector< Label* > items;
std::vector< Label* > hover_section;
std::vector< bool > hover;
For some reason it doesnt work, however in another scene ("main_menu") I have identical vector of labels (only captions are different) which works ok.
Now this one is more interesting that it seems. Since not only does it not display first item, but it displays 1st hover item even if mouse is completely out its range.
If I replace std::vector
for direct Label* menu_item_1
in SceneSettings header, it displays correctly. Which leads me to think its connected to std::vector
One more thing I don't quite understand is, that if I run it in debug mode and going by steps, it displays correctly, however neither watches nor call stack does show anything unusual.
Any help is appreciated.
Upvotes: 1
Views: 111
Reputation: 249
It turns out the problem was in Label
class, in which I neglected to initialize texture and buffer ids for GLSL. Adding initial values (0) to them in Label
constructor fixed the problem.
Upvotes: 1
Reputation: 409166
If you are passing SceneSettings
objects by value anywhere, either as arguments to functions or returning such objects, then you definitely need to consider your use of pointers in the vectors, or have to implement a copy-constructor and a copy-assignment operator (as told by the rule of three).
The default functions created by the compiler will only do shallow copying, i.e. it copies the vectors and the pointers, it doesn't create new pointers (deep copying). That leads to you having two objects both containing pointers to the same objects in the vectors, and if one object is destructed if will free the memory, leaving the other object with stray pointers and that will lead to undefined behavior.
Upvotes: 1