Sto facendo bene?Utilizzo di una DLL basata su Qt in un'applicazione non-Qt
Un mio cliente ha un gruppo in cui sto sviluppando roba client-server basata su Qt con un sacco di cose e prese di widget divertenti.
Un altro gruppo all'interno dell'azienda desidera utilizzare una versione compressa delle classi del fornitore di dati client basate su QTcpSocket. (Che in pratica suona come funziona, fornisce i dati dal server ai display client)
Tuttavia, quel gruppo ha un'enorme applicazione costruita principalmente con MFC e che semplicemente non cambierà molto presto. La DLL basata su Qt è anche in fase di caricamento in ritardo in modo che possa essere distribuita senza questa funzionalità in determinate configurazioni.
Ho funzionato, ma è un po 'hacky. Ecco la mia soluzione al momento:
Il costruttore della classe wrapper DLL chiama QCoreApplication :: instance() per vedere se è NULL o no. Se è NULL, si presuppone che sia in un'applicazione non di Qt, e crea un'istanza QCoreApplication di essa la propria:
if (QCoreApplication::instance() == NULL)
{
int argc = 1;
char* argv[] = { "dummy.exe", NULL };
d->_app = new QCoreApplication(argc, argv); // safe?
}
else
d->_app = NULL;
E poi istituirà un timer finestre di chiamare di tanto in tanto processEvents():
if (eventTimerInterval > 0)
{
// STATE: start a timer to occasionally process the Qt events in the event queue
SetTimer(NULL, (UINT_PTR)this, eventTimerInterval, CDatabaseLayer_TimerCallback);
}
Il callback chiama semplicemente la funzione processEvents() utilizzando il timerID come puntatore all'istanza della classe. I documenti SetTimer() dicono che quando HWND è NULL ignora il timerID, quindi questo sembra essere perfettamente valido.
VOID CALLBACK BLAHBLAH_TimerCallback(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
((BLAHBLAH*)idEvent)->processEvents(); // basically just calls d->_app->processEvents();
}
Quindi ho eliminato l'istanza QCoreApplication come l'ultima cosa nel distruttore.
BLAHBLAH::~BLAHBLAH()
{
.. other stuff
QCoreApplication* app = d->_app;
d->_app = NULL;
delete d;
if (app != NULL)
delete app;
}
Se l'applicazione di hosting vuole per tempo le chiamate a processEvents() in sé, può passare 0 a eventTimerInterval e chiamare blahblah :: processEvents() stesso.
Qualche idea su questo? Portare l'app su Qt non è un'opzione. Non è nostro.
Sembra funzionare, ma ci sono probabilmente diverse supposizioni in corso. Posso semplicemente costruire una QCoreApplication con argomenti fittizi del genere? La coda degli eventi è sicura per operare in questo modo?
Non voglio che questo mi esploda in faccia dopo. Pensieri?
sto ricorrere a fare questo io stesso. Qt 3 apparentemente aveva il supporto per la creazione di plugin dlls - ad es. plugin di tipo npapi per browser Chrome e browser basati su Mozilla. Ma sembra che sia stato lasciato cadere da Qt 4. –
Grazie per aver fatto la domanda! sai se questo è l'approccio migliore ora in 4.8, o c'è un modo migliore. In realtà eseguo un QThread separato e creo ed eseguo QCoreApplication lì (globale argc e argv). QThread non ha bisogno di QCoreApplication, solo alcuni messaggi a livello di sistema come il timer hanno bisogno del dispatcher. – dashesy