Mindstormsforum
Dateiupload | Links | Lexikon | NXT Shop | RobotC.de | Wettbewerbe |

gelöst: Wii Nunchuk direkt an NXT koppeln

Atmel, PIC, VEX, Fischertechnik

Moderator: Moderatoren

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

gelöst: Wii Nunchuk direkt an NXT koppeln

Beitragvon tom123 » 15. Nov 2008 17:00

Die Wii Nunchuk verfügt über einen Analog-Stick(!), zwei Tasten und den 3-Achsen-Beschleunigungs-Sensor ADXL330(!). Die Kommunikation zur Wii-Remote erfolgt über I2C und ist ausreichend dokumentiert:
http://www.windmeadow.com/node/42
Auf die techn. Details (Pullups, I2C-Code etc) will ich hier nicht mehr eingehen. Ich habe diese ins engl. Forum gepostet: http://forums.nxtasy.org/index.php?showtopic=3043&st=0

Zur Erinnerung: Der LEGO Beschleunigungssensor kostet bei http://www.lego.de (Artikel-Nr.: MS1040) z.Z. 54,99EUR.

verwendete Materialien:
1x Nunchuk (15EUR)
1/2 NXT Kabel (0,75EUR)
2x Widerstände 33k (0,10EUR)
1x Diode 1N4148 (0,10EUR)

Hinweis: Im Legoshop kosten 7 ganze Kabel nur 10,29EUR. Das macht dann 14 Kabel für Lötkolben-Erweiterungen etc. Wer das hier nachbaut, sollte sich auch an weitere Sensor-Erweiterungen heranwagen. Mein Favorit sind die Sharp Entfernungssensoren GP2D12 an Greifarmen (40$ bei http://www.mindsensors.com ). Einfach genial...

Bauanleitung Nunchuk:

1. Ihr kauft Euch bei ebay eine Nunchuk (ca. 15EUR)

2. Ihr öffnet das Nunchuk-Gehäuse mit einem kleinen Schraubendreher (1,5mm).
Ein Video dazu gibt es hier: http://www.youtube.com/watch?v=V4Jc2usqBIg

3. Ihr seit jetzt hier: http://wiire.org/Wii/nunchuk

4. Ihr lötet die 1,8k Pullup-Widerstände R1 und R2 ab. Keine Angst for SMD. Einfach draufhalten - die kleinen Widerstände bleiben am Lötkölben kleben.
Bild
Bild

5. Ihr lötet neue Pullup-Widerstände ein. Die Lego-Spezifikation verlangt 82kohm. Damit läuft die Nunchuk nicht sauber durch. Ich habe 33kohm eingebaut und diese als SMD wieder an die richtige Stelle gelötet. Falls ihr keine SMD habt, nehmt normale Widerstände 33k/0,25W und baut die ins Gehäuse mit ein - direkt an die Anschlußkabel.
Ich habe zusätzlich noch eine Schutzdiode eingebaut, da der Bewegungssensor nur bis 3,6V spezifiziert ist:http://www.st.com/stonline/products/literature/ds/11668.pdf
Im Roboternetz haben aber einige die Nunchuk ohne Probleme an 5V laufen. Müsst ihr selber entscheiden.

Schaltplan: Bild
Hier ein Bild meiner eingebauten Diode: Ihr seht, das ist genügend Platz für die beiden Widerstände:
Bild

6. Jetzt noch Kabel abschneiden und verbinden:
Bild

7. Lötkolben aus und durchatmen:
Bild

8. Testprogramm hochladen. Ich habe ein NXC Programm für die enhanced firmware von John Hansen geschrieben:
http://bricxcc.sourceforge.net/
Die "Enhanced Firmware" nutze ich wg. der praktischen Hex-Ausgabe über FormatNum("%02X", outbuf[i]). Ihr könnt das Beispiel problemlos anpassen. Auch NXT-G ist möglich mit den I2C-Bausteinen.

Code: Alles auswählen

#include "NXCDefs.h"

byte CMDNunchukInit[] = {0xA4, 0x40, 0x00};
byte CMDNunchukWrite[] = {0xA4, 0x00};
byte CMDNunchukRead[] = {0xA4};

byte nbytes;
byte outbuf[];

// port is the NXT port
// i2c_cmd is the nunchuk internal address register
// at i2c_cmd=0...5 are 6 Byte of sensor values
// at i2c_cmd=0x20 ... 0x2F  you get 16 Byte of calibration data
sub NunchukGetParamter(byte port, byte i2c_cmd)
{
  // Initialize the Nunchuk
  SetSensorLowspeed(port);
  LowspeedWrite(port, 0, CMDNunchukInit); //ask for 0 bytes
  while(LowspeedStatus(port, nbytes)>0);

  // Wait(1) is needless, the NXT command interpreter delays next i2c access 3ms

  CMDNunchukWrite[1] =i2c_cmd; //at 0x00: 6 Bytes of sensor values
  LowspeedWrite(port, 0, CMDNunchukWrite);   // write Nunchuk register address
  while(LowspeedStatus(port, nbytes)>0);

  byte count = 6;
  LowspeedWrite(port, count, CMDNunchukRead); //ask for count bytes
  while(LowspeedStatus(port, nbytes)>0);
 
  if(nbytes == count){
    LowspeedRead(port, count, outbuf)  //read data from buffer
    for(int i=0; i<count; i++ ){
      outbuf[i]=(outbuf[i]^0x17) + 0x17;
    }
  }
  else {
    ArrayInit(outbuf,0,0);    //error
  }
}

task main()
{
  while (true)
  {
    NunchukGetParamter(S1, 0x00);          //see comment for i2c_cmd
    if (ArrayLen(outbuf)==6) {
       string Nunchuk="aXaYgXgYgZCZ";
       if ((outbuf[5]&0x01)!=0) {Nunchuk[11]=122;}  //Show Z-Button
       if ((outbuf[5]&0x02)!=0) {Nunchuk[10]=99;}   //Show C-Button
       ClearScreen();
       for(int i=0; i<ArrayLen(outbuf); i++ ) {
         TextOut(15*i, LCD_LINE3, SubStr(Nunchuk, 2*i, 2));
         //TextOut(15*i, LCD_LINE5, FormatNum("%02X", outbuf[i]));  //hex: enhanced firmware
         NumOut(15*i, LCD_LINE5, outbuf[i]);  //dez: lego firmware
       }
       CircleOut((outbuf[0]-0x1E)/2, (outbuf[1]-0x1E)/3, 3);    //analog stick
       RectOut((outbuf[2]-0x46), (outbuf[3]-0x46)/2, 6, 6);    //acceleration value
    }
    Wait(100);
  }
}

Diese Demo bewegt einen Kreis mit dem Analog-Stick und ein Rechteck mit den Beschleunigungssensor.
Bild

9. zum Schluß noch ein Video:
http://www.youtube.com/watch?v=HFQtyna58Kg
<object width="425" height="344"><param name="movie" value="http://www.youtube.com/v/HFQtyna58Kg&hl=de&fs=1"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="always"></param><embed src="http://www.youtube.com/v/HFQtyna58Kg&hl=de&fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"></embed></object>
Zuletzt geändert von tom123 am 2. Jun 2010 11:58, insgesamt 3-mal geändert.

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 15. Nov 2008 19:30

irre!
krass!
Wahnsinn!

Applaus, Applaus! :applaus:

wenn du es jetzt noch schaffst, den Treiber auch für RobotC zu schreiben...?

die RobotC-Befehle für I²C sind mir leider zu blöde und zu kompliziert :?
Zuletzt geändert von HaWe am 16. Nov 2008 13:03, insgesamt 1-mal geändert.
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

Beitragvon tom123 » 15. Nov 2008 21:27

Ford Prefect hat geschrieben:wenn du es jetzt noch schaffst, den Treiber auch für RobotC zu schreiben...?

Uups - ich benutze doch nur normale Funktionen der Firmware.
Die Nunchuk läuft unter jeder NXC-Sprache. Auch NXT-G!

Das klappt doch mit RobotC genauso. Du musst nur den Code geringfügig an Deine I2C-Befehle anpassen:

Code: Alles auswählen

  sendI2CMsg(port, CMDNunchukInit[0], sizeof(CMDNunchukInit));
  waitForI2CBus();
  readI2CReply(port, outbuf[0], 6);
 ... usw


Ford Prefect hat geschrieben:die RobotC-Befehle für I²C sind mir leider zu blöde und zu kompliziert :?

Moderator! Ich hoffe Du scherzt!
Du schreibst in Deinem Profil "Interessen: Mathematik, Informatik, KI"
Ich habe Dir die beiden RobotC-Befehle schon aufgeschrieben...

Übrigens ist die Dokumentation von RobotC eine Katastrophe. Warum nimmst Du nicht NXC? John Hansen macht eine gute Arbeit. NXC ist kostenlos und sehr gut dokumentiert.

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 16. Nov 2008 00:24

ok, ist jetzt
[OT]
, aber es ist DEIN Thread ;)

warum nicht NXC?
tät ich gerne!
leider hat es John Hansen bis heute nicht geschafft, Fließkomma-Artithmetik einzubauen!

DAS ist ein schwaches Bild!

Wie soll ich NN's und Navigation machen ohne fp? ;-)

Das war der einzige Grund für RobotC gewesen, ich schwörrr ! Aber Structures und fp brauch ich halt leider
Aber wenn NXC den ANSI C99 Standard erfüllt, wechsele ich sofort, keine Frage!

[/OT]
Zuletzt geändert von HaWe am 16. Nov 2008 15:12, insgesamt 5-mal geändert.
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

Benutzeravatar
Tim Sasdrich
Enorm-Viel-Schreiber
Enorm-Viel-Schreiber
Beiträge: 797
Registriert: 14. Okt 2007 12:19
Wohnort: VS
Kontaktdaten:

Beitragvon Tim Sasdrich » 16. Nov 2008 14:48

Kann man da alles abfragen?

Antwort hat geschrieben:: ja, aber wie musst du im NXT-G-Forum fragen!

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

Beitragvon tom123 » 16. Nov 2008 16:44

OK, ich helfe gerne
Anbei mein erstes RobotC Programm

Code: Alles auswählen

byte CMDNunchukInit[] = {0x03, 0xA4, 0x40, 0x00};
byte CMDNunchukWrite[] = {0x02, 0xA4, 0x00};
byte CMDNunchukRead[] = {0x01, 0xA4};

// byte nbytes;    //NXC
byte outbuf[6];
int outbuf1[6];   //ubyte workaround for RobotC

//  This function allows conversion of an unsigned byte to a signed int
//  This is a workaround for RobotC
int ubyteToInt(ubyte _byte) {
   int _ret = 0;
   _ret = (_byte & 0x80) ? (_byte & 0x7F) + 0x80 : _byte;
   return _ret;
}

// port is the NXT port, i2c_cmd is the nunchuk internal address register
// at i2c_cmd=0...5 are 6 Byte of sensor values
// at i2c_cmd=0x20 ... 0x2F  you get 16 Byte of calibration data

//sub NunchukGetParamter(byte port, byte i2c_cmd)    //NXC
sub NunchukGetParamter(tSensors port, byte i2c_cmd)  //RobotC
{
  // Initialize the Nunchuk
  //SetSensorLowspeed(port);  //NQC
   SensorType[port] = sensorI2CCustom;  //RobotC

  //LowspeedWrite(port, 0, CMDNunchukInit); //NXC ask for 0 bytes
   sendI2CMsg(port, CMDNunchukInit[0], 0); //RobotC

  //while(LowspeedStatus(port, nbytes)>0);  //NQC
  while (nI2CStatus[port] == STAT_COMM_PENDING) ; // RobotC Wait for I2C bus to be ready

  //CMDNunchukWrite[1] =i2c_cmd;   //NXC at 0x00: 6 Bytes of sensor values
  CMDNunchukWrite[2] =i2c_cmd;     //RobotC

  //LowspeedWrite(port, 0, CMDNunchukWrite);   //NXC write Nunchuk register address
   sendI2CMsg(port, CMDNunchukWrite[0], 0);     //RobotC

  //while(LowspeedStatus(port, nbytes)>0);        //NXC
  while (nI2CStatus[port] == STAT_COMM_PENDING) ; // RobotC Wait for I2C bus to be ready

  byte count = 6;
  //LowspeedWrite(port, count, CMDNunchukRead); //NXC: ask for count bytes
   sendI2CMsg(port, CMDNunchukRead[0], count);   //RobotC

  //while(LowspeedStatus(port, nbytes)>0);        //NXC
  while (nI2CStatus[port] == STAT_COMM_PENDING) ; // Wait for I2C bus to be ready

  //if(nbytes == count){                  //NXC
  if(nI2CBytesReady[port] == count){      //RobotC

    //LowspeedRead(port, count, outbuf)  //NXC read data from buffer
      readI2CReply(port, outbuf[0], 6);    //RobotC

    for(int i=0; i<count; i++ ){
       outbuf1[i]=ubyteToInt(outbuf[i]);   //ubyte workaround for RobotC
      outbuf1[i]=(outbuf1[i]^0x17) + 0x17;
    }
  }
  else {
    //ArrayInit(outbuf,0,0);    //NXC: error
     memset(outbuf, 0, 0);       //RobotC
  }
}

task main()
{
  while (true)
  {
    NunchukGetParamter(S1, 0x00);          //see comment for i2c_cmd

    //if (ArrayLen(outbuf)==6) {     //NXC
    if (sizeof(outbuf)==6)    {      //RobotC

       //string Nunchuk="aXaYgXgYgZCZ";     //NXC
       char Nunchuk[16];                    //RobotC
       strcpy(Nunchuk, "aXaYgXgYgZCZ");     //RobotC

       if ((outbuf1[5]&0x01)!=0) {Nunchuk[11]=122;}  //Show Z-Button
       if ((outbuf1[5]&0x02)!=0) {Nunchuk[10]=99;}   //Show C-Button

       // ClearScreen();  //NXC
       eraseDisplay();   //RobotC

       // for(int i=0; i<ArrayLen(outbuf); i++ ) {  //NXC
       for(int i=0; i<6; i++ ) {  //RobotC

         //TextOut(15*i, LCD_LINE3, SubStr(Nunchuk, 2*i, 2));   //NXC
         nxtDisplayStringAt(15*i,50,"%c", Nunchuk[2*i]);         //RobotC
         nxtDisplayStringAt(15*i+5,50,"%c", Nunchuk[2*i+1]);       //RobotC

         //TextOut(15*i, LCD_LINE5, FormatNum("%02X", outbuf[i]));     //NXC
         nxtDisplayStringAt(15*i,40,"%02X", outbuf1[i]);               //RobotC
       }

       // CircleOut((outbuf[0]-0x1E)/2, (outbuf[1]-0x1E)/3, 3);    //NXC analog stick
       nxtDrawCircle((outbuf1[0]-0x1E)/2, (outbuf1[1]-0x1E)/3, 3);   //RobotC

       // RectOut((outbuf[2]-0x46), (outbuf[3]-0x46)/2, 6, 6);    //NXC acceleration value
       nxtDrawCircle((outbuf1[2]-0x46), (outbuf1[3]-0x46)/2, 6);
    }
    // Wait(100);  //NXC
    wait1Msec(100);    //RobotC
  }
}

Ich habe auf meinem NXT extra für Dich die RobotC Firmware installiert :no:

Damit Du Dich in NXC einarbeiten kannst, habe ich die NXC Zeilen auskommentiert und die RobotC Zeilen darunter geschrieben.
Am längsten habe ich gebraucht, das UBYTE Problem von RobotC zu knacken. Ich habe dazu die zusätzliche Funktion ubyteToInt() eingefügt.

Anbei ein Screenshot vom RobotC-Programm:
Bild
Diese Demo bewegt einen kleinen Kreis mit dem Analog-Stick und ein großen Kreis mit den Beschleunigungssensor.

[OT]
Ich will keine Diskussion über Progammiersprachen führen. Dazu nur soviel:
- hier im Forum ist der Preis von RobotC für viele eine Hürde
- NXC ist kostenlos und für alle genauso leicht erlernbar wie RobotC
- für NXC-Einsteiger gibt es deutschsprachige Seiten

Ford Prefect hat geschrieben:leider hat es John Hansen bis heute nicht geschafft, Fließkomma-Artithmetik einzubauen!

Wir programmieren einen Microcontroller und keinen Intel Quad-Core! Man sollte immer die zur Verfügung stehenden Resourcen im Auge behalten.
Im Roboternetz haben wir bisher jede Anfrage zu Fließkomma-Arithmetik auf ein Festkomma-Arithmetik-Problem reduzieren können. Und Festkomma-Arithmetik sollte man auf µC immer mit int bzw. long machen und erst in der Display-Ausgabe das Komma setzen.

Ford Prefect hat geschrieben:Aber wenn NXC den ANSI C99 Standard erfüllt, wechsele ich sofort, keine Frage!

Klar ist NXC nicht C Standard. Na und? Ich programmiere auf Microcontrollern in jeder Sprache. Kennst Du eine, kennst Du alle.
Das hier ist mein erstes RobotC-Programm. Der Befehlssatz (bzw. die Bibliotheken) von jedem NXT Compiler sind so klein, da kommt man schnell rein. Zum besseren Vergleich habe ich auch im Quelltext NXC und RobotC nebeneinander stehen lassen.
[/OT]

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 16. Nov 2008 17:34

danke, danke, tausend Dank! :D

Das mit dem µC-Programmieren hast du mir sicher voraus - ich mag die hartwär-nahe Programmierung einfach nicht.
ich mach mehr die "Anwendungen" mit Makro-Befehlen für meine KI- und Navi-Dinger, deshalb will ich mich auch nicht mit Typumwandlungen long -> float rumschlagen.

Aber zum RobotC-Preis:

wer eine Betaversion aus dem Forum downloaded, kriegte bisher eine kostenlose 365 Tage-Lizenz.
Die Betas sind meist besser als die bisherigen Finals, nur sehr selten wird dann bis zur nächsten Final noch was wesentliches umgeschmissen.

Also nochmal danke für deine Mühe!
wenn ich wieder mal was "Größeres" fertig habe, werde ich mich dafür auch wieder mit nem Source-Posting revanchieren! :D
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 16. Nov 2008 18:50

nun noch die Gretchen-Frage:

was denkst du:
kriegt man auch einen Adapter-Stecker hin, dass man die Nunchuck wahlweise am wii u/o am nxt anschließen kann?
Ich will mir jetzt grade zum ersten mal ne wii anschaffen, da wär's zu schade, wenn dann gleich der nunchuck bei drauf geht :?
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

Beitragvon tom123 » 16. Nov 2008 20:32

für den Stecker-Adapter sehe ich mehrere Möglichkeiten:

Variante 1:
Du kannt vier dicke Drähte auch Lochraster löten und hast einen halbwegs stabilen Stecker. Ich hatte den Stecker in ein Steckbrett gesteckt:
Bild

Variante 2:
ein kommerzieller Adapter von http://store.fungizmos.com/index.php?ma ... cts_id=212
Bild

Variante 3:
Aus einem alten Floppy Adapter kann man sich aus dem Steckverbinder einer alten ISA Karte einen Nunchuk-Adapter basteln.
Bild


Ford Prefect hat geschrieben:wenn ich wieder mal was "Größeres" fertig habe, werde ich mich dafür auch wieder mit nem Source-Posting revanchieren! :D

Ein großes Wort. Zu viele sitzen auf ihrem Source Code.
In den non-commercial Foren sollten keine Fragen beantwortet werden, wenn der Fragende nicht die entsprechende Source-Sequenz offenlegt.

Ford Prefect hat geschrieben:Ich will mir jetzt grade zum ersten mal ne wii anschaffen, da wär's zu schade, wenn dann gleich der nunchuck bei drauf geht :?

Dann lass das Löten der Pullups und nimm einen I2C-Portadapter:
http://focus.ti.com/lit/ds/symlink/p82b96.pdf

alternativ die den Pegelwandler aus einer Philips Application note.
http://www.nxp.com/acrobat_download/app ... 0441_1.pdf
Rp auf der linken Seite sind schon da / Rp rechts = 82k Lego
Bild
Zuletzt geändert von tom123 am 2. Jun 2010 11:59, insgesamt 1-mal geändert.

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 16. Nov 2008 20:55

hi,
da hat wirklich ein Fachmann gesprochen. Alle Achtung! :respekt:

Vielen Dank für deine Hilfe und deine Mühe mit dem Code und den Bastel- und Kauftipps für alle mit > 1 linken Händen!

vG.!
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

Benutzeravatar
Tim Sasdrich
Enorm-Viel-Schreiber
Enorm-Viel-Schreiber
Beiträge: 797
Registriert: 14. Okt 2007 12:19
Wohnort: VS
Kontaktdaten:

Beitragvon Tim Sasdrich » 23. Nov 2008 21:26

Habe mir auch so eine Nunchuk umgebaut.
Um sie an der Wii nutzen zu können werden die 33 KOhm Widerstände im Adapterteil für die Wii (habe RJ45 Stecker als Verbindung) mit 1,9 KOhm Widerständen durch Parallelschaltung auf ca. 1,8 KOhm gebracht.

Hier mein Progamm in NXC für die Original LEGO Mindstorms NXT Firmware V1.05:

Code: Alles auswählen

#include "NXCDefs.h"

byte CMDNunchukInit[] = {0xA4, 0x40, 0x00};
byte CMDNunchukWrite[] = {0xA4, 0x00};
byte CMDNunchukRead[] = {0xA4};

byte nbytes;
byte outbuf[];

// port is the NXT port
// i2c_cmd is the nunchuk internal address register
// at i2c_cmd=0...5 are 6 Byte of sensor values
// at i2c_cmd=0x20 ... 0x2F  you get 16 Byte of calibration data
sub NunchukGetParamter(byte port, byte i2c_cmd)
{
  // Initialize the Nunchuk
  SetSensorLowspeed(port);
  LowspeedWrite(port, 0, CMDNunchukInit); //ask for 0 bytes
  while(LowspeedStatus(port, nbytes)>0);

  // Wait(1) is needless, the NXT command interpreter delays next i2c access 3ms

  CMDNunchukWrite[1] =i2c_cmd; //at 0x00: 6 Bytes of sensor values
  LowspeedWrite(port, 0, CMDNunchukWrite);   // write Nunchuk register address
  while(LowspeedStatus(port, nbytes)>0);

  byte count = 6;
  LowspeedWrite(port, count, CMDNunchukRead); //ask for count bytes
  while(LowspeedStatus(port, nbytes)>0);

  if(nbytes == count){
    LowspeedRead(port, count, outbuf)  //read data from buffer
    for(int i=0; i<count; i++ ){
      outbuf[i]=(outbuf[i]^0x17) + 0x17;
    }
  }
  else {
    ArrayInit(outbuf,0,0);    //error
  }
}

task main()
{
  SetSensorTouch(IN_2);
  SetSensorType (IN_3, IN_TYPE_LIGHT_INACTIVE);
  int a = 0;
  int b = 0;
  while (true)
  {
      NunchukGetParamter(S1, 0x00);          //see comment for i2c_cmd
      if (ArrayLen(outbuf)==6) {
       if (ButtonPressed(BTN4, true)) {ForceOff(true);}
       if (b < 1) {if ((outbuf[5]&0x02)!=2) {if (a < 1)
       {SetSensorType (IN_3, IN_TYPE_LIGHT_ACTIVE);a =2;}else
       {SetSensorType (IN_3, IN_TYPE_LIGHT_INACTIVE);a =0;};
       b = 2;}}else{if ((outbuf[5]&0x02)!=0) {b = 0;}}
       if ((outbuf[5]&0x01)!=1) {
       OnFwd (OUT_B, (((outbuf[3]-0x1E)-100)*(-2))-(outbuf[2]-0x1E)/2+56);
       OnFwd (OUT_C, (((outbuf[3]-0x1E)-100)*(-2))+(outbuf[2]-0x1E)/2-36);}else{if ((outbuf[5]&0x02)!=0){
       OnFwd (OUT_B, (((outbuf[1]-0x1E)-100)*(-1))-(outbuf[0]-0x1E)/2+46);
       OnFwd (OUT_C, (((outbuf[1]-0x1E)-100)*(-1))+(outbuf[0]-0x1E)/2-46);}else{Off(OUT_BC);}}
       ClearScreen();
       CircleOut((outbuf[0]-0x1E)/3+17, (outbuf[1]-0x1E)/3, 3);    //analog stick
       CircleOut((outbuf[2]-0x46)/2+20, (outbuf[3]-0x46)/2, 6);    //acceleration value
       if (b > 1) {if (a > 1) {OnFwd (OUT_A, (((outbuf[1]-0x1E)-100)/(-10)));}}else{Off(OUT_A);};
     }
  }
}


Anschlussbelegungen:

  • Motoren:
  • A=Höhenverstellung Lichtsensor; vorwärts = vorwärts
  • B=Motor rechts; vorwärts = rückwärts
  • C=Motor links; vorwärts = rückwärts
  • Sensoren:
  • Nunchuk = Port 1
  • Lichtsensor = Port 3


Es kann Folgendes:

  • Positionsanzeige von Analogstick und Beschleunigungssensor in Form von Kreisen auf dem Display
  • Steuern eines Fahrrobos
  • Z-Taste gedrückt: Beschleunigungssensor
  • Z-Taste nicht gedrückt: Analogstik
  • Lichtsteuerung (Lichtsensor Aktiv/Passiv)
  • C-Taste gedrückt: Licht an & Motor A = Höhenverstelung mit dem Analogstick
  • C-Taste nochmal gedrückt: Licht aus
  • Orangene NXT-Taste gedrückt = NXT ausschalten
Zuletzt geändert von Tim Sasdrich am 24. Nov 2008 17:00, insgesamt 1-mal geändert.

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

Beitragvon tom123 » 24. Nov 2008 11:45

@Tim Sasdrich
Gratulation - der erste Nachbau!

Tim Sasdrich hat geschrieben:Um sie an der Wii nutzen zu können werden die 33 KOhm Widerstände im Adapterteil für die Wii (habe RJ45 Stecker als Verbindung) mit 1,9 KOhm Widerständen durch Parallelschaltung auf ca. 1,8 KOhm gebracht.

Das verstehe ich nicht. Welches Widerstände im Adapterteil für die Wii? Schick bitte mal eine Skizze.

Benutzt Du eine Original Nintendo Nunchuk oder einen Nachbau? Ich vermute da Unterschiede im I2C-Timing...

@Ford Prefect
Schön dass Du die Seite in das RobotC Forum verlinkt hast:
http://www.robotc.net/forums/viewtopic.php?f=41&p=4372
ergänze doch mal im engl. Forum den Link zur englischsprachigen Seite:
http://forums.nxtasy.org/index.php?showtopic=3075

So und jetzt mal im Ernst:
Was soll das rumgehacke im engl. RobotC Forum zu meiner Aussage betr. NXC/RobotC? Ich habe bis heute keine PDF gefunden, die alle RobotC Befehle zum NXT in einem Dokument zusammenfasst. Alles steht irgendwo. Schlechte Dokumentation führt dann dazu, dass ein anerkannter RobotC-Experte wie Du sagt: "die RobotC-Befehle für I²C sind mir leider zu blöde und zu kompliziert".
Ich kenne die Vorteile von RobotC genau und will das nicht leugnen.
Hier im Forum programmieren viele (Schüler) mit NXT-G. Um diese zu einem Umstieg zu motivieren, halte ich ein gut dokumentiertes Open Source Programm wie NXC besser geeignet, als ein 30EUR RobotC. Die Hemmschwelle zum Umstieg liegt niedriger. Für Schüler gibt es z.B. hier eine deutschsprachige Einstiegsseite für NXC: http://www.debacher.de/wiki/NXC

Ford Prefect hat geschrieben:Aber zum RobotC-Preis:wer eine Betaversion aus dem Forum downloaded, kriegte bisher eine kostenlose 365 Tage-Lizenz.
ich habe die aktuelle Beta installiert -> 30 Tage Lizenz

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 4692
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Beitragvon HaWe » 24. Nov 2008 12:36

[OT]
rumgehacke? nicht von meiner Seite!
ich finde selber, dass RobotC viel zu schlecht dokumentiert ist (habe ich auch im englischen RobotC.net-Forum geschrieben) und der Support durch die RobotC-Entwickler hundsmiserabel ist.
ich finde, dass NXC 1000 mal besser geeignet ist - sowohl für Umsteiger als auch für erfahrenere Anwender und viele Dinge 100 mal einfacher zu programmieren sind als in RobotC.

Der einzige Nachteil : NXC hat keine Fließkomma- oder Festkomma-Arithmetik. Dies ist so ziemlich der einzige Mangel, der mich hindert, mit NXC überhaupt anzufangen.

Den Rest an Diskussion über Vor/Nachteile von Programiersprachen sollten wir in einem eigenen Thread führen und Missverständnisse eher per PM klären.

Danke aber für dein Posting.
[/OT]
Gruß,
HaWe
±·≠≈²³αβγδε∂ζλμνπξφωΔΦ≡ΠΣΨΩ∫√∀∃∈∉∧∨¬⊂⊄∩∪∅∞
NXT NXC SCHACHROBOTER: https://www.youtube.com/watch?v=Cv-yzuebC7E

Benutzeravatar
Tim Sasdrich
Enorm-Viel-Schreiber
Enorm-Viel-Schreiber
Beiträge: 797
Registriert: 14. Okt 2007 12:19
Wohnort: VS
Kontaktdaten:

Beitragvon Tim Sasdrich » 24. Nov 2008 17:59

Ich habe folgendes (um-)gebaut:

Original Nuchuk:
    Wiederstände R1 + R2 entfernt
    Kabel duchgeschnitten
    RJ45er Buchse angelötet:
      Pin 1: weiß
      Pin 2: rot
      Pin 3: gelb
      Pin 4: grün
      rest: frei
    zwischen Pin 2 und 3 und zwischen Pin 2 und 4 33 KOhm-Widerstände eingelötet.
Adapter für NXT:
    NXT-Kabel durchgeschnitten
    RJ45er Stecker drangekrimpt:
      Pin 1: rot
      Pin 2: grün
      Pin 3: gelb
      Pin 4: blau
      rest: frei
Adaper für Wii:
    Rest des Kabels der Nunchuk mit dem Stecker genommen
    RJ45er Kabel Durchgeschnitten und angelötet:
      Pin 1: weiß
      Pin 2: rot
      Pin 3: gelb
      Pin 4: grün
      rest: frei

    1,9 KOhm-Widerstände zwischen Pin 2 und 3 und Pin 2 und 4 gelötet


PS: Ich habe es ohne Schutzdiode gemacht.

Ich kann diesen "Sensor" nur empfehlen, da man max. 25€ zahlen muss und einen Beschleunigungssensor, einen Analogstick und zwei Tasten hat, die man an einen Sensorport anschließen kann.

tom123
Schreibt ab und zu
Schreibt ab und zu
Beiträge: 38
Registriert: 28. Mär 2008 15:08

Beitragvon tom123 » 24. Nov 2008 21:44

Danke, jetzt habe ich es verstanden. Ich dachte schon, Du hättest einen neuen Weg gefunden, das Auslöten der Nunchuk-Widerstände zu vermeiden.

Im engl. Forum habe ich eine Idee für einen bidirektionalen Level-Shifter gepostet, um das Auslöten zu vermeiden:
http://forums.nxtasy.org/index.php?showtopic=3075
Bild
Leider kann ich das nicht testen, da meine Kabel alle wieder verklebt sind und ich sie nicht mehr aufreißen möchte.
Prinzip: Die komplimentären Darlington Transistoren verstärken den schwachen LOW-Pegel des NXT zweimal invertiert. Zieht der Nunchuk auf LOW geht die Spannungsversorgung der beiden Transistoren auf Null und damit auch der LOW-Pegel auf der NXT Seite.
Zuletzt geändert von tom123 am 2. Jun 2010 12:04, insgesamt 1-mal geändert.


Zurück zu „allgemeine / Nicht-Lego-Robotik und Elektronik“

Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 1 Gast

Lego Mindstorms EV3, NXT und RCX Forum : Haftungsauschluss
cron