24 #include <QtCore/QMetaEnum>
25 #include <QtCore/QMetaType>
26 #include <QtCore/QDebug>
27 #include <QtGui/QWidget>
29 #include <kjs/interpreter.h>
36 using namespace KJSEmbed;
39 :
QObject(parent), m_interpreter(interpreter), m_object(obj)
41 m_signature = QMetaObject::normalizedSignature( signature );
42 uint signatureSize = m_signature.size() + 1;
57 m_data[11] = 10 + signatureSize;
58 m_data[12] = 10 + signatureSize;
59 m_data[13] = 10 + signatureSize;
63 m_stringData = QByteArray(
"SlotProxy\0", 10);
64 m_stringData += m_signature;
65 m_stringData += QByteArray(
"\0\0", 2);
71 #ifdef DEBUG_SLOTPROXY
72 qDebug() <<
"SlotProxy() obj=" <<
this <<
" m_signature=" << m_signature;
78 #ifdef DEBUG_SLOTPROXY
79 qDebug() <<
"??????SlotProxy::~SlotProxy() obj=" <<
this <<
" m_signature=" << m_signature;
90 if (!_clname)
return 0;
91 if (!strcmp(_clname, m_stringData))
92 return static_cast<void*
>(
const_cast<SlotProxy*
>(
this));
93 return QObject::qt_metacast(_clname);
96 KJS::JSValue *SlotProxy::callMethod(
const QByteArray & methodName,
void **_a )
98 #ifdef DEBUG_SLOTPROXY
99 qDebug() <<
"SlotProxy::callMethod(" << methodName <<
",_a) obj=" <<
this;
101 KJS::ExecState *exec = m_interpreter->globalExec();
102 exec->clearException();
106 KJS::List args = convertArguments(exec, _a);
107 KJS::Identifier
id = KJS::Identifier( KJS::UString(methodName.data()));
108 KJS::JSObject *fun = m_object->get(exec,
id )->toObject( exec );
109 KJS::JSValue *retValue;
110 if ( !fun->implementsCall() )
112 #ifdef DEBUG_SLOTPROXY
113 qDebug() <<
"SlotProxy::callMethod got bad handler";
115 QString msg = i18n(
"Bad slot handler: Object %1 Identifier %2 Method %3 Signature: %4.",
116 m_object->className().ascii(),
119 QString(m_signature));
121 retValue =
throwError(exec, KJS::TypeError, msg);
124 retValue = fun->call(exec, m_object, args);
126 if( exec->hadException() )
128 #ifdef DEBUG_SLOTPROXY
129 qDebug() <<
"SlotProxy::callMethod had exception";
131 if (m_interpreter->shouldPrintExceptions())
134 KJS::JSObject* exceptObj = exec->exception()->toObject(exec);
136 QString sourceURL =
toQString(exceptObj->get(exec,
"sourceURL")->toString(exec));
137 int sourceId = exceptObj->get(exec,
"sourceId")->toUInt32(exec);
139 int line = exceptObj->get(exec,
"line")->toUInt32(exec);
140 (*
KJSEmbed::conerr()) << i18n(
"Exception calling '%1' slot from %2:%3:%4", QString(methodName), !sourceURL.isEmpty() ? sourceURL : QString::number(sourceId), line,
message) << endl;
144 exec->clearException();
146 return KJS::jsNull();
150 if( retValue->type() == 1 || retValue->type() == 0)
152 return KJS::jsNull();
158 KJS::List SlotProxy::convertArguments(KJS::ExecState *exec,
void **_a )
161 int offset =
metaObject()->indexOfMethod(m_signature);
162 QMetaMethod method =
metaObject()->method(offset);
163 QList<QByteArray> params = method.parameterTypes();
165 #ifdef DEBUG_SLOTPROXY
166 qDebug() <<
"SlotProxy::convertArguments(): obj=" <<
this <<
" m_signature=" << m_signature <<
" offset=" << offset <<
" params=" << params ;
168 foreach(
const QByteArray ¶m, params )
170 #ifdef DEBUG_SLOTPROXY
171 int type = QMetaType::type( param.constData() );
172 qDebug(
"\tGot a %d - %s - _a[%d] = %p", type, param.data(),
idx, _a[
idx]);
173 qDebug(
"\t QMetaType::type()=%d", QMetaType::type(QByteArray(
"Pinya::") + param.constData()));
175 int tp = QVariant::nameToType(param.constData());
179 args.append(KJS::jsNumber(*(
int*)_a[idx]));
182 args.append(KJS::jsNumber(*(uint*)_a[idx]));
184 case QVariant::LongLong:
185 args.append(KJS::jsNumber(*(qlonglong*)_a[idx]));
187 case QVariant::ULongLong:
188 args.append(KJS::jsNumber(*(qulonglong*)_a[idx]));
190 case QVariant::Double:
191 args.append(KJS::jsNumber(*(
double*)_a[idx]));
194 args.append(KJS::jsBoolean(*(
bool*)_a[idx]));
196 case QVariant::String:
197 args.append(
KJS::jsString((*
reinterpret_cast<QString(*)
>(_a[idx]))));
199 case QVariant::UserType:
201 KJS::JSObject* returnValue;
202 KJS::JSObject*
parent = exec->dynamicInterpreter()->globalObject();
203 QByteArray typeName = param.constData();
204 bool isPtr = typeName.contains(
"*");
206 typeName.replace(
"*",
"");
207 #ifdef DEBUG_SLOTPROXY
208 qDebug() <<
"\tQVariant::UserType: typeName=" << typeName <<
" param=" << param.constData() <<
" isPtr" << isPtr;
210 if ( parent->hasProperty( exec, KJS::Identifier(
toUString(typeName))) )
214 ((qObj = *reinterpret_cast<QObject**>(_a[idx])) != 0))
216 #ifdef DEBUG_SLOTPROXY
217 qDebug() <<
"qObj=" << qObj;
223 args.append(returnValue);
228 #ifdef DEBUG_SLOTPROXY
229 qDebug(
"\t\tNo binding retrieved");
234 if(
QObjectBinding *objImp = KJSEmbed::extractBindingImp<QObjectBinding>(exec, returnValue))
236 #ifdef DEBUG_SLOTPROXY
237 qDebug() <<
"\t\t\tFound QObjectBinding";
240 objImp->setObject(qObj);
241 if (qObj->parent() != 0)
245 args.append(returnValue);
254 #ifdef DEBUG_SLOTPROXY
255 qDebug(
"\t\tNo binding registered");
257 KJS::JSObject* returnValue = 0;
258 switch( QMetaType::type( param.constData() ) )
260 case QMetaType::QObjectStar: {
264 case QMetaType::QWidgetStar: {
269 #ifdef DEBUG_SLOTPROXY
270 qDebug(
"\t\tInvalid type !");
275 args.append(returnValue);
280 case QVariant::StringList:
285 QVariant variant(tp, _a[idx]);
297 #ifdef DEBUG_SLOTPROXY
298 qDebug(
"SlotProxy::qt_metacall(_c=%d, _id=%d, _a=%p _a[0]=%p _a[1]=%p) obj=", _c, _id, _a, _a[0], _a[1],
this);
300 _id = QObject::qt_metacall(_c, _id, _a);
303 if (_c == QMetaObject::InvokeMetaMethod)
309 QByteArray method = m_signature.left(m_signature.indexOf(
'('));
310 KJS::JSValue *
result = callMethod(method, _a);
312 #ifdef DEBUG_SLOTPROXY
313 qDebug()<<
"SlotProxy::qt_metacall result="<<m_tmpResult.toString();
315 _a[0] = &(m_tmpResult);
QVariant KJSEMBED_EXPORT convertToVariant(KJS::ExecState *exec, KJS::JSValue *value)
Convert a KJS::JSValue into a QVariant object.
int qt_metacall(QMetaObject::Call _c, int _id, void **_a)
SlotProxy(KJS::JSObject *obj, KJS::Interpreter *interpreter, QObject *parent, const QByteArray &signature)
KJS::JSObject * construct(KJS::ExecState *exec, const KJS::List &args)
Calls the callback that will in turn create a new instance of this object with the arguments passed i...
KJSEMBED_EXPORT KJS::JSObject * createQObject(KJS::ExecState *exec, QObject *value, KJSEmbed::ObjectBinding::Ownership owner=KJSEmbed::ObjectBinding::JSOwned)
Returns a binding object for the specified QObject.
void * qt_metacast(const char *_clname)
QMetaObject staticMetaObject
static KJS::JSObject * bind(KJS::ExecState *exec, const QString &className, PointerBase &objPtr)
KJS::JSCell * jsString(const QString &s)
KJS::UString toUString(const QString &qs)
KJSEMBED_EXPORT KJS::JSValue * convertToValue(KJS::ExecState *exec, const QVariant &value)
Convert a QVariant to a KJS::JSValue.
const QMetaObject * metaObject() const
JSObject * throwError(ExecState *e, ErrorType t, const QString &m)
KJSEMBED_EXPORT QTextStream * conerr()
QString toQString(const KJS::UString &u)