2012-03-25 11 views
12

Per collegare i segnali agli slot, per quanto ne so, i parametri del segnale devono corrispondere ai parametri dello slot. Così, per esempio:segnali Collegare le slot con valori costanti

connect(dockWidget->titleBarWidget(), SIGNAL(closeButtonClicked()), ui->sideControls, SLOT(closeDockWidget())); 

Ma cosa succede se voglio avere un segnale di chiamata uno slot che ha una diversa quantità di parametri, ma sempre passare un valore costante nella fessura. Ad esempio, utilizzando il pezzo sopra di codice:

connect(dockWidget->titleBarWidget(), SIGNAL(closeButtonClicked()), ui->sideControls, SLOT(setDockWidget(false))); 

In altre parole, ogni volta che si preme il pulsante, chiama la funzione setDockWidget() con il parametro false. È possibile?

risposta

8

No, non è possibile. È consentito collegare solo slot con un numero di argomenti inferiore o uguale rispetto al segnale corrispondente. (Vedi documentation)

È necessario creare slot di proxy, che chiamerà quello desiderato.

+1

Questa risposta non è più realmente valida, come la sintassi QT5 su C++ 11 rende molto facile da usare un lambda per questo scopo. –

+1

@ André, D'altra parte, si può solo creare 'slot di proxy, che chiamerà desiderato one.' ora in atto – Lol4t0

+1

Certo, è possibile. Ma uno slot extra significa più elementi nella tua intestazione che non vuoi, esponendo a chiamate esterne (sì, anche se è possibile chiamare uno slot privato dall'esterno) e diffondendo il tuo codice su più posizioni. Potresti anche aver bisogno di variabili membro aggiuntive per contenere i valori che vuoi passare, introducendo così uno stato aggiuntivo nella tua classe. La soluzione lambda è molto più elegante che squalifica l'introduzione di uno slot proxy come soluzione IMO. –

6

In un certo senso sì, è possibile. Ma non è molto potente: basta dichiarare il setDockWidget in questo modo:

[virtual] void setDockWidget(bool state=false) ; 

e dichiarare la connessione in questo modo:

connect(emitter, SIGNAL(closeButtonClicked()), receiver, SLOT(setDockWidget())); 

setDockWidget chiamato senza argomenti prendere quelli di default.

8

È possibile utilizzare lambda con chiamata desiderata con argomento costante. Esempio:

connect(obj, &ObjType::signalName, [this]() { desiredCall(constantArgument); }); 

più su nuova sintassi Connect: https://wiki.qt.io/New_Signal_Slot_Syntax.

+0

Nel tuo caso è possibile mescolare argomenti costanti con variabili? –

+0

@AlekseyKontsevich: Se ho capito bene, vuoi passare anche una variabile dal segnale allo slot? Certo che puoi. Rendilo argomento al lambda e usa quell'argomento nella funzione invocazione. Tuttavia, ti raccomando di usare anche l'argomento di contesto con il valore 'this'. In questo modo, puoi essere sicuro che la connessione viene distrutta se l'oggetto ricevente viene distrutto. Altrimenti, potresti finire in un comportamento indefinito. –