lib
eventslot.cpp
00001 /*************************************************************************** 00002 * eventslot.cpp 00003 * This file is part of the KDE project 00004 * copyright (C)2004-2005 by Sebastian Sauer (mail@dipe.org) 00005 * 00006 * This program is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Library General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2 of the License, or (at your option) any later version. 00010 * This program is distributed in the hope that it will be useful, 00011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00013 * Library General Public License for more details. 00014 * You should have received a copy of the GNU Library General Public License 00015 * along with this program; see the file COPYING. If not, write to 00016 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 00017 * Boston, MA 02110-1301, USA. 00018 ***************************************************************************/ 00019 00020 #include "eventslot.h" 00021 00022 #include "variant.h" 00023 #include "qtobject.h" 00024 00025 #include <qmetaobject.h> 00026 #include <private/qucom_p.h> // for the Qt QUObject API. 00027 00028 using namespace Kross::Api; 00029 00030 EventSlot::EventSlot(const QString& name, Object::Ptr parent, QObject* receiver, QCString slot) 00031 : Event<EventSlot>(name, parent) 00032 , m_receiver(receiver) 00033 , m_slot(slot) //QObject::normalizeSignalSlot(slot) 00034 { 00035 } 00036 00037 EventSlot::~EventSlot() 00038 { 00039 } 00040 00041 const QString EventSlot::getClassName() const 00042 { 00043 return "Kross::Api::EventSlot"; 00044 } 00045 00046 Object::Ptr EventSlot::call(const QString& /*name*/, List::Ptr arguments) 00047 { 00048 #ifdef KROSS_API_EVENTSLOT_CALL_DEBUG 00049 kdDebug() << QString("EventSlot::call() name=%1 m_slot=%2 arguments=%3").arg(name).arg(m_slot).arg(arguments->toString()) << endl; 00050 #endif 00051 00052 QString n = m_slot; //TODO name; //Variant::toString(args->item(0)); 00053 00054 if(n.startsWith("1")) // Remove prefix of SLOT-macros 00055 n.remove(0,1); 00056 00057 int slotid = m_receiver->metaObject()->findSlot(n.latin1(), false); 00058 if(slotid < 0) 00059 throw Exception::Ptr( new Exception(QString("No such slot '%1'.").arg(n)) ); 00060 00061 QUObject* uo = QtObject::toQUObject(n, arguments); 00062 m_receiver->qt_invoke(slotid, uo); // invoke the slot 00063 delete [] uo; 00064 00065 return new Variant(true, "Kross::Api::EventSlot::Bool"); 00066 } 00067 00068 /* 00069 QCString EventSlot::getSlot(const QCString& signal) 00070 { 00071 QString signature = QString(signal).mid(1); 00072 int startpos = signature.find("("); 00073 int endpos = signature.findRev(")"); 00074 if(startpos < 0 || startpos > endpos) { 00075 kdWarning() << QString("EventSlot::getSlot(%1) Invalid signal.").arg(signal) << endl; 00076 return QCString(); 00077 } 00078 QString signalname = signature.left(startpos); 00079 QString params = signature.mid(startpos + 1, endpos - startpos - 1); 00080 //QStringList paramlist = QStringList::split(",", params); 00081 QCString slot = QString("callback(" + params + ")").latin1(); //normalizeSignalSlot(); 00082 00083 QMetaObject* mo = metaObject(); 00084 int slotid = mo->findSlot(slot, false); 00085 if(slotid < 0) { 00086 kdDebug() << QString("EventSlot::getSlot(%1) No such slot '%2' avaiable.").arg(signal).arg(slot) << endl; 00087 return QCString(); 00088 } 00089 00090 const QMetaData* md = mo->slot(slotid, false); 00091 if(md->access != QMetaData::Public) { 00092 kdDebug() << QString("EventSlot::getSlot(%1) The slot '%2' is not public.").arg(signal).arg(slot) << endl; 00093 return QCString(); 00094 } 00095 00096 //QMember* member = md->member; 00097 //const QUMethod *method = md->method; 00098 00099 kdDebug()<<"signal="<<signal<<" slot="<<slot<<" slotid="<<slotid<<" params="<<params<<" md->name="<<md->name<<endl; 00100 return QCString("1" + slot); // Emulate the SLOT(...) macro by adding as first char a "1". 00101 } 00102 00103 bool EventSlot::connect(EventManager* eventmanager, QObject* senderobj, const QCString& signal, QString function, const QCString& slot) 00104 { 00105 if(m_sender && ! disconnect()) 00106 return false; 00107 00108 const QCString& myslot = slot.isEmpty() ? getSlot(signal) : slot; 00109 if(! myslot) 00110 return false; 00111 00112 if(! m_eventmanager) { 00113 EventSlot* eventslot = create(eventmanager); 00114 eventslot->connect(eventmanager, senderobj, signal, function, slot); 00115 m_slots.append(eventslot); 00116 kdDebug() << QString("EventSlot::connect(%1, %2, %3) added child EventSlot !!!").arg(senderobj->name()).arg(signal).arg(function) << endl; 00117 } 00118 else { 00119 m_sender = senderobj; 00120 m_signal = signal; 00121 m_function = function; 00122 m_slot = myslot; 00123 if(! QObject::connect((QObject*)senderobj, signal, this, myslot)) { 00124 kdDebug() << QString("EventSlot::connect(%1, %2, %3) failed.").arg(senderobj->name()).arg(signal).arg(function) << endl; 00125 return false; 00126 } 00127 kdDebug() << QString("EventSlot::connect(%1, %2, %3) successfully connected.").arg(senderobj->name()).arg(signal).arg(function) << endl; 00128 } 00129 return true; 00130 } 00131 00132 bool EventSlot::disconnect() 00133 { 00134 if(! m_sender) return false; 00135 QObject::disconnect((QObject*)m_sender, m_signal, this, m_slot); 00136 m_sender = 0; 00137 m_signal = 0; 00138 m_slot = 0; 00139 m_function = QString::null; 00140 return true; 00141 } 00142 00143 void EventSlot::call(const QVariant& variant) 00144 { 00145 kdDebug() << QString("EventSlot::call() sender='%1' signal='%2' function='%3'") 00146 .arg(m_sender->name()).arg(m_signal).arg(m_function) << endl; 00147 00148 Kross::Api::List* arglist = 0; 00149 00150 QValueList<Kross::Api::Object*> args; 00151 if(variant.isValid()) { 00152 args.append(Kross::Api::Variant::create(variant)); 00153 arglist = Kross::Api::List::create(args); 00154 } 00155 00156 try { 00157 m_eventmanager->m_scriptcontainer->callFunction(m_function, arglist); 00158 } 00159 catch(Exception& e) { 00160 //TODO add hadError(), getError() and setError() 00161 kdDebug() << QString("EXCEPTION in EventSlot::call('%1') type='%2' description='%3'").arg(variant.toString()).arg(e.type()).arg(e.description()) << endl; 00162 } 00163 } 00164 00165 void EventSlot::callback() { 00166 call(QVariant()); } 00167 void EventSlot::callback(short s) { 00168 call(QVariant(s)); } 00169 void EventSlot::callback(int i) { 00170 call(QVariant(i)); } 00171 void EventSlot::callback(int i1, int i2) { 00172 call(QVariant( QValueList<QVariant>() << i1 << i2 )); } 00173 void EventSlot::callback(int i1, int i2, int i3) { 00174 call(QVariant( QValueList<QVariant>() << i1 << i2 << i3 )); } 00175 void EventSlot::callback(int i1, int i2, int i3, int i4) { 00176 call(QVariant( QValueList<QVariant>() << i1 << i2 << i3 << i4 )); } 00177 void EventSlot::callback(int i1, int i2, int i3, int i4, int i5) { 00178 call(QVariant( QValueList<QVariant>() << i1 << i2 << i3 << i4 << i5 )); } 00179 void EventSlot::callback(int i1, int i2, int i3, int i4, bool b) { 00180 call(QVariant( QValueList<QVariant>() << i1 << i2 << i3 << i4 << b )); } 00181 void EventSlot::callback(int i1, bool b) { 00182 call(QVariant( QValueList<QVariant>() << i1 << b )); } 00183 void EventSlot::callback(int i1, int i2, bool b) { 00184 call(QVariant( QValueList<QVariant>() << i1 << i2 << b )); } 00185 void EventSlot::callback(int i1, int i2, const QString& s) { 00186 call(QVariant( QValueList<QVariant>() << i1 << i2 << s )); } 00187 void EventSlot::callback(uint i) { 00188 call(QVariant(i)); } 00189 void EventSlot::callback(long l) { 00190 call(QVariant((Q_LLONG)l)); } 00191 void EventSlot::callback(ulong l) { 00192 call(QVariant((Q_ULLONG)l)); } 00193 void EventSlot::callback(double d) { 00194 call(QVariant(d)); } 00195 void EventSlot::callback(const char* c) { 00196 call(QVariant(c)); } 00197 void EventSlot::callback(bool b) { 00198 call(QVariant(b)); } 00199 void EventSlot::callback(const QString& s) { 00200 call(QVariant(s)); } 00201 void EventSlot::callback(const QString& s, int i) { 00202 call(QVariant( QValueList<QVariant>() << s << i )); } 00203 void EventSlot::callback(const QString& s, int i1, int i2) { 00204 call(QVariant( QValueList<QVariant>() << s << i1 << i2 )); } 00205 void EventSlot::callback(const QString& s, uint i) { 00206 call(QVariant( QValueList<QVariant>() << s << i )); } 00207 void EventSlot::callback(const QString& s, bool b) { 00208 call(QVariant( QValueList<QVariant>() << s << b )); } 00209 void EventSlot::callback(const QString& s, bool b1, bool b2) { 00210 call(QVariant( QValueList<QVariant>() << s << b1 << b2 )); } 00211 void EventSlot::callback(const QString& s, bool b, int i) { 00212 call(QVariant( QValueList<QVariant>() << s << b << i )); } 00213 void EventSlot::callback(const QString& s1, const QString& s2) { 00214 call(QVariant( QValueList<QVariant>() << s1 << s2 )); } 00215 void EventSlot::callback(const QString& s1, const QString& s2, const QString& s3) { 00216 call(QVariant( QValueList<QVariant>() << s1 << s2 << s3 )); } 00217 void EventSlot::callback(const QStringList& sl) { 00218 call(QVariant(sl)); } 00219 void EventSlot::callback(const QVariant& variant) { 00220 call(variant); } 00221 */