[gelöst]Slots mit Übergabeparameter

Alles zum Qt Framework für Java
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

[gelöst]Slots mit Übergabeparameter

Beitrag von Tobi1988 »

Hallo zusammen,

ich hoffe, dass mir jemand bei meinem Problem weiterhelfen kann :)

Ich kann bei einem Slot keine Übergabeparameter machen. Also bspw. so:

Code: Alles auswählen

TabellenButtonRow.get(i).clicked.connect(this,"bearbeiten(i)");
Fehlermeldung:

Could not find slot with signature: bearbeiten(i)
Possible matching methods:
bearbeiten(int)

Wenn ich den Slot ohne Übergabeparameter mache und dann natürlich die Slot-Methode ohne Übergabeparameter anpasse, dann funktioniert das.

MfG
Tobi
Zuletzt geändert von Tobi1988 am 8. Juli 2008 12:22, insgesamt 1-mal geändert.
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

Ich nehme an, TabellenButtonRow.get(i) liefert eine QPushButton Instanz. Dann meinst du mit clicked das vererbte Signal1 von QAbstractButton. Dieses versedet ein boolean. Du must dann
TabellenButtonRow.get(i).clicked.connect(this,"bearbeiten(boolean)");
machen und eine Methhode
... bearbeiten(boolean b) {
}
implementieren, in der gleichen Klasse, wo du das connecten tust, da du "this" angibst
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

Beitrag von Tobi1988 »

Hi,

TableButtonRow ist eine "LinkedList", welche "QPushButton" enthält. Um jetzt die Buttons einzeln anzusprechen, muss ich sie aus der Liste nehmen also:

TabellenButtonRow.get(i)

Um nun herauszufinden, welcher Button gedrückt wurde, brauche ich nun den Übergabeparameter.

MfG
Tobi
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

ich hab oben noch editiert bevor du gepostet hast ;)

aber mal ne Gegenfrage: ich bin auch grat am programmieren und hab grat das problem, dass ich ziemlich viele Instanzen in einem Array ein und derselben Klasse habe. Jetzt wollt ich denen Leben einverleiben und dachte, ich connecte die mal alle mit ein und der selben Methode und mach nicht extra für jedes eine auf. Weil je nachdem an welcher position die objekte im array sind, will ich so gut wie bis auf ein paar zeilen für alle immer das gleiche ausführen, und dann wärs halt blöd zig slots dafür zu machen.
Um aber die paar Zeilen an Ausführung zu unterscheiden müsste ich ja sozusagen wissen, wer den slot von den ganzen Objekten aus dem Array überhaupt aufgerufen hat. Gibts da irgendwas um das rauszufinden? Mit dem Listener Konzept aus Java wärs kein Problem ;) Aber hier bekomme ich ja nur den wert des Signals übergeben (ist ein "int"). und keine ahnung wer's jetzt war ...
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Beitrag von Christian81 »

Ich glaube ihr sucht QSignalMapper oder QObject::sender()
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

Beitrag von Tobi1988 »

Danke erstmal für deine ausführliche Antwort.

Nun zu deiner Frage:

Ich habe genau das selbe Problem. Deshalb wollte ich halt einen Wert übergeben, damit ich weiß von welchem Button das Signal kommt.

Wenn du eine Möglichkeit gefunden hast, dann her damit :-)

Ich werde dich auch auf den laufenden halten.
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

ah stimmt, du willst ja, das gleiche, hab den letzten satz wohl überflogen.

also übergeben kannst dus so ja nicht. du musst schon das übergeben, wozu das signal geschaffen ist und somit brauchst du auch genau die methode die den typ des signals hat.

ne möglichkeit wäre das signal an ein andres signal weiterzuleiten, das den aufrufer als objekt mitschickt. ist mir grat eingefallen :lol:

oder es geht vielleicht irgendwie einfacher mit irgend ner static QApplication oder irgend ner static Klassenmethode die einem sagt wer der aufrufer ist. das wüsst ich dann auch gern obs auch so geht.

ich versuch jedenfalls mal mein vorschlag mit dem neuen signal umzusetzen ...

EDIT: Argh hab gar nicht den Post von Christian81 gesehen. Dem werd ich mal nachgehen. Das sieht gut aus :) Thx.
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

QObject::sender() gibts zwar net, oder ich bin blind,
aber QSignalEmitter hat ne static signalSender() Methode. Tada. Und es funzt. einfach den dann mit .equals(...) vergleichen. Man kann ihn auch zurückcasten und sonstwas damit machen. Wert auslesen. keine ahnung.

Aber dieser Ansatz mit dem QSignalMapper hab ich grat versucht zu implementieren. Haut erstens nicht hin. Der Slot wird bei mir nie aufgerufen. Und zum andren blick allein das bsp. in der API nicht. wieso bekomm ich dann ein String? ist des einfach ein Mapper, der das signal z.B. int in String ummappt? dann ist das doch gar nicht das was wir suchen???? Des müsst mir echt mal einer erklären...
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Beitrag von Christian81 »

Schonmal die Foren-Suche bemüht??
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

jetzt ja, trotzdem nirgendswo eine anleitung für QSignalMapper gefunden, vielleicht hast du ja für mich einen link

EDIT: oder ein ausführbarer demo jambi code wär auch gut.
EDIT2: ah, ich hab jetzt rumprobiert. ich bekomm jetzt die id übertragen. habs jetzt so wie unten gemacht.
... kann man dann auch gleich den eigentlichen value des Objektes mitübertragen, der ja ursprünglich durch das Signal versendet wird? Ist auch nicht schlimm, wenn nicht, dann muss man ihn sich einfach aus dem array nur 1 mal holen. man weiß ja wo aus dem array wegen der id.

Code: Alles auswählen

{
...
spinBoxArray = new QSpinBox[7];
for(int i=0; i<=6; i++) {
        	spinBoxArray[i] = new QSpinBox();
        	spinBoxArray[i].setRange(0, 9);
        	spinBoxArray[i].setValue(0);
        	signalMapper.mappedInteger.connect(this, "spinBoxValueChanged(int)");
        	spinBoxArray[i].valueChanged.connect(signalMapper, "map()");
        	signalMapper.setMapping(spinBoxArray[i], i);
...
}
}
public void spinBoxValueChanged(int i) { ... }
EDIT4: hab edit3 gelöscht und was an edit2 korrigiert :wink:
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

Beitrag von Tobi1988 »

Hi nochmal,

hab gestern nichts mehr gemacht, da ich dann endlich auch mal frei hatte :D
deshalb habe ich nicht mehr gepostet.

Danke für deine Lösung Forest. Damit hast du mir sehr weitergeholen. Nun bekomme ich jedoch das Signal so oft geschickt, wie es Buttons gibt, wegen der Schleife. Das werde ich jedoch jetzt noch hinbekommen :wink:

Zu deiner Frage bei EDIT 2:

Ich denke nicht, dass du die Änderung direkt schicken kannst. Aber wie du schon selbst gesagt hast, bekommst du ja die ID übergeben, von welchem Widget das Signal kommt und somit kannste dir ja die Änderung darausholen. Also so, wie du schon selbst gesagt hast. Ich würde es auch so machen.

Danke nochmal :)

MfG
Tobi
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

Beitrag von Tobi1988 »

Hi nochmal,

ich hatte ja erwähnt, dass ich das Signal so oft geschickt bekomme, wie es Schleifendurchläufe gibt. Hast du nicht auch das Problem, Forest? Also bei dir merkst du das dann evetuell nicht, jenachdem, was dann die Methode macht, die du dann aufrufst, aber bei mir soll sich dann ein neue Fenster öffnen und dann fällt das schon auf, wenn sich statt einem Fenster 17 Fenster öffnen :D

Ich habe zwar eine Lösung gefunden aber die ist ziemlich blöde. Ich habe einfach einen Zähler in der Methode gemacht, die aufgerufen wird, wenn das Signal gesendet wurde. Wenn nun die Methode das letzte mal aufgerufen wird, so werden erst die Sachen ausgeführt (das Fenster geöffnet)

Code: Alles auswählen

public void bearbeiten(int i) {
			zaehler++;
			if(TabellenFelderRow.size()==zaehler) {
				key = prikey();
				mysql.bearbeiten(TabellenFelderRow.get(i),key);
				bearbeitenFenster = new Bearbeiten();
				bearbeitenFenster.show();
				System.out.println("ausgewählt: " + i);
				zaehler=0;
			}
		}
MfG
Tobi
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

verstehe nicht wieso du das so oft bekommst...
die schleife soll doch im konstruktor sein. und da musst du das alte .connect direkt an die methode wegmachen.
ich hab einfach ein system.out.println in der methode zu testzwecken rein gemacht. ich bekomme immer nur z.B. bei meinen spinBoxen den Platz im spinboxarray wo der User gerade eine Änderung veranlasst hat geschickt. So wie ich es ja auch wollte. Also verstehe dann nicht ganz was bei dir schief läuft.
du musst mal genauer erklären was du machst oder willst, oder mehr code (vor allem dann vom konstruktor wahrscheinlich) posten ...

versteh auch nicht genau was deine absichten sind ... willst du auch sowas wie ich?
zig QPushButtons an eine Methode connecten und dann in der methode abfragen welcher gedrückt wurde???

Edit: wobei bei letzterem du dann nicht noch abfragen solltest ob clicked true ist, da er ja bereits losgelassen worden sein könnte. Du weißt ja dann, dass er aufjedenfall geklickt worden ist, da die Methode aufgerufen wurde, schaust an der id welcher button es ist, und tust was du musst. Versteh eh nicht ganz wieso clicked ein Signal1 ist ... Hätten die ja auch als Signal0 machen können. Oder du kannst auch das Signal0 pressed Signal verwenden.

Edit2: Im falle des pressed signal müsste man ja noch die id irgendwie hinzufügen. Hmm, also den QSignalMapper hab ich noch nicht ganz intus ...
Tobi1988
Beiträge: 28
Registriert: 13. Juni 2008 09:14

Beitrag von Tobi1988 »

hi

also bei mir läuft das nicht im Konstruktor, da ich die Buttons erst später einfüge. Also im Prinzip mache ich das, was du machst. Ich füge ein bestimmte Zahl an Buttons ein und dann will ich wissen, welcher gedrückt wurde. Naja dann lasse ich es vorerst so.

Habe mal die Schleife in den Konstruktor gemacht, aber da passiert dann gar nichts, wenn ich einen Button klicke. Habe den Überblick etwas verloren bei über 800Zeilen code. Ich gucke später nochmal, wie ich das hinbekomme. Aber danke erstmal für die Hilfe.

MfG
Tobi
Forest
Beiträge: 26
Registriert: 22. Juni 2008 03:10

Beitrag von Forest »

ja, gut, auch wenn du die buttons von mir aus irgendwann während der laufzeit aus einer methode erzeugst und sie mit der QSignalMapper Instanz connectest, dann sollte es trotzdem funktionieren. kann dir auch nicht sagen wo der Fehler ist. Müsstest dann irgendwie aus den 800 zeilen die nötigen 40 zeilen rausziehen und mir posten.
oder schnell ein kleine test klasse erstellen, die einfach nur das implementiert wo der hacken ist, also ohne funktion etc. das geht bestimmt in paar dutzend zeilen ...
Antworten