So I've had a lot of trouble with Cocos2d's auto-release shenanigans, and (almost) wish that I could just handle all of that myself...
Anyways, the problem I've had is with creating some animations. I've got a class called AnimatedDamageableSprite which inherits from DamageableSprite which inherits from Sprite which inherits from CCSprite etc...
When I create an AnimatedDamageableSprite, I have a successful animation on the screen, which runs as it should.
When I create a Suicider, which (you guessed it) inherits from AnimatedDamageableSprite, the CCArray which contains the frames for animation doesn't survive beyond the first loop, and on the second update attempt, the program gets an AV error.
Here's the code for the two classes:
Sprite.h
// This class works
class AnimatedDamageableSprite :public DamageableSprite {
public:
AnimatedDamageableSprite(int hp, CCPoint pos, CCTexture2D* tex, int rows, int columns, float scaleX, float scaleY);
virtual ~AnimatedDamageableSprite();
virtual void update(float dt);
virtual bool updateFrame(float dt);
virtual SpriteType getType() { return ANIMATED_DAMAGEABLE_SPRITE; };
protected:
float m_frameNum;
CCArray* m_frames;
int m_numOfFrames;
};
// This class doesn't
class Suicider :public AnimatedDamageableSprite {
public:
Suicider(int difficulty);
virtual ~Suicider();
virtual void update(float dt);
virtual SpriteType getType() { return SUICIDER; };
private:
float m_speed;
};
Sprite.cpp
AnimatedDamageableSprite::AnimatedDamageableSprite(int hp, CCPoint pos, CCTexture2D* tex, int rows, int columns, float scaleX, float scaleY)
:DamageableSprite(hp, pos, tex, scaleX, scaleY), m_frameNum(0), m_numOfFrames(rows*columns) {
float texWidth = tex->getContentSize().width / (float)columns;
float texHeight = tex->getContentSize().height / (float)rows;
m_frames = CCArray::createWithCapacity(m_numOfFrames);
m_frames->retain();
for (unsigned int i = 0; i < columns; i++) {
for (unsigned int j = 0; j < rows; j++) {
CCRect r(i*texWidth, j*texHeight, texWidth, texHeight);
m_frames->addObject(new CCSpriteFrame);
((CCSpriteFrame*)m_frames->lastObject())->createWithTexture(tex, r);
((CCSpriteFrame*)m_frames->lastObject())->initWithTexture(tex, r);
m_frames->lastObject()->retain();
}
}
initWithSpriteFrame((CCSpriteFrame*)m_frames->objectAtIndex(m_frameNum));
setTexture(tex);
setPosition(pos);
setScaleX(scaleX);
setScaleY(scaleY);
updateTransform();
}
// This function is called every frame. It returns a boolean for unrelated reasons
bool AnimatedDamageableSprite::updateFrame(float dt) {
bool retVal = false;
// Assume animations are at 30 FPS for now
m_frameNum += dt * 0.03f;
while (m_frameNum >= m_numOfFrames) {
m_frameNum -= m_numOfFrames;
retVal = true;
}
setDisplayFrame((CCSpriteFrame*)m_frames->objectAtIndex(m_frameNum));
updateTransform();
return retVal;
}
// This class calls the constructor of the one that works, and does nothing else relevant to the problem
// It also doesn't override the updateImage() function
Suicider::Suicider(int difficulty)
: AnimatedDamageableSprite(1, CCPoint(10,10), g_textureManager.getTexture("Suicider Sheet"), 6, 10, SCALE_WIDTH, SCALE_HEIGHT) {
// ...
}
EDIT:
Seems I forgot to actually point out the problem.
The CCArray* m_frames declared in AnimatedDamageableSprite is fine when used in that instance, but it is deleted at the end of a frame when used in the Suicider class - i.e. it isn't being retained. Hence the AV error when I try to access an item inside it which no-longer exists
I tried retaining it in the Suicider constructor as well, although that didn't change anything.
Related
I am trying to load a bitmap animation to the screen. I have a float variable holdTime that is specified to hold the "holdtime" value for the animation. In my constructor I set the holdtimevariable to 0.1f but when I try to access the method in the class that is using the holdTime variable, the value of holdTime has changed to -107374176f. So somewhere between my constructor call and the method call the value has changed from 0.1f to -107374176f.
To make things a little bit more clearer let me show you some code:
Here is the header file for the Game class, this is where I call the constructor of the Animation class that has the holdTime variable.
#pragma once
#include "Graphics.h"
#include "Surface.h"
#include "Animation.h"
#include "FrameTimer.h"
class Game
{
public:
Game( class MainWindow& wnd );
void Go();
private:
void UpdateModel();
private:
MainWindow& wnd;
FrameTimer ft;
Surface surf = Surface("Test32x48.bmp");
Animation testAnimation = Animation(0, 0, 32, 48, 4, surf, 0.1f);
};
You see that I have this testAnimation at the bottom of the class. The last argument in the constructor call is the value that is ought be in holdTime.
This is how my Animation header file looks like:
#include "Surface.h"
#include "Graphics.h"
#include <vector>
class Animation {
public:
Animation(int x, int y, int width, int height, int count, const Surface& sprite, float holdtime, Color chroma = Colors::Magenta);
void Update(float dt);
private:
void Advance();
private:
std::vector<RectI> frames;
int iCurFrame = 0;
float holdTime = 0;
float curFrameTime = 0.0f;
};
And this is the Animation Cpp file:
#include "Animation.h"
Animation::Animation(int x, int y, int width, int height, int count,
const Surface& sprite, float holdtime, Color chroma)
:
sprite(sprite),
holdTime(holdTime),
chroma(chroma)
{
for (int i = 0; i < count; i++)
{
frames.emplace_back(x + i * width, x + (i + 1) * width,y, y + height);
}
}
void Animation::Update(float dt)
{
curFrameTime += dt;
while(curFrameTime >= holdTime) {
Advance();
curFrameTime -= holdTime;
}
}
void Animation::Advance()
{
if (++iCurFrame >= frames.size()) {
iCurFrame = 0;
}
}
There is only one method that is making use of holdTime and that is the method Update(float dt).
If we go back to the Game class and look at the Game.cpp file:
#include "MainWindow.h"
#include "Game.h"
Game::Game( MainWindow& wnd )
:
wnd( wnd ),
gfx( wnd )
{
}
void Game::Go()
{
UpdateModel();
}
void Game::UpdateModel()
{
testAnimation.Update(ft.Mark());
}
In the Method Go() we call the method UpdateModel() which in turn is calling the Update() method in the animation class. This means that the first method to be executed in the Animation class after the constructor call is the update() method. When I debug the program I can see that the value of holdtime has changed between the constructor call and the Update() method call. But I don't know how since it I am not modifying the value somewhere else. It also seemes that the new value of holdTime is garbage value.
It became a lot of code in this question and it looks a bit messy and even though I lack the skills of writing a good Title I hope I made you somewhat clear what my problem is.
Thanks!
Update:
Here is the code for the FrameTimer class since the value returned from one of its methods is passed in into the Update() method:
FrameTimer.H:
#pragma once
#include <chrono>
class FrameTimer
{
public:
FrameTimer();
float Mark();
private:
std::chrono::steady_clock::time_point last;
};
FrameTimer.cpp:
#include "FrameTimer.h"
using namespace std::chrono;
FrameTimer::FrameTimer()
{
last = steady_clock::now();
}
float FrameTimer::Mark()
{
const auto old = last;
last = steady_clock::now();
const duration<float> frameTime = last - old;
return frameTime.count();
}
Edit:
main.cpp:
int WINAPI wWinMain( HINSTANCE hInst,HINSTANCE,LPWSTR pArgs,INT )
{
MainWindow wnd( hInst,pArgs );
Game game( wnd );
while( wnd.ProcessMessage() )
{
game.Go();
}
}
As you can see the game.Go() method is the first method that is called in main.
Your Animation constructor is at fault:
Animation::Animation(int x, int y, int width, int height, int count,
const Surface& sprite, float holdtime, Color chroma)
:
sprite(sprite),
holdTime(holdTime),
chroma(chroma)
{
for (int i = 0; i < count; i++)
{
frames.emplace_back(x + i * width, x + (i + 1) * width,y, y + height);
}
}
Here you attempt to initialise the member holdTime from the parameter holdTime.
Except, there is no parameter holdTime. There is only the parameter holdtime.
Hence instead you are actually initialising the member holdTime from itself (the next nearest "match" for that name), so it only retains its original, unspecified value (and in fact, reading an uninitialised variable results in your program having undefined behaviour).
So, you see, your member variable doesn't "change" at all — you never set it correctly. You'd have known that had you put some diagnostic output inside that constructor to examine the value and see whether it's what you thought it should be. None of the rest of the code was relevant or necessary.
A properly-configured compiler should have warned you about this.
I have a Rectangle class shown below:
Header:
class Rectangle: public Polygon {
private:
float _width, _height;
public:
Rectangle(float width, float height);
float getWidth(float* width) const;
float getHeight(float* height) const;
bool isCollidingWith(Rectangle* other) const;
};
Selected Implementation:
Rectangle::Rectangle(float width, float height) : Polygon(explodeRect(width, height, new struct vertex[4]), 4) {
printf("creating rect %f x %f\n", width, height);
_width = width;
_height = height;
printf("set _width to %f\n", _width);
}
float Rectangle::getWidth(float* width) const {
printf("_w: %f\n", _width);
*width = _width;
return *width;
//return (*width = _width);
}
float Rectangle::getHeight(float* height) const {
return (*height = _height);
}
I initialize an instance of the Rectangle class, and the output indicates that the _width variable is being correctly assigned. However, when I later try to read the variable using the getWidth method, I get an EXC_BAD_ACCESS error on the line:
printf("_w: %f\n", _width);
Why can I no longer read this variable? I get the same problem with the _height variable as well.
EDIT: I would also like to note that if I skip reading the width, I get an error trying to read public variables directly from the object, e.g. when I try to read its x position with obj->x.
EDIT 2: Could this be from the fact that the object is an instance of a subclass of Rectangle, and this subclass is defined in a different file than Rectangle is? I am also reading the values from a third file.
EDIT 3: More code below.
I am trying to re-create Tetris with OpenGL. In my display method, I have this code to draw the rectangles:
if(fallingBlock != nullptr) {
printf("drawing falling block at (%f, %f)\n", fallingBlock->x, fallingBlock->y);
draw(fallingBlock);
}
fallingBlock is defined as a global variable at the top of my file:
Block* fallingBlock;
From my main, I call an initVars method that subsequently calls a startDroppingBlock method. Here it is:
void startDroppingBlock() {
Block* block = availableBlocks[random() % numAvailableBlocks].copy();
block->x = 0.5;
block->y = SCREEN_TOP;
block->dy = -0.01f;
//printf("copied block is at (%f, %f)\n", block->x, block->y);
fallingBlock = block;
}
And here is my block drawing method:
void draw(Block* obj) {
bool shape[3][3];
obj->getShape(shape);
//printf("got shape: {%d, %d, %d}, {%d, %d, %d}, {%d, %d, %d}\n", shape[0][0], shape[0][1], shape[0][2], shape[1][0], shape[1][1], shape[1][2], shape[2][0], shape[2][1], shape[2][2]);
/*float pieceWidth;
obj->getWidth(&pieceWidth);
pieceWidth /= 3.0f;*/
float pieceWidth = obj->getWidth();
for(unsigned int i=0; i<3; i++) {
for(unsigned int j=0; j<3; j++) {
if(shape[i][j]) {
Square rect = Square(pieceWidth);
rect.x = obj->x + pieceWidth * j;
rect.y = obj->y + pieceWidth * i;
rect.color = obj->color;
draw(&rect);
}
}
}
}
I get an EXC_BAD_ACCESS error on the line [...]. Why can I no longer read this variable? I get the same problem with the _height variable as well. [later...] I have tried both float pieceWidth; obj->getWidth(&pieceWidth); and obj->getWidth(new float) - the actual error is on the line where I read _width, before I even use the passed in pointer. [later...] I modified the getWidth and getHeight methods to just simply return _width and _height. Now I just get an error on return _width;
In this case I see you are using a Rectangle* pointer as obj->getWidth which can as well lead to a bad access error if obj is not a valid pointer.
It is to note that I don't quite understand your getter method at all. A simplified (and possibly standard) version of it might be:
float Rectangle::getWidth() const {
return _width;
}
With the only difference that when you used:
// float a;
// float b;
a = rect.getWidth(&b);
you can now do:
// float a;
// float b;
a = b = rect.getWidth();
which is possibly cleaner and will surely don't cause such an error. A good rule of thumb is never to use pointers when possible. If you need to modify a variable inside a function just use a reference.
new here, so be gentle, I'm currently doing my Major Project for my course and, I'm not asking for homework to be done for me, i just can't wrap my head around a strange problem i am having and have not been able to find an answer for it, even on here. I'm using SDL for my Drawing.
I'm doing Object Orientated Programming with my Project or a "state Machine" (which sounds less painful in a newbies mind, believe me), and in the render part of my Class Game1.cpp i am trying to call a Draw Function of my Player Class, but for some unknown reason that i can not fathom, it just skips this function call completely.
I have no errors, i even used breakpoints to find out what was happening, but it just skipped it completely every time, it is drawing the screen black as well without fail. Any help as t why it is skipping this would be really appreciated.
I honestly feel like it's a simple rookie mistake, but any and all scrutiny is welcome of my code, anything i can do to better myself is appreciated.
Game1.cpp:
#include "Game1.h"
#include "PlayerCharacter.h"
Game1::Game1( World * worldObject )
{
//object setup
this->worldObject = worldObject;
setDone (false);
}
Game1::~Game1()
{
}
void Game1::handle_events()
{
//*******************************************
//**//////////////Call Input///////////////**
//*******************************************
//******Check for Keyboard Input*************
//******Check Keyboard Logic*****************
//******Check for Mouse Input****************
//The mouse offsets
x = 0, y = 0;
//If the mouse moved
if (SDL_PollEvent(&worldObject->event))
{
if( worldObject->event.type == SDL_MOUSEMOTION )
{
//Get the mouse offsets
x = worldObject->event.motion.x;
y = worldObject->event.motion.y;
}
}
//******Check Mouse Logic********************
}
void Game1::logic()
{
//*******************************************
//**//////////Collision Detection//////////**
//*******************************************
//******Check Player Bullet Collision Loop***
//Check for collision with enemies
//Check for collision with bitmap mask (walls)
//******Check Enemy Bullet Collision Loop****
//Check for Collision with Player
//Check for collision with bitmap mask (walls)
}
void Game1::render()
{
//*******************************************
//**////////////////Drawing////////////////**
//*******************************************
//******Blit Black Background****************
SDL_FillRect(worldObject->Screen , NULL , 0xff000000);
//******Blit Bitmap Mask*********************
//******Blit Flashlight**********************
//******Blit Map*****************************
//******Blit Pickups*************************
//******Blit Bullets*************************
//******Blit Player**************************
&PlayerCharacter.Draw; // <----- Skips this line completely, no idea why
//******Blit Enemies*************************
//******Blit Blackened Overlay***************
//******Blit HUD*****************************
//******Flip Screen**************************
SDL_Flip(worldObject->Screen);
}
Game1.h
#ifndef __Game1_H_INLUDED__
#define __Game1_H_INLUDED__
#include "GameState.h"
#include "SDL.h"
#include "ImageLoader.h"
using namespace IMGLoader;
class Game1 : public GameState
{
private:
//Menu Image
World * worldObject;
SDL_Rect PauseMenu,Item1Tile,Item2Tile,Item3Tile;
/*bool bPauseMenu, bItem1Tile, bItem2Tile, bItem3Tile;
int ButtonSpace,ButtonSize;
float x,y;
int Alpha1,Alpha2;*/
//Clipping Window
//SDL_Rect sclip,dclip;
public:
//Loads Menu resources
Game1 (World * worldObject);
//Frees Menu resources
~Game1();
//Main loop functions
void handle_events();
void logic();
void render();
};
#endif
PlayerCharacter.cpp
#include "PlayerCharacter.h"
SDL_Rect psclip,pdclip;
PlayerCharacter::PlayerCharacter ( float X, float Y, float dX, float dY, float Angle, float Speed, bool Existance, int Height, int Width, int Health, int Shield, SDL_Surface* Player ):Characters ( X, Y, dX, dY, Angle, Speed, Existance, Height, Width, Health )
{
this->Player = Player;
this->Shield = Shield;
this->Player = load_image("image\Player1.png");
}
void PlayerCharacter::setShield ( int Shield )
{
this->Shield = Shield;
}
int PlayerCharacter::getShield ( void )
{
return Shield;
}
void PlayerCharacter::Draw( )
{
psclip.x = 0; psclip.y = 0; psclip.w = 64; psclip.h = 64;
pdclip.x = 640; pdclip.y = 318; pdclip.w = 64; pdclip.h = 64;
SDL_BlitSurface(Player, &psclip, worldObject->Screen, &pdclip);
}
PlayerCharacter.h
#ifndef __PlayerCharacter_H_INCLUDED__
#define __PlayerCharacter_H_INCLUDED__
#include "Characters.h"
class PlayerCharacter : public Characters
{
private:
int Shield;
SDL_Surface* Player;
World *worldObject;
public:
PlayerCharacter ( float X, float Y, float dX, float dY, float Angle, float Speed, bool Existance, int Height, int Width, int Health, int Shield, SDL_Surface* Player );
void setShield ( int Shield );
int getShield ( void );
void Draw ( );
};
#endif
The line
&PlayerCharacter.Draw; // <----- Skips this line completely, no idea why
is not actually a function call. It's an expression that take the address of the Draw function in the PlayerCharacter class and does nothing with it.
I'm actually kind of surprised it compiles without errors, or at least tons of warnings.
You need to create a PlayerCharacter object, and then call the function in the object.
&PlayerCharacter.Draw is not a function call. PlayerCharacter::Draw() is not a static class method, so you need a PlayerCharacter object to invoke this method on.
You have a class PlayerCharacter, which defines what a PlayerCharacter is and what can be done with it. But as far as I see, you don't have a single PlayerCharacter object, i.e. no player character. If you had one, let's call him pc, then you could draw him with pc.Draw(). For that, you would have to instantiate the class, e.g. via PlayerCharacter pc( ... ), with the ... replaced by some appropriate values for the multitude of constructor parameters you have there. (You really want a default constructor, initializing all those to zero or other appropriate "start" value...)
So I was working on my code, which is designed in a modular way. Now, one of my classes; called Splash has to create a object of another class which is called Emitter. Normally you would just create the object and be done with it, but that doesn't work here, as the Emitter class has a custom constructor. But when I try to create an object, it doesn't work.
As an example;
Emitter has a constructor like so: Emitter::Emitter(int x, int y, int amount); and needs to be created so it can be accessed in the Splash class.
I tried to do this, but it didn't work:
class Splash{
private:
Emitter ps(100, 200, 400, "firstimage.png", "secondimage.png"); // Try to create object, doesn't work.
public:
// Other splash class functions.
}
I also tried this, which didn't work either:
class Splash{
private:
Emitter ps; // Try to create object, doesn't work.
public:
Splash() : ps(100, 200, 400, "firstimage.png", "secondimage.png")
{};
}
Edit: I know the second way is supposed to work, however it doesn't. If I remove the Emitter Section, the code works. but when I do it the second way, no window opens, no application is executed.
So how can I create my Emitter object for use in Splash?
Edit:
Here is my code for the emitter class and header:
Header
// Particle engine for the project
#ifndef _PARTICLE_H_
#define _PARTICLE_H_
#include <vector>
#include <string>
#include "SDL/SDL.h"
#include "SDL/SDL_image.h"
#include "image.h"
extern SDL_Surface* gameScreen;
class Particle{
private: // Particle settings
int x, y;
int lifetime;
private: // Particle surface that shall be applied
SDL_Surface* particleScreen;
public: // Constructor and destructor
Particle(int xA, int yA, string particleSprite);
~Particle(){};
public: // Various functions
void show();
bool isDead();
};
class Emitter{
private: // Emitter settings
int x, y;
int xVel, yVel;
private: // The particles for a dot
vector<Particle> particles;
SDL_Surface* emitterScreen;
string particleImg;
public: // Constructor and destructor
Emitter(int amount, int x, int y, string particleImage, string emitterImage);
~Emitter();
public: // Helper functions
void move();
void show();
void showParticles();
};
#endif
and here is the emitter functions:
#include "particle.h"
// The particle class stuff
Particle::Particle(int xA, int yA, string particleSprite){
// Draw the particle in a random location about the emitter within 25 pixels
x = xA - 5 + (rand() % 25);
y = yA - 5 + (rand() % 25);
lifetime = rand() % 6;
particleScreen = Image::loadImage(particleSprite);
}
void Particle::show(){
// Apply surface and age particle
Image::applySurface(x, y, particleScreen, gameScreen);
++lifetime;
}
bool Particle::isDead(){
if(lifetime > 11)
return true;
return false;
}
// The emitter class stuff
Emitter::Emitter(int amount, int x, int y, string particleImage, string emitterImage){
// Seed the time for random emitter
srand(SDL_GetTicks());
// Set up the variables and create the particles
x = y = xVel = yVel = 0;
particles.resize(amount, Particle(x, y, particleImage));
emitterScreen = Image::loadImage(emitterImage);
particleImg = particleImage;
}
Emitter::~Emitter(){
particles.clear();
}
void Emitter::move(){
}
void Emitter::show(){
// Show the dot image.
Image::applySurface(x, y, emitterScreen, gameScreen);
}
void Emitter::showParticles(){
// Go through all the particles
for(vector<Particle>::size_type i = 0; i != particles.size(); i++){
if(particles[i].isDead() == true){
particles.erase(particles.begin() + i);
particles.insert(particles.begin() + i, Particle(x, y, particleImg));
}
}
// And show all the particles
for(vector<Particle>::size_type i = 0; i != particles.size(); i++){
particles[i].show();
}
}
Also here is the Splash Class and the Splash Header.
The second option should work, and I would start looking at compilation errors to see why it doesn't. In fact, please post any compilation errors you have related to this code.
In the meantime, you can do something like this:
class Splash{
private:
Emitter* ps;
public:
Splash() { ps = new Emitter(100,200,400); }
Splash(const Splash& copy_from_me) { //you are now responsible for this }
Splash & operator= (const Splash & other) { //you are now responsible for this}
~Splash() { delete ps; }
};
Well, I managed to fix it, in a hackish way though. What I did was create a default constructor, and move my normal Constructor code into a new function. Then I created the object and called the the new init function to set everything up.
I'm researching UI's as a portfolio project and I ran into a little bit of trouble when it comes to inheritance. The problem I'm facing is this: I have two classes, R_GUI, in which I draw the form, and Button, where I draw the buttons. I want the Buttons to be positioned inside the FORM. I store the FORM position as form_x, and form_y. Here are my two classes:
class R_GUI
{
private:
bool get_pos_only_once;
bool move_form;
public:
int form_x, form_y;
int form_height, form_width;
int handle_bar_y;
inline void Form(int pos_x, int pos_y, int height, int width);
//inline void Button(int id, string ButtonText, int pos_x, int pos_y);
inline void Update_form(void);
inline void UPDATE(void);
inline ~R_GUI( );
inline R_GUI( )
{
d3dInit();
get_pos_only_once = false;
move_form = false;
form_x = 0;
form_y = 0;
handle_bar_y = 40;
}
};
and the Button class:
class Button: public R_GUI
{
private:
int b_form_x, b_form_y;
int b_handle_y;
int button_width, button_height;
public:
inline void Draw(string ButtonText, int b_pos_x, int b_pos_y);
Button()
{
b_form_x = R_GUI::form_x;
b_form_y = R_GUI::form_y;
b_handle_y = 20;
button_width = 90;
button_height = 35;
}
~Button();
};
As you can see, I'm trying to give b_form_x the value of form_x (which is a variable from R_GUI). form_x has a value, given in Form( );:
inline void R_GUI::Form(int pos_x, int pos_y, int height, int width)
{
if(get_pos_only_once == false)
{
form_x = pos_x;
form_y = pos_y;
form_height = height;
form_width = width;
get_pos_only_once = true;
}
//Create the form outline
d3dLine(pos_x,pos_y,pos_x+width,pos_y,dbRGB(50,50,50));
d3dLine(pos_x,pos_y,pos_x,pos_y+height,dbRGB(50,50,50));
d3dLine(pos_x+width,pos_y,pos_x+width,pos_y+height,dbRGB(50,50,50));
d3dLine(pos_x,pos_y+height,pos_x+width,pos_y+height,dbRGB(50,50,50));
//Create the handle bar
d3dLine(pos_x,pos_y+handle_bar_y,pos_x+width,pos_y+handle_bar_y,dbRGB(50,50,50));
//Fill the Handlebar;
d3dBox(pos_x,pos_y,pos_x+width,pos_y+handle_bar_y,dbRGB(3,3,3),dbRGB(3,3,3),dbRGB(3,3,3),dbRGB(3,3,3));
}
Yet, when I update the Form's Position, R_GUI::form_x value doesn't change. Any idea what I am doing wrong?
You don't want to have a second variable in your subclass (b_form_x). Eliminate it entirely. Instead, you want to use this->form_x, which in the Button will be inherited from R_GUI. The same applies for b_form_y.
this refers to the current instance of an object, and contains not only your local member variables but also any member variables inherited from classes all the way up the hierarchy as well.