KcFnMi
KcFnMi

Reputation: 6161

Minimalist framework

I've read somewhere the Inversion of Control (IoC) is (kind of) a principle of a framework.

Is it correct to (taking advantage of that) say I designed a framework for X just because the IoC pattern is employed?

May I ask for a minimal framework example (C++ code please)?

Or instead, I can try to be more specific, providing some code (a complete Qt project) and asking if there is a framework there.

The class FrameworkForX (below, at the end) might be called a framework?

framework.pro

QT       += core gui

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

TARGET = framework
TEMPLATE = app

SOURCES += main.cpp\
        widget.cpp \
    frameworkforx.cpp \
    solvemyproblem.cpp

HEADERS  += widget.h \
    frameworkforx.h \
    solvemyproblem.h

main.cpp

#include "widget.h"
#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Widget w;
    w.show();

    return a.exec();
}

widget.h

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>

class QLineEdit;
class QLabel;
class SolveMyProblem;

class Widget : public QWidget
{
    Q_OBJECT
public:
    Widget(QWidget *parent = 0);
    ~Widget();

private:
    QLineEdit *lineEdit;
    QLabel *label;
    SolveMyProblem *solveMyProblem;

public slots:
    void doit();
    void onResult(int result);
};

#endif // WIDGET_H

widget.cpp

#include "widget.h"

#include "QVBoxLayout"
#include "QPushButton"
#include "QLineEdit"
#include "QLabel"

#include "solvemyproblem.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent), solveMyProblem(new SolveMyProblem)
{
    QVBoxLayout *vLayout = new QVBoxLayout(this);

    lineEdit = new QLineEdit;
    vLayout->addWidget(lineEdit);

    QPushButton *bt = new QPushButton("Do It!");
    connect(bt, &QPushButton::clicked, this, &Widget::doit);
    vLayout->addWidget(bt, 1, Qt::AlignRight);

    label = new QLabel("The result will be shown here.");
    connect(solveMyProblem, &SolveMyProblem::result, this, &Widget::onResult);
    vLayout->addWidget(label);

    resize(400, 100);
    setWindowTitle("Is it (FrameworkForX) a framework?");
}

Widget::~Widget()
{

}

void Widget::doit()
{
    QString text = lineEdit->text();
    solveMyProblem->doSomething(text);
}

void Widget::onResult(int result)
{
    QString text = QString::number(result);
    label->setText(text);
}

solvemyproblem.h

#ifndef SOLVEMYPROBLEM_H
#define SOLVEMYPROBLEM_H

#include "frameworkforx.h"

class SolveMyProblem : public FrameworkForX
{
public:
    SolveMyProblem();

    int doSpecificJob(const QString &text);
};

#endif // SOLVEMYPROBLEM_H

solvemyproblem.cpp

#include "solvemyproblem.h"

SolveMyProblem::SolveMyProblem()
{

}

int SolveMyProblem::doSpecificJob(const QString &text)
{
    int i = text.size();
    return i;
}

frameworkforx.h

#ifndef FRAMEWORKFORX_H
#define FRAMEWORKFORX_H

#include "QObject"

class QString;

class FrameworkForX : public QObject
{
    Q_OBJECT
public:
    FrameworkForX();

    void doSomething(const QString &text);

protected:
    virtual int doSpecificJob(const QString &text) = 0;

signals:
    void result(int i);

};

#endif // FRAMEWORKFORX_H

frameworkforx.cpp

#include "frameworkforx.h"

FrameworkForX::FrameworkForX()
{

}

void FrameworkForX::doSomething(const QString &text)
{
    int value = doSpecificJob(text);
    emit result(value);
}

Upvotes: 0

Views: 124

Answers (1)

Nico Schertler
Nico Schertler

Reputation: 32587

Your example is close to a framework. And it's close to IoC. But in my opinion, it is not the exact pattern because of this part:

Widget::Widget(QWidget*)
: ... solveMyProblem(new SolveMyProblem)

The Widget still has control over its strategy. It even constructs it. Therefore, there is no inversion. A proper IoC implementation would take the strategy e.g. as a parameter. Then, it makes only sense to require the base class or interface:

Widget::Widget(QWidget*, FrameworkForX* mySolver)
: ... solveMyProblem(mySolver) 
//of course, the declaration of solveMyProblem has to be adapted

So far for the IoC part. Let's come to the framework part. A possible definition of a framework is the following:

A framework is a software component with extension points and variation points.

A software component could be anything. It could be a class, a library, a whole set of libraries... What IoC offers is a variation point. You can vary the functionality of a class (in this case of Widget) by supplying a custom implementation. You can plug that implementation into the framework to build a fully functional software component (whereas the framework is usually only a kind of skeleton).

So: Yes. In my opinion, every IoC implementation can be seen as a framework. In your concrete example, the framework would consist of Widget and FrameworkForX (where FrameworkForX could even be just an interface). SolveMyProblem is a custom implementation which is plugged into this framework.

Upvotes: 1

Related Questions