[89] | 1 | #ifndef IN_OUT_INTERFACE_H
|
---|
| 2 | #define IN_OUT_INTERFACE_H
|
---|
| 3 |
|
---|
[95] | 4 | #include <Pacpus/kernel/Log.h>
|
---|
[89] | 5 | #include <Pacpus/kernel/inputOutputBase.h>
|
---|
[110] | 6 | #include <QApplication>
|
---|
| 7 | #include <typeinfo>
|
---|
[89] | 8 |
|
---|
| 9 | #include <QDebug>
|
---|
[110] | 10 | #include <QThread>
|
---|
[89] | 11 |
|
---|
| 12 | #include <QByteArray>
|
---|
| 13 |
|
---|
| 14 | #define ADD_INPUT(name,ComponentType, DataType, functionName) input.insert(name,new InputInterface<DataType,ComponentType> (name,this,&ComponentType::functionName))
|
---|
| 15 | #define ADD_OUTPUT(name,ComponentType, DataType) output.insert(name,new OutputInterface<DataType,ComponentType> (name,this))
|
---|
[110] | 16 |
|
---|
[89] | 17 | #define GET_OUTPUT(name,ComponentType, DataType) dynamic_cast<OutputInterface<DataType,ComponentType> *> (output.value(name))
|
---|
[110] | 18 | #define GET_INPUT(name,ComponentType, DataType) dynamic_cast<InputInterface<DataType,ComponentType> *> (input.value(name))
|
---|
[89] | 19 |
|
---|
| 20 | namespace pacpus {
|
---|
| 21 |
|
---|
| 22 | template <class T, class C>
|
---|
| 23 | class InputInterface : public InputInterfaceBase
|
---|
| 24 | {
|
---|
| 25 | public:
|
---|
| 26 | InputInterface(QString name, C * component, void (C::*m)(const T&)):InputInterfaceBase(name,component,component), method(m) {}
|
---|
| 27 | ~InputInterface() {}
|
---|
| 28 | size_t getDataSize() {return sizeof(T);}
|
---|
| 29 | QString getDataType() {return QString(typeid(T).name());}
|
---|
| 30 |
|
---|
[110] | 31 | protected:
|
---|
[89] | 32 |
|
---|
[110] | 33 | public:
|
---|
[89] | 34 |
|
---|
[110] | 35 | PacpusEvent* getEventTemplate() {return new PacpusTypedEvent<T>(TYPED_EVENT); }
|
---|
[96] | 36 |
|
---|
[89] | 37 | void customEvent(QEvent* event) {
|
---|
| 38 |
|
---|
| 39 | switch (event->type()) {
|
---|
| 40 |
|
---|
[110] | 41 | // from Component to Component (T->T)
|
---|
| 42 | case TYPED_EVENT: {
|
---|
| 43 | PacpusTypedEvent<T> * typedEvent = dynamic_cast<PacpusTypedEvent<T> *> (event);
|
---|
[89] | 44 |
|
---|
[110] | 45 | qDebug() << "Revever " << getSignature() << " thread " << QThread::currentThread() << " Data & " << & typedEvent->data_;
|
---|
| 46 |
|
---|
| 47 | if(typedEvent->tr_ < 500 && readingMode_ == TimeBounded) {
|
---|
| 48 | //LOG_WARN("Incorrect TimeRange (0), switch to NeverSkip");
|
---|
| 49 | qDebug() << "Incorrect TimeRange (0), switch to NeverSkip";
|
---|
| 50 | readingMode_ = NeverSkip;}
|
---|
| 51 |
|
---|
| 52 | switch (readingMode_){
|
---|
| 53 | case TimeBounded:
|
---|
| 54 | qDebug() << "Input " << this->getSignature().leftJustified(20) << QString("Time bournded").leftJustified(15) << road_time()- typedEvent->t_ << "\t" << typedEvent->tr_;
|
---|
| 55 |
|
---|
| 56 | if(road_time() - typedEvent->t_> typedEvent->tr_)
|
---|
| 57 | {qDebug() << "Data skip " << this->getSignature(); break;}
|
---|
| 58 |
|
---|
| 59 | (dynamic_cast<C*>(_component)->*method)(typedEvent->data_);
|
---|
[89] | 60 | break;
|
---|
[110] | 61 |
|
---|
| 62 | case GetLast:
|
---|
| 63 | qDebug() << "Input " << this->getSignature().leftJustified(20) << QString("GetLast").leftJustified(15) << road_time() - typedEvent->t_ << "\t" << typedEvent->tr_;
|
---|
| 64 |
|
---|
| 65 | (dynamic_cast<C*>(_component)->*method)(typedEvent->data_);
|
---|
| 66 | QCoreApplication::removePostedEvents(this,TYPED_EVENT); // delete all remining events
|
---|
| 67 | break;
|
---|
| 68 |
|
---|
| 69 | case NeverSkip:
|
---|
| 70 | qDebug() << "Input " << this->getSignature().leftJustified(20) << QString("NeverSkip").leftJustified(15) << road_time() - typedEvent->t_ << "\t" << typedEvent->tr_;
|
---|
| 71 |
|
---|
| 72 | default:
|
---|
| 73 | (dynamic_cast<C*>(_component)->*method)(typedEvent->data_);
|
---|
[89] | 74 | }
|
---|
[110] | 75 | break;
|
---|
| 76 | }
|
---|
[89] | 77 |
|
---|
[110] | 78 | // from Connection interface to Component (G->T)
|
---|
| 79 | /* case GENERIC_EVENT2: {
|
---|
[89] | 80 | PacpusTypedEvent<QByteArray> * genericEvent = dynamic_cast<PacpusTypedEvent<QByteArray> *> (event);
|
---|
| 81 | T data;
|
---|
[110] | 82 | QByteArray& buf = (QByteArray&) genericEvent->data_;
|
---|
[89] | 83 | QDataStream in(&buf,QIODevice::ReadOnly);
|
---|
| 84 |
|
---|
| 85 | (dynamic_cast<C*>(_component)->*method)(data); // copy 8 X
|
---|
| 86 | break;
|
---|
| 87 | }
|
---|
| 88 |
|
---|
| 89 | // from Component to Connection interface (T->G) (Typed in QByteArray)
|
---|
| 90 | case GENERIC_EVENT3: {
|
---|
| 91 | PacpusTypedEvent<T> * typedEvent = dynamic_cast<PacpusTypedEvent<T> *> (event);
|
---|
[110] | 92 | (dynamic_cast<C*>(_component)->*method)(typedEvent->data_); // copy 3 X
|
---|
[96] | 93 |
|
---|
[89] | 94 | break;
|
---|
[96] | 95 | }*/
|
---|
[89] | 96 |
|
---|
[110] | 97 | default:
|
---|
[89] | 98 |
|
---|
[96] | 99 | qDebug() << "Unknown event ID " << event->type();
|
---|
[110] | 100 | break;
|
---|
[89] | 101 | }
|
---|
[110] | 102 | event->accept();
|
---|
| 103 | }
|
---|
[89] | 104 |
|
---|
[110] | 105 | T& getData() {
|
---|
| 106 | T data;
|
---|
| 107 | // TODO ask output data;
|
---|
[89] | 108 |
|
---|
[110] | 109 | //LOG4CXX_INFO(getLogger(), "Hello, World");
|
---|
| 110 |
|
---|
| 111 | return data;
|
---|
[89] | 112 | }
|
---|
| 113 |
|
---|
| 114 | protected:
|
---|
| 115 | void (C::*method)(const T&);
|
---|
| 116 |
|
---|
[110] | 117 | /* log4cxx::LoggerPtr& getLogger() {
|
---|
| 118 | static log4cxx::LoggerPtr logger(log4cxx::Logger::getLogger( LOG4CXX_LOCATION.getClassName()));
|
---|
| 119 | return logger;
|
---|
| 120 | }*/
|
---|
| 121 |
|
---|
[89] | 122 | };
|
---|
| 123 |
|
---|
| 124 | template <class T, class C>
|
---|
| 125 | class OutputInterface : public OutputInterfaceBase
|
---|
| 126 | {
|
---|
| 127 | public:
|
---|
| 128 | OutputInterface(QString name, C * component):OutputInterfaceBase(name,component,component) {}
|
---|
| 129 | ~OutputInterface() {}
|
---|
| 130 |
|
---|
| 131 | // Used by Components to send data througth typed output
|
---|
[102] | 132 | void send(const T & data, road_time_t t = road_time(), road_timerange_t tr = 0) {
|
---|
[110] | 133 |
|
---|
| 134 | //QSharedPointer<T> sharedPointer = new T(data);
|
---|
| 135 |
|
---|
[89] | 136 | for(QList<ConnectionBase>::iterator it = _connection.begin(); it!=_connection.end(); ++it){
|
---|
[110] | 137 | QApplication::postEvent(it->getInterface(),new PacpusTypedEvent<T>(TYPED_EVENT,data,t,tr),it->getPriority()); // Event is delete by the event loop handler
|
---|
| 138 | qDebug() << "sender " << it->getInterface()->getSignature() << " thread " << QThread::currentThread() << " Data & " << &data << " ";
|
---|
| 139 | // TODO DAta SHAred
|
---|
| 140 | }
|
---|
| 141 | }
|
---|
[89] | 142 |
|
---|
[110] | 143 | /* void send(const T & data, road_time_t t = road_time(), road_timerange_t tr = 0) {
|
---|
| 144 | for(QList<ConnectionBase>::iterator it = _connection.begin(); it!=_connection.end(); ++it){
|
---|
| 145 |
|
---|
| 146 | if(it->getInterface()->getDataType() != QString(typeid(QByteArray).name()))
|
---|
[102] | 147 | QApplication::postEvent(it->getInterface(),new PacpusTypedEvent<T>(TYPED_EVENT,data,t,tr),it->getPriority());
|
---|
[110] | 148 | else {
|
---|
[89] | 149 | QByteArray buf;
|
---|
| 150 | QDataStream out(&buf,QIODevice::ReadWrite);
|
---|
[96] | 151 | PacpusTypedEvent<QByteArray> * ev =new PacpusTypedEvent<QByteArray>(GENERIC_EVENT3,buf);
|
---|
| 152 | QApplication::postEvent(it->getInterface(),ev,it->getPriority()); // Copy 2 (ctor)
|
---|
[110] | 153 | }
|
---|
[89] | 154 | }
|
---|
| 155 | }
|
---|
| 156 |
|
---|
| 157 | // Used by Connection Interfaces only to pose generic event
|
---|
[110] | 158 | void sendGenericData(char * data, size_t size) {
|
---|
[89] | 159 | QByteArray buf(data,size); // copy 5
|
---|
| 160 | for(QList<ConnectionBase>::iterator it = _connection.begin(); it!=_connection.end(); ++it)
|
---|
[96] | 161 | QApplication::postEvent(it->getInterface(),new PacpusTypedEvent<QByteArray>(GENERIC_EVENT2,buf),it->getPriority()); // Copy 6(ctor)
|
---|
| 162 |
|
---|
| 163 |
|
---|
[89] | 164 | }
|
---|
[96] | 165 | */
|
---|
[89] | 166 | size_t getDataSize() {return sizeof(T);}
|
---|
| 167 | QString getDataType() {return QString(typeid(T).name());}
|
---|
| 168 | };
|
---|
| 169 |
|
---|
| 170 |
|
---|
| 171 | } // namespace pacpus
|
---|
| 172 |
|
---|
| 173 | #endif // IN_OUT_INTERFACE_H
|
---|