How do I create an object with sub functions in C++? - c++

I'm not very good at C++ so prepare for improper use of terms.
Basically I want to gather a bunch of functions inside a sub class of another class, so I would interface with it kinda like this:
mainWindow.add.menubar();
^- this is the part I don't know how to do
My class looks something like this at the moment:
namespace GUI {
class Window {
public:
std::string title = "Empty Title";
int show();
// Using a struct didn't work but it's what I have at the moment.
struct add {
int menubar();
};
};
}
Obviously I could simply use mainWindow.addMenubar() but it would be much nicer to add it to a subclass (sub object? I don't know, I'm more used to Javascript programming).
And yes, I'm basically creating my own GUI framework with insufficient C++ expertise, I know it's a bad idea, but it didn't stop me from modifying the Linux kernel to allow me to install Nethunter on my Samsung S4 and it's not gonna stop me now.

You can inject Window* pointer to the struct Add() constructor, something like:
namespace GUI {
class Window {
public:
std::string title = "Empty Title";
Add add; // <- NOTICE: this is an instance of struct Add
// which holds the pointer to the window you want
// to draw on
public:
Window() : add{this} {}
int show();
// Using a struct didn't work but it's what I have at the moment.
struct Add {
Window* win;
Add(Window* w) : win{w} {}
int menubar() {
// here you can use win to draw the puppy :)
}
};
};
}
and then use it like
Widow w;
w.add.menubar();
Of course, you could do more styling here (for the real world code): separate declaration from definition via .h/.cpp files, hide the data you dont want to expose with private, declare Add as a friend class etc.

For it to work, add must be a variable:
#include <string>
namespace GUI {
class Window {
public:
std::string title = "Empty Title";
int show();
// Using a struct didn't work but it's what I have at the moment.
struct Add {
int menubar();
};
Add add;
};
}

Related

Macros for creating named constructors

I am trying to play with c++ and macros for the first time. SO basically in a lecture I know where a coded value is used to distinguish different modes of an object (game_type in this case), then these objects must be created via constructors with meaningful named constructors. SO I created createSinglePlayerGame() and named constructors. Then I tried to optimize this code using macros. SO In the Game class I define the function- like macro consructor A ## operator which runs parameter replacement on the two identifiers and then concatenates the result ("token pasting).
Can you look at my code and suggest a better way of doing this, also do you see any hygiene problem that my macros may be used incorrectly,
class Game
{
public:
#define CONSTRUCTOR(name, a) static Game create_##name() { return Game(a);}
CONSTRUCTOR(Single, 0)
CONSTRUCTOR(Multiple, 2)
// named constructors
static Game createSinglePlayerGame() { return Game(0); }
static Game createMultiPlayerGame() { return Game(1); }
protected:
Game(int game_type);
};
int main()
{
Game myGame = Game::createSinglePlayerGame();
Game second = Game::create_Single();
}
A more conventional way would be:
enum class GameType {
SinglePlayer,
MultiPlayer,
};
class Game
{
public:
explicit Game(GameType type);
};
int main()
{
Game myGame(GameType::SinglePlayer);
}
This is simpler and will be less surprising for other C++ developers to read. It's also less error-prone: even your example code confuses 1 and 2 for multiplayer mode, and since you use raw integers to store it, there's no complaint from the compiler. Using enum class it will be much harder to make such mistakes.
As an alternative to John Zwincks solution, you can also use inheritance:
class Game {
protected:
Game(int game_type);
};
class SinglePlayerGame: public Game {
public:
SinglePlayerGame(): Game(0) {}
};
class MultiPlayerGame: public Game {
public:
MultiPlayerGame(): Game(1) {}
};
int main() {
SinglePlayerGame myGame;
...
}
Although I would only use this method if there were more differences in the interface between single- and multiplayer games than just the constructor.
If you want an alternative to macros you can also use templates. Templates is something that compiler "understand" and optimize.
Their syntax may be confusing at start but if you play with them you can get used to it...
// Tag types for template dispatching
struct SinglePlayer {};
struct MultiPlayer {};
// Default single player
template <typename G>
class Game {
public:
Game () { /* create default single player game */ }
};
// Specialization for multi player
template <>
class Game <MultiPlayer> {
public:
Game () { /* create multiplayer player game */}
};
int main (void) {
Game g1 = Game<SinglePlayer>();
Game g2 = Game<MultiPlayer>();
}
This approach split the class definition into 2. One for single player and one for multi player. If they share a lot of common staff and you believe that this should not be the case, you may consider to avoid the class template and use std::enable_if<> in the constructor's level.
For example:
#include <type_traits>
// Tag types for template dispatching
struct SinglePlayer{};
struct MultiPlayer{};
struct Game {
public:
template <
typename G,
std::enable_if_t<std::is_same<G, SinglePlayer>::value, int> = 0
>
Game(G) { /* create a single player game */ }
template <
typename G,
std::enable_if_t<std::is_same<G, MultiPlayer>::value, int> = 0
>
Game(G) { /* create a multi player game */ }
};
int main (void) {
Game g1 = Game(SinglePlayer{});
Game g2 = Game(MultiPlayer{});
}
Notice that there is no class template any more, only a SFINAE dispatch for the constructors. The disadvantage is the dummy pass of a SinglePlayer{} or MultiPlayer{} object to the constructor.

Best way to call a function in a class from an object in that class

Okay sorry if this is a silly question. Lets say I have a class, and i want to call a function from that class using an object inside that class to change something within the class. For example:
class Foo;
class Bar{
public:
Bar(Foo *parent): parent(parent) {}
void barClickEvent(){
parent->changeSomething(10);
}
private:
Foo * parent;
};
class Foo {
public:
Foo():bar(this), something(5) {}
void changeSomething(int x){something = x;}
private:
Bar bar;
int something;
};
I create an object of type Foo (which automatically creates an object of type Bar). In order to all Bar to access the functions in Foo, I pass a pointer to Bar pointing to Foo(its parent). Is this the most efficient way of doing this?
The reason I ask this, is because I am implementing something similar to this for the GUI of some software, for example I may click a button in a sidebar, which, in turn, changes the colour of the parent (the main window). In this instance it may not be too bad, but what about when I want to change the entire theme of a UI, and need to call functions in many objects from many parents. I would need alot of pointers, and it could get a bit messy.
Any suggestions on the best way to go about a problem such as this?
Thanks
The most appropriate way to do this is using observer pattern. The idea is to pass a functional object to the source of the event. This will ensure that you will be able to set any action for the event without the source of the event knowing what exactly it is.
The easiest way to implement this in C++ is using std::function class. For example:
#include <functional>
class Bar {
public:
using OnClicked = std::function<void(int)>;
void onClicked(OnClicked callback) {
m_OnClicked = std::move(callback);
}
void barClickEvent() {
if (m_OnClicked)
m_OnClicked(10);
}
private:
OnClicked m_OnClicked;
};
class Foo {
public:
Foo() : something(5) {
bar.onClicked([this](int value) {
changeSomething(value);
});
}
void changeSomething(int x){something = x;}
private:
Bar bar;
int something;
};
As you can see, Bar knows nothing about Foo which ensures loose coupling of your components, and now you can have each instance of Bar do a completely different thing when event occurs.

Proper design setup for derived classes with common attributes but different values

So I can think of a few ways to do this but I feel like I am just retyping the same thing with each new subclass. Is there a design pattern where I can set up the full structure for my subclasses in a way where I reduce the amount of code needed for implementation (and also enforce proper implementation if possible?)
This seems simple but the ideas I've had don't work, and the best I've found is to either hard code in the parameters when calling the constructor or to set up new constants within each child class then use those.
What I currently have is something like this:
"parent.hpp"
class Parent {
private:
std::string name;
int someValue;
protected:
Parent(std::string name, int someValue); // NOTE: There will be 7 parameters/attributes that need initial base values
void setName(std::string name) { this->name = name; }
void setSomeValue(int someValue) { this->someValue = someValue; }
public:
std::string getName() { return this->name; }
int getSomeValue() { return this->someValue; }
};
"parent.cpp"
Parent::Parent(std::string name, int someValue) {
setName(name);
setSomeValue(someValue);
}
"child.hpp"
class Child : public Parent {
public:
Child();
};
"child.cpp - option 1"
static const std::string DEFAULT_NAME = "Jon";
static const int DEFAULT_SOME_VALUE = 100;
Child::Child() : Parent(DEFAULT_NAME, DEFAULT_SOME_VALUE) {
// other stuff if needed
}
"child.cpp - option 2"
Child::Child() : Parent("Jon", 100) {
// other stuff if needed
}
There will be virtual methods and such I'll add later, but for now I just want to know of the right design pattern for having (potentially) many subclasses. There are also more parameters that will be in common which are all int values. It would seem unclear to me to have the constructors be Child::Child("string", 1, 2, 3, 4, 5, 6) albeit it would be easier to implement new subclasses.
On the other hand if I am just retyping the boiler plate constants for the base values in each subclass, the constructors will be more descriptive, but there would be a lot of code reuse.
It would seem to me what I would want to do is have virtual protected constants in the Parent class which the Child classes would need to define, then call those from the constructors, but that is not allowed. Is one of the two options a better one? Is there a better "long-term" setup for this?
I looked through all of the Similar Questions and the closest I found was this: Proper way to make base class setup parent class. Though I'm not really sure if that idea would fix my issue or make anything clearer.
Another idea I had was to call pure virtual methods from the default constructor, but as I learned that is also not allowed.
I would use another object to hold the state like Ami, although I would have done it for a different reason. Since the state is a separate class, you can fully construct it before the actual Parent and Child are constructed, and it can have its own hierarcy.
header
class Parent {
protected:
struct ParentState {
std::string name;
int someValue;
};
Parent(ParentState);
void setName(std::string name) { data.name = name; }
void setSomeValue(int someValue) { data.someValue = someValue; }
public:
std::string getName() { return data.name; }
int getSomeValue() { return data.someValue; }
private:
ParentState data;
};
class Child : public Parent {
struct ChildDefaults : public Parent::ParentState {
ChildDefaults();
};
public:
Child();
};
implementation
Parent::Parent(ParentState init) {
// since you have setters, they should be used
// instead of just data=init;
setName(init.name);
setSomeValue(init.someValue);
}
Child::ChildDefaults::ChildDefaults(){
name = "Jon";
someValue = 100;
}
Child::Child() : Parent(ChildDefaults()){
// other stuff if needed
}
If you put the ParentState and ChildDefault classes in a separate file, you can use that file to put all the defaults in one place where you can easily look them up or change them. They also might be prettier if they are not hidden inside the classes, forcing the extra scope syntax.
addendum:
To put the whole default settings heirarchy together in its own header, just move them all to one header. Be sure to do an include guard to avoid multiply defining the constructors.
#ifndef THE_DEFAULTS_H
#define THE_DEFAULTS_H
struct ParentState {
std::string name;
int someValue;
};
struct ChildDefaults : public Parent::ParentState {
ChildDefaults() {
name = "Jon";
someValue = 100;
}
};
// more default settings for other classes
#endif
Perhaps you could combine here two ideas:
Avoiding a large number of args passed to a function in general (including a ctor).
Method chaining.
(The first one is more fundamental here, and the second one is less essintial, and is here just for improved readability.)
In more detail:
Having any function, a ctor of a base class in particular, taking 7 parameters, seems very verbose & fragile. Suppose you realize that you needed to add another parameter. Would you now have to go over all the derived classes? That's problematic.
So let's start with something like:
class Parent
{
protected:
explicit Parent(const ParentParams &params);
};
And ParentParams looks something like this:
class ParentParams
{
public:
// Initialize with default stuff.
ParentParams();
// Changing only the foo aspect (via method chaining).
ParentParams &setFoo(Foo foo_val)
{
m_foo = foo_val;
return *this;
}
// Changing only the bar aspect (via method chaining).
ParentParams &setBar(Bar bar_val)
{
m_bar = bar_val;
return *this;
}
// Many more - you mentioned at least 7.
....
};
Now a child could look something like this:
// A child that happens to have the property that it changes foo and bar aspects.
class FooBarChangingChild :
public Parent
{
public:
FooBarChangingChild();
};
And in its implementation:
// Static cpp function just creating the params.
static ParentParams makeParams()
{
// Note the clarity of which options are being changed.
return ParentParams()
.setFoo(someFooVal)
.setBar(someBarVal);
}
FooBarChangingChild::FooBarChangingChild() :
Parent(makeParams())
{
}

Is it possible to add class members to base class A from derived class?

I was just thinking about it and wondering if it's totally possible, just out of curiosity, as it would be very usefull I think. (but most of my ideas are crazy/insane anyway).
So here it goes:
Is it possible to create a class A, and class B, then add a member to class A by using class B?
Let's suppose we are making a game, or some program in which this would be usefull:
class Player
{
public:
float health;
};
Now, you think of a way to allow extensions by using include files or something:
#define INCLUDE_SPEEDO_METER
#ifdef INCLUDE_SPEEDO_METER
class PlayerSpeedo : public Player
{
public:
float absolute_speed;
//Do some Magic here & there
};
#endif
Now let's suppose we want to access the absolute speed of a player from the Player class like Player.absolute_speed.
Is this possible in any way?
No, that's not possible. You can't "inject" members into another class. Frankly, I can't see why you would ever want to. No one else than you would be aware of this "injected" member.
While you can't syntactically do what you are hoping to do, you can achieve something very close by storing a map in the base class.
class Player
{
public:
Player(float health = 0) { data["health"] = health; }
float health() const { return get("health"); }
float get(std::string const& field) const { return data[field]; }
protected:
std::map<std::string, float> data;
};
class PlayerSpeedo : public Player
{
public:
PlayerSpeedo(float absolute_speed) {data["absolute_speed" = absolute_speed; }
float absolute_speed() const { return get("absolute_speed"); }
};
What you're talking about is not possible in a statically typed language, but it would work in a dynamically typed language (like Python).
A way of achieving that in C++ would be to use a Map between string names of properties and some generic wrapper for property values.
Not quite what you're asking for, but would give you somewhat similar capabilities is the recent proposal for a future version of the C++ standard Call syntax: x.f(y) vs. f(x,y)
This would enable you to write a standalone function float absolute_speed(const Player& p) { return 0.0f; } that you could call via Player p; auto speed = p.absolute_speed() without changing the definition of Player. This is a similar idea to extension methods in C#.
Maybe you like the way which is often done to extend a base class by another class with a template like the following. There is no need for runtime polymorphism which is often a criteria for speed while optimizing can go down to the executed functions without stopping at the virtual functions.
As you can see from the example, it looks like injection of methods and attributes. C++11 offer it to use the constructor from the class which you use to extend the given class very simple. OK, this is a stupied example but maybe it give you an idea how the thing works.
#include <iostream>
class Empty
{
public:
void DoSomething() { std::cout << "Nothing" << std::endl;}
};
class Extender
{
private:
int x;
public:
Extender(int _x):x(_x) {}
void DoSomething() { std::cout << "Value " << x << std::endl; }
};
template <typename ExtendWith>
class User: public ExtendWith
{
public:
using ExtendWith::ExtendWith;
void DoIt() { ExtendWith::DoSomething(); }
};
int main()
{
User<Empty> userEmpty;
userEmpty.DoIt();
User<Extender> userExtended(100);
userExtended.DoIt();
}
I don't think the language could allow what you're trying to do without introducing inconsistencies.
I don't think you want to modify the actual type though, since what you describe is essentially converting a super-type instance into a sub-type instance. You could do this by adding a constructor to the sub-type...
class PlayerSpeedo : public Player {
public:
float absolute_speed;
explcit PlayerSpeedo(const Player& p, float absolute_speed=0, ...) : health(p.health) {
// copy Player values
}
Another option might be storing a reference to the original object, and decorating it. This doesn't alter the type though.

Is there a better way than friend classes here?

Programming in C++ for Windows although this situation could arise anywhere. This is a simplified version of my problem to keep the question manageable so don't get too caught up on the detail :)
I have a class class Window which contains a windows HWND data item. I want to fully encapsulate that HWND so that the user of the class has to go through the class to perform any operations on that window, so it's stored in a private member variable. I don't want to provide any public "getter" for it as that would break the encapsulation allowing the user to bypass my class.
Now I want to create a class class Direct3d11 to encapsulate some of the directx api. In order to create an instance of this class it requires the HWND of a window so I pass it a Window object in it's constructor.
class Direct3D11
{
public:
Direct3D11(const Window& window);
};
Inside the constructor it has access to the window object, however it requires the HWND contained within in order to be able to physically create the windows objects that the Direct3D11 class will manage, but there is no way for it to obtain that information.
I could add a private getter function to get the HWND to the Window class, and then make the Direct3D11 class a friend class of Window so that it call call the function.
However this doesn't seem very elegant not least because class Window has otherwise no need to know anything at all about class Direct3D11.
Am I missing a better way to achieve this? Friend classes don't appeal, and having a public getter function doesn't much appeal either.
You could create the Direct3D11 class inside Window, since Windows owns the HWND.
Something along these lines:
class Window
{
HWND hwnd;
Direct3D11 d;
public:
Window() : d(hwnd) {}
Direct3D11& getDirect3D()
{
return d;
}
}
In your case I suggest to provide a getter for the HWND because you will probably be needing that more often. Providing the getter does not mean that you take the responsibility of your Window class, it is still responsible for the window's life cycle. You just make it more usable and easier to divide your code in use cases.
That said, here is a more generic approach that you could try:
class Window;
class Direct3D {
public:
void apply(Window &window, HWND hWnd);
};
class Window {
public:
void accept(Direct3D &direct3d) {
direct3d.apply(*this, this->m_hWnd);
}
};
You could maybe have a function on Window called Execute. It would take in a std::function with a placeholder for HWND as a parameter. Window would then call the function with HWND as its only parameter.
This would require c++11, but the code would be similar to :
#include <functional>
#include <iostream>
struct Foo {
explicit Foo(int num) : num_(num) {}
template<typename T>
void execute(std::function<T> f) const { f(num_); }
private:
int num_;
};
struct Bar{
void print_nums(int i,int j)
{
std::cout << "i:" << i << ", " << "j:" << j << std::endl;
}
};
int main()
{
Foo o(42);
Bar b;
//the function we want to execute requires an int
//that Foo knows about
typedef void myFunction(int);
// store the result of a call to std::bind
std::function<myFunction> display_1337_first = std::bind(&Bar::print_nums, b,1337, std::placeholders::_1);
std::function<myFunction> display_1337_last = std::bind(&Bar::print_nums, b, std::placeholders::_1, 1337);
o.execute<myFunction>(display_1337_first);
o.execute<myFunction>(display_1337_last);
return 0;
}
//output:
//i:1337, j:42
//i:42, j:1337
If you are willing to use the friend keyword you can make sure window has no knowledge of the class that needs the hwnd. Just make classes (that window and DirectX inherit from) that handle the actions for you. This allows you to solve the problem for DirectX, AND for the next time it comes around.
Side Rant:
Friend is not a four-letter word. Friend, if used reasonably, is actually a great way to add gradation to C++'s access control (public, friend (when in protected), protected, friend (when in private) , private).
#include <iostream>
class HwndOwner;
class HwndWanter
{
protected:
HwndWanter(){}
int getHwndFromOwner(HwndOwner & owner);
};
class HwndOwner
{
protected:
HwndOwner() : hwnd(42){}
private:
friend class HwndWanter;
int getHwnd()
{
return hwnd;
}
int hwnd;
};
class Window : public HwndOwner
{
//This is not the class you are looking for...
};
class Direct3D : private HwndWanter
{
public:
Direct3D(HwndOwner & owner)
: HwndWanter()
{
std::cout << getHwndFromOwner(owner) << std::endl;
}
};
int HwndWanter::getHwndFromOwner(HwndOwner & owner)
{
return owner.getHwnd();
}
int main()
{
Window window;
Direct3D hwndWanter(window);
}
Output:
42