"Multiple definition of 'gridLayout'"
I'm just starting out in C++ (coded a lot in Java and some hobby stuff in PHP) and I just ran into this weird problem:
I have 2 classes, MainWindow (QMainWindow) & PokerTableInfo (QWidget). The layout for both of them uses a gridLayout. The MainWindow consists of a label and multiple instances of PokerTableInfo (so I got an #include PokerTableInfo.h in MainWindow). Now, so far so good, everything actually worked fine, but then I started cleaning up some code (MainWindow originally had multiple inheritance and it was unnecessary & made things ugly). In the declaration of both classes I have:
Now, for some reason the linker is telling me that there's multiple definitions of gridLayout. I don't quite get this... Sure, the variables have the same type & name, but they're both in a completely different class (and private on top of that as well, not that it should matter). I have a MainWindow.gridLayout and a MainWindow.PokerTableInfoInstance.gridLayout, how and where does this become a problem?
I'm used to working in Java and I never encountered something weird like that even though I use the same variable name for general stuff all the time (String lblName, etc.,...). So, can anyone explain to me why I'm getting this error and how to fix it? (Apart from the obvious renaming of the variable.)
Re: "Multiple definition of 'gridLayout'"
Quote:
telling me that there's multiple definitions of gridLayout.
It should also tell you where the previous deceleration is.
Are you headers protected with #ifdef??
Re: "Multiple definition of 'gridLayout'"
Yes, everything's protected with #ifndef. And indeed, it does say where it's defined previously, it's just that I can't make sense of it. The errors point to 2 private pointers with the same name inside 2 different classes. Like this:
Code:
{
...
private:
...
};
{
...
private:
...
};
I really don't get what I'm doing wrong. There's a Q_OBJECT macro in both the class definitions, maybe it's that? The explanation in the help files on what it does exactly is really vague, so I'm not sure. I does say that it has to be there though, so I can't really delete it.
Re: "Multiple definition of 'gridLayout'"
Its really hard to tell like that.
Such errors are coding errors, and with out the relevant code, its almost impossible to tell where the problem is.
If its a small project, zip and post it, so that we can try and compile it, or post all the relevant code, if it not too much.
1 Attachment(s)
Re: "Multiple definition of 'gridLayout'"
Ok, well, the code that's giving errors isn't too big, so I'll post it here. Note that these are just the header files, the .cpp's are included in the attached zip file.
PokerInfoTable.h
Code:
#include <Qt stuff here (multiple lines)>
#include <string>
#include <vector>
class PokerTableInfo
: public QWidget{
Q_OBJECT
public:
PokerTableInfo
(QWidget *parent
= 0);
~PokerTableInfo();
void setTableName(std::string *tableName);
std::string *getTableName();
void setFolded();
void newRound();
void setNumPlayers(int numPlayers);
void setProfit(double *dProfit);
void setHandFlavorText(std::string *sFlavor);
void addHandCard(char rank, char suit);
void addBoardCard(char rank, char suit);
private:
bool folded;
std::vector<char> handCardsRank;
std::vector<char> handCardsSuit;
std::vector<char> boardCardsRank;
std::vector<char> boardCardsSuit;
std::string *tableName;
void setupUi();
void resetHandCards();
void resetBoardCards();
void setHandText();
void setBoardText();
static bool isLegalRank(char rank);
static bool isLegalSuit(char suit);
static void getCardText
(std
::vector<char>
*rank, std
::vector<char>
*suit,
QString *cardText
);
};
MainWindow.h
Code:
#include <QtGui/QWidget>
#include <vector>
#include "PokerTableInfo.h"
{
Q_OBJECT
public:
~MainWindow();
std::vector<PokerTableInfo*> getPokerTables();
void addPokerTable();
void removePokerTable(int tableNr);
private:
std::vector<PokerTableInfo*> pokerTables;
void autoResize(int numPokerTables);
void autoRearange();
void setNewSize(int width, int height);
void setupUi();
PokerTableInfo *pokerTableInfo;
};
The error says gridLayout is already defined in MainWindow.h (4th line from the bottom) and it's being redefined in PokerInfoTable.h (3rd line after private declarations start).
In case you want to see for yourself, I made a minimalist project that still gives exactly the same error, just run compile.bat in the attached zip file.
Re: "Multiple definition of 'gridLayout'"
What are these variables for in PokerTableInfo.cpp?
Re: "Multiple definition of 'gridLayout'"
They are the elements composing the PokerTableInfo widget. I originally made it in Designer, compiled the .ui file and then just took the parts I needed for Ui_PokerInfoTable.h and put them in the PokerTableInfo class (so that I didn't have to let it inherit Ui_PokerInfoTable). It works fine if I change the name of the gridLayout variable to gridLayout1.
Re: "Multiple definition of 'gridLayout'"
Quote:
Originally Posted by
Darhuuk
I originally made it in Designer, compiled the .ui file and then just took the parts I needed for Ui_PokerInfoTable.h and put them in the PokerTableInfo class
These variables are global, they don't belong to any class.
Quote:
Originally Posted by
Darhuuk
so that I didn't have to let it inherit Ui_PokerInfoTable
You don't have to inherit from Ui:xxx classes to use them. You can use aggregation instead. With your approach you have lost possibility to change the layout with Designer.
Quote:
Originally Posted by
Darhuuk
It works fine if I change the name of the gridLayout variable to gridLayout1.
That's because you never use those variables.
Re: "Multiple definition of 'gridLayout'"
Quote:
Originally Posted by
jacek
These variables are global, they don't belong to any class.
Ah, I finally get it now. I thought I had to redeclare the variables declared in the header file in the .cpp file. Beginner's mistake I guess :). Thanks for helping me realize.
Quote:
Originally Posted by
jacek
You don't have to inherit from Ui:xxx classes to use them. You can use aggregation instead. With your approach you have lost possibility to change the layout with Designer.
Hm, yes, true, I'm aware of that. It's just that I found it cleaner this way, otherwise every time I wanted to change something in the widget during runtime I would have had to reference to the aggregated class (Ok, only a little bit more typing, but meh). And it's a very small design, I could have made it by hand. If it were big with tons of widgets in it, I would have kept it as it originally was so that I could still edit it in Designer.
Thanks again, stupid C++ newbie problem #10000 solved :)!
Re: "Multiple definition of 'gridLayout'"
Quote:
Originally Posted by
Darhuuk
I thought I had to redeclare the variables declared in the header file in the .cpp file.
You have to do this only for static variables.
Re: "Multiple definition of 'gridLayout'"
Quote:
Originally Posted by
jacek
You have to do this only for static variables.
Oh, ok, thanks!