Here's what I've come up with.
AbstractTableModelPlugin.h
Code: Select all
#ifndef ABSTRACTTABLEMODELPLUGIN_H
#define ABSTRACTTABLEMODELPLUGIN_H
#include <QObject>
#include <QDebug>
#include <QScriptEngine>
#include <QAbstractTableModel>
#include <string>
#include "RPluginInterface.h"
class AbstractTableModelAdapter : public QAbstractTableModel
{
Q_OBJECT
public:
AbstractTableModelAdapter(QObject* parent = 0) : QAbstractTableModel(parent) {}
~AbstractTableModelAdapter() {}
// The following functions are to be overridden
// by javascript prototype.
int rowCount(const QModelIndex &parent) const {
Q_UNUSED(parent)
return 10;
}
int columnCount(const QModelIndex &parent) const {
Q_UNUSED(parent)
return 10;
}
QVariant data(const QModelIndex &index, int role) const {
Q_UNUSED(index)
if (role == Qt::DisplayRole) {
return QVariant("Row " + QString::number(index.row()) + " Col " + QString::number(index.column()));
}
return QVariant();
}
// QVariant headerData(int section, Qt::Orientation orientation, int role);
// bool setData(QModelIndex &index, const QVariant &value, int role);
};
Q_DECLARE_METATYPE(AbstractTableModelAdapter*)
class AbstractTableModelPlugin : public QObject, public RPluginInterface
{
Q_OBJECT
Q_INTERFACES(RPluginInterface)
#if QT_VERSION >= 0x050000
Q_PLUGIN_METADATA(IID "org.qcad.AbstractTableModelPlugin")
#endif
public:
AbstractTableModelPlugin() : QObject() {}
~AbstractTableModelPlugin() {}
virtual bool init();
virtual void uninit(bool) {}
virtual void postInit(InitStatus status);
virtual void initScriptExtensions(QScriptEngine& engine);
virtual RPluginInfo getPluginInfo();
static QScriptValue createAbstractTableModelAdapter(QScriptContext* context, QScriptEngine* engine);
};
Q_DECLARE_METATYPE(AbstractTableModelPlugin*)
#endif // ABSTRACTTABLEMODELPLUGIN_H
AbstractTableModelPlugin.cpp
Code: Select all
#include "AbstractTableModelPlugin.h"
#include "RVersion.h"
#include "REcmaHelper.h"
#include "RSettings.h"
bool AbstractTableModelPlugin::init() {
qDebug() << "AbstractTableModelPlugin::init";
return true;
}
void AbstractTableModelPlugin::postInit(InitStatus status) {
if (status != RPluginInterface::AllDone) {
return;
}
}
void AbstractTableModelPlugin::initScriptExtensions(QScriptEngine &engine) {
QScriptValue* proto = new QScriptValue(engine.newVariant(qVariantFromValue((AbstractTableModelAdapter*)0)));
QScriptValue dpt = engine.defaultPrototype(qMetaTypeId<QAbstractTableModel*>());
proto->setPrototype(dpt);
engine.setDefaultPrototype(qMetaTypeId<AbstractTableModelAdapter*>(), *proto);
QScriptValue ctor = engine.newFunction(AbstractTableModelPlugin::createAbstractTableModelAdapter, *proto, 0);
engine.globalObject().setProperty("AbstractTableModelAdapter", ctor, QScriptValue::SkipInEnumeration);
}
RPluginInfo AbstractTableModelPlugin::getPluginInfo() {
RPluginInfo ret;
ret.set("Version", R_QCAD_VERSION_STRING);
ret.set("ID", "AbstractTableModelPlugin");
ret.set("Name", "AbstractTableModelPlugin");
ret.set("License", "GPLv3");
ret.set("URL", "http://qcad.org");
return ret;
}
QScriptValue AbstractTableModelPlugin::createAbstractTableModelAdapter(QScriptContext* context, QScriptEngine* engine) {
if (context->thisObject().strictlyEquals(engine->globalObject())) {
return REcmaHelper::throwError(QString::fromLatin1("AbstractTableModelAdapter(): Did you forget to construct with 'new'?"), context);
}
// constructor without arguments:
if (context->argumentCount() == 0) {
qDebug() << "AbstractTableModelPlugin::create... arg count == 0";
AbstractTableModelAdapter* cppResult = new AbstractTableModelAdapter();
return engine->newQObject(context->thisObject(), cppResult);
}
else if (context->argumentCount() == 1) {
qDebug() << "AbstractTableModelPlugin::create... arg count == 1";
QObject* a0 = context->argument(0).toQObject();
AbstractTableModelAdapter* cppResult = new AbstractTableModelAdapter(a0);
return engine->newQObject(context->thisObject(), cppResult);
} else {
return REcmaHelper::throwError(QString::fromLatin1("AbstractTableModelAdapter(): no matching constructor found."), context);
}
}
BomModel.js
Code: Select all
function BomModel(parent) {
AbstractTableModelAdapter.call(this, parent);
}
BomModel.prototype = new AbstractTableModelAdapter();
BomModel.prototype.rowCount = function (qModelindex) {
EAction.handleUserMessage("BomModel.rowCount()");
return 2;
}
BomModel.prototype.columnCount = function (qModelIndex) {
EAction.handleUserMessage("BomModel.columnCount()");
return 3;
}
BomModel.prototype.data = function (index, role) {
EAction.handleUserMessage("BomModel.data()");
if (role === Qt.DisplayRole) {
return ("Row%1, Column%2").arg(index.row()).arg(index.column());
}
return;
}
Is this along the lines of what you were thinking?
I haven't gotten my JS prototype functions to override the AbstractTableModelAdapter functions yet.