|
-
February 7th, 2008, 12:11 PM
#1
Problems with Absract Classes
I have a two classes one is abstract and another is inherited
Code:
// this is part of CGUI.h
class CGUI
{
public:
//other stuff
virtual void Init() = 0;
virtual void Paint() = 0;
};
Code:
//this is part of LoadScreen.h
#include "CGUI.h"
class LoadScreen : public CGUI
{
public:
virtual void Init();
virtual void Paint();
}
now in my definition of those classes I get problems
Code:
//this is part of LoadScreen.cpp
#include "LoadScreen.h"
void LoadScreen::Paint()
{
//stuff
}
void LoadScreen::Init()
{
//stuff
}
when I do this I get 2 errors
error LNK2001: unresolved external symbol "public virtual void __thiscall CGUI::Paint(void)" (?Paint@CGUI@@UAEXXZ)
error LNK2001: unresolved external symbol "public virtual void __thiscall CGUI::Init(void)" (?Init@CGUI@@UAEXXZ)
fatal error LNK1120: 2 unresolved externals
KTNXBYE
-
February 7th, 2008, 12:17 PM
#2
Re: Problems with Absract Classes
Based on the limited information you posted (which is obviously not enough to reproduce the problem), everything looks good. What Compiler (including version) are you using???
TheCPUWizard is a registered trademark, all rights reserved. (If this post was helpful, please RATE it!)
2008, 2009,2010
In theory, there is no difference between theory and practice; in practice there is.
* Join the fight, refuse to respond to posts that contain code outside of [code] ... [/code] tags. See here for instructions 
* How NOT to post a question here
* Of course you read this carefully before you posted
* Need homework help? Read this first
-
February 7th, 2008, 12:32 PM
#3
Re: Problems with Absract Classes
Not entirely certain how important it is, since it has been a while for abstract classes for me, but I do notice that you don't have a semicolon on the end of your Loadscreen.h
-
February 7th, 2008, 01:38 PM
#4
Re: Problems with Absract Classes
I'll post the whole header file if that makes a difference. I'm using Visual Studio 2005.
Code:
#ifndef LOADSCREEN_H
#define LOADSCREEN_H
#include "CGUI.h"
class CGUI;
class LoadScreen: public CGUI
{
public:
virtual void Init();
virtual void Paint();
///constructor
LoadScreen();
//destructor
~LoadScreen();
};
#endif LOADSCREEN_H
Code:
#ifndef CGUI_H
#define CGUI_H
#include "CommonInclude.h"
#include "EventReciver.h"
#define DO_NOT_EXIT -1
#define WINDOW_HEIGHT 640
#define WINDOW_WIDTH 480
class EventReciver;
class CGUI
{
public:
//variables
IrrlichtDevice* m_Device;
EventReciver* m_EventReciver;
s32 m_ExitCode;
//functions
virtual void Init() = 0;
virtual void Paint() = 0;
void Exit(s32 exitCode);
//constructor
CGUI();
//destructor
~CGUI();
};
#endif CGUI_H
Code:
//this is LoadScreen.cpp
#include "LoadScreen.h"
LoadScreen::~LoadScreen()
{
}
void onPlay(SEvent event, CGUI* source)
{
//stuff
}
void onOption(SEvent event, CGUI* source)
{
//stuff
}
void onHelp(SEvent event, CGUI* source)
{
//stuff
}
void onExit(SEvent event, CGUI* source)
{
//stuff
}
LoadScreen::LoadScreen()
{
}
void LoadScreen::Paint()
{
//stuff
}
void LoadScreen::Init()
{
// stuff
}
I can always post more code if necessay, but I don't think you all want to spend all day reading through everything. I thought I had everything necessary in the first post. But it is odd because I am using the open source Irrlicht Graphics Engine and it defines a class IEventReciver which is abstract and I overwrite it with EventReciver, but that doesn't seem to cause a problem when I implement its pure virtual functions.
KTNXBYE
-
February 7th, 2008, 01:53 PM
#5
Re: Problems with Absract Classes
I just skimmed through your code, but I noticed that you never defined (or at least, never showed us that you did) CGUI's constructor and destructor.
-
February 7th, 2008, 01:58 PM
#6
Re: Problems with Absract Classes
I suggest that you simplify to:
Code:
#ifndef LOADSCREEN_H
#define LOADSCREEN_H
#include "CGUI.h"
class LoadScreen : public CGUI
{
public:
virtual void Init();
virtual void Paint();
///constructor
LoadScreen();
//destructor
~LoadScreen();
};
#endif
Code:
#ifndef CGUI_H
#define CGUI_H
class CGUI
{
public:
virtual void Init() = 0;
virtual void Paint() = 0;
//destructor
virtual ~CGUI() {}
};
#endif
Code:
//this is LoadScreen.cpp
#include "LoadScreen.h"
LoadScreen::~LoadScreen()
{
}
LoadScreen::LoadScreen()
{
}
void LoadScreen::Paint()
{
}
void LoadScreen::Init()
{
}
Then test with:
Code:
#include <memory>
#include "CGUI.h"
#include "LoadScreen.h"
int main()
{
LoadScreen screen;
screen.Paint();
screen.Init();
std::auto_ptr<CGUI> gui(new LoadScreen);
gui->Paint();
gui->Init();
}
Note that CGUI's destructor should be declared virtual since it is a base class.
Last edited by laserlight; February 7th, 2008 at 02:01 PM.
-
February 8th, 2008, 12:43 AM
#7
Re: Problems with Absract Classes
I got the link errors to go away by adding a body for the two virtual functions. Now I don't want to use the Paint and Init functions I defined right there. I want to use the init and paint functions I define in the derived class. When I take away those lines I get the linker errors
Code:
#include "CGUI.h"
CGUI::~CGUI()
{
this->Exit(0);
}
CGUI::CGUI()
{
m_ExitCode = DO_NOT_EXIT;
m_EventReciver = new EventReciver();
m_Device = createDevice(video::EDT_OPENGL,core::dimension2d<s32>(WINDOW_HEIGHT,WINDOW_WIDTH),16,false,true,true,m_EventReciver);
if(m_Device == 0)
{
printf("\nFatal Error: Device could not be created\n");
this->Exit(1);
}
else{
video::IVideoDriver* driver = m_Device->getVideoDriver();
gui::IGUIEnvironment* env = m_Device->getGUIEnvironment();
Init();
while(m_Device->run() && driver)
{
if(m_ExitCode != DO_NOT_EXIT)
{
break;
}
else if (m_Device->isWindowActive())
{
driver->beginScene(true, true,video::SColor(255,255,255,255));
Paint();
driver->endScene();
}
}
}
}
void CGUI::Exit(s32 exitCode)
{
m_ExitCode = exitCode;
}
void CGUI::Paint(){}
void CGUI::Init(){}
KTNXBYE
-
February 8th, 2008, 12:52 AM
#8
Re: Problems with Absract Classes
I got the link errors to go away by adding a body for the two virtual functions.
Have you tried out my minimal example? I did not need to turn the pure virtual functions into ordinary virtual functions, yet I did not get any linker errors when I tested.
-
February 8th, 2008, 01:05 AM
#9
Re: Problems with Absract Classes
I did try your test, however it did not work, but I just figured out why. In the constructor for CGUI I made a call to Init and Paint, however they were defined as pure virtual functions so it gave me a linker error. How can I call those functions and just get whatever the base class defines them as?
KTNXBYE
-
February 8th, 2008, 01:12 AM
#10
Re: Problems with Absract Classes
 Originally Posted by BossOfTheGame
I did try your test, however it did not work,
So the test that was posted as-is by laserlight didn't work, or it did work?
but I just figured out why. In the constructor for CGUI I made a call to Init and Paint
If they are unimplemented, you can't call them without a linker error.
Regards,
Paul McKenzie
-
February 8th, 2008, 01:14 AM
#11
Re: Problems with Absract Classes
In the constructor for CGUI I made a call to Init and Paint, however they were defined as pure virtual functions so it gave me a linker error. How can I call those functions and just get whatever the base class defines them as?
Do not call virtual functions (pure or otherwise) in constructors. They will probably not do what you expect.
Read: When my base class's constructor calls a virtual function on its this object, why doesn't my derived class's override of that virtual function get invoked?
EDIT:
Oh wait, you wanted to "just get whatever the base class defines them as". In that case obviously they cannot be pure virtual, and you will get what you expect when you call them in the base class constructor.
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|